Low watch CVSS 6.5 chrome Type Confusion 📄 Reporter bug report 🔧 Commit mapped

Overview

Low
Severity
6.5
CVSS
No
Exploited ITW
Fixed
Fix Status
ImpactType Confusion in Bluetooth
DescriptionType Confusion in Bluetooth
ComponentBluetooth
Sub-componentBluetooth
Bug ClassType Confusion
Action tierwatch — corruption primitive but gated (uncommon) — not default-reachable
Computed by PatchGap's deterministic exploitability ruler from the fixing commit. patch-now = RCE-class & attacker-reachable in a default config, or exploited in the wild; watch = real security signal below that bar; noise = no security relevance.
Tracker513775483
Fix commit064b1ed634c2 (chromium/src) +3/-0
CWECWE-843 (Type confusion)
CVSS vectorCVSS:3.1/AV:A/AC:L/PR:N/UI:N/S:U/C:H/I:N/A:N
CISA KEVNot listed
CreditedGoogle
Reported2026-05-16 (per vendor advisory)
Fix landed2026-05-20 (public git)
Disclosed2026-06-30
Patch gap41 days — fix public in source before the advisory

Background

`SDP_ELEMENT_DATA`
a Windows Bluetooth SDP structure that is a tagged union carrying an SDP_TYPE type discriminant alongside a data union whose active member depends on that type.
`SDP_TYPE_SEQUENCE`
the SDP_TYPE value indicating the element is a container sequence, meaning the data.sequence union member (value pointer and length) is the valid interpretation.
`BluetoothSdpGetContainerElementData`
a Windows API that walks the child elements of an SDP container, taking the sequence’s value buffer and length as input.
Type confusion
a class of bug where memory belonging to one union variant is interpreted as another, so raw bytes are misread as an unrelated pointer/length pair.

Root Cause Analysis

The enclosing function (named AdvanceToSdpType in the commit message; the name does not appear in the @@ hunk itself) received an SDP_ELEMENT_DATA value in sequence_data and immediately read sequence_data.data.sequence.value and sequence_data.data.sequence.length to pass into BluetoothSdpGetContainerElementData, without first confirming that sequence_data.type was actually SDP_TYPE_SEQUENCE. Because SDP_ELEMENT_DATA is a tagged union, reading the data.sequence members when the discriminant indicates some other type reinterprets whatever bytes occupy that union (for example an integer, UUID, or string variant) as a buffer pointer and length.

The patch adds an early if (sequence_data.type != SDP_TYPE_SEQUENCE) { return false; } guard that runs before any data.sequence access, so a non-sequence element now cleanly fails instead of being misinterpreted. This tightens the code by enforcing the union’s discriminant invariant prior to dereferencing its members.

Key insight
The single mistake was accessing a tagged-union variant (data.sequence) without checking the discriminant (type); the fix restores the invariant by validating type == SDP_TYPE_SEQUENCE before the union member is ever read.

Attack Path

  1. Deliver crafted SDP data A malicious or malfunctioning remote Bluetooth device advertises a service record whose SDP element tree contains an element that is not a real sequence where the parser expects one.
  2. Reach the unchecked access Chrome’s Windows SDP parsing calls into the enclosing function with an SDP_ELEMENT_DATA whose type is not SDP_TYPE_SEQUENCE, and the pre-patch code proceeds straight to sequence_data.data.sequence.value/.length.
  3. Trigger type confusion The wrong union variant’s bytes are handed to BluetoothSdpGetContainerElementData as a value pointer and length, causing the API to treat attacker-influenced data as a container buffer descriptor.
  4. Memory disclosure or corruption (inferred) Misinterpreting arbitrary union bytes as a pointer/length pair can lead to out-of-bounds reads or further parsing of attacker-controlled memory, but the diff does not demonstrate a concrete primitive.

Impact Assessment

An attacker in Bluetooth range (or a paired/attacker-controlled device) that can supply crafted SDP service records can induce a type confusion in the Bluetooth SDP parsing code on Windows, potentially yielding memory misinterpretation and instability. The vendor advisory rates this low severity and does not report in-the-wild exploitation; NVD scores it CVSS 6.5. Any escalation to a read/write primitive or code execution is (inferred). Preconditions include Bluetooth being active and the victim processing the malicious device’s SDP data.

Changed Functions

FunctionChangeNotes
if
device/bluetooth/bluetooth_service_record_win.cc
modified

Files Changed

  • device/bluetooth/bluetooth_service_record_win.cc

Audit Directions

  • Tagged-union discriminant checks
    Audit every access to SDP_ELEMENT_DATA::data (and similar tagged unions) to confirm the corresponding type/discriminant is validated first before the member is read.
  • External Bluetooth/HID parsing
    Review other Windows Bluetooth API wrappers that consume remotely supplied SDP or descriptor data for pointer/length fields extracted without type verification.
  • Container-walk entry points
    Trace all callers of BluetoothSdpGetContainerElementData and analogous container APIs to ensure the buffer descriptor passed in originates from a verified sequence element.
From 064b1ed634c2e0972ff071e4c740fdfc7f62fd2f Mon Sep 17 00:00:00 2001
From: Matt Reynolds <mattreynolds@google.com>
Date: Wed, 20 May 2026 14:04:05 -0700
Subject: [PATCH] bluetooth: Check union type before SDP_ELEMENT_DATA access

AdvanceToSdpType unsafely accesses an SDP_ELEMENT_DATA object's data
field without first checking its SDP_TYPE. This CL prevents the access
if the type is not SDP_TYPE_SEQUENCE.

Bug: 513775483
Change-Id: I7f0555c497048b73f822127946d6c2e059db097c
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/7861521
Reviewed-by: Alvin Ji <alvinji@chromium.org>
Commit-Queue: Matt Reynolds <mattreynolds@chromium.org>
Cr-Commit-Position: refs/heads/main@{#1633821}
---

diff --git a/device/bluetooth/bluetooth_service_record_win.cc b/device/bluetooth/bluetooth_service_record_win.cc
index 14936214..6761488 100644
--- a/device/bluetooth/bluetooth_service_record_win.cc
+++ b/device/bluetooth/bluetooth_service_record_win.cc
@@ -24,6 +24,9 @@
                       SDP_TYPE type,
                       HBLUETOOTH_CONTAINER_ELEMENT* element,
                       SDP_ELEMENT_DATA* sdp_data) {
+  if (sequence_data.type != SDP_TYPE_SEQUENCE) {
+    return false;
+  }
   while (ERROR_SUCCESS == BluetoothSdpGetContainerElementData(
       sequence_data.data.sequence.value,
       sequence_data.data.sequence.length,
Loading diff…

Original Bug Report

reported by vm...@google.com

Potential Arbitrary Memory Read in Device Service via Bluetooth SDP Type Confusion on Windows

Project Fortify, an experimental security project, has identified the following potential security issue. If you’re a feature owner CC-ed on this bug, please do your best to review these reports. Please see https://chromium.googlesource.com/chromium/src/+/main/docs/security/ai-generated-security-bugs-faq.md for more information.

Overview: A potential type confusion vulnerability in BluetoothServiceRecordWin allows a paired Bluetooth device to trigger an arbitrary memory read in the Chromium Device Service process on Windows. The issue arises from a failure to validate the data type of Service Discovery Protocol (SDP) elements before accessing union-mapped fields, allowing attacker-controlled integers to be misinterpreted as memory addresses.

Affected files:

  • device/bluetooth/bluetooth_service_record_win.cc
  • device/bluetooth/bluetooth_task_manager_win.cc
  • device/bluetooth/bluetooth_device_win.cc
  • services/device/serial/serial_port_manager_impl.cc
  • content/browser/serial/serial_service.cc

Estimated timestamp from git blame: Unknown (Google3 checkout)

Summary

A potential type confusion vulnerability has been identified in the handling of Bluetooth Service Discovery Protocol (SDP) records within the Chromium Device Service on Windows. The vulnerability exists in device/bluetooth/bluetooth_service_record_win.cc, where the code fails to verify the type discriminant of an SDP_ELEMENT_DATA structure before accessing its union members. On 64-bit systems, this leads to union punning where an attacker-controlled integer can be misinterpreted as a memory pointer, potentially leading to an arbitrary memory read or a process crash.

Root Cause Analysis

In device/bluetooth/bluetooth_service_record_win.cc, the constructor for BluetoothServiceRecordWin retrieves SDP attributes using the Windows API BluetoothSdpGetAttributeValue. The resulting SDP_ELEMENT_DATA structure contains a type field and a data union.

// device/bluetooth/bluetooth_service_record_win.cc:148-152
SDP_ELEMENT_DATA uuid_data;
if (ERROR_SUCCESS == BluetoothSdpGetAttributeValue(
                         blob_data, blob_size, kUuidId, &uuid_data)) {
  ExtractUuid(uuid_data, &uuid_);
}

The ExtractUuid function passes this data to AdvanceToSdpType, which immediately accesses the sequence member of the data union without checking if the type is actually SDP_TYPE_SEQUENCE:

// device/bluetooth/bluetooth_service_record_win.cc:23-31
bool AdvanceToSdpType(const SDP_ELEMENT_DATA& sequence_data, ... ) {
  while (ERROR_SUCCESS == BluetoothSdpGetContainerElementData(
      sequence_data.data.sequence.value,
      sequence_data.data.sequence.length,
      element,
      sdp_data)) { ... }
}

On 64-bit Windows, the data.uint128 member (16 bytes) aliases the data.sequence structure, which contains an 8-byte LPBYTE value pointer and a 4-byte ULONG length. If a malicious Bluetooth device provides an SDP attribute encoded as a UINT128, the first 8 bytes of that integer will be reinterpreted as the value pointer in AdvanceToSdpType. This causes BluetoothSdpGetContainerElementData to attempt to parse memory at an arbitrary, attacker-controlled address.

Potential Impact

The Device Service on Windows typically runs as an unsandboxed utility process (kNoSandbox). An arbitrary memory read in this process could allow an attacker to:

  1. Information Leak: Exfiltrate memory contents. If the bytes at the target address can be successfully parsed as an SDP UUID element, the value is stored in the service record and can be read by a malicious webpage via SerialPort.getInfo().bluetoothServiceClassId in the Web Serial API.
  2. Denial of Service: Trigger a crash of the Device Service by providing an invalid or unmapped memory address, affecting all hardware-related functionality in Chrome (Serial, HID, USB, etc.).

Suggested Potential Trigger Steps

  1. An attacker-controlled Bluetooth Classic device is configured to return a UINT128 for SDP attribute ID 1 (ServiceClassIDList).
  2. The attacker-controlled device is paired with a victim’s Windows machine.
  3. The victim visits a site that triggers Bluetooth device enumeration (e.g., via navigator.serial.getPorts()).
  4. Chrome’s Device Service polls the device’s SDP records, triggering the type confusion and subsequent arbitrary memory access.

Suggested Fix

The functions ExtractUuid and ExtractChannels should verify that the type field of the SDP_ELEMENT_DATA returned by BluetoothSdpGetAttributeValue matches the expected type (SDP_TYPE_UUID, SDP_TYPE_SEQUENCE, etc.) before further processing. Additionally, AdvanceToSdpType should include a check to ensure sequence_data.type is a valid container type (e.g., SDP_TYPE_SEQUENCE or SDP_TYPE_ALTERNATIVE) before accessing the data.sequence union member.

Evaluated with Chrome root at commit: 1a8d40fc44df2088d5945c0bf53584038aa1614a


Results so far have been promising, but there can be wrong deductions. Feel free to adjust as follows:

  • If you are familiar with the severity guidelines, you may adjust the severity.
  • If this is a false positive, and there’s no work to be done, please close as WAI.
  • If there is work to do here but not a vulnerability, please change the issue type to Task/Bug/FR.

Data from false positives will be used to improve accuracy over time. And please feel free to reach out to me directly if you have concerns or feedback on the project.

View on issue tracker