qcacmn: Add API for cancellation of non-blocking cmd

Add API to support cancellation of a non-scan command to match with the
vdev and is a non-blocking serialization command.

Change-Id: I31556ea8f35b9caf314f10eba0f0f655e3fce806
CRs-Fixed: 2481935
This commit is contained in:
Santosh Anbu 2019-06-24 15:52:54 +05:30 • committed by nshrivas
commit f8ed4b9824
8 changed files with 109 additions and 18 deletions

View file

@ -237,6 +237,8 @@ enum wlan_serialization_cmd_type {
* @WLAN_SER_CANCEL_VDEV_NON_SCAN_CMD: Cancel all non scans on a given vdev
* @WLAN_SER_CANCEL_VDEV_NON_SCAN_CMD_TYPE: Cancel all non scans on a given vdev
* and matching cmd type
* @WLAN_SER_CANCEL_VDEV_NON_SCAN_NB_CMD: Cancel all non-blocking,
* non-scan commands of a given vdev
* @WLAN_SER_CANCEL_NON_SCAN_CMD: Cancel the given non scan command
*/
enum wlan_serialization_cancel_type {
@ -246,6 +248,7 @@ enum wlan_serialization_cancel_type {
WLAN_SER_CANCEL_PDEV_NON_SCAN_CMD,
WLAN_SER_CANCEL_VDEV_NON_SCAN_CMD,
WLAN_SER_CANCEL_VDEV_NON_SCAN_CMD_TYPE,
WLAN_SER_CANCEL_VDEV_NON_SCAN_NB_CMD,
WLAN_SER_CANCEL_NON_SCAN_CMD,
WLAN_SER_CANCEL_MAX,
};
@ -286,6 +289,18 @@ enum wlan_serialization_cmd_status {
WLAN_SER_CMD_NOT_FOUND,
};
/**
* enum wlan_ser_cmd_attr - Serialization cmd attribute
* @WLAN_SER_CMD_ATTR_NONE - No attribuate associated
* @WLAN_SER_CMD_ATTR_BLOCK - Blocking attribute
* @WLAN_SER_CMD_ATTR_NONBLOCK - Non-blocking attribute
*/
enum wlan_ser_cmd_attr {
WLAN_SER_CMD_ATTR_NONE,
WLAN_SER_CMD_ATTR_BLOCK,
WLAN_SER_CMD_ATTR_NONBLOCK,
};
/**
* struct wlan_serialization_command - Command to be serialized
* @wlan_serialization_cmd_type: Type of command

View file

@ -821,9 +821,11 @@ void wlan_serialization_purge_all_pdev_cmd(struct wlan_objmgr_pdev *pdev)
wlan_ser_cancel_scan_cmd(ser_pdev_obj, pdev, NULL, NULL,
WLAN_SER_CMD_SCAN, true);
wlan_ser_cancel_non_scan_cmd(ser_pdev_obj, pdev, NULL, NULL,
WLAN_SER_CMD_NONSCAN, false);
WLAN_SER_CMD_NONSCAN, false,
WLAN_SER_CMD_ATTR_NONE);
wlan_ser_cancel_non_scan_cmd(ser_pdev_obj, pdev, NULL, NULL,
WLAN_SER_CMD_NONSCAN, true);
WLAN_SER_CMD_NONSCAN, true,
WLAN_SER_CMD_ATTR_NONE);
}
static inline
@ -870,7 +872,8 @@ void wlan_serialization_purge_all_pending_cmd_by_vdev_id(
wlan_ser_cancel_scan_cmd(ser_pdev_obj, pdev, vdev, NULL,
WLAN_SER_CMD_SCAN, false);
wlan_ser_cancel_non_scan_cmd(ser_pdev_obj, pdev, vdev, NULL,
WLAN_SER_CMD_NONSCAN, false);
WLAN_SER_CMD_NONSCAN, false,
WLAN_SER_CMD_ATTR_NONE);
wlan_objmgr_vdev_release_ref(vdev, WLAN_SERIALIZATION_ID);
}

View file

@ -371,7 +371,8 @@ timer_failed:
wlan_serialization_cmd_cancel_handler(
ser_pdev_obj, &cmd_list->cmd,
NULL, NULL, cmd_list->cmd.cmd_type,
WLAN_SERIALIZATION_ACTIVE_QUEUE);
WLAN_SERIALIZATION_ACTIVE_QUEUE,
WLAN_SER_CMD_ATTR_NONE);
error:
return status;
}
@ -847,7 +848,8 @@ wlan_serialization_cmd_cancel_handler(
struct wlan_ser_pdev_obj *ser_obj,
struct wlan_serialization_command *cmd,
struct wlan_objmgr_pdev *pdev, struct wlan_objmgr_vdev *vdev,
enum wlan_serialization_cmd_type cmd_type, uint8_t queue_type)
enum wlan_serialization_cmd_type cmd_type, uint8_t queue_type,
enum wlan_ser_cmd_attr cmd_attr)
{
enum wlan_serialization_cmd_status active_status =
WLAN_SER_CMD_NOT_FOUND;
@ -871,7 +873,7 @@ wlan_serialization_cmd_cancel_handler(
else
active_status = wlan_ser_cancel_non_scan_cmd(
ser_obj, pdev, vdev, cmd,
cmd_type, true);
cmd_type, true, cmd_attr);
}
if (queue_type & WLAN_SERIALIZATION_PENDING_QUEUE) {
@ -882,7 +884,7 @@ wlan_serialization_cmd_cancel_handler(
else
pending_status = wlan_ser_cancel_non_scan_cmd(
ser_obj, pdev, vdev, cmd,
cmd_type, false);
cmd_type, false, cmd_attr);
}
if (active_status == WLAN_SER_CMD_IN_ACTIVE_LIST &&
@ -931,37 +933,43 @@ wlan_serialization_find_and_cancel_cmd(
/* remove scan cmd which matches the given cmd struct */
status = wlan_serialization_cmd_cancel_handler(
ser_obj, cmd, NULL, NULL,
WLAN_SER_CMD_SCAN, queue_type);
WLAN_SER_CMD_SCAN, queue_type,
WLAN_SER_CMD_ATTR_NONE);
break;
case WLAN_SER_CANCEL_PDEV_SCANS:
/* remove all scan cmds which matches the pdev object */
status = wlan_serialization_cmd_cancel_handler(
ser_obj, NULL, pdev, NULL,
WLAN_SER_CMD_SCAN, queue_type);
WLAN_SER_CMD_SCAN, queue_type,
WLAN_SER_CMD_ATTR_NONE);
break;
case WLAN_SER_CANCEL_VDEV_SCANS:
/* remove all scan cmds which matches the vdev object */
status = wlan_serialization_cmd_cancel_handler(
ser_obj, NULL, NULL, cmd->vdev,
WLAN_SER_CMD_SCAN, queue_type);
WLAN_SER_CMD_SCAN, queue_type,
WLAN_SER_CMD_ATTR_NONE);
break;
case WLAN_SER_CANCEL_NON_SCAN_CMD:
/* remove nonscan cmd which matches the given cmd */
status = wlan_serialization_cmd_cancel_handler(
ser_obj, cmd, NULL, NULL,
WLAN_SER_CMD_NONSCAN, queue_type);
WLAN_SER_CMD_NONSCAN, queue_type,
WLAN_SER_CMD_ATTR_NONE);
break;
case WLAN_SER_CANCEL_PDEV_NON_SCAN_CMD:
/* remove all non scan cmds which matches the pdev object */
status = wlan_serialization_cmd_cancel_handler(
ser_obj, NULL, pdev, NULL,
WLAN_SER_CMD_NONSCAN, queue_type);
WLAN_SER_CMD_NONSCAN, queue_type,
WLAN_SER_CMD_ATTR_NONE);
break;
case WLAN_SER_CANCEL_VDEV_NON_SCAN_CMD:
/* remove all non scan cmds which matches the vdev object */
status = wlan_serialization_cmd_cancel_handler(
ser_obj, NULL, NULL, cmd->vdev,
WLAN_SER_CMD_NONSCAN, queue_type);
WLAN_SER_CMD_NONSCAN, queue_type,
WLAN_SER_CMD_ATTR_NONE);
break;
case WLAN_SER_CANCEL_VDEV_NON_SCAN_CMD_TYPE:
/*
@ -970,7 +978,18 @@ wlan_serialization_find_and_cancel_cmd(
*/
status = wlan_serialization_cmd_cancel_handler(
ser_obj, NULL, NULL, cmd->vdev,
cmd->cmd_type, queue_type);
cmd->cmd_type, queue_type,
WLAN_SER_CMD_ATTR_NONE);
break;
case WLAN_SER_CANCEL_VDEV_NON_SCAN_NB_CMD:
/*
* remove all non-blocking non-scan cmds which matches the given
* vdev
*/
status = wlan_serialization_cmd_cancel_handler(
ser_obj, NULL, NULL, cmd->vdev,
WLAN_SER_CMD_NONSCAN, queue_type,
WLAN_SER_CMD_ATTR_NONBLOCK);
break;
default:
ser_err("Invalid request");

View file

@ -205,6 +205,7 @@ wlan_serialization_find_and_cancel_cmd(
* @vdev: pointer to vdev
* @cmd_type: pointer to cmd_type
* @queue_type: If active queue or pending queue
* @cmd_attr: Attrbute to indicate a blocking or a non-blocking command
*
* This API will decide from which queue, command needs to be cancelled
* and pass that queue and other parameter required to cancel the command
@ -219,5 +220,6 @@ wlan_serialization_cmd_cancel_handler(
struct wlan_objmgr_pdev *pdev,
struct wlan_objmgr_vdev *vdev,
enum wlan_serialization_cmd_type cmd_type,
uint8_t queue_type);
uint8_t queue_type,
enum wlan_ser_cmd_attr cmd_attr);
#endif

View file

@ -461,7 +461,7 @@ wlan_ser_cancel_non_scan_cmd(
struct wlan_objmgr_pdev *pdev, struct wlan_objmgr_vdev *vdev,
struct wlan_serialization_command *cmd,
enum wlan_serialization_cmd_type cmd_type,
uint8_t is_active_queue)
uint8_t is_active_queue, enum wlan_ser_cmd_attr cmd_attr)
{
qdf_list_t *pdev_queue;
qdf_list_t *vdev_queue;
@ -540,6 +540,18 @@ wlan_ser_cancel_non_scan_cmd(
continue;
}
/*
* If a non-blocking cmd is required to be cancelled, but
* the nnode cmd is a blocking cmd then continue with the
* next command in the list else proceed with cmd cancel.
*/
if ((cmd_attr == WLAN_SER_CMD_ATTR_NONBLOCK) &&
wlan_serialization_match_cmd_blocking(nnode,
WLAN_SER_PDEV_NODE)) {
pnode = nnode;
continue;
}
/*
* active queue can't be removed directly, requester needs to
* wait for active command response and send remove request for

View file

@ -1,5 +1,5 @@
/*
* Copyright (c) 2017-2018 The Linux Foundation. All rights reserved.
* Copyright (c) 2017-2019 The Linux Foundation. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -115,6 +115,8 @@ wlan_ser_remove_non_scan_cmd(struct wlan_ser_pdev_obj *ser_pdev_obj,
* @cmd_type: Serialization command type to be cancelled
* @is_active_queue: If the cmd has to be removed from active queue or pending
* queue
* @cmd_attr: Indicate the attribute of the cmd to be cancelled
* i.e blocking/non-blocking
*
* Return: Status specifying the cancel of a command from the given queue
*/
@ -124,5 +126,6 @@ wlan_ser_cancel_non_scan_cmd(struct wlan_ser_pdev_obj *ser_obj,
struct wlan_objmgr_vdev *vdev,
struct wlan_serialization_command *cmd,
enum wlan_serialization_cmd_type cmd_type,
uint8_t is_active_queue);
uint8_t is_active_queue,
enum wlan_ser_cmd_attr cmd_attr);
#endif

View file

@ -775,6 +775,30 @@ bool wlan_serialization_match_cmd_pdev(qdf_list_node_t *nnode,
return match_found;
}
bool wlan_serialization_match_cmd_blocking(
qdf_list_node_t *nnode,
enum wlan_serialization_node node_type)
{
struct wlan_serialization_command_list *cmd_list = NULL;
bool match_found = false;
if (node_type == WLAN_SER_PDEV_NODE)
cmd_list =
qdf_container_of(nnode,
struct wlan_serialization_command_list,
pdev_node);
else
cmd_list =
qdf_container_of(nnode,
struct wlan_serialization_command_list,
vdev_node);
if (cmd_list->cmd.is_blocking)
match_found = true;
return match_found;
}
qdf_list_node_t *
wlan_serialization_find_cmd(qdf_list_t *queue,
enum wlan_serialization_match_type match_type,

View file

@ -546,6 +546,19 @@ bool wlan_serialization_match_cmd_pdev(qdf_list_node_t *nnode,
struct wlan_objmgr_pdev *pdev,
enum wlan_serialization_node node_type);
/**
* wlan_serialization_match_cmd_blocking() - Check for a blocking cmd
* @nnode: The node on which the matching has to be done
* @node_type: Pdev node or vdev node
*
* This API will check if the give command of nnode is a blocking command.
*
* Return: True if blocking command, false otherwise.
*/
bool wlan_serialization_match_cmd_blocking(
qdf_list_node_t *nnode,
enum wlan_serialization_node node_type);
/**
* wlan_serialization_find_cmd() - Find the cmd matching the given criterias
* @cmd: Serialization command information