1  /*
2   * Copyright (c) 2017-2018 The Linux Foundation. All rights reserved.
3   *
4   * Permission to use, copy, modify, and/or distribute this software for
5   * any purpose with or without fee is hereby granted, provided that the
6   * above copyright notice and this permission notice appear in all
7   * copies.
8   *
9   * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
10   * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
11   * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
12   * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
13   * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
14   * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
15   * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
16   * PERFORMANCE OF THIS SOFTWARE.
17   */
18  /**
19   * DOC: wlan_serialization_queue.c
20   * This file defines the functions which deals with the
21   * serialization queue objects.
22   */
23  #include <wlan_objmgr_vdev_obj.h>
24  #include <wlan_objmgr_pdev_obj.h>
25  #include <wlan_objmgr_psoc_obj.h>
26  #include <qdf_list.h>
27  #include <qdf_status.h>
28  #include "wlan_serialization_api.h"
29  #include "wlan_serialization_main_i.h"
30  #include "wlan_serialization_utils_i.h"
31  #include "wlan_serialization_queue_i.h"
32  
wlan_serialization_get_pdev_queue_obj(struct wlan_ser_pdev_obj * pdev_obj,enum wlan_serialization_cmd_type cmd_type)33  struct wlan_serialization_pdev_queue *wlan_serialization_get_pdev_queue_obj(
34  		struct wlan_ser_pdev_obj *pdev_obj,
35  		enum wlan_serialization_cmd_type cmd_type)
36  {
37  	struct wlan_serialization_pdev_queue *pdev_queue = NULL;
38  
39  	if (cmd_type < WLAN_SER_CMD_NONSCAN)
40  		pdev_queue = &pdev_obj->pdev_q[SER_PDEV_QUEUE_COMP_SCAN];
41  	else
42  		pdev_queue = &pdev_obj->pdev_q[SER_PDEV_QUEUE_COMP_NON_SCAN];
43  
44  	return pdev_queue;
45  }
46  
wlan_serialization_get_vdev_queue_obj(struct wlan_ser_vdev_obj * vdev_obj,enum wlan_serialization_cmd_type cmd_type)47  struct wlan_serialization_vdev_queue *wlan_serialization_get_vdev_queue_obj(
48  		struct wlan_ser_vdev_obj *vdev_obj,
49  		enum wlan_serialization_cmd_type cmd_type)
50  {
51  	struct wlan_serialization_vdev_queue *vdev_queue = NULL;
52  
53  	vdev_queue = &vdev_obj->vdev_q[SER_VDEV_QUEUE_COMP_NON_SCAN];
54  
55  	return vdev_queue;
56  }
57  
wlan_serialization_get_list_from_pdev_queue(struct wlan_ser_pdev_obj * pdev_obj,enum wlan_serialization_cmd_type cmd_type,uint8_t is_active_cmd)58  qdf_list_t *wlan_serialization_get_list_from_pdev_queue(
59  		struct wlan_ser_pdev_obj *pdev_obj,
60  		enum wlan_serialization_cmd_type cmd_type,
61  		uint8_t is_active_cmd)
62  {
63  	struct wlan_serialization_pdev_queue *pdev_queue;
64  	qdf_list_t *queue = NULL;
65  
66  	pdev_queue = wlan_serialization_get_pdev_queue_obj(pdev_obj, cmd_type);
67  	if (is_active_cmd)
68  		queue = &pdev_queue->active_list;
69  	else
70  		queue = &pdev_queue->pending_list;
71  
72  	return queue;
73  }
74  
wlan_serialization_get_list_from_vdev_queue(struct wlan_ser_vdev_obj * vdev_obj,enum wlan_serialization_cmd_type cmd_type,uint8_t is_active_cmd)75  qdf_list_t *wlan_serialization_get_list_from_vdev_queue(
76  		struct wlan_ser_vdev_obj *vdev_obj,
77  		enum wlan_serialization_cmd_type cmd_type,
78  		uint8_t is_active_cmd)
79  {
80  	struct wlan_serialization_vdev_queue *vdev_queue;
81  	qdf_list_t *queue = NULL;
82  
83  	vdev_queue = wlan_serialization_get_vdev_queue_obj(vdev_obj, cmd_type);
84  	if (is_active_cmd)
85  		queue = &vdev_queue->active_list;
86  	else
87  		queue = &vdev_queue->pending_list;
88  
89  	return queue;
90  }
91  
92  enum wlan_serialization_status
wlan_serialization_add_cmd_to_pdev_queue(struct wlan_ser_pdev_obj * pdev_obj,struct wlan_serialization_command_list * cmd_list,uint8_t for_active_queue)93  wlan_serialization_add_cmd_to_pdev_queue(
94  		struct wlan_ser_pdev_obj *pdev_obj,
95  		struct wlan_serialization_command_list *cmd_list,
96  		uint8_t for_active_queue)
97  {
98  	qdf_list_t *queue;
99  	enum wlan_serialization_status status = WLAN_SER_CMD_DENIED_UNSPECIFIED;
100  
101  	if (!pdev_obj) {
102  		ser_err("invalid serialization pdev");
103  		status = WLAN_SER_CMD_DENIED_UNSPECIFIED;
104  		goto error;
105  	}
106  
107  	queue = wlan_serialization_get_list_from_pdev_queue(
108  			pdev_obj, cmd_list->cmd.cmd_type, for_active_queue);
109  
110  	status = wlan_serialization_add_cmd_to_queue(queue, cmd_list,
111  						     pdev_obj,
112  						     for_active_queue,
113  						     WLAN_SER_PDEV_NODE);
114  
115  error:
116  	return status;
117  }
118  
119  enum wlan_serialization_status
wlan_serialization_add_cmd_to_vdev_queue(struct wlan_ser_pdev_obj * pdev_obj,struct wlan_serialization_command_list * cmd_list,uint8_t for_active_queue)120  wlan_serialization_add_cmd_to_vdev_queue(
121  		struct wlan_ser_pdev_obj *pdev_obj,
122  		struct wlan_serialization_command_list *cmd_list,
123  		uint8_t for_active_queue)
124  {
125  	qdf_list_t *queue;
126  	enum wlan_serialization_status status;
127  	struct wlan_serialization_command *cmd;
128  	struct wlan_ser_vdev_obj *vdev_obj;
129  	struct wlan_serialization_vdev_queue *vdev_queue_obj;
130  
131  	cmd = &cmd_list->cmd;
132  
133  	vdev_obj = wlan_serialization_get_vdev_obj(
134  			wlan_serialization_get_vdev_from_cmd(cmd));
135  
136  	vdev_queue_obj =
137  			wlan_serialization_get_vdev_queue_obj(
138  				vdev_obj,
139  				cmd->cmd_type);
140  
141  	queue = wlan_serialization_get_list_from_vdev_queue(vdev_obj,
142  							    cmd->cmd_type,
143  							    for_active_queue);
144  
145  	status = wlan_serialization_add_cmd_to_queue(queue, cmd_list,
146  						     pdev_obj,
147  						     for_active_queue,
148  						     WLAN_SER_VDEV_NODE);
149  
150  	if (cmd->queue_disable)
151  		vdev_queue_obj->queue_disable = true;
152  
153  	return status;
154  }
155  
156  QDF_STATUS
wlan_serialization_remove_cmd_from_pdev_queue(struct wlan_ser_pdev_obj * pdev_obj,struct wlan_serialization_command_list ** pcmd_list,struct wlan_serialization_command * cmd,uint8_t is_active_queue)157  wlan_serialization_remove_cmd_from_pdev_queue(
158  		struct wlan_ser_pdev_obj *pdev_obj,
159  		struct wlan_serialization_command_list **pcmd_list,
160  		struct wlan_serialization_command *cmd,
161  		uint8_t is_active_queue)
162  {
163  	qdf_list_t *queue;
164  	QDF_STATUS status = QDF_STATUS_E_FAILURE;
165  
166  	if (!pdev_obj) {
167  		ser_err("Invalid pdev");
168  		return status;
169  	}
170  
171  	queue = wlan_serialization_get_list_from_pdev_queue(
172  			pdev_obj, cmd->cmd_type, is_active_queue);
173  
174  	status = wlan_serialization_remove_cmd_from_queue(queue, cmd,
175  							  pcmd_list,
176  							  pdev_obj,
177  							  WLAN_SER_PDEV_NODE);
178  
179  	return status;
180  }
181  
182  QDF_STATUS
wlan_serialization_remove_cmd_from_vdev_queue(struct wlan_ser_pdev_obj * pdev_obj,struct wlan_serialization_command_list ** pcmd_list,struct wlan_serialization_command * cmd,uint8_t is_active_queue)183  wlan_serialization_remove_cmd_from_vdev_queue(
184  		struct wlan_ser_pdev_obj *pdev_obj,
185  		struct wlan_serialization_command_list **pcmd_list,
186  		struct wlan_serialization_command *cmd,
187  		uint8_t is_active_queue)
188  {
189  	qdf_list_t *queue;
190  	QDF_STATUS status = QDF_STATUS_E_FAILURE;
191  	struct wlan_ser_vdev_obj *vdev_obj;
192  
193  	vdev_obj = wlan_serialization_get_vdev_obj(
194  			wlan_serialization_get_vdev_from_cmd(cmd));
195  
196  	queue = wlan_serialization_get_list_from_vdev_queue(vdev_obj,
197  							    cmd->cmd_type,
198  							    is_active_queue);
199  
200  	status = wlan_serialization_remove_cmd_from_queue(queue, cmd,
201  							  pcmd_list,
202  							  pdev_obj,
203  							  WLAN_SER_VDEV_NODE);
204  
205  	return status;
206  }
207  
208