FA-90096 / Bytecode virtual machines / Open access
Upvalues: reads decide by slot existence instead of open state · case 01
A closure reads whatever local now occupies its old slot.
ROOT CAUSE
uget chooses the stack when the slot index is in range, even for closed upvalues.
VERIFIED REPAIR
Read the stack only while the upvalue is open.
Unsuccessful approach: Testing the closed value for truthiness sends closed zeros back to the stack.
Case contract
A register/stack VM with open and closed upvalues. ["local", v] pushes a slot; ["set", s, v] and ["get", s] access slots; ["closure", id, [slots]] captures slots, reusing the existing open upvalue for a slot so closures share variables; ["uset"/"uget", id, k, (v)] access the k-th upvalue, going to the stack slot while open and to the upvalue's own cell once closed; ["close", level] closes every open upvalue whose slot >= level (copying the slot value) and truncates the stack to level. Accessing a vanished slot appends "dangling-slot" and stops.
Why this case matters
Closure capture and upvalue closing are subtle lifetime transitions in register-based VMs.
1 / The failure
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(events):
stack = []
open_uv = []
closures = {}
out = []
try:
for ev in events:
op = ev[0]
if op == 'local':
stack.append(ev[1])
elif op == 'set':
stack[ev[1]] = ev[2]
elif op == 'get':
out.append(stack[ev[1]])
elif op == 'closure':
ups = []
for s in ev[2]:
uv = next((u for u in open_uv if u['slot'] == s), None)
if uv is None:
uv = {'slot': s, 'open': True, 'value': None}
open_uv.append(uv)
ups.append(uv)
closures[ev[1]] = ups
elif op == 'uset':
uv = closures[ev[1]][ev[2]]
if uv['open']:
stack[uv['slot']] = ev[3]
else:
uv['value'] = ev[3]
elif op == 'uget':
uv = closures[ev[1]][ev[2]]
out.append(stack[uv['slot']] if uv['slot'] < len(stack) else uv['value'])
elif op == 'close':
level = ev[1]
for uv in open_uv:
if uv['slot'] >= level:
uv['value'] = stack[uv['slot']]
uv['open'] = False
open_uv = [u for u in open_uv if u['open']]
del stack[level:]
except IndexError:
out.append('dangling-slot')
return out
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
cases = [[('two closures share one open upvalue',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1]],),
[6, 6]),
('closing a scope keeps closures linked',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[6, 6, 0]),
('regression: new local reusing a closed slot',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[6, 6, 0, 78, 0]),
('open upvalue tracks later stack writes',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 3],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[6, 6, 0, 78, 0, 10, 3, 78]),
('slot reuse after closing everything',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 3],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[6, 6, 0, 78, 0, 10, 3, 78, 109, 3, 109]),
('closure over only the outer local',
([['local', 1], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[1, 2]),
('control: plain locals', ([['local', 1], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 1])],
[('two closures share one open upvalue',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1]],),
[7, 7]),
('closing a scope keeps closures linked',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[7, 7, 0]),
('regression: new local reusing a closed slot',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[7, 7, 0, 79, 0]),
('open upvalue tracks later stack writes',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 6],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[7, 7, 0, 79, 0, 20, 6, 79]),
('slot reuse after closing everything',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 6],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[7, 7, 0, 79, 0, 20, 6, 79, 109, 6, 109]),
('closure over only the outer local',
([['local', 2], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[2, 2]),
('control: plain locals', ([['local', 2], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 2])],
[('two closures share one open upvalue',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1]],),
[8, 8]),
('closing a scope keeps closures linked',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[8, 8, 0]),
('regression: new local reusing a closed slot',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[8, 8, 0, 80, 0]),
('open upvalue tracks later stack writes',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 9],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[8, 8, 0, 80, 0, 30, 9, 80]),
('slot reuse after closing everything',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 9],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[8, 8, 0, 80, 0, 30, 9, 80, 109, 9, 109]),
('closure over only the outer local',
([['local', 3], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[3, 2]),
('control: plain locals', ([['local', 3], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 3])],
[('two closures share one open upvalue',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1]],),
[9, 9]),
('closing a scope keeps closures linked',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[9, 9, 0]),
('regression: new local reusing a closed slot',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[9, 9, 0, 81, 0]),
('open upvalue tracks later stack writes',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 12],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[9, 9, 0, 81, 0, 40, 12, 81]),
('slot reuse after closing everything',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 12],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[9, 9, 0, 81, 0, 40, 12, 81, 109, 12, 109]),
('closure over only the outer local',
([['local', 4], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[4, 2]),
('control: plain locals', ([['local', 4], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 4])],
[('two closures share one open upvalue',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1]],),
[10, 10]),
('closing a scope keeps closures linked',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[10, 10, 0]),
('regression: new local reusing a closed slot',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[10, 10, 0, 82, 0]),
('open upvalue tracks later stack writes',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 15],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[10, 10, 0, 82, 0, 50, 15, 82]),
('slot reuse after closing everything',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 15],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[10, 10, 0, 82, 0, 50, 15, 82, 109, 15, 109]),
('closure over only the outer local',
([['local', 5], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[5, 2]),
('control: plain locals', ([['local', 5], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 5])]]
for label, args, expected in cases[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 |
|---|---|---|---|
| two closures share one open upvalue | [6, 6] | [6, 6] | Passed |
| closing a scope keeps closures linked | [6, 6, 0] | [6, 6, 0] | Passed |
| regression: new local reusing a closed slot | [6, 6, 0, 78, 78] | [6, 6, 0, 78, 0] | Failed |
| open upvalue tracks later stack writes | [6, 6, 0, 78, 78, 10, 3, 78] | [6, 6, 0, 78, 0, 10, 3, 78] | Failed |
| slot reuse after closing everything | [6, 6, 0, 78, 78, 10, 3, 78, 109, 109, 109] | [6, 6, 0, 78, 0, 10, 3, 78, 109, 3, 109] | Failed |
| closure over only the outer local | [2, 2] | [1, 2] | Failed |
| control: plain locals | [4, 1] | [4, 1] | Passed |
SHA-256 / 3d5ba39595e36a6fed3a41d273a9a394ff127a6a98abe27c3390fdabece46b52
2 / The unsuccessful fix
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(events):
stack = []
open_uv = []
closures = {}
out = []
try:
for ev in events:
op = ev[0]
if op == 'local':
stack.append(ev[1])
elif op == 'set':
stack[ev[1]] = ev[2]
elif op == 'get':
out.append(stack[ev[1]])
elif op == 'closure':
ups = []
for s in ev[2]:
uv = next((u for u in open_uv if u['slot'] == s), None)
if uv is None:
uv = {'slot': s, 'open': True, 'value': None}
open_uv.append(uv)
ups.append(uv)
closures[ev[1]] = ups
elif op == 'uset':
uv = closures[ev[1]][ev[2]]
if uv['open']:
stack[uv['slot']] = ev[3]
else:
uv['value'] = ev[3]
elif op == 'uget':
uv = closures[ev[1]][ev[2]]
out.append(uv['value'] if not uv['open'] and uv['value'] else stack[uv['slot']])
elif op == 'close':
level = ev[1]
for uv in open_uv:
if uv['slot'] >= level:
uv['value'] = stack[uv['slot']]
uv['open'] = False
open_uv = [u for u in open_uv if u['open']]
del stack[level:]
except IndexError:
out.append('dangling-slot')
return out
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
cases = [[('two closures share one open upvalue',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1]],),
[6, 6]),
('closing a scope keeps closures linked',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[6, 6, 0]),
('regression: new local reusing a closed slot',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[6, 6, 0, 78, 0]),
('open upvalue tracks later stack writes',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 3],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[6, 6, 0, 78, 0, 10, 3, 78]),
('slot reuse after closing everything',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 3],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[6, 6, 0, 78, 0, 10, 3, 78, 109, 3, 109]),
('closure over only the outer local',
([['local', 1], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[1, 2]),
('control: plain locals', ([['local', 1], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 1])],
[('two closures share one open upvalue',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1]],),
[7, 7]),
('closing a scope keeps closures linked',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[7, 7, 0]),
('regression: new local reusing a closed slot',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[7, 7, 0, 79, 0]),
('open upvalue tracks later stack writes',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 6],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[7, 7, 0, 79, 0, 20, 6, 79]),
('slot reuse after closing everything',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 6],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[7, 7, 0, 79, 0, 20, 6, 79, 109, 6, 109]),
('closure over only the outer local',
([['local', 2], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[2, 2]),
('control: plain locals', ([['local', 2], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 2])],
[('two closures share one open upvalue',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1]],),
[8, 8]),
('closing a scope keeps closures linked',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[8, 8, 0]),
('regression: new local reusing a closed slot',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[8, 8, 0, 80, 0]),
('open upvalue tracks later stack writes',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 9],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[8, 8, 0, 80, 0, 30, 9, 80]),
('slot reuse after closing everything',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 9],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[8, 8, 0, 80, 0, 30, 9, 80, 109, 9, 109]),
('closure over only the outer local',
([['local', 3], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[3, 2]),
('control: plain locals', ([['local', 3], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 3])],
[('two closures share one open upvalue',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1]],),
[9, 9]),
('closing a scope keeps closures linked',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[9, 9, 0]),
('regression: new local reusing a closed slot',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[9, 9, 0, 81, 0]),
('open upvalue tracks later stack writes',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 12],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[9, 9, 0, 81, 0, 40, 12, 81]),
('slot reuse after closing everything',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 12],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[9, 9, 0, 81, 0, 40, 12, 81, 109, 12, 109]),
('closure over only the outer local',
([['local', 4], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[4, 2]),
('control: plain locals', ([['local', 4], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 4])],
[('two closures share one open upvalue',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1]],),
[10, 10]),
('closing a scope keeps closures linked',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[10, 10, 0]),
('regression: new local reusing a closed slot',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[10, 10, 0, 82, 0]),
('open upvalue tracks later stack writes',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 15],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[10, 10, 0, 82, 0, 50, 15, 82]),
('slot reuse after closing everything',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 15],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[10, 10, 0, 82, 0, 50, 15, 82, 109, 15, 109]),
('closure over only the outer local',
([['local', 5], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[5, 2]),
('control: plain locals', ([['local', 5], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 5])]]
for label, args, expected in cases[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 |
|---|---|---|---|
| two closures share one open upvalue | [6, 6] | [6, 6] | Passed |
| closing a scope keeps closures linked | [6, 6, 'dangling-slot'] | [6, 6, 0] | Failed |
| regression: new local reusing a closed slot | [6, 6, 'dangling-slot'] | [6, 6, 0, 78, 0] | Failed |
| open upvalue tracks later stack writes | [6, 6, 'dangling-slot'] | [6, 6, 0, 78, 0, 10, 3, 78] | Failed |
| slot reuse after closing everything | [6, 6, 'dangling-slot'] | [6, 6, 0, 78, 0, 10, 3, 78, 109, 3, 109] | Failed |
| closure over only the outer local | [1, 2] | [1, 2] | Passed |
| control: plain locals | [4, 1] | [4, 1] | Passed |
SHA-256 / ff42ddee469b3ab17beceef8e57af2fcce9da84d6c41eff2c2b906b326b82fd1
3 / The verified repair
Exit 0"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(events):
stack = []
open_uv = []
closures = {}
out = []
try:
for ev in events:
op = ev[0]
if op == 'local':
stack.append(ev[1])
elif op == 'set':
stack[ev[1]] = ev[2]
elif op == 'get':
out.append(stack[ev[1]])
elif op == 'closure':
ups = []
for s in ev[2]:
uv = next((u for u in open_uv if u['slot'] == s), None)
if uv is None:
uv = {'slot': s, 'open': True, 'value': None}
open_uv.append(uv)
ups.append(uv)
closures[ev[1]] = ups
elif op == 'uset':
uv = closures[ev[1]][ev[2]]
if uv['open']:
stack[uv['slot']] = ev[3]
else:
uv['value'] = ev[3]
elif op == 'uget':
uv = closures[ev[1]][ev[2]]
out.append(stack[uv['slot']] if uv['open'] else uv['value'])
elif op == 'close':
level = ev[1]
for uv in open_uv:
if uv['slot'] >= level:
uv['value'] = stack[uv['slot']]
uv['open'] = False
open_uv = [u for u in open_uv if u['open']]
del stack[level:]
except IndexError:
out.append('dangling-slot')
return out
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
cases = [[('two closures share one open upvalue',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1]],),
[6, 6]),
('closing a scope keeps closures linked',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[6, 6, 0]),
('regression: new local reusing a closed slot',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[6, 6, 0, 78, 0]),
('open upvalue tracks later stack writes',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 3],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[6, 6, 0, 78, 0, 10, 3, 78]),
('slot reuse after closing everything',
([['local', 10],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 6],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 78],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 3],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[6, 6, 0, 78, 0, 10, 3, 78, 109, 3, 109]),
('closure over only the outer local',
([['local', 1], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[1, 2]),
('control: plain locals', ([['local', 1], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 1])],
[('two closures share one open upvalue',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1]],),
[7, 7]),
('closing a scope keeps closures linked',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[7, 7, 0]),
('regression: new local reusing a closed slot',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[7, 7, 0, 79, 0]),
('open upvalue tracks later stack writes',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 6],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[7, 7, 0, 79, 0, 20, 6, 79]),
('slot reuse after closing everything',
([['local', 20],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 7],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 79],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 6],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[7, 7, 0, 79, 0, 20, 6, 79, 109, 6, 109]),
('closure over only the outer local',
([['local', 2], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[2, 2]),
('control: plain locals', ([['local', 2], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 2])],
[('two closures share one open upvalue',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1]],),
[8, 8]),
('closing a scope keeps closures linked',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[8, 8, 0]),
('regression: new local reusing a closed slot',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[8, 8, 0, 80, 0]),
('open upvalue tracks later stack writes',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 9],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[8, 8, 0, 80, 0, 30, 9, 80]),
('slot reuse after closing everything',
([['local', 30],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 8],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 80],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 9],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[8, 8, 0, 80, 0, 30, 9, 80, 109, 9, 109]),
('closure over only the outer local',
([['local', 3], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[3, 2]),
('control: plain locals', ([['local', 3], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 3])],
[('two closures share one open upvalue',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1]],),
[9, 9]),
('closing a scope keeps closures linked',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[9, 9, 0]),
('regression: new local reusing a closed slot',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[9, 9, 0, 81, 0]),
('open upvalue tracks later stack writes',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 12],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[9, 9, 0, 81, 0, 40, 12, 81]),
('slot reuse after closing everything',
([['local', 40],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 9],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 81],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 12],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[9, 9, 0, 81, 0, 40, 12, 81, 109, 12, 109]),
('closure over only the outer local',
([['local', 4], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[4, 2]),
('control: plain locals', ([['local', 4], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 4])],
[('two closures share one open upvalue',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1]],),
[10, 10]),
('closing a scope keeps closures linked',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1]],),
[10, 10, 0]),
('regression: new local reusing a closed slot',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1]],),
[10, 10, 0, 82, 0]),
('open upvalue tracks later stack writes',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 15],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0]],),
[10, 10, 0, 82, 0, 50, 15, 82]),
('slot reuse after closing everything',
([['local', 50],
['local', 0],
['closure', 'f', [0, 1]],
['closure', 'g', [1]],
['uset', 'f', 1, 10],
['uget', 'g', 0],
['get', 1],
['close', 1],
['uset', 'g', 0, 0],
['uget', 'f', 1],
['local', 82],
['closure', 'h', [1]],
['uget', 'h', 0],
['uget', 'f', 1],
['uget', 'f', 0],
['set', 0, 15],
['uget', 'f', 0],
['close', 0],
['uget', 'h', 0],
['local', 109],
['closure', 'k', [0]],
['uget', 'k', 0],
['uget', 'f', 0],
['get', 0]],),
[10, 10, 0, 82, 0, 50, 15, 82, 109, 15, 109]),
('closure over only the outer local',
([['local', 5], ['closure', 'c', [0]], ['close', 0], ['local', 2], ['uget', 'c', 0], ['get', 0]],),
[5, 2]),
('control: plain locals', ([['local', 5], ['local', 2], ['set', 1, 4], ['get', 1], ['get', 0]],), [4, 5])]]
for label, args, expected in cases[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 |
|---|---|---|---|
| two closures share one open upvalue | [6, 6] | [6, 6] | Passed |
| closing a scope keeps closures linked | [6, 6, 0] | [6, 6, 0] | Passed |
| regression: new local reusing a closed slot | [6, 6, 0, 78, 0] | [6, 6, 0, 78, 0] | Passed |
| open upvalue tracks later stack writes | [6, 6, 0, 78, 0, 10, 3, 78] | [6, 6, 0, 78, 0, 10, 3, 78] | Passed |
| slot reuse after closing everything | [6, 6, 0, 78, 0, 10, 3, 78, 109, 3, 109] | [6, 6, 0, 78, 0, 10, 3, 78, 109, 3, 109] | Passed |
| closure over only the outer local | [1, 2] | [1, 2] | Passed |
| control: plain locals | [4, 1] | [4, 1] | Passed |
SHA-256 / b40f53a6d9e9da906a69be80b4a5a5cfe135df9463b5c13c1b0f134eeb6c0f3b
Verification & scope
A deterministic, bounded teaching model of one bytecode virtual machine mechanism with a stipulated instruction encoding; it is not a production VM and claims no conformance to any real specification. 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:23.426057+00:00.
Case digest / fd67cb8041a5a875d444e219ae3e8477bd5bfe16c3d2b8fe364b0c99829cf211