From 6b385e62ba3e2a7b39beafa1fcdbb3417be728b1 Mon Sep 17 00:00:00 2001 From: Claude Date: Mon, 22 Jun 2026 04:25:26 +0000 Subject: [PATCH] docs: update SWBF2 guide with direct-exe bypass and Origin registry spoof Revised approach: skip link2ea:// and EA App account requirement entirely. Launch starwarsbattlefrontii.exe directly via the wrapper, spoof Origin registry entries so the game's built-in launcher check passes. Documents what doesn't work and why (msiexec/bwrap/EA account issues). Co-Authored-By: Claude Sonnet 4.6 Claude-Session: https://claude.ai/code/session_01D8ckUJQtj1pH8jtAddBDZs --- docs/SWBF2-2017-wolf-setup.md | 295 +++++++++++++++++----------------- 1 file changed, 148 insertions(+), 147 deletions(-) diff --git a/docs/SWBF2-2017-wolf-setup.md b/docs/SWBF2-2017-wolf-setup.md index 8f9ca6b..37a88f4 100644 --- a/docs/SWBF2-2017-wolf-setup.md +++ b/docs/SWBF2-2017-wolf-setup.md @@ -9,11 +9,13 @@ ## Why this is hard SWBF2 (2017) is an EA game. EA mandated their **EA App** launcher for all EA Steam titles. -On launch, SWBF2 calls `ShellExecuteW("link2ea://launchgame/1237950?platform=steam&theme=swbfii")`. -GE-Proton's `steam.exe` intercepts that URL, finds `Link2EA.exe` from the EA Desktop install, and -hands off to the EA App which then launches the actual game. +On launch, Steam passes `link2ea://launchgame/1237950?platform=steam&theme=swbfii` as the +"executable" to GE-Proton. The game binary itself also checks for Origin/EA App in the +registry before starting. -Without EA Desktop installed in the Wine prefix, the game exits immediately. +EA App requires an EA account login, and ea.com/signup has been unreliable. The workaround +here **bypasses EA App entirely**: launch the game executable directly and spoof the Origin +registry entries so the game thinks its launcher is installed. --- @@ -35,214 +37,213 @@ Only Steam itself can properly launch programs through sniper+GE-Proton. --- -## Solution: Steam launch wrapper +## Solution overview -Use SWBF2's **Steam launch options** to intercept the launch, run a helper script, -then pass control back to Steam's real launch chain. +1. Intercept the Steam launch with a wrapper script (via launch options) +2. Spoof Origin registry entries so SWBF2 thinks its launcher is present +3. Skip link2ea:// entirely — launch `starwarsbattlefrontii.exe` directly -Steam passes all its args to the wrapper as `$@`: -``` -steam-launch-wrapper -- reaper SteamLaunch AppId=1237950 -- --verb=waitforexitandrun -- waitforexitandrun -``` - -The wrapper runs msiexec (or anything else) inside the full sniper+GE-Proton environment -that Steam set up, then `exec "$@"` to hand off to the game. +No EA account needed. No EA App login needed. --- ## Step-by-step -### 1. Lock localconfig.vdf against Steam overwriting it - -Steam uses atomic rename (write temp + rename) when saving config. -`chmod 444` on the file is bypassed. Lock the **directory** instead: +### 1. Find the WolfSteam container name and Steam user ID ```bash -WOLF_CONTAINER="WolfSteam_XXXXXXXXXXXXXXXX" # docker ps to find exact name -CONFIG_DIR="/home/retro/.steam/steam/userdata/XXXXXXXXX/config" +WOLF_CONTAINER=$(docker ps --format '{{.Names}}' | grep Wolf) +echo "$WOLF_CONTAINER" -# Find container name -docker ps --format '{{.Names}}' | grep Wolf +STEAM_UID=$(docker exec "$WOLF_CONTAINER" ls /home/retro/.steam/steam/userdata/) +echo "$STEAM_UID" -# Find Steam user ID -docker exec "$WOLF_CONTAINER" ls /home/retro/.steam/steam/userdata/ +CONFIG_DIR="/home/retro/.steam/steam/userdata/$STEAM_UID/config" +``` +### 2. Lock localconfig.vdf against Steam overwriting it + +Steam uses atomic rename (write temp + rename) when saving config. +`chmod 444` on the file is bypassed by the rename. Lock the **directory** instead: + +```bash docker exec "$WOLF_CONTAINER" chmod 555 "$CONFIG_DIR" ``` -### 2. Set SWBF2 launch options +### 3. Set SWBF2 launch options in localconfig.vdf -Edit localconfig.vdf **while Steam is not running** (or kill Steam first): +Kill Steam first so it flushes and releases the file, then edit: ```bash -CONFIG_FILE="$CONFIG_DIR/localconfig.vdf" - -# Kill Steam so it flushes and stops watching docker exec "$WOLF_CONTAINER" pkill -f steam.sh || true sleep 3 -# Edit — find the LaunchOptions line for AppID 1237950 -# Add before it if missing: -docker exec "$WOLF_CONTAINER" bash -c " - sed -i '/\"1237950\"/,/}/ s/\"LaunchOptions\"\s*\"[^\"]*\"/\"LaunchOptions\"\t\t\"STEAM_UNIX_SOCKET=\/tmp\/steam.sock \/home\/retro\/ea_install.sh %command%\"/' '$CONFIG_FILE' -" -# Or if LaunchOptions key doesn't exist yet, add it manually. -# Verify: -docker exec "$WOLF_CONTAINER" grep -A5 '"1237950"' "$CONFIG_FILE" | grep LaunchOptions +CONFIG_FILE="$CONFIG_DIR/localconfig.vdf" + +# The file needs a LaunchOptions entry under AppID 1237950. +# Find the block and add/replace LaunchOptions: +docker exec "$WOLF_CONTAINER" grep -A5 '"1237950"' "$CONFIG_FILE" +# If LaunchOptions is missing, add it manually to the 1237950 block: +# "LaunchOptions" "STEAM_UNIX_SOCKET=/tmp/steam.sock /home/retro/ea_install.sh %command%" ``` -### 3. Write the EA install wrapper +The launch option value must be: +``` +STEAM_UNIX_SOCKET=/tmp/steam.sock /home/retro/ea_install.sh %command% +``` -The wrapper runs `msiexec /a` (administrative install — no custom actions) to extract -EA Desktop files, then execs the real game: +### 4. Write the Origin registry spoof + +SWBF2's binary checks for Origin in the registry before starting. Spoof it by writing +directly to Wine's system.reg (plain text file — no Wine needed): + +```bash +SYSREG="/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/system.reg" +TIMESTAMP=$(date +%s) + +docker exec "$WOLF_CONTAINER" bash -c "cat >> '$SYSREG' << 'REGEOF' + +[Software\\\\Origin] $TIMESTAMP +\"ClientPath\"=\"C:\\\\\\\\Program Files\\\\\\\\Electronic Arts\\\\\\\\EA Desktop\\\\\\\\EA Desktop\\\\\\\\EADesktop.exe\" +\"InstallDir\"=\"C:\\\\\\\\Program Files\\\\\\\\Electronic Arts\\\\\\\\EA Desktop\\\\\\\\EA Desktop\\\\\\\\\" + +[Software\\\\Wow6432Node\\\\Origin] $TIMESTAMP +\"ClientPath\"=\"C:\\\\\\\\Program Files\\\\\\\\Electronic Arts\\\\\\\\EA Desktop\\\\\\\\EA Desktop\\\\\\\\EADesktop.exe\" +\"InstallDir\"=\"C:\\\\\\\\Program Files\\\\\\\\Electronic Arts\\\\\\\\EA Desktop\\\\\\\\EA Desktop\\\\\\\\\" +REGEOF" + +# Verify +docker exec "$WOLF_CONTAINER" grep -A3 'Software\\\\Origin' "$SYSREG" +``` + +### 5. Write the launch wrapper + +The wrapper receives Steam's full launch chain as `$@` (args 1–11 are the +sniper+GE-Proton preamble, arg 12 is normally `link2ea://...`). Replace the last +arg with the actual game executable: ```bash cat > /tmp/ea_install.sh << 'EOF' #!/bin/bash -echo "=== ea_install.sh called $(date) ===" >> /tmp/ea_install.log -echo "Args: $@" >> /tmp/ea_install.log -"$1" "$2" "$3" "$4" "$5" "$6" "$7" "$8" "$9" "${10}" "${11}" \ - msiexec /i "C:\\ea_app.msi" /qn \ - TARGETDIR="C:\\Program Files\\Electronic Arts" \ - /l*v "C:\\msi_admin.log" \ - >> /tmp/ea_install.log 2>&1 -echo "MSI exit: $?" >> /tmp/ea_install.log -exec "$@" +echo "=== launch $(date) ===" >> /tmp/ea_install.log +GAME_EXE="/home/retro/.steam/steam/steamapps/common/STAR WARS Battlefront II/starwarsbattlefrontii.exe" +exec "$1" "$2" "$3" "$4" "$5" "$6" "$7" "$8" "$9" "${10}" "${11}" "$GAME_EXE" EOF chmod +x /tmp/ea_install.sh docker cp /tmp/ea_install.sh "$WOLF_CONTAINER":/home/retro/ea_install.sh ``` -### 4. Get the EA App MSI +### 6. Launch SWBF2 in Moonlight -The MSI ships inside SWBF2's game files. Copy it into the Wine prefix: +Steam → wrapper → `starwarsbattlefrontii.exe` runs directly inside sniper+GE-Proton. +The game checks Origin registry, finds the spoofed entries, and starts. + +You may see Vulkan shader compilation prompts on first launch — these can be skipped; +the game will still proceed (shaders compile lazily or are skipped). + +### 7. Restore clean state (after confirmed working) ```bash -MSI_SRC="/home/retro/.steam/steam/steamapps/common/STAR WARS Battlefront II/__Installer/Origin/redist/internal/EAappInstaller.exe" -# EAappInstaller.exe is a WiX Burn bootstrapper — the real MSI is buried inside. -# Easier: use the MSI that gets extracted to the Wine prefix during a first launch attempt: -MSI_IN_PREFIX="/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/ea_app.msi" +# Restore directory to writable so Steam can save normally +docker exec "$WOLF_CONTAINER" chmod 755 "$CONFIG_DIR" + +# Remove LaunchOptions for 1237950 from localconfig.vdf while Steam is stopped ``` -The MSI appears in the Wine prefix (`drive_c/ea_app.msi`, ~227 MB) after SWBF2 is launched -once — GE-Proton's protonfixes or steam.exe drops it there. +--- -### 5. Extract EA Desktop files on the host (bypassing Wine custom actions) +## Background: what Steam actually passes to the wrapper -The MSI's `JunoConfigureRegistry` custom action fails in Wine (it tries to set registry -ACLs via `SetSecurityDescriptorSddlForm` which Wine doesn't support). This causes -MSI rollback and removes all installed files. Bypass it by extracting on Linux: +``` +$1 = /path/to/steam-launch-wrapper +$2 = -- +$3 = /path/to/reaper +$4 = SteamLaunch +$5 = AppId=1237950 +$6 = -- +$7 = /path/to/SteamLinuxRuntime_sniper/_v2-entry-point +$8 = --verb=waitforexitandrun +$9 = -- +$10 = /path/to/GE-Proton10-34/proton +$11 = waitforexitandrun +$12 = link2ea://launchgame/1237950?platform=steam&theme=swbfii ← we replace this +``` +--- + +## What doesn't work (and why) + +### Running msiexec / Wine via docker exec +`docker exec` carries Linux capabilities that break bwrap. Any attempt to run +Proton/wine64 outside Steam's own launch chain gets: +``` +setting up uid map: Permission denied +``` + +### Running the EA App MSI through Wine (INST-14-1603) +The MSI's `JunoConfigureRegistry` .NET custom action uses `SetSecurityDescriptorSddlForm` +to set registry ACLs. Wine doesn't support this — the action returns 0 (failure), +causing the entire install to roll back. `DISABLEROLLBACK=1` doesn't help because +MSI logs the product as already-registered from the first attempt, causing subsequent +runs to produce an empty log and exit. + +### link2ea:// approach with EA account +EA App requires an EA account linked to your Steam account. `ea.com/signup` is +unreliable. Even with an account, EA Desktop must be installed in the Wine prefix +(see msiextract bypass below if needed). Bypassing the game exe directly is simpler. + +### msiextract bypass (if EA App files are needed for something else) +If you need EA Desktop files in the prefix for another reason: ```bash -# Copy MSI out of container +# Copy MSI out of container (appears in drive_c after first launch attempt) docker cp "$WOLF_CONTAINER:/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/ea_app.msi" \ /tmp/ea_app.msi -# Extract (msitools package) +# Extract on host (bypasses JunoConfigureRegistry entirely) sudo apt-get install -y msitools mkdir -p /tmp/ea_app_extracted msiextract -C /tmp/ea_app_extracted /tmp/ea_app.msi -``` -### 6. Copy EA Desktop into the Wine prefix - -The MSI installs to `C:\Program Files\Electronic Arts\EA Desktop\` with a versioned -subdirectory (`14.2.0.3345`) and a symlink `EA Desktop -> 14.2.0.3345`. - -The normal MSI install creates that symlink via `JunoSetupSymlinkMode`. After a -failed install + rollback, the symlink may remain but the versioned dir is gone. - -```bash PFXBASE="/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/Program Files/Electronic Arts/EA Desktop" - -# Remove any broken symlink docker exec "$WOLF_CONTAINER" bash -c " [ -L '$PFXBASE/EA Desktop' ] && rm '$PFXBASE/EA Desktop' mkdir -p '$PFXBASE/14.2.0.3345' ln -s 14.2.0.3345 '$PFXBASE/EA Desktop' " - -# Copy extracted files into versioned directory docker cp "/tmp/ea_app_extracted/Electronic Arts/EA Desktop/EA Desktop/." \ "$WOLF_CONTAINER:$PFXBASE/14.2.0.3345/" - -# Verify -docker exec "$WOLF_CONTAINER" find "$PFXBASE" -name "Link2EA.exe" -``` - -Expected output: -``` -/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/Program Files/Electronic Arts/EA Desktop/14.2.0.3345/Link2EA.exe -``` - -### 7. Switch wrapper to pass-through and launch - -Once EA Desktop files are in place, update the wrapper to just exec the game: - -```bash -cat > /tmp/ea_passthrough.sh << 'EOF' -#!/bin/bash -echo "=== launch $(date) ===" >> /tmp/ea_install.log -exec "$@" -EOF -chmod +x /tmp/ea_passthrough.sh -docker cp /tmp/ea_passthrough.sh "$WOLF_CONTAINER":/home/retro/ea_install.sh -``` - -Launch SWBF2 in Moonlight. Steam → GE-Proton → SWBF2 → link2ea:// → steam.exe -finds Link2EA.exe → EA App launches → SWBF2 loads. - -### 8. EA account login (one-time) - -On first launch, EA Desktop will show a login screen. Log in with your EA account. -Credentials are cached; subsequent launches skip login. - -### 9. Restore clean state - -After EA Desktop is confirmed working, remove the launch wrapper: - -```bash -# Restore directory to writable -docker exec "$WOLF_CONTAINER" chmod 755 "$CONFIG_DIR" - -# Remove LaunchOptions from localconfig.vdf -# (edit the file while Steam is stopped, remove the LaunchOptions line for 1237950) ``` --- ## Troubleshooting -### "link2ea not found" / game exits in ~6 seconds -EA Desktop files are missing or in wrong path. Check: +### Game exits in ~6 seconds, no popup +Check wrapper log inside container: ```bash -docker exec "$WOLF_CONTAINER" find \ - "/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/Program Files/Electronic Arts" \ - -name "Link2EA.exe" +docker exec "$WOLF_CONTAINER" bash -c " + cat /tmp/ea_install.log | tail -20 + find /home/retro/.steam/steam/steamapps/compatdata/1237950/ -name '*.log' \ + -newer /tmp/ea_install.log 2>/dev/null | xargs tail -20 2>/dev/null +" +``` + +### "Origin is not installed" popup +Origin registry entries missing. Repeat step 4 and verify: +```bash +docker exec "$WOLF_CONTAINER" grep -A3 'Software\\\\Origin' \ + '/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/system.reg' ``` ### Wrapper never runs (Steam ignores launch options) -Steam wrote config before chmod 555 was applied. Kill Steam, chmod 555 the directory, -then edit localconfig.vdf. Steam reads config fresh on startup. - -### INST-14-1603 error in EA App installer -`JunoConfigureRegistry` .NET custom action returns 0 in Wine. This is a Wine limitation -with registry ACL operations. Use the `msiextract` bypass (Step 5–6) instead of -running the MSI through Wine. - -### msiexec DISABLEROLLBACK=1 produces empty log -MSI detected a stale product registration from a previous failed install. -Check: `grep -i C2622085 /home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/system.reg` -If present, delete those registry keys then retry. - -### wine64 segfaults outside Steam (exit 139) -GE-Proton10's wine64 requires the sniper runtime. Never call it directly from -`docker exec` — always use Steam's launch chain via the wrapper approach. +Steam wrote config before chmod 555 was applied. Kill Steam, verify chmod 555 is set +on the config directory, edit localconfig.vdf, then start Steam again. ### localconfig.vdf gets overwritten on Steam shutdown -Steam uses atomic rename (temp file + rename into place). `chmod 444` on the file -is bypassed by the rename. Solution: `chmod 555` on the **directory** containing -localconfig.vdf — this prevents new files being renamed into the directory. +`chmod 555` on the directory (not the file) prevents the atomic rename Steam uses. + +### wine64 segfaults outside Steam (exit 139) +GE-Proton10's wine64 requires the sniper runtime. Never call it via `docker exec`. --- @@ -251,9 +252,9 @@ localconfig.vdf — this prevents new files being renamed into the directory. | Path | Description | |------|-------------| | `/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/` | SWBF2 Wine prefix | -| `/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/ea_app.msi` | EA App MSI (~227 MB) | -| `/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/Program Files/Electronic Arts/EA Desktop/14.2.0.3345/` | EA Desktop files | -| `/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/Program Files/Electronic Arts/EA Desktop/EA Desktop` | Symlink → `14.2.0.3345` | +| `/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/system.reg` | Wine HKLM registry (plain text) | +| `/home/retro/.steam/steam/steamapps/compatdata/1237950/pfx/drive_c/ea_app.msi` | EA App MSI (~227 MB, appears after first launch) | +| `/home/retro/.steam/steam/steamapps/common/STAR WARS Battlefront II/starwarsbattlefrontii.exe` | Actual game binary | | `/home/retro/.steam/steam/userdata//config/localconfig.vdf` | Steam per-user config (launch options) | | `/home/retro/ea_install.sh` | Launch wrapper script | -| `/tmp/ea_install.log` | Wrapper log (inside container) | +| `/tmp/ea_install.log` | Wrapper log (inside container, resets on container restart) |