Debugger für Arduino UNO

Hallo allerseits,

es ist oft schwierig logische Fehler in einem Programm zu finden. Aus diesem Grund habe ich mir einen Debugger “gebastelt”

Der Debugger besteht aus zwei Teilen, einen Sender und einen Empfänger.
Der Sender ist ein Arduino UNO. Auf diesen läuft das zu überprüfende Programm. In diesem Programm kann man beliebig viele Haltepunkte setzen. Damit ist auch ein quasi Schrittbetrieb möglich. Bei Erreichen eines Haltepunktes wird das zu untersuchende Programm gestoppt und bis zu 4 Parameter an den Empfänger (Arduino UNO) gesendet. Es können bei jedem Haltepunkt unterschiedliche Parameter gesendet werden.
Durch den Empfänger kann bestimmt werden, wann das zu untersuchende Programm wieder weiter läuft.

Die verwendeten Programme können hier geladen werden: http://www.huk-2.de/debugger/debugger_v3_1.zip

Der Empfänger ist ebenfalls ein Arduino UNO. Dieser steuert eine 2 X 16 Anzeige an. Weiterhin befindet sich dort ein Taster. Nach Übermittlung der Daten werden diese auf dem Display angezeigt. Nach einem Tastendruck wird das zu untersuchende Programm nach einer kurzen Pause wieder frei gegeben.

Während der Datenübertragung wird mit Sternen angezeigt, welche Parameter gerade geladen werden
Beim ersten Parameter ein *, beim zweiten **, usw.
Bei kleinen Ziffern geht das sehr schnell. Bei 9999 dauert es in etwa eine Sekunde.

Zum definierten Starten sollte folgende Reihenfolge eingehalten werden. Nach dem das zu untersuchende Programm geladen wurde, Datenverbindung herstellen. Mit Reset den Empfänger starten. Wenn die Anzeige verlischt den Sender sofort mit Reset starten.

Aufgebaut sieht der Empfänger bei mir so aus:

Der blaue Draht ist die Masseverbindung, der rot die Datenleitung

Die Anschlüsse sind wie folgt verschaltet:

Digital 0 = Daten
Analog 4 = SDA Anzeige (Daten)
Analog 5 = SCL Anzeige (Takt)
Digital 9 = Taster gegen GND

Bei Digital 0 (Daten) ist noch folgendes zu beachten:
An diesen Pin müssen zwei Widerstände angeschlossen werden. Ein Widerstand (6,8 KOhm, ist nicht kritisch) an GDN. Es kann sein, dass sowohl das Daten-Pin beim Sender und Empfänger auf Eingang geschaltet sind. Dann tritt ein nicht definierter Zustand ein der zu Funktionsstörungen führen kann.
Der zweite Widerstand (270 Ohm) liegt in Reihe zwischen den beiden Daten-Pin (Sender <-> Empfänger).
Ich kann nicht ausschließen, dass kurzeitig beide Daten-Pin auf Ausgang geschaltet sind und unterschiedliches Potenzial führen. Das kann zu Zerstörung der Ausgänge führen.

Das Programmpaket für den Sender besteht aus drei Programmen:

debug_sender_v3_1.ino → Hier kann das zu überprüfende Programm rein geschrieben werden.
programm.ino → Dieses Programm läuft nach erreichen eines Haltepunktes im Hintergrund und erledigt den Datenaustausch.
up1.h → In diesen Programm werden die für Programm.ino benötigten Variablen deklariert.

Alle drei Programme müssen sich im gleichen Ordner befinden. Gestartet wird der Sender mit debug_sender_v3_1.ino. Das Programm kann beliebig umbenannt werden. Sinnvollerweise nach dem Start mit „Speichern unter“. Dann wird automatisch ein neuer Ordner angelegt. In ihm befinden sich dann gleich alle drei Programme.

Nach dem Start sollte sich folgendes Bild zeigen:

Wichtig, dass alle drei Programm zu sehen sind.

Auch beim Sender sollte das Daten-Pin mit einen 6,8 KOhm Widerstand gegen GND gezogen werden. Im Prinzip ist es egal, welches Port man wählt. Es mus dann nur in up.h (int deb_daten=13;) geändert werden.
Die 13 habe ich gewählt, weil eine LED auf dem Bord mit diesem Pin verbunden ist. Man kann dann sehen, ob gesendet wird.

Zur Funktion müssen beide Bords mit dem GND, so wie die Daten-Pin über den Widerstand (270 Ohm, wie oben beschrieben) verbunden sein.
Beim Übertragen der jeweiligen Programme auf die Platinen muss die Datenleitung getrennt sein. Mache ich das nicht, kann ich den Rechner neu starten. Er erkennt die USB Schnittstelle nicht mehr. Kann auf anderen Rechnern auch anders sein.

Verwendet man mehrere HP macht es Sinn, als erstes Parameter die Nummer des HP zu übertragen.

Der Datenaustausch erfolgt nach folgendem Muster:

Am Anfang ist der Daten-Pin des Empfängers auf Eingang geschaltet.

Nach erreichen eines Haltepunktes wird der Pin des Senders auf Ausgang geschaltet. Es wird ein Start-Bit gesendet. Dann erfolgt das Senden des ersten Datenpaketes als Mäander.

Nach dem ersten Datenpaket kommt eine Pause. Diese wird vom Empfänger erkannt und die nachfolgenden Daten dem zweiten Parameter zugeordnet.

Die Übertragung des zweiten Parameters beginnt wieder mit einen Start-Bit. Das ist nötig, da sonst eine Null nicht übertragen werden kann.

Nach Übertragung des 4. Paketes schaltet das Daten-Pin des Senders auf Eingang, dass des Empfängers auf Ausgang (LOW),

Nach der Darstellung der Ziffern und dem Start mit dem Taster, wird ein HIGH vom Empfänger gesendet und danach das Daten-Pin wieder auf Eingang geschaltet.

Das gesendete HIGH ist für den Sender das Signal, das zu untersuchende Programm wieder frei zu geben und das Spiel beginnt wieder von vorn.

Implementiert man den Sender oder Empfänger auf einen anderen Typ des Arduino kann die Pausenerkennung kritisch sein. Diese ist im Programm des Empfänger (int l_test = 5500;). Dann muss man diesen Wert ändern. Ist die Ziffer zu klein, wird das erste Parameter entweder als 0 oder 1 dargestellt, unabhängig was gesendet wurde. Ist sie zu groß, kommen nur undefinierte Werte an.

Ich hoffe das war jetzt nicht zu großes Kauderwelsch. Bei Fragen fragen . . .

Auch wenn ich auf dem Gebiet der Programmierung (Assembler, Maschine) jahrelang (lang ist es her) gearbeitet habe, ist diese Art für mich Neuland. Für Ratschläge bin ich dankbar. Es würde mich auch interessieren, wenn es jemand zum Laufen gebracht hat und es anwendet.

M.f.G.

Hans-Ulrich

Hallo,

habe es nur gerade gesehen und eine Frage:
eigenes Übertragungsverfahren statt SoftSerial um Speicher zu sparen?

Bisher bin ich da ganz gut mit Debug-Ausgaben über die normale Serielle ausgekommen, man hat so auch gleich ein Log auf dem Bildschirm und kann das Programm relativ ungebremst weiterlaufen lassen.
Mir erschließt sich Deine Anwendung noch nicht so ganz.

Gruß aus Berlin
Michael

Der Witz beim "echten" Debuggen im Vergleich zu programmierten Serial.print Debugausgaben ist doch, dass man

  • an einem Haltepunkt interaktiv verschiedene Variable ansehen kann.
  • interaktiv den nächsten Haltepunkt setzen kann.

Weitere Wünsche (z.B. Variable modifizieren, lokale Variable ansehen) können gerne später kommen.

Dein wesentlicher Unterschied zum üblichen Serial.print ist die Ausgabe an einen zweiten Arduino, der dann eine 16x2 Anzeige und einen "Weiter" - Taster hat ?
Die Stopps und die Auswahl der anzuzeigenden Variablen werden auf dem Testling programmiert, oder hab ich das nicht richtig verstanden?

Hallo,

@ Michael (1)

Bisher bin ich da ganz gut mit Debug-Ausgaben über die normale Serielle ausgekommen, man hat so auch gleich ein Log auf dem Bildschirm und kann das Programm relativ ungebremst weiterlaufen lassen.

Es führen viele Wege nach Rom . .

Wenn es darauf ankommt, dass das Programm ungehindert weiter läuft ist dieser Weg ungeeignet. Wenn es nicht nötig ist, kann ich hier an beliebigen Stellen HP setzen und beliebig viele Parameter mir anschauen. Dabei kann ich immer die Parameter nehmen, die für den betreffenden HP wichtig sind. Ich kann auch mehrere HP hintereinander setzen und damit noch mehr Parameter an dieser Stelle anzeigen.
Hat alles seine Vor- und Nachteile.

@ Michael (2)

Dein wesentlicher Unterschied zum üblichen Serial.print ist die Ausgabe an einen zweiten Arduino, der dann eine 16x2 Anzeige und einen "Weiter" - Taster hat ?
Die Stopps und die Auswahl der anzuzeigenden Variablen werden auf dem Testling programmiert

Genau so ist es.

Die betreffende Zeile sieht so aus: para1= 1; para2= 2; para3= 3;para4= 4; halt();

Steht im Programm als Beispiel.

Die werte für die Parameter sind hier nur Symbolisch. Es können Zahlen (z.B. Nummer des Haltepunktes) oder die Nahmen von Parametern eingegeben werden. Wobei die bei jedem Haltepunkt beliebig sind. Das richtet sich immer danach, was ich an dieser Stelle wissen möchte.
Es sollte aber immer etwas eingegeben werden, ansonsten wird der letzte an einen HP eingegebene Wert angezeigt (kann auch manchmal gewünscht sein, um die Veränderung zu dokumentieren).

M.f.G.

Hans-Ulrich