Forum: PC-Programmierung Raspberry Laufzeit in millisekunden


Announcement: there is an English version of this forum on EmbDev.net. Posts you create there will be displayed on Mikrocontroller.net and EmbDev.net.
von Simo (Gast)


Bewertung
0 lesenswert
nicht lesenswert
Hallo,

wie komme ich unter mit C (unter Raspbian auf den Raspberry) an die 
Laufzeit in Millisekunden?

aus der Zum Wörterbuch hinzufügen kenne ich den Befehl millis(); leider 
ist der beim PI nicht Standard implementiert.

Vielen Dank

von Christophe J. (chj)


Bewertung
0 lesenswert
nicht lesenswert

von Rolf M. (rmagnus)


Bewertung
2 lesenswert
nicht lesenswert
Siehe "man clock_gettime".

von asdf (Gast)


Bewertung
0 lesenswert
nicht lesenswert
Simo schrieb:
> aus der Zum Wörterbuch hinzufügen kenne ich den Befehl millis(); leider
> ist der beim PI nicht Standard implementiert.

So weit ich das sehe, ist millis() eine Funktion, die im Arduino 
verwendet wird. Und auf dem PI läuft kein Arduino, sondern Linux.
Weil millis() nicht zum Sprachumfang von C gehört, ist es auch nicht 
sinnvoll, wenn du sagst, daß der PI "nicht standard implementiert" ist.
Schau mal nach den Zeitfunktionen von C. Links dafür hast du ja schon 
bekommen. Und die Suchmaschine wird dir sicher auch einiges verraten. 
Unter anderem auch Beispiele, wie man die C-Funktionen verwendet.

von PittyJ (Gast)


Bewertung
0 lesenswert
nicht lesenswert
man gettimeofday

von Johnny B. (johnnyb)


Bewertung
0 lesenswert
nicht lesenswert
Wenn ich "Millisekunden" im Zusammenhang mit Raspberry und Raspbian 
höre, läuten bei mir die Alarmglocken.
Raspbian ist kein Echtzeitbetriebssystem, dem muss man sich bewusst 
sein. Selbst wenn es so eine Funktion gäbe, wäre die Genauigkeit nicht 
vorhersehbar.

von Peter II (Gast)


Bewertung
1 lesenswert
nicht lesenswert
Johnny B. schrieb:
> Wenn ich "Millisekunden" im Zusammenhang mit Raspberry und Raspbian
> höre, läuten bei mir die Alarmglocken.
> Raspbian ist kein Echtzeitbetriebssystem, dem muss man sich bewusst
> sein. Selbst wenn es so eine Funktion gäbe, wäre die Genauigkeit nicht
> vorhersehbar.

warum sollte die Genauigkeit nicht vorhersehbar sein? Auch eine Rapsi 
hat Timer die sehr genau sind und diese werden dafür nur abgefragt.

Du meinst das Timing eines kompletten Programm, ja das ist nicht auf die 
MS genau vorhersehbar. Aber die Zeit selber ist kein Problem.

von Simo (Gast)


Bewertung
0 lesenswert
nicht lesenswert
vielen Dank für die nachrichten...

joa millis() kenn ich von Arduino <- weiß nich was für nen kack ich da 
oben geschrieben habe, aber vermutlich war ich opfer der Autokorrektur 
und habs nicht gemerkt.

Genauigkeit ist nicht so wichtig... ich möchte im 400ms und im 700ms 
takt 2 tools abfrage / starten

dazu brauch ich eine whileschleife die dauerläuft
1
definiere timer, old1, old2; 
2
dauer1 = 400;
3
dauer2 = 700;
4
5
while(1){
6
  timer = JETZT[ms]
7
8
  if( old1 + dauer1 < timer ) {
9
    old1 = timer //update old1
10
    machwas 1;
11
  }
12
13
  if( old2 + dauer2 < timer ) {
14
    old2 = timer //update old2
15
    machwas 2;
16
  }
17
18
19
}

leider bekomm ichs auf dem PI nicht hin :(

ob das jetzt 50ms eher oder später kommt ist VÖLLIG egal... ebenso kann 
es sein, dass "machwas 1" mit "machwas 2" kollidiert und dann eines auf 
das andere warten muss (das wären dann ~4-6ms), aber das ist völlig 
egal!

Vielen Dank

von Christoph db1uq K. (christoph_kessler)


Bewertung
0 lesenswert
nicht lesenswert
Mit Python und pigpio geht es recht genau, ein paar Mikrosekunden sollen 
es angeblich sein. Der Trick ist, schnell zwei Zeitpunkte zu erfassen 
und in Ruhe danach die Zeitdifferenz auszurechnen:

Das hier habe ich vor ein paar Tagen gepostet, aus einem anderen 
Programm umgeschrieben.
https://www.raspberrypi.org/forums/viewtopic.php?f=28&t=134270&start=25
1
def WaitDRDY():
2
    start = pi.get_current_tick()
3
    elapsed = pi.get_current_tick() - start
4
    # Waits for DRDY to go to zero or TIMEOUT seconds to pass
5
    drdy_level = pi.read(17) # ADS1256 /DRDY
6
    while (drdy_level == 1) and (elapsed < 500000):
7
        elapsed = pi.get_current_tick() - start
8
        drdy_level = drdy_level = pi.read(17)
9
    if elapsed >= 800000:
10
        print("WaitDRDY() Timeout\r\n")

von R. M. (rmax)


Bewertung
1 lesenswert
nicht lesenswert
Simo schrieb:

> dazu brauch ich eine whileschleife die dauerläuft

Solche Busy-Loops sind unter Multitasking-Betriebssystemen wie Linux 
meist keine gute Idee, weil sie unnötig Rechenzeit verbraten. 
Stattdessen gibt es Möglichkeiten, einen Prozeß schlafen zu legen "bis 
seine Zeit gekommen ist". Während der Wartezeit kann die CPU dann 
entweder andere Prozesse bearbeiten oder Strom sparen.

Schau Dir mal select() an, damit kann man sowas machen.

: Bearbeitet durch User
von Operator S. (smkr)


Bewertung
0 lesenswert
nicht lesenswert
oben genannt wurde ja schon clock_gettime()
nimm nun noch nanosleep hinzu und schon hast du deine wartefunktion ohne 
busy waiting

Wenns dir nicht um die Genauigkeit geht, kannst du auch sowas machen:
1
struct timespec sleepTime;
2
3
sleepTime.tv_nsec = 100000000; //100ms
4
sleepTime.tv_sec = 0;
5
6
int dauer1 = 0;
7
int dauer2 = 0;
8
while(1){
9
10
  nanosleep(&sleepTime, NULL);
11
12
  if(dauer1 > 3 ) {
13
    dauer1 = 0 //update old1
14
    machwas 1;
15
  } else {
16
    dauer1++;
17
  }
18
19
  if( dauer2 >6 ) {
20
    dauer2 = 0 //update old2
21
    machwas 2;
22
  } else {
23
    dauer2++;
24
  }
25
26
}

so als quick&dirty Lösung, ansonsten 2 Threads machen mit der jeweils 
eigenen nanosleep Zeit.

von Simo (Gast)


Bewertung
0 lesenswert
nicht lesenswert
@Christoph Kessler:
Python kommt nicht in Frage...

@R. Max
Select klingt spannend, leider finde ich nur wenig lösungen dir mir 
helfen, da ich zu schnell im datenbanksektor bin...
evtl. kannst du mir ne genauere erläuterung geben

@Operator S.
die idee ist gut... werde ich nochmal "genauer" verfolgen :) ...

=> trotzalledem würden mich "multithreads" noch mehr interessieren...
wie kann ich zwei sachen "gleichzeitig" abarbeiten, ohne dass diese sich 
in die quere kommen <- bisher habe ich immer nur ein Programm, dass mehr 
oder weniger von oben nach unten abarbeitet ...


Dankööö

von Operator S. (smkr)


Bewertung
1 lesenswert
nicht lesenswert
Schau dir pthread an oder generell POSIX Threads. Ist am Anfang etwas 
hakelig wenn man sich nur sequentielle Programmierung gewohnt ist, aber 
wenn mans mal raus hat, ist man auch schneller gewillt threads 
einzusetzen statt alles in einem. Definitiv die Einarbeitungszeit wert, 
auch wenns etwas länger dauern sollte. Nicht aufgeben!
Bei C++ hättest du auch std::thread, wenn das eine Option für dich ist.

von R. M. (rmax)


Bewertung
0 lesenswert
nicht lesenswert
Simo schrieb:

> @R. Max
> Select klingt spannend, leider finde ich nur wenig lösungen dir mir
> helfen, da ich zu schnell im datenbanksektor bin...
> evtl. kannst du mir ne genauere erläuterung geben

Hier ertsmal die Doku zu select():
http://man7.org/linux/man-pages/man2/select.2.html

Damit kann man auf Ereignisse ("es sind neue Daten angekommen" bzw. "es 
können Daten abgeschickt werden") auf mehreren Filedeskriptoren (offenen 
Dateien oder Netzwerkverbindungen) gleichzeitig warten und zusätzlich 
einen Timeout setzen, nach dessen Ablauf der Aufruf in jedem Fall 
zurückkehrt. Läßt man die Filedeskriptoren weg und setzt nur den 
Timeout, macht select() im Grunde das gleiche wie nanosleep(), 
allerdings mit einer zeitlichen Auflösung in Mikrosekunden statt 
Nanosekunden.

Als Alternative zu einem festen Takt (einfach, aber unflexibel) oder 
Threads (halte ich hier für Overkill) könntest Du jeweils ausrechnen, 
wieviel Zeit bis zum nächsten Ereignis noch vergehen muß und die Zeit 
für select() oder nanosleep() dementsprechend setzen.

von Christoph db1uq K. (christoph_kessler)


Bewertung
0 lesenswert
nicht lesenswert
http://abyz.co.uk/rpi/pigpio/
pigpio läuft auch mit C, das ist nicht an Python gebunden. Im 
Raspbian-Image ist es schon vorinstalliert.
Die Quellen sind auf Github:
https://github.com/joan2937/pigpio

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.