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 #include <stdint.h>
20 #include <assert.h>
21 #include <string.h>
22 #include "syscfg/syscfg.h"
23 #include "nimble/ble.h"
24 #include "nimble/hci_common.h"
25 #include "nimble/ble_hci_trans.h"
26 #include "controller/ble_ll.h"
27 #include "controller/ble_ll_hci.h"
28 #include "controller/ble_ll_ctrl.h"
29 #include "ble_ll_conn_priv.h"
30
31 #if (BLETEST_CONCURRENT_CONN_TEST == 1)
32 extern void bletest_ltk_req_reply(uint16_t handle);
33 #endif
34
35 /**
36 * Send a data length change event for a connection to the host.
37 *
38 * @param connsm Pointer to connection state machine
39 */
40 void
ble_ll_hci_ev_datalen_chg(struct ble_ll_conn_sm * connsm)41 ble_ll_hci_ev_datalen_chg(struct ble_ll_conn_sm *connsm)
42 {
43 uint8_t *evbuf;
44
45 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_DATA_LEN_CHG)) {
46 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
47 if (evbuf) {
48 evbuf[0] = BLE_HCI_EVCODE_LE_META;
49 evbuf[1] = BLE_HCI_LE_DATA_LEN_CHG_LEN;
50 evbuf[2] = BLE_HCI_LE_SUBEV_DATA_LEN_CHG;
51 put_le16(evbuf + 3, connsm->conn_handle);
52 put_le16(evbuf + 5, connsm->eff_max_tx_octets);
53 put_le16(evbuf + 7, connsm->eff_max_tx_time);
54 put_le16(evbuf + 9, connsm->eff_max_rx_octets);
55 put_le16(evbuf + 11, connsm->eff_max_rx_time);
56 ble_ll_hci_event_send(evbuf);
57 }
58 }
59 }
60
61 /**
62 * Send a connection parameter request event for a connection to the host.
63 *
64 * @param connsm Pointer to connection state machine
65 */
66 void
ble_ll_hci_ev_rem_conn_parm_req(struct ble_ll_conn_sm * connsm,struct ble_ll_conn_params * cp)67 ble_ll_hci_ev_rem_conn_parm_req(struct ble_ll_conn_sm *connsm,
68 struct ble_ll_conn_params *cp)
69 {
70 uint8_t *evbuf;
71
72 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_REM_CONN_PARM_REQ)) {
73 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
74 if (evbuf) {
75 evbuf[0] = BLE_HCI_EVCODE_LE_META;
76 evbuf[1] = BLE_HCI_LE_REM_CONN_PARM_REQ_LEN;
77 evbuf[2] = BLE_HCI_LE_SUBEV_REM_CONN_PARM_REQ;
78 put_le16(evbuf + 3, connsm->conn_handle);
79 put_le16(evbuf + 5, cp->interval_min);
80 put_le16(evbuf + 7, cp->interval_max);
81 put_le16(evbuf + 9, cp->latency);
82 put_le16(evbuf + 11, cp->timeout);
83 ble_ll_hci_event_send(evbuf);
84 }
85 }
86 }
87
88 /**
89 * Send a connection update event.
90 *
91 * @param connsm Pointer to connection state machine
92 * @param status The error code.
93 */
94 void
ble_ll_hci_ev_conn_update(struct ble_ll_conn_sm * connsm,uint8_t status)95 ble_ll_hci_ev_conn_update(struct ble_ll_conn_sm *connsm, uint8_t status)
96 {
97 uint8_t *evbuf;
98
99 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_CONN_UPD_COMPLETE)) {
100 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
101 if (evbuf) {
102 evbuf[0] = BLE_HCI_EVCODE_LE_META;
103 evbuf[1] = BLE_HCI_LE_CONN_UPD_LEN;
104 evbuf[2] = BLE_HCI_LE_SUBEV_CONN_UPD_COMPLETE;
105 evbuf[3] = status;
106 put_le16(evbuf + 4, connsm->conn_handle);
107 put_le16(evbuf + 6, connsm->conn_itvl);
108 put_le16(evbuf + 8, connsm->slave_latency);
109 put_le16(evbuf + 10, connsm->supervision_tmo);
110 ble_ll_hci_event_send(evbuf);
111 }
112 }
113 }
114
115 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_ENCRYPTION) == 1)
116 void
ble_ll_hci_ev_encrypt_chg(struct ble_ll_conn_sm * connsm,uint8_t status)117 ble_ll_hci_ev_encrypt_chg(struct ble_ll_conn_sm *connsm, uint8_t status)
118 {
119 uint8_t evcode;
120 uint8_t *evbuf;
121 uint8_t evlen;
122
123 if (CONN_F_ENC_CHANGE_SENT(connsm) == 0) {
124 evcode = BLE_HCI_EVCODE_ENCRYPT_CHG;
125 evlen = BLE_HCI_EVENT_ENCRYPT_CHG_LEN;
126 } else {
127 evcode = BLE_HCI_EVCODE_ENC_KEY_REFRESH;
128 evlen = BLE_HCI_EVENT_ENC_KEY_REFRESH_LEN;
129 }
130
131 if (ble_ll_hci_is_event_enabled(evcode)) {
132 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
133 if (evbuf) {
134 evbuf[0] = evcode;
135 evbuf[1] = evlen;
136 evbuf[2] = status;
137 put_le16(evbuf + 3, connsm->conn_handle);
138 if (evcode == BLE_HCI_EVCODE_ENCRYPT_CHG) {
139 if (status == BLE_ERR_SUCCESS) {
140 evbuf[5] = 0x01;
141 } else {
142 evbuf[5] = 0;
143 }
144 }
145 ble_ll_hci_event_send(evbuf);
146 }
147 }
148 CONN_F_ENC_CHANGE_SENT(connsm) = 1;
149 }
150
151 /**
152 * Send a long term key request event for a connection to the host.
153 *
154 * @param connsm Pointer to connection state machine
155 */
156 int
ble_ll_hci_ev_ltk_req(struct ble_ll_conn_sm * connsm)157 ble_ll_hci_ev_ltk_req(struct ble_ll_conn_sm *connsm)
158 {
159 int rc;
160 uint8_t *evbuf;
161
162 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_LT_KEY_REQ)) {
163 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
164 if (evbuf) {
165 evbuf[0] = BLE_HCI_EVCODE_LE_META;
166 evbuf[1] = BLE_HCI_LE_LT_KEY_REQ_LEN;
167 evbuf[2] = BLE_HCI_LE_SUBEV_LT_KEY_REQ;
168 put_le16(evbuf + 3, connsm->conn_handle);
169 put_le64(evbuf + 5, connsm->enc_data.host_rand_num);
170 put_le16(evbuf + 13, connsm->enc_data.enc_div);
171 ble_ll_hci_event_send(evbuf);
172 }
173 rc = 0;
174 } else {
175 rc = -1;
176 }
177
178 #if (BLETEST_CONCURRENT_CONN_TEST == 1)
179 if (rc == 0) {
180 bletest_ltk_req_reply(connsm->conn_handle);
181 }
182 #endif
183 return rc;
184 }
185 #endif
186
187 void
ble_ll_hci_ev_rd_rem_used_feat(struct ble_ll_conn_sm * connsm,uint8_t status)188 ble_ll_hci_ev_rd_rem_used_feat(struct ble_ll_conn_sm *connsm, uint8_t status)
189 {
190 uint8_t *evbuf;
191
192 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_RD_REM_USED_FEAT)) {
193 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
194 if (evbuf) {
195 evbuf[0] = BLE_HCI_EVCODE_LE_META;
196 evbuf[1] = BLE_HCI_LE_RD_REM_USED_FEAT_LEN;
197 evbuf[2] = BLE_HCI_LE_SUBEV_RD_REM_USED_FEAT;
198 evbuf[3] = status;
199 put_le16(evbuf + 4, connsm->conn_handle);
200 memset(evbuf + 6, 0, BLE_HCI_RD_LOC_SUPP_FEAT_RSPLEN);
201 evbuf[6] = connsm->conn_features;
202 memcpy(evbuf + 7, connsm->remote_features, 7);
203 ble_ll_hci_event_send(evbuf);
204 }
205 }
206 }
207
208 void
ble_ll_hci_ev_rd_rem_ver(struct ble_ll_conn_sm * connsm,uint8_t status)209 ble_ll_hci_ev_rd_rem_ver(struct ble_ll_conn_sm *connsm, uint8_t status)
210 {
211 uint8_t *evbuf;
212
213 if (ble_ll_hci_is_event_enabled(BLE_HCI_EVCODE_RD_REM_VER_INFO_CMP)) {
214 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
215 if (evbuf) {
216 evbuf[0] = BLE_HCI_EVCODE_RD_REM_VER_INFO_CMP;
217 evbuf[1] = BLE_HCI_EVENT_RD_RM_VER_LEN;
218 evbuf[2] = status;
219 put_le16(evbuf + 3, connsm->conn_handle);
220 evbuf[5] = connsm->vers_nr;
221 put_le16(evbuf + 6, connsm->comp_id);
222 put_le16(evbuf + 8, connsm->sub_vers_nr);
223 ble_ll_hci_event_send(evbuf);
224 }
225 }
226 }
227
228 /**
229 * Send a HW error to the host.
230 *
231 * @param hw_err
232 *
233 * @return int 0: event masked or event sent, -1 otherwise
234 */
235 int
ble_ll_hci_ev_hw_err(uint8_t hw_err)236 ble_ll_hci_ev_hw_err(uint8_t hw_err)
237 {
238 int rc;
239 uint8_t *evbuf;
240
241 rc = 0;
242 if (ble_ll_hci_is_event_enabled(BLE_HCI_EVCODE_HW_ERROR)) {
243 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
244 if (evbuf) {
245 evbuf[0] = BLE_HCI_EVCODE_HW_ERROR;
246 evbuf[1] = BLE_HCI_EVENT_HW_ERROR_LEN;
247 evbuf[2] = hw_err;
248 ble_ll_hci_event_send(evbuf);
249 } else {
250 rc = -1;
251 }
252 }
253 return rc;
254 }
255
256 void
ble_ll_hci_ev_databuf_overflow(void)257 ble_ll_hci_ev_databuf_overflow(void)
258 {
259 uint8_t *evbuf;
260
261 if (ble_ll_hci_is_event_enabled(BLE_HCI_EVCODE_DATA_BUF_OVERFLOW)) {
262 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
263 if (evbuf) {
264 evbuf[0] = BLE_HCI_EVCODE_DATA_BUF_OVERFLOW;
265 evbuf[1] = BLE_HCI_EVENT_DATABUF_OVERFLOW_LEN;
266 evbuf[2] = BLE_HCI_EVENT_ACL_BUF_OVERFLOW;
267 ble_ll_hci_event_send(evbuf);
268 }
269 }
270 }
271
272 /**
273 * Send a LE Channel Selection Algorithm event.
274 *
275 * @param connsm Pointer to connection state machine
276 */
277 #if (MYNEWT_VAL(BLE_LL_CFG_FEAT_LE_CSA2) == 1)
278 void
ble_ll_hci_ev_le_csa(struct ble_ll_conn_sm * connsm)279 ble_ll_hci_ev_le_csa(struct ble_ll_conn_sm *connsm)
280 {
281 uint8_t *evbuf;
282
283 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_CHAN_SEL_ALG)) {
284 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
285 if (evbuf) {
286 evbuf[0] = BLE_HCI_EVCODE_LE_META;
287 evbuf[1] = BLE_HCI_LE_SUBEV_CHAN_SEL_ALG_LEN;
288 evbuf[2] = BLE_HCI_LE_SUBEV_CHAN_SEL_ALG;
289 put_le16(evbuf + 3, connsm->conn_handle);
290 evbuf[5] = connsm->csmflags.cfbit.csa2_supp ? 0x01 : 0x00;
291 ble_ll_hci_event_send(evbuf);
292 }
293 }
294 }
295 #endif
296
297 /**
298 * Sends the LE Scan Request Received event
299 *
300 */
301 #if MYNEWT_VAL(BLE_LL_CFG_FEAT_LL_EXT_ADV)
302 void
ble_ll_hci_ev_send_scan_req_recv(uint8_t adv_handle,const uint8_t * peer,uint8_t peer_addr_type)303 ble_ll_hci_ev_send_scan_req_recv(uint8_t adv_handle, const uint8_t *peer,
304 uint8_t peer_addr_type)
305 {
306 uint8_t *evbuf;
307
308 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_SCAN_REQ_RCVD)) {
309 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
310 if (evbuf) {
311 evbuf[0] = BLE_HCI_EVCODE_LE_META;
312 evbuf[1] = BLE_HCI_LE_SUBEV_SCAN_REQ_RCVD_LEN;
313 evbuf[2] = BLE_HCI_LE_SUBEV_SCAN_REQ_RCVD;
314 evbuf[3] = adv_handle;
315 evbuf[4] = peer_addr_type;
316 memcpy(&evbuf[5], peer, BLE_DEV_ADDR_LEN);
317 ble_ll_hci_event_send(evbuf);
318 }
319 }
320 }
321 #endif
322
323 /**
324 * Sends the LE Scan Timeout Event
325 *
326 */
327 #if MYNEWT_VAL(BLE_LL_CFG_FEAT_LL_EXT_ADV)
328 void
ble_ll_hci_ev_send_scan_timeout(void)329 ble_ll_hci_ev_send_scan_timeout(void)
330 {
331 uint8_t *evbuf;
332
333 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_SCAN_TIMEOUT)) {
334 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
335 if (evbuf) {
336 evbuf[0] = BLE_HCI_EVCODE_LE_META;
337 evbuf[1] = BLE_HCI_LE_SUBEV_SCAN_TIMEOUT_LEN;
338 evbuf[2] = BLE_HCI_LE_SUBEV_SCAN_TIMEOUT;
339 ble_ll_hci_event_send(evbuf);
340 }
341 }
342 }
343 #endif
344
345 /**
346 * Sends the LE Advertising Set Terminated event
347 *
348 */
349 #if MYNEWT_VAL(BLE_LL_CFG_FEAT_LL_EXT_ADV)
350 void
ble_ll_hci_ev_send_adv_set_terminated(uint8_t status,uint8_t adv_handle,uint16_t conn_handle,uint8_t events)351 ble_ll_hci_ev_send_adv_set_terminated(uint8_t status, uint8_t adv_handle,
352 uint16_t conn_handle, uint8_t events)
353 {
354 uint8_t *evbuf;
355
356 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_ADV_SET_TERMINATED)) {
357 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
358 if (evbuf) {
359 evbuf[0] = BLE_HCI_EVCODE_LE_META;
360 evbuf[1] = BLE_HCI_LE_SUBEV_ADV_SET_TERMINATED_LEN;
361 evbuf[2] = BLE_HCI_LE_SUBEV_ADV_SET_TERMINATED;
362 evbuf[3] = status;
363 evbuf[4] = adv_handle;
364 put_le16(evbuf + 5, conn_handle);
365 evbuf[7] = events;
366 ble_ll_hci_event_send(evbuf);
367 }
368 }
369 }
370 #endif
371
372 /**
373 * Send a PHY update complete event
374 *
375 * @param connsm Pointer to connection state machine
376 * @param status error status of event
377 */
378 #if (BLE_LL_BT5_PHY_SUPPORTED == 1)
379 int
ble_ll_hci_ev_phy_update(struct ble_ll_conn_sm * connsm,uint8_t status)380 ble_ll_hci_ev_phy_update(struct ble_ll_conn_sm *connsm, uint8_t status)
381 {
382 int rc;
383 uint8_t *evbuf;
384
385 rc = 0;
386 if (ble_ll_hci_is_le_event_enabled(BLE_HCI_LE_SUBEV_PHY_UPDATE_COMPLETE)) {
387 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
388 if (evbuf) {
389 evbuf[0] = BLE_HCI_EVCODE_LE_META;
390 evbuf[1] = BLE_HCI_LE_PHY_UPD_LEN;
391 evbuf[2] = BLE_HCI_LE_SUBEV_PHY_UPDATE_COMPLETE;
392 evbuf[3] = status;
393 put_le16(evbuf + 4, connsm->conn_handle);
394 evbuf[6] = connsm->phy_data.cur_tx_phy;
395 evbuf[7] = connsm->phy_data.cur_rx_phy;
396 ble_ll_hci_event_send(evbuf);
397 } else {
398 rc = BLE_ERR_MEM_CAPACITY;
399 }
400 }
401 return rc;
402 }
403 #endif
404
405 void
ble_ll_hci_ev_send_vendor_err(char * file,uint32_t line)406 ble_ll_hci_ev_send_vendor_err(char *file, uint32_t line)
407 {
408 uint8_t *evbuf;
409 uint8_t file_len = strlen(file);
410
411 evbuf = ble_hci_trans_buf_alloc(BLE_HCI_TRANS_BUF_EVT_HI);
412 if (!evbuf) {
413 return;
414 }
415
416 evbuf[0] = BLE_HCI_EVCODE_VENDOR_DEBUG;
417 evbuf[1] = file_len + sizeof(line) + 1;
418 /* Debug id for future use */
419 evbuf[2] = 0x00;
420 memcpy(&evbuf[3], file, file_len);
421 put_le32(&evbuf[3] + file_len, line);
422 ble_ll_hci_event_send(evbuf);
423 }
424