xref: /wlan-dirver/qca-wifi-host-cmn/umac/mlme/vdev_mgr/core/src/vdev_mlme_sm.c (revision 11f5a63a6cbdda84849a730de22f0a71e635d58c)
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 any
5  * purpose with or without fee is hereby granted, provided that the above
6  * copyright notice and this permission notice appear in all copies.
7  *
8  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15  */
16 
17 /**
18  * DOC: Implements VDEV MLME SM
19  */
20 
21 #include <wlan_objmgr_vdev_obj.h>
22 #include <wlan_mlme_dbg.h>
23 #include <wlan_sm_engine.h>
24 #include "include/wlan_vdev_mlme.h"
25 #include "vdev_mlme_sm.h"
26 
27 /**
28  * mlme_vdev_set_state() - set mlme state
29  * @vdev: VDEV object
30  * @state: MLME state
31  *
32  * API to set MLME state
33  *
34  * Return: void
35  */
36 static void mlme_vdev_set_state(struct wlan_objmgr_vdev *vdev,
37 				enum wlan_vdev_state state)
38 {
39 	if (state < WLAN_VDEV_S_MAX) {
40 		vdev->vdev_mlme.mlme_state = state;
41 	} else {
42 		mlme_err("mlme state (%d) is invalid", state);
43 		QDF_BUG(0);
44 	}
45 }
46 
47 /**
48  * mlme_vdev_set_substate() - set mlme sub state
49  * @vdev: VDEV object
50  * @substate: MLME sub state
51  *
52  * API to set MLME sub state
53  *
54  * Return: void
55  */
56 static void mlme_vdev_set_substate(struct wlan_objmgr_vdev *vdev,
57 				   enum wlan_vdev_state substate)
58 {
59 	if ((substate > WLAN_VDEV_S_MAX) && (substate < WLAN_VDEV_SS_MAX)) {
60 		vdev->vdev_mlme.mlme_substate = substate;
61 	} else {
62 		mlme_err(" mlme sub state (%d) is invalid", substate);
63 		QDF_BUG(0);
64 	}
65 }
66 
67 /**
68  * mlme_vdev_sm_state_update() - set mlme state and sub state
69  * @vdev_mlme: MLME VDEV comp object
70  * @state: MLME state
71  * @substate: MLME sub state
72  *
73  * API to invoke util APIs to set state and MLME sub state
74  *
75  * Return: void
76  */
77 static void mlme_vdev_sm_state_update(struct vdev_mlme_obj *vdev_mlme,
78 				      enum wlan_vdev_state state,
79 				      enum wlan_vdev_state substate)
80 {
81 	struct wlan_objmgr_vdev *vdev;
82 
83 	vdev = vdev_mlme->vdev;
84 	if (!vdev) {
85 		mlme_err(" VDEV is NULL");
86 		QDF_BUG(0);
87 	}
88 
89 	mlme_vdev_set_state(vdev, state);
90 	mlme_vdev_set_substate(vdev, substate);
91 }
92 
93 /**
94  * mlme_vdev_sm_transition_to() - invokes state transition
95  * @vdev_mlme: MLME VDEV comp object
96  * @state: new MLME state
97  *
98  * API to invoke SM API to move to new state
99  *
100  * Return: void
101  */
102 static void mlme_vdev_sm_transition_to(struct vdev_mlme_obj *vdev_mlme,
103 				       enum wlan_vdev_state state)
104 {
105 	wlan_sm_transition_to(vdev_mlme->sm_hdl, state);
106 }
107 
108 /**
109  * mlme_vdev_state_init_entry() - Entry API for Init state
110  * @ctx: VDEV MLME object
111  *
112  * API to perform operations on moving to INIT state
113  *
114  * Return: void
115  */
116 static void mlme_vdev_state_init_entry(void *ctx)
117 {
118 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
119 
120 	mlme_vdev_sm_state_update(vdev_mlme, WLAN_VDEV_S_INIT,
121 				  WLAN_VDEV_SS_IDLE);
122 }
123 
124 /**
125  * mlme_vdev_state_init_exit() - Exit API for Init state
126  * @ctx: VDEV MLME object
127  *
128  * API to perform operations on moving out of INIT state
129  *
130  * Return: void
131  */
132 static void mlme_vdev_state_init_exit(void *ctx)
133 {
134 	/* NONE */
135 }
136 
137 /**
138  * mlme_vdev_state_init_event() - Init State event handler
139  * @ctx: VDEV MLME object
140  *
141  * API to handle events in INIT state
142  *
143  * Return: SUCCESS: on handling event
144  *         FAILURE: on ignoring the event
145  */
146 static bool mlme_vdev_state_init_event(void *ctx, uint16_t event,
147 				       uint16_t event_data_len,
148 				       void *event_data)
149 {
150 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
151 	bool status;
152 
153 	switch (event) {
154 	case WLAN_VDEV_SM_EV_START:
155 		/* call mlme callback API for sanity checks */
156 		if (mlme_vdev_validate_basic_params(vdev_mlme, event_data_len,
157 					event_data) == QDF_STATUS_SUCCESS) {
158 			mlme_vdev_sm_transition_to(vdev_mlme,
159 						   WLAN_VDEV_S_START);
160 			mlme_vdev_sm_deliver_event(vdev_mlme,
161 						   WLAN_VDEV_SM_EV_START_REQ,
162 						   event_data_len, event_data);
163 			status = true;
164 		} else {
165 			mlme_err(
166 			"failed to validate vdev init params to move to START state");
167 			status = true;
168 			mlme_vdev_notify_down_complete(vdev_mlme,
169 						       event_data_len,
170 						       event_data);
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_STOP_REQ,
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_SUSPEND_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_SUSPEND_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 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
891 
892 	mlme_vdev_notify_start_state_exit(vdev_mlme);
893 }
894 
895 /**
896  * mlme_vdev_subst_start_conn_progress_event() - Event handler API for Conn.
897  *                                                Progress substate
898  * @ctx: VDEV MLME object
899  *
900  * API to handle events in CONN-PROGRESS substate
901  *
902  * Return: SUCCESS: on handling event
903  *         FAILURE: on ignoring the event
904  */
905 static bool mlme_vdev_subst_start_conn_progress_event(void *ctx,
906 						      uint16_t event,
907 						      uint16_t event_data_len,
908 						      void *event_data)
909 {
910 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
911 	enum QDF_OPMODE mode;
912 	struct wlan_objmgr_vdev *vdev;
913 	bool status;
914 
915 	vdev = vdev_mlme->vdev;
916 
917 	mode = wlan_vdev_mlme_get_opmode(vdev);
918 
919 	switch (event) {
920 	case WLAN_VDEV_SM_EV_CONN_PROGRESS:
921 		/* This API decides to move to DFS CAC WAIT or UP state,
922 		 * for station notify connection state machine */
923 		if (mlme_vdev_start_continue(vdev_mlme, event_data_len,
924 					     event_data) != QDF_STATUS_SUCCESS)
925 			mlme_vdev_sm_deliver_event(
926 					vdev_mlme,
927 					WLAN_VDEV_SM_EV_CONNECTION_FAIL,
928 					event_data_len, event_data);
929 		status = true;
930 		break;
931 
932 	case WLAN_VDEV_SM_EV_DFS_CAC_WAIT:
933 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_DFS_CAC_WAIT);
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_START_SUCCESS:
940 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_UP);
941 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
942 					   event_data_len, event_data);
943 		status = true;
944 		break;
945 
946 	case WLAN_VDEV_SM_EV_STA_CONN_START:
947 		/* This event triggers station connection, if it is blocked for
948 		 * CAC WAIT
949 		 */
950 		if (mode != QDF_STA_MODE)
951 			QDF_BUG(0);
952 
953 		mlme_vdev_sta_conn_start(vdev_mlme, event_data_len, event_data);
954 		status = true;
955 		break;
956 
957 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
958 		if (mode != QDF_STA_MODE)
959 			QDF_BUG(0);
960 
961 		status = true;
962 		break;
963 
964 	case WLAN_VDEV_SM_EV_DOWN:
965 	case WLAN_VDEV_SM_EV_CONNECTION_FAIL:
966 		mlme_vdev_sm_transition_to(vdev_mlme,
967 					   WLAN_VDEV_SS_START_DISCONN_PROGRESS);
968 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
969 					   event_data_len, event_data);
970 		status = true;
971 		break;
972 
973 	default:
974 		status = false;
975 		break;
976 	}
977 
978 	return status;
979 }
980 
981 /**
982  * mlme_vdev_subst_start_disconn_progress_entry() - Entry API for Disconn
983  *                                                  progress sub state
984  * @ctx: VDEV MLME object
985  *
986  * API to perform operations on moving to DISCONN-PROGRESS substate
987  *
988  * Return: SUCCESS: on handling event
989  *         FAILURE: on ignoring the event
990  */
991 static void mlme_vdev_subst_start_disconn_progress_entry(void *ctx)
992 {
993 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
994 	struct wlan_objmgr_vdev *vdev;
995 
996 	vdev = vdev_mlme->vdev;
997 
998 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_START)
999 		QDF_BUG(0);
1000 
1001 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_START_DISCONN_PROGRESS);
1002 }
1003 
1004 /**
1005  * mlme_vdev_subst_start_disconn_progress_exit() - Exit API for Disconn Progress
1006  *                                                sub state
1007  * @ctx: VDEV MLME object
1008  *
1009  * API to perform operations on moving out of DISCONN-PROGRESS substate
1010  *
1011  * Return: void
1012  */
1013 static void mlme_vdev_subst_start_disconn_progress_exit(void *ctx)
1014 {
1015 	/* NONE */
1016 }
1017 
1018 /**
1019  * mlme_vdev_subst_start_disconn_progress_event() - Event handler API for Discon
1020  *                                                Progress substate
1021  * @ctx: VDEV MLME object
1022  *
1023  * API to handle events in DISCONN-PROGRESS substate
1024  *
1025  * Return: SUCCESS: on handling event
1026  *         FAILURE: on ignoring the event
1027  */
1028 static bool mlme_vdev_subst_start_disconn_progress_event(void *ctx,
1029 		uint16_t event, uint16_t event_data_len, void *event_data)
1030 {
1031 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1032 	bool status;
1033 
1034 	switch (event) {
1035 	case WLAN_VDEV_SM_EV_START_RESP:
1036 	/* clean up, if any needs to be cleaned up */
1037 	case WLAN_VDEV_SM_EV_CONNECTION_FAIL:
1038 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_STOP);
1039 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_STOP_REQ,
1040 					   event_data_len, event_data);
1041 		status = true;
1042 		break;
1043 
1044 	case WLAN_VDEV_SM_EV_RESTART_RESP:
1045 	case WLAN_VDEV_SM_EV_RESTART_REQ_FAIL:
1046 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_SUSPEND);
1047 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_DOWN,
1048 					   event_data_len, event_data);
1049 		status = true;
1050 		break;
1051 
1052 	case WLAN_VDEV_SM_EV_START_REQ_FAIL:
1053 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_INIT);
1054 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
1055 					   event_data_len, event_data);
1056 		status = true;
1057 		break;
1058 
1059 	default:
1060 		status = false;
1061 		break;
1062 	}
1063 
1064 	return status;
1065 }
1066 
1067 /**
1068  * mlme_vdev_subst_suspend_suspend_down_entry() - Entry API for Suspend down
1069  *                                                sub state
1070  * @ctx: VDEV MLME object
1071  *
1072  * API to perform operations on moving to SUSPEND-DOWN substate
1073  *
1074  * Return: void
1075  */
1076 static void mlme_vdev_subst_suspend_suspend_down_entry(void *ctx)
1077 {
1078 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1079 	struct wlan_objmgr_vdev *vdev;
1080 
1081 	vdev = vdev_mlme->vdev;
1082 
1083 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1084 		QDF_BUG(0);
1085 
1086 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1087 }
1088 
1089 /**
1090  * mlme_vdev_subst_suspend_suspend_down_exit() - Exit API for Suspend down
1091  *                                                sub state
1092  * @ctx: VDEV MLME object
1093  *
1094  * API to perform operations on moving out of SUSPEND-DOWN substate
1095  *
1096  * Return: void
1097  */
1098 static void mlme_vdev_subst_suspend_suspend_down_exit(void *ctx)
1099 {
1100 	/* NONE */
1101 }
1102 
1103 /**
1104  * mlme_vdev_subst_suspend_suspend_down_event() - Event handler API for Suspend
1105  *                                                down substate
1106  * @ctx: VDEV MLME object
1107  *
1108  * API to handle events in SUSPEND-DOWN substate
1109  *
1110  * Return: SUCCESS: on handling event
1111  *         FAILURE: on ignoring the event
1112  */
1113 static bool mlme_vdev_subst_suspend_suspend_down_event(void *ctx,
1114 		uint16_t event, uint16_t event_data_len, void *event_data)
1115 {
1116 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1117 	bool status;
1118 
1119 	switch (event) {
1120 	case WLAN_VDEV_SM_EV_DOWN:
1121 	case WLAN_VDEV_SM_EV_RESTART_REQ_FAIL:
1122 		mlme_vdev_disconnect_peers(vdev_mlme,
1123 					   event_data_len, event_data);
1124 		status = true;
1125 		break;
1126 
1127 	case WLAN_VDEV_SM_EV_DISCONNECT_COMPLETE:
1128 		/* clean up, if any needs to be cleaned up */
1129 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_STOP);
1130 		mlme_vdev_sm_deliver_event(vdev_mlme, WLAN_VDEV_SM_EV_STOP_REQ,
1131 					   event_data_len, event_data);
1132 		status = true;
1133 		break;
1134 
1135 	default:
1136 		status = false;
1137 		break;
1138 	}
1139 
1140 	return status;
1141 }
1142 
1143 /**
1144  * mlme_vdev_subst_suspend_suspend_restart_entry() - Entry API for Suspend
1145  *                                                   restart substate
1146  * @ctx: VDEV MLME object
1147  *
1148  * API to perform operations on moving to SUSPEND-RESTART substate
1149  *
1150  * Return: void
1151  */
1152 static void mlme_vdev_subst_suspend_suspend_restart_entry(void *ctx)
1153 {
1154 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1155 	struct wlan_objmgr_vdev *vdev;
1156 
1157 	vdev = vdev_mlme->vdev;
1158 
1159 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1160 		QDF_BUG(0);
1161 
1162 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_SUSPEND_RESTART);
1163 }
1164 
1165 /**
1166  * mlme_vdev_subst_suspend_suspend_restart_exit() - Exit API for Suspend restart
1167  *                                                sub state
1168  * @ctx: VDEV MLME object
1169  *
1170  * API to perform operations on moving out of SUSPEND-RESTART substate
1171  *
1172  * Return: void
1173  */
1174 static void mlme_vdev_subst_suspend_suspend_restart_exit(void *ctx)
1175 {
1176 	/* NONE */
1177 }
1178 
1179 /**
1180  * mlme_vdev_subst_suspend_suspend_restart_event() - Event handler API for
1181  *                                                   Suspend restart substate
1182  * @ctx: VDEV MLME object
1183  *
1184  * API to handle events in SUSPEND-RESTART substate
1185  *
1186  * Return: SUCCESS: on handling event
1187  *         FAILURE: on ignoring the event
1188  */
1189 static bool mlme_vdev_subst_suspend_suspend_restart_event(void *ctx,
1190 		uint16_t event, uint16_t event_data_len, void *event_data)
1191 {
1192 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1193 	bool status;
1194 
1195 	switch (event) {
1196 	case WLAN_VDEV_SM_EV_SUSPEND_RESTART:
1197 		mlme_vdev_disconnect_peers(vdev_mlme,
1198 					   event_data_len, event_data);
1199 		status = true;
1200 		break;
1201 
1202 	case WLAN_VDEV_SM_EV_DISCONNECT_COMPLETE:
1203 		/* clean up, if any needs to be cleaned up */
1204 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_START);
1205 		mlme_vdev_sm_deliver_event(vdev_mlme,
1206 					   WLAN_VDEV_SM_EV_RESTART_REQ,
1207 					   event_data_len, event_data);
1208 		status = true;
1209 		break;
1210 
1211 	case WLAN_VDEV_SM_EV_DOWN:
1212 		mlme_vdev_sm_transition_to(vdev_mlme,
1213 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1214 		status = true;
1215 		break;
1216 
1217 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
1218 		mlme_vdev_sm_transition_to(vdev_mlme,
1219 					   WLAN_VDEV_SS_SUSPEND_CSA_RESTART);
1220 		mlme_vdev_sm_deliver_event(vdev_mlme,
1221 					   WLAN_VDEV_SM_EV_CSA_RESTART,
1222 					   event_data_len, event_data);
1223 		status = true;
1224 		break;
1225 
1226 	default:
1227 		status = false;
1228 		break;
1229 	}
1230 
1231 	return status;
1232 }
1233 
1234 /**
1235  * mlme_vdev_subst_suspend_host_restart_entry() - Entry API for Host restart
1236  *                                                substate
1237  * @ctx: VDEV MLME object
1238  *
1239  * API to perform operations on moving to HOST-RESTART substate
1240  *
1241  * Return: void
1242  */
1243 static void mlme_vdev_subst_suspend_host_restart_entry(void *ctx)
1244 {
1245 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1246 	struct wlan_objmgr_vdev *vdev;
1247 
1248 	vdev = vdev_mlme->vdev;
1249 
1250 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1251 		QDF_BUG(0);
1252 
1253 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_HOST_RESTART);
1254 }
1255 
1256 /**
1257  * mlme_vdev_subst_suspend_host_restart_exit() - Exit API for host restart
1258  *                                                sub state
1259  * @ctx: VDEV MLME object
1260  *
1261  * API to perform operations on moving out of HOST-RESTART substate
1262  *
1263  * Return: void
1264  */
1265 static void mlme_vdev_subst_suspend_host_restart_exit(void *ctx)
1266 {
1267     /* NONE */
1268 }
1269 
1270 /**
1271  * mlme_vdev_subst_suspend_host_restart_entry() - Event handler API for Host
1272  *                                                restart substate
1273  * @ctx: VDEV MLME object
1274  *
1275  * API to handle events in HOST-RESTART substate
1276  *
1277  * Return: void
1278  */
1279 static bool mlme_vdev_subst_suspend_host_restart_event(void *ctx,
1280 		uint16_t event, uint16_t event_data_len, void *event_data)
1281 {
1282 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1283 	bool status;
1284 
1285 	switch (event) {
1286 	case WLAN_VDEV_SM_EV_HOST_RESTART:
1287 		mlme_vdev_disconnect_peers(vdev_mlme,
1288 					   event_data_len, event_data);
1289 		status = true;
1290 		break;
1291 
1292 	case WLAN_VDEV_SM_EV_DISCONNECT_COMPLETE:
1293 		/* VDEV up command need not be sent */
1294 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_UP);
1295 		mlme_vdev_sm_deliver_event(vdev_mlme,
1296 					   WLAN_VDEV_SM_EV_UP_HOST_RESTART,
1297 					   event_data_len, event_data);
1298 		status = true;
1299 		break;
1300 
1301 	case WLAN_VDEV_SM_EV_DOWN:
1302 		mlme_vdev_sm_transition_to(vdev_mlme,
1303 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1304 		status = true;
1305 		break;
1306 
1307 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
1308 		mlme_vdev_sm_transition_to(vdev_mlme,
1309 					   WLAN_VDEV_SS_SUSPEND_CSA_RESTART);
1310 		mlme_vdev_sm_deliver_event(vdev_mlme,
1311 					   WLAN_VDEV_SM_EV_CSA_RESTART,
1312 					   event_data_len, event_data);
1313 		status = true;
1314 		break;
1315 
1316 	default:
1317 		status = false;
1318 		break;
1319 	}
1320 
1321 	return status;
1322 }
1323 
1324 /**
1325  * mlme_vdev_subst_suspend_csa_restart_entry() - Entry API for CSA restart
1326  *                                               substate
1327  * @ctx: VDEV MLME object
1328  *
1329  * API to perform operations on moving to CSA-RESTART substate
1330  *
1331  * Return: void
1332  */
1333 static void mlme_vdev_subst_suspend_csa_restart_entry(void *ctx)
1334 {
1335 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1336 	struct wlan_objmgr_vdev *vdev;
1337 
1338 	vdev = vdev_mlme->vdev;
1339 
1340 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_SUSPEND)
1341 		QDF_BUG(0);
1342 
1343 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_SUSPEND_CSA_RESTART);
1344 }
1345 
1346 /**
1347  * mlme_vdev_subst_suspend_csa_restart_exit() - Exit API for CSA restart
1348  *                                                sub state
1349  * @ctx: VDEV MLME object
1350  *
1351  * API to perform operations on moving out of CSA-RESTART substate
1352  *
1353  * Return: void
1354  */
1355 static void mlme_vdev_subst_suspend_csa_restart_exit(void *ctx)
1356 {
1357     /* NONE */
1358 }
1359 
1360 /**
1361  * mlme_vdev_subst_suspend_csa_restart_event() - Event handler API for CSA
1362  *                                               restart substate
1363  * @ctx: VDEV MLME object
1364  *
1365  * API to handle events in CSA-RESTART substate
1366  *
1367  * Return: SUCCESS: on handling event
1368  *         FAILURE: on ignoring the event
1369  */
1370 static bool mlme_vdev_subst_suspend_csa_restart_event(void *ctx,
1371 		uint16_t event, uint16_t event_data_len, void *event_data)
1372 {
1373 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1374 	bool status;
1375 
1376 	switch (event) {
1377 	case WLAN_VDEV_SM_EV_CSA_RESTART:
1378 		mlme_vdev_update_beacon(vdev_mlme, BEACON_CSA,
1379 					event_data_len, event_data);
1380 		status = true;
1381 		break;
1382 	case WLAN_VDEV_SM_EV_CSA_COMPLETE:
1383 		if (mlme_vdev_is_newchan_no_cac(vdev_mlme) ==
1384 						QDF_STATUS_SUCCESS) {
1385 			mlme_vdev_sm_transition_to(vdev_mlme,
1386 						   WLAN_VDEV_S_START);
1387 			mlme_vdev_sm_deliver_event(vdev_mlme,
1388 						   WLAN_VDEV_SM_EV_RESTART_REQ,
1389 						   event_data_len, event_data);
1390 		} else {
1391 			mlme_vdev_sm_transition_to
1392 				(vdev_mlme,
1393 				 WLAN_VDEV_SS_SUSPEND_SUSPEND_RESTART);
1394 			mlme_vdev_sm_deliver_event
1395 				(vdev_mlme, WLAN_VDEV_SM_EV_SUSPEND_RESTART,
1396 				 event_data_len, event_data);
1397 		}
1398 		status = true;
1399 		break;
1400 
1401 	case WLAN_VDEV_SM_EV_DOWN:
1402 		mlme_vdev_sm_transition_to(vdev_mlme,
1403 					   WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN);
1404 		mlme_vdev_sm_deliver_event(vdev_mlme, event,
1405 					   event_data_len, event_data);
1406 		status = true;
1407 		break;
1408 
1409 	case WLAN_VDEV_SM_EV_RADAR_DETECTED:
1410 		/* since channel change is already in progress,
1411 		 * dfs ignore radar detected event
1412 		 */
1413 		status = true;
1414 		break;
1415 
1416 	default:
1417 		status = false;
1418 		break;
1419 	}
1420 
1421 	return status;
1422 }
1423 
1424 /**
1425  * mlme_vdev_subst_stop_stop_progress_entry() - Entry API for Stop Progress
1426  *                                                sub state
1427  * @ctx: VDEV MLME object
1428  *
1429  * API to perform operations on moving to STOP-PROGRESS substate
1430  *
1431  * Return: void
1432  */
1433 static void mlme_vdev_subst_stop_stop_progress_entry(void *ctx)
1434 {
1435 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *) ctx;
1436 	struct wlan_objmgr_vdev *vdev;
1437 
1438 	vdev = vdev_mlme->vdev;
1439 
1440 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_STOP)
1441 		QDF_BUG(0);
1442 
1443 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_STOP_STOP_PROGRESS);
1444 }
1445 
1446 /**
1447  * mlme_vdev_subst_stop_stop_progress_exit() - Exit API for Stop Progress
1448  *                                                sub state
1449  * @ctx: VDEV MLME object
1450  *
1451  * API to perform operations on moving out of STOP-PROGRESS substate
1452  *
1453  * Return: void
1454  */
1455 static void mlme_vdev_subst_stop_stop_progress_exit(void *ctx)
1456 {
1457     /* NONE */
1458 }
1459 
1460 /**
1461  * mlme_vdev_subst_stop_stop_progress_event() - Event handler API for Stop
1462  *                                                Progress substate
1463  * @ctx: VDEV MLME object
1464  *
1465  * API to handle events in STOP-PROGRESS substate
1466  *
1467  * Return: SUCCESS: on handling event
1468  *         FAILURE: on ignoring the event
1469  */
1470 static bool mlme_vdev_subst_stop_stop_progress_event(void *ctx,
1471 		uint16_t event, uint16_t event_data_len, void *event_data)
1472 {
1473 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1474 	bool status;
1475 
1476 	/* Debug framework is required to hold the events */
1477 
1478 	switch (event) {
1479 	case WLAN_VDEV_SM_EV_STOP_REQ:
1480 		/* send vdev stop command to FW and delete BSS peer*/
1481 		mlme_vdev_stop_send(vdev_mlme, event_data_len, event_data);
1482 		status = true;
1483 		break;
1484 
1485 	case WLAN_VDEV_SM_EV_STOP_RESP:
1486 		/* Processes stop response, and checks BSS peer delete wait
1487 		 * is needed
1488 		 */
1489 		mlme_vdev_stop_continue(vdev_mlme, event_data_len, event_data);
1490 		status = true;
1491 		break;
1492 
1493 	/* This event should be given by MLME on stop complete and BSS
1494 	 * peer delete complete to move forward
1495 	 */
1496 	case WLAN_VDEV_SM_EV_MLME_DOWN_REQ:
1497 		mlme_vdev_sm_transition_to(vdev_mlme,
1498 					   WLAN_VDEV_SS_STOP_DOWN_PROGRESS);
1499 		mlme_vdev_sm_deliver_event(vdev_mlme,
1500 					   WLAN_VDEV_SM_EV_MLME_DOWN_REQ,
1501 					   event_data_len, event_data);
1502 		status = true;
1503 		break;
1504 
1505 	case WLAN_VDEV_SM_EV_STOP_FAIL:
1506 		mlme_vdev_sm_transition_to(vdev_mlme,
1507 					   WLAN_VDEV_SS_STOP_DOWN_PROGRESS);
1508 		mlme_vdev_sm_deliver_event(vdev_mlme,
1509 					   WLAN_VDEV_SM_EV_MLME_DOWN_REQ,
1510 					   event_data_len, event_data);
1511 		status = true;
1512 		break;
1513 
1514 	default:
1515 		status = false;
1516 		break;
1517 	}
1518 
1519 	return status;
1520 }
1521 
1522 /**
1523  * mlme_vdev_subst_stop_down_progress_entry() - Entry API for Down Progress
1524  *                                                sub state
1525  * @ctx: VDEV MLME object
1526  *
1527  * API to perform operations on moving to DOWN-PROGRESS substate
1528  *
1529  * Return: void
1530  */
1531 static void mlme_vdev_subst_stop_down_progress_entry(void *ctx)
1532 {
1533 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1534 	struct wlan_objmgr_vdev *vdev;
1535 
1536 	vdev = vdev_mlme->vdev;
1537 
1538 	if (wlan_vdev_mlme_get_state(vdev) != WLAN_VDEV_S_STOP)
1539 		QDF_BUG(0);
1540 
1541 	mlme_vdev_set_substate(vdev, WLAN_VDEV_SS_STOP_DOWN_PROGRESS);
1542 }
1543 
1544 /**
1545  * mlme_vdev_subst_stop_down_progress_exit() - Exit API for Down Progress
1546  *                                                sub state
1547  * @ctx: VDEV MLME object
1548  *
1549  * API to perform operations on moving out of DOWN-PROGRESS substate
1550  *
1551  * Return: void
1552  */
1553 static void mlme_vdev_subst_stop_down_progress_exit(void *ctx)
1554 {
1555 	/* NONE */
1556 }
1557 
1558 /**
1559  * mlme_vdev_subst_stop_down_progress_event() - Event handler API for Down
1560  *                                                Progress substate
1561  * @ctx: VDEV MLME object
1562  *
1563  * API to handle events in DOWN-PROGRESS substate
1564  *
1565  * Return: SUCCESS: on handling event
1566  *         FAILURE: on ignoring the event
1567  */
1568 static bool mlme_vdev_subst_stop_down_progress_event(void *ctx,
1569 		uint16_t event, uint16_t event_data_len, void *event_data)
1570 {
1571 	struct vdev_mlme_obj *vdev_mlme = (struct vdev_mlme_obj *)ctx;
1572 	bool status;
1573 
1574 	switch (event) {
1575 	case WLAN_VDEV_SM_EV_DOWN:
1576 		status = true;
1577 		break;
1578 
1579 	case WLAN_VDEV_SM_EV_MLME_DOWN_REQ:
1580 		/* send vdev down command to FW, if send is successful, sends
1581 		 * DOWN_COMPLETE event
1582 		 */
1583 		mlme_vdev_down_send(vdev_mlme, event_data_len, event_data);
1584 		status = true;
1585 		break;
1586 
1587 	case WLAN_VDEV_SM_EV_DOWN_COMPLETE:
1588 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_INIT);
1589 		mlme_vdev_sm_deliver_event(vdev_mlme,
1590 					   WLAN_VDEV_SM_EV_DOWN_COMPLETE,
1591 					   event_data_len, event_data);
1592 		status = true;
1593 		break;
1594 
1595 	case WLAN_VDEV_SM_EV_DOWN_FAIL:
1596 		mlme_vdev_sm_transition_to(vdev_mlme, WLAN_VDEV_S_INIT);
1597 		mlme_vdev_sm_deliver_event(vdev_mlme,
1598 					   WLAN_VDEV_SM_EV_DOWN_COMPLETE,
1599 					   event_data_len, event_data);
1600 		status = true;
1601 		break;
1602 
1603 	default:
1604 		status = false;
1605 		break;
1606 	}
1607 
1608 	return status;
1609 }
1610 
1611 
1612 static const char *vdev_sm_event_names[] = {
1613 	"EV_START",
1614 	"EV_START_REQ",
1615 	"EV_RESTART_REQ",
1616 	"EV_START_RESP",
1617 	"EV_RESTART_RESP",
1618 	"EV_START_REQ_FAIL",
1619 	"EV_RESTART_REQ_FAIL",
1620 	"EV_START_SUCCESS",
1621 	"EV_CONN_PROGRESS",
1622 	"EV_STA_CONN_START",
1623 	"EV_DFS_CAC_WAIT",
1624 	"EV_DFS_CAC_COMPLETED",
1625 	"EV_DOWN",
1626 	"EV_CONNECTION_FAIL",
1627 	"EV_STOP_RESP",
1628 	"EV_STOP_FAIL",
1629 	"EV_DOWN_FAIL",
1630 	"EV_DISCONNECT_COMPLETE",
1631 	"EV_SUSPEND_RESTART",
1632 	"EV_HOST_RESTART",
1633 	"EV_UP_HOST_RESTART",
1634 	"EV_FW_VDEV_RESTART",
1635 	"EV_UP_FAIL",
1636 	"EV_RADAR_DETECTED",
1637 	"EV_CSA_RESTART",
1638 	"EV_CSA_COMPLETE",
1639 	"EV_MLME_DOWN_REQ",
1640 	"EV_DOWN_COMPLETE",
1641 	"EV_ROAM",
1642 	"EV_STOP_REQ",
1643 };
1644 
1645 struct wlan_sm_state_info sm_info[] = {
1646 	{
1647 		(uint8_t)WLAN_VDEV_S_INIT,
1648 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1649 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1650 		true,
1651 		"INIT",
1652 		mlme_vdev_state_init_entry,
1653 		mlme_vdev_state_init_exit,
1654 		mlme_vdev_state_init_event
1655 	},
1656 	{
1657 		(uint8_t)WLAN_VDEV_S_START,
1658 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1659 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1660 		true,
1661 		"START",
1662 		mlme_vdev_state_start_entry,
1663 		mlme_vdev_state_start_exit,
1664 		mlme_vdev_state_start_event
1665 	},
1666 	{
1667 		(uint8_t)WLAN_VDEV_S_DFS_CAC_WAIT,
1668 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1669 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1670 		true,
1671 		"DFS_CAC_WAIT",
1672 		mlme_vdev_state_dfs_cac_wait_entry,
1673 		mlme_vdev_state_dfs_cac_wait_exit,
1674 		mlme_vdev_state_dfs_cac_wait_event
1675 	},
1676 	{
1677 		(uint8_t)WLAN_VDEV_S_UP,
1678 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1679 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1680 		true,
1681 		"UP",
1682 		mlme_vdev_state_up_entry,
1683 		mlme_vdev_state_up_exit,
1684 		mlme_vdev_state_up_event
1685 	},
1686 	{
1687 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1688 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1689 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1690 		true,
1691 		"SUSPEND",
1692 		mlme_vdev_state_suspend_entry,
1693 		mlme_vdev_state_suspend_exit,
1694 		mlme_vdev_state_suspend_event
1695 	},
1696 	{
1697 		(uint8_t)WLAN_VDEV_S_STOP,
1698 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1699 		(uint8_t)WLAN_VDEV_SS_STOP_STOP_PROGRESS,
1700 		true,
1701 		"STOP",
1702 		mlme_vdev_state_stop_entry,
1703 		mlme_vdev_state_stop_exit,
1704 		mlme_vdev_state_stop_event
1705 	},
1706 	{
1707 		(uint8_t)WLAN_VDEV_S_MAX,
1708 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1709 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1710 		false,
1711 		"INVALID",
1712 		NULL,
1713 		NULL,
1714 		NULL
1715 	},
1716 	{
1717 		(uint8_t)WLAN_VDEV_SS_START_START_PROGRESS,
1718 		(uint8_t)WLAN_VDEV_S_START,
1719 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1720 		false,
1721 		"ST-START_PROG",
1722 		mlme_vdev_subst_start_start_progress_entry,
1723 		mlme_vdev_subst_start_start_progress_exit,
1724 		mlme_vdev_subst_start_start_progress_event
1725 	},
1726 	{
1727 		(uint8_t)WLAN_VDEV_SS_START_RESTART_PROGRESS,
1728 		(uint8_t)WLAN_VDEV_S_START,
1729 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1730 		false,
1731 		"ST-RESTART_PROG",
1732 		mlme_vdev_subst_start_restart_progress_entry,
1733 		mlme_vdev_subst_start_restart_progress_exit,
1734 		mlme_vdev_subst_start_restart_progress_event
1735 	},
1736 	{
1737 		(uint8_t)WLAN_VDEV_SS_START_CONN_PROGRESS,
1738 		(uint8_t)WLAN_VDEV_S_START,
1739 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1740 		false,
1741 		"ST-CONN_PROG",
1742 		mlme_vdev_subst_start_conn_progress_entry,
1743 		mlme_vdev_subst_start_conn_progress_exit,
1744 		mlme_vdev_subst_start_conn_progress_event
1745 	},
1746 	{
1747 		(uint8_t)WLAN_VDEV_SS_START_DISCONN_PROGRESS,
1748 		(uint8_t)WLAN_VDEV_S_START,
1749 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1750 		false,
1751 		"ST-DISCONN_PROG",
1752 		mlme_vdev_subst_start_disconn_progress_entry,
1753 		mlme_vdev_subst_start_disconn_progress_exit,
1754 		mlme_vdev_subst_start_disconn_progress_event
1755 	},
1756 	{
1757 		(uint8_t)WLAN_VDEV_SS_SUSPEND_SUSPEND_DOWN,
1758 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1759 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1760 		false,
1761 		"SP-SUSPEND_DOWN",
1762 		mlme_vdev_subst_suspend_suspend_down_entry,
1763 		mlme_vdev_subst_suspend_suspend_down_exit,
1764 		mlme_vdev_subst_suspend_suspend_down_event
1765 	},
1766 	{
1767 		(uint8_t)WLAN_VDEV_SS_SUSPEND_SUSPEND_RESTART,
1768 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1769 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1770 		false,
1771 		"SP-SUSPEND_RESTART",
1772 		mlme_vdev_subst_suspend_suspend_restart_entry,
1773 		mlme_vdev_subst_suspend_suspend_restart_exit,
1774 		mlme_vdev_subst_suspend_suspend_restart_event
1775 	},
1776 	{
1777 		(uint8_t)WLAN_VDEV_SS_SUSPEND_HOST_RESTART,
1778 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1779 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1780 		false,
1781 		"SP-HOST_RESTART",
1782 		mlme_vdev_subst_suspend_host_restart_entry,
1783 		mlme_vdev_subst_suspend_host_restart_exit,
1784 		mlme_vdev_subst_suspend_host_restart_event
1785 	},
1786 	{
1787 		(uint8_t)WLAN_VDEV_SS_SUSPEND_CSA_RESTART,
1788 		(uint8_t)WLAN_VDEV_S_SUSPEND,
1789 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1790 		false,
1791 		"SP-CSA_RESTART",
1792 		mlme_vdev_subst_suspend_csa_restart_entry,
1793 		mlme_vdev_subst_suspend_csa_restart_exit,
1794 		mlme_vdev_subst_suspend_csa_restart_event
1795 	},
1796 	{
1797 		(uint8_t)WLAN_VDEV_SS_STOP_STOP_PROGRESS,
1798 		(uint8_t)WLAN_VDEV_S_STOP,
1799 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1800 		false,
1801 		"STOP-STOP_PROG",
1802 		mlme_vdev_subst_stop_stop_progress_entry,
1803 		mlme_vdev_subst_stop_stop_progress_exit,
1804 		mlme_vdev_subst_stop_stop_progress_event
1805 	},
1806 	{
1807 		(uint8_t)WLAN_VDEV_SS_STOP_DOWN_PROGRESS,
1808 		(uint8_t)WLAN_VDEV_S_STOP,
1809 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1810 		false,
1811 		"STOP-DOWN_PROG",
1812 		mlme_vdev_subst_stop_down_progress_entry,
1813 		mlme_vdev_subst_stop_down_progress_exit,
1814 		mlme_vdev_subst_stop_down_progress_event
1815 	},
1816 	{
1817 		(uint8_t)WLAN_VDEV_SS_IDLE,
1818 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1819 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1820 		false,
1821 		"IDLE",
1822 		NULL,
1823 		NULL,
1824 		NULL,
1825 	},
1826 	{
1827 		(uint8_t)WLAN_VDEV_SS_MAX,
1828 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1829 		(uint8_t)WLAN_SM_ENGINE_STATE_NONE,
1830 		false,
1831 		"INVALID",
1832 		NULL,
1833 		NULL,
1834 		NULL,
1835 	},
1836 };
1837 
1838 QDF_STATUS mlme_vdev_sm_deliver_event(struct vdev_mlme_obj *vdev_mlme,
1839 				      enum wlan_vdev_sm_evt event,
1840 				      uint16_t event_data_len, void *event_data)
1841 {
1842 	return wlan_sm_dispatch(vdev_mlme->sm_hdl, event,
1843 				event_data_len, event_data);
1844 }
1845 
1846 void mlme_vdev_sm_print_state_event(struct vdev_mlme_obj *vdev_mlme,
1847 				    enum wlan_vdev_sm_evt event)
1848 {
1849 	enum wlan_vdev_state state;
1850 	enum wlan_vdev_state substate;
1851 	struct wlan_objmgr_vdev *vdev;
1852 
1853 	vdev = vdev_mlme->vdev;
1854 
1855 	state = wlan_vdev_mlme_get_state(vdev);
1856 	substate = wlan_vdev_mlme_get_substate(vdev);
1857 
1858 	mlme_nofl_debug("[%s]%s - %s, %s", vdev_mlme->sm_hdl->name,
1859 			sm_info[state].name, sm_info[substate].name,
1860 			vdev_sm_event_names[event]);
1861 }
1862 
1863 void mlme_vdev_sm_print_state(struct vdev_mlme_obj *vdev_mlme)
1864 {
1865 	enum wlan_vdev_state state;
1866 	enum wlan_vdev_state substate;
1867 	struct wlan_objmgr_vdev *vdev;
1868 
1869 	vdev = vdev_mlme->vdev;
1870 
1871 	state = wlan_vdev_mlme_get_state(vdev);
1872 	substate = wlan_vdev_mlme_get_substate(vdev);
1873 
1874 	mlme_nofl_debug("[%s]%s - %s", vdev_mlme->sm_hdl->name,
1875 			sm_info[state].name, sm_info[substate].name);
1876 }
1877 
1878 #ifdef SM_ENG_HIST_ENABLE
1879 void mlme_vdev_sm_history_print(struct vdev_mlme_obj *vdev_mlme)
1880 {
1881 	return wlan_sm_print_history(vdev_mlme->sm_hdl);
1882 }
1883 #endif
1884 
1885 QDF_STATUS mlme_vdev_sm_create(struct vdev_mlme_obj *vdev_mlme)
1886 {
1887 	struct wlan_sm *sm;
1888 	uint8_t name[WLAN_SM_ENGINE_MAX_NAME];
1889 
1890 	qdf_snprintf(name, sizeof(name), "VDEV%d-MLME",
1891 		     wlan_vdev_get_id(vdev_mlme->vdev));
1892 	sm = wlan_sm_create(name, vdev_mlme,
1893 			    WLAN_VDEV_S_INIT,
1894 			    sm_info,
1895 			    QDF_ARRAY_SIZE(sm_info),
1896 			    vdev_sm_event_names,
1897 			    QDF_ARRAY_SIZE(vdev_sm_event_names));
1898 	if (!sm) {
1899 		mlme_err("VDEV MLME SM allocation failed");
1900 		return QDF_STATUS_E_FAILURE;
1901 	}
1902 	vdev_mlme->sm_hdl = sm;
1903 
1904 	mlme_vdev_sm_spinlock_create(vdev_mlme);
1905 
1906 	mlme_vdev_cmd_mutex_create(vdev_mlme);
1907 
1908 	return QDF_STATUS_SUCCESS;
1909 }
1910 
1911 QDF_STATUS mlme_vdev_sm_destroy(struct vdev_mlme_obj *vdev_mlme)
1912 {
1913 	mlme_vdev_cmd_mutex_destroy(vdev_mlme);
1914 
1915 	mlme_vdev_sm_spinlock_destroy(vdev_mlme);
1916 
1917 	wlan_sm_delete(vdev_mlme->sm_hdl);
1918 
1919 	return QDF_STATUS_SUCCESS;
1920 }
1921