Generated reference › Simulation Pace — Control Systems/Model Wide Utilities
kind: generated#block#control-systems-model-wide-utilities

Simulation Pace — Control Systems/Model Wide Utilities

Control_Systems/Model_Wide_Utilities/Simulation_Pace · 0 input / 0 output port(s) at insert · exports to Python, MATLAB, Java, Rust, C, C++, VHDL, Verilog, SystemVerilog, PLC Structured Text

Description#

The block's own DESCRIPTION_HTML, rendered verbatim — the same text the config dialog's info panel and the library navigator show. Fix a wrong sentence in the block's .cpp (R-D9), never here.

Simulation Pace

Control Systems / Model Wide Utilities

Slows a live run down so that simulated time keeps step with the wall clock. At each of its sample hits the block measures how far the run is ahead of the wall clock,

error = (t − t₀) / Pace − (wall(t) − wall(t₀)),

in wall-clock seconds, where t₀ is the run's first hit, and waits that long when it is positive – never more than 10 s per hit. A run that is on time or behind is not held back at all. It has no ports and changes no signal.

Ports

  • None. Not one input, not one output. The pace error is shown on the block's face during a live run instead of on a port – see Notes.

Parameters

  • Simulation Pace – simulation seconds per wall-clock second, a positive finite scalar. 1 (the default) is real time, 2 runs twice as fast as real time, 0.5 half as fast. Zero, a negative value, infinity or a matrix is refused when the run starts.
  • Sleep Mode – how the block waits:
    • Auto – the default; the same as Thread Sleep.
    • Thread Sleep – the solver thread sleeps, using no processor time. Timing is as fine as the operating system's sleep, a millisecond or so.
    • Busy-Wait – the solver thread spins on the clock: the most exact timing, at the cost of one processor core for the whole wait.
    • Off – never waits. The error is still measured and shown, which tells you how much faster than the chosen pace the model can run.
  • Sampling Time (s) – zero or less inherits the solver's rate; a positive value runs the block at that period. The block waits only at its own hits, so this is how finely the run is paced; inherited, it paces every step.

Which runs are paced

Only a live run – one started with Run, or a console run. The trace computations behind code-export verification, the Simulink parity suite and the documentation samples are never paced, so this block never slows a test suite down. Pausing a run, stepping it in debug mode, or an infinite run wrapping its clock back to the start makes the run fall far behind the wall clock; when the error goes below −1 s, or time goes backwards, the block starts its schedule again from that hit instead of racing to catch up.

Code export

All ten targets – Python, MATLAB, Java, C, C++, Rust, VHDL, Verilog, SystemVerilog and PLC Structured Text – and in every one of them the block is a comment and nothing else. A generated core is stepped by whatever calls it (a real-time scheduler, a test bench, a PLC task), so pacing it is the caller's job; a wait inside the core would hold up that caller, and the hardware languages have no wall clock to wait on. This is what Simulink Coder does with the same block: its code-generation file says the pacer "generates no code, it is only active in interpreted simulation".

Simulink bridge

Both directions, to aerolibanimutils/Simulation Pace (Aerospace Blockset). Simulation Pace ↔ SimulationPace; Sleep Mode ↔ SleepMode, one for one: Auto ↔ Auto, Thread Sleep ↔ MATLAB Thread, Busy-Wait ↔ Busy-Wait, Off ↔ Off. OutputPaceError is always written as off: a Simulink block with it on has an output port this block does not, and is reported on import. Sampling Time (s) → SampleTime, as on every block; the inherited default crosses as -1, which Simulink's pacer accepts (it refuses 0).

Notes

  • No state and no arithmetic on any signal: removing the block changes no result, only how long a live run takes.
  • One per model. A second Simulation Pace in the same model stops the run when it starts, even with Sleep Mode Off – as Simulink does.
  • The last hit of a run does not wait, as in Simulink: the run ends as soon as it is computed.
  • The face shows the pace and, during a live run, the latest error: positive is ahead of the wall clock, negative is behind. Simulink can output that error on a port; here it is only shown, because it is a wall-clock measurement that no two runs reproduce and that generated code would never move.
  • A pace whose wait per hit, Sampling Time / Pace, exceeds 10 s is warned about at the start of the run and each wait is limited to 10 s, as in Simulink.

Code facts#

FactValue
registered typeControl_Systems/Model_Wide_Utilities/Simulation_Pace
familyControl_Systems/Model_Wide_Utilities
solver environment classICoreBlock_0_Control_Systems_1_Model_Wide_Utilities_2_Simulation_Pace
sourcesrc/ICoreBlocks/ICoreBlockLibrary/Blocks/Control_Systems/Model_Wide_Utilities/Simulation_Pace/ICoreBlock_0_Control_Systems_1_Model_Wide_Utilities_2_Simulation_Pace.cpp
headersrc/ICoreBlocks/ICoreBlockLibrary/Blocks/Control_Systems/Model_Wide_Utilities/Simulation_Pace/ICoreBlock_0_Control_Systems_1_Model_Wide_Utilities_2_Simulation_Pace.h
default size on canvas120 × 70 px
ports at insert0 in, 0 out
code generators implementedPython, MATLAB, Java, Rust, C, C++, VHDL, Verilog, SystemVerilog, PLC Structured Text

Ports#

The constructor creates no port explicitly — the port list comes from registerInitialPorts (0 in, 0 out) or from the block's configuration.

Configuration variables#

Config variableDefaultSimulink parameter
Simulation Pace1SimulationPace
Sleep ModeAuto%~%Thread Sleep%~%Busy-Wait%~%Off~~AutoSleepMode

Every block also carries Sampling Time (s) from ICoreBlockSolverEnvironment: zero or less inherits the solver's rate, a positive value runs the block at that period.

supportSupport::Both
Simulink pathaerolibanimutils/Simulation Pace
port-count rulePortsParam::None
SampleTime parameteryes
always setOutputPaceError = off
ICore configSimulink parameterValue translation
Simulation PaceSimulationPacepasses through
Sleep ModeSleepModeAuto → Auto, Thread Sleep → MATLAB Thread, Busy-Wait → Busy-Wait, Off → Off

Caveat (shown to the user): Aerospace Blockset's pacer (an S-Function, saeroclockpacer). OutputPaceError is fixed at off: turning it on gives the Simulink block an output port carrying a wall-clock measurement, which this block shows on its face instead, so such a block is reported on import. The inherited Sampling Time crosses as SampleTime -1, which the pacer accepts; it refuses 0 (measured on R2026a)

Catalog contract: src/ICoreBlocks/ICoreCoder/ICoreCommandSystem/SimulinkBridge/ICoreSimulinkBlockCatalog.h

Description vs code#

The checker has a blind spot here — it could not resolve something (a grouped port bullet, a computed config name), which is reported and never counted as a pass. A reader has to settle it:

  • B0 no sample under docs/generated/samples/ — nothing to cross-check (P8.1)

The verdict above is tools/docs/check_block_descriptions.py (P7.1), which compares LISTS. It cannot read a sentence: "stateless" on a block with a state, an initial-value semantic the recursion does not implement, a "not synthesizable" caveat the HDL banner contradicts. That is the agent audit (P7.3) on BLOCK_DESCRIPTION_AUDIT.md, and this tool's green is not a substitute for one.

File banner (developer view)#

The top comment of the block's .cpp — the maths, the realization and the export strategy, addressed to whoever changes it. It must not contradict the description above (P7.5).

Simulation Pace -- slows a LIVE run down so simulated time keeps step with the wall clock Aerospace Blockset's aerolibanimutils/Simulation Pace. Zero ports, no state, no arithmetic on any signal. At each of its sample hits it compares where the run IS against where the wall clock says it should be, and waits for the difference:

error(t) = (t - t0) / Pace - (wall(t) - wall(t0)) [wall-clock seconds]

where t0 is the run's first hit. A positive error means the simulation is AHEAD of the wall clock, so the block waits that long (never more than 10 s per hit); zero or negative means it is on time or behind, and it does not wait at all. Pace is simulation seconds per wall-clock second: 1 is real time, 2 runs twice as fast as real time, 0.5 half as fast.

⚠ WHICH RUNS ARE PACED -- AND WHY A TEST SUITE IS NEVER SLOWED BY IT. Only a LIVE run waits: one started from Run (or from a console run), which the simulator reports through ICoreModelSimulator::isRunLive(). The synchronous trace computation that code-export verification, the Simulink parity suite and the documentation samples all use never sets that flag, so there the block records nothing, waits for nothing and costs one branch per hit. That mirrors Simulink itself: the pacer's own code-generation file (saeroclockpacer.tlc) says it "generates no code, it is only active in interpreted simulation", and warns in accelerator modes. Measured on R2026a: sim() under matlab -batch DOES pace -- a 2 s run took 0.98 s at Pace 4 and 0.31 s with Sleep Mode Off -- so a live console run here is paced too.

⚠ MEASURED ON R2026a (matlab -batch, a probe model per case, 2026-09-17):

  • MaskType "Simulation Pace", an S-Function (saeroclockpacer). Parameters SimulationPace (1),

SleepMode {Off | MATLAB Thread | Busy-Wait | Auto} (Auto), OutputPaceError (off), SampleTime (1/30). ZERO ports by default; OutputPaceError on adds exactly one output.

  • The pace-error output IS the formula above: 0 at the first hit, measured BEFORE that hit's

wait. Sleep Mode Off, Pace 1: at t = 1 it read 0.99926 against 0.99923 predicted; a model slowed by 0.1 s per step read -3.00366 against -3.00357.

  • The schedule is ABSOLUTE and a late run never skips ahead: a lagging model's error just

keeps falling, and the block stops waiting.

  • A wait is capped at 10 s per hit, with the warning "Specified pace is currently limited

to 10 seconds of ... wall-clock sleep per time step" when SampleTime / Pace exceeds 10.

  • The FINAL hit does not wait: with only two hits (Ts 0.1, Pace 0.005, stop 0.1) the run

took 0.2 s where a 20 s wait was asked for.

  • TWO pacers in one model are REFUSED at start, even when both are Sleep Mode Off ("only

one can be active at a time"). Pace -1, 0 and inf are refused; SampleTime 0 is refused and -1 (inherited) runs.

⚠ WHAT IS NOT CARRIED, AND WHY. The pace-error OUTPUT PORT. Its values are wall-clock

Sample results#

No sample run is committed for this block. Samples come from the headless harness (DOCS_PLAN.md P8.1) into docs/generated/samples/; until one exists this block's behaviour is witnessed by the parity and export-verification suites, not by a plot here.