Forum: Mikrocontroller und Digitale Elektronik Arduino - Serielle Schnittstelle


von Hans (Gast)


Lesenswert?

Hi,
ich habe mal wieder eine Frage.
Ich habe an sich folgendes Problem:
Ich habe mir ein Menü gebastelt für den SerialMonitor in der ich 
verschiedene Kommandos senden kann.
Wird ein richtiges Kommando erkannt, wird die dazugehörige Funktion 
aufgerufen.
Die eingegebenen Daten empfange ich im Moment mir der SerialEvent() 
Funktion, weil ich dachte, dass dies eine Interrupt-Funktion ist.
Jetzt habe ich aber gelesen, dass diese Funktion immer erst nach einem 
loop()-Durchlauf aufgerufen wird, also keine richtige Interrupt-Funktion 
ist.
Wenn ich mich jetzt innerhalb einer Funktion befinde und warte dort auf 
ein Signal, kann ich ja dann diese Funktion nicht verwenden.
Gibt es eine andere "wirkliche" Interrupt-Funktion die ich verwenden 
kann?

Oder gibt es eine verbesserte Bibliothek für die serielle Schnittstelle, 
mit mehr Möglichkeiten?

Viele Grüße

Hans

von Karl H. (kbuchegg)


Lesenswert?

Hans schrieb:

> Wenn ich mich jetzt innerhalb einer Funktion befinde und warte dort auf
> ein Signal

dann warte halt einfach nicht.
Das Arduino-System ist so ausgelegt, dass loop() aufgerufen wird, sich 
kurz die vorliegende Situation ansieht, eventuell davon abhängige 
Entscheidungen trifft und dann kehrt loop() wieder zu Aufrufer zurück.

Wenn du das anders machst, und in der loop() exzessiv wartest, dann 
betreibst du einen Missbrauch des Arduino Systems. Logisch blockierst du 
dann alles. Spiele nach den Regeln, dann kannst du dich auf die Dinge 
verlassen, die dir vom System zugestanden werden. Das ist überall im 
Leben so, Computer zu programmieren macht da keine Ausnahme.

von Markus U. (markjus) Benutzerseite


Lesenswert?

Ja, man kann auch einen seriellen Interrupt am ATMEGA328 auslösen. Ist 
aber nicht mehr ganz so trivial wie Serial.read() oder Serial.Event().

Ich hatte zu der USART Schnittstelle ATMEGA/ ADC-Schnittstelle vor 
kurzem eine Präsentation in unserem Makerspace Attraktor und die 
Powerpoint-Folien findest Du unter dem Link unten. Vielleicht hilft das 
weiter. Da sind auch Beispiele, wie man die USART-Register setzt etc. 
(ab Seite 19). Interrupts kann man mit den entsprechenden Registern auch 
auslösen (steht im ATMEGA-Datenblatt sehr genau erklärt).

http://lookmanowire.blogspot.de/2013/06/arduino-basics-part-2-presentation-on.html

Markus

von Hans (Gast)


Lesenswert?

Karl Heinz Buchegger schrieb:
> Hans schrieb:
>
>> Wenn ich mich jetzt innerhalb einer Funktion befinde und warte dort auf
>> ein Signal
>
> dann warte halt einfach nicht.
> Das Arduino-System ist so ausgelegt, dass loop() aufgerufen wird, sich
> kurz die vorliegende Situation ansieht, eventuell davon abhängige
> Entscheidungen trifft und dann kehrt loop() wieder zu Aufrufer zurück.
>
> Wenn du das anders machst, und in der loop() exzessiv wartest, dann
> betreibst du einen Missbrauch des Arduino Systems. Logisch blockierst du
> dann alles. Spiele nach den Regeln, dann kannst du dich auf die Dinge
> verlassen, die dir vom System zugestanden werden. Das ist überall im
> Leben so, Computer zu programmieren macht da keine Ausnahme.


Ok wie würde man es denn dann konform zu der Idee hinter Arduino machen?
Also es soll quasi so aussehen:
Ich habe bestimme Befehle die ich über die Serielle Schnittstelle senden 
kann. (z.B. CONFIG, READ ....)
Mit READ werden Daten von einem Sensor gelesen
Mit CONFIG werden bestimmte Einstellungen abgefragt (also werde ich nach 
der Eingabe von CONFIG in eine Art Untermenü weitergeleitet in der die 
Einstellungen abgefragt werden z.B. Offset usw.)
Diese Einstellungen werden dann auch per SerialMonitor gesendet und nach 
kompletter Eingabe der Einstellungen gelangt der Benutzer zurück zum 
Hauptfenster.

Im Moment habe ich das wie gesagt so gelöst, dass wenn ich CONFIG 
eingegeben habe, eine Funktion aufgerufen wird, in der eben die 
Einstellungen abgefragt werden sollen.
Dies geht jetzt aber nicht mit der SerialEvent() Funktion und eine neue 
Funktion zum Empfangen zu schreiben ist ja auch nicht im Sinne des 
Erfinders.

Viele Grüße

von Karl H. (kbuchegg)


Lesenswert?

Hier ist doch ein schönes Beispiel dafür, wie man mit SerialEvent 
arbeitet
http://arduino.cc/en/Tutorial/SerialEvent

> Im Moment habe ich das wie gesagt so gelöst, dass wenn ich CONFIG
> eingegeben habe, eine Funktion aufgerufen wird, in der eben die
> Einstellungen abgefragt werden sollen.

Was heist: 'Die Einstellungen abgefragt'

Du sitzt vor dem Terminal und tippst:
CONFIG BAUD 4500<Return>

Über SerialEvent werden die Zeichen gesammelt und wenn du Return 
drückst, geht stringComplete auf true und als Folge davon wird in loop 
dann die Eingabezeile ausgewertet.

Das ist das Grundprinzip. Wie das dann in dein Programm passt, kann ich 
nicht sagen, ohne zu wissen was du eigentlich genau machen willst. Aber 
ich könnte mir vorstellen, dass so etwas wie das Konzept einer 
Statemachine (diesmal eben um Benutzerinteraktion zu regeln) dein 
Problem lösen würde, das es eine Art Dialog zwischen Programm und 
Benutzer gibt.

von Hans (Gast)


Lesenswert?

Also es sieht so aus:
der User tippt z.B. CONFIG über die Konsole ein.
dann erscheint "Adresse eingeben". Dann muss das Programm quasi warten 
bis eine Eingabe kam (ob korrekt erstmal egal).
Dann werden weitere Paramter abgefragt z.b. "Offset eingeben" etc.

Also wenn ich dich dann richtig verstanden habe, funktioniert das nur 
gut, wenn ich eine riesige Statemachine in  der loop() generiere.

Das wäre dann z.b. so
state 0: keine eingabe - warten auf Befehl
state 1: READ Befehl - senden der daten
state 2: CONFIG Befehl
state 3: Adresse eingeben
state 4: Offset eingeben
...

Und wenn quasi der CONFIG Befehl eingeben wurde gehe ich in state 3.
wenn dann was eingeben wurde in state 4.
wenn die Eingaben für die CONFIG fertig sind wieder in state 0.

Habe ich das so richtig verstanden?
Was halt unschön ist, dass ich immer wieder abfragen muss, ob dann schon 
z.B. die Aufforderung "Adresse eingeben" gesendet wurde, da die ja nicht 
die ganze Zeit gesendet werden muss, bis der User eine Adresse eingibt.

von state (Gast)


Lesenswert?

Das ist der Unterschied zwischen "Kennen einer Programmiersprache" und 
"Programmieren"! :-P

Du versteckst die ganzen "unschönen" Sachen in die "State Machine". 
Diese verwaltet die ganzen Zustände und weiss auch wann und wie die 
Zustände geändert werden müssen. Die Definition und Implementierung ist 
nicht Trivial.

Da wirst du dich schlau machen müssen. Es gibt genug Literatur darüber.

Hier kannst Du ja mal anfangen: 
http://de.wikipedia.org/wiki/Endlicher_Automat

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.