1 /* 2 * Copyright (C) 2021 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef OHOS_STA_MACHINE_H 17 #define OHOS_STA_MACHINE_H 18 19 #include <map> 20 #include <string> 21 #include <vector> 22 #include "handler.h" 23 #include "message_queue.h" 24 #include "state.h" 25 26 namespace OHOS { 27 namespace Wifi { 28 #define CMD_SET_OPERATIONAL_MODE 1 29 /* Message Processed */ 30 static const bool EXECUTED = true; 31 /* The message is not processed. */ 32 static const bool NOT_EXECUTED = false; 33 34 class StateMachineHandler; 35 class StateMachine { 36 public: 37 /** 38 * @Description : StateMachine Initialization Function 39 * 40 * @return true :success, false : failed. 41 */ 42 bool InitialStateMachine(const std::string &name = "RunHandleThread"); 43 44 /** 45 * @Description : Start StateMachine. 46 * 47 */ 48 void StartStateMachine(); 49 50 /** 51 * @Description : Set Handler. 52 * 53 * @param handler - StateMachineHandler instance.[in] 54 */ 55 void SetHandler(StateMachineHandler *handler); 56 57 /** 58 * @Description : The Message is not handled. 59 * 60 * @param msg - Message object.[in] 61 */ 62 void NotExecutedMessage(const InternalMessagePtr msg); 63 64 /** 65 * @Description Stop Handler Thread. 66 * 67 */ 68 void StopHandlerThread(); 69 70 /** 71 * @Description : Start the timer. 72 * 73 * @param timerName - Timer Name.[in] 74 * @param interval - Timer duration, in milliseconds.[in] 75 */ 76 virtual void StartTimer(int timerName, int64_t interval); 77 78 /** 79 * @Description : Stop the timer. 80 * 81 * @param timerName - Timer Name.[in] 82 */ 83 virtual void StopTimer(int timerName); 84 85 /** 86 * @Description : Construct internal messages. 87 * 88 * @return InternalMessagePtr : Pointer to the constructed internal message. 89 */ 90 InternalMessagePtr CreateMessage(); 91 92 /** 93 * @Description : Construct an information message based on 94 * the original message. 95 * 96 * @param orig - Original message.[in] 97 * @return InternalMessagePtr : Pointer to the constructed internal message. 98 */ 99 InternalMessagePtr CreateMessage(const InternalMessagePtr orig); 100 101 /** 102 * @Description : Construct internal messages. 103 * 104 * @param msgName - Message Name.[in] 105 * @return InternalMessagePtr : Pointer to the constructed internal message. 106 */ 107 InternalMessagePtr CreateMessage(int msgName); 108 109 /** 110 * @Description : Construct internal messages. 111 * 112 * @param msgName - Message Name.[in] 113 * @param param1 - Message parameters.[in] 114 * @return InternalMessagePtr : Pointer to the constructed internal message. 115 */ 116 InternalMessagePtr CreateMessage(int msgName, int param1); 117 118 /** 119 * @Description : Construct internal messages. 120 * 121 * @param msgName - Message Name.[in] 122 * @param param1 - Message parameters.[in] 123 * @param param2 - Message parameters.[in] 124 * @return InternalMessagePtr : Pointer to the constructed internal message. 125 */ 126 InternalMessagePtr CreateMessage(int msgName, int param1, int param2); 127 128 /** 129 * @Description : Construct internal messages. 130 * 131 * @param msgName - Message Name.[in] 132 * @param messageObj - User-defined data 133 * @return InternalMessagePtr : Pointer to the constructed internal message. 134 */ 135 InternalMessagePtr CreateMessage(int msgName, const std::any &messageObj); 136 137 /** 138 * @Description : Constructs internal messages. 139 * 140 * @param msgName - Message name.[in] 141 * @param param1 - First Message parameter.[in] 142 * @param param2 - Second Message parameter.[in] 143 * @param messageObj - User-defined data 144 * @return InternalMessagePtr : Pointer to the constructed internal message. 145 */ 146 InternalMessagePtr CreateMessage(int msgName, int param1, int param2, const std::any &messageObj); 147 148 /** 149 * @Description : Constructs internal messages and places the 150 * messages in the message queue of the state machine. 151 * 152 * @param msgName - Message name.[in] 153 */ 154 virtual void SendMessage(int msgName); 155 156 /** 157 * @Description : Constructs internal messages and places the messages 158 * in the message queue of the state machine. 159 * 160 * @param msgName - Message name.[in] 161 * @param param1 - Message parameter.[in] 162 */ 163 virtual void SendMessage(int msgName, int param1); 164 165 /** 166 * @Description : Constructs internal messages and places the messages 167 * in the message queue of the state machine. 168 * 169 * @param msgName - Message name.[in] 170 * @param param1 - Message parameter.[in] 171 * @param param2 - Message parameter.[in] 172 */ 173 virtual void SendMessage(int msgName, int param1, int param2); 174 175 /** 176 * @Description : Puts messages into the message queue of the state machine. 177 * 178 * @param msg - Message to be sent.[in] 179 */ 180 virtual void SendMessage(InternalMessagePtr msg); 181 182 /** 183 * @Description : Puts messages into the message queue of the state machine. 184 * 185 * @param msgName - Message Name.[in] 186 * @param messageObj - User-defined data 187 */ 188 virtual void SendMessage(int msgName, const std::any &messageObj); 189 190 /** 191 * @Description : Puts messages into the message queue of the state machine. 192 * 193 * @param msgName - Message Name.[in] 194 * @param param1 - Message parameters.[in] 195 * @param param2 - Message parameters.[in] 196 * @param messageObj - User-defined data 197 */ 198 virtual void SendMessage(int msgName, int param1, int param2, const std::any &messageObj); 199 200 /** 201 * @Description Constructs internal messages and places them in the 202 * message queue of the state machine. The messages are processed 203 * after the specified delay time. 204 * 205 * @param msgName - Message Name.[in] 206 * @param delayTimeMs - Delay time, in milliseconds.[in] 207 */ 208 void MessageExecutedLater(int msgName, int64_t delayTimeMs); 209 210 /** 211 * @Description : Constructs internal messages and places them in the 212 * message queue of the state machine. The messages are processed 213 * after the specified delay time. 214 * 215 * @param msgName - Message Name.[in] 216 * @param param1 - Message parameters.[in] 217 * @param delayTimeMs - Delay time, in milliseconds.[in] 218 */ 219 void MessageExecutedLater(int msgName, int param1, int64_t delayTimeMs); 220 221 /** 222 * @Description : Constructs internal messages and places them in the 223 * message queue of the state machine. The messages are processed 224 * after the specified delay time. 225 * 226 * @param msgName - Message Name.[in] 227 * @param param1 - Message parameters.[in] 228 * @param param2 - Message parameters.[in] 229 * @param delayTimeMs - Delay time, in milliseconds.[in] 230 */ 231 void MessageExecutedLater(int msgName, int param1, int param2, int64_t delayTimeMs); 232 233 /** 234 * @Description : Constructs internal messages and places them in the 235 * message queue of the state machine. The messages are processed 236 * after the specified delay time. 237 * 238 * @param msg - Message to be sent.[in] 239 * @param delayTimeMs - Delay time, in milliseconds.[in] 240 */ 241 void MessageExecutedLater(InternalMessagePtr msg, int64_t delayTimeMs); 242 243 /** 244 * @Description : Constructs internal messages and places them in the 245 * message queue of the state machine. The messages are processed 246 * after the specified delay time. 247 * 248 * @param msgName - Message Name.[in] 249 * @param messageObj -User-defined data 250 * @param delayTimeMs - Delay time, in milliseconds.[in] 251 */ 252 void MessageExecutedLater(int msgName, const std::any &messageObj, int64_t delayTimeMs); 253 254 /** 255 * @Description : Constructs internal messages and places them in the 256 * message queue of the state machine. The messages are processed 257 * after the specified delay time. 258 * 259 * @param msgName - Message Name.[in] 260 * @param param1 - Message parameters.[in] 261 * @param param2 - Message parameters.[in] 262 * @param messageObj - User-defined data 263 * @param delayTimeMs - Delay time, in milliseconds.[in] 264 */ 265 void MessageExecutedLater(int msgName, int param1, int param2, const std::any &messageObj, int64_t delayTimeMs); 266 267 /** 268 * @Description : Constructs internal messages and places them in the 269 * front of message queue of the state machine. 270 * 271 * @param msgName - Message Name.[in] 272 * @param param1 - Message parameters.[in] 273 */ 274 void SendMessageAtFrontOfQueue(int msgName, int param1); 275 276 /** 277 * @Description : get current state name. 278 */ 279 std::string GetCurStateName(); 280 281 protected: 282 /** 283 * @Description : Construct a new State Machine:: State Machine object. 284 * 285 * @param name - State name.[in] 286 */ 287 explicit StateMachine(const std::string &name); 288 289 /** 290 * @Description : Destroy the State Machine:: State Machine object. 291 * 292 */ 293 virtual ~StateMachine(); 294 295 /** 296 * @Description : Add state. 297 * 298 * @param state - state.[in] 299 * @param upper - upper state.[in] 300 */ 301 void StatePlus(State *state, State *upper); 302 303 /** 304 * @Description : Remove state. 305 * 306 * @param state - state.[in] 307 */ 308 void StateDelete(State *state); 309 310 /** 311 * @Description : Set first state. 312 * 313 * @param firstState - First state.[in] 314 */ 315 void SetFirstState(State *firstState); 316 317 /** 318 * @Description : Transition to orther state. 319 * 320 * @param targetState - state.[in] 321 */ 322 void SwitchState(State *targetState); 323 324 /** 325 * @Description : Delay Message. 326 * 327 * @param msg - Message object.[in] 328 */ 329 void DelayMessage(const InternalMessagePtr msg); 330 331 private: 332 StateMachineHandler *pStateMachineHandler; 333 std::string mStateName; 334 }; 335 336 typedef struct StateInfo { 337 State *state; 338 StateInfo *upperStateInfo; 339 bool active; 340 } StateInfo; 341 342 class StateMachineHandler : public Handler { 343 public: 344 using StateInfoMap = std::map<std::string, StateInfo *>; 345 using StateVector = std::vector<StateInfo *>; 346 using DelayedMessage = std::vector<InternalMessagePtr >; 347 348 /** 349 * @Description : Construct a new state machine Handler:: StateMachine Handler object. 350 * 351 * @param pStateMgr - Handler pointer.[in] 352 */ 353 explicit StateMachineHandler(StateMachine *pStateMgr); 354 355 /** 356 * @Description : Destroy the StateMachine Handler:: StateMachine Handler object. 357 * 358 */ 359 ~StateMachineHandler(); 360 361 /** 362 * @Description : StateMachineHandler Initialization Function. 363 * 364 * @return true : success, false : failed. 365 */ 366 bool InitialSmHandler(const std::string &name); 367 368 /** 369 * @Description : Add a new state. 370 * 371 * @param state - State to be added.[in] 372 * @param upper - upper of state.[in] 373 * @return StateInfo* 374 */ 375 StateInfo *StatePlus(State *state, State *upper); 376 377 /** 378 * @Description : Delete a state. 379 * 380 * @param state - State to be deleted.[in] 381 */ 382 void StateDelete(State *state); 383 384 /** 385 * @Description : Sets the Initialization State. 386 * 387 * @param firstState - Initialization State.[in] 388 */ 389 void SetFirstState(State *firstState); 390 391 /** 392 * @Description : State transition function. 393 * 394 * @param targetState - Destination State.[in] 395 */ 396 void SwitchState(State *targetState); 397 398 /** 399 * @Description : Delay Message Processing Function. 400 * 401 * @param msg - Message body pointer.[in] 402 */ 403 void DelayMessage(const InternalMessagePtr msg); 404 405 /** 406 * @Description : The state machine is constructed. 407 * 408 */ 409 void BuildTreeComplete(); 410 411 /** 412 * @Description : get current state name. 413 */ 414 std::string GetCurStateName(); 415 416 private: 417 /** 418 * @Description : Sets the initial state sequence. 419 * 420 */ 421 void BuildStateInitVector(); 422 423 /** 424 * @Description : Writes the inactive upper states of targetState 425 * and targetState to the sequenceStateVector list. 426 * 427 * @param targetState - Target State Machine.[in] 428 * @return StateInfo* 429 */ 430 StateInfo *BuildSequenceStateVector(State *targetState); 431 432 /** 433 * @Description : Move Delayed Message At Front Of Queue. 434 * 435 */ 436 void PlaceDelayedMsgQueueTop(); 437 438 /** 439 * @Description : Release all messages in delayed Messages. 440 * 441 */ 442 void ReleaseDelayedMessages(); 443 444 /** 445 * @Description : Fill the status in the sequential status 446 * list in reverse order. 447 * 448 * @return int 449 */ 450 int MoveSequenceToStateVector(); 451 452 /** 453 * @Description : Invoke the ExecuteStateMsg interface of the current state 454 * to process messages sent to the state machine. The entry/exit of the 455 * state machine is also called, and the delayed messagei s put back 456 * into queue when transitioning to a new state. 457 * 458 * @param msg - Messages.[in] 459 */ 460 void ExecuteMessage(InternalMessagePtr msg) override; 461 462 /** 463 * @Description : Clean up After Quitting. 464 * 465 */ 466 void ClearWhenQuit(); 467 468 /** 469 * @Description : Performing Status Transitions. 470 * 471 * @param msgProcessedState - Message processing status.[in] 472 * @param msg - Messages.[in] 473 */ 474 void PerformSwitchState(State *msgProcessedState, InternalMessagePtr msg); 475 476 /** 477 * @Description : Process messages. If the current state does not process it, 478 * the upper state processing is called, and so on. If all upper states 479 * are not processed, invoke the NotExecutedMessage method of the state machine. 480 * 481 * @param msg - Message body pointer.[in] 482 * @return State* 483 */ 484 State *ExecuteTreeStateMsg(InternalMessagePtr msg); 485 486 /** 487 * @Description : Invoke GoOutState() for each state from the first 488 * state in the list to the public upper state. 489 * 490 * @param commonStateInfo - common upper state machine.[in] 491 */ 492 void CallTreeStateExits(StateInfo *commonStateInfo); 493 494 /** 495 * @Description : Call the GoInState method from the start state 496 * index to the top of the state stack. 497 * 498 * @param index - Start state index of the 499 * state machine list. 500 */ 501 void CallTreeStateEnters(int index); 502 503 private: 504 /* All state mappings of the state machine */ 505 StateInfoMap mStateInfoMap; 506 /* From child state to upper state list */ 507 StateVector mStateVector; 508 /* Top index of mStateVector */ 509 int mStateVectorTopIndex; 510 /* From upper state to child state list */ 511 StateVector mSequenceStateVector; 512 /* Top of mSequenceStateVector */ 513 int mSequenceStateVectorCount; 514 /* Delayed Message Queue */ 515 DelayedMessage mDelayedMessages; 516 /* State machine instance */ 517 StateMachine *pStateMachine; 518 /* Initial state */ 519 State *pFirstState; 520 /* Target Status */ 521 State *pTargetState; 522 /* StateMachine exit or not */ 523 bool mQuitFlag; 524 /* Whether the state machine has been built */ 525 bool mBuildCompleteFlag; 526 /* 527 * All State exit/enter calls are true before the 528 * last enter call in the target state. 529 */ 530 bool mSwitchingStateFlag; 531 /* Current Message */ 532 InternalMessagePtr pCurrentMsg; 533 }; 534 } // namespace Wifi 535 } // namespace OHOS 536 #endif 537