FAILURE MAP
← Case archive

FA-89966 / Bytecode virtual machines / Open access

Exception tables: handler requires the exact thrown type · case 01

catch (IOException) no longer catches FileNotFoundException.

Verified by executionVariant 1 · 10 checks per implementationDownload source bundle ↓JSON ↗

ROOT CAUSE

The type test compares names for equality rather than walking the superclass chain.

VERIFIED REPAIR

Accept the handler when the thrown type or one of its ancestors equals the catch type.

Unsuccessful approach: Walking the hierarchy from the catch type upward lets subclass handlers catch superclass exceptions.

Case contract

frames are ordered outermost first; the innermost frame carries the faulting pc, every caller carries the return address "ret" and the invoke opcode "via" (invokeinterface and invokedynamic are 5 bytes, other invokes 3), and the lookup pc is the invoke's own address. Each table entry [start, end, handler, type] covers start <= pc < end; entries are tried in table order; type None catches anything, otherwise the thrown type or any ancestor (parents map) must equal it. Return handler, number of frames unwound and the operand stack at the handler (cleared, then the exception pushed).

Why this case matters

Exception dispatch correctness depends on half-open ranges, table order, type hierarchy and pc attribution.

1 / The failure

Exit 1
"""Failure Map reference implementation. Python standard library only."""
import json

N = 1
observations = []
def solve(frames, exc, parents):
    def is_sub(t, target):
        while t is not None:
            if t == target:
                return True
            t = parents.get(t)
        return False
    unwound = 0
    for depth, frame in enumerate(reversed(frames)):
        if depth == 0:
            pc = frame['pc']
        else:
            pc = frame['ret'] - (5 if frame['via'] in ('invokeinterface', 'invokedynamic') else 3)
        for start, end, handler, catch in frame['table']:
            if start <= pc < end and (catch is None or exc == catch):
                return {'handler': handler, 'unwound': unwound, 'stack': [exc]}
        unwound += 1
    return {'handler': None, 'unwound': unwound, 'stack': []}
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
cases = [[('range end is exclusive',
   ([{'pc': 20, 'stack': [1, 2], 'table': [[10, 20, 100, 'IOException'], [20, 30, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 10, 'stack': [1, 2], 'table': [[10, 15, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 17, 'stack': [1, 2], 'table': [[10, 30, 100, 'Exception'], [15, 20, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 11, 'stack': [1, 2], 'table': [[10, 19, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 11, 'stack': [1, 2], 'table': [[10, 19, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 12, 'stack': [1, 2], 'table': [[10, 19, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 12, 'stack': [1, 2], 'table': [[10, 19, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 23, 'stack': [1], 'table': [[20, 23, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [1, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 25, 'stack': [1], 'table': [[20, 25, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [1, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 13, 'stack': [], 'table': [[15, 19, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [1, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 30, 'stack': [2, 2], 'table': [[20, 30, 100, 'IOException'], [30, 40, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 20, 'stack': [2, 2], 'table': [[20, 25, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 27, 'stack': [2, 2], 'table': [[20, 40, 100, 'Exception'], [25, 30, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 21, 'stack': [2, 2], 'table': [[20, 29, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 21, 'stack': [2, 2], 'table': [[20, 29, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 22, 'stack': [2, 2], 'table': [[20, 29, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 22, 'stack': [2, 2], 'table': [[20, 29, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 33, 'stack': [1], 'table': [[30, 33, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [2, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 35, 'stack': [1], 'table': [[30, 35, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [2, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 23, 'stack': [], 'table': [[25, 29, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [2, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 40, 'stack': [3, 2], 'table': [[30, 40, 100, 'IOException'], [40, 50, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 30, 'stack': [3, 2], 'table': [[30, 35, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 37, 'stack': [3, 2], 'table': [[30, 50, 100, 'Exception'], [35, 40, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 31, 'stack': [3, 2], 'table': [[30, 39, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 31, 'stack': [3, 2], 'table': [[30, 39, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 32, 'stack': [3, 2], 'table': [[30, 39, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 32, 'stack': [3, 2], 'table': [[30, 39, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 43, 'stack': [1], 'table': [[40, 43, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [3, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 45, 'stack': [1], 'table': [[40, 45, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [3, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 33, 'stack': [], 'table': [[35, 39, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [3, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 50, 'stack': [4, 2], 'table': [[40, 50, 100, 'IOException'], [50, 60, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 40, 'stack': [4, 2], 'table': [[40, 45, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 47, 'stack': [4, 2], 'table': [[40, 60, 100, 'Exception'], [45, 50, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 41, 'stack': [4, 2], 'table': [[40, 49, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 41, 'stack': [4, 2], 'table': [[40, 49, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 42, 'stack': [4, 2], 'table': [[40, 49, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 42, 'stack': [4, 2], 'table': [[40, 49, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 53, 'stack': [1], 'table': [[50, 53, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [4, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 55, 'stack': [1], 'table': [[50, 55, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [4, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 43, 'stack': [], 'table': [[45, 49, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [4, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 60, 'stack': [5, 2], 'table': [[50, 60, 100, 'IOException'], [60, 70, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 50, 'stack': [5, 2], 'table': [[50, 55, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 57, 'stack': [5, 2], 'table': [[50, 70, 100, 'Exception'], [55, 60, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 51, 'stack': [5, 2], 'table': [[50, 59, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 51, 'stack': [5, 2], 'table': [[50, 59, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 52, 'stack': [5, 2], 'table': [[50, 59, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 52, 'stack': [5, 2], 'table': [[50, 59, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 63, 'stack': [1], 'table': [[60, 63, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [5, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 65, 'stack': [1], 'table': [[60, 65, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [5, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 53, 'stack': [], 'table': [[55, 59, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [5, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})]]
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 fixtureActualExpectedOutcome
range end is exclusive{'handler': 200, 'stack': ['IOException'], 'unwound': 0}{'handler': 200, 'stack': ['IOException'], 'unwound': 0}Passed
range start is inclusive{'handler': None, 'stack': [], 'unwound': 1}{'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}Failed
regression: first matching entry in table order wins{'handler': None, 'stack': [], 'unwound': 1}{'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}Failed
subclass instance caught by superclass handler{'handler': None, 'stack': [], 'unwound': 1}{'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}Failed
superclass instance not caught by subclass handler{'handler': None, 'stack': [], 'unwound': 1}{'handler': None, 'stack': [], 'unwound': 1}Passed
any-type entry catches errors{'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}{'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}Passed
Exception handler does not catch Error{'handler': None, 'stack': [], 'unwound': 1}{'handler': None, 'stack': [], 'unwound': 1}Passed
caller frame after 3-byte invoke{'handler': None, 'stack': [], 'unwound': 2}{'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}Failed
caller frame after 5-byte invokeinterface{'handler': 600, 'stack': ['IOException'], 'unwound': 1}{'handler': 600, 'stack': ['IOException'], 'unwound': 1}Passed
control: uncaught through two frames{'handler': None, 'stack': [], 'unwound': 2}{'handler': None, 'stack': [], 'unwound': 2}Passed

SHA-256 / c42a0e228c2570b6ffc2510580198a45c9cd759912cb8a2e47a1f72a99db5b96

2 / The unsuccessful fix

Exit 1
"""Failure Map reference implementation. Python standard library only."""
import json

N = 1
observations = []
def solve(frames, exc, parents):
    def is_sub(t, target):
        while t is not None:
            if t == target:
                return True
            t = parents.get(t)
        return False
    unwound = 0
    for depth, frame in enumerate(reversed(frames)):
        if depth == 0:
            pc = frame['pc']
        else:
            pc = frame['ret'] - (5 if frame['via'] in ('invokeinterface', 'invokedynamic') else 3)
        for start, end, handler, catch in frame['table']:
            if start <= pc < end and (catch is None or is_sub(catch, exc)):
                return {'handler': handler, 'unwound': unwound, 'stack': [exc]}
        unwound += 1
    return {'handler': None, 'unwound': unwound, 'stack': []}
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
cases = [[('range end is exclusive',
   ([{'pc': 20, 'stack': [1, 2], 'table': [[10, 20, 100, 'IOException'], [20, 30, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 10, 'stack': [1, 2], 'table': [[10, 15, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 17, 'stack': [1, 2], 'table': [[10, 30, 100, 'Exception'], [15, 20, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 11, 'stack': [1, 2], 'table': [[10, 19, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 11, 'stack': [1, 2], 'table': [[10, 19, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 12, 'stack': [1, 2], 'table': [[10, 19, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 12, 'stack': [1, 2], 'table': [[10, 19, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 23, 'stack': [1], 'table': [[20, 23, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [1, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 25, 'stack': [1], 'table': [[20, 25, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [1, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 13, 'stack': [], 'table': [[15, 19, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [1, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 30, 'stack': [2, 2], 'table': [[20, 30, 100, 'IOException'], [30, 40, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 20, 'stack': [2, 2], 'table': [[20, 25, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 27, 'stack': [2, 2], 'table': [[20, 40, 100, 'Exception'], [25, 30, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 21, 'stack': [2, 2], 'table': [[20, 29, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 21, 'stack': [2, 2], 'table': [[20, 29, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 22, 'stack': [2, 2], 'table': [[20, 29, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 22, 'stack': [2, 2], 'table': [[20, 29, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 33, 'stack': [1], 'table': [[30, 33, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [2, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 35, 'stack': [1], 'table': [[30, 35, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [2, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 23, 'stack': [], 'table': [[25, 29, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [2, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 40, 'stack': [3, 2], 'table': [[30, 40, 100, 'IOException'], [40, 50, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 30, 'stack': [3, 2], 'table': [[30, 35, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 37, 'stack': [3, 2], 'table': [[30, 50, 100, 'Exception'], [35, 40, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 31, 'stack': [3, 2], 'table': [[30, 39, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 31, 'stack': [3, 2], 'table': [[30, 39, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 32, 'stack': [3, 2], 'table': [[30, 39, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 32, 'stack': [3, 2], 'table': [[30, 39, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 43, 'stack': [1], 'table': [[40, 43, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [3, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 45, 'stack': [1], 'table': [[40, 45, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [3, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 33, 'stack': [], 'table': [[35, 39, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [3, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 50, 'stack': [4, 2], 'table': [[40, 50, 100, 'IOException'], [50, 60, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 40, 'stack': [4, 2], 'table': [[40, 45, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 47, 'stack': [4, 2], 'table': [[40, 60, 100, 'Exception'], [45, 50, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 41, 'stack': [4, 2], 'table': [[40, 49, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 41, 'stack': [4, 2], 'table': [[40, 49, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 42, 'stack': [4, 2], 'table': [[40, 49, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 42, 'stack': [4, 2], 'table': [[40, 49, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 53, 'stack': [1], 'table': [[50, 53, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [4, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 55, 'stack': [1], 'table': [[50, 55, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [4, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 43, 'stack': [], 'table': [[45, 49, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [4, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 60, 'stack': [5, 2], 'table': [[50, 60, 100, 'IOException'], [60, 70, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 50, 'stack': [5, 2], 'table': [[50, 55, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 57, 'stack': [5, 2], 'table': [[50, 70, 100, 'Exception'], [55, 60, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 51, 'stack': [5, 2], 'table': [[50, 59, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 51, 'stack': [5, 2], 'table': [[50, 59, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 52, 'stack': [5, 2], 'table': [[50, 59, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 52, 'stack': [5, 2], 'table': [[50, 59, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 63, 'stack': [1], 'table': [[60, 63, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [5, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 65, 'stack': [1], 'table': [[60, 65, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [5, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 53, 'stack': [], 'table': [[55, 59, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [5, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})]]
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 fixtureActualExpectedOutcome
range end is exclusive{'handler': 200, 'stack': ['IOException'], 'unwound': 0}{'handler': 200, 'stack': ['IOException'], 'unwound': 0}Passed
range start is inclusive{'handler': None, 'stack': [], 'unwound': 1}{'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}Failed
regression: first matching entry in table order wins{'handler': None, 'stack': [], 'unwound': 1}{'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}Failed
subclass instance caught by superclass handler{'handler': None, 'stack': [], 'unwound': 1}{'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}Failed
superclass instance not caught by subclass handler{'handler': 150, 'stack': ['IOException'], 'unwound': 0}{'handler': None, 'stack': [], 'unwound': 1}Failed
any-type entry catches errors{'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}{'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}Passed
Exception handler does not catch Error{'handler': None, 'stack': [], 'unwound': 1}{'handler': None, 'stack': [], 'unwound': 1}Passed
caller frame after 3-byte invoke{'handler': None, 'stack': [], 'unwound': 2}{'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}Failed
caller frame after 5-byte invokeinterface{'handler': 600, 'stack': ['IOException'], 'unwound': 1}{'handler': 600, 'stack': ['IOException'], 'unwound': 1}Passed
control: uncaught through two frames{'handler': None, 'stack': [], 'unwound': 2}{'handler': None, 'stack': [], 'unwound': 2}Passed

SHA-256 / 4d6a79052ef13e8d173e56ae307e83ba45fbd810fd60411cc8a74311744aae3d

3 / The verified repair

Exit 0
"""Failure Map reference implementation. Python standard library only."""
import json

N = 1
observations = []
def solve(frames, exc, parents):
    def is_sub(t, target):
        while t is not None:
            if t == target:
                return True
            t = parents.get(t)
        return False
    unwound = 0
    for depth, frame in enumerate(reversed(frames)):
        if depth == 0:
            pc = frame['pc']
        else:
            pc = frame['ret'] - (5 if frame['via'] in ('invokeinterface', 'invokedynamic') else 3)
        for start, end, handler, catch in frame['table']:
            if start <= pc < end and (catch is None or is_sub(exc, catch)):
                return {'handler': handler, 'unwound': unwound, 'stack': [exc]}
        unwound += 1
    return {'handler': None, 'unwound': unwound, 'stack': []}
def check(label, actual, expected):
    observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
cases = [[('range end is exclusive',
   ([{'pc': 20, 'stack': [1, 2], 'table': [[10, 20, 100, 'IOException'], [20, 30, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 10, 'stack': [1, 2], 'table': [[10, 15, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 17, 'stack': [1, 2], 'table': [[10, 30, 100, 'Exception'], [15, 20, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 11, 'stack': [1, 2], 'table': [[10, 19, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 11, 'stack': [1, 2], 'table': [[10, 19, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 12, 'stack': [1, 2], 'table': [[10, 19, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 12, 'stack': [1, 2], 'table': [[10, 19, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 23, 'stack': [1], 'table': [[20, 23, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [1, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 25, 'stack': [1], 'table': [[20, 25, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [1, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 13, 'stack': [], 'table': [[15, 19, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [1, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 30, 'stack': [2, 2], 'table': [[20, 30, 100, 'IOException'], [30, 40, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 20, 'stack': [2, 2], 'table': [[20, 25, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 27, 'stack': [2, 2], 'table': [[20, 40, 100, 'Exception'], [25, 30, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 21, 'stack': [2, 2], 'table': [[20, 29, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 21, 'stack': [2, 2], 'table': [[20, 29, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 22, 'stack': [2, 2], 'table': [[20, 29, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 22, 'stack': [2, 2], 'table': [[20, 29, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 33, 'stack': [1], 'table': [[30, 33, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [2, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 35, 'stack': [1], 'table': [[30, 35, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [2, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 23, 'stack': [], 'table': [[25, 29, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [2, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 40, 'stack': [3, 2], 'table': [[30, 40, 100, 'IOException'], [40, 50, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 30, 'stack': [3, 2], 'table': [[30, 35, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 37, 'stack': [3, 2], 'table': [[30, 50, 100, 'Exception'], [35, 40, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 31, 'stack': [3, 2], 'table': [[30, 39, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 31, 'stack': [3, 2], 'table': [[30, 39, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 32, 'stack': [3, 2], 'table': [[30, 39, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 32, 'stack': [3, 2], 'table': [[30, 39, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 43, 'stack': [1], 'table': [[40, 43, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [3, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 45, 'stack': [1], 'table': [[40, 45, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [3, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 33, 'stack': [], 'table': [[35, 39, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [3, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 50, 'stack': [4, 2], 'table': [[40, 50, 100, 'IOException'], [50, 60, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 40, 'stack': [4, 2], 'table': [[40, 45, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 47, 'stack': [4, 2], 'table': [[40, 60, 100, 'Exception'], [45, 50, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 41, 'stack': [4, 2], 'table': [[40, 49, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 41, 'stack': [4, 2], 'table': [[40, 49, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 42, 'stack': [4, 2], 'table': [[40, 49, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 42, 'stack': [4, 2], 'table': [[40, 49, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 53, 'stack': [1], 'table': [[50, 53, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [4, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 55, 'stack': [1], 'table': [[50, 55, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [4, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 43, 'stack': [], 'table': [[45, 49, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [4, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})],
 [('range end is exclusive',
   ([{'pc': 60, 'stack': [5, 2], 'table': [[50, 60, 100, 'IOException'], [60, 70, 200, 'IOException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 200, 'stack': ['IOException'], 'unwound': 0}),
  ('range start is inclusive',
   ([{'pc': 50, 'stack': [5, 2], 'table': [[50, 55, 300, 'Exception']]}],
    'ArithmeticException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}),
  ('regression: first matching entry in table order wins',
   ([{'pc': 57, 'stack': [5, 2], 'table': [[50, 70, 100, 'Exception'], [55, 60, 200, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('subclass instance caught by superclass handler',
   ([{'pc': 51, 'stack': [5, 2], 'table': [[50, 59, 150, 'IOException']]}],
    'FileNotFoundException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}),
  ('superclass instance not caught by subclass handler',
   ([{'pc': 51, 'stack': [5, 2], 'table': [[50, 59, 150, 'FileNotFoundException']]}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('any-type entry catches errors',
   ([{'pc': 52, 'stack': [5, 2], 'table': [[50, 59, 400, None]]}],
    'StackOverflowError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}),
  ('Exception handler does not catch Error',
   ([{'pc': 52, 'stack': [5, 2], 'table': [[50, 59, 410, 'Exception']]}],
    'AssertionError',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 1}),
  ('caller frame after 3-byte invoke',
   ([{'ret': 63, 'stack': [1], 'table': [[60, 63, 500, 'Exception']], 'via': 'invokestatic'},
     {'pc': 3, 'stack': [5, 2], 'table': []}],
    'RuntimeException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}),
  ('caller frame after 5-byte invokeinterface',
   ([{'ret': 65, 'stack': [1], 'table': [[60, 65, 600, None]], 'via': 'invokeinterface'},
     {'pc': 3, 'stack': [5, 2], 'table': []}],
    'IOException',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': 600, 'stack': ['IOException'], 'unwound': 1}),
  ('control: uncaught through two frames',
   ([{'ret': 53, 'stack': [], 'table': [[55, 59, 1, None]], 'via': 'invokevirtual'},
     {'pc': 4, 'stack': [5, 2], 'table': [[0, 3, 2, None]]}],
    'Error',
    {'ArithmeticException': 'RuntimeException',
     'AssertionError': 'Error',
     'Error': 'Throwable',
     'Exception': 'Throwable',
     'FileNotFoundException': 'IOException',
     'IOException': 'Exception',
     'RuntimeException': 'Exception',
     'StackOverflowError': 'VirtualMachineError',
     'VirtualMachineError': 'Error'}),
   {'handler': None, 'stack': [], 'unwound': 2})]]
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 fixtureActualExpectedOutcome
range end is exclusive{'handler': 200, 'stack': ['IOException'], 'unwound': 0}{'handler': 200, 'stack': ['IOException'], 'unwound': 0}Passed
range start is inclusive{'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}{'handler': 300, 'stack': ['ArithmeticException'], 'unwound': 0}Passed
regression: first matching entry in table order wins{'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}{'handler': 100, 'stack': ['FileNotFoundException'], 'unwound': 0}Passed
subclass instance caught by superclass handler{'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}{'handler': 150, 'stack': ['FileNotFoundException'], 'unwound': 0}Passed
superclass instance not caught by subclass handler{'handler': None, 'stack': [], 'unwound': 1}{'handler': None, 'stack': [], 'unwound': 1}Passed
any-type entry catches errors{'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}{'handler': 400, 'stack': ['StackOverflowError'], 'unwound': 0}Passed
Exception handler does not catch Error{'handler': None, 'stack': [], 'unwound': 1}{'handler': None, 'stack': [], 'unwound': 1}Passed
caller frame after 3-byte invoke{'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}{'handler': 500, 'stack': ['RuntimeException'], 'unwound': 1}Passed
caller frame after 5-byte invokeinterface{'handler': 600, 'stack': ['IOException'], 'unwound': 1}{'handler': 600, 'stack': ['IOException'], 'unwound': 1}Passed
control: uncaught through two frames{'handler': None, 'stack': [], 'unwound': 2}{'handler': None, 'stack': [], 'unwound': 2}Passed

SHA-256 / 0c14b5d32c1af4605ea8187f01afd426afd16aee58098c0b4f381b865e9c7b37

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:22.424950+00:00.

Case digest / 435ce807bc2b8175708e342cb6f586fcad3182149df6e58ce318b8e913a809f1