Skip to content

bugfix: Fix LAN IP selection and periodic input stalls on macOS/iOS#13

Open
DmytryS wants to merge 3 commits into
ammaarreshi:mainfrom
DmytryS:fix/lan-ip-and-monotonic-clock
Open

bugfix: Fix LAN IP selection and periodic input stalls on macOS/iOS#13
DmytryS wants to merge 3 commits into
ammaarreshi:mainfrom
DmytryS:fix/lan-ip-and-monotonic-clock

Conversation

@DmytryS

@DmytryS DmytryS commented Jul 7, 2026

Copy link
Copy Markdown

Merge with Rebase (three standalone fixes, each compiles independently)

What this fixes

1. LAN multiplayer binds to an unreachable IP address (network)

On POSIX platforms IPEnumeration::getAddresses() accepts every non-loopback
IPv4 interface. On iOS this includes cellular (pdp_ip*) and VPN tunnel
(utun*) interfaces, and on macOS link-local 169.254.0.0/16 addresses from
auxiliary interfaces (e.g. the iPhone-USB bridge). Because the list is sorted
ascending and the LAN lobby takes the first entry, these addresses win over the
real Wi-Fi/Ethernet address and LAN games bind to an interface no LAN peer can
reach. The fix skips IFF_POINTOPOINT interfaces and link-local addresses.
Interface names are deliberately not whitelisted so hotspot play (bridge100)
keeps working.

2. Recurring 10-15 second UI/input stalls (system)

timeGetTime() is implemented with gettimeofday() on POSIX (both CompatLib
copies and systimer.h). Wall time steps backward on NTP/carrier time sync —
frequent on iOS. Every elapsed-time gate in the engine (shell screen updates,
window animations, transitions, network resend timers) then stalls until the
clock catches back up, which presents as the game ignoring touches for the
size of the step while rendering continues. Reproduced on device: the engine
log shows button taps registering (Shell::push) while the pending screen
transition sits unprocessed for many seconds. The fix switches both shims to
CLOCK_MONOTONIC.

3. iOS packaging script fails on multi-word device names (tooling)

devicectl list devices output is parsed by column position, which shifts
with names like "iPhone 15 Pro Max". Parse the identifier by UUID shape
instead.

Testing

  • The LAN IP fix is verified on device (iPhone 15 Pro Max) and on an Apple
    Silicon Mac: the LAN lobby now selects the Wi-Fi address (previously a
    cellular 10.x address on iOS and a link-local 169.254.x address on macOS).
  • The monotonic clock fix is build-verified; on-device soak testing in progress.
  • Builds clean for macos-vulkan (Zero Hour + Generals) and ios-vulkan
    (Zero Hour) presets.

AI disclosure

The changes in this PR were generated with an LLM (Claude Code), reviewed
line-by-line, and tested by the author as described above.

🤖 Generated with Claude Code

DmytryS and others added 3 commits July 7, 2026 18:27
…numerating LAN IP addresses

Cellular (pdp_ip*) and VPN tunnel (utun*) interfaces sorted below the
Wi-Fi address and were picked as the default LAN IP on iOS and macOS,
so LAN games bound to an interface no LAN peer can reach.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
gettimeofday follows wall time, which steps backward on NTP/carrier
time sync (frequent on iOS). Every elapsed-time gate in the engine
(shell updates, animations, network resend timers) then stalls until
the clock catches back up, freezing UI response for the size of the
step while rendering and input events keep flowing.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
…g script

The devicectl column position shifts with multi-word device names
(e.g. "iPhone 15 Pro Max"), so parse the identifier by its UUID shape
instead of by column index.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant