T05 · Unauthorized Access and Privilege Escalation
Error
- Location
- scripts/tiandao_mcp_server.py:465
- Finding
- Unauthenticated SSE Service Exposes Token-Backed MCP Operations## Vulnerability Details **File Location**: `scripts/tiandao_mcp_server.py:465-486` **Vulnerability Type**: Missing authentication and unsafe network exposure **Risk Level**: High ### Vulnerable Code ```python sse_transport = SseServerTransport("/messages/") async def handle_sse(request): async with sse_transport.connect_sse( request.scope, request.receive, request._send ) as streams: await server.run( streams[0], streams[1], server.create_initialization_options() ) starlette_app = Starlette( routes=[ Route("/sse", endpoint=handle_sse), Mount("/messages/", app=sse_transport.handle_post_message), ] ) uvicorn.run(starlette_app, host="0.0.0.0", port=args.port) ``` The token selection logic also falls back to the default bearer token for any supplied agent identifier: ```python def _get_token(agent_id: str = "default") -> str | None: return _token_store.get(agent_id) or _token_store.get("default") ``` ### Technical Analysis SSE mode binds the MCP service to `0.0.0.0`, making it reachable through every available network interface. Neither the `/sse` endpoint nor the `/messages/` endpoint performs client authentication or authorization before establishing an MCP session. MCP clients connected through this interface can invoke all registered tools, including perception, whisper, combat, trading, item transfer, and other state-changing actions. These operations are forwarded to the world engine with the bearer token held by the server. The default-token fallback compounds the problem. An arbitrary `agent_id` supplied by a caller does not create an authorization boundary because `_get_token()` uses the default token whenever no token exists for the requested identifier. ### Attack Path 1. A user starts the application with `--transport sse`. 2. The application listens on all interfaces, normally on TCP port 8765. 3. An at ...[truncated 1039 chars]
- Remediation
- ## Remediation Suggestions 1. Bind SSE mode to `127.0.0.1` by default and require an explicit option before listening on external interfaces. 2. Require strong client authentication for both `/sse` and `/messages/`, such as a separate high-entropy service credential or mutually authenticated TLS. 3. Authorize each MCP caller for the specific agent identity and operation being requested. 4. Remove the default-token fallback for caller-supplied agent identifiers. Return an authorization error when an exact token mapping is unavailable. 5. Add origin and host validation where browser-accessible transports may be used. 6. Place remote deployments behind TLS, firewall restrictions, and a trusted authenticated reverse proxy. 7. Clearly document that SSE mode exposes token-backed operations and must not be placed directly on an untrusted network. 8. Add automated tests confirming that unauthenticated clients cannot initialize sessions or submit MCP messages.
