Read and Parse KLV Metadata from MPEG-TS with FFmpeg

This article provides a practical guide on how to extract, read, and parse Key-Length-Value (KLV) metadata embedded within MPEG-TS (MPEG Transport Stream) files using FFmpeg and FFprobe. You will learn how to identify KLV telemetry streams, extract the raw binary metadata payload, and inspect the packet data directly from the command line.

Step 1: Identify the KLV Metadata Stream

Before extracting KLV data (often used for MISB drone telemetry in military and civilian aerospace applications), you must identify which stream inside the MPEG-TS file contains the metadata.

Run the following ffprobe command to inspect the streams:

ffprobe -i input.ts

In the output, look for a stream labeled with Data or klva (KLV Asynchronous) or klvs (KLV Synchronous). It will look similar to this:

Stream #0:2[0x1f1]: Data: bin_data (klva / 0x61766c6b)

In this example, the metadata is on stream index 0:2 (data stream).

Step 2: Extract Raw KLV Metadata to a File

Once you know the stream index, you can use ffmpeg to extract the raw KLV binary payload without re-encoding the video or audio.

Use the following command to map the data stream and output it as a raw binary file:

ffmpeg -i input.ts -map 0:d -c copy -f data output.klv

Step 3: Inspect KLV Packets Using FFprobe

If you want to view the raw hex representation of the KLV packets directly in the terminal without exporting a file, you can use ffprobe to dump the packet payloads.

Run this command:

ffprobe -v error -select_streams d -show_packets -show_data input.ts

The output will display packets containing the 16-byte Universal Label (Key), the length field, and the value payload:

[PACKET]
codec_type=data
stream_index=2
pts=85700
dts=85700
duration=3600
size=127
data=
00000000  06 0e 2b 34 02 0b 01 01  0e 01 03 01 01 00 00 00  ..+4............
00000010  51 81 80 02 01 01 02 08  00 04 60 50 58 74 e7 c0  Q.........`PXt..
...
[/PACKET]

Step 4: Understanding and Parsing the KLV Structure

The extracted .klv file or hex payload follows the SMPTE ST 336 standard. To parse this binary data into human-readable metrics (such as latitude, longitude, and altitude), you must decode the three elements of the KLV structure:

  1. Key (Universal Label): A 16-byte unique identifier that defines what the data is (e.g., the MISB ST 0601 UAS Local Metadata Set key: 06 0E 2B 34 02 0B 01 01 0E 01 03 01 01 00 00 00).
  2. Length: A variable-length field (often BER-encoded) indicating the size of the value payload in bytes.
  3. Value: The actual telemetry data payload, which is parsed based on the specific standard identified by the Key.

Because FFmpeg does not natively decode the internal telemetry fields of MISB/KLV standards into text, you must pass the extracted raw output.klv file to a dedicated KLV parser library (such as Python’s klvdata package or custom C/C++ parsers) to map the binary values to real-world coordinates and sensor headings.