Tak, przeszukałem fora Arduino.cc i tutaj. Tak, znalazłem artykuły dotyczące biblioteki ps2dev. Tak, przeczytałem (w porządku, trochę przeszukałem) ostateczny artykuł na temat interfejsu PS / 2 na tej stronie . Tak, to działa. Potrzebuję kilku pomysłów, aby zrobić krok do pełnego działania. :)
Nie, nie mogę po prostu emulować klawiatury USB HID i zostawić ją przy tym - musi to być emulacja klawiatury PS / 2. Tak, wysyłam odpowiednie sygnały make i break - obsługuje nawet bardzo skomplikowane kombinacje klawiszy. W tej chwili mam napisany kod dla mojego Arduino, jak napisano poniżej (technicznie Freeduino 1.22), i wysłałem naciśnięcia klawiszy za pomocą Serial Monitor lub terminala PuTTY, a także z poręcznym opakowaniem / sterownikiem Python, który wysyła rzeczywiste Informacja o skancodzie PS / 2 - i ogólnie znacznie ułatwia mi życie - również odciąża Arduino.
W tej chwili mam szkic działający na Arduino, który emuluje klawiaturę PS / 2. Oczywiście muszę uruchomić moją maszynę „docelową” (maszynę, do której wchodzi wtyczka PS / 2) i widzę, że odbywa się „handshake”. Uruchom do WinDoze, otwórz notatnik i poprowadź naciśnięcia klawiszy na ekranie (z powodzeniem) za pomocą mojego „sterownika” Pythona. (Sterownik po prostu odbywa się na terminalu Serial Monitor / PuTTY i odczytuje / zapisuje do portu szeregowego za pomocą modułu o nazwie PySerial.) Wszystko to odbywa się na AMD w płycie docelowej płyty głównej ASUS.
Teraz celem jest, aby działał na moim procesorze Intel na płycie głównej „Intel” na płycie głównej Intela, podłączam go, uruchamiam i nie ma kości. Zmodyfikowałem więc trochę szkic, aby dowiedzieć się, co się właściwie dzieje z moim małym przyjacielem Ardy. Wersja po modyfikacjach jest wyświetlana poniżej. Jak rozumiem (kod został „wypożyczony” z innego postu na forum Arduino.cc, tutaj ) Najpierw spróbuje nawiązać połączenie z „celem” na PS / 2, mrugając diodę pokładową co 0,5 sekundy, aż do połączenie jest ustanowione. Cel Intela nie przekroczył 0,5 sekundy, a połączenie szeregowe nigdy nie jest ustanawiane z „hostem”.
Moje pytanie brzmi: czy istnieje zasadnicza różnica w sposobie, w jaki klawiatury ps / 2 nawiązują komunikację z maszyną docelową? Czy to naprawdę różnica w projekcie, czy powinienem szukać czegoś bardziej podstawowego, o co tu chodzi? Słyszałem coś o potrzebie podciągania rezystorów na wejściach danych / zegara, ale to powinno być załatwione w kodzie, szczególnie dlatego, że DZIAŁA na innym celu, po prostu nie tym, nad którym muszę pracować.
Jakieś pomysły? Chciałbym uzyskać ten działający jak najszybciej - zamierzam nadal debugować, wszelkie wskazówki lub sugestie byłyby bardzo mile widziane. Wszyscy zostaną dokładnie rozważeni, ponieważ potrzebuję świeżego spojrzenia na tę kwestię. Być może potrzebna jest lepsza implementacja w bibliotece ps2dev?
#include "ps2dev.h" // to emulate a PS/2 device
// Orange = 2
// Blue = 3
// Red = 5V (3 in)
// Black = GND (4 in)
// EXT Power, USB for COM only
PS2dev keyboard(3,2); // PS2dev object (2:data, 3:clock)
int enabled = 0; // pseudo variable for state of "keyboard"
boolean serialConnected = false;
int incomingByte = 0;
void ack() {
//acknowledge commands
while(keyboard.write(0xFA));
}
int kbdCmd(int command) {
unsigned char val;
switch (command) {
case 0xFF: //reset
ack();
//the while loop lets us wait for the host to be ready
while(keyboard.write(0xAA)!=0);
break;
case 0xFE: //resend
ack();
break;
case 0xF6: //set defaults
//enter stream mode
ack();
break;
case 0xF5: //disable data reporting
//FM
enabled = 0;
ack();
break;
case 0xF4: //enable data reporting
//FM
enabled = 1;
ack();
break;
case 0xF3: //set typematic rate
ack();
keyboard.read(&val); //do nothing with the rate
ack();
break;
case 0xF2: //get device id
ack();
keyboard.write(0xAB);
keyboard.write(0x83);
break;
case 0xF0: //set scan code set
ack();
keyboard.read(&val); //do nothing with the rate
ack();
break;
case 0xEE: //echo
//ack();
keyboard.write(0xEE);
break;
case 0xED: //set/reset LEDs
ack();
keyboard.read(&val); //do nothing with the rate
ack();
break;
}
}
void connectHost() {
while (Serial.available() <= 0) {
Serial.print('A'); // send a capital A
delay(300);
}
}
void setup() {
pinMode(13, OUTPUT);
//establish serial connection with host
Serial.begin(9600);
// establish ps/2 connection with target
while(keyboard.write(0xAA)!=0){
digitalWrite(13, HIGH);
delay(500);
digitalWrite(13, LOW);
delay(500);
}
delay(100);
connectHost();
Serial.println("\nSerial Host Connected");
Serial.flush();
}
void loop() {
unsigned char c;
if( (digitalRead(3)==LOW) || (digitalRead(2) == LOW)) {
if(digitalRead(3)==LOW){
Serial.println("pin 3 is LOW");
} else {
Serial.println("pin 2 is LOW");
}
while(keyboard.read(&c));
kbdCmd(c);
Serial.print("Target: 0x");
Serial.println(c, HEX);
}
else {//if host device wants to send a command:
//echo ASCII code from terminal and write to ps/2
if(Serial.available() > 0) {
incomingByte = Serial.read();
keyboard.write(incomingByte);
Serial.print("Host: 0x");
Serial.print(incomingByte, HEX);
Serial.print(" ");
Serial.print(incomingByte);
Serial.print(" ");
Serial.println(incomingByte, BIN);
}
}
}