Merge branch 'bugfix/dpp_deinit_memleak_v52' into 'release/v5.2'

Fix a memory leak in dpp deinit path(v5.2)

See merge request espressif/esp-idf!27680
This commit is contained in:
Jiang Jiang Jian
2023-12-06 13:22:28 +08:00
6 changed files with 166 additions and 60 deletions

View File

@@ -416,6 +416,9 @@ static const esp_err_msg_t esp_err_msg_table[] = {
# endif # endif
# ifdef ESP_ERR_WIFI_DISCARD # ifdef ESP_ERR_WIFI_DISCARD
ERR_TBL_IT(ESP_ERR_WIFI_DISCARD), /* 12315 0x301b Discard frame */ ERR_TBL_IT(ESP_ERR_WIFI_DISCARD), /* 12315 0x301b Discard frame */
# endif
# ifdef ESP_ERR_WIFI_ROC_IN_PROGRESS
ERR_TBL_IT(ESP_ERR_WIFI_ROC_IN_PROGRESS), /* 12316 0x301c ROC op is in progress */
# endif # endif
// components/wpa_supplicant/esp_supplicant/include/esp_wps.h // components/wpa_supplicant/esp_supplicant/include/esp_wps.h
# ifdef ESP_ERR_WIFI_REGISTRAR # ifdef ESP_ERR_WIFI_REGISTRAR
@@ -464,6 +467,9 @@ static const esp_err_msg_t esp_err_msg_table[] = {
# endif # endif
# ifdef ESP_ERR_DPP_INVALID_ATTR # ifdef ESP_ERR_DPP_INVALID_ATTR
ERR_TBL_IT(ESP_ERR_DPP_INVALID_ATTR), /* 12441 0x3099 Encountered invalid DPP Attribute */ ERR_TBL_IT(ESP_ERR_DPP_INVALID_ATTR), /* 12441 0x3099 Encountered invalid DPP Attribute */
# endif
# ifdef ESP_ERR_DPP_AUTH_TIMEOUT
ERR_TBL_IT(ESP_ERR_DPP_AUTH_TIMEOUT), /* 12442 0x309a DPP Auth response was not recieved in time */
# endif # endif
// components/esp_common/include/esp_err.h // components/esp_common/include/esp_err.h
# ifdef ESP_ERR_MESH_BASE # ifdef ESP_ERR_MESH_BASE

View File

@@ -88,6 +88,7 @@ extern "C" {
#define ESP_ERR_WIFI_TWT_SETUP_TXFAIL (ESP_ERR_WIFI_BASE + 25) /*!< TWT setup frame tx failed */ #define ESP_ERR_WIFI_TWT_SETUP_TXFAIL (ESP_ERR_WIFI_BASE + 25) /*!< TWT setup frame tx failed */
#define ESP_ERR_WIFI_TWT_SETUP_REJECT (ESP_ERR_WIFI_BASE + 26) /*!< The twt setup request was rejected by the AP */ #define ESP_ERR_WIFI_TWT_SETUP_REJECT (ESP_ERR_WIFI_BASE + 26) /*!< The twt setup request was rejected by the AP */
#define ESP_ERR_WIFI_DISCARD (ESP_ERR_WIFI_BASE + 27) /*!< Discard frame */ #define ESP_ERR_WIFI_DISCARD (ESP_ERR_WIFI_BASE + 27) /*!< Discard frame */
#define ESP_ERR_WIFI_ROC_IN_PROGRESS (ESP_ERR_WIFI_BASE + 28) /*!< ROC op is in progress */
/** /**
* @brief WiFi stack configuration parameters passed to esp_wifi_init call. * @brief WiFi stack configuration parameters passed to esp_wifi_init call.
@@ -411,9 +412,9 @@ esp_err_t esp_wifi_deauth_sta(uint16_t aid);
/** /**
* @brief Scan all available APs. * @brief Scan all available APs.
* *
* @attention If this API is called, the found APs are stored in WiFi driver dynamic allocated memory and the * @attention If this API is called, the found APs are stored in WiFi driver dynamic allocated memory. And then
* will be freed in esp_wifi_scan_get_ap_records, so generally, call esp_wifi_scan_get_ap_records to cause * can be freed in esp_wifi_scan_get_ap_records(), esp_wifi_scan_get_ap_record() or esp_wifi_clear_ap_list(),
* the memory to be freed once the scan is done * so call any one to free the memory once the scan is done.
* @attention The values of maximum active scan time and passive scan time per channel are limited to 1500 milliseconds. * @attention The values of maximum active scan time and passive scan time per channel are limited to 1500 milliseconds.
* Values above 1500ms may cause station to disconnect from AP and are not recommended. * Values above 1500ms may cause station to disconnect from AP and are not recommended.
* *
@@ -460,7 +461,9 @@ esp_err_t esp_wifi_scan_stop(void);
esp_err_t esp_wifi_scan_get_ap_num(uint16_t *number); esp_err_t esp_wifi_scan_get_ap_num(uint16_t *number);
/** /**
* @brief Get AP list found in last scan * @brief Get AP list found in last scan.
*
* @attention This API will free all memory occupied by scanned AP list.
* *
* @param[inout] number As input param, it stores max AP number ap_records can hold. * @param[inout] number As input param, it stores max AP number ap_records can hold.
* As output param, it receives the actual AP number this API returns. * As output param, it receives the actual AP number this API returns.
@@ -475,11 +478,30 @@ esp_err_t esp_wifi_scan_get_ap_num(uint16_t *number);
*/ */
esp_err_t esp_wifi_scan_get_ap_records(uint16_t *number, wifi_ap_record_t *ap_records); esp_err_t esp_wifi_scan_get_ap_records(uint16_t *number, wifi_ap_record_t *ap_records);
/**
* @brief Get one AP record from the scanned AP list.
*
* @attention Different from esp_wifi_scan_get_ap_records(), this API only gets one AP record
* from the scanned AP list each time. This API will free the memory of one AP record,
* if the user doesn't get all records in the scannned AP list, then needs to call esp_wifi_clear_ap_list()
* to free the remaining memory.
*
* @param[out] ap_record pointer to one AP record
*
* @return
* - ESP_OK: succeed
* - ESP_ERR_WIFI_NOT_INIT: WiFi is not initialized by esp_wifi_init
* - ESP_ERR_WIFI_NOT_STARTED: WiFi is not started by esp_wifi_start
* - ESP_ERR_INVALID_ARG: invalid argument
* - ESP_FAIL: scan APs is NULL, means all AP records fetched or no AP found
*/
esp_err_t esp_wifi_scan_get_ap_record(wifi_ap_record_t *ap_record);
/** /**
* @brief Clear AP list found in last scan * @brief Clear AP list found in last scan
* *
* @attention When the obtained ap list fails,bss info must be cleared,otherwise it may cause memory leakage. * @attention This API will free all memory occupied by scanned AP list.
* When the obtained AP list fails, AP records must be cleared,otherwise it may cause memory leakage.
* *
* @return * @return
* - ESP_OK: succeed * - ESP_OK: succeed

View File

@@ -1,5 +1,5 @@
/* /*
* SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD * SPDX-FileCopyrightText: 2020-2023 Espressif Systems (Shanghai) CO LTD
* *
* SPDX-License-Identifier: Apache-2.0 * SPDX-License-Identifier: Apache-2.0
*/ */
@@ -15,10 +15,12 @@
extern "C" { extern "C" {
#endif #endif
#define ESP_DPP_AUTH_TIMEOUT_SECS 1
#define ESP_ERR_DPP_FAILURE (ESP_ERR_WIFI_BASE + 151) /*!< Generic failure during DPP Operation */ #define ESP_ERR_DPP_FAILURE (ESP_ERR_WIFI_BASE + 151) /*!< Generic failure during DPP Operation */
#define ESP_ERR_DPP_TX_FAILURE (ESP_ERR_WIFI_BASE + 152) /*!< DPP Frame Tx failed OR not Acked */ #define ESP_ERR_DPP_TX_FAILURE (ESP_ERR_WIFI_BASE + 152) /*!< DPP Frame Tx failed OR not Acked */
#define ESP_ERR_DPP_INVALID_ATTR (ESP_ERR_WIFI_BASE + 153) /*!< Encountered invalid DPP Attribute */ #define ESP_ERR_DPP_INVALID_ATTR (ESP_ERR_WIFI_BASE + 153) /*!< Encountered invalid DPP Attribute */
#define ESP_ERR_DPP_AUTH_TIMEOUT (ESP_ERR_WIFI_BASE + 154) /*!< DPP Auth response was not recieved in time */
/** @brief Types of Bootstrap Methods for DPP. */ /** @brief Types of Bootstrap Methods for DPP. */
typedef enum dpp_bootstrap_type { typedef enum dpp_bootstrap_type {
DPP_BOOTSTRAP_QR_CODE, /**< QR Code Method */ DPP_BOOTSTRAP_QR_CODE, /**< QR Code Method */

View File

@@ -6,6 +6,7 @@
#include "utils/includes.h" #include "utils/includes.h"
#include "utils/common.h" #include "utils/common.h"
#include "utils/eloop.h"
#include "common/defs.h" #include "common/defs.h"
#include "esp_dpp_i.h" #include "esp_dpp_i.h"
@@ -21,8 +22,7 @@ static void *s_dpp_task_hdl = NULL;
static void *s_dpp_evt_queue = NULL; static void *s_dpp_evt_queue = NULL;
static void *s_dpp_api_lock = NULL; static void *s_dpp_api_lock = NULL;
static bool s_dpp_stop_listening; static bool s_dpp_listen_in_progress;
static int s_dpp_auth_retries;
static struct esp_dpp_context_t s_dpp_ctx; static struct esp_dpp_context_t s_dpp_ctx;
static wifi_action_rx_cb_t s_action_rx_cb = esp_supp_rx_action; static wifi_action_rx_cb_t s_action_rx_cb = esp_supp_rx_action;
@@ -37,6 +37,7 @@ struct action_rx_param {
struct ieee80211_action *action_frm; struct ieee80211_action *action_frm;
}; };
static int esp_dpp_post_evt(uint32_t evt_id, uint32_t data) static int esp_dpp_post_evt(uint32_t evt_id, uint32_t data)
{ {
dpp_event_t *evt = os_zalloc(sizeof(dpp_event_t)); dpp_event_t *evt = os_zalloc(sizeof(dpp_event_t));
@@ -73,9 +74,27 @@ end:
static void esp_dpp_call_cb(esp_supp_dpp_event_t evt, void *data) static void esp_dpp_call_cb(esp_supp_dpp_event_t evt, void *data)
{ {
if ( evt == ESP_SUPP_DPP_FAIL && s_dpp_ctx.dpp_auth) {
dpp_auth_deinit(s_dpp_ctx.dpp_auth);
s_dpp_ctx.dpp_auth = NULL;
}
s_dpp_ctx.dpp_event_cb(evt, data); s_dpp_ctx.dpp_event_cb(evt, data);
} }
static void esp_dpp_auth_conf_wait_timeout(void *eloop_ctx, void *timeout_ctx)
{
if (!s_dpp_ctx.dpp_auth || !s_dpp_ctx.dpp_auth->waiting_auth_conf)
return;
wpa_printf(MSG_DEBUG,
"DPP: Terminate authentication exchange due to Auth Confirm timeout");
if (s_dpp_ctx.dpp_auth) {
dpp_auth_deinit(s_dpp_ctx.dpp_auth);
s_dpp_ctx.dpp_auth = NULL;
}
esp_dpp_call_cb(ESP_SUPP_DPP_FAIL, (void *)ESP_ERR_DPP_AUTH_TIMEOUT);
}
void esp_send_action_frame(uint8_t *dest_mac, const uint8_t *buf, uint32_t len, void esp_send_action_frame(uint8_t *dest_mac, const uint8_t *buf, uint32_t len,
uint8_t channel, uint32_t wait_time_ms) uint8_t channel, uint32_t wait_time_ms)
{ {
@@ -141,15 +160,20 @@ static void esp_dpp_rx_auth_req(struct action_rx_param *rx_param, uint8_t *dpp_d
rc = ESP_ERR_DPP_INVALID_ATTR; rc = ESP_ERR_DPP_INVALID_ATTR;
goto fail; goto fail;
} }
if (s_dpp_ctx.dpp_auth) {
wpa_printf(MSG_DEBUG, "DPP: Already in DPP authentication exchange - ignore new one");
return;
}
s_dpp_ctx.dpp_auth = dpp_auth_req_rx(NULL, DPP_CAPAB_ENROLLEE, 0, NULL, s_dpp_ctx.dpp_auth = dpp_auth_req_rx(NULL, DPP_CAPAB_ENROLLEE, 0, NULL,
own_bi, rx_param->channel, own_bi, rx_param->channel,
(const u8 *)&rx_param->action_frm->u.public_action.v, dpp_data, len); (const u8 *)&rx_param->action_frm->u.public_action.v, dpp_data, len);
os_memcpy(s_dpp_ctx.dpp_auth->peer_mac_addr, rx_param->sa, ETH_ALEN); os_memcpy(s_dpp_ctx.dpp_auth->peer_mac_addr, rx_param->sa, ETH_ALEN);
esp_send_action_frame(rx_param->sa, wpabuf_head(s_dpp_ctx.dpp_auth->resp_msg), esp_send_action_frame(rx_param->sa, wpabuf_head(s_dpp_ctx.dpp_auth->resp_msg),
wpabuf_len(s_dpp_ctx.dpp_auth->resp_msg), wpabuf_len(s_dpp_ctx.dpp_auth->resp_msg),
rx_param->channel, OFFCHAN_TX_WAIT_TIME); rx_param->channel, OFFCHAN_TX_WAIT_TIME);
eloop_cancel_timeout(esp_dpp_auth_conf_wait_timeout, NULL,NULL);
eloop_register_timeout(ESP_DPP_AUTH_TIMEOUT_SECS, 0, esp_dpp_auth_conf_wait_timeout,NULL, NULL);
return; return;
fail: fail:
esp_dpp_call_cb(ESP_SUPP_DPP_FAIL, (void *)rc); esp_dpp_call_cb(ESP_SUPP_DPP_FAIL, (void *)rc);
@@ -203,7 +227,7 @@ static int esp_dpp_handle_config_obj(struct dpp_authentication *auth,
wpa_printf(MSG_INFO, DPP_EVENT_CONNECTOR "%s", wpa_printf(MSG_INFO, DPP_EVENT_CONNECTOR "%s",
conf->connector); conf->connector);
} }
s_dpp_stop_listening = false; s_dpp_listen_in_progress = true;
esp_wifi_action_tx_req(WIFI_OFFCHAN_TX_CANCEL, 0, 0, NULL); esp_wifi_action_tx_req(WIFI_OFFCHAN_TX_CANCEL, 0, 0, NULL);
esp_dpp_call_cb(ESP_SUPP_DPP_CFG_RECVD, wifi_cfg); esp_dpp_call_cb(ESP_SUPP_DPP_CFG_RECVD, wifi_cfg);
@@ -234,6 +258,8 @@ static void esp_dpp_rx_auth_conf(struct action_rx_param *rx_param, uint8_t *dpp_
goto fail; goto fail;
} }
eloop_cancel_timeout(esp_dpp_auth_conf_wait_timeout, NULL, NULL);
if (dpp_auth_conf_rx(auth, (const u8 *)&public_action->v, if (dpp_auth_conf_rx(auth, (const u8 *)&public_action->v,
dpp_data, len) < 0) { dpp_data, len) < 0) {
wpa_printf(MSG_DEBUG, "DPP: Authentication failed"); wpa_printf(MSG_DEBUG, "DPP: Authentication failed");
@@ -283,7 +309,7 @@ static void gas_query_resp_rx(struct action_rx_param *rx_param)
int i, res; int i, res;
if (pos[1] == WLAN_EID_VENDOR_SPECIFIC && pos[2] == 5 && if (pos[1] == WLAN_EID_VENDOR_SPECIFIC && pos[2] == 5 &&
WPA_GET_BE24(&pos[3]) == OUI_WFA && pos[6] == 0x1a && pos[7] == 1) { WPA_GET_BE24(&pos[3]) == OUI_WFA && pos[6] == 0x1a && pos[7] == 1 && auth) {
if (dpp_conf_resp_rx(auth, resp, rx_param->vendor_data_len - 2) < 0) { if (dpp_conf_resp_rx(auth, resp, rx_param->vendor_data_len - 2) < 0) {
wpa_printf(MSG_DEBUG, "DPP: Configuration attempt failed"); wpa_printf(MSG_DEBUG, "DPP: Configuration attempt failed");
goto fail; goto fail;
@@ -319,7 +345,7 @@ static void esp_dpp_rx_action(struct action_rx_param *rx_param)
(size_t)(public_action->v.pa_vendor_spec.vendor_data - (size_t)(public_action->v.pa_vendor_spec.vendor_data -
(u8 *)rx_param->action_frm); (u8 *)rx_param->action_frm);
if (!s_dpp_stop_listening) { if (s_dpp_listen_in_progress) {
esp_supp_dpp_stop_listen(); esp_supp_dpp_stop_listen();
} }
@@ -356,6 +382,21 @@ static void esp_dpp_task(void *pvParameters )
switch (evt->id) { switch (evt->id) {
case SIG_DPP_DEL_TASK: case SIG_DPP_DEL_TASK:
struct dpp_bootstrap_params_t *params = &s_dpp_ctx.bootstrap_params;
eloop_cancel_timeout(esp_dpp_auth_conf_wait_timeout, NULL, NULL);
if (params->info) {
os_free(params->info);
params->info = NULL;
}
if (s_dpp_ctx.dpp_global) {
dpp_global_deinit(s_dpp_ctx.dpp_global);
s_dpp_ctx.dpp_global = NULL;
}
if (s_dpp_ctx.dpp_auth) {
dpp_auth_deinit(s_dpp_ctx.dpp_auth);
s_dpp_ctx.dpp_auth = NULL;
}
task_del = true; task_del = true;
break; break;
@@ -380,14 +421,20 @@ static void esp_dpp_task(void *pvParameters )
struct dpp_bootstrap_params_t *p = &s_dpp_ctx.bootstrap_params; struct dpp_bootstrap_params_t *p = &s_dpp_ctx.bootstrap_params;
static int counter; static int counter;
int channel; int channel;
esp_err_t ret = 0;
if (p->num_chan <= 0) { if (p->num_chan <= 0) {
wpa_printf(MSG_ERROR, "Listen channel not set"); wpa_printf(MSG_ERROR, "Listen channel not set");
break; break;
} }
channel = p->chan_list[counter++ % p->num_chan]; channel = p->chan_list[counter++ % p->num_chan];
esp_wifi_remain_on_channel(WIFI_IF_STA, WIFI_ROC_REQ, channel, ret = esp_wifi_remain_on_channel(WIFI_IF_STA, WIFI_ROC_REQ, channel,
BOOTSTRAP_ROC_WAIT_TIME, s_action_rx_cb); BOOTSTRAP_ROC_WAIT_TIME, s_action_rx_cb);
if (ret != ESP_OK) {
wpa_printf(MSG_ERROR, "Failed ROC. error : 0x%x", ret);
break;
}
s_dpp_listen_in_progress = true;
} }
break; break;
@@ -460,13 +507,14 @@ static void offchan_event_handler(void *arg, esp_event_base_t event_base,
evt->status, (uint32_t)evt->context); evt->status, (uint32_t)evt->context);
if (evt->status) { if (evt->status) {
eloop_cancel_timeout(esp_dpp_auth_conf_wait_timeout, NULL, NULL);
esp_dpp_call_cb(ESP_SUPP_DPP_FAIL, (void *)ESP_ERR_DPP_TX_FAILURE); esp_dpp_call_cb(ESP_SUPP_DPP_FAIL, (void *)ESP_ERR_DPP_TX_FAILURE);
} }
} else if (event_id == WIFI_EVENT_ROC_DONE) { } else if (event_id == WIFI_EVENT_ROC_DONE) {
wifi_event_roc_done_t *evt = (wifi_event_roc_done_t *)event_data; wifi_event_roc_done_t *evt = (wifi_event_roc_done_t *)event_data;
if (!s_dpp_stop_listening && evt->context == (uint32_t)s_action_rx_cb) { if (s_dpp_listen_in_progress && evt->context == (uint32_t)s_action_rx_cb) {
esp_dpp_post_evt(SIG_DPP_LISTEN_NEXT_CHANNEL, 0); esp_dpp_post_evt(SIG_DPP_LISTEN_NEXT_CHANNEL, 0);
} }
} }
@@ -591,6 +639,11 @@ fail:
esp_err_t esp_supp_dpp_start_listen(void) esp_err_t esp_supp_dpp_start_listen(void)
{ {
if (s_dpp_listen_in_progress) {
wpa_printf(MSG_ERROR, "DPP: Failed to start listen as listen is already in progress.");
return ESP_FAIL;
}
if (!s_dpp_ctx.dpp_global || s_dpp_ctx.id < 1) { if (!s_dpp_ctx.dpp_global || s_dpp_ctx.id < 1) {
wpa_printf(MSG_ERROR, "DPP: failed to start listen as dpp not initialized or bootstrapped."); wpa_printf(MSG_ERROR, "DPP: failed to start listen as dpp not initialized or bootstrapped.");
return ESP_FAIL; return ESP_FAIL;
@@ -601,13 +654,12 @@ esp_err_t esp_supp_dpp_start_listen(void)
return ESP_ERR_INVALID_STATE; return ESP_ERR_INVALID_STATE;
} }
s_dpp_stop_listening = false;
return esp_dpp_post_evt(SIG_DPP_LISTEN_NEXT_CHANNEL, 0); return esp_dpp_post_evt(SIG_DPP_LISTEN_NEXT_CHANNEL, 0);
} }
void esp_supp_dpp_stop_listen(void) void esp_supp_dpp_stop_listen(void)
{ {
s_dpp_stop_listening = true; s_dpp_listen_in_progress = false;
esp_wifi_remain_on_channel(WIFI_IF_STA, WIFI_ROC_CANCEL, 0, 0, NULL); esp_wifi_remain_on_channel(WIFI_IF_STA, WIFI_ROC_CANCEL, 0, 0, NULL);
} }
@@ -618,6 +670,7 @@ bool is_dpp_enabled(void)
esp_err_t esp_supp_dpp_init(esp_supp_dpp_event_cb_t cb) esp_err_t esp_supp_dpp_init(esp_supp_dpp_event_cb_t cb)
{ {
esp_err_t ret = ESP_OK;
wifi_mode_t mode = 0; wifi_mode_t mode = 0;
if (esp_wifi_get_mode(&mode) || ((mode != WIFI_MODE_STA) && (mode != WIFI_MODE_APSTA))) { if (esp_wifi_get_mode(&mode) || ((mode != WIFI_MODE_STA) && (mode != WIFI_MODE_APSTA))) {
wpa_printf(MSG_ERROR, "DPP: failed to init as not in station mode."); wpa_printf(MSG_ERROR, "DPP: failed to init as not in station mode.");
@@ -632,31 +685,42 @@ esp_err_t esp_supp_dpp_init(esp_supp_dpp_event_cb_t cb)
wpa_printf(MSG_ERROR, "DPP: failed to init as init already done."); wpa_printf(MSG_ERROR, "DPP: failed to init as init already done.");
return ESP_FAIL; return ESP_FAIL;
} }
struct dpp_global_config cfg = {0};
int ret;
os_bzero(&s_dpp_ctx, sizeof(s_dpp_ctx)); os_bzero(&s_dpp_ctx, sizeof(s_dpp_ctx));
s_dpp_ctx.dpp_event_cb = cb; struct dpp_global_config cfg = {0};
cfg.cb_ctx = &s_dpp_ctx; cfg.cb_ctx = &s_dpp_ctx;
cfg.msg_ctx = &s_dpp_ctx; cfg.msg_ctx = &s_dpp_ctx;
s_dpp_ctx.dpp_global = dpp_global_init(&cfg); s_dpp_ctx.dpp_global = dpp_global_init(&cfg);
if (!s_dpp_ctx.dpp_global) {
s_dpp_stop_listening = false; wpa_printf(MSG_ERROR, "DPP: failed to allocate memory for dpp_global");
s_dpp_evt_queue = os_queue_create(3, sizeof(dpp_event_t)); ret = ESP_ERR_NO_MEM;
ret = os_task_create(esp_dpp_task, "dppT", DPP_TASK_STACK_SIZE, NULL, 2, &s_dpp_task_hdl); goto init_fail;
if (ret != TRUE) {
wpa_printf(MSG_ERROR, "DPP: failed to create task");
return ESP_FAIL;
} }
s_dpp_api_lock = os_recursive_mutex_create(); s_dpp_api_lock = os_recursive_mutex_create();
if (!s_dpp_api_lock) { if (!s_dpp_api_lock) {
esp_supp_dpp_deinit();
wpa_printf(MSG_ERROR, "DPP: dpp_init: failed to create DPP API lock"); wpa_printf(MSG_ERROR, "DPP: dpp_init: failed to create DPP API lock");
return ESP_ERR_NO_MEM; ret = ESP_ERR_NO_MEM;
goto init_fail;
} }
s_dpp_evt_queue = os_queue_create(3, sizeof(dpp_event_t));
if (!s_dpp_evt_queue) {
wpa_printf(MSG_ERROR, "DPP: dpp_init: failed to create DPP API queue");
ret = ESP_ERR_NO_MEM;
goto init_fail;
}
ret = os_task_create(esp_dpp_task, "dppT", DPP_TASK_STACK_SIZE, NULL, 2, &s_dpp_task_hdl);
if (ret != TRUE) {
wpa_printf(MSG_ERROR, "DPP: failed to create task");
ret = ESP_ERR_NO_MEM;
goto init_fail;
}
s_dpp_listen_in_progress = false;
s_dpp_ctx.dpp_event_cb = cb;
esp_event_handler_register(WIFI_EVENT, WIFI_EVENT_ACTION_TX_STATUS, esp_event_handler_register(WIFI_EVENT, WIFI_EVENT_ACTION_TX_STATUS,
&offchan_event_handler, NULL); &offchan_event_handler, NULL);
esp_event_handler_register(WIFI_EVENT, WIFI_EVENT_ROC_DONE, esp_event_handler_register(WIFI_EVENT, WIFI_EVENT_ROC_DONE,
@@ -665,25 +729,32 @@ esp_err_t esp_supp_dpp_init(esp_supp_dpp_event_cb_t cb)
wpa_printf(MSG_INFO, "esp_dpp_task prio:%d, stack:%d", 2, DPP_TASK_STACK_SIZE); wpa_printf(MSG_INFO, "esp_dpp_task prio:%d, stack:%d", 2, DPP_TASK_STACK_SIZE);
return ESP_OK; return ESP_OK;
init_fail:
if (s_dpp_ctx.dpp_global) {
dpp_global_deinit(s_dpp_ctx.dpp_global);
s_dpp_ctx.dpp_global = NULL;
}
if (s_dpp_api_lock) {
os_mutex_delete(s_dpp_api_lock);
s_dpp_api_lock = NULL;
}
if (s_dpp_evt_queue) {
os_queue_delete(s_dpp_evt_queue);
s_dpp_evt_queue = NULL;
}
return ret;
} }
void esp_supp_dpp_deinit(void) void esp_supp_dpp_deinit(void)
{ {
struct dpp_bootstrap_params_t *params = &s_dpp_ctx.bootstrap_params;
if (params->info) {
os_free(params->info);
params->info = NULL;
}
esp_event_handler_unregister(WIFI_EVENT, WIFI_EVENT_ACTION_TX_STATUS, esp_event_handler_unregister(WIFI_EVENT, WIFI_EVENT_ACTION_TX_STATUS,
&offchan_event_handler); &offchan_event_handler);
esp_event_handler_unregister(WIFI_EVENT, WIFI_EVENT_ROC_DONE, esp_event_handler_unregister(WIFI_EVENT, WIFI_EVENT_ROC_DONE,
&offchan_event_handler); &offchan_event_handler);
s_dpp_auth_retries = 0;
if (s_dpp_ctx.dpp_global) { if (s_dpp_ctx.dpp_global) {
dpp_global_deinit(s_dpp_ctx.dpp_global); if (esp_dpp_post_evt(SIG_DPP_DEL_TASK, 0)) {
s_dpp_ctx.dpp_global = NULL; wpa_printf(MSG_ERROR, "DPP Deinit Failed");
esp_dpp_post_evt(SIG_DPP_DEL_TASK, 0); }
} }
} }
#endif #endif

View File

@@ -158,9 +158,11 @@ void wps_task(void *pvParameters )
if (e->sig == SIG_WPS_ENABLE) { if (e->sig == SIG_WPS_ENABLE) {
param->ret = wifi_wps_enable_internal((esp_wps_config_t *)(param->arg)); param->ret = wifi_wps_enable_internal((esp_wps_config_t *)(param->arg));
} else if (e->sig == SIG_WPS_DISABLE) { } else if (e->sig == SIG_WPS_DISABLE) {
DATA_MUTEX_TAKE();
param->ret = wifi_wps_disable_internal(); param->ret = wifi_wps_disable_internal();
del_task = true; del_task = true;
s_wps_task_hdl = NULL; s_wps_task_hdl = NULL;
DATA_MUTEX_GIVE();
} else { } else {
param->ret = wifi_station_wps_start(); param->ret = wifi_station_wps_start();
} }
@@ -221,6 +223,12 @@ int wps_post(uint32_t sig, uint32_t par)
wpa_printf(MSG_DEBUG, "wps post: sig=%" PRId32 " cnt=%d", sig, s_wps_sig_cnt[sig]); wpa_printf(MSG_DEBUG, "wps post: sig=%" PRId32 " cnt=%d", sig, s_wps_sig_cnt[sig]);
DATA_MUTEX_TAKE(); DATA_MUTEX_TAKE();
if (!s_wps_task_hdl) {
wpa_printf(MSG_DEBUG, "wps post: sig=%" PRId32 " failed as wps task has been deinited", sig);
DATA_MUTEX_GIVE();
return ESP_FAIL;
}
if (s_wps_sig_cnt[sig]) { if (s_wps_sig_cnt[sig]) {
wpa_printf(MSG_DEBUG, "wps post: sig=%" PRId32 " processing", sig); wpa_printf(MSG_DEBUG, "wps post: sig=%" PRId32 " processing", sig);
DATA_MUTEX_GIVE(); DATA_MUTEX_GIVE();
@@ -1710,12 +1718,6 @@ int wps_task_deinit(void)
wps_rxq_deinit(); wps_rxq_deinit();
} }
if (s_wps_data_lock) {
os_semphr_delete(s_wps_data_lock);
s_wps_data_lock = NULL;
wpa_printf(MSG_DEBUG, "wps task deinit: free data lock");
}
return ESP_OK; return ESP_OK;
} }
@@ -1727,10 +1729,12 @@ int wps_task_init(void)
*/ */
wps_task_deinit(); wps_task_deinit();
s_wps_data_lock = os_recursive_mutex_create();
if (!s_wps_data_lock) { if (!s_wps_data_lock) {
wpa_printf(MSG_ERROR, "wps task init: failed to alloc data lock"); s_wps_data_lock = os_recursive_mutex_create();
goto _wps_no_mem; if (!s_wps_data_lock) {
wpa_printf(MSG_ERROR, "wps task init: failed to alloc data lock");
goto _wps_no_mem;
}
} }
s_wps_api_sem = os_semphr_create(1, 0); s_wps_api_sem = os_semphr_create(1, 0);
@@ -1827,6 +1831,11 @@ int esp_wifi_wps_enable(const esp_wps_config_t *config)
return ESP_ERR_WIFI_MODE; return ESP_ERR_WIFI_MODE;
} }
if (is_dpp_enabled()) {
wpa_printf(MSG_ERROR, "wps enabled failed since DPP is initialized");
return ESP_FAIL;
}
API_MUTEX_TAKE(); API_MUTEX_TAKE();
if (s_wps_enabled) { if (s_wps_enabled) {
if (sm && os_memcmp(sm->identity, WSC_ID_REGISTRAR, sm->identity_len) == 0) { if (sm && os_memcmp(sm->identity, WSC_ID_REGISTRAR, sm->identity_len) == 0) {
@@ -1879,10 +1888,6 @@ int wifi_wps_enable_internal(const esp_wps_config_t *config)
wpa_printf(MSG_ERROR, "wps enable: invalid wps type"); wpa_printf(MSG_ERROR, "wps enable: invalid wps type");
return ESP_ERR_WIFI_WPS_TYPE; return ESP_ERR_WIFI_WPS_TYPE;
} }
if (is_dpp_enabled()) {
wpa_printf(MSG_ERROR, "wps enabled failed since DPP is initialized");
return ESP_FAIL;
}
wpa_printf(MSG_DEBUG, "Set factory information."); wpa_printf(MSG_DEBUG, "Set factory information.");
ret = wps_set_factory_info(config); ret = wps_set_factory_info(config);
if (ret != 0) { if (ret != 0) {
@@ -1908,6 +1913,11 @@ int wifi_wps_enable_internal(const esp_wps_config_t *config)
int wifi_wps_disable_internal(void) int wifi_wps_disable_internal(void)
{ {
wps_set_status(WPS_STATUS_DISABLE); wps_set_status(WPS_STATUS_DISABLE);
/* Call wps_delete_timer to delete all WPS timer, no timer will call wps_post()
* to post message to wps_task once this function returns.
*/
wps_delete_timer();
wifi_station_wps_deinit(); wifi_station_wps_deinit();
return ESP_OK; return ESP_OK;
} }
@@ -1935,11 +1945,6 @@ int esp_wifi_wps_disable(void)
wpa_printf(MSG_INFO, "wifi_wps_disable"); wpa_printf(MSG_INFO, "wifi_wps_disable");
wps_set_type(WPS_TYPE_DISABLE); /* Notify WiFi task */ wps_set_type(WPS_TYPE_DISABLE); /* Notify WiFi task */
/* Call wps_delete_timer to delete all WPS timer, no timer will call wps_post()
* to post message to wps_task once this function returns.
*/
wps_delete_timer();
#ifdef USE_WPS_TASK #ifdef USE_WPS_TASK
ret = wps_post_block(SIG_WPS_DISABLE, 0); ret = wps_post_block(SIG_WPS_DISABLE, 0);
#else #else