Skip to content

gatt_find_info_rsp integer underflow

Moderate
ceolin published GHSA-gmfv-4vfh-2mh8 Mar 29, 2024

Package

zephyr (zephyr)

Affected versions

<= 3.6

Patched versions

None

Description

Summary

The function gatt_find_info_rsp in subsys/bluetooth/host/gatt.c does not process the gatt packet
properly when parsing data.
An malicious BLE device can crash BLE victim device by sending malformed gatt packet.

static void gatt_find_info_rsp(struct bt_conn *conn, uint8_t err,
			       const void *pdu, uint16_t length,
			       void *user_data)
{
	const struct bt_att_find_info_rsp *rsp = pdu;
	struct bt_gatt_discover_params *params = user_data;
	uint16_t handle = 0U;
	uint16_t len;
	union {
		const struct bt_att_info_16 *i16;
		const struct bt_att_info_128 *i128;
	} info;
	union {
		struct bt_uuid uuid;
		struct bt_uuid_16 u16;
		struct bt_uuid_128 u128;
	} u;
	int i;
	bool skip = false;
	...
	// (1) - Integer underflow occurs when length is 0
	length--;
	/* Check if there is a least one descriptor in the response */
	if (length < len) {
		goto done;
	}
	/* Parse descriptors found */
	for (i = length / len, pdu = rsp->info; i != 0;
	     i--, pdu = (const uint8_t *)pdu + len) {
		struct bt_gatt_attr attr;
		// (2) - pdu could be an invalid pointer
		info.i16 = pdu;handle = sys_le16_to_cpu(info.i16->handle);
		if (skip) {
			skip = false;
			continue;
		}
		switch (u.uuid.type) {
		case BT_UUID_TYPE_16:
			// (3) - Accessing invalid point will result in a crash
			u.u16.val = sys_le16_to_cpu(info.i16->uuid);
			break;
		case BT_UUID_TYPE_128:
			memcpy(u.u128.val, info.i128->uuid, 16);
			break;
		}
		...
	}
	...
}
  • (1) - Integer underflow occurs when length is 0. Since the forth argument which is length of this function may be 0, length-- could lead to integer underflow (0xffff).
  • (2) - pdu could be an invalid pointer. In the for loop, the number of iterations is determined by length / len . In each iteration, pdu will be assigned to (const uint8_t *)pdu + len . Due to (1), pdu could be assigned to an invalid pointer that is outside the boundary of pdu.
  • (3) - Accessing invalid point will result in a crash. In (2), pdu is assigned to an invalid pointer, so attempting to access info.i16->handle will result in a crash.

Functions Susceptible to Vulnerabilities:
In subsys/bluetooth/host/gatt.c, parse_include, parse_characteristic , parse_read_std_char_desc, parse_service and parse_read_by_uuid have same same vulnerable pattern. These functions could also be vulnerable.

Patches

main: #69396

For more information

If you have any questions or comments about this advisory:

embargo: 2024-03-10

Credits

Reported by Wei Che Kao (Xiaobye), graduate student from National Yang Ming Chiao Tung University, Dept.
of CS, Security and Systems Lab.

Severity

Moderate

CVSS overall score

This score calculates overall vulnerability severity from 0 to 10 and is based on the Common Vulnerability Scoring System (CVSS).
/ 10

CVSS v3 base metrics

Attack vector
Adjacent
Attack complexity
Low
Privileges required
Low
User interaction
None
Scope
Unchanged
Confidentiality
Low
Integrity
Low
Availability
High

CVSS v3 base metrics

Attack vector: More severe the more the remote (logically and physically) an attacker can be in order to exploit the vulnerability.
Attack complexity: More severe for the least complex attacks.
Privileges required: More severe if no privileges are required.
User interaction: More severe when no user interaction is required.
Scope: More severe when a scope change occurs, e.g. one vulnerable component impacts resources in components beyond its security scope.
Confidentiality: More severe when loss of data confidentiality is highest, measuring the level of data access available to an unauthorized user.
Integrity: More severe when loss of data integrity is the highest, measuring the consequence of data modification possible by an unauthorized user.
Availability: More severe when the loss of impacted component availability is highest.
CVSS:3.1/AV:A/AC:L/PR:L/UI:N/S:U/C:L/I:L/A:H

CVE ID

CVE-2024-3077

Credits