Forum: Mikrocontroller und Digitale Elektronik Arduino ohne delay und millis


von Ardu Ino (Gast)


Lesenswert?

Hallo

um Timerfunktionen z.b für ein Blinken, in der Arduino Umgebung 
(Software) zu nutzen gibt es die delay Funktion, mit allen ihren 
Problemen wenn das Programm ein wenig mehr machen soll.
Das ist selbst den Arduinoentwicklern klar und deshalb gibt es auch eine 
Funktion millis, auf die ich aber auch gerne verzichten würde.
Wieso, weshalb, warum steht nicht zu Diskussion, und zwar bezüglich 
meines Wunsch auf Verzicht als auch (!) warum ich die Arduino 
Entwicklungsumgebung nutze obwohl ich teilweise Hardware nah arbeiten 
möchte - Glaubenskrieger und Missionare können sich woanders austoben 
-Danke.

Jetzt findet Google zwar 1001 Tutorials zu "Arduino without delay" aber 
bei "Arduino without delay and millis" und Ähnliches erhalte ich keine 
brauchbaren Treffer sondern letztendlich die gleichen Tutorials, Fragen, 
Hinweise... wie bei der reinen "... without delay..." Suche.
Deutschsprachige Suche bringt eher noch weniger.

Ich möchte aber in der Arduinoumgebung (und nicht in reinen C, 
Assembler...)  Hardwarenah den ATMega328 bezüglich den Timer (sowohl 
"Timer" in der Bedeutung beim µC als auch wie sie im Allgemeinen 
Sprachgebrauch verwendet wird)verstehen und nutzen.

Dafür gibt es doch mit hoher Wahrscheinlichkeit schon Tutorials - nur 
ich finde diese nicht da die gefühlt Millionen Tutorials zum Ersatz der 
Delay Funktion das Auffinden unmöglich machen.

Wer kann helfen (Link, genialer Suchbegriff, eigene Worte...)?

Ardu Ino

von Kirsch (Gast)


Lesenswert?

Wie ist denn die Blink-Frequenz?

Im Idealfall gibt es in der Loop() kein einzigen Aufruf der eine 
Wartezeit verursacht.

Sodas die Loop() mit einer sehr hohen Frequenz durchlaufen ist.

Um ein Blinken ohne Nutzung einer Delay-Funktion zu erzeugen, muss du in 
der Loop die vergangene Zeit messen.
Ist die gewünschte Zeit (z.B. 0,5 Sekunden) abgelaufen, schaltest du den 
Ausgang um und startest eine neue Zeitmessung, so bekommst du eine 
Blinkfrequenz von z.B. 1Hz

von Mick (Gast)


Lesenswert?

Evtl. ist das hier für dich interessant: 
http://forum.arduino.cc/index.php?topic=403637.0

von g457 (Gast)


Lesenswert?

> Wer kann helfen (Link, genialer Suchbegriff, eigene Worte...)?

Suchbegriff: "pferd von hinten aufzäumen". Verabschiede Dich von der 
Arduinolaufzeitarchitektur oder von genauen Timings. In ersterem Falle: 
Herzlichen Glückwunsch, als nächstes bitte das Datenplatt zum 
Mikrocontroller lesen und verstehen.

von Wolfgang (Gast)


Lesenswert?

Ardu Ino schrieb:
> ... obwohl ich teilweise Hardware nah arbeiten möchte

Es hindert dich keiner daran, eigene Funktionen für hardwarenahen 
Anwendungen zu verwenden.

> ... und deshalb gibt es auch eine Funktion millis, auf die ich
> aber auch gerne verzichten würde.

Selber schuld - warum?

> -Danke.

Bitte

Ardu Ino schrieb:
> Wer kann helfen (Link, genialer Suchbegriff, eigene Worte...)?

Geniale Suchbegriffe wären z.B. "Timer" und "Interrupt".
Wenn du dem Timer-Interrupt, der hinter millis() steht, nicht traust, 
setze doch einen eigenen Timer auf. Die Registerbezeichnungen stehen im 
Datenblatt und sind auch in der Arduino IDE verfügbar.

Wenn du das nicht kannst/möchtest nutze die Arduino Umgebnung oder lese 
dir   Grundlagen an, z.B.
https://www.robotshop.com/letsmakerobots/arduino-101-timers-and-interrupts

Wasch mir den Pelz, aber mach mich nicht nass funktioniert hier nicht, 
wenn Copy&Paste schon an elementaren Suchbegriffen scheitert

von Auch Duino (Gast)


Lesenswert?

Ardu Ino schrieb:
> Ich möchte aber in der Arduinoumgebung (und nicht in reinen C,
> Assembler...)  Hardwarenah den ATMega328 bezüglich den Timer (sowohl
> "Timer" in der Bedeutung beim µC als auch wie sie im Allgemeinen
> Sprachgebrauch verwendet wird)verstehen und nutzen.

Schreibe deine Funktion

int main (void)
{
.....
}

in deiner Arduino IDE und vermeide die Implementierungen

Setup();

und

Loop();

Damit bist du Herr über alles ohne auch nur eine Mikrosekunde
deines Controllers hergeschenkt zu haben. Und alle Hardware,
auch die Timer, ist/sind frei verfügbar.

von Dieter F. (Gast)


Lesenswert?

Ardu Ino schrieb:
> Ich möchte aber in der Arduinoumgebung (und nicht in reinen C,
> Assembler...)  Hardwarenah den ATMega328 bezüglich den Timer (sowohl
> "Timer" in der Bedeutung beim µC als auch wie sie im Allgemeinen
> Sprachgebrauch verwendet wird)verstehen und nutzen.

Schon mal drüber nachgedacht, das Datenblatt zu studieren? Da steht 
alles drin, was man so wissen muss.

von Michael U. (amiga)


Lesenswert?

Hallo,

auch in der Arduino-IDE niemand hindert Dich niemand eigene 
Timerinterrups einzubauen.

https://github.com/esp8266/Arduino/blob/master/libraries/Ticker/Ticker.h
ist möglicher Weg.

Das stammt aus einer Scrollroutine eines meiner Displays:
1
#include <Ticker.h>       // Bibliothek einbinden
2
3
Ticker scroll_display;    // Instanz anmelden 
4
5
int scrollpos = 0;        // aktuelle Scrollposition
6
int scrolltime  = 250;    // Zeit in ms zwischen den Scrollschritten
7
8
9
void scrollen()           // Scrollroutine die vom Ticker-Interrupt aufgerufen wird 
10
{
11
  scrollpos++;
12
  if (disp_buf[scrollpos] == 0)                    // Stringende   
13
  {
14
    scrollpos = 0;
15
  }
16
17
  int aktpos = scrollpos;
18
  
19
  for (int i = 0; i < 16; i++)
20
  {
21
    if (disp_buf[aktpos] == 0)                    // Stringende   
22
    {
23
      aktpos = 0;                                 // von vorne      
24
    }
25
    displayWriteChar(i, disp_buf[aktpos]);
26
    aktpos++;
27
  }
28
}

Im loop dann eben mit
  scroll_display.attach_ms(scrolltime, scrollen);

und mit
  scroll_display.detach();
ausschalten.

Gruß aus Berlin
Michael

von PittyJ (Gast)


Lesenswert?

Ich verstehe das Problem nicht. Warum sollte auf millis() verzichtet 
werden? Das ist doch einfach zu benutzen und man kann überprüfen ob eine 
Zeit schon abgelaufen ist.

Was ist das Problem mit millis() ?

von Stefan F. (Gast)


Lesenswert?

> Was ist das Problem mit millis() ?

Verstehe ich auch nicht. Jedes PC Betriebssystem hat das, jedes 
Smartphone und ARM Kerne haben dazu sogar einen extra Timer integriert.

Wie willst du sonst Zeiten messen? Etwa mit Kondensatoren?

von Falk B. (falk)


Lesenswert?

@Ardu Ino (Gast)

>Jetzt findet Google zwar 1001 Tutorials zu "Arduino without delay" aber
>bei "Arduino without delay and millis" und Ähnliches erhalte ich keine
>brauchbaren Treffer sondern letztendlich die gleichen Tutorials, Fragen,
>Hinweise... wie bei der reinen "... without delay..." Suche.
>Deutschsprachige Suche bringt eher noch weniger.

Dann suchst du falsch.

>Ich möchte aber in der Arduinoumgebung (und nicht in reinen C,
>Assembler...)  Hardwarenah den ATMega328 bezüglich den Timer (sowohl
>"Timer" in der Bedeutung beim µC als auch wie sie im Allgemeinen
>Sprachgebrauch verwendet wird)verstehen und nutzen.

Das ist leicht, denn Arduino ist nicht sooo isoliert wie manche meinen. 
Es ist "nur" eine Sammlung von Bibliotheken, die man nutzen KANNN (und 
meist auch sollte), der Rest des AVRs ist aber genauso verfügbar und 
zugreifbar wie in reinem C ohne Arduino.

>Dafür gibt es doch mit hoher Wahrscheinlichkeit schon Tutorials

Jaja, die ganze Welt als Tutorial. Nerd 2.0

>ich finde diese nicht da die gefühlt Millionen Tutorials zum Ersatz der
>Delay Funktion das Auffinden unmöglich machen.

Ich schon. Siehe Multitasking.

Einen Interrupt kann man beim Arduino genauso leicht nutzen wie ohne.

Beitrag "Re: Arduino Nano, SD Card, PCM"

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

millis() ist genau das, was der TO braucht, unabhängig davon, was er 
will. Den millis() arbeitet ja mit einem Timer und dessen Interrupt.
Ich vermute sehr, der TO weiß nur nicht, wie man diese Funktion am 
besten einsetzt und zyklisch mit Zustandsautomaten programmiert 
(Stichwort Mainloop).
Und deshalb versucht er, seinen Schopf über ein Programm, das direkt im 
Timerinterrupt läuft, aus der Schlinge zu ziehen.
Dass er sich damit ganz andere Probleme an die Backe klebt, weiß er 
allerdings auch nicht (Stichworte Semaphorenproblem und Racecondition).

von Joachim B. (jar)


Lesenswert?

Ardu Ino schrieb:
> Ich möchte aber in der Arduinoumgebung (und nicht in reinen C,
> Assembler...)  Hardwarenah den ATMega328 bezüglich den Timer (sowohl
> "Timer" in der Bedeutung beim µC als auch wie sie im Allgemeinen
> Sprachgebrauch verwendet wird)verstehen und nutzen.

tue es doch

ich kam vom nackten Atmel AVR mit AVR Studio 4.18 zum Arduino, nutze 
eigene C-Module die ich einbinde als *.ino als auch LIBs der Arduinio 
wahlweise nach Bedarf.

Mich stört weder setup(), noch loop() auch nicht millis() oder eigene 
Timerinterrupts, alles kooperiert nach meinen Wunsch und wenn mal nicht 
schaue ich wo ich ändern muss, z.B. mal einen anderen Timer wählen.

von majortom (Gast)


Lesenswert?

zur erhellung ohne delay ...

#ifndef PERIODIC_H
#define PERIODIC_H

//usage:
//  PERIODIC(100) //{
//    digitalWrite(PIN, HIGH/LOW)
//  }

//create an unique name from given parameter and line number
#define UNIQUE(name) __CONCAT(name,__LINE__)

//creates an unique timer for each instance, ms period in milli-seconds
#define WAITBLOCK(ms)                                     \
  static uint32_t UNIQUE(timer) = millis();               \
  if (millis() - UNIQUE(timer) >= ms) {

//creates an unique timer for each instance, ms period in milli-seconds
#define PERIODIC(ms)                                      \
  static uint32_t UNIQUE(timer) = millis();                \
  if (millis() - UNIQUE(timer) >= ms) {                   \
    UNIQUE(timer) = millis();

//XPERIODIC(ms,1) = WAITBLOCK but takes more program code space!
//XPERIODIC(ms,0) = PERIODIC
//creates an unique timer for each instance, x: repeats 0-255, 0=endless
#define XPERIODIC(ms, x)                                  \
  static uint32_t UNIQUE(timer) = millis();               \
  static uint8_t UNIQUE(xRepeats) = x;                    \
  static uint8_t UNIQUE(lock);                            \
  if (millis() - UNIQUE(timer) >= ms) {                   \
    if (!UNIQUE(lock)) {                                  \
      if ((UNIQUE(xRepeats)==0) || (--UNIQUE(xRepeats)))  \
        UNIQUE(timer) = millis();                         \
      else UNIQUE(lock)=1;                                \
    }

#endif //PERIODIC_H

von Falk B. (falk)


Angehängte Dateien:

Lesenswert?

@Lothar Miller (lkmiller) (Moderator) Benutzerseite

>millis() ist genau das, was der TO braucht,

Nein, denn diese Funktion liefert nur einen Timerwert, welche in einem 
1ms Timer-Interrupt hochgezählt wird. Die nützt rein gar nichts, wenn 
andere Funktionen, warum auch immer, den Programmablauf längere Zeit 
"blockieren".

> unabhängig davon, was er
>will. Den millis() arbeitet ja mit einem Timer und dessen Interrupt.

Dort kommt man aber so direkt nicht ran, sprich, man kann sich NICHT in 
den 1ms Timer einklinken! Dazu müßte es eine Funktion geben, die der 
Anwender erstellen kann, welche dann vom Arduino-Framework im 1ms 
Interrupt aufgerufen wird. So etwas gibt es nicht, u.a. weil es dem 
Konzept der Vereinfachung deutlich widerspricht.

>Ich vermute sehr, der TO weiß nur nicht, wie man diese Funktion am
>besten einsetzt und zyklisch mit Zustandsautomaten programmiert
>(Stichwort Mainloop).

Das ist nur ein Würg-Around mit begrenzter Leistung. Siehe oben.

>Und deshalb versucht er, seinen Schopf über ein Programm, das direkt im
>Timerinterrupt läuft, aus der Schlinge zu ziehen.

Genau DAS ist aber die Lösung der allermeisten Probleme dieser Art!
Außerdem hat der OP ganz sicher sehr wenig Plan von AVRs und Interrupts, 
denn ich wette 1 Kasten Bier, daß er für seine Drehgeberauswertung die 
rudimentäre Interrupt-Funktionalität des Arduinos nutzt.

https://www.arduino.cc/reference/en/language/functions/external-interrupts/attachinterrupt/

>Dass er sich damit ganz andere Probleme an die Backe klebt, weiß er
>allerdings auch nicht (Stichworte Semaphorenproblem und Racecondition).

Jaja, und schon wieder sind am Sonntag Morgen die Reichsbdenkenträger 
voll dabei, die Welt zur retten. ODer zumindest viel Staub aufzuwirblen! 
:-(

Siehe Anhang!!!

von Falk B. (falk)


Lesenswert?

@majortom (Gast)

>zur erhellung ohne delay ...

Du hast eine merkwürdige Vorstellung von "Erhellung".

von Stefan F. (Gast)


Lesenswert?

>> millis() ist genau das, was der TO braucht,

> Nein, denn diese Funktion liefert nur einen Timerwert, welche in einem
> 1ms Timer-Interrupt hochgezählt wird. Die nützt rein gar nichts, wenn
> andere Funktionen, warum auch immer, den Programmablauf längere Zeit
> "blockieren".


Die millis() Funktion ist ideal, um innerhalb eines Zustandsautomaten 
Aktionen zu einem bestimmten Zeitpunkt auszuführen. Das Abwarten einer 
Zeitspanne zählt auch dazu.

> wenn andere Funktionen... den Programmablauf längere Zeit "blockieren".

Das ist in vernünftigen Multi-Task fähigen Anwendungen ohnehin nicht 
zulässig. Größere Aktionen müssen ggf. in kleinere zerlegt werden.

Zustandsautomaten ist das Stichwort zum lernen, sobald man die Grenzen 
von delay() und anderen blockierenden Aktionen erkannt hat.

von Falk B. (falk)


Lesenswert?

@Stefan Us (stefanus)

>>> millis() ist genau das, was der TO braucht,

>> Nein, denn diese Funktion liefert nur einen Timerwert, welche in einem
>> 1ms Timer-Interrupt hochgezählt wird. Die nützt rein gar nichts, wenn
>> andere Funktionen, warum auch immer, den Programmablauf längere Zeit
>> "blockieren".


>Die millis() Funktion ist ideal, um innerhalb eines Zustandsautomaten
>Aktionen zu einem bestimmten Zeitpunkt auszuführen. Das Abwarten einer
>Zeitspanne zählt auch dazu.

FALSCH! Auch du hast das Problem NICHT verstanden!

>> wenn andere Funktionen... den Programmablauf längere Zeit "blockieren".

>Das ist in vernünftigen Multi-Task fähigen Anwendungen ohnehin nicht
>zulässig. Größere Aktionen müssen ggf. in kleinere zerlegt werden.

Jaja, soweit die Theorie. Dumm nur, daß das selbt für Profis bisweilen 
nicht möglich ist, weil bestimmte Funktionen bzw. Bibliotheksfunktionen 
schlicht länger dauern und nicht teilbar sind.

Hier geht es um das gleiche Problem. Und besonders dort ist millis() 
fehl am Platz. Der schelle, zeitkritische Kram gehört in die Timer-ISR, 
der langsame LCD-Kram in die Hauptschleife.

Beitrag ""Interrupt" durch Vergleich von Variablen möglich? Timingprobleme durch zu lange Programmlaufzeit"

>Zustandsautomaten ist das Stichwort zum lernen, sobald man die Grenzen
>von delay() und anderen blockierenden Aktionen erkannt hat.

Eben dafür braucht es KEINE gottverdammte millis() Funktion, die nur ein 
Arduino-Würg-Around ist! Denn in den allermeisten Fällen will man 
diverse State Machines mit einer definierten, konstanten Frequenz 
aufrufen, damit ergibt sich das Timing von allein und diverse 
Verzögerungen werden in den FSMs per Zustand und Zähler gemacht. Un komm 
mir jetzt nicht mit der 101 Ausnahme, welche die Regel bestätigt!

von Stefan F. (Gast)


Lesenswert?

> millis() Funktion, die nur ein Arduino-Würg-Around ist!

Dann schau Dir mal Java an, oder Windows, oder Linux, oder Android, oder 
ARM Kerne. Die haben alle einen Millisekunden-Zähler mit mehr oder 
weniger ähnlichem Namen.

> weil bestimmte Funktionen bzw. Bibliotheksfunktionen
> schlicht länger dauern und nicht teilbar sind

Diese Funktionen würde ich als Designfehler bezeichnen. Mit einem OS das 
aktiv Threads unterbricht könnte man sie verwenden, aber auf µC wären 
sie fehl am Platz.

Blockierende Warteschleifen dürfen meiner Meinung nach nur wenige Nano-
 bis Mikrosekunden dauern.

von Falk B. (falk)


Lesenswert?

@ Stefan Us (stefanus)

>> millis() Funktion, die nur ein Arduino-Würg-Around ist!

>Dann schau Dir mal Java an, oder Windows, oder Linux, oder Android, oder
>ARM Kerne. Die haben alle einen Millisekunden-Zähler mit mehr oder
>weniger ähnlichem Namen.

Du Nase! Wer hat denn die Existenz dieser Sache abgestritten?
Es ging um die Frage, wie man sinnvoller, bzw. optimalerweise ein 
minimales Multitasking auf einem uC gestaltet. Und schau dir mal 
diverse Java-Anwendungen an, dann weißt du, warum die Mist sind 
(Performance, was ist das?) Ob das an den schlechten Konzepten der 
mittelmäßigen Programmierer und dernen millis() Funktion liegt?

von Falk B. (falk)


Lesenswert?

@Stefan Us (stefanus)

>
>> weil bestimmte Funktionen bzw. Bibliotheksfunktionen
>> schlicht länger dauern und nicht teilbar sind

>Diese Funktionen würde ich als Designfehler bezeichnen. Mit einem OS das
>aktiv Threads unterbricht könnte man sie verwenden, aber auf µC wären
>sie fehl am Platz.

Schon wieder Unsinn. Heute nicht dein Tag, oder?

Beispiel. Das VORZÜGLICHE FATfs vom Meister Elm Chan aus dem fernen 
Osten hat diverse Funktion, die halt mal länger und mal kürzer dauern. 
Willst du daraus schließen, daß dFATfs Mist ist? NEIN! Denn wenn man 
damit was performantes auf die Beine stellen will, muss man halt "nur" 
wissen wie das geht. Mein schon mehrfach zitierter DMX Rekorder macht 
das mit 22kB/s. Totz daß diverse FATfs Funktionen eher Millisekunden 
brauchen.

von Stefan F. (Gast)


Lesenswert?

Wie kann denn etwas ein Arduino-Würg-Around sein, was in praktisch allen 
anderen Programmiersprachen und Betriebssystemen ebenso vorhanden ist?

> in den allermeisten Fällen will man diverse State Machines
> mit einer definierten, konstanten Frequenz aufrufen

Ich kenne das als eine mögliche Lösung.

Ich habe aber schon wesentlich mehr State Machines gesehen, deren 
hauptschleife einfach nur schnellstmöglich ausgeführt wird. Unter 
anderem in Arduino, µC Projekte die auf LwIp und µIP basieren (somit 
auch ESP8266), fast alle meine eigenen µC Projekte, zahlreiche Windows 
Programme, die Event-Loop vom QT Framework, ...

Vielleicht beginnst du mal zu akzeptieren, dass viele Wege zum Ziel 
führen und deiner nicht der einzig richtige ist.

von Einer K. (Gast)


Lesenswert?

In Sachen millis() und delay(), bin ich schon fast eine Fachkraft.
Zumindest eine eingewiesene Person, mit fundiertem Halbwissen.


Die Hierarchie des ArduinoZeitHändlings:

Einfache Dinge ruhig mit delay().
Solange, bis es einem auf die Füße fällt....

Dann das BlinkWithoutDelay Konzept anwenden.
Damit kann man eigentlich alles erschlagen.
Ja, wenn es einen nicht stört, dass dauernd millis() aufgerufen und 
verglichen wird.


Wird dann schlußendlich ein exaktes Timing gebraucht, kann man  ja noch 
immer die HardwareTimer zur Hilfe nehmen. Ein UNO hat 3 davon, wobei 
Timer0 vom Core belegt wird.
Da ist man dann an dem Punkt, wo es ohne Datenblatt nicht weiter geht.


----

Auch gibt es die Chance den Arduino Core abzuändern.
In dessen Timer0 ISR eine Weak Funktion rein zu klemmen ist eine 
Kleinigkeit von 3 oder 4 Zeilen.
Dieser Interrupt kommt alle, ca. 1ms. Er ist nicht ganz exakt. Damit 
millis() korrekt läuft wird da im Core noch rumkorrigiert.

von Thomas E. (thomase)


Lesenswert?

Arduino F. schrieb:
> Dieser Interrupt kommt alle, ca. 1ms. Er ist nicht ganz exakt. Damit
> millis() korrekt läuft wird da im Core noch rumkorrigiert.

Warum? 16MHz:1KHz geht doch im CTC-Mode glatt auf. Oder benutzen sie den 
Timer als Atmega8-Gedächtnis-Timer nur im OVF?

von chris (Gast)


Lesenswert?


von Einer K. (Gast)


Lesenswert?

Ich kann mich nicht für die Jungs und Mädels rechtfertigen....
Das lohnt nicht.


Der Timer wird auch für PWM genutzt.
Und er hat eben nur 8 Bit.

Vielleicht fehlte da einfach der Hut, um da beides drunter zu bekommen.

https://www.arduino.cc/en/Tutorial/SecretsOfArduinoPWM
https://playground.arduino.cc/Main/TimerPWMCheatsheet

von chris (Gast)


Lesenswert?

Ich kopier's mal raus:
1
// the prescaler is set so that timer0 ticks every 64 clock cycles, and the
2
// the overflow handler is called every 256 ticks.
3
#define MICROSECONDS_PER_TIMER0_OVERFLOW (clockCyclesToMicroseconds(64 * 256))
4
5
// the whole number of milliseconds per timer0 overflow
6
#define MILLIS_INC (MICROSECONDS_PER_TIMER0_OVERFLOW / 1000)
7
8
// the fractional number of milliseconds per timer0 overflow. we shift right
9
// by three to fit these numbers into a byte. (for the clock speeds we care
10
// about - 8 and 16 MHz - this doesn't lose precision.)
11
#define FRACT_INC ((MICROSECONDS_PER_TIMER0_OVERFLOW % 1000) >> 3)
12
#define FRACT_MAX (1000 >> 3)
13
14
volatile unsigned long timer0_overflow_count = 0;
15
volatile unsigned long timer0_millis = 0;
16
static unsigned char timer0_fract = 0;
17
18
#if defined(__AVR_ATtiny24__) || defined(__AVR_ATtiny44__) || defined(__AVR_ATtiny84__)
19
ISR(TIM0_OVF_vect)
20
#else
21
ISR(TIMER0_OVF_vect)
22
#endif
23
{
24
  // copy these to local variables so they can be stored in registers
25
  // (volatile variables must be read from memory on every access)
26
  unsigned long m = timer0_millis;
27
  unsigned char f = timer0_fract;
28
29
  m += MILLIS_INC;
30
  f += FRACT_INC;
31
  if (f >= FRACT_MAX) {
32
    f -= FRACT_MAX;
33
    m += 1;
34
  }
35
36
  timer0_fract = f;
37
  timer0_millis = m;
38
  timer0_overflow_count++;
39
}
40
41
unsigned long millis()
42
{
43
  unsigned long m;
44
  uint8_t oldSREG = SREG;
45
46
  // disable interrupts while we read timer0_millis or we might get an
47
  // inconsistent value (e.g. in the middle of a write to timer0_millis)
48
  cli();
49
  m = timer0_millis;
50
  SREG = oldSREG;
51
52
  return m;
53
}

Beitrag #5238637 wurde vom Autor gelöscht.
von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Falk B. schrieb:
> @Lothar Miller (lkmiller) (Moderator) Benutzerseite
>> millis() ist genau das, was der TO braucht,
> Nein, denn diese Funktion liefert nur einen Timerwert, welche in einem
> 1ms Timer-Interrupt hochgezählt wird.
Das reicht für übliche zeitliche Abläufe völlig aus.

> Die nützt rein gar nichts, wenn andere Funktionen, warum auch immer,
> den Programmablauf längere Zeit "blockieren".
Dann haben wir das Problem ja schon erkannt: der Programmablauf der 
Hauptschleife darf schlicht und einfach nicht blockiert werden. Das 
wars. Wenn man sich daran hält, dann kann man ganz einfach wartbare und 
erweiterbare und vor allem portierbare Programme schreiben.

Die wichtigste (Überwachungs-)Funktion meiner Hauptschleife ist der 
Abschnitt, wo die minimale, maximale und durchschnittliche Zykluszeit 
berechnet wird. Und wenn ein durch die Anwendung bestimmter Grenzwert 
der maximalen Zykluszeit überschritten wird, dann habe ich gerade eben 
einen Fehler reinprogrammiert.

Merke: der am einfachsten erkennbare Programmierfehler ist ein 
delay_ms().

Falk B. schrieb:
> Das VORZÜGLICHE FATfs vom Meister Elm Chan aus dem fernen Osten hat
> diverse Funktion, die halt mal länger und mal kürzer dauern. Willst du
> daraus schließen, daß dFATfs Mist ist?
Doch. Genau das ist es: wenn es mir wegen irgendwelcher Warterei auf 
irgendwelche Hardware das Timing verhagelt, dann ist das Murks.
Und ich muss dann auf die eine oder andere Art einen Workaroud drumrum 
basteln.

Falk B. schrieb:
>> Dass er sich damit ganz andere Probleme an die Backe klebt, weiß er
>>>allerdings auch nicht (Stichworte Semaphorenproblem und Racecondition).
> Jaja, und schon wieder sind am Sonntag Morgen die Reichsbdenkenträger
> voll dabei, die Welt zur retten. ODer zumindest viel Staub aufzuwirblen!
Falk, du lenkst ab. Hier schlagen doch laufend Anfänger auf, die sich 
wundern, warum ihre volatile Variable, die im Interrupt und im 
Huptprogramm verwendet wird, ab&zu "spinnt".
Und ich kenne einige Fälle, wo Anfänger um genau solche Fälle dann mit 
"Dreifach-Abfragen mit anschließendem Vergleich" übel um genau dieses 
Semaphoren-Problem herumflicken.
Denn das ist nichts, was einem Angst machen soll, sondern man muss es 
einfach wissen um daraus entstehende Probleme zu vermeiden. So wie du es 
weißt und auf diese Art Probleme vermeidest.

Falk B. schrieb:
> Du Nase!
Falk, könntest du bitte die Antworten OHNE solche absolut vollkommen 
unnötigen persönlichen Angriffe und Beleidigungen schreiben? Den Rest 
meiner Antwort spare ich mir!

: Bearbeitet durch Moderator
von Falk B. (falk)


Lesenswert?

@Stefan Us (stefanus)

>Wie kann denn etwas ein Arduino-Würg-Around sein, was in praktisch allen
>anderen Programmiersprachen und Betriebssystemen ebenso vorhanden ist?

Falsch! Du verwechselst die Verfügbarkeit einer Methode mit deren 
optimalem Einsatz.

>> in den allermeisten Fällen will man diverse State Machines
>> mit einer definierten, konstanten Frequenz aufrufen

>Ich kenne das als eine mögliche Lösung.

Na immerhin.

>Ich habe aber schon wesentlich mehr State Machines gesehen, deren
>hauptschleife einfach nur schnellstmöglich ausgeführt wird. Unter
>anderem in Arduino,

WOW! Was für eine Referenz! Vor allem was die Performance angeht!

> µC Projekte die auf LwIp und µIP basieren (somit
>auch ESP8266),

Hmm.

>fast alle meine eigenen µC Projekte,

Naja.

> zahlreiche Windows
>Programme, die Event-Loop vom QT Framework, ...

Sinngemäßes Zitat von Bertrand Russel

"Nur weil eine Meinung von der Mehrheit vertreten wird, ist kein Beweis, 
daß es nicht vollkommener Unsinn ist."

Mein letztes Plädoyer zum Thema.

Man KANN mit einer Funktion ala millis() diverse Statemachine betreiben, 
die ggf. auch nur so schnell wie möglich oder auch langsamer aufgerufen 
werden. Für einige Anwendungen ist das ausreichend.

Manchmal MUSS man es machen, weil es nicht besser geht und ggf. mit den 
daraus folgenden Einschränkungen leben.

ABER!!!!!

Wenn möglich, versucht man bei einer Problemlösung von vorn herein 
erstmal KEINE Kompromisse zu schließen und eine schnelle, 
leistungsfähige Lösung anzustreben. Das bedeutet hier, eine Statemachine 
mittels Timer oder gar ISR im festen Zeitraster aufzurufen, ohne 
sonstige Kompromisse. Und genau DAS will und braucht der OP!!! OK, es 
war der andere Thread, die Diskussion ist aber praktisch die Gleiche, 
weil das grundlegende Problem das Gleiche ist!

Beitrag ""Interrupt" durch Vergleich von Variablen möglich? Timingprobleme durch zu lange Programmlaufzeit"

>Vielleicht beginnst du mal zu akzeptieren, dass viele Wege zum Ziel
>führen und deiner nicht der einzig richtige ist.

Das habe ich nie behauptet. Siehe oben.

von Falk B. (falk)


Lesenswert?

@ Lothar Miller (lkmiller) (Moderator)

>>> millis() ist genau das, was der TO braucht,
>> Nein, denn diese Funktion liefert nur einen Timerwert, welche in einem
>> 1ms Timer-Interrupt hochgezählt wird.
>Das reicht für übliche zeitliche Abläufe völlig aus.

Nö. Definiere mal "übliche zeitliche Abläufe".

>> Die nützt rein gar nichts, wenn andere Funktionen, warum auch immer,
>> den Programmablauf längere Zeit "blockieren".

>Dann haben wir das Problem ja schon erkannt: der Programmablauf der
>Hauptschleife darf schlicht und einfach nicht blockiert werden. Das
>wars. Wenn man sich daran hält, dann kann man ganz einfach wartbare und
>erweiterbare und vor allem portierbare Programme schreiben.

Bla! Auch das ist, wie bereits geschrieben, in einigen Fällen nicht 
möglich, vor allem bei Einsatz von Fremdsoftware oder Bibliotheken.

>> Das VORZÜGLICHE FATfs vom Meister Elm Chan aus dem fernen Osten hat
>> diverse Funktion, die halt mal länger und mal kürzer dauern. Willst du
>> daraus schließen, daß dFATfs Mist ist?

>Doch. Genau das ist es: wenn es mir wegen irgendwelcher Warterei auf
>irgendwelche Hardware das Timing verhagelt, dann ist das Murks.

Pure Arroganz und Ignoranz! Beschäftige dich mal mit der Software, dann 
kannst du ggf. einen fundierten Kommentar abgeben!

>Und ich muss dann auf die eine oder andere Art einen Workaroud drumrum
>basteln.

Jain. Eine vergleichbare Software, die beliebig multitaskingfähig ist, 
braucht entweder ein echtes, prääemtives Multitasking oder einen 
deutlich anderen Softwareansatz. Beides ist ziemlich aufwändig. Der 
Kompromiss der bestehenden Lösung ist IMO optimal.

Natürlich muss man des Öfteren Kompromisse und manchmal auch Workarounds 
machen. Die Frage ist aber, ob man ohne Not gleich damit anfängt. Und 
meine Antwort darauf ist: NEIN!

Falk B. schrieb:
>> Dass er sich damit ganz andere Probleme an die Backe klebt, weiß er
>>>allerdings auch nicht (Stichworte Semaphorenproblem und Racecondition).
> Jaja, und schon wieder sind am Sonntag Morgen die Reichsbdenkenträger
> voll dabei, die Welt zur retten. ODer zumindest viel Staub aufzuwirblen!

>Falk, du lenkst ab. Hier schlagen doch laufend Anfänger auf, die sich
>wundern, warum ihre volatile Variable, die im Interrupt und im
>Huptprogramm verwendet wird, ab&zu "spinnt".

Ja und? Das Problem ist mit einem volatile lösbar. Und die Grundlagen 
dazu sind im Artikel Interrupt zu finden.

>Und ich kenne einige Fälle, wo Anfänger um genau solche Fälle dann mit
>"Dreifach-Abfragen mit anschließendem Vergleich" übel um genau dieses
>Semaphoren-Problem herumflicken.

Auch das ist ein lösbares Problem. millis() macht es nicht wirklich 
besser. Du willst nicht die Stützräder am Fahrrad abschrauben sondern 
bunt anmalen. Das klingt sehr fürsorglich, entmündigt aber nur.

>> Du Nase!
>Falk, könntest du bitte die Antworten OHNE solche absolut vollkommen
>unnötigen persönlichen Angriffe und Beleidigungen schreiben?

Nö, manchmal geht es einfach nicht anders.

> Den Rest meiner Antwort spare ich mir!

Ist auch besser so, moralinsaure Gardinenpredigten sind sowieso sinnlos, 
in meinem Alter erst recht ;-)

von Ardu Ino (Gast)


Lesenswert?

Hallo

danke für die diversen Links und auch für die sich entwickelnde 
Diskussion die meist interessant und teilweise sogar hilfreich für mich 
ist.

Aber bitte: Es handelt sich um ein Technisches Thema - da sollte eine 
vernünftige Diskussionskultur doch möglich sein?
Das sich hier einige Leute herumtreiben die erkennbar richtig viel 
Wissen und Erfahrung in anspruchsvollen Technischen Bereichen haben, 
aber gleichzeitig wie ein Holligan oder ein 18 jähriger besoffener am 
Samstagmorgen um 4:00Uhr in der Partymeile einer Großstadt 
"argumentieren" ist nur noch als beschämend zu bezeichnen.

Mensch Leute, seid Nett zueinander, akzeptiert andere Meinungen, 
Vorgehensweisen und das nicht alle genauso viel fachlich Wissen wie man 
selbst.

Ardu Ino

von Peter D. (peda)


Lesenswert?

Ardu Ino schrieb:
> deshalb gibt es auch eine
> Funktion millis, auf die ich aber auch gerne verzichten würde.
> Wieso, weshalb, warum steht nicht zu Diskussion

Sollte es aber.
"millis" gibt Dir nur einen Zeitstempel zurück, ist also überhaupt nicht 
böse. Es gibt daher keinen Grund darauf verzichten zu wollen. Der 
Unterschied, ob man CPU-Leistung verschwendet oder nicht, liegt allein 
an Dir, wie Du "millis" anwendest.

Eine bequeme Lösung für parallele Tasks mit verschiedenen Verzögerungen 
kann dann ein Scheduler sein, der z.B. in 1ms oder 10ms Schritten 
aufgerufen wird:
Beitrag "Wartezeiten effektiv (Scheduler)"

von Matthias M. (Firma: privat) (quadraturencoder)


Lesenswert?

Ich verstehe den Aufruhr nicht. Hat doch bei Heise alles schon mal 
gestanden. Man nimmt einen Timer Interrupt und gut:

https://www.heise.de/developer/artikel/Timer-Counter-und-Interrupts-3273309.html

von Falk B. (falk)


Lesenswert?

@Matthias Melcher (Firma: privat) (quadraturencoder)

>Ich verstehe den Aufruhr nicht. Hat doch bei Heise alles schon mal
>gestanden. Man nimmt einen Timer Interrupt und gut:

Na wenn das bei heise steht, MUSS es ja die reine Wahrheit sein ;-)

Naja, die Begründung, warum ein delay() schlecht ist, ist aber auch eher 
schlecht 8-0

Daß dabei die CPU steht und zum Nichtstun verdonnert wird, kommt dort 
nicht wirklich rüber! Außerdem ist die Ungenauigkeit der Funktion das 
kleinste der Probleme, mal ganz davon abgesehen, daß sie gar nicht so 
ungenau ist, sondern mit einer Auflösung und Genauigkeit von wenigen 
CPU-Takten arbeitet. Naja, das übliche IT-Fastfood von heute . . .

: Bearbeitet durch User
von Krull (Gast)


Lesenswert?

Falk B. schrieb:
> @Matthias Melcher (Firma: privat) (quadraturencoder)
>
>>Ich verstehe den Aufruhr nicht. Hat doch bei Heise alles schon mal
>>gestanden. Man nimmt einen Timer Interrupt und gut:
>
> Na wenn das bei heise steht, MUSS es ja die reine Wahrheit sein ;-)

Auch wenn das gleiche bei Falk B. steht? ;-)

Falk B. schrieb:
> Das bedeutet hier, eine Statemachine
> mittels Timer oder gar ISR im festen Zeitraster aufzurufen, ohne
> sonstige Kompromisse. Und genau DAS will und braucht der OP!!!

Warum machst du dich jetzt über heise lustig, obwohl dort die gleiche 
Meinung vertreten wird, wie du sie vertrittst?

von Falk B. (falk)


Lesenswert?

@Krull (Gast)

>Warum machst du dich jetzt über heise lustig, obwohl dort die gleiche
>Meinung vertreten wird, wie du sie vertrittst?

Weil die Begründung eher schlecht ist. Man kann das richtige meinen aber 
schlecht ausdrücken.

von Krull (Gast)


Lesenswert?

Falk B. schrieb:
> mal ganz davon abgesehen, daß sie gar nicht so
> ungenau ist, sondern mit einer Auflösung und Genauigkeit von wenigen
> CPU-Takten arbeitet. Naja, das übliche IT-Fastfood von heute . . .

...aber (fast) jedes µC-Programm arbeitet auch mit Interrupts. Und diese 
Interrupts unterbrechen logischerweise auch ein delay(). Damit (und das 
ist eigentlich der Normalfall) wird das delay() auf jeden Fall nicht 
mit der Genauigkeit von wenigen CPU-Takten arbeiten!

von Falk B. (falk)


Lesenswert?

@Krull (Gast)

>> mal ganz davon abgesehen, daß sie gar nicht so
>> ungenau ist, sondern mit einer Auflösung und Genauigkeit von wenigen
>> CPU-Takten arbeitet. Naja, das übliche IT-Fastfood von heute . . .

>...aber (fast) jedes µC-Programm arbeitet auch mit Interrupts.

Viele. Die Arduino-Welt nahezu ohne, vom "unsichtbaren" 1ms Timer mal 
abgesehen.

>Und diese
>Interrupts unterbrechen logischerweise auch ein delay(). Damit (und das
>ist eigentlich der Normalfall) wird das delay() auf jeden Fall nicht
>mit der Genauigkeit von wenigen CPU-Takten arbeiten!

Nö, du konstruierst schon wieder eine Sachlage, die so gar nicht 
existiert. So nach dem Motto, wenn ich ein 10m Maßband nur zu Hälft 
ausrolle, kann ich keine 10m messen. ;-)

Wer des Lesens und vor allem des sinnerfassenden Lesens mächtig ist, 
wird in der Doku davor gewarnt. Und dann kann man mit delay() recht 
genaue Zeiten erreichen, z.B. einfache Pulsgeneratoren. Für einige 
Anwendungen ist das OK, wenn die CPU so oder so nix besseres zu tun hat. 
In vielen Fällen hat sie das aber.

von Jens G. (jensg)


Lesenswert?

Das hier könnte sehr interessant sein:
http://www.avdweb.nl/arduino/libraries/virtualdelay.html

von Falk B. (falk)


Lesenswert?

@Jens Grabner (jensg)

>Das hier könnte sehr interessant sein:
>http://www.avdweb.nl/arduino/libraries/virtualdelay.html

Naja, das ist auch nur eine aufgezuckerte Variate der millis() Nutzung.

von Krull (Gast)


Lesenswert?

Falk B. schrieb:
> Nö, du konstruierst schon wieder eine Sachlage, die so gar nicht
> existiert. So nach dem Motto, wenn ich ein 10m Maßband nur zu Hälft
> ausrolle, kann ich keine 10m messen. ;-)

Und wenn ich mein Maßband in 1µm kleine Teile schneide, kann ich sogar 
sehr genau messen ;-)
Ich frage mich, wer hier etwas konstruiert, nur damit er recht behält.

Willst du allen ernstes behaupten, daß ein delay(), wenn es tausendmal 
durch einen Interrupt unterbrochen wird, der selbst ja logischerweise 
auch Zeit braucht, dann genauso lang ist wie ein delay(), was ganz 
allein und ungestört läuft? Ein delay() weiß doch nicht, wie lange ein 
Interrupt dauert, oder? Vor allem, weil ja innerhalb der isr noch 
Verzweigungen auftreten können, die auch von externen Ereignissen 
bestimmt werden können...

von Falk B. (falk)


Lesenswert?

@Krull (Gast)

>Willst du allen ernstes behaupten, daß ein delay(), wenn es tausendmal
>durch einen Interrupt unterbrochen wird, der selbst ja logischerweise
>auch Zeit braucht, dann genauso lang ist wie ein delay(), was ganz
>allein und ungestört läuft?

Keine Sekunde, nicht mal delay(1) ;-)

Mein Gott, willst du mich nicht verstehen oder kannst du mich nicht 
verstehen oder willst du nur schwätzen um des Schwätzens willen?

>Ein delay() weiß doch nicht, wie lange ein
>Interrupt dauert, oder?

Jaja, also doch nur Schwätzen!

>Vor allem, weil ja innerhalb der isr noch
>Verzweigungen auftreten können, die auch von externen Ereignissen
>bestimmt werden können...

BlaBlaBla!

von Jens G. (jensg)


Lesenswert?

Krull schrieb:
> Ein delay() weiß doch nicht, wie lange ein
> Interrupt dauert, oder? Vor allem, weil ja innerhalb der isr noch
> Verzweigungen auftreten können, die auch von externen Ereignissen
> bestimmt werden können...
Bitte "Non-blocking Virtual Delay" anschauen - es wird ein Vergleich mit 
dem internen 1ms-Timer gemacht  --  der Fehler der dabei entsteht ist .. 
1ms  --  was häufig ausreichen sollte. Wie lang andere Abläufe dauern 
ist dabei nicht wichtig.

von Falk B. (falk)


Lesenswert?

@ Jens Grabner (jensg)

>Bitte "Non-blocking Virtual Delay" anschauen

Hab ich gemacht.

>- es wird ein Vergleich mit
>dem internen 1ms-Timer gemacht

Stimmt.

>  --  der Fehler der dabei entsteht ist ..
>1ms

Stimmt nicht!

> --  was häufig ausreichen sollte.

Dito!

> Wie lang andere Abläufe dauern ist dabei nicht wichtig.

Falsch! Es wird nur festgestellt, ob die vorgegebene Wartezeit erreicht 
wurde oder nicht. Ob die um 1, 10, oder 1.000.000 ms überschritten wurde 
wird weder geprüft, noch gemeldet noch könnte man was dagegen tun! 
Zumindest nicht direkt. Denn wenn die anderen Abläufe zu lange brauchen, 
erfolgt die Prüfung und damit ggf. die Reaktion auch zu spät. Und wenn 
man dann periodisch den virtuellen Timer wieder starten will, 
akkumuliert sich der Fehler! Ganz toll!

Mal ganz abgesehen davon, daß auch die Beispiele dort Mist sind. So 
lernt niemand eine gescheite Programmierung und Struktur von Programmen, 
sondern nur den allgegenwärtigen Arduino-Murks.

Ergo. Gute Tutorials fallen nicht vom Himmel und sind eher rar.

von Einer K. (Gast)


Lesenswert?

Falk B. schrieb:
> @ Jens Grabner (jensg)
>
>>Bitte "Non-blocking Virtual Delay" anschauen
>
> Hab ich gemacht.

Ich auch....

Selbst wenn ich ähnliche Verfahren anwende, muss ich sagen, dass das 
Tutorial/Code nicht schön ist.

z.B. static in Makros.
Darauf reagiere ich mittlerweile recht allergisch.
Das kann die Wiederverwendung von Funktionen und Klassen/Objekten derbe 
einschränken.

von Krull (Gast)


Lesenswert?

Könntest du bitte mal meine Fragen beantworten?
Deine drei letzten "Antworten" sind dafür nicht geeignet.

Ich frage dich, ob ein delay, das durch Interrupts ständig unterbrochen 
wird, genauso lang ist ist, wie ein "ungestörtes" delay?
Und du antwortest darauf:
> "keine Sekunde" ---???

Ich frage dich, ob ein delay weiß, wie lange Interrupts brauchen?
Deine Antwort:
> Jaja, also doch nur Schwätzen! --???

Ich stelle fest, daß innerhalb der isr noch Verzweigungen auftreten 
können und damit die Ausführungsdauer einer isr nicht bestimmbar ist.
Deine Antwort:
> BlaBlaBla!

Also bitte gib mir jetzt die richtigen Antworten, ja?

von Jens G. (jensg)


Lesenswert?

Falk Brunner -- Besten dank für die genaue Beschreibung -- ein 
RealTimeOS oder auch nur ein Sytem zur Zeitsteuerung ist für viele 
"Anfänger" einfach schon eine Hürde  --  Arduino ist auf der anderen 
Seite auch nie für professionelle Dinge gedacht gewesen -- weshalb hier 
sehr heftig unterschiedliche Denkmuster zusammenlaufen.

aber gut -- delay() und die Beispiele dazu hätten "nie" Standard werden 
dürfen -- ohne delay() vermeidet man viele Probleme.

von Falk B. (falk)


Lesenswert?

@Jens Grabner (jensg)

>RealTimeOS oder auch nur ein Sytem zur Zeitsteuerung ist für viele
>"Anfänger" einfach schon eine Hürde

Sicher.

>--  Arduino ist auf der anderen
>Seite auch nie für professionelle Dinge gedacht gewesen -- weshalb hier
>sehr heftig unterschiedliche Denkmuster zusammenlaufen.

Mag sein.

>aber gut -- delay() und die Beispiele dazu hätten "nie" Standard werden
>dürfen -- ohne delay() vermeidet man viele Probleme.

Mag auch sein. delay() hat schon seine Berechtigung, sei es für 
einfach(ste) Arduino-Sachen oder wo es halt unkritisch ist. Ebenso die 
Funktion millis() und deren Anwendung. Man sollte aber dennoch in einer 
vernünftigen, anschaulichen Art und Weise zeigen, wie man es besser 
machen kann, wenn es denn nötig ist. Nicht mehr und nicht weniger wollte 
ich sagen.

von Einer K. (Gast)


Lesenswert?

Jens G. schrieb:
> delay() und die Beispiele dazu hätten "nie" Standard werden
> dürfen

Schwachsinn!

Ein delay() ist leicht zu verstehen, und tut genau das, wofür es 
vorgesehen ist.

Außerdem kan man während eines delay() noch tausend andere feine Dinge 
tun, nur nicht das delay() vorzeitig abbrechen.

von Michi (Gast)


Lesenswert?

Vielleicht habe ich ja auch Aussagen oder Anforderungen überlesen:

Aus Prinzip alles in eine isr zu packen ist sicher kurzsichtig und blöd. 
Falk B. sprach vom Drehgeber. Klar Stich gemacht, aber man weiß doch gar 
nicht, WAS der TO eigentlich machen will. Ein Dogma erarbeiten ist da 
nun auch nicht zielführend.

Eine Statemachine die millis() benutzt hat von mir auch quasi jedes 
Programm. Zugegebenermaßen neben härteren Echtzeit-Geschichten. Wenn ich 
alle 10s einen Feuchtigkeitswert angucken will, mache ich da keinen 
Timer für, sondern vergleiche mit der Systemzeit.

Mit delay_ms() operieren zu wollen ist an sich (fast) immer unklug. ich 
sage fast, weil man damit auch ein Programm schreiben kann, welches gut 
damit funktionieren kann wenn man das im Vorfeld weiß.

Werkzeug zum Problem wählen.

von Krull (Gast)


Lesenswert?

@Falk:
Könntest du bitte mal meine Fragen beantworten?
Deine drei letzten "Antworten" sind dafür nicht geeignet.

Ich frage dich, ob ein delay, das durch Interrupts ständig unterbrochen
wird, genauso lang ist ist, wie ein "ungestörtes" delay?
Und du antwortest darauf:
> "keine Sekunde" ---???

Ich frage dich, ob ein delay weiß, wie lange Interrupts brauchen?
Deine Antwort:
> Jaja, also doch nur Schwätzen! --???

Ich stelle fest, daß innerhalb der isr noch Verzweigungen auftreten
können und damit die Ausführungsdauer einer isr nicht bestimmbar ist.
Deine Antwort:
> BlaBlaBla! ---???

Also bitte gib mir jetzt die richtigen Antworten, ja?

von Einer K. (Gast)


Lesenswert?

Krull schrieb:
> Ich frage dich, ob ein delay, das durch Interrupts ständig unterbrochen
> wird, genauso lang ist ist, wie ein "ungestörtes" delay?
> Und du antwortest darauf:


Ein bisschen verspannt heute?

Weißt du es wirklich nicht, oder willst du nur Streit?

von Krull (Gast)


Lesenswert?

Arduino F. schrieb:
> Krull schrieb:
>> Ich frage dich, ob ein delay, das durch Interrupts ständig unterbrochen
>> wird, genauso lang ist ist, wie ein "ungestörtes" delay?
>> Und du antwortest darauf:
>
> Ein bisschen verspannt heute?
>
> Weißt du es wirklich nicht, oder willst du nur Streit?

Ich suche absolut keinen Streit. Ich habe dem Falk ein paar Fragen 
gestellt. Seine "Antworten" kannst du selbst lesen.

Aber vielleicht kannst du mir die Fragen beantworten? Falk will es 
offensichtlich nicht.

von Philipp K. (philipp_k59)


Lesenswert?

Wichtig ist zu erkennen ob Delay das Projekt nun "zerstört" oder 
hinreichend ist. Im ersteren Falle muss man einen einfachen Workaround 
schaffen, da brauch man nicht diskutieren und lange Sinnlos Schwafeln.

Wenn Du alles unbedingt mit einem Timer umsetzen möchtest, geht das 
auch..

Die Frage ist nur, reichen Deine Fähigkeiten dazu aus das ohne 
Delay/Millis zu machen oder nicht.

Millis ist schonmal ein guter Ansatz das Delay zu umgehen.. das ist 
mehrschichtig auch nicht "Super einfach" und verlangt auch schon Grips. 
(Bei einem siehts einafch aus.. mach mal nen BlinkWithoutDelay mit 3 
LEDS, und 3 IF/FOR)

Wenn man das mit Millis kann braucht es nur noch eine 
Timerinitialisierung und ein "Suchen/ersetzen" um es auf einen Timer 
umzumünzen.

von Einer K. (Gast)


Lesenswert?

Krull schrieb:
> Aber vielleicht kannst du mir die Fragen beantworten?

Sicher!

Es liegt ganz an der Implementierung!

1: Das AVR Lib (util/delay.h) Delay wird von jedem ISR Ereignis 
verlängert.


2: Bein Arduino delay() verlängert, schlimmstenfalls, die letzte ISR die 
Pause.

Jetzt alle Klarheiten beseitigt?

von Krull (Gast)


Lesenswert?

Arduino F. schrieb:
> Krull schrieb:
>> Aber vielleicht kannst du mir die Fragen beantworten?
>
> Sicher!
>
> Es liegt ganz an der Implementierung!
>
> 1: Das AVR Lib (util/delay.h) Delay wird von jedem ISR Ereignis
> verlängert.
>
> 2: Bein Arduino delay() verlängert, schlimmstenfalls, die letzte ISR die
> Pause.
>
> Jetzt alle Klarheiten beseitigt?

Alle noch nicht, aber damit kann ich auf jeden Fall wesentlich mehr 
anfangen als mit der "Gesprächskultur" von Falk.
Danke dir dafür.
Der erste Punkt (AVR-Delay) war mir bekannt, deshalb habe ich dem Falk 
die Fragen gestellt.
Der zweite Punkt ist mir neu. Da werde ich mich mal damit 
auseinandersetzen und versuchen den Grund herauszufinden, warum nur die 
letzte ISR das Delay verlängert. Allein daß das so ist, wußte ich nicht.
Das ist aber (meiner Meinung nach) kein Grund für Falk, mir nur mit 
"blabla" zu antworten. Ist er so abgehoben, daß er sich nicht vorstellen 
kann, daß es noch Leute gibt, die weniger wissen als er? Ich für meinen 
Teil finde das einfach arrogant. Sorry :-(

Auf jeden Fall danke ich dir für deine Antworten :-)

von Einer K. (Gast)


Lesenswert?

Krull schrieb:
> arrogant

Ich halte es für recht schwierig, Arroganz und Kompetenz auseinander zu 
halten, wenn ich die Person nicht kenne.

Auch kommen soziale und fachliche Kompetenz nicht immer in Personalunion 
vor.

PS:
Auch du zeigst hier ein irritierendes Verhalten.
(ein mich irritierendes)

von BlaBla (Gast)


Lesenswert?

Liegt wohl heute am Wetter. Ich hoffe es sind keine Psychopathen 
oder/und Soziopathen unter uns.

von Krull (Gast)


Lesenswert?

Arduino F. schrieb:
> Krull schrieb:
>> arrogant
>
> Ich halte es für recht schwierig, Arroganz und Kompetenz auseinander zu
> halten, wenn ich die Person nicht kenne.
>
> Auch kommen soziale und fachliche Kompetenz nicht immer in Personalunion
> vor.

Das mag ja sein, aber wenn ich kompetent bin, gibt mir das nicht das 
Recht, jemandes Frage einfach mit "blabla" zu beantworten. Das ist dann 
der Punkt, wo sich die fachliche Kompetenz von der sozialen Kompetenz 
gründlich verabschiedet hat. Tut mir auch leid für Falk. Ich hoffe, er 
hatte nur einen "schlechten Tag" und ist nicht immer so :-)

von Einer K. (Gast)


Lesenswert?

BlaBla schrieb:
> Liegt wohl heute am Wetter. Ich hoffe es sind keine Psychopathen
> oder/und Soziopathen unter uns.

Da mache dir mal keine zu großen Hoffnungen.

Meiner Schätzung nach tragen ca 2% der Weltbevölkerung eine neurotische 
Fehlanpassung mit sich rum.

Ob die sich hier rudeln, ka, manchmal kommt es mir so vor.

von Krull (Gast)


Lesenswert?

Arduino F. schrieb:
> PS:
> Auch du zeigst hier ein irritierendes Verhalten.
> (ein mich irritierendes)

Darf ich mal fragen, was genau dich irritiert?
Kommt es nicht so häufig vor, daß man Antworten einfordert, wenn man 
Fragen gestellt hat? Oder was ist es?

von Einer K. (Gast)


Lesenswert?

Krull schrieb:
> Kommt es nicht so häufig vor, daß man Antworten einfordert, wenn man
> Fragen gestellt hat?

Z.B.:
Wenn in Fragen schon die gewünschte Antwort vorgegeben wird, empfinde 
ich das als provokant.
Als unangenehm.

Oft wird sowas (unbewusst?) als subtile Methode genutzt, um eine 
Eskalationsspirale zu starten, oder zu fördern.

Und das ist etwas, woran ich nur selten Spaß habe.

von Dieter F. (Gast)


Lesenswert?

Arduino F. schrieb:
> 2: Bein Arduino delay() verlängert, schlimmstenfalls, die letzte ISR die
> Pause.

Das würde ich etwas relativieren.

Das Arduino-Delay (ms) basiert auf den "Standard-Millis". Wenn da 
mehrere Interrupts hintereinander kommen (incl. der Millis ...) dann 
wartet das Arduino-Delay diese alle ab (soweit mein Verständnis). Wenn 
ein Spassvogel die "Millis" deaktiviert, dann gibt es gar ein St. 
Nimmerlein-delay.

Das (Arduino-Delay (µs) ) arbeitet mit "NOP" und kann gleichfalls 
beliebig durch ISR unterbrochen und verzögert werden.

von Einer K. (Gast)


Lesenswert?

Das halte ich für einen konstruierten Sonderfall.

Wenn die ISR so dicht aufeinander folgen, dass noch nicht mal ein 
delay() sein Ende (recht pünktlich) findet, dann ist was ganz anderes 
faul.


Mindestens ein Maschinenbefehl, des Hauptprogramms, wird zwischen 2 ISR 
ausgeführt!?!

Also findet das delay() sein Ende.

von Thomas E. (thomase)


Lesenswert?

Arduino F. schrieb:
> Also findet das delay() sein Ende.

Ja. Irgendwann.

von Dieter F. (Gast)


Lesenswert?

Arduino F. schrieb:
> Das halte ich für einen konstruierten Sonderfall.

Das ist Dein gutes Recht:-) - aber der "schlimmste Fall"

Arduino F. schrieb:
> 2: Bein Arduino delay() verlängert, schlimmstenfalls, die letzte ISR die
> Pause.

ist nunmal oft ein Sonderfall.


Arduino F. schrieb:
> Mindestens ein Maschinenbefehl, des Hauptprogramms, wird zwischen 2 ISR
> ausgeführt!?!

So sei es. Die "Arduino-Delay (ms)"-Routine besteht aus einigen 
"Maschinenbefehlen" - oder?
1
void delay( uint32_t ms )
2
{
3
  if ( ms == 0 )
4
  {
5
    return ;
6
  }
7
8
  uint32_t start = _ulTickCount ;
9
10
  do
11
  {
12
    yield() ;
13
  } while ( _ulTickCount - start < ms ) ;
14
}

von chris (Gast)


Lesenswert?

Warum nicht direkt in den Code schauen? :
Beitrag "Re: Arduino ohne delay und millis"

von Dieter F. (Gast)


Lesenswert?

chris schrieb:
> Warum nicht direkt in den Code schauen? :

Wessen - von wann? Wir schreiben das Jahr 2017 ...

von Manfred (Gast)


Lesenswert?

Arduino F. schrieb:
> Außerdem kan man während eines delay() noch tausend andere feine Dinge
> tun, nur nicht das delay() vorzeitig abbrechen.

Das würde ich gerne erklärt bekommen. Nach meinem Verständnis ist delay 
blockierend, während dieser Zeit kann kein weiterer Code ausgeführt 
werden.

von chris (Gast)


Lesenswert?

>Wessen - von wann? Wir schreiben das Jahr 2017 ...
Genau so ist es. Im Jahr 2017 gibt es GitHub. Und dort befindet sich das 
aktuelle Arduino Repository. Und darauf habe ich verlinkt. Sogar auf's 
richtige File mit Angabe der Zeilennummer.

Zu schwer?

von Stefan F. (Gast)


Lesenswert?

> Das würde ich gerne erklärt bekommen. Nach meinem Verständnis ist delay
> blockierend, während dieser Zeit kann kein weiterer Code ausgeführt
> werden.

Interrupts können delay() unterbrechen.

Ich schätze, du hast den Thread nicht mitverfolgt, oder?

von Einer K. (Gast)


Lesenswert?

Manfred schrieb:
> Das würde ich gerne erklärt bekommen. Nach meinem Verständnis ist delay
> blockierend, während dieser Zeit kann kein weiterer Code ausgeführt
> werden.

Testprogramm:
1
unsigned long counter;
2
3
void yield(void) 
4
{
5
  counter++;
6
}
7
8
9
void setup(void) 
10
{
11
  Serial.begin(9600);
12
}
13
14
void loop(void) 
15
{
16
   delay(1000);
17
   Serial.print("Counter: ");  Serial.println(counter);
18
}

Ausgabe:
1
Counter: 185875
2
Counter: 371726
3
Counter: 557577
4
Counter: 743427
5
Counter: 929278
6
Counter: 1115129
7
Counter: 1300979
8
Counter: 1486828
9
Counter: 1672677
10
Counter: 1858528
11
Counter: 2044379
12
Counter: 2230230
13
Counter: 2416081
14
Counter: 2601932
15
Counter: 2787783
16
Counter: 2973634
17
Counter: 3159485
18
Counter: 3345336
19
Counter: 3531186

von Dieter F. (Gast)


Lesenswert?

chris schrieb:
> Genau so ist es. Im Jahr 2017 gibt es GitHub. Und dort befindet sich das
> aktuelle Arduino Repository. Und darauf habe ich verlinkt. Sogar auf's
> richtige File mit Angabe der Zeilennummer.
>
> Zu schwer?

Scheinbar ... 2005 - 2006 war einmal (von wem auch immer ...)
1
/*
2
  wiring.c - Partial implementation of the Wiring API for the ATmega8.
3
  Part of Arduino - http://www.arduino.cc/
4
  Copyright (c) 2005-2006 David A. Mellis

Neu ist
1
/*
2
  Copyright (c) 2015 Arduino LLC.  All right reserved. 
3
4
..
5
6
7
void delay( uint32_t ms )
8
{
9
  if ( ms == 0 )
10
  {
11
    return ;
12
  }
13
14
  uint32_t start = _ulTickCount ;
15
16
  do
17
  {
18
    yield() ;
19
  }

von Dieter F. (Gast)


Lesenswert?

Arduino F. schrieb:
> Manfred schrieb:
>> Das würde ich gerne erklärt bekommen. Nach meinem Verständnis ist delay
>> blockierend, während dieser Zeit kann kein weiterer Code ausgeführt
>> werden.

Außer ISR - und das kannst Du nachlesen :-)

von Joachim B. (jar)


Lesenswert?

man lernt hier immer noch dazu, danke an alle

wie ist das mit Serial.event und Serial.available() mit Serial.read();

unterbricht das delay_ms()?

Das ich eigene ISR nutzen kann weiss ich schon.

von Einer K. (Gast)


Lesenswert?

Joachim B. schrieb:
> wie ist das mit Serial.event und Serial.available() mit Serial.read();
>
> unterbricht das delay_ms()?
Nein!

Aber der von Serial genutzte Interrupt tut das.
Also: JA!

ööhmmmm...
Ein kleines Jain, auf die Frage, weil sie in sich einen logischen Fehler 
hat.

von Stefan F. (Gast)


Lesenswert?

Das paradoxe an Frameworks ist: Sie sollen die Arbeit erleichtern. Doch 
früher oder später kommen Detailfragen auf, zu deren Beantwortung man in 
den Quelltext schauen muss. Spätestens, wenn das Framework darüber 
hinaus nicht genau das tut, was man braucht, muss man sich fragen, warum 
man überhaupt ein Framework verwendet hat.

Ich wollte diese Erkenntnis als Java Enterprise Entwickler viele Jahre 
lang nicht akzeptieren, doch mittlerweile wurde ich mehrfach auf die 
harte Tour (durch negative Erfahrung) eines besseren belehrt.

von chris (Gast)


Lesenswert?

>Das paradoxe an Frameworks ist: Sie sollen die Arbeit erleichtern...

Ja, heutzutage kämpft man eigentlich nur noch mit den Frameworks.
Ich neige dazu, alles selber schreiben zu wollen. Aber am Ende bleibt 
einem halt doch nur, Frameworks nutzen zu müssen.
Bei den Arduinosachen hat man zumindest die Möglichkeit bis auf die 
unterste Ebene rein zu schauen und notfalls kann man da was ändern.
Bei den STM-HAL Sachen kann das aber richtig übel werden und eigentlich 
helfen da nur Workarrounds.

von Joachim B. (jar)


Lesenswert?

Arduino F. schrieb:
> ööhmmmm...
> Ein kleines Jain, auf die Frage, weil sie in sich einen logischen Fehler
> hat.

wo?

ich habe void serialEvent(void) erst spät entdeckt ist ja eine 
Interruptnutzung

somit müsste

void serialEvent(void)
{ while (Serial.available())
  { char incomingByte = (char)Serial.read();

auch delay_ms unterbrechen

wo soll der logische Fehler sein?

von Rolf M. (rmagnus)


Lesenswert?

Stefan U. schrieb:
> Interrupts können delay() unterbrechen.

Allerdings würde ich in einer ISR nicht

Arduino F. schrieb:
> noch tausend andere feine Dinge

tun.

von chris (Gast)


Lesenswert?

Autor: Dieter F. (jim_quakenbush)
>Scheinbar ... 2005 - 2006 war einmal (von wem auch immer ...)
Oha, ich dachte mein Link sei das Main-Arduino-Repository.
Falls jemand das von 2015 findet, würde mich ein Link stark 
interessieren.

von Einer K. (Gast)


Lesenswert?

Joachim B. schrieb:
> ich habe void serialEvent(void) erst spät entdeckt ist ja eine
> Interruptnutzung

Ist es nicht.
serialEvent() wird in der main() Loop aufgerufen.
Ein Schritt vor, oder nach, dem Aufruf von loop().
Also im ganz normalen Programmkontext.
Nicht in einem Interrupt.

von Einer K. (Gast)


Lesenswert?

Rolf M. schrieb:
> Stefan U. schrieb:
>> Interrupts können delay() unterbrechen.
>
> Allerdings würde ich in einer ISR nicht
>
> Arduino F. schrieb:
>> noch tausend andere feine Dinge
>
> tun.

Ein drohendes Darama bei dem yield() ist, dass rekursive Aufrufe 
stattfinden könnten.
Das wird man (durch Disziplin?) unterbinden müssen.

von Dieter F. (Gast)


Lesenswert?

chris schrieb:
> Falls jemand das von 2015 findet, würde mich ein Link stark
> interessieren.

Google kennst Du? Die Welt hat sich weiter gedreht :-)

von Manfred (Gast)


Lesenswert?

Stefan U. schrieb:
> Nach meinem Verständnis ist delay
>> blockierend, während dieser Zeit kann kein weiterer Code ausgeführt
>> werden.
>
> Interrupts können delay() unterbrechen.

Das ist mir klar, aber ich sehe diese eher als Sonderform zeitkritischer 
Anwendungen denn im Tagesgeschäft.

> Ich schätze, du hast den Thread nicht mitverfolgt, oder?

Aber doch! Bei solchen Themen schaue ich immer, ob ich ein paar 
Informationen oder Anregungen für mich mitnehmen kann.

von Dieter F. (Gast)


Lesenswert?

Manfred schrieb:
> Das ist mir klar, aber ich sehe diese eher als Sonderform zeitkritischer
> Anwendungen denn im Tagesgeschäft.

Was hast Du denn für ein Tagesgeschäft mit AVR-Mikrocontrollern?

von chris (Gast)


Lesenswert?

Autor: Dieter F. (jim_quakenbush)
>Google kennst Du? Die Welt hat sich weiter gedreht :-)
Bei mir wirft Google dieses:
https://github.com/arduino

Aber Google ist ja schlau und präsentiert Userabhängige Ergebnisse. 
Vielleicht will's mich ärgern, weil ich kein Android-Handy habe.

Jetzt zeig mal den Link den Google Dir zeigt.

von Dieter F. (Gast)


Lesenswert?

chris schrieb:
> Jetzt zeig mal den Link den Google Dir zeigt.

Ich wusste gar nicht, dass dafür ein Kurs erforderlcih ist :-)

https://github.com/arduino-org/arduino-core-nrf52/blob/master/cores/arduino/delay.c

von Manfred (Gast)


Lesenswert?

Arduino F. schrieb:
>> Das würde ich gerne erklärt bekommen. Nach meinem Verständnis ist delay
>> blockierend, während dieser Zeit kann kein weiterer Code ausgeführt
>> werden.
> Testprogramm:

Oops, da hast Du etwas gemacht, was mir vollkommen unbekannt ist. Mit 
einer Internetsuche lande ich auf einer Bachelorarbeit an der Uni 
Hamburg und finde "yield" als Scheduler beschrieben.

Heisst also, mit "void setup(void) und void loop(void)"
springst Du jedesmal durch void yield(void)?

Das muß ich erstmal sacken lassen :-)

Danke Dir!

von Dieter F. (Gast)


Lesenswert?

chris schrieb:
> Vielleicht will's mich ärgern, weil ich kein Android-Handy habe.

Dann müsste Google mich noch mehr ärgern, weil ich gar kein 
Schei..-Handy/-Schmartphone habe :-) (auch kein Fatzebook und kein 
Whatsapp etc. ) habe

von Thomas E. (thomase)


Lesenswert?

Dieter F. schrieb:
> weil gar kein
> Schei..-Handy/-Schmartphone habe :-) (auch kein Fatzebook und kein
> sonstwas

Ich bin ja doch nicht alleine.

von Dieter F. (Gast)


Lesenswert?

Thomas E. schrieb:
> Ich bin ja doch nicht alleine.

Willkommen im Club der Ignoranten :-)

von Einer K. (Gast)


Lesenswert?

Dieter F. schrieb:
> chris schrieb:
>> Jetzt zeig mal den Link den Google Dir zeigt.
>
> Ich wusste gar nicht, dass dafür ein Kurs erforderlcih ist :-)
>
> https://github.com/arduino-org/arduino-core-nrf52/...

Arduino.org ist ein toter Ast in der Arduinowelt.
Und der nrf52 ist kein typischer Arduino.

Dein Link zeigt also ins Gebüsch.

von Dieter F. (Gast)


Lesenswert?

Arduino F. schrieb:
> Dein Link zeigt also ins Gebüsch.

Na, dann zeig doch mal den aktuellen Link (von welcher Arduino-Fraktion 
auch immer)

von Thomas E. (thomase)


Lesenswert?

Dieter F. schrieb:
> Willkommen im Club der Ignoranten

Wer weiß, vielleicht sind wir ja noch mehr.

Arduino F. schrieb:
> Arduino.org ist ein toter Ast in der Arduinowelt.

Und wo wachsen die Blätter? Arduino.org hört sich für mich nach oberster 
Instanz an. Oder ist das jetzt Alduino.cn?

von Stefan F. (Gast)


Lesenswert?

Arduino.cc ist die aktuelle Seite. Zumindest war das gestern noch so.

von Dieter F. (Gast)


Lesenswert?

Thomas E. schrieb:
> Wer weiß, vielleicht sind wir ja noch mehr

Die Hoffnung stirbt zuletzt :-)

von Einer K. (Gast)


Lesenswert?

Manfred schrieb:
> und finde "yield" als Scheduler beschrieben.
Über die Geschichte weiß ich nichts...

Aber irgendwo in den Tiefen der Arduino Doku findet sich ein Spruch 
dazu:
> yield() ist für Entwickler von Libraries bestimmt,
> um Kooperative Scheduler zu implementieren.
(möglichst sinngemäß wiedergegebeben)

Manfred schrieb:
> Heisst also, mit "void setup(void) und void loop(void)"
> springst Du jedesmal durch void yield(void)?

yield() wird in delay() aufgerufen.
Halt um die Wartezeit sinnvoll nutzen zu können.

von Einer K. (Gast)


Lesenswert?

Thomas E. schrieb:
> Und wo wachsen die Blätter? Arduino.org hört sich für mich nach oberster
> Instanz an. Oder ist das jetzt Alduino.cn?

Der Arduino.cc Trupp hat sich in die Wolle bekommen.

Arduino.org hat sich abgespalten.

Kürzlich war die Wiedervereinigung.

Damit ist Arduino.org weg vom Fenster.

Das war ein Prozess über ca. 2 Jahre.

von Dieter F. (Gast)


Lesenswert?

Dieter F. schrieb:
> Na, dann zeig doch mal den aktuellen Link (von welcher Arduino-Fraktion
> auch immer)

Such mal schön selbst ...

von Einer K. (Gast)


Lesenswert?

Dieter F. schrieb:
> Arduino F. schrieb:
>> Dein Link zeigt also ins Gebüsch.
>
> Na, dann zeig doch mal den aktuellen Link (von welcher Arduino-Fraktion
> auch immer)

Wurde hier schon gezeigt!
https://github.com/arduino/Arduino/blob/master/hardware/arduino/avr/cores/arduino/wiring.c

von Dieter F. (Gast)


Lesenswert?

Arduino F. schrieb:
> yield()

Ist irgendwie seit dem ESP ... erfunden worden (soweit mir bekannt) aber 
ihr könnt mich auch einfach ignorieren :-)

von Dieter F. (Gast)


Lesenswert?

Arduino F. schrieb:
> Wurde hier schon gezeigt!
> 
https://github.com/arduino/Arduino/blob/master/hardware/arduino/avr/cores/arduino/wiring.c


  Copyright (c) 2005-2006 David A. Mellis

lol - aber vergiss es, ich lasse euch jetzt in Ruhe :-)

von Manfred (Gast)


Lesenswert?

Dieter F. schrieb:
>> Das ist mir klar, aber ich sehe diese eher als Sonderform zeitkritischer
>> Anwendungen denn im Tagesgeschäft.
> Was hast Du denn für ein Tagesgeschäft mit AVR-Mikrocontrollern?

Mein Tagesgeschäft im beruflichen Erwerbsleben hat leider keine Hardware 
mehr, früher war ich dort mal mit 2MHz-Taktfrequenz und Assembler 
unterwegs.

Arduino setze ich im Hobbybereich ein, für überschaubare Steuerungs- / 
Meßaufgaben. Meist renne ich da in einer Schleife herum und vergleiche 
diverse Millisekunden, um dann in einer Unterroutine etwas zu tun. Diese 
Unterroutine kann auch mal blockierend sein oder einige Dutzend 
Millisekunden dauern.

Interrupt habe ich eingesetzt, um auf eine Eingabe in akzeptabler Zeit 
zu reagieren.

Als nächstes will ich Entladekurven von Akkus auf eine SD-Karte 
schreiben, das wird aus Sicht des Prozessors im Prinzip unendlich 
langsam ablaufen.

von Joachim B. (jar)


Lesenswert?

Arduino F. schrieb:
> Ist es nicht.
> serialEvent() wird in der main() Loop aufgerufen.

nö, nicht bei mir
1
  my_delay(100);
2
} // loop()  
3
4
5
void serialEvent(void)

sitzt definitiv ausserhalb der loop

von chris (Gast)


Lesenswert?

>  Copyright (c) 2005-2006 David A. Mellis
>lol - aber vergiss es, ich lasse euch jetzt in Ruhe :-)

Die letzte Änderung im File ist aber vom Dez.2015:
https://github.com/arduino/Arduino/commit/b1231c39e9fa6d8602ac24305b07f074c1145633

Es sieht so aus, als wenn sie das Datum im Header nicht aktualisiert 
haben.
Das ist aber auch lästig, wenn man wegen jeder kleinen Änderung im File 
den Copyright Header ändern muss.

von Einer K. (Gast)


Lesenswert?

Joachim B. schrieb:
> sitzt definitiv ausserhalb der loop

Außerhalb von loop(), ja.
Aber innerhalb der Schleife, welche sich typischer weise in main() 
befindet.
Und damit eben nicht in einem Interrupt.
Es verlängert nicht das delay_ms()

Das Gegenteil ist der Fall:
Ein delay_ms() verzögert den serialEvent() Aufruf.


Siehe:
https://github.com/arduino/Arduino/blob/master/hardware/arduino/avr/cores/arduino/main.cpp

Dort wird serialEventRun() aufgerufen, welches wiederum dann die 
diversen  serialEvent() aufruft.

Beitrag #5240298 wurde von einem Moderator gelöscht.
von Thomas E. (thomase)


Lesenswert?

Arduino F. schrieb:
> yield() wird in delay() aufgerufen.
> Halt um die Wartezeit sinnvoll nutzen zu können.

1
void yield(void) 
2
{
3
  delay(-1);
4
}

Und was macht er damit?

von Einer K. (Gast)


Lesenswert?

Thomas E. schrieb:
> Und was macht er damit?

Habe ich eben schon beschrieben:

Arduino F. schrieb:
> Ein drohendes Darama bei dem yield() ist, dass rekursive Aufrufe
> stattfinden könnten.
> Das wird man (durch Disziplin?) unterbinden müssen.

von Thomas E. (thomase)


Lesenswert?

Arduino F. schrieb:
> Habe ich eben schon beschrieben:

Sorry, das habe ich überlesen.

von Joachim B. (jar)


Lesenswert?

Arduino F. schrieb:
> Außerhalb von loop(), ja.
> Aber innerhalb der Schleife, welche sich typischer weise in main()
> befindet.
> Und damit eben nicht in einem Interrupt.
> Es verlängert nicht das delay_ms()

das wiederum hatte ich nirgens behauptet, es wurde behauptet das während 
delay_ms nichts abgearbeitet wird, das war meine Frage, aber egal ich 
nutze mein eigenes my_delay_ms() und da wird nebenbei anderes 
abgearbeitet.

D.h. während my_delay wartet wird dort weitergearbeitet.

Arduino F. schrieb:
> Ist es nicht.
> serialEvent() wird in der main() Loop aufgerufen.

hört sich nach Ausrede an, in der Arduinowelt gibts nur loop()

klar liegt noch eine main loop drüber, dann schreibe das doch 
deutlicher, wenn in Arduino von loop gesprochen wird dann ist doch 
loop() gemeint und nicht while(1);

: Bearbeitet durch User
von Einer K. (Gast)


Lesenswert?

Dabei habe ich doch extra  "main() Loop" geschrieben!
Die Klammern mit Bedacht gesetzt.

Merksatz:
> Ich bin für das verantwortlich, was ich sage.
> Nicht für das, was du verstehst.

Und von deinem_delay() weiß ich natürlich nichts...
Aber das könntest du gerne mal zeigen.

Joachim B. schrieb:
> in der Arduinowelt gibts nur loop()
Das ist übrigens auch nicht richtig.

Ein korrektes Arduino Programm kann auch so aussehen:
1
int main()
2
{
3
  for(;;);
4
  return 0;
5
}
Man wird dann aber auch auf die ganzen Arduino Features verzichten 
müssen.

von Joachim B. (jar)


Lesenswert?

Arduino F. schrieb:
> Ein korrektes Arduino Programm kann

stimmt, nur dann brauchts auch nicht mehr die IDE

Arduino F. schrieb:
> Merksatz:
>> Ich bin für das verantwortlich, was ich sage.
>> Nicht für das, was du verstehst.

kenne ich schon, ist aber auch nur platt

Arduino F. schrieb:
> Aber das könntest du gerne mal zeigen.

dazu bin ich ein zu schlechter progger, das hilft niemanden hier und 
Häme gibts ja genug, das brauche ich nicht, für mich reichts eben :)

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.