diff --git a/boards/realtek/rtl8752h_evb/rtl8752h_evb.dts b/boards/realtek/rtl8752h_evb/rtl8752h_evb.dts index c831aca5d899d..36e8f0c1b5a98 100644 --- a/boards/realtek/rtl8752h_evb/rtl8752h_evb.dts +++ b/boards/realtek/rtl8752h_evb/rtl8752h_evb.dts @@ -50,6 +50,7 @@ pinctrl-1 = <&uart2_sleep>; pinctrl-names = "default", "sleep"; status = "okay"; + //status = "disabled"; current-speed = <2000000>; parity = "none"; stop-bits = "1"; diff --git a/drivers/bluetooth/hci/hci_rtl87x2g.c b/drivers/bluetooth/hci/hci_rtl87x2g.c index bcbfa355014b4..5592503a6205a 100644 --- a/drivers/bluetooth/hci/hci_rtl87x2g.c +++ b/drivers/bluetooth/hci/hci_rtl87x2g.c @@ -1,3 +1,9 @@ +/* + * Copyright(c) 2020, Realtek Semiconductor Corporation. + * + * SPDX-License-Identifier: Apache-2.0 + */ + /* * Copyright(c) 2020, Realtek Semiconductor Corporation. * @@ -11,6 +17,10 @@ #include "rtl_bt_hci.h" #include "trace.h" +/* RTL_FIXME[🧩📡🔌] rtl hci driver */ + +#if 0//defined(CONFIG_BT_RECV_BLOCKING) + #define F_RTK_BT_HCI_H2C_POOL_SIZE 3 * 1024 LOG_MODULE_REGISTER(bt_driver, CONFIG_BT_HCI_DRIVER_LOG_LEVEL); @@ -60,9 +70,55 @@ static bool bt_rtl87x2x_check_hci_event_discardable(const uint8_t *event_data) } } + +#if defined(CONFIG_SOC_SERIES_RTL8752H) +#include "rtl876x_pinmux.h" +#elif defined(CONFIG_SOC_SERIES_RTL87X2G) +#include "rtl_pinmux.h" +#endif + + +#define BT_HCI_EVT_FLAG_RECV_PRIO BIT(0) +#define BT_HCI_EVT_FLAG_RECV BIT(1) + +void hci_event_prio(struct net_buf *buf); + +static inline uint8_t bt_hci_evt_get_flags(uint8_t evt) +{ + switch (evt) { + case BT_HCI_EVT_DISCONN_COMPLETE: + return BT_HCI_EVT_FLAG_RECV | BT_HCI_EVT_FLAG_RECV_PRIO; + /* fallthrough */ +#if defined(CONFIG_BT_CONN) || defined(CONFIG_BT_ISO) + case BT_HCI_EVT_NUM_COMPLETED_PACKETS: +#if defined(CONFIG_BT_CONN) + case BT_HCI_EVT_DATA_BUF_OVERFLOW: + __fallthrough; +#endif /* defined(CONFIG_BT_CONN) */ +#endif /* CONFIG_BT_CONN || CONFIG_BT_ISO */ + case BT_HCI_EVT_CMD_COMPLETE: + case BT_HCI_EVT_CMD_STATUS: + return BT_HCI_EVT_FLAG_RECV_PRIO; + default: + return BT_HCI_EVT_FLAG_RECV; + } +} + + +int bt_recv_prio(struct net_buf *buf) +{ + //bt_monitor_send(bt_monitor_opcode(buf), buf->data, buf->len); + + //BT_ASSERT(bt_buf_get_type(buf) == BT_BUF_EVT); + + hci_event_prio(buf); + + return 0; +} static bool bt_rtl87x2x_recv_cb(T_RTL_BT_HCI_EVT evt, bool status, uint8_t *p_buf, uint32_t len) { int ret = 0; + //const struct device *dev = DEVICE_DT_GET(DT_DRV_INST(0)); LOG_DBG("%s: evt %u status %u, type %u, len %u", __func__, evt, status, p_buf[0], len); switch (evt) { @@ -75,8 +131,45 @@ static bool bt_rtl87x2x_recv_cb(T_RTL_BT_HCI_EVT evt, bool status, uint8_t *p_bu case BT_HCI_EVT_DATA_IND: { T_RTL_BT_RX_BUF *p_rx_buf; + if (p_buf[0] == H4_EVT) { + uint8_t evt_flags; + struct bt_hci_evt_hdr hdr; + + memcpy((void *)&hdr, &p_buf[1], sizeof(hdr)); + evt_flags = bt_hci_evt_get_flags(hdr.evt); + //if (evt_flags & BT_HCI_EVT_FLAG_RECV_PRIO) { + if (IS_ENABLED(CONFIG_BT_RECV_BLOCKING) && (evt_flags & BT_HCI_EVT_FLAG_RECV_PRIO)) { + size_t buf_tailroom; + struct net_buf *z_buf = bt_buf_get_evt(hdr.evt, false, K_NO_WAIT); + if (z_buf != NULL) { + buf_tailroom = net_buf_tailroom(z_buf); + + if (buf_tailroom >= (hdr.len + 2)) { + net_buf_add_mem(z_buf, &p_buf[1], hdr.len + 2); + bt_buf_set_type(z_buf, BT_BUF_EVT); + bt_recv_prio(z_buf); + if ((evt_flags & BT_HCI_EVT_FLAG_RECV) == 0) { + rtl_bt_hci_ack(p_buf); + break; + } else { + net_buf_unref(z_buf); + } + } else { + DBG_DIRECT("[ERR] H4_EVT prio: event 0x%x, buf_tailroom %d, alloc failed", + hdr.evt, buf_tailroom); + LOG_ERR("H4_EVT prio: event 0x%x, buf_tailroom %d, alloc failed", hdr.evt, buf_tailroom); + net_buf_unref(z_buf); + } + } else { + DBG_DIRECT("[ERR] H4_EVT prio: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); + LOG_ERR("H4_EVT prio: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); + } + } + } + // Pad_Config(P2_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_HIGH); p_rx_buf = calloc(1, sizeof(T_RTL_BT_RX_BUF)); + // Pad_Config(P2_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_LOW); if (p_rx_buf) { /* DBG_DIRECT("[BT] p_rx_buf %p, p_buf %p", p_rx_buf, p_buf); */ p_rx_buf->p_buf = p_buf; @@ -119,15 +212,18 @@ void bt_rtl87x2x_handle_rx_data(T_RTL_BT_RX_BUF *p_rx_buf) memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); discardable = bt_rtl87x2x_check_hci_event_discardable(&p_rx_buf->p_buf[1]); - + //Pad_Config(P2_1, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_HIGH); z_buf = bt_buf_get_evt(hdr.evt, discardable, K_NO_WAIT); + //Pad_Config(P2_1, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_LOW); if (z_buf != NULL) { buf_tailroom = net_buf_tailroom(z_buf); if (buf_tailroom >= (hdr.len + sizeof(hdr))) { net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); LOG_DBG("H4_EVT: event 0x%x", hdr.evt); + //Pad_Config(P2_1, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_HIGH); hci->recv(dev, z_buf); + //Pad_Config(P2_1, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_LOW); break; } net_buf_unref(z_buf); @@ -214,6 +310,738 @@ static void rtl_rx_thread(void *p1, void *p2, void *p3) } } +#else +// static bool bt_rtl87x2x_recv_cb(T_RTL_BT_HCI_EVT evt, bool status, uint8_t *p_buf, uint32_t len) +// { +// int ret = 0; + +// LOG_DBG("%s: evt %u status %u, type %u, len %u", __func__, evt, status, p_buf[0], len); +// switch (evt) { +// case BT_HCI_EVT_OPENED: { +// LOG_DBG("BT_HCI_EVT_OPENED"); +// if (status == false) { +// ret = -EXDEV; +// } +// } break; + +// case BT_HCI_EVT_DATA_IND: { +// T_RTL_BT_RX_BUF *p_rx_buf; + +// p_rx_buf = calloc(1, sizeof(T_RTL_BT_RX_BUF)); +// if (p_rx_buf) { +// /* DBG_DIRECT("[BT] p_rx_buf %p, p_buf %p", p_rx_buf, p_buf); */ +// p_rx_buf->p_buf = p_buf; +// p_rx_buf->len = len; +// k_fifo_put(&rx.fifo, p_rx_buf); +// break; +// } +// rtl_bt_hci_ack(p_buf); +// } break; + +// default: +// ret = -EINVAL; +// break; +// } + +// if (ret != 0) { +// DBG_DIRECT("[ERR] bt_rtl87x2g_recv_cb: error, evt %d status %d, type %d, len %d, " +// "ret %d", +// evt, status, p_buf[0], len, ret); +// LOG_ERR("bt_rtl87x2g_recv_cb: error, evt %u status %u, type %u, len %u, ret %d", +// evt, status, p_buf[0], len, ret); +// return false; +// } + +// return true; +// } + +// void bt_rtl87x2x_handle_rx_data(T_RTL_BT_RX_BUF *p_rx_buf) +// { +// const struct device *dev = DEVICE_DT_GET(DT_DRV_INST(0)); +// struct bt_rtl_data *hci = dev->data; +// struct net_buf *z_buf = NULL; +// size_t buf_tailroom = 0; +// /* First byte is packet type */ +// switch (p_rx_buf->p_buf[0]) { +// case H4_EVT: { +// bool discardable = false; +// struct bt_hci_evt_hdr hdr; + +// memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + +// discardable = bt_rtl87x2x_check_hci_event_discardable(&p_rx_buf->p_buf[1]); + +// z_buf = bt_buf_get_evt(hdr.evt, discardable, K_NO_WAIT); +// if (z_buf != NULL) { +// buf_tailroom = net_buf_tailroom(z_buf); + +// if (buf_tailroom >= (hdr.len + sizeof(hdr))) { +// net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); +// LOG_DBG("H4_EVT: event 0x%x", hdr.evt); +// hci->recv(dev, z_buf); +// break; +// } +// net_buf_unref(z_buf); +// } +// DBG_DIRECT("[ERR] H4_EVT: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); +// LOG_ERR("H4_EVT: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); +// } break; + +// case H4_ACL: { +// struct bt_hci_acl_hdr hdr; + +// memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + +// z_buf = bt_buf_get_rx(BT_BUF_ACL_IN, K_NO_WAIT); +// if (z_buf != NULL) { +// buf_tailroom = net_buf_tailroom(z_buf); +// if (buf_tailroom >= (hdr.len + sizeof(hdr))) { +// net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); +// LOG_DBG("H4_ACL: handle 0x%x, Calling bt_recv(%p)", hdr.handle, +// z_buf); +// hci->recv(dev, z_buf); +// break; +// } +// net_buf_unref(z_buf); +// } +// DBG_DIRECT("[ERR] H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// LOG_ERR("H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// } break; + +// case H4_ISO: { +// struct bt_hci_iso_hdr hdr; + +// memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + +// z_buf = bt_buf_get_rx(BT_BUF_ISO_IN, K_NO_WAIT); +// if (z_buf != NULL) { +// buf_tailroom = net_buf_tailroom(z_buf); +// if (buf_tailroom >= (hdr.len + sizeof(hdr))) { +// net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); +// LOG_DBG("H4_ISO: handle 0x%x, Calling bt_recv(%p)", hdr.handle, +// z_buf); +// hci->recv(dev, z_buf); +// break; +// } +// net_buf_unref(z_buf); +// } +// DBG_DIRECT("[ERR] H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// LOG_ERR("H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// } break; + +// default: +// DBG_DIRECT("[ERR] rtl_rx_thread: invalid type %d", p_rx_buf->p_buf[0]); +// LOG_ERR("rtl_rx_thread: invalid type %d", p_rx_buf->p_buf[0]); +// break; +// } +// rtl_bt_hci_ack(p_rx_buf->p_buf); +// free(p_rx_buf); +// } + +// static void rtl_rx_thread(void *p1, void *p2, void *p3) +// { +// T_RTL_BT_RX_BUF *p_rx_buf; + +// ARG_UNUSED(p1); +// ARG_UNUSED(p2); +// ARG_UNUSED(p3); + +// while (1) { +// p_rx_buf = k_fifo_get(&rx.fifo, K_FOREVER); +// do { +// /* DBG_DIRECT("[BT] thread, p_rx_buf %p, p_buf %p", p_rx_buf, +// * p_rx_buf->p_buf); +// */ +// bt_rtl87x2x_handle_rx_data(p_rx_buf); + +// /* Give other threads a chance to run if the ISR +// * is receiving data so fast that rx.fifo never +// * or very rarely goes empty. +// */ +// k_yield(); + +// p_rx_buf = k_fifo_get(&rx.fifo, K_NO_WAIT); +// } while (p_rx_buf); +// } +// } + + +/*zhiyuan-fix-2025-07-30*/ +// #include "rtl_bt_hci.h" +// #include "trace.h" + +// #define BT_HCI_EVT_FLAG_RECV_PRIO BIT(0) +// #define BT_HCI_EVT_FLAG_RECV BIT(1) + +// #define F_RTK_BT_HCI_H2C_POOL_SIZE 3*1024 + +// LOG_MODULE_REGISTER(bt_driver, CONFIG_BT_HCI_DRIVER_LOG_LEVEL); +// #define DT_DRV_COMPAT realtek_bee_bt_hci + +// struct k_thread rx_thread_data; +// static K_KERNEL_STACK_DEFINE(rx_thread_stack, CONFIG_BT_RX_STACK_SIZE); + +// typedef struct +// { +// intptr_t _unused; +// uint8_t *p_buf; +// uint32_t len; +// } T_RTL_BT_RX_BUF; + +// static struct +// { +// struct k_fifo fifo; +// } rx = +// { +// .fifo = Z_FIFO_INITIALIZER(rx.fifo), +// }; + +// struct bt_rtl_data { +// bt_hci_recv_t recv; +// }; + +// static inline uint8_t bt_hci_evt_get_flags(uint8_t evt) +// { +// switch (evt) { +// case BT_HCI_EVT_DISCONN_COMPLETE: +// return BT_HCI_EVT_FLAG_RECV | BT_HCI_EVT_FLAG_RECV_PRIO; +// /* fallthrough */ +// #if defined(CONFIG_BT_CONN) || defined(CONFIG_BT_ISO) +// case BT_HCI_EVT_NUM_COMPLETED_PACKETS: +// #if defined(CONFIG_BT_CONN) +// case BT_HCI_EVT_DATA_BUF_OVERFLOW: +// __fallthrough; +// #endif /* defined(CONFIG_BT_CONN) */ +// #endif /* CONFIG_BT_CONN || CONFIG_BT_ISO */ +// case BT_HCI_EVT_CMD_COMPLETE: +// case BT_HCI_EVT_CMD_STATUS: +// return BT_HCI_EVT_FLAG_RECV_PRIO; +// default: +// return BT_HCI_EVT_FLAG_RECV; +// } +// } + +// extern void hci_event_prio(struct net_buf *buf); +// static int bt_recv_prio(struct net_buf *buf) +// { +// //bt_monitor_send(bt_monitor_opcode(buf), buf->data, buf->len); + +// //BT_ASSERT(bt_buf_get_type(buf) == BT_BUF_EVT); + +// hci_event_prio(buf); + +// return 0; +// } + +// static bool bt_rtl87x2x_check_hci_event_discardable(const uint8_t *event_data) +// { +// uint8_t event_type = event_data[0]; + +// switch (event_type) { +// #if defined(CONFIG_BT_CLASSIC) +// case BT_HCI_EVT_INQUIRY_RESULT_WITH_RSSI: +// case BT_HCI_EVT_EXTENDED_INQUIRY_RESULT: +// return true; +// #endif +// case BT_HCI_EVT_LE_META_EVENT: +// { +// uint8_t sub_event_type = event_data[sizeof(struct bt_hci_evt_hdr)]; + +// switch (sub_event_type) { +// case BT_HCI_EVT_LE_ADVERTISING_REPORT: +// return true; +// default: +// return false; +// } +// } +// default: +// return false; +// } +// } + + + +// static bool bt_rtl87x2x_recv_cb(T_RTL_BT_HCI_EVT evt, bool status, uint8_t *p_buf, uint32_t len) +// { +// int ret = 0; +// // const struct device *dev = DEVICE_DT_GET(DT_DRV_INST(0)); + +// LOG_DBG("%s: evt %u status %u, type %u, len %u", __func__, evt, +// status, p_buf[0], len); +// switch (evt) { +// case BT_HCI_EVT_OPENED: +// { +// LOG_DBG("BT_HCI_EVT_OPENED"); +// if (status == false) { +// ret = -EXDEV; +// } +// } +// break; + +// case BT_HCI_EVT_DATA_IND: +// { +// T_RTL_BT_RX_BUF *p_rx_buf; + +// if (p_buf[0] == H4_EVT) { +// uint8_t evt_flags; +// struct bt_hci_evt_hdr hdr; + +// memcpy((void *)&hdr, &p_buf[1], sizeof(hdr)); +// evt_flags = bt_hci_evt_get_flags(hdr.evt); +// if (evt_flags & BT_HCI_EVT_FLAG_RECV_PRIO) { +// size_t buf_tailroom; +// struct net_buf *z_buf = bt_buf_get_evt(hdr.evt, false, K_NO_WAIT); + +// if (z_buf != NULL) { +// buf_tailroom = net_buf_tailroom(z_buf); + +// if (buf_tailroom >= (hdr.len + 2)) { +// net_buf_add_mem(z_buf, &p_buf[1], hdr.len + 2); +// bt_buf_set_type(z_buf, BT_BUF_EVT); +// bt_recv_prio(z_buf); +// if ((evt_flags & BT_HCI_EVT_FLAG_RECV) == 0) { +// rtl_bt_hci_ack(p_buf); +// break; +// } else { +// net_buf_unref(z_buf); +// } +// } else { +// DBG_DIRECT("[ERR] H4_EVT prio: event 0x%x, buf_tailroom %d, alloc failed", +// hdr.evt, buf_tailroom); +// LOG_ERR("H4_EVT prio: event 0x%x, buf_tailroom %d, alloc failed", hdr.evt, buf_tailroom); +// net_buf_unref(z_buf); +// } +// } else { +// DBG_DIRECT("[ERR] H4_EVT prio: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); +// LOG_ERR("H4_EVT prio: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); +// } +// } +// } + +// p_rx_buf = calloc(1, sizeof(T_RTL_BT_RX_BUF)); +// if (p_rx_buf) { +// /* DBG_DIRECT("[BT] p_rx_buf %p, p_buf %p", p_rx_buf, p_buf); */ +// p_rx_buf->p_buf = p_buf; +// p_rx_buf->len = len; +// k_fifo_put(&rx.fifo, p_rx_buf); +// break; +// } +// rtl_bt_hci_ack(p_buf); +// } +// break; +// default: +// ret = -EINVAL; +// break; +// } +// if (ret != 0) { +// DBG_DIRECT("[ERR] bt_rtl87x2g_recv_cb: error, evt %d status %d, type %d, len %d, ret %d", +// evt, status, p_buf[0], len, ret); +// LOG_ERR("bt_rtl87x2g_recv_cb: error, evt %u status %u, type %u, len %u, ret %d", evt, +// status, p_buf[0], len, ret); +// return false; +// } +// return true; +// } + +// void bt_rtl87x2x_handle_rx_data(T_RTL_BT_RX_BUF *p_rx_buf) +// { +// const struct device *dev = DEVICE_DT_GET(DT_DRV_INST(0)); +// struct bt_rtl_data *hci = dev->data; +// struct net_buf *z_buf = NULL; +// size_t buf_tailroom = 0; +// /* First byte is packet type */ +// switch (p_rx_buf->p_buf[0]) { +// case H4_EVT: +// { +// bool discardable = false; +// struct bt_hci_evt_hdr hdr; +// memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); +// discardable = bt_rtl87x2x_check_hci_event_discardable(&p_rx_buf->p_buf[1]); + +// z_buf = bt_buf_get_evt(hdr.evt, discardable, K_NO_WAIT); +// if (z_buf != NULL) { +// buf_tailroom = net_buf_tailroom(z_buf); + +// if (buf_tailroom >= (hdr.len + sizeof(hdr))) { +// net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); +// LOG_DBG("H4_EVT: event 0x%x", hdr.evt); +// hci->recv(dev, z_buf); +// break; +// } +// net_buf_unref(z_buf); +// } +// DBG_DIRECT("[ERR] H4_EVT: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); +// LOG_ERR("H4_EVT: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); +// } +// break; +// case H4_ACL: +// { +// struct bt_hci_acl_hdr hdr; + +// memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + +// z_buf = bt_buf_get_rx(BT_BUF_ACL_IN, K_NO_WAIT); +// if (z_buf != NULL) { +// buf_tailroom = net_buf_tailroom(z_buf); +// if (buf_tailroom >= (hdr.len + sizeof(hdr))) { +// net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); +// LOG_DBG("H4_ACL: handle 0x%x, Calling bt_recv(%p)", hdr.handle, z_buf); +// hci->recv(dev, z_buf); +// break; +// } +// net_buf_unref(z_buf); +// } +// DBG_DIRECT("[ERR] H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// LOG_ERR("H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// } +// break; + +// case H4_ISO: +// { +// struct bt_hci_iso_hdr hdr; + +// memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + +// z_buf = bt_buf_get_rx(BT_BUF_ISO_IN, K_NO_WAIT); +// if (z_buf != NULL) { +// buf_tailroom = net_buf_tailroom(z_buf); +// if (buf_tailroom >= (hdr.len + sizeof(hdr))) { +// net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); +// LOG_DBG("H4_ISO: handle 0x%x, Calling bt_recv(%p)", hdr.handle, z_buf); +// hci->recv(dev, z_buf); +// break; +// } +// net_buf_unref(z_buf); +// } +// DBG_DIRECT("[ERR] H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// LOG_ERR("H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); +// } +// break; + +// default: +// DBG_DIRECT("[ERR] rtl_rx_thread: invalid type %d", p_rx_buf->p_buf[0]); +// LOG_ERR("rtl_rx_thread: invalid type %d", p_rx_buf->p_buf[0]); +// break; +// } +// rtl_bt_hci_ack(p_rx_buf->p_buf); +// free(p_rx_buf); +// } + +// static void rtl_rx_thread(void *p1, void *p2, void *p3) +// { +// T_RTL_BT_RX_BUF *p_rx_buf; + + + +// ARG_UNUSED(p1); +// ARG_UNUSED(p2); +// ARG_UNUSED(p3); + +// while (1) { +// p_rx_buf = k_fifo_get(&rx.fifo, K_FOREVER); +// do { +// /* DBG_DIRECT("[BT] thread, p_rx_buf %p, p_buf %p", p_rx_buf, p_rx_buf->p_buf); */ + +// bt_rtl87x2x_handle_rx_data(p_rx_buf); + +// /* Give other threads a chance to run if the ISR +// * is receiving data so fast that rx.fifo never +// * or very rarely goes empty. +// */ +// k_yield(); + +// p_rx_buf = k_fifo_get(&rx.fifo, K_NO_WAIT); +// } while (p_rx_buf); +// } +// } + +/* + grok3 fix 2025-08-01 + */ +#include +/* RTL_FIXME[🧩📡🔌] rtl hci driver */ +#define F_RTK_BT_HCI_H2C_POOL_SIZE 3 * 1024 + +LOG_MODULE_REGISTER(bt_driver, CONFIG_BT_HCI_DRIVER_LOG_LEVEL); + +#define DT_DRV_COMPAT realtek_bee_bt_hci + +typedef struct { + intptr_t _unused; + uint8_t *p_buf; + uint32_t len; +} T_RTL_BT_RX_BUF; + +// ---- FIFO和SLAB初始化 ---- + +// 定义FIFO: 放入结构体(Zephyr官方写法) +static struct { + struct k_fifo fifo; +} rx = { + .fifo = Z_FIFO_INITIALIZER(rx.fifo), +}; + +// SLAB 不要放进结构体,单独全局静态定义 +K_MEM_SLAB_DEFINE(rx_slab, sizeof(T_RTL_BT_RX_BUF), 16, 4); + +struct bt_rtl_data { + bt_hci_recv_t recv; +}; + +struct k_thread rx_thread_data; +static K_KERNEL_STACK_DEFINE(rx_thread_stack, CONFIG_BT_RX_STACK_SIZE); + +static bool bt_rtl87x2x_check_hci_event_discardable(const uint8_t *event_data) +{ + uint8_t event_type = event_data[0]; + switch (event_type) { +#if defined(CONFIG_BT_CLASSIC) + case BT_HCI_EVT_INQUIRY_RESULT_WITH_RSSI: + case BT_HCI_EVT_EXTENDED_INQUIRY_RESULT: + return true; +#endif + case BT_HCI_EVT_LE_META_EVENT: { + uint8_t sub_event_type = event_data[sizeof(struct bt_hci_evt_hdr)]; + switch (sub_event_type) { + case BT_HCI_EVT_LE_ADVERTISING_REPORT: + return true; + default: + return false; + } + } + default: + return false; + } +} + +#if defined(CONFIG_SOC_SERIES_RTL8752H) +#include "rtl876x_pinmux.h" +#elif defined(CONFIG_SOC_SERIES_RTL87X2G) +#include "rtl_pinmux.h" +#endif + +#define BT_HCI_EVT_FLAG_RECV_PRIO BIT(0) +#define BT_HCI_EVT_FLAG_RECV BIT(1) + +void hci_event_prio(struct net_buf *buf); + +static inline uint8_t bt_hci_evt_get_flags(uint8_t evt) +{ + switch (evt) { + case BT_HCI_EVT_DISCONN_COMPLETE: + return BT_HCI_EVT_FLAG_RECV | BT_HCI_EVT_FLAG_RECV_PRIO; +#if defined(CONFIG_BT_CONN) || defined(CONFIG_BT_ISO) + case BT_HCI_EVT_NUM_COMPLETED_PACKETS: +#if defined(CONFIG_BT_CONN) + case BT_HCI_EVT_DATA_BUF_OVERFLOW: + __fallthrough; +#endif /* defined(CONFIG_BT_CONN) */ +#endif /* CONFIG_BT_CONN || CONFIG_BT_ISO */ + case BT_HCI_EVT_CMD_COMPLETE: + case BT_HCI_EVT_CMD_STATUS: + return BT_HCI_EVT_FLAG_RECV_PRIO; + default: + return BT_HCI_EVT_FLAG_RECV; + } +} + +int bt_recv_prio(struct net_buf *buf) +{ + hci_event_prio(buf); + return 0; +} + +T_RTL_BT_RX_BUF *rx_p_buf = NULL; +int slab_ret; +static bool bt_rtl87x2x_recv_cb(T_RTL_BT_HCI_EVT evt, bool status, uint8_t *p_buf, uint32_t len) +{ + int ret = 0; + + LOG_DBG("%s: evt %u status %u, type %u, len %u", __func__, evt, status, p_buf[0], len); + + switch (evt) { + case BT_HCI_EVT_OPENED: { + LOG_DBG("BT_HCI_EVT_OPENED"); + if (status == false) { + ret = -EXDEV; + } + } break; + + case BT_HCI_EVT_DATA_IND: { + if (p_buf[0] == H4_EVT) { + uint8_t evt_flags; + struct bt_hci_evt_hdr hdr; + + memcpy((void *)&hdr, &p_buf[1], sizeof(hdr)); + evt_flags = bt_hci_evt_get_flags(hdr.evt); + if (evt_flags & BT_HCI_EVT_FLAG_RECV_PRIO) { + size_t buf_tailroom; + struct net_buf *z_buf = bt_buf_get_evt(hdr.evt, false, K_NO_WAIT); + + if (z_buf != NULL) { + buf_tailroom = net_buf_tailroom(z_buf); + + if (buf_tailroom >= (hdr.len + 2)) { + net_buf_add_mem(z_buf, &p_buf[1], hdr.len + 2); + bt_buf_set_type(z_buf, BT_BUF_EVT); + bt_recv_prio(z_buf); + if ((evt_flags & BT_HCI_EVT_FLAG_RECV) == 0) { + rtl_bt_hci_ack(p_buf); + break; + } else { + net_buf_unref(z_buf); + } + } else { + DBG_DIRECT("[ERR] H4_EVT prio: event 0x%x, buf_tailroom %d, alloc failed", + hdr.evt, buf_tailroom); + LOG_ERR("H4_EVT prio: event 0x%x, buf_tailroom %d, alloc failed", hdr.evt, buf_tailroom); + net_buf_unref(z_buf); + } + } else { + DBG_DIRECT("[ERR] H4_EVT prio: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); + LOG_ERR("H4_EVT prio: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); + } + } + } + //Pad_Config(P2_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_HIGH); + slab_ret = k_mem_slab_alloc(&rx_slab, (void **)&rx_p_buf, K_NO_WAIT); + //Pad_Config(P2_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_LOW); + if (slab_ret == 0) { + rx_p_buf->p_buf = p_buf; + rx_p_buf->len = len; + k_fifo_put(&rx.fifo, rx_p_buf); + } else { + // DBG_DIRECT("[ERR] H4_%s: alloc failed", p_buf[0] == H4_EVT ? "EVT" : + // p_buf[0] == H4_ACL ? "ACL" : "ISO"); + // LOG_ERR("H4_%s: alloc failed", p_buf[0] == H4_EVT ? "EVT" : + // p_buf[0] == H4_ACL ? "ACL" : "ISO"); + rtl_bt_hci_ack(p_buf); + LOG_ERR("H4_%s: alloc failed", p_buf[0] == H4_EVT ? "EVT" :"ACL"); + //p_buf[0] == H4_ACL ? "ACL" : "ISO"); + ret = -ENOMEM; + } + } break; + + default: + ret = -EINVAL; + break; + } + + if (ret != 0) { + DBG_DIRECT("[ERR] bt_rtl87x2x_recv_cb: evt %d status %d, type %d, len %d, ret %d", + evt, status, p_buf[0], len, ret); + LOG_ERR("bt_rtl87x2x_recv_cb: evt %u status %u, type %u, len %u, ret %d", + evt, status, p_buf[0], len, ret); + return false; + } + + return true; +} + +// 其余接口不变,唯一变化点是 slab 用 rx_slab,全局独立访问 +void bt_rtl87x2x_handle_rx_data(T_RTL_BT_RX_BUF *p_rx_buf) +{ + const struct device *dev = DEVICE_DT_GET(DT_DRV_INST(0)); + struct bt_rtl_data *hci = dev->data; + struct net_buf *z_buf = NULL; + size_t buf_tailroom = 0; + + switch (p_rx_buf->p_buf[0]) { + case H4_EVT: { + + bool discardable = false; + struct bt_hci_evt_hdr hdr; + memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + discardable = bt_rtl87x2x_check_hci_event_discardable(&p_rx_buf->p_buf[1]); + + z_buf = bt_buf_get_evt(hdr.evt, discardable, K_NO_WAIT); + if (z_buf != NULL) { + buf_tailroom = net_buf_tailroom(z_buf); + + if (buf_tailroom >= (hdr.len + sizeof(hdr))) { + net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); + LOG_DBG("H4_EVT: event 0x%x", hdr.evt); + hci->recv(dev, z_buf); + break; + } + net_buf_unref(z_buf); + + } else { + DBG_DIRECT("[ERR] H4_EVT: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); + LOG_ERR("H4_EVT: event 0x%x, len %d, alloc failed", hdr.evt, hdr.len); + } + } break; + + case H4_ACL: { + struct bt_hci_acl_hdr hdr; + memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + z_buf = bt_buf_get_rx(BT_BUF_ACL_IN, K_NO_WAIT); + if (z_buf != NULL) { + buf_tailroom = net_buf_tailroom(z_buf); + if (buf_tailroom >= (hdr.len + sizeof(hdr))) { + net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); + LOG_DBG("H4_ACL: handle 0x%x, Calling bt_recv(%p)", hdr.handle, z_buf); + hci->recv(dev, z_buf); + } else { + DBG_DIRECT("[ERR] H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + LOG_ERR("H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + net_buf_unref(z_buf); + } + } else { + DBG_DIRECT("[ERR] H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + LOG_ERR("H4_ACL: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + } + } break; + + case H4_ISO: { + struct bt_hci_iso_hdr hdr; + memcpy((void *)&hdr, &p_rx_buf->p_buf[1], sizeof(hdr)); + z_buf = bt_buf_get_rx(BT_BUF_ISO_IN, K_NO_WAIT); + if (z_buf != NULL) { + buf_tailroom = net_buf_tailroom(z_buf); + if (buf_tailroom >= (hdr.len + sizeof(hdr))) { + net_buf_add_mem(z_buf, &p_rx_buf->p_buf[1], hdr.len + sizeof(hdr)); + LOG_DBG("H4_ISO: handle 0x%x, Calling bt_recv(%p)", hdr.handle, z_buf); + hci->recv(dev, z_buf); + } else { + DBG_DIRECT("[ERR] H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + LOG_ERR("H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + net_buf_unref(z_buf); + } + } else { + DBG_DIRECT("[ERR] H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + LOG_ERR("H4_ISO: handle 0x%x, len %d, alloc failed", hdr.handle, hdr.len); + } + } break; + + default: + DBG_DIRECT("[ERR] rtl_rx_thread: invalid type %d", p_rx_buf->p_buf[0]); + LOG_ERR("rtl_rx_thread: invalid type %d", p_rx_buf->p_buf[0]); + break; + } + + rtl_bt_hci_ack(p_rx_buf->p_buf); + k_mem_slab_free(&rx_slab, p_rx_buf); +} + +static void rtl_rx_thread(void *p1, void *p2, void *p3) +{ + T_RTL_BT_RX_BUF *p_rx_buf; + ARG_UNUSED(p1); + ARG_UNUSED(p2); + ARG_UNUSED(p3); + + while (1) { + p_rx_buf = k_fifo_get(&rx.fifo, K_FOREVER); + do { + bt_rtl87x2x_handle_rx_data(p_rx_buf); + k_yield(); + p_rx_buf = k_fifo_get(&rx.fifo, K_NO_WAIT); + } while (p_rx_buf); + } +} + +#endif static int bt_rtl87x2x_send(const struct device *dev, struct net_buf *buf) { diff --git a/drivers/gpio/gpio_bee.c b/drivers/gpio/gpio_bee.c index 7bdf4cf6f7d46..e4b9d786dc73b 100644 --- a/drivers/gpio/gpio_bee.c +++ b/drivers/gpio/gpio_bee.c @@ -501,10 +501,15 @@ static void output_pad_pm_suspend(const struct device *port, struct pm_pad_node GPIO_TypeDef *port_base = config->port_base; #endif uint8_t pad_num, gpio_num; + //uint8_t pad_num, gpio_num,val; pad_num = pad_node->pad_num; gpio_num = pad_node->gpio_num; - + //val= BEE_GPIO_ReadOutputDataBit(port_base, BIT(gpio_num)); + //DBG_DIRECT("output suspend pad num=%d,gpio num= %d,val=%d",pad_num,gpio_num,val); + //BEE_Pad_SetOutputLevel(pad_num, val); + //Pad_Config(pad_num, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_UP, PAD_OUT_ENABLE,PAD_OUT_HIGH); + BEE_Pad_SetOutputLevel(pad_num, BEE_GPIO_ReadOutputDataBit(port_base, BIT(gpio_num))); BEE_Pad_SetControlMode(pad_num, PAD_SW_MODE); } @@ -514,6 +519,7 @@ static void input_pad_pm_suspend(const struct device *port, struct pm_pad_node * uint8_t pad_num; pad_num = pad_node->pad_num; + //DBG_DIRECT("input suspend pad num=%d",pad_num); BEE_Pad_SetControlMode(pad_num, PAD_SW_MODE); } @@ -591,7 +597,7 @@ static void wakeup_pad_pm_resume(const struct device *port, struct pm_pad_node * Pinmux_Config(pad_num, DWGPIO); BEE_Pad_SetControlMode(pad_num, PAD_PINMUX_MODE); } - +#include static int gpio_bee_pm_action(const struct device *port, enum pm_device_action action) { const struct gpio_bee_config *config = port->config; diff --git a/samples/bluetooth/mesh/CMakeLists.txt b/samples/bluetooth/mesh/CMakeLists.txt index 01348921b1eb7..1b43262238650 100644 --- a/samples/bluetooth/mesh/CMakeLists.txt +++ b/samples/bluetooth/mesh/CMakeLists.txt @@ -19,3 +19,4 @@ if (CONFIG_BUILD_WITH_TFM) $/api_ns/interface/include ) endif() +# zephyr_code_relocate(FILES ${WEST_TOPDIR}/modules/hal/realtek/bee/drivers/pinmux/src/rtl8752h/rtl876x_pinmux.c LOCATION RAM) \ No newline at end of file diff --git a/samples/bluetooth/mesh/boards/rtl8752h_evb.conf b/samples/bluetooth/mesh/boards/rtl8752h_evb.conf index 9793685ce9f27..c635677c5fa08 100644 --- a/samples/bluetooth/mesh/boards/rtl8752h_evb.conf +++ b/samples/bluetooth/mesh/boards/rtl8752h_evb.conf @@ -1,11 +1,19 @@ +#RTL_DEBUG[🔧]rtl8762h mesh 开启gpio led pwm +CONFIG_GPIO=y +CONFIG_PWM=n +CONFIG_LED=y + #default use ext adv CONFIG_BT_EXT_ADV=y +#legacy adv情况下,要设置mesh adv stack,defult值1024不够用,在extend adv模式下不起作用 +CONFIG_BT_MESH_ADV_STACK_SIZE=2500 - -CONFIG_PM=y +CONFIG_PM=n CONFIG_LOG=y +CONFIG_UART_BEE_KEEP_ACTIVE_AFTER_RX_WAKEUP=y +CONFIG_UART_BEE_KEEP_ACTIVE_TIMEOUT_MSEC=10000 CONFIG_BT_MESH_CDB=y @@ -27,7 +35,8 @@ CONFIG_IDLE_STACK_SIZE=1024 #zephyr\subsys\bluetooth\common\Kconfig中配置的值:开启extend adv,值是58,开启leagcy adv,值是255 -# CONFIG_BT_BUF_EVT_DISCARDABLE_SIZE=255 +#如果没有开启blocking机制,则需要配置discardable size为255 +CONFIG_BT_BUF_EVT_DISCARDABLE_SIZE=255 CONFIG_BT_BUF_EVT_DISCARDABLE_COUNT=5 @@ -93,7 +102,16 @@ CONFIG_BT_MESH_ADV_BUF_COUNT=12 # for debug CONFIG_THREAD_NAME=y -CONFIG_ASSERT=y +#开启这个config,log_stack会由默认的768变为2048,见在zephyr\subsys\logging\Kconfig.processing中LOG_PROCESS_THREAD_STACK_SIZE +#CONFIG_ASSERT=y CONFIG_BT_MESH_PROV_LOG_LEVEL_DBG=y CONFIG_BT_MESH_TRANS_LOG_LEVEL_DBG=y CONFIG_SYS_HEAP_RUNTIME_STATS=y + +CONFIG_CODE_DATA_RELOCATION=y + +CONFIG_BT_DEVICE_NAME="RTK bee3plus Mesh Light" + +#在zephyr\subsys\bluetooth\host\Kconfig和hci core.c中添加的blocking去掉了,恢复原始的设置,因为验证: +#hci_rtl87x2g.c所以此处注销 +# CONFIG_BT_RECV_BLOCKING=y \ No newline at end of file diff --git a/samples/bluetooth/mesh/boards/rtl8752h_evb.overlay b/samples/bluetooth/mesh/boards/rtl8752h_evb.overlay new file mode 100644 index 0000000000000..739b17dad5d8b --- /dev/null +++ b/samples/bluetooth/mesh/boards/rtl8752h_evb.overlay @@ -0,0 +1,141 @@ +/ { + /*RTL_DEBUG[🔧] rtl8762h mesh gpio button pwm*/ + aliases { + sw0 = &button_0; + led0 = &led_0; + pwm-led = &pwmleds; + }; + + gpio_keys { + compatible = "gpio-keys"; + button_0: button_0 { + gpios = <&gpio 20 GPIO_ACTIVE_HIGH>; + //status = "disabled"; + }; + }; + + gpio-led { + compatible = "gpio-leds"; + led_0: led_0 { + gpios = <&gpio 13 GPIO_ACTIVE_HIGH>;/*modules\hal\realtek\bee\rtl8752h\boot\inc\rtl876x.h */ + //status = "disabled"; + }; + }; + + + +}; + +&gpio{ + status = "okay"; +}; + +/*RTK 40M clock*/ +&timer2 { + status = "disabled"; + /* 40000000/40 = 1000000 */ + prescaler = <40>; +}; + +&timer5 { + status = "okay"; + prescaler = <1>; + pwm5: pwm5 { + status = "okay"; + pinctrl-0 = <&pwm5_default>; + pinctrl-1 = <&pwm5_sleep>; + pinctrl-names = "default","sleep"; + //pinctrl-names = "default"; + }; +}; +&timer6{ + status = "okay"; + prescaler = <1>; + pwm6: pwm6{ + status = "okay"; + pinctrl-0 = <&pwm6_default>; + pinctrl-1 = <&pwm6_sleep>; + pinctrl-names = "default","sleep"; + //pinctrl-names = "default"; + }; +}; +&timer7 { + status = "okay"; + prescaler = <1>; + pwm7: pwm7 { + status = "okay"; + pinctrl-0 = <&pwm7_default>; + pinctrl-1 = <&pwm7_sleep>; + pinctrl-names = "default","sleep"; + //pinctrl-names = "default"; + }; +}; + +&pinctrl { + uart2_sleep: uart2_sleep { + group1 { + psels = ; + wakeup-low; + }; + group2 { + psels = ; + }; + }; + + pwm5_default: pwm5_default { + group1 { + psels = ; + }; + }; + pwm5_sleep: pwm5_sleep { + group1 { + psels = ; + + }; + }; + + pwm6_default: pwm6_default { + group1 { + psels = ; + }; + }; + + pwm6_sleep: pwm6_sleep { + group1 { + psels = ; + + }; + }; + + pwm7_default: pwm7_default { + group1 { + psels = ; + }; + }; + pwm7_sleep: pwm7_sleep { + group1 { + psels = ; + //psels = ; + }; + }; +}; + +/ { + pwmleds: pwmleds { + compatible = "pwm-leds"; + blue_pwm_led: blue_pwm_led { + pwms = <&pwm5 0 PWM_MSEC(5) 0>; + }; + red_pwm_led: red_pwm_led { + pwms = <&pwm6 0 PWM_MSEC(5) 0>; + }; + green_pwm_led: green_pwm_led { + pwms = <&pwm7 0 PWM_MSEC(5) 0>; + }; + + }; + +}; + + + diff --git a/samples/bluetooth/mesh/boards/rtl87x2g_evb.conf b/samples/bluetooth/mesh/boards/rtl87x2g_evb.conf new file mode 100644 index 0000000000000..166531999c972 --- /dev/null +++ b/samples/bluetooth/mesh/boards/rtl87x2g_evb.conf @@ -0,0 +1,36 @@ +#RTL_DEBUG[🔧] rtl8762g mesh 开启gpio pwm led +CONFIG_GPIO=y +CONFIG_PWM=y +CONFIG_LED=y + +#RTL_DEBUG[🔧] rtl8762g mesh conf +CONFIG_SYSTEM_WORKQUEUE_STACK_SIZE=3072 + +CONFIG_BT_MESH_SETTINGS_WORKQ_STACK_SIZE=2048 + +CONFIG_BT_EXT_ADV=y +#legacy adv情况下,要设置mesh adv stack,defult值1024不够用 +CONFIG_BT_MESH_ADV_STACK_SIZE=2500 + +CONFIG_BT_BUF_EVT_DISCARDABLE_SIZE=255 +CONFIG_BT_BUF_EVT_DISCARDABLE_COUNT=10 + +CONFIG_IDLE_STACK_SIZE=1024 +CONFIG_COUNTER=y + +CONFIG_BT_DEVICE_NAME="RTK bee4 Mesh Light" + +CONFIG_SHELL=y +CONFIG_BT_MESH_SHELL=y +# CONFIG_SHELL_HISTORY=n +CONFIG_SHELL_CMDS_SELECT=n +# CONFIG_SHELL_HELP=n +CONFIG_SHELL_TAB_AUTOCOMPLETION=n +# CONFIG_SHELL_STACK_SIZE=1500 +# CONFIG_SHELL_CMD_BUFF_SIZE=32 +CONFIG_FLASH_SHELL=n + + +CONFIG_LOG_BUFFER_SIZE=4096 +CONFIG_DEBUG_COREDUMP=y +CONFIG_DEBUG_COREDUMP_BACKEND_LOGGING=y \ No newline at end of file diff --git a/samples/bluetooth/mesh/boards/rtl87x2g_evb.overlay b/samples/bluetooth/mesh/boards/rtl87x2g_evb.overlay new file mode 100644 index 0000000000000..37f767709b672 --- /dev/null +++ b/samples/bluetooth/mesh/boards/rtl87x2g_evb.overlay @@ -0,0 +1,123 @@ +/ { + /*RTL_DEBUG[🔧] rtl8762g mesh gpio button pwm*/ + aliases { + sw0 = &button_0; + led0 = &led_0; + pwm-led = &pwmleds; + }; + + gpio_keys { + compatible = "gpio-keys"; + button_0: button_0 { + gpios = <&gpioa 25 GPIO_ACTIVE_HIGH>; + }; + }; + + gpio-led { + compatible = "gpio-leds"; + led_0: led_0 { + gpios = <&gpiob 8 GPIO_ACTIVE_HIGH>; + }; + }; + // pwmleds { + // compatible = "pwm-leds"; + + // /* NOTE: bridge TIMER0_CH0 (PA8) and LED1 (PC0) */ + // pwm_led: pwm_led { + // pwms = <&pwm8 0 0>; + + // }; + // }; + + +}; + +&gpioa { + status = "okay"; +}; + + +&gpiob { + status = "okay"; +}; + +// &timer8 { +// status = "okay"; +// prescaler = <1>; +// pwm8: pwm { +// status = "okay"; +// pinctrl-0 = <&pwm8_default>; +// pinctrl-names = "default"; +// }; +// }; + +// &pinctrl { +// pwm8_default: pwm8_default { +// group1 { +// psels = ; +// }; +// }; +// }; + +&timer8 { + status = "okay"; + prescaler = <1>; + pwm8: pwm8 { + status = "okay"; + pinctrl-0 = <&pwm8_default>; + pinctrl-names = "default"; + }; +}; +&timer9 { + status = "okay"; + prescaler = <1>; + pwm9: pwm9{ + status = "okay"; + pinctrl-0 = <&pwm9_default>; + pinctrl-names = "default"; + }; +}; +&timer10 { + status = "okay"; + prescaler = <1>; + pwm10: pwm10 { + status = "okay"; + pinctrl-0 = <&pwm10_default>; + pinctrl-names = "default"; + }; +}; + +&pinctrl { + pwm8_default: pwm8_default { + group1 { + psels = ; + }; + }; + pwm9_default: pwm9_default { + group1 { + psels = ; + }; + }; + pwm10_default: pwm10_default { + group1 { + psels = ; + }; + }; +}; + +/ { + pwmleds: pwmleds { + compatible = "pwm-leds"; + blue_pwm_led: blue_pwm_led { + pwms = <&pwm8 0 PWM_MSEC(5) 0>; + }; + red_pwm_led: red_pwm_led { + pwms = <&pwm9 0 PWM_MSEC(5) 0>; + }; + green_pwm_led: green_pwm_led { + pwms = <&pwm10 0 PWM_MSEC(5) 0>; + }; + + }; + +}; diff --git a/samples/bluetooth/mesh/prj.conf b/samples/bluetooth/mesh/prj.conf index 9c8daad91316c..361ed7146437d 100644 --- a/samples/bluetooth/mesh/prj.conf +++ b/samples/bluetooth/mesh/prj.conf @@ -25,7 +25,7 @@ CONFIG_BT_CTLR_CHAN_SEL_2=n CONFIG_BT_MESH=y CONFIG_BT_MESH_MODEL_EXTENSIONS=y CONFIG_BT_MESH_RELAY=y -CONFIG_BT_MESH_FRIEND=y +CONFIG_BT_MESH_FRIEND=n CONFIG_BT_MESH_PB_GATT=y CONFIG_BT_MESH_PB_ADV=y CONFIG_BT_MESH_GATT_PROXY=y @@ -34,3 +34,62 @@ CONFIG_BT_MESH_SUBNET_COUNT=2 CONFIG_BT_MESH_APP_KEY_COUNT=2 CONFIG_BT_MESH_MODEL_GROUP_COUNT=2 CONFIG_BT_MESH_LABEL_COUNT=3 + + +#RTL_DEBUG[🔧] common mesh conf +#2025-07-30 +CONFIG_DEBUG_OPTIMIZATIONS=n + +CONFIG_LOG=y + +CONFIG_SHELL=y +CONFIG_BT_MESH_SHELL=y +# CONFIG_SHELL_HISTORY=n +CONFIG_SHELL_CMDS_SELECT=n +CONFIG_SHELL_HELP=n +CONFIG_SHELL_TAB_AUTOCOMPLETION=n +CONFIG_SHELL_CMD_BUFF_SIZE=32 +CONFIG_FLASH_SHELL=n +#配置为1500 发现执行mesh reset-local会出现shell uart线程的栈溢出 +CONFIG_SHELL_STACK_SIZE=2048 + +CONFIG_LOG_BUFFER_SIZE=1024 + + +CONFIG_BT_MESH_CDB=y + +CONFIG_BT_MESH_CRPL=30 +CONFIG_BT_MESH_MSG_CACHE_SIZE=30 + +CONFIG_NVS_LOOKUP_CACHE=y +CONFIG_SETTINGS_NVS_NAME_CACHE=y +CONFIG_SETTINGS_NVS_NAME_CACHE_SIZE=32 + +#长时间运行mesh 使用率有720byte +CONFIG_MAIN_STACK_SIZE=1200 + +CONFIG_SPEED_OPTIMIZATIONS=y + + +# CONFIG_STDOUT_CONSOLE=y +# enable to use thread names +CONFIG_SEGGER_SYSTEMVIEW=n +CONFIG_THREAD_NAME=y +CONFIG_USE_SEGGER_RTT=y +CONFIG_TRACING=y +CONFIG_TRACING_BACKEND_RAM=y +# enable for post-mortem tracing +CONFIG_SEGGER_SYSVIEW_POST_MORTEM_MODE=n +CONFIG_TRACING_BUFFER_SIZE=4096 + +CONFIG_TICKLESS_KERNEL=n +CONFIG_TIMESLICE_SIZE=10 + +CONFIG_BT_MESH_UNPROV_BEACON_INT=10 + +#使用pubic addr +CONFIG_BT_PRIVACY=n + +CONFIG_DEBUG_COREDUMP=y +CONFIG_DEBUG_COREDUMP_BACKEND_LOGGING=y + diff --git a/samples/bluetooth/mesh/src/board.c b/samples/bluetooth/mesh/src/board.c index 3c16279774f58..3680f2489413d 100644 --- a/samples/bluetooth/mesh/src/board.c +++ b/samples/bluetooth/mesh/src/board.c @@ -63,9 +63,13 @@ static int led_init(void) if (!device_is_ready(led_dev)) { return -ENODEV; } - - err = gpio_pin_configure(led_dev, LED0_PIN, - LED0_FLAGS | GPIO_OUTPUT_INACTIVE); + //2025-07-30 + // err = gpio_pin_configure(led_dev, LED0_PIN, + // LED0_FLAGS | GPIO_OUTPUT_INACTIVE); + // err = gpio_pin_configure(led_dev, LED0_PIN, + // LED0_FLAGS | GPIO_OUTPUT_ACTIVE | GPIO_PULL_UP); + err = gpio_pin_configure(led_dev, LED0_PIN, + LED0_FLAGS | GPIO_OUTPUT_INACTIVE | GPIO_PULL_DOWN); if (err) { return err; } @@ -80,9 +84,11 @@ static int button_init(struct k_work *button_pressed) { #if DT_NODE_EXISTS(BUTTON0) int err; - - err = gpio_pin_configure(button_dev, BUTTON0_PIN, - BUTTON0_FLAGS | GPIO_INPUT); + //2025-07-30 + // err = gpio_pin_configure(button_dev, BUTTON0_PIN, + // BUTTON0_FLAGS | GPIO_INPUT); + err = gpio_pin_configure(button_dev, BUTTON0_PIN, + BUTTON0_FLAGS | GPIO_INPUT | GPIO_PULL_DOWN); if (err) { return err; } diff --git a/samples/bluetooth/mesh/src/main.c b/samples/bluetooth/mesh/src/main.c index b220b354fd5c1..c23af69156015 100644 --- a/samples/bluetooth/mesh/src/main.c +++ b/samples/bluetooth/mesh/src/main.c @@ -20,11 +20,118 @@ #include "board.h" +#if defined(CONFIG_SOC_SERIES_RTL8752H) +#include "rtl876x_pinmux.h" +#elif defined(CONFIG_SOC_SERIES_RTL87X2G) +#include "rtl_pinmux.h" +#endif + + #define OP_ONOFF_GET BT_MESH_MODEL_OP_2(0x82, 0x01) #define OP_ONOFF_SET BT_MESH_MODEL_OP_2(0x82, 0x02) #define OP_ONOFF_SET_UNACK BT_MESH_MODEL_OP_2(0x82, 0x03) #define OP_ONOFF_STATUS BT_MESH_MODEL_OP_2(0x82, 0x04) +#if CONFIG_PM +#if defined(CONFIG_SOC_SERIES_RTL8752H) +#include "rtl876x_pinmux.h" +#elif defined(CONFIG_SOC_SERIES_RTL87X2G) +#include "rtl_pinmux.h" +#endif +#include "mesh/adv.h" +#include "trace.h" +#include "dlps.h" +#if defined(CONFIG_BT_MESH_SHELL) +#include +#endif + +void pm_test_timer_expired_handler(struct k_timer *timer); +K_TIMER_DEFINE(pm_test_timer, pm_test_timer_expired_handler, NULL); +void pm_test_timer_expired_handler(struct k_timer *timer) +{ + +} +bool is_app_enabled_dlps = true; +int pm_user_ctl(const struct shell *sh, size_t argc, char **argv) +{ + int err = 0; + uint16_t pm_ctl =0; + #if defined(CONFIG_BT_MESH_SHELL) + pm_ctl = shell_strtoul(argv[1], 0, &err); + #endif + if(pm_ctl ==0) is_app_enabled_dlps =false; + else is_app_enabled_dlps =true; + + return 0; +} + +extern void (*platform_pm_register_callback_func_with_priority)(void *, PlatformPMStage, int8_t); + +enum PMCheckResult app_enter_dlps_check(void) { + //DBG_DIRECT("app check dlps flag %d", app_global_data.is_app_enabled_dlps); + //return app_global_data.is_app_enabled_dlps ? PM_CHECK_PASS : PM_CHECK_FAIL; + //printk("dlps_check\n"); + //DBG_DIRECT("dlps_check\n"); + //return is_app_enabled_dlps ? PM_CHECK_PASS : PM_CHECK_FAIL; + return PM_CHECK_PASS ; + //return is_app_enabled_dlps; +} + +void sync_entim_exit_dlps_cb(void) +{ + //printk("exit_dlps_cb\n"); + //uint32_t reason= power_get_wakeup_reason(); + //Pad_Config(P4_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_LOW); + uint32_t reason = platform_pm_get_wakeup_reason(); + //DBG_DIRECT("exit_dlps_cb reason=0x%x",reason); + printk("ext=0x%08x\n",reason); + // #if defined(CONFIG_SHELL) + // if (System_WakeUpInterruptValue(P3_1) == SET) + // { + // //DBG_DIRECT("wakeup by P31"); + // Pad_ClearWakeupINTPendingBit(P3_1); + // System_WakeUpPinDisable(P3_1); + // printk("p31 wake up\n"); + // is_app_enabled_dlps=false; + // } + // Pad_ControlSelectValue(P3_0, PAD_PINMUX_MODE); + // Pad_ControlSelectValue(P3_1, PAD_PINMUX_MODE); + // //Pad_ControlSelectValue(P2_4, PAD_PINMUX_MODE);//button pin + // //Pad_ControlSelectValue(P4_0, PAD_PINMUX_MODE);//gpio led pin + // #endif + +} +void sync_entim_enter_dlps_cb(void) +{ + printk("en_cb\n"); + //DBG_DIRECT("enter_dlps_cb"); + // #if defined(CONFIG_SHELL) + // //Pad_Config(P4_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_HIGH); + // Pad_ControlSelectValue(P3_0, PAD_SW_MODE);//tx pin + // Pad_ControlSelectValue(P3_1, PAD_SW_MODE);//rx pin + // //Pad_ControlSelectValue(P2_4, PAD_SW_MODE);//button pin + // //Pad_ControlSelectValue(P4_0, PAD_SW_MODE);//gpio led pin + // #if defined(CONFIG_SOC_SERIES_RTL8752H) + // System_WakeUpPinEnable(P3_1, PAD_WAKEUP_POL_LOW, 0,20); + // #elif defined(CONFIG_SOC_SERIES_RTL87X2G) + // System_WakeUpPinEnable(P3_1, PAD_WAKEUP_POL_LOW, 0); + // #endif + // #endif + +} + + +static void app_dlps_check_cb_register(void) { + platform_pm_register_callback_func_with_priority((void *)app_enter_dlps_check, PLATFORM_PM_CHECK,1); +} +static void app_dlps_enter_cb_register(void) { + platform_pm_register_callback_func_with_priority((void *)sync_entim_enter_dlps_cb, PLATFORM_PM_ENTER,1); +} +static void app_dlps_exit_cb_register(void) { + platform_pm_register_callback_func_with_priority((void *)sync_entim_exit_dlps_cb, PLATFORM_PM_EXIT,1); +} +#endif + static void attention_on(const struct bt_mesh_model *mod) { board_led_set(true); @@ -167,7 +274,7 @@ static int gen_onoff_set_unack(const struct bt_mesh_model *model, uint8_t tid = net_buf_simple_pull_u8(buf); int32_t trans = 0; int32_t delay = 0; - + //Pad_Config(P3_2, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_HIGH); if (buf->len) { trans = model_time_decode(net_buf_simple_pull_u8(buf)); delay = net_buf_simple_pull_u8(buf) * 5; @@ -197,7 +304,10 @@ static int gen_onoff_set_unack(const struct bt_mesh_model *model, /* Schedule the next action to happen on the delay, and keep * transition time stored, so it can be applied in the timeout. */ - k_work_reschedule(&onoff.work, K_MSEC(delay)); + //k_work_reschedule(&onoff.work, K_MSEC(delay)); + /*led闪烁改为直接操作gpio,不使用k_work sched,这样一致性好,2025-7-30 */ + board_led_set(onoff.val); + //Pad_Config(P3_2, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_LOW); return 0; } @@ -206,9 +316,14 @@ static int gen_onoff_set(const struct bt_mesh_model *model, struct bt_mesh_msg_ctx *ctx, struct net_buf_simple *buf) { + #if CONFIG_PM + is_app_enabled_dlps=false; + #endif (void)gen_onoff_set_unack(model, ctx, buf); - onoff_status_send(model, ctx); - + //onoff_status_send(model, ctx); //2025-07-30 + #if CONFIG_PM + is_app_enabled_dlps=true; + #endif return 0; } @@ -300,11 +415,13 @@ static const struct bt_mesh_prov prov = { }; /** Send an OnOff Set message from the Generic OnOff Client to all nodes. */ -static int gen_onoff_send(bool val) +//static int gen_onoff_send(bool val) //2025-07-30 +static int gen_onoff_send(bool val,uint16_t dst) { struct bt_mesh_msg_ctx ctx = { .app_idx = models[3].keys[0], /* Use the bound key */ - .addr = BT_MESH_ADDR_ALL_NODES, + //.addr = BT_MESH_ADDR_ALL_NODES, //2025-07-30 + .addr = dst, .send_ttl = BT_MESH_TTL_DEFAULT, }; static uint8_t tid; @@ -328,7 +445,8 @@ static int gen_onoff_send(bool val) static void button_pressed(struct k_work *work) { if (bt_mesh_is_provisioned()) { - (void)gen_onoff_send(!onoff.val); + //(void)gen_onoff_send(!onoff.val); //2025-07-30 + (void)gen_onoff_send(!onoff.val,0); return; } @@ -374,6 +492,8 @@ static void button_pressed(struct k_work *work) printk("Provisioned and configured!\n"); } +char addr_s[BT_ADDR_LE_STR_LEN];//2025-07-30 +int bt_mesh_scan_disable(void); static void bt_ready(int err) { if (err) { @@ -393,12 +513,246 @@ static void bt_ready(int err) settings_load(); } + /*get mac address for uuid 2024-7-30*/ + bt_addr_le_t device_addr; + size_t count = 1; + bt_id_get(&device_addr, &count); + memcpy(dev_uuid,device_addr.a.val,6); + bt_addr_le_to_str(&device_addr, addr_s, sizeof(addr_s)); + printk("advertising addr as %s\n", addr_s); + /* This will be a no-op if settings_load() loaded provisioning info */ bt_mesh_prov_enable(BT_MESH_PROV_ADV | BT_MESH_PROV_GATT); - + // bt_mesh_scan_disable(); printk("Mesh initialized\n"); } + +/*RTL_DEBUG[🔧]:使用shell指令,增加mesh device的调试code*/ +/* + sw timer +*/ +#if defined(CONFIG_BT_MESH_SHELL) + +#include +#include +#include "mesh/access.h" +#include "mesh/net.h" +#include "common/bt_str.h" +#include "mesh/shell/utils.h" +#include + +struct app_key_val { + uint16_t net_idx; + bool updated; + struct bt_mesh_key val[2]; +} __packed; + +char net_key_index[8]; +void read_app_key(uint16_t app_idx,struct app_key_val *app_key); +struct app_key_val read_appkey; + +/* nvs read seq*/ +struct read_seq_val { + uint8_t val[3]; +} __packed; + +int settings_read_one(const char *name, void *value, size_t read_len); + + +K_MSGQ_DEFINE(swtimer_msgq, 32, 10, 4); + +typedef struct +{ + uint8_t buf; + uint32_t len; +} T_RTL_MESH_SEND_BUF; +T_RTL_MESH_SEND_BUF mesh_send_buf; + +uint16_t mesh_msg_send_count=0; +uint16_t mesh_msg_send_max_count=0; + +void timer_expired_handler(struct k_timer *timer); +K_TIMER_DEFINE(test_timer, timer_expired_handler, NULL); + +uint16_t send_dst = 0; + + +void heap_test_timer_expired_handler(struct k_timer *timer); +K_TIMER_DEFINE(heap_test_timer, heap_test_timer_expired_handler, NULL); + +uint16_t heap_mesh_msg_send_count=0; +uint16_t heap_msg_send_max_count=0; + +static int cmd_heap_test_start(const struct shell *sh, size_t argc, + char **argv, uint32_t period) +{ + ARG_UNUSED(argv); + k_timer_start(&heap_test_timer, K_MSEC(period), K_MSEC(period));//K_NO_WAIT); + + return 0; +} + +void heap_test_timer_expired_handler(struct k_timer *timer) +{ + //LOG_INF("Timer expired"); + //print_cpu_state(); + if(heap_msg_send_max_count!=0) + { + heap_mesh_msg_send_count++; + if(heap_mesh_msg_send_count 0){ + bt_mesh.seq = sys_get_le24(nvs_read_seq.val); + } + else { + bt_mesh.seq = 0; + } + sub = bt_mesh_subnet_get(0); + shell_print(sh, "argv[0]=%s",argv[0]); + //sscanf(argv[1], "%hhd", net_key_index); + net_key_index[0]=shell_strtoul(argv[1], 0, &err); + read_app_key(0,&read_appkey); + //unsigned int net_key_index =hex_string_to_int(argv[1]); + shell_print(sh, "argv[1]=%s",argv[1]); + shell_print(sh, "net_key_index[0]=%d",net_key_index[0]); + shell_print(sh,"NetKey %s", bt_hex(&sub->keys[0].net, sizeof(struct bt_mesh_key))); + shell_print(sh,"devKey %s", bt_hex(&bt_mesh.dev_key, sizeof(struct bt_mesh_key))); + shell_print(sh,"appKey %s", bt_hex(&read_appkey.val[0], sizeof(struct bt_mesh_key))); + shell_print(sh, "IV Index is 0x%08x", bt_mesh.iv_index); + shell_print(sh, "seq is 0x%08x", bt_mesh.seq); + uint16_t ele_addr=bt_mesh_primary_addr(); + shell_print(sh, "primary_addr=%x",ele_addr); + elem = bt_mesh_elem_find(ele_addr); + for (uint16_t i = 0U; i < comp.elem[0].model_count; i++) { + shell_print(sh,"model_id(elem 0)=%x", comp.elem[0].models[i].id); + if(ele_addr !=0) { + for (uint8_t j = 0; j < elem->models[i].keys_cnt; j++) { + if (elem->models[i].keys[j] != BT_MESH_KEY_UNUSED) { + shell_print(sh,"appkeys_bind_idx =%d",elem->models[i].keys[j]); + } + } + } + } + return 0; +} + + + +SHELL_STATIC_SUBCMD_SET_CREATE(mesh_user_cmds, + SHELL_CMD_ARG(heap-test, NULL, "[ count:(0=>unlimited)>]", cmd_heap_test_start_demo, 1,2), + SHELL_CMD_ARG(key-show, NULL, "netkey index", mesh_key_info, 1, 1), + SHELL_CMD_ARG(mesh-send, NULL, "[0xffff)> unlimited)>]", cmd_mesh_test_start_demo, 1, 3), + #if CONFIG_PM + SHELL_CMD_ARG(pm-ctl, NULL, "[exit 1=>enter)>]", pm_user_ctl, 1, 1), + #endif + SHELL_SUBCMD_SET_END + ); + SHELL_CMD_ARG_REGISTER(mesh_user, &mesh_user_cmds, "mesh user define commands", NULL, 1, 1); + +#endif + + int main(void) { static struct k_work button_work; @@ -430,5 +784,69 @@ int main(void) if (err) { printk("Bluetooth init failed (err %d)\n", err); } + #if CONFIG_PM + app_dlps_check_cb_register(); + app_dlps_enter_cb_register(); + app_dlps_exit_cb_register(); + //k_timer_start(&pm_test_timer, K_MSEC(300), K_MSEC(300));//K_NO_WAIT); + #endif + #if defined(CONFIG_BT_MESH_SHELL) + /* + 2025-7-30 lq_liu + get info from my_fifo to send mesh message by gen_onoff_send + */ + //T_RTL_MESH_SEND_BUF *rx_data; + while (1) { + + k_msgq_get(&swtimer_msgq, &mesh_send_buf, K_FOREVER); + if(mesh_send_buf.buf==1) + { + mesh_send_buf.buf=0; + //lq_threads_test(lq_sh); + onoff.val=!onoff.val; + err=gen_onoff_send(onoff.val,send_dst); + if(err!=0) + { + k_timer_stop(&test_timer); + printk("gen_onoff_send err=%d\n",err); + } + //rx_data->buf=0; + + } + else if(mesh_send_buf.buf==2) + { + mesh_send_buf.buf=0; + #ifdef CONFIG_SYS_HEAP_RUNTIME_STATS + #include "mem_types.h" + extern bool os_mem_peek_zephyr(RAM_TYPE ram_type, size_t *p_size); + size_t p_size; + os_mem_peek_zephyr(RAM_TYPE_DATA_ON, &p_size); + //printk("data ram os_heap peek size=%d\n",p_size); + os_mem_peek_zephyr(RAM_TYPE_BUFFER_ON, &p_size); + //printk("buffer ram os_heap peek size=%d\n", p_size); + + // size_t p_size; + // os_mem_peek_zephyr(0, &p_size); + // os_mem_peek_zephyr(1, &p_size); + // struct sys_memory_stats stats; + // // low level接口 + // sys_heap_runtime_stats_get(&z_malloc_heap, &stats); + // log_isr_stack_usage(); + // printk("stdlib malloc heap: heap size: %d, allocated %d, free %d, max allocated %d\n", CONFIG_COMMON_LIBC_MALLOC_ARENA_SIZE, stats.allocated_bytes, stats.free_bytes, stats.max_allocated_bytes); + // print_cpu_state(); + // if(heap_mesh_msg_send_count==9) + // { + // DBG_DIRECT("test"); + // while (1) + // { + // /* code */ + // } + + // } + #endif + } + k_yield(); + } + #endif return 0; } diff --git a/samples/bluetooth/mesh_provisioner/boards/rtl8752h_evb.conf b/samples/bluetooth/mesh_provisioner/boards/rtl8752h_evb.conf new file mode 100644 index 0000000000000..50a76f2dfdfc3 --- /dev/null +++ b/samples/bluetooth/mesh_provisioner/boards/rtl8752h_evb.conf @@ -0,0 +1,2 @@ +#RTL_DEBUG[🔧]provisioner:rtl8762h 开启gpio +CONFIG_GPIO=y diff --git a/samples/bluetooth/mesh_provisioner/boards/rtl8752h_evb.overlay b/samples/bluetooth/mesh_provisioner/boards/rtl8752h_evb.overlay new file mode 100644 index 0000000000000..485efa34c42b5 --- /dev/null +++ b/samples/bluetooth/mesh_provisioner/boards/rtl8752h_evb.overlay @@ -0,0 +1,29 @@ +/ { + /*RTL_DEBUG[🔧]provisioner:rtl8752h gpio led */ + aliases { + sw0 = &button_0; + led0 = &led_0; + }; + + gpio_keys { + compatible = "gpio-keys"; + button_0: button_0 { + gpios = <&gpio 20 GPIO_ACTIVE_HIGH>; + }; + }; + + gpio-led { + compatible = "gpio-leds"; + led_0: led_0 { + gpios = <&gpio 31 GPIO_ACTIVE_HIGH>; + }; + }; + + +}; + +&gpio{ + status = "okay"; +}; + + diff --git a/samples/bluetooth/mesh_provisioner/boards/rtl87x2g_evb.conf b/samples/bluetooth/mesh_provisioner/boards/rtl87x2g_evb.conf new file mode 100644 index 0000000000000..81c492692304b --- /dev/null +++ b/samples/bluetooth/mesh_provisioner/boards/rtl87x2g_evb.conf @@ -0,0 +1 @@ +CONFIG_GPIO=y \ No newline at end of file diff --git a/samples/bluetooth/mesh_provisioner/boards/rtl87x2g_evb.overlay b/samples/bluetooth/mesh_provisioner/boards/rtl87x2g_evb.overlay new file mode 100644 index 0000000000000..1548888e4e938 --- /dev/null +++ b/samples/bluetooth/mesh_provisioner/boards/rtl87x2g_evb.overlay @@ -0,0 +1,30 @@ +/ { + + aliases { + sw0 = &button_0; + led0 = &led_0; + }; + + gpio_keys { + compatible = "gpio-keys"; + button_0: button_0 { + gpios = <&gpioa 25 GPIO_ACTIVE_HIGH>; + }; + }; + + gpio-led { + compatible = "gpio-leds"; + led_0: led_0 { + gpios = <&gpiob 8 GPIO_ACTIVE_HIGH>; + }; + }; +}; + +&gpioa { + status = "okay"; +}; + + +&gpiob { + status = "okay"; +}; \ No newline at end of file diff --git a/samples/bluetooth/mesh_provisioner/prj.conf b/samples/bluetooth/mesh_provisioner/prj.conf index 8055e388df141..bd4025275ce3f 100644 --- a/samples/bluetooth/mesh_provisioner/prj.conf +++ b/samples/bluetooth/mesh_provisioner/prj.conf @@ -1,5 +1,6 @@ #CONFIG_INIT_STACKS=y -CONFIG_MAIN_STACK_SIZE=2048 +#默认2048不是太够,调整为3500 +CONFIG_MAIN_STACK_SIZE=3500 CONFIG_SYSTEM_WORKQUEUE_STACK_SIZE=2048 # The Bluetooth API should not be used from a preemptive thread: CONFIG_MAIN_THREAD_PRIORITY=-2 @@ -59,3 +60,106 @@ CONFIG_BT_MESH_RPL_STORE_TIMEOUT=600 #CONFIG_BT_MESH_BEACON_LOG_LEVEL_DBG=y #CONFIG_BT_MESH_CRYPTO_LOG_LEVEL_DBG=y #CONFIG_BT_MESH_ADV_LOG_LEVEL_DBG=y + + +#RTL_DEBUG[🔧]provisioner conf +CONFIG_LOG=y + +CONFIG_BT_EXT_ADV=y +#如果开启legacy adv,需要设置mesh adv stack size,默认是1024,不够,需要调大 +CONFIG_BT_MESH_ADV_STACK_SIZE=2048 + +CONFIG_BT_BUF_EVT_DISCARDABLE_SIZE=255 +# CONFIG_BT_BUF_EVT_DISCARDABLE_COUNT=10 + + +CONFIG_BT_MESH_CRPL=60 +CONFIG_BT_MESH_MSG_CACHE_SIZE=60 +CONFIG_BT_MESH_CDB=y +CONFIG_BT_MESH_CDB_NODE_COUNT=60 + +CONFIG_NVS_LOOKUP_CACHE=y +CONFIG_SETTINGS_NVS_NAME_CACHE=y +CONFIG_SETTINGS_NVS_NAME_CACHE_SIZE=64 + + +CONFIG_SHELL=y +CONFIG_BT_MESH_SHELL=y +CONFIG_BT_MESH_SHELL_CDB=y + +#配置为1500 发现执行mesh reset-local会出现shell uart线程的栈溢出 +CONFIG_SHELL_STACK_SIZE=2048 +CONFIG_SHELL_CMD_BUFF_SIZE=64 +CONFIG_FLASH_SHELL=n + +# CONFIG_BT_MESH_ADV_STACK_SIZE=2000 +CONFIG_BT_MESH_SETTINGS_WORKQ_STACK_SIZE=1500 +# CONFIG_BT_MESH_SHELL_PROV_CTX_INSTANCE=y + + +# CONFIG_BT_MESH_ADV_STACK_SIZE=3000 + +CONFIG_LOG_BUFFER_SIZE=1024 + +CONFIG_SYS_HEAP_RUNTIME_STATS=y + + +CONFIG_REALTEK_BT_CONTROLLER_STACK_SIZE=2520 + +CONFIG_CODE_DATA_RELOCATION=n + +CONFIG_SPEED_OPTIMIZATIONS=y + + +# CONFIG_BT_MESH_GATT_PROXY_ENABLED=y + +CONFIG_BT_MESH_PROV_LOG_LEVEL_DBG=y + +# CONFIG_BT_MESH_PROXY_LOG_LEVEL_DBG=y + +CONFIG_BT_MESH_TRANS_LOG_LEVEL_DBG=y + + +# CONFIG_STDOUT_CONSOLE=y +# enable to use thread names +CONFIG_THREAD_NAME=y +CONFIG_SEGGER_SYSTEMVIEW=n +CONFIG_USE_SEGGER_RTT=y +CONFIG_TRACING=y +CONFIG_TRACING_BACKEND_RAM=y +# enable for post-mortem tracing +CONFIG_SEGGER_SYSVIEW_POST_MORTEM_MODE=n + +CONFIG_TRACING_BUFFER_SIZE=4096 + +CONFIG_TICKLESS_KERNEL=n +CONFIG_TIMESLICE_SIZE=10 + + +#zephyr\subsys\bluetooth\mesh\Kconfig中: +#BT_MESH_PB_ADV_TRANS_PDU_RETRANSMIT_COUNT的defult值为0,BT_MESH_PB_ADV_TRANS_ACK_RETRANSMIT_COUNT为2 +#开启extend adv情况下,extend scan效率较legacy scan要低一点,所以要增加重传 + +#Link Open 和 Transaction PDU 的重传次数,(默认:使用BT_MESH_PB_ADV_USE_RELAY_SETS=y 中继集时 7,否则 0;范围:0–7) +CONFIG_BT_MESH_PB_ADV_TRANS_PDU_RETRANSMIT_COUNT=3 + +#Link Ack 和 Transaction Acknowledgment PDU 的重传次数,(默认:2,范围:0–7),较高值确保确认消息送达,但过多重传可能导致网络拥堵 +CONFIG_BT_MESH_PB_ADV_TRANS_ACK_RETRANSMIT_COUNT=3 + +#Link Close PDU 的重传次数,(默认:使用BT_MESH_PB_ADV_USE_RELAY_SETS=y,即中继集时 7,否则 2;范围:0–7) +CONFIG_BT_MESH_PB_ADV_LINK_CLOSE_RETRANSMIT_COUNT=3 +#配网 PDU 重传的超时时间,较短的超时加快重传,适合噪声环境,但可能增加网络负载;较长的超时可能降低成功率 +CONFIG_BT_MESH_PB_ADV_RETRANS_TIMEOUT=350 + + +#zephyr\subsys\bluetooth\mesh\Kconfig中: +#BT_MESH_NETWORK_TRANSMIT_COUNT的defult值为20,BT_MESH_NETWORK_TRANSMIT_COUNT的defult值为2 +#开启extend adv情况下,extend scan效率较legacy scan要低一点,所以要增加重传 +CONFIG_BT_MESH_NETWORK_TRANSMIT_INTERVAL=15 +CONFIG_BT_MESH_NETWORK_TRANSMIT_COUNT=2 + +#zephyr\subsys\bluetooth\mesh\Kconfig中: +#BT_MESH_UNPROV_BEACON_INT的defult值为5 +#控制未配网节点定期发送未配网 Beacon(Unprovisioned Beacon)包的时间间隔 +CONFIG_BT_MESH_UNPROV_BEACON_INT=10 + diff --git a/samples/bluetooth/mesh_provisioner/src/main.c b/samples/bluetooth/mesh_provisioner/src/main.c index 472dc020d438e..fcb471c7b0543 100644 --- a/samples/bluetooth/mesh_provisioner/src/main.c +++ b/samples/bluetooth/mesh_provisioner/src/main.c @@ -304,15 +304,35 @@ static int bt_ready(void) static uint8_t check_unconfigured(struct bt_mesh_cdb_node *node, void *data) { - if (!atomic_test_bit(node->flags, BT_MESH_CDB_NODE_CONFIGURED)) { + // if (!atomic_test_bit(node->flags, BT_MESH_CDB_NODE_CONFIGURED)) { + // if (node->addr == self_addr) { + // configure_self(node); + // } else { + // configure_node(node); + // } + // } + /* 优化configuration过程 2025-07-30*/ + if (!atomic_test_bit(node->flags, BT_MESH_CDB_NODE_CONFIGURED)) { if (node->addr == self_addr) { configure_self(node); } else { + printk("Waiting for node to be added...\n"); + int err = k_sem_take(&sem_node_added, K_SECONDS(5)); + if (err == -EAGAIN) { + printk("Timeout waitingfor node to be added\n"); + } + else if(err==0){ + //configure_node(node); + printk("node has been added\n"); + } configure_node(node); + k_sem_reset(&sem_node_added); + //configure_node(node); } } - + printk("CDB_ITER_CONTINUE\n"); return BT_MESH_CDB_ITER_CONTINUE; + } #if DT_NODE_HAS_STATUS(SW0_NODE, okay) @@ -332,7 +352,8 @@ static void button_init(void) printk("Error: button device %s is not ready\n", button.port->name); return; } - ret = gpio_pin_configure_dt(&button, GPIO_INPUT); + //ret = gpio_pin_configure_dt(&button, GPIO_INPUT); //按照bee3plus mesh dongle的配置设置 2025-07-30 + ret = gpio_pin_configure_dt(&button, GPIO_INPUT| GPIO_PULL_DOWN); if (ret != 0) { printk("Error %d: failed to configure %s pin %d\n", ret, button.port->name, button.pin); @@ -382,32 +403,36 @@ int main(void) } bin2hex(node_uuid, 16, uuid_hex_str, sizeof(uuid_hex_str)); - -#if DT_NODE_HAS_STATUS(SW0_NODE, okay) - k_sem_reset(&sem_button_pressed); - printk("Device %s detected, press button 1 to provision.\n", uuid_hex_str); - err = k_sem_take(&sem_button_pressed, K_SECONDS(30)); - if (err == -EAGAIN) { - printk("Timed out, button 1 wasn't pressed in time.\n"); - continue; - } -#endif - - printk("Provisioning %s\n", uuid_hex_str); - err = bt_mesh_provision_adv(node_uuid, net_idx, 0, 0); - if (err < 0) { - printk("Provisioning failed (err %d)\n", err); - continue; - } - - printk("Waiting for node to be added...\n"); - err = k_sem_take(&sem_node_added, K_SECONDS(10)); - if (err == -EAGAIN) { - printk("Timeout waiting for node to be added\n"); - continue; - } - - printk("Added node 0x%04x\n", node_addr); + + //RTL_DEBUG[🔧]开启配网,显示uprov beacon,去掉button激活配网 2025-07-30 + bin2hex(node_uuid, 16, uuid_hex_str, sizeof(uuid_hex_str)); + printk("unprov beacon %s\n", uuid_hex_str); + +// #if DT_NODE_HAS_STATUS(SW0_NODE, okay) +// k_sem_reset(&sem_button_pressed); +// printk("Device %s detected, press button 1 to provision.\n", uuid_hex_str); +// err = k_sem_take(&sem_button_pressed, K_SECONDS(30)); +// if (err == -EAGAIN) { +// printk("Timed out, button 1 wasn't pressed in time.\n"); +// continue; +// } +// #endif + +// printk("Provisioning %s\n", uuid_hex_str); +// err = bt_mesh_provision_adv(node_uuid, net_idx, 0, 0); +// if (err < 0) { +// printk("Provisioning failed (err %d)\n", err); +// continue; +// } + +// printk("Waiting for node to be added...\n"); +// err = k_sem_take(&sem_node_added, K_SECONDS(10)); +// if (err == -EAGAIN) { +// printk("Timeout waiting for node to be added\n"); +// continue; +// } + +// printk("Added node 0x%04x\n", node_addr); } return 0; } diff --git a/samples/bluetooth/peripheral/prj.conf b/samples/bluetooth/peripheral/prj.conf index 5d577265d6ef3..50b34376c7c6c 100644 --- a/samples/bluetooth/peripheral/prj.conf +++ b/samples/bluetooth/peripheral/prj.conf @@ -23,3 +23,13 @@ CONFIG_FLASH=y CONFIG_FLASH_MAP=y CONFIG_NVS=y CONFIG_SETTINGS=y + +CONFIG_PM=y + +CONFIG_SHELL=y +CONFIG_SHELL_CMDS_SELECT=n +CONFIG_SHELL_HELP=n +CONFIG_SHELL_TAB_AUTOCOMPLETION=n +CONFIG_SHELL_STACK_SIZE=1500 +CONFIG_SHELL_CMD_BUFF_SIZE=32 +CONFIG_FLASH_SHELL=n \ No newline at end of file diff --git a/samples/bluetooth/peripheral/src/main.c b/samples/bluetooth/peripheral/src/main.c index 1abc19166d2c0..28ff583625963 100644 --- a/samples/bluetooth/peripheral/src/main.c +++ b/samples/bluetooth/peripheral/src/main.c @@ -350,6 +350,110 @@ static void hrs_notify(void) bt_hrs_notify(heartrate); } +#if CONFIG_PM +#if defined(CONFIG_SOC_SERIES_RTL8752H) +#include "rtl876x_pinmux.h" +#elif defined(CONFIG_SOC_SERIES_RTL87X2G) +#include "rtl_pinmux.h" +#endif +#include "mesh/adv.h" +#include "trace.h" +#include "dlps.h" + +bool is_app_enabled_dlps = true; +//extern PowerModeWakeupReason power_get_wakeup_reason(); +#if defined(CONFIG_SHELL) +#include +#endif + +#if defined(CONFIG_SHELL) + +int pm_user_ctl(const struct shell *sh, size_t argc, char **argv) +{ + int err = 0; + + uint16_t pm_ctl = shell_strtoul(argv[1], 0, &err); + if(pm_ctl ==0) is_app_enabled_dlps =false; + else is_app_enabled_dlps =true; + + return 0; +} + +SHELL_STATIC_SUBCMD_SET_CREATE(user_cmds, + SHELL_CMD_ARG(pm-ctl, NULL, "[exit 1=>enter)>]", pm_user_ctl, 1, 1), + SHELL_SUBCMD_SET_END + ); +SHELL_CMD_ARG_REGISTER(user_test, &user_cmds, "user define commands", + NULL, 1, 1); + +#endif + + + +extern void (*platform_pm_register_callback_func_with_priority)(void *, PlatformPMStage, int8_t); + +enum PMCheckResult app_enter_dlps_check(void) { + //DBG_DIRECT("app check dlps flag %d", app_global_data.is_app_enabled_dlps); + //return app_global_data.is_app_enabled_dlps ? PM_CHECK_PASS : PM_CHECK_FAIL; + //printk("dlps_check\n"); + //DBG_DIRECT("dlps_check\n"); + return is_app_enabled_dlps ? PM_CHECK_PASS : PM_CHECK_FAIL; + //return is_app_enabled_dlps; +} + +void sync_entim_exit_dlps_cb(void) +{ + //printk("exit_dlps_cb\n"); + //uint32_t reason= power_get_wakeup_reason(); + //Pad_Config(P4_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_LOW); + uint32_t reason = platform_pm_get_wakeup_reason(); + //DBG_DIRECT("exit_dlps_cb reason=0x%x",reason); + printk("exit_dlps_cb reason=0x%08x\n",reason); + #if defined(CONFIG_SHELL) + if (System_WakeUpInterruptValue(P3_1) == SET) + { + //DBG_DIRECT("wakeup by P31"); + Pad_ClearWakeupINTPendingBit(P3_1); + System_WakeUpPinDisable(P3_1); + printk("p31 wake up\n"); + is_app_enabled_dlps=false; + } + Pad_ControlSelectValue(P3_0, PAD_PINMUX_MODE); + Pad_ControlSelectValue(P3_1, PAD_PINMUX_MODE); + #endif + +} +void sync_entim_enter_dlps_cb(void) +{ + printk("enter_dlps_cb\n"); + //DBG_DIRECT("enter_dlps_cb"); + #if defined(CONFIG_SHELL) + //Pad_Config(P4_0, PAD_SW_MODE, PAD_IS_PWRON, PAD_PULL_DOWN, PAD_OUT_ENABLE, PAD_OUT_HIGH); + Pad_ControlSelectValue(P3_0, PAD_SW_MODE);//tx pin + Pad_ControlSelectValue(P3_1, PAD_SW_MODE);//rx pin + #if defined(CONFIG_SOC_SERIES_RTL8752H) + System_WakeUpPinEnable(P3_1, PAD_WAKEUP_POL_LOW, 0,20); + #elif defined(CONFIG_SOC_SERIES_RTL87X2G) + System_WakeUpPinEnable(P3_1, PAD_WAKEUP_POL_LOW, 0); + #endif + #endif + +} + + +static void app_dlps_check_cb_register(void) { + platform_pm_register_callback_func_with_priority((void *)app_enter_dlps_check, PLATFORM_PM_CHECK,1); +} +static void app_dlps_enter_cb_register(void) { + platform_pm_register_callback_func_with_priority((void *)sync_entim_enter_dlps_cb, PLATFORM_PM_ENTER,1); +} +static void app_dlps_exit_cb_register(void) { + platform_pm_register_callback_func_with_priority((void *)sync_entim_exit_dlps_cb, PLATFORM_PM_EXIT,1); +} + +#endif + + int main(void) { struct bt_gatt_attr *vnd_ind_attr; @@ -363,7 +467,11 @@ int main(void) } bt_ready(); - + #if CONFIG_PM + app_dlps_check_cb_register(); + app_dlps_enter_cb_register(); + app_dlps_exit_cb_register(); + #endif bt_gatt_cb_register(&gatt_callbacks); bt_conn_auth_cb_register(&auth_cb_display); @@ -371,7 +479,7 @@ int main(void) &vnd_enc_uuid.uuid); bt_uuid_to_str(&vnd_enc_uuid.uuid, str, sizeof(str)); printk("Indicate VND attr %p (UUID %s)\n", vnd_ind_attr, str); - + /* Implement notification. At the moment there is no suitable way * of starting delayed work so we do it here */ diff --git a/soc/realtek/bee/rtl8752h/CMakeLists.txt b/soc/realtek/bee/rtl8752h/CMakeLists.txt index 36e5cb8918ab2..efa1f7afd2ed7 100644 --- a/soc/realtek/bee/rtl8752h/CMakeLists.txt +++ b/soc/realtek/bee/rtl8752h/CMakeLists.txt @@ -6,8 +6,12 @@ zephyr_linker_sources(SECTIONS trace_section.ld) zephyr_library_sources(soc.c) zephyr_include_directories(.) set(SOC_LINKER_SCRIPT ${ZEPHYR_BASE}/include/zephyr/arch/arm/cortex_m/scripts/linker.ld CACHE INTERNAL "") - +if (CONFIG_CODE_DATA_RELOCATION) +zephyr_code_relocate(FILES ${ZEPHYR_BASE}/subsys/shell/backends/shell_uart.c LOCATION RAM2_BSS) +endif() if (CONFIG_PM) zephyr_library_sources(power.c) zephyr_code_relocate(FILES ${ZEPHYR_BASE}/arch/arm/core/nmi.c LOCATION RAM) #for z_arm_nmi +# zephyr_code_relocate(FILES power.c LOCATION RAM) +# zephyr_code_relocate(FILES ${ZEPHYR_BASE}/subsys/pm/device.c LOCATION RAM) endif() diff --git a/soc/realtek/bee/rtl8752h/power.c b/soc/realtek/bee/rtl8752h/power.c index 4dd8e5f966021..124b941af37e6 100644 --- a/soc/realtek/bee/rtl8752h/power.c +++ b/soc/realtek/bee/rtl8752h/power.c @@ -19,7 +19,7 @@ #include LOG_MODULE_DECLARE(soc, CONFIG_SOC_LOG_LEVEL); -#define REALTEK_POWER_LOG 0 +#define REALTEK_POWER_LOG 1 /* ROM Extern Variables and Functions */ /* #include */ @@ -195,7 +195,7 @@ static int pm_suspend_devices_rtk(void) TYPE_SECTION_START(pm_device_slots)[num_susp_rtk] = dev; num_susp_rtk++; } - + POWER_LOG("enter is called"); return 0; } diff --git a/subsys/bluetooth/mesh/adv.h b/subsys/bluetooth/mesh/adv.h index da86f697c2df9..a81b3b2bdd8bf 100644 --- a/subsys/bluetooth/mesh/adv.h +++ b/subsys/bluetooth/mesh/adv.h @@ -11,7 +11,7 @@ #define BT_MESH_ADV_DATA_SIZE 29 #define BT_MESH_ADV_SCAN_UNIT(_ms) ((_ms) * 8 / 5) -#define BT_MESH_SCAN_INTERVAL_MS 30 +#define BT_MESH_SCAN_INTERVAL_MS 100 #define BT_MESH_SCAN_WINDOW_MS 30 enum bt_mesh_adv_type { diff --git a/subsys/bluetooth/mesh/app_keys.c b/subsys/bluetooth/mesh/app_keys.c index 5afd887a8e803..4b80d2232d36e 100644 --- a/subsys/bluetooth/mesh/app_keys.c +++ b/subsys/bluetooth/mesh/app_keys.c @@ -721,3 +721,21 @@ void bt_mesh_app_key_pending_store(void) } } } + +/*RTL_DEBUG[📶🔧]:subsys:app keys:增加自定义的api:read_app_key*/ +#if defined(CONFIG_BT_MESH_SHELL) +void read_app_key(uint16_t app_idx,struct app_key_val *app_key) +{ + const struct app_key *app; + app = app_get(app_idx); + if (!app) { + LOG_WRN("ApKeyIndex 0x%03x not found", app_idx); + return; + } + app_key->net_idx = app->net_idx, + app_key->updated = app->updated, + memcpy(&app_key->val[0], &app->keys[0].val, sizeof(struct bt_mesh_key)); + memcpy(&app_key->val[1], &app->keys[1].val, sizeof(struct bt_mesh_key)); + +} +#endif diff --git a/subsys/net/buf.c b/subsys/net/buf.c index 8267943dc0130..2807c2811d961 100644 --- a/subsys/net/buf.c +++ b/subsys/net/buf.c @@ -450,6 +450,11 @@ void net_buf_put(struct k_fifo *fifo, struct net_buf *buf) k_fifo_put(fifo, buf); } +// 定义全局自旋锁 +/* +RTL_FIXME[🛠️] 优化net buf释放:加lock保护 2025-07-30 +*/ +struct k_spinlock buf_unref_lock;// add #if defined(CONFIG_NET_BUF_LOG) void net_buf_unref_debug(struct net_buf *buf, const char *func, int line) #else @@ -457,11 +462,13 @@ void net_buf_unref(struct net_buf *buf) #endif { __ASSERT_NO_MSG(buf); - + // k_spinlock_key_t key = k_spin_lock(&buf_unref_lock); while (buf) { - struct net_buf *frags = buf->frags; + struct net_buf_pool *pool; - + /*加锁保护整个操作,包括 frags 的定义*/ + //k_spinlock_key_t key = k_spin_lock(&buf_unref_lock); + struct net_buf *frags = buf->frags; #if defined(CONFIG_NET_BUF_LOG) if (!buf->ref) { NET_BUF_ERR("%s():%d: buf %p double free", func, line, @@ -473,6 +480,8 @@ void net_buf_unref(struct net_buf *buf) buf->pool_id, buf->frags); if (--buf->ref > 0) { + /*引用计数仍大于 0,解锁并返回*/ + //k_spin_unlock(&buf_unref_lock, key); return; } @@ -485,15 +494,27 @@ void net_buf_unref(struct net_buf *buf) atomic_inc(&pool->avail_count); __ASSERT_NO_MSG(atomic_get(&pool->avail_count) <= pool->buf_count); #endif - + //k_spin_unlock(&buf_unref_lock, key);//解锁 if (pool->destroy) { pool->destroy(buf); + //key = k_spin_lock(&buf_unref_lock);//上锁 + /* 在调用 pool->destroy 前解锁*/ + // k_spin_unlock(&buf_unref_lock, key); + // pool->destroy(buf); + // key = k_spin_lock(&buf_unref_lock); + // buf = frags; + // k_spin_unlock(&buf_unref_lock, key); } else { + //key = k_spin_lock(&buf_unref_lock);//上锁 net_buf_destroy(buf); + /*默认 destroy 完成后解锁*/ + //buf = frags; + //k_spin_unlock(&buf_unref_lock, key); } buf = frags; } + //k_spin_unlock(&buf_unref_lock, key);//解锁 } struct net_buf *net_buf_ref(struct net_buf *buf) diff --git a/subsys/settings/src/settings_nvs.c b/subsys/settings/src/settings_nvs.c index 6764c7587a3b0..8c5bbdac70497 100644 --- a/subsys/settings/src/settings_nvs.c +++ b/subsys/settings/src/settings_nvs.c @@ -211,7 +211,77 @@ static int settings_nvs_load(struct settings_store *cs, } return ret; } +/* RTL_DEBUG[🔌🔧]:subsys:settings_nvs.c增加settings_nvs_read_by_name,通过name读取对应的data */ +int settings_nvs_read_by_name(struct settings_store *cs, const char *name, char *value, size_t val_len) +{ + struct settings_nvs *cf = CONTAINER_OF(cs, struct settings_nvs, cf_store); + char rdname[SETTINGS_MAX_NAME_LEN + SETTINGS_EXTRA_LEN + 1]; + uint16_t name_id = NVS_NAMECNT_ID; + uint16_t read_name_id= NVS_NAMECNT_ID; + int rc = 0; + + if (!name) { + return -EINVAL; + } + +#if CONFIG_SETTINGS_NVS_NAME_CACHE + name_id = settings_nvs_cache_match(cf, name, rdname, sizeof(rdname)); + if (name_id != NVS_NAMECNT_ID) { + read_name_id = name_id; + goto found; + } +#endif + + name_id = cf->last_name_id + 1; + +#if CONFIG_SETTINGS_NVS_NAME_CACHE + /* We can skip reading NVS if we know that the cache wasn't overflowed. */ + if (cf->loaded && !SETTINGS_NVS_CACHE_OVFL(cf)) { + goto found; + } +#endif + + while (1) { + name_id--; + if (name_id == NVS_NAMECNT_ID) { + break; + } + + rc = nvs_read(&cf->cf_nvs, name_id, &rdname, sizeof(rdname)); + + if (rc < 0) { + /* Error or entry not found */ + if (rc == -ENOENT) { + read_name_id = name_id; + } + continue; + } + rdname[rc] = '\0'; + + if (strcmp(name, rdname)) { + continue; + } + read_name_id = name_id; + goto found; + } + +found: + if(name_id != NVS_NAMECNT_ID) + { + /* write the value */ + rc = nvs_read(&cf->cf_nvs, read_name_id + NVS_NAME_ID_OFFSET,value, val_len); + if (rc < 0) { + return rc; + } + + } + else{ + return -ENOENT; + } + return rc; +} +/* RTL_DEBUG[🔌🔧]:subsys:settings_nvs.c:调试setting_nvs_save */ static int settings_nvs_save(struct settings_store *cs, const char *name, const char *value, size_t val_len) { diff --git a/subsys/settings/src/settings_store.c b/subsys/settings/src/settings_store.c index b697f993d9416..7bf4207360d3d 100644 --- a/subsys/settings/src/settings_store.c +++ b/subsys/settings/src/settings_store.c @@ -88,6 +88,32 @@ int settings_load_subtree_direct( return 0; } +int settings_nvs_read_by_name(struct settings_store *cs, const char *name,char *value, size_t val_len); +/* + * read a single value to buffer. + RTL_DEBUG[🔌🔧]:subsys:settings-store:增加settings_read_one,使用name读取对应的一笔数据 + 调用settings_nvs_read_by_name + */ +int settings_read_one(const char *name, void *value, size_t read_len) +{ + int rc; + struct settings_store *cs; + + cs = settings_save_dst; + if (!cs) { + return -ENOENT; + } + + k_mutex_lock(&settings_lock, K_FOREVER); + + rc = settings_nvs_read_by_name(cs, name, (char *)value, read_len); + + k_mutex_unlock(&settings_lock); + + return rc; +} + +/* RTL_DEBUG[🔌🔧]:subsys:settings-store:调试setting_save_one */ /* * Append a single value to persisted config. Don't store duplicate value. */