3.4 KiB
Retire initial population intent before purging
The first native guard-cancel test failed in logs_2026-09-19_07-27-00: at 07:27:50.658 it proved the empty automatic six-slot group had entered native initialization without dispatching a member, then stopped its pending owner twice. At 07:27:51.671 the group had received a later dispatch or member. The old purge-only implementation therefore did not establish cancellation for an incomplete group kept alive. The first log does not distinguish a later native expansion pass from an unobserved later request; the new fixture records owner cancellation calls, tagged EOnInit, RequestSpawn and ExpandOneMember calls while delegating every native method unchanged.
Installed SCR_AIGroup explains why a queued request is not the complete population contract:
EOnInitat line 2578 checksm_bSpawnImmediately, then requests the slot-array count.RequestSpawnat 2684 enqueues intoChimeraAIWorld; its documentation describes later expansion to full size.ExpandOneMemberat 2725 returns without spawning whenm_aUnitPrefabSlotsis null/empty, and otherwise computes capacity from its count.IsExpandCompleteat 2771 treats null/empty configured slots as complete; this is native production behavior, not a fixture override.SetSpawnImmediatelyat 2643 changes the per-instance automatic-initialization flag.DespawnMembersat 2872 returns before its queue purge when no physical members exist.
For successor-owned PENDING initial preparation only, cancellation now disables automatic spawning, assigns a new empty prefab-slot array to that group instance, then purges its native queue requests. It never clears a possibly shared array, changes installed resources, invents dead counts, calls a spawn function, or suppresses ExpandOneMember. Existing partial members remain physical and owned until normal Rollback deletes them. READY gameplay groups remain excluded by the existing Stop state gate, so losses during ordinary play cannot cause this startup path to refill or rewrite their profile.
The unchanged core cancellation assertions still require zero further dispatches and stable cancelled members while an uncancelled control physically reaches six. Additional assertions verify that cancellation runs once, cancelled instance arrays become empty, and the control retains its six-slot profile and automatic-spawn setting. The test still deletes all disposable groups and actual characters through owner rollback and observes late activity.
test_guard_cancellation_policy.py executes the actual cancellation and Stop bodies with two cancelled groups sharing an authored six-slot array with an uncancelled control. It proves replacement does not mutate that shared array, existing physical actor counts stay unchanged, unrequested groups are skipped, READY owners do not retire profiles, and repeated Stop is idempotent. This is source-policy evidence only. The fix and diagnostics still require native compilation and another engine run; the failed first run remains a failure.
Native cancellation now passes in 073601: 68 assertions, no engine/script errors. Empty and partial groups remain stable through a fifteen-second observation while the uncancelled control fills. Owned rollback deletes all captured actors/groups, and the original mission groups remain unchanged.