[Erledigt] Interrupt und GPIO in C

Begonnen von Per, 28 Juli 2017, 11:28:36

Vorheriges Thema - Nächstes Thema

Per

Hat einer mal ein einfaches Beispiel für die Programmierung eines Interrupts für einen GPIO in C (Arduino IDE)?
Ich finde immer nur global galaktische Sachen, die einen Anfänger nicht weiterhelfen oder so kompliziertes Zeug, was einem Anfänger auch nicht weiterhilft :D.

Beta-User

Server: HP-elitedesk@Debian 12, aktuelles FHEM@ConfigDB | CUL_HM (VCCU) | MQTT2: ZigBee2mqtt, MiLight@ESP-GW, BT@OpenMQTTGw | ZWave | SIGNALduino | MapleCUN | RHASSPY
svn: u.a Weekday-&RandomTimer, Twilight,  div. attrTemplate-files, MySensors

Per

#2
Habe inzwischen das gefunden, das verstehe sogar ich ;).
Trotzdem danke, jetzt kann ich sogar dein Beispiel nachvollziehen. ;D

bugster_de

nur meine 5 cents zum Thema:
das Beispiel zeigt zwar schön einfach, wie man einen Interrupt Handler installiert, so dass der dann auch ausgeführt wird.
Es zeigt aber auch schön auf, was man unter dem Stichwort Interrupt sicheres Programmieren nicht verstehen sollte: die gleiche Variable wird sowohl im ISR als auch im Main loop verändert. Im Beispiel zwar unkritisch, da nur Plus und Minus aber wenn es mal komplexer wird, dann kann das schnell schief gehen.

Bsp.

int a = 16;
int b = 4;
int c;

void ISR_function() {
  b =0;
}

void loop( void ) {
  if( b != 0 ) {
    c= a / b;
  }
}


Ich hoffe ihr seht das Problem? Nein?
Wenn der Interrupt zwischen dem if( b != 0 ) und dem c = a / b kommt, dann ist auf einmal b doch gleich 0. Sowas zu debuggen ist echt eklig.

Besser:
void loop( void ) {
  int a_buf;
  int b_buf;
  no_isr();
  a_buf = a;
  b_buf = b;
  allow_isr();
if( b_buf != 0 ) {
    c= a_buf / b_buf;
  }
}


Kann man beliebig weiter spinnen, aber ISR immer daran denken, was passieren kann, wenn der ISR zu jedem belibigen Zeitpunkt käme.

justme1968

noch eine anmerkung: variablen die in einem interupt handler verändert werden sollte man immer volatile deklarieren. sonst pfuscht einem die optimierung unter umständen dazwischen da der compiler nicht weiß das die variable außerhalb des programmflusses geändert wird.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

Per

Danke für diese Tipps, wer nicht ständig Multitreading programmiert, denkt an sowas nicht unbedingt.

Per

Gleich noch ne Frage: ich will einen Webserver machen, dessen Inhalt von den Interrupts geändert wird.
Das Hauptprogramm würde dann gar nix machen. Wie sieht das dann aus?
void loop() {
delay(10000);
}

?

nils_

Zitat von: Per am 28 Juli 2017, 16:31:23
Danke für diese Tipps, wer nicht ständig Multitreading programmiert, denkt an sowas nicht unbedingt.
das ist wieder aber was anderes....

Zitat von: Per am 29 Juli 2017, 21:28:54
Gleich noch ne Frage: ich will einen Webserver machen, dessen Inhalt von den Interrupts geändert wird.
Das Hauptprogramm würde dann gar nix machen. Wie sieht das dann aus?
void loop() {
delay(10000);
}

?
d.h. du hast nur die interrupte laufen....?
und wer liefert dann die daten deines webservers aus? da kommt ja von außen noch ne anfrage, die muss bearbeitet werden. (ethernet?? auch wieder interrupte und/oder threads....)
viele Wege in FHEM es gibt!

Per

Zitat von: nils_ am 31 Juli 2017, 12:13:35und wer liefert dann die daten deines webservers aus? da kommt ja von außen noch ne anfrage, die muss bearbeitet werden. (ethernet?? auch wieder interrupte und/oder threads....)
Ich gehe von Threads aus, das Web-Server-Modul ist ja schon fertig und relativ unabhängig von meinem Code. Darauf wird auch nur (serverseitig) zugegriffen, wenn es eine Änderung im Inhalt gibt. Greift ein Client von außen über das (W)Lan zu, sehe ich das nicht, das verwaltet alles das Web-Server-Modul.

nils_

ach so.

ich dachte du wolltest alles selbst programmieren  ::)
viele Wege in FHEM es gibt!

Per

Häh? Ich bin froh, wenn ich es zusammenkopiert bekomme!