Skip to content

analog M4d-b: the delay cell remembers its last edge -- repeated clkc falls within 1.8 % of ngspice PSP103, CK edges within 1 % (Closes #10848) - #10898

Merged
gHashTag merged 1 commit into
masterfrom
claude/analog-m4d-delay-history-10848
Oct 19, 2026
Merged

gHashTag merged 1 commit into
masterfrom
claude/analog-m4d-delay-history-10848

Conversation

@gHashTag

Copy link
Copy Markdown
Owner

Closes #10848

Follow-up of M4d (#10754, PR #10845). The gate-level SAR logic had a stateless delay cell (a table of settled delays); in the self-timed loop nothing settles, and its repeated clkc falls came 13.2 ns after Valid against ngspice's 7.0 ns. This PR gives the delay cell a state. All numbers below are from t27c test-report specs/analog/sar_logic.t27 and ngspice-47 + PSP103 (mos_tt, 50 C) runs of the committed decks.

The state model

The state of an output is its AGE: the time since it last crossed the other way (the nodes are first-order, so their voltage is a function of that time). In ngspice every edge's delay is a single-valued curve of the age (sar_delay_hist.cir, 29 pulse-train chains). The model keeps ms[SL_TCH + g], the time gate g's output last went from one known value to the other (out of the unknown start: a long rest), and scales the settled delay of an edge by a table of that age:

Table Edge Age of From (ps range, settled end)
SL_H_N1F nor3 output n1 falls (Valid rises) n1's last rise 590 .. 2887
SL_H_N2R delay cell output n2 rises n2's last fall 3944 .. 10551
SL_H_N1R n1 rises (Valid falls) n2's last rise (Miller pull-up) 5775 .. 7352
SL_H_N2F n2 falls n2's last rise 6520 .. 8081

Each table is 11 MEASURED points (linear between, flat outside), read from the fourth pulse of the 21 calibration chains (Wh = 30 ns with Wl = 16 .. 120 ns; Wl = 30 ns with Wh = 14 .. 120 ns). They are not fitted constants. Code 000 only; other codes scale it by their settled delay (not checked).

Numbers that ARE fitted or taken from a deck, with their source:

  • SL_TG_IN_LOAD = 0.43 inverter inputs (was 0.15): FITTED to the CK11 .. CK2 delay; one number, so those ten edges are not an independent check of it.
  • SL_C2_PM = 806: delay cell rise with two nor3 inputs high (Valid and CK1 on the last pulse), 4905 ps over the table's 6083 ps at that age, chain k01 of sar_delay_hist.cir. FITTED at one point.
  • SL_IV_R (626, 466, 466, 436, 466, 436, 436, 657 ps by trim code) and SL_IV_F = 114: the inverter after the delay cell sees a slow edge; MEASURED as iv_<code>_r/f in sar_delay_cell.cir.
  • A node that held a weak value when a strong driver arrives stays until the weak driver lets go (the fight of the skew window; no number).

Repeated clkc edges at the golden pace (sar_logic_ref.cir, SAR_logic + clock_gen, 11 Valid pulses), model against ngspice

Edge model ps ngspice ps error before
first fall (settled) 11858 11996 -1.2 % within 15 % (M4d bound; not re-measured)
falls 2, 3, 4 .. 10 7108, 6887, 6880 (x7) 7207, 6962, 6952 -1.4 %, -1.1 %, -1.0 % +83 .. +127 %
fall 11 (CK1 up as well) 5704 5807 -1.8 %
first rise (settled) 16145 16232 -0.5 % within 15 % (M4d bound; not re-measured)
rises 2 .. 11 14067, 14699, 14720 (x8) 14020, 14662, 14688 +0.3 %, +0.3 %, +0.2 % +6 .. +11 %

SL_REPEAT_F_BOUND_PM = 1300 and SL_REPEAT_R_BOUND_PM are removed. Every one of the 22 clkc edges is held to SL_CLKC_BOUND_PM = 80 (8 %); the issue asked for 15 %.

Held-out check

Seven pulse trains (sar_delay_hist.cir h01 .. h07: Wh / Wl = 20.2 / 19.8, 15 / 15, 25 / 25, 18 / 22, 24 / 16, 30 / 20, 22 / 38 ns, six pulses each) were not used for any table entry. Every one of their 42 falls and 42 rises is within the 8 % bound: worst 5.1 % (a fall, the second pulse of 15 / 15), the settled falls within 1.7 %, the settled rises within 0.4 %. The 21 calibration chains, whose points are in the tables, are reproduced within 0.9 % (falls) and 0.4 % (rises) at the fourth pulse, and not exactly (bound 3 %).

CK edge error (FR-002)

model ps ngspice ps error
CK11 .. CK2, M4d 458 548 -16 %
+ the fight of the skew window 505 548 -7.8 %
+ SL_TG_IN_LOAD (fitted) 546 548 -0.4 %
CK1 672 654 +2.8 %

Explanation: the keeper's NMOS still pushes a weak 1 while the slave's NMOS pulls net3 down, so ngspice's net3 falls 28 ps after nCLK (133 ps after Valid), not 83 ps (the tgate arc alone). The remaining 41 ps is the tgate In terminal, which no arc deck measures: 0.15 inverter inputs was a guess, 0.43 reproduces ngspice. What is not explained: why the real terminal is 0.43 (4 um of diffusion, measured by nothing here), and the input-slope term is still absent. A CK FALLING (the swapped-pins control only) is still 20 % early (426 against 535 ps), unchanged. SL_CK_BOUND_PM 200 -> 50 permille, SL_CK_ABS_PS 100 -> 30.

Negative control

With the history switched off (ms[SL_HON] = 0, the stateless cell of M4d) the golden pace's repeated falls are 83 .. 90 % late (828 .. 895 permille) and fail the check the remembering cell passes, and the 15 / 15 ns pace is 181 % off (assert in negative_control_the_stateless_delay_cell_fails_the_repeated_fall_check_that_the_remembering_one_passes).

Other

  • The SAR_GOLDEN_SUBCKTS extraction line in the spec header and in sar_logic_ref.cir / sar_gate_arcs.cir (grep -v -E '^.(end|global)') dropped every .ends too; ngspice stopped at "Mismatch of .subckt ... .ends". Fixed to '^\.(end|global)([[:space:]]|$)' (verified identical to the file the decks need).
  • The new deck uses option klu and set num_threads=8: 3 m 38 s for the 29 chains.
  • ms grew from 5000 to 5500 slots (SL_TCH, SL_CELL, SL_FED, SL_HON); no other spec imports sar_logic.

Gates

  • t27c test-report specs/analog/sar_logic.t27: tests 17, pass 17, FAIL 0, vacuous passes 0 of 17 (t27b: 17 passed, 0 failed).
  • t27c seal --save then --verify: all hashes MATCH; no other seal imports sar_logic.
  • python3 -I tools/dupe_scan.py: no new duplicate body, none of the known groups grew.
  • tri types ratchet: RATCHET: CLEAN.

Not covered

Trim codes other than 000 (the history of 000 is scaled), ages below the calibrated range (Wh < 14 ns, Wl < 16 ns; a scratch prototype of the same law was 17 % off on the first rise of a 12 / 28 ns train), the closed loop through the comparator (M4e), other corners. Model speed against ngspice is not claimed.

🤖 Generated with Claude Code

… falls within 1.8 % of ngspice PSP103, CK edges within 1 % (Closes #10848)

The gate-level SAR logic of M4d had a stateless delay cell: a table of settled
delays. In the self-timed loop nothing settles, and the repeated clkc falls came
13.2 ns after Valid against ngspice's 7.0 ns (83 to 90 % late).

- The state of the nor3 output n1 and of the delay cell output n2 is their AGE,
  the time since each last crossed the other way. Four tables of age against
  delay (SL_HIST, 11 measured points each) from 21 calibration chains of the new
  specs/analog/decks/sar_delay_hist.cir scale the settled delays of the nor3 fall
  and rise and of the delay cell rise and fall; the age is ms[SL_TCH + g].
- Held-out check: 7 pulse trains (other spacings, none in the tables) are
  reproduced at every fall and rise within 5.1 %, the settled ones within 1.7 %.
- Negative control: ms[SL_HON] = 0 (the stateless cell) fails the repeated-fall
  check by 83 to 90 % (180 % at the 15 / 15 ns pace).
- Last fall with CK1 up as well: SL_C2_PM, fitted at one point.
- Inverter after the delay cell: ngspice's delay for a slow edge (SL_IV_R/F).
- CK edges (were 17 % early): the fight of the skew window (a node that held the
  weak value stays until the weak driver lets go) and the tgate In terminal load
  (SL_TG_IN_LOAD, fitted); CK11 .. CK2 within 1 %, CK1 3 % late.
- SL_REPEAT_F_BOUND_PM = 1300 and SL_REPEAT_R_BOUND_PM removed; every clkc edge is
  held to SL_CLKC_BOUND_PM = 8 %.
- The SAR_GOLDEN_SUBCKTS extraction line in the header and two decks dropped every
  `.ends`; fixed.

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
@gHashTag
gHashTag enabled auto-merge (squash) October 19, 2026 05:59
@gHashTag
gHashTag disabled auto-merge October 19, 2026 06:15
@github-actions

Copy link
Copy Markdown
Contributor

PR Dashboard

Generated at: 2026-10-19 06:34:42 UTC

Summary

Status Count
Total Open PRs 50
PRs with Failing Checks 45
PRs with All Checks Green 5
READY 2
FAILING 45
PENDING 0
NO CHECKS YET 0

These columns do not partition: 2 + 45 + 0 + 0 = 47, and there are 50 open PRs. A PR is being counted twice or not at all.

Seal Status

  • ⚠️ STALE -- sha256(compiler.rs)=88b8cb73ceda != manifest seal=87e5cbd3ad94.
    The committed NMSE numbers were certified against an older compiler.rs.
    Run scripts/reseal-check.sh locally for the two-step reseal command (advisory; not a merge gate).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

analog M4d-b: the delay cell is history dependent -- repeated clkc falls 83-127 % late in the gate-level model

2 participants