Safe Penetration Testing Labs · intermediate · ~15 min

Extract the local name from a BLE advertisement

Walk a Bluetooth Low Energy advertisement payload and pull out the Complete Local Name field.

Overview

Walk TLVs with strict bounds checks; on type 0x09/0x08, bounded-copy the value.

Why it matters

TLV walking is a foundational pattern. Get it right once and every other TLV protocol falls out.

Lesson

Why this matters

A BLE advertisement is a stream of TLVs (length / type / value). Every BLE sniffer parses them; we're going to parse one too — just the Local Name field, type 0x09 (Complete) or 0x08 (Shortened).

This is the same shape of code you'd write to walk an EXTHDR option list, a DHCP option list, or any TLV-encoded record.

What the bytes look like

[len1] [type1] [val1...] [len2] [type2] [val2...] ...

len is the number of bytes in type + value, so the next record starts at offset + len + 1.

Your job

Implement int extract_local_name(const uint8_t *adv, size_t n, char *out, size_t cap). Walk the TLVs. When you hit type 0x09 or 0x08, copy the value bytes into out (bounded by cap), NUL-terminate, and return the byte count written.

Return -1 if:

  • Any input is NULL, or cap == 0
  • A length would walk past n
  • The name would overflow cap
  • No name field is found

Common mistakes

  • Forgetting the length-byte itself is not counted in len. The next record is at offset + len + 1.
  • Allowing a len == 0 record to spin the loop forever.
  • Reading the value before bounds-checking the length.

What this is NOT

  • A full BLE GAP parser. Other fields (Flags, Service UUIDs, manuf data) are out of scope.
  • A scanner. We read a static payload from the harness.

Summary

Loop with offset + len + 1. Bounds-check before every read. Bail on len == 0 or out-of-range.

Practice with these exercises