1 /*
2  * Copyright (c) 2012-2015,2020-2021 The Linux Foundation. All rights reserved.
3  * Copyright (c) 2021-2023 Qualcomm Innovation Center, Inc. All rights reserved.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for any
6  * purpose with or without fee is hereby granted, provided that the above
7  * copyright notice and this permission notice appear in all copies.
8  *
9  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16  */
17 
18 /**
19  * DOC: wlan_cm_sm.h
20  *
21  * This header file maintain structures required for connection mgr sm infra
22  */
23 
24 #ifndef __WLAN_CM_SM_H__
25 #define __WLAN_CM_SM_H__
26 
27 #include <wlan_sm_engine.h>
28 
29 /**
30  * enum wlan_cm_sm_evt - connection manager related events
31  * Note: make sure to update cm_sm_event_names on updating this enum
32  * @WLAN_CM_SM_EV_CONNECT_REQ:            Connect request event from requester
33  * @WLAN_CM_SM_EV_SCAN:                   Event to start connect scan
34  * @WLAN_CM_SM_EV_SCAN_SUCCESS:           Connect scan success event
35  * @WLAN_CM_SM_EV_SCAN_FAILURE:           Connect scan fail event
36  * @WLAN_CM_SM_EV_HW_MODE_SUCCESS:        Hw mode change is success
37  * @WLAN_CM_SM_EV_HW_MODE_FAILURE:        Hw mode change is failure
38  * @WLAN_CM_SM_EV_CONNECT_START:          Connect start process initiate
39  * @WLAN_CM_SM_EV_CONNECT_ACTIVE:         Connect request is activated
40  * @WLAN_CM_SM_EV_CONNECT_SUCCESS:        Connect success
41  * @WLAN_CM_SM_EV_BSS_SELECT_IND_SUCCESS: Mlme resp for BSS select indication
42  * @WLAN_CM_SM_EV_BSS_CREATE_PEER_SUCCESS: BSS peer create success
43  * @WLAN_CM_SM_EV_CONNECT_GET_NEXT_CANDIDATE: Get next candidate for connection
44  * @WLAN_CM_SM_EV_CONNECT_FAILURE:        Connect failed for all candidate
45  * @WLAN_CM_SM_EV_DISCONNECT_REQ:         Disconnect request event from
46  * requester
47  * @WLAN_CM_SM_EV_DISCONNECT_START:       Start disconnect sequence
48  * @WLAN_CM_SM_EV_DISCONNECT_ACTIVE:      Process disconnect after in active cmd
49  * @WLAN_CM_SM_EV_DISCONNECT_DONE:        Disconnect done event
50  * @WLAN_CM_SM_EV_ROAM_START:             Roam start event for LFR2 and LFR3
51  * @WLAN_CM_SM_EV_ROAM_SYNC:              Roam sync event for LFR3
52  * @WLAN_CM_SM_EV_ROAM_INVOKE_FAIL:       Roam invoke fail event
53  * @WLAN_CM_SM_EV_ROAM_HO_FAIL:           Hands off failed event
54  * @WLAN_CM_SM_EV_PREAUTH_DONE:           Preauth is completed
55  * @WLAN_CM_SM_EV_GET_NEXT_PREAUTH_AP:    Get next candidate as preauth failed
56  * @WLAN_CM_SM_EV_PREAUTH_FAIL:           Preauth failed for all candidate
57  * @WLAN_CM_SM_EV_START_REASSOC:          Start reassoc after preauth done
58  * @WLAN_CM_SM_EV_REASSOC_ACTIVE:         Reassoc request activated
59  * @WLAN_CM_SM_EV_REASSOC_DONE:           Reassoc completed
60  * @WLAN_CM_SM_EV_REASSOC_FAILURE:        Reassoc failed
61  * @WLAN_CM_SM_EV_ROAM_COMPLETE:          Roaming completed
62  * @WLAN_CM_SM_EV_ROAM_REQ:               LFR3/FW roam - Roam req from connect
63  *                                        LFR2/Host roam - Roam req from host/FW
64  * @WLAN_CM_SM_EV_ROAM_INVOKE:            Host initiated LFR3/FW roam req
65  * @WLAN_CM_SM_EV_ROAM_ABORT:             Roam abort
66  * @WLAN_CM_SM_EV_ROAM_DONE:              Roam done
67  * @WLAN_CM_SM_EV_PREAUTH_ACTIVE:         Preauth active
68  * @WLAN_CM_SM_EV_PREAUTH_RESP:           Preauth response
69  * @WLAN_CM_SM_EV_REASSOC_TIMER:          Reassoc timer expired
70  * @WLAN_CM_SM_EV_HO_ROAM_DISCONNECT_DONE: Disconnect done for hands off/roaming
71  * @WLAN_CM_SM_EV_RSO_STOP_RSP:           Event to continue disconnect after
72  *                                        RSO stop response is received
73  * @WLAN_CM_SM_EV_BEARER_SWITCH_COMPLETE: Event to continue connect after bearer
74  *                                       switch complete
75  * @WLAN_CM_SM_EV_MAX:                    Max event
76  */
77 enum wlan_cm_sm_evt {
78 	WLAN_CM_SM_EV_CONNECT_REQ = 0,
79 	WLAN_CM_SM_EV_SCAN = 1,
80 	WLAN_CM_SM_EV_SCAN_SUCCESS = 2,
81 	WLAN_CM_SM_EV_SCAN_FAILURE = 3,
82 	WLAN_CM_SM_EV_HW_MODE_SUCCESS = 4,
83 	WLAN_CM_SM_EV_HW_MODE_FAILURE = 5,
84 	WLAN_CM_SM_EV_CONNECT_START = 6,
85 	WLAN_CM_SM_EV_CONNECT_ACTIVE = 7,
86 	WLAN_CM_SM_EV_CONNECT_SUCCESS = 8,
87 	WLAN_CM_SM_EV_BSS_SELECT_IND_SUCCESS = 9,
88 	WLAN_CM_SM_EV_BSS_CREATE_PEER_SUCCESS = 10,
89 	WLAN_CM_SM_EV_CONNECT_GET_NEXT_CANDIDATE = 11,
90 	WLAN_CM_SM_EV_CONNECT_FAILURE = 12,
91 	WLAN_CM_SM_EV_DISCONNECT_REQ = 13,
92 	WLAN_CM_SM_EV_DISCONNECT_START = 14,
93 	WLAN_CM_SM_EV_DISCONNECT_ACTIVE = 15,
94 	WLAN_CM_SM_EV_DISCONNECT_DONE = 16,
95 	WLAN_CM_SM_EV_ROAM_START = 17,
96 	WLAN_CM_SM_EV_ROAM_SYNC = 18,
97 	WLAN_CM_SM_EV_ROAM_INVOKE_FAIL = 19,
98 	WLAN_CM_SM_EV_ROAM_HO_FAIL = 20,
99 	WLAN_CM_SM_EV_PREAUTH_DONE = 21,
100 	WLAN_CM_SM_EV_GET_NEXT_PREAUTH_AP = 22,
101 	WLAN_CM_SM_EV_PREAUTH_FAIL = 23,
102 	WLAN_CM_SM_EV_START_REASSOC = 24,
103 	WLAN_CM_SM_EV_REASSOC_ACTIVE = 25,
104 	WLAN_CM_SM_EV_REASSOC_DONE = 26,
105 	WLAN_CM_SM_EV_REASSOC_FAILURE = 27,
106 	WLAN_CM_SM_EV_ROAM_COMPLETE = 28,
107 	WLAN_CM_SM_EV_ROAM_REQ = 29,
108 	WLAN_CM_SM_EV_ROAM_INVOKE = 30,
109 	WLAN_CM_SM_EV_ROAM_ABORT = 31,
110 	WLAN_CM_SM_EV_ROAM_DONE = 32,
111 	WLAN_CM_SM_EV_PREAUTH_ACTIVE = 33,
112 	WLAN_CM_SM_EV_PREAUTH_RESP = 34,
113 	WLAN_CM_SM_EV_REASSOC_TIMER = 35,
114 	WLAN_CM_SM_EV_HO_ROAM_DISCONNECT_DONE = 36,
115 	WLAN_CM_SM_EV_RSO_STOP_RSP = 37,
116 	WLAN_CM_SM_EV_BEARER_SWITCH_COMPLETE = 38,
117 	WLAN_CM_SM_EV_MAX,
118 };
119 
120 /**
121  * cm_sm_create() - Invoke SM creation for connection manager
122  * @cm_ctx:  connection manager ctx
123  *
124  * API allocates CM MLME SM and initializes SM lock
125  *
126  * Return: SUCCESS on successful allocation
127  *         FAILURE, if registration fails
128  */
129 QDF_STATUS cm_sm_create(struct cnx_mgr *cm_ctx);
130 
131 /**
132  * cm_sm_destroy() - Invoke SM deletion for connection manager
133  * @cm_ctx:  connection manager ctx
134  *
135  * API destroys CM MLME SM and SM lock
136  *
137  * Return: SUCCESS on successful deletion
138  *         FAILURE, if deletion fails
139  */
140 QDF_STATUS cm_sm_destroy(struct cnx_mgr *cm_ctx);
141 
142 /**
143  * cm_sm_history_print() - Prints SM history
144  * @vdev:  vdev object
145  *
146  * API to print CM SM history
147  *
148  * Return: void
149  */
150 #ifdef SM_ENG_HIST_ENABLE
151 void cm_sm_history_print(struct wlan_objmgr_vdev *vdev);
152 #else
153 static inline
cm_sm_history_print(struct wlan_objmgr_vdev * vdev)154 void cm_sm_history_print(struct wlan_objmgr_vdev *vdev)
155 { }
156 #endif
157 
158 #ifdef WLAN_CM_USE_SPINLOCK
159 /**
160  * cm_lock_create() - Create CM SM mutex/spinlock
161  * @cm_ctx:  connection manager ctx
162  *
163  * Creates CM SM mutex/spinlock
164  *
165  * Return: void
166  */
167 static inline void
cm_lock_create(struct cnx_mgr * cm_ctx)168 cm_lock_create(struct cnx_mgr *cm_ctx)
169 {
170 	qdf_spinlock_create(&cm_ctx->sm.cm_sm_lock);
171 }
172 
173 /**
174  * cm_lock_destroy() - Destroy CM SM mutex/spinlock
175  * @cm_ctx:  connection manager ctx
176  *
177  * Destroy CM SM mutex/spinlock
178  *
179  * Return: void
180  */
181 static inline void
cm_lock_destroy(struct cnx_mgr * cm_ctx)182 cm_lock_destroy(struct cnx_mgr *cm_ctx)
183 {
184 	qdf_spinlock_destroy(&cm_ctx->sm.cm_sm_lock);
185 }
186 
187 /**
188  * cm_lock_acquire() - acquire CM SM mutex/spinlock
189  * @cm_ctx:  connection manager ctx
190  *
191  * acquire CM SM mutex/spinlock
192  *
193  * return: void
194  */
cm_lock_acquire(struct cnx_mgr * cm_ctx)195 static inline void cm_lock_acquire(struct cnx_mgr *cm_ctx)
196 {
197 	qdf_spin_lock_bh(&cm_ctx->sm.cm_sm_lock);
198 }
199 
200 /**
201  * cm_lock_release() - release CM SM mutex/spinlock
202  * @cm_ctx:  connection manager ctx
203  *
204  * release CM SM mutex/spinlock
205  *
206  * return: void
207  */
cm_lock_release(struct cnx_mgr * cm_ctx)208 static inline void cm_lock_release(struct cnx_mgr *cm_ctx)
209 {
210 	qdf_spin_unlock_bh(&cm_ctx->sm.cm_sm_lock);
211 }
212 #else
213 static inline void
cm_lock_create(struct cnx_mgr * cm_ctx)214 cm_lock_create(struct cnx_mgr *cm_ctx)
215 {
216 	qdf_mutex_create(&cm_ctx->sm.cm_sm_lock);
217 }
218 
219 static inline void
cm_lock_destroy(struct cnx_mgr * cm_ctx)220 cm_lock_destroy(struct cnx_mgr *cm_ctx)
221 {
222 	qdf_mutex_destroy(&cm_ctx->sm.cm_sm_lock);
223 }
224 
cm_lock_acquire(struct cnx_mgr * cm_ctx)225 static inline void cm_lock_acquire(struct cnx_mgr *cm_ctx)
226 {
227 	qdf_mutex_acquire(&cm_ctx->sm.cm_sm_lock);
228 }
229 
cm_lock_release(struct cnx_mgr * cm_ctx)230 static inline void cm_lock_release(struct cnx_mgr *cm_ctx)
231 {
232 	qdf_mutex_release(&cm_ctx->sm.cm_sm_lock);
233 }
234 #endif /* WLAN_CM_USE_SPINLOCK */
235 
236 /**
237  * cm_sm_transition_to() - invokes state transition
238  * @cm_ctx:  connection manager ctx
239  * @state: new cm state
240  *
241  * API to invoke SM API to move to new state
242  *
243  * Return: void
244  */
cm_sm_transition_to(struct cnx_mgr * cm_ctx,enum wlan_cm_sm_state state)245 static inline void cm_sm_transition_to(struct cnx_mgr *cm_ctx,
246 				       enum wlan_cm_sm_state state)
247 {
248 	wlan_sm_transition_to(cm_ctx->sm.sm_hdl, state);
249 }
250 
251 /**
252  * cm_get_state() - get mlme state
253  * @cm_ctx: connection manager SM ctx
254  *
255  * API to get cm state
256  *
257  * Return: state of cm
258  */
259 enum wlan_cm_sm_state cm_get_state(struct cnx_mgr *cm_ctx);
260 
261 /**
262  * cm_get_sub_state() - get mlme substate
263  * @cm_ctx: connection manager SM ctx
264  *
265  * API to get cm substate
266  *
267  * Return: substate of cm
268  */
269 enum wlan_cm_sm_state cm_get_sub_state(struct cnx_mgr *cm_ctx);
270 
271 /**
272  * cm_set_state() - set cm mlme state
273  * @cm_ctx: connection manager SM ctx
274  * @state: cm state
275  *
276  * API to set cm state
277  *
278  * Return: void
279  */
280 void cm_set_state(struct cnx_mgr *cm_ctx, enum wlan_cm_sm_state state);
281 
282 /**
283  * cm_set_substate() - set cm mlme sub state
284  * @cm_ctx: connection manager SM ctx
285  * @substate: cm sub state
286  *
287  * API to set cm sub state
288  *
289  * Return: void
290  */
291 void cm_set_substate(struct cnx_mgr *cm_ctx,
292 		     enum wlan_cm_sm_state substate);
293 
294 /**
295  * cm_sm_state_update() - set cm mlme state and sub state
296  * @cm_ctx: connection manager SM ctx
297  * @state: cm state
298  * @substate: cm sub state
299  *
300  * API to invoke util APIs to set state and MLME sub state
301  *
302  * Return: void
303  */
304 void cm_sm_state_update(struct cnx_mgr *cm_ctx,
305 			enum wlan_cm_sm_state state,
306 			enum wlan_cm_sm_state substate);
307 
308 /**
309  * cm_sm_deliver_event_sync() - Delivers event to connection manager SM while
310  * holding lock
311  * @cm_ctx: cm ctx
312  * @event: CM event
313  * @data_len: data size
314  * @data: event data
315  *
316  * API to dispatch event to VDEV MLME SM without lock, in case lock is already
317  * held.
318  *
319  * Context: Can be called from any context, This should be called in case
320  * SM lock is already taken. If lock is not taken use cm_sm_deliver_event API
321  * instead.
322  *
323  * Return: SUCCESS: on handling event
324  *         FAILURE: If event not handled
325  */
326 static inline
cm_sm_deliver_event_sync(struct cnx_mgr * cm_ctx,enum wlan_cm_sm_evt event,uint16_t data_len,void * data)327 QDF_STATUS cm_sm_deliver_event_sync(struct cnx_mgr *cm_ctx,
328 				    enum wlan_cm_sm_evt event,
329 				    uint16_t data_len, void *data)
330 {
331 	return wlan_sm_dispatch(cm_ctx->sm.sm_hdl, event, data_len, data);
332 }
333 
334 /**
335  * cm_sm_deliver_event() - Delivers event to connection manager SM
336  * @vdev: Object manager VDEV object
337  * @event: CM event
338  * @data_len: data size
339  * @data: event data
340  *
341  * API to dispatch event to VDEV MLME SM with lock. To be used while posting
342  * events from API called from public API. i.e. indication/response/request
343  * from any other module or NB/SB req/resp.
344  *
345  * Context: Can be called from any context, This should be called in case
346  * SM lock is not taken, the API will take the lock before posting to SM.
347  * If lock is already taken use cm_sm_deliver_event_sync API instead.
348  *
349  * Return: SUCCESS: on handling event
350  *         FAILURE: If event not handled
351  */
352 QDF_STATUS  cm_sm_deliver_event(struct wlan_objmgr_vdev *vdev,
353 				enum wlan_cm_sm_evt event,
354 				uint16_t data_len, void *data);
355 
356 /**
357  * cm_fill_vdev_crypto_params() - Update the vdev crypto params
358  * from the connect req structure
359  * @cm_ctx: connection manager SM ctx
360  * @req: connect request structure
361  *
362  * Return: void
363  */
364 void cm_fill_vdev_crypto_params(struct cnx_mgr *cm_ctx,
365 				struct wlan_cm_connect_req *req);
366 #endif /* __WLAN_CM_SM_H__ */
367