Summary
txAdmin's OAuth login builds the callback URL from a value the caller supplies freely via
a query parameter — with no validation against a host or an allowlist. At the same
time the OAuth state is bound to the caller's session, not to the person who actually
logs in later. There is no PKCE.
Together, an unauthenticated attacker can craft a login URL whose callback points at their own target, send it to a panel admin, and — after the admin's normal login — take over the resulting session as that admin.
Root cause
- The redirect endpoint reads the origin from the query and builds the OAuth
redirect_urifrom it — the value is accepted as an arbitrary string, with no host/allowlist check. - The OAuth
stateis bound to the requester's session, not to the person logging in. - The token exchange uses the session-stored (attacker) callback URL, and there is no
PKCE — even though the identity provider's metadata explicitly advertises PKCE
(
S256). Nothing binds the authorization code to the legitimate panel. - On callback, txAdmin authenticates whatever session presents a valid code+state pair as the account that logged in.
Because OAuth is the stronger auth method, the attack bypasses password hardening entirely.
Impact
Full takeover of any txAdmin admin account (including master) by a remote, unauthenticated
attacker plus one clicked link. Master access means arbitrary changes to server.cfg and
resources — and therefore code execution on the game server's host.
Fix
- Never trust the client-supplied origin: derive the callback origin server-side from the request host (proxy-aware) or from a configured base URL / allowlist, and reject mismatches.
- Enable PKCE (S256) — the identity provider supports it per its own metadata. PKCE
alone would prevent the redemption step even with an open
redirect_uri. - At callback time, verify that the presented callback origin matches the session-stored one (defense in depth).