1 /*
2  * Copyright (C) 2022 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 HID_HOST_STATEMACHINE_H
17 #define HID_HOST_STATEMACHINE_H
18 #include <list>
19 #include <memory>
20 #include <string>
21 
22 #include "interface_adapter_manager.h"
23 #include "interface_adapter_classic.h"
24 #include "interface_adapter_ble.h"
25 #include "state_machine.h"
26 #include "hid_host_defines.h"
27 #include "hid_host_l2cap_connection.h"
28 #include "hid_host_sdp_client.h"
29 #include "hid_host_uhid.h"
30 #include "hid_host_hogp.h"
31 #include "timer.h"
32 
33 namespace OHOS {
34 namespace bluetooth {
35 /**
36  * @brief Class for hid host state machine.
37  */
38 class HidHostStateMachine : public utility::StateMachine {
39 public:
40     /**
41      * @brief Construct a new HidHostStateMachine object.
42      *
43      * @param address Device address.
44      */
45     explicit HidHostStateMachine(const std::string &address);
46 
47     /**
48      * @brief Destroy the HidHostStateMachine object.
49      */
50     ~HidHostStateMachine() = default;
51 
52     /**
53      * @brief Initialise the state machine.
54      */
55     void Init();
56 
57     /**
58      * @brief Check if current statemachine is removing.
59      *
60      * @return Returns <b>true</b> if the statemachine is removing; returns <b>false</b> if not.
61      */
62     bool IsRemoving() const;
63 
64     /**
65      * @brief Mark statemachine removing.
66      *
67      * @param isRemoving removing mark.
68      */
69     void SetRemoving(bool isRemoving);
70 
71     /**
72      * @brief Get the State Int object.
73      *
74      * @return Returns the state number.
75      */
76     int GetDeviceStateInt() const;
77 
78     uint16_t GetDeviceControlLcid();
79 
80     uint16_t GetDeviceInterruptLcid();
81 
82     int GetDeviceType();
83 
84     void ProcessL2capConnectionEvent(const HidHostMessage &event);
85 
86     void ProcessHogpEvent(const HidHostMessage &event);
87 
88     void ConnectionTimeout() const;
89     void DisonnectionTimeout() const;
90     void StartConnectionTimer() const;
91     void StopConnectionTimer() const;
92     void StartDisconnectionTimer() const;
93     void StopDisconnectionTimer() const;
94     void AddDeferredMessage(const HidHostMessage &msg);
95     void ProcessDeferredMessage();
96     std::string GetDeviceAdress();
97     void NotifyStateTransitions();
98     static std::string GetEventName(int what);
99 
100     void ProcessStartSdp(const HidHostMessage &msg);
101     void ProcessOpenDevice(const HidHostMessage &msg);
102     void ProcessCloseDeviceReq(const HidHostMessage &msg);
103     void ProcessCloseDevice(const HidHostMessage &msg);
104     void ProcessReciveData(const HidHostMessage &msg);
105     void ProcessReciveControlData(const HidHostMessage &msg);
106     void ProcessReciveHandshake(const HidHostMessage &msg);
107     void ProcessWriteData(const HidHostMessage &msg);
108     void ProcessSdpComplete(const HidHostMessage &msg);
109     void ProcessOpenComplete(const HidHostMessage &msg);
110 
111     void ProcessBleOpenDeviceReq(const HidHostMessage &msg);
112     void ProcessBleCloseDeviceReq(const HidHostMessage &msg);
113     void ProcessBleCloseDevice(const HidHostMessage &msg);
114     void ProcessBleReciveData(const HidHostMessage &msg);
115     void ProcessBleReciveControlData(const HidHostMessage &msg);
116     void ProcessBleReciveHandshake(const HidHostMessage &msg);
117     void ProcessBleWriteData(const HidHostMessage &msg);
118     void ProcessBleOpenComplete(const HidHostMessage &msg);
119 
120     inline static const std::string DISCONNECTED = "Disconnected";
121     inline static const std::string CONNECTING = "Connecting";
122     inline static const std::string DISCONNECTING = "Disconnecting";
123     inline static const std::string CONNECTED = "Connected";
124 
125 private:
126 
127     std::string address_;
128     bool isRemoving_ {false};
129     int preState_ {0};
130     int deviceType_ {HID_HOST_DEVICE_TYPE_UNKNOWN};
131     std::list<HidHostMessage> deferMsgs_ {};
132     std::unique_ptr<utility::Timer> connTimer_ {nullptr};
133     std::unique_ptr<utility::Timer> disconnTimer_ {nullptr};
134     inline static const int CONNECTION_TIMEOUT_MS {60000};  // 60s
135     inline static const int DISCONNECTION_TIMEOUT_MS {60000};
136 
137     std::unique_ptr<HidHostL2capConnection> l2capConnection_ {nullptr};
138     HidHostUhid uhid_;
139     std::unique_ptr<HidHostSdpClient> sdpClient_ {nullptr};
140     std::unique_ptr<HidHostHogp> hogp_ {nullptr};
141 
142     void SetDeviceType();
143 
144     BT_DISALLOW_COPY_AND_ASSIGN(HidHostStateMachine);
145 };
146 
147 class HidHostState : public utility::StateMachine::State {
148 public:
HidHostState(const std::string & name,utility::StateMachine & statemachine,int stateInt,utility::StateMachine::State & parent)149     HidHostState(const std::string &name, utility::StateMachine &statemachine, int stateInt,
150         utility::StateMachine::State &parent)
151         : State(name, statemachine, parent), stateInt_(stateInt), stateMachine_((HidHostStateMachine &)statemachine)
152     {}
153 
HidHostState(const std::string & name,utility::StateMachine & statemachine,int stateInt)154     HidHostState(const std::string &name, utility::StateMachine &statemachine, int stateInt)
155         : State(name, statemachine), stateInt_(stateInt), stateMachine_((HidHostStateMachine &)statemachine)
156     {}
157 
~HidHostState()158     virtual ~HidHostState()
159     {}
GetStateInt()160     int GetStateInt() const
161     {
162         return stateInt_;
163     }
164 
165 protected:
166     int stateInt_ {HID_HOST_STATE_DISCONNECTED};
167     HidHostStateMachine &stateMachine_;
168 };
169 
170 class HidHostDisconnectedState : public HidHostState {
171 public:
HidHostDisconnectedState(const std::string & name,utility::StateMachine & statemachine)172     HidHostDisconnectedState(const std::string &name, utility::StateMachine &statemachine)
173         : HidHostState(name, statemachine, HID_HOST_STATE_DISCONNECTED)
174     {}
175     ~HidHostDisconnectedState() override = default;
176     void Entry() override;
177     void Exit() override;
178     bool Dispatch(const utility::Message &msg) override;
179 
180 private:
181     bool isReentry_ {false};
182 
183     bool DispatchBle(const utility::Message &msg);
184 };
185 
186 class HidHostConnectingState : public HidHostState {
187 public:
HidHostConnectingState(const std::string & name,utility::StateMachine & statemachine)188     HidHostConnectingState(const std::string &name, utility::StateMachine &statemachine)
189         : HidHostState(name, statemachine, HID_HOST_STATE_CONNECTING)
190     {}
191     ~HidHostConnectingState() override = default;
192     void Entry() override;
193     void Exit() override;
194     bool Dispatch(const utility::Message &msg) override;
195 
196 private:
197     bool DispatchBle(const utility::Message &msg);
198 };
199 
200 class HidHostDisconnectingState : public HidHostState {
201 public:
HidHostDisconnectingState(const std::string & name,utility::StateMachine & statemachine)202     HidHostDisconnectingState(const std::string &name, utility::StateMachine &statemachine)
203         : HidHostState(name, statemachine, HID_HOST_STATE_DISCONNECTING)
204     {}
205     ~HidHostDisconnectingState() override = default;
206     void Entry() override;
207     void Exit() override;
208     bool Dispatch(const utility::Message &msg) override;
209 
210 private:
211     bool DispatchBle(const utility::Message &msg);
212 };
213 
214 class HidHostConnectedState : public HidHostState {
215 public:
HidHostConnectedState(const std::string & name,utility::StateMachine & statemachine)216     HidHostConnectedState(const std::string &name, utility::StateMachine &statemachine)
217         : HidHostState(name, statemachine, HID_HOST_STATE_CONNECTED)
218     {}
219     ~HidHostConnectedState() override = default;
220     void Entry() override;
221     void Exit() override;
222     bool Dispatch(const utility::Message &msg) override;
223 
224 private:
225     bool DispatchBle(const utility::Message &msg);
226 };
227 }  // namespace bluetooth
228 }  // namespace OHOS
229 #endif  // HID_HOST_STATEMACHINE_H
230