Gibt es einen einfachen Weg, um eine Liste aller aktuell wartenden Timer zu erhalten, die mit erlang:send_after
, erlang:apply_after
usw. in Erlang gestartet wurden?Aktive Timer in Erlang überprüfen
Antwort
Für Debugging-Zwecke können Sie dbg
:) verwenden.
Erstellen Sie zuerst eine ETS-Tabelle, in der alle Timerreferenzen gespeichert werden.
1> ets:new(timer_dbg, ['public', 'named_table', 'bag']).
timer_dbg
Dann eine DBG-Handler-Funktion erstellen, die von erlang Rückkehr für Anrufe überprüft: send_after, und speichert den zurück Timer Bezug auf die Tabelle
2> Fun = fun({'trace', _Pid, 'return_from', {erlang, send_after, 3}, Ref}, []) ->
2> ets:insert(timer_dbg, {Ref}), [];
2> (_Msg, []) ->
2> []
2> end.
#Fun<erl_eval.12.113037538>
die Funktion als Trace-Handler-Set. Auch ermöglichen auf den Aufruf von erlang:send_after()
auf alle Prozesse
3> dbg:tracer('process', {Fun, []}).
{ok,<0.35.0>}
4> dbg:p('all', 'c').
{ok,[{matched,[email protected],26}]}
5> dbg:tpl(erlang, send_after, [{'_', [], [{'return_trace'}]}]).
{ok,[{matched,[email protected],1},{saved,1}]}
Machen Sie einige Testanrufe zu erlang:send_after()
6> erlang:send_after(1000, self(), {}).
#Ref<0.0.0.43>
7> erlang:send_after(1000, self(), {}).
#Ref<0.0.0.47>
8> erlang:send_after(1000, self(), {}).
#Ref<0.0.0.51>
Schließlich überprüfen passend, dass die Tabelle diese Verweise enthält:
9> ets:tab2list(timer_dbg).
[{#Ref<0.0.0.51>},{#Ref<0.0.0.43>},{#Ref<0.0.0.47>}]
Auf diese Weise Sie speichern alle Timer-Referenzen, die jemals von einem Prozess erstellt wurden, der erlang:send_after()
aufruft. Sie können sie über erlang:read_timer()
abbilden, um die aktiven Timer zu filtern.
Auf ähnliche Weise können Sie Anrufe an send_after
verfolgen. Es ist auch möglich, unter cancel_timer
eine Übereinstimmung zu finden und die stornierten Referenzen manuell aus der Tabelle zu entfernen.
Wenn Sie nicht über eine Anwendung mit hoher Nachrichtenintensität verfügen, sollten Sie in der Lage sein, nach Nachrichten und/oder Funktionen zu suchen, die von diesen Zeitgebern ausgelöst wurden, und die abgelaufenen Referenzen aus der Liste entfernen.
Sie die Referenzen von send_after zurückgegeben, aply_after usw. und die Verwendung erlang retten könnte: read_timer zu prüfen, ob es noch wartet (read_timer false zurück, wenn der Timer abgebrochen wurde oder wartet nicht mehr)
Das wird nicht _all_ Timer geben, sondern nur diejenigen, die ich explizit gespeichert habe. –
das ist ein Hack aber benutze: ets: tab2list (timer_tab). Für zwei Timer gilt:
ets:tab2list(timer_tab).
[{{1288384968923398,#Ref<0.0.0.30>},
timeout,
{erlang,integer_to_list,[23]}},
{{23334621698390115688,#Ref<0.0.0.189>},
timeout,
{erlang,integer_to_list,[23]}}]
Es ist nur nützlich für 'Timer'-Modul-Timer, aber nicht für Timer, die mit' erlang: send_after', 'erlang: apply_after' erstellt wurden. – hdima
true .. und du meinst erlang: send_after nur, denke ich. Gibt es so etwas wie erlang? – user425720
Oh, du hast recht, ich kopiere nur Funktionsnamen von der ursprünglichen Frage. – hdima
auf den Code der Suche in erl_bif_timer.c denke ich, Crash-Dump der einzige Ort ist, wo Sie eine Liste aller BIF-Timer finden kann, die gerade aktiv waren. :-)
Nun, schade :) Danke! –
Ich laufe heute auf die gleiche Notwendigkeit von Tracking-Timern.
Es ist auf Produktion, also möchte ich nicht dbg verwenden. Dies sind Erlang: Timer, so dass meine vorherige Lösung nutzlos ist.
Stattdessen analysierte ich nbif_timer Parameter von binary_to_list (erlang: system_info (info)).
Ich glaube (noch nicht bestätigt), es meldet Speicher für Timer zugeordnet. Auf meinem System x64 wären es 17 Wörter mit 8 Bytes = 136 Bytes.
Die Überwachung dieses Wertes zeigt deutlich an, wenn das System eine hohe Anzahl von Timern einstellt.
genießen.
Schade, dass es keinen direkten Weg gibt, der aber für Testzwecke nutzbar genug sein sollte. (Ich plane, es in meine Eigentests zu integrieren.) – eriksoe
- 1. Testing Erlang Funktion Leistung mit Timer
- 2. erlang: START_TIMER/3 vs Timer: send_after/3
- 3. kann nicht Zustand boolean in Timer überprüfen
- 4. Hervorhebung aktive Elemente mit jQuery
- 5. Wie überprüfen Sie die Betriebszeit einer Phoenix/Elixir/Erlang-Anwendung?
- 6. aktive APC in PHP
- 7. Android-Benachrichtigungsleiste letzte aktive Aktivität öffnen?
- 8. Animation und aktive Taste
- 9. ERLANG - Timing Anwendungen
- 10. hash_hmac in erlang
- 11. Zustand in Erlang Digraphen
- 12. Erlang Edoc in Emacs
- 13. Kompilieren Erlang in Intellij
- 14. Genaue Uhr in Erlang
- 15. JSON in Erlang analysieren
- 16. Umschreiben Erlang in F #
- 17. Selektives Empfangen in Erlang
- 18. idiomatische Prozesssynchronisation in Erlang
- 19. SOAP-Webdienste in Erlang
- 20. Erklärung ETS in Erlang
- 21. Ausnahmefehler in Erlang
- 22. Anonyme Variablen in Erlang
- 23. sha256 Verschlüsselung in erlang
- 24. Backtracking in Erlang
- 25. nicht initialisierte Konstante Timer :: Timer
- 26. Erlang: Wie implementiert man Erlang Listenverständnis?
- 27. Wie führe ich eine Erlang-Anwendung in der Erlang-Shell
- 28. Konvertieren eines Erlang-C-Portbeispiels in Erlang-Golang
- 29. Erlang Compilation - Erlang als eigenständige ausführbare
- 30. Mehrere aktive Ergebnismengen in NCache
Eigentlich gibt es kein 'erlang: apply_after' sondern nur' timer: apply_after'. Hast du wirklich 'erlang:' gemeint, aber nicht 'timer:'? Denn Timer, die mit 'erlang: send_after' und' erlang: start_timer' erstellt wurden, sind komplett anders und leichter als Timer, die mit dem 'timer' Modul erstellt wurden. – hdima
Ich meine 'erlang:' weil ich bereits wusste, wie man mit Timers umgeht, die von 'timer:' erstellt wurden :) –
Warum würden Sie das brauchen? –