Integer Overflow with Bearer Tokens
How Integer Overflow Manifests in Bearer Tokens
Integer overflow vulnerabilities in Bearer Token systems typically emerge through improper handling of numeric values in token claims, expiration timestamps, and permission scopes. When a server decodes a JWT token and performs arithmetic operations on numeric claims without proper validation, attackers can exploit integer overflow to bypass authorization checks or cause denial of service.
Consider a scenario where a Bearer Token contains a numeric claim representing user permissions:
const token = jwt.sign({
userId: 1234,
permissions: 2147483647, // max 32-bit signed int
exp: Math.floor(Date.now() / 1000) + 3600
}, 'secret');If the authorization system performs operations like adding permissions or calculating access levels, an overflow can occur:
// Vulnerable authorization check
function hasPermission(token, requiredPermission) {
const permissions = token.permissions + requiredPermission;
return permissions > 0; // Overflow can make this true unexpectedly
}In 32-bit signed integer systems, adding 1 to 2147483647 wraps around to -2147483648, potentially granting unauthorized access. This becomes particularly dangerous in Bearer Token systems where the token is decoded server-side and the numeric claims are used in security-critical calculations.
Time-based vulnerabilities also arise when tokens use numeric timestamps. An attacker might manipulate expiration times:
// Vulnerable expiration check
const now = Math.floor(Date.now() / 1000);
if (token.exp - now > 0) { // Can overflow with large exp values
// Grant access
}Using excessively large expiration timestamps can cause subtraction to overflow, potentially resulting in negative values that bypass expiration checks.
Bearer Tokens-Specific Detection
Detecting integer overflow in Bearer Token systems requires examining both the token validation logic and the runtime behavior of numeric operations. Static analysis tools can identify vulnerable patterns, but runtime scanning provides the most reliable detection.
middleBrick's API security scanner specifically tests for integer overflow vulnerabilities in Bearer Token implementations through several techniques:
Numeric Claim Boundary Testing: The scanner generates tokens with boundary values for numeric claims:
const boundaryTokens = [
{ permissions: 2147483647 }, // Max 32-bit signed int
{ permissions: 2147483648 }, // Overflow boundary
{ permissions: -2147483648 }, // Min 32-bit signed int
{ exp: 9999999999 } // Large timestamp
];Arithmetic Operation Fuzzing: The scanner tests how the API handles arithmetic operations on decoded token claims:
// Test cases sent to API
const fuzzValues = [
{ permissions: 2147483647 }, // Max value
{ permissions: 2147483647 + 1 }, // Overflow attempt
{ permissions: 2147483647 - 1 }, // Near boundary
{ exp: 4294967295 } // Max 32-bit unsigned
];Runtime Behavior Analysis: middleBrick monitors API responses for indicators of integer overflow:
// Indicators of overflow vulnerabilities
const overflowIndicators = [
'unexpected access granted',
'internal server error',
'numeric value out of range',
'authorization bypass'
];The scanner also examines OpenAPI specifications for numeric types that could be vulnerable:
// Checking spec for vulnerable numeric types
const vulnerableTypes = [
'integer', // Default signed
'int32', // 32-bit signed
'int64' // Can overflow in 32-bit systems
];middleBrick's LLM security features additionally check for AI systems that might mishandle numeric token claims, detecting prompt injection attempts that could manipulate integer values in token processing logic.
Bearer Tokens-Specific Remediation
Remediating integer overflow vulnerabilities in Bearer Token systems requires both defensive coding practices and proper token validation. The most effective approach combines input validation, safe arithmetic operations, and appropriate data type selection.
Safe Numeric Claim Handling: Always validate and sanitize numeric claims before use:
function validateNumericClaim(value, min, max) {
if (typeof value !== 'number' || !Number.isInteger(value)) {
throw new Error('Invalid numeric claim');
}
if (value < min || value > max) {
throw new Error('Numeric claim out of bounds');
}
return value;
}
// Usage in token validation
const permissions = validateNumericClaim(decoded.permissions, 0, 1000000);
const exp = validateNumericClaim(decoded.exp, 0, 4294967295);Safe Arithmetic Operations: Use BigInt or safe integer libraries for critical calculations:
// Safe permission calculation using BigInt
function hasPermission(tokenPermissions, requiredPermission) {
const safePermissions = BigInt(tokenPermissions);
const safeRequired = BigInt(requiredPermission);
const result = safePermissions + safeRequired;
if (result > BigInt(Number.MAX_SAFE_INTEGER)) {
throw new Error('Permission calculation overflow');
}
return Number(result) > 0;
}TypeScript Enforcement: Use TypeScript to prevent accidental numeric overflows:
// Strict numeric type definitions
interface TokenClaims {
userId: number; // Use string for very large IDs
permissions: number; // Validate range
exp: number; // Validate timestamp range
scopes?: string[];
}
// Safe timestamp validation
function validateTimestamp(exp) {
const now = Math.floor(Date.now() / 1000);
const maxFuture = now + 31536000; // 1 year max
if (exp < now || exp > maxFuture) {
throw new Error('Invalid expiration timestamp');
}
return exp;
}Library-Based Protection: Use JWT libraries with built-in overflow protection:
// Using jsonwebtoken with validation
import jwt from 'jsonwebtoken';
function verifyToken(token, secret) {
try {
const decoded = jwt.verify(token, secret, {
algorithms: ['HS256'],
maxAge: '1y' // Prevents large timestamp attacks
});
// Additional validation
if (typeof decoded.permissions !== 'number') {
throw new Error('Invalid permissions claim');
}
return decoded;
} catch (error) {
if (error.name === 'JsonWebTokenError' || error.name === 'TokenExpiredError') {
throw new Error('Invalid or expired token');
}
throw error;
}
}