54ad9e8f79
Records the operator-assisted live A/B on the REAL imported club (1949/1962, 13 Legends deferred): real club render, clean pagination, Special filter (1665, 0 base leaked), squad edit persistence + cold relaunch, and rollback->Python->Rust re-enable. Documents the three real-data fidelity fixes (versioned resourceIde187cd4, rareflag626c972, rare=SP filter6f16a23) and the nation/league/team model correction (44fcf24). Marks PRODUCTION NOT READY pending .105 Legends name data for the 13 deferred assets. Aggregate counts only; no private identity.
16 KiB
16 KiB
OpenFUT — Project State
Canonical source:
../OpenFUT-Vault/06 Agent Memory/Project State.mdThis file is a mirror. If the two disagree, the vault wins. Update the vault first.
Factual snapshot. Prefer this over the stale root README.md/CLAUDE.md status tables (FIFA 23).
Last compiled from repository evidence during context initialization.
Working
- FIFA 17 offline FUT stack, end-to-end. Proven 2026-08-01: auth → Blaze login → device-trust →
the FUT hub. Brought up by
fifa17-recon/tools/openfut-fut.sh start. Evidence:FUT-RUNBOOK.md,fifa17-recon/README.md, the five responder scripts, gate-ladder troubleshooting table. - ProtoSSL cert-pin defeat — two live
/proc/PID/mempatches (autopatch.py), VAs stable across launches. gdb-verified which gate was the wall. - LSX / Origin layer — crypto handshake reversed byte-exact and confirmed against the repack's
own emu disassembly (
docs/REPACK_INTEL.md); Origin login gates cleared. - Blaze redirector + Fire2/Heat2 — both hops defeated; preAuth/login/personas answered.
- UTAS/RS4 FUT API —
ut/auth+ boot calls + device-trust reach the hub with hand-authored JSON. - Persistent FIFA 17 account selection — the launcher synchronizes one configured EA persona to
the Python backend before starting LSX/FIFA. LSX, Blaze, POW/EASFC, and UTAS then share that
identity, while FUT coins, inventory, squads, progression, and unopened packs persist in an
isolated save beneath
fifa17-recon/docker/state/accounts/<persona-id>/. The POW level/XP/funds shown in FIFA's general account bar are account-scoped but remain distinct from FUT club coins. A reversible server test on 2026-08-09 verified profile switching, POW values, a 400-coin pack debit, five awarded items, and restoration of the original profile. - Account-scoped FUT security compatibility — launcher account synchronization initializes a
persisted
securityQuestionverification record in that persona's FIFA 17 profile. The UTAS PHISHING handler returns the complete CardsDLL trusted-console response (changed,exists,locked,trusted), accepts only well-formed legacy setup/validate requests underX-UT-SID, and never stores or logs the client-transformed answer. This is server-side emulation; the hook and launcher do not contain an answer or add UI automation. Automated contract coverage is infifa17-recon/docker/ctx/tools/test_security_question.py; live first/repeat-launch acceptance is partially complete: the first launch entered FUT without a security dialog on 2026-08-09; a second fresh-process FUT entry is still required to close persistence acceptance. - Safe responder diagnostics — ordinary LSX logs redact challenge/session/auth-code attributes;
ordinary Blaze logs redact auth/session keys and no longer emit raw Fire2 hex, decoded TDF, or
config values. Forensic Blaze capture remains available only with the explicit
OPENFUT_BLAZE_DUMP_FRAMES=1opt-in. LSX and Blaze self-tests cover the new defaults. - OpenFUT Core — Rust FUT economy backend, feature-complete for its scope and tested: profiles,
clubs, coins, packs, cards, squads, chemistry styles, SBCs, objectives, matches, market (NPC),
draft, FUT Champs, seasons, statistics, achievements, events, daily check-in, division
leaderboard, market trade history. 13 migrations. Integration suite (
tests/integration_test.rs, 96 test fns) runs against in-memory SQLite; CI (fmt/clippy/build/test) green onopenfut-core.
Partially implemented
- FIFA 17 FUT hub depth — reaching the hub is proven, but how much of FUT is fully navigable beyond it (playing matches, pack opening, SBC submission through the game UI vs. spinner/error states) is not documented as complete. The runbook's gate ladder lists failure modes still guarded against. Treat "past the hub" as unverified.
- Pack opening through the game UI — proven live on 2026-08-09 with the recovered CAGE test
profile: purchase, reveal, item assignment/quick-sell, wallet refresh, and return from the reveal
all completed. The Python transaction path also passes its 446-check contract suite. FIFA's
hardcoded post-reveal
mypacksreturn is supported by a short-lived active grace record for every opened pack; it is excluded from unopened-pack counts and retired at the next hub request. - FIFA 17 FUT match lifecycle — CardsDLL static analysis and isolated responder tests now cover
CREATE→READY→PLAY→END. Bare
/matchrequests carrying bodymatchIdare classified as PLAY instead of accidentally allocating another match; READY returns the verified scalarmatchIdandopponentPersonaIdfields; END persists W/D/L, matches played, and coin rewards per account. The implementation is deployed andtest_match_lifecycle.pypasses, but no football match has started or completed in FIFA yet. The READY opponentitemscontract and client mode-entry gate remain unresolved;FUT_MODEStherefore stays off by default. - Core ↔ emulation integration — the two halves exist and wiring has started. First
slice (2026-08-11): the My Squad owned-player search.
openfut-coregained a semantic, game-independent owned-inventory query (services::inventory::{OwnedItemQuery, apply_query}- a
Qualitytier) that filters (AND) → orders deterministically → paginates, wired intoGET /collection;openfut-adapter-fifa17::fut::owned_queryparses the FIFA17/clubwire query and resolves numeric league/nation/team ids → semantic names (unknown id = hard error, no raw-id passthrough). Intentional fix, not parity: Python applies onlyleague+teamand ignoreslevel/rare/position/nation/start/count(the request-amplification bug); Core applies all proven filters and paginates.rare=SPsemantics UNKNOWN, unimplemented. Slice 2 (2026-08-11):openfut-utas-host— the first live UTAS host. ServesGET …/clubfrom Core through the adapter and reverse-proxies every other UTAS route verbatim to the Python oracle (utas_server.py); plaintext HTTP/1.1 keep-alive, classify-before-execute, no python-fallback after a Core error.CoreAccessis a host-owned boundary (the adapter stays transport-agnostic). 11 host + 22 adapter tests; 10/10 mutations killed; fmt/clippy clean. Slice 3 (2026-08-11,3ef3bc3): the realFifa17IdentityResolver— catalog (card id → real asset id) + persistentopenfut-identitystore (owned instance → stable/reversible wire int) + wire-id policy, replacing all placeholders (one production path). Wire-id namespace is globally monotonic within(fifa17, owned-item), not per-account (Core owned ids are UUIDs → unambiguous reverse). Slice 4 (2026-08-11, core36abd4b): a curated 32-card real FIFA17 dev content pack (data/games/fifa17/dev/cards.json, idsfifa17_<asset>), loaded only via opt-inConfig.dev_content_games;seed-devgrants agame_id=fifa17profile+club realOwnedCards (no FIFA wire ids — the resolver mints those at request time), idempotent, default content untouched. Slice 5 (2026-08-11,5276dd2): the host sendsX-OpenFUT-Game: fifa17so/clubresolves the all-mapped fifa17 profile — composition proven live over HTTP (real Core+host, no FIFA client): FIFA wire query → realresourceIds (catalog) + stable/reversible wireids (store); 33 renderable, gold=22, Premier League=18, pagination page1=11/page2=7/overlap=0 (clean paging, no drops). The only remaining gate is the live retail FIFA A/B (no FIFA client in the build env; runbookopenfut-utas-host/README.md). See the vault UTAS Endpoint Map + Known Issues (incl. "identity resolution is NOT authorization" for later mutations). Slice 6 (2026-08-11):/clubRUNTIME VALIDATED on retail FIFA 17 — operator-assisted live A/B (.105client →.120backend via a source-scoped NAT redirect into a staged36abd4bCore +openfut-utas-host). Every checkpoint passed on the real client: transport, per-route Python fallback, Python-negative/club, CoreX-OpenFUT-Gamescoping, real card + persistent owned-item identity (incl. the two-copy fixture), no-filter/Gold/position/nation/league/team/combined-AND filtering, retail pagination with no amplification, card selection, identity stability across relaunch, Python rollback, and Rust re-enable (identity store byte-identical across the cycle, 0 reallocation). Live findings: the retail client stepsstart += 10withcount=11(sometimes bulkcount=100) — Core honoursoffsetand terminates; the My Club UI nests team under league; the "~1900" club counter is PythonuserMassInfo, not/club. Remaining is operational only (promote the staged stack to a durable deployment).
- a
- Slice 7 (2026-08-12): FUT squad authority (read + write) RUNTIME VALIDATED on retail FIFA 17.
Staged operator-assisted A/B (
.105retail client →.120, source-scoped utas switch:8099→:8199intoopenfut-utas-hostover a staged615c5fdCore seeded byseed-devwith the dev 33-card inventory). FIFA itself consumed the Rust squad path end-to-end: FUT boot servedRUST_OVERLAY userMassInfo(squad overlay) and the squad screen rendered the dev XI; a controlled in-game squad edit issuedPUT …/squad/0→ hostsquad-replace→ Core →{"id":0}; an in-game formation change f442→f433 persisted to Core (canonical fingerprint changed,position_indexremapped 0–10); a FULL FIFA relaunch cold-fetched and rendered the persisted f433 squad (no client cache). Reversibility proven on the exact client path by log presence, not response data (both backends coincidentally hold the same dev squad — the Python oraclefifa17_profile.jsonwas seeded from the samesquad_put_f442.jsoncapture): disarmed.105:8099reached Python (absent from host log), re-armed reached Rust (route=club limit=Some(9)present); the persistent identity store survived the cycle with 0 reallocation. Non-migrated routes (/ut/auth,account/sync,accountinfo,settings,hub, store txn) correctly Python-fallback. NEW startup requirement: the Core server loads dev card defs only for games in envOPENFUT_DEV_CONTENT_GAMES(comma-sep); omittingfifa17makesget_collectionsilently drop every owned card (empty/collection, "no squad") despite a successful seed — MUST become a deployment/preflight assertion. Preceded the same day by a staged two-process parity gate (real Core+host over HTTP, no FIFA) confirming byte- shape parity ofuserMassInfo.squadvs the captured oracle. Next milestone: real-data Core import / profile strategy → production Rust UTAS. Blaze deferred. - Slice 8 (2026-08-12): REAL-DATA staged retail A/B PASS (import + club + squad). The real FIFA 17
profile was imported into a staged Core via the two-store protocol (
openfut-import-fifa17 --apply: generic transactional Core import +openfut-identityseeding, idempotent), then FIFA itself consumed it end-to-end over the source-scoped utas switch (.105→.120:8199). Imported population 1949 of 1962 player instances (13 Legend/special assets deferred as unnameable — 9 NoName + the 4 copies of169193), every original Python wire id preserved (set-equal, 0 minted/dropped), each owned instance an opaque Core UUID. On the retail client: real club rendered (1949, not the 33-card dev XI);/clubpagination clean (paged==full, no loop/overlap/drop); theSpecialquality filter returned only specials (1665, 0 base leaked) and paginated the filtered set; a squad edit persisted to Core (canonical + opaque extension atomically, fingerprint recomputed) and survived a full cold relaunch; rollback→Python→Rust re-enable proven on the exact client path (disarm reached Python, re-arm returned the imported club + edited squad; identity store 0 reallocation). Three real-data fidelity gaps the base-only dev fixture had hidden were found on the live client and fixed: (1)e187cd4versionedresourceId—shape_itememitted the base assetId asresourceId, collapsing every special onto its base card art;Fifa17Identitynow carries the versionedresource_id. (2)626c972observedrareflag—shape_itemhardcodedrareflag=1, so all specials rendered as basic rare;rareflagnow flows through the FIFA catalog and onto the wire (wire distribution == source exactly). (3)6f16a23rare=SPSpecial filter — previously a no-op ("semantics UNKNOWN"), now grounded asrareflag > 1and applied host-side (Core has no rareflag). Also44fcf24: nation/league/team proven to be INSTANCE metadata (not definition identity — the 4 copies of169193are identical but for club), so the definition-consistency gate now compares identity only (no--defer-conflictneeded; no majority-vote). PRODUCTION NOT READY: the 13 deferred Legends are unnameable from the.120client dump (absent/placeholder inplayers.json; DLC/Legends name tables empty) — honest names require the FIFA 17 Legends locale data from the.105client. Next: resolve the 13 names → re-import to 1962/0 → full-fidelity gate → gitlink reconcile → production Rust UTAS.
Stubbed / planned
fifa-blaze(Rust) — Milestone 1 capture stub only. Two TLS listeners that log packets; no FIFA 23 component/command handlers. Its own README says IDs are unknown. Superseded in practice by the Python FIFA 17 responders, kept as the intended FIFA 23 implementation surface.openfut-launcherlegacy controls — core/bridge and FIFA 23 setup controls belong to a superseded plan. The launcher now also owns the live FIFA 17 client flow: server/hook config, account synchronization, local LSX, privileged autopatch, and game launch.tools/(file-watch-diff, squad-injector, exporters) — helpers for the FLE-Lua-bridge idea indocs/direction.md. Not part of the live FIFA 17 path.docs/foundational-xi-injection-test.md— a planned (not executed) test procedure for the FLE bridge route.
Stubbed / blocked (FIFA 23 lineage)
openfut-bridge— in-processversion.dllhook on ProtoSSL. Git history: injection works but the effort hit an "architectural wall" (async event-driven gate, not a poll). Superseded first by the FLE-bridge pivot, then by the FIFA 17 route. ItsCLAUDE.mdtask list is historical.
Unknown / requires investigation
- Whether the FIFA 17 hub supports actually playing a FUT match offline and getting results back.
- Whether FUT actions beyond the now-verified pack reveal/assignment flow (submit SBC, transfer
market buy/sell, matches) round-trip correctly through
utas_server.py. - The exact division of FUT state ownership once Core is wired in (who is source of truth).
- Degree of FIFA 23 wire-format identity — asserted ("identical wire format") but the FIFA 23 client has not been re-tested against these responders in this repo's evidence.
Known technical debt / hazards
- Root docs are stale.
README.md,CLAUDE.md,openfut-bridge/CLAUDE.mdall describe FIFA 23 as the target and mark FIFA 23 integration as the open item — they predate the FIFA 17 success. - All host state is volatile across reboot except the
/etc/hostsline — re-runopenfut-fut.sh start. Requiresptrace_scope=0+ root arming (security-relevant). - Whole stack rides on EAAC staying neutralized and game updates being off; a client update can break the memory patches (VAs) and cert bypass.
fifa17-recon/tools/lsx_responder_v2.pyis currently modified in the working tree (uncommitted).33068179/CAGEremains the responder fallback, but the launcher now blocks one-button launch until an explicit persona is configured and synchronized across LSX, Blaze, POW, and UTAS.