Ich habe studiert, um TDD in der eingebetteten Entwicklung zu machen. Bis jetzt habe ich hauptsächlich Anwendungen studiert, daher werde ich versuchen, etwas zu erstellen, das ein bisschen wie eingebettet aussieht (vorausgesetzt, es ist eingebettetes Linux). Da es sich um eine Glattstellung handelt, kann sich die Richtlinie unterwegs ändern. Sie werden es nicht wissen, bis Sie es tatsächlich tun, also schauen Sie bitte mit warmen Augen zu.
Bitte zögern Sie nicht, uns Ihre Meinungen und Wünsche mitzuteilen! Es ist sehr ermutigend.
Apropos eingebaut, es wäre L Chika! Ich möchte es jedoch einfacher machen, es zu versuchen, also werde ich die LED auf der Tastatur flackern lassen (z. B. Feststelltaste). Es wird keine Hochleistungsbibliothek verwendet, sondern durch Bearbeiten von Gerätedateien verwaltet.
Wenn es zu einfach ist, ist es zu einfach und nicht praktisch, also werde ich darüber nachdenken, die nächste Funktion zu realisieren.
Berücksichtigen Sie immer die Portabilität auf eine andere Hardware, da diese integriert ist.
OS | Virtual box ubuntu 16.04 |
Compiler | gcc (Ubuntu 5.4.0-6ubuntu1~16.04.5) 5.4.0 20160609 |
Werkzeug erstellen | autotools, pkg-config |
Bibliothek | libevdev-1.0 |
Test-Framework | googletest/googlemock@62ba5d9 |
Produktcode | C or C++(Ich denke) |
Voruntersuchungen sind wichtig für alles, was Sie tun. Vorerst werde ich meine Umgebung untersuchen.
Überwachen Sie die Datei / dev / input / event 〇〇, um Tastatureingabeereignisse unter Linux abzurufen. Zahlen werden im Teil von 〇〇 eingegeben, aber die Nummer der Tastatur ändert sich in der Reihenfolge, die in der Umgebung und beim Start erkannt wird (es ist möglich, sie mit udev zu beheben, aber dieses Mal werde ich sie vorerst belassen).
Suchen Sie in / proc / bus / input / device nach der Tastatur. Derzeit unterstützt event2 (input2) Tastaturen.
cat /proc/bus/input/devices
==Unterwegs weggelassen==
I: Bus=0011 Vendor=0001 Product=0001 Version=ab41
N: Name="AT Translated Set 2 keyboard"
P: Phys=isa0060/serio0/input0
S: Sysfs=/devices/platform/i8042/serio0/input/input2
U: Uniq=
H: Handlers=sysrq kbd event2 leds
B: PROP=0
B: EV=120013
B: KEY=402000000 3803078f800d001 feffffdfffefffff fffffffffffffffe
B: MSC=10
B: LED=7
==Unten weggelassen==
Für Ereignisgeräte wie / dev / input bietet Linux eine evdev-Schnittstelle (Linux Input drivers v1.0) tun. Die Wrapper-Bibliothek für dieses evdev ist libevdev. Dieses Mal werden wir dieses libevdev verwenden.
Überprüfen Sie anschließend die LED auf der Tastatur. Linux bietet eine LED-Klasse. Wenn Linux die LED erkennt, wird sie unter / sys / class / leds in sysfs exportiert. Die LEDs für Capslock, Numlock und Scrolllock werden erkannt. (Meine Tastatur hat keine LEDs an den Numlock- und Scrolllock-Tasten ... Recherche erforderlich)
ls /sys/class/leds/
input2::capslock input2::numlock input2::scrolllock
Da wir von dem privilegierten Zustand ausgegangen sind, sowohl Hardware (Tastatur) als auch Bibliothek (libevdev) zu haben, werden wir Tests schreiben, um die Zielbibliothek zu verstehen. Wenn Sie diesen Test schreiben, testen Sie Ihr Verständnis der Bibliothek. Es scheint sehr gut, dass das, was Sie verstehen, als Test bleibt.
Wenn dies auf dem Host-Computer möglich ist, haben Sie Glück.
Wenn es 1 ist, können Sie gehorsam mit dem Crossbuilding fortfahren. Im Fall von 2, wenn Sie die API kennen, machen wir einen Mock. Wenn die Realität herauskommt, können Sie testen, ob die im Test geschriebene Verwendung korrekt ist. Wenn Sie die API nicht verstehen, können Sie sich vorstellen, einen Mock zu machen. Das Erstellen eines Modells ohne Kenntnis der Implementierungsdetails hat auch seine Vorteile, und die API kann angemessen abstrahiert werden.
Die Einführung ist lang geworden, aber schauen wir uns den Test an, den ich dieses Mal geschrieben habe. Ich werde einen Teil des Codes weglassen. Wenn Sie das gesamte Bild sehen möchten, klicken Sie hier [https://github.com/tomoyuki-nakabayashi/TDDforEmbeddedSystem].
Holen Sie sich zunächst die Steuerdaten von evdev aus dem Dateideskriptor. Bei Erfolg werden 0 oder mehr zurückgegeben. Dieser Test schlug zunächst fehl. Jetzt, da wir wissen, dass wir Root-Rechte benötigen, werden wir den Testnamen bekannt geben (AsRoot hinzufügen). Jetzt werden Sie zu einem späteren Zeitpunkt nicht mehr von derselben Sache abhängig sein. Wenn Sie plötzlich jemanden übernehmen, werden Sie feststellen, dass Sie es nicht ohne Root-Rechte ausführen können.
TEST_F(EvdevSampleTest, InputEventFileCanOpenAsRoot) {
struct libevdev *dev = nullptr;
int fd = open("/dev/input/event2", O_RDONLY|O_NONBLOCK);
int rc = libevdev_new_from_fd(fd, &dev);
EXPECT_GE(rc, 0);
}
Da die Kontrolldaten von evdev erfasst wurden, bestätigen Sie, dass EAGAIN zurückgegeben wird, wenn keine Eingabe erfolgt. Dies ging in einem Schuss vorbei.
TEST_F(EvdevSampleTest, ReturnsEAGAIN) {
input_event ev {};
int actual = libevdev_next_event(evdev_, LIBEVDEV_READ_FLAG_NORMAL, &ev);
EXPECT_EQ(-EAGAIN, actual);
}
Drücken Sie dann die Eingabetaste und es wird LIBEVDEV_READ_STATUS_SUCCESS zurückgegeben, um zu testen, ob Sie das erwartete input_event erhalten können. Nach dem Ausführen des Tests wird der Test während der Ausführung dieses Tests angehalten. Wenn Sie also die Eingabetaste drücken, besteht der Test (es ist kein Komponententest mehr, aber es ist mir egal). Bis wir das endgültige EXPECT_EQ erreichen, haben wir bestätigt, dass die Ereignisse, die wir erfasst haben, wie erwartet sind, aber wir kümmern uns vorerst nicht darum.
TEST_F(EvdevSampleTest, CaptureEnterKeyPress) {
auto expect = create_key_event(KEY_ENTER, KEY_PRESSED);
input_event actual {};
while (true) {
int rc = libevdev_next_event(evdev_, LIBEVDEV_READ_FLAG_NORMAL, &actual);
if ((rc == LIBEVDEV_READ_STATUS_SUCCESS) && actual == expect) break;
}
EXPECT_EQ(expect, actual);
}
In Anbetracht der Tatsache, dass es mit anderen Eingabegeräten verwendet werden kann, wäre es schön, eine universelle Rückrufschnittstelle zu haben. libevdev bietet keinen Rückrufmechanismus, daher frage ich mich, ob ich einen Rückrufmechanismus von Grund auf neu erstellen kann.
Nächster: Versuchen Sie, etwas zu entwickeln, das mit TDD nahezu eingebettet ist ~ Problemauslösung ~
Recommended Posts