Unplugged-cable behavior fixed end to end: heat grid rolls on the slot boundary (view computes the newest slot from the draw clock; history sampled every frame so slots color within a frame; noise phase displayed as commanded straight from the shared clock — radiating and the per-slot vote deleted), SNR ghost panic disambiguated via the PMA 1.1 latch (link dropped mid-read discards the batch, ghost on a proven-up link still dies), measure skips the 25s relink wait when the ECD verdict says faulted and the header says MEASURING instead of GOOD while a diag runs, RollBall mailbox deadline resized to 10s from bench measurement (<25ms linked, ~220ms no-link, >3s during a live plug's training; docs/modules/wiitek updated)

This commit is contained in:
flamingcow
2026-08-17 21:29:02 -07:00
parent 916c0150ef
commit be2bf56fa7
7 changed files with 81 additions and 40 deletions
+16 -7
View File
@@ -326,8 +326,10 @@ func (d *display) heatCell(rowY, k int, c rgb) {
// The verdict names the newest thing wrong at any horizon: the cable's own
// fault first, then the most recent traffic fault with its age, and only a
// clean record reads GOOD.
func (d *display) drawHeader(v view, phy phyDisplay, hv histView, now time.Time) {
// clean record reads GOOD. While a measure runs the tester is asserting
// nothing, and says so instead of GOOD.
func (d *display) drawHeader(v view, phy phyDisplay, hv histView, measuring bool,
now time.Time) {
good := true
word, sub := "GOOD", []seg{{d.text, "no faults", uiInk2}}
if i, age, ok := hv.newestFault(now); ok {
@@ -349,13 +351,18 @@ func (d *display) drawHeader(v view, phy phyDisplay, hv histView, now time.Time)
if !good {
col = uiCrit
}
if measuring {
word, sub, col = "MEASURING", []seg{{d.text, "cable diag running", uiInk2}}, uiMuted
}
rx, ry := uiMargin, headerTop
d.fb.roundRect(rx, ry, ringD, ringD, ringD/2, col)
d.fb.roundRect(rx+ringEdge, ry+ringEdge, ringD-2*ringEdge, ringD-2*ringEdge,
ringD/2-ringEdge, uiBg)
if good {
switch {
case measuring:
case good:
d.check(rx+ringD/2, ry+ringD/2, 44, col)
} else {
default:
d.cross(rx+ringD/2, ry+ringD/2, 40, col)
}
@@ -476,11 +483,13 @@ func (d *display) drawRows(v view, phy phyDisplay, measuring bool, nv noiseView,
} else {
d.colText(d.text, nowR, y, state, uiInk2)
}
// The lane shows the commanded phase, a pure function of each
// slot's parity; only slots the run never lived through are unknown.
for k, s := range hv.slots {
c := uiCellNA
if s.sampled && s.noiseN > 0 {
if s.sampled {
c = uiNoise0
if 2*s.noiseOn >= s.noiseN {
if slotUp(s.seq) {
c = uiNoise
}
}
@@ -548,7 +557,7 @@ func (d *display) render(v view, elapsed time.Duration, phy phyDisplay,
fb := d.fb
fb.fill(uiBg)
d.drawHeader(v, phy, hv, time.Now())
d.drawHeader(v, phy, hv, measuring, time.Now())
d.hairline(d.headerH - 1)
d.drawColHeaders()
d.drawRows(v, phy, measuring, nv, hv, target)