"""Execute production refresh/adoption methods against adversarial radio/solver outcomes. The real scheduler, refresh, cancellation and projectile-bookkeeping bodies run. Native route/ballistic/crew-readiness operations, battery Update and initial-order progression are boundary adapters; this is not native delivery, death or firing. """ import re from policy_harness import ROOT, body, run r=ROOT/'addons/core/Scripts/Game/ERR/10_AI' def cpp(path, signature): code=body(r/path,signature).replace('protected ','') for typ in ['ERR_MortarBattery','ERR_MortarSystem','ERR_HQReport','ERR_HQRoute','ERR_MortarRefresh','ERR_MortarAimSolution']: code=re.sub(r'\b'+typ+r' (\w+)',typ+r'* \1',code) for name in ['battery','report','current','incoming','update','route','commanded','updated','system','m_HQ','newest','selected','target','m_Transfer','Activity']: code=code.replace(name+'.',name+'->') # Members are owning/weak script references, both represented as pointers. for name in ['Route','Report','Refresh','AimSolver']: code=code.replace('.'+name+'.','.'+name+'->').replace('->'+name+'.','->'+name+'->') code=code.replace('Route.Advance','Route->Advance') for name in ['ERR_MortarPrediction','ERR_MortarRefreshRules','ERR_MortarAimRules','ERR_MortarBattery']: code=code.replace(name+'.',name+'::') code=code.replace('null','nullptr').replace('IEntity gun;','IEntity gun=nullptr;').replace('ResourceName ammo;','std::string ammo;') code=code.replace('string reason','std::string reason') # Only journal formatting is inert; authorization/solver mutations are real bodies. code=re.sub(r'^.*Audit\([^\n]*$', ';', code, flags=re.M) code=code.replace('vector.Distance','vector::Distance').replace('Math.AbsFloat','std::fabs') code=code.replace('array reports = {};','Items reports;') code=re.sub(r'foreach \((ERR_MortarBattery|ERR_HQReport)\* (\w+) : (\w+)\)',r'for (\1* \2 : \3.values)',code) code=re.sub(r'(ERR_MortarBattery|ERR_HQReport)\* (newest|selected|target);',r'\1* \2=nullptr;',code) code=code.replace('Replication.IsServer()', 'Replication::IsServer()').replace('float.MAX','1e30f') return code constructor=cpp('ERR_MortarRefresh.c','void ERR_MortarRefresh(').replace('void ERR_MortarRefresh(', 'ERR_MortarRefresh(') newer=cpp('ERR_MortarRefresh.c','static bool Newer(') owns=cpp('ERR_MortarRefresh.c','bool Owns(') delivered=cpp('ERR_MortarRefresh.c','bool DeliveredFor(') fresh=cpp('ERR_MortarPrediction.c','static bool Fresh(') equivalent=cpp('ERR_MortarAimSolution.c','static bool Equivalent(') matches=cpp('ERR_MortarAimSolution.c','bool Matches(') can=cpp('ERR_MortarBattery.c','bool CanRefresh(') begin=cpp('ERR_MortarBattery.c','bool BeginRefresh(') reject=cpp('ERR_MortarBattery.c','void RejectRefresh(') advance=cpp('ERR_MortarSystem.c','protected void AdvanceRefresh(') adopt=cpp('ERR_MortarFiring.c','bool ERR_AdoptReport(') cancel=cpp('ERR_MortarBattery.c','void Cancel(') projectile=cpp('ERR_MortarBattery.c','void ObserveProjectile(') queue_method=cpp('ERR_MortarSystem.c','protected void QueueRefreshes(') tick=cpp('ERR_MortarSystem.c','void Tick(') # Supply owners before methods that dereference them, without replacing method logic. can=can.replace('bool CanRefresh(', 'bool ERR_MortarBattery::CanRefresh(') begin=begin.replace('bool BeginRefresh(', 'bool ERR_MortarBattery::BeginRefresh(') reject=reject.replace('void RejectRefresh(', 'void ERR_MortarBattery::RejectRefresh(') advance=advance.replace('void AdvanceRefresh(', 'void ERR_MortarSystem::AdvanceRefresh(') adopt=adopt.replace('bool ERR_AdoptReport(', 'bool Node::ERR_AdoptReport(') cancel=cancel.replace('void Cancel(', 'void ERR_MortarBattery::Cancel(').replace('std::string reason = "cancel requested"','std::string reason') projectile=projectile.replace('void ObserveProjectile(', 'void ERR_MortarBattery::ObserveProjectile(') queue_method=queue_method.replace('void QueueRefreshes(', 'void ERR_MortarSystem::QueueRefreshes(') tick=tick.replace('void Tick(', 'void ERR_MortarSystem::Tick(') run(r''' #include #include #include #include #include struct vector {float x=0,y=0,z=0;std::string ToString(){return "point";}static float Distance(vector a,vector b){return std::sqrt((a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y)+(a.z-b.z)*(a.z-b.z));}static float DistanceXZ(vector a,vector b){a.y=0;b.y=0;return Distance(a,b);}}; using IEntity=void*; templatestruct Items {std::vector values;void Insert(T t){values.push_back(t);}}; struct Replication {static inline bool server=true;static bool IsServer(){return server;}}; struct ERR_HQReport {IEntity Target=this;int MessageId=1;float ObservedAt=0;bool Distress=false;vector Position{};std::string TravelMode="foot";std::string Description(float){return "contact";}ERR_HQReport* Snapshot(){return new ERR_HQReport(*this);}}; struct ERR_MortarPrediction {static constexpr float MAX_REPORT_AGE_MS=60000;static bool Predict(ERR_HQReport*,float,float,vector&){return true;} '''+fresh+r'''}; struct ERR_MortarRefreshRules { '''+newer+r'''}; struct ERR_MortarAimRules { '''+equivalent+r'''}; struct ERR_MortarBattery;struct ERR_MortarSystem;struct ERR_MortarRefresh;struct ERR_MortarAimSolution;struct Node; struct ERR_HQRoute {int MessageId=9,state=0,calls=0;int Advance(float,int){calls++;return state;}}; struct HQ {Items contacts;ERR_HQRoute* nextRoute=nullptr;int downlinks=0;int Journal(){return 0;}void SupportContacts(Items& out,float){out=contacts;}ERR_HQRoute* Downlink(IEntity,const char*,std::string,int){downlinks++;return nextRoute;}}; struct Ledger {std::set claimed;bool Available(int id,float,float){return !claimed.count(id);}bool Claim(int id,float,float){return claimed.insert(id).second;}}; struct FakeActivity {int completions=0;void Complete(){completions++;}}; struct Transfer {int invalidated=0;void Invalidate(){invalidated++;}}; struct ERR_MortarBattery { static inline std::string SHELL="HE"; IEntity Gun=this,Group=this;int OrderId=1,OrderShots=0,TotalShots=0,RadioId=0;float OrderedAt=500,AimedAt=1000,AimValidatedAt=1000,NextOrder=0;vector Position{}; bool m_Stopped=false,CommandOpen=true,RefreshRejected=false,Rejected=false,Released=false,operational=true,StartupActivated=true; FakeActivity originalActivity;FakeActivity* Activity=&originalActivity;Transfer transfer;Transfer* m_Transfer=&transfer; ERR_HQRoute* RadioOrder=nullptr;ERR_HQReport* PendingRadioReport=nullptr;ERR_HQReport* PendingSupplyReport=nullptr; std::string LastFailure;ERR_HQReport* Report=nullptr;ERR_MortarRefresh* Refresh=nullptr;ERR_MortarAimSolution* AimSolution=nullptr;Node* AimSolver=nullptr;Ledger m_ReportLedger; bool Operational(){return operational;} bool CanRefresh(ERR_HQReport*,float);bool BeginRefresh(ERR_HQReport*,ERR_HQRoute*,float);void RejectRefresh(std::string); void Cancel(std::string reason="cancel requested");void ObserveProjectile(IEntity,IEntity,bool);void FlushTraces(){}void DetachActivity(){} void Trace(std::string,std::string,std::string){} void Update(float){}bool SupplyPending(){return false;}int CountShells(){return 27;} bool CanRequest(ERR_HQReport*,float){return false;}bool BeginRequest(ERR_HQReport*,float){assert(false);return false;} }; struct ERR_MortarRefresh { IEntity Gun=nullptr,Group=nullptr;int OrderId=0,RadioId=0;ERR_HQReport* Report=nullptr;ERR_HQRoute* Route=nullptr; '''+constructor+owns+delivered+r'''}; struct ERR_MortarAimSolution { IEntity Gun=nullptr;ERR_HQReport* Report=nullptr;int OrderId=1,Shot=0,Charge=0;vector GunOrigin{},Impact{500,0,0},AimTarget{500,500,0};float FlightTime=30; '''+matches+r'''}; struct ERR_MortarSystem { HQ hq;HQ* m_HQ=&hq;int failures=0;std::string SafetyReason;bool Safe(ERR_MortarBattery*,vector,float){return true;} Items m_Batteries;bool m_Stopped=false;float m_NextDecision=1e9f,m_NextRefreshDecision=0; bool Withhold(ERR_MortarBattery* b,const char* why){b->Rejected=true;b->LastFailure=why;failures++;return false;} void AdvanceRefresh(ERR_MortarBattery*,float); void SpottingTick(float){}void QueueRefreshes(float);void Tick(float);void AdvanceOrder(ERR_MortarBattery*,float){}bool OutsideSettlements(vector){return true;} }; struct Node { static constexpr int PORT_ARTILLERY_ENTITY=1,PORT_AMMO_PREFAB=2; IEntity portGun=nullptr;std::string portAmmo=ERR_MortarBattery::SHELL;ERR_MortarAimSolution* calculated=nullptr;int solves=0; void GetVariableIn(int,IEntity& out){out=portGun;}void GetVariableIn(int,std::string& out){out=portAmmo;} ERR_MortarAimSolution* ERR_Solve(ERR_MortarBattery*,ERR_MortarSystem*,ERR_HQReport*,float){solves++;return calculated;} bool ERR_AdoptReport(ERR_MortarBattery*,ERR_MortarSystem*,ERR_HQReport*,float); }; '''+can+begin+reject+adopt+advance+cancel+projectile+queue_method+tick+r''' struct F { ERR_MortarBattery b;ERR_HQReport old,next;ERR_HQRoute route;ERR_MortarSystem system;ERR_MortarAimSolution original,solved;Node node; F(){next=old;next.MessageId=2;next.ObservedAt=20000;b.Report=&old;original.Gun=b.Gun;original.Report=&old;solved=original;node.portGun=b.Gun;node.calculated=&solved;b.AimSolver=&node;system.m_Batteries.Insert(&b);} bool queue(){return b.BeginRefresh(&next,&route,25000);} void aim(){b.AimSolution=&original;} void delivery(float now=26000){route.state=1;system.AdvanceRefresh(&b,now);} }; int main(){ F good;assert(good.queue());assert(!good.queue());assert(good.b.m_ReportLedger.claimed.count(2)); good.system.AdvanceRefresh(&good.b,25000);assert(good.b.Report==&good.old&&good.route.calls==1); // no instant HQ knowledge good.delivery();assert(!good.b.Refresh&&!good.b.RefreshRejected&&good.b.Report->MessageId==2); assert(good.b.Report->ObservedAt==20000&&good.b.OrderId==1&&good.b.OrderShots==0&&good.b.OrderedAt==500&&good.b.Activity); assert(!good.queue());good.b.Report=&good.old;assert(!good.queue()); // claimed refresh cannot become replay after original restored for(int fault=0;fault<10;fault++){ F f; if(fault==0)f.next.Target=&f; if(fault==1)f.next.ObservedAt=0; if(fault==2)f.next.ObservedAt=-1; if(fault==3)f.next.ObservedAt=25001; if(fault==4)f.next.MessageId=1; if(fault==5)f.next.MessageId=0; if(fault==6)f.next.Distress=true; if(fault==7)f.next.TravelMode="aircraft"; if(fault==8)f.b.CommandOpen=false; if(fault==9)f.b.operational=false; assert(!f.queue()&&f.b.m_ReportLedger.claimed.empty()); } F absent;assert(!absent.b.BeginRefresh(&absent.next,nullptr,25000)&&absent.b.m_ReportLedger.claimed.empty()); F expired;assert(expired.queue());expired.delivery(80001);assert(expired.b.RefreshRejected&&expired.b.Report==&expired.old); F failed;assert(failed.queue());failed.route.state=-1;failed.system.AdvanceRefresh(&failed.b,26000);assert(failed.b.RefreshRejected&&!failed.b.Refresh&&failed.b.Report==&failed.old); F changed;assert(changed.queue());changed.b.Gun=&changed.old;changed.delivery();assert(changed.b.RefreshRejected); F group;assert(group.queue());group.b.Group=&group.old;group.delivery();assert(group.b.RefreshRejected); F stale;assert(stale.queue());stale.b.OrderId++;stale.delivery();assert(!stale.b.Refresh&&!stale.b.RefreshRejected&&stale.b.Report==&stale.old&&stale.route.calls==0); F closed;assert(closed.queue());closed.b.CommandOpen=false;closed.delivery();assert(!closed.b.Refresh&&!closed.b.RefreshRejected&&closed.route.calls==0); F committed;assert(committed.queue());committed.b.Released=true;committed.delivery(); assert(committed.b.Refresh&&!committed.b.Refresh->Route&&committed.b.Report==&committed.old&&committed.b.Released); committed.b.Released=false;committed.b.OrderShots=1;committed.system.AdvanceRefresh(&committed.b,27000); assert(!committed.b.Refresh&&committed.b.Report->MessageId==2&&committed.b.OrderShots==1&&committed.b.OrderId==1); F failInFlight;assert(failInFlight.queue());failInFlight.b.Released=true;failInFlight.route.state=-1;failInFlight.system.AdvanceRefresh(&failInFlight.b,26000); assert(failInFlight.b.RefreshRejected&&failInFlight.b.Released&&failInFlight.b.CommandOpen&&failInFlight.b.Report==&failInFlight.old); // callback ownership retained; future load gate closes F validAim;validAim.aim();assert(validAim.queue());validAim.delivery(); assert(validAim.node.solves==1&&!validAim.b.RefreshRejected&&validAim.b.Report->MessageId==2&&validAim.original.Report==validAim.b.Report); assert(validAim.b.AimedAt==1000&&validAim.b.AimValidatedAt==26000&&validAim.b.AimSolution==&validAim.original&&validAim.original.Impact.x==500); for(int fault=0;fault<10;fault++){ F f;f.aim();assert(f.queue()); if(fault==0)f.solved.Impact.x+=.101f; if(fault==1)f.solved.Charge++; if(fault==2)f.solved.AimTarget.y+=.101f; if(fault==3)f.solved.GunOrigin.y+=.051f; if(fault==4)f.solved.FlightTime+=.051f; if(fault==5)f.node.portGun=&f.old; if(fault==6)f.node.portAmmo="other"; if(fault==7)f.b.AimSolver=nullptr; if(fault==8)f.node.calculated=nullptr; if(fault==9)f.b.AimedAt=27000; f.delivery();assert(f.b.RefreshRejected&&f.b.Report==&f.old&&f.original.Report==&f.old&&f.b.AimValidatedAt==1000); } F notDelivered;notDelivered.aim();assert(notDelivered.queue());assert(!notDelivered.node.ERR_AdoptReport(¬Delivered.b,¬Delivered.system,notDelivered.b.Refresh->Report,26000));assert(notDelivered.node.solves==0); F creep;creep.aim();creep.solved.Impact.x+=.06f;assert(creep.queue());creep.delivery();assert(!creep.b.RefreshRejected); creep.next.MessageId=3;creep.next.ObservedAt=22000;creep.solved.Impact.x+=.06f;assert(creep.queue());creep.delivery(27000); assert(creep.b.RefreshRejected&&creep.original.Impact.x==500&&creep.b.Report->MessageId==2&&creep.b.AimedAt==1000); // Execute the actual HQ tick, refresh scheduler, cancellation and projectile // bookkeeping together. Native route/crew/ballistic operations remain stubs. F repeated;repeated.system.hq.contacts.Insert(&repeated.next);repeated.system.hq.nextRoute=&repeated.route; repeated.system.Tick(25000);assert(repeated.system.hq.downlinks==1&&repeated.b.Refresh&&repeated.route.calls==0); repeated.system.Tick(25001);repeated.system.Tick(30000);assert(repeated.system.hq.downlinks==1&&repeated.route.calls==2); repeated.route.state=1;repeated.system.Tick(30001);assert(!repeated.b.Refresh&&repeated.b.Report->MessageId==2); repeated.system.Tick(35000);repeated.system.hq.contacts.Insert(&repeated.old);repeated.system.Tick(40000); assert(repeated.system.hq.downlinks==1&&repeated.b.OrderId==1&&repeated.b.Activity==&repeated.b.originalActivity); assert(repeated.b.m_ReportLedger.claimed.size()==1&&repeated.b.Report->ObservedAt==20000); F snapshot;assert(snapshot.queue());snapshot.next.MessageId=99;snapshot.next.ObservedAt=24999; snapshot.delivery();assert(snapshot.b.Report->MessageId==2&&snapshot.b.Report->ObservedAt==20000); // in-flight packet is immutable F newest;ERR_HQReport later=newest.next;later.MessageId=3;later.ObservedAt=22000; newest.system.hq.contacts.Insert(&newest.next);newest.system.hq.contacts.Insert(&later);newest.system.hq.nextRoute=&newest.route; newest.system.Tick(25000);assert(newest.b.Refresh->Report->MessageId==3&&newest.b.m_ReportLedger.claimed.count(3)&&!newest.b.m_ReportLedger.claimed.count(2)); F interrupted;assert(interrupted.queue());interrupted.b.Released=true; interrupted.system.Tick(25000);interrupted.route.state=-1;interrupted.system.Tick(25001); assert(interrupted.b.RefreshRejected&&interrupted.b.Released&&interrupted.b.CommandOpen&&interrupted.b.Report==&interrupted.old); interrupted.system.Tick(25002);assert(interrupted.b.RefreshRejected&&interrupted.b.Released&&interrupted.route.calls==2); interrupted.b.ObserveProjectile(&interrupted.next,nullptr,false); // actual physical-event bookkeeping, not native launch proof assert(!interrupted.b.Released&&interrupted.b.OrderShots==1&&interrupted.b.TotalShots==1&&interrupted.b.Report==&interrupted.old); interrupted.system.Tick(25003);assert(!interrupted.b.CommandOpen&&!interrupted.b.Activity&&!interrupted.b.Report&&!interrupted.b.RefreshRejected); assert(interrupted.b.originalActivity.completions==1&&interrupted.b.transfer.invalidated==1&&interrupted.b.NextOrder==85003); assert(interrupted.b.OrderShots==1&&interrupted.b.TotalShots==1&&interrupted.b.m_ReportLedger.claimed.count(2)); F noRoute;noRoute.system.hq.contacts.Insert(&noRoute.next);noRoute.b.Released=true; noRoute.system.Tick(25000);assert(noRoute.system.hq.downlinks==1&&noRoute.b.RefreshRejected&&noRoute.b.Released); noRoute.system.Tick(30000);assert(noRoute.system.hq.downlinks==1&&noRoute.b.CommandOpen); // latch cannot reset while committed F deliveredThenRadioDies;assert(deliveredThenRadioDies.queue());deliveredThenRadioDies.b.Released=true;deliveredThenRadioDies.route.state=1; deliveredThenRadioDies.system.Tick(26000);assert(deliveredThenRadioDies.b.Refresh&&!deliveredThenRadioDies.b.Refresh->Route&&deliveredThenRadioDies.route.calls==1); deliveredThenRadioDies.route.state=-1; // loss AFTER complete delivery cannot erase the packet already received deliveredThenRadioDies.b.ObserveProjectile(&deliveredThenRadioDies.next,nullptr,false); deliveredThenRadioDies.system.Tick(27000);assert(!deliveredThenRadioDies.b.RefreshRejected&&deliveredThenRadioDies.b.Report->MessageId==2&&deliveredThenRadioDies.route.calls==1); assert(deliveredThenRadioDies.b.AimedAt==-1&&deliveredThenRadioDies.b.AimValidatedAt==-1&&deliveredThenRadioDies.b.OrderShots==1); F expiresInFlight;assert(expiresInFlight.queue());expiresInFlight.b.Released=true;expiresInFlight.route.state=1; expiresInFlight.system.Tick(26000);expiresInFlight.system.Tick(80001); assert(expiresInFlight.b.RefreshRejected&&expiresInFlight.b.Released&&expiresInFlight.b.Report==&expiresInFlight.old); expiresInFlight.b.ObserveProjectile(&expiresInFlight.next,nullptr,false);expiresInFlight.system.Tick(80002); assert(!expiresInFlight.b.CommandOpen&&expiresInFlight.b.TotalShots==1&&expiresInFlight.b.OrderShots==1); F crewLost;assert(crewLost.queue());crewLost.b.operational=false;crewLost.delivery(); assert(crewLost.b.RefreshRejected&&crewLost.route.calls==0&&crewLost.b.Report==&crewLost.old); // readiness loss refuses before delivery F cancelled;assert(cancelled.queue());ERR_MortarRefresh* cancelledPacket=cancelled.b.Refresh; cancelled.b.Cancel("explicit cancellation");cancelled.route.state=1;cancelled.system.Tick(26000); assert(!cancelled.b.Refresh&&!cancelled.b.Report&&cancelled.route.calls==0&&cancelled.b.m_ReportLedger.claimed.count(2)); cancelled.b.OrderId=2;cancelled.b.CommandOpen=true;cancelled.b.Activity=&cancelled.b.originalActivity;cancelled.b.Report=&cancelled.next; cancelled.b.Refresh=cancelledPacket;cancelled.system.AdvanceRefresh(&cancelled.b,27000); // delayed old-order transaction cannot hit replacement assert(!cancelled.b.Refresh&&!cancelled.b.RefreshRejected&&cancelled.b.CommandOpen&&cancelled.b.OrderId==2&&cancelled.b.Report==&cancelled.next&&cancelled.route.calls==0); F stopped;assert(stopped.queue());stopped.system.m_Stopped=true;stopped.system.Tick(26000);assert(stopped.route.calls==0&&stopped.b.Refresh); stopped.system.m_Stopped=false;Replication::server=false;stopped.system.Tick(26000);assert(stopped.route.calls==0);Replication::server=true; } ''') # Boundaries not modeled as native C++ operations: real HQ route construction, # projectile latch, immutable report timestamps, existing cadence and cleanup. system=(r/'ERR_MortarSystem.c').read_text(); battery=(r/'ERR_MortarBattery.c').read_text() queue=body(r/'ERR_MortarSystem.c','protected void QueueRefreshes(') assert 'm_HQ.SupportContacts(reports, now)' in queue and 'm_HQ.Downlink(' in queue assert 'new SCR_AIStaticArtilleryActivity' not in queue+begin+advance+adopt assert 'ObservedAt =' not in queue+begin+advance+adopt assert 'OrderId++' not in queue+begin+advance+adopt assert 'OrderedAt =' not in queue+begin+advance+adopt assert 'battery.RefreshRejected' in body(r/'ERR_MortarSystem.c','bool AllowShot(') assert '(battery.Rejected || battery.RefreshRejected) && !battery.Released' in system assert 'Refresh = null;' in body(r/'ERR_MortarBattery.c','void Cancel(') assert 'AimValidatedAt = -1;' in body(r/'ERR_MortarBattery.c','void ObserveProjectile(') assert 'battery.AimedAt = now;' not in body(r/'ERR_MortarFiring.c','bool ERR_AdoptReport(') assert 'battery.AimSolution = updated' not in adopt print('PASS: actual refresh scheduler/delivery/cancellation/projectile methods reject interrupted or replayed reports, retain committed ownership, preserve immutable snapshots/aim geometry and isolate stopped or replaced orders; native radio/crew behavior remains separate')