diff --git a/components/bt/esp_ble_mesh/Kconfig.in b/components/bt/esp_ble_mesh/Kconfig.in index 746b4c78d..0ca4b6be8 100644 --- a/components/bt/esp_ble_mesh/Kconfig.in +++ b/components/bt/esp_ble_mesh/Kconfig.in @@ -56,7 +56,7 @@ if BLE_MESH config BLE_MESH_WAIT_FOR_PROV_MAX_DEV_NUM int "Maximum number of unprovisioned devices that can be added to device queue" - default 20 + default 10 range 1 100 help This option specifies how many unprovisioned devices can be added to device @@ -64,20 +64,9 @@ if BLE_MESH queue in the bottom layer which is used to store unprovisioned device information (e.g. Device UUID, address). - config BLE_MESH_MAX_STORED_NODES - int "Maximum number of nodes whose information can be stored" - default 20 - range BLE_MESH_MAX_PROV_NODES 1000 - help - This option specifies the maximum number of nodes whose information can be - stored by a Provisioner in its upper layer. - Users can change this value according to the number of nodes whose information - (e.g. Device UUID, unicast address, element number) are going to be stored by - a Provisioner. And the nodes include the provisioned ones and user-added ones. - config BLE_MESH_MAX_PROV_NODES int "Maximum number of devices that can be provisioned by Provisioner" - default 20 + default 10 range 1 1000 help This option specifies how many devices can be provisioned by a Provisioner. @@ -348,6 +337,11 @@ if BLE_MESH The replay protection list is used to prevent a node from replay attack, which will store the source address and sequence number of the received mesh messages. + For Provisioner, the replay protection list size should not be smaller than + the maximum number of nodes whose information can be stored. And the element + number of each node should also be taken into consideration. For example, if + Provisioner can provision up to 20 nodes and each node contains two elements, + then the replay protection list size of Provisioner should be at least 40. config BLE_MESH_MSG_CACHE_SIZE int "Network message cache size" diff --git a/components/bt/esp_ble_mesh/btc/btc_ble_mesh_prov.c b/components/bt/esp_ble_mesh/btc/btc_ble_mesh_prov.c index 18c90116f..1b8b897ae 100644 --- a/components/bt/esp_ble_mesh/btc/btc_ble_mesh_prov.c +++ b/components/bt/esp_ble_mesh/btc/btc_ble_mesh_prov.c @@ -994,7 +994,7 @@ const esp_ble_mesh_comp_t *btc_ble_mesh_comp_get(void) u16_t btc_ble_mesh_provisioner_get_prov_node_count(void) { - return bt_mesh_provisioner_get_prov_node_count(); + return bt_mesh_provisioner_get_node_count(); } /* Configuration Models */ @@ -1783,7 +1783,7 @@ void btc_ble_mesh_prov_call_handler(btc_msg_t *msg) act = ESP_BLE_MESH_PROVISIONER_DELETE_NODE_WITH_ADDR_COMP_EVT; param.provisioner_delete_node_with_addr_comp.unicast_addr = arg->delete_node_with_addr.unicast_addr; param.provisioner_delete_node_with_addr_comp.err_code = - bt_mesh_provisioner_delete_node_with_addr(arg->delete_node_with_addr.unicast_addr); + bt_mesh_provisioner_delete_node_with_node_addr(arg->delete_node_with_addr.unicast_addr); break; #endif /* CONFIG_BLE_MESH_PROVISIONER */ #if CONFIG_BLE_MESH_FAST_PROV diff --git a/components/bt/esp_ble_mesh/mesh_core/beacon.c b/components/bt/esp_ble_mesh/mesh_core/beacon.c index 1e720eb08..0dd02a1ad 100644 --- a/components/bt/esp_ble_mesh/mesh_core/beacon.c +++ b/components/bt/esp_ble_mesh/mesh_core/beacon.c @@ -269,7 +269,7 @@ static bool ready_to_send(void) } if (IS_ENABLED(CONFIG_BLE_MESH_PROVISIONER) && bt_mesh_is_provisioner_en()) { - if (bt_mesh_provisioner_get_all_node_count()) { + if (bt_mesh_provisioner_get_node_count()) { return true; } } diff --git a/components/bt/esp_ble_mesh/mesh_core/net.c b/components/bt/esp_ble_mesh/mesh_core/net.c index 3eeae3802..36308d9df 100644 --- a/components/bt/esp_ble_mesh/mesh_core/net.c +++ b/components/bt/esp_ble_mesh/mesh_core/net.c @@ -1389,7 +1389,7 @@ static bool ready_to_recv(void) if (IS_ENABLED(CONFIG_BLE_MESH_NODE) && bt_mesh_is_provisioned()) { return true; } else if (IS_ENABLED(CONFIG_BLE_MESH_PROVISIONER) && bt_mesh_is_provisioner_en()) { - if (bt_mesh_provisioner_get_all_node_count()) { + if (bt_mesh_provisioner_get_node_count()) { return true; } } diff --git a/components/bt/esp_ble_mesh/mesh_core/provisioner_main.c b/components/bt/esp_ble_mesh/mesh_core/provisioner_main.c index 0802821d5..f84fcd491 100644 --- a/components/bt/esp_ble_mesh/mesh_core/provisioner_main.c +++ b/components/bt/esp_ble_mesh/mesh_core/provisioner_main.c @@ -29,10 +29,9 @@ #if CONFIG_BLE_MESH_PROVISIONER -static struct bt_mesh_node *mesh_nodes[CONFIG_BLE_MESH_MAX_STORED_NODES]; +static struct bt_mesh_node *mesh_nodes[CONFIG_BLE_MESH_MAX_PROV_NODES]; static bt_mesh_mutex_t provisioner_lock; -static u16_t all_node_count; -static u16_t prov_node_count; +static u16_t node_count; static int provisioner_remove_node(u16_t index, bool erase); @@ -195,12 +194,11 @@ int bt_mesh_provisioner_deinit(bool erase) bt_mesh_clear_p_app_idx(); } - for (i = 0; i < CONFIG_BLE_MESH_MAX_STORED_NODES; i++) { + for (i = 0; i < CONFIG_BLE_MESH_MAX_PROV_NODES; i++) { provisioner_remove_node(i, erase); } - all_node_count = 0U; - prov_node_count = 0U; + node_count = 0U; bt_mesh_provisioner_mutex_free(); @@ -249,45 +247,31 @@ bool bt_mesh_provisioner_check_is_addr_dup(u16_t addr, u8_t elem_num, bool comp_ return false; } -static void provisioner_node_count_inc(bool prov) +static void provisioner_node_count_inc(void) { - all_node_count++; - if (prov) { - prov_node_count++; + node_count++; +} + +static void provisioner_node_count_dec(void) +{ + if (node_count) { + node_count--; } } -static void provisioner_node_count_dec(bool prov) +u16_t bt_mesh_provisioner_get_node_count(void) { - if (all_node_count) { - all_node_count--; - } - if (prov) { - if (prov_node_count) { - prov_node_count--; - } - } + return node_count; } -u16_t bt_mesh_provisioner_get_prov_node_count(void) +static int provisioner_store_node(struct bt_mesh_node *node, bool store, u16_t *index) { - return prov_node_count; -} - -u16_t bt_mesh_provisioner_get_all_node_count(void) -{ - return all_node_count; -} - -static int provisioner_store_node(struct bt_mesh_node *node, bool prov, bool store, u16_t *index) -{ - u16_t min = 0U, max = 0U; - size_t i = 0U; + int i; bt_mesh_provisioner_lock(); /* Check if the node already exists */ - for (i = 0U; i < ARRAY_SIZE(mesh_nodes); i++) { + for (i = 0; i < ARRAY_SIZE(mesh_nodes); i++) { if (mesh_nodes[i] && !memcmp(mesh_nodes[i]->dev_uuid, node->dev_uuid, 16)) { BT_WARN("Node already exists, uuid %s", bt_hex(node->dev_uuid, 16)); bt_mesh_provisioner_unlock(); @@ -295,19 +279,7 @@ static int provisioner_store_node(struct bt_mesh_node *node, bool prov, bool sto } } - /** - * 0 ~ (CONFIG_BLE_MESH_MAX_PROV_NODES - 1) are used to store - * the information of self-provisioned nodes. - */ - if (prov) { - min = 0U; - max = CONFIG_BLE_MESH_MAX_PROV_NODES; - } else { - min = CONFIG_BLE_MESH_MAX_PROV_NODES; - max = ARRAY_SIZE(mesh_nodes); - } - - for (i = min; i < max; i++) { + for (i = 0; i < ARRAY_SIZE(mesh_nodes); i++) { if (mesh_nodes[i] == NULL) { mesh_nodes[i] = bt_mesh_calloc(sizeof(struct bt_mesh_node)); if (!mesh_nodes[i]) { @@ -317,13 +289,13 @@ static int provisioner_store_node(struct bt_mesh_node *node, bool prov, bool sto } memcpy(mesh_nodes[i], node, sizeof(struct bt_mesh_node)); - provisioner_node_count_inc(prov); + provisioner_node_count_inc(); if (index) { *index = i; } if (IS_ENABLED(CONFIG_BLE_MESH_SETTINGS) && store) { - bt_mesh_store_node_info(mesh_nodes[i], prov); + bt_mesh_store_node_info(mesh_nodes[i]); } bt_mesh_provisioner_unlock(); @@ -336,14 +308,14 @@ static int provisioner_store_node(struct bt_mesh_node *node, bool prov, bool sto return -ENOMEM; } -int bt_mesh_provisioner_restore_node_info(struct bt_mesh_node *node, bool prov) +int bt_mesh_provisioner_restore_node_info(struct bt_mesh_node *node) { if (!node) { BT_ERR("%s, Invalid parameter", __func__); return -EINVAL; } - return provisioner_store_node(node, prov, false, NULL); + return provisioner_store_node(node, false, NULL); } int bt_mesh_provisioner_provision(const bt_mesh_addr_t *addr, const u8_t uuid[16], u16_t oob_info, @@ -375,13 +347,12 @@ int bt_mesh_provisioner_provision(const bt_mesh_addr_t *addr, const u8_t uuid[16 node.iv_index = iv_index; memcpy(node.dev_key, dev_key, 16); - return provisioner_store_node(&node, true, true, index); + return provisioner_store_node(&node, true, index); } static int provisioner_remove_node(u16_t index, bool erase) { struct bt_mesh_node *node = NULL; - bool is_prov = false; int i; BT_DBG("%s, reset node %d", __func__, index); @@ -410,10 +381,8 @@ static int provisioner_remove_node(u16_t index, bool erase) bt_mesh_friend_remove_lpn(node->unicast_addr); } - is_prov = index < CONFIG_BLE_MESH_MAX_PROV_NODES ? true : false; - if (erase && IS_ENABLED(CONFIG_BLE_MESH_SETTINGS)) { - bt_mesh_clear_node_info(node->unicast_addr, is_prov); + bt_mesh_clear_node_info(node->unicast_addr); } if (mesh_nodes[index]->comp_data) { @@ -422,7 +391,7 @@ static int provisioner_remove_node(u16_t index, bool erase) bt_mesh_free(mesh_nodes[index]); mesh_nodes[index] = NULL; - provisioner_node_count_dec(is_prov); + provisioner_node_count_dec(); bt_mesh_provisioner_unlock(); return 0; @@ -455,41 +424,6 @@ static struct bt_mesh_node *provisioner_find_node_with_uuid(const u8_t uuid[16], return NULL; } -bool bt_mesh_provisioner_find_node_with_uuid(const u8_t uuid[16], bool reset) -{ - struct bt_mesh_node *node = NULL; - u16_t index = 0U; - - node = provisioner_find_node_with_uuid(uuid, &index); - if (!node) { - return false; - } - - if (reset) { - provisioner_remove_node(index, true); - } - return true; -} - -bool bt_mesh_provisioner_find_node_with_addr(const bt_mesh_addr_t *addr, bool reset) -{ - int i; - - for (i = 0; i < ARRAY_SIZE(mesh_nodes); i++) { - if (mesh_nodes[i]) { - if (!memcmp(mesh_nodes[i]->addr, addr->val, BLE_MESH_ADDR_LEN) && - mesh_nodes[i]->addr_type == addr->type) { - if (reset) { - provisioner_remove_node(i, true); - } - return true; - } - } - } - - return false; -} - int bt_mesh_provisioner_remove_node(const u8_t uuid[16]) { struct bt_mesh_node *node = NULL; @@ -559,7 +493,7 @@ int bt_mesh_provisioner_restore_node_name(u16_t addr, const char *name) return 0; } -int bt_mesh_provisioner_restore_node_comp_data(u16_t addr, const u8_t *data, u16_t length, bool prov) +int bt_mesh_provisioner_restore_node_comp_data(u16_t addr, const u8_t *data, u16_t length) { struct bt_mesh_node *node = NULL; @@ -611,7 +545,7 @@ int bt_mesh_provisioner_delete_node_with_uuid(const u8_t uuid[16]) return 0; } -int bt_mesh_provisioner_delete_node_with_addr(u16_t unicast_addr) +int bt_mesh_provisioner_delete_node_with_node_addr(u16_t unicast_addr) { struct bt_mesh_node *node = NULL; u16_t index = 0U; @@ -626,6 +560,21 @@ int bt_mesh_provisioner_delete_node_with_addr(u16_t unicast_addr) return 0; } +int bt_mesh_provisioner_delete_node_with_dev_addr(const bt_mesh_addr_t *addr) +{ + int i; + + for (i = 0; i < ARRAY_SIZE(mesh_nodes); i++) { + if (mesh_nodes[i] && mesh_nodes[i]->addr_type == addr->type && + !memcmp(mesh_nodes[i]->addr, addr->val, BLE_MESH_ADDR_LEN)) { + return provisioner_remove_node(i, true); + } + } + + BT_WARN("Node not exist, device address %s", bt_hex(addr->val, BLE_MESH_ADDR_LEN)); + return -ENODEV; +} + static int provisioner_check_node_index(u16_t index) { BT_DBG("%s", __func__); @@ -677,11 +626,10 @@ int bt_mesh_provisioner_set_node_name(u16_t index, const char *name) } memset(mesh_nodes[index]->name, 0, BLE_MESH_NODE_NAME_SIZE); - strncpy(mesh_nodes[index]->name, name, length); + if (IS_ENABLED(CONFIG_BLE_MESH_SETTINGS)) { - bt_mesh_store_node_name(mesh_nodes[index], - index < CONFIG_BLE_MESH_MAX_PROV_NODES ? true : false); + bt_mesh_store_node_name(mesh_nodes[index]); } return 0; @@ -757,8 +705,7 @@ int bt_mesh_provisioner_store_node_comp_data(u16_t addr, const u8_t *data, u16_t node->comp_length = length; if (IS_ENABLED(CONFIG_BLE_MESH_SETTINGS)) { - bt_mesh_store_node_comp_data(node, - index < CONFIG_BLE_MESH_MAX_PROV_NODES ? true : false); + bt_mesh_store_node_comp_data(node); } return 0; @@ -1545,6 +1492,8 @@ int bt_mesh_print_local_composition_data(void) #if CONFIG_BLE_MESH_TEST_AUTO_ENTER_NETWORK int bt_mesh_provisioner_store_node_info(struct bt_mesh_node *node) { + int err = 0; + if (!node) { BT_ERR("%s, Invalid parameter", __func__); return -EINVAL; @@ -1565,12 +1514,24 @@ int bt_mesh_provisioner_store_node_info(struct bt_mesh_node *node) return -EINVAL; } + if (node->unicast_addr + node->element_num - 1 > 0x7FFF) { + BT_ERR("%s, Not enough unicast address for the node", __func__); + return -EIO; + } + if (bt_mesh_provisioner_net_key_get(node->net_idx) == NULL) { BT_ERR("%s, Invalid NetKey Index 0x%03x", __func__, node->net_idx); return -EINVAL; } - return provisioner_store_node(node, false, true, NULL); + err = provisioner_store_node(node, true, NULL); + if (err) { + BT_ERR("%s, Failed to store node info", __func__); + return err; + } + + bt_mesh_test_provisioner_update_alloc_addr(node->unicast_addr, node->element_num); + return 0; } #endif /* CONFIG_BLE_MESH_TEST_AUTO_ENTER_NETWORK */ diff --git a/components/bt/esp_ble_mesh/mesh_core/provisioner_main.h b/components/bt/esp_ble_mesh/mesh_core/provisioner_main.h index 79cdbb4e9..fcee9fdd9 100644 --- a/components/bt/esp_ble_mesh/mesh_core/provisioner_main.h +++ b/components/bt/esp_ble_mesh/mesh_core/provisioner_main.h @@ -55,25 +55,19 @@ int bt_mesh_provisioner_deinit(bool erase); bool bt_mesh_provisioner_check_is_addr_dup(u16_t addr, u8_t elem_num, bool comp_with_own); -u16_t bt_mesh_provisioner_get_prov_node_count(void); +u16_t bt_mesh_provisioner_get_node_count(void); -u16_t bt_mesh_provisioner_get_all_node_count(void); - -int bt_mesh_provisioner_restore_node_info(struct bt_mesh_node *node, bool prov); +int bt_mesh_provisioner_restore_node_info(struct bt_mesh_node *node); int bt_mesh_provisioner_provision(const bt_mesh_addr_t *addr, const u8_t uuid[16], u16_t oob_info, u16_t unicast_addr, u8_t element_num, u16_t net_idx, u8_t flags, u32_t iv_index, const u8_t dev_key[16], u16_t *index); -bool bt_mesh_provisioner_find_node_with_uuid(const u8_t uuid[16], bool reset); - -bool bt_mesh_provisioner_find_node_with_addr(const bt_mesh_addr_t *addr, bool reset); - int bt_mesh_provisioner_remove_node(const u8_t uuid[16]); int bt_mesh_provisioner_restore_node_name(u16_t addr, const char *name); -int bt_mesh_provisioner_restore_node_comp_data(u16_t addr, const u8_t *data, u16_t length, bool prov); +int bt_mesh_provisioner_restore_node_comp_data(u16_t addr, const u8_t *data, u16_t length); struct bt_mesh_node *bt_mesh_provisioner_get_node_with_uuid(const u8_t uuid[16]); @@ -81,7 +75,9 @@ struct bt_mesh_node *bt_mesh_provisioner_get_node_with_addr(u16_t unicast_addr); int bt_mesh_provisioner_delete_node_with_uuid(const u8_t uuid[16]); -int bt_mesh_provisioner_delete_node_with_addr(u16_t unicast_addr); +int bt_mesh_provisioner_delete_node_with_node_addr(u16_t unicast_addr); + +int bt_mesh_provisioner_delete_node_with_dev_addr(const bt_mesh_addr_t *addr); int bt_mesh_provisioner_set_node_name(u16_t index, const char *name); diff --git a/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.c b/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.c index 8df45ed4c..7c930965b 100644 --- a/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.c +++ b/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.c @@ -552,7 +552,7 @@ static bool is_unprov_dev_being_provision(const u8_t uuid[16]) * Unprovisioned Device Beacon when Transaction ACK for Provisioning Complete * is received). So in Fast Provisioning the Provisioner should ignore this. */ - if (bt_mesh_provisioner_find_node_with_uuid(uuid, false)) { + if (bt_mesh_provisioner_get_node_with_uuid(uuid)) { BT_WARN("Device has already been provisioned"); return true; } @@ -625,17 +625,11 @@ static int provisioner_check_unprov_dev_info(const u8_t uuid[16], bt_mesh_prov_b } /* Check if the device has already been provisioned */ - if (bt_mesh_provisioner_find_node_with_uuid(uuid, false)) { - BT_WARN("Provisioned before, start to provision again"); + if (bt_mesh_provisioner_get_node_with_uuid(uuid)) { + BT_INFO("Provisioned before, start to provision again"); return 0; } - /* Check if the provisioned nodes queue is full */ - if (bt_mesh_provisioner_get_prov_node_count() == CONFIG_BLE_MESH_MAX_PROV_NODES) { - BT_WARN("Current provisioned devices reach max limit"); - return -ENOMEM; - } - return 0; } @@ -660,6 +654,7 @@ static int provisioner_start_prov_pb_adv(const u8_t uuid[16], const bt_mesh_addr if (assign_addr == BLE_MESH_ADDR_UNASSIGNED && prov_ctx.curr_alloc_addr == BLE_MESH_ADDR_UNASSIGNED) { BT_ERR("No available unicast address to assign"); + bt_mesh_pb_adv_unlock(); return -EIO; } @@ -718,6 +713,7 @@ static int provisioner_start_prov_pb_gatt(const u8_t uuid[16], const bt_mesh_add if (assign_addr == BLE_MESH_ADDR_UNASSIGNED && prov_ctx.curr_alloc_addr == BLE_MESH_ADDR_UNASSIGNED) { BT_ERR("No available unicast address to assign"); + bt_mesh_pb_gatt_unlock(); return -EIO; } @@ -818,6 +814,14 @@ int bt_mesh_provisioner_add_unprov_dev(struct bt_mesh_unprov_dev_add *add_dev, u #endif } + /* Check if the provisioned nodes array is full */ + if (bt_mesh_provisioner_get_node_with_uuid(add_dev->uuid) == NULL) { + if (bt_mesh_provisioner_get_node_count() == CONFIG_BLE_MESH_MAX_PROV_NODES) { + BT_WARN("Current provisioned devices reach max limit"); + return -ENOMEM; + } + } + add_addr.type = add_dev->addr_type; memcpy(add_addr.val, add_dev->addr, BLE_MESH_ADDR_LEN); @@ -877,10 +881,12 @@ start: } /* Check if current provisioned node count + active link reach max limit */ - if (bt_mesh_provisioner_get_prov_node_count() + prov_ctx.pba_count + \ - prov_ctx.pbg_count >= CONFIG_BLE_MESH_MAX_PROV_NODES) { - BT_ERR("Node count + active link count reach max limit"); - return -EIO; + if (bt_mesh_provisioner_get_node_with_uuid(add_dev->uuid) == NULL) { + if (bt_mesh_provisioner_get_node_count() + prov_ctx.pba_count + \ + prov_ctx.pbg_count >= CONFIG_BLE_MESH_MAX_PROV_NODES) { + BT_WARN("Node count + active link count reach max limit"); + return -EIO; + } } if ((err = provisioner_check_unprov_dev_info(add_dev->uuid, add_dev->bearer))) { @@ -952,11 +958,19 @@ int bt_mesh_provisioner_prov_device_with_addr(const u8_t uuid[16], const u8_t ad * can not know the exactly allocated addresses of them. */ - /* Check if current provisioned node count + active link reach max limit */ - if (bt_mesh_provisioner_get_prov_node_count() + prov_ctx.pba_count + \ - prov_ctx.pbg_count >= CONFIG_BLE_MESH_MAX_PROV_NODES) { - BT_ERR("Node count + active link count reach max limit"); - return -EIO; + if (bt_mesh_provisioner_get_node_with_uuid(uuid) == NULL) { + /* Check if the provisioned nodes array is full */ + if (bt_mesh_provisioner_get_node_count() == CONFIG_BLE_MESH_MAX_PROV_NODES) { + BT_WARN("Current provisioned devices reach max limit"); + return -ENOMEM; + } + + /* Check if current provisioned node count + active link reach max limit */ + if (bt_mesh_provisioner_get_node_count() + prov_ctx.pba_count + \ + prov_ctx.pbg_count >= CONFIG_BLE_MESH_MAX_PROV_NODES) { + BT_WARN("Node count + active link count reach max limit"); + return -EIO; + } } if ((err = provisioner_check_unprov_dev_info(uuid, bearer))) { @@ -1049,15 +1063,11 @@ int bt_mesh_provisioner_delete_device(struct bt_mesh_device_delete *del_dev) /* Third: find if the device is been provisioned */ if (addr_cmp && (del_dev->addr_type <= BLE_MESH_ADDR_RANDOM)) { - if (bt_mesh_provisioner_find_node_with_addr(&del_addr, true)) { - return 0; - } + bt_mesh_provisioner_delete_node_with_dev_addr(&del_addr); } if (uuid_cmp) { - if (bt_mesh_provisioner_find_node_with_uuid(del_dev->uuid, true)) { - return 0; - } + bt_mesh_provisioner_delete_node_with_uuid(del_dev->uuid); } return 0; @@ -1243,6 +1253,26 @@ int bt_mesh_provisioner_set_primary_elem_addr(u16_t addr) return 0; } +#if CONFIG_BLE_MESH_TEST_AUTO_ENTER_NETWORK +int bt_mesh_test_provisioner_update_alloc_addr(u16_t unicast_addr, u16_t element_num) +{ + u16_t max_addr = FAST_PROV_ENABLE() ? prov_ctx.fast_prov.unicast_addr_max : PROV_MAX_ADDR_TO_ASSIGN; + + if (unicast_addr + element_num > max_addr) { + BT_WARN("%s, Not enough unicast address to allocate", __func__); + prov_ctx.curr_alloc_addr = BLE_MESH_ADDR_UNASSIGNED; + } else { + prov_ctx.curr_alloc_addr = unicast_addr + element_num; + } + + if (IS_ENABLED(CONFIG_BLE_MESH_SETTINGS)) { + bt_mesh_store_prov_info(prov_ctx.primary_addr, prov_ctx.curr_alloc_addr); + } + + return 0; +} +#endif /* CONFIG_BLE_MESH_TEST_AUTO_ENTER_NETWORK */ + /* The following APIs are for fast provisioning */ void bt_mesh_provisioner_fast_prov_enable(bool enable) @@ -2470,38 +2500,35 @@ static void send_prov_data(const u8_t idx) sys_put_be16(prev_addr, &pdu[23]); link[idx].unicast_addr = prev_addr; } else { + u16_t alloc_addr = BLE_MESH_ADDR_UNASSIGNED; + if (BLE_MESH_ADDR_IS_UNICAST(link[idx].assign_addr)) { - if (link[idx].assign_addr + link[idx].element_num - 1 > max_addr) { - BT_ERR("%s, Too large assigned address for the device", __func__); - goto fail; - } - - /* Make sure the assigned unicast address is not identical with any unicast address - * of other nodes. Also need to make sure the address is not identical with any - * address of Provisioner. - */ - if (bt_mesh_provisioner_check_is_addr_dup(link[idx].assign_addr, link[idx].element_num, true)) { - BT_ERR("%s, Assigned address 0x%04x is duplicated", __func__, link[idx].assign_addr); - goto fail; - } - - sys_put_be16(link[idx].assign_addr, &pdu[23]); - link[idx].unicast_addr = link[idx].assign_addr; + alloc_addr = link[idx].assign_addr; } else { /* If this device to be provisioned is a new device */ if (prov_ctx.curr_alloc_addr == BLE_MESH_ADDR_UNASSIGNED) { BT_ERR("%s, No unicast address can be allocated", __func__); goto fail; } - - if (prov_ctx.curr_alloc_addr + link[idx].element_num - 1 > max_addr) { - BT_ERR("%s, Not enough unicast address for the device", __func__); - goto fail; - } - - sys_put_be16(prov_ctx.curr_alloc_addr, &pdu[23]); - link[idx].unicast_addr = prov_ctx.curr_alloc_addr; + alloc_addr = prov_ctx.curr_alloc_addr; } + + if (alloc_addr + link[idx].element_num - 1 > max_addr) { + BT_ERR("%s, Not enough unicast address for the device", __func__); + goto fail; + } + + /* Make sure the assigned unicast address is not identical with any unicast + * address of other nodes. And make sure the address is not identical with + * any unicast address of Provisioner. + */ + if (bt_mesh_provisioner_check_is_addr_dup(alloc_addr, link[idx].element_num, true)) { + BT_ERR("%s, Assigned address 0x%04x is duplicated", __func__, alloc_addr); + goto fail; + } + + sys_put_be16(alloc_addr, &pdu[23]); + link[idx].unicast_addr = alloc_addr; } prov_buf_init(&buf, PROV_DATA); diff --git a/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.h b/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.h index d5dd9fb8f..05071fe82 100644 --- a/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.h +++ b/components/bt/esp_ble_mesh/mesh_core/provisioner_prov.h @@ -335,6 +335,18 @@ u16_t bt_mesh_provisioner_get_primary_elem_addr(void); */ int bt_mesh_provisioner_set_primary_elem_addr(u16_t addr); +/** + * @brief This function is used to update next allocated address by Provisioner. + * + * @note This function is used for mesh internal test. + * + * @param[in] unicast_addr: unicast address of the node + * @param[in] element_num: element count of the node + * + * @return Zero - success, otherwise - fail + */ +int bt_mesh_test_provisioner_update_alloc_addr(u16_t unicast_addr, u16_t element_num); + /** * @brief This function is called to input number/string out-put by unprovisioned device. * diff --git a/components/bt/esp_ble_mesh/mesh_core/settings.c b/components/bt/esp_ble_mesh/mesh_core/settings.c index 2792d893d..3e62f9fb1 100644 --- a/components/bt/esp_ble_mesh/mesh_core/settings.c +++ b/components/bt/esp_ble_mesh/mesh_core/settings.c @@ -1039,14 +1039,14 @@ free: return err; } -static int node_info_set(u16_t addr, bool prov, bool *exist) +static int node_info_set(u16_t addr, bool *exist) { struct bt_mesh_node node = {0}; struct node_info info = {0}; char get[16] = {'\0'}; int err = 0; - sprintf(get, prov ? "mesh/pn/%04x/i" : "mesh/sn/%04x/i", addr); + sprintf(get, "mesh/pn/%04x/i", addr); err = bt_mesh_load_core_settings(get, (u8_t *)&info, sizeof(info), exist); if (err) { BT_ERR("%s, Failed to load node %s", __func__, get); @@ -1068,7 +1068,7 @@ static int node_info_set(u16_t addr, bool prov, bool *exist) node.iv_index = info.iv_index; memcpy(node.dev_key, info.dev_key, 16); - err = bt_mesh_provisioner_restore_node_info(&node, prov); + err = bt_mesh_provisioner_restore_node_info(&node); if (err) { BT_ERR("%s, Failed to restore node 0x%04x", __func__, addr); return -EIO; @@ -1079,14 +1079,14 @@ static int node_info_set(u16_t addr, bool prov, bool *exist) return 0; } -static int node_name_set(u16_t addr, bool prov) +static int node_name_set(u16_t addr) { char name[BLE_MESH_NODE_NAME_SIZE] = {0}; char get[16] = {'\0'}; bool exist = false; int err = 0; - sprintf(get, prov ? "mesh/pn/%04x/n" : "mesh/sn/%04x/n", addr); + sprintf(get, "mesh/pn/%04x/n", addr); err = bt_mesh_load_core_settings(get, (u8_t *)name, BLE_MESH_NODE_NAME_SIZE, &exist); if (err) { BT_ERR("%s, Failed to load node name %s", __func__, get); @@ -1108,19 +1108,19 @@ static int node_name_set(u16_t addr, bool prov) return 0; } -static int node_comp_data_set(u16_t addr, bool prov) +static int node_comp_data_set(u16_t addr) { struct net_buf_simple *buf = NULL; char get[16] = {'\0'}; int err = 0; - sprintf(get, prov ? "mesh/pn/%04x/c" : "mesh/sn/%04x/c", addr); + sprintf(get, "mesh/pn/%04x/c", addr); buf = bt_mesh_get_core_settings_item(get); if (!buf) { return 0; } - err = bt_mesh_provisioner_restore_node_comp_data(addr, buf->data, buf->len, prov); + err = bt_mesh_provisioner_restore_node_comp_data(addr, buf->data, buf->len); if (err) { BT_ERR("%s, Failed to restore node comp data 0x%04x", __func__, addr); } @@ -1134,7 +1134,7 @@ static int node_comp_data_set(u16_t addr, bool prov) static int p_node_set(const char *name) { struct net_buf_simple *buf = NULL; - bool exist = false, prov = false; + bool exist = false; size_t length = 0U; int err = 0; int i; @@ -1144,40 +1144,38 @@ static int p_node_set(const char *name) return 0; } - prov = strcmp(name, "mesh/p_pnode") == 0 ? true : false; length = buf->len; for (i = 0; i < length / SETTINGS_ITEM_SIZE; i++) { u16_t addr = net_buf_simple_pull_le16(buf); if (!BLE_MESH_ADDR_IS_UNICAST(addr)) { BT_ERR("%s, 0x%04x is not a unicast address", __func__, addr); - goto free; + continue; } - err = node_info_set(addr, prov, &exist); + err = node_info_set(addr, &exist); if (err) { BT_ERR("%s, Failed to load node 0x%04x info", __func__, addr); - goto free; + continue; } if (exist == false) { continue; } - err = node_name_set(addr, prov); + err = node_name_set(addr); if (err) { BT_ERR("%s, Failed to load node 0x%04x name", __func__, addr); - goto free; + continue; } - err = node_comp_data_set(addr, prov); + err = node_comp_data_set(addr); if (err) { BT_ERR("%s, Failed to load node 0x%04x comp data", __func__, addr); - goto free; + continue; } } -free: bt_mesh_free_buf(buf); return err; } @@ -1207,8 +1205,7 @@ const struct bt_mesh_setting { { "mesh/p_appidx", p_app_idx_set }, { "mesh/p_netkey", p_net_key_set }, { "mesh/p_appkey", p_app_key_set }, - { "mesh/p_pnode", p_node_set }, - { "mesh/p_snode", p_node_set }, + { "mesh/p_node", p_node_set }, #endif }; @@ -1248,8 +1245,7 @@ int settings_core_load(void) !strcmp(settings[i].name, "mesh/p_appidx") || !strcmp(settings[i].name, "mesh/p_netkey") || !strcmp(settings[i].name, "mesh/p_appkey") || - !strcmp(settings[i].name, "mesh/p_pnode") || - !strcmp(settings[i].name, "mesh/p_snode")) && + !strcmp(settings[i].name, "mesh/p_node")) && (!IS_ENABLED(CONFIG_BLE_MESH_PROVISIONER) || bt_mesh_is_node())) { BT_DBG("Not restoring %s for node", settings[i].name); continue; @@ -2252,14 +2248,10 @@ void bt_mesh_store_label(void) * key: "mesh/pnk/xxxx" -> write/read to set/get the "xxxx" NetKey * key: "mesh/p_appkey" -> write/read to set/get all Provisioner AppKey Index * key: "mesh/pak/xxxx" -> write/read to set/get the "xxxx" AppKey - * key: "mesh/p_pnode" -> write/read to set/get all self-provisioned nodes info + * key: "mesh/p_node" -> write/read to set/get all self-provisioned nodes info * key: "mesh/pn/xxxx/i" -> write/read to set/get the "xxxx" provisioned node info * key: "mesh/pn/xxxx/n" -> write/read to set/get the "xxxx" provisioned node name * key: "mesh/pn/xxxx/c" -> write/read to set/get the "xxxx" provisioned node composition data - * key: "mesh/p_snode" -> write/read to set/get all locally stored nodes info - * key: "mesh/sn/xxxx/i" -> write/read to set/get the "xxxx" stored node info - * key: "mesh/sn/xxxx/n" -> write/read to set/get the "xxxx" stored node name - * key: "mesh/sn/xxxx/c" -> write/read to set/get the "xxxx" stored node composition data */ void bt_mesh_store_prov_info(u16_t primary_addr, u16_t alloc_addr) { @@ -2449,7 +2441,7 @@ void bt_mesh_clear_rpl_single(u16_t src) } } -void bt_mesh_store_node_info(struct bt_mesh_node *node, bool prov) +void bt_mesh_store_node_info(struct bt_mesh_node *node) { struct node_info val = {0}; char name[16] = {'\0'}; @@ -2471,43 +2463,43 @@ void bt_mesh_store_node_info(struct bt_mesh_node *node, bool prov) val.iv_index = node->iv_index; memcpy(val.dev_key, node->dev_key, 16); - sprintf(name, prov ? "mesh/pn/%04x/i" : "mesh/sn/%04x/i", node->unicast_addr); + sprintf(name, "mesh/pn/%04x/i", node->unicast_addr); err = bt_mesh_save_core_settings(name, (const u8_t *)&val, sizeof(val)); if (err) { BT_ERR("%s, Failed to save node %s", __func__, name); return; } - err = bt_mesh_add_core_settings_item(prov ? "mesh/p_pnode" : "mesh/p_snode", node->unicast_addr); + err = bt_mesh_add_core_settings_item("mesh/p_node", node->unicast_addr); if (err) { BT_ERR("%s, Failed to add node 0x%04x", __func__, node->unicast_addr); } } -static void clear_node(u16_t addr, bool prov) +static void clear_node(u16_t addr) { char name[16] = {'\0'}; int err = 0; /* Clear node information */ - sprintf(name, prov ? "mesh/pn/%04x/i" : "mesh/sn/%04x/i", addr); + sprintf(name, "mesh/pn/%04x/i", addr); bt_mesh_save_core_settings(name, NULL, 0); /* Clear node name */ - sprintf(name, prov ? "mesh/pn/%04x/n" : "mesh/sn/%04x/n", addr); + sprintf(name, "mesh/pn/%04x/n", addr); bt_mesh_save_core_settings(name, NULL, 0); /* Clear node composition data */ - sprintf(name, prov ? "mesh/pn/%04x/c" : "mesh/sn/%04x/c", addr); + sprintf(name, "mesh/pn/%04x/c", addr); bt_mesh_save_core_settings(name, NULL, 0); - err = bt_mesh_remove_core_settings_item(prov ? "mesh/p_pnode" : "mesh/p_snode", addr); + err = bt_mesh_remove_core_settings_item("mesh/p_node", addr); if (err) { BT_ERR("%s, Failed to remove node 0x%04x", __func__, addr); } } -void bt_mesh_clear_node_info(u16_t unicast_addr, bool prov) +void bt_mesh_clear_node_info(u16_t unicast_addr) { if (!BLE_MESH_ADDR_IS_UNICAST(unicast_addr)) { BT_ERR("%s, Invalid unicast address 0x%04x", __func__, unicast_addr); @@ -2516,10 +2508,10 @@ void bt_mesh_clear_node_info(u16_t unicast_addr, bool prov) BT_DBG("Unicast address 0x%04x", unicast_addr); - clear_node(unicast_addr, prov); + clear_node(unicast_addr); } -void bt_mesh_store_node_name(struct bt_mesh_node *node, bool prov) +void bt_mesh_store_node_name(struct bt_mesh_node *node) { char node_name[BLE_MESH_NODE_NAME_SIZE] = {0}; char name[16] = {'\0'}; @@ -2532,14 +2524,14 @@ void bt_mesh_store_node_name(struct bt_mesh_node *node, bool prov) strncpy(node_name, node->name, BLE_MESH_NODE_NAME_SIZE); - sprintf(name, prov ? "mesh/pn/%04x/n" : "mesh/sn/%04x/n", node->unicast_addr); + sprintf(name, "mesh/pn/%04x/n", node->unicast_addr); err = bt_mesh_save_core_settings(name, (const u8_t *)node_name, BLE_MESH_NODE_NAME_SIZE); if (err) { BT_ERR("%s, Failed to save node name %s", __func__, name); } } -void bt_mesh_store_node_comp_data(struct bt_mesh_node *node, bool prov) +void bt_mesh_store_node_comp_data(struct bt_mesh_node *node) { char name[16] = {'\0'}; int err = 0; @@ -2549,7 +2541,7 @@ void bt_mesh_store_node_comp_data(struct bt_mesh_node *node, bool prov) return; } - sprintf(name, prov ? "mesh/pn/%04x/c" : "mesh/sn/%04x/c", node->unicast_addr); + sprintf(name, "mesh/pn/%04x/c", node->unicast_addr); err = bt_mesh_save_core_settings(name, (const u8_t *)node->comp_data, node->comp_length); if (err) { BT_ERR("%s, Failed to save node comp data %s", __func__, name); diff --git a/components/bt/esp_ble_mesh/mesh_core/settings.h b/components/bt/esp_ble_mesh/mesh_core/settings.h index ba60d4c96..52a7b2cd0 100644 --- a/components/bt/esp_ble_mesh/mesh_core/settings.h +++ b/components/bt/esp_ble_mesh/mesh_core/settings.h @@ -53,10 +53,10 @@ void bt_mesh_store_p_app_key(struct bt_mesh_app_key *key); void bt_mesh_clear_p_subnet(struct bt_mesh_subnet *sub); void bt_mesh_clear_p_app_key(struct bt_mesh_app_key *key); void bt_mesh_clear_rpl_single(u16_t src); -void bt_mesh_store_node_info(struct bt_mesh_node *node, bool prov); -void bt_mesh_clear_node_info(u16_t unicast_addr, bool prov); -void bt_mesh_store_node_name(struct bt_mesh_node *node, bool prov); -void bt_mesh_store_node_comp_data(struct bt_mesh_node *node, bool prov); +void bt_mesh_store_node_info(struct bt_mesh_node *node); +void bt_mesh_clear_node_info(u16_t unicast_addr); +void bt_mesh_store_node_name(struct bt_mesh_node *node); +void bt_mesh_store_node_comp_data(struct bt_mesh_node *node); #endif int bt_mesh_settings_init(void); diff --git a/components/bt/esp_ble_mesh/mesh_models/client/client_common.c b/components/bt/esp_ble_mesh/mesh_models/client/client_common.c index a3f68834b..5718d5202 100644 --- a/components/bt/esp_ble_mesh/mesh_models/client/client_common.c +++ b/components/bt/esp_ble_mesh/mesh_models/client/client_common.c @@ -178,10 +178,10 @@ static s32_t bt_mesh_client_calc_timeout(struct bt_mesh_msg_ctx *ctx, struct net_buf_simple *msg, u32_t opcode, s32_t timeout) { - s32_t seg_retrans_to, duration, time; - u8_t seg_count, seg_retrans_num; - u8_t mic_size; - bool need_seg; + s32_t seg_retrans_to = 0, duration = 0, time = 0; + u8_t seg_count = 0, seg_retrans_num = 0; + bool need_seg = false; + u8_t mic_size = 0; if (msg->len > UNSEG_ACCESS_MSG_MAX_LEN || ctx->send_rel) { need_seg = true; /* Needs segmentation */ diff --git a/examples/bluetooth/esp_ble_mesh/ble_mesh_console/ble_mesh_provisioner/sdkconfig.defaults b/examples/bluetooth/esp_ble_mesh/ble_mesh_console/ble_mesh_provisioner/sdkconfig.defaults index e4d43ea2b..b562b2470 100644 --- a/examples/bluetooth/esp_ble_mesh/ble_mesh_console/ble_mesh_provisioner/sdkconfig.defaults +++ b/examples/bluetooth/esp_ble_mesh/ble_mesh_console/ble_mesh_provisioner/sdkconfig.defaults @@ -12,6 +12,7 @@ CONFIG_BT_BTU_TASK_STACK_SIZE=4512 # Override some defaults of ESP BLE Mesh CONFIG_BLE_MESH=y CONFIG_BLE_MESH_PROVISIONER=y +CONFIG_BLE_MESH_MAX_PROV_NODES=40 CONFIG_BLE_MESH_PB_GATT=y CONFIG_BLE_MESH_PBA_SAME_TIME=10 CONFIG_BLE_MESH_PBG_SAME_TIME=3 @@ -19,7 +20,7 @@ CONFIG_BLE_MESH_TX_SEG_MSG_COUNT=3 CONFIG_BLE_MESH_RX_SEG_MSG_COUNT=3 CONFIG_BLE_MESH_CFG_CLI=y CONFIG_BLE_MESH_GENERIC_ONOFF_CLI=y -CONFIG_BLE_MESH_MAX_STORED_NODES=40 CONFIG_BLE_MESH_MSG_CACHE_SIZE=60 CONFIG_BLE_MESH_ADV_BUF_COUNT=200 -CONFIG_BLE_MESH_SELF_TEST=y \ No newline at end of file +CONFIG_BLE_MESH_CRPL=40 +CONFIG_BLE_MESH_SELF_TEST=y