Mit Interruptüberlauf meinte ich eine zu lange ISR die noch nicht fertig ist wenn der nächste Interrupt schon ansteht.
Druckbare Version
Mit Interruptüberlauf meinte ich eine zu lange ISR die noch nicht fertig ist wenn der nächste Interrupt schon ansteht.
Ich glaube ich habe gestern den fehler des zuckens gefunden, irgendwie mag es die Berechnung der IK nicht wenn während der berechnung die Interrupts der Servoansteuerung kommen. ich habe jetzt mal die Berechnung in die Pausen gelegt wo die Servoansteurung zeit hat und jetzt gehts.
aber erklären kann ich es mir nicht... schon komisch... eventuell ein Bug von Bascom? vielleicht wird irgendwo eine Speicherzelle überschrieben, was ich mir aber fast nicht vorstellen kann...
@Klingon77:
Ich werde dann nach ein Paar Betriebsstunden mal ein Paar Servos zerlegen und schauen wie es innen aussieht und dann weiter entscheiden...
gruss Bluesmash
Die HS475 laufen bei mir schon einige Betriebsstunden ohne Probleme, ich denke du musst da keinen auseinander bauen. Die sind an und für sich ganz in Ordnung.
Verwendest du jetzt eigentlich noch die Plastik Servohörner oder hast du dir welche aus Metall besorgt?
Ich habe mir beim grossen "C" welche aus Alu gekauft, die sitzen bombenfest auf den Servohörnern. Die aus Kunstoff waren mir einfach zu "labbrig" und hatten zu viel spiel... so sind nun die verbindungen recht steif. Das grösste Spiel hat nun das Getriebe, welches aber schlecht optimiert werden kann...
gruss Bluesmash
Das Problem habe ich,Zitat:
Zitat von radbruch
allzuviel darf man in der ISR nicht machen
Das klingt mir ganz danach als gäbe es da einen Konflikt beim Zugriff auf eine Variable...Zitat:
Ich glaube ich habe gestern den fehler des zuckens gefunden, irgendwie mag es die Berechnung der IK nicht wenn während der berechnung die Interrupts der Servoansteuerung kommen. ich habe jetzt mal die Berechnung in die Pausen gelegt wo die Servoansteurung zeit hat und jetzt gehts.
aber erklären kann ich es mir nicht... schon komisch... eventuell ein Bug von Bascom? vielleicht wird irgendwo eine Speicherzelle überschrieben, was ich mir aber fast nicht vorstellen kann...
Nehmen wir an du hättest irgendeine 16Bit Variable die in einer ISR geschrieben und im Programm irgendwo gelesen wird (oder umgekehrt, völlig egal). Dann musst du beachten, daß bei einem 8-Bit µC in der Regel jeweils 2 Operationen dafür benötigt werden. Tritt jetzt nach der ersten Operation der Interrupt auf, wurde die Variable erst "zur Hälfte" gelesen bzw. geschrieben und das kann Probleme geben.
Ein Beispiel:
Ich habe eine Timer-ISR die einfach nur eine 16-Bit Variable jeweils um 1 inkrementiert, und an verschiedenen Stellen im Programm lese ich diese Variable ein um z.B. irgendwelche Zeiten zu messen.
So, gehen wir mal davon aus daß die Variable aktuell einen Wert von 0x00FF hat und beim Zugriff jeweils immer das untere Byte zuerst kommt. Wir wollen den Wert im Programm also einlesen, und bekommen als erstes das untere Byte mit dem Wert 0xFF, aber dann kommt der Interrupt und inkrementiert die Variable um 1 so daß ihr Inhalt jetzt eigentlich 0x0100 ist. Dummerweise weiß das Programm davon aber nichts und macht nach dem Rücksprung einfach mit dem lesen der zweiten Hälfte der Variable weiter, nämlich 0x01. Das Programm hat also 0x01FF gelesen, ein Wert der natürlich viel zu groß ist.
Solche Probleme können nicht nur auftreten wenn die ISR schreibt und das Programm liest, sondern auch wenn das Programm schreibt und die ISR liest, auch welcher Teil der Variable zuerst gelesen wird ist egal.
Prüfe deinen Code mal auf derartige Konflikte
Diese Idee hatte ich auch schon... ich schreibe die berechneten Servopositionen in eine 16bit variable. welche dann vom interrupt dem Timerwert zugewiesen wird.
Ich habe es so gelöst dass ich 2 Blöcke gemacht habe, in etwa so:
servo_umsch=1
servo_1(1) = servo_pos(1)
servo_1(2) = servo_pos(2)
servo_1(3) = servo_pos(3)
servo_umsch=0
servo_2(1) = servo_pos(1)
servo_2(2) = servo_pos(2)
servo_2(3) = servo_pos(3)
Jenachdem ob servo_umsch 1 oder 0 ist lese ich in der ISR die variablen servo_1 oder servo_2. So kann ich verhindern dass ich eine Variable lese welche gerade beschrieben wird....
gruss bluesmash
Hmm, das sollte eigentlich funktionieren, auch wenn es nicht gerade die platzsparendste Lösung ist (den zweiten Block Variablen könnte man sparen, wenn man vor dem Zugriff einfach den Interrupt abschaltet).
Spontan fällt mir aber auch kein anderer "typischer" Fehler ein, der solche Probleme auslösen kann.
Naja diese lösung ist aus der not entstanden als es immer noch nicht funktionierte. werde dann wahrscheinlich deine lösung einbauen. Danke!
könnte es sein dass, bei bascom die Trigonometrischen Funktionen (Sin/Cos/Tan) irgendwie ein Problem mit dem Interrupt haben? dass da irgendwelche Variablen überschrieben werden oder irgend sowas? Bei der überprüfung gestern habe ich herausgefunden dass zwischendurch wirklich falsche positionen berechnet werden und die servos für einen kurzen Augenblick an eine falsche Position fahren wollen....
gruss Bluesmash
Hallo,
erstmal: Applaus für das tolle Projekt. IK Bewegungen sehen irgendwie immer sehr "schön" aus.
Ich hatte vor einiger Zeit auch ein ähnliches Problem. Ich hab in Bascom die tan Funktion benutzt(Mega32) und wenn ich dann zur Performancemessung einen regelmäßigen Interrupt ausgeführt habe(die Zeit spielte keine Rolle, es war auch egal ob mit timer0 oder timer1) hat der controller total angefangen zu spinnen. zufällige ports wurden gesetzt, etc. (zumindest sah es für mich zufällig aus). Kann sein das dies auch aus einer fehlerhaft modifizierten Variable entstanden ist.
Ich hatte dann aber keine Lust mehr das Problem weiter zu verfolgen und habs anders gelöst.
Könnte aber sein das das das gleiche Problem ist...
Gruß,
Majus