Forum: Compiler & IDEs Ich werd noch bekloppt - prog geht nicht


von thkais (Thomas Kaiser) (Gast)


Angehängte Dateien:

Lesenswert?

Moin allerseits.

Im Anhang habe ich ein Ding, an dem ich mir die Zähne ausbeisse.
Es geht um die Auswertung eines Jog-Rades, das mit zwei
phasenversetzten Signalen sowohl Drehrichtung als auch Drehimpulse
ausgibt (gleiches Prinzip wie in den alten mechanischen Mäusen).
Damit das Ganze im Hintergrund abläuft, habe ich die Auswertung in
Interrupts gepackt, und zwar Ext. 0 und 1. Beide Interrupts sind so
definiert, dass sie bei jedem Flankenwechsel ausgelöst werden.
Im Hauptprogramm wird einfach der Zählerstand binär auf 8 LEDs
ausgegeben, Bit 0-5 auf PortB und Bit 6,7 auf PortD.
Das funktioniert wunderbar, solange der Zähler rückwärts zählt, auch
der Überlauf 0xFF -> 0x00 macht keine Probleme. Drehe ich das Rad so
herum, dass der Zähler aufwärts zählt, bekomme ich beim Übergang 0x3F
-> 0x40 einen Reset. Von 0x00 - 0x3F zählts wunderbar.
Ich habe keinen blassen Schimmer, woran das liegen könnte - HELP !!
Der im Anhang gepostete Codeschnipsel ist lauffähig und macht genau den
gleichen Mist, wie der Code in meinem Gesamtprojekt.
Was zum Teufel habe ich übersehen?

von ..,- (Gast)


Lesenswert?

Lass das mit den externen Interrupts, diese Jog-Räder prellen wie Sau.
Die beste Lösung ist die Auswertung im Timerinterrupt, wie es der
µC-Gott Peter gemacht hat:
http://www.mikrocontroller.net/forum/read-4-37992.html#214943

von Thomas K. (thkais)


Lesenswert?

Prellen? Keine Probleme. Ich habe genau diese Auswertungsmethode auf
anderen Controllern (z.B. 80C535) seit Jahren laufen, ohne jegliche
Probleme. Wüßte auch garnicht, warum die optische Abtastung prellen
sollte. Ich steige nur nicht dahinter, warum sich der Zähler so seltsam
verhält, auch der Assemblercode scheint mir in Ordnung.
Vor allem muss da etwas ganz und gar schief gehen, wenn die
Reset-Routine ausgelöst wird.

von Jörg W. (dl8dtl) (Moderator) Benutzerseite


Lesenswert?

Die optische Abtastung (dass du eine solche hast, schrobst du oben
nicht -- die Mehrzahl dieser Teile hat wohl eher nur mechanische
Kontakte) kann zwar nicht wirklich prellen, aber sie kann auch ,,auf
der Kippe'' stehen.  Je nachdem, wie schnell du mit der Auswertung
bist, kann dir dann der Wert auch einseitig weglaufen (wenn du
vielleicht immer einen Übergang aus vieren verpasst).  Das ist in
de.sci.electronics schon ausführlich diskutiert worden.

von Thomas K. (thkais)


Lesenswert?

Ne,ne, da läuft nix weg.
Selbst wenn eine de Lichtschranken auf Kippe stehen würde, würde der
Zähler im ungünstigsten Fall nur hin- und herzählen (um eine Stelle),
weil die andere Lichtschranke sicher auf einem Pegel steht.
Positioniergenauigkeit ist auch kein Thema, weils als Poti-Ersatz
verwendet wird.
Ich sehe das Problem nicht in der Hardware, die funktioniert genauso in
fünf weiteren Anwendungen, nur dass ein 80C535 anstelle Atmel verbaut
ist. Die Abfrage habe ich bei dem 80C535 auch per Flanken-Interrupt
gelöst.

von Peter Dannegger (Gast)


Lesenswert?

"bekomme ich beim Übergang 0x3F
-> 0x40 einen Reset. Von 0x00 - 0x3F zählts wunderbar."


Nun, dann hast Du ja auch ausmaskiert, muß also so sein.

Hast Du denn die restlichen LEDs an PORTD angeschlossen ?


Peter

von thkais (Gast)


Lesenswert?

@Peter: Natürlich habe ich die ausmaskiert, sonst würde ich den Rest des
PortD ja auch ändern. Das mit den angeschlossenen LEDs meinst Du aber
nicht ernst, oder ;)

Rückwärts zählt der Zähler. *Alle 8 LEDs* werden binär durchgezählt,
wie man es erwarten würde, also alle Werte 0xFF....0x00 und dann wieder
0xFF...etc. Habe ich in meinem Eingangsposting aber schon geschrieben
;)

Nur vorwärts nicht, da bekomme ich bei 0x3F->0x40 einen Reset, d.h.
der Controller führt die Init-Routine aus, aber ich weiss nicht,
warum.

Alles sehr seltsam, da ist garantiert in einer ganz anderen Ecke etwas
faul.

von Peter Dannegger (Gast)


Lesenswert?

"Das mit den angeschlossenen LEDs meinst Du aber
nicht ernst, oder ;)"


Doch, das meinte ich ganz ernst.

Die Interrupts haben ja nirgends ein 0x3F im Code.

Die einzige Stelle, wo die ominösen 0x3F auftreten, ist ja in der
Mainloop zur Ausgabe.

Sind Pins kurzgeschlossen oder hast Du keine Abblock-Cs oder ist Deine
VCC zu lasch oder schwingt was oder sind die Pullups zu groß oder Reset
floated, läuft der Quarz ordentlich ?
Die üblichen Verdächtigen also.


Peter

von thkais (Thomas Kaiser) (Gast)


Lesenswert?

VCC, Stützkondensatoren etc. alles da, wo es hingehört. Ich mache das
auch nicht zum ersten Mal ;)
Wenn die LEDs nicht angeschlossen wären, hätte ich das beim
Rückwärtszählen ja bereits bemerkt.

Ich habs gefunden. Ich mags ja garnicht schreiben, so trivial ist
es...
Es war das ISP-Kabel. Frag mich keiner warum und wie das geht, aber
wenn ich es abziehe,klappts. Ich war eigentlich der Überzeugung, dass
der 74xx244 im parallel-Kabel auf Tristate schaltet. Vielleicht auch
irgendein übersprechen im Programmierkabel (das ansonsten perfekt
funktioniert). Ich ziehe das Kabel seit Jahren eigentlich nie ab, und
hatte noch nie ein solch seltsames Verhalten, auch nicht bei anderen
Anwendungen, die PortB als Ausgang benutzten.
Warum der Zähler rückwärts, aber nicht vorwärts funktionierte, erklärt
das aber immer noch nicht. Es kommen ja die gleichen Bitmuster vor, nur
eben in umgekehrter Reihenfolge.

von Peter Dannegger (Gast)


Lesenswert?

Wenn viele Ausgänge gleichzeitig auf low schalten, gibt das einen
schönen Impuls, der auf die floatende und lange Resetleitung koppeln
kann.

Der Reset sollte daher nicht auf tristate sondern auf strong high
geschaltet werden bzw. einen möglichst kleinen Pullup haben.

Manche Programmiersoftware ist auch so clever, den Resetpuls schön lang
zu machen, damit selbst ein 10µF am Reset nicht stört.

Der oft zu sehende 47pF am Reset ist nonsens.


Peter

von thkais (Thomas Kaiser) (Gast)


Lesenswert?

Das ist eine einleuchtende Erklärung, hätte ich auch selbst drauf kommen
müssen. Aber manchmal sieht man den Wald vor lauter Bäumen nicht.

Danke an alle fürs mitsuchen !

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.