mediumCWE-208A02:2021

Time-based Attack

Using standard string comparison (=== or ==) for secrets like API keys or tokens allows attackers to guess values character by character by measuring response time differences.

How It Works

Standard string comparison operators check characters sequentially and return false at the first mismatch. This means comparing 'AAAA' against 'ABCD' takes less time than comparing 'ABCA' against 'ABCD' because the first comparison fails at character 2 while the second fails at character 4. By measuring response times with microsecond precision, an attacker can determine how many leading characters are correct. They brute-force one character at a time: try all possibilities for the first character, keep the one with the longest response time, then move to the second character. A 32-character token that would take billions of years to brute-force can be cracked in minutes with timing attacks.

Vulnerable Code
app.post('/api/webhook', (req, res) => {
  const signature = req.headers['x-webhook-signature'];
  const expected = computeHmac(req.body, SECRET);
  if (signature !== expected) {
    return res.status(401).json({ error: 'Invalid signature' });
  }
  processWebhook(req.body);
  res.json({ ok: true });
});
Secure Code
const crypto = require('crypto');
app.post('/api/webhook', (req, res) => {
  const signature = req.headers['x-webhook-signature'];
  const expected = computeHmac(req.body, SECRET);
  const sigBuf = Buffer.from(signature, 'hex');
  const expBuf = Buffer.from(expected, 'hex');
  if (sigBuf.length !== expBuf.length ||
      !crypto.timingSafeEqual(sigBuf, expBuf)) {
    return res.status(401).json({ error: 'Invalid signature' });
  }
  processWebhook(req.body);
  res.json({ ok: true });
});

Real-World Example

In 2014, researchers demonstrated practical timing attacks against OAuth HMAC implementations in multiple web frameworks. By sending thousands of requests and statistically analyzing response times, they recovered HMAC secrets used to verify API signatures, enabling full API access without valid credentials.

How to Prevent It

  • Use crypto.timingSafeEqual() for all secret comparisons in Node.js
  • Always compare buffers of equal length to avoid leaking length information
  • Use HMAC-based verification libraries that handle constant-time comparison internally
  • Add random response delays for authentication failures to further obscure timing

Affected Technologies

Node.jsPythonJavaGoC#

Data Hogo detects this vulnerability automatically.

Scan Your Repo Free

Related Vulnerabilities