FA-82451 / Chess move legality / Open access
Castling with a knight in the rook corner · case 01
White castles kingside with a knight or an enemy rook on h1.
ROOT CAUSE
The corner is only checked for being occupied.
THE FAILURE
The corner is only checked for being occupied.
Unsuccessful approach: Hard-coding the white rook letter rejects every black castling move.
Case contract
Input: {"board", "side": "w" or "b", "wing": "K" or "Q", "rights": subset of "KQkq"}. Standard castling is legal when the right is held, the king is on e1/e8 and the matching own rook on h- or a-file, the squares between them are empty (f,g or b,c,d), and none of the king's squares e, f, g (kingside) or e, d, c (queenside) is attacked by the opponent.
Why this case matters
Move validators gate every move in engines, servers and arbiters; accepting an illegal move or rejecting a legal one corrupts the game record.
1 / The failure
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(x):
def attacked(bd, sq, by_white):
f,r=ord(sq[0])-97,int(sq[1])-1
def at(ff,rr):
return bd.get(chr(97+ff)+str(rr+1)) if 0<=ff<8 and 0<=rr<8 else None
P,N,B,R,Q,K=('PNBRQK' if by_white else 'pnbrqk')
pr=r-1 if by_white else r+1
if at(f-1,pr)==P or at(f+1,pr)==P: return True
for df,dr in ((1,2),(2,1),(-1,2),(-2,1),(1,-2),(2,-1),(-1,-2),(-2,-1)):
if at(f+df,r+dr)==N: return True
for df in (-1,0,1):
for dr in (-1,0,1):
if (df or dr) and at(f+df,r+dr)==K: return True
for df,dr,kinds in ((1,0,(R,Q)),(-1,0,(R,Q)),(0,1,(R,Q)),(0,-1,(R,Q)),(1,1,(B,Q)),(1,-1,(B,Q)),(-1,1,(B,Q)),(-1,-1,(B,Q))):
ff,rr=f+df,r+dr
while 0<=ff<8 and 0<=rr<8:
v=at(ff,rr)
if v:
if v in kinds: return True
break
ff+=df; rr+=dr
return False
b=x['board']; white=x['side']=='w'; wing=x['wing']
rank='1' if white else '8'
right=wing if white else wing.lower()
if right not in x['rights']: return False
if b.get('e'+rank)!=('K' if white else 'k'): return False
rook_sq=('h' if wing=='K' else 'a')+rank
if rook_sq not in b: return False
between='fg' if wing=='K' else 'bcd'
if any(f+rank in b for f in between): return False
path='efg' if wing=='K' else 'edc'
return not any(attacked(b, f+rank, not white) for f in path)
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('white kingside clear',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'KQkq', 'side': 'w', 'wing': 'K'}, True),
('queenside b-file blocked',
{'board': {'a1': 'R', 'b1': 'N', 'e1': 'K', 'e8': 'k'},
'rights': 'KQ',
'side': 'w',
'wing': 'Q'},
False),
('queenside b-file attacked',
{'board': {'a1': 'R', 'b8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
True),
('in check',
{'board': {'a8': 'k', 'e1': 'K', 'e8': 'r', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('f1 attacked',
{'board': {'c4': 'b', 'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('black uses own right',
{'board': {'e1': 'K', 'e8': 'k', 'h8': 'r'}, 'rights': 'K', 'side': 'b', 'wing': 'K'}, False),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False)],
[('in check',
{'board': {'a8': 'k', 'e1': 'K', 'e8': 'r', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('f1 attacked',
{'board': {'c4': 'b', 'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('black uses own right',
{'board': {'e1': 'K', 'e8': 'k', 'h8': 'r'}, 'rights': 'K', 'side': 'b', 'wing': 'K'}, False),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('enemy rook in corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'r'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('pawn attacks g1 from h2',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R', 'h2': 'p'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('white pawn on f2 harmless',
{'board': {'e1': 'K', 'e8': 'k', 'g2': 'P', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
True)],
[('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('enemy rook in corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'r'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('pawn attacks g1 from h2',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R', 'h2': 'p'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('white pawn on f2 harmless',
{'board': {'e1': 'K', 'e8': 'k', 'g2': 'P', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
True),
('black pawn attacks f8 check',
{'board': {'e1': 'K', 'e7': 'P', 'e8': 'k', 'h8': 'r'}, 'rights': 'k', 'side': 'b', 'wing': 'K'},
False),
('shielded rook attack',
{'board': {'a8': 'k', 'e1': 'K', 'f4': 'P', 'f8': 'r', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True),
('own piece shields g1',
{'board': {'a8': 'k', 'e1': 'K', 'g3': 'N', 'g5': 'q', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True)],
[('white kingside clear',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'KQkq', 'side': 'w', 'wing': 'K'}, True),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('black pawn attacks f8 check',
{'board': {'e1': 'K', 'e7': 'P', 'e8': 'k', 'h8': 'r'}, 'rights': 'k', 'side': 'b', 'wing': 'K'},
False),
('shielded rook attack',
{'board': {'a8': 'k', 'e1': 'K', 'f4': 'P', 'f8': 'r', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True),
('own piece shields g1',
{'board': {'a8': 'k', 'e1': 'K', 'g3': 'N', 'g5': 'q', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True),
('c1 attacked',
{'board': {'a1': 'R', 'e1': 'K', 'e8': 'k', 'h6': 'b'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False),
('d1 blocked',
{'board': {'a1': 'R', 'd1': 'Q', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False)],
[('white kingside clear',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'KQkq', 'side': 'w', 'wing': 'K'}, True),
('queenside b-file blocked',
{'board': {'a1': 'R', 'b1': 'N', 'e1': 'K', 'e8': 'k'},
'rights': 'KQ',
'side': 'w',
'wing': 'Q'},
False),
('queenside b-file attacked',
{'board': {'a1': 'R', 'b8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
True),
('in check',
{'board': {'a8': 'k', 'e1': 'K', 'e8': 'r', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('c1 attacked',
{'board': {'a1': 'R', 'e1': 'K', 'e8': 'k', 'h6': 'b'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False),
('d1 blocked',
{'board': {'a1': 'R', 'd1': 'Q', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False)]]
for label, args, expected in fixtures[N-1]:
try:
actual = solve(args)
except Exception as exc:
actual = 'error:' + type(exc).__name__
check(label, actual, expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| white kingside clear | True | True | Passed |
| queenside b-file blocked | False | False | Passed |
| queenside b-file attacked | True | True | Passed |
| in check | False | False | Passed |
| f1 attacked | False | False | Passed |
| black uses own right | False | False | Passed |
| black has right | True | True | Passed |
| knight in rook corner | True | False | Failed |
SHA-256 / 68c034d8520420783cc4328493d29f9878e39012f60ca629d5a4f963c7625e1f
2 / The unsuccessful fix
Exit 1"""Failure Map reference implementation. Python standard library only."""
import json
N = 1
observations = []
def solve(x):
def attacked(bd, sq, by_white):
f,r=ord(sq[0])-97,int(sq[1])-1
def at(ff,rr):
return bd.get(chr(97+ff)+str(rr+1)) if 0<=ff<8 and 0<=rr<8 else None
P,N,B,R,Q,K=('PNBRQK' if by_white else 'pnbrqk')
pr=r-1 if by_white else r+1
if at(f-1,pr)==P or at(f+1,pr)==P: return True
for df,dr in ((1,2),(2,1),(-1,2),(-2,1),(1,-2),(2,-1),(-1,-2),(-2,-1)):
if at(f+df,r+dr)==N: return True
for df in (-1,0,1):
for dr in (-1,0,1):
if (df or dr) and at(f+df,r+dr)==K: return True
for df,dr,kinds in ((1,0,(R,Q)),(-1,0,(R,Q)),(0,1,(R,Q)),(0,-1,(R,Q)),(1,1,(B,Q)),(1,-1,(B,Q)),(-1,1,(B,Q)),(-1,-1,(B,Q))):
ff,rr=f+df,r+dr
while 0<=ff<8 and 0<=rr<8:
v=at(ff,rr)
if v:
if v in kinds: return True
break
ff+=df; rr+=dr
return False
b=x['board']; white=x['side']=='w'; wing=x['wing']
rank='1' if white else '8'
right=wing if white else wing.lower()
if right not in x['rights']: return False
if b.get('e'+rank)!=('K' if white else 'k'): return False
rook_sq=('h' if wing=='K' else 'a')+rank
if b.get(rook_sq)!='R': return False
between='fg' if wing=='K' else 'bcd'
if any(f+rank in b for f in between): return False
path='efg' if wing=='K' else 'edc'
return not any(attacked(b, f+rank, not white) for f in path)
def check(label, actual, expected):
observations.append({"check": label, "actual": actual, "expected": expected, "passed": actual == expected})
fixtures = [[('white kingside clear',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'KQkq', 'side': 'w', 'wing': 'K'}, True),
('queenside b-file blocked',
{'board': {'a1': 'R', 'b1': 'N', 'e1': 'K', 'e8': 'k'},
'rights': 'KQ',
'side': 'w',
'wing': 'Q'},
False),
('queenside b-file attacked',
{'board': {'a1': 'R', 'b8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
True),
('in check',
{'board': {'a8': 'k', 'e1': 'K', 'e8': 'r', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('f1 attacked',
{'board': {'c4': 'b', 'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('black uses own right',
{'board': {'e1': 'K', 'e8': 'k', 'h8': 'r'}, 'rights': 'K', 'side': 'b', 'wing': 'K'}, False),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False)],
[('in check',
{'board': {'a8': 'k', 'e1': 'K', 'e8': 'r', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('f1 attacked',
{'board': {'c4': 'b', 'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('black uses own right',
{'board': {'e1': 'K', 'e8': 'k', 'h8': 'r'}, 'rights': 'K', 'side': 'b', 'wing': 'K'}, False),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('enemy rook in corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'r'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('pawn attacks g1 from h2',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R', 'h2': 'p'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('white pawn on f2 harmless',
{'board': {'e1': 'K', 'e8': 'k', 'g2': 'P', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
True)],
[('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('enemy rook in corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'r'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('pawn attacks g1 from h2',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R', 'h2': 'p'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('white pawn on f2 harmless',
{'board': {'e1': 'K', 'e8': 'k', 'g2': 'P', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
True),
('black pawn attacks f8 check',
{'board': {'e1': 'K', 'e7': 'P', 'e8': 'k', 'h8': 'r'}, 'rights': 'k', 'side': 'b', 'wing': 'K'},
False),
('shielded rook attack',
{'board': {'a8': 'k', 'e1': 'K', 'f4': 'P', 'f8': 'r', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True),
('own piece shields g1',
{'board': {'a8': 'k', 'e1': 'K', 'g3': 'N', 'g5': 'q', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True)],
[('white kingside clear',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'KQkq', 'side': 'w', 'wing': 'K'}, True),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('black pawn attacks f8 check',
{'board': {'e1': 'K', 'e7': 'P', 'e8': 'k', 'h8': 'r'}, 'rights': 'k', 'side': 'b', 'wing': 'K'},
False),
('shielded rook attack',
{'board': {'a8': 'k', 'e1': 'K', 'f4': 'P', 'f8': 'r', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True),
('own piece shields g1',
{'board': {'a8': 'k', 'e1': 'K', 'g3': 'N', 'g5': 'q', 'h1': 'R'},
'rights': 'K',
'side': 'w',
'wing': 'K'},
True),
('c1 attacked',
{'board': {'a1': 'R', 'e1': 'K', 'e8': 'k', 'h6': 'b'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False),
('d1 blocked',
{'board': {'a1': 'R', 'd1': 'Q', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False)],
[('white kingside clear',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'R'}, 'rights': 'KQkq', 'side': 'w', 'wing': 'K'}, True),
('queenside b-file blocked',
{'board': {'a1': 'R', 'b1': 'N', 'e1': 'K', 'e8': 'k'},
'rights': 'KQ',
'side': 'w',
'wing': 'Q'},
False),
('queenside b-file attacked',
{'board': {'a1': 'R', 'b8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
True),
('in check',
{'board': {'a8': 'k', 'e1': 'K', 'e8': 'r', 'h1': 'R'}, 'rights': 'K', 'side': 'w', 'wing': 'K'},
False),
('black has right',
{'board': {'a8': 'r', 'e1': 'K', 'e8': 'k'}, 'rights': 'q', 'side': 'b', 'wing': 'Q'}, True),
('knight in rook corner',
{'board': {'e1': 'K', 'e8': 'k', 'h1': 'N'}, 'rights': 'K', 'side': 'w', 'wing': 'K'}, False),
('c1 attacked',
{'board': {'a1': 'R', 'e1': 'K', 'e8': 'k', 'h6': 'b'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False),
('d1 blocked',
{'board': {'a1': 'R', 'd1': 'Q', 'e1': 'K', 'e8': 'k'}, 'rights': 'Q', 'side': 'w', 'wing': 'Q'},
False)]]
for label, args, expected in fixtures[N-1]:
try:
actual = solve(args)
except Exception as exc:
actual = 'error:' + type(exc).__name__
check(label, actual, expected)
print(json.dumps({"observations": observations, "passed": all(x["passed"] for x in observations)}, ensure_ascii=False))
raise SystemExit(0 if all(x["passed"] for x in observations) else 1)
| Boundary fixture | Actual | Expected | Outcome |
|---|---|---|---|
| white kingside clear | True | True | Passed |
| queenside b-file blocked | False | False | Passed |
| queenside b-file attacked | True | True | Passed |
| in check | False | False | Passed |
| f1 attacked | False | False | Passed |
| black uses own right | False | False | Passed |
| black has right | False | True | Failed |
| knight in rook corner | False | False | Passed |
SHA-256 / 02bce4c23e67b69ab1672350748019c6d8804bea0940e13ec508c86f80eafb66
HELD IN THE MEMBER ARCHIVE
The verified repair and its recorded checks are member-only.
This mechanism has 8 recorded checks per implementation. The open-access tier publishes the failure and the unsuccessful fix; the repaired source that passes every check, and the observations that prove it, are available to members.
Every case sharing this mechanism uses the same contract and the same repair, so this one record is held back for all of them.
Member access is invitation-based. Sign in with your invited account to inspect the repair.
Sign in to the archive ↗Verification & scope
A deterministic toy model with an explicitly stated contract; boards are {square: piece} with white upper-case and black lower-case pieces; no claim of full FIDE Laws conformance. 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:50:12.152633+00:00.
Case digest / cce8078844b9c27e21d63df4522dce3b9a7d28f8cc8f22bda931c0138010bb58