a500kbd

view src/ps2kbd.c @ 2:a4fd9c5a6655

first working version
author John Tsiombikas <nuclear@member.fsf.org>
date Tue, 17 Oct 2017 15:25:33 +0300
parents
children 31a1f0b53d98
line source
1 #include <avr/io.h>
2 #include <avr/interrupt.h>
3 #include <util/delay.h>
4 #include "ps2kbd.h"
5 #include "defs.h"
7 #define BUF_SZ 16
8 #define BUF_IDX_MASK (BUF_SZ - 1)
9 #define NEXT_IDX(x) (((x) + 1) & BUF_IDX_MASK)
10 static volatile unsigned char keybuf[BUF_SZ];
11 static volatile unsigned char key_rd, key_wr;
13 static volatile int sending;
15 void ps2write(unsigned char c)
16 {
17 #if 0
18 int i;
19 unsigned short out = (unsigned short)c | ((unsigned short)(parity_even_bit(c) & 1) << 8);
21 /* pull clock low for >60us */
22 PS2LOW(BIT_CLK);
23 _delay_us(60);
25 /* then pull data low and release clock */
26 PS2LOW(BIT_DATA);
27 PS2REL(BIT_CLK);
29 for(i=0; i<9; i++) {
30 while(PINB & BIT_CLK); /* wait for kbd to drive the clock low */
31 PORTB |= out & 1;
32 out >>= 1;
33 while(!(PINB & BIT_CLK)); /* wait for kbd to drive the clock high */
34 }
36 PS2REL(BIT_DATA);
37 /* wait for ack */
38 while(PINB & BIT_DATA);
39 while(!(PINB & BIT_DATA));
40 #endif
41 }
43 unsigned char ps2read(void)
44 {
45 unsigned char key;
47 while(key_rd == key_wr) {
48 }
50 cli();
51 key = keybuf[key_rd];
52 key_rd = NEXT_IDX(key_rd);
53 sei();
55 return key;
56 }
58 int ps2pending(void)
59 {
60 return key_rd != key_wr;
61 }
63 ISR(INT0_vect)
64 {
65 static unsigned char value, parity;
66 /*static unsigned char valp;*/
67 static int nbits;
69 if(sending) {
70 } else {
71 if(nbits > 0 && nbits < 9) {
72 value >>= 1;
73 if(PIND & PDATA_BIT) {
74 value |= 0x80;
75 parity ^= 1;
76 }
77 }/* else if(nbits == 9) {
78 valp = (PIND >> PDATA) & 1;
79 }*/
80 if(++nbits >= 11) {
81 nbits = 0;
83 /* check parity */
84 /*if((parity & 1) == (valp & 1)) {}*/
85 keybuf[key_wr] = (unsigned char)value;
86 key_wr = NEXT_IDX(key_wr);
88 value = 0;
89 parity = 0;
90 }
91 }
92 }