Merge "qcacmn: Fix stability caused by unwanted recursive calls in serialization"
This commit is contained in:

committad av
Gerrit - the friendly Code Review server

incheckning
458de35c6d
@@ -203,9 +203,12 @@ wlan_serialization_request(struct wlan_serialization_command *cmd)
|
|||||||
{
|
{
|
||||||
bool is_active_cmd_allowed;
|
bool is_active_cmd_allowed;
|
||||||
QDF_STATUS status;
|
QDF_STATUS status;
|
||||||
|
enum wlan_serialization_status serialization_status;
|
||||||
uint8_t comp_id;
|
uint8_t comp_id;
|
||||||
struct wlan_serialization_psoc_priv_obj *ser_soc_obj;
|
struct wlan_serialization_psoc_priv_obj *ser_soc_obj;
|
||||||
union wlan_serialization_rules_info info;
|
union wlan_serialization_rules_info info;
|
||||||
|
struct wlan_serialization_pdev_priv_obj *ser_pdev_obj = NULL;
|
||||||
|
struct wlan_objmgr_pdev *pdev = NULL;
|
||||||
|
|
||||||
serialization_enter();
|
serialization_enter();
|
||||||
if (!cmd) {
|
if (!cmd) {
|
||||||
@@ -224,6 +227,18 @@ wlan_serialization_request(struct wlan_serialization_command *cmd)
|
|||||||
return WLAN_SER_CMD_DENIED_UNSPECIFIED;
|
return WLAN_SER_CMD_DENIED_UNSPECIFIED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pdev = wlan_serialization_get_pdev_from_cmd(cmd);
|
||||||
|
if (!pdev) {
|
||||||
|
serialization_err("pdev is invalid");
|
||||||
|
return WLAN_SER_CMD_DENIED_UNSPECIFIED;
|
||||||
|
}
|
||||||
|
|
||||||
|
ser_pdev_obj = wlan_objmgr_pdev_get_comp_private_obj(pdev,
|
||||||
|
WLAN_UMAC_COMP_SERIALIZATION);
|
||||||
|
if (!ser_pdev_obj) {
|
||||||
|
serialization_err("Invalid ser_pdev_obj");
|
||||||
|
return WLAN_SER_CMD_DENIED_UNSPECIFIED;
|
||||||
|
}
|
||||||
/*
|
/*
|
||||||
* Get Component Info callback by calling
|
* Get Component Info callback by calling
|
||||||
* each registered module
|
* each registered module
|
||||||
@@ -240,7 +255,11 @@ wlan_serialization_request(struct wlan_serialization_command *cmd)
|
|||||||
}
|
}
|
||||||
|
|
||||||
is_active_cmd_allowed = wlan_serialization_is_active_cmd_allowed(cmd);
|
is_active_cmd_allowed = wlan_serialization_is_active_cmd_allowed(cmd);
|
||||||
return wlan_serialization_enqueue_cmd(cmd, is_active_cmd_allowed);
|
serialization_status = wlan_serialization_enqueue_cmd(
|
||||||
|
cmd, is_active_cmd_allowed);
|
||||||
|
if (WLAN_SER_CMD_ACTIVE == serialization_status)
|
||||||
|
wlan_serialization_activate_cmd(cmd->cmd_type, ser_pdev_obj);
|
||||||
|
return serialization_status;
|
||||||
}
|
}
|
||||||
|
|
||||||
enum wlan_serialization_cmd_status
|
enum wlan_serialization_cmd_status
|
||||||
|
@@ -73,9 +73,11 @@ void wlan_serialization_move_pending_to_active(
|
|||||||
serialization_err("Can't move cmd to activeQ id-%d type-%d",
|
serialization_err("Can't move cmd to activeQ id-%d type-%d",
|
||||||
cmd_list->cmd.cmd_id, cmd_list->cmd.cmd_type);
|
cmd_list->cmd.cmd_id, cmd_list->cmd.cmd_type);
|
||||||
return;
|
return;
|
||||||
}
|
} else {
|
||||||
wlan_serialization_put_back_to_global_list(pending_queue,
|
wlan_serialization_put_back_to_global_list(pending_queue,
|
||||||
ser_pdev_obj, cmd_list);
|
ser_pdev_obj, cmd_list);
|
||||||
|
wlan_serialization_activate_cmd(cmd_type, ser_pdev_obj);
|
||||||
|
}
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@@ -77,43 +77,80 @@ wlan_serialization_add_cmd_to_given_queue(qdf_list_t *queue,
|
|||||||
return WLAN_SER_CMD_DENIED_UNSPECIFIED;
|
return WLAN_SER_CMD_DENIED_UNSPECIFIED;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (is_cmd_for_active_queue) {
|
if (is_cmd_for_active_queue)
|
||||||
/*
|
|
||||||
* command is already pushed to active queue above
|
|
||||||
* now start the timer and notify requestor
|
|
||||||
*/
|
|
||||||
wlan_serialization_find_and_start_timer(psoc,
|
|
||||||
&cmd_list->cmd);
|
|
||||||
if (cmd_list->cmd.cmd_cb) {
|
|
||||||
/*
|
|
||||||
* Remember that serialization module may send
|
|
||||||
* this callback in same context through which it
|
|
||||||
* received the serialization request. Due to which
|
|
||||||
* it is caller's responsibility to ensure acquiring
|
|
||||||
* and releasing its own lock appropriately.
|
|
||||||
*/
|
|
||||||
qdf_status = cmd_list->cmd.cmd_cb(&cmd_list->cmd,
|
|
||||||
WLAN_SER_CB_ACTIVATE_CMD);
|
|
||||||
if (qdf_status != QDF_STATUS_SUCCESS) {
|
|
||||||
wlan_serialization_find_and_stop_timer(psoc,
|
|
||||||
&cmd_list->cmd);
|
|
||||||
cmd_list->cmd.cmd_cb(&cmd_list->cmd,
|
|
||||||
WLAN_SER_CB_RELEASE_MEM_CMD);
|
|
||||||
wlan_serialization_put_back_to_global_list(
|
|
||||||
queue, ser_pdev_obj, cmd_list);
|
|
||||||
wlan_serialization_move_pending_to_active(
|
|
||||||
cmd_list->cmd.cmd_type,
|
|
||||||
ser_pdev_obj);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
status = WLAN_SER_CMD_ACTIVE;
|
status = WLAN_SER_CMD_ACTIVE;
|
||||||
} else {
|
else
|
||||||
status = WLAN_SER_CMD_PENDING;
|
status = WLAN_SER_CMD_PENDING;
|
||||||
}
|
|
||||||
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void wlan_serialization_activate_cmd(enum wlan_serialization_cmd_type cmd_type,
|
||||||
|
struct wlan_serialization_pdev_priv_obj *ser_pdev_obj)
|
||||||
|
{
|
||||||
|
QDF_STATUS qdf_status = QDF_STATUS_SUCCESS;
|
||||||
|
qdf_list_t *queue = NULL;
|
||||||
|
qdf_list_node_t *nnode = NULL;
|
||||||
|
struct wlan_serialization_command_list *cmd_list = NULL;
|
||||||
|
struct wlan_objmgr_psoc *psoc = NULL;
|
||||||
|
|
||||||
|
if (cmd_type < WLAN_SER_CMD_NONSCAN)
|
||||||
|
queue = &ser_pdev_obj->active_scan_list;
|
||||||
|
else
|
||||||
|
queue = &ser_pdev_obj->active_list;
|
||||||
|
if (qdf_list_empty(queue)) {
|
||||||
|
serialization_err("nothing in active queue");
|
||||||
|
QDF_ASSERT(0);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (QDF_STATUS_SUCCESS != qdf_list_peek_front(queue, &nnode)) {
|
||||||
|
serialization_err("can't read from active queue");
|
||||||
|
serialization_debug("cmd_type - %d", cmd_type);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
cmd_list = qdf_container_of(nnode,
|
||||||
|
struct wlan_serialization_command_list, node);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* command is already pushed to active queue above
|
||||||
|
* now start the timer and notify requestor
|
||||||
|
*/
|
||||||
|
wlan_serialization_find_and_start_timer(psoc,
|
||||||
|
&cmd_list->cmd);
|
||||||
|
if (cmd_list && cmd_list->cmd.cmd_cb) {
|
||||||
|
if (cmd_list->cmd.vdev) {
|
||||||
|
psoc = wlan_vdev_get_psoc(cmd_list->cmd.vdev);
|
||||||
|
if (psoc == NULL) {
|
||||||
|
serialization_err("invalid psoc");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
serialization_err("invalid cmd.vdev");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
* Remember that serialization module may send
|
||||||
|
* this callback in same context through which it
|
||||||
|
* received the serialization request. Due to which
|
||||||
|
* it is caller's responsibility to ensure acquiring
|
||||||
|
* and releasing its own lock appropriately.
|
||||||
|
*/
|
||||||
|
qdf_status = cmd_list->cmd.cmd_cb(&cmd_list->cmd,
|
||||||
|
WLAN_SER_CB_ACTIVATE_CMD);
|
||||||
|
if (qdf_status != QDF_STATUS_SUCCESS) {
|
||||||
|
wlan_serialization_find_and_stop_timer(psoc,
|
||||||
|
&cmd_list->cmd);
|
||||||
|
cmd_list->cmd.cmd_cb(&cmd_list->cmd,
|
||||||
|
WLAN_SER_CB_RELEASE_MEM_CMD);
|
||||||
|
wlan_serialization_put_back_to_global_list(
|
||||||
|
queue, ser_pdev_obj, cmd_list);
|
||||||
|
wlan_serialization_move_pending_to_active(
|
||||||
|
cmd_list->cmd.cmd_type,
|
||||||
|
ser_pdev_obj);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
enum wlan_serialization_status
|
enum wlan_serialization_status
|
||||||
wlan_serialization_enqueue_cmd(struct wlan_serialization_command *cmd,
|
wlan_serialization_enqueue_cmd(struct wlan_serialization_command *cmd,
|
||||||
uint8_t is_cmd_for_active_queue)
|
uint8_t is_cmd_for_active_queue)
|
||||||
|
@@ -398,4 +398,14 @@ wlan_serialization_remove_all_cmd_from_queue(qdf_list_t *queue,
|
|||||||
bool wlan_serialization_is_cmd_present_queue(
|
bool wlan_serialization_is_cmd_present_queue(
|
||||||
struct wlan_serialization_command *cmd,
|
struct wlan_serialization_command *cmd,
|
||||||
uint8_t is_active_queue);
|
uint8_t is_active_queue);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* wlan_serialization_activate_cmd() - activate first cmd in active queue
|
||||||
|
* @cmd_type: Command Type
|
||||||
|
* @ser_pdev_obj: Serialization private pdev object
|
||||||
|
*
|
||||||
|
* Return: None
|
||||||
|
*/
|
||||||
|
void wlan_serialization_activate_cmd(enum wlan_serialization_cmd_type cmd_type,
|
||||||
|
struct wlan_serialization_pdev_priv_obj *ser_pdev_obj);
|
||||||
#endif
|
#endif
|
||||||
|
Referens i nytt ärende
Block a user