1 /*
2  * Copyright 2023-2025 NXP
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 /* -------------------------------------------------------------------------- */
8 /*                                  Includes                                  */
9 /* -------------------------------------------------------------------------- */
10 
11 #include <zephyr/init.h>
12 #include <zephyr/drivers/bluetooth.h>
13 #include <zephyr/logging/log.h>
14 #include <zephyr/sys/byteorder.h>
15 #include <zephyr/device.h>
16 #include <zephyr/drivers/flash.h>
17 #include <zephyr/bluetooth/hci_types.h>
18 #include <soc.h>
19 #include <zephyr/pm/policy.h>
20 
21 #include <fwk_platform_ble.h>
22 #include <fwk_platform.h>
23 
24 /* -------------------------------------------------------------------------- */
25 /*                                  Definitions                               */
26 /* -------------------------------------------------------------------------- */
27 
28 #define DT_DRV_COMPAT nxp_hci_ble
29 
30 struct bt_nxp_data {
31 	bt_hci_recv_t recv;
32 };
33 
34 struct hci_data {
35 	uint8_t packetType;
36 	uint8_t *data;
37 	uint16_t len;
38 };
39 
40 #define LOG_LEVEL CONFIG_BT_HCI_DRIVER_LOG_LEVEL
41 LOG_MODULE_REGISTER(bt_driver);
42 
43 /* Vendor specific commands */
44 #define HCI_CMD_STORE_BT_CAL_DATA_OCF                   0x61U
45 #define HCI_CMD_STORE_BT_CAL_DATA_PARAM_LENGTH          32U
46 #define HCI_CMD_STORE_BT_CAL_DATA_ANNEX100_OCF          0xFFU
47 #define HCI_CMD_STORE_BT_CAL_DATA_PARAM_ANNEX100_LENGTH 16U
48 #define HCI_CMD_SET_BT_SLEEP_MODE_OCF                   0x23U
49 #define HCI_CMD_SET_BT_SLEEP_MODE_PARAM_LENGTH          3U
50 #define HCI_CMD_BT_HOST_SLEEP_CONFIG_OCF                0x59U
51 #define HCI_CMD_BT_HOST_SLEEP_CONFIG_PARAM_LENGTH       2U
52 #define HCI_CMD_BT_HOST_SET_MAC_ADDR_PARAM_LENGTH       8U
53 #define HCI_SET_MAC_ADDR_CMD                            0x0022U
54 #define BT_USER_BD                                      254
55 #define BD_ADDR_OUI                                     0x37U, 0x60U, 0x00U
56 #define BD_ADDR_OUI_PART_SIZE                           3U
57 #define BD_ADDR_UUID_PART_SIZE                          3U
58 
59 #if !defined(CONFIG_HCI_NXP_SET_CAL_DATA)
60 #define bt_nxp_set_calibration_data() 0
61 #endif
62 
63 #if !defined(CONFIG_HCI_NXP_SET_CAL_DATA_ANNEX100)
64 #define bt_nxp_set_calibration_data_annex100() 0
65 #endif
66 
67 #if !defined(CONFIG_HCI_NXP_ENABLE_AUTO_SLEEP)
68 #define nxp_bt_set_host_sleep_config()       0
69 #define nxp_bt_enable_controller_autosleep() 0
70 #endif
71 
72 #if !defined(CONFIG_BT_HCI_SET_PUBLIC_ADDR)
73 #define bt_nxp_set_mac_address(public_addr) 0
74 #endif
75 
76 #if DT_NODE_HAS_STATUS(DT_NODELABEL(standby), okay) && defined(CONFIG_PM) &&\
77 	defined(CONFIG_HCI_NXP_ENABLE_AUTO_SLEEP)
78 #define HCI_NXP_LOCK_STANDBY_BEFORE_SEND
79 #endif
80 
81 /* -------------------------------------------------------------------------- */
82 /*                              Public prototypes                             */
83 /* -------------------------------------------------------------------------- */
84 
85 /* -------------------------------------------------------------------------- */
86 /*                             Private functions                              */
87 /* -------------------------------------------------------------------------- */
88 
89 #if defined(CONFIG_HCI_NXP_ENABLE_AUTO_SLEEP) || defined(CONFIG_HCI_NXP_SET_CAL_DATA) ||\
90 	defined(CONFIG_BT_HCI_SET_PUBLIC_ADDR)
nxp_bt_send_vs_command(uint16_t opcode,const uint8_t * params,uint8_t params_len)91 static int nxp_bt_send_vs_command(uint16_t opcode, const uint8_t *params, uint8_t params_len)
92 {
93 	if (IS_ENABLED(CONFIG_BT_HCI_HOST)) {
94 		struct net_buf *buf;
95 
96 		/* Allocate buffer for the hci command */
97 		buf = bt_hci_cmd_alloc(K_FOREVER);
98 		if (buf == NULL) {
99 			LOG_ERR("Unable to allocate command buffer");
100 			return -ENOMEM;
101 		}
102 
103 		/* Add data part of packet */
104 		net_buf_add_mem(buf, params, params_len);
105 
106 		/* Send the command */
107 		return bt_hci_cmd_send_sync(opcode, buf, NULL);
108 	} else {
109 		return 0;
110 	}
111 }
112 #endif
113 
114 #if defined(CONFIG_HCI_NXP_ENABLE_AUTO_SLEEP)
nxp_bt_enable_controller_autosleep(void)115 static int nxp_bt_enable_controller_autosleep(void)
116 {
117 	uint16_t opcode = BT_OP(BT_OGF_VS, HCI_CMD_SET_BT_SLEEP_MODE_OCF);
118 	const uint8_t params[HCI_CMD_SET_BT_SLEEP_MODE_PARAM_LENGTH] = {
119 		0x02U, /* Auto sleep enable */
120 		0x00U, /* Idle timeout LSB */
121 		0x00U  /* Idle timeout MSB */
122 	};
123 
124 	/* Send the command */
125 	return nxp_bt_send_vs_command(opcode, params, HCI_CMD_SET_BT_SLEEP_MODE_PARAM_LENGTH);
126 }
127 
nxp_bt_set_host_sleep_config(void)128 static int nxp_bt_set_host_sleep_config(void)
129 {
130 	uint16_t opcode = BT_OP(BT_OGF_VS, HCI_CMD_BT_HOST_SLEEP_CONFIG_OCF);
131 	const uint8_t params[HCI_CMD_BT_HOST_SLEEP_CONFIG_PARAM_LENGTH] = {
132 		0xFFU, /* BT_HIU_WAKEUP_INBAND */
133 		0xFFU, /* BT_HIU_WAKE_GAP_WAIT_FOR_IRQ */
134 	};
135 
136 	/* Send the command */
137 	return nxp_bt_send_vs_command(opcode, params, HCI_CMD_BT_HOST_SLEEP_CONFIG_PARAM_LENGTH);
138 }
139 #endif /* CONFIG_HCI_NXP_ENABLE_AUTO_SLEEP */
140 
141 #if defined(CONFIG_HCI_NXP_SET_CAL_DATA)
bt_nxp_set_calibration_data(void)142 static int bt_nxp_set_calibration_data(void)
143 {
144 	uint16_t opcode = BT_OP(BT_OGF_VS, HCI_CMD_STORE_BT_CAL_DATA_OCF);
145 	extern const uint8_t hci_cal_data_params[HCI_CMD_STORE_BT_CAL_DATA_PARAM_LENGTH];
146 
147 	/* Send the command */
148 	return nxp_bt_send_vs_command(opcode, hci_cal_data_params,
149 				      HCI_CMD_STORE_BT_CAL_DATA_PARAM_LENGTH);
150 }
151 
152 #if defined(CONFIG_HCI_NXP_SET_CAL_DATA_ANNEX100)
bt_nxp_set_calibration_data_annex100(void)153 static int bt_nxp_set_calibration_data_annex100(void)
154 {
155 	uint16_t opcode = BT_OP(BT_OGF_VS, HCI_CMD_STORE_BT_CAL_DATA_ANNEX100_OCF);
156 
157 	extern const uint8_t
158 		hci_cal_data_annex100_params[HCI_CMD_STORE_BT_CAL_DATA_PARAM_ANNEX100_LENGTH];
159 
160 	/* Send the command */
161 	return nxp_bt_send_vs_command(opcode, hci_cal_data_annex100_params,
162 				      HCI_CMD_STORE_BT_CAL_DATA_PARAM_ANNEX100_LENGTH);
163 }
164 #endif /* CONFIG_HCI_NXP_SET_CAL_DATA_ANNEX100 */
165 
166 #endif /* CONFIG_HCI_NXP_SET_CAL_DATA */
167 
168 #if defined(CONFIG_BT_HCI_SET_PUBLIC_ADDR)
169 /* Currently, we cannot use nxp_bt_send_vs_command because the controller
170  * fails to send the command complete event expected by Zephyr Host stack.
171  * To workaround it, we directly send the message using our PLATFORM API.
172  * This will be reworked once it is fixed on the controller side.
173  */
bt_nxp_set_mac_address(const bt_addr_t * public_addr)174 static int bt_nxp_set_mac_address(const bt_addr_t *public_addr)
175 {
176 	uint8_t bleDeviceAddress[BT_ADDR_SIZE] = {0};
177 	uint16_t opcode = BT_OP(BT_OGF_VS, HCI_SET_MAC_ADDR_CMD);
178 	uint8_t addrOUI[BD_ADDR_OUI_PART_SIZE] = {BD_ADDR_OUI};
179 	uint8_t uid[16] = {0};
180 	uint8_t uuidLen;
181 	uint8_t params[HCI_CMD_BT_HOST_SET_MAC_ADDR_PARAM_LENGTH] = {
182 		BT_USER_BD,
183 		0x06U
184 	};
185 
186 	/* If no public address is provided by the user, use a unique address made
187 	 * from the device's UID (unique ID)
188 	 */
189 	if (bt_addr_eq(public_addr, BT_ADDR_ANY) || bt_addr_eq(public_addr, BT_ADDR_NONE)) {
190 		PLATFORM_GetMCUUid(uid, &uuidLen);
191 		/* Set 3 LSB of MAC address from UUID */
192 		if (uuidLen > BD_ADDR_UUID_PART_SIZE) {
193 			memcpy((void *)bleDeviceAddress,
194 			       (void *)(uid + uuidLen - (BD_ADDR_UUID_PART_SIZE + 1)),
195 			       BD_ADDR_UUID_PART_SIZE);
196 		}
197 		/* Set 3 MSB of MAC address from OUI */
198 		memcpy((void *)(bleDeviceAddress + BD_ADDR_UUID_PART_SIZE), (void *)addrOUI,
199 		       BD_ADDR_OUI_PART_SIZE);
200 	} else {
201 		bt_addr_copy((bt_addr_t *)bleDeviceAddress, public_addr);
202 	}
203 
204 	memcpy(&params[2], (const void *)bleDeviceAddress,
205 		BD_ADDR_UUID_PART_SIZE + BD_ADDR_OUI_PART_SIZE);
206 
207 	/* Send the command */
208 	return nxp_bt_send_vs_command(opcode, params,
209 					HCI_CMD_BT_HOST_SET_MAC_ADDR_PARAM_LENGTH);
210 }
211 #endif /* CONFIG_BT_HCI_SET_PUBLIC_ADDR */
212 
is_hci_event_discardable(const uint8_t * evt_data)213 static bool is_hci_event_discardable(const uint8_t *evt_data)
214 {
215 	bool ret = false;
216 	uint8_t evt_type = evt_data[0];
217 
218 	switch (evt_type) {
219 	case BT_HCI_EVT_LE_META_EVENT: {
220 		uint8_t subevt_type = evt_data[sizeof(struct bt_hci_evt_hdr)];
221 
222 		switch (subevt_type) {
223 		case BT_HCI_EVT_LE_ADVERTISING_REPORT:
224 			ret = true;
225 			break;
226 #if defined(CONFIG_BT_EXT_ADV)
227 		case BT_HCI_EVT_LE_EXT_ADVERTISING_REPORT:
228 		{
229 			const struct bt_hci_evt_le_ext_advertising_report *ext_adv =
230 				(void *)&evt_data[3];
231 
232 			return (ext_adv->num_reports == 1) &&
233 				   ((ext_adv->adv_info[0].evt_type &
234 					 BT_HCI_LE_ADV_EVT_TYPE_LEGACY) != 0);
235 		}
236 #endif
237 		default:
238 			break;
239 		}
240 	} break;
241 
242 	default:
243 		break;
244 	}
245 
246 	return ret;
247 }
248 
bt_evt_recv(uint8_t * data,size_t len)249 static struct net_buf *bt_evt_recv(uint8_t *data, size_t len)
250 {
251 	struct net_buf *buf;
252 	uint8_t payload_len;
253 	uint8_t evt_hdr;
254 	bool discardable_evt;
255 	size_t space_in_buffer;
256 
257 	payload_len = data[1];
258 	evt_hdr = data[0];
259 	discardable_evt = false;
260 
261 	/* Data Check */
262 	if (len < BT_HCI_EVT_HDR_SIZE) {
263 		LOG_ERR("Event header is missing");
264 		return NULL;
265 	}
266 	if ((len - BT_HCI_EVT_HDR_SIZE) != payload_len) {
267 		LOG_ERR("Event payload length is incorrect");
268 		return NULL;
269 	}
270 
271 	discardable_evt = is_hci_event_discardable(data);
272 
273 	/* Allocate a buffer for the HCI Event */
274 	buf = bt_buf_get_evt(evt_hdr, discardable_evt, (discardable_evt ? K_NO_WAIT : K_FOREVER));
275 
276 	if (buf) {
277 		space_in_buffer = net_buf_tailroom(buf);
278 		if (len > space_in_buffer) {
279 			LOG_ERR("Buffer size error,INFO : evt_hdr=%d, data_len=%zu, buf_size=%zu",
280 				evt_hdr, len, space_in_buffer);
281 			net_buf_unref(buf);
282 			return NULL;
283 		}
284 		/* Copy the data to the buffer */
285 		net_buf_add_mem(buf, data, len);
286 	} else {
287 		if (discardable_evt) {
288 			LOG_DBG("Discardable buffer pool full, ignoring event");
289 		} else {
290 			LOG_ERR("No available event buffers!");
291 		}
292 		return NULL;
293 	}
294 
295 	return buf;
296 }
297 
bt_acl_recv(uint8_t * data,size_t len)298 static struct net_buf *bt_acl_recv(uint8_t *data, size_t len)
299 {
300 	struct net_buf *buf;
301 	uint16_t payload_len;
302 
303 	/* Data Check */
304 	if (len < BT_HCI_ACL_HDR_SIZE) {
305 		LOG_ERR("ACL header is missing");
306 		return NULL;
307 	}
308 	memcpy((void *)&payload_len, (void *)&data[2], 2);
309 	if ((len - BT_HCI_ACL_HDR_SIZE) != payload_len) {
310 		LOG_ERR("ACL payload length is incorrect");
311 		return NULL;
312 	}
313 	/* Allocate a buffer for the received data */
314 	buf = bt_buf_get_rx(BT_BUF_ACL_IN, K_NO_WAIT);
315 
316 	if (buf) {
317 		if (len > net_buf_tailroom(buf)) {
318 			LOG_ERR("Buffer doesn't have enough space to store the data");
319 			net_buf_unref(buf);
320 			return NULL;
321 		}
322 		/* Copy the data to the buffer */
323 		net_buf_add_mem(buf, data, len);
324 	} else {
325 		LOG_ERR("ACL buffer is empty");
326 		return NULL;
327 	}
328 
329 	return buf;
330 }
331 
process_rx(uint8_t packetType,uint8_t * data,uint16_t len)332 static void process_rx(uint8_t packetType, uint8_t *data, uint16_t len)
333 {
334 	const struct device *dev = DEVICE_DT_GET(DT_DRV_INST(0));
335 	struct bt_nxp_data *hci = dev->data;
336 	struct net_buf *buf;
337 
338 	switch (packetType) {
339 	case BT_HCI_H4_EVT:
340 		/* create a buffer and fill it out with event data  */
341 		buf = bt_evt_recv(data, len);
342 		break;
343 	case BT_HCI_H4_ACL:
344 		/* create a buffer and fill it out with ACL data  */
345 		buf = bt_acl_recv(data, len);
346 		break;
347 	default:
348 		buf = NULL;
349 		LOG_ERR("Unknown HCI type");
350 	}
351 
352 	if (buf) {
353 		/* Provide the buffer to the host */
354 		hci->recv(dev, buf);
355 	}
356 }
357 
358 #if defined(CONFIG_HCI_NXP_RX_THREAD)
359 
360 K_MSGQ_DEFINE(rx_msgq, sizeof(struct hci_data), CONFIG_HCI_NXP_RX_MSG_QUEUE_SIZE, 4);
361 
bt_rx_thread(void * p1,void * p2,void * p3)362 static void bt_rx_thread(void *p1, void *p2, void *p3)
363 {
364 	ARG_UNUSED(p1);
365 	ARG_UNUSED(p2);
366 	ARG_UNUSED(p3);
367 
368 	struct hci_data hci_rx_frame;
369 
370 	while (true) {
371 		if (k_msgq_get(&rx_msgq, &hci_rx_frame, K_FOREVER) < 0) {
372 			LOG_ERR("Failed to get RX data from message queue");
373 			continue;
374 		}
375 		process_rx(hci_rx_frame.packetType, hci_rx_frame.data, hci_rx_frame.len);
376 		k_free(hci_rx_frame.data);
377 	}
378 }
379 
380 K_THREAD_DEFINE(nxp_hci_rx_thread, CONFIG_BT_DRV_RX_STACK_SIZE, bt_rx_thread, NULL, NULL, NULL,
381 		K_PRIO_COOP(CONFIG_BT_DRIVER_RX_HIGH_PRIO), 0, 0);
382 
hci_rx_cb(uint8_t packetType,uint8_t * data,uint16_t len)383 static void hci_rx_cb(uint8_t packetType, uint8_t *data, uint16_t len)
384 {
385 	struct hci_data hci_rx_frame;
386 	int ret;
387 
388 	hci_rx_frame.packetType = packetType;
389 	hci_rx_frame.data = k_malloc(len);
390 
391 	if (!hci_rx_frame.data) {
392 		LOG_ERR("Failed to allocate RX buffer");
393 		return;
394 	}
395 
396 	memcpy(hci_rx_frame.data, data, len);
397 	hci_rx_frame.len = len;
398 
399 	ret = k_msgq_put(&rx_msgq, &hci_rx_frame, K_NO_WAIT);
400 	if (ret < 0) {
401 		LOG_ERR("Failed to push RX data to message queue: %d", ret);
402 		k_free(hci_rx_frame.data);
403 	}
404 }
405 
406 #else  /* CONFIG_HCI_NXP_RX_THREAD */
407 
hci_rx_cb(uint8_t packetType,uint8_t * data,uint16_t len)408 static void hci_rx_cb(uint8_t packetType, uint8_t *data, uint16_t len)
409 {
410 	process_rx(packetType, data, len);
411 }
412 #endif /* CONFIG_HCI_NXP_RX_THREAD */
413 
bt_nxp_send(const struct device * dev,struct net_buf * buf)414 static int bt_nxp_send(const struct device *dev, struct net_buf *buf)
415 {
416 	ARG_UNUSED(dev);
417 
418 #if defined(HCI_NXP_LOCK_STANDBY_BEFORE_SEND)
419 	/* Sending an HCI message requires to wake up the controller core if it's asleep.
420 	 * Platform controllers may send reponses using non wakeable interrupts which can
421 	 * be lost during standby usage.
422 	 * Blocking standby usage until the HCI message is sent.
423 	 */
424 	pm_policy_state_lock_get(PM_STATE_STANDBY, PM_ALL_SUBSTATES);
425 #endif
426 	PLATFORM_SendHciMessage(buf->data, buf->len);
427 #if defined(HCI_NXP_LOCK_STANDBY_BEFORE_SEND)
428 	pm_policy_state_lock_put(PM_STATE_STANDBY, PM_ALL_SUBSTATES);
429 #endif
430 
431 	net_buf_unref(buf);
432 
433 	return 0;
434 }
435 
bt_nxp_open(const struct device * dev,bt_hci_recv_t recv)436 static int bt_nxp_open(const struct device *dev, bt_hci_recv_t recv)
437 {
438 	struct bt_nxp_data *hci = dev->data;
439 	int ret = 0;
440 
441 	do {
442 		ret = PLATFORM_InitBle();
443 		if (ret < 0) {
444 			LOG_ERR("Failed to initialize BLE controller");
445 			break;
446 		}
447 
448 		ret = PLATFORM_SetHciRxCallback(hci_rx_cb);
449 		if (ret < 0) {
450 			LOG_ERR("BLE HCI RX callback registration failed");
451 			break;
452 		}
453 
454 		ret = PLATFORM_StartHci();
455 		if (ret < 0) {
456 			LOG_ERR("HCI open failed");
457 			break;
458 		}
459 
460 		hci->recv = recv;
461 	} while (false);
462 
463 	return ret;
464 }
465 
bt_nxp_setup(const struct device * dev,const struct bt_hci_setup_params * params)466 int bt_nxp_setup(const struct device *dev, const struct bt_hci_setup_params *params)
467 {
468 	ARG_UNUSED(dev);
469 
470 	int ret = 0;
471 
472 	do {
473 		if (IS_ENABLED(CONFIG_HCI_NXP_SET_CAL_DATA)) {
474 			ret = bt_nxp_set_calibration_data();
475 			if (ret < 0) {
476 				LOG_ERR("Failed to set calibration data");
477 				break;
478 			}
479 			if (IS_ENABLED(CONFIG_HCI_NXP_SET_CAL_DATA_ANNEX100)) {
480 				/* After send annex55 to CPU2, CPU2 need reset,
481 				 * a delay of at least 20ms is required to continue sending annex100
482 				 */
483 				k_sleep(Z_TIMEOUT_MS(20));
484 
485 				ret = bt_nxp_set_calibration_data_annex100();
486 				if (ret < 0) {
487 					LOG_ERR("Failed to set calibration data");
488 					break;
489 				}
490 			}
491 		}
492 
493 		if (IS_ENABLED(CONFIG_HCI_NXP_ENABLE_AUTO_SLEEP)) {
494 			ret = nxp_bt_set_host_sleep_config();
495 			if (ret < 0) {
496 				LOG_ERR("Failed to set host sleep config");
497 				break;
498 			}
499 
500 			ret = nxp_bt_enable_controller_autosleep();
501 			if (ret < 0) {
502 				LOG_ERR("Failed to configure controller autosleep");
503 				break;
504 			}
505 		}
506 
507 		if (IS_ENABLED(CONFIG_BT_HCI_SET_PUBLIC_ADDR)) {
508 			ret = bt_nxp_set_mac_address(&(params->public_addr));
509 			if (ret < 0) {
510 				LOG_ERR("Failed to set MAC address");
511 				break;
512 			}
513 		}
514 	} while (false);
515 
516 	return ret;
517 }
518 
bt_nxp_close(const struct device * dev)519 static int bt_nxp_close(const struct device *dev)
520 {
521 	struct bt_nxp_data *hci = dev->data;
522 	int ret = 0;
523 
524 	hci->recv = NULL;
525 
526 	return ret;
527 }
528 
529 static DEVICE_API(bt_hci, drv) = {
530 	.open = bt_nxp_open,
531 	.setup = bt_nxp_setup,
532 	.close = bt_nxp_close,
533 	.send = bt_nxp_send,
534 };
535 
bt_nxp_init(const struct device * dev)536 static int bt_nxp_init(const struct device *dev)
537 {
538 	int status;
539 	int ret = 0;
540 
541 	ARG_UNUSED(dev);
542 
543 	do {
544 		status = PLATFORM_InitBle();
545 		if (status < 0) {
546 			LOG_ERR("BLE Controller initialization failed");
547 			ret = status;
548 			break;
549 		}
550 	} while (0);
551 
552 	return ret;
553 }
554 
555 #define HCI_DEVICE_INIT(inst) \
556 	static struct bt_nxp_data hci_data_##inst = { \
557 	}; \
558 	DEVICE_DT_INST_DEFINE(inst, bt_nxp_init, NULL, &hci_data_##inst, NULL, \
559 			      POST_KERNEL, CONFIG_BT_HCI_INIT_PRIORITY, &drv)
560 
561 /* Only one instance supported right now */
562 HCI_DEVICE_INIT(0)
563