— Samy Kamkar, DEF CON 23 (2015)">
Classroom Glossary Public page

WIR-101 Week 10 — Rolling Codes, Replay Attacks, and Sub-GHz Protocol Security

1,256 words

"The rolling code prevents simple replay. The Rolljam exploit prevents rolling codes from preventing anything." — Samy Kamkar, DEF CON 23 (2015)


Lecture (50 min)

10.1 Why Rolling Codes Exist

Before rolling codes (1990s), RF remotes used fixed codes. The attack was trivially simple:

  1. Point an RTL-SDR at a target garage, capture the transmission when the owner leaves
  2. Replay the captured signal when the owner is away
  3. Garage door opens

A fixed-code remote with a 12-bit code space has 4,096 possible codes. An attacker can enumerate all of them in seconds with a replay device -- the code grabber attack.

Rolling codes (also called hopping codes) were introduced to defeat replay. The remote and the receiver share a secret seed and a synchronized PRNG. Each press generates the next code in the sequence. The receiver accepts a code only if it matches one of the next N expected codes in the sequence (the "synchronization window," typically N=256 to handle missed presses).

10.2 The Rolling Code Mechanism

The three dominant rolling-code schemes in consumer hardware:

KeeLoq (1980s-2000s): proprietary 64-bit block cipher developed by Microchip. The key is derived from the manufacturer key and the serial number. KeeLoq was fully broken in 2007 by Bogdanov et al. using slide attacks; the manufacturer key can be recovered from a single device with a few hours of hardware computation. Still used in older systems.

AUT64 / HCS-series (Microchip HCS300/301/320/360/361/410): commercial automotive and garage door standard. 66-bit rolling code with 32-bit counter + 32-bit discriminator. The counter increments with each press; the receiver accepts codes within a synchronization window. The seed is factory-programmed at manufacture.

Rolling-Code-64 / Generic PRNG designs: many consumer devices use a simple 32-bit LFSR or LCG as the PRNG. If the polynomial or multiplier is known (or derivable from two consecutive captures), the full future sequence is predictable.

10.3 The Rolljam Attack (Kamkar, 2015)

Samy Kamkar demonstrated at DEF CON 23 that rolling codes can be defeated without brute force or cryptanalytic attacks, using a purely physical-layer attack:

Setup: a Rolljam device contains two transceivers:

  • Jammer: transmits RF noise in the same band as the target, preventing the garage door receiver from receiving the owner's remote
  • Receiver: simultaneously records the owner's transmission (despite the jamming -- it uses a directional antenna and spatial separation to receive the remote's signal while the jammer is on)

Attack sequence:

  1. Owner presses remote (Code 1). Jammer prevents Code 1 from reaching the receiver. Rolljam records Code 1.
  2. Owner presses remote again (Code 2). Jammer prevents Code 2 from reaching the receiver. Rolljam records Code 2 and immediately replays Code 1 (Code 1 is still valid because the receiver hasn't seen it).
  3. Garage door opens (from Code 1 replay). Owner is satisfied. Rolljam retains Code 2.
  4. Later, attacker replays Code 2. Garage door opens.

Why it works: the synchronization window. The receiver accepts codes within N steps ahead of its current expected code. Code 2 is one step ahead of Code 1 from the receiver's perspective, so it remains valid.

The defense problem: there is no strong defense against Rolljam short of:

  • Ultra-wideband (UWB) ranging + challenge-response (as in newer BMW/Tesla key systems post-2020)
  • Requiring the remote to be in physical proximity (RF ranging at sub-1m accuracy)
  • Abandoning rolling codes for mutual-authentication protocols (as in modern TPMS v2 and PKES systems)

10.4 URH Signal Analysis Workflow

Universal Radio Hacker (URH) provides a graphical pipeline for reverse engineering proprietary RF protocols:

Stage 1 — Signal view: load IQ file, view amplitude envelope, demodulate (AM/FM/PSK autodetect or manual).

Stage 2 — Analysis: identify bit boundaries (symbol rate), threshold, decode to bit sequence.

Stage 3 — Protocol view: split bit sequence into frames, auto-detect preamble, identify repeating fields (which bits are constant = device ID; which change = rolling counter).

For the rolling-code demo device, after recording 5 transmissions you should see:

  • Fixed preamble: same in all frames (used for clock sync and frame start detection)
  • Fixed serial: the device's permanent identifier (8-16 bits, constant across all frames)
  • Incrementing counter: a field that increases by 1 with each transmission

If you can identify the counter field and observe it incrementing, you have confirmed the mechanism and can explain why replay fails.

10.5 Seed Recovery and Full Sequence Prediction

If the rolling code uses a weak PRNG (LFSR or LCG), two consecutive captured codes may be enough to recover the seed.

LFSR recovery: given two consecutive 32-bit output words of a maximal-length LFSR, the polynomial can be recovered using the Berlekamp-Massey algorithm (O(n^2) time, n = register length).

LCG recovery: a 32-bit LCG x_{n+1} = ax_n + c (mod 2^32) has knowable constants (many commercial LCGs use documented multipliers). Given two consecutive outputs, the relationship x2 = ax1 + c (mod 2^32) allows recovery of a and c if outputs are known.

With the seed and algorithm recovered, all future codes are predictable. An attacker with a single Rolljam recording session and LFSR knowledge can compute Code 3, Code 4, ... Code 1000 without additional proximity.

This is why the seed is a secret in well-designed systems: even if the algorithm is known, without the seed the attacker cannot predict the sequence.

10.6 Sub-GHz Protocol Security Summary

Attack Prerequisite Defenses
Fixed-code replay Single capture Rolling codes
Code grabber (brute force) Physical proximity, time Rolling codes, rate limiting
KeeLoq cryptanalysis Hardware access + compute AES-based key derivation
Rolljam Proximity during press UWB proximity verification, challenge-response
Seed recovery (LFSR/LCG) Two consecutive captures CSPRNG (AES-CTR), hardware RNG seed
PRNG exhaustion Many captures Large counter space (48-bit+)

Lab Preview

Lab 10 focuses on BLE sniffing and GATT enumeration (see Lab 10 file). Rolling-code analysis is embedded in Lab 9 Exercise C and is examined in the capstone.


Homework

Reading (45 min): Read the Samy Kamkar Rolljam project page (rolljam.website -- linked from course portal) and the associated DEF CON 23 slides. Then read CVE-2019-9433 (Tesla key fob rolling code vulnerability, 2019).

Hands-on (60 min): Implement an LFSR-based rolling code emitter in Python:

import numpy as np

def lfsr(seed, poly, length=32):
    state = seed
    for _ in range(100):
        out = state & 1
        feedback = bin(state & poly).count('1') % 2
        state = (state >> 1) | (feedback << (length-1))
        yield state

# Generate 10 consecutive codes from seed 0xDEADBEEF
codes = list(lfsr(0xDEADBEEF, 0xB8000000))
print([hex(c) for c in codes[:10]])

Given codes[0] and codes[1], recover poly using Berlekamp-Massey (research the algorithm; a reference Python implementation is linked from the course portal). Verify you can predict codes[2] through codes[9].


Toolchain Diary Entry

Deepen this week: URH (Universal Radio Hacker) -- Protocol Analysis stage

URH Protocol view workflow:

  1. File → Load recording → set sample rate + center frequency
  2. Analysis tab → autodetect or set: modulation, bit length (samples/symbol), error tolerance
  3. Protocol → create message type → set field names (preamble, serial, counter, CRC)
  4. Export bit sequences for external analysis

URH Decoder plugin: supports Manchester, NRZ-L, NRZ-I, Differential Manchester, and custom decoding tables. Most sub-GHz consumer remotes use NRZ-L or Manchester.


Key Terms

  • Rolling code: RF remote security scheme where each transmission uses a unique code from a PRNG sequence; prevents simple replay
  • KeeLoq: Microchip proprietary 64-bit block cipher used in rolling-code systems; fully broken cryptanalytically in 2007
  • LFSR: Linear Feedback Shift Register; simple PRNG; predictable once two consecutive outputs are known via Berlekamp-Massey
  • Rolljam: Samy Kamkar's 2015 physical-layer attack; jams + records Code N while owner presses, replays Code N to satisfy receiver, retains Code N+1 for later use
  • Synchronization window: range of future PRNG states an RF receiver accepts to handle missed presses; typically 256 steps; enables the Rolljam attack
  • CSPRNG: Cryptographically Secure Pseudo-Random Number Generator (e.g., AES-CTR with hardware-generated seed); resistant to prediction from observed outputs; the correct defense for rolling code systems