单片机驱动标准pc机键盘的C51程序
网上流行的这个程充很垃圾,
在我的单片机上无论如何都调试不成功.
正确的程序见http://home.hn8868.com/tary/download.html
该程序由AVR程序移植过来...
C语言写的,风格棒极了.
在P1口显示ASCII吗,也有使用LCD1602显示的,需要的请连系我.
以下是主要的代码KB.C
#include <Atmel\AT89X52.h> #include "Pindefs.h" #include "kb.h" #include "gpr.h" #include "Disp1602.h" #include "Scancodes.h"
#define BUFF_SIZE 32
unsigned char edge, bitcount; // 0 = neg. 1 = pos. unsigned char kb_buffer[BUFF_SIZE]; unsigned char *inpt, *outpt; unsigned char buffcnt;
void init_kb(void) { inpt = kb_buffer; // Initialize buffer outpt = kb_buffer; buffcnt = 0;
// INT0 interrupt on falling edge
edge = 0; // 0 = falling edge 1 = rising edge bitcount = 11; }
void INT0_interrupt(void) interrupt 0 using 2 { static unsigned char cdata; // Holds the received scan code
EA = 0;
if (!edge) // Routine entered at falling edge { if(bitcount < 11 && bitcount > 2) // Bit 3 to 10 is data. Parity bit, { // start and stop bits are ignored. cdata = (cdata >> 1); if(PIND) cdata = cdata | 0x80; // Store a '1' }
/*MCUCR = 3; */ // Set interrupt on rising edge edge = 1;
} if (edge) { // Routine entered at rising edge /*MCUCR = 2; */ // Set interrupt on falling edge edge = 0;
if(--bitcount == 0) // All bits received { decode(cdata); bitcount = 11; } } EA = 1; }
void decode(unsigned char sc) { //extern void clr(void); static unsigned char is_up = 0, shift = 0, mode = 0; unsigned char i;
if (!is_up) // Last data received was the up-key identifier { switch (sc) { case 0xF0 : // The up-key identifier is_up = 1; break; case 0x12 : // Left SHIFT shift = 1; break; case 0x59 : // Right SHIFT shift = 1; break; case 0x05 : // F1 if(mode == 0) mode = 1; // Enter scan code mode if(mode == 2) mode = 3; // Leave scan code mode break; default: if(mode == 0 || mode == 3) // If ASCII mode { if(!shift) // If shift not pressed, { // do a table look-up for(i = 0; unshifted[0]!=sc && unshifted[0]; i++); if (unshifted[0] == sc) { put_kbbuff(unshifted[1]); } } else { // If shift pressed for(i = 0; shifted[0]!=sc && shifted[0]; i++); if (shifted[0] == sc) { put_kbbuff(shifted[1]); } } } else{ // Scan code mode print_hexbyte(sc); // Print scan code put_kbbuff(' '); put_kbbuff(' '); } break; } } else { is_up = 0; // Two 0xF0 in a row not allowed switch (sc) { case 0x12 : // Left SHIFT shift = 0; break; case 0x59 : // Right SHIFT shift = 0; break; case 0x05 : // F1 if(mode == 1) mode = 2; if(mode == 3) mode = 0; break; case 0x06 : // F2 clr(); break; } } }
void put_kbbuff(unsigned char c) { if (buffcnt < BUFF_SIZE) // If buffer not full { *inpt = c; // Put character into buffer inpt++; // Increment pointer
buffcnt++;
if (inpt >= kb_buffer + BUFF_SIZE) // Pointer wrapping inpt = kb_buffer; } }
int getchar(void) { int byte;
while(buffcnt == 0); // Wait for data byte = *outpt; // Get byte
outpt++; // Increment pointer if (outpt >= kb_buffer + BUFF_SIZE) // Pointer wrapping outpt = kb_buffer;
buffcnt--; // Decrement buffer count return byte; }
相关链接:http://home.hn8868.com/tary/download.html |