⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ps2通信协议源代码.c

📁 51单片机和PC键盘的接口通信协议源代码
💻 C
字号:
#include<reg51.h>
#include<intrins.h>

#define F_ST1 0x6e            //帧头标志                  n 
#define F_ST2 0x79            //帧头标志                  y 
//命令帧格式
#define F_M 0x4d              //帧类型 命令帧
#define F_V 0x56              //帧类型 恒速运动           v 
#define F_P 0x50              //帧类型 点位运动           p 
#define F_S 0x53              //帧类型 停止运动           s 
#define F_R 0x52              //帧类型 读状态信息指令     r
#define F_W 0x57              //帧类型 修改状态信息指令   w
#define F_D 0x44              //帧类型 回传数据           d 
#define F_B 0x62              //帧类型 写回应帧           b
#define F_C 0x63              //帧类型 重发命令帧         c 
#define F_Q 0x71              //帧类型 放弃帧             q 
#define F_HOME 0x48           //已到达中心点,请重新输入操作指令     H
#define F_LIMITUP 0x4c        //已到达极限点,请重新输入操作指令    L
#define F_LIMITDOWN 0x49        //已到达极限点,请重新输入操作指令  I
//其他用途帧格式
#define F_ADDR 0x31           //器件地址                   1 
#define F_END 0x7a            //帧尾标志                   z 
#define F_SPACE 0x30          //空标志                     0 
#define F_ERR1 0x34           //错误标志1,结束标志错误     4 
#define F_ERR2 0x32           //错误标志2 校验和错误       2 
#define F_ERR3 0x33           //错误标志3 缓存区已满       3
#define F_ERR4 0x35           //错误标志4 命令参数超出范围 5 
#define F_ERR5 0x36           //错误标志5 过流保护发生     6
#define F_ERR6 0x37           //错误标志6 命令暂时无法执行     7


sbit Key_Data=P3^4;
sbit Key_Clk=P3^3;

void Delay(unsigned char ms);
void Decode(unsigned Scancode);
void go(void);
void process(void);
void com_initialization(void);
void send(unsigned char  ch); 

unsigned char code Scancodechange[23][3]={
0x45,0x3F,0,//0-9
0x16,0x06,1,
0x1E,0x5B,2,
0x26,0x4F,3,
0x25,0x66,4,
0x2E,0x6D,5,
0x36,0x7D,6,
0x3D,0x07,7,
0x3E,0x7F,8,
0x46,0x6F,9,
0x32,0x7C,'b',
0x21,0x39,'c',
0x23,0x5E,'d',
0x24,0x79,'e',
0x2B,0x71,'f',
0x34,0x6F,'g',
0x33,0x74,'h',
0x4B,0x38,'l',
0x44,0x45,'o',
0x4D,0x73,'p',
0x1B,0x6D,'s',
0x35,0x6E,'y',
0x3C,0x3E,'u',
};//0~9,b,c,d,e,f,g,h,l,o,p,s,u,y的扫描码到0~9,b,c,d,E,F,g,h,L,o,p,s,U,y的段码的转换(共阴)


#define max 20

static unsigned char IntNum=0;    //键盘输入需要定义的变量
static unsigned char KeyV;
static unsigned char DisNum=0;     //led位置指针
static unsigned char Key_UP=0;
static unsigned char BF=0;

static data unsigned char key_data[max]; //键盘输入缓冲区变量 
unsigned char key_in=0;
unsigned char key_out=0;
unsigned char key_count=0;       //键盘缓冲区计数器

unsigned char tempbuf[10];     //字符处理变量
unsigned char p;               //字符数


unsigned char LedNumber=4;   //数码管的位数
unsigned char dis_buf[4];  //数码管显示值缓冲
unsigned char dis_digit=0x88;   //数码管选通信号
unsigned char dis_index;    //显示索引变量

unsigned char k=0;
/*
static unsigned char flag=0; //发送接受状态标志位
static unsigned char led_status;//led_status其bit0-scroll lock led关0、开1;bit1-num lock led关为0,开为1;bit2-caps lock led关为0,开为1;bit3~bit7总是0;
*/
unsigned char a[]={0x4d,0x4d,0x16,0x16,0x45,0x45,0x5a,0x5a};

void main(void)
{
	 unsigned char s;
    P0=0x00;
    P2=0x00;
	 dis_digit=0x88;
	 dis_index=0;
	 Delay(100);
	 IT1=0;
	 EA=1;
	 EX1=1;
	 com_initialization();
	 do 
	    {  
	        if(BF)
	              Decode(KeyV);
	        else
	              EA=1;
			  while(LedNumber--)
			  {
			     P0=dis_buf[dis_index++];
				  P2=dis_digit;
				  Delay(5);
				  dis_digit=_cror_(dis_digit,1);
                  if(dis_index==4)
				  dis_index=0;
			  }
			  LedNumber=4; 
		      KeyV=a[s];
				s++;
				BF=1;
	     }while(1);

 }

void Delay(unsigned char ms)             // 延时子程序(晶振12M)
{                        
    unsigned char i;
    while(ms--)
    {
        for(i=0;i<120;i++);
    }
}


void Keyboard_out(void) interrupt 2
{
	 if((IntNum>0)&&(IntNum<9))
	 {
	    KeyV=KeyV>>1;
	    if(Key_Data) KeyV=KeyV|0x80;
	 }
	 IntNum++;
	 while(!Key_Clk);
	
	 if(IntNum>10)
	 {
	    IntNum=0;
	    BF=1;
	 }
}
		
		
void Decode(unsigned Scancode)
{
   unsigned char TempC;
   if(!Key_UP)
    {
        char i;
	    switch(Scancode)
	    {
			 case 0xF0:   //收到断码标志
	          Key_UP=1;
				 break;
			 case 0x5a:    //enter
			    go();
				 break;
			 case 0x55:    //清楚
			    for(i=0;i<=3;i++)
				 {
				     dis_buf[i]=0;
				 }
				 break;
	        default:
	              for(TempC=0;(Scancodechange[TempC][0]!=Scancode)&&(TempC<23);TempC++);
	              if((Scancodechange[TempC][0]==Scancode)&&(k%2==0))
	                {
						    for(i=2;i>=0;i--)   
							 {
							     dis_buf[i+1]=dis_buf[i];
							 }
						     dis_buf[0]=Scancodechange[TempC][1];
                      if(key_count<=max)
							 {
							     key_data[key_in++]=Scancodechange[TempC][2];
								  key_count++;
								  if(key_in==max)
								  key_in=0;
							 }
	                }
                 k++;
			  break;
			}
    }
    else Key_UP=0;
    BF=0;	 
}


void go(void)    //执行指令
{
	 unsigned char j=0;
    if(key_count==0)
	 ;
	 else
	 {
	    p=key_count;
	    while(key_count--!=0) 
	    tempbuf[j++]=key_data[key_out++];
       process();
	 }
}

void process(void)
{
    unsigned int  sum=0;
	 unsigned char  sum1=0;
     switch(tempbuf[0])
	 {
	    case 'p':
		     switch(p-1)
			  {
			      case 4:
					  sum+=tempbuf[1]*1000;
					  sum+=tempbuf[2]*100;
					  sum+=tempbuf[3]*10;
					  sum+=tempbuf[4];
					  break; 
					case 3:
					  sum+=tempbuf[1]*100;
					  sum+=tempbuf[2]*10;
					  sum+=tempbuf[3];
					  break; 
					case 2:
					  sum+=tempbuf[1]*10;
					  sum+=tempbuf[2];
					  break; 
			  }
			  send(F_ST1);
			  send(F_ST2);
			  send(F_M);
              send(F_ADDR);
			  send(F_P);
              send(sum/256);
			  send(sum%256);
			  send(0);
			  send(0);
			  send(0);
			  sum1=0x4d+sum/256+sum%256;
			  send(sum1);
			  send(F_END);        //发送数据帧完毕
			  break;
		 case 'l':
		     switch(p-1)
			  {
			      case 4:
					  sum+=tempbuf[1]*1000;
					  sum+=tempbuf[2]*100;
					  sum+=tempbuf[3]*10;
					  sum+=tempbuf[4];
					  break; 
					case 3:
					  sum+=tempbuf[1]*100;
					  sum+=tempbuf[2]*10;
					  sum+=tempbuf[3];
					  break; 
					case 2:
					  sum+=tempbuf[1]*10;
					  sum+=tempbuf[2];
					  break; 
			  }
			  send(F_ST1);
			  send(F_ST2);
			  send(F_M);
           send(F_ADDR);
			  send(F_V);
           send(sum/256);
			  send(sum%256);
			  send(0);
			  send(0);
			  send(0);
			  sum1=0x4d+sum/256+sum%256;
			  send(sum1);
			  send(F_END);        //发送数据帧完毕
		     break;
		  case 'h':
		      send(F_ST1);
			  send(F_ST2);
			  send(F_S);
              send(F_ADDR);
			  send(0X20);
			  send(0X20);
              send(F_END);
	 }

}

///////////////////////////////////////////////////////////////////// 
//函 数 名:send() 
//功能描述:向串口发送一个字符 
//函数说明: 
//调用函数: 
//全局变量: 
//输    入:ch-要发送的16进制字符 
//返    回:无 
//设 计 者: 
//修 改 者: 
//版    本: 
///////////////////////////////////////////////////////////////////// 
void send(unsigned char  ch) 
{
    SBUF=ch;
    while(TI==0);
    TI=0;
} 

///////////////////////////////////////////////////////////////////// 
//函 数 名:com_int() 
//功能描述:初始化串口 
//函数说明:默认其他参数为[baud_rate],n,8,1 
//调用函数: 
//全局变量: 
//输    入:baud_rate 波特率 
//返    回:无 
//设 计 者:
//修 改 者: 
//版    本: 
///////////////////////////////////////////////////////////////////// 
void com_initialization(void)
{ 
    EA=0;   
    SCON = 0x50;    /* 0x52;//SCON */ 
    TMOD = 0x21;    /*0x20;// TMOD */  
    PCON=0X00; 
	 RI=0;
	 TI=0;
    TL1=0xfa;
    TH1=0Xfa;
	 TR1=1;
	 ES=1;
    EA=1;
}  

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -