- LiTime Speicher und Akkus         
Seite 1 von 7 123 ... LetzteLetzte
Ergebnis 1 bis 10 von 69

Thema: Welche Möglichkeiten der Fehlersuche hat man beim Arduino?

  1. #1
    Erfahrener Benutzer Begeisterter Techniker
    Registriert seit
    18.03.2013
    Beiträge
    242

    Welche Möglichkeiten der Fehlersuche hat man beim Arduino?

    Anzeige

    LiFePo4 Akku selber bauen - Video
    Hallo,

    nachdem ich nun schon 2 Tage lang einen Programmfehler suche, bin ich mit meinem Latein am Ende und versuche es doch mal hier mit folgender Frage:

    ich nutze bisher nur die Möglichkeit, diverse Variablen an verschiedenen Stellen des Programmablaufs an den seriellen Monitor auszugeben.
    Außerdem habe ich den Prgrammablauf als Flussdiagramm dargestellt, um ihn besser überblicken zu können.
    Das Ergebnis ist, dass ich die Situation, in der der Fehler auftritt relativ genau kenne, aber trotzdem nicht verstehe, wieso es genau passiert.

    Das Fatale bei der Sache ist, dass der Ablauf (mehrere Antriebe sollen nacheinander in eine bestimmte Position fahren und auf Tasterbetätigung dort stehen bleiben) nach einem Neustart prima funktioniert, aber wenn das nach dem ersten, vollständigen Ablauf durch die Betätigung und Wiederfreigabe eines STOP-Schalters noch mal ablaufen soll, dann macht das nur der erste Motor und die Restlichen melden sofort, dass sie fertig sind. Dabei spielt es keine Rolle, dass die Antriebe bereits in der richtigen Stellung stehen, denn das tun sie beim ersten Mal auch.

    Nun erwarte ich natürlich nicht, dass mir jemand sagen kann, wo der Fehler liegt.

    Ich Suche aber nach einer Möglichkeit, durch einen Interrrupt, der auf eine Veränderung einer Variablen reagiert und die Position im Programm ausgibt, die genaue Stelle im Programm zu finden.

    Ist sowas möglich?

    vG

    fredyxx

  2. #2
    Erfahrener Benutzer Robotik Einstein Avatar von i_make_it
    Registriert seit
    29.07.2008
    Ort
    Raum DA
    Alter
    55
    Beiträge
    2.814
    Fehlersuche in einem Programm ist ohne Quellcode schon mal zielmlich schwierig (bis unmöglich).
    auf Verdacht sage ich mal in "void setup()" initialiserst Du was und in "Void loop()" wird es verändert aber nicht wieder auf den Startwert gesetzt"
    ggf. mal versuchen entweder die Initialisierung von "void Setup()" nach "void Loop()" zu verlagern (so das es bei jedem Durchlauf einmal ausgeführt wird)
    oder einen eigenen Abschnitt schreiben der in "void loop()" dafür sorgt das Zustandsmerker auf den Startwert gesetzt werden.

    Es gibt auch Debug Möglichkeiten für Arduino:
    http://www.visualmicro.com/page/Debu...r-Arduino.aspx

    Ups, habe den Post von Mxt vor meinem Update nicht angezeigt bekommen.
    Na ja doppelt schadet ja nicht
    Geändert von i_make_it (14.09.2016 um 12:19 Uhr)

  3. #3
    Erfahrener Benutzer Roboter Experte
    Registriert seit
    04.09.2011
    Ort
    Hessen
    Beiträge
    707
    Hallo,

    tja, man kann in die kleinen Dinger nicht so gut hineinsehen.

    Ich Suche aber nach einer Möglichkeit, durch einen Interrrupt, der auf eine Veränderung einer Variablen reagiert
    Technisch betrachtet würde man dafür ein Board brauchen, das Hardwaredebugging unterstützt. Außer dem Zero geht das auf keinem Arduino, das findet man eher bei anderen Boards wie ST Nucleo. In so einem Falle kann man mit Tools wie dem hier
    http://visualgdb.com/
    von Visual Studio aus debuggen.

    Eine Art Softwaredebugging für Arduinos kann die kostenpflichtige Variante des Visual Studio Plugins von Visual Micro
    http://www.visualmicro.com/post/2012...-Overview.aspx

    Beide habe ich mir aber bisher immer sparen können. Irgendwie bin ich immer über serielle Ausgaben dem Übel auf die Schliche gekommen. Am besten geht das, wenn der Code in Form von State Machines strukturiert ist und man sich bei jedem Zustandswechsel Ausgaben einbaut, die zeigen von wo nach wo gewechselt wurde.

  4. #4
    Erfahrener Benutzer Begeisterter Techniker
    Registriert seit
    18.03.2013
    Beiträge
    242
    Mit dem STOP-Schalter hatte ich bereits ein Unterprogramm gestartet, in dem m.E. alles Nötige auf Anfang gesetzt wird. Das habe ich noch mal überprüft und um noch einiges ergänzt. Ohne Erfolg.
    "void Setup()" nach "void Loop()" nützt auch nichts.

    Für das VisualStudio müsste ich wohl erst mal einen Lehrgang machen, weil insbesondere Englisch nicht zu meinen Stärken gehört.

    Im Moment bin ich der folgender Meinung:

    Das Programm springt in ein UP ohne über den Anfang des UP's rein zu kommen, weil:

    im hinteren Teil des UP's (da wo die Variable Motor fertig = true gesetzt wird; das ist eine von nur 2 Stellen im gesamten Programm) initiiere ich eine Ausgabe an den Monitor, die auch kommt, während eine andere Ausgabe an den Monitor direkt am Anfang des UP's gar nicht erscheint. Ich habe auch überprüft, dass die Sprungmarke, die zu dieser Stelle führt, im Programm sicher nur von Sprungbefehlen im eigenen UP angesprungen wird und die liegen alle natürlich hinter dem UP-Anfang.
    Kann da irgendwo eine vom Kompiler berechnete Sprungadresse vermurkst sein?

    Da fällt mir dann erst mal nichts mehr zu ein.

    vG

    fredyx

  5. #5
    Erfahrener Benutzer Roboter Experte
    Registriert seit
    04.09.2011
    Ort
    Hessen
    Beiträge
    707
    Achso, jetzt fällt es mir erst auf. Beim Wort "Unterprogramm". Du bist der von letztens mit den gotos.

    Ja, da wundert das nicht.

  6. #6
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    13.01.2014
    Beiträge
    454
    Blog-Einträge
    3
    In C / C++ sind es häufig diese Fehler:
    1) = statt == in logischen Abfragen
    2) break in switch-Blöcken vergessen
    3) Arrayindex größer als Arraygröße
    4) Integerdivision
    5) Division durch Null
    6) Nicht inizialisierte Pointer
    7) falsche Schleifenbedingung

    Kann da irgendwo eine vom Kompiler berechnete Sprungadresse vermurkst sein?
    - Nein.
    Sprungmarken außerhalb von Switch-Case-Blöcken solltest du nach Möglichkeit vermeiden, genauso wie den Sprungbefehl 'goto'. Nicht weil es nicht funktioniert, sondern weil es zu schwer durchschaubarem Spaghetti-Code führt.

  7. #7
    Erfahrener Benutzer Roboter Experte
    Registriert seit
    04.09.2011
    Ort
    Hessen
    Beiträge
    707
    Zitat Zitat von Sisor Beitrag anzeigen
    Nicht weil es nicht funktioniert, sondern weil es zu schwer durchschaubarem Spaghetti-Code führt.
    Das hat es schon
    https://www.roboternetz.de/community...l=1#post630697

  8. #8
    Erfahrener Benutzer Begeisterter Techniker
    Registriert seit
    18.03.2013
    Beiträge
    242
    Zitat Zitat von Mxt Beitrag anzeigen
    Achso, jetzt fällt es mir erst auf. Beim Wort "Unterprogramm". Du bist der von letztens mit den gotos.

    Ja, da wundert das nicht.
    Was soll das heißen?

    Ich kann mir kein umfangreiches Programm ohne UP's vorstellen. Das trägt doch eindeutig zur Übersichtlichkeit bei, wenn es mal klappt. Außerdem können große Programmteile übersprungen werden, die für einen bestimmten Ablauf nicht benötigt werden und verkürzen dadurch die Programmlaufzeit.
    Außerdem springe ich mit goto nicht nach vorne , sondern nur nach hinten!!

    vG

    fredyxx

    - - - Aktualisiert - - -

    Zitat Zitat von Sisor Beitrag anzeigen
    In C / C++ sind es häufig diese Fehler:
    1) = statt == in logischen Abfragen
    2) break in switch-Blöcken vergessen
    3) Arrayindex größer als Arraygröße
    4) Integerdivision
    5) Division durch Null
    6) Nicht inizialisierte Pointer
    7) falsche Schleifenbedingung


    - Nein.
    Sprungmarken außerhalb von Switch-Case-Blöcken solltest du nach Möglichkeit vermeiden, genauso wie den Sprungbefehl 'goto'. Nicht weil es nicht funktioniert, sondern weil es zu schwer durchschaubarem Spaghetti-Code führt.
    1) = statt == in logischen Abfragen
    ja, ist mir bekannt, habe ich vor kurzem erst noch praktiziert

    break in switch-Blöcken vergessen
    werde ich prüfen

    Arrayindex größer als Arraygröße
    Habe ich nicht verwendet

    4) Integerdivision und 5) Division durch Null
    werde ich prüfen

    Nicht inizialisierte Pointer
    Was ist das?

    falsche Schleifenbedingung
    ??

    vG
    fredyxx
    Geändert von fredyxx (14.09.2016 um 17:30 Uhr)

  9. #9
    Erfahrener Benutzer Robotik Einstein Avatar von i_make_it
    Registriert seit
    29.07.2008
    Ort
    Raum DA
    Alter
    55
    Beiträge
    2.814
    Zitat Zitat von fredyxx Beitrag anzeigen
    "void Setup()" nach "void loop()" nützt auch nichts.
    Davon hatte ich auch nichts gesagt.
    Sondern das was in "void Setup()" steht nach "void loop()" zu verschieben.
    Also

    void Setup() {

    bla
    bla
    von hier
    bla
    bla
    }

    void loop() {

    nach hier
    code
    code
    noch mehr code
    }

    Bei Arduino wird "void Setup()" immer genau einmal beim Start ausgeführt. "void loop()"dagegen wird in Endlosschleife ausgeführt bis der Strom weg ist ode rein Reset erfolgt.
    "void Setup()" kann man also sogar gezielt dazu nutzen um einen Code beim Einschalten immer genau einmal auszuführen.

    wenn Du allerdings mit Gotos um dich wirfst, dann ist Das was Du bekommen hast nicht weit.
    Gotos kann man nehmen wenn man damit klar kommt.
    Bei Assembler hat sogar nur Jump (also Goto) aber da muß man halt aufpassen das man auch immer wirklich da raus kommt wo man hin will (also zu der Situation)

    Um code in bestimmten Situationen zu überspringen gibt es z.B. IF und CASE. Da ist Quasi ein GOTO eingebaut.
    Dann gibt es noch Funktionen und Subroutinen (was Du Unterprogramme nennst). Bei einem Microcontroller mit genau einem Programm im Speicher gibt es keine Unterprogramme.
    Die Hauptschleife void loop() enthällt dann den code der immer durchlaufen werden muß und der Rest ist in Funktionen ausgelager.
    Das spart Laufzeit und verhindert Spagetti Code.

    Das von mir vorgeschlagene Verlagern der Initialisierung wird demnach vermutlich nichst bringen, kannst Du also lassen.

    Geh mal die Fehlersuche von Sisor durch und druck dir deinen Code aus.
    Dann nimm Textmarker und makiere alle Funktionsblöcke vom Beginn "{" bis Ende "}".
    Hast Du richtig codiert, darf sich keine Linie mit einer anderen überschneiden.
    Dann nimm Deine GoTOs und Deine Sprungmarken die Verbindungen dürfen dann auch nicht in verschiedenen Funktionsblöcken liegen.
    Wenn Ja liegt eigentlich ein bedingter Sprung vor also mußst Du vor dem GOTO oder nach der Sprungmarke dafür sorgen das die Bedingungen auch in jedem Fall immer erfüllt werden.
    Lustig wird es wenn von mehreren Gotos auf eine Sprungmarke gesprungen wird und dabei X Bedingungen vorliegen weil Variablenwerte nicht mehr korrekt verändert werden.

    Da ich sehr viele Quick and dirty Batch Scripte in Windows Umgebungen schreibe, bin ich mit den Fallstricken von GOTO ziemlich vertraut.
    Vor allem Da Notepad nicht wirklich eine IDE ist die auf Syntax oder Kontext prüft.
    Nur bin ich meist mit meinem Script schon am Arbeiten wenn die Programmierer in ihrer IDE ein Projekt eröffnet haben und anfangen wollen loszucoden.

    Also Analysier mal Deinen Code auf Papier, da wird vermutlich rauskommen das Deine Sprünge die Grenzen von Funktionsblöcken verletzen und deshalb Variablen nicht die richtigen Werte bekommen.
    Falls nicht ein Syntaxfehler vorliegt den die IDE nicht als solchen erkennt.
    Wie bei Vergleich und Zuweisung. Beides an sich syntaktisch richtig aber im Kontext eines Vergleichs ist die Syntax einer Zuweisung halt falsch.
    Geändert von i_make_it (19.09.2016 um 07:58 Uhr)

  10. #10
    Erfahrener Benutzer Roboter Experte
    Registriert seit
    04.09.2011
    Ort
    Hessen
    Beiträge
    707
    Zitat Zitat von fredyxx Beitrag anzeigen
    Was soll das heißen?
    Ich programmiere schon seit über 35 Jahren und habe schon genug solcher Programme gesehen. Nach dem ersten Blick auf den Code in dem zitierten Thread und war damals schon klar, dass es zu einem Thread wie diesem kommen würde.

    Zitat Zitat von fredyxx Beitrag anzeigen
    Ich kann mir kein umfangreiches Programm ohne UP's vorstellen. Das trägt doch eindeutig zur Übersichtlichkeit bei
    Du redest davon, tust es aber nicht. Das Konzept in C um Programme zu Strukturieren sind Funktionen nicht gotos.

    Statt wie bei dir
    Code:
    switch(irgendwas)
    { 
      case 0:
        Mx =42;
        goto Mblub;
        break;
    	
        // ...
    	
    Mblub:
    
       // code ...
       
       goto Mbob;
       
       // anderes Zeug
       
    Mbob:
    
       // nochmehr Code
       
       goto Nochweiter;
    ist die Sprache eigentlich so gedacht
    Code:
    void blub(int paran)
    {
      // Der Code hinter dem einen Label
    }
    
    void bob()
    {
      // Der Code beim anderen
    }
    
    // ...
    
    switch(irgendwas)
    {
      case 0:
        blub(42);
        bob();
        break;
    
       // ...
    und nicht kilometerlanger Bandwurmcode in dem mit goto rumgehüpft wird.

    Dann hätten einmal mehr Leute überhaupt Lust sich das anzusehen und man kann jede Funktion mit Ausgaben versehen.
    Eventuell auch mit zusätzlichen Parametern, die nur dazu dienen in der Ausgabe anzuzeigen, woher der Aufruf kam.

    Also in der Art
    Code:
    void foo(int caller, int arg)
    {
      Serial.print("Aufruf von");
      Serial.print(caller);
      Serial.print(" mit ");
      Serial.println(arg);
    }
    und bei der Verwendung

    Code:
       // Eine Stelle
    
       foo(1, M42);
    
    
       // woanders
    
       foo(2, M42);

Seite 1 von 7 123 ... LetzteLetzte

Ähnliche Themen

  1. 18 PWM Kanäle - Welche Möglichkeiten?
    Von Hardware-Entwickler im Forum Elektronik
    Antworten: 7
    Letzter Beitrag: 19.12.2015, 15:16
  2. Antworten: 8
    Letzter Beitrag: 21.10.2014, 10:18
  3. Möglichkeiten der AVR/Arduino PWM?
    Von ichbinsisyphos im Forum Arduino -Plattform
    Antworten: 10
    Letzter Beitrag: 23.02.2013, 10:03
  4. Spannungen mit PC-Computer Messen. Welche Möglichkeiten?
    Von petermetertr im Forum PC-, Pocket PC, Tablet PC, Smartphone oder Notebook
    Antworten: 14
    Letzter Beitrag: 26.08.2009, 17:36
  5. [ERLEDIGT] 20 mikrovolt-Hirnwellen registrieren-Welche möglichkeiten?
    Von Thomas Wellheim im Forum Allgemeines zum Thema Roboter / Modellbau
    Antworten: 13
    Letzter Beitrag: 18.12.2004, 19:43

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

LiTime Speicher und Akkus