FA-88941 / Digital logic simulation / Open access
Transition exactly one setup time before the edge flagged · case 01
Data that changes exactly setup time units before the clock edge is reported as a setup violation.
ROOT CAUSE
The setup window is closed at its start, including the instant e - setup.
THE FAILURE
The setup window is closed at its start, including the instant e - setup.
Unsuccessful approach: Also closing the upper bound moves the edge instant from hold into setup without fixing the start boundary.
Case contract
Input [c0, clock, data, setup, hold]: c0 is the initial clock level, clock is time-sorted [t, v] transitions (possibly redundant), data is a list of data transition times. Rising edges are 0->1 changes only. For every data time t and every rising edge e: e-setup < t < e is a 'setup' violation, e <= t < e+hold is a 'hold' violation. Return all [e, t, kind] sorted by edge, then time.
Why this case matters
Timing checks in gate-level simulation decide which transitions corrupt a register; window boundaries and edge extraction are the classic bug sites.
1 / The failure
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(*args):
c0, clock, data, s, h = args
edges = []
prev = c0
for t, v in clock:
if prev == 0 and v == 1:
edges.append(t)
prev = v
out = []
for t in data:
for e in edges:
if e - s <= t < e:
out.append([e, t, 'setup'])
elif e <= t < e + h:
out.append([e, t, 'hold'])
return sorted(out)
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 18, 27], 3, 2], [[10, 8, 'setup'], [20, 18, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 29], 3, 2], [[20, 20, 'hold'], [30, 29, 'setup']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 25], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [21, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [13, 1]], [3, 5, 11], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 6], 2, 2], [[4, 3, 'setup']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 19, 27], 3, 2], [[10, 8, 'setup'], [20, 19, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 30], 3, 2], [[20, 20, 'hold'], [30, 30, 'hold']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 26], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [22, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [14, 1]], [3, 5, 12], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 5], 2, 2], [[4, 3, 'setup'], [4, 5, 'hold']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 17, 27], 3, 2], [[10, 8, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 29], 3, 2], [[20, 20, 'hold'], [30, 29, 'setup']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 25], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [23, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [15, 1]], [3, 5, 13], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 6], 2, 2], [[4, 3, 'setup']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 18, 27], 3, 2], [[10, 8, 'setup'], [20, 18, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 30], 3, 2], [[20, 20, 'hold'], [30, 30, 'hold']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 26], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [24, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [16, 1]], [3, 5, 14], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 5], 2, 2], [[4, 3, 'setup'], [4, 5, 'hold']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 19, 27], 3, 2], [[10, 8, 'setup'], [20, 19, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 29], 3, 2], [[20, 20, 'hold'], [30, 29, 'setup']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 25], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [25, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [17, 1]], [3, 5, 15], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 6], 2, 2], [[4, 3, 'setup']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])]]
for label, args, expected in fixtures[N-1]:
check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| setup window boundaries | [[10, 7, 'setup'], [10, 8, 'setup'], [20, 18, 'setup'], [30, 27, 'setup']] | [[10, 8, 'setup'], [20, 18, 'setup']] | Failed |
| transition exactly at the clock edge | [[20, 20, 'hold'], [30, 29, 'setup']] | [[20, 20, 'hold'], [30, 29, 'setup']] | Passed |
| falling clock edges are not checked | [] | [] | Passed |
| redundant high transition is not an edge | [] | [] | Passed |
| clock already high at start | [[13, 11, 'setup']] | [] | Failed |
| clock low at start rises first | [[4, 3, 'setup']] | [[4, 3, 'setup']] | Passed |
| overlapping windows reported by edge | [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']] | [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']] | Passed |
SHA-256 / e4be23ba5e16b2b6d6ae279168e35394f846914b1dc4d148e5f814e36393fbb9
2 / The unsuccessful fix
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(*args):
c0, clock, data, s, h = args
edges = []
prev = c0
for t, v in clock:
if prev == 0 and v == 1:
edges.append(t)
prev = v
out = []
for t in data:
for e in edges:
if e - s <= t <= e:
out.append([e, t, 'setup'])
elif e <= t < e + h:
out.append([e, t, 'hold'])
return sorted(out)
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 18, 27], 3, 2], [[10, 8, 'setup'], [20, 18, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 29], 3, 2], [[20, 20, 'hold'], [30, 29, 'setup']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 25], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [21, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [13, 1]], [3, 5, 11], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 6], 2, 2], [[4, 3, 'setup']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 19, 27], 3, 2], [[10, 8, 'setup'], [20, 19, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 30], 3, 2], [[20, 20, 'hold'], [30, 30, 'hold']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 26], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [22, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [14, 1]], [3, 5, 12], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 5], 2, 2], [[4, 3, 'setup'], [4, 5, 'hold']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 17, 27], 3, 2], [[10, 8, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 29], 3, 2], [[20, 20, 'hold'], [30, 29, 'setup']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 25], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [23, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [15, 1]], [3, 5, 13], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 6], 2, 2], [[4, 3, 'setup']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 18, 27], 3, 2], [[10, 8, 'setup'], [20, 18, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 30], 3, 2], [[20, 20, 'hold'], [30, 30, 'hold']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 26], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [24, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [16, 1]], [3, 5, 14], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 5], 2, 2], [[4, 3, 'setup'], [4, 5, 'hold']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])], [('setup window boundaries', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [7, 8, 19, 27], 3, 2], [[10, 8, 'setup'], [20, 19, 'setup']]), ('transition exactly at the clock edge', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [20, 22, 29], 3, 2], [[20, 20, 'hold'], [30, 29, 'setup']]), ('falling clock edges are not checked', [0, [[10, 1], [15, 0], [20, 1], [25, 0], [30, 1]], [16, 25], 3, 2], []), ('redundant high transition is not an edge', [0, [[5, 1], [10, 1], [12, 0], [25, 1]], [9, 11], 3, 2], []), ('clock already high at start', [1, [[4, 1], [8, 0], [17, 1]], [3, 5, 15], 2, 2], []), ('clock low at start rises first', [0, [[4, 1], [8, 0], [12, 1]], [3, 6], 2, 2], [[4, 3, 'setup']]), ('overlapping windows reported by edge', [0, [[10, 1], [11, 0], [12, 1]], [11, 12], 3, 3], [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']])]]
for label, args, expected in fixtures[N-1]:
check(label, solve(*args), expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| setup window boundaries | [[10, 7, 'setup'], [10, 8, 'setup'], [20, 18, 'setup'], [30, 27, 'setup']] | [[10, 8, 'setup'], [20, 18, 'setup']] | Failed |
| transition exactly at the clock edge | [[20, 20, 'setup'], [30, 29, 'setup']] | [[20, 20, 'hold'], [30, 29, 'setup']] | Failed |
| falling clock edges are not checked | [] | [] | Passed |
| redundant high transition is not an edge | [] | [] | Passed |
| clock already high at start | [[13, 11, 'setup']] | [] | Failed |
| clock low at start rises first | [[4, 3, 'setup']] | [[4, 3, 'setup']] | Passed |
| overlapping windows reported by edge | [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'setup']] | [[10, 11, 'hold'], [10, 12, 'hold'], [12, 11, 'setup'], [12, 12, 'hold']] | Failed |
SHA-256 / df3b5dd6c9ed2137b07d21b6347ae25c8b9cee3f757ec2a81c0836e9643324a5
HELD IN THE MEMBER ARCHIVE
The verified repair and its recorded checks are member-only.
This mechanism has 7 recorded checks per implementation. The open-access tier publishes the failure and the unsuccessful fix; the repaired source that passes every check, and the observations that prove it, are available to members.
Every case sharing this mechanism uses the same contract and the same repair, so this one record is held back for all of them.
Member access is invitation-based. Sign in with your invited account to inspect the repair.
Sign in to the archive ↗Verification & scope
A deterministic bounded teaching model of one simulator rule set; the contract is stipulated and is not a claim of conformance to any HDL standard or commercial simulator. This reproducer isolates one failure mechanism. Results cover the supplied fixtures. Variants within a family share a test contract and should remain grouped when constructing evaluation splits. Related mechanisms with a shared evaluation_group must also remain together; these controlled models are not independent production incidents.
Observations recorded using Python 3.12.14 at 2026-09-29T14:51:12.984258+00:00.
Case digest / fef010c68d0915db4c302f4070974db27c6860e59b7a1a7e1ce468b4e04e4733