1 /*
2  * Copyright (c) 2017-2020 The Linux Foundation. All rights reserved.
3  * Copyright (c) 2022-2024 Qualcomm Innovation Center, Inc. All rights reserved.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for
6  * any purpose with or without fee is hereby granted, provided that the
7  * above copyright notice and this permission notice appear in all
8  * copies.
9  *
10  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
11  * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
12  * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
13  * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
14  * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
15  * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
16  * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
17  * PERFORMANCE OF THIS SOFTWARE.
18  */
19 
20 /**
21  * DOC: contains scan cache entry api
22  */
23 
24 #ifndef _WLAN_SCAN_CACHE_DB_H_
25 #define _WLAN_SCAN_CACHE_DB_H_
26 
27 #include <scheduler_api.h>
28 #include <wlan_objmgr_psoc_obj.h>
29 #include <wlan_objmgr_pdev_obj.h>
30 #include <wlan_objmgr_vdev_obj.h>
31 #include <wlan_scan_public_structs.h>
32 
33 #define SCAN_HASH_SIZE 64
34 #define SCAN_GET_HASH(addr) \
35 	(((const uint8_t *)(addr))[QDF_MAC_ADDR_SIZE - 1] % SCAN_HASH_SIZE)
36 
37 #define ADJACENT_CHANNEL_RSSI_THRESHOLD -80
38 #define ADJACENT_CHANNEL_RSSI_DIFF_THRESHOLD 40
39 
40 /**
41  * struct scan_dbs - scan cache data base definition
42  * @num_entries: number of scan entries
43  * @scan_db_lock: lock for @scan_hash_tbl
44  * @scan_hash_tbl: link list of bssid hashed scan cache entries for a pdev
45  */
46 struct scan_dbs {
47 	uint32_t num_entries;
48 	qdf_spinlock_t scan_db_lock;
49 	qdf_list_t scan_hash_tbl[SCAN_HASH_SIZE];
50 };
51 
52 /**
53  * struct scan_bcn_probe_event - beacon/probe info
54  * @frm_type: frame type
55  * @rx_data: mgmt rx data
56  * @psoc: psoc pointer
57  * @save_rnr_info: save the RNR entries into RNR db
58  * @buf: rx frame
59  */
60 struct scan_bcn_probe_event {
61 	uint32_t frm_type;
62 	struct mgmt_rx_event_params *rx_data;
63 	struct wlan_objmgr_psoc *psoc;
64 	bool save_rnr_info;
65 	qdf_nbuf_t buf;
66 };
67 
68 /**
69  * scm_handle_bcn_probe() - Process beacon and probe rsp
70  * @msg: schedular msg with bcn info;
71  *
72  * API to handle the beacon/probe resp. msg->bodyptr will be consumed and freed
73  * by this func
74  *
75  * Return: QDF status.
76  */
77 QDF_STATUS scm_handle_bcn_probe(struct scheduler_msg *msg);
78 
79 /**
80  * __scm_handle_bcn_probe() - Process beacon and probe rsp
81  * @bcn: beacon info;
82  *
83  * API to handle the beacon/probe resp. bcn will be consumed and freed by this
84  * func
85  *
86  * Return: QDF status.
87  */
88 QDF_STATUS __scm_handle_bcn_probe(struct scan_bcn_probe_event *bcn);
89 
90 /**
91  * scm_age_out_entries() - Age out entries older than aging time
92  * @psoc: psoc pointer
93  * @scan_db: scan database
94  *
95  * Return: void.
96  */
97 void scm_age_out_entries(struct wlan_objmgr_psoc *psoc,
98 	struct scan_dbs *scan_db);
99 
100 /**
101  * scm_get_scan_result() - fetches scan result
102  * @pdev: pdev info
103  * @filter: Filters
104  *
105  * This function fetches scan result
106  *
107  * Return: scan list
108  */
109 qdf_list_t *scm_get_scan_result(struct wlan_objmgr_pdev *pdev,
110 	struct scan_filter *filter);
111 
112 /**
113  * scm_purge_scan_results() - purge the scan list
114  * @scan_result: scan list to be purged
115  *
116  * This function purge the temp scan list
117  *
118  * Return: QDF_STATUS
119  */
120 QDF_STATUS scm_purge_scan_results(qdf_list_t *scan_result);
121 
122 /**
123  * scm_update_scan_mlme_info() - updates scan entry with mlme data
124  * @pdev: pdev object
125  * @scan_entry: source scan entry to read mlme info
126  *
127  * This function updates scan db with scan_entry->mlme_info
128  *
129  * Return: QDF_STATUS
130  */
131 QDF_STATUS scm_update_scan_mlme_info(struct wlan_objmgr_pdev *pdev,
132 	struct scan_cache_entry *scan_entry);
133 
134 /**
135  * scm_flush_results() - flush scan entries matching the filter
136  * @pdev: vdev object
137  * @filter: filter to flush the scan entries
138  *
139  * Flush scan entries matching the filter.
140  *
141  * Return: QDF status.
142  */
143 QDF_STATUS scm_flush_results(struct wlan_objmgr_pdev *pdev,
144 	struct scan_filter *filter);
145 
146 /**
147  * scm_filter_valid_channel() - The Public API to filter scan result
148  * based on valid channel list
149  * @pdev: pdev object
150  * @chan_freq_list: valid channel frequency (in MHz) list
151  * @num_chan: number of valid channels
152  *
153  * The Public API to to filter scan result
154  * based on valid channel list.
155  *
156  * Return: void.
157  */
158 void scm_filter_valid_channel(struct wlan_objmgr_pdev *pdev,
159 	uint32_t *chan_freq_list, uint32_t num_chan);
160 
161 /**
162  * scm_iterate_scan_db() - function to iterate scan table
163  * @pdev: pdev object
164  * @func: iterator function pointer
165  * @arg: argument to be passed to func()
166  *
167  * API, this API iterates scan table and invokes func
168  * on each scan enetry by passing scan entry and arg.
169  *
170  * Return: QDF_STATUS
171  */
172 QDF_STATUS
173 scm_iterate_scan_db(struct wlan_objmgr_pdev *pdev,
174 	scan_iterator_func func, void *arg);
175 
176 /**
177  * scm_scan_register_bcn_cb() - API to register api to indicate bcn/probe
178  * as soon as they are received
179  * @psoc: psoc
180  * @cb: callback to be registered
181  * @type: Type of callback to be registered
182  *
183  * Return: enum scm_scan_status
184  */
185 QDF_STATUS scm_scan_register_bcn_cb(struct wlan_objmgr_psoc *psoc,
186 	update_beacon_cb cb, enum scan_cb_type type);
187 
188 /**
189  * scm_scan_register_mbssid_cb() - API to register api to handle bcn/probe
190  * as soon as they are generated
191  * @psoc: psoc object
192  * @cb: callback to be registered
193  *
194  * Return: QDF_STATUS
195  */
196 QDF_STATUS scm_scan_register_mbssid_cb(struct wlan_objmgr_psoc *psoc,
197 				       update_mbssid_bcn_prb_rsp cb);
198 
199 /**
200  * scm_reset_scan_chan_info() - API to reset the scan channel info
201  * @psoc: psoc object
202  * @pdev_id: pdev id of which info need to be reset
203  *
204  * Return: void
205  */
206 void scm_reset_scan_chan_info(struct wlan_objmgr_psoc *psoc, uint8_t pdev_id);
207 
208 /**
209  * scm_db_init() - API to init scan db
210  * @psoc: psoc
211  *
212  * Return: QDF_STATUS
213  */
214 QDF_STATUS scm_db_init(struct wlan_objmgr_psoc *psoc);
215 
216 /**
217  * scm_db_deinit() - API to deinit scan db
218  * @psoc: psoc
219  *
220  * Return: QDF_STATUS
221  */
222 QDF_STATUS scm_db_deinit(struct wlan_objmgr_psoc *psoc);
223 
224 #ifdef FEATURE_6G_SCAN_CHAN_SORT_ALGO
225 
226 /**
227  * scm_get_rnr_channel_db() - API to get rnr db
228  * @psoc: psoc
229  *
230  * Return: rnr db
231  */
232 struct channel_list_db *scm_get_rnr_channel_db(struct wlan_objmgr_psoc *psoc);
233 
234 /**
235  * scm_get_chan_meta() - API to return channel meta
236  * @psoc: psoc
237  * @chan_freq: channel frequency
238  *
239  * Return: channel meta information
240  */
241 struct meta_rnr_channel *scm_get_chan_meta(struct wlan_objmgr_psoc *psoc,
242 					   uint32_t chan_freq);
243 
244 /**
245  * scm_channel_list_db_init() - API to init scan list priority list db
246  * @psoc: psoc
247  *
248  * Return: QDF_STATUS
249  */
250 QDF_STATUS scm_channel_list_db_init(struct wlan_objmgr_psoc *psoc);
251 
252 /**
253  * scm_channel_list_db_deinit() - API to deinit scan list priority list db
254  * @psoc: psoc
255  *
256  * Return: QDF_STATUS
257  */
258 QDF_STATUS scm_channel_list_db_deinit(struct wlan_objmgr_psoc *psoc);
259 
260 /**
261  * scm_rnr_db_flush() - API to flush rnr entries
262  * @psoc: psoc
263  *
264  * Return: QDF_STATUS
265  */
266 QDF_STATUS scm_rnr_db_flush(struct wlan_objmgr_psoc *psoc);
267 
268 /**
269  * scm_update_rnr_from_scan_cache() - API to update rnr info from scan cache
270  * @pdev: pdev
271  *
272  * Return: void
273  */
274 void scm_update_rnr_from_scan_cache(struct wlan_objmgr_pdev *pdev);
275 
276 /**
277  * scm_filter_rnr_flag_pno() - Remove FLAG_SCAN_ONLY_IF_RNR_FOUND flag
278  *                             in channel if ssid is different for colocated AP,
279  *                             during pno scan request
280  * @vdev: vdev
281  * @short_ssid: short ssid
282  * @chan_list: channel list
283  *
284  * Remove FLAG_SCAN_ONLY_IF_RNR_FOUND flag in channel if ssid is different for
285  * colocated AP, in pno scan request
286  *
287  * Return: None
288  */
289 void
290 scm_filter_rnr_flag_pno(struct wlan_objmgr_vdev *vdev,
291 			uint32_t short_ssid,
292 			struct chan_list *chan_list);
293 
294 #else
295 static inline struct channel_list_db *
scm_get_rnr_channel_db(struct wlan_objmgr_psoc * psoc)296 scm_get_rnr_channel_db(struct wlan_objmgr_psoc *psoc)
297 {
298 	return NULL;
299 }
300 
scm_channel_list_db_init(struct wlan_objmgr_psoc * psoc)301 static inline QDF_STATUS scm_channel_list_db_init(struct wlan_objmgr_psoc *psoc)
302 {
303 	return QDF_STATUS_SUCCESS;
304 }
305 
306 static inline
scm_channel_list_db_deinit(struct wlan_objmgr_psoc * psoc)307 QDF_STATUS scm_channel_list_db_deinit(struct wlan_objmgr_psoc *psoc)
308 {
309 	return QDF_STATUS_SUCCESS;
310 }
311 
312 static inline void
scm_filter_rnr_flag_pno(struct wlan_objmgr_vdev * vdev,uint32_t short_ssid,struct chan_list * chan_list)313 scm_filter_rnr_flag_pno(struct wlan_objmgr_vdev *vdev,
314 			uint32_t short_ssid,
315 			struct chan_list *chan_list)
316 {
317 }
318 #endif
319 
320 /**
321  * scm_scan_update_mlme_by_bssinfo() - updates scan entry with mlme data
322  * @pdev: pdev object
323  * @bss_info: BSS information
324  * @mlme: scan entry MLME info
325  *
326  * This function updates scan db with scan_entry->mlme_info
327  *
328  * Return: QDF_STATUS
329  */
330 QDF_STATUS scm_scan_update_mlme_by_bssinfo(struct wlan_objmgr_pdev *pdev,
331 		struct bss_info *bss_info, struct mlme_info *mlme);
332 
333 uint32_t scm_get_last_scan_time_per_channel(struct wlan_objmgr_vdev *vdev,
334 					    uint32_t freq);
335 
336 /**
337  * scm_scan_get_scan_entry_by_mac_freq() - Get scan entry by mac and freq
338  * @pdev: pdev info
339  * @bssid: BSSID of the bcn/probe response to be fetched from scan db
340  * @freq: freq for scan filter
341  *
342  * Return: scan entry if found, else NULL
343  */
344 struct scan_cache_entry *
345 scm_scan_get_scan_entry_by_mac_freq(struct wlan_objmgr_pdev *pdev,
346 				    struct qdf_mac_addr *bssid,
347 				    uint16_t freq);
348 
349 /**
350  * scm_scan_get_entry_by_mac_addr() - Get bcn/probe rsp from scan db
351  * @pdev: pdev info
352  * @bssid: BSSID of the bcn/probe response to be fetched from scan db
353  * @frame: Frame from scan db with given bssid.
354  *
355  * This API allocates the memory for bcn/probe rsp frame and returns
356  * to caller through @frame->ptr. It's caller responsibility to free
357  * the memory once it's done with the usage.
358  *
359  * Return: QDF_STATUS_SUCCESS if scan entry is present in db
360  */
361 QDF_STATUS
362 scm_scan_get_entry_by_mac_addr(struct wlan_objmgr_pdev *pdev,
363 			       struct qdf_mac_addr *bssid,
364 			       struct element_info *frame);
365 
366 /**
367  * scm_scan_get_entry_by_bssid() - function to get scan entry by bssid
368  * @pdev: pdev object
369  * @bssid: bssid to be fetched from scan db
370  *
371  * Return : scan entry if found, else NULL
372  */
373 struct scan_cache_entry *
374 scm_scan_get_entry_by_bssid(struct wlan_objmgr_pdev *pdev,
375 			    struct qdf_mac_addr *bssid);
376 
377 #ifdef WLAN_FEATURE_11BE_MLO
378 /**
379  * scm_get_mld_addr_by_link_addr() - function to fetch the peer mld address from
380  * the scan entry for the given link address.
381  * @pdev: pdev object
382  * @link_addr: link address
383  * @mld_mac_addr: pointer to mld_mac_address
384  *
385  * Return : scan entry if found, else NULL
386  */
387 QDF_STATUS
388 scm_get_mld_addr_by_link_addr(struct wlan_objmgr_pdev *pdev,
389 			      struct qdf_mac_addr *link_addr,
390 			      struct qdf_mac_addr *mld_mac_addr);
391 #else
392 static inline QDF_STATUS
scm_get_mld_addr_by_link_addr(struct wlan_objmgr_pdev * pdev,struct qdf_mac_addr * link_addr,struct qdf_mac_addr * mld_mac_addr)393 scm_get_mld_addr_by_link_addr(struct wlan_objmgr_pdev *pdev,
394 			      struct qdf_mac_addr *link_addr,
395 			      struct qdf_mac_addr *mld_mac_addr)
396 {
397 	return QDF_STATUS_E_NOSUPPORT;
398 }
399 #endif
400 
401 /**
402  * scm_scan_entries_contain_cmn_akm() - Check if two entries have common
403  * RSN capabilities.
404  * @entry1: Primary scan entry for comparison
405  * @entry2: Secondary scan entry for comparison
406  *
407  * Checks various RSN parameters of two scan entries to determine
408  * whether both have similar capabilities or not.
409  *
410  * Return: bool
411  */
412 bool scm_scan_entries_contain_cmn_akm(struct scan_cache_entry *entry1,
413 				      struct scan_cache_entry *entry2);
414 #endif
415