C Mastery / Sanitizers: ASan, UBSan, TSan, MSan
Part 6 — Debugging and Optimization

Sanitizers: ASan, UBSan, TSan, MSan

This chapter covers the four major sanitizers: AddressSanitizer, Undefined Behavior Sanitizer, ThreadSanitizer, and MemorySanitizer. They instrument your code to catch bugs at run time that would otherwise be invisible.

Why This Matters

Sanitizers turn silent memory corruption and undefined behavior into clear, actionable reports. They are the single most effective way to find the bugs that "only happen sometimes" or "only in release."

Prerequisites

Core Concept

A sanitizer instruments the program (via compiler flags) to add runtime checks or tracking. When a violation is detected, it prints a report and aborts.

SanitizerDetectsFlag
ASanbuffer overflow, use-after-free, double free, leaks (with -fsanitize=address)-fsanitize=address
UBSansigned overflow, invalid shift, misaligned access, etc.-fsanitize=undefined
TSandata races-fsanitize=thread
MSanuninitialized memory reads-fsanitize=memory (Clang)

Examples

ASan

cc -g -fsanitize=address main.c -o app
./app

A heap overflow produces a report with the offending access, the allocation site, and a stack trace.

UBSan

cc -g -fsanitize=undefined main.c -o app
./app

Signed overflow produces: runtime error: signed integer overflow: ....

TSan

cc -g -fsanitize=thread -pthread main.c -o app
./app

A data race produces a report showing the two conflicting accesses.

How It Works

ASan uses shadow memory: it maps every 8 bytes of application memory to a shadow byte describing its state (addressable/poisoned). Instrumented loads/ stores check the shadow. UBSan inserts checks at operations that can be UB. TSan tracks happens-before relations and detects conflicting accesses. MSan tracks which memory is initialized.

Variations

Combining sanitizers

ASan and UBSan combine well (-fsanitize=address,undefined). TSan is generally not combined with ASan (different runtimes).

LeakSanitizer

ASan includes leak detection (or use -fsanitize=leak).

Common Mistakes

bugs).

Undefined Behavior

build still aborts on the first violation.

Portability

primarily Clang (TSan also on GCC Linux). MSVC has /fsanitize=address.

Under the Hood

ASan's shadow-memory model is the classic design. UBSan emits a branch check before each risky operation. TSan maintains a shadow of memory access metadata and a happens-before graph. MSan tracks definedness bit-by-bit.

Practical Usage

Exercises

1. Write a program with a heap buffer overflow and run it under ASan. 2. Write a program with signed overflow and run it under UBSan. 3. Write a program with a data race and run it under TSan. 4. (Clang) Write a program reading uninitialized memory and run it under MSan.

Deep Challenge

Explain how ASan's shadow memory detects a use-after-free: what happens to the shadow bytes at free, and why the subsequent access traps. Then discuss the overhead and limitations.

References

Verification

verified.`

Progress

Concept checkboxes

Mastery levels

ConceptCurrent level (0–8)Target level
c.debug.asan06
c.debug.ubsan06
c.debug.tsan05
c.debug.msan05