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/08 02:54:48 UTC
incubator-mynewt-larva git commit: Discover All Characteristic
Descriptors GATT proc.
Repository: incubator-mynewt-larva
Updated Branches:
refs/heads/master 5089258db -> d5ba6afe5
Discover All Characteristic Descriptors GATT proc.
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/d5ba6afe
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/tree/d5ba6afe
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/diff/d5ba6afe
Branch: refs/heads/master
Commit: d5ba6afe57d03f68626d254a22bf6615344083a8
Parents: 5089258
Author: Christopher Collins <cc...@gmail.com>
Authored: Thu Jan 7 16:26:06 2016 -0800
Committer: Christopher Collins <cc...@gmail.com>
Committed: Thu Jan 7 17:54:24 2016 -0800
----------------------------------------------------------------------
net/nimble/host/include/host/ble_gatt.h | 10 +-
net/nimble/host/include/host/ble_hs_test.h | 1 +
net/nimble/host/src/ble_att_clt.c | 23 +-
net/nimble/host/src/ble_att_cmd.h | 3 +
net/nimble/host/src/ble_gatt_priv.h | 3 +
net/nimble/host/src/ble_gattc.c | 165 ++++++++-
net/nimble/host/src/test/ble_gatt_disc_d_test.c | 356 +++++++++++++++++++
net/nimble/host/src/test/ble_hs_test.c | 1 +
net/nimble/host/src/test/ble_hs_test_util.c | 7 +
net/nimble/host/src/test/ble_hs_test_util.h | 1 +
10 files changed, 555 insertions(+), 15 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/include/host/ble_gatt.h
----------------------------------------------------------------------
diff --git a/net/nimble/host/include/host/ble_gatt.h b/net/nimble/host/include/host/ble_gatt.h
index ce6f816..1cc4085 100644
--- a/net/nimble/host/include/host/ble_gatt.h
+++ b/net/nimble/host/include/host/ble_gatt.h
@@ -52,9 +52,12 @@ typedef int ble_gatt_attr_fn(uint16_t conn_handle, int status,
typedef int ble_gatt_chr_fn(uint16_t conn_handle, int status,
struct ble_gatt_chr *chr, void *arg);
+typedef int ble_gatt_dsc_fn(uint16_t conn_handle, int status,
+ uint16_t chr_val_handle, uint16_t dsc_handle,
+ uint8_t *dsc_uuid128, void *arg);
+
int ble_gattc_disc_all_svcs(uint16_t conn_handle,
- ble_gatt_disc_svc_fn *cb,
- void *cb_arg);
+ ble_gatt_disc_svc_fn *cb, void *cb_arg);
int ble_gattc_disc_svc_by_uuid(uint16_t conn_handle, void *service_uuid128,
ble_gatt_disc_svc_fn *cb, void *cb_arg);
int ble_gattc_find_inc_svcs(uint16_t conn_handle, uint16_t start_handle,
@@ -66,6 +69,9 @@ int ble_gattc_disc_all_chrs(uint16_t conn_handle, uint16_t start_handle,
int ble_gattc_disc_chrs_by_uuid(uint16_t conn_handle, uint16_t start_handle,
uint16_t end_handle, void *uuid128,
ble_gatt_chr_fn *cb, void *cb_arg);
+int ble_gattc_disc_all_dscs(uint16_t conn_handle, uint16_t chr_val_handle,
+ uint16_t chr_end_handle,
+ ble_gatt_dsc_fn *cb, void *cb_arg);
int ble_gattc_read(uint16_t conn_handle, uint16_t attr_handle,
ble_gatt_attr_fn *cb, void *cb_arg);
int ble_gattc_write_no_rsp(uint16_t conn_handle, uint16_t attr_handle,
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/include/host/ble_hs_test.h
----------------------------------------------------------------------
diff --git a/net/nimble/host/include/host/ble_hs_test.h b/net/nimble/host/include/host/ble_hs_test.h
index cb5d588..39de412 100644
--- a/net/nimble/host/include/host/ble_hs_test.h
+++ b/net/nimble/host/include/host/ble_hs_test.h
@@ -32,6 +32,7 @@ int ble_os_test_all(void);
int ble_uuid_test_all(void);
int ble_gatt_disc_s_test_all(void);
int ble_gatt_disc_c_test_all(void);
+int ble_gatt_disc_d_test_all(void);
int ble_gatt_read_test_all(void);
int ble_gatt_write_test_all(void);
int ble_gatt_conn_test_all(void);
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/src/ble_att_clt.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_att_clt.c b/net/nimble/host/src/ble_att_clt.c
index 42934e4..5951fd6 100644
--- a/net/nimble/host/src/ble_att_clt.c
+++ b/net/nimble/host/src/ble_att_clt.c
@@ -212,7 +212,8 @@ ble_att_clt_rx_find_info(struct ble_hs_conn *conn, struct ble_l2cap_chan *chan,
while (off < OS_MBUF_PKTLEN(rxom)) {
rc = os_mbuf_copydata(rxom, off, 2, &handle_id);
if (rc != 0) {
- return BLE_HS_EINVAL;
+ rc = BLE_HS_EBADDATA;
+ goto done;
}
off += 2;
handle_id = le16toh(&handle_id);
@@ -221,33 +222,41 @@ ble_att_clt_rx_find_info(struct ble_hs_conn *conn, struct ble_l2cap_chan *chan,
case BLE_ATT_FIND_INFO_RSP_FORMAT_16BIT:
rc = os_mbuf_copydata(rxom, off, 2, &uuid16);
if (rc != 0) {
- return BLE_HS_EINVAL;
+ rc = BLE_HS_EBADDATA;
+ goto done;
}
off += 2;
uuid16 = le16toh(&uuid16);
rc = ble_uuid_16_to_128(uuid16, uuid128);
if (rc != 0) {
- return BLE_HS_EINVAL;
+ rc = BLE_HS_EBADDATA;
+ goto done;
}
break;
case BLE_ATT_FIND_INFO_RSP_FORMAT_128BIT:
rc = os_mbuf_copydata(rxom, off, 16, &uuid128);
if (rc != 0) {
- rc = BLE_HS_EINVAL;
+ rc = BLE_HS_EBADDATA;
+ goto done;
}
off += 16;
break;
default:
- return BLE_HS_EINVAL;
+ rc = BLE_HS_EBADDATA;
+ goto done;
}
- /* XXX: Notify GATT of handle-uuid pair. */
+ ble_gattc_rx_find_info_entry(conn, 0, handle_id, uuid128);
}
- return 0;
+ rc = 0;
+
+done:
+ ble_gattc_rx_find_info_complete(conn, rc);
+ return rc;
}
int
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/src/ble_att_cmd.h
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_att_cmd.h b/net/nimble/host/src/ble_att_cmd.h
index 73c8ea2..5de82f9 100644
--- a/net/nimble/host/src/ble_att_cmd.h
+++ b/net/nimble/host/src/ble_att_cmd.h
@@ -75,6 +75,9 @@ struct ble_att_find_info_rsp {
#define BLE_ATT_FIND_INFO_RSP_FORMAT_16BIT 1
#define BLE_ATT_FIND_INFO_RSP_FORMAT_128BIT 2
+#define BLE_ATT_FIND_INFO_IDATA_16_SZ 4
+#define BLE_ATT_FIND_INFO_IDATA_128_SZ 18
+
/**
* | Parameter | Size (octets) |
* +------------------------------------+-------------------+
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/src/ble_gatt_priv.h
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/ble_gatt_priv.h b/net/nimble/host/src/ble_gatt_priv.h
index 7deacd2..5b6e344 100644
--- a/net/nimble/host/src/ble_gatt_priv.h
+++ b/net/nimble/host/src/ble_gatt_priv.h
@@ -57,6 +57,9 @@ void ble_gattc_rx_find_type_value_hinfo(struct ble_hs_conn *conn,
void ble_gattc_rx_find_type_value_complete(struct ble_hs_conn *conn, int rc);
void ble_gattc_rx_write_rsp(struct ble_hs_conn *conn);
void ble_gattc_rx_indicate_rsp(struct ble_hs_conn *conn);
+void ble_gattc_rx_find_info_entry(struct ble_hs_conn *conn, int status,
+ uint16_t handle, uint8_t *uuid128);
+void ble_gattc_rx_find_info_complete(struct ble_hs_conn *conn, int status);
void ble_gattc_connection_txable(uint16_t conn_handle);
void ble_gattc_connection_broken(uint16_t conn_handle);
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/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 37452e7..77e9284 100644
--- a/net/nimble/host/src/ble_gattc.c
+++ b/net/nimble/host/src/ble_gattc.c
@@ -83,6 +83,14 @@ struct ble_gattc_entry {
} disc_chr_uuid;
struct {
+ uint16_t chr_val_handle;
+ uint16_t prev_handle;
+ uint16_t end_handle;
+ ble_gatt_dsc_fn *cb;
+ void *cb_arg;
+ } disc_all_dscs;
+
+ struct {
uint16_t handle;
ble_gatt_attr_fn *cb;
void *cb_arg;
@@ -112,11 +120,12 @@ struct ble_gattc_entry {
#define BLE_GATT_OP_FIND_INC_SVCS 3
#define BLE_GATT_OP_DISC_ALL_CHRS 4
#define BLE_GATT_OP_DISC_CHRS_UUID 5
-#define BLE_GATT_OP_READ 6
-#define BLE_GATT_OP_WRITE_NO_RSP 7
-#define BLE_GATT_OP_WRITE 8
-#define BLE_GATT_OP_INDICATE 9
-#define BLE_GATT_OP_MAX 10
+#define BLE_GATT_OP_DISC_ALL_DSCS 6
+#define BLE_GATT_OP_READ 7
+#define BLE_GATT_OP_WRITE_NO_RSP 8
+#define BLE_GATT_OP_WRITE 9
+#define BLE_GATT_OP_INDICATE 10
+#define BLE_GATT_OP_MAX 11
static struct os_callout_func ble_gattc_heartbeat_timer;
@@ -129,6 +138,7 @@ static int ble_gattc_kick_disc_svc_uuid(struct ble_gattc_entry *entry);
static int ble_gattc_kick_find_inc_svcs(struct ble_gattc_entry *entry);
static int ble_gattc_kick_disc_all_chrs(struct ble_gattc_entry *entry);
static int ble_gattc_kick_disc_chr_uuid(struct ble_gattc_entry *entry);
+static int ble_gattc_kick_disc_all_dscs(struct ble_gattc_entry *entry);
static int ble_gattc_kick_read(struct ble_gattc_entry *entry);
static int ble_gattc_kick_write_no_rsp(struct ble_gattc_entry *entry);
static int ble_gattc_kick_write(struct ble_gattc_entry *entry);
@@ -145,6 +155,8 @@ static void ble_gattc_err_disc_all_chrs(struct ble_gattc_entry *entry,
int status);
static void ble_gattc_err_disc_chr_uuid(struct ble_gattc_entry *entry,
int status);
+static void ble_gattc_err_disc_all_dscs(struct ble_gattc_entry *entry,
+ int status);
static void ble_gattc_err_read(struct ble_gattc_entry *entry, int status);
static void ble_gattc_err_write(struct ble_gattc_entry *entry, int status);
static void ble_gattc_err_indicate(struct ble_gattc_entry *entry, int status);
@@ -206,6 +218,10 @@ static const struct ble_gattc_dispatch_entry
.kick_cb = ble_gattc_kick_disc_chr_uuid,
.err_cb = ble_gattc_err_disc_chr_uuid,
},
+ [BLE_GATT_OP_DISC_ALL_DSCS] = {
+ .kick_cb = ble_gattc_kick_disc_all_dscs,
+ .err_cb = ble_gattc_err_disc_all_dscs,
+ },
[BLE_GATT_OP_READ] = {
.kick_cb = ble_gattc_kick_read,
.err_cb = ble_gattc_err_read,
@@ -1393,7 +1409,144 @@ ble_gattc_disc_chrs_by_uuid(uint16_t conn_handle, uint16_t start_handle,
}
/*****************************************************************************
- * @read *
+ * $discover all characteristic descriptors *
+ *****************************************************************************/
+
+static int
+ble_gattc_disc_all_dscs_cb(struct ble_gattc_entry *entry, int status,
+ uint16_t dsc_handle, uint8_t *dsc_uuid128)
+{
+ int rc;
+
+ if (entry->disc_all_dscs.cb == NULL) {
+ rc = 0;
+ } else {
+ rc = entry->disc_all_dscs.cb(entry->conn_handle, status,
+ entry->disc_all_dscs.chr_val_handle,
+ dsc_handle, dsc_uuid128,
+ entry->disc_all_dscs.cb_arg);
+ }
+
+ return rc;
+}
+
+static int
+ble_gattc_kick_disc_all_dscs(struct ble_gattc_entry *entry)
+{
+ struct ble_att_find_info_req req;
+ struct ble_hs_conn *conn;
+ int rc;
+
+ conn = ble_hs_conn_find(entry->conn_handle);
+ if (conn == NULL) {
+ rc = BLE_HS_ENOTCONN;
+ goto err;
+ }
+
+ req.bafq_start_handle = entry->disc_all_dscs.prev_handle + 1;
+ req.bafq_end_handle = entry->disc_all_dscs.end_handle;
+
+ rc = ble_att_clt_tx_find_info(conn, &req);
+ if (rc != 0) {
+ goto err;
+ }
+
+ return 0;
+
+err:
+ if (ble_gattc_tx_postpone_chk(entry, rc)) {
+ return BLE_HS_EAGAIN;
+ }
+
+ ble_gattc_disc_all_dscs_cb(entry, rc, 0, NULL);
+ return rc;
+}
+
+static void
+ble_gattc_err_disc_all_dscs(struct ble_gattc_entry *entry, int status)
+{
+ if (status == BLE_HS_ATT_ERR(BLE_ATT_ERR_ATTR_NOT_FOUND)) {
+ /* Discovery is complete. */
+ status = 0;
+ }
+
+ ble_gattc_disc_all_dscs_cb(entry, status, 0, NULL);
+}
+
+void
+ble_gattc_rx_find_info_entry(struct ble_hs_conn *conn, int status,
+ uint16_t handle, uint8_t *uuid128)
+{
+ struct ble_gattc_entry *entry;
+ struct ble_gattc_entry *prev;
+ int rc;
+
+ entry = ble_gattc_find(conn->bhc_handle, BLE_GATT_OP_DISC_ALL_DSCS, 1,
+ &prev);
+ if (entry == NULL) {
+ /* Not expecting a response from this device. */
+ return;
+ }
+
+ rc = ble_gattc_disc_all_dscs_cb(entry, status, handle, uuid128);
+ if (rc != 0) {
+ ble_gattc_entry_remove_free(entry, prev);
+ } else if (status != 0) {
+ /* Error. */
+ ble_gattc_disc_all_dscs_cb(entry, status, 0, NULL);
+ ble_gattc_entry_remove_free(entry, prev);
+ } else {
+ entry->disc_all_dscs.prev_handle = handle;
+ }
+}
+
+void
+ble_gattc_rx_find_info_complete(struct ble_hs_conn *conn, int status)
+{
+ struct ble_gattc_entry *entry;
+ struct ble_gattc_entry *prev;
+
+ entry = ble_gattc_find(conn->bhc_handle, BLE_GATT_OP_DISC_ALL_DSCS, 1,
+ &prev);
+ if (entry == NULL) {
+ /* Not expecting a response from this device. */
+ return;
+ }
+
+ if (status != 0 || entry->disc_all_dscs.prev_handle ==
+ entry->disc_all_dscs.end_handle) {
+ /* Error or all descriptors discovered. */
+ ble_gattc_disc_all_dscs_cb(entry, status, 0, NULL);
+ ble_gattc_entry_remove_free(entry, prev);
+ } else {
+ /* Send follow-up request. */
+ ble_gattc_entry_set_pending(entry);
+ }
+}
+
+int
+ble_gattc_disc_all_dscs(uint16_t conn_handle, uint16_t chr_val_handle,
+ uint16_t chr_end_handle,
+ ble_gatt_dsc_fn *cb, void *cb_arg)
+{
+ struct ble_gattc_entry *entry;
+ int rc;
+
+ rc = ble_gattc_new_entry(conn_handle, BLE_GATT_OP_DISC_ALL_DSCS, &entry);
+ if (rc != 0) {
+ return rc;
+ }
+ entry->disc_all_dscs.chr_val_handle = chr_val_handle;
+ entry->disc_all_dscs.prev_handle = chr_val_handle;
+ entry->disc_all_dscs.end_handle = chr_end_handle;
+ entry->disc_all_dscs.cb = cb;
+ entry->disc_all_dscs.cb_arg = cb_arg;
+
+ return 0;
+}
+
+/*****************************************************************************
+ * $read *
*****************************************************************************/
static int
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/src/test/ble_gatt_disc_d_test.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/test/ble_gatt_disc_d_test.c b/net/nimble/host/src/test/ble_gatt_disc_d_test.c
new file mode 100644
index 0000000..5add73d
--- /dev/null
+++ b/net/nimble/host/src/test/ble_gatt_disc_d_test.c
@@ -0,0 +1,356 @@
+/**
+ * Copyright (c) 2015 Runtime Inc.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <string.h>
+#include <errno.h>
+#include <limits.h>
+#include "testutil/testutil.h"
+#include "nimble/ble.h"
+#include "host/ble_hs_test.h"
+#include "host/ble_gatt.h"
+#include "host/ble_uuid.h"
+#include "ble_hs_priv.h"
+#include "ble_att_cmd.h"
+#include "ble_gatt_priv.h"
+#include "ble_hs_conn.h"
+#include "ble_hs_test_util.h"
+
+struct ble_gatt_disc_d_test_dsc {
+ uint16_t chr_val_handle; /* 0 if last entry. */
+ uint16_t dsc_handle;
+ uint8_t dsc_uuid128[16];
+};
+
+#define BLE_GATT_DISC_D_TEST_MAX_DSCS 256
+static struct ble_gatt_disc_d_test_dsc
+ ble_gatt_disc_d_test_dscs[BLE_GATT_DISC_D_TEST_MAX_DSCS];
+static int ble_gatt_disc_d_test_num_dscs;
+static int ble_gatt_disc_d_test_rx_complete;
+
+static void
+ble_gatt_disc_d_test_init(void)
+{
+ ble_hs_test_util_init();
+
+ ble_gatt_disc_d_test_num_dscs = 0;
+ ble_gatt_disc_d_test_rx_complete = 0;
+}
+
+static int
+ble_gatt_disc_d_test_misc_rx_rsp_once(
+ struct ble_hs_conn *conn, struct ble_gatt_disc_d_test_dsc *dscs)
+{
+ struct ble_att_find_info_rsp rsp;
+ struct ble_l2cap_chan *chan;
+ uint8_t buf[1024];
+ uint16_t uuid16_cur;
+ uint16_t uuid16_0;
+ int off;
+ int rc;
+ int i;
+
+ /* Send the pending ATT Read By Type Request. */
+ ble_hs_test_util_tx_all();
+
+ uuid16_0 = ble_uuid_128_to_16(dscs[0].dsc_uuid128);
+ if (uuid16_0 != 0) {
+ rsp.bafp_format = BLE_ATT_FIND_INFO_RSP_FORMAT_16BIT;
+ } else {
+ rsp.bafp_format = BLE_ATT_FIND_INFO_RSP_FORMAT_128BIT;
+ }
+
+ rc = ble_att_find_info_rsp_write(buf, BLE_ATT_FIND_INFO_RSP_BASE_SZ, &rsp);
+ TEST_ASSERT_FATAL(rc == 0);
+
+ off = BLE_ATT_FIND_INFO_RSP_BASE_SZ;
+ for (i = 0; ; i++) {
+ if (dscs[i].chr_val_handle == 0) {
+ /* No more descriptors. */
+ break;
+ }
+
+ /* If the value length is changing, we need a separate response. */
+ uuid16_cur = ble_uuid_128_to_16(dscs[i].dsc_uuid128);
+ if (((uuid16_0 == 0) ^ (uuid16_cur == 0)) != 0) {
+ break;
+ }
+
+ htole16(buf + off, dscs[i].dsc_handle);
+ off += 2;
+
+ if (uuid16_cur != 0) {
+ htole16(buf + off, uuid16_cur);
+ off += 2;
+ } else {
+ memcpy(buf + off, dscs[i].dsc_uuid128, 16);
+ off += 16;
+ }
+ }
+
+ chan = ble_hs_conn_chan_find(conn, BLE_L2CAP_CID_ATT);
+ TEST_ASSERT_FATAL(chan != NULL);
+
+ rc = ble_hs_test_util_l2cap_rx_payload_flat(conn, chan, buf, off);
+ TEST_ASSERT(rc == 0);
+
+ return i;
+}
+
+static void
+ble_gatt_disc_d_test_misc_rx_rsp(struct ble_hs_conn *conn,
+ uint16_t end_handle,
+ struct ble_gatt_disc_d_test_dsc *dscs)
+{
+ int count;
+ int idx;
+
+ idx = 0;
+ while (dscs[idx].chr_val_handle != 0) {
+ count = ble_gatt_disc_d_test_misc_rx_rsp_once(conn, dscs + idx);
+ if (count == 0) {
+ break;
+ }
+ idx += count;
+ }
+
+ if (dscs[idx - 1].dsc_handle != end_handle) {
+ /* Send the pending ATT Request. */
+ ble_hs_test_util_tx_all();
+ ble_hs_test_util_rx_att_err_rsp(conn, BLE_ATT_OP_FIND_INFO_REQ,
+ BLE_ATT_ERR_ATTR_NOT_FOUND,
+ end_handle);
+ }
+}
+
+static void
+ble_gatt_disc_d_test_misc_verify_dscs(struct ble_gatt_disc_d_test_dsc *dscs,
+ int stop_after)
+{
+ int i;
+
+ if (stop_after == 0) {
+ stop_after = INT_MAX;
+ }
+
+ for (i = 0; i < stop_after && dscs[i].chr_val_handle != 0; i++) {
+ TEST_ASSERT(dscs[i].chr_val_handle ==
+ ble_gatt_disc_d_test_dscs[i].chr_val_handle);
+ TEST_ASSERT(dscs[i].dsc_handle ==
+ ble_gatt_disc_d_test_dscs[i].dsc_handle);
+ TEST_ASSERT(memcmp(dscs[i].dsc_uuid128,
+ ble_gatt_disc_d_test_dscs[i].dsc_uuid128,
+ 16) == 0);
+ }
+
+ TEST_ASSERT(i == ble_gatt_disc_d_test_num_dscs);
+ TEST_ASSERT(ble_gatt_disc_d_test_rx_complete);
+}
+
+static int
+ble_gatt_disc_d_test_misc_cb(uint16_t conn_handle, int status,
+ uint16_t chr_val_handle, uint16_t dsc_handle,
+ uint8_t *dsc_uuid128, void *arg)
+{
+ struct ble_gatt_disc_d_test_dsc *dsc;
+ int *stop_after;
+
+ TEST_ASSERT(status == 0);
+ TEST_ASSERT(!ble_gatt_disc_d_test_rx_complete);
+
+ stop_after = arg;
+
+ if (dsc_handle == 0) {
+ ble_gatt_disc_d_test_rx_complete = 1;
+ } else {
+ TEST_ASSERT_FATAL(ble_gatt_disc_d_test_num_dscs <
+ BLE_GATT_DISC_D_TEST_MAX_DSCS);
+
+ dsc = ble_gatt_disc_d_test_dscs + ble_gatt_disc_d_test_num_dscs++;
+ dsc->chr_val_handle = chr_val_handle;
+ dsc->dsc_handle = dsc_handle;
+ memcpy(dsc->dsc_uuid128, dsc_uuid128, 16);
+ }
+
+ if (*stop_after > 0) {
+ (*stop_after)--;
+ if (*stop_after == 0) {
+ ble_gatt_disc_d_test_rx_complete = 1;
+ return 1;
+ }
+ }
+
+ return 0;
+}
+
+static void
+ble_gatt_disc_d_test_misc_all(uint16_t chr_val_handle, uint16_t end_handle,
+ int stop_after,
+ struct ble_gatt_disc_d_test_dsc *dscs)
+{
+ struct ble_hs_conn *conn;
+ int num_left;
+ int rc;
+
+ ble_gatt_disc_d_test_init();
+
+ conn = ble_hs_test_util_create_conn(2, ((uint8_t[]){2,3,4,5,6,7,8,9}));
+
+ num_left = stop_after;
+ rc = ble_gattc_disc_all_dscs(2, chr_val_handle, end_handle,
+ ble_gatt_disc_d_test_misc_cb, &num_left);
+ TEST_ASSERT(rc == 0);
+
+ ble_gatt_disc_d_test_misc_rx_rsp(conn, end_handle, dscs);
+ ble_gatt_disc_d_test_misc_verify_dscs(dscs, stop_after);
+}
+
+TEST_CASE(ble_gatt_disc_d_test_1)
+{
+ /*** One 16-bit descriptor. */
+ ble_gatt_disc_d_test_misc_all(5, 10, 0,
+ ((struct ble_gatt_disc_d_test_dsc[]) { {
+ .chr_val_handle = 5,
+ .dsc_handle = 6,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x1234),
+ }, {
+ 0
+ } })
+ );
+
+ /*** Two 16-bit descriptors. */
+ ble_gatt_disc_d_test_misc_all(50, 100, 0,
+ ((struct ble_gatt_disc_d_test_dsc[]) { {
+ .chr_val_handle = 50,
+ .dsc_handle = 51,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x1111),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 52,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x2222),
+ }, {
+ 0
+ } })
+ );
+
+ /*** Five 16-bit descriptors. */
+ ble_gatt_disc_d_test_misc_all(50, 100, 0,
+ ((struct ble_gatt_disc_d_test_dsc[]) { {
+ .chr_val_handle = 50,
+ .dsc_handle = 51,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x1111),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 52,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x2222),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 53,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x3333),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 54,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x4444),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 55,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x5555),
+ }, {
+ 0
+ } })
+ );
+
+ /*** Interleaved 16-bit and 128-bit descriptors. */
+ ble_gatt_disc_d_test_misc_all(50, 100, 0,
+ ((struct ble_gatt_disc_d_test_dsc[]) { {
+ .chr_val_handle = 50,
+ .dsc_handle = 51,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x1111),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 52,
+ .dsc_uuid128 = { 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15 },
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 53,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x3333),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 54,
+ .dsc_uuid128 = { 1,0,4,0,6,9,17,7,8,43,7,4,12,43,19,35 },
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 55,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x5555),
+ }, {
+ 0
+ } })
+ );
+
+ /*** Ends with final handle ID. */
+ ble_gatt_disc_d_test_misc_all(50, 52, 0,
+ ((struct ble_gatt_disc_d_test_dsc[]) { {
+ .chr_val_handle = 50,
+ .dsc_handle = 51,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x1111),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 52,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x2222),
+ }, {
+ 0
+ } })
+ );
+
+ /*** Stop after two descriptors. */
+ ble_gatt_disc_d_test_misc_all(50, 100, 2,
+ ((struct ble_gatt_disc_d_test_dsc[]) { {
+ .chr_val_handle = 50,
+ .dsc_handle = 51,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x1111),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 52,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x2222),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 53,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x3333),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 54,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x4444),
+ }, {
+ .chr_val_handle = 50,
+ .dsc_handle = 55,
+ .dsc_uuid128 = BLE_UUID16_ARR(0x5555),
+ }, {
+ 0
+ } })
+ );
+}
+
+TEST_SUITE(ble_gatt_disc_d_test_suite)
+{
+ ble_gatt_disc_d_test_1();
+}
+
+int
+ble_gatt_disc_d_test_all(void)
+{
+ ble_gatt_disc_d_test_suite();
+
+ return tu_any_failed;
+}
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/src/test/ble_hs_test.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/test/ble_hs_test.c b/net/nimble/host/src/test/ble_hs_test.c
index d7cfa60..d959f11 100644
--- a/net/nimble/host/src/test/ble_hs_test.c
+++ b/net/nimble/host/src/test/ble_hs_test.c
@@ -58,6 +58,7 @@ main(void)
ble_uuid_test_all();
ble_gatt_disc_s_test_all();
ble_gatt_disc_c_test_all();
+ ble_gatt_disc_d_test_all();
ble_gatt_read_test_all();
ble_gatt_write_test_all();
ble_gatt_conn_test_all();
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/src/test/ble_hs_test_util.c
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/test/ble_hs_test_util.c b/net/nimble/host/src/test/ble_hs_test_util.c
index 4f4f49d..ff7963e 100644
--- a/net/nimble/host/src/test/ble_hs_test_util.c
+++ b/net/nimble/host/src/test/ble_hs_test_util.c
@@ -329,6 +329,13 @@ ble_hs_test_util_rx_dir_adv_acks(void)
}
void
+ble_hs_test_util_tx_all(void)
+{
+ ble_gattc_wakeup();
+ ble_hs_process_tx_data_queue();
+}
+
+void
ble_hs_test_util_init(void)
{
int rc;
http://git-wip-us.apache.org/repos/asf/incubator-mynewt-larva/blob/d5ba6afe/net/nimble/host/src/test/ble_hs_test_util.h
----------------------------------------------------------------------
diff --git a/net/nimble/host/src/test/ble_hs_test_util.h b/net/nimble/host/src/test/ble_hs_test_util.h
index 1a8cf4a..335dc75 100644
--- a/net/nimble/host/src/test/ble_hs_test_util.h
+++ b/net/nimble/host/src/test/ble_hs_test_util.h
@@ -55,6 +55,7 @@ void ble_hs_test_util_rx_num_completed_pkts_event(
void ble_hs_test_util_rx_und_adv_acks(void);
void ble_hs_test_util_rx_und_adv_acks_count(int count);
void ble_hs_test_util_rx_dir_adv_acks(void);
+void ble_hs_test_util_tx_all(void);
void ble_hs_test_util_init(void);
#endif