{"abstract":"An unreachable object with a finalizer is resurrected forever and never freed.","category":"Garbage collector invariants","checks":6,"contract":"Each cycle: trace strong reachability from roots (weak and phantom references are not traced); weak references whose referent is not strongly reachable are cleared; pending finalizable objects that are not strongly reachable are queued for finalization once and resurrected together with everything they reach for this cycle; phantom references are enqueued only when their referent is not reachable even through the resurrected set; everything else is freed. Return per cycle the cleared weak refs, finalized objects, enqueued phantoms and freed objects.","contract_signature":"heap, roots, weak, finalizable, phantom, cycles","evaluation_group":"w2-garbage-collector-invariants-reference-processing","failed_approach":"Replacing the pending set with just the finalized objects re-queues exactly them next cycle.","family":"w2-garbage-collector-invariants-reference-processing-single-finalization","id":"FA-90536","implementations":{"attempt":{"sha256":"89fbec295cb65b11e1d91a99c72103e24b764177111040b5be1bf09b2635b61c","source":"\"\"\"Failure Map reference implementation. Python standard library only.\"\"\"\nimport json\n\nN = 1\nobservations = []\ndef solve(heap, roots, weak, finalizable, phantom, cycles):\n    heap = {k: list(v) for k, v in heap.items()}\n    weak = {r: t for r, t in weak}\n    phantom = {r: t for r, t in phantom}\n    pending = set(finalizable)\n    out = []\n    def trace(starts, seen):\n        stack = list(starts)\n        while stack:\n            o = stack.pop()\n            if o is None or o in seen or o not in heap:\n                continue\n            seen.add(o)\n            stack.extend(heap[o])\n        return seen\n    for _ in range(cycles):\n        strong = trace(roots, set())\n        to_final = sorted(o for o in pending if o not in strong and o in heap)\n        reach = trace(to_final, set(strong))\n        cleared = sorted(r for r, t in weak.items() if t is not None and t not in strong)\n        for r in cleared:\n            weak[r] = None\n        pending = set(to_final)\n        enq = sorted(r for r, t in phantom.items() if t is not None and t not in reach)\n        for r in enq:\n            phantom[r] = None\n        freed = sorted(o for o in heap if o not in reach)\n        for o in freed:\n            del heap[o]\n        out.append({'weak': cleared, 'finalize': to_final, 'phantom': enq, 'freed': freed})\n    return out\ndef check(label, actual, expected):\n    observations.append({\"check\": label, \"actual\": actual, \"expected\": expected, \"passed\": actual == expected})\ncases = [[('regression: finalizable object over two cycles',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []},\n    [11],\n    [['w1', 13], ['w2', 12]],\n    [13],\n    [['p1', 14], ['p2', 16]],\n    2),\n   [{'finalize': [13], 'freed': [16], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [13, 14, 15], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [['w1', 13]], [13], [], 1),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [], [13], [], 3),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [13, 14, 15], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [], [13], [['p1', 15]], 1),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [], [13], [['p1', 14]], 2),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [13, 14, 15], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []},\n    [11, 13, 16],\n    [['w1', 13], ['w2', 12]],\n    [13],\n    [['p1', 14], ['p2', 16]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []},\n    [21],\n    [['w1', 23], ['w2', 22]],\n    [23],\n    [['p1', 24], ['p2', 26]],\n    2),\n   [{'finalize': [23], 'freed': [26], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [23, 24, 25], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [['w1', 23]], [23], [], 1),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [], [23], [], 3),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [23, 24, 25], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [], [23], [['p1', 25]], 1),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [], [23], [['p1', 24]], 2),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [23, 24, 25], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []},\n    [21, 23, 26],\n    [['w1', 23], ['w2', 22]],\n    [23],\n    [['p1', 24], ['p2', 26]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []},\n    [31],\n    [['w1', 33], ['w2', 32]],\n    [33],\n    [['p1', 34], ['p2', 36]],\n    2),\n   [{'finalize': [33], 'freed': [36], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [33, 34, 35], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [['w1', 33]], [33], [], 1),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [], [33], [], 3),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [33, 34, 35], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [], [33], [['p1', 35]], 1),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [], [33], [['p1', 34]], 2),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [33, 34, 35], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []},\n    [31, 33, 36],\n    [['w1', 33], ['w2', 32]],\n    [33],\n    [['p1', 34], ['p2', 36]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []},\n    [41],\n    [['w1', 43], ['w2', 42]],\n    [43],\n    [['p1', 44], ['p2', 46]],\n    2),\n   [{'finalize': [43], 'freed': [46], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [43, 44, 45], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [['w1', 43]], [43], [], 1),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [], [43], [], 3),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [43, 44, 45], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [], [43], [['p1', 45]], 1),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [], [43], [['p1', 44]], 2),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [43, 44, 45], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []},\n    [41, 43, 46],\n    [['w1', 43], ['w2', 42]],\n    [43],\n    [['p1', 44], ['p2', 46]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []},\n    [51],\n    [['w1', 53], ['w2', 52]],\n    [53],\n    [['p1', 54], ['p2', 56]],\n    2),\n   [{'finalize': [53], 'freed': [56], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [53, 54, 55], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [['w1', 53]], [53], [], 1),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [], [53], [], 3),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [53, 54, 55], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [], [53], [['p1', 55]], 1),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [], [53], [['p1', 54]], 2),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [53, 54, 55], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []},\n    [51, 53, 56],\n    [['w1', 53], ['w2', 52]],\n    [53],\n    [['p1', 54], ['p2', 56]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])]]\nfor label, args, expected in cases[N - 1]:\n    check(label, solve(*args), expected)\nprint(json.dumps({\"observations\": observations, \"passed\": all(x[\"passed\"] for x in observations)}, ensure_ascii=False))\nraise SystemExit(0 if all(x[\"passed\"] for x in observations) else 1)\n"},"broken":{"sha256":"4eb0c8d683289029d269d8f713c5a41c1c394d2e00e4c2ea6d49adaa76adaec1","source":"\"\"\"Failure Map reference implementation. Python standard library only.\"\"\"\nimport json\n\nN = 1\nobservations = []\ndef solve(heap, roots, weak, finalizable, phantom, cycles):\n    heap = {k: list(v) for k, v in heap.items()}\n    weak = {r: t for r, t in weak}\n    phantom = {r: t for r, t in phantom}\n    pending = set(finalizable)\n    out = []\n    def trace(starts, seen):\n        stack = list(starts)\n        while stack:\n            o = stack.pop()\n            if o is None or o in seen or o not in heap:\n                continue\n            seen.add(o)\n            stack.extend(heap[o])\n        return seen\n    for _ in range(cycles):\n        strong = trace(roots, set())\n        to_final = sorted(o for o in pending if o not in strong and o in heap)\n        reach = trace(to_final, set(strong))\n        cleared = sorted(r for r, t in weak.items() if t is not None and t not in strong)\n        for r in cleared:\n            weak[r] = None\n        pending = set(pending)\n        enq = sorted(r for r, t in phantom.items() if t is not None and t not in reach)\n        for r in enq:\n            phantom[r] = None\n        freed = sorted(o for o in heap if o not in reach)\n        for o in freed:\n            del heap[o]\n        out.append({'weak': cleared, 'finalize': to_final, 'phantom': enq, 'freed': freed})\n    return out\ndef check(label, actual, expected):\n    observations.append({\"check\": label, \"actual\": actual, \"expected\": expected, \"passed\": actual == expected})\ncases = [[('regression: finalizable object over two cycles',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []},\n    [11],\n    [['w1', 13], ['w2', 12]],\n    [13],\n    [['p1', 14], ['p2', 16]],\n    2),\n   [{'finalize': [13], 'freed': [16], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [13, 14, 15], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [['w1', 13]], [13], [], 1),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [], [13], [], 3),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [13, 14, 15], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [], [13], [['p1', 15]], 1),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []}, [11], [], [13], [['p1', 14]], 2),\n   [{'finalize': [13], 'freed': [16], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [13, 14, 15], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({11: [12], 12: [], 13: [14], 14: [15], 15: [], 16: []},\n    [11, 13, 16],\n    [['w1', 13], ['w2', 12]],\n    [13],\n    [['p1', 14], ['p2', 16]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []},\n    [21],\n    [['w1', 23], ['w2', 22]],\n    [23],\n    [['p1', 24], ['p2', 26]],\n    2),\n   [{'finalize': [23], 'freed': [26], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [23, 24, 25], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [['w1', 23]], [23], [], 1),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [], [23], [], 3),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [23, 24, 25], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [], [23], [['p1', 25]], 1),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []}, [21], [], [23], [['p1', 24]], 2),\n   [{'finalize': [23], 'freed': [26], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [23, 24, 25], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({21: [22], 22: [], 23: [24], 24: [25], 25: [], 26: []},\n    [21, 23, 26],\n    [['w1', 23], ['w2', 22]],\n    [23],\n    [['p1', 24], ['p2', 26]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []},\n    [31],\n    [['w1', 33], ['w2', 32]],\n    [33],\n    [['p1', 34], ['p2', 36]],\n    2),\n   [{'finalize': [33], 'freed': [36], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [33, 34, 35], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [['w1', 33]], [33], [], 1),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [], [33], [], 3),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [33, 34, 35], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [], [33], [['p1', 35]], 1),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []}, [31], [], [33], [['p1', 34]], 2),\n   [{'finalize': [33], 'freed': [36], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [33, 34, 35], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({31: [32], 32: [], 33: [34], 34: [35], 35: [], 36: []},\n    [31, 33, 36],\n    [['w1', 33], ['w2', 32]],\n    [33],\n    [['p1', 34], ['p2', 36]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []},\n    [41],\n    [['w1', 43], ['w2', 42]],\n    [43],\n    [['p1', 44], ['p2', 46]],\n    2),\n   [{'finalize': [43], 'freed': [46], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [43, 44, 45], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [['w1', 43]], [43], [], 1),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [], [43], [], 3),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [43, 44, 45], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [], [43], [['p1', 45]], 1),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []}, [41], [], [43], [['p1', 44]], 2),\n   [{'finalize': [43], 'freed': [46], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [43, 44, 45], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({41: [42], 42: [], 43: [44], 44: [45], 45: [], 46: []},\n    [41, 43, 46],\n    [['w1', 43], ['w2', 42]],\n    [43],\n    [['p1', 44], ['p2', 46]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])],\n [('regression: finalizable object over two cycles',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []},\n    [51],\n    [['w1', 53], ['w2', 52]],\n    [53],\n    [['p1', 54], ['p2', 56]],\n    2),\n   [{'finalize': [53], 'freed': [56], 'phantom': ['p2'], 'weak': ['w1']},\n    {'finalize': [], 'freed': [53, 54, 55], 'phantom': ['p1'], 'weak': []}]),\n  ('weak reference to a resurrected object',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [['w1', 53]], [53], [], 1),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': ['w1']}]),\n  ('finalizer runs only once',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [], [53], [], 3),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [53, 54, 55], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}]),\n  ('children of a finalizable object stay alive',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [], [53], [['p1', 55]], 1),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': []}]),\n  ('phantom of an object only reachable from a finalizable one',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []}, [51], [], [53], [['p1', 54]], 2),\n   [{'finalize': [53], 'freed': [56], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [53, 54, 55], 'phantom': ['p1'], 'weak': []}]),\n  ('control: all strongly reachable',\n   ({51: [52], 52: [], 53: [54], 54: [55], 55: [], 56: []},\n    [51, 53, 56],\n    [['w1', 53], ['w2', 52]],\n    [53],\n    [['p1', 54], ['p2', 56]],\n    2),\n   [{'finalize': [], 'freed': [], 'phantom': [], 'weak': []},\n    {'finalize': [], 'freed': [], 'phantom': [], 'weak': []}])]]\nfor label, args, expected in cases[N - 1]:\n    check(label, solve(*args), expected)\nprint(json.dumps({\"observations\": observations, \"passed\": all(x[\"passed\"] for x in observations)}, ensure_ascii=False))\nraise SystemExit(0 if all(x[\"passed\"] for x in observations) else 1)\n"}},"limitations":"A deterministic, bounded teaching model of one garbage-collector mechanism with stipulated rules; it is not a production collector and claims no conformance to any particular runtime. 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.","method":"Deterministic executable model with adversarial boundary fixtures.","provenance":{"created_by":"Failure Map","dependencies":"Python standard library","family":"w2-garbage-collector-invariants-reference-processing-single-finalization","generated_at":"2026-09-29T14:51:27.743441+00:00","license":"CC0-1.0","python":"3.12.14","seed":1,"split":"open-access"},"relevance":"Reference-processing order decides whether code can observe resurrected or half-dead objects.","root_cause":"Objects queued for finalization are never removed from the pending set.","sha256":"f87e99d872bf7f2e11ad9f295ab22fecbae6be9a4981e7631bcf6cd0e0ca4a40","title":"Reference processing: finalizers run every cycle · case 01","variant":1,"variant_policy":"Five numbered records share a model and may reuse boundary fixtures.","verified":true,"visibility":"public","verification":{"attempt":{"elapsed_ms":41.074,"exit_code":1,"observations":[{"actual":[{"finalize":[13],"freed":[16],"phantom":["p2"],"weak":["w1"]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]}],"check":"regression: finalizable object over two cycles","expected":[{"finalize":[13],"freed":[16],"phantom":["p2"],"weak":["w1"]},{"finalize":[],"freed":[13,14,15],"phantom":["p1"],"weak":[]}],"passed":false},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":["w1"]}],"check":"weak reference to a resurrected object","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":["w1"]}],"passed":true},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]}],"check":"finalizer runs only once","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[],"freed":[13,14,15],"phantom":[],"weak":[]},{"finalize":[],"freed":[],"phantom":[],"weak":[]}],"passed":false},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]}],"check":"children of a finalizable object stay alive","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]}],"passed":true},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]}],"check":"phantom of an object only reachable from a finalizable one","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[],"freed":[13,14,15],"phantom":["p1"],"weak":[]}],"passed":false},{"actual":[{"finalize":[],"freed":[],"phantom":[],"weak":[]},{"finalize":[],"freed":[],"phantom":[],"weak":[]}],"check":"control: all strongly reachable","expected":[{"finalize":[],"freed":[],"phantom":[],"weak":[]},{"finalize":[],"freed":[],"phantom":[],"weak":[]}],"passed":true}],"passed":false,"stderr":"","stdout":"{\"observations\": [{\"check\": \"regression: finalizable object over two cycles\", \"actual\": [{\"weak\": [\"w1\"], \"finalize\": [13], \"phantom\": [\"p2\"], \"freed\": [16]}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [\"p2\"], \"weak\": [\"w1\"]}, {\"finalize\": [], \"freed\": [13, 14, 15], \"phantom\": [\"p1\"], \"weak\": []}], \"passed\": false}, {\"check\": \"weak reference to a resurrected object\", \"actual\": [{\"weak\": [\"w1\"], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": [\"w1\"]}], \"passed\": true}, {\"check\": \"finalizer runs only once\", \"actual\": [{\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [13, 14, 15], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [], \"phantom\": [], \"weak\": []}], \"passed\": false}, {\"check\": \"children of a finalizable object stay alive\", \"actual\": [{\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": []}], \"passed\": true}, {\"check\": \"phantom of an object only reachable from a finalizable one\", \"actual\": [{\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [13, 14, 15], \"phantom\": [\"p1\"], \"weak\": []}], \"passed\": false}, {\"check\": \"control: all strongly reachable\", \"actual\": [{\"weak\": [], \"finalize\": [], \"phantom\": [], \"freed\": []}, {\"weak\": [], \"finalize\": [], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [], \"freed\": [], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [], \"phantom\": [], \"weak\": []}], \"passed\": true}], \"passed\": false}\n"},"broken":{"elapsed_ms":42.229,"exit_code":1,"observations":[{"actual":[{"finalize":[13],"freed":[16],"phantom":["p2"],"weak":["w1"]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]}],"check":"regression: finalizable object over two cycles","expected":[{"finalize":[13],"freed":[16],"phantom":["p2"],"weak":["w1"]},{"finalize":[],"freed":[13,14,15],"phantom":["p1"],"weak":[]}],"passed":false},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":["w1"]}],"check":"weak reference to a resurrected object","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":["w1"]}],"passed":true},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]}],"check":"finalizer runs only once","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[],"freed":[13,14,15],"phantom":[],"weak":[]},{"finalize":[],"freed":[],"phantom":[],"weak":[]}],"passed":false},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]}],"check":"children of a finalizable object stay alive","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]}],"passed":true},{"actual":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[13],"freed":[],"phantom":[],"weak":[]}],"check":"phantom of an object only reachable from a finalizable one","expected":[{"finalize":[13],"freed":[16],"phantom":[],"weak":[]},{"finalize":[],"freed":[13,14,15],"phantom":["p1"],"weak":[]}],"passed":false},{"actual":[{"finalize":[],"freed":[],"phantom":[],"weak":[]},{"finalize":[],"freed":[],"phantom":[],"weak":[]}],"check":"control: all strongly reachable","expected":[{"finalize":[],"freed":[],"phantom":[],"weak":[]},{"finalize":[],"freed":[],"phantom":[],"weak":[]}],"passed":true}],"passed":false,"stderr":"","stdout":"{\"observations\": [{\"check\": \"regression: finalizable object over two cycles\", \"actual\": [{\"weak\": [\"w1\"], \"finalize\": [13], \"phantom\": [\"p2\"], \"freed\": [16]}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [\"p2\"], \"weak\": [\"w1\"]}, {\"finalize\": [], \"freed\": [13, 14, 15], \"phantom\": [\"p1\"], \"weak\": []}], \"passed\": false}, {\"check\": \"weak reference to a resurrected object\", \"actual\": [{\"weak\": [\"w1\"], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": [\"w1\"]}], \"passed\": true}, {\"check\": \"finalizer runs only once\", \"actual\": [{\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [13, 14, 15], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [], \"phantom\": [], \"weak\": []}], \"passed\": false}, {\"check\": \"children of a finalizable object stay alive\", \"actual\": [{\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": []}], \"passed\": true}, {\"check\": \"phantom of an object only reachable from a finalizable one\", \"actual\": [{\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": [16]}, {\"weak\": [], \"finalize\": [13], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [13], \"freed\": [16], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [13, 14, 15], \"phantom\": [\"p1\"], \"weak\": []}], \"passed\": false}, {\"check\": \"control: all strongly reachable\", \"actual\": [{\"weak\": [], \"finalize\": [], \"phantom\": [], \"freed\": []}, {\"weak\": [], \"finalize\": [], \"phantom\": [], \"freed\": []}], \"expected\": [{\"finalize\": [], \"freed\": [], \"phantom\": [], \"weak\": []}, {\"finalize\": [], \"freed\": [], \"phantom\": [], \"weak\": []}], \"passed\": true}], \"passed\": false}\n"}},"member_only":{"stages":["fixed"],"fields":["implementations.fixed","verification.fixed","harness","repair"],"note":"The verified repair, its recorded checks, the repair description, and the scoring harness are available to members."}}