All protocols
Data Link / Physical (ISO 11898)

CAN

Controller Area Network — the backbone of in-vehicle communication.

Bitrate
Up to 1 Mbit/s
Topology
Multi-master, twisted-pair bus (CAN_H / CAN_L)
Introduced
1986

Overview

CAN is a robust, message-based serial bus introduced by Bosch. ECUs broadcast frames identified by an arbitration ID; lower IDs win arbitration. CRC, ACK, and bit-stuffing make it extremely reliable for hard real-time control such as engine, transmission and ABS.

Frame format

FieldBitsDescription
SOF1Start of Frame (dominant)
Identifier11 / 29Standard or extended message ID
RTR1Remote transmission request
Control6IDE + reserved + DLC (data length code)
Data0–64Up to 8 bytes of payload
CRC1615-bit CRC + delimiter
ACK2Acknowledge slot + delimiter
EOF7End of Frame (recessive)

All CAN Frame Formats (ISO 11898-1)

Five frame types defined by the CAN protocol. Bit values: 0 = dominant, 1 = recessive.

Standard Data Frame (CAN 2.0A — 11-bit ID)

44 + 8·DLC bits (max 108 bits with 8-byte payload)

Transports application payload using an 11-bit identifier.

FieldBitsValueDescription
SOF10Start Of Frame — dominant bit, marks frame start.
Identifier110x000–0x7FFMessage ID; lower value = higher priority.
RTR10Remote Transmission Request — dominant for data frame.
IDE10Identifier Extension — dominant = standard format.
r010Reserved bit, transmitted as dominant.
DLC40–8Data Length Code — number of payload bytes.
Data0–64payloadApplication payload, 0 to 8 bytes.
CRC15computedCyclic Redundancy Check over preceding fields.
CRC Delimiter11Recessive delimiter bit.
ACK Slot11→0Transmitter sends recessive; receivers pull dominant.
ACK Delimiter11Recessive delimiter bit.
EOF71111111End Of Frame — seven recessive bits.
IFS≥3111Inter-Frame Space — minimum gap before next frame.
Example
0x123 [8] 11 22 33 44 55 66 77 88
ID 0x123, DLC=8, payload 11 22 33 44 55 66 77 88
Logical view as decoded by a CAN controller / candump.

Extended Data Frame (CAN 2.0B — 29-bit ID)

64 + 8·DLC bits (max 128 bits)

Same as standard but with 29-bit identifier (used by SAE J1939, OBD-II 29-bit).

FieldBitsValueDescription
SOF10Start Of Frame.
Base ID (ID-A)11upper 11 bitsMost significant 11 bits of 29-bit identifier.
SRR11Substitute Remote Request — recessive in extended frame.
IDE11Identifier Extension — recessive = extended format.
Extended ID (ID-B)18lower 18 bitsLower 18 bits of 29-bit identifier.
RTR10Remote Transmission Request — dominant for data frame.
r110Reserved bit.
r010Reserved bit.
DLC40–8Data Length Code.
Data0–64payload0 to 8 bytes.
CRC15computedCRC over preceding fields.
CRC Delimiter11Recessive.
ACK Slot11→0Acknowledged by any receiver.
ACK Delimiter11Recessive.
EOF71111111End Of Frame.
IFS≥3111Inter-Frame Space.
Example
0x18FEF100 [8] FF FF FF 68 13 FF FF FF
J1939 PGN 0xFEF1 (Cruise/Vehicle Speed), source 0x00, priority 6
29-bit ID = priority(3) | reserved(1) | DP(1) | PGN(16) | SA(8).

Remote Frame (RTR)

44 bits (standard) / 64 bits (extended)

Requests a data frame with the same identifier from another node. No payload is transmitted.

FieldBitsValueDescription
SOF10Start Of Frame.
Identifier11 or 29target IDID of the data frame being requested.
RTR11RECESSIVE — distinguishes remote from data frame.
IDE10/1Standard (0) or Extended (1) format.
r0 (+r1)1 or 20Reserved bits.
DLC4expected lengthLength of the requested data — no actual payload sent.
Data0No data field in a remote frame.
CRC15computedCRC over the remote frame.
CRC Delimiter11Recessive.
ACK Slot + Delim20,1Acknowledgement.
EOF71111111End Of Frame.
Example
0x200 [4] (RTR=1, no payload)
Request data for ID 0x200, expecting 4 bytes
Rarely used in modern automotive networks; many stacks disable RTR handling.

Error Frame

12–18 bits (variable)

Signals a detected bus error (bit, stuff, CRC, form, or ACK error). Aborts the current frame for all nodes.

FieldBitsValueDescription
Error Flag (active)6000000Six consecutive DOMINANT bits transmitted by an error-active node. Violates bit-stuffing → all nodes detect.
Error Flag (passive)6111111Six consecutive RECESSIVE bits transmitted by an error-passive node.
Error Flag Echo0–6000000Other nodes append their own error flags after detecting the violation (superposition).
Error Delimiter811111111Eight recessive bits marking the end of the error frame.
IFS≥3111Inter-Frame Space before bus returns to normal arbitration.
Example
0x100 → [ERROR FRAME] → retransmit
Bit error during data field of ID 0x100
Transmitter increments TEC by 8; faulty node may transition to error-passive or bus-off.

Note: Error states: Error-Active (TEC<128 & REC<128), Error-Passive (≥128), Bus-Off (TEC≥256). Bus-off requires reset/recovery sequence (128×11 recessive bits).

Overload Frame

14–20 bits

Forces extra delay between data/remote frames when a receiver is not ready or detects illegal IFS bits.

FieldBitsValueDescription
Overload Flag6000000Six dominant bits, similar to active error flag.
Overload Flag Echo0–6000000Other nodes superimpose their own overload flags.
Overload Delimiter811111111Eight recessive bits ending the overload frame.
IFS≥3111Inter-Frame Space resumes normal bus operation.
Example
0x150 [...] → [OVERLOAD FRAME] → next frame delayed
Receiver requests delay after frame 0x150
Maximum two consecutive overload frames allowed per ISO 11898-1.

Note: Triggered by: (a) receiver internal conditions, or (b) detection of dominant bit during IFS / EOF (last bit) / inter-frame gap.

Quick comparison
Frame typeIdentifierPayloadRTRIDEPurpose
Standard Data11-bit0–8 B00Send payload
Extended Data29-bit0–8 B01J1939, OBD 29-bit
Remote11/29-bit10/1Request data
ErrorSignal bus error
OverloadForce extra delay
DLC → payload bytes (Classic CAN vs CAN-FD)
DLC (dec)DLC (hex / 4 bits)Classic CAN bytesCAN-FD bytesNotes
00x000Empty payload (valid; ACK only).
10x111
20x222
30x333
40x444
50x555
60x666
70x777
80x888Maximum payload for Classic CAN.
90x98*12Classic CAN: clamped to 8 bytes (DLC 9–15 transmitted but data length stays 8).
100xA8*16CAN-FD only beyond 8 bytes.
110xB8*20
120xC8*24
130xD8*32
140xE8*48
150xF8*64Maximum payload for CAN-FD.
*Classic CAN (ISO 11898-1:2003): the DLC field is 4 bits (0–15) but the actual data length is min(DLC, 8). Values 9–15 are legal on the wire and some controllers transmit them, but the receiver uses 8 bytes. CAN-FD reinterprets DLC 9–15 as the non-linear lengths {12, 16, 20, 24, 32, 48, 64}.
Payload length edge cases
Info
DLC = 0 (zero-length data field)

Legal frame with no data bytes. Used for handshakes / triggers (e.g., wakeup). CRC is still computed over header + (empty) data.

Watch out
Classic CAN DLC 9–15 (over-DLC)

Receiver MUST clamp data length to 8 bytes. Some legacy controllers (e.g., older SJA1000) transmit DLC=15 but only 8 data bytes; others reject. Test stacks should accept and normalize.

Pitfall
Mismatch between DLC and actual bytes provided by application

If the application supplies fewer bytes than DLC indicates, controllers typically pad with 0x00 (CAN_PAD_DATA), 0xCC, or undefined memory. Always pad explicitly in test scripts.

Watch out
CAN-FD non-contiguous lengths (9–11, 13–15, 17–19, …)

Lengths like 9, 10, 11 bytes are NOT representable. Application must pad up to next valid length: 12, 16, 20, 24, 32, 48, 64. ISO-TP/CAN-TP stacks insert padding bytes (often 0xCC or 0xAA).

Info
ISO-TP single-frame length limits

Classic CAN: SF up to 7 data bytes (1 byte PCI + 7 data). CAN-FD: SF up to 62 bytes via escape PCI (2-byte PCI + up to 62). Beyond → multi-frame (FF/CF).

Watch out
Padding for CAN-FD (CAN_PAD_DATA)

When payload length ∈ {9, 10, 11, 13, 14, 15, 17–19, 21–23, 25–31, 33–47, 49–63}, the stack MUST pad to next valid DLC. Common padding: 0xCC (Vector), 0xAA (some OEMs), 0x00 (default).

Pitfall
Remote frame with non-zero DLC

Remote frames carry DLC = expected response length but transmit ZERO data bytes. Receivers must not interpret any bytes after the DLC/CRC sequence as payload.

Info
Bit stuffing impact on effective payload

After 5 identical consecutive bits, transmitter inserts an opposite stuff bit. Worst case adds ~24% overhead; effective frame length varies, complicating exact bus-load calculation.

CAN Frame Validator

Enter the bit-level fields of a CAN frame; each format is checked against ISO 11898-1 rules.

Summary
Matches 1 format: Standard
Standard Data Frame (CAN 2.0A, 11-bit)Match
  • ID fits 11 bits (≤ 0x7FF)
    0x123 = 9 bits
  • IDE = 0 (standard)
  • RTR = 0 (data frame)
  • DLC 0–15 (data clamped to 8)
    effective length = 8 bytes
  • Data bytes match effective length
    provided 8, expected 8
  • ACK slot = 0 (dominant)
  • CRC present (15-bit)
Extended Data Frame (CAN 2.0B, 29-bit)No match
  • ID fits 29 bits (≤ 0x1FFFFFFF)
    9 bits used
  • IDE = 1 (extended)
  • RTR = 0 (data frame)
  • DLC 0–15 (data clamped to 8)
    effective length = 8 bytes
  • Data bytes match effective length
    provided 8, expected 8
  • ACK slot = 0 (dominant)
  • CRC present (15-bit)
Remote Frame — Standard (RTR, 11-bit)No match
  • ID fits 11 bits
  • IDE = 0 (standard)
  • RTR = 1 (remote)
  • DLC 0–8 (requested length)
  • Data field empty (no payload)
    provided 8 bytes
  • ACK slot = 0 (dominant)
  • CRC present (15-bit)
Remote Frame — Extended (RTR, 29-bit)No match
  • ID fits 29 bits
  • IDE = 1 (extended)
  • RTR = 1 (remote)
  • DLC 0–8 (requested length)
  • Data field empty (no payload)
    provided 8 bytes
  • ACK slot = 0 (dominant)
  • CRC present (15-bit)
Error FrameNo match
  • No identifier (N/A)
    Error frames have no ID/DLC fields — cannot match a user-supplied frame.
Overload FrameNo match
  • No identifier (N/A)
    Overload frames have no ID/DLC fields — cannot match a user-supplied frame.

CAN Test Case Generator

Generates a functional + boundary + negative test matrix for the CAN frame you describe. Adapts to Classic CAN vs CAN-FD and 11-bit vs 29-bit identifiers.

F-001

Happy path — valid data frame

functional
ID: 0x7E0
IDE/RTR: 0/0
DLC: 3
Data: 02 10 03
Expected: 0x7E8 → 02 50 03
Nominal request with valid ID, DLC matches data length.
F-002

Remote frame request

functional
ID: 0x7E0
IDE/RTR: 0/1
DLC: 3
Data:
Expected: Responder transmits data frame with same ID
RTR=1 must carry no payload; DLC indicates requested length.
F-003

Minimum payload (DLC=0)

functional
ID: 0x7E0
IDE/RTR: 0/0
DLC: 0
Data:
Expected: Frame accepted; receiver handles zero-length payload
DLC=0 is legal; commonly used for heartbeats.
B-001

Maximum 11-bit identifier

boundary
ID: 0x7FF
IDE/RTR: 0/0
DLC: 3
Data: 02 10 03
Expected: Frame transmitted, no form/CRC error
Highest legal 11-bit identifier.
B-002

Maximum Classic CAN payload (8 B, DLC=8)

boundary
ID: 0x7E0
IDE/RTR: 0/0
DLC: 8
Data: 00 01 02 03 04 05 06 07
Expected: All bytes received intact
Classic CAN clamps DLC>8 to 8 data bytes.
N-001

ID out of range

negative
ID: 0x800
IDE/RTR: 0/0
DLC: 3
Data: 02 10 03
Expected: Transmitter rejects / driver returns EINVAL
ID exceeds 11-bit limit (0x7FF).
N-002

DLC mismatch — fewer data bytes than DLC claims

negative
ID: 0x7E0
IDE/RTR: 0/0
DLC: 8
Data: 11 22
Expected: Stack rejects malformed frame OR pads with undefined bytes
Detects layer that fails to validate DLC vs payload length.
N-003

RTR with payload (illegal)

negative
ID: 0x7E0
IDE/RTR: 0/1
DLC: 3
Data: 02 10 03
Expected: Frame rejected; RTR frames must not carry data
ISO 11898-1: Remote frames have no data field.
N-004

Bus-off recovery

negative
ID: 0x7E0
IDE/RTR: 0/0
DLC: 3
Data: 02 10 03
Expected: Node enters bus-off after TEC>255, recovers after 128×11 recessive bits
Validate fault-confinement state machine.

CAN Test Script Generator

Emits runnable Python (python-can) and CAPL (Vector CANoe) scripts that send a CAN request, wait for the expected response, and report pass/fail.

test_can_roundtrip.py
"""
Auto-generated CAN test script (python-can)
Request : 0x7E0 -> 02 10 03
Expected: 0x7E8
Bus     : can0 @ 500000 bps  (Classic CAN)
"""
import can
import sys

REQ_ID    = 0x7E0
RESP_ID   = 0x7E8
REQ_DATA  = [0x02, 0x10, 0x03]
EXTENDED  = False
TIMEOUT_S = 1.00

def main() -> int:
    bus = can.interface.Bus(
        channel="can0",
        bustype="socketcan",
        bitrate=500000,
        fd=False,
    )

    msg = can.Message(
        arbitration_id=REQ_ID,
        data=REQ_DATA,
        is_extended_id=EXTENDED,
        is_fd=False,
    )
    print(f"TX  {hex(REQ_ID)} {bytes(REQ_DATA).hex(' ')}")
    bus.send(msg)

    rx = bus.recv(timeout=TIMEOUT_S)
    if rx is None:
        print("FAIL: timeout waiting for response")
        return 1
    print(f"RX  {hex(rx.arbitration_id)} {bytes(rx.data).hex(' ')}")

    if rx.arbitration_id != RESP_ID:
        print(f"FAIL: expected ID {hex(RESP_ID)}, got {hex(rx.arbitration_id)}")
        return 2

    print("PASS")
    return 0

if __name__ == "__main__":
    sys.exit(main())

Byte structure — request & response

Classical CAN — ISO 11898-1

Frame template
[SOF:1b][ID:11b][RTR:1b][IDE:1b][r0:1b][DLC:4b][Data:0–8B][CRC:15b][CRC-Del:1b][ACK:1b][ACK-Del:1b][EOF:7b]
Request
OffSizeFieldValueDescription
011 bitArbitration ID0x123Message identifier (lower = higher priority).
1 bitRTR00 = data frame, 1 = remote request.
4 bitDLC0x8Data length code (0–8).
0…70–8 BData11 22 33 44 55 66 77 88Payload bytes (max 8).
15 bitCRCautoCRC over SOF…Data.
1 bitACK slot0Receivers pull dominant to acknowledge.
Response
OffSizeFieldValueDescription
011 bitArbitration ID0x124Reply uses a different broadcast ID (CAN has no per-message reply concept).
4 bitDLC0x2Number of data bytes.
0…12 BData0F 01Application response payload.
1 bitACK0Other nodes acknowledge bit.

CAN is broadcast: there is no inherent request/response. Higher protocols (UDS, J1939) layer Q/R semantics on top of two CAN IDs (e.g. 0x7E0 → 0x7E8).

Use cases

  • · Powertrain control
  • · Body electronics
  • · ABS / ESP
  • · Instrument cluster

Pros

  • Deterministic arbitration
  • Mature ecosystem
  • Robust error detection

Cons

  • Max 8 bytes payload
  • Bandwidth limited to 1 Mbit/s
  • No native security

Request / Response examples

Engine RPM broadcast (ID 0x0C9)

Request
ID:0x0C9DLC:8Data:14000FA000000000
Response
(broadcastframenoresponse)

Bytes 2–3 (0x0FA0) decode to 4000 RPM using factor 0.25 RPM/bit.

Door lock command (ID 0x3B0)

Request
ID:0x3B0DLC:2Data:010F
Response
StatusframeID0x3B1DLC:1Data:0F

Byte 0 = command (lock all), byte 1 = mask. ECU echoes the new lock state.