Time Funktion, weche Zeiteinheit?

Für Fragen zur Programmiersprache auf welcher Lazarus aufbaut

Re: Time Funktion, weche Zeiteinheit?

Beitragvon mschnell » 24. Okt 2018, 09:05 Re: Time Funktion, weche Zeiteinheit?

Unter Windows oder "normalem" Linux ist eine Zeitmessung sowieso nur sinnvoll, wen die zeitlichen Messpunkte nicht kritisch sind. Das OS kann Dein Programm ungefragt Sekunden lang einfach nicht ranlassen, wenn da irgendwelche internen Prozesse Vorrang haben (z.B. ein USB-Stick wird erkannt) .

-Michael
mschnell
 
Beiträge: 3284
Registriert: 11. Sep 2006, 09:24
Wohnort: Krefeld
OS, Lazarus, FPC: svn (Window32, Linux x64, Linux ARM (QNAP) (cross+nativ) | 
CPU-Target: X32 / X64 / ARMv5
Nach oben

Beitragvon Timm Thaler » 24. Okt 2018, 11:52 Re: Time Funktion, weche Zeiteinheit?

Naja, die Wahrscheinlichkeit dafür ist mit Mehrkern-Prozessoren deutlich gesunken. Und wenn man wirklich zeitkritische Sachen machen muss, kann man auch - konnte man zumindest früher unter Windows - die Prozesspriorität kurzzeitig bis auf "Realtime" erhöhen. Aber wirklich nur kurzzeitig, denn das hat den Rest fast komplett lahmgelegt. Geht das heute nicht mehr?
Timm Thaler
 
Beiträge: 833
Registriert: 20. Mär 2016, 22:14
OS, Lazarus, FPC: Win7-64bit Laz1.9.0 FPC3.1.1 für Win, RPi, AVR embedded | 
CPU-Target: Raspberry Pi 3
Nach oben

Beitragvon mschnell » 24. Okt 2018, 14:05 Re: Time Funktion, weche Zeiteinheit?

Genau !

Ob man mit "Wahrscheinlichkeit dass der Messwert einigermaßen stimmt" leben kann, hängt natürlich von der Anwendung ab.

-Michael
Zuletzt geändert von mschnell am 25. Okt 2018, 10:44, insgesamt 1-mal geändert.
mschnell
 
Beiträge: 3284
Registriert: 11. Sep 2006, 09:24
Wohnort: Krefeld
OS, Lazarus, FPC: svn (Window32, Linux x64, Linux ARM (QNAP) (cross+nativ) | 
CPU-Target: X32 / X64 / ARMv5
Nach oben

Beitragvon siro » 24. Okt 2018, 14:43 Re: Time Funktion, weche Zeiteinheit?

Für Zeitmessungen unter Windows nehme ich jetzt immer folgenden Code:

Wichtig: es muss
Uses Windows mit aufgenommen werden.
Code: Alles auswählen
 
var freq,tStart,tStop:Int64;
var t:Single;
 
procedure TForm1.FormCreate(Sender: TObject);
begin
  QueryPerformanceFrequency(freq)
 
  QueryPerformanceCounter(tStart);   // Startzeit
  Sleep(1000);                           
  QueryPerformanceCounter(tStop)// Endzeit
 
  t:=(tStop-tStart) / freq;    // in Sekunden umrechnen
  Form1.caption:=FloatToStr(t)// Ausgabe
end;         
Grüße von Siro
Bevor ich "C" ertragen muß, nehm ich lieber Lazarus...
siro
 
Beiträge: 333
Registriert: 23. Aug 2016, 13:25
Wohnort: Berlin
OS, Lazarus, FPC: Windows 7 Windows 8.1 Windows 10 | 
CPU-Target: 64Bit
Nach oben

Beitragvon Timm Thaler » 24. Okt 2018, 17:42 Re: Time Funktion, weche Zeiteinheit?

Ich hab so dunkel im Hinterkopf, dass das ziemlich genau das ist, was auch GetTickCounts unter Windows macht.
Timm Thaler
 
Beiträge: 833
Registriert: 20. Mär 2016, 22:14
OS, Lazarus, FPC: Win7-64bit Laz1.9.0 FPC3.1.1 für Win, RPi, AVR embedded | 
CPU-Target: Raspberry Pi 3
Nach oben

Beitragvon siro » 25. Okt 2018, 14:12 Re: Time Funktion, weche Zeiteinheit?

Du kannst mit QueryPerformanceCounter viel präziser auflösen, wohl bis zu 100 Nanosekunden.

https://docs.microsoft.com/de-de/window ... ime-stamps
Grüße von Siro
Bevor ich "C" ertragen muß, nehm ich lieber Lazarus...
siro
 
Beiträge: 333
Registriert: 23. Aug 2016, 13:25
Wohnort: Berlin
OS, Lazarus, FPC: Windows 7 Windows 8.1 Windows 10 | 
CPU-Target: 64Bit
Nach oben

Beitragvon mschnell » 25. Okt 2018, 15:30 Re: Time Funktion, weche Zeiteinheit?

Was soll eine Hohe Auflösung nützen, wenn eine Präzision sowieso nur im Sekunden-Bereich möglich ist ?

-Michael
mschnell
 
Beiträge: 3284
Registriert: 11. Sep 2006, 09:24
Wohnort: Krefeld
OS, Lazarus, FPC: svn (Window32, Linux x64, Linux ARM (QNAP) (cross+nativ) | 
CPU-Target: X32 / X64 / ARMv5
Nach oben

Beitragvon Timm Thaler » 25. Okt 2018, 19:39 Re: Time Funktion, weche Zeiteinheit?

mschnell hat geschrieben:Was soll eine Hohe Auflösung nützen, wenn eine Präzision sowieso nur im Sekunden-Bereich möglich ist ?


Ist sie ja nicht. Mit Priorität auf RealTime ist reproduzierbares Timing im 100usec und msec-Bereich möglich. Ich hab das mal für MM-Protokoll für Modellbahn über die serielle Schnittstelle gemacht*. Zumindest unter Win98 ging das, ob das moderne OS noch zulassen weiß ich nicht.

Man muss aber aufpassen, das System wird echt unbedienbar, wenn man vergisst die Prio wieder zurückzustellen, und nach 2 Sekunden schießt Windows das Programm dann ab.

*) und natürlich geht das nur mit echten Uarts, nicht mit OS-gepufferten USB-seriell-Wandlern.
Timm Thaler
 
Beiträge: 833
Registriert: 20. Mär 2016, 22:14
OS, Lazarus, FPC: Win7-64bit Laz1.9.0 FPC3.1.1 für Win, RPi, AVR embedded | 
CPU-Target: Raspberry Pi 3
Nach oben

Beitragvon siro » 26. Okt 2018, 07:15 Re: Time Funktion, weche Zeiteinheit?

Die hohe Auflösung gibt Sinn wenn man mal eine Abschätzung für die Laufzeit einer Funktion haben möchte,
oder vergleichen will, geht der Code schneller, oder doch eher da andere.

@TimmThaler:
Schade, haste leider recht, die echten Uarts gibts ja nicht mehr.
Da konnte ich noch direkt die Interrupts programjerien usw.
Mit den USB Convertern geht das leider nicht mehr. Die Puffern zu viel.
Man hinkt immer hinterher, obwohl man das teilweise einstellen kann.
Grüße von Siro
Bevor ich "C" ertragen muß, nehm ich lieber Lazarus...
siro
 
Beiträge: 333
Registriert: 23. Aug 2016, 13:25
Wohnort: Berlin
OS, Lazarus, FPC: Windows 7 Windows 8.1 Windows 10 | 
CPU-Target: 64Bit
Nach oben

Beitragvon Timm Thaler » 26. Okt 2018, 09:36 Re: Time Funktion, weche Zeiteinheit?

siro hat geschrieben:Schade, haste leider recht, die echten Uarts gibts ja nicht mehr.
Da konnte ich noch direkt die Interrupts programjerien usw.


Zum einen haben viele Motherboards noch eine COM1, nur nicht nach aussen geführt. Zum anderen gibt es PCI-Steckkarten für bis zu 8 Uarts. Die sind schon sehr Echtzeit. Nur über Register ansprechend kannst Du die auch nicht, das geht aber seit Win98 nicht mehr, oder war es Win95?

Also wer noch echte Uarts braucht, hat schon Möglichkeiten.
Timm Thaler
 
Beiträge: 833
Registriert: 20. Mär 2016, 22:14
OS, Lazarus, FPC: Win7-64bit Laz1.9.0 FPC3.1.1 für Win, RPi, AVR embedded | 
CPU-Target: Raspberry Pi 3
Nach oben

Beitragvon mschnell » 26. Okt 2018, 10:45 Re: Time Funktion, weche Zeiteinheit?

Timm Thaler hat geschrieben: Mit Priorität auf RealTime ist reproduzierbares Timing im 100usec und msec-Bereich möglich.

Die Frage ist nicht nach "möglich" sondern nach "garantiert".

-Michael
mschnell
 
Beiträge: 3284
Registriert: 11. Sep 2006, 09:24
Wohnort: Krefeld
OS, Lazarus, FPC: svn (Window32, Linux x64, Linux ARM (QNAP) (cross+nativ) | 
CPU-Target: X32 / X64 / ARMv5
Nach oben

Beitragvon Timm Thaler » 26. Okt 2018, 12:53 Re: Time Funktion, weche Zeiteinheit?

mschnell hat geschrieben:Die Frage ist nicht nach "möglich" sondern nach "garantiert".


Dann schreib ichs halt noch mal um: Mit Priorität auf RealTime ist reproduzierbares Timing im 100usec und msec-Bereich garantiert.

Und ja, das war garantiert. Mit RealRTime hattest Du die höchste Priorität, und alle anderen Prozesse wurden zurückgestellt. Da reagierte auch kein Fenster mehr und andere Programme hatten Pause. Da liefen nur noch die rudimentärsten Betriebssystemaufgaben, die dann zum Beispiel Dein Programm abgeschossen haben, wenn Du das zu lange getrieben hast.
Timm Thaler
 
Beiträge: 833
Registriert: 20. Mär 2016, 22:14
OS, Lazarus, FPC: Win7-64bit Laz1.9.0 FPC3.1.1 für Win, RPi, AVR embedded | 
CPU-Target: Raspberry Pi 3
Nach oben

Beitragvon mschnell » 26. Okt 2018, 13:29 Re: Time Funktion, weche Zeiteinheit?

OK ! Super !

Mit welchen Windows Versionen geht das und wie genau (in Lazarus) ?

Gruß und Dank,
-Michael
mschnell
 
Beiträge: 3284
Registriert: 11. Sep 2006, 09:24
Wohnort: Krefeld
OS, Lazarus, FPC: svn (Window32, Linux x64, Linux ARM (QNAP) (cross+nativ) | 
CPU-Target: X32 / X64 / ARMv5
Nach oben

Beitragvon Timm Thaler » 26. Okt 2018, 21:03 Re: Time Funktion, weche Zeiteinheit?

mschnell hat geschrieben:Mit welchen Windows Versionen geht das und wie genau (in Lazarus) ?


Nix Lazarus. Das war in PureBasic unter Zugriff auf die Win-Api.

Hiermit wurde der Kalibrierwert ermittelt für 100usec:

Code: Alles auswählen
Procedure.f InitTimer()
  FREQ.Large_integer 
  mem = AllocateMemory(8)  ;Speicher reservieren, sonst gehts nich
  If QueryPerformanceFrequency_(mem)  ;Bestimmen der frequenz
    CopyMemory(mem, @FREQ, 8)  ;Variable kopieren
    Zeit.f = (FREQ\lowpart) / 10000  ;Kalibrierwert Counts pro 100usec
    ProcedureReturn Zeit.f
  Else
    ProcedureReturn 0  ;kein Hardware-Timer
  EndIf
  FreeMemory(mem) 
EndProcedure


Hiermit wurde die Pause erzeugt:

Code: Alles auswählen
Procedure.f DelayTimer(tdelay.f)
  TIMER.Large_integer
  mem = AllocateMemory(8)  ;Speicher reservieren, sonst gehts nich
  If QueryPerformanceCounter_(mem)
    CopyMemory(mem, @TIMER, 8)
    start = TIMER\lowpart  ;alten Low-wert sichern
    Repeat
      If QueryPerformanceCounter_(mem)
        CopyMemory(mem, @TIMER, 8)
        Zeit.f = TIMER\lowpart - start
      EndIf
    Until Zeit >= tdelay
    ProcedureReturn Zeit.f
  Else
    ProcedureReturn 0  ;kein Hardware-Timer
  EndIf
  FreeMemory(mem)
EndProcedure


Und hiermit wurde es aufgerufen:

Code: Alles auswählen
  SetPriorityClass_(GetCurrentProcess_(),#REALTIME_PRIORITY_CLASS) 
  ComSendByte(hcom, @dtxd(0), 9)
  DelayTimer(vdel * t100us)
  ComSendByte(hcom, @dtxd(0), 9)
  DelayTimer(vdel * t100us)
  ComSendByte(hcom, @dtxd(0), 9)
  DelayTimer(vdel * t100us)
  ComSendByte(hcom, @dtxd(0), 9)
  DelayTimer(2 * vdel * t100us)
  SetPriorityClass_(GetCurrentProcess_(),#NORMAL_PRIORITY_CLASS)


Der Witz war, dass Märklin-Motorola eine Codierung mit "Trits" gemacht hat (http://home.mnet-online.de/modelleisenbahn-digital/Dig-tutorial-start.html), weil sie Motorola-Chips für IR-Fernbedienungen als Sender in der Basisstation und Empfänger in den Loks und Weichendekodern verwendet haben. Diese Chips haben eine Adresse und dann einen Befehl geschickt. Adresse und Befehl wurden mit kurzen oder langen Pulsen derart kodiert, dass zwei Pulse jeweils ein "Trit" mit 3 Zuständen ergaben.

Nun konnte man den Uart auf 38400 Baud und 6 Datenbits setzen und konnte dann mit den 8 Bits (Startbit, 6 Datenbits, Stoppbit) genau das Muster für 2 Pulse bzw. ein "Trit" erzeugen, das machen die ComSend-Aufrufe für jeweils eine Folge von 5 Adress-Trits + 4 Befehls-Trits. Damit der Empfänger das akzeptiert, musste der Befehl aber in einem engen Zeitraster wiederholt werden. Das Zeitraster machen die DelayTimer-Aufrufe.

Für Loks wurde mit der halben Taktrate wie für Weichen gesendet. Da der Empfänger nur jeweils Befehle seiner Taktrate (eingestellt mit RC-Glied) erkannte, konnte man alle Adressen doppelt belegen.

Märklin hat hier ganz clever die IR-Fernbedienungschips zweckentfremdet. Heute würde man das natürlich mit einem µC machen.
Timm Thaler
 
Beiträge: 833
Registriert: 20. Mär 2016, 22:14
OS, Lazarus, FPC: Win7-64bit Laz1.9.0 FPC3.1.1 für Win, RPi, AVR embedded | 
CPU-Target: Raspberry Pi 3
Nach oben

• Themenende •
Vorherige

Zurück zu Freepascal



Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder und 12 Gäste

porpoises-institution
accuracy-worried