xref: /nrf52832-nimble/packages/NimBLE-latest/apps/bletest/src/bletest.c (revision 042d53a763ad75cb1465103098bb88c245d95138)
1 /*
2  * Licensed to the Apache Software Foundation (ASF) under one
3  * or more contributor license agreements.  See the NOTICE file
4  * distributed with this work for additional information
5  * regarding copyright ownership.  The ASF licenses this file
6  * to you under the Apache License, Version 2.0 (the
7  * "License"); you may not use this file except in compliance
8  * with the License.  You may obtain a copy of the License at
9  *
10  *  http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing,
13  * software distributed under the License is distributed on an
14  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15  * KIND, either express or implied.  See the License for the
16  * specific language governing permissions and limitations
17  * under the License.
18  */
19 
20 #include <assert.h>
21 #include <string.h>
22 
23 /* BLE */
24 #include "nimble/ble.h"
25 #include "nimble/ble_hci_trans.h"
26 #include "nimble/hci_common.h"
27 #include "host/ble_hs.h"
28 
29 #include "nimble/nimble_npl.h"
30 #include "nimble/npl_shell.h"
31 
32 /* XXX: An app should not include private headers from a library.  The bletest
33  * app uses some of nimble's internal details for logging.
34  */
35 #include "ble_hs_priv.h"
36 #include "bletest_priv.h"
37 
38 #include <rtthread.h>
39 
40 #define BLETEST_TASK_PRIO               5
41 
42 /* For LED toggling */
43 int g_led_pin;
44 
45 /* A buffer for host advertising data */
46 uint8_t g_host_adv_data[BLE_HCI_MAX_ADV_DATA_LEN];
47 uint8_t g_host_adv_len;
48 static uint8_t _g_dev_addr[BLE_DEV_ADDR_LEN];
49 
50 /* Some application configurations */
51 #define BLETEST_ROLE_NONE               (0)
52 #define BLETEST_ROLE_ADVERTISER         (1)
53 #define BLETEST_ROLE_SCANNER            (2)
54 #define BLETEST_ROLE_INITIATOR          (3)
55 
56 #define MYNEWT_VAL_BLETEST_ROLE BLETEST_ROLE_ADVERTISER
57 
58 #if MYNEWT_VAL(BLETEST_ROLE) == BLETEST_ROLE_ADVERTISER
59 #define BLETEST_CFG_ROLE                BLETEST_ROLE_ADVERTISER
60 #endif
61 #if MYNEWT_VAL(BLETEST_ROLE) == BLETEST_ROLE_SCANNER
62 #define BLETEST_CFG_ROLE                BLETEST_ROLE_SCANNER
63 #endif
64 #if MYNEWT_VAL(BLETEST_ROLE) == BLETEST_ROLE_INITIATOR
65 #define BLETEST_CFG_ROLE                BLETEST_ROLE_INITIATOR
66 #endif
67 
68 #ifndef BLETEST_CFG_ROLE
69 #error "No role defined! Must define a valid role in syscfg.yml in apps/bletest"
70 #endif
71 
72 /* Advertiser config */
73 #define BLETEST_CFG_ADV_OWN_ADDR_TYPE   (BLE_HCI_ADV_OWN_ADDR_PUBLIC)
74 #define BLETEST_CFG_ADV_PEER_ADDR_TYPE  (BLE_HCI_ADV_PEER_ADDR_PUBLIC)
75 #define BLETEST_CFG_ADV_ITVL            (60000 / BLE_HCI_ADV_ITVL)
76 #define BLETEST_CFG_ADV_TYPE            BLE_HCI_ADV_TYPE_ADV_IND
77 #define BLETEST_CFG_ADV_FILT_POLICY     (BLE_HCI_ADV_FILT_NONE)
78 #define BLETEST_CFG_ADV_ADDR_RES_EN     (0)
79 
80 /* Multi-adv config */
81 /*
82  * Number of advertising instances to start up, not including the default
83  * instance. The default instance is used to connect. If this number is greater
84  * than the number of available advertising instances, we only use the number
85  * of available advertising instances (defined by the configuration setting:
86  * BLE_MULTI_ADV_INSTANCES.
87  */
88 #define BLETEST_CFG_ADV_TEST_INSTANCES     (8)
89 
90 struct bletest_multi_adv_interval
91 {
92     uint8_t adv_type;
93     /*
94      * Note: if own addr type greater than 1, we use own addr field; otherwise
95      * we use the set multi random address call to set the random address
96      */
97     uint8_t adv_own_addr_type;
98     uint16_t adv_itvl;
99 };
100 
101 /*
102  * NOTE: currently, these are all NONCONN_IND. Thus, must be 100 msecs or
103  * greater
104  */
105 const struct bletest_multi_adv_interval
106 bletest_multi_adv_instances[BLETEST_CFG_ADV_TEST_INSTANCES] = {
107     {BLE_HCI_ADV_TYPE_ADV_NONCONN_IND,
108      BLE_HCI_ADV_OWN_ADDR_PUBLIC,
109      (100000 / BLE_HCI_ADV_ITVL)},
110 
111     {BLE_HCI_ADV_TYPE_ADV_SCAN_IND,
112      BLE_HCI_ADV_OWN_ADDR_RANDOM,
113      (110000 / BLE_HCI_ADV_ITVL)},
114 
115     {BLE_HCI_ADV_TYPE_ADV_NONCONN_IND,
116      BLE_HCI_ADV_OWN_ADDR_RANDOM,
117      (120000 / BLE_HCI_ADV_ITVL)},
118 
119     {BLE_HCI_ADV_TYPE_ADV_NONCONN_IND,
120      BLE_HCI_ADV_OWN_ADDR_PUBLIC,
121      (130000 / BLE_HCI_ADV_ITVL)},
122 
123     {BLE_HCI_ADV_TYPE_ADV_SCAN_IND,
124      BLE_HCI_ADV_OWN_ADDR_MAX + 1,
125      (140000 / BLE_HCI_ADV_ITVL)},
126 
127     {BLE_HCI_ADV_TYPE_ADV_NONCONN_IND,
128      BLE_HCI_ADV_OWN_ADDR_MAX + 1,
129      (150000 / BLE_HCI_ADV_ITVL)},
130 
131     {BLE_HCI_ADV_TYPE_ADV_NONCONN_IND,
132      BLE_HCI_ADV_OWN_ADDR_PUBLIC,
133      (160000 / BLE_HCI_ADV_ITVL)},
134 
135     {BLE_HCI_ADV_TYPE_ADV_SCAN_IND,
136      BLE_HCI_ADV_OWN_ADDR_PUBLIC,
137      (170000 / BLE_HCI_ADV_ITVL)}
138 };
139 
140 /*
141  * Determines if own address contains random address or set through the
142  * multi-adv set random address command
143  */
144 #define BLETEST_CFG_MULTI_ADV_RANDOM_OWN    (0)
145 
146 /* Scan config */
147 #define BLETEST_CFG_SCAN_ITVL           (700000 / BLE_HCI_SCAN_ITVL)
148 #define BLETEST_CFG_SCAN_WINDOW         (700000 / BLE_HCI_SCAN_ITVL)
149 #define BLETEST_CFG_SCAN_TYPE           (BLE_HCI_SCAN_TYPE_PASSIVE)
150 #define BLETEST_CFG_SCAN_OWN_ADDR_TYPE  (BLE_HCI_ADV_OWN_ADDR_PUBLIC)
151 #define BLETEST_CFG_SCAN_FILT_POLICY    (BLE_HCI_SCAN_FILT_NO_WL)
152 #define BLETEST_CFG_FILT_DUP_ADV        (1)
153 
154 /* Connection config */
155 #define BLETEST_CFG_CONN_ITVL           (128)  /* in 1.25 msec increments */
156 #define BLETEST_CFG_SLAVE_LATENCY       (0)
157 #define BLETEST_CFG_INIT_FILTER_POLICY  (BLE_HCI_CONN_FILT_NO_WL)
158 #define BLETEST_CFG_CONN_SPVN_TMO       (1000)  /* 10 msec increments */
159 #define BLETEST_CFG_MIN_CE_LEN          (6)
160 #define BLETEST_CFG_MAX_CE_LEN          (BLETEST_CFG_CONN_ITVL)
161 #define BLETEST_CFG_CONN_PEER_ADDR_TYPE (BLE_HCI_CONN_PEER_ADDR_PUBLIC)
162 #define BLETEST_CFG_CONN_OWN_ADDR_TYPE  (BLE_HCI_ADV_OWN_ADDR_PUBLIC)
163 #define BLETEST_CFG_CONCURRENT_CONNS    (1)
164 
165 /* Test packet config */
166 #define BLETEST_CFG_RAND_PKT_SIZE       (1)
167 #define BLETEST_CFG_SUGG_DEF_TXOCTETS   (251)
168 #define BLETEST_CFG_SUGG_DEF_TXTIME     (2000)
169 
170 /* Test configurations. One of these should be set to 1 */
171 #if !defined(BLETEST_CONCURRENT_CONN_TEST) && !defined(BLETEST_THROUGHPUT_TEST)
172     #define BLETEST_CONCURRENT_CONN_TEST    (1)
173 #endif
174 
175 /* BLETEST variables */
176 #undef BLETEST_ADV_PKT_NUM
177 #define BLETEST_MAX_PKT_SIZE            (247)
178 #define BLETEST_PKT_SIZE                (247)
179 #define BLETEST_STACK_SIZE              (256)
180 uint32_t g_next_os_time;
181 int g_bletest_state;
182 struct ble_npl_eventq g_bletest_evq;
183 struct ble_npl_callout g_bletest_timer;
184 //struct ble_npl_task bletest_task;
185 //bssnz_t os_stack_t bletest_stack[BLETEST_STACK_SIZE];
186 uint32_t g_bletest_conn_end;
187 int g_bletest_start_update;
188 uint32_t g_bletest_conn_upd_time;
189 uint8_t g_bletest_current_conns;
190 uint8_t g_bletest_cur_peer_addr[BLE_DEV_ADDR_LEN];
191 uint8_t g_last_handle_used;
192 uint8_t g_bletest_led_state;
193 uint32_t g_bletest_led_rate;
194 uint32_t g_bletest_next_led_time;
195 uint16_t g_bletest_handle;
196 uint16_t g_bletest_completed_pkts;
197 uint16_t g_bletest_outstanding_pkts;
198 uint16_t g_bletest_ltk_reply_handle;
199 uint32_t g_bletest_hw_id[4];
200 struct hci_create_conn g_cc;
201 
202 /* --- For LE encryption testing --- */
203 /* Key: 0x4C68384139F574D836BCF34E9DFB01BF */
204 const uint8_t g_ble_ll_encrypt_test_key[16] =
205 {
206     0x4c, 0x68, 0x38, 0x41, 0x39, 0xf5, 0x74, 0xd8,
207     0x36, 0xbc, 0xf3, 0x4e, 0x9d, 0xfb, 0x01, 0xbf
208 };
209 
210 /* Plaint text: 0x0213243546576879acbdcedfe0f10213 */
211 const uint8_t g_ble_ll_encrypt_test_plain_text[16] =
212 {
213     0x02, 0x13, 0x24, 0x35, 0x46, 0x57, 0x68, 0x79,
214     0xac, 0xbd, 0xce, 0xdf, 0xe0, 0xf1, 0x02, 0x13
215 };
216 
217 /* Encrypted data: 0x99ad1b5226a37e3e058e3b8e27c2c666 */
218 const uint8_t g_ble_ll_encrypt_test_encrypted_data[16] =
219 {
220     0x99, 0xad, 0x1b, 0x52, 0x26, 0xa3, 0x7e, 0x3e,
221     0x05, 0x8e, 0x3b, 0x8e, 0x27, 0xc2, 0xc6, 0x66
222 };
223 
224 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LL_PRIVACY) == 1)
225 uint8_t g_bletest_adv_irk[16] = {
226     0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05,
227     0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b
228 };
229 
230 uint8_t g_bletest_init_irk[16] = {
231     0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08,
232     0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10
233 };
234 #endif
235 
236 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_ENCRYPTION) == 1)
237 /* LTK 0x4C68384139F574D836BCF34E9DFB01BF */
238 const uint8_t g_bletest_LTK[16] =
239 {
240     0x4C,0x68,0x38,0x41,0x39,0xF5,0x74,0xD8,
241     0x36,0xBC,0xF3,0x4E,0x9D,0xFB,0x01,0xBF
242 };
243 uint16_t g_bletest_EDIV = 0x2474;
244 uint64_t g_bletest_RAND = 0xABCDEF1234567890;
245 uint64_t g_bletest_SKDm = 0xACBDCEDFE0F10213;
246 uint64_t g_bletest_SKDs = 0x0213243546576879;
247 uint32_t g_bletest_IVm = 0xBADCAB24;
248 uint32_t g_bletest_IVs = 0xDEAFBABE;
249 #endif
250 
251 #if (BLETEST_THROUGHPUT_TEST == 1)
252 void
bletest_completed_pkt(uint16_t handle)253 bletest_completed_pkt(uint16_t handle)
254 {
255     os_sr_t sr;
256 
257     OS_ENTER_CRITICAL(sr);
258     if (handle == g_bletest_handle) {
259         ++g_bletest_completed_pkts;
260     }
261     OS_EXIT_CRITICAL(sr);
262 }
263 #endif
264 
265 #ifdef BLETEST_ADV_PKT_NUM
266 void
bletest_inc_adv_pkt_num(void)267 bletest_inc_adv_pkt_num(void)
268 {
269     int rc;
270     uint8_t *dptr;
271     uint8_t digit;
272 
273     if (g_host_adv_len != 0) {
274         dptr = &g_host_adv_data[18];
275         while (dptr >= &g_host_adv_data[13]) {
276             digit = *dptr;
277             ++digit;
278             if (digit == 58) {
279                 digit = 48;
280                 *dptr = digit;
281                 --dptr;
282             } else {
283                 *dptr = digit;
284                 break;
285             }
286         }
287 
288         rc = bletest_hci_le_set_adv_data(g_host_adv_data, g_host_adv_len);
289         assert(rc == 0);
290     }
291 }
292 #endif
293 
294 /**
295  * Sets the advertising data to be sent in advertising pdu's which contain
296  * advertising data.
297  *
298  * @param dptr
299  * @return uint8_t
300  */
301 uint8_t
bletest_set_adv_data(uint8_t * dptr,uint8_t * addr)302 bletest_set_adv_data(uint8_t *dptr, uint8_t *addr)
303 {
304     uint8_t len;
305 
306     /* Place flags in first */
307     dptr[0] = 0x02;
308     dptr[1] = 0x01;     /* Flags identifier */
309     dptr[2] = 0x06;
310     dptr += 3;
311     len = 3;
312 
313     /*  Add HID service */
314     dptr[0] = 0x03;
315     dptr[1] = 0x03;
316     dptr[2] = 0x12;
317     dptr[3] = 0x18;
318     dptr += 4;
319     len += 4;
320 
321     /* Add local name */
322     dptr[0] = 12;   /* Length of this data, not including the length */
323     dptr[1] = 0x09;
324     dptr[2] = 'r';
325     dptr[3] = 'u';
326     dptr[4] = 'n';
327     dptr[5] = 't';
328     dptr[6] = 'i';
329     dptr[7] = 'm';
330     dptr[8] = 'e';
331     dptr[9] = '-';
332     dptr[10] = '0';
333     dptr[11] = '0';
334     dptr[12] = '7';
335     dptr += 13;
336     len += 13;
337 
338     /* Add local device address */
339     dptr[0] = 0x08;
340     dptr[1] = 0x1B;
341     dptr[2] = 0x00;
342     memcpy(dptr + 3, addr, BLE_DEV_ADDR_LEN);
343     len += 9;
344 
345     g_host_adv_len = len;
346 
347     return len;
348 }
349 
350 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_ADVERTISER)
351 #if MYNEWT_VAL(BLE_ANDROID_MULTI_ADV_SUPPORT)
352 void
bletest_init_adv_instances(void)353 bletest_init_adv_instances(void)
354 {
355     uint8_t i;
356     int rc;
357     uint8_t *addr;
358     uint8_t adv_len;
359     uint8_t inst_allowed;
360     uint8_t rand_addr[BLE_DEV_ADDR_LEN];
361     struct hci_multi_adv_params adv;
362 
363     inst_allowed = MYNEWT_VAL(BLE_MULTI_ADV_INSTANCES);
364     if (inst_allowed > BLETEST_CFG_ADV_TEST_INSTANCES) {
365         inst_allowed = BLETEST_CFG_ADV_TEST_INSTANCES;
366     }
367 
368     /* Start up all the instances */
369     for (i = 1; i <= inst_allowed; ++i) {
370         memset(&adv, 0, sizeof(struct hci_multi_adv_params));
371 
372         adv.own_addr_type = bletest_multi_adv_instances[i-1].adv_own_addr_type;
373         if (adv.own_addr_type == BLE_HCI_ADV_OWN_ADDR_PUBLIC) {
374             addr = _g_dev_addr;
375         } else {
376             memcpy(rand_addr, _g_dev_addr, BLE_DEV_ADDR_LEN);
377             rand_addr[5] |= 0xc0;
378             rand_addr[0] = i;
379             /*
380              * NOTE: we overload own address type with a special case
381              * to denote if we use own address or call to set multi random
382              * address.
383              */
384             if (adv.own_addr_type == BLE_HCI_ADV_OWN_ADDR_RANDOM) {
385                 rc = bletest_hci_le_set_multi_rand_addr(rand_addr, i);
386                 assert(rc == 0);
387                 addr = rand_addr;
388             } else {
389                 adv.own_addr_type = BLE_HCI_ADV_OWN_ADDR_RANDOM;
390                 addr = rand_addr;
391                 memcpy(adv.own_addr, addr, BLE_DEV_ADDR_LEN);
392             }
393         }
394 
395         adv.adv_type = bletest_multi_adv_instances[i - 1].adv_type;
396         adv.adv_channel_map = 0x07;
397         adv.adv_filter_policy = BLE_HCI_ADV_FILT_NONE;
398         adv.peer_addr_type = BLE_HCI_ADV_PEER_ADDR_PUBLIC;
399         adv_len = bletest_set_adv_data(&g_host_adv_data[0], addr);
400 
401         adv.adv_itvl_min = bletest_multi_adv_instances[i - 1].adv_itvl;
402         adv.adv_itvl_max = bletest_multi_adv_instances[i - 1].adv_itvl;
403         adv.adv_tx_pwr = -1 * i;
404 
405         /* Set the advertising parameters */
406         rc = bletest_hci_le_set_multi_adv_params(&adv, i);
407         assert(rc == 0);
408 
409         /* Set advertising data */
410         if (adv_len != 0) {
411             rc = bletest_hci_le_set_multi_adv_data(&g_host_adv_data[0], adv_len,
412                                                    i);
413             assert(rc == 0);
414 
415             /* Set scan response data */
416             rc = bletest_hci_le_set_multi_scan_rsp_data(&g_host_adv_data[0],
417                                                         adv_len, i);
418             assert(rc == 0);
419         }
420 
421         /* Set the advertising parameters */
422         rc = bletest_hci_le_set_multi_adv_enable(1, i);
423         assert(rc == 0);
424     }
425 }
426 
427 void
bletest_init_advertising(uint8_t instance,int8_t txpwr)428 bletest_init_advertising(uint8_t instance, int8_t txpwr)
429 {
430     int rc;
431     int set_peer_addr;
432     uint8_t adv_len;
433     uint8_t *addr;
434     uint8_t rand_addr[BLE_DEV_ADDR_LEN];
435     struct hci_multi_adv_params adv;
436 
437     /* Make sure it is a valid instance */
438     assert(instance < BLE_LL_ADV_INSTANCES);
439 
440     /* Just zero out advertising */
441     set_peer_addr = 0;
442     memset(&adv, 0, sizeof(struct hci_multi_adv_params));
443 
444     /* If we are using a random address, we need to set it */
445     adv.own_addr_type = BLETEST_CFG_ADV_OWN_ADDR_TYPE;
446     if (adv.own_addr_type & 1) {
447         memcpy(rand_addr, _g_dev_addr, BLE_DEV_ADDR_LEN);
448         rand_addr[5] |= 0xc0;
449         if (BLETEST_CFG_MULTI_ADV_RANDOM_OWN == 1) {
450             addr = rand_addr;
451             memcpy(adv.own_addr, addr, BLE_DEV_ADDR_LEN);
452         } else {
453             rc = bletest_hci_le_set_multi_rand_addr(rand_addr, instance);
454             assert(rc == 0);
455             addr = rand_addr;
456         }
457     } else {
458         addr = _g_dev_addr;
459     }
460 
461     /* Set advertising parameters */
462     adv.adv_type = BLETEST_CFG_ADV_TYPE;
463     adv.adv_channel_map = 0x07;
464     adv.adv_filter_policy = BLETEST_CFG_ADV_FILT_POLICY;
465     if ((adv.adv_filter_policy & 1) || (BLETEST_CFG_ADV_ADDR_RES_EN == 1)) {
466         set_peer_addr = 1;
467     }
468     adv.peer_addr_type = BLETEST_CFG_ADV_PEER_ADDR_TYPE;
469     if ((adv.adv_type == BLE_HCI_ADV_TYPE_ADV_DIRECT_IND_HD) ||
470         (adv.adv_type == BLE_HCI_ADV_TYPE_ADV_DIRECT_IND_LD)) {
471         set_peer_addr = 1;
472         adv_len = 0;
473     } else {
474         adv_len = bletest_set_adv_data(&g_host_adv_data[0], addr);
475     }
476 
477     /* Not allowed for multi-adv command */
478     if (adv.own_addr_type > BLE_HCI_ADV_OWN_ADDR_RANDOM) {
479         assert(0);
480     }
481 
482     if (set_peer_addr) {
483         memcpy(adv.peer_addr, g_bletest_cur_peer_addr, BLE_DEV_ADDR_LEN);
484         if (adv.peer_addr_type == BLE_HCI_ADV_PEER_ADDR_RANDOM) {
485             adv.peer_addr[5] |= 0xc0;
486         }
487     }
488 
489     console_printf("Trying to connect to %x.%x.%x.%x.%x.%x\n",
490                    adv.peer_addr[0], adv.peer_addr[1], adv.peer_addr[2],
491                    adv.peer_addr[3], adv.peer_addr[4], adv.peer_addr[5]);
492 
493     if (adv.adv_type == BLE_HCI_ADV_TYPE_ADV_DIRECT_IND_HD) {
494         adv.adv_itvl_min = 0;
495         adv.adv_itvl_max = 0;
496     } else {
497         adv.adv_itvl_min = BLETEST_CFG_ADV_ITVL;
498         adv.adv_itvl_max = BLETEST_CFG_ADV_ITVL; /* Advertising interval */
499     }
500 
501     adv.adv_tx_pwr = txpwr;
502 
503     /* Set the advertising parameters */
504     rc = bletest_hci_le_set_multi_adv_params(&adv, instance);
505     assert(rc == 0);
506 
507     /* Set advertising data */
508     if (adv_len != 0) {
509         rc = bletest_hci_le_set_multi_adv_data(&g_host_adv_data[0], adv_len,
510                                                instance);
511         assert(rc == 0);
512 
513         /* Set scan response data */
514         rc = bletest_hci_le_set_multi_scan_rsp_data(&g_host_adv_data[0],adv_len,
515                                                     instance);
516         assert(rc == 0);
517     }
518 }
519 #else
520 void
bletest_init_advertising(void)521 bletest_init_advertising(void)
522 {
523     int rc;
524     int set_peer_addr;
525     uint8_t adv_len;
526     uint8_t *addr;
527     uint8_t rand_addr[BLE_DEV_ADDR_LEN];
528     struct hci_adv_params adv;
529 
530     /* Just zero out advertising */
531     set_peer_addr = 0;
532     memset(&adv, 0, sizeof(struct hci_adv_params));
533 
534     /* If we are using a random address, we need to set it */
535     adv.own_addr_type = BLETEST_CFG_ADV_OWN_ADDR_TYPE;
536     if (adv.own_addr_type & 1) {
537         memcpy(rand_addr, _g_dev_addr, BLE_DEV_ADDR_LEN);
538         rand_addr[5] |= 0xc0;
539         rc = bletest_hci_le_set_rand_addr(rand_addr);
540         assert(rc == 0);
541         addr = rand_addr;
542     } else {
543         addr = _g_dev_addr;
544     }
545 
546     /* Set advertising parameters */
547     adv.adv_type = BLETEST_CFG_ADV_TYPE;
548     adv.adv_channel_map = 0x07;
549     adv.adv_filter_policy = BLETEST_CFG_ADV_FILT_POLICY;
550     if ((adv.adv_filter_policy & 1) || (BLETEST_CFG_ADV_ADDR_RES_EN == 1)) {
551         set_peer_addr = 1;
552     }
553     adv.peer_addr_type = BLETEST_CFG_ADV_PEER_ADDR_TYPE;
554     if ((adv.adv_type == BLE_HCI_ADV_TYPE_ADV_DIRECT_IND_HD) ||
555         (adv.adv_type == BLE_HCI_ADV_TYPE_ADV_DIRECT_IND_LD)) {
556         set_peer_addr = 1;
557         adv_len = 0;
558     } else {
559         adv_len = bletest_set_adv_data(&g_host_adv_data[0], addr);
560     }
561 
562     if (adv.own_addr_type > BLE_HCI_ADV_OWN_ADDR_RANDOM) {
563         set_peer_addr = 1;
564     }
565 
566     if (set_peer_addr) {
567         memcpy(adv.peer_addr, g_bletest_cur_peer_addr, BLE_DEV_ADDR_LEN);
568         if (adv.peer_addr_type == BLE_HCI_ADV_PEER_ADDR_RANDOM) {
569             adv.peer_addr[5] |= 0xc0;
570         }
571     }
572 
573     console_printf("Trying to connect to %x.%x.%x.%x.%x.%x\n",
574                    adv.peer_addr[0], adv.peer_addr[1], adv.peer_addr[2],
575                    adv.peer_addr[3], adv.peer_addr[4], adv.peer_addr[5]);
576 
577     if (adv.adv_type == BLE_HCI_ADV_TYPE_ADV_DIRECT_IND_HD) {
578         adv.adv_itvl_min = 0;
579         adv.adv_itvl_max = 0;
580     } else {
581         adv.adv_itvl_min = BLETEST_CFG_ADV_ITVL;
582         adv.adv_itvl_max = BLETEST_CFG_ADV_ITVL; /* Advertising interval */
583     }
584 
585     /* Set the advertising parameters */
586     rc = bletest_hci_le_set_adv_params(&adv);
587     assert(rc == 0);
588 
589 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LL_PRIVACY) == 1)
590     if ((adv.own_addr_type > BLE_HCI_ADV_OWN_ADDR_RANDOM) ||
591         (BLETEST_CFG_ADV_ADDR_RES_EN == 1)) {
592         rc = bletest_hci_le_add_resolv_list(g_bletest_adv_irk,
593                                             g_bletest_init_irk,
594                                             adv.peer_addr,
595                                             adv.peer_addr_type);
596         assert(rc == 0);
597 
598         rc = bletest_hci_le_enable_resolv_list(1);
599         assert(rc == 0);
600     }
601 #endif
602 
603     /* Set advertising data */
604     if (adv_len != 0) {
605         rc = bletest_hci_le_set_adv_data(&g_host_adv_data[0], adv_len);
606         assert(rc == 0);
607 
608         /* Set scan response data */
609         rc = bletest_hci_le_set_scan_rsp_data(&g_host_adv_data[0], adv_len);
610         assert(rc == 0);
611     }
612 }
613 #endif  /* MULTI_ADV SUPPORT */
614 #endif  /* BLETEST_ROLE_ADVERTISER */
615 
616 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_SCANNER)
617 void
bletest_init_scanner(void)618 bletest_init_scanner(void)
619 {
620     int rc;
621     uint8_t own_addr_type;
622     uint8_t buf[BLE_HCI_SET_SCAN_PARAM_LEN];
623     uint8_t add_whitelist;
624 
625     own_addr_type = BLETEST_CFG_SCAN_OWN_ADDR_TYPE;
626     rc = ble_hs_hci_cmd_build_le_set_scan_params(BLETEST_CFG_SCAN_TYPE,
627                                                BLETEST_CFG_SCAN_ITVL,
628                                                BLETEST_CFG_SCAN_WINDOW,
629                                                own_addr_type,
630                                                BLETEST_CFG_SCAN_FILT_POLICY,
631                                                buf, sizeof buf);
632     assert(rc == 0);
633     rc = ble_hs_hci_cmd_tx_empty_ack(BLE_HCI_OP(BLE_HCI_OGF_LE,
634                                                 BLE_HCI_OCF_LE_SET_SCAN_PARAMS),
635                                                 buf, sizeof(buf));
636     assert(rc == 0);
637     if (rc == 0) {
638         add_whitelist = BLETEST_CFG_SCAN_FILT_POLICY;
639 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LL_PRIVACY) == 1)
640         if (own_addr_type > BLE_HCI_ADV_OWN_ADDR_RANDOM) {
641             rc = bletest_hci_le_add_resolv_list(g_bletest_init_irk,
642                                                 g_bletest_adv_irk,
643                                                 g_bletest_cur_peer_addr,
644                                                 BLETEST_CFG_ADV_PEER_ADDR_TYPE);
645             assert(rc == 0);
646 
647             rc = bletest_hci_le_enable_resolv_list(1);
648             assert(rc == 0);
649         }
650 #endif
651         if (add_whitelist & 1) {
652             rc = bletest_hci_le_add_to_whitelist(g_bletest_cur_peer_addr,
653                                                  BLE_ADDR_RANDOM);
654             assert(rc == 0);
655         }
656     }
657 }
658 
659 void
bletest_execute_scanner(void)660 bletest_execute_scanner(void)
661 {
662     int rc;
663 
664     /* Enable scanning */
665     if ((int32_t)(ble_npl_time_get() - g_next_os_time) >= 0) {
666         if (g_bletest_state) {
667             rc = bletest_hci_le_set_scan_enable(0, BLETEST_CFG_FILT_DUP_ADV);
668             assert(rc == 0);
669             g_bletest_state = 0;
670         } else {
671             rc = bletest_hci_le_set_scan_enable(1, BLETEST_CFG_FILT_DUP_ADV);
672             assert(rc == 0);
673             g_bletest_state = 1;
674         }
675         g_next_os_time += (OS_TICKS_PER_SEC * 60);
676     }
677 }
678 #endif
679 
680 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_INITIATOR)
681 void
bletest_init_initiator(void)682 bletest_init_initiator(void)
683 {
684     int rc;
685     uint8_t rand_addr[BLE_DEV_ADDR_LEN];
686     struct hci_create_conn *hcc;
687 
688     /* Enable initiating */
689     hcc = &g_cc;
690     hcc->conn_itvl_max = BLETEST_CFG_CONN_ITVL;
691     hcc->conn_itvl_min = BLETEST_CFG_CONN_ITVL;
692     hcc->conn_latency = BLETEST_CFG_SLAVE_LATENCY;
693     hcc->filter_policy = BLETEST_CFG_INIT_FILTER_POLICY;
694     hcc->supervision_timeout = BLETEST_CFG_CONN_SPVN_TMO;
695     hcc->scan_itvl = BLETEST_CFG_SCAN_ITVL;
696     hcc->scan_window = BLETEST_CFG_SCAN_WINDOW;
697     hcc->peer_addr_type = BLETEST_CFG_CONN_PEER_ADDR_TYPE;
698     memcpy(hcc->peer_addr, g_bletest_cur_peer_addr, BLE_DEV_ADDR_LEN);
699     if (hcc->peer_addr_type == BLE_HCI_CONN_PEER_ADDR_RANDOM) {
700         hcc->peer_addr[5] |= 0xc0;
701     }
702     hcc->own_addr_type = BLETEST_CFG_CONN_OWN_ADDR_TYPE;
703     hcc->min_ce_len = BLETEST_CFG_MIN_CE_LEN;
704     hcc->max_ce_len = BLETEST_CFG_MAX_CE_LEN;
705 
706     console_printf("Trying to connect to %x.%x.%x.%x.%x.%x\n",
707                    hcc->peer_addr[0], hcc->peer_addr[1], hcc->peer_addr[2],
708                    hcc->peer_addr[3], hcc->peer_addr[4], hcc->peer_addr[5]);
709 
710     /* If we are using a random address, we need to set it */
711     if (hcc->own_addr_type == BLE_HCI_ADV_OWN_ADDR_RANDOM) {
712         memcpy(rand_addr, _g_dev_addr, BLE_DEV_ADDR_LEN);
713         rand_addr[5] |= 0xc0;
714         rc = bletest_hci_le_set_rand_addr(rand_addr);
715         assert(rc == 0);
716     }
717 
718 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LL_PRIVACY) == 1)
719         if ((hcc->peer_addr_type > BLE_HCI_CONN_PEER_ADDR_RANDOM) ||
720             (hcc->own_addr_type > BLE_HCI_ADV_OWN_ADDR_RANDOM)) {
721             rc = bletest_hci_le_add_resolv_list(g_bletest_init_irk,
722                                                 g_bletest_adv_irk,
723                                                 g_bletest_cur_peer_addr,
724                                                 BLETEST_CFG_ADV_PEER_ADDR_TYPE);
725             assert(rc == 0);
726 
727             rc = bletest_hci_le_enable_resolv_list(1);
728             assert(rc == 0);
729         }
730 #endif
731 
732     bletest_hci_le_create_connection(hcc);
733 }
734 
735 void
bletest_execute_initiator(void)736 bletest_execute_initiator(void)
737 {
738     int i;
739     int rc;
740     int8_t rssi;
741     uint16_t handle;
742     uint8_t new_chan_map[5];
743 
744     /*
745      * Determine if there is an active connection for the current handle
746      * we are trying to create. If so, start looking for the next one
747      */
748     if (g_bletest_current_conns < BLETEST_CFG_CONCURRENT_CONNS) {
749         handle = g_bletest_current_conns + 1;
750         if (ble_hs_conn_find(handle)) {
751             /* Set LED to slower blink rate */
752             g_bletest_led_rate = OS_TICKS_PER_SEC;
753 
754             /* Ask for version information */
755             rc = bletest_hci_rd_rem_version(handle);
756 
757             /* Ask for remote used features */
758             rc = bletest_hci_le_read_rem_used_feat(handle);
759 
760             /* Add to current connections */
761             if (!rc) {
762                 ++g_bletest_current_conns;
763 
764                 /* Move to next connection */
765                 if (g_bletest_current_conns < BLETEST_CFG_CONCURRENT_CONNS) {
766                     /* restart initiating */
767                     g_bletest_cur_peer_addr[5] += 1;
768                     _g_dev_addr[5] += 1;
769                     bletest_init_initiator();
770                 }
771             }
772         } else {
773             bletest_hci_le_create_connection(&g_cc);
774         }
775     } else {
776         if ((int32_t)(ble_npl_time_get() - g_next_os_time) >= 0) {
777             if ((g_bletest_state == 1) || (g_bletest_state == 3)) {
778                 for (i = 0; i < g_bletest_current_conns; ++i) {
779                     if (ble_hs_conn_find(i + 1)) {
780                         bletest_hci_le_rd_chanmap(i+1);
781                     }
782                 }
783             } else if (g_bletest_state == 2) {
784                 new_chan_map[0] = 0;
785                 new_chan_map[1] = 0x3;
786                 new_chan_map[2] = 0;
787                 new_chan_map[3] = 0x1F;
788                 new_chan_map[4] = 0;
789                 bletest_hci_le_set_host_chan_class(new_chan_map);
790             } else if (g_bletest_state == 4) {
791 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_ENCRYPTION) == 1)
792                 struct hci_start_encrypt hsle;
793                 for (i = 0; i < g_bletest_current_conns; ++i) {
794                     if (ble_hs_conn_find(i + 1)) {
795                         hsle.connection_handle = i + 1;
796                         hsle.encrypted_diversifier = g_bletest_EDIV;
797                         hsle.random_number = g_bletest_RAND;
798                         swap_buf(hsle.long_term_key, (uint8_t *)g_bletest_LTK,
799                                  16);
800                         bletest_hci_le_start_encrypt(&hsle);
801                     }
802                 }
803 #endif
804             } else if (g_bletest_state == 8) {
805 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_ENCRYPTION) == 1)
806                 struct hci_start_encrypt hsle;
807                 for (i = 0; i < g_bletest_current_conns; ++i) {
808                     if (ble_hs_conn_find(i + 1)) {
809                         hsle.connection_handle = i + 1;
810                         hsle.encrypted_diversifier = g_bletest_EDIV;
811                         hsle.random_number = ~g_bletest_RAND;
812                         swap_buf(hsle.long_term_key, (uint8_t *)g_bletest_LTK,
813                                  16);
814                         bletest_hci_le_start_encrypt(&hsle);
815                     }
816                 }
817 #endif
818             } else {
819                 for (i = 0; i < g_bletest_current_conns; ++i) {
820                     if (ble_hs_conn_find(i + 1)) {
821                         ble_hs_hci_util_read_rssi(i+1, &rssi);
822                     }
823                 }
824             }
825 
826             ++g_bletest_state;
827             if (g_bletest_state > 9) {
828                 g_bletest_state = 9;
829             }
830             g_next_os_time = ble_npl_time_get() + OS_TICKS_PER_SEC * 3;
831         }
832     }
833 }
834 #endif
835 
836 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_ADVERTISER)
837 /*
838  * Test wrapper to get packets. Only get a packet if we have more than half
839  * left
840  */
841 static struct os_mbuf *
bletest_get_packet(void)842 bletest_get_packet(void)
843 {
844     struct os_mbuf *om;
845 
846     om = NULL;
847     if (os_msys_num_free() >= 5) {
848         om = os_msys_get_pkthdr(0, sizeof(struct ble_mbuf_hdr));
849     }
850     return om;
851 }
852 
853 static struct os_mbuf *
bletest_send_packet(uint16_t handle)854 bletest_send_packet(uint16_t handle)
855 {
856     int j;
857     uint8_t val;
858     struct os_mbuf *om;
859     uint16_t pktlen;
860 
861     om = bletest_get_packet();
862     if (om) {
863         /* set payload length */
864 #if BLETEST_THROUGHPUT_TEST
865         pktlen = BLETEST_PKT_SIZE;
866 #else
867 #if (BLETEST_CFG_RAND_PKT_SIZE == 1)
868         pktlen = rand() % (BLETEST_MAX_PKT_SIZE + 1);
869 #else
870         pktlen = BLETEST_PKT_SIZE;
871 #endif
872 #endif
873 
874         /* Put the HCI header in the mbuf */
875         put_le16(om->om_data, handle);
876         put_le16(om->om_data + 2, pktlen + 4);
877 
878         /* Place L2CAP header in packet */
879         put_le16(om->om_data + 4, pktlen);
880         om->om_data[6] = 0;
881         om->om_data[7] = 0;
882         om->om_len = 8;
883         OS_MBUF_PKTHDR(om)->omp_len = 8;
884 
885         /* Fill with incrementing pattern (starting from 1) */
886         for (j = 0; j < pktlen; ++j) {
887             val = j + 1;
888             os_mbuf_append(om, &val, 1);
889         }
890 
891         /* Transmit it */
892         ble_hci_trans_hs_acl_tx(om);
893     }
894 
895     return om;
896 }
897 
898 static void
bletest_execute_advertiser(void)899 bletest_execute_advertiser(void)
900 {
901     int i;
902 #if (BLETEST_CONCURRENT_CONN_TEST == 1)
903 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_ENCRYPTION) == 1)
904     uint16_t mask;
905     uint16_t reply_handle;
906 #endif
907 #endif
908     int rc;
909     uint16_t handle;
910     struct os_mbuf *om;
911 #if (BLETEST_THROUGHPUT_TEST == 1)
912     os_sr_t sr;
913     uint16_t completed_pkts;
914 #endif
915 
916     /* See if we should start advertising again */
917     if (g_bletest_current_conns < BLETEST_CFG_CONCURRENT_CONNS) {
918         handle = g_bletest_current_conns + 1;
919         if (ble_hs_conn_find(handle)) {
920             /* Set LED to slower blink rate */
921             g_bletest_led_rate = OS_TICKS_PER_SEC;
922 
923 #if (BLETEST_THROUGHPUT_TEST == 1)
924             /* Set next os time to 10 seconds after 1st connection */
925             if (g_next_os_time == 0) {
926                 g_next_os_time = os_time_get() + (10 * OS_TICKS_PER_SEC);
927                 g_bletest_handle = handle;
928             }
929 #endif
930             /* Send the remote used features command */
931             rc = bletest_hci_le_read_rem_used_feat(handle);
932             if (rc) {
933                 return;
934             }
935 
936             /* Send the remote read version command */
937             rc = bletest_hci_rd_rem_version(handle);
938             if (rc) {
939                 return;
940             }
941 
942             /* set conn update time */
943             g_bletest_conn_upd_time = ble_npl_time_get() + (OS_TICKS_PER_SEC * 5);
944             g_bletest_start_update = 1;
945 
946             /* Add to current connections */
947             ++g_bletest_current_conns;
948 
949             /* Move to next connection */
950             if (g_bletest_current_conns < BLETEST_CFG_CONCURRENT_CONNS) {
951                 /* restart initiating */
952                 g_bletest_cur_peer_addr[5] += 1;
953                 _g_dev_addr[5] += 1;
954 #if MYNEWT_VAL(BLE_ANDROID_MULTI_ADV_SUPPORT)
955                 bletest_init_advertising(0,0);
956                 bletest_hci_le_set_multi_adv_enable(1, 0);
957 #else
958                 bletest_init_advertising();
959                 bletest_hci_le_set_adv_enable(1);
960 #endif
961             }
962         } else {
963             /* If we failed to start advertising we should keep trying */
964 #if MYNEWT_VAL(BLE_ANDROID_MULTI_ADV_SUPPORT)
965             bletest_hci_le_set_multi_adv_enable(1, 0);
966 #else
967             bletest_hci_le_set_adv_enable(1);
968 #endif
969         }
970     }
971 #if 0
972     if (g_bletest_start_update) {
973         if ((int32_t)(os_time_get() - g_bletest_conn_upd_time) >= 0) {
974             bletest_send_conn_update(1);
975             g_bletest_start_update = 0;
976         }
977     }
978 #endif
979 
980 #if (BLETEST_CONCURRENT_CONN_TEST == 1)
981     /* See if it is time to hand a data packet to the connection */
982     if ((int32_t)(ble_npl_time_get() - g_next_os_time) >= 0) {
983 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_ENCRYPTION) == 1)
984         /* Do we need to send a LTK reply? */
985         mask = 1;
986         reply_handle = 1;
987         while (g_bletest_ltk_reply_handle && mask) {
988             if (g_bletest_ltk_reply_handle & mask) {
989                 bletest_send_ltk_req_reply(reply_handle);
990                 //bletest_send_ltk_req_neg_reply(reply_handle);
991                 g_bletest_ltk_reply_handle &= ~mask;
992             }
993             ++reply_handle;
994             mask <<= 1;
995         }
996 #endif
997         if (g_bletest_current_conns) {
998             for (i = 0; i < g_bletest_current_conns; ++i) {
999                 if ((g_last_handle_used == 0) ||
1000                     (g_last_handle_used > g_bletest_current_conns)) {
1001                     g_last_handle_used = 1;
1002                 }
1003                 handle = g_last_handle_used;
1004                 if (ble_hs_conn_find(handle)) {
1005                     om = bletest_send_packet(handle);
1006                     if (om) {
1007                         /* Increment last handle used */
1008                         ++g_last_handle_used;
1009                     }
1010                 } else {
1011                     ++g_last_handle_used;
1012                 }
1013             }
1014         }
1015         g_next_os_time = ble_npl_time_get() + OS_TICKS_PER_SEC;
1016     }
1017 #endif
1018 
1019 #if (BLETEST_THROUGHPUT_TEST == 1)
1020     /* Nothing to do if no connections */
1021     if (!g_bletest_current_conns) {
1022         return;
1023     }
1024 
1025     /* See if it is time to start throughput testing */
1026     if ((int32_t)(os_time_get() - g_next_os_time) >= 0) {
1027         /* Keep window full */
1028         OS_ENTER_CRITICAL(sr);
1029         completed_pkts = g_bletest_completed_pkts;
1030         g_bletest_completed_pkts = 0;
1031         OS_EXIT_CRITICAL(sr);
1032 
1033         assert(g_bletest_outstanding_pkts >= completed_pkts);
1034         g_bletest_outstanding_pkts -= completed_pkts;
1035 
1036         while (g_bletest_outstanding_pkts < 20) {
1037             om = bletest_send_packet(g_bletest_handle);
1038             if (om) {
1039                 ++g_bletest_outstanding_pkts;
1040             }
1041         }
1042     }
1043 #endif /* XXX: throughput test */
1044 }
1045 #endif /* XXX: BLETEST_ROLE_ADVERTISER */
1046 
1047 /**
1048  * Main bletest function. Called by the task timer every 50 msecs.
1049  *
1050  */
1051 void
bletest_execute(void)1052 bletest_execute(void)
1053 {
1054     /* Toggle LED at set rate */
1055     if ((int32_t)(ble_npl_time_get() - g_bletest_next_led_time) >= 0) {
1056         // hal_gpio_toggle(LED_BLINK_PIN);
1057         g_bletest_next_led_time = ble_npl_time_get() + g_bletest_led_rate;
1058     }
1059 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_ADVERTISER)
1060     bletest_execute_advertiser();
1061 #endif
1062 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_SCANNER)
1063     bletest_execute_scanner();
1064 #endif
1065 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_INITIATOR)
1066     bletest_execute_initiator();
1067 #endif
1068 }
1069 
1070 /**
1071  * Callback when BLE test timer expires.
1072  *
1073  * @param arg
1074  */
1075 void
bletest_timer_cb(struct ble_npl_event * ev)1076 bletest_timer_cb(struct ble_npl_event *ev)
1077 {
1078     /* Call the bletest code */
1079     bletest_execute();
1080 
1081     /* Re-start the timer (run every 10 msecs) */
1082     ble_npl_callout_reset(&g_bletest_timer, OS_TICKS_PER_SEC / 100);
1083 }
1084 
1085 /**
1086  * BLE test task
1087  *
1088  * @param arg
1089  */
1090 void
bletest_task_handler(void * arg)1091 bletest_task_handler(void *arg)
1092 {
1093     int rc;
1094     uint64_t rand64;
1095     uint64_t event_mask;
1096 
1097     /* Set LED blink rate */
1098     g_bletest_led_rate = OS_TICKS_PER_SEC / 20;
1099 
1100     /* Wait one second before starting test task */
1101     ble_npl_time_delay(OS_TICKS_PER_SEC);
1102 
1103     /* Initialize the host timer */
1104     ble_npl_callout_init(&g_bletest_timer, &g_bletest_evq, bletest_timer_cb,
1105                     NULL);
1106 
1107     ble_hs_dbg_set_sync_state(BLE_HS_SYNC_STATE_GOOD);
1108 
1109     /* Send the reset command first */
1110     rc = bletest_hci_reset_ctlr();
1111     assert(rc == 0);
1112 
1113 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_ADVERTISER)
1114     /* Initialize the advertiser */
1115     console_printf("Starting BLE test task as advertiser\n");
1116 #if MYNEWT_VAL(BLE_ANDROID_MULTI_ADV_SUPPORT)
1117     /* Start up all advertising instances except default one */
1118     bletest_init_adv_instances();
1119 
1120     /* Start advertising on instance 0 at 0 dbm */
1121     bletest_init_advertising(0, 0);
1122 #else
1123     bletest_init_advertising();
1124 #endif
1125 #endif
1126 
1127 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_SCANNER)
1128     /* Initialize the scanner */
1129     console_printf("Starting BLE test task as scanner\n");
1130     bletest_init_scanner();
1131 #endif
1132 
1133 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_INITIATOR)
1134     /* Initialize the scanner */
1135     console_printf("Starting BLE test task as initiator\n");
1136     bletest_init_initiator();
1137 #endif
1138 
1139     /* Read unique HW id */
1140     // rc = hal_bsp_hw_id((void *)&g_bletest_hw_id[0], sizeof(g_bletest_hw_id));
1141     // assert(rc == 16);
1142     console_printf("HW id=%04x%04x%04x%04x\n",
1143                    (unsigned int)g_bletest_hw_id[0],
1144                    (unsigned int)g_bletest_hw_id[1],
1145                    (unsigned int)g_bletest_hw_id[2],
1146                    (unsigned int)g_bletest_hw_id[3]);
1147 
1148     /* Set the event mask we want to display */
1149     event_mask = 0x7FF;
1150     rc = bletest_hci_le_set_event_mask(event_mask);
1151     assert(rc == 0);
1152 
1153     /* Turn on all events */
1154     event_mask = 0xffffffffffffffff;
1155     rc = bletest_hci_set_event_mask(event_mask);
1156     assert(rc == 0);
1157 
1158     /* Read device address */
1159     rc = bletest_hci_rd_bd_addr();
1160     assert(rc == 0);
1161 
1162     /* Read local features */
1163     rc = bletest_hci_rd_local_feat();
1164     assert(rc == 0);
1165 
1166     /* Read local commands */
1167     rc = bletest_hci_rd_local_supp_cmd();
1168     assert(rc == 0);
1169 
1170     /* Read version */
1171     rc = bletest_hci_rd_local_version();
1172     assert(rc == 0);
1173 
1174     /* Read supported states */
1175     rc = bletest_hci_le_read_supp_states();
1176     assert(rc == 0);
1177 
1178     /* Read maximum data length */
1179     rc = bletest_hci_le_rd_max_datalen();
1180     assert(rc == 0);
1181 
1182 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_DATA_LEN_EXT) == 1)
1183     /* Read suggested data length */
1184     rc = bletest_hci_le_rd_sugg_datalen();
1185     assert(rc == 0);
1186 
1187     /* write suggested default data length */
1188     rc = bletest_hci_le_write_sugg_datalen(BLETEST_CFG_SUGG_DEF_TXOCTETS,
1189                                            BLETEST_CFG_SUGG_DEF_TXTIME);
1190     assert(rc == 0);
1191 
1192     /* Read suggested data length */
1193     rc = bletest_hci_le_rd_sugg_datalen();
1194     assert(rc == 0);
1195 
1196     /* Set data length (note: we know there is no connection; just a test) */
1197     rc = bletest_hci_le_set_datalen(0x1234, BLETEST_CFG_SUGG_DEF_TXOCTETS,
1198                                     BLETEST_CFG_SUGG_DEF_TXTIME);
1199     assert(rc != 0);
1200 #endif
1201 
1202     /* Encrypt a block */
1203 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_ENCRYPTION) == 1)
1204     rc = bletest_hci_le_encrypt((uint8_t *)g_ble_ll_encrypt_test_key,
1205                                 (uint8_t *)g_ble_ll_encrypt_test_plain_text);
1206     assert(rc == 0);
1207 #endif
1208 
1209     /* Get a random number */
1210     rc = ble_hs_hci_util_rand(&rand64, 8);
1211     assert(rc == 0);
1212 
1213     /* Wait some time before starting */
1214     ble_npl_time_delay(OS_TICKS_PER_SEC);
1215 
1216     /* Init state */
1217     g_bletest_state = 0;
1218 
1219     /* Begin advertising if we are an advertiser */
1220 #if (BLETEST_CFG_ROLE == BLETEST_ROLE_ADVERTISER)
1221 #if MYNEWT_VAL(BLE_ANDROID_MULTI_ADV_SUPPORT)
1222     rc = bletest_hci_le_set_multi_adv_enable(1, 0);
1223     assert(rc == 0);
1224 #else
1225     rc = bletest_hci_le_set_adv_enable(1);
1226     assert(rc == 0);
1227 #endif
1228 #endif
1229 
1230     bletest_timer_cb(NULL);
1231 }
1232 
1233 extern int nimble_ble_enable(void);
1234 /**
1235  * main
1236  *
1237  * The main task for the project. This function initializes the packages,
1238  * then starts serving events from default event queue.
1239  *
1240  * @return int NOTE: this function should never return!
1241  */
bletest(void)1242 static int bletest(void)
1243 {
1244     rt_thread_t tid;
1245 
1246     /* startup bluetooth host stack*/
1247     ble_hs_thread_startup();
1248 
1249     /* Dummy device address */
1250 #if BLETEST_CFG_ROLE == BLETEST_ROLE_ADVERTISER
1251     _g_dev_addr[0] = 0x00;
1252     _g_dev_addr[1] = 0x00;
1253     _g_dev_addr[2] = 0x00;
1254     _g_dev_addr[3] = 0x88;
1255     _g_dev_addr[4] = 0x88;
1256     _g_dev_addr[5] = 0x08;
1257 
1258     g_bletest_cur_peer_addr[0] = 0x00;
1259     g_bletest_cur_peer_addr[1] = 0x00;
1260     g_bletest_cur_peer_addr[2] = 0x00;
1261     g_bletest_cur_peer_addr[3] = 0x99;
1262     g_bletest_cur_peer_addr[4] = 0x99;
1263     g_bletest_cur_peer_addr[5] = 0x09;
1264 #else
1265     _g_dev_addr[0] = 0x00;
1266     _g_dev_addr[1] = 0x00;
1267     _g_dev_addr[2] = 0x00;
1268     _g_dev_addr[3] = 0x99;
1269     _g_dev_addr[4] = 0x99;
1270     _g_dev_addr[5] = 0x09;
1271 
1272     g_bletest_cur_peer_addr[0] = 0x00;
1273     g_bletest_cur_peer_addr[1] = 0x00;
1274     g_bletest_cur_peer_addr[2] = 0x00;
1275     g_bletest_cur_peer_addr[3] = 0x88;
1276     g_bletest_cur_peer_addr[4] = 0x88;
1277     g_bletest_cur_peer_addr[5] = 0x08;
1278 #endif
1279 
1280     /* Set the led pin as an output */
1281     // g_led_pin = LED_BLINK_PIN;
1282     // hal_gpio_init_out(g_led_pin, 1);
1283 
1284     /* Initialize eventq for bletest task */
1285     ble_npl_eventq_init(&g_bletest_evq);
1286 
1287     tid = rt_thread_create("ble_test", bletest_task_handler, RT_NULL, 1024, 10, 10);
1288     if(tid != RT_NULL)
1289         rt_thread_startup(tid);
1290 
1291     return 0;
1292 }
1293 MSH_CMD_EXPORT_ALIAS(bletest, bletest, "bluetooth test sample");
1294