Skip to content

julianjc84/TPMS

 
 

Repository files navigation

BLE TPMS - Bluetooth Tire Pressure Monitoring System

Interactive desktop tool to monitor external TPMS sensors via Bluetooth Low Energy.

Features

  • Interactive UI - Menu-driven interface for discovering and monitoring sensors
  • Auto-Detection - Automatically identifies TPMS sensors from all nearby BLE devices
  • Multi-Sensor - Track 4+ sensors simultaneously with friendly names
  • Modular Decoders - Plugin system supports different TPMS sensor types
  • Dual Units - Pressure displayed in both BAR and PSI
  • HEX Packet View - Raw BLE packet data for debugging
  • Color-Coded Display - Status indicators at a glance
  • Saved Configuration - Remembers your sensors between sessions
  • Packet Log - Every TPMS-decodable packet is appended to packet_log.jsonl (timestamp, raw hex, decoded fields) during discovery and monitoring - the long-term dataset behind the protocol reverse-engineering in PROTOCOL.md

Supported Sensors

Decoder Sensor Type Data Size Identification Status
TPMS3-16byte Generic BLE TPMS (VSTM/ZEEPIN/TP630) 16 bytes Name TPMS{N}_*, CID 0x0100 Tested (incl. rapid-drop alarm)
LyTPMS-15byte Nameless "5BC45B"-type (CID 0x00AC) 15 bytes MAC-in-payload match, structure, UUID 0xFBB0 Tested (2 units, pressure calibrated)
BR-7byte Generic "BR" sensors 7 bytes Name "BR", UUID 0x27a5 Reference
SYTPMS-6byte SYTPMS sensors 6 bytes Name "TPMS", 6-byte data Reference
Generic Unknown sensors 4+ bytes Fallback with heuristics Always

Tested with: Generic external BLE TPMS cap sensors (VSTM/Visture, ZEEPIN/TP630, WISTEK, and other rebranded variants widely sold on AliExpress/Amazon)

New sensor types can be added via the modular decoder system. See DECODER_GUIDE.md.

Quick Start

# One-time setup (creates virtual environment, installs dependencies)
./setup.sh

# Run the monitor
./run.sh

Usage

Main Menu

BLE TPMS Monitor - Interactive
================================

Current Configuration:
  Front Left         (AC:15:85:C3:A2:01)
  Rear Left          (82:EA:CA:33:4F:E2)

Options:
  1 - Discover and select sensors
  2 - Start monitoring
  3 - Remove a sensor
  4 - Clear all sensors
  5 - List available decoders
  q - Quit

Workflow

  1. Discover - Scan for nearby BLE devices (option 1)
  2. Select - Choose which sensors to monitor, give them names
  3. Monitor - Start live monitoring (option 2)

Device Discovery

#    MAC Address          Name            RSSI   Decoder          TPMS?
---------------------------------------------------------------------------
1    82:EA:CA:33:4F:E2   TPMS3_334FE2   -45    TPMS3-16byte     TPMS Sensor
2    AC:15:85:C3:A2:01   BR             -48    BR-7byte         BR Sensor
3    AA:BB:CC:DD:EE:FF   Unknown        -72    Unknown

Select sensors by number, or press a to auto-select all detected TPMS devices.

Live Monitoring

Sensor          Decoder        Pressure                Temp    Battery   Note              HEX Packet
------------------------------------------------------------------------------------------------------
Rear Left       TPMS3-16byte   1.82 bar (26.4 psi)     29C     100%      Pos:RL Abs:40.9   82eaca334fe2...
Front Left      BR-7byte       2.15 bar (31.2 psi)     22C     2.9V      ROTAT             281d160105a376

Press Ctrl+C to stop monitoring and return to menu.

Sensor Behavior

TPMS{N} Sensors (most common)

Pressure change is the ONLY wake trigger. Extensive testing confirmed these sensors contain no roll switch, accelerometer, or wake timer - the MEMS pressure interrupt is the sole wake mechanism. Motion, rotation, and vibration have zero effect. (On a driven tire they broadcast anyway, because flexing and thermal drift constantly cross the pressure threshold.)

Sleep / Wake cycle:

  • Deep sleep - No broadcasts. Default state; only a pressure change wakes it
  • On tire (parked) - Occasional wakes as thermal drift crosses the pressure threshold
  • Pressure event - Immediate ~36 s burst at ~4 s intervals

Rapid-drop alarm (byte 15): flips to 0x01 on a fast pressure drop (even ~1 PSI in a moment), clears within one broadcast on pressure recovery, and latches ~40 s if pressure stays low - so a puncture keeps alarming in every packet. Rising pressure never sets it. See PROTOCOL.md for the full dynamics.

Tip: If no sensor is detected, deflate/inflate the tire slightly, or slowly screw the sensor on/off the valve to create air flow. See PROTOCOL.md for full details.

Valve interaction: An internal pin depresses the Schrader valve core when the sensor is screwed on, opening an air path. A twist-lock nut must be engaged for a proper seal. Without engagement, the sensor only reads atmospheric pressure (~0 PSI gauge).

LyTPMS Sensors (nameless, CID 0x00AC)

Broadcast-only like the TPMS{N}, also purely pressure-event driven. Notable protocol features (fully documented in PROTOCOL.md):

  • Trend byte: every packet carries a pressure-trend state - stable, falling, or rising (shown live in the monitor). falling is effectively the deflation alarm; it needs a drop faster than ~0.1-0.3 PSI/s to set and clears within seconds of stability
  • Coarse readings by design: pressure in 0.45 PSI steps, temperature in 1 C
  • Wake burst is ~48 identical frames in ~1.4 s, then new readings every ~2 s while pressure changes, occasional idle reports ~26 s apart, then silence

BR Sensors

  • Rotating: Frequent broadcasts (~10-30s) above 4 km/h
  • Stationary: Every 2-5 minutes
  • Pressure change: Immediate transmission on >0.5 psi change

Requirements

  • Python 3.7+
  • Bluetooth adapter
  • Linux, macOS, or Windows

Dependencies installed automatically by setup.sh:

  • bleak - Cross-platform BLE library (no sudo required)
  • colorama - Colored terminal output

Project Structure

TPMS/
├── tpms-interactive.py    # Main application
├── sensor_decoders.py     # Modular decoder library
├── btsnoop_analyze.py     # Offline analyzer for Android btsnoop HCI captures
├── setup.sh               # One-time setup (venv + dependencies)
├── run.sh                 # Launch the app
├── activate.sh            # Quick venv activation helper
├── requirements.txt       # Python dependencies
├── README.md              # This file
├── PROTOCOL.md            # BLE TPMS protocol documentation
├── DECODER_GUIDE.md       # Guide for adding new sensor types
├── packet_log.jsonl       # Persistent packet capture log (grows as you monitor)
└── BTSnoopLogs/           # Raw Android btsnoop captures used for analysis

Adding New Sensor Types

  1. Create a decoder class in sensor_decoders.py
  2. Implement can_decode() to identify your sensor
  3. Implement decode() to parse the data
  4. Register it in the factory

See DECODER_GUIDE.md for a complete guide with a real-world reverse-engineering case study.

Troubleshooting

No sensors detected

  • Verify Bluetooth is enabled
  • Sensor is likely asleep - these sensors wake on PRESSURE CHANGE, not motion
  • To wake: deflate/inflate the tire briefly, or slowly screw the sensor on/off a valve
  • Rolling or shaking the sensor will NOT wake it
  • Use the interactive discovery (option 1) and keep scanning in 5-second rounds
  • Use a BLE scanner app (e.g., nRF Connect) to verify the sensor is broadcasting
  • Move closer to sensors (<5m)

Sensor reads ~0 PSI gauge on a tire

  • The twist-lock mechanism may not be engaged
  • Sensor must fully depress the Schrader valve core to read tire pressure
  • Without engagement, it correctly reads atmospheric pressure (~14.5 PSI absolute = ~0 gauge)

Setup issues

  • If pip install fails with "externally-managed-environment", use ./setup.sh (uses venv)
  • If python3-venv is missing: sudo apt install python3-venv

References

License

This project is provided as-is for educational and personal use.

About

Decode tire pressure monitoring system TPMS BLE 433MHz CC1101 ESP8266 ESP32

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages

  • Python 95.4%
  • Shell 4.6%