1 /******************************************************************************
2 *
3 * Copyright (C) 1999-2012 Broadcom Corporation
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at:
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 *
17 ******************************************************************************/
18
19 /******************************************************************************
20 *
21 * This file contains function of the HCIC unit to format and send HCI
22 * commands.
23 *
24 ******************************************************************************/
25
26 #include "bt_common.h"
27 #include "bt_target.h"
28 #include "btu.h"
29 #include "hcidefs.h"
30 #include "hcimsgs.h"
31
32 #include <base/bind.h>
33 #include <stddef.h>
34 #include <string.h>
35
btsnd_hcic_ble_set_local_used_feat(uint8_t feat_set[8])36 void btsnd_hcic_ble_set_local_used_feat(uint8_t feat_set[8]) {
37 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
38 uint8_t* pp = (uint8_t*)(p + 1);
39
40 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_SET_USED_FEAT_CMD;
41 p->offset = 0;
42
43 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_LOCAL_SPT_FEAT);
44 ARRAY_TO_STREAM(pp, feat_set, HCIC_PARAM_SIZE_SET_USED_FEAT_CMD);
45
46 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
47 }
48
btsnd_hcic_ble_set_random_addr(BD_ADDR random_bda)49 void btsnd_hcic_ble_set_random_addr(BD_ADDR random_bda) {
50 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
51 uint8_t* pp = (uint8_t*)(p + 1);
52
53 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_WRITE_RANDOM_ADDR_CMD;
54 p->offset = 0;
55
56 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_RANDOM_ADDR);
57 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_WRITE_RANDOM_ADDR_CMD);
58
59 BDADDR_TO_STREAM(pp, random_bda);
60
61 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
62 }
63
btsnd_hcic_ble_write_adv_params(uint16_t adv_int_min,uint16_t adv_int_max,uint8_t adv_type,uint8_t addr_type_own,uint8_t addr_type_dir,BD_ADDR direct_bda,uint8_t channel_map,uint8_t adv_filter_policy)64 void btsnd_hcic_ble_write_adv_params(uint16_t adv_int_min, uint16_t adv_int_max,
65 uint8_t adv_type, uint8_t addr_type_own,
66 uint8_t addr_type_dir, BD_ADDR direct_bda,
67 uint8_t channel_map,
68 uint8_t adv_filter_policy) {
69 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
70 uint8_t* pp = (uint8_t*)(p + 1);
71
72 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_WRITE_ADV_PARAMS;
73 p->offset = 0;
74
75 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_ADV_PARAMS);
76 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_WRITE_ADV_PARAMS);
77
78 UINT16_TO_STREAM(pp, adv_int_min);
79 UINT16_TO_STREAM(pp, adv_int_max);
80 UINT8_TO_STREAM(pp, adv_type);
81 UINT8_TO_STREAM(pp, addr_type_own);
82 UINT8_TO_STREAM(pp, addr_type_dir);
83 BDADDR_TO_STREAM(pp, direct_bda);
84 UINT8_TO_STREAM(pp, channel_map);
85 UINT8_TO_STREAM(pp, adv_filter_policy);
86
87 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
88 }
btsnd_hcic_ble_read_adv_chnl_tx_power(void)89 void btsnd_hcic_ble_read_adv_chnl_tx_power(void) {
90 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
91 uint8_t* pp = (uint8_t*)(p + 1);
92
93 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_READ_CMD;
94 p->offset = 0;
95
96 UINT16_TO_STREAM(pp, HCI_BLE_READ_ADV_CHNL_TX_POWER);
97 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_READ_CMD);
98
99 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
100 }
101
btsnd_hcic_ble_set_adv_data(uint8_t data_len,uint8_t * p_data)102 void btsnd_hcic_ble_set_adv_data(uint8_t data_len, uint8_t* p_data) {
103 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
104 uint8_t* pp = (uint8_t*)(p + 1);
105
106 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA + 1;
107 p->offset = 0;
108
109 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_ADV_DATA);
110 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA + 1);
111
112 memset(pp, 0, HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA);
113
114 if (p_data != NULL && data_len > 0) {
115 if (data_len > HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA)
116 data_len = HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA;
117
118 UINT8_TO_STREAM(pp, data_len);
119
120 ARRAY_TO_STREAM(pp, p_data, data_len);
121 }
122 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
123 }
btsnd_hcic_ble_set_scan_rsp_data(uint8_t data_len,uint8_t * p_scan_rsp)124 void btsnd_hcic_ble_set_scan_rsp_data(uint8_t data_len, uint8_t* p_scan_rsp) {
125 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
126 uint8_t* pp = (uint8_t*)(p + 1);
127
128 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP + 1;
129 p->offset = 0;
130
131 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_SCAN_RSP_DATA);
132 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP + 1);
133
134 memset(pp, 0, HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP);
135
136 if (p_scan_rsp != NULL && data_len > 0) {
137 if (data_len > HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP)
138 data_len = HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP;
139
140 UINT8_TO_STREAM(pp, data_len);
141
142 ARRAY_TO_STREAM(pp, p_scan_rsp, data_len);
143 }
144
145 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
146 }
147
btsnd_hcic_ble_set_adv_enable(uint8_t adv_enable)148 void btsnd_hcic_ble_set_adv_enable(uint8_t adv_enable) {
149 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
150 uint8_t* pp = (uint8_t*)(p + 1);
151
152 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_WRITE_ADV_ENABLE;
153 p->offset = 0;
154
155 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_ADV_ENABLE);
156 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_WRITE_ADV_ENABLE);
157
158 UINT8_TO_STREAM(pp, adv_enable);
159
160 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
161 }
btsnd_hcic_ble_set_scan_params(uint8_t scan_type,uint16_t scan_int,uint16_t scan_win,uint8_t addr_type_own,uint8_t scan_filter_policy)162 void btsnd_hcic_ble_set_scan_params(uint8_t scan_type, uint16_t scan_int,
163 uint16_t scan_win, uint8_t addr_type_own,
164 uint8_t scan_filter_policy) {
165 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
166 uint8_t* pp = (uint8_t*)(p + 1);
167
168 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_WRITE_SCAN_PARAM;
169 p->offset = 0;
170
171 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_SCAN_PARAMS);
172 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_WRITE_SCAN_PARAM);
173
174 UINT8_TO_STREAM(pp, scan_type);
175 UINT16_TO_STREAM(pp, scan_int);
176 UINT16_TO_STREAM(pp, scan_win);
177 UINT8_TO_STREAM(pp, addr_type_own);
178 UINT8_TO_STREAM(pp, scan_filter_policy);
179
180 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
181 }
182
btsnd_hcic_ble_set_scan_enable(uint8_t scan_enable,uint8_t duplicate)183 void btsnd_hcic_ble_set_scan_enable(uint8_t scan_enable, uint8_t duplicate) {
184 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
185 uint8_t* pp = (uint8_t*)(p + 1);
186
187 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_WRITE_SCAN_ENABLE;
188 p->offset = 0;
189
190 UINT16_TO_STREAM(pp, HCI_BLE_WRITE_SCAN_ENABLE);
191 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_WRITE_SCAN_ENABLE);
192
193 UINT8_TO_STREAM(pp, scan_enable);
194 UINT8_TO_STREAM(pp, duplicate);
195
196 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
197 }
198
199 /* link layer connection management commands */
btsnd_hcic_ble_create_ll_conn(uint16_t scan_int,uint16_t scan_win,uint8_t init_filter_policy,uint8_t addr_type_peer,BD_ADDR bda_peer,uint8_t addr_type_own,uint16_t conn_int_min,uint16_t conn_int_max,uint16_t conn_latency,uint16_t conn_timeout,uint16_t min_ce_len,uint16_t max_ce_len)200 void btsnd_hcic_ble_create_ll_conn(uint16_t scan_int, uint16_t scan_win,
201 uint8_t init_filter_policy,
202 uint8_t addr_type_peer, BD_ADDR bda_peer,
203 uint8_t addr_type_own, uint16_t conn_int_min,
204 uint16_t conn_int_max, uint16_t conn_latency,
205 uint16_t conn_timeout, uint16_t min_ce_len,
206 uint16_t max_ce_len) {
207 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
208 uint8_t* pp = (uint8_t*)(p + 1);
209
210 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_CREATE_LL_CONN;
211 p->offset = 0;
212
213 UINT16_TO_STREAM(pp, HCI_BLE_CREATE_LL_CONN);
214 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_CREATE_LL_CONN);
215
216 UINT16_TO_STREAM(pp, scan_int);
217 UINT16_TO_STREAM(pp, scan_win);
218 UINT8_TO_STREAM(pp, init_filter_policy);
219
220 UINT8_TO_STREAM(pp, addr_type_peer);
221 BDADDR_TO_STREAM(pp, bda_peer);
222 UINT8_TO_STREAM(pp, addr_type_own);
223
224 UINT16_TO_STREAM(pp, conn_int_min);
225 UINT16_TO_STREAM(pp, conn_int_max);
226 UINT16_TO_STREAM(pp, conn_latency);
227 UINT16_TO_STREAM(pp, conn_timeout);
228
229 UINT16_TO_STREAM(pp, min_ce_len);
230 UINT16_TO_STREAM(pp, max_ce_len);
231
232 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
233 }
234
btsnd_hcic_ble_create_conn_cancel(void)235 void btsnd_hcic_ble_create_conn_cancel(void) {
236 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
237 uint8_t* pp = (uint8_t*)(p + 1);
238
239 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_CREATE_CONN_CANCEL;
240 p->offset = 0;
241
242 UINT16_TO_STREAM(pp, HCI_BLE_CREATE_CONN_CANCEL);
243 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_CREATE_CONN_CANCEL);
244
245 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
246 }
247
btsnd_hcic_ble_clear_white_list(void)248 void btsnd_hcic_ble_clear_white_list(void) {
249 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
250 uint8_t* pp = (uint8_t*)(p + 1);
251
252 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_CLEAR_WHITE_LIST;
253 p->offset = 0;
254
255 UINT16_TO_STREAM(pp, HCI_BLE_CLEAR_WHITE_LIST);
256 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_CLEAR_WHITE_LIST);
257
258 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
259 }
260
btsnd_hcic_ble_add_white_list(uint8_t addr_type,BD_ADDR bda)261 void btsnd_hcic_ble_add_white_list(uint8_t addr_type, BD_ADDR bda) {
262 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
263 uint8_t* pp = (uint8_t*)(p + 1);
264
265 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_ADD_WHITE_LIST;
266 p->offset = 0;
267
268 UINT16_TO_STREAM(pp, HCI_BLE_ADD_WHITE_LIST);
269 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_ADD_WHITE_LIST);
270
271 UINT8_TO_STREAM(pp, addr_type);
272 BDADDR_TO_STREAM(pp, bda);
273
274 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
275 }
276
btsnd_hcic_ble_remove_from_white_list(uint8_t addr_type,BD_ADDR bda)277 void btsnd_hcic_ble_remove_from_white_list(uint8_t addr_type, BD_ADDR bda) {
278 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
279 uint8_t* pp = (uint8_t*)(p + 1);
280
281 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_REMOVE_WHITE_LIST;
282 p->offset = 0;
283
284 UINT16_TO_STREAM(pp, HCI_BLE_REMOVE_WHITE_LIST);
285 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_REMOVE_WHITE_LIST);
286
287 UINT8_TO_STREAM(pp, addr_type);
288 BDADDR_TO_STREAM(pp, bda);
289
290 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
291 }
292
btsnd_hcic_ble_upd_ll_conn_params(uint16_t handle,uint16_t conn_int_min,uint16_t conn_int_max,uint16_t conn_latency,uint16_t conn_timeout,uint16_t min_ce_len,uint16_t max_ce_len)293 void btsnd_hcic_ble_upd_ll_conn_params(uint16_t handle, uint16_t conn_int_min,
294 uint16_t conn_int_max,
295 uint16_t conn_latency,
296 uint16_t conn_timeout,
297 uint16_t min_ce_len,
298 uint16_t max_ce_len) {
299 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
300 uint8_t* pp = (uint8_t*)(p + 1);
301
302 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_UPD_LL_CONN_PARAMS;
303 p->offset = 0;
304
305 UINT16_TO_STREAM(pp, HCI_BLE_UPD_LL_CONN_PARAMS);
306 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_UPD_LL_CONN_PARAMS);
307
308 UINT16_TO_STREAM(pp, handle);
309
310 UINT16_TO_STREAM(pp, conn_int_min);
311 UINT16_TO_STREAM(pp, conn_int_max);
312 UINT16_TO_STREAM(pp, conn_latency);
313 UINT16_TO_STREAM(pp, conn_timeout);
314 UINT16_TO_STREAM(pp, min_ce_len);
315 UINT16_TO_STREAM(pp, max_ce_len);
316
317 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
318 }
319
btsnd_hcic_ble_set_host_chnl_class(uint8_t chnl_map[HCIC_BLE_CHNL_MAP_SIZE])320 void btsnd_hcic_ble_set_host_chnl_class(
321 uint8_t chnl_map[HCIC_BLE_CHNL_MAP_SIZE]) {
322 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
323 uint8_t* pp = (uint8_t*)(p + 1);
324
325 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_SET_HOST_CHNL_CLASS;
326 p->offset = 0;
327
328 UINT16_TO_STREAM(pp, HCI_BLE_SET_HOST_CHNL_CLASS);
329 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_SET_HOST_CHNL_CLASS);
330
331 ARRAY_TO_STREAM(pp, chnl_map, HCIC_BLE_CHNL_MAP_SIZE);
332
333 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
334 }
335
btsnd_hcic_ble_read_chnl_map(uint16_t handle)336 void btsnd_hcic_ble_read_chnl_map(uint16_t handle) {
337 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
338 uint8_t* pp = (uint8_t*)(p + 1);
339
340 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_READ_CHNL_MAP;
341 p->offset = 0;
342
343 UINT16_TO_STREAM(pp, HCI_BLE_READ_CHNL_MAP);
344 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_READ_CHNL_MAP);
345
346 UINT16_TO_STREAM(pp, handle);
347
348 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
349 }
350
btsnd_hcic_ble_read_remote_feat(uint16_t handle)351 void btsnd_hcic_ble_read_remote_feat(uint16_t handle) {
352 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
353 uint8_t* pp = (uint8_t*)(p + 1);
354
355 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_READ_REMOTE_FEAT;
356 p->offset = 0;
357
358 UINT16_TO_STREAM(pp, HCI_BLE_READ_REMOTE_FEAT);
359 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_READ_REMOTE_FEAT);
360
361 UINT16_TO_STREAM(pp, handle);
362
363 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
364 }
365
366 /* security management commands */
btsnd_hcic_ble_encrypt(uint8_t * key,uint8_t key_len,uint8_t * plain_text,uint8_t pt_len,void * p_cmd_cplt_cback)367 void btsnd_hcic_ble_encrypt(uint8_t* key, uint8_t key_len, uint8_t* plain_text,
368 uint8_t pt_len, void* p_cmd_cplt_cback) {
369 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
370 uint8_t* pp = (uint8_t*)(p + 1);
371
372 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_ENCRYPT;
373 p->offset = sizeof(void*);
374
375 *((void**)pp) =
376 p_cmd_cplt_cback; /* Store command complete callback in buffer */
377 pp += sizeof(void*); /* Skip over callback pointer */
378
379 UINT16_TO_STREAM(pp, HCI_BLE_ENCRYPT);
380 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_ENCRYPT);
381
382 memset(pp, 0, HCIC_PARAM_SIZE_BLE_ENCRYPT);
383
384 if (key_len > HCIC_BLE_ENCRYT_KEY_SIZE) key_len = HCIC_BLE_ENCRYT_KEY_SIZE;
385 if (pt_len > HCIC_BLE_ENCRYT_KEY_SIZE) pt_len = HCIC_BLE_ENCRYT_KEY_SIZE;
386
387 ARRAY_TO_STREAM(pp, key, key_len);
388 pp += (HCIC_BLE_ENCRYT_KEY_SIZE - key_len);
389 ARRAY_TO_STREAM(pp, plain_text, pt_len);
390
391 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
392 }
393
btsnd_hcic_ble_rand(base::Callback<void (BT_OCTET8)> cb)394 void btsnd_hcic_ble_rand(base::Callback<void(BT_OCTET8)> cb) {
395 btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_RAND, nullptr, 0,
396 base::Bind(
397 [](base::Callback<void(BT_OCTET8)> cb,
398 uint8_t* param, uint16_t param_len) {
399 CHECK(param[0] == 0)
400 << "LE Rand return status must be zero";
401 cb.Run(param + 1 /* skip status */);
402 },
403 std::move(cb)));
404 }
405
btsnd_hcic_ble_start_enc(uint16_t handle,uint8_t rand[HCIC_BLE_RAND_DI_SIZE],uint16_t ediv,uint8_t ltk[HCIC_BLE_ENCRYT_KEY_SIZE])406 void btsnd_hcic_ble_start_enc(uint16_t handle,
407 uint8_t rand[HCIC_BLE_RAND_DI_SIZE],
408 uint16_t ediv,
409 uint8_t ltk[HCIC_BLE_ENCRYT_KEY_SIZE]) {
410 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
411 uint8_t* pp = (uint8_t*)(p + 1);
412
413 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_START_ENC;
414 p->offset = 0;
415
416 UINT16_TO_STREAM(pp, HCI_BLE_START_ENC);
417 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_START_ENC);
418
419 UINT16_TO_STREAM(pp, handle);
420 ARRAY_TO_STREAM(pp, rand, HCIC_BLE_RAND_DI_SIZE);
421 UINT16_TO_STREAM(pp, ediv);
422 ARRAY_TO_STREAM(pp, ltk, HCIC_BLE_ENCRYT_KEY_SIZE);
423
424 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
425 }
426
btsnd_hcic_ble_ltk_req_reply(uint16_t handle,uint8_t ltk[HCIC_BLE_ENCRYT_KEY_SIZE])427 void btsnd_hcic_ble_ltk_req_reply(uint16_t handle,
428 uint8_t ltk[HCIC_BLE_ENCRYT_KEY_SIZE]) {
429 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
430 uint8_t* pp = (uint8_t*)(p + 1);
431
432 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_LTK_REQ_REPLY;
433 p->offset = 0;
434
435 UINT16_TO_STREAM(pp, HCI_BLE_LTK_REQ_REPLY);
436 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_LTK_REQ_REPLY);
437
438 UINT16_TO_STREAM(pp, handle);
439 ARRAY_TO_STREAM(pp, ltk, HCIC_BLE_ENCRYT_KEY_SIZE);
440
441 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
442 }
443
btsnd_hcic_ble_ltk_req_neg_reply(uint16_t handle)444 void btsnd_hcic_ble_ltk_req_neg_reply(uint16_t handle) {
445 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
446 uint8_t* pp = (uint8_t*)(p + 1);
447
448 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_LTK_REQ_NEG_REPLY;
449 p->offset = 0;
450
451 UINT16_TO_STREAM(pp, HCI_BLE_LTK_REQ_NEG_REPLY);
452 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_LTK_REQ_NEG_REPLY);
453
454 UINT16_TO_STREAM(pp, handle);
455
456 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
457 }
458
btsnd_hcic_ble_receiver_test(uint8_t rx_freq)459 void btsnd_hcic_ble_receiver_test(uint8_t rx_freq) {
460 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
461 uint8_t* pp = (uint8_t*)(p + 1);
462
463 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_WRITE_PARAM1;
464 p->offset = 0;
465
466 UINT16_TO_STREAM(pp, HCI_BLE_RECEIVER_TEST);
467 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_WRITE_PARAM1);
468
469 UINT8_TO_STREAM(pp, rx_freq);
470
471 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
472 }
473
btsnd_hcic_ble_transmitter_test(uint8_t tx_freq,uint8_t test_data_len,uint8_t payload)474 void btsnd_hcic_ble_transmitter_test(uint8_t tx_freq, uint8_t test_data_len,
475 uint8_t payload) {
476 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
477 uint8_t* pp = (uint8_t*)(p + 1);
478
479 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_WRITE_PARAM3;
480 p->offset = 0;
481
482 UINT16_TO_STREAM(pp, HCI_BLE_TRANSMITTER_TEST);
483 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_WRITE_PARAM3);
484
485 UINT8_TO_STREAM(pp, tx_freq);
486 UINT8_TO_STREAM(pp, test_data_len);
487 UINT8_TO_STREAM(pp, payload);
488
489 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
490 }
491
btsnd_hcic_ble_test_end(void)492 void btsnd_hcic_ble_test_end(void) {
493 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
494 uint8_t* pp = (uint8_t*)(p + 1);
495
496 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_READ_CMD;
497 p->offset = 0;
498
499 UINT16_TO_STREAM(pp, HCI_BLE_TEST_END);
500 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_READ_CMD);
501
502 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
503 }
504
btsnd_hcic_ble_read_host_supported(void)505 void btsnd_hcic_ble_read_host_supported(void) {
506 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
507 uint8_t* pp = (uint8_t*)(p + 1);
508
509 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_READ_CMD;
510 p->offset = 0;
511
512 UINT16_TO_STREAM(pp, HCI_READ_LE_HOST_SUPPORT);
513 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_READ_CMD);
514
515 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
516 }
517
518 #if (BLE_LLT_INCLUDED == TRUE)
519
btsnd_hcic_ble_rc_param_req_reply(uint16_t handle,uint16_t conn_int_min,uint16_t conn_int_max,uint16_t conn_latency,uint16_t conn_timeout,uint16_t min_ce_len,uint16_t max_ce_len)520 void btsnd_hcic_ble_rc_param_req_reply(uint16_t handle, uint16_t conn_int_min,
521 uint16_t conn_int_max,
522 uint16_t conn_latency,
523 uint16_t conn_timeout,
524 uint16_t min_ce_len,
525 uint16_t max_ce_len) {
526 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
527 uint8_t* pp = (uint8_t*)(p + 1);
528
529 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_REPLY;
530 p->offset = 0;
531
532 UINT16_TO_STREAM(pp, HCI_BLE_RC_PARAM_REQ_REPLY);
533 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_REPLY);
534
535 UINT16_TO_STREAM(pp, handle);
536 UINT16_TO_STREAM(pp, conn_int_min);
537 UINT16_TO_STREAM(pp, conn_int_max);
538 UINT16_TO_STREAM(pp, conn_latency);
539 UINT16_TO_STREAM(pp, conn_timeout);
540 UINT16_TO_STREAM(pp, min_ce_len);
541 UINT16_TO_STREAM(pp, max_ce_len);
542
543 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
544 }
545
btsnd_hcic_ble_rc_param_req_neg_reply(uint16_t handle,uint8_t reason)546 void btsnd_hcic_ble_rc_param_req_neg_reply(uint16_t handle, uint8_t reason) {
547 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
548 uint8_t* pp = (uint8_t*)(p + 1);
549
550 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_NEG_REPLY;
551 p->offset = 0;
552
553 UINT16_TO_STREAM(pp, HCI_BLE_RC_PARAM_REQ_NEG_REPLY);
554 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_NEG_REPLY);
555
556 UINT16_TO_STREAM(pp, handle);
557 UINT8_TO_STREAM(pp, reason);
558
559 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
560 }
561 #endif
562
btsnd_hcic_ble_add_device_resolving_list(uint8_t addr_type_peer,BD_ADDR bda_peer,uint8_t irk_peer[HCIC_BLE_IRK_SIZE],uint8_t irk_local[HCIC_BLE_IRK_SIZE])563 void btsnd_hcic_ble_add_device_resolving_list(
564 uint8_t addr_type_peer, BD_ADDR bda_peer,
565 uint8_t irk_peer[HCIC_BLE_IRK_SIZE], uint8_t irk_local[HCIC_BLE_IRK_SIZE]) {
566 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
567 uint8_t* pp = (uint8_t*)(p + 1);
568
569 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_ADD_DEV_RESOLVING_LIST;
570 p->offset = 0;
571
572 UINT16_TO_STREAM(pp, HCI_BLE_ADD_DEV_RESOLVING_LIST);
573 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_ADD_DEV_RESOLVING_LIST);
574 UINT8_TO_STREAM(pp, addr_type_peer);
575 BDADDR_TO_STREAM(pp, bda_peer);
576 ARRAY_TO_STREAM(pp, irk_peer, HCIC_BLE_ENCRYT_KEY_SIZE);
577 ARRAY_TO_STREAM(pp, irk_local, HCIC_BLE_ENCRYT_KEY_SIZE);
578
579 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
580 }
581
btsnd_hcic_ble_rm_device_resolving_list(uint8_t addr_type_peer,BD_ADDR bda_peer)582 void btsnd_hcic_ble_rm_device_resolving_list(uint8_t addr_type_peer,
583 BD_ADDR bda_peer) {
584 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
585 uint8_t* pp = (uint8_t*)(p + 1);
586
587 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_RM_DEV_RESOLVING_LIST;
588 p->offset = 0;
589
590 UINT16_TO_STREAM(pp, HCI_BLE_RM_DEV_RESOLVING_LIST);
591 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_RM_DEV_RESOLVING_LIST);
592 UINT8_TO_STREAM(pp, addr_type_peer);
593 BDADDR_TO_STREAM(pp, bda_peer);
594
595 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
596 }
597
btsnd_hcic_ble_set_privacy_mode(uint8_t addr_type_peer,BD_ADDR bda_peer,uint8_t privacy_type)598 void btsnd_hcic_ble_set_privacy_mode(uint8_t addr_type_peer, BD_ADDR bda_peer,
599 uint8_t privacy_type) {
600 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
601 uint8_t* pp = (uint8_t*)(p + 1);
602
603 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_SET_PRIVACY_MODE;
604 p->offset = 0;
605
606 UINT16_TO_STREAM(pp, HCI_BLE_SET_PRIVACY_MODE);
607 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_SET_PRIVACY_MODE);
608 UINT8_TO_STREAM(pp, addr_type_peer);
609 BDADDR_TO_STREAM(pp, bda_peer);
610 UINT8_TO_STREAM(pp, privacy_type);
611
612 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
613 }
614
btsnd_hcic_ble_clear_resolving_list(void)615 void btsnd_hcic_ble_clear_resolving_list(void) {
616 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
617 uint8_t* pp = (uint8_t*)(p + 1);
618
619 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_CLEAR_RESOLVING_LIST;
620 p->offset = 0;
621
622 UINT16_TO_STREAM(pp, HCI_BLE_CLEAR_RESOLVING_LIST);
623 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_CLEAR_RESOLVING_LIST);
624
625 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
626 }
627
btsnd_hcic_ble_read_resolvable_addr_peer(uint8_t addr_type_peer,BD_ADDR bda_peer)628 void btsnd_hcic_ble_read_resolvable_addr_peer(uint8_t addr_type_peer,
629 BD_ADDR bda_peer) {
630 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
631 uint8_t* pp = (uint8_t*)(p + 1);
632
633 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_PEER;
634 p->offset = 0;
635
636 UINT16_TO_STREAM(pp, HCI_BLE_READ_RESOLVABLE_ADDR_PEER);
637 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_PEER);
638 UINT8_TO_STREAM(pp, addr_type_peer);
639 BDADDR_TO_STREAM(pp, bda_peer);
640
641 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
642 }
643
btsnd_hcic_ble_read_resolvable_addr_local(uint8_t addr_type_peer,BD_ADDR bda_peer)644 void btsnd_hcic_ble_read_resolvable_addr_local(uint8_t addr_type_peer,
645 BD_ADDR bda_peer) {
646 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
647 uint8_t* pp = (uint8_t*)(p + 1);
648
649 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_LOCAL;
650 p->offset = 0;
651
652 UINT16_TO_STREAM(pp, HCI_BLE_READ_RESOLVABLE_ADDR_LOCAL);
653 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_LOCAL);
654 UINT8_TO_STREAM(pp, addr_type_peer);
655 BDADDR_TO_STREAM(pp, bda_peer);
656
657 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
658 }
659
btsnd_hcic_ble_set_addr_resolution_enable(uint8_t addr_resolution_enable)660 void btsnd_hcic_ble_set_addr_resolution_enable(uint8_t addr_resolution_enable) {
661 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
662 uint8_t* pp = (uint8_t*)(p + 1);
663
664 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_SET_ADDR_RESOLUTION_ENABLE;
665 p->offset = 0;
666
667 UINT16_TO_STREAM(pp, HCI_BLE_SET_ADDR_RESOLUTION_ENABLE);
668 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_SET_ADDR_RESOLUTION_ENABLE);
669 UINT8_TO_STREAM(pp, addr_resolution_enable);
670
671 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
672 }
673
btsnd_hcic_ble_set_rand_priv_addr_timeout(uint16_t rpa_timout)674 void btsnd_hcic_ble_set_rand_priv_addr_timeout(uint16_t rpa_timout) {
675 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
676 uint8_t* pp = (uint8_t*)(p + 1);
677
678 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_SET_RAND_PRIV_ADDR_TIMOUT;
679 p->offset = 0;
680
681 UINT16_TO_STREAM(pp, HCI_BLE_SET_RAND_PRIV_ADDR_TIMOUT);
682 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_SET_RAND_PRIV_ADDR_TIMOUT);
683 UINT16_TO_STREAM(pp, rpa_timout);
684
685 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
686 }
687
btsnd_hcic_ble_set_data_length(uint16_t conn_handle,uint16_t tx_octets,uint16_t tx_time)688 void btsnd_hcic_ble_set_data_length(uint16_t conn_handle, uint16_t tx_octets,
689 uint16_t tx_time) {
690 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
691 uint8_t* pp = (uint8_t*)(p + 1);
692
693 p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_BLE_SET_DATA_LENGTH;
694 p->offset = 0;
695
696 UINT16_TO_STREAM(pp, HCI_BLE_SET_DATA_LENGTH);
697 UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_SET_DATA_LENGTH);
698
699 UINT16_TO_STREAM(pp, conn_handle);
700 UINT16_TO_STREAM(pp, tx_octets);
701 UINT16_TO_STREAM(pp, tx_time);
702
703 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
704 }
705
btsnd_hcic_ble_set_extended_scan_params(uint8_t own_address_type,uint8_t scanning_filter_policy,uint8_t scanning_phys,scanning_phy_cfg * phy_cfg)706 void btsnd_hcic_ble_set_extended_scan_params(uint8_t own_address_type,
707 uint8_t scanning_filter_policy,
708 uint8_t scanning_phys,
709 scanning_phy_cfg* phy_cfg) {
710 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
711 uint8_t* pp = (uint8_t*)(p + 1);
712
713 int phy_cnt =
714 std::bitset<std::numeric_limits<uint8_t>::digits>(scanning_phys).count();
715
716 uint16_t param_len = 3 + (5 * phy_cnt);
717 p->len = HCIC_PREAMBLE_SIZE + param_len;
718 p->offset = 0;
719
720 UINT16_TO_STREAM(pp, HCI_LE_SET_EXTENDED_SCAN_PARAMETERS);
721 UINT8_TO_STREAM(pp, param_len);
722
723 UINT8_TO_STREAM(pp, own_address_type);
724 UINT8_TO_STREAM(pp, scanning_filter_policy);
725 UINT8_TO_STREAM(pp, scanning_phys);
726
727 for (int i = 0; i < phy_cnt; i++) {
728 UINT8_TO_STREAM(pp, phy_cfg[i].scan_type);
729 UINT16_TO_STREAM(pp, phy_cfg[i].scan_int);
730 UINT16_TO_STREAM(pp, phy_cfg[i].scan_win);
731 }
732
733 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
734 }
735
btsnd_hcic_ble_set_extended_scan_enable(uint8_t enable,uint8_t filter_duplicates,uint16_t duration,uint16_t period)736 void btsnd_hcic_ble_set_extended_scan_enable(uint8_t enable,
737 uint8_t filter_duplicates,
738 uint16_t duration,
739 uint16_t period) {
740 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
741 uint8_t* pp = (uint8_t*)(p + 1);
742
743 const int param_len = 6;
744 p->len = HCIC_PREAMBLE_SIZE + param_len;
745 p->offset = 0;
746
747 UINT16_TO_STREAM(pp, HCI_LE_SET_EXTENDED_SCAN_ENABLE);
748 UINT8_TO_STREAM(pp, param_len);
749
750 UINT8_TO_STREAM(pp, enable);
751 UINT8_TO_STREAM(pp, filter_duplicates);
752 UINT16_TO_STREAM(pp, duration);
753 UINT16_TO_STREAM(pp, period);
754
755 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
756 }
757
btsnd_hcic_ble_ext_create_conn(uint8_t init_filter_policy,uint8_t addr_type_own,uint8_t addr_type_peer,BD_ADDR bda_peer,uint8_t initiating_phys,EXT_CONN_PHY_CFG * phy_cfg)758 void btsnd_hcic_ble_ext_create_conn(uint8_t init_filter_policy,
759 uint8_t addr_type_own,
760 uint8_t addr_type_peer, BD_ADDR bda_peer,
761 uint8_t initiating_phys,
762 EXT_CONN_PHY_CFG* phy_cfg) {
763 BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
764 uint8_t* pp = (uint8_t*)(p + 1);
765
766 int phy_cnt =
767 std::bitset<std::numeric_limits<uint8_t>::digits>(initiating_phys)
768 .count();
769
770 /* param_len = initial_params + size_per_channel * num_of_channels */
771 uint8_t param_len = 10 + (16 * phy_cnt);
772
773 p->len = HCIC_PREAMBLE_SIZE + param_len;
774 p->offset = 0;
775
776 UINT16_TO_STREAM(pp, HCI_LE_EXTENDED_CREATE_CONNECTION);
777 UINT8_TO_STREAM(pp, param_len);
778
779 UINT8_TO_STREAM(pp, init_filter_policy);
780 UINT8_TO_STREAM(pp, addr_type_own);
781 UINT8_TO_STREAM(pp, addr_type_peer);
782 BDADDR_TO_STREAM(pp, bda_peer);
783
784 UINT8_TO_STREAM(pp, initiating_phys);
785
786 for (int i = 0; i < phy_cnt; i++) {
787 UINT16_TO_STREAM(pp, phy_cfg[i].scan_int);
788 UINT16_TO_STREAM(pp, phy_cfg[i].scan_win);
789 UINT16_TO_STREAM(pp, phy_cfg[i].conn_int_min);
790 UINT16_TO_STREAM(pp, phy_cfg[i].conn_int_max);
791 UINT16_TO_STREAM(pp, phy_cfg[i].conn_latency);
792 UINT16_TO_STREAM(pp, phy_cfg[i].sup_timeout);
793 UINT16_TO_STREAM(pp, phy_cfg[i].min_ce_len);
794 UINT16_TO_STREAM(pp, phy_cfg[i].max_ce_len);
795 }
796
797 btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
798 }
799