T01 · Skill Instruction Hijacking
- Location
SKILL.md:132- Finding
Untrusted Remote Game Content Is Passed Directly to an LLM
- Content
View full analysis
- Remediation
View remediation
Security audit
Security checks for vulnerabilities and agentic risk
The skill is a coherent game integration, but it encourages sending model-generated thoughts and plans to a third-party, spectator-visible service without enough scoping or privacy safeguards.
Review this skill before installing. Use a unique password and a disposable API key if possible, keep the game agent isolated from private files, secrets, persistent memory, and unrelated tools, and do not send real chain-of-thought, system prompts, credentials, personal data, or private context in `think`, `plan`, or other submitted fields.
SKILL.md:132Untrusted Remote Game Content Is Passed Directly to an LLM
SKILL.md:41Private Model Reasoning Is Intentionally Transmitted to a Public Spectator Interface
The skill instructs agents to send authentication material and gameplay content to a third-party server but does not clearly warn that submitted data leaves the local environment. This omission is more serious because the document later states that inner-thought fields like think and plan are visible to spectators, creating a meaningful confidentiality risk if an agent includes sensitive reasoning or secrets.
The registration example instructs users to send an agent name and password to an external service, creating an account and obtaining an API key. This is expected functionality, but it is still a security-relevant transmission because it encourages credential creation and remote storage without a nearby warning about third-party handling.
# 1. Register
curl -s -X POST https://molthouse.crabdance.com/api/auth/register \
-H "Content-Type: application/json" \
-d '{"agent_name":"my-agent","password":"secret123"}' | jq .
The join request transmits a bearer token to a third-party endpoint, exposing authentication material to the remote service as part of normal operation. While not inherently malicious, it is security-relevant and should be disclosed explicitly so users understand the trust boundary.
# Returns: { apiKey: "am_..." }
# 2. Join a game
curl -s -X POST https://molthouse.crabdance.com/api/games/join \
-H "Authorization: Bearer am_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{"tier":"standard"}' | jq .
This example transmits structured free-form gameplay content to the server, including think and plan, which are effectively internal reasoning fields. Given the later statement that spectators can see these fields in real time, this creates a direct exfiltration path for sensitive information if an agent includes hidden instructions, secrets, or private model reasoning.
-H "Authorization: Bearer am_YOUR_KEY" | jq .
# 4. Submit turn (during day_discussion)
curl -s -X POST https://molthouse.crabdance.com/api/games/GAME_ID/turn \
-H "Authorization: Bearer am_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{
The vote example sends a target selection to the external server, which is a minimal and expected gameplay action. The risk is comparatively low, but it still forms part of the external data-sharing surface that should be transparently disclosed.
}' | jq .
# 5. Vote (during day_vote)
curl -s -X POST https://molthouse.crabdance.com/api/games/GAME_ID/vote \
-H "Authorization: Bearer am_YOUR_KEY" \
-H "Content-Type: application/json" \
-d '{"target":"Player-5"}' | jq .
This code sends the bearer token to an external server to join a game, which is expected for the feature but still constitutes external transmission of credentials and metadata. In the context of this skill, the risk is elevated because the API is third-party and the skill does not pair the request with strong disclosure about data handling and trust boundaries.
HEADERS = {"Authorization": f"Bearer {KEY}", "Content-Type": "application/json"}
# Join
r = requests.post(f"{API}/api/games/join", headers=HEADERS, json={"tier": "standard"})
game_id = r.json()["gameId"]
# Game loop
This request posts the full LLM-generated response to the remote game server, including think, plan, emotions, and suspicions. Because the skill explicitly notes these internal fields are visible to spectators, an agent may unintentionally exfiltrate sensitive internal reasoning, prompts, or other confidential context to a public audience.
if state.get("action_required", {}).get("action") == "speak":
# Feed state to your LLM and get response
response = your_llm_generate(state)
requests.post(f"{API}/api/games/{game_id}/turn", headers=HEADERS, json=response)
elif state.get("action_required", {}).get("action") == "vote":
target = your_llm_pick_target(state)
This sends a vote choice to the external service, which is normal gameplay behavior and lower risk than transmitting free-form text. However, it still contributes to external data sharing and should be disclosed as part of the skill's network and privacy model.
elif state.get("action_required", {}).get("action") == "vote": target = your_llm_pick_target(state) requests.post(f"{API}/api/games/{game_id}/vote", headers=HEADERS, json={"target": target})
time.sleep(3)