CNA-PLAT-018: Online PlayerMatch and Ranked session traffic needs a libcurl with WebSocket support; with macOS's system libcurl the relay refuses with RELAY_SECURE_WEBSOCKET_UNAVAILABLE
Evidence basis: source-verified at the pinned commit; recorded by CNA's own run (not repeated here); tests exist (not executed for this page). Claims on this page were checked by reading the CNA source at commit c1c316b9; unless a sentence says otherwise, nothing here was built or executed. Nothing on this page was executed unless the Evidence section says so.
PlayerMatch and Ranked sessions carry their traffic over a WSS relay through libcurl's WebSocket API, so a libcurl without ws/wss and TLS (Apple's system libcurl 8.7.1, or one older than 7.86) refuses the relay and those sessions cannot run.
- Identifier
CNA-PLAT-018- Category
- Platform limitation
- Subsystem
- Networking & gamer services
- Status
- Open
- Verified against
- CNA
c1c316b9(c1c316b9c7a846ce8002809c151fcd1af14942c9) - Evidence basis
- Recorded by CNA: CNA's own recorded run, not repeated here
- Tests touching this area
- Yes: see Current tests
- Affected contract
- Microsoft::Xna::Framework::Net::NetworkSession Create, Join and JoinInvited for NetworkSessionType::PlayerMatch and Ranked with a configured CNA gamer-services endpoint; the realtime relay at /cna/relay/v1 and the push channel /cna/v1/events
Expected behaviour
Once a CNA gamer-services endpoint is configured, online PlayerMatch and Ranked sessions work on every desktop host CNA builds for, as they do on Linux.
Actual behaviour at TARGET
Online session traffic (game data, voice, readiness) travels between machines through the service's authenticated WSS datagram relay, which CNA reaches through libcurl's WebSocket API (curl_ws_send/curl_ws_recv). Before it authenticates, RelayWebSocket.cpp checks the linked libcurl with relayTransportRefusal(): relayTransportRefusalFor refuses with RELAY_SECURE_WEBSOCKET_UNAVAILABLE unless the version is at least 7.86.0, its protocol list offers both ws and wss, and it has a TLS backend. Apple's system libcurl 8.7.1, which a macOS build links unless another curl is found, has no WebSocket support, so on such a build the relay never connects; the online session cannot become ready and, by reading ServiceENetSession.cpp, ends with a relay failure once its 15-second relay-recovery window has passed. The account's push channel (/cna/v1/events) uses the same libcurl WebSocket API in GamerServicesBackend.cpp; without it the hints never arrive and the client falls back to its ordinary polling (invitations and parties every 5 seconds, messages and friends every 15). Sign-in, profiles, achievements, leaderboards, the session directory and SystemLink sessions do not use WebSockets and are unaffected. Before 14f74e81f the same build reported a misleading RELAY_CONFIGURATION instead of this refusal.
Source locations
modules/net/src/Internal/RelayWebSocket.cpp— relayTransportRefusalFor and relayTransportRefusal: ws and wss with TLS from libcurl 7.86.0, otherwise RELAY_SECURE_WEBSOCKET_UNAVAILABLE; relayEndpoint uses CURLU_NON_SUPPORT_SCHEMEmodules/net/tests/Microsoft/Xna/Framework/Net/RelayTransportTests.cpp— RelayTransportTest.RefusalNeedsWsAndWssWithTlsFromCurl7860, including Apple's system libcurl 8.7.1 protocol listmodules/net/src/Internal/ServiceENetSession.cpp— relay recovery inside RecoveryWindow, then failmodules/gamer-services/src/Internal/GamerServicesBackend.cpp— the events push channel over curl_ws_send and curl_ws_recv, with polling as fallbackdocs/apple-platforms.md— cna-gamer-services-server row: a build linking the SDK's libcurl 8.7.1 refuses the relay transport by namedocs/gamer-services-server.md— private client relay requires libcurl >= 7.86 built with TLS and ws/wssplans/plan_apple_m4.md— AM4-044 owner decision: with the system libcurl the relay cannot work on macOS; AM4-123
Evidence
Read at c1c316b9; nothing was built or executed for this entry. The capability rule is pinned by RelayTransportTest.RefusalNeedsWsAndWssWithTlsFromCurl7860 on synthetic version data (8.11 and 7.86.0 with ws/wss and TLS accepted; 7.85, Apple's 8.7.1 protocol list, ws without wss, no TLS and no protocol list refused). CNA's own record states the platform consequence: plan_apple_m4.md AM4-044 records the owner decision that with the system libcurl the relay cannot work on macOS and that Homebrew curl 8.22 has ws/wss, and apple-platforms.md records that a CNA build linking the SDK's libcurl 8.7.1 refuses the relay transport by name, so the server's harness-driven tests on the Mac needed a tree that found Homebrew curl. How the failure reaches a game (the relay-recovery window, then the session's failure code) was established by reading only. Which libcurl a given Linux distribution ships with WebSockets enabled was not surveyed; WebSockets became a default libcurl feature only in 8.11.
Focused reproduction
No focused reproduction is known. Nothing has been invented here; the evidence above is what exists.
Current tests
RelayTransportTest.RefusalNeedsWsAndWssWithTlsFromCurl7860 pins the capability rule and RelayTransportTest.ConnectionFailureIsObservedWithoutCallbackOrDetachedWorker expects the build's own refusal where it cannot connect. No test runs an online session against a libcurl without WebSockets end to end.
Regression test
None needed for the rule itself; a configure-time check that warns when networking is enabled against a libcurl lacking ws/wss would surface the limitation at build time instead of at the first online session.
Blast radius
Games that use online PlayerMatch or Ranked sessions (and their voice) in builds linked against a libcurl without WebSocket support, notably macOS builds that link the system libcurl; push hints in such builds degrade to polling. Local, LocalWithLeaderboards and SystemLink sessions and the non-realtime gamer services are unaffected. iOS builds currently disable networking altogether, and an Android build without a target libcurl refuses the service as a browser does (CNA records both separately).
Workaround
Build against a libcurl that offers ws and wss with TLS, for example Homebrew curl on macOS, so that CMake finds it before the system library.
Related pages
The same subject is explained at several altitudes. These are the neighbouring pages at each one.
- User guide
- Gamer Services: the CNA service
- Known issues
- Platform limitation index