Anybody can find the problem in this chunk of code ? When I hit 'A' I get 1C as code but when I release I get a 70 instead of an F0. If you can of course. It seams that the first bit is never read. Thank you.
unsigned char getKey() { unsigned char n,dato; n = 0; // Inizializza il contatore dato = 0; // Inizializza il dato while(CLOCK); // Se il clock rimane a 1 aspetta while(!CLOCK); // La prossima discesa e' quella con il primo bit for (n = 0; n < 7; n++) { while(CLOCK); // Aspetta il bit n-esimo if (DATA) dato = dato | 0x80; // Bitwise OR dato = dato >> 1; // Shift a destra while(!CLOCK); // Aspetta la risalita del clock } while(CLOCK); // Aspetta il parity bit parity = DATA; while(!CLOCK); while(CLOCK); // Aspetta lo stop bit while(!CLOCK);
return dato; }
Read the posting tips for source code, and try again.
unsigned char getKey() { unsigned char n,dato; n = 0; // Inizializza il contatore dato = 0; // Inizializza il dato while(CLOCK); // Se il clock rimane a 1 aspetta while(!CLOCK); // La prossima discesa e' quella con il primo bit for (n = 0; n < 7; n++) { while(CLOCK); // Aspetta il bit n-esimo if (DATA) dato = dato | 0x80; // Bitwise OR dato = dato >> 1; // Shift a destra while(!CLOCK); // Aspetta la risalita del clock } while(CLOCK); // Aspetta il parity bit parity = DATA; while(!CLOCK); while(CLOCK); // Aspetta lo stop bit while(!CLOCK); return dato; }
I tried, in case it soesn't work this is a link to a picture
www.while1.eu/.../PS2.jpg
How do you expect to be able to capture F0?
That means that your loop must be able to exit with the most significant bit set.
But after you do "dato = dato | 0x80" you have an obligatory shift right. So it's impossible for you to ever exit that loop with the most significant bit set.
Another thing, just to make sure: are you planning to read 7 or 8 bits of data in the loop?
Because I am using a Keyboard and when I release a button I get an F0. Thank you for your help, and yes they are 8 but with 7 I was able to see something right. Now everything works. The only problem I have is that if I don't add sendChar(' '); after sendHex(getKey()); I still get some errors. But with it everything is fine. Thank you again.
// Read a code from a PS2 Keyboard unsigned char getKey() { unsigned char n,dato; n = 0; // Inizializza il contatore dato = 0; // Inizializza il dato while(CLOCK); // Se il clock rimane a 1 aspetta while(!CLOCK); // La prossima discesa e' quella con il primo bit for (n =0; n < 8; n++) { while(CLOCK); // Aspetta il bit n-esimo if (DATA) dato = dato | 0x80; // Bitwise OR if (n < 7) dato = dato >> 1; // Shift a destra tranne ultimo bit while(!CLOCK); // Aspetta la risalita del clock } while(CLOCK); // Aspetta il parity bit parity = DATA; while(!CLOCK); while(CLOCK); // Aspetta lo stop bit while(!CLOCK); return dato; } void main() { initSio(); // Inizializza la seriale a 9600 while(1) { sendHex(getKey()); sendChar(' '); // parity ? sendChar('t') : sendChar('f'); } while(1); }
Have you never considered that you do the shift in the wrong order?
Consider what happens if you instead write:
for (n = 0; n < 8; n++) { while(CLOCK); // Aspetta il bit n-esimo dato >>= 1; // Make room for a new bit. if (DATA) dato |= 0x80; // Assign bit if set. while(!CLOCK); // Aspetta la risalita del clock }
By the way - if your source code indents with spaces, then you are more likely to get good results when you try to paste the source code into other editors or into web pages. There are no world-wide standard for how much to indent when a tab character is seen.
You are two times right, then again this is the difference between an amateur and a professional. I am learning a lot just reading other posting too. I sow an array used as look up table to get the ascii code from the keyboard code. Thank you very much Westermark, there is neither need for a delay everithing works fine and reliably.
Now I am trying to send data to the keyboard. I just began
I know it could be too much but I would like an help for the second part. This code sending the the commands 0xED and 0x07 to the keyboard to switch on the LEDs sometimes switches on only two LEDs but I expected to switch on the all three LEDs. Could you please tell me where could be the problem ?
void delay() { unsigned char a; for (a = 0; a < 200; a++); } // Send a command to a PS2 keyboard void sendCmd(unsigned char com) { bit parity = 1; unsigned int n; DATA = 1; CLOCK = 1; delay(); CLOCK = 0; delay(); DATA = 0; CLOCK = 1; // Partenza dati while(CLOCK); // Aspetto la prima discesa while(!CLOCK); // Alla prossima discesa la tastiera si aspetta D0 for (n = 0; n < 8; n++) { DATA = com & 0x01; parity = parity ^ (com & 0x01); com = com >> 1; while(CLOCK); while(!CLOCK); } DATA = parity; while(CLOCK); // Aspetto la prima discesa while(!CLOCK) DATA = 0; // Stop bit while(CLOCK); // Aspetto la prima discesa while(!CLOCK); DATA = 1; CLOCK = 1; }
Is your clock phase correct? I don't know the outside of your hardware but doesn't the keyboard read the data on rising edge of the clock signal?
You seem to set the data when the clock goes high, unless you are inverting the signal on the outside.
Here is a link about the protocol: www.computer-engineering.org/.../