Core UDS Services
Module 3 of 5 · 3 lessons · ~75 min · ← Back to Learning Hub
Lesson 1: SID 0x10 — Diagnostic Session Control
Purpose
Controls which diagnostic session the ECU operates in. Different sessions enable different levels of diagnostic access and functionality. Every diagnostic sequence begins here.
Session Types
0x01 — Default Session
- Normal vehicle operation mode
- Limited diagnostics: read DTCs, read basic data
- No security access required
- Active at vehicle power-up
0x02 — Programming Session
- ECU software updates and calibration data writing
- Enables memory write and flash download (SID 0x34/0x36)
- Typically requires security access (SID 0x27) first
- Not available during normal driving (conditionsNotCorrect)
0x03 — Extended Diagnostic Session
- Full diagnostic access: all read/write operations, routine control, actuator tests
- Requires Tester Present (0x3E) to maintain
- Most common session for dealer diagnostics
0x04 — Safety System Diagnostic Session
- Safety-critical ECU access (airbags, ABS, ESC)
- Manufacturer-specific availability
Request and Response Format
Diagnostic Session Control requests are two-byte frames specifying the target session. The positive response echos the session and returns the active server response timings (P2 and P2*). Select a session and click any byte below to inspect its protocol field definition:
Tap any byte to inspect its field definition.
| Operation | Request | Response |
|---|---|---|
Enter Extended Session | ||
Return to Default | ||
Enter Programming |
Session State Machine
The ECU operates as a finite state machine where each session enforces distinct privilege boundaries. Review the state nodes and valid transitions below:
0x01Power-on default. No security required.
0x02Flash reprogramming; requires SecurityAccess.
0x03Advanced diagnostics. Most common non-default.
0x04ASIL-rated system isolation.
- Default → Programming
10 02 - Default → Extended
10 03 - Default → Safety
10 04 - Extended → Programming
10 02 - Any non-default → Default
10 01 / S3 timeout - Safety → Extended
10 030x22 - Programming → Programming
10 020x22 - Safety → Any other
10 xx0x22
Any non-default session automatically reverts to Default Session (0x01) if the S3 inactivity timer expires (S3 = 5000 ms).
Negative Response Codes
| NRC | Trigger |
|---|---|
Sub-function not supported (session type unknown) | |
conditionsNotCorrect — e.g. requesting Programming session while driving | |
serviceNotSupportedInActiveSession |
Common Use Cases
- Dealer Diagnostics: → enter Extended → perform diagnostics → return to Default
- ECU Reprogramming: → enter Programming → Security Access → erase → flash → checksum → reset
- End of Diagnostics: Always return to Default when complete
Best Practices
- Always return to Default Session () when diagnostics are complete
- Monitor S3 timeout — send Tester Present () if operation takes longer than 2–3 seconds
- Check the P2/P2* values in the session response to set your client timeouts correctly
Lesson 2: SID 0x27 — Security Access
Purpose
Implements challenge-response authentication to prevent unauthorized access to protected ECU operations. Required before flash programming, critical calibration writes, or access to sensitive vehicle data.
Why Security Matters
Without Security Access, any tool connected to the OBD-II port could reprogram an ECU or disable safety systems. The seed-key mechanism ensures only authorized tools with the correct algorithm can unlock protected operations.
Authentication Flow
Security access follows a strict challenge-response sequence. The tester requests a pseudo-random seed from the ECU, calculates a secret response key using the proprietary manufacturer algorithm, and returns the key to unlock the privileged security level:
Security Levels
Odd sub-functions request a seed; the matching even sub-function sends the key:
| Seed Request | Key Send | Typical Use |
|---|---|---|
Level 1 — extended diagnostics | ||
Level 2 — ECU reprogramming | ||
Level 3 — calibration/supplier |
Already Unlocked
If the ECU is already unlocked at the requested level, it returns a seed of all zeros. In this case, send a confirmation key of all zeros to maintain the unlocked security state:
Seed-Key Algorithms
The algorithm is manufacturer-specific and kept confidential. Common approaches:
- XOR with a proprietary constant (simple, less secure)
- CRC32-based transformation
- AES encryption using a hardware-stored secret key
- Combination of seed + VIN + ECU serial number
Example for learning only (never use in production):
function calculateKey(seed) {
// Simple XOR — DO NOT USE IN REAL IMPLEMENTATIONS
return seed ^ 0x12345678;
}Anti-Brute-Force Protections
- Failed attempts increment a counter
- After N failures (typically 2–5), NRC (exceededNumberOfAttempts) is returned
- After that, NRC (requiredTimeDelayNotExpired) blocks further attempts
- The delay period is typically 10 seconds to several minutes
- Some ECUs require a power cycle to reset the counter
Negative Response Codes
| NRC | Meaning | Resolution |
|---|---|---|
conditionsNotCorrect | Must be in Extended/Programming session first | |
requestSequenceError | You sent key without requesting seed first | |
invalidKey | Key calculation is wrong — check algorithm | |
exceededNumberOfAttempts | Too many failures — trigger delay | |
requiredTimeDelayNotExpired | Wait the full delay before retrying |
Best Practices
- Always request seed before sending key — never skip
- Protect seed-key algorithms as trade secrets
- Limit retry attempts in your client to avoid triggering ECU lockout
- Log all security access events for audit trails
- Security unlock persists for the active diagnostic session only
Lesson 3: SID 0x19 — Read DTC Information
Purpose
Retrieves Diagnostic Trouble Codes (DTCs) and their associated data from ECU memory. This is the primary service for fault diagnosis — you’ll use it in nearly every diagnostic session.
DTC Format
A standard UDS DTC (Diagnostic Trouble Code) is encoded across exactly 3 bytes: [High Byte] (system prefix + top nibble), [Middle Byte] (fault core), and [Low Byte / FTB] (fault subtype). Use the interactive encoder/decoder below to inspect how alphanumeric trouble codes map to physical hex frames:
Engine, transmission, fuel system
DTC Category Prefixes (from high byte):
| Range | Category | Description |
|---|---|---|
0x00–0x3F | P (Powertrain) | Engine, transmission, fuel system |
0x40–0x7F | C (Chassis) | ABS, steering, suspension |
0x80–0xBF | B (Body) | Airbags, windows, lighting |
0xC0–0xFF | U (Network) | CAN bus, gateway, ECU communication |
DTC Status Byte
Every DTC stored in ECU non-volatile memory is paired with an 8-bit status byte tracking its lifecycle from initial transient detection to confirmed fault memory storage. Toggle individual bits or select presets below to inspect live mask calculations:
All flags clear — no fault history detected.
Sub-Functions
0x01 — reportNumberOfDTCByStatusMask
Count DTCs matching a status mask (does not return DTC values, just count):
0x01 specifies the ISO 14229-1 DTC format (standard 3-byte DTC representation).
Two-byte big-endian unsigned integer representing 5 total DTCs currently matching the requested mask.
0x02 — reportDTCByStatusMask
List all DTCs matching the mask:
Filters ECU memory to return only confirmed faults (Bit 3: confirmedDTC).
Each fault entry consists of exactly 4 bytes: 3-byte DTC number + 1-byte current status mask.
0x04 — reportDTCSnapshotRecordByDTCNumber
Get freeze frame data captured when the DTC was set:
Requesting 0xFF commands the ECU to return all stored snapshot records for the target DTC.
Indicates the number of Data Identifiers stored in the snapshot record, followed by the DID values.
0x06 — reportDTCExtDataRecordByDTCNumber
Get extended counters, aging data, and healing progress:
Manufacturer-specific payload: occurrence counter (0x03 = failed 3 times) and aging counter (0x0A = 10 clean drive cycles remaining).
0x0A — reportSupportedDTCs
List all DTCs the ECU is capable of detecting:
Sub-function 0x0A does not require a status mask parameter in the request payload.
Returns every 3-byte DTC the ECU software can detect, each followed by its current status byte (often 0x00 if not failing).
Status Mask Reference
| Mask | Use Case |
|---|---|
Currently failing tests | |
Pending DTCs | |
Confirmed DTCs | |
Confirmed or currently failing | |
Warning lamp active | |
All DTCs regardless of status |
Negative Response Codes
| NRC | Trigger |
|---|---|
Sub-function not supported | |
requestOutOfRange — invalid DTC or record number |
Key Takeaways
- DTC = 3 bytes; status byte = 8 flags describing the fault’s lifecycle
- Sub-function with mask is the most common: “read confirmed DTCs”
- Sub-function shows what the ECU can detect (all possible DTCs)
- Freeze frames () capture the exact conditions when a fault was first logged
- Use status mask to see all DTCs in any state
Next Steps
Continue to Practical Testing to see how these services work together in a real DTC diagnosis workflow.