diff --git a/libraries/Zigbee/src/ZigbeeEP.cpp b/libraries/Zigbee/src/ZigbeeEP.cpp index e7d507dc441..a1ca2a4f4ad 100644 --- a/libraries/Zigbee/src/ZigbeeEP.cpp +++ b/libraries/Zigbee/src/ZigbeeEP.cpp @@ -19,6 +19,8 @@ ZigbeeEP::ZigbeeEP(uint8_t endpoint) { _ep_config.endpoint = 0; _cluster_list = nullptr; _on_identify = nullptr; + _read_model = nullptr; // Explicitly initialize here + _read_manufacturer = nullptr; // Explicitly initialize here _time_status = 0; if (!lock) { lock = xSemaphoreCreateBinary(); @@ -33,38 +35,41 @@ void ZigbeeEP::setVersion(uint8_t version) { } bool ZigbeeEP::setManufacturerAndModel(const char *name, const char *model) { + constexpr size_t ZB_MAX_NAME_LENGTH = 32; // Convert manufacturer to ZCL string size_t name_length = strlen(name); size_t model_length = strlen(model); - if (name_length > 32 || model_length > 32) { + if (name_length > ZB_MAX_NAME_LENGTH || model_length > ZB_MAX_NAME_LENGTH) { log_e("Manufacturer or model name is too long"); return false; } // Allocate a new array of size length + 2 (1 for the length, 1 for null terminator) - char *zb_name = new char[name_length + 2]; - char *zb_model = new char[model_length + 2]; + std::vector zb_name(name_length + 2); + std::vector zb_model(model_length + 2); // Store the length as the first element zb_name[0] = static_cast(name_length); // Cast size_t to char zb_model[0] = static_cast(model_length); // Use memcpy to copy the characters to the result array - memcpy(zb_name + 1, name, name_length); - memcpy(zb_model + 1, model, model_length); + memcpy(zb_name.data() + 1, name, name_length); + memcpy(zb_model.data() + 1, model, model_length); // Null-terminate the array zb_name[name_length + 1] = '\0'; zb_model[model_length + 1] = '\0'; // Get the basic cluster and update the manufacturer and model attributes esp_zb_attribute_list_t *basic_cluster = esp_zb_cluster_list_get_cluster(_cluster_list, ESP_ZB_ZCL_CLUSTER_ID_BASIC, ESP_ZB_ZCL_CLUSTER_SERVER_ROLE); - esp_err_t ret_name = esp_zb_basic_cluster_add_attr(basic_cluster, ESP_ZB_ZCL_ATTR_BASIC_MANUFACTURER_NAME_ID, (void *)zb_name); + if (!basic_cluster) { + log_e("Failed to get basic cluster"); + return false; + } + esp_err_t ret_name = esp_zb_basic_cluster_add_attr(basic_cluster, ESP_ZB_ZCL_ATTR_BASIC_MANUFACTURER_NAME_ID, (void *)zb_name.data()); if (ret_name != ESP_OK) { log_e("Failed to set manufacturer: 0x%x: %s", ret_name, esp_err_to_name(ret_name)); } - esp_err_t ret_model = esp_zb_basic_cluster_add_attr(basic_cluster, ESP_ZB_ZCL_ATTR_BASIC_MODEL_IDENTIFIER_ID, (void *)zb_model); + esp_err_t ret_model = esp_zb_basic_cluster_add_attr(basic_cluster, ESP_ZB_ZCL_ATTR_BASIC_MODEL_IDENTIFIER_ID, (void *)zb_model.data()); if (ret_model != ESP_OK) { log_e("Failed to set model: 0x%x: %s", ret_model, esp_err_to_name(ret_model)); } - delete[] zb_name; - delete[] zb_model; return ret_name == ESP_OK && ret_model == ESP_OK; } @@ -163,9 +168,7 @@ char *ZigbeeEP::readManufacturer(uint8_t endpoint, uint16_t short_addr, esp_zb_i read_req.attr_number = ZB_ARRAY_LENTH(attributes); read_req.attr_field = attributes; - if (_read_manufacturer != nullptr) { - free(_read_manufacturer); - } + free(_read_manufacturer); // CPP tests it for nullptr _read_manufacturer = nullptr; esp_zb_lock_acquire(portMAX_DELAY); @@ -201,9 +204,7 @@ char *ZigbeeEP::readModel(uint8_t endpoint, uint16_t short_addr, esp_zb_ieee_add read_req.attr_number = ZB_ARRAY_LENTH(attributes); read_req.attr_field = attributes; - if (_read_model != nullptr) { - free(_read_model); - } + free(_read_model); // CPP tests it for nullptr _read_model = nullptr; esp_zb_lock_acquire(portMAX_DELAY); @@ -245,20 +246,22 @@ void ZigbeeEP::zbReadBasicCluster(const esp_zb_zcl_attribute_t *attribute) { /* Basic cluster attributes */ if (attribute->id == ESP_ZB_ZCL_ATTR_BASIC_MANUFACTURER_NAME_ID && attribute->data.type == ESP_ZB_ZCL_ATTR_TYPE_CHAR_STRING && attribute->data.value) { zbstring_t *zbstr = (zbstring_t *)attribute->data.value; - char *string = (char *)malloc(zbstr->len + 1); - memcpy(string, zbstr->data, zbstr->len); - string[zbstr->len] = '\0'; - log_i("Peer Manufacturer is \"%s\"", string); - _read_manufacturer = string; + std::vector zb_manufacturer(zbstr->len + 1); + memcpy(zb_manufacturer.data(), zbstr->data, zbstr->len); + zb_manufacturer[zbstr->len] = '\0'; + log_i("Peer Manufacturer is \"%s\"", zb_manufacturer.data()); + free(_read_manufacturer); // Free any previously allocated memory + _read_manufacturer = strdup(zb_manufacturer.data()); // Duplicate the information for persistent storage xSemaphoreGive(lock); } if (attribute->id == ESP_ZB_ZCL_ATTR_BASIC_MODEL_IDENTIFIER_ID && attribute->data.type == ESP_ZB_ZCL_ATTR_TYPE_CHAR_STRING && attribute->data.value) { zbstring_t *zbstr = (zbstring_t *)attribute->data.value; - char *string = (char *)malloc(zbstr->len + 1); - memcpy(string, zbstr->data, zbstr->len); - string[zbstr->len] = '\0'; - log_i("Peer Model is \"%s\"", string); - _read_model = string; + std::vector zb_model(zbstr->len + 1); + memcpy(zb_model.data(), zbstr->data, zbstr->len); + zb_model[zbstr->len] = '\0'; + log_i("Peer Model is \"%s\"", zb_model.data()); + free(_read_model); // Free any previously allocated memory + _read_model = strdup(zb_model.data()); // Duplicate the information for persistent storage xSemaphoreGive(lock); } }