Emulates FIFA 17's full online + Ultimate Team stack against an offline,
clean-room backend (no EA servers). Proven end-to-end 2026-08-01:
Origin login -> Blaze login -> device-trust -> the FUT hub.
Package:
- tools/openfut-fut.sh one-command orchestrator (start/stop/status/restart)
- tools/root_arm.sh idempotent host arm (sysctls, DNAT, /etc/hosts easw)
- tools/{lsx_responder_v2,blaze_responder_v3b,roster_server,utas_server,autopatch}.py
the 5 servers (Origin LSX :4216, Blaze :42127/42130/42131, roster :8081,
FUT/UTAS :8099) + heat2.py (Fire2/Heat2 TDF codec)
- FUT-RUNBOOK.md runbook + gate-ladder troubleshooting
- docs/, tools/login_dump/*.md the reverse-engineering write-ups
All findings are clean-room, from binaries we own; nothing from any leak.
The wire protocol maps 1:1 to FIFA 23.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01PN5bmpDVQR1aXgefyWAt7o
4.4 KiB
Agent brief — reverse "Unable to connect to the EA servers" (post-login Blaze QoS/online gate) (clean-room)
Clean-room rule (HARD)
Derive ONLY from decrypted dumps + live /proc/PID/mem (pgrep -x FIFA17.exe, live 50676) + our
LSX/Blaze logs. NEVER leaked EA source/headers. (Our own binary carries the RTTI symbols we need.)
Where we are — the WIN, and the new gate
This session cracked the ENTIRE Origin+Blaze LOGIN chain (each gate = a 1-attribute LSX-responder fix,
last one AuthCode value=). FIFA now performs Blaze Authentication::login (1/0x0A) and the full
post-login handshake (postAuth, UserSessions, AssociationLists, Stats, etc.) — CONFIRMED in
/tmp/blaze_responder.log at 16:38. New on-screen error: "Unable to connect to the EA servers at this
time." (age/underage gate is GONE.)
The exact behaviour (from /tmp/blaze_responder.log)
- Session 1 (16:38, boot login): getServerInstance('fifa-2017-pc') -> Blaze conn -> preAuth -> login -> FULL online handshake, then STABLE ~2.5 min of pings. WORKS.
- Session 2 (16:40:34, user goes online): getServerInstance('fifa-2017-pc', SAME service) -> new
Blaze conn -> we send the SAME preAuth reply (772B) -> FIFA CLOSES the connection IMMEDIATELY,
never sends login -> "unable to connect".
[16:40:34] BLAZE (...): closedright afterTX #4009.0 Util::preAuth. - So a post-preAuth check on the online-feature connection fails (session 1's login path doesn't run this check; session 2 does, and drops before login).
Top suspect: QoS / ping sites (our preAuth QOSS is under-populated)
Our preAuth reply's QOSS (blaze_responder_v3b.py qos_config() ~:527) advertises:
BWPS { PSA="127.0.0.1", PSP=17502 }— a QoS ping server at 127.0.0.1:17502 we DO NOT serve.LTPS(latency ping-site map) = EMPTY.LNP=10,TIME=5000000. CONF has enableQosBandwidthTest=false / enableQosFirewallTest=false, but the ping-site LATENCY path may still run on the online connection. Blaze-SDK RTTI in our image (live-read) proves the subsystem:SetPingSiteLatency@0x14395c880,GetBestPingSiteAlias@0x14398ab20,SetBestPingSite@0x14398ab38,RestorePingSiteLatencyValues@0x14398ab48,GetPingSiteAliasList@0x143990d78,GetBestPingSiteAliasForClubs@0x143990da8,PinQosError_ReferenceEvent@0x1439de5c8,POW:sConnectionManager@0x143995b88. Hypothesis: with an EMPTY ping-site list FIFA cannot compute a best ping site / QoS fails -> the connection is torn down before login -> "unable to connect".
Questions to answer
- WHY does FIFA close the 2nd Blaze connection right after preAuth (before login)? Reverse the
Blaze-SDK preAuth-RESPONSE handler and what it does with
QOSS(parse ping sites, kick a QoS probe, validate the ping server). Find the tear-down/"unable to connect" decision and its precondition. Anchors: the RTTI names above (find their vtables/methods), the connection managerPOW:sConnectionManager, andPinQosError. The Blaze-SDK code region is ~0x146d00000-0x147000000 (login stub 0x146e15070, sendRequest 0x146df0e80, LoginState vtables 0x14389f5a0/0x14389f828/938/a70/b98). - Is it the QoS ping-site latency probe? Does FIFA try to reach 127.0.0.1:17502 (TCP/UDP) or need a
non-empty
LTPS? TraceSetPingSiteLatency/GetBestPingSiteAliasand where a missing ping site aborts the connect. (Session 1 didn't hit it; session 2 does — WHY the asymmetry? maybe session 2 requests a QoS-gated component/service.) - What does session 2 actually want vs session 1 — re-check the getServerInstance requests and the post-preAuth client behaviour. If it's a genuinely different connection purpose, name it.
- The fix: concrete blaze_responder_v3b.py change — populate
LTPSwith >=1 reachable ping site (and/or serve the QoS ping server on :17502), or whatever the reverse shows FIFA needs. Give the exact QOSS/preAuth content + the observable success signal (session 2 proceeds to login instead of closing).
Method / dumps
objdump Intel, VMA==runtime VA. Dump more live: f.seek(va);f.read(n) + objdump --adjust-vma. Our Blaze responder: blaze_responder_v3b.py (preAuth builder, qos_config, fetchQosConfig cmd 0x15). Logs: /tmp/blaze_responder.log (both sessions), /tmp/lsx.log. To reproduce session 2 live, the user would need to re-enter online — but static RE of the preAuth handler + QoS path should answer it. Every claim needs a VA/bytes/disasm/log line.