|
楼主 |
发表于 2020-4-29 07:21:00
|
显示全部楼层
本帖最后由 liudingding 于 2020-4-29 07:23 编辑
我看了一下,单片机接收键盘发来的数据是正确的,单片机向键盘发送复位数据再发送翻转指示灯数据,不确定发送那个数据后指示灯闪一下,应该是向键盘发送数据的程序有问题,这个程序是我用51的程序改的,附上程序请兄弟们看一下,程序上半段是我修改后的AVR程序,下半段是原先的51程序
#define PS2DATA PINE&0x10 // PS2数据 E4,
#define PS2CLK PINE&0x20 // PS2时钟 E5,
#define SPD PORTE|=0x10 // PS2
#define CPD PORTE&=~0x10 // PS2
#define SPK PORTE|=0x20 // PS2
#define CPK PORTE&=~0x20 // PS2
void ps2_sentchar(unsigned char sentchar) // 单片机向ps2键盘发送数据
{
unsigned char sentbit_cnt; // 数据
unsigned char sentchar_chk = 0x00; // 校验
unsigned char i;
CLI(); //关外部中断1
EICRB&=~0x08; //extended ext ints
DDRE|=0x30; //发起一个传送,发起始位
CPK; //将时钟线拉低并保持100 us
delayus(100);
CPD; //起始位
delayus(8);
DDRE&=~0x20; //发送DATA0-7
SPK;
for(sentbit_cnt=0;sentbit_cnt< 8;sentbit_cnt++)
{
while(PS2CLK); // 等待时钟线变为低
if( sentchar& 0x01)
{
SPD; // 发送数据
sentchar_chk++; // 计算校验
}
else
CPD;
while(!PS2CLK) ; // 等待时钟线变高
sentchar>>=1; // 待发送数据右移一位
}
//发送校验位
while(PS2CLK); //等待时钟线变低
switch(sentchar_chk)
{
case 0:
case 2:
case 4:
case 6: SPD;break;//奇校验
case 1:
case 3:
case 5:
case 7: CPD;break;//奇校验
default:break;
}
while(!PS2CLK); // 等待时钟线变高
while(PS2CLK); // 等待时钟线变低
SPD; // 发送停止位,停止位总为1
DDRE&=~0x10;
// while(!PS2CLK) ; // 等待时钟线变高
// while(PS2CLK) ; // 等待时钟线变低
//接收ACK
// if(PS2_SGN_DATA) error();
//ACK信号由键盘发出,总为低电平
// while(!PS2CLK) ; // 等待时钟线变高
delayms(1);
EICRB|= 0x08; //extended ext ints
SEI(); //开外部中断1
}
/* 我参考的原先的51程序
void ps2_sentchar(unsigned char sentchar) // 单片机向ps2键盘发送数据
{
unsigned char sentbit_cnt= 0x00; // 数据
unsigned char sentchar_chk = 0x00; // 校验
unsigned char i;
CLI();//EX1=0; //关外部中断1
//发起一个传送,发起始位
PS2CLK = 0; //将时钟线拉低并保持100 us
i=60;while(--i);
PS2DATA= 0; //起始位
i=5;while(--i);
PS2CLK = 1;
//发送DATA0-7
for(sentbit_cnt=0;sentbit_cnt< 8;sentbit_cnt++)
{
while(PS2CLK); // 等待时钟线变为低
PS2DATA = sentchar& 0x01; // 发送数据
if(PS2DATA) sentchar_chk++; // 计算校验
while(!PS2CLK) ; // 等待时钟线变高
sentchar>>=1; // 待发送数据右移一位
}
//发送校验位
while(PS2CLK); //等待时钟线变低
switch(sentchar_chk)
{
case 0:
case 2:
case 4:
case 6: PS2DATA =1;break;//奇校验
case 1:
case 3:
case 5:
case 7: PS2DATA = 0;break;//奇校验
default:break;
}
while(!PS2CLK); // 等待时钟线变高
while(PS2CLK); // 等待时钟线变低
PS2DATA =1; // 发送停止位,停止位总为1
//while(!PS2CLK) ; // 等待时钟线变高
//while(PS2CLK) ; // 等待时钟线变低
//接收ACK
//if(PS2_SGN_DATA) error();
//ACK信号由键盘发出,总为低电平
//while(!PS2CLK) ; // 等待时钟线变高
SEI(); //开外部中断1
}
*/
|
|