You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mynewt.apache.org by cc...@apache.org on 2016/01/09 01:18:35 UTC
[02/10] incubator-mynewt-larva git commit: Add some sanity checking
for GATT responses.
Add some sanity checking for GATT responses.
Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/commit/54453e47
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/tree/54453e47
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/diff/54453e47
Branch: refs/heads/master
Commit: 54453e47624d7ba15980063909c5effe87f21b6d
Parents: 4305b6e
Author: Christopher Collins <cc...@gmail.com>
Authored: Fri Jan 8 14:02:47 2016 -0800
Committer: Christopher Collins <cc...@gmail.com>
Committed: Fri Jan 8 16:18:04 2016 -0800
----------------------------------------------------------------------
net/nimble/host/src/ble_gattc.c | 102 ++++++++++++++++++++++++++++-------
1 file changed, 83 insertions(+), 19 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/54453e47/net/nimble/host/src/ble_gattc.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_gattc.c b/net/nimble/host/src/ble_gattc.c
index 26b934c..90b0845 100644
--- a/net/nimble/host/src/ble_gattc.c
+++ b/net/nimble/host/src/ble_gattc.c
@@ -750,6 +750,12 @@ ble_gattc_rx_read_group_type_entry(struct ble_hs_conn *conn,
goto done;
}
+ if (adata->end_group_handle <= entry->disc_all_svcs.prev_handle) {
+ /* Peer sent services out of order; terminate procedure. */
+ rc = BLE_HS_EBADDATA;
+ goto done;
+ }
+
entry->disc_all_svcs.prev_handle = adata->end_group_handle;
service.start_handle = adata->att_handle;
@@ -878,6 +884,7 @@ ble_gattc_rx_find_type_value_hinfo(struct ble_hs_conn *conn,
struct ble_gatt_service service;
struct ble_gattc_entry *entry;
struct ble_gattc_entry *prev;
+ int cbrc;
int rc;
entry = ble_gattc_find(conn->bhc_handle, BLE_GATT_OP_DISC_SVC_UUID, 1,
@@ -887,14 +894,23 @@ ble_gattc_rx_find_type_value_hinfo(struct ble_hs_conn *conn,
return;
}
+ if (hinfo->group_end_handle <= entry->disc_svc_uuid.prev_handle) {
+ /* Peer sent services out of order; terminate procedure. */
+ rc = BLE_HS_EBADDATA;
+ goto done;
+ }
+
entry->disc_svc_uuid.prev_handle = hinfo->group_end_handle;
service.start_handle = hinfo->attr_handle;
service.end_handle = hinfo->group_end_handle;
memcpy(service.uuid128, entry->disc_svc_uuid.service_uuid, 16);
- rc = ble_gattc_disc_svc_uuid_cb(entry, 0, &service);
- if (rc != 0) {
+ rc = 0;
+
+done:
+ cbrc = ble_gattc_disc_svc_uuid_cb(entry, rc, &service);
+ if (rc != 0 || cbrc != 0) {
ble_gattc_entry_remove_free(entry, prev);
}
}
@@ -1025,11 +1041,12 @@ ble_gattc_find_inc_svcs_rx_read_rsp(struct ble_gattc_entry *entry,
void *value, int value_len)
{
struct ble_gatt_service service;
+ int cbrc;
int rc;
if (entry->find_inc_svcs.cur_start == 0) {
/* Unexpected read response; terminate procedure. */
- rc = BLE_HS_EBADDATA; // XXX
+ rc = BLE_HS_EBADDATA;
goto done;
}
@@ -1041,6 +1058,7 @@ ble_gattc_find_inc_svcs_rx_read_rsp(struct ble_gattc_entry *entry,
if (value_len != 16) {
/* Invalid UUID. */
rc = BLE_HS_EBADDATA;
+ goto done;
}
service.start_handle = entry->find_inc_svcs.cur_start;
@@ -1055,7 +1073,10 @@ ble_gattc_find_inc_svcs_rx_read_rsp(struct ble_gattc_entry *entry,
rc = 0;
done:
- ble_gattc_find_inc_svcs_cb(entry, rc, &service);
+ cbrc = ble_gattc_find_inc_svcs_cb(entry, rc, &service);
+ if (rc == 0) {
+ rc = cbrc;
+ }
return rc;
}
@@ -1066,6 +1087,8 @@ ble_gattc_find_inc_svcs_rx_adata(struct ble_gattc_entry *entry,
{
struct ble_gatt_service service;
uint16_t uuid16;
+ int call_cb;
+ int cbrc;
int rc;
if (entry->find_inc_svcs.cur_start != 0) {
@@ -1075,12 +1098,21 @@ ble_gattc_find_inc_svcs_rx_adata(struct ble_gattc_entry *entry,
return 0;
}
+ call_cb = 1;
+
+ if (adata->att_handle <= entry->find_inc_svcs.prev_handle) {
+ /* Peer sent services out of order; terminate procedure. */
+ rc = BLE_HS_EBADDATA;
+ goto done;
+ }
+
entry->find_inc_svcs.prev_handle = adata->att_handle;
switch (adata->value_len) {
case BLE_GATTS_INC_SVC_LEN_NO_UUID:
entry->find_inc_svcs.cur_start = le16toh(adata->value + 0);
entry->find_inc_svcs.cur_end = le16toh(adata->value + 2);
+ call_cb = 0;
break;
case BLE_GATTS_INC_SVC_LEN_UUID:
@@ -1089,20 +1121,27 @@ ble_gattc_find_inc_svcs_rx_adata(struct ble_gattc_entry *entry,
uuid16 = le16toh(adata->value + 4);
rc = ble_uuid_16_to_128(uuid16, service.uuid128);
if (rc != 0) {
- return BLE_HS_EBADDATA;
+ rc = BLE_HS_EBADDATA;
+ goto done;
}
- rc = ble_gattc_find_inc_svcs_cb(entry, 0, &service);
- if (rc != 0) {
- return rc;
- }
break;
default:
return BLE_HS_EBADDATA;
}
- return 0;
+ rc = 0;
+
+done:
+ if (call_cb) {
+ cbrc = ble_gattc_find_inc_svcs_cb(entry, 0, &service);
+ if (rc != 0) {
+ rc = cbrc;
+ }
+ }
+
+ return rc;
}
static int
@@ -1239,11 +1278,16 @@ ble_gattc_disc_all_chrs_rx_adata(struct ble_gattc_entry *entry,
goto done;
}
- entry->disc_all_chrs.prev_handle = adata->att_handle;
-
chr.properties = adata->value[0];
chr.value_handle = le16toh(adata->value + 1);
+ if (adata->att_handle <= entry->disc_all_chrs.prev_handle) {
+ /* Peer sent characteristics out of order; terminate procedure. */
+ rc = BLE_HS_EBADDATA;
+ goto done;
+ }
+ entry->disc_all_chrs.prev_handle = adata->att_handle;
+
rc = 0;
done:
@@ -1390,15 +1434,23 @@ ble_gattc_disc_chr_uuid_rx_adata(struct ble_gattc_entry *entry,
goto done;
}
- entry->disc_chr_uuid.prev_handle = adata->att_handle;
-
chr.properties = adata->value[0];
chr.value_handle = le16toh(adata->value + 1);
+ if (adata->att_handle <= entry->disc_chr_uuid.prev_handle) {
+ /* Peer sent characteristics out of order; terminate procedure. */
+ rc = BLE_HS_EBADDATA;
+ goto done;
+ }
+
+ entry->disc_chr_uuid.prev_handle = adata->att_handle;
+
rc = 0;
done:
- if (memcmp(chr.uuid128, entry->disc_chr_uuid.chr_uuid, 16) == 0) {
+ if (rc != 0 ||
+ memcmp(chr.uuid128, entry->disc_chr_uuid.chr_uuid, 16) == 0) {
+
cbrc = ble_gattc_disc_chr_uuid_cb(entry, rc, &chr);
if (rc == 0) {
rc = cbrc;
@@ -1516,6 +1568,7 @@ ble_gattc_rx_find_info_entry(struct ble_hs_conn *conn,
{
struct ble_gattc_entry *entry;
struct ble_gattc_entry *prev;
+ int cbrc;
int rc;
entry = ble_gattc_find(conn->bhc_handle, BLE_GATT_OP_DISC_ALL_DSCS, 1,
@@ -1525,12 +1578,23 @@ ble_gattc_rx_find_info_entry(struct ble_hs_conn *conn,
return;
}
- rc = ble_gattc_disc_all_dscs_cb(entry, 0, idata->attr_handle,
- idata->uuid128);
+ if (idata->attr_handle <= entry->disc_all_dscs.prev_handle) {
+ /* Peer sent descriptors out of order; terminate procedure. */
+ rc = BLE_HS_EBADDATA;
+ goto done;
+ }
+ entry->disc_all_dscs.prev_handle = idata->attr_handle;
+
+ rc = 0;
+
+done:
+ cbrc = ble_gattc_disc_all_dscs_cb(entry, 0, idata->attr_handle,
+ idata->uuid128);
+ if (rc == 0) {
+ rc = cbrc;
+ }
if (rc != 0) {
ble_gattc_entry_remove_free(entry, prev);
- } else {
- entry->disc_all_dscs.prev_handle = idata->attr_handle;
}
}