LittlePlyResearch notebook

match_runner.py

python · 389 lines · Sanitized derivative

Line 1 ↗

Sanitized derivative: private paths or personal test identities use explicit placeholders. Original line count is preserved.

Version & provenance · cm8-evaluation-v1

Recorded SHA-256 95e7eba750a4175e1f16f283bce437642147510d189414439837dbfc990f16a3Rendered SHA-256 57c9e2251f588318514943f420ae071d395f418822865797a097910f002b7759

Original LittlePly code: Apache-2.0. External Rust helper remains a separate GPL component. License notes. Line links are stable within this snapshot. Frozen research implementation; host paths redacted. Original and rendered digests identify the derivative; not a portable launcher or complete training payload.

1"""Frozen-suite runner. Default is plan-only; matches require a reviewed release.
2
3Existing model/harness/serving files are read-only. Linux guardian owns the match
4worker/model group; detached UCI children additionally die with their parent.
5"""
6import argparse,ctypes,hashlib,importlib.util,io,json,math,os,re,signal,subprocess,sys,time,uuid
7from pathlib import Path
8
9def engine_child(parent,command):
10    """Contain the engine before importing project packages or executing it."""
11    if os.name!='posix':raise RuntimeError('Linux parent-death handling required')
12    if ctypes.CDLL(None,use_errno=True).prctl(1,signal.SIGKILL,0,0,0)!=0:raise OSError(ctypes.get_errno(),'PDEATHSIG failed')
13    if os.getppid()!=parent:raise RuntimeError('engine parent disappeared before initialization')
14    os.execv(command[0],command)
15
16if __name__=='__main__' and sys.argv[1:2]==['--engine-child']:
17    engine_child(int(sys.argv[2]),sys.argv[3:])
18
19ROOT=Path(__file__).resolve().parent
20PROJECT=ROOT.parent
21HARNESS_ROOT=ROOT
22SUNFISH_ROOT=PROJECT.parent.parent/'task-16'
23GUARDIAN_PATH=(PROJECT/'scaleup-v1/runtime/training_deadline.py').resolve()
24MODEL_METRICS={'raw_greedy_tokens','raw_greedy_legal','legal_joint_probability',
25               'illegal_or_nonmove_three_token_probability','selected_joint_log_probability','forward_calls'}
26APPROVAL_KEYS={'approved','run_id','run_directory','suite_sha256','execution_contract_sha256','runner_sha256','guardian_sha256','checkpoint','checkpoint_sha256','dataset_manifest','dataset_manifest_sha256','device','role','budget_seconds'}
27sys.path[:0]=[str(PROJECT),str(HARNESS_ROOT),str(PROJECT/'scaleup-v1/runtime')]
28# Make only the existing pure-Python chess package visible in spawned model workers.
29if importlib.util.find_spec('chess') is None:
30    package=Path('/REDACTED')
31    spec=importlib.util.spec_from_file_location('chess',package/'__init__.py',submodule_search_locations=[str(package)])
32    module=importlib.util.module_from_spec(spec);sys.modules['chess']=module;spec.loader.exec_module(module)
33
34def sha(path):
35    h=hashlib.sha256()
36    with Path(path).open('rb') as stream:
37        while block:=stream.read(8*1024*1024):h.update(block)
38    return h.hexdigest()
39
40def load_guardian(expected_hash=None):
41    """Load exactly the approved file, independent of sys.path/sys.modules."""
42    path=GUARDIAN_PATH.resolve()
43    source=path.read_bytes()
44    if expected_hash is not None and hashlib.sha256(source).hexdigest()!=expected_hash:raise ValueError('approved guardian changed')
45    spec=importlib.util.spec_from_file_location('_chess_match_guardian_'+uuid.uuid4().hex,path)
46    module=importlib.util.module_from_spec(spec);exec(compile(source,str(path),'exec'),module.__dict__)
47    if Path(module.__file__).resolve()!=path:raise RuntimeError('guardian module identity mismatch')
48    return module
49
50def require_guardian():
51    if os.environ.get('CHESS_MATCH_GUARDED')!='1' or os.getpgrp()!=os.getpid():raise RuntimeError('match worker requires its guardian-owned process group')
52    parent_command=Path(f'/proc/{os.getppid()}/cmdline').read_bytes().split(b'\0')
53    if str(GUARDIAN_PATH).encode() not in parent_command or b'--guardian' not in parent_command:
54        raise RuntimeError('match worker parent is not the approved guardian')
55
56def model_metrics(row,board):
57    """Raw model rows cannot evade denominators or omit probability diagnostics."""
58    import chess
59    if row.get('model_query')!='queried' or not MODEL_METRICS.issubset(row):raise ValueError('model policy requires queried and complete raw metrics')
60    raw=row['raw_greedy_tokens']
61    if not isinstance(raw,list) or len(raw)!=3 or any(type(t)is not int or not 0<=t<512 for t in raw):raise ValueError('invalid raw greedy tokens')
62    if type(row['raw_greedy_legal'])is not bool:raise ValueError('invalid raw legality flag')
63    promotions={None:64,chess.KNIGHT:65,chess.BISHOP:66,chess.ROOK:67,chess.QUEEN:68}
64    legal=any(raw==[m.from_square,m.to_square,promotions[m.promotion]] for m in board.legal_moves)
65    if row['raw_greedy_legal']!=legal:raise ValueError('raw greedy legality disagrees with board')
66    for key in ('legal_joint_probability','illegal_or_nonmove_three_token_probability','selected_joint_log_probability'):
67        if type(row[key])not in (int,float) or not math.isfinite(row[key]):raise ValueError('invalid raw model metrics')
68    mass=row['legal_joint_probability'];illegal=row['illegal_or_nonmove_three_token_probability']
69    if not 0<=mass<=1+1e-8 or not 0<=illegal<=1+1e-8 or abs(illegal-max(0.,1.-mass))>1e-8:raise ValueError('invalid probability mass accounting')
70    if row['selected_joint_log_probability']>1e-8:raise ValueError('invalid selected log probability')
71    if type(row['forward_calls'])is not int or row['forward_calls']<1:raise ValueError('invalid forward-call count')
72def write(path,value):
73    path=Path(path);tmp=path.with_name(path.name+'.tmp')
74    with tmp.open('w',encoding='utf-8') as stream:
75        stream.write(value if isinstance(value,str) else json.dumps(value,indent=2));stream.flush();os.fsync(stream.fileno())
76    tmp.replace(path)
77def inputs():
78    contract=json.loads((ROOT/'execution-contract.json').read_text())
79    if sha(ROOT/'suite-100.json')!=contract['suite_sha256']:raise ValueError('frozen suite changed')
80    suite=json.loads((ROOT/'suite-100.json').read_text())
81    from checkpoint_gate import validate_suite
82    validate_suite(suite,contract)
83    return suite,contract
84
85def verify_sources(contract):
86    for name,expected in contract['source_hashes'].items():
87        if sha(Path(name))!=expected:raise ValueError('execution source changed: '+name)
88    git=['git','-c','core.autocrlf=true','-c','core.filemode=false','-C',str(SUNFISH_ROOT/'sunfish')]
89    if subprocess.check_output(git+['rev-parse','HEAD'],text=True).strip()!=contract['sunfish_commit']:
90        raise ValueError('Sunfish commit changed')
91    if subprocess.check_output(git+['status','--porcelain'],text=True).strip():raise ValueError('Sunfish checkout modified')
92
93def proof_check(h,board,proof,color,depth=0):
94    import chess
95    if depth>7 or board.fen()!=proof['fen']:raise ValueError('bad mate proof state')
96    if proof['kind']=='checkmate':
97        if not board.is_checkmate() or board.turn==color:raise ValueError('false mate proof')
98        return
99    if depth>=7 or h.outcome(board) is not None:raise ValueError('mate proof crosses end/depth')
100    branches=proof['branches']
101    if board.turn!=color:
102        if sorted(x['move'] for x in branches)!=sorted(m.uci() for m in board.legal_moves):raise ValueError('missing defender proof branch')
103    elif len(branches)!=1:raise ValueError('invalid attacker proof branch')
104    for branch in branches:
105        move=chess.Move.from_uci(branch['move'])
106        if move not in board.legal_moves:raise ValueError('illegal proof move')
107        board.push(move)
108        try:proof_check(h,board,branch['child'],color,depth+1)
109        finally:board.pop()
110
111def audit(h,folder,report,opening,color):
112    import chess,chess.pgn
113    with (folder/'game.pgn').open(encoding='utf-8') as stream:game=chess.pgn.read_game(stream)
114    if game is None or game.errors:raise ValueError('invalid played PGN')
115    moves=list(game.mainline_moves());n=opening['autoplay_plies']
116    if [m.uci() for m in moves[:n]]!=opening['uci'] or len(moves)!=report['plies']:raise ValueError('autoplay/ply count mismatch')
117    rows=report['moves'];by_ply={r['ply']:r for r in rows}
118    if len(by_ply)!=len(rows) or set(by_ply)!=set(range(n+1,len(moves)+1)):raise ValueError('book moves included in metrics or missing played moves')
119    board=chess.Board();queried=[];overrides=0;model_turn_seconds=0.;searches=[]
120    for ply,move in enumerate(moves,1):
121        if move not in board.legal_moves:raise ValueError('illegal played move')
122        row=by_ply.get(ply)
123        if row:
124            if row['uci']!=move.uci():raise ValueError('move report mismatch')
125            if board.turn==color and row.get('decision_source') not in ('model_policy','forced_mate_override'):raise ValueError('missing model attribution')
126            if board.turn!=color and ('model_query' in row or 'decision_source' in row or MODEL_METRICS.intersection(row)):raise ValueError('engine attributed to model')
127            if not math.isfinite(row['seconds']) or row['seconds']<0:raise ValueError('invalid move latency')
128            if board.turn==color:
129                model_turn_seconds+=row['seconds']
130                search=row.get('mate_search',{})
131                if search.get('max_plies')!=7 or search.get('node_budget')!=50000 or search.get('time_budget_seconds',1)>.25:raise ValueError('helper budget mismatch')
132                if search.get('status') not in ('proven','unknown','no_forced_mate'):raise ValueError('helper status missing')
133                if not math.isfinite(search.get('seconds',float('nan'))) or search['seconds']<0:raise ValueError('helper timing')
134                searches.append({k:search.get(k) for k in ('status','reason','seconds','completed_depth_plies','iteration_depths','workers','nodes','proof_verified')})
135            if row.get('decision_source')=='model_policy':
136                model_metrics(row,board)
137                queried.append(row)
138            if row.get('decision_source')=='forced_mate_override':
139                if board.turn!=color or row.get('model_query')!='not_queried' or MODEL_METRICS.intersection(row):raise ValueError('helper/model attribution mismatch')
140                search=row.get('mate_search',{});proof=search.get('proof',{});branches=proof.get('branches',[])
141                if search.get('status')!='proven' or search.get('move')!=move.uci():raise ValueError('helper move/status mismatch')
142                if not isinstance(branches,list) or len(branches)!=1 or branches[0].get('move')!=move.uci():raise ValueError('helper proof root differs from played move')
143                proof_check(h,board,proof,color);overrides+=1
144        board.push(move)
145    if board.fen()!=report['final_fen'] or game.headers['Result']!=report['result']:raise ValueError('final board/result mismatch')
146    outcome=board.outcome(claim_draw=True)
147    if report['result']!='*' and (outcome is None or outcome.result()!=report['result']):raise ValueError('fabricated scored result')
148    nodes=[];path=folder/'uci.log'
149    if path.exists():
150        for block in path.read_text().split('> go nodes 1000')[1:]:
151            observed=re.findall(r' nodes (\d+)',block);nodes.append(int(observed[-1]) if observed else None)
152    game.headers.update(OpeningID=opening['opening_id'],AutoplayPlies=str(n),SourceOpeningName=opening['name'])
153    node=game
154    for _ in range(n):node=node.variation(0);node.comment='Book autoplay; excluded from model metrics.'
155    return game,{'plies':len(moves),'autoplay_plies':n,'model_queries':len(queried),
156                 'raw_greedy_legal':sum(r['raw_greedy_legal'] for r in queried),'raw_legal_probability_sum':sum(r['legal_joint_probability'] for r in queried),
157                 'helper_overrides':overrides,'helper_searches':searches,'sunfish_reported_nodes':nodes,'result':report['result'],
158                 'model_turn_seconds':model_turn_seconds,'latency_protocol':'model turns include helper attempt and decode; excludes book autoplay and model loading',
159                 'termination':report['termination'],'error':report['error'],'cleanup_error':report['cleanup_error'],
160                 'seconds':report['seconds'],'pgn_and_proofs_verified':True}
161
162def summarize(rows,total=100):
163    scored=[r for r in rows if r['result']!='*'];wins=draws=losses=0
164    for row in scored:
165        if row['result']=='1/2-1/2':draws+=1
166        elif row['result']==('1-0' if row['model_color']=='white' else '0-1'):wins+=1
167        else:losses+=1
168    paired={}
169    for row in rows:paired.setdefault(row['pair_id'],[]).append(row)
170    scores=[]
171    for pair in paired.values():
172        if len(pair)==2 and all(r['result']!='*' for r in pair):
173            scores.append(sum(.5 if r['result']=='1/2-1/2' else float(r['result']==('1-0' if r['model_color']=='white' else '0-1')) for r in pair)/2)
174    import statistics
175    return {'scheduled_games':total,'audited_games':len(rows),'unattempted_or_unaudited':total-len(rows),
176            'wins':wins,'draws':draws,'losses':losses,'unfinished':len(rows)-len(scored),
177            'score_on_scored_games':(wins+.5*draws)/len(scored) if scored else None,
178            'fully_scored_pairs':len(scores),'pair_mean_score':statistics.mean(scores) if scores else None,
179            'pair_standard_error':statistics.stdev(scores)/math.sqrt(len(scores)) if len(scores)>1 else None,
180            'uncertainty_limit':'paired-opening standard error; small selected suite, not an Elo/generalization estimate',
181            'model_queries':sum(r['model_queries'] for r in rows),'helper_overrides':sum(r['helper_overrides'] for r in rows),
182            'autoplay_excluded_from_model_metrics':True}
183
184def play(suite,out,checkpoint,h,clock,model_factory=None):
185    """Dependency-injected for offline scheduler/audit/cleanup tests."""
186    p=suite['protocol'];openings={o['opening_id']:o for o in suite['openings']};rows=[];games=[]
187    factory=model_factory or h.ModelWorker
188    write(out/'summary.json',summarize(rows,len(suite['schedule'])))
189    for item in suite['schedule']:
190        if clock.soft_stop():break
191        opening=openings[item['opening_id']];folder=out/item['game_id'];model=None
192        try:
193            timeout=min(p['model_timeout_seconds'],clock.remaining()-5)
194            if timeout<=0:break
195            load_started=time.monotonic();model=factory('adapter:load',checkpoint,item['seed'],timeout)
196            load_seconds=time.monotonic()-load_started
197            remaining=clock.remaining()-5
198            if remaining<=0:break
199            game_budget=min(p['game_walltime_seconds'],remaining)
200            game_end=time.monotonic()+game_budget
201            def engine():
202                available=min(clock.remaining()-5,game_end-time.monotonic())
203                if available<=0:raise TimeoutError('no time for engine initialization')
204                # UCI constructor performs two handshakes before the first search.
205                timeout=min(p['engine_timeout_seconds'],available/2)
206                command=[sys.executable,str(Path(__file__).resolve()),'--engine-child',str(os.getpid()),*h.engine_command()]
207                return h.UCI(command,timeout)
208            report=h.game(model,engine,item['model_color']=='white',folder,
209                cap=p['ply_cap_including_autoplay'],nodes=p['sunfish_requested_nodes'],opening=opening['uci'],
210                walltime=game_budget,label=f'Frozen paired{len(suite["schedule"])}; no Elo claim',
211                mate_override=True,mate_nodes=p['helper_nodes'],mate_seconds=p['helper_seconds'])
212            game,row=audit(h,folder,report,opening,item['model_color']=='white')
213            row.update(item);row['model_load_seconds']=load_seconds;rows.append(row);games.append(str(game))
214            write(folder/'game.pgn',str(game)+'\n')
215            row['pgn_sha256']=sha(folder/'game.pgn');row['game_json_sha256']=sha(folder/'game.json')
216            write(folder/'audit.json',row)
217            write(out/'results.json',rows);write(out/'summary.json',summarize(rows,len(suite['schedule'])))
218            write(out/'games.pgn','\n\n'.join(games)+'\n')
219            if report['cleanup_error'] or report['error']:break  # No hidden retry/new budget.
220        finally:
221            if model is not None:model.close()
222    write(out/'summary.json',summarize(rows,len(suite['schedule'])))
223    return rows
224
225def compare(baseline,candidate,baseline_rows,candidate_rows,suite):
226    """Paired comparison only after checking identical evaluation conditions."""
227    import statistics
228    if baseline['request']['role']!='baseline' or candidate['request']['role']!='candidate':raise ValueError('comparison roles mismatch')
229    keys=('suite_sha256','execution_contract_sha256','runner_sha256','guardian_sha256','device','budget_seconds')
230    if any(baseline['request'][k]!=candidate['request'][k] for k in keys):raise ValueError('matched execution identity differs')
231    if any(baseline[k]!=candidate[k] for k in ('protocol','model_config','python','torch','transformers','python_chess')):raise ValueError('matched protocol/runtime differs')
232    if baseline['request']['suite_sha256']!=inputs()[1]['suite_sha256']:raise ValueError('comparison uses another suite')
233    if baseline['request']['checkpoint_sha256']!=suite['protocol']['baseline_checkpoint_sha256']:raise ValueError('wrong comparison baseline')
234    schedule={g['game_id']:g for g in suite['schedule']}
235    mapped=[]
236    for rows in (baseline_rows,candidate_rows):
237        table={r['game_id']:r for r in rows}
238        if len(table)!=len(rows) or set(table)!=set(schedule):raise ValueError('comparison requires all100 scheduled audits')
239        for key,row in table.items():
240            if any(row[k]!=schedule[key][k] for k in ('opening_id','model_color','seed','pair_id')) or row.get('pgn_and_proofs_verified') is not True:raise ValueError('comparison schedule/audit mismatch')
241        mapped.append(table)
242    complete=all(r['result']!='*' and not r['error'] and not r['cleanup_error'] for rows in mapped for r in rows.values())
243    result={'identical_protocol_verified':True,'all_games_scored_without_errors':complete,
244            'baseline':summarize(baseline_rows),'candidate':summarize(candidate_rows),'promotion_authorized':False}
245    if not complete:
246        return dict(result,comparison_status='incomplete; no improvement conclusion',evidence_for_improvement=False)
247    def score(row):return .5 if row['result']=='1/2-1/2' else float(row['result']==('1-0' if row['model_color']=='white' else '0-1'))
248    differences=[]
249    for opening in suite['openings']:
250        ids=[g['game_id'] for g in suite['schedule'] if g['opening_id']==opening['opening_id']]
251        differences.append(sum(score(mapped[1][key])-score(mapped[0][key]) for key in ids)/2)
252    mean=statistics.mean(differences);se=statistics.stdev(differences)/math.sqrt(len(differences))
253    interval=[mean-1.96*se,mean+1.96*se]
254    return dict(result,comparison_status='matched',candidate_minus_baseline_score=mean,
255                opening_pair_standard_error=se,approximate_95_percent_interval=interval,
256                evidence_for_improvement=interval[0]>0,
257                uncertainty_limit='normal approximation over50 opening pairs; selected suite, not an Elo estimate; independent review required')
258
259def compare_directories(baseline_path,candidate_path):
260    suite,contract=inputs();verify_sources(contract)
261    import harness as h
262    openings={o['opening_id']:o for o in suite['openings']};manifests=[];results=[]
263    for root in map(Path,(baseline_path,candidate_path)):
264        manifest=json.loads((root/'manifest.json').read_text());manifests.append(manifest)
265        expected={'execution_contract_sha256':sha(ROOT/'execution-contract.json'),'runner_sha256':sha(__file__),
266                  'guardian_sha256':sha(GUARDIAN_PATH),'suite_sha256':contract['suite_sha256']}
267        if any(manifest['request'][k]!=v for k,v in expected.items()) or manifest['protocol']!=suite['protocol']:raise ValueError('comparison source contract changed')
268        rows=json.loads((root/'results.json').read_text())
269        for row in rows:
270            folder=(root/row['game_id']).resolve()
271            if folder.parent!=root.resolve():raise ValueError('unsafe game artifact path')
272            if sha(folder/'game.pgn')!=row['pgn_sha256'] or sha(folder/'game.json')!=row['game_json_sha256']:raise ValueError('played artifacts changed')
273            report=json.loads((folder/'game.json').read_text())
274            _,checked=audit(h,folder,report,openings[row['opening_id']],row['model_color']=='white')
275            if any(row[key]!=checked[key] for key in ('result','termination','error','cleanup_error','plies','autoplay_plies','model_queries','helper_overrides','raw_greedy_legal','raw_legal_probability_sum')):
276                raise ValueError('stored result differs from replayed game audit')
277        results.append(rows)
278    return compare(*manifests,*results,suite)
279
280def worker(request_path):
281    # The private entry point must not bypass the external hard watchdog.
282    require_guardian()
283    request=json.loads(Path(request_path).read_text());out=Path(request_path).parent
284    guardian=load_guardian(request.get('guardian_sha256'))
285    value=guardian.read_deadline(out/'deadline.json')
286    expected_budget=7200
287    if (set(request)!=APPROVAL_KEYS or value['identity']!=request or request.get('approved') is not True
288            or request['budget_seconds']!=expected_budget or value['budget_seconds']!=expected_budget or value['checkpoint_margin_seconds']!=30):raise ValueError('worker request/deadline mismatch')
289    if str(uuid.UUID(request['run_id']))!=request['run_id']:raise ValueError('invalid worker run UUID')
290    if out.resolve()!=(ROOT/'runs'/request['run_id']).resolve() or str(out.resolve())!=request['run_directory']:raise ValueError('noncanonical worker run directory')
291    clock=guardian.Deadline(value)
292    if clock.soft_stop():raise TimeoutError('evaluation budget expired before setup')
293    suite,contract=inputs();verify_sources(contract)
294    if request['suite_sha256']!=contract['suite_sha256'] or request['runner_sha256']!=sha(__file__) or request['execution_contract_sha256']!=sha(ROOT/'execution-contract.json') or request['guardian_sha256']!=sha(GUARDIAN_PATH):
295        raise ValueError('worker approved source changed')
296    if request['device'] not in ('cuda:0','cuda:1') or request['role'] not in ('baseline','candidate'):raise ValueError('invalid worker role/device')
297    if request['role']=='baseline' and request['checkpoint_sha256']!=suite['protocol']['baseline_checkpoint_sha256']:raise ValueError('wrong worker baseline')
298    if sha(request['checkpoint'])!=request['checkpoint_sha256'] or sha(request['dataset_manifest'])!=request['dataset_manifest_sha256']:raise ValueError('checkpoint/dataset changed')
299    # Single attempt even when the private worker entry point is invoked twice.
300    with (out/'worker-started.json').open('x') as marker:
301        json.dump({'pid':os.getpid(),'started_unix':time.time(),'request_sha256':sha(request_path)},marker);marker.flush();os.fsync(marker.fileno())
302    import torch,transformers,chess
303    saved=torch.load(request['checkpoint'],map_location='cpu',weights_only=True)
304    cfg=saved['model_config']
305    from checkpoint_gate import permitted,validate_milestone
306    from adapter import validate_identity
307    stage,ref=permitted(contract);validate_identity(saved,stage);validate_milestone(saved,contract)
308    if ref!={'path':request['checkpoint'],'sha256':request['checkpoint_sha256']} or cfg['vocab_size']!=512:raise ValueError('wrong certified state checkpoint')
309    if saved['identity']['sealed_dataset_manifest_sha256']!=request['dataset_manifest_sha256']:raise ValueError('checkpoint dataset mismatch')
310    write(out/'manifest.json',{'request':request,'protocol':suite['protocol'],'model_config':cfg,
311        'checkpoint_identity':saved['identity'],'checkpoint_cursor':saved['exposures']['cursor'],'checkpoint_updates':saved['updates'],
312        'python':sys.version,'torch':str(torch.__version__),'transformers':transformers.__version__,
313        'python_chess':chess.__version__,'model_reload_each_game':True,'test_set_evaluated':False})
314    del saved
315    import harness as h
316    os.environ['CHESS_INFERENCE_DEVICE']=request['device']
317    from resource_guard import check, baseline
318    baseline(out)
319    check(force=True)
320    try:
321        # Same enforceable model-worker deadline as matches, before any game.
322        preflight=h.ModelWorker('adapter:load',Path(request['checkpoint']),20261029,min(60.,clock.remaining()-5))
323        try:
324            board=chess.Board();move,metrics=preflight.choose(board)
325            if move not in board.legal_moves:raise ValueError('preflight illegal move')
326            model_metrics(dict(metrics,model_query='queried'),board)
327            checks=[]
328            for _ in range(12):
329                time.sleep(.25);check(force=True)
330                move,metrics=preflight.choose(board)
331                if move not in board.legal_moves:raise ValueError('probe illegal move')
332                model_metrics(dict(metrics,model_query='queried'),board)
333                checks.append(check(force=True))
334            write(out/'joint-probe.json',{'checks':checks,'checkpoint_sha256':request['checkpoint_sha256'],'physical_gpu':1})
335            write(out/'preflight.json',{'legal_move':move.uci(),'metrics':metrics,'checkpoint_sha256':request['checkpoint_sha256'],'unix':time.time()})
336        finally:preflight.close()
337        rows=play(suite,out,Path(request['checkpoint']),h,clock)
338        write(out/'terminal.json',{'status':'all_scheduled_audited' if len(rows)==len(suite['schedule']) else 'partial','audited_games':len(rows),'test_set_evaluated':False})
339    except BaseException as error:
340        write(out/'failure.json',{'error':repr(error)});raise
341
342def launch(approval_path):
343    import fcntl
344    suite,contract=inputs();approval=json.loads(Path(approval_path).read_text());run_id=approval.get('run_id')
345    expected_budget=7200
346    if str(uuid.UUID(run_id))!=run_id:raise ValueError('canonical run UUID required')
347    if set(approval)!=APPROVAL_KEYS or approval['approved'] is not True or approval['budget_seconds']!=expected_budget:raise ValueError('exact reviewed match approval required')
348    if approval['suite_sha256']!=contract['suite_sha256'] or approval['execution_contract_sha256']!=sha(ROOT/'execution-contract.json') or approval['runner_sha256']!=sha(__file__):raise ValueError('approved source/suite mismatch')
349    guardian=load_guardian(approval['guardian_sha256'])
350    if approval['device'] not in ('cuda:0','cuda:1') or approval['role'] not in ('baseline','candidate'):raise ValueError('invalid reviewed device/role')
351    if approval['role']=='baseline' and approval['checkpoint_sha256']!=suite['protocol']['baseline_checkpoint_sha256']:raise ValueError('incorrect baseline checkpoint')
352    for key in ('checkpoint','dataset_manifest'):
353        if str(Path(approval[key]).resolve())!=approval[key] or not Path(approval[key]).is_file():raise ValueError('canonical existing input required')
354    out=(ROOT/'runs'/run_id).resolve();out.parent.mkdir(exist_ok=True)
355    if approval['run_directory']!=str(out):raise ValueError('alternate run directory forbidden')
356    # Fresh UUID directory only; no replay/resume/reset of an earlier match budget.
357    out.mkdir(exist_ok=False)
358    with (out/'owner.lock').open('x') as lock:
359        fcntl.flock(lock,fcntl.LOCK_EX|fcntl.LOCK_NB)
360        value=guardian.create_or_resume(out/'deadline.json',approval,budget=expected_budget,margin=30)
361        write(out/'request.json',approval)
362        env=dict(os.environ,CHESS_JOB_LOCK_FD=str(lock.fileno()),CHESS_MATCH_GUARDED='1')
363        command=[sys.executable,str(Path(__file__).resolve()),'--worker',str(out/'request.json')]
364        result=guardian.supervise(command,value,env);write(out/'supervision.json',result)
365        return result
366
367def main():
368    if sys.argv[1:2]==['--engine-child']:
369        return engine_child(int(sys.argv[2]),sys.argv[3:])
370    if sys.argv[1:2]==['--worker']:
371        path=Path(sys.argv[2]).resolve()
372        if path.name!='request.json' or path.parent.parent!=(ROOT/'runs').resolve():raise ValueError('private worker path outside run registry')
373        with (path.parent/'worker.log').open('a',buffering=1) as log:
374            os.dup2(log.fileno(),1);os.dup2(log.fileno(),2)
375            return worker(path)
376    parser=argparse.ArgumentParser();parser.add_argument('--approval');parser.add_argument('--authorize-matches',action='store_true')
377    parser.add_argument('--compare',nargs=2,metavar=('BASELINE','CANDIDATE'))
378    args=parser.parse_args()
379    if args.compare:raise ValueError('legacy comparison disabled; use per-game diagnostic reports')
380    if args.compare:
381        if args.authorize_matches or args.approval:parser.error('comparison is read-only and cannot launch')
382        print(json.dumps(compare_directories(*args.compare),indent=2));return
383    if not args.authorize_matches:
384        suite,contract=inputs();print(json.dumps({'status':'plan_only','games_per_checkpoint':len(suite['schedule']),'suite_sha256':contract['suite_sha256'],'runner_sha256':sha(__file__),'matches_run':0}));return
385    if not args.approval:parser.error('reviewed approval file required')
386    result=launch(args.approval)
387    if result['returncode'] or result['deadline_expired']:raise SystemExit(result['returncode'] or 124)
388if __name__=='__main__':main()
389