{"abstract":"A stiff spring that should orbit with bounded energy gains amplitude every frame.","category":"Physics integrator stability","checks":8,"contract":"solve(x0, v0, k, m, c, dt, steps): damped spring a=(-k*x-c*v)/m integrated with semi-implicit Euler (velocity first, then position with the new velocity). Each frame of length dt is split into ceil(dt/0.05) equal substeps (at least one). Return [x, v] rounded to 6 decimals after steps frames.","contract_signature":"x0, v0, k, m, c, dt, steps","evaluation_group":"w2-physics_integrator_stability-substep-symplectic-euler","failed_approach":"Averaging old and new velocity for the drift gives a trapezoid-like scheme that is not the contracted symplectic update.","family":"w2-physics_integrator_stability-substep-symplectic-euler-position-update-ordering","id":"FA-86841","implementations":{"attempt":{"sha256":"2d4a1157e497fa18200bb64c91ad6f71d123d21e5190d0710a15eea3dba22edd","source":"\"\"\"Failure Map reference implementation. Python standard library only.\"\"\"\nimport json\nimport math\nN = 1\nobservations = []\ndef solve(x0, v0, k, m, c, dt, steps):\n    n_sub = max(1, math.ceil(dt / 0.05 - 1e-12))\n    h = dt / n_sub\n    x, v = x0, v0\n    for _ in range(steps):\n        for _ in range(n_sub):\n            a = (-k * x - c * v) / m\n            vn = v + a * h\n            x = x + 0.5 * (v + vn) * h\n            v = vn\n    return [round(x, 6), round(v, 6)]\ndef check(label, actual, expected):\n    observations.append({\"check\": label, \"actual\": actual, \"expected\": expected, \"passed\": actual == expected})\nfixtures = [[[[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[-0.958, 1.121, 24.102, 1.592, 0.332, 0.04, 3], [-0.694302, 2.683815]], [[-1.072, -0.219, 22.982, 2.32, 1.666, 0.05, 1], [-1.056009, 0.319827]], [[1.454, -0.539, 11.28, 2.71, 0.785, 0.07, 0], [1.454, -0.539]], [[1.545, 1.962, 22.255, 1.613, 1.385, 0.02, 0], [1.545, 1.962]], [[0.428, -0.176, 18.564, 2.203, 1.454, 0.07, 2], [0.36285, -0.625106]], [[0.514, 1.143, 25.432, 0.518, 1.496, 0.13, 9], [-0.010702, -0.661591]], [[-1.539, -1.291, 32.554, 2.072, 1.066, 0.07, 3], [-1.199771, 3.497044]]], [[[1.742, -0.907, 38.421, 2.244, 0.819, 0.1, 5], [-1.031195, -5.442883]], [[-1.037, 0.234, 1.989, 0.946, 0.544, 0.01, 8], [-1.011063, 0.39269]], [[1.602, 1.18, 24.517, 1.738, 1.228, 0.05, 12], [-0.636953, -4.398087]], [[-0.384, 0.483, 39.776, 2.351, 1.463, 0.04, 0], [-0.384, 0.483]], [[-1.526, 0.873, 6.362, 1.828, 1.137, 0.13, 0], [-1.526, 0.873]], [[-1.985, 0.451, 27.993, 1.055, 0.395, 0.02, 2], [-1.904435, 2.527224]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[-0.365, 1.406, 18.892, 1.116, 1.872, 0.05, 6], [0.118578, 1.39259]]], [[[1.454, 1.519, 3.577, 1.401, 0.303, 0.04, 8], [1.697018, 0.15014]], [[-1.712, -1.9, 9.139, 0.693, 0.61, 0.05, 13], [0.624756, 4.351887]], [[0.87, 1.182, 19.781, 1.146, 0.3, 0.1, 0], [0.87, 1.182]], [[0.116, -1.998, 11.275, 2.342, 1.481, 0.1, 12], [-0.366142, 1.157058]], [[-0.541, 0.707, 32.675, 1.469, 1.372, 0.2, 9], [0.199962, 0.643469]], [[-1.675, 0.095, 12.217, 1.214, 0.078, 0.13, 11], [0.14895, -5.038149]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[1.648, -0.117, 24.609, 0.651, 1.732, 0.05, 0], [1.648, -0.117]]], [[[0.286, 1.636, 25.073, 1.437, 1.309, 0.1, 0], [0.286, 1.636]], [[-0.07, 1.272, 25.671, 1.8, 0.333, 0.02, 8], [0.132138, 1.188849]], [[-1.284, 1.069, 32.194, 0.542, 0.353, 0.05, 11], [0.174523, -8.251404]], [[-1.975, -1.176, 27.308, 0.777, 1.386, 0.04, 3], [-1.482343, 6.386036]], [[1.974, -1.489, 34.073, 1.218, 1.372, 0.05, 10], [-1.429284, -2.634338]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[0.484, 0.239, 12.355, 0.868, 0.3, 0.07, 0], [0.484, 0.239]], [[-0.117, 1.853, 21.165, 2.719, 0.626, 0.07, 12], [0.503218, -0.957084]]], [[[-0.078, -0.863, 3.994, 2.622, 1.462, 0.1, 0], [-0.078, -0.863]], [[-0.056, -1.079, 26.249, 1.108, 0.441, 0.07, 8], [-0.030782, 0.966174]], [[0.855, 1.882, 14.464, 2.712, 0.17, 0.02, 0], [0.855, 1.882]], [[0.633, -1.784, 4.173, 2.063, 1.163, 0.13, 21], [0.109799, 0.812645]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[-0.29, -0.513, 1.621, 0.73, 0.535, 0.2, 8], [-0.052879, 0.418713]], [[1.617, 1.871, 21.063, 0.682, 0.338, 0.02, 7], [1.325932, -4.832529]], [[1.925, -1.211, 19.503, 2.115, 0.02, 0.13, 1], [1.574252, -3.400654]]]]\nfor i, (args, expected) in enumerate(fixtures[N-1]):\n    check(\"case %d\" % i, solve(*args), expected)\nprint(json.dumps({\"observations\": observations, \"passed\": all(x[\"passed\"] for x in observations)}, ensure_ascii=False))\nraise SystemExit(0 if all(x[\"passed\"] for x in observations) else 1)\n"},"broken":{"sha256":"e4825c66a36c03ef84fc6bf3cffece47887de3ae7899eb463dd5a92119c959cc","source":"\"\"\"Failure Map reference implementation. Python standard library only.\"\"\"\nimport json\nimport math\nN = 1\nobservations = []\ndef solve(x0, v0, k, m, c, dt, steps):\n    n_sub = max(1, math.ceil(dt / 0.05 - 1e-12))\n    h = dt / n_sub\n    x, v = x0, v0\n    for _ in range(steps):\n        for _ in range(n_sub):\n            a = (-k * x - c * v) / m\n            x = x + v * h\n            v = v + a * h\n    return [round(x, 6), round(v, 6)]\ndef check(label, actual, expected):\n    observations.append({\"check\": label, \"actual\": actual, \"expected\": expected, \"passed\": actual == expected})\nfixtures = [[[[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[-0.958, 1.121, 24.102, 1.592, 0.332, 0.04, 3], [-0.694302, 2.683815]], [[-1.072, -0.219, 22.982, 2.32, 1.666, 0.05, 1], [-1.056009, 0.319827]], [[1.454, -0.539, 11.28, 2.71, 0.785, 0.07, 0], [1.454, -0.539]], [[1.545, 1.962, 22.255, 1.613, 1.385, 0.02, 0], [1.545, 1.962]], [[0.428, -0.176, 18.564, 2.203, 1.454, 0.07, 2], [0.36285, -0.625106]], [[0.514, 1.143, 25.432, 0.518, 1.496, 0.13, 9], [-0.010702, -0.661591]], [[-1.539, -1.291, 32.554, 2.072, 1.066, 0.07, 3], [-1.199771, 3.497044]]], [[[1.742, -0.907, 38.421, 2.244, 0.819, 0.1, 5], [-1.031195, -5.442883]], [[-1.037, 0.234, 1.989, 0.946, 0.544, 0.01, 8], [-1.011063, 0.39269]], [[1.602, 1.18, 24.517, 1.738, 1.228, 0.05, 12], [-0.636953, -4.398087]], [[-0.384, 0.483, 39.776, 2.351, 1.463, 0.04, 0], [-0.384, 0.483]], [[-1.526, 0.873, 6.362, 1.828, 1.137, 0.13, 0], [-1.526, 0.873]], [[-1.985, 0.451, 27.993, 1.055, 0.395, 0.02, 2], [-1.904435, 2.527224]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[-0.365, 1.406, 18.892, 1.116, 1.872, 0.05, 6], [0.118578, 1.39259]]], [[[1.454, 1.519, 3.577, 1.401, 0.303, 0.04, 8], [1.697018, 0.15014]], [[-1.712, -1.9, 9.139, 0.693, 0.61, 0.05, 13], [0.624756, 4.351887]], [[0.87, 1.182, 19.781, 1.146, 0.3, 0.1, 0], [0.87, 1.182]], [[0.116, -1.998, 11.275, 2.342, 1.481, 0.1, 12], [-0.366142, 1.157058]], [[-0.541, 0.707, 32.675, 1.469, 1.372, 0.2, 9], [0.199962, 0.643469]], [[-1.675, 0.095, 12.217, 1.214, 0.078, 0.13, 11], [0.14895, -5.038149]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[1.648, -0.117, 24.609, 0.651, 1.732, 0.05, 0], [1.648, -0.117]]], [[[0.286, 1.636, 25.073, 1.437, 1.309, 0.1, 0], [0.286, 1.636]], [[-0.07, 1.272, 25.671, 1.8, 0.333, 0.02, 8], [0.132138, 1.188849]], [[-1.284, 1.069, 32.194, 0.542, 0.353, 0.05, 11], [0.174523, -8.251404]], [[-1.975, -1.176, 27.308, 0.777, 1.386, 0.04, 3], [-1.482343, 6.386036]], [[1.974, -1.489, 34.073, 1.218, 1.372, 0.05, 10], [-1.429284, -2.634338]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[0.484, 0.239, 12.355, 0.868, 0.3, 0.07, 0], [0.484, 0.239]], [[-0.117, 1.853, 21.165, 2.719, 0.626, 0.07, 12], [0.503218, -0.957084]]], [[[-0.078, -0.863, 3.994, 2.622, 1.462, 0.1, 0], [-0.078, -0.863]], [[-0.056, -1.079, 26.249, 1.108, 0.441, 0.07, 8], [-0.030782, 0.966174]], [[0.855, 1.882, 14.464, 2.712, 0.17, 0.02, 0], [0.855, 1.882]], [[0.633, -1.784, 4.173, 2.063, 1.163, 0.13, 21], [0.109799, 0.812645]], [[1.0, 0.0, 10.0, 1.0, 0.0, 0.05, 0], [1.0, 0.0]], [[-0.29, -0.513, 1.621, 0.73, 0.535, 0.2, 8], [-0.052879, 0.418713]], [[1.617, 1.871, 21.063, 0.682, 0.338, 0.02, 7], [1.325932, -4.832529]], [[1.925, -1.211, 19.503, 2.115, 0.02, 0.13, 1], [1.574252, -3.400654]]]]\nfor i, (args, expected) in enumerate(fixtures[N-1]):\n    check(\"case %d\" % i, solve(*args), expected)\nprint(json.dumps({\"observations\": observations, \"passed\": all(x[\"passed\"] for x in observations)}, ensure_ascii=False))\nraise SystemExit(0 if all(x[\"passed\"] for x in observations) else 1)\n"}},"limitations":"A deterministic bounded teaching model with stipulated toy conventions and rounded float output; not a production physics engine or a proof of numerical stability. This reproducer isolates one failure mechanism. Results cover the supplied fixtures. Variants within a family share a test contract and should remain grouped when constructing evaluation splits. Related mechanisms with a shared evaluation_group must also remain together; these controlled models are not independent production incidents.","method":"Deterministic executable model with adversarial boundary fixtures.","provenance":{"created_by":"Failure Map","dependencies":"Python standard library","family":"w2-physics_integrator_stability-substep-symplectic-euler-position-update-ordering","generated_at":"2026-09-29T14:50:53.362280+00:00","license":"CC0-1.0","python":"3.12.14","seed":1,"split":"open-access"},"relevance":"Game and robotics physics loops depend on integrator update order, step control and stabilization terms; a wrong decision point turns a stable simulation into drifting or exploding motion.","root_cause":"The position update runs before the velocity kick, turning the scheme into explicit forward Euler.","sha256":"530a969b66bcb355fd0c2307827a567ca7d6adc72c9f63e6944714aa37eb921f","title":"Symplectic Euler substep drifts position with the pre-kick velocity · case 01","variant":1,"variant_policy":"Five numbered records share a model and may reuse boundary fixtures.","verified":true,"visibility":"public","verification":{"attempt":{"elapsed_ms":46.202,"exit_code":1,"observations":[{"actual":[1.0,0.0],"check":"case 0","expected":[1.0,0.0],"passed":true},{"actual":[-0.724881,2.703859],"check":"case 1","expected":[-0.694302,2.683815],"passed":false},{"actual":[-1.069479,0.319827],"check":"case 2","expected":[-1.056009,0.319827],"passed":false},{"actual":[1.454,-0.539],"check":"case 3","expected":[1.454,-0.539],"passed":true},{"actual":[1.545,1.962],"check":"case 4","expected":[1.545,1.962],"passed":true},{"actual":[0.37056,-0.628685],"check":"case 5","expected":[0.36285,-0.625106],"passed":false},{"actual":[-0.010003,-1.316001],"check":"case 6","expected":[-0.010702,-0.661591],"passed":false},{"actual":[-1.275917,3.611958],"check":"case 7","expected":[-1.199771,3.497044],"passed":false}],"passed":false,"stderr":"","stdout":"{\"observations\": [{\"check\": \"case 0\", \"actual\": [1.0, 0.0], \"expected\": [1.0, 0.0], \"passed\": true}, {\"check\": \"case 1\", \"actual\": [-0.724881, 2.703859], \"expected\": [-0.694302, 2.683815], \"passed\": false}, {\"check\": \"case 2\", \"actual\": [-1.069479, 0.319827], \"expected\": [-1.056009, 0.319827], \"passed\": false}, {\"check\": \"case 3\", \"actual\": [1.454, -0.539], \"expected\": [1.454, -0.539], \"passed\": true}, {\"check\": \"case 4\", \"actual\": [1.545, 1.962], \"expected\": [1.545, 1.962], \"passed\": true}, {\"check\": \"case 5\", \"actual\": [0.37056, -0.628685], \"expected\": [0.36285, -0.625106], \"passed\": false}, {\"check\": \"case 6\", \"actual\": [-0.010003, -1.316001], \"expected\": [-0.010702, -0.661591], \"passed\": false}, {\"check\": \"case 7\", \"actual\": [-1.275917, 3.611958], \"expected\": [-1.199771, 3.497044], \"passed\": false}], \"passed\": false}\n"},"broken":{"elapsed_ms":47.784,"exit_code":1,"observations":[{"actual":[1.0,0.0],"check":"case 0","expected":[1.0,0.0],"passed":true},{"actual":[-0.756262,2.724071],"check":"case 1","expected":[-0.694302,2.683815],"passed":false},{"actual":[-1.08295,0.319827],"check":"case 2","expected":[-1.056009,0.319827],"passed":false},{"actual":[1.454,-0.539],"check":"case 3","expected":[1.454,-0.539],"passed":true},{"actual":[1.545,1.962],"check":"case 4","expected":[1.545,1.962],"passed":true},{"actual":[0.378395,-0.63229],"check":"case 5","expected":[0.36285,-0.625106],"passed":false},{"actual":[0.021512,-2.569141],"check":"case 6","expected":[-0.010702,-0.661591],"passed":false},{"actual":[-1.356003,3.729909],"check":"case 7","expected":[-1.199771,3.497044],"passed":false}],"passed":false,"stderr":"","stdout":"{\"observations\": [{\"check\": \"case 0\", \"actual\": [1.0, 0.0], \"expected\": [1.0, 0.0], \"passed\": true}, {\"check\": \"case 1\", \"actual\": [-0.756262, 2.724071], \"expected\": [-0.694302, 2.683815], \"passed\": false}, {\"check\": \"case 2\", \"actual\": [-1.08295, 0.319827], \"expected\": [-1.056009, 0.319827], \"passed\": false}, {\"check\": \"case 3\", \"actual\": [1.454, -0.539], \"expected\": [1.454, -0.539], \"passed\": true}, {\"check\": \"case 4\", \"actual\": [1.545, 1.962], \"expected\": [1.545, 1.962], \"passed\": true}, {\"check\": \"case 5\", \"actual\": [0.378395, -0.63229], \"expected\": [0.36285, -0.625106], \"passed\": false}, {\"check\": \"case 6\", \"actual\": [0.021512, -2.569141], \"expected\": [-0.010702, -0.661591], \"passed\": false}, {\"check\": \"case 7\", \"actual\": [-1.356003, 3.729909], \"expected\": [-1.199771, 3.497044], \"passed\": false}], \"passed\": false}\n"}},"member_only":{"stages":["fixed"],"fields":["implementations.fixed","verification.fixed","harness","repair"],"note":"The verified repair, its recorded checks, the repair description, and the scoring harness are available to members."}}