xref: /wlan-dirver/qca-wifi-host-cmn/umac/mlme/vdev_mgr/core/src/vdev_mlme_sm.c (revision 1397a33f48ea6455be40871470b286e535820eb8)
1 /*
2  * Copyright (c) 2018-2019 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 /**
20  * DOC: Implements VDEV MLME SM
21  */
22 
23 #include <wlan_objmgr_vdev_obj.h>
24 #include <wlan_mlme_dbg.h>
25 #include <wlan_sm_engine.h>
26 #include "include/wlan_vdev_mlme.h"
27 #include "vdev_mlme_sm.h"
28 
29 #ifdef CMN_VDEV_MLME_SM_ENABLE
30 /**
31  * mlme_vdev_set_state() - set mlme state
32  * @vdev: VDEV object
33  * @state: MLME state
34  *
35  * API to set MLME state
36  *
37  * Return: void
38  */
39 static void mlme_vdev_set_state(struct wlan_objmgr_vdev *vdev,
40 				enum wlan_vdev_state state)
41 {
42 	if (state < WLAN_VDEV_S_MAX) {
43 		vdev->vdev_mlme.mlme_state = state;
44 	} else {
45 		mlme_err("mlme state (%d) is invalid", state);
46 		QDF_BUG(0);
47 	}
48 }
49 
50 /**
51  * mlme_vdev_set_substate() - set mlme sub state
52  * @vdev: VDEV object
53  * @substate: MLME sub state
54  *
55  * API to set MLME sub state
56  *
57  * Return: void
58  */
59 static void mlme_vdev_set_substate(struct wlan_objmgr_vdev *vdev,
60 				   enum wlan_vdev_state substate)
61 {
62 	if ((substate > WLAN_VDEV_S_MAX) && (substate < WLAN_VDEV_SS_MAX)) {
63 		vdev->vdev_mlme.mlme_substate = substate;
64 	} else {
65 		mlme_err(" mlme sub state (%d) is invalid", substate);
66 		QDF_BUG(0);
67 	}
68 }
69 
70 /**
71  * mlme_vdev_sm_state_update() - set mlme state and sub state
72  * @vdev_mlme: MLME VDEV comp object
73  * @state: MLME state
74  * @substate: MLME sub state
75  *
76  * API to invoke util APIs to set state and MLME sub state
77  *
78  * Return: void
79  */
80 static void mlme_vdev_sm_state_update(struct vdev_mlme_obj *vdev_mlme,
81 				      enum wlan_vdev_state state,
82 				      enum wlan_vdev_state substate)
83 {
84 	struct wlan_objmgr_vdev *vdev;
85 
86 	vdev = vdev_mlme->vdev;
87 	if (!vdev) {
88 		mlme_err(" VDEV is NULL");
89 		QDF_BUG(0);
90 	}
91 
92 	mlme_vdev_set_state(vdev, state);
93 	mlme_vdev_set_substate(vdev, substate);
94 }
95 
96 /**
97  * mlme_vdev_sm_transition_to() - invokes state transition
98  * @vdev_mlme: MLME VDEV comp object
99  * @state: new MLME state
100  *
101  * API to invoke SM API to move to new state
102  *
103  * Return: void
104  */
105 static void mlme_vdev_sm_transition_to(struct vdev_mlme_obj *vdev_mlme,
106 				       enum wlan_vdev_state state)
107 {
108 	wlan_sm_transition_to(vdev_mlme->sm_hdl, state);
109 }
110 
111 /**
112  * mlme_vdev_state_init_entry() - Entry API for Init state
113  * @ctx: VDEV MLME object
114  *
115  * API to perform operations on moving to INIT state
116  *
117  * Return: void
118  */
119 static void mlme_vdev_state_init_entry(void *ctx)
120 {
121 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
122 
123 	mlme_vdev_sm_state_update(vdev_mlme, WLAN_VDEV_S_INIT,
124 				  WLAN_VDEV_SS_IDLE);
125 }
126 
127 /**
128  * mlme_vdev_state_init_exit() - Exit API for Init state
129  * @ctx: VDEV MLME object
130  *
131  * API to perform operations on moving out of INIT state
132  *
133  * Return: void
134  */
135 static void mlme_vdev_state_init_exit(void *ctx)
136 {
137 	/* NONE */
138 }
139 
140 /**
141  * mlme_vdev_state_init_event() - Init State event handler
142  * @ctx: VDEV MLME object
143  *
144  * API to handle events in INIT state
145  *
146  * Return: SUCCESS: on handling event
147  *         FAILURE: on ignoring the event
148  */
149 static bool mlme_vdev_state_init_event(void *ctx, uint16_t event,
150 				       uint16_t event_data_len,
151 				       void *event_data)
152 {
153 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
154 	bool status;
155 
156 	switch (event) {
157 	case WLAN_VDEV_SM_EV_START:
158 		/* call mlme callback API for sanity checks */
159 		if (mlme_vdev_validate_basic_params(vdev_mlme, event_data_len,
160 					event_data) == QDF_STATUS_SUCCESS) {
161 			mlme_vdev_sm_transition_to(vdev_mlme,
162 						   WLAN_VDEV_S_START);
163 			mlme_vdev_sm_deliver_event(vdev_mlme,
164 						   WLAN_VDEV_SM_EV_START_REQ,
165 						   event_data_len, event_data);
166 			status = true;
167 		} else {
168 			mlme_err(
169 			"failed to validate vdev init params to move to START state");
170 			status = true;
171 		}
172 		break;
173 
174 	case WLAN_VDEV_SM_EV_DOWN_COMPLETE:
175 	case WLAN_VDEV_SM_EV_DOWN:
176 	case WLAN_VDEV_SM_EV_START_REQ_FAIL:
177 		/* already in down state, notify DOWN command is completed */
178 		/* NOTE: Keep this function call always at the end, to allow
179 		 * connection restart from this event
180 		 */
181 		mlme_vdev_notify_down_complete(vdev_mlme, event_data_len,
182 					       event_data);
183 		status = true;
184 		break;
185 
186 	default:
187 		status = false;
188 		break;
189 	}
190 
191 	return status;
192 }
193 
194 /**
195  * mlme_vdev_state_start_entry() - Entry API for Start state
196  * @ctx: VDEV MLME object
197  *
198  * API to perform operations on moving to START state
199  *
200  * Return: void
201  */
202 static void mlme_vdev_state_start_entry(void *ctx)
203 {
204 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
205 
206 	mlme_vdev_sm_state_update(vdev_mlme, WLAN_VDEV_S_START,
207 				  WLAN_VDEV_SS_IDLE);
208 }
209 
210 /**
211  * mlme_vdev_state_start_exit() - Exit API for Start state
212  * @ctx: VDEV MLME object
213  *
214  * API to perform operations on moving out of START state
215  *
216  * Return: void
217  */
218 static void mlme_vdev_state_start_exit(void *ctx)
219 {
220 	/* NONE */
221 }
222 
223 /**
224  * mlme_vdev_state_start_event() - Start State event handler
225  * @ctx: VDEV MLME object
226  *
227  * API to handle events in START state
228  *
229  * Return: SUCCESS: on handling event
230  *         FAILURE: on ignoring the event
231  */
232 static bool mlme_vdev_state_start_event(void *ctx, uint16_t event,
233 					uint16_t event_data_len,
234 					void *event_data)
235 {
236 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
237 	bool status;
238 
239 	switch (event) {
240 	case WLAN_VDEV_SM_EV_START_REQ:
241 		mlme_vdev_sm_transition_to(vdev_mlme,
242 					   WLAN_VDEV_SS_START_START_PROGRESS);
243 		mlme_vdev_sm_deliver_event(vdev_mlme, event, event_data_len,
244 					   event_data);
245 		status = true;
246 		break;
247 
248 	case WLAN_VDEV_SM_EV_RESTART_REQ:
249 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
250 		mlme_vdev_sm_transition_to(vdev_mlme,
251 					   WLAN_VDEV_SS_START_RESTART_PROGRESS);
252 		mlme_vdev_sm_deliver_event(vdev_mlme, event, event_data_len,
253 					   event_data);
254 		status = true;
255 		break;
256 
257 	case WLAN_VDEV_SM_EV_STA_CONN_START:
258 		mlme_vdev_sm_transition_to(vdev_mlme,
259 					   WLAN_VDEV_SS_START_CONN_PROGRESS);
260 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
261 					   event_data_len, event_data);
262 		status = true;
263 		break;
264 
265 	default:
266 		status = false;
267 		break;
268 	}
269 
270 	return status;
271 }
272 
273 /**
274  * mlme_vdev_state_dfs_cac_wait_entry() - Entry API for DFS CAC WAIT state
275  * @ctx: VDEV MLME object
276  *
277  * API to perform operations on moving to DFS CAC WAIT state
278  *
279  * Return: void
280  */
281 static void mlme_vdev_state_dfs_cac_wait_entry(void *ctx)
282 {
283 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
284 
285 	mlme_vdev_sm_state_update(vdev_mlme, WLAN_VDEV_S_DFS_CAC_WAIT,
286 				  WLAN_VDEV_SS_IDLE);
287 }
288 
289 /**
290  * mlme_vdev_state_dfs_cac_wait_exit() - Exit API for DFS CAC WAIT state
291  * @ctx: VDEV MLME object
292  *
293  * API to perform operations on moving out of DFS CAC WAIT state
294  *
295  * Return: void
296  */
297 static void mlme_vdev_state_dfs_cac_wait_exit(void *ctx)
298 {
299 	/* NONE */
300 }
301 
302 /**
303  * mlme_vdev_state_dfs_cac_wait_event() - DFS CAC WAIT State event handler
304  * @ctx: VDEV MLME object
305  *
306  * API to handle events in DFS CAC WAIT state
307  *
308  * Return: SUCCESS: on handling event
309  *         FAILURE: on ignoring the event
310  */
311 static bool mlme_vdev_state_dfs_cac_wait_event(void *ctx, uint16_t event,
312 					       uint16_t event_data_len,
313 					       void *event_data)
314 {
315 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
316 	enum QDF_OPMODE mode;
317 	struct wlan_objmgr_vdev *vdev;
318 	bool status;
319 
320 	vdev = vdev_mlme->vdev;
321 
322 	mode = wlan_vdev_mlme_get_opmode(vdev);
323 
324 	switch (event) {
325 	case WLAN_VDEV_SM_EV_DFS_CAC_WAIT:
326 		/* DFS timer should have started already, then only this event
327 		 * could have been triggered
328 		 */
329 		status = true;
330 		break;
331 
332 	case WLAN_VDEV_SM_EV_DOWN:
333 		/* stop the CAC timer, then notify state machine */
334 		mlme_vdev_dfs_cac_timer_stop(vdev_mlme, event_data_len,
335 					     event_data);
336 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_STOP);
337 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_DOWN,
338 					   event_data_len, event_data);
339 		status = true;
340 		break;
341 
342 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
343 		/* the random channel should have been selected, before issuing
344 		 * this event
345 		 */
346 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_START);
347 		mlme_vdev_sm_deliver_event(vdev_mlme,
348 					   WLAN_VDEV_SM_EV_RESTART_REQ,
349 					   event_data_len, event_data);
350 		status = true;
351 		break;
352 
353 	case WLAN_VDEV_SM_EV_DFS_CAC_COMPLETED:
354 		if (mode == QDF_STA_MODE) {
355 			mlme_vdev_sm_transition_to(vdev_mlme,
356 						   WLAN_VDEV_S_START);
357 			mlme_vdev_sm_deliver_event(vdev_mlme,
358 						WLAN_VDEV_SM_EV_STA_CONN_START,
359 						event_data_len, event_data);
360 		} else {
361 			mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_UP);
362 			mlme_vdev_sm_deliver_event(vdev_mlme,
363 						WLAN_VDEV_SM_EV_START_SUCCESS,
364 						event_data_len, event_data);
365 		}
366 		status = true;
367 		break;
368 
369 	default:
370 		status = false;
371 		break;
372 	}
373 
374 	return status;
375 }
376 
377 /**
378  * mlme_vdev_state_up_entry() - Entry API for UP state
379  * @ctx: VDEV MLME object
380  *
381  * API to perform operations on moving to UP state
382  *
383  * Return: void
384  */
385 static void mlme_vdev_state_up_entry(void *ctx)
386 {
387 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
388 
389 	mlme_vdev_sm_state_update(vdev_mlme, WLAN_VDEV_S_UP,
390 				  WLAN_VDEV_SS_IDLE);
391 }
392 
393 /**
394  * mlme_vdev_state_up_exit() - Exit API for UP state
395  * @ctx: VDEV MLME object
396  *
397  * API to perform operations on moving out of UP state
398  *
399  * Return: void
400  */
401 static void mlme_vdev_state_up_exit(void *ctx)
402 {
403 	/* NONE */
404 }
405 
406 /**
407  * mlme_vdev_state_up_event() - UP State event handler
408  * @ctx: VDEV MLME object
409  *
410  * API to handle events in UP state
411  *
412  * Return: SUCCESS: on handling event
413  *         FAILURE: on ignoring the event
414  */
415 static bool mlme_vdev_state_up_event(void *ctx, uint16_t event,
416 				     uint16_t event_data_len, void *event_data)
417 {
418 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
419 	enum QDF_OPMODE mode;
420 	struct wlan_objmgr_vdev *vdev;
421 	bool status;
422 
423 	vdev = vdev_mlme->vdev;
424 	mode = wlan_vdev_mlme_get_opmode(vdev);
425 
426 	switch (event) {
427 	case WLAN_VDEV_SM_EV_START_SUCCESS:
428 		mlme_vdev_update_beacon(vdev_mlme, BEACON_INIT,
429 					event_data_len, event_data);
430 		if (mlme_vdev_up_send(vdev_mlme, event_data_len,
431 				      event_data) != QDF_STATUS_SUCCESS)
432 			mlme_vdev_sm_deliver_event(vdev_mlme,
433 						   WLAN_VDEV_SM_EV_UP_FAIL,
434 						   event_data_len, event_data);
435 		else
436 			mlme_vdev_notify_up_complete(vdev_mlme, event_data_len,
437 						     event_data);
438 
439 		status = true;
440 		break;
441 
442 	case WLAN_VDEV_SM_EV_SUPSEND_RESTART:
443 	case WLAN_VDEV_SM_EV_HOST_RESTART:
444 	case WLAN_VDEV_SM_EV_CSA_RESTART:
445 		/* These events are not supported in STA mode */
446 		if (mode == QDF_STA_MODE)
447 			QDF_BUG(0);
448 
449 	case WLAN_VDEV_SM_EV_DOWN:
450 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_SUSPEND);
451 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
452 					   event_data_len, event_data);
453 		status = true;
454 		break;
455 
456 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
457 		/* These events are not supported in STA mode */
458 		if (mode == QDF_STA_MODE)
459 			QDF_BUG(0);
460 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_SUSPEND);
461 		mlme_vdev_sm_deliver_event(vdev_mlme,
462 					   WLAN_VDEV_SM_EV_CSA_RESTART,
463 					   event_data_len, event_data);
464 		status = true;
465 		break;
466 
467 	case WLAN_VDEV_SM_EV_UP_HOST_RESTART:
468 		/* Reinit beacon, send template to FW(use ping-pong buffer) */
469 		mlme_vdev_update_beacon(vdev_mlme, BEACON_UPDATE,
470 					event_data_len, event_data);
471 	case WLAN_VDEV_SM_EV_START:
472 		/* notify that UP command is completed */
473 		mlme_vdev_notify_up_complete(vdev_mlme,
474 					     event_data_len, event_data);
475 		status = true;
476 		break;
477 
478 	case WLAN_VDEV_SM_EV_FW_VDEV_RESTART:
479 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_START);
480 		mlme_vdev_sm_deliver_event(vdev_mlme,
481 					   WLAN_VDEV_SM_EV_RESTART_REQ,
482 					   event_data_len, event_data);
483 		status = true;
484 		break;
485 
486 	case WLAN_VDEV_SM_EV_UP_FAIL:
487 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_SUSPEND);
488 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
489 					   event_data_len, event_data);
490 		status = true;
491 		break;
492 
493 	case WLAN_VDEV_SM_EV_ROAM:
494 		mlme_vdev_notify_roam_start(vdev_mlme, event_data_len,
495 					    event_data);
496 		status = true;
497 		break;
498 
499 	default:
500 		status = false;
501 		break;
502 	}
503 
504 	return status;
505 }
506 
507 /**
508  * mlme_vdev_state_suspend_entry() - Entry API for Suspend state
509  * @ctx: VDEV MLME object
510  *
511  * API to perform operations on moving to SUSPEND state
512  *
513  * Return: void
514  */
515 static void mlme_vdev_state_suspend_entry(void *ctx)
516 {
517 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
518 
519 	mlme_vdev_sm_state_update(vdev_mlme, WLAN_VDEV_S_SUSPEND,
520 				  WLAN_VDEV_SS_IDLE);
521 }
522 
523 /**
524  * mlme_vdev_state_suspend_exit() - Exit API for Suspend state
525  * @ctx: VDEV MLME object
526  *
527  * API to perform operations on moving out of SUSPEND state
528  *
529  * Return: void
530  */
531 static void mlme_vdev_state_suspend_exit(void *ctx)
532 {
533 	/* NONE */
534 }
535 
536 /**
537  * mlme_vdev_state_suspend_event() - Suspend State event handler
538  * @ctx: VDEV MLME object
539  *
540  * API to handle events in SUSPEND state
541  *
542  * Return: SUCCESS: on handling event
543  *         FAILURE: on ignoring the event
544  */
545 static bool mlme_vdev_state_suspend_event(void *ctx, uint16_t event,
546 					  uint16_t event_data_len,
547 					  void *event_data)
548 {
549 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
550 	bool status;
551 
552 	switch (event) {
553 	case WLAN_VDEV_SM_EV_DOWN:
554 	case WLAN_VDEV_SM_EV_RESTART_REQ_FAIL:
555 		mlme_vdev_sm_transition_to(vdev_mlme,
556 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
557 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
558 					   event_data_len, event_data);
559 		status = true;
560 		break;
561 
562 	case WLAN_VDEV_SM_EV_SUPSEND_RESTART:
563 		mlme_vdev_sm_transition_to(vdev_mlme,
564 					  WLAN_VDEV_SS_SUSPEND_SUSPEND_RESTART);
565 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
566 					   event_data_len, event_data);
567 		status = true;
568 		break;
569 
570 	case WLAN_VDEV_SM_EV_HOST_RESTART:
571 		mlme_vdev_sm_transition_to(vdev_mlme,
572 					   WLAN_VDEV_SS_SUSPEND_HOST_RESTART);
573 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
574 					   event_data_len, event_data);
575 		status = true;
576 		break;
577 
578 	case WLAN_VDEV_SM_EV_CSA_RESTART:
579 		mlme_vdev_sm_transition_to(vdev_mlme,
580 					   WLAN_VDEV_SS_SUSPEND_CSA_RESTART);
581 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
582 					   event_data_len, event_data);
583 		status = true;
584 		break;
585 
586 	case WLAN_VDEV_SM_EV_UP_FAIL:
587 		mlme_vdev_sm_transition_to(vdev_mlme,
588 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
589 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_DOWN,
590 					   event_data_len, event_data);
591 		status = true;
592 		break;
593 
594 	default:
595 		status = false;
596 		break;
597 	}
598 
599 	return status;
600 }
601 
602 /**
603  * mlme_vdev_state_stop_entry() - Entry API for Stop state
604  * @ctx: VDEV MLME object
605  *
606  * API to perform operations on moving to STOP state
607  *
608  * Return: void
609  */
610 static void mlme_vdev_state_stop_entry(void *ctx)
611 {
612 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *) ctx;
613 
614 	mlme_vdev_sm_state_update(vdev_mlme, WLAN_VDEV_S_STOP,
615 				  WLAN_VDEV_SS_IDLE);
616 }
617 
618 /**
619  * mlme_vdev_state_stop_exit() - Exit API for Stop state
620  * @ctx: VDEV MLME object
621  *
622  * API to perform operations on moving out of STOP state
623  *
624  * Return: void
625  */
626 static void mlme_vdev_state_stop_exit(void *ctx)
627 {
628 	/* NONE */
629 }
630 
631 /**
632  * mlme_vdev_state_stop_event() - Stop State event handler
633  * @ctx: VDEV MLME object
634  *
635  * API to handle events in STOP state
636  *
637  * Return: SUCCESS: on handling event
638  *         FAILURE: on ignoring the event
639  */
640 static bool mlme_vdev_state_stop_event(void *ctx, uint16_t event,
641 				       uint16_t event_data_len,
642 				       void *event_data)
643 {
644 	QDF_BUG(0);
645 	return false;
646 }
647 
648 /**
649  * mlme_vdev_subst_start_start_progress_entry() - Entry API for Start Progress
650  *                                                sub state
651  * @ctx: VDEV MLME object
652  *
653  * API to perform operations on moving to START-PROGRESS substate
654  *
655  * Return: void
656  */
657 static void mlme_vdev_subst_start_start_progress_entry(void *ctx)
658 {
659 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
660 	struct wlan_objmgr_vdev *vdev;
661 
662 	vdev = vdev_mlme->vdev;
663 
664 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_START)
665 		QDF_BUG(0);
666 
667 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_START_START_PROGRESS);
668 }
669 
670 /**
671  * mlme_vdev_subst_start_start_progress_exit() - Exit API for Start Progress
672  *                                                sub state
673  * @ctx: VDEV MLME object
674  *
675  * API to perform operations on moving out of START-PROGRESS substate
676  *
677  * Return: void
678  */
679 static void mlme_vdev_subst_start_start_progress_exit(void *ctx)
680 {
681 	/* NONE */
682 }
683 
684 /**
685  * mlme_vdev_subst_start_start_progress_event() - Event handler API for Start
686  *                                                Progress substate
687  * @ctx: VDEV MLME object
688  *
689  * API to handle events in START-PROGRESS substate
690  *
691  * Return: SUCCESS: on handling event
692  *         FAILURE: on ignoring the event
693  */
694 static bool mlme_vdev_subst_start_start_progress_event(void *ctx,
695 		uint16_t event, uint16_t event_data_len, void *event_data)
696 {
697 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
698 	struct wlan_objmgr_vdev *vdev;
699 	bool status;
700 
701 	vdev = vdev_mlme->vdev;
702 
703 	switch (event) {
704 	case WLAN_VDEV_SM_EV_START_REQ:
705 		/* send vdev start req command to FW */
706 		mlme_vdev_start_send(vdev_mlme,	event_data_len, event_data);
707 		status = true;
708 		break;
709 	/* While waiting for START response, move to RESTART_PROGRESS,
710 	 * wait for START response to send RESTART req */
711 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
712 		mlme_vdev_sm_transition_to(vdev_mlme,
713 					   WLAN_VDEV_SS_START_RESTART_PROGRESS);
714 		status = true;
715 		break;
716 	case WLAN_VDEV_SM_EV_START_RESP:
717 	case WLAN_VDEV_SM_EV_RESTART_RESP:
718 		mlme_vdev_sm_transition_to(vdev_mlme,
719 					   WLAN_VDEV_SS_START_CONN_PROGRESS);
720 		mlme_vdev_sm_deliver_event(vdev_mlme,
721 					   WLAN_VDEV_SM_EV_CONN_PROGRESS,
722 					   event_data_len, event_data);
723 		status = true;
724 		break;
725 
726 	case WLAN_VDEV_SM_EV_START_REQ_FAIL:
727 		mlme_vdev_start_req_failed(vdev_mlme,
728 					   event_data_len, event_data);
729 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_INIT);
730 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
731 					   event_data_len, event_data);
732 		status = true;
733 		break;
734 
735 	case WLAN_VDEV_SM_EV_DOWN:
736 		mlme_vdev_sm_transition_to(vdev_mlme,
737 					   WLAN_VDEV_SS_START_DISCONN_PROGRESS);
738 		/* block start request, if it is pending */
739 		mlme_vdev_stop_start_send(vdev_mlme, START_REQ,
740 					  event_data_len, event_data);
741 		status = true;
742 		break;
743 
744 	default:
745 		status = false;
746 		break;
747 	}
748 
749 	return status;
750 }
751 
752 /**
753  * mlme_vdev_subst_start_restart_progress_entry() - Entry API for Restart
754  *                                                  progress sub state
755  * @ctx: VDEV MLME object
756  *
757  * API to perform operations on moving to RESTART-PROGRESS substate
758  *
759  * Return: void
760  */
761 static void mlme_vdev_subst_start_restart_progress_entry(void *ctx)
762 {
763 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
764 	struct wlan_objmgr_vdev *vdev;
765 
766 	vdev = vdev_mlme->vdev;
767 
768 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_START)
769 		QDF_BUG(0);
770 
771 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_START_RESTART_PROGRESS);
772 }
773 
774 /**
775  * mlme_vdev_subst_start_restart_progress_exit() - Exit API for Restart Progress
776  *                                                 sub state
777  * @ctx: VDEV MLME object
778  *
779  * API to perform operations on moving out of RESTART-PROGRESS substate
780  *
781  * Return: void
782  */
783 static void mlme_vdev_subst_start_restart_progress_exit(void *ctx)
784 {
785 	/* NONE */
786 }
787 
788 /**
789  * mlme_vdev_subst_start_restart_progress_event() - Event handler API for
790  *                                                  Restart Progress substate
791  * @ctx: VDEV MLME object
792  *
793  * API to handle events in RESTART-PROGRESS substate
794  *
795  * Return: SUCCESS: on handling event
796  *         FAILURE: on ignoring the event
797  */
798 static bool mlme_vdev_subst_start_restart_progress_event(void *ctx,
799 		uint16_t event, uint16_t event_data_len, void *event_data)
800 {
801 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
802 	struct wlan_objmgr_vdev *vdev;
803 	bool status;
804 
805 	vdev = vdev_mlme->vdev;
806 
807 	switch (event) {
808 	case WLAN_VDEV_SM_EV_RESTART_REQ:
809 	/* If Start resp is pending, send restart after start response */
810 	case WLAN_VDEV_SM_EV_START_RESP:
811 		/* send vdev restart req command to FW */
812 		mlme_vdev_restart_send(vdev_mlme, event_data_len, event_data);
813 		status = true;
814 		break;
815 	case WLAN_VDEV_SM_EV_RESTART_RESP:
816 		mlme_vdev_sm_transition_to(vdev_mlme,
817 					   WLAN_VDEV_SS_START_CONN_PROGRESS);
818 		mlme_vdev_sm_deliver_event(vdev_mlme,
819 					   WLAN_VDEV_SM_EV_CONN_PROGRESS,
820 					   event_data_len, event_data);
821 		status = true;
822 		break;
823 
824 	case WLAN_VDEV_SM_EV_RESTART_REQ_FAIL:
825 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_SUSPEND);
826 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
827 					   event_data_len, event_data);
828 		status = true;
829 		break;
830 
831 	case WLAN_VDEV_SM_EV_DOWN:
832 		mlme_vdev_sm_transition_to(vdev_mlme,
833 					   WLAN_VDEV_SS_START_DISCONN_PROGRESS);
834 		/* block restart request, if it is pending */
835 		mlme_vdev_stop_start_send(vdev_mlme, RESTART_REQ,
836 					  event_data_len, event_data);
837 		status = true;
838 		break;
839 
840 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
841 		/* It is complicated to handle RADAR detected in this substate,
842 		 * as vdev updates des channels as bss channel on response,
843 		 * it would be easily handled, if it is deferred by DFS module
844 		 */
845 		QDF_BUG(0);
846 		status = true;
847 		break;
848 
849 	default:
850 		status = false;
851 		break;
852 	}
853 
854 	return status;
855 }
856 
857 /**
858  * mlme_vdev_subst_start_conn_progress_entry() - Entry API for Conn. Progress
859  *                                                sub state
860  * @ctx: VDEV MLME object
861  *
862  * API to perform operations on moving to CONN-PROGRESS substate
863  *
864  * Return: void
865  */
866 static void mlme_vdev_subst_start_conn_progress_entry(void *ctx)
867 {
868 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
869 	struct wlan_objmgr_vdev *vdev;
870 
871 	vdev = vdev_mlme->vdev;
872 
873 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_START)
874 		QDF_BUG(0);
875 
876 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_START_CONN_PROGRESS);
877 }
878 
879 /**
880  * mlme_vdev_subst_start_conn_progress_exit() - Exit API for Conn. Progress
881  *                                              sub state
882  * @ctx: VDEV MLME object
883  *
884  * API to perform operations on moving out of CONN-PROGRESS substate
885  *
886  * Return: void
887  */
888 static void mlme_vdev_subst_start_conn_progress_exit(void *ctx)
889 {
890 	/* NONE */
891 }
892 
893 /**
894  * mlme_vdev_subst_start_conn_progress_event() - Event handler API for Conn.
895  *                                                Progress substate
896  * @ctx: VDEV MLME object
897  *
898  * API to handle events in CONN-PROGRESS substate
899  *
900  * Return: SUCCESS: on handling event
901  *         FAILURE: on ignoring the event
902  */
903 static bool mlme_vdev_subst_start_conn_progress_event(void *ctx,
904 						      uint16_t event,
905 						      uint16_t event_data_len,
906 						      void *event_data)
907 {
908 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
909 	enum QDF_OPMODE mode;
910 	struct wlan_objmgr_vdev *vdev;
911 	bool status;
912 
913 	vdev = vdev_mlme->vdev;
914 
915 	mode = wlan_vdev_mlme_get_opmode(vdev);
916 
917 	switch (event) {
918 	case WLAN_VDEV_SM_EV_CONN_PROGRESS:
919 		/* This API decides to move to DFS CAC WAIT or UP state,
920 		 * for station notify connection state machine */
921 		mlme_vdev_start_continue(vdev_mlme, event_data_len, event_data);
922 		status = true;
923 		break;
924 
925 	case WLAN_VDEV_SM_EV_DFS_CAC_WAIT:
926 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_DFS_CAC_WAIT);
927 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
928 					   event_data_len, event_data);
929 		status = true;
930 		break;
931 
932 	case WLAN_VDEV_SM_EV_START_SUCCESS:
933 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_UP);
934 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
935 					   event_data_len, event_data);
936 		status = true;
937 		break;
938 
939 	case WLAN_VDEV_SM_EV_STA_CONN_START:
940 		/* This event triggers station connection, if it is blocked for
941 		 * CAC WAIT
942 		 */
943 		if (mode != QDF_STA_MODE)
944 			QDF_BUG(0);
945 
946 		mlme_vdev_sta_conn_start(vdev_mlme, event_data_len, event_data);
947 		status = true;
948 		break;
949 
950 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
951 		if (mode != QDF_STA_MODE)
952 			QDF_BUG(0);
953 
954 		status = true;
955 		break;
956 
957 	case WLAN_VDEV_SM_EV_DOWN:
958 	case WLAN_VDEV_SM_EV_CONNECTION_FAIL:
959 		mlme_vdev_sm_transition_to(vdev_mlme,
960 					   WLAN_VDEV_SS_START_DISCONN_PROGRESS);
961 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
962 					   event_data_len, event_data);
963 		status = true;
964 		break;
965 
966 	default:
967 		status = false;
968 		break;
969 	}
970 
971 	return status;
972 }
973 
974 /**
975  * mlme_vdev_subst_start_disconn_progress_entry() - Entry API for Disconn
976  *                                                  progress sub state
977  * @ctx: VDEV MLME object
978  *
979  * API to perform operations on moving to DISCONN-PROGRESS substate
980  *
981  * Return: SUCCESS: on handling event
982  *         FAILURE: on ignoring the event
983  */
984 static void mlme_vdev_subst_start_disconn_progress_entry(void *ctx)
985 {
986 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
987 	struct wlan_objmgr_vdev *vdev;
988 
989 	vdev = vdev_mlme->vdev;
990 
991 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_START)
992 		QDF_BUG(0);
993 
994 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_START_DISCONN_PROGRESS);
995 }
996 
997 /**
998  * mlme_vdev_subst_start_disconn_progress_exit() - Exit API for Disconn Progress
999  *                                                sub state
1000  * @ctx: VDEV MLME object
1001  *
1002  * API to perform operations on moving out of DISCONN-PROGRESS substate
1003  *
1004  * Return: void
1005  */
1006 static void mlme_vdev_subst_start_disconn_progress_exit(void *ctx)
1007 {
1008 	/* NONE */
1009 }
1010 
1011 /**
1012  * mlme_vdev_subst_start_disconn_progress_event() - Event handler API for Discon
1013  *                                                Progress substate
1014  * @ctx: VDEV MLME object
1015  *
1016  * API to handle events in DISCONN-PROGRESS substate
1017  *
1018  * Return: SUCCESS: on handling event
1019  *         FAILURE: on ignoring the event
1020  */
1021 static bool mlme_vdev_subst_start_disconn_progress_event(void *ctx,
1022 		uint16_t event, uint16_t event_data_len, void *event_data)
1023 {
1024 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1025 	bool status;
1026 
1027 	switch (event) {
1028 	case WLAN_VDEV_SM_EV_START_RESP:
1029 	/* clean up, if any needs to be cleaned up */
1030 	case WLAN_VDEV_SM_EV_CONNECTION_FAIL:
1031 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_STOP);
1032 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_DOWN,
1033 					   event_data_len, event_data);
1034 		status = true;
1035 		break;
1036 
1037 	case WLAN_VDEV_SM_EV_RESTART_RESP:
1038 	case WLAN_VDEV_SM_EV_RESTART_REQ_FAIL:
1039 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_SUSPEND);
1040 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_DOWN,
1041 					   event_data_len, event_data);
1042 		status = true;
1043 		break;
1044 
1045 	case WLAN_VDEV_SM_EV_START_REQ_FAIL:
1046 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_INIT);
1047 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
1048 					   event_data_len, event_data);
1049 		status = true;
1050 		break;
1051 
1052 	default:
1053 		status = false;
1054 		break;
1055 	}
1056 
1057 	return status;
1058 }
1059 
1060 /**
1061  * mlme_vdev_subst_suspend_suspend_down_entry() - Entry API for Suspend down
1062  *                                                sub state
1063  * @ctx: VDEV MLME object
1064  *
1065  * API to perform operations on moving to SUSPEND-DOWN substate
1066  *
1067  * Return: void
1068  */
1069 static void mlme_vdev_subst_suspend_suspend_down_entry(void *ctx)
1070 {
1071 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1072 	struct wlan_objmgr_vdev *vdev;
1073 
1074 	vdev = vdev_mlme->vdev;
1075 
1076 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1077 		QDF_BUG(0);
1078 
1079 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1080 }
1081 
1082 /**
1083  * mlme_vdev_subst_suspend_suspend_down_exit() - Exit API for Suspend down
1084  *                                                sub state
1085  * @ctx: VDEV MLME object
1086  *
1087  * API to perform operations on moving out of SUSPEND-DOWN substate
1088  *
1089  * Return: void
1090  */
1091 static void mlme_vdev_subst_suspend_suspend_down_exit(void *ctx)
1092 {
1093 	/* NONE */
1094 }
1095 
1096 /**
1097  * mlme_vdev_subst_suspend_suspend_down_event() - Event handler API for Suspend
1098  *                                                down substate
1099  * @ctx: VDEV MLME object
1100  *
1101  * API to handle events in SUSPEND-DOWN substate
1102  *
1103  * Return: SUCCESS: on handling event
1104  *         FAILURE: on ignoring the event
1105  */
1106 static bool mlme_vdev_subst_suspend_suspend_down_event(void *ctx,
1107 		uint16_t event, uint16_t event_data_len, void *event_data)
1108 {
1109 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1110 	bool status;
1111 
1112 	switch (event) {
1113 	case WLAN_VDEV_SM_EV_DOWN:
1114 	case WLAN_VDEV_SM_EV_RESTART_REQ_FAIL:
1115 		mlme_vdev_disconnect_peers(vdev_mlme,
1116 					   event_data_len, event_data);
1117 		status = true;
1118 		break;
1119 
1120 	case WLAN_VDEV_SM_EV_DISCONNECT_COMPLETE:
1121 		/* clean up, if any needs to be cleaned up */
1122 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_STOP);
1123 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_DOWN,
1124 					   event_data_len, event_data);
1125 		status = true;
1126 		break;
1127 
1128 	default:
1129 		status = false;
1130 		break;
1131 	}
1132 
1133 	return status;
1134 }
1135 
1136 /**
1137  * mlme_vdev_subst_suspend_suspend_restart_entry() - Entry API for Suspend
1138  *                                                   restart substate
1139  * @ctx: VDEV MLME object
1140  *
1141  * API to perform operations on moving to SUSPEND-RESTART substate
1142  *
1143  * Return: void
1144  */
1145 static void mlme_vdev_subst_suspend_suspend_restart_entry(void *ctx)
1146 {
1147 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1148 	struct wlan_objmgr_vdev *vdev;
1149 
1150 	vdev = vdev_mlme->vdev;
1151 
1152 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1153 		QDF_BUG(0);
1154 
1155 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_SUSPEND_RESTART);
1156 }
1157 
1158 /**
1159  * mlme_vdev_subst_suspend_suspend_restart_exit() - Exit API for Suspend restart
1160  *                                                sub state
1161  * @ctx: VDEV MLME object
1162  *
1163  * API to perform operations on moving out of SUSPEND-RESTART substate
1164  *
1165  * Return: void
1166  */
1167 static void mlme_vdev_subst_suspend_suspend_restart_exit(void *ctx)
1168 {
1169 	/* NONE */
1170 }
1171 
1172 /**
1173  * mlme_vdev_subst_suspend_suspend_restart_event() - Event handler API for
1174  *                                                   Suspend restart substate
1175  * @ctx: VDEV MLME object
1176  *
1177  * API to handle events in SUSPEND-RESTART substate
1178  *
1179  * Return: SUCCESS: on handling event
1180  *         FAILURE: on ignoring the event
1181  */
1182 static bool mlme_vdev_subst_suspend_suspend_restart_event(void *ctx,
1183 		uint16_t event, uint16_t event_data_len, void *event_data)
1184 {
1185 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1186 	bool status;
1187 
1188 	switch (event) {
1189 	case WLAN_VDEV_SM_EV_SUPSEND_RESTART:
1190 		mlme_vdev_disconnect_peers(vdev_mlme,
1191 					   event_data_len, event_data);
1192 		status = true;
1193 		break;
1194 
1195 	case WLAN_VDEV_SM_EV_DISCONNECT_COMPLETE:
1196 		/* clean up, if any needs to be cleaned up */
1197 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_START);
1198 		mlme_vdev_sm_deliver_event(vdev_mlme,
1199 					   WLAN_VDEV_SM_EV_RESTART_REQ,
1200 					   event_data_len, event_data);
1201 		status = true;
1202 		break;
1203 
1204 	case WLAN_VDEV_SM_EV_DOWN:
1205 		mlme_vdev_sm_transition_to(vdev_mlme,
1206 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1207 		status = true;
1208 		break;
1209 
1210 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
1211 		mlme_vdev_sm_transition_to(vdev_mlme,
1212 					   WLAN_VDEV_SS_SUSPEND_CSA_RESTART);
1213 		mlme_vdev_sm_deliver_event(vdev_mlme,
1214 					   WLAN_VDEV_SM_EV_CSA_RESTART,
1215 					   event_data_len, event_data);
1216 		status = true;
1217 		break;
1218 
1219 	default:
1220 		status = false;
1221 		break;
1222 	}
1223 
1224 	return status;
1225 }
1226 
1227 /**
1228  * mlme_vdev_subst_suspend_host_restart_entry() - Entry API for Host restart
1229  *                                                substate
1230  * @ctx: VDEV MLME object
1231  *
1232  * API to perform operations on moving to HOST-RESTART substate
1233  *
1234  * Return: void
1235  */
1236 static void mlme_vdev_subst_suspend_host_restart_entry(void *ctx)
1237 {
1238 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1239 	struct wlan_objmgr_vdev *vdev;
1240 
1241 	vdev = vdev_mlme->vdev;
1242 
1243 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1244 		QDF_BUG(0);
1245 
1246 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_HOST_RESTART);
1247 }
1248 
1249 /**
1250  * mlme_vdev_subst_suspend_host_restart_exit() - Exit API for host restart
1251  *                                                sub state
1252  * @ctx: VDEV MLME object
1253  *
1254  * API to perform operations on moving out of HOST-RESTART substate
1255  *
1256  * Return: void
1257  */
1258 static void mlme_vdev_subst_suspend_host_restart_exit(void *ctx)
1259 {
1260     /* NONE */
1261 }
1262 
1263 /**
1264  * mlme_vdev_subst_suspend_host_restart_entry() - Event handler API for Host
1265  *                                                restart substate
1266  * @ctx: VDEV MLME object
1267  *
1268  * API to handle events in HOST-RESTART substate
1269  *
1270  * Return: void
1271  */
1272 static bool mlme_vdev_subst_suspend_host_restart_event(void *ctx,
1273 		uint16_t event, uint16_t event_data_len, void *event_data)
1274 {
1275 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1276 	bool status;
1277 
1278 	switch (event) {
1279 	case WLAN_VDEV_SM_EV_HOST_RESTART:
1280 		mlme_vdev_disconnect_peers(vdev_mlme,
1281 					   event_data_len, event_data);
1282 		status = true;
1283 		break;
1284 
1285 	case WLAN_VDEV_SM_EV_DISCONNECT_COMPLETE:
1286 		/* VDEV up command need not be sent */
1287 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_UP);
1288 		mlme_vdev_sm_deliver_event(vdev_mlme,
1289 					   WLAN_VDEV_SM_EV_UP_HOST_RESTART,
1290 					   event_data_len, event_data);
1291 		status = true;
1292 		break;
1293 
1294 	case WLAN_VDEV_SM_EV_DOWN:
1295 		mlme_vdev_sm_transition_to(vdev_mlme,
1296 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1297 		status = true;
1298 		break;
1299 
1300 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
1301 		mlme_vdev_sm_transition_to(vdev_mlme,
1302 					   WLAN_VDEV_SS_SUSPEND_CSA_RESTART);
1303 		mlme_vdev_sm_deliver_event(vdev_mlme,
1304 					   WLAN_VDEV_SM_EV_CSA_RESTART,
1305 					   event_data_len, event_data);
1306 		status = true;
1307 		break;
1308 
1309 	default:
1310 		status = false;
1311 		break;
1312 	}
1313 
1314 	return status;
1315 }
1316 
1317 /**
1318  * mlme_vdev_subst_suspend_csa_restart_entry() - Entry API for CSA restart
1319  *                                               substate
1320  * @ctx: VDEV MLME object
1321  *
1322  * API to perform operations on moving to CSA-RESTART substate
1323  *
1324  * Return: void
1325  */
1326 static void mlme_vdev_subst_suspend_csa_restart_entry(void *ctx)
1327 {
1328 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1329 	struct wlan_objmgr_vdev *vdev;
1330 
1331 	vdev = vdev_mlme->vdev;
1332 
1333 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1334 		QDF_BUG(0);
1335 
1336 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_CSA_RESTART);
1337 }
1338 
1339 /**
1340  * mlme_vdev_subst_suspend_csa_restart_exit() - Exit API for CSA restart
1341  *                                                sub state
1342  * @ctx: VDEV MLME object
1343  *
1344  * API to perform operations on moving out of CSA-RESTART substate
1345  *
1346  * Return: void
1347  */
1348 static void mlme_vdev_subst_suspend_csa_restart_exit(void *ctx)
1349 {
1350     /* NONE */
1351 }
1352 
1353 /**
1354  * mlme_vdev_subst_suspend_csa_restart_event() - Event handler API for CSA
1355  *                                               restart substate
1356  * @ctx: VDEV MLME object
1357  *
1358  * API to handle events in CSA-RESTART substate
1359  *
1360  * Return: SUCCESS: on handling event
1361  *         FAILURE: on ignoring the event
1362  */
1363 static bool mlme_vdev_subst_suspend_csa_restart_event(void *ctx,
1364 		uint16_t event, uint16_t event_data_len, void *event_data)
1365 {
1366 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1367 	bool status;
1368 
1369 	switch (event) {
1370 	case WLAN_VDEV_SM_EV_CSA_RESTART:
1371 		mlme_vdev_update_beacon(vdev_mlme, BEACON_CSA,
1372 					event_data_len, event_data);
1373 		status = true;
1374 		break;
1375 	case WLAN_VDEV_SM_EV_CSA_COMPLETE:
1376 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_START);
1377 		mlme_vdev_sm_deliver_event(vdev_mlme,
1378 					   WLAN_VDEV_SM_EV_RESTART_REQ,
1379 					   event_data_len, event_data);
1380 		status = true;
1381 		break;
1382 
1383 	case WLAN_VDEV_SM_EV_DOWN:
1384 		mlme_vdev_sm_transition_to(vdev_mlme,
1385 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1386 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
1387 					   event_data_len, event_data);
1388 		status = true;
1389 		break;
1390 
1391 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
1392 		/* since channel change is already in progress,
1393 		 * dfs ignore radar detected event
1394 		 */
1395 		status = true;
1396 		break;
1397 
1398 	default:
1399 		status = false;
1400 		break;
1401 	}
1402 
1403 	return status;
1404 }
1405 
1406 /**
1407  * mlme_vdev_subst_stop_stop_progress_entry() - Entry API for Stop Progress
1408  *                                                sub state
1409  * @ctx: VDEV MLME object
1410  *
1411  * API to perform operations on moving to STOP-PROGRESS substate
1412  *
1413  * Return: void
1414  */
1415 static void mlme_vdev_subst_stop_stop_progress_entry(void *ctx)
1416 {
1417 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *) ctx;
1418 	struct wlan_objmgr_vdev *vdev;
1419 
1420 	vdev = vdev_mlme->vdev;
1421 
1422 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_STOP)
1423 		QDF_BUG(0);
1424 
1425 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_STOP_STOP_PROGRESS);
1426 }
1427 
1428 /**
1429  * mlme_vdev_subst_stop_stop_progress_exit() - Exit API for Stop Progress
1430  *                                                sub state
1431  * @ctx: VDEV MLME object
1432  *
1433  * API to perform operations on moving out of STOP-PROGRESS substate
1434  *
1435  * Return: void
1436  */
1437 static void mlme_vdev_subst_stop_stop_progress_exit(void *ctx)
1438 {
1439     /* NONE */
1440 }
1441 
1442 /**
1443  * mlme_vdev_subst_stop_stop_progress_event() - Event handler API for Stop
1444  *                                                Progress substate
1445  * @ctx: VDEV MLME object
1446  *
1447  * API to handle events in STOP-PROGRESS substate
1448  *
1449  * Return: SUCCESS: on handling event
1450  *         FAILURE: on ignoring the event
1451  */
1452 static bool mlme_vdev_subst_stop_stop_progress_event(void *ctx,
1453 		uint16_t event, uint16_t event_data_len, void *event_data)
1454 {
1455 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1456 	bool status;
1457 
1458 	/* Debug framework is required to hold the events */
1459 
1460 	switch (event) {
1461 	case WLAN_VDEV_SM_EV_DOWN:
1462 		/* send vdev stop command to FW and delete BSS peer*/
1463 		mlme_vdev_stop_send(vdev_mlme, event_data_len, event_data);
1464 		status = true;
1465 		break;
1466 
1467 	case WLAN_VDEV_SM_EV_STOP_RESP:
1468 		/* Processes stop response, and checks BSS peer delete wait
1469 		 * is needed
1470 		 */
1471 		mlme_vdev_stop_continue(vdev_mlme, event_data_len, event_data);
1472 		status = true;
1473 		break;
1474 
1475 	/* This event should be given by MLME on stop complete and BSS
1476 	 * peer delete complete to move forward
1477 	 */
1478 	case WLAN_VDEV_SM_EV_MLME_DOWN_REQ:
1479 		mlme_vdev_sm_transition_to(vdev_mlme,
1480 					   WLAN_VDEV_SS_STOP_DOWN_PROGRESS);
1481 		mlme_vdev_sm_deliver_event(vdev_mlme,
1482 					   WLAN_VDEV_SM_EV_MLME_DOWN_REQ,
1483 					   event_data_len, event_data);
1484 		status = true;
1485 		break;
1486 
1487 	case WLAN_VDEV_SM_EV_STOP_FAIL:
1488 		mlme_vdev_sm_transition_to(vdev_mlme,
1489 					   WLAN_VDEV_SS_STOP_DOWN_PROGRESS);
1490 		mlme_vdev_sm_deliver_event(vdev_mlme,
1491 					   WLAN_VDEV_SM_EV_MLME_DOWN_REQ,
1492 					   event_data_len, event_data);
1493 		status = true;
1494 		break;
1495 
1496 	default:
1497 		status = false;
1498 		break;
1499 	}
1500 
1501 	return status;
1502 }
1503 
1504 /**
1505  * mlme_vdev_subst_stop_down_progress_entry() - Entry API for Down Progress
1506  *                                                sub state
1507  * @ctx: VDEV MLME object
1508  *
1509  * API to perform operations on moving to DOWN-PROGRESS substate
1510  *
1511  * Return: void
1512  */
1513 static void mlme_vdev_subst_stop_down_progress_entry(void *ctx)
1514 {
1515 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1516 	struct wlan_objmgr_vdev *vdev;
1517 
1518 	vdev = vdev_mlme->vdev;
1519 
1520 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_STOP)
1521 		QDF_BUG(0);
1522 
1523 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_STOP_DOWN_PROGRESS);
1524 }
1525 
1526 /**
1527  * mlme_vdev_subst_stop_down_progress_exit() - Exit API for Down Progress
1528  *                                                sub state
1529  * @ctx: VDEV MLME object
1530  *
1531  * API to perform operations on moving out of DOWN-PROGRESS substate
1532  *
1533  * Return: void
1534  */
1535 static void mlme_vdev_subst_stop_down_progress_exit(void *ctx)
1536 {
1537 	/* NONE */
1538 }
1539 
1540 /**
1541  * mlme_vdev_subst_stop_down_progress_event() - Event handler API for Down
1542  *                                                Progress substate
1543  * @ctx: VDEV MLME object
1544  *
1545  * API to handle events in DOWN-PROGRESS substate
1546  *
1547  * Return: SUCCESS: on handling event
1548  *         FAILURE: on ignoring the event
1549  */
1550 static bool mlme_vdev_subst_stop_down_progress_event(void *ctx,
1551 		uint16_t event, uint16_t event_data_len, void *event_data)
1552 {
1553 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1554 	bool status;
1555 
1556 	switch (event) {
1557 	case WLAN_VDEV_SM_EV_DOWN:
1558 		status = true;
1559 		break;
1560 
1561 	case WLAN_VDEV_SM_EV_MLME_DOWN_REQ:
1562 		/* send vdev down command to FW, if send is successful, sends
1563 		 * DOWN_COMPLETE event
1564 		 */
1565 		mlme_vdev_down_send(vdev_mlme, event_data_len, event_data);
1566 		status = true;
1567 		break;
1568 
1569 	case WLAN_VDEV_SM_EV_DOWN_COMPLETE:
1570 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_INIT);
1571 		mlme_vdev_sm_deliver_event(vdev_mlme,
1572 					   WLAN_VDEV_SM_EV_DOWN_COMPLETE,
1573 					   event_data_len, event_data);
1574 		status = true;
1575 		break;
1576 
1577 	case WLAN_VDEV_SM_EV_DOWN_FAIL:
1578 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_INIT);
1579 		mlme_vdev_sm_deliver_event(vdev_mlme,
1580 					   WLAN_VDEV_SM_EV_DOWN_COMPLETE,
1581 					   event_data_len, event_data);
1582 		status = true;
1583 		break;
1584 
1585 	default:
1586 		status = false;
1587 		break;
1588 	}
1589 
1590 	return status;
1591 }
1592 
1593 
1594 static const char *vdev_sm_event_names[] = {
1595 	"VDEV_SM_EV_START",
1596 	"VDEV_SM_EV_START_REQ",
1597 	"VDEV_SM_EV_RESTART_REQ",
1598 	"VDEV_SM_EV_START_RESP",
1599 	"VDEV_SM_EV_RESTART_RESP",
1600 	"VDEV_SM_EV_START_REQ_FAIL",
1601 	"VDEV_SM_EV_RESTART_REQ_FAIL",
1602 	"VDEV_SM_EV_START_SUCCESS",
1603 	"VDEV_SM_EV_CONN_PROGRESS",
1604 	"VDEV_SM_EV_STA_CONN_START",
1605 	"VDEV_SM_EV_DFS_CAC_WAIT",
1606 	"VDEV_SM_EV_DFS_CAC_COMPLETED",
1607 	"VDEV_SM_EV_DOWN",
1608 	"VDEV_SM_EV_CONNECTION_FAIL",
1609 	"VDEV_SM_EV_STOP_RESP",
1610 	"VDEV_SM_EV_STOP_FAIL",
1611 	"VDEV_SM_EV_DOWN_FAIL",
1612 	"VDEV_SM_EV_DISCONNECT_COMPLETE",
1613 	"VDEV_SM_EV_SUPSEND_RESTART",
1614 	"VDEV_SM_EV_HOST_RESTART",
1615 	"VDEV_SM_EV_UP_HOST_RESTART",
1616 	"VDEV_SM_EV_FW_VDEV_RESTART",
1617 	"VDEV_SM_EV_UP_FAIL",
1618 	"VDEV_SM_EV_RADAR_DETECTED",
1619 	"VDEV_SM_EV_CSA_RESTART",
1620 	"VDEV_SM_EV_CSA_COMPLETE",
1621 	"VDEV_SM_EV_MLME_DOWN_REQ",
1622 	"VDEV_SM_EV_DOWN_COMPLETE",
1623 };
1624 
1625 struct wlan_sm_state_info sm_info[] = {
1626 	{
1627 		(uint8_t)WLAN_VDEV_S_INIT,
1628 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1629 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1630 		true,
1631 		"INIT",
1632 		mlme_vdev_state_init_entry,
1633 		mlme_vdev_state_init_exit,
1634 		mlme_vdev_state_init_event
1635 	},
1636 	{
1637 		(uint8_t)WLAN_VDEV_S_START,
1638 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1639 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1640 		true,
1641 		"START",
1642 		mlme_vdev_state_start_entry,
1643 		mlme_vdev_state_start_exit,
1644 		mlme_vdev_state_start_event
1645 	},
1646 	{
1647 		(uint8_t)WLAN_VDEV_S_DFS_CAC_WAIT,
1648 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1649 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1650 		true,
1651 		"DFS_CAC_WAIT",
1652 		mlme_vdev_state_dfs_cac_wait_entry,
1653 		mlme_vdev_state_dfs_cac_wait_exit,
1654 		mlme_vdev_state_dfs_cac_wait_event
1655 	},
1656 	{
1657 		(uint8_t)WLAN_VDEV_S_UP,
1658 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1659 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1660 		true,
1661 		"UP",
1662 		mlme_vdev_state_up_entry,
1663 		mlme_vdev_state_up_exit,
1664 		mlme_vdev_state_up_event
1665 	},
1666 	{
1667 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1668 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1669 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1670 		true,
1671 		"SUSPEND",
1672 		mlme_vdev_state_suspend_entry,
1673 		mlme_vdev_state_suspend_exit,
1674 		mlme_vdev_state_suspend_event
1675 	},
1676 	{
1677 		(uint8_t)WLAN_VDEV_S_STOP,
1678 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1679 		(uint8_t)WLAN_VDEV_SS_STOP_STOP_PROGRESS,
1680 		true,
1681 		"STOP",
1682 		mlme_vdev_state_stop_entry,
1683 		mlme_vdev_state_stop_exit,
1684 		mlme_vdev_state_stop_event
1685 	},
1686 	{
1687 		(uint8_t)WLAN_VDEV_S_MAX,
1688 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1689 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1690 		false,
1691 		"INVALID",
1692 		NULL,
1693 		NULL,
1694 		NULL
1695 	},
1696 	{
1697 		(uint8_t)WLAN_VDEV_SS_START_START_PROGRESS,
1698 		(uint8_t)WLAN_VDEV_S_START,
1699 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1700 		false,
1701 		"START-START_PROGRESS",
1702 		mlme_vdev_subst_start_start_progress_entry,
1703 		mlme_vdev_subst_start_start_progress_exit,
1704 		mlme_vdev_subst_start_start_progress_event
1705 	},
1706 	{
1707 		(uint8_t)WLAN_VDEV_SS_START_RESTART_PROGRESS,
1708 		(uint8_t)WLAN_VDEV_S_START,
1709 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1710 		false,
1711 		"START-RESTART_PROGRESS",
1712 		mlme_vdev_subst_start_restart_progress_entry,
1713 		mlme_vdev_subst_start_restart_progress_exit,
1714 		mlme_vdev_subst_start_restart_progress_event
1715 	},
1716 	{
1717 		(uint8_t)WLAN_VDEV_SS_START_CONN_PROGRESS,
1718 		(uint8_t)WLAN_VDEV_S_START,
1719 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1720 		false,
1721 		"START-CONN_PROGRESS",
1722 		mlme_vdev_subst_start_conn_progress_entry,
1723 		mlme_vdev_subst_start_conn_progress_exit,
1724 		mlme_vdev_subst_start_conn_progress_event
1725 	},
1726 	{
1727 		(uint8_t)WLAN_VDEV_SS_START_DISCONN_PROGRESS,
1728 		(uint8_t)WLAN_VDEV_S_START,
1729 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1730 		false,
1731 		"START-DISCONN_PROGRESS",
1732 		mlme_vdev_subst_start_disconn_progress_entry,
1733 		mlme_vdev_subst_start_disconn_progress_exit,
1734 		mlme_vdev_subst_start_disconn_progress_event
1735 	},
1736 	{
1737 		(uint8_t)WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN,
1738 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1739 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1740 		false,
1741 		"SUSPEND-SUSPEND_DOWN",
1742 		mlme_vdev_subst_suspend_suspend_down_entry,
1743 		mlme_vdev_subst_suspend_suspend_down_exit,
1744 		mlme_vdev_subst_suspend_suspend_down_event
1745 	},
1746 	{
1747 		(uint8_t)WLAN_VDEV_SS_SUSPEND_SUSPEND_RESTART,
1748 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1749 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1750 		false,
1751 		"SUSPEND-SUSPEND_RESTART",
1752 		mlme_vdev_subst_suspend_suspend_restart_entry,
1753 		mlme_vdev_subst_suspend_suspend_restart_exit,
1754 		mlme_vdev_subst_suspend_suspend_restart_event
1755 	},
1756 	{
1757 		(uint8_t)WLAN_VDEV_SS_SUSPEND_HOST_RESTART,
1758 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1759 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1760 		false,
1761 		"SUSPEND-HOST_RESTART",
1762 		mlme_vdev_subst_suspend_host_restart_entry,
1763 		mlme_vdev_subst_suspend_host_restart_exit,
1764 		mlme_vdev_subst_suspend_host_restart_event
1765 	},
1766 	{
1767 		(uint8_t)WLAN_VDEV_SS_SUSPEND_CSA_RESTART,
1768 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1769 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1770 		false,
1771 		"SUSPEND-CSA_RESTART",
1772 		mlme_vdev_subst_suspend_csa_restart_entry,
1773 		mlme_vdev_subst_suspend_csa_restart_exit,
1774 		mlme_vdev_subst_suspend_csa_restart_event
1775 	},
1776 	{
1777 		(uint8_t)WLAN_VDEV_SS_STOP_STOP_PROGRESS,
1778 		(uint8_t)WLAN_VDEV_S_STOP,
1779 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1780 		false,
1781 		"STOP-STOP_PROGRESS",
1782 		mlme_vdev_subst_stop_stop_progress_entry,
1783 		mlme_vdev_subst_stop_stop_progress_exit,
1784 		mlme_vdev_subst_stop_stop_progress_event
1785 	},
1786 	{
1787 		(uint8_t)WLAN_VDEV_SS_STOP_DOWN_PROGRESS,
1788 		(uint8_t)WLAN_VDEV_S_STOP,
1789 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1790 		false,
1791 		"STOP-DOWN_PROGRESS",
1792 		mlme_vdev_subst_stop_down_progress_entry,
1793 		mlme_vdev_subst_stop_down_progress_exit,
1794 		mlme_vdev_subst_stop_down_progress_event
1795 	},
1796 	{
1797 		(uint8_t)WLAN_VDEV_SS_IDLE,
1798 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1799 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1800 		false,
1801 		"INVALID",
1802 		NULL,
1803 		NULL,
1804 		NULL,
1805 	},
1806 	{
1807 		(uint8_t)WLAN_VDEV_SS_MAX,
1808 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1809 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1810 		false,
1811 		"INVALID",
1812 		NULL,
1813 		NULL,
1814 		NULL,
1815 	},
1816 };
1817 
1818 QDF_STATUS mlme_vdev_sm_deliver_event(struct vdev_mlme_obj *vdev_mlme,
1819 				      enum wlan_vdev_sm_evt event,
1820 				      uint16_t event_data_len, void *event_data)
1821 {
1822 	return wlan_sm_dispatch(vdev_mlme->sm_hdl, event,
1823 				event_data_len, event_data);
1824 }
1825 
1826 #ifdef SM_ENG_HIST_ENABLE
1827 void mlme_vdev_sm_history_print(struct vdev_mlme_obj *vdev_mlme)
1828 {
1829 	return wlan_sm_print_history(vdev_mlme->sm_hdl);
1830 }
1831 #endif
1832 
1833 QDF_STATUS mlme_vdev_sm_create(struct vdev_mlme_obj *vdev_mlme)
1834 {
1835 	struct wlan_sm *sm;
1836 	uint8_t name[WLAN_SM_ENGINE_MAX_NAME];
1837 
1838 	qdf_snprintf(name, sizeof(name), "VDEV%d-MLME",
1839 		     wlan_vdev_get_id(vdev_mlme->vdev));
1840 	sm = wlan_sm_create(name, vdev_mlme,
1841 			    WLAN_VDEV_S_INIT,
1842 			    sm_info,
1843 			    QDF_ARRAY_SIZE(sm_info),
1844 			    vdev_sm_event_names,
1845 			    QDF_ARRAY_SIZE(vdev_sm_event_names));
1846 	if (!sm) {
1847 		mlme_err("VDEV MLME SM allocation failed");
1848 		return QDF_STATUS_E_FAILURE;
1849 	}
1850 	vdev_mlme->sm_hdl = sm;
1851 
1852 	mlme_vdev_sm_spinlock_create(vdev_mlme);
1853 
1854 	mlme_vdev_cmd_mutex_create(vdev_mlme);
1855 
1856 	return QDF_STATUS_SUCCESS;
1857 }
1858 
1859 #else
1860 
1861 QDF_STATUS mlme_vdev_sm_create(struct vdev_mlme_obj *vdev_mlme)
1862 {
1863 	struct wlan_sm *sm;
1864 	uint8_t name[WLAN_SM_ENGINE_MAX_NAME];
1865 
1866 	qdf_snprintf(name, sizeof(name), "VDEV%d-MLME",
1867 		     wlan_vdev_get_id(vdev_mlme->vdev));
1868 
1869 	sm = wlan_sm_create(name, vdev_mlme, 0, NULL, 0, NULL, 0);
1870 	if (!sm) {
1871 		mlme_err("VDEV MLME SM allocation failed");
1872 		return QDF_STATUS_E_FAILURE;
1873 	}
1874 	vdev_mlme->sm_hdl = sm;
1875 
1876 	mlme_vdev_sm_spinlock_create(vdev_mlme);
1877 
1878 	mlme_vdev_cmd_mutex_create(vdev_mlme);
1879 
1880 	return QDF_STATUS_SUCCESS;
1881 }
1882 #endif
1883 
1884 QDF_STATUS mlme_vdev_sm_destroy(struct vdev_mlme_obj *vdev_mlme)
1885 {
1886 	mlme_vdev_cmd_mutex_destroy(vdev_mlme);
1887 
1888 	mlme_vdev_sm_spinlock_destroy(vdev_mlme);
1889 
1890 	wlan_sm_delete(vdev_mlme->sm_hdl);
1891 
1892 	return QDF_STATUS_SUCCESS;
1893 }
1894