1 /*
2  * Copyright (c) 2021-2024 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 #include "softbus_adapter_bt_common.h"
17 
18 #include <stdbool.h>
19 
20 #include "c_header/ohos_bt_def.h"
21 #include "c_header/ohos_bt_gap.h"
22 #include "c_header/ohos_bt_gatt.h"
23 #include "comm_log.h"
24 #include "securec.h"
25 #include "softbus_common.h"
26 #include "softbus_def.h"
27 #include "softbus_errcode.h"
28 
29 #define STATE_LISTENER_MAX_NUM 16
30 #define BR_STATE_CB_TRANSPORT 1
31 
32 typedef struct {
33     bool isUsed;
34     SoftBusBtStateListener *listener;
35 } StateListener;
36 
ConvertBtState(int transport,int state)37 static int ConvertBtState(int transport, int state)
38 {
39     switch (state) {
40         case OHOS_GAP_STATE_TURNING_ON:
41             return (transport == BR_STATE_CB_TRANSPORT) ? SOFTBUS_BR_STATE_TURNING_ON : SOFTBUS_BLE_STATE_TURNING_ON;
42         case OHOS_GAP_STATE_TURN_ON:
43             return (transport == BR_STATE_CB_TRANSPORT) ? SOFTBUS_BR_STATE_TURN_ON : SOFTBUS_BLE_STATE_TURN_ON;
44         case OHOS_GAP_STATE_TURNING_OFF:
45             return (transport == BR_STATE_CB_TRANSPORT) ? SOFTBUS_BR_STATE_TURNING_OFF : SOFTBUS_BLE_STATE_TURNING_OFF;
46         case OHOS_GAP_STATE_TURN_OFF:
47             return (transport == BR_STATE_CB_TRANSPORT) ? SOFTBUS_BR_STATE_TURN_OFF : SOFTBUS_BLE_STATE_TURN_OFF;
48         default:
49             return SOFTBUS_COMM_BLUETOOTH_SWITCH_STATE_ERR;
50     }
51 }
52 
ConvertAclState(GapAclState state)53 static int ConvertAclState(GapAclState state)
54 {
55     switch (state) {
56         case OHOS_GAP_ACL_STATE_CONNECTED:
57             return SOFTBUS_ACL_STATE_CONNECTED;
58         case OHOS_GAP_ACL_STATE_DISCONNECTED:
59             return SOFTBUS_ACL_STATE_DISCONNECTED;
60         case OHOS_GAP_ACL_STATE_LE_CONNECTED:
61             return SOFTBUS_ACL_STATE_LE_CONNECTED;
62         case OHOS_GAP_ACL_STATE_LE_DISCONNECTED:
63             return SOFTBUS_ACL_STATE_LE_DISCONNECTED;
64         default:
65             break;
66     }
67     return SOFTBUS_COMM_BLUETOOTH_ACL_SWITCH_STATE_ERR;
68 }
69 
ConvertBtAddr(const BdAddr * bdAddr)70 static SoftBusBtAddr ConvertBtAddr(const BdAddr *bdAddr)
71 {
72     SoftBusBtAddr btAddr = {0};
73     if (memcpy_s(btAddr.addr, sizeof(btAddr.addr), bdAddr->addr, sizeof(bdAddr->addr)) != EOK) {
74         COMM_LOGE(COMM_ADAPTER, "copy bdAddr fail");
75     }
76     return btAddr;
77 }
78 
79 static StateListener g_stateListener[STATE_LISTENER_MAX_NUM];
80 static bool g_isBleTurnOn = false;
81 static bool g_isBrTurnOn = false;
82 static SoftBusMutex g_lock = {0};
IsRepeatNotify(int status)83 static bool IsRepeatNotify(int status)
84 {
85     COMM_LOGI(COMM_ADAPTER, "current state=%{public}d, isbleTurnOn=%{public}d, isbrTurnOn=%{public}d",
86         status, g_isBleTurnOn, g_isBrTurnOn);
87     COMM_CHECK_AND_RETURN_RET_LOGE(SoftBusMutexLock(&g_lock) == SOFTBUS_OK, false,
88         COMM_ADAPTER, "try to lock failed");
89     bool result = false;
90     switch (status) {
91         case SOFTBUS_BLE_STATE_TURN_ON:
92             result = g_isBleTurnOn;
93             g_isBleTurnOn = true;
94             break;
95         case SOFTBUS_BR_STATE_TURN_ON:
96             result = g_isBrTurnOn;
97             g_isBrTurnOn = true;
98             break;
99         case SOFTBUS_BLE_STATE_TURN_OFF:
100             result = !g_isBleTurnOn;
101             g_isBleTurnOn = false;
102             break;
103         case SOFTBUS_BR_STATE_TURN_OFF:
104             result = !g_isBrTurnOn;
105             g_isBrTurnOn = false;
106             break;
107         default:
108             break;
109     }
110     (void)SoftBusMutexUnlock(&g_lock);
111     return result;
112 }
113 
SoftBusOnBtSateChanged(int32_t status)114 static void SoftBusOnBtSateChanged(int32_t status)
115 {
116     if (IsRepeatNotify(status)) {
117         COMM_LOGI(COMM_ADAPTER, "current state=%{public}d, isbleTurnOn=%{public}d, isbrTurnOn=%{public}d",
118             status, g_isBleTurnOn, g_isBrTurnOn);
119         return;
120     }
121     int listenerId;
122     for (listenerId = 0; listenerId < STATE_LISTENER_MAX_NUM; listenerId++) {
123         if (g_stateListener[listenerId].isUsed &&
124             g_stateListener[listenerId].listener != NULL &&
125             g_stateListener[listenerId].listener->OnBtStateChanged != NULL) {
126             g_stateListener[listenerId].listener->OnBtStateChanged(listenerId, status);
127         }
128     }
129 }
130 
WrapperStateChangeCallback(const int transport,const int status)131 static void WrapperStateChangeCallback(const int transport, const int status)
132 {
133     COMM_LOGI(COMM_ADAPTER, "transport = %{public}d (1-BT, 2-BLE), "
134         "status = %{public}d (0-turning on, 1-on, 2-turning off, 3-off)", transport, status);
135     int st = ConvertBtState(transport, status);
136     SoftBusOnBtSateChanged(st);
137 }
138 
WrapperAclStateChangedCallback(const BdAddr * bdAddr,GapAclState state,unsigned int reason)139 static void WrapperAclStateChangedCallback(const BdAddr *bdAddr, GapAclState state, unsigned int reason)
140 {
141     if (bdAddr == NULL) {
142         COMM_LOGE(COMM_ADAPTER, "WrapperAclStateChangedCallback addr is null");
143         return;
144     }
145 
146     COMM_LOGD(COMM_ADAPTER,
147         "WrapperAclStateChangedCallback, addr=%{public}02X:%{public}02X:***%{public}02X, state=%{public}d, "
148         "reason=%{public}u",
149         bdAddr->addr[MAC_FIRST_INDEX], bdAddr->addr[MAC_ONE_INDEX], bdAddr->addr[MAC_FIVE_INDEX], state, reason);
150     int listenerId;
151     int aclState = ConvertAclState(state);
152     SoftBusBtAddr btAddr = ConvertBtAddr(bdAddr);
153     for (listenerId = 0; listenerId < STATE_LISTENER_MAX_NUM; listenerId++) {
154         if (g_stateListener[listenerId].isUsed &&
155             g_stateListener[listenerId].listener != NULL &&
156             g_stateListener[listenerId].listener->OnBtAclStateChanged != NULL) {
157             g_stateListener[listenerId].listener->OnBtAclStateChanged(listenerId, &btAddr, aclState, 0);
158         }
159     }
160 }
161 
WrapperPairRequestedCallback(const BdAddr * bdAddr,int transport)162 static void WrapperPairRequestedCallback(const BdAddr *bdAddr, int transport)
163 {
164     if (bdAddr == NULL) {
165         COMM_LOGE(COMM_ADAPTER, "WrapperPairRequestedCallback addr is null");
166         return;
167     }
168 
169     COMM_LOGI(COMM_ADAPTER,
170         "WrapperPairRequestedCallback, addr=%{public}02X:%{public}02X:***%{public}02X, transport=%{public}d",
171         bdAddr->addr[MAC_FIRST_INDEX], bdAddr->addr[MAC_ONE_INDEX], bdAddr->addr[MAC_FIVE_INDEX], transport);
172     if (!PairRequestReply(bdAddr, transport, true)) {
173         COMM_LOGE(COMM_ADAPTER, "PairRequestReply error");
174     }
175 }
176 
WrapperPairConfiremedCallback(const BdAddr * bdAddr,int transport,int reqType,int number)177 static void WrapperPairConfiremedCallback(const BdAddr *bdAddr, int transport, int reqType,
178     int number)
179 {
180     if (bdAddr == NULL) {
181         COMM_LOGE(COMM_ADAPTER, "WrapperPairConfirmedCallback addr is null");
182         return;
183     }
184 
185     COMM_LOGI(COMM_ADAPTER,
186         "WrapperPairConfirmedCallback, addr=%{public}02X:%{public}02X:***%{public}02X, "
187         "transport=%{public}d, reqType=%{public}d, number=%{public}d",
188         bdAddr->addr[MAC_FIRST_INDEX], bdAddr->addr[MAC_ONE_INDEX], bdAddr->addr[MAC_FIVE_INDEX],
189         transport, reqType, number);
190     if (!SetDevicePairingConfirmation(bdAddr, transport, true)) {
191         COMM_LOGE(COMM_ADAPTER, "SetDevicePairingConfirmation error");
192     }
193 }
194 
195 static BtGapCallBacks g_softbusGapCb = {
196     .stateChangeCallback = WrapperStateChangeCallback,
197     .aclStateChangedCallbak = WrapperAclStateChangedCallback,
198     .pairRequestedCallback = WrapperPairRequestedCallback,
199     .pairConfiremedCallback = WrapperPairConfiremedCallback
200 };
201 
SoftBusAddBtStateListener(const SoftBusBtStateListener * listener)202 int SoftBusAddBtStateListener(const SoftBusBtStateListener *listener)
203 {
204     if (listener == NULL) {
205         return SOFTBUS_INVALID_PARAM;
206     }
207     for (int index = 0; index < STATE_LISTENER_MAX_NUM; index++) {
208         if (!g_stateListener[index].isUsed) {
209             g_stateListener[index].isUsed = true;
210             g_stateListener[index].listener = (SoftBusBtStateListener *)listener;
211             return index;
212         }
213     }
214     return SOFTBUS_COMM_BLUETOOTH_ADD_STATE_LISTENER_ERR;
215 }
216 
SoftBusRemoveBtStateListener(int listenerId)217 int SoftBusRemoveBtStateListener(int listenerId)
218 {
219     if (listenerId < 0 || listenerId >= STATE_LISTENER_MAX_NUM) {
220         return SOFTBUS_INVALID_PARAM;
221     }
222     g_stateListener[listenerId].isUsed = false;
223     g_stateListener[listenerId].listener = NULL;
224     return SOFTBUS_OK;
225 }
226 
SoftBusEnableBt(void)227 int SoftBusEnableBt(void)
228 {
229     if (EnableBle()) {
230         return SOFTBUS_OK;
231     }
232     return SOFTBUS_COMM_BLE_ENABLE_ERR;
233 }
234 
SoftBusDisableBt(void)235 int SoftBusDisableBt(void)
236 {
237     if (DisableBle()) {
238         return SOFTBUS_OK;
239     }
240     return SOFTBUS_COMM_BLE_DISABLE_ERR;
241 }
242 
SoftBusGetBtState(void)243 int SoftBusGetBtState(void)
244 {
245     if (IsBleEnabled()) {
246         return BLE_ENABLE;
247     }
248     return BLE_DISABLE;
249 }
250 
SoftBusGetBrState(void)251 int SoftBusGetBrState(void)
252 {
253     if (GetBtState() == OHOS_GAP_STATE_TURN_ON) {
254         return BR_ENABLE;
255     }
256     return BR_DISABLE;
257 }
258 
SoftBusGetBtMacAddr(SoftBusBtAddr * mac)259 int SoftBusGetBtMacAddr(SoftBusBtAddr *mac)
260 {
261     if (mac == NULL) {
262         return SOFTBUS_INVALID_PARAM;
263     }
264 
265     if (!GetLocalAddr(mac->addr, BT_ADDR_LEN)) {
266         return SOFTBUS_COMM_BLUETOOTH_UNDERLAY_GET_ADDR_ERR;
267     }
268     return SOFTBUS_OK;
269 }
270 
SoftBusGetBtName(unsigned char * name,unsigned int * len)271 int SoftBusGetBtName(unsigned char *name, unsigned int *len)
272 {
273     (void)name;
274     (void)len;
275     return SOFTBUS_OK;
276 }
277 
SoftBusSetBtName(const char * name)278 int SoftBusSetBtName(const char *name)
279 {
280     if (SetLocalName((unsigned char *)name, strlen(name))) {
281         return SOFTBUS_OK;
282     }
283     return SOFTBUS_COMM_BLUETOOTH_UNDERLAY_SET_NAME_ERR;
284 }
285 
SoftBusComputeWaitBleSendDataTime(uint32_t waitMillis,SoftBusSysTime * outtime)286 void SoftBusComputeWaitBleSendDataTime(uint32_t waitMillis, SoftBusSysTime *outtime)
287 {
288 #define USECTONSEC 1000
289     SoftBusSysTime now;
290     (void)SoftBusGetTime(&now);
291     int64_t time = now.sec * USECTONSEC * USECTONSEC + now.usec + (int64_t)waitMillis * USECTONSEC;
292     outtime->sec = time / USECTONSEC / USECTONSEC;
293     outtime->usec = time % (USECTONSEC * USECTONSEC);
294 }
295 
SoftBusBtInit(void)296 int SoftBusBtInit(void)
297 {
298     if (SoftBusMutexInit(&g_lock, NULL) != SOFTBUS_OK) {
299         COMM_LOGE(COMM_ADAPTER, "init lock error");
300         return SOFTBUS_LOCK_ERR;
301     }
302     if (GapRegisterCallbacks(&g_softbusGapCb) != OHOS_BT_STATUS_SUCCESS) {
303         SoftBusMutexDestroy(&g_lock);
304         return SOFTBUS_COMM_BLUETOOTH_UNDERLAY_REGISTER_CB_ERR;
305     }
306     if (SoftBusGetBtState() == BLE_ENABLE) {
307         SoftBusOnBtSateChanged(SOFTBUS_BLE_STATE_TURN_ON);
308     }
309     if (SoftBusGetBrState() == BR_ENABLE) {
310         SoftBusOnBtSateChanged(SOFTBUS_BR_STATE_TURN_ON);
311     }
312     return SOFTBUS_OK;
313 }
314