Clock calibration normally takes several seconds to zero in on somewhat
accurate values for reasonable synchronization of simulated time to wall
clock time. Often this doesn't matter one way or another. However,
one thing which requires somewhat accurate clock calibration is the
pacing of output to serial ports on the host system. Pacing happens
at the configured bits per second rates as long as the simulators
instruction execution rate has been reasonably calibrated with respect
to wall clock time. A given host system will most likely simulate
instructions at the same rate from one run to the next, so running a
simulator for a little while and then examining the execution rate with
the SHOW CLOCK command can provide knowledge about the calibrated
execution rate which can be used to start a future simulator's execution
with a very good estimate of what the ultimate calibrated rate will be.
If the SHOW CLOCK shows simulator execution at 120,000,000 instructions
per second, and the simulated system has a simulated clock that runs at
60 hz, then the pre-calibrated values can be set with these commands:
sim> DEPOSIT INT-CLOCK TICK_SIZE_0 2000000
sim> DEPOSIT INT-CLOCK TICK_RATE_0 60
sim> DEPOSIT INT-CLOCK INTERNAL_TICK_SIZE 12000000
The INTERNAL_TIMER runs in the background whenever the simulator
doesn't have a calibrated timer running. It runs at 10 Hz.
Previously, only long delays that would transition the next clock
calibration would be coscheduled unless an explicit timer was
specified to coschedule with.
This may help with the problem discussed in #508
Without this change, timer events don't get queued correctly when the
simulator isn't running (i.e. when at the command prompt or as a consequence
of a RESET command (or during boot preparation)).
This only affects when timers are asynchronous which is not the current
default.
- Throttling delays are self adjusting for specific speed throttling
(K cycles and M cycles and % cycles).
- Throttling starts after THROT_DELAY seconds of execution.
- THROT_DELAY is a register accessible via EXAMINE and DEPOSIT
once throttling has been enabled.
- Throttle sleep times are recalibrated every 10 seconds based on
execution performance for the prior 10 seconds if the current
execution rate differs from the desired rate by more than
THROT_DRIFT_PCT. THROT_DRIFT_PCT defaults to 5 and is a
register accessible via EXAMINE and DEPOSIT once throttling has
been enabled.
- Addressing details reported in #508
Part of a previous change introduced logice which used the throttling
execution rate calibrated value to determine clock calibration when
throttling is enabled. This provides significantly worse results than the
normal self correcting calibration process. This commit reverses that
part of the previous change.
Added debug CHECK option to the sim_timer_activate_after() to verify
that coscheduled events actually have sim_activate_time_usecs() results
which are consistent with each other.
Additionally, coschedule tick processing now properly counts down
pending coschedule queued activities.
- Add support to query remaining usecs on pending events.
- Generalized the sim_interval adjustment in sim_idle to allow more than
a single decrement.
- More overhead reduction when idling.
- Carry usec values as double through out to fully support long wall clock
delays.
- Support for arbitrary long wait intervals in sim_activate_after with
precisely correct delays aligned with the calibrated clock once
per second.
- Proper handling of calls to sim_cancel for calibrated timer units
- Properly allow stopping of calibrated clock by calling sim_rtcn_calb
with a ticksper == 0
- Only schedule asynchronous timer activities for delays longer than
the minimal OS sleep time
- Only wake asynchronous timer thread to queue new timer events
that are shorter than the currently shortest scheduled event
Also:
- Avoid potential divide by zero when stopping a running calibrated clock.
- Quickly reflect newly calibrated clock info in additional timers that may be running
Also:
- allow a timer to dynamically stop itself (by calling sim_rtcn_calb
with tps=0), and then to start the internal timer to provide a calibration
baseline if necessary.
- Fix coschedule interval computation when the queue is empty.
- Properly select the correct timer for coscheduling without a specific tmr
- Properly adjust the coschedule queue's next time value when entries are
canceled.
- Cleaned up throttling to behave well with all potential throttling rates and
to make visible what is happening when boundaries are reached.
Additionally, calls to sim_activate_after with delay values that exceed
twice the tick size of the calibrated clock are now coscheduled with
the calibrated clock.
Historically, hosts which have a tick size slower than the tick a simulator
wants to implement can't idle effectively and keep good time.
This change allows simulators which call sim_rtcn_tick_ack() to provide
useful idling behavior while still keeping the passage of wall clock time
to time in the simulator accurate.
Also:
- Added more statistics
- Made sleep measurements more precise
- Correct idle sleep decision logic without regard to host tick size
- Fix calibration setup/teardown when host tick size is large (>10ms)
- Generalized large host tick test capability (MS_MIN_GRANULARITY)
- Fixed Windows sim_os_msec() to always use timeGetTime()
- Fixed coschedule routines (that don't mentoin a tmr) to default to
timer 0 and fallback to the internal timer otherwise.
- Removed dependency on sizeof(tv_sec) in timespec structure for MinGW
Clock devices which call sim_register_clock_unit or sim_register_clock_unit_tmr
are best behaved if they use sim_activate_after to schedule their tick events.
When the timer subsystem hasn't gotten fully initialized, devices may
attempt to coschedule schedule events before the clock has gotten
far enough along to be fully initialized. When this happens we now
make sure to avoid the potential for a zero delay which will may cause
an infinite scheduling loop.
Asynchronous clocks are now built for all simulators which are built with
SIM_ASYNCH_IO defined. The default behavior has asynchronous clocks
disabled since this is still experimental, but it can be enabled with
SET TIMER ASYNC.
Catchup clock ticks are now available, but since they're experimental,
they aren't enabled by default. Catchup ticks are only available if the
simulators clock device calls sim_rtcn_tick_ack to acknowledge processing
of clock ticks. The VAX simulators have been modified to leverage this.
Catchup clock ticks can be enabled with SET TIMER CATCHUP
Additionally, an idle threshold is provided which can be used to
influence when clock calibration may be suppressed. The default is not
to suppress calibration activities.
The various timer behaviors are visible with the SHOW TIMER command.
The state of the operating timer facilities is visible with: SHOW CLOCK
Timer events which are queued are visible with the SHOW QUEUE command.