Tcl Source Code

View Ticket
Login
Ticket UUID: fdfbd5e10fefdb605abf34f65535054c323d9394
Title: Event, Notifier and Timer optimizations / implementation of TIPs #302, #434
Type: RFE Version: 8.5 / 8.6
Submitter: sebres Created on: 2017-07-10 12:17:30
Subsystem: 02. Event Loops Assigned To: nobody
Priority: 5 Medium Severity: Minor
Status: Open Last Modified: 2021-09-03 12:31:16
Resolution: None Closed By: nobody
    Closed on:
Description:

Implementation:

  - [sebres-8-6-event-perf-branch] - 8.6 based branch
  - [sebres-8-5-event-perf-branch] - 8.5 based branch

First implemented (squashed rebased and cherry-picked) for 8.5-branch, because I made it basically for fork of this branch (it was just easy as direct for 8.6).

Contains:

  • massive performance optimization of event-driven handling (test-cases included), so can be see as part of flightaware/Tcl-bounties#21;
  • whole event-driven functionality is up to 1000-times faster now (especially by large event resp. timer lists, but also basic multi-threaded event-related things like async-IO, reflected channels, etc.);
  • provided monotonic time (windows/unix);
  • timer events and wait facilities are time-jump safe at all - implementation for TIP #302.
  • full NRT- resp. RTS-capabilities (micro- resp. nanoseconds precise);
  • implemented wide-clicks on unix (1 wide-click == 0.001 microseconds (1 nanosecond)), so more precise now (e. g. by time measurement etc.);
  • windows high-resolution time rewritten without calibration thread now (faster, more robust and provides in addition monotonic time, not affected from the time-jumps);
  • implements new sub-command after at for async trigger resp. sleep using absolute time (in seconds), that also time-jump safe, and in contrary to after $offs uses absolute based time as due-time.
    after at [clock scan "16:00:00"] {do_it_in_1600}
    after at [clock scan "+1 minute"]; # wait to the next minute
  • thus fully implements flightaware/Tcl-bounties#2
  • timer-events distinguish now between relative time-intervals (which use monotonic based time) and absolute due-time (which uses real-time base);
  • ultimate solution (resp. fix) for ticket 0520d17284500573d7c46aa88e0c6b4ebc9b6a02
  • handling round about objects returned by after (and some internal interfaces) are more faster now, because hold the timer-event in the internal representation of object, so e. g. after info, after cancel etc don't need to search an event in event-lists anymore (and therefore don't block the list with lock for the long time);
  • event (Tcl_Event) prolongation functionality (setting of event->proc to the callback causes reattach of this event to end of the queue, in contrary to return 0, which leaves the event on the current position, and thus can repeat it too early);
  • timer prolongation functionality (ATM only in C-API as TclpProlongTimerEvent, can be later used as new sub-command after prolong);
  • Bonus:
    • commands vwait and update can control which events should be accepted:
      update -timer
      update -noidle
      vwait -async -timer x
    • commands vwait can use optional timeout:
      if {![vwait -timer 10 tmrVar]} continue; # do something other resp. try later
      if {![vwait 1000 evVar]} { error "timeout occurred" }
    • commands vwait can work similar to update, without waiting for events (process only already occurring events):
      if {[info exists evVar] || [vwait -nowait 10 evVar]} { puts "event already launched" }
      ## update and check we are done:
      while {![vwait -nowait 0 done]} { do something other }
    • commands after and vwait are microsecond precise now (so NRT-capable, also accept time as double):
      after 0.01 [list accept $socket]; # do it in 10 microseconds
      ## wait 5 µs for "x" and if not yet ready, 25 µs for "y":
      if {![vwait 0.005 x]} {vwait 0.025 y}
    • new clock sub-command clock monotonic to provide monotonic time at tcl-level also;
    • etc. (I'll provide additional info later).

Summaries of the performance test-cases:

See sebres/tcl#4 (comment) for the performance comparision.

User Comments: chw added on 2021-09-03 12:31:16:
For the POSIX implementation, there's a lack of using CLOCK_MONOTONIC
in the pthread_cond_*() functions, i.e. testing for availability and/or
usability of pthread_condattr_setclock(). This is essential for really
being immune against hiccups in CLOCK_REALTIME.

oehhar added on 2021-09-03 12:06:51:

Sebres remarked today, that this TIP also solves TIP302 for Unix and Windows.

That is really amazing stuff. Aparently, we at the TCL side have no Wizards who are even close to understand this.

Thank you again, I appreciate, Harald


sebres added on 2017-11-07 12:38:40:

Just noticed that TIPs #434, #455 are also involved (#434 almost completely implemented here, #455 partially resp. affected by introducing of new options).

Has someone already tested it? Reviews, objections, etc?


sebres added on 2017-07-13 16:10:14:

It looks like I had forgotten to back-port a small but important fix (sometimes causes busy wait in event-cycle).
Done now and merged in both branches.