1 /*
2 * Copyright (C) 2023 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 "napi_bluetooth_connection.h"
17
18 #include <set>
19
20 #include "napi_bluetooth_connection_observer.h"
21 #include "napi_bluetooth_remote_device_observer.h"
22 #include "bluetooth_log.h"
23 #include "bluetooth_errorcode.h"
24 #include "napi_bluetooth_error.h"
25 #include "napi_async_work.h"
26 #include "napi_bluetooth_utils.h"
27 #include "parser/napi_parser_utils.h"
28
29 namespace OHOS {
30 namespace Bluetooth {
31 std::shared_ptr<NapiBluetoothConnectionObserver> g_connectionObserver =
32 std::make_shared<NapiBluetoothConnectionObserver>();
33 std::shared_ptr<NapiBluetoothRemoteDeviceObserver> g_remoteDeviceObserver =
34 std::make_shared<NapiBluetoothRemoteDeviceObserver>();
35 std::mutex deviceMutex;
36
37 std::map<std::string, std::function<napi_value(napi_env env)>> g_callbackDefaultValue = {
38 {REGISTER_DEVICE_FIND_TYPE,
__anonf2a9bdc00102() 39 [](napi_env env) -> napi_value {
40 napi_value result = 0;
41 napi_value value = 0;
42 napi_create_array(env, &result);
43 napi_create_string_utf8(env, INVALID_DEVICE_ID.c_str(), NAPI_AUTO_LENGTH, &value);
44 napi_set_element(env, result, 0, value);
45 return result;
46 }},
47 {REGISTER_PIN_REQUEST_TYPE,
__anonf2a9bdc00202() 48 [](napi_env env) -> napi_value {
49 napi_value result = 0;
50 napi_value deviceId = nullptr;
51 napi_value pinCode = nullptr;
52 napi_create_object(env, &result);
53 napi_create_string_utf8(env, INVALID_DEVICE_ID.c_str(), NAPI_AUTO_LENGTH, &deviceId);
54 napi_set_named_property(env, result, "deviceId", deviceId);
55 napi_create_string_utf8(env, INVALID_PIN_CODE.c_str(), NAPI_AUTO_LENGTH, &pinCode);
56 napi_set_named_property(env, result, "pinCode", pinCode);
57 return result;
58 }},
__anonf2a9bdc00302() 59 {REGISTER_BOND_STATE_TYPE, [](napi_env env) -> napi_value {
60 napi_value result = 0;
61 napi_value deviceId = nullptr;
62 napi_value state = nullptr;
63 napi_create_object(env, &result);
64 napi_create_string_utf8(env, INVALID_DEVICE_ID.c_str(), NAPI_AUTO_LENGTH, &deviceId);
65 napi_set_named_property(env, result, "deviceId", deviceId);
66 napi_create_int32(env, static_cast<int32_t>(BondState::BOND_STATE_INVALID), &state);
67 napi_set_named_property(env, result, "state", state);
68 return result;
69 }}};
70
DefineConnectionFunctions(napi_env env,napi_value exports)71 napi_value DefineConnectionFunctions(napi_env env, napi_value exports)
72 {
73 HILOGD("enter");
74 RegisterObserverToHost();
75 ConnectionPropertyValueInit(env, exports);
76 napi_property_descriptor desc[] = {
77 DECLARE_NAPI_FUNCTION("getBtConnectionState", GetBtConnectionState),
78 #ifdef BLUETOOTH_API_SINCE_10
79 DECLARE_NAPI_FUNCTION("pairDevice", PairDeviceAsync),
80 DECLARE_NAPI_FUNCTION("cancelPairedDevice", CancelPairedDeviceAsync),
81 DECLARE_NAPI_FUNCTION("getProfileConnectionState", GetProfileConnectionStateEx),
82 #else
83 DECLARE_NAPI_FUNCTION("pairDevice", PairDevice),
84 DECLARE_NAPI_FUNCTION("cancelPairedDevice", CancelPairedDevice),
85 DECLARE_NAPI_FUNCTION("getProfileConnectionState", GetProfileConnectionState),
86 #endif
87 DECLARE_NAPI_FUNCTION("getRemoteDeviceName", GetRemoteDeviceName),
88 DECLARE_NAPI_FUNCTION("getRemoteDeviceClass", GetRemoteDeviceClass),
89 DECLARE_NAPI_FUNCTION("getLocalName", GetLocalName),
90 DECLARE_NAPI_FUNCTION("getPairedDevices", GetPairedDevices),
91 DECLARE_NAPI_FUNCTION("getProfileConnState", GetProfileConnectionState),
92 DECLARE_NAPI_FUNCTION("setDevicePairingConfirmation", SetDevicePairingConfirmation),
93 DECLARE_NAPI_FUNCTION("setLocalName", SetLocalName),
94 DECLARE_NAPI_FUNCTION("setBluetoothScanMode", SetBluetoothScanMode),
95 DECLARE_NAPI_FUNCTION("getBluetoothScanMode", GetBluetoothScanMode),
96 DECLARE_NAPI_FUNCTION("startBluetoothDiscovery", StartBluetoothDiscovery),
97 DECLARE_NAPI_FUNCTION("stopBluetoothDiscovery", StopBluetoothDiscovery),
98 #ifdef BLUETOOTH_API_SINCE_10
99 DECLARE_NAPI_FUNCTION("setDevicePinCode", SetDevicePinCode),
100 DECLARE_NAPI_FUNCTION("cancelPairingDevice", CancelPairingDevice),
101 DECLARE_NAPI_FUNCTION("pairCredibleDevice", PairCredibleDevice),
102 DECLARE_NAPI_FUNCTION("getLocalProfileUuids", GetLocalProfileUuids),
103 DECLARE_NAPI_FUNCTION("getRemoteProfileUuids", GetRemoteProfileUuids),
104 DECLARE_NAPI_FUNCTION("on", RegisterConnectionObserver),
105 DECLARE_NAPI_FUNCTION("off", DeRegisterConnectionObserver),
106 DECLARE_NAPI_FUNCTION("isBluetoothDiscovering", IsBluetoothDiscovering),
107 DECLARE_NAPI_FUNCTION("getPairState", GetPairState),
108 DECLARE_NAPI_FUNCTION("connectAllowedProfiles", ConnectAllowedProfiles),
109 DECLARE_NAPI_FUNCTION("disconnectAllowedProfiles", DisconnectAllowedProfiles),
110 DECLARE_NAPI_FUNCTION("getRemoteProductId", GetRemoteProductId),
111 #endif
112 };
113
114 napi_define_properties(env, exports, sizeof(desc) / sizeof(desc[0]), desc);
115 return exports;
116 }
117
IsValidObserverType(const std::string & callbackName)118 static bool IsValidObserverType(const std::string &callbackName)
119 {
120 if (callbackName == REGISTER_DEVICE_FIND_TYPE || callbackName == REGISTER_PIN_REQUEST_TYPE ||
121 callbackName == REGISTER_BOND_STATE_TYPE) {
122 return true;
123 } else {
124 HILOGE("not support %{public}s.", callbackName.c_str());
125 return false;
126 }
127 }
128
CheckRegisterObserver(napi_env env,napi_callback_info info)129 napi_status CheckRegisterObserver(napi_env env, napi_callback_info info)
130 {
131 size_t argc = ARGS_SIZE_TWO;
132 napi_value argv[ARGS_SIZE_TWO] = {0};
133 napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr);
134 NAPI_BT_RETURN_IF(argc != ARGS_SIZE_TWO, "Requires 2 arguments.", napi_invalid_arg);
135
136 std::string callbackName;
137 NAPI_BT_CALL_RETURN(NapiParseString(env, argv[PARAM0], callbackName));
138 NAPI_BT_RETURN_IF(!IsValidObserverType(callbackName), "Invalid type", napi_invalid_arg);
139
140 auto napiCallback = std::make_shared<NapiCallback>(env, argv[PARAM1]);
141 if (callbackName == REGISTER_BOND_STATE_TYPE) {
142 g_remoteDeviceObserver->RegisterCallback(callbackName, napiCallback);
143 } else {
144 g_connectionObserver->RegisterCallback(callbackName, napiCallback);
145 }
146 HILOGI("%{public}s registered", callbackName.c_str());
147 return napi_ok;
148 }
149
CheckDeRegisterObserver(napi_env env,napi_callback_info info)150 napi_status CheckDeRegisterObserver(napi_env env, napi_callback_info info)
151 {
152 size_t argc = ARGS_SIZE_TWO;
153 napi_value argv[ARGS_SIZE_TWO] = {0};
154 napi_value thisVar = nullptr;
155 NAPI_BT_CALL_RETURN(napi_get_cb_info(env, info, &argc, argv, &thisVar, nullptr));
156 NAPI_BT_RETURN_IF(argc != ARGS_SIZE_ONE && argc != ARGS_SIZE_TWO, "Requires 1 or 2 arguments.", napi_invalid_arg);
157
158 std::string callbackName;
159 NAPI_BT_CALL_RETURN(NapiParseString(env, argv[PARAM0], callbackName));
160 NAPI_BT_RETURN_IF(!IsValidObserverType(callbackName), "Invalid type", napi_invalid_arg);
161
162 if (callbackName == REGISTER_BOND_STATE_TYPE) {
163 g_remoteDeviceObserver->DeRegisterCallback(callbackName);
164 } else {
165 g_connectionObserver->DeRegisterCallback(callbackName);
166 }
167 HILOGI("%{public}s unregistered", callbackName.c_str());
168 return napi_ok;
169 }
170
RegisterConnectionObserver(napi_env env,napi_callback_info info)171 napi_value RegisterConnectionObserver(napi_env env, napi_callback_info info)
172 {
173 HILOGD("enter");
174 auto status = CheckRegisterObserver(env, info);
175 NAPI_BT_ASSERT_RETURN_UNDEF(env, status == napi_ok, BT_ERR_INVALID_PARAM);
176
177 napi_value ret = nullptr;
178 napi_get_undefined(env, &ret);
179 return ret;
180 }
181
DeRegisterConnectionObserver(napi_env env,napi_callback_info info)182 napi_value DeRegisterConnectionObserver(napi_env env, napi_callback_info info)
183 {
184 HILOGD("enter");
185 auto status = CheckDeRegisterObserver(env, info);
186 NAPI_BT_ASSERT_RETURN_UNDEF(env, status == napi_ok, BT_ERR_INVALID_PARAM);
187
188 napi_value ret = nullptr;
189 napi_get_undefined(env, &ret);
190 return ret;
191 }
192
GetBtConnectionState(napi_env env,napi_callback_info info)193 napi_value GetBtConnectionState(napi_env env, napi_callback_info info)
194 {
195 HILOGD("enter");
196 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
197 int state = static_cast<int>(BTConnectState::DISCONNECTED);
198 int32_t err = host->GetBtConnectionState(state);
199 HILOGI("start state %{public}d", state);
200 napi_value result = nullptr;
201 napi_create_int32(env, GetProfileConnectionState(state), &result);
202 NAPI_BT_ASSERT_RETURN(env, err == BT_NO_ERROR, err, result);
203 HILOGI("end");
204 return result;
205 }
206
PairDevice(napi_env env,napi_callback_info info)207 napi_value PairDevice(napi_env env, napi_callback_info info)
208 {
209 HILOGD("enter");
210 std::string remoteAddr = INVALID_MAC_ADDRESS;
211 bool checkRet = CheckDeivceIdParam(env, info, remoteAddr);
212 NAPI_BT_ASSERT_RETURN_FALSE(env, checkRet, BT_ERR_INVALID_PARAM);
213
214 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
215 int32_t ret = remoteDevice.StartPair();
216 NAPI_BT_ASSERT_RETURN_FALSE(env, ret == BT_NO_ERROR, ret);
217 return NapiGetBooleanTrue(env);
218 }
219
CancelPairedDevice(napi_env env,napi_callback_info info)220 napi_value CancelPairedDevice(napi_env env, napi_callback_info info)
221 {
222 HILOGD("enter");
223 std::string remoteAddr{};
224 bool checkRet = CheckDeivceIdParam(env, info, remoteAddr);
225 NAPI_BT_ASSERT_RETURN_FALSE(env, checkRet, BT_ERR_INVALID_PARAM);
226
227 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
228 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
229 int32_t ret = host->RemovePair(remoteDevice);
230 NAPI_BT_ASSERT_RETURN_FALSE(env, ret == BT_NO_ERROR, ret);
231
232 return NapiGetBooleanTrue(env);
233 }
234
GetRemoteDeviceName(napi_env env,napi_callback_info info)235 napi_value GetRemoteDeviceName(napi_env env, napi_callback_info info)
236 {
237 HILOGD("start");
238 std::string remoteAddr = INVALID_MAC_ADDRESS;
239 std::string name = INVALID_NAME;
240 napi_value result = nullptr;
241 bool checkRet = CheckDeivceIdParam(env, info, remoteAddr);
242 napi_create_string_utf8(env, name.c_str(), name.size(), &result);
243 NAPI_BT_ASSERT_RETURN(env, checkRet == true, BT_ERR_INVALID_PARAM, result);
244
245 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
246 int32_t err = remoteDevice.GetDeviceName(name);
247 napi_create_string_utf8(env, name.c_str(), name.size(), &result);
248 NAPI_BT_ASSERT_RETURN(env, err == BT_NO_ERROR, err, result);
249 return result;
250 }
251
GetRemoteDeviceClass(napi_env env,napi_callback_info info)252 napi_value GetRemoteDeviceClass(napi_env env, napi_callback_info info)
253 {
254 HILOGD("start");
255 std::string remoteAddr = INVALID_MAC_ADDRESS;
256 bool checkRet = CheckDeivceIdParam(env, info, remoteAddr);
257 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet, BT_ERR_INVALID_PARAM);
258
259 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
260 int tmpCod = MajorClass::MAJOR_UNCATEGORIZED;
261 int tmpMajorClass = MajorClass::MAJOR_UNCATEGORIZED;
262 int tmpMajorMinorClass = MajorClass::MAJOR_UNCATEGORIZED;
263 int32_t err = remoteDevice.GetDeviceProductType(tmpCod, tmpMajorClass, tmpMajorMinorClass);
264
265 napi_value result = nullptr;
266 napi_create_object(env, &result);
267 napi_value majorClass = 0;
268 napi_create_int32(env, tmpMajorClass, &majorClass);
269 napi_set_named_property(env, result, "majorClass", majorClass);
270 napi_value majorMinorClass = 0;
271 napi_create_int32(env, tmpMajorMinorClass, &majorMinorClass);
272 napi_set_named_property(env, result, "majorMinorClass", majorMinorClass);
273 napi_value cod = 0;
274 napi_create_int32(env, tmpCod, &cod);
275 napi_set_named_property(env, result, "classOfDevice", cod);
276 NAPI_BT_ASSERT_RETURN(env, err == BT_NO_ERROR, err, result);
277 return result;
278 }
279
GetLocalName(napi_env env,napi_callback_info info)280 napi_value GetLocalName(napi_env env, napi_callback_info info)
281 {
282 napi_value result = nullptr;
283 HILOGD("enter");
284 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
285 std::string localName = INVALID_NAME;
286 int32_t err = host->GetLocalName(localName);
287 napi_create_string_utf8(env, localName.c_str(), localName.size(), &result);
288 NAPI_BT_ASSERT_RETURN(env, err == BT_NO_ERROR, err, result);
289 HILOGI("end");
290 return result;
291 }
292
GetPairedDevices(napi_env env,napi_callback_info info)293 napi_value GetPairedDevices(napi_env env, napi_callback_info info)
294 {
295 HILOGD("enter");
296 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
297 std::vector<BluetoothRemoteDevice> remoteDeviceLists;
298 int32_t ret = host->GetPairedDevices(BT_TRANSPORT_BREDR, remoteDeviceLists);
299 napi_value result = nullptr;
300 int count = 0;
301 napi_create_array(env, &result);
302 for (auto vec : remoteDeviceLists) {
303 napi_value remoteDeviceResult;
304 napi_create_string_utf8(env, vec.GetDeviceAddr().c_str(), vec.GetDeviceAddr().size(), &remoteDeviceResult);
305 napi_set_element(env, result, count, remoteDeviceResult);
306 count++;
307 }
308 NAPI_BT_ASSERT_RETURN(env, ret == BT_NO_ERROR, ret, result);
309 HILOGI("end");
310 return result;
311 }
312
GetProfileConnectionState(napi_env env,napi_callback_info info)313 napi_value GetProfileConnectionState(napi_env env, napi_callback_info info)
314 {
315 HILOGD("enter");
316 int profileId = 0;
317 bool checkRet = CheckProfileIdParam(env, info, profileId);
318 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet, BT_ERR_INVALID_PARAM);
319
320 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
321 int state = static_cast<int>(BTConnectState::DISCONNECTED);
322 int32_t err = host->GetBtProfileConnState(GetProfileId(profileId), state);
323 int status = GetProfileConnectionState(state);
324 napi_value ret = nullptr;
325 napi_create_int32(env, status, &ret);
326 NAPI_BT_ASSERT_RETURN(env, err == BT_NO_ERROR, err, ret);
327 HILOGI("status: %{public}d", status);
328 return ret;
329 }
330
GetProfileConnectionStateEx(napi_env env,napi_callback_info info)331 napi_value GetProfileConnectionStateEx(napi_env env, napi_callback_info info)
332 {
333 HILOGD("enter");
334 int profileId = 0;
335 size_t argSize = ARGS_SIZE_ONE;
336 bool checkRet = CheckProfileIdParamEx(env, info, profileId, argSize);
337 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet, BT_ERR_INVALID_PARAM);
338 HILOGD("argSize = %{public}zu", argSize);
339
340 napi_value ret = nullptr;
341 if (argSize == 0) {
342 ret = GetBtConnectionState(env, info);
343 } else {
344 ret = GetProfileConnectionState(env, info);
345 }
346 return ret;
347 }
348
SetDevicePairingConfirmation(napi_env env,napi_callback_info info)349 napi_value SetDevicePairingConfirmation(napi_env env, napi_callback_info info)
350 {
351 HILOGD("enter");
352 std::string remoteAddr{};
353 bool accept = false;
354 bool checkRet = CheckSetDevicePairingConfirmationParam(env, info, remoteAddr, accept);
355 NAPI_BT_ASSERT_RETURN_FALSE(env, checkRet, BT_ERR_INVALID_PARAM);
356
357 HILOGI("SetDevicePairingConfirmation::accept = %{public}d", accept);
358 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
359 int32_t ret = BT_NO_ERROR;
360 if (accept) {
361 ret = remoteDevice.SetDevicePairingConfirmation(accept);
362 } else {
363 ret = remoteDevice.CancelPairing();
364 }
365 NAPI_BT_ASSERT_RETURN_FALSE(env, ret == BT_NO_ERROR, ret);
366 return NapiGetBooleanTrue(env);
367 }
368
SetLocalName(napi_env env,napi_callback_info info)369 napi_value SetLocalName(napi_env env, napi_callback_info info)
370 {
371 HILOGD("enter");
372 std::string localName = INVALID_NAME;
373 bool checkRet = CheckLocalNameParam(env, info, localName);
374 NAPI_BT_ASSERT_RETURN_FALSE(env, checkRet, BT_ERR_INVALID_PARAM);
375
376 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
377 int32_t ret = host->SetLocalName(localName);
378 NAPI_BT_ASSERT_RETURN_FALSE(env, ret == BT_NO_ERROR, ret);
379 return NapiGetBooleanTrue(env);
380 }
381
SetBluetoothScanMode(napi_env env,napi_callback_info info)382 napi_value SetBluetoothScanMode(napi_env env, napi_callback_info info)
383 {
384 HILOGD("enter");
385 int32_t mode = 0;
386 int32_t duration = 0;
387 bool checkRet = CheckSetBluetoothScanModeParam(env, info, mode, duration);
388 NAPI_BT_ASSERT_RETURN_FALSE(env, checkRet, BT_ERR_INVALID_PARAM);
389 HILOGI("mode = %{public}d,duration = %{public}d", mode, duration);
390
391 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
392 int32_t ret = host->SetBtScanMode(mode, duration);
393 NAPI_BT_ASSERT_RETURN_FALSE(env, ret == BT_NO_ERROR, ret);
394 host->SetBondableMode(BT_TRANSPORT_BREDR, 1);
395 return NapiGetBooleanTrue(env);
396 }
397
GetBluetoothScanMode(napi_env env,napi_callback_info info)398 napi_value GetBluetoothScanMode(napi_env env, napi_callback_info info)
399 {
400 HILOGD("enter");
401 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
402 int32_t scanMode = 0;
403 int32_t err = host->GetBtScanMode(scanMode);
404 napi_value result = nullptr;
405 napi_create_uint32(env, scanMode, &result);
406 NAPI_BT_ASSERT_RETURN(env, err == BT_NO_ERROR, err, result);
407 HILOGI("end");
408 return result;
409 }
410
StartBluetoothDiscovery(napi_env env,napi_callback_info info)411 napi_value StartBluetoothDiscovery(napi_env env, napi_callback_info info)
412 {
413 HILOGD("enter");
414 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
415 int ret = host->StartBtDiscovery();
416 NAPI_BT_ASSERT_RETURN_FALSE(env, ret == BT_NO_ERROR, ret);
417 return NapiGetBooleanTrue(env);
418 }
419
StopBluetoothDiscovery(napi_env env,napi_callback_info info)420 napi_value StopBluetoothDiscovery(napi_env env, napi_callback_info info)
421 {
422 HILOGD("enter");
423 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
424 int ret = host->CancelBtDiscovery();
425 NAPI_BT_ASSERT_RETURN_FALSE(env, ret == BT_NO_ERROR, ret);
426 return NapiGetBooleanTrue(env);
427 }
428
429 #ifdef BLUETOOTH_API_SINCE_10
ParseSetDevicePinCodeParameters(napi_env env,napi_callback_info info,std::string & outRemoteAddr,std::string & outPinCode)430 napi_status ParseSetDevicePinCodeParameters(napi_env env, napi_callback_info info,
431 std::string &outRemoteAddr, std::string &outPinCode)
432 {
433 HILOGD("enter");
434 std::string remoteAddr{};
435 std::string pinCode{};
436 size_t argc = ARGS_SIZE_THREE;
437 napi_value argv[ARGS_SIZE_THREE] = {nullptr};
438 NAPI_BT_CALL_RETURN(napi_get_cb_info(env, info, &argc, argv, nullptr, NULL));
439 NAPI_BT_RETURN_IF(argc != ARGS_SIZE_TWO && argc != ARGS_SIZE_THREE,
440 "Requires 2 or 3 arguments.", napi_invalid_arg);
441 NAPI_BT_CALL_RETURN(NapiParseBdAddr(env, argv[PARAM0], remoteAddr));
442 NAPI_BT_RETURN_IF(!ParseString(env, pinCode, argv[PARAM1]), "pinCode ParseString failed", napi_invalid_arg);
443 outRemoteAddr = remoteAddr;
444 outPinCode = pinCode;
445 return napi_ok;
446 }
447
SetDevicePinCode(napi_env env,napi_callback_info info)448 napi_value SetDevicePinCode(napi_env env, napi_callback_info info)
449 {
450 HILOGD("enter");
451 std::string remoteAddr = "";
452 std::string pinCode = "";
453 auto status = ParseSetDevicePinCodeParameters(env, info, remoteAddr, pinCode);
454 NAPI_BT_ASSERT_RETURN_UNDEF(env, status == napi_ok, BT_ERR_INVALID_PARAM);
455
456 auto func = [remoteAddr, pinCode]() {
457 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
458 int32_t err = remoteDevice.SetDevicePin(pinCode);
459 HILOGI("SetDevicePinCode err: %{public}d", err);
460 return NapiAsyncWorkRet(err);
461 };
462 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
463 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
464 asyncWork->Run();
465 return asyncWork->GetRet();
466 }
467
CheckDeviceAsyncParam(napi_env env,napi_callback_info info,std::string & addr)468 napi_status CheckDeviceAsyncParam(napi_env env, napi_callback_info info, std::string &addr)
469 {
470 size_t argc = ARGS_SIZE_TWO;
471 napi_value argv[ARGS_SIZE_TWO] = {nullptr};
472 NAPI_BT_CALL_RETURN(napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr));
473 NAPI_BT_RETURN_IF(argc != ARGS_SIZE_ONE && argc != ARGS_SIZE_TWO, "Requires 1 or 2 arguments", napi_invalid_arg);
474 NAPI_BT_CALL_RETURN(NapiParseBdAddr(env, argv[PARAM0], addr));
475 return napi_ok;
476 }
477
PairDeviceAsync(napi_env env,napi_callback_info info)478 napi_value PairDeviceAsync(napi_env env, napi_callback_info info)
479 {
480 HILOGD("enter");
481 std::string remoteAddr = INVALID_MAC_ADDRESS;
482 auto checkRet = CheckDeviceAsyncParam(env, info, remoteAddr);
483 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet == napi_ok, BT_ERR_INVALID_PARAM);
484
485 auto func = [remoteAddr]() {
486 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
487 int32_t err = remoteDevice.StartPair();
488 HILOGI("err: %{public}d", err);
489 return NapiAsyncWorkRet(err);
490 };
491 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
492 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
493 asyncWork->Run();
494 return asyncWork->GetRet();
495 }
496
CancelPairedDeviceAsync(napi_env env,napi_callback_info info)497 napi_value CancelPairedDeviceAsync(napi_env env, napi_callback_info info)
498 {
499 HILOGD("enter");
500 std::string remoteAddr {};
501 bool checkRet = CheckDeviceAsyncParam(env, info, remoteAddr);
502 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet == napi_ok, BT_ERR_INVALID_PARAM);
503
504 auto func = [remoteAddr]() {
505 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
506 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
507 int32_t err = host->RemovePair(remoteDevice);
508 HILOGI("err: %{public}d", err);
509 return NapiAsyncWorkRet(err);
510 };
511 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
512 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
513 asyncWork->Run();
514 return asyncWork->GetRet();
515 }
516
CancelPairingDevice(napi_env env,napi_callback_info info)517 napi_value CancelPairingDevice(napi_env env, napi_callback_info info)
518 {
519 HILOGD("enter");
520 std::string remoteAddr{};
521 bool checkRet = CheckDeviceAsyncParam(env, info, remoteAddr);
522 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet == napi_ok, BT_ERR_INVALID_PARAM);
523
524 auto func = [remoteAddr]() {
525 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
526 int32_t err = remoteDevice.CancelPairing();
527 HILOGI("err: %{public}d", err);
528 return NapiAsyncWorkRet(err);
529 };
530 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
531 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
532 asyncWork->Run();
533 return asyncWork->GetRet();
534 }
535
CheckPairCredibleDeviceParam(napi_env env,napi_callback_info info,std::string & addr,int & transport)536 napi_status CheckPairCredibleDeviceParam(napi_env env, napi_callback_info info, std::string &addr, int &transport)
537 {
538 size_t argc = ARGS_SIZE_THREE;
539 napi_value argv[ARGS_SIZE_THREE] = {nullptr};
540 NAPI_BT_CALL_RETURN(napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr));
541 NAPI_BT_RETURN_IF(argc != ARGS_SIZE_TWO && argc != ARGS_SIZE_THREE, "Requires 2 or 3 arguments.", napi_invalid_arg);
542 NAPI_BT_CALL_RETURN(NapiParseBdAddr(env, argv[PARAM0], addr));
543 NAPI_BT_RETURN_IF(!ParseInt32(env, transport, argv[PARAM1]), "ParseInt32 failed", napi_invalid_arg);
544 NAPI_BT_RETURN_IF(!IsValidTransport(transport), "Invalid transport", napi_invalid_arg);
545 return napi_ok;
546 }
547
PairCredibleDevice(napi_env env,napi_callback_info info)548 napi_value PairCredibleDevice(napi_env env, napi_callback_info info)
549 {
550 HILOGD("enter");
551 std::string remoteAddr = INVALID_MAC_ADDRESS;
552 int transport = BT_TRANSPORT_NONE;
553 auto status = CheckPairCredibleDeviceParam(env, info, remoteAddr, transport);
554 NAPI_BT_ASSERT_RETURN_UNDEF(env, status == napi_ok, BT_ERR_INVALID_PARAM);
555
556 auto func = [remoteAddr, transport]() {
557 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr, transport);
558 int32_t err = remoteDevice.StartCrediblePair();
559 HILOGI("err: %{public}d", err);
560 return NapiAsyncWorkRet(err);
561 };
562 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
563 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
564 asyncWork->Run();
565 return asyncWork->GetRet();
566 }
567
CheckGetProfileUuids(napi_env env,napi_callback_info info,std::string & address)568 napi_status CheckGetProfileUuids(napi_env env, napi_callback_info info, std::string &address)
569 {
570 size_t argc = ARGS_SIZE_TWO;
571 napi_value argv[ARGS_SIZE_TWO] = {0};
572 NAPI_BT_CALL_RETURN(napi_get_cb_info(env, info, &argc, argv, nullptr, nullptr));
573 NAPI_BT_RETURN_IF(argc != ARGS_SIZE_ONE && argc != ARGS_SIZE_TWO, "Requires 1 or 2 arguments.", napi_invalid_arg);
574 NAPI_BT_CALL_RETURN(NapiParseBdAddr(env, argv[PARAM0], address));
575 return napi_ok;
576 }
577
GetLocalProfileUuids(napi_env env,napi_callback_info info)578 napi_value GetLocalProfileUuids(napi_env env, napi_callback_info info)
579 {
580 HILOGD("enter");
581 auto func = []() {
582 std::vector<std::string> uuids{};
583 int32_t err = BluetoothHost::GetDefaultHost().GetLocalProfileUuids(uuids);
584 HILOGI("err: %{public}d", err);
585 auto object = std::make_shared<NapiNativeUuidsArray>(uuids);
586 return NapiAsyncWorkRet(err, object);
587 };
588 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
589 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
590 asyncWork->Run();
591 return asyncWork->GetRet();
592 }
593
GetRemoteProfileUuids(napi_env env,napi_callback_info info)594 napi_value GetRemoteProfileUuids(napi_env env, napi_callback_info info)
595 {
596 HILOGD("enter");
597 std::string address;
598 auto status = CheckGetProfileUuids(env, info, address);
599 NAPI_BT_ASSERT_RETURN_UNDEF(env, status == napi_ok, BT_ERR_INVALID_PARAM);
600 auto func = [address]() {
601 std::vector<std::string> uuids{};
602 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(address);
603 int32_t err = remoteDevice.GetDeviceUuids(uuids);
604 HILOGI("err: %{public}d", err);
605 auto object = std::make_shared<NapiNativeUuidsArray>(uuids);
606 return NapiAsyncWorkRet(err, object);
607 };
608 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
609 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
610 asyncWork->Run();
611 return asyncWork->GetRet();
612 }
613
IsBluetoothDiscovering(napi_env env,napi_callback_info info)614 napi_value IsBluetoothDiscovering(napi_env env, napi_callback_info info)
615 {
616 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
617 bool isDiscovering = false;
618 int32_t err = host->IsBtDiscovering(isDiscovering);
619 napi_value result = nullptr;
620 NAPI_BT_ASSERT_RETURN(env, napi_get_boolean(env, isDiscovering, &result) == napi_ok, err, result);
621 NAPI_BT_ASSERT_RETURN(env, err = BT_NO_ERROR, err, result);
622 HILOGE("isBluetoothDiscovering :%{public}d", isDiscovering);
623 return result;
624 }
625
GetPairState(napi_env env,napi_callback_info info)626 napi_value GetPairState(napi_env env, napi_callback_info info)
627 {
628 std::string remoteAddr = INVALID_MAC_ADDRESS;
629 bool checkRet = CheckDeivceIdParam(env, info, remoteAddr);
630 NAPI_BT_ASSERT_RETURN_FALSE(env, checkRet, BT_ERR_INVALID_PARAM);
631 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
632 int pairState = PAIR_NONE;
633 int32_t err = remoteDevice.GetPairState(pairState);
634 napi_value result = nullptr;
635 NAPI_BT_ASSERT_RETURN(env, napi_create_int32(env, pairState, &result) == napi_ok, err, result);
636 NAPI_BT_ASSERT_RETURN(env, err = BT_NO_ERROR, err, result);
637 HILOGE("getPairState :%{public}d", pairState);
638 return result;
639 }
640
ConnectAllowedProfiles(napi_env env,napi_callback_info info)641 napi_value ConnectAllowedProfiles(napi_env env, napi_callback_info info)
642 {
643 HILOGI("enter");
644 std::string remoteAddr = INVALID_MAC_ADDRESS;
645 auto checkRet = CheckDeviceAsyncParam(env, info, remoteAddr);
646 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet == napi_ok, BT_ERR_INVALID_PARAM);
647
648 auto func = [remoteAddr]() {
649 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
650 int32_t ret = host->ConnectAllowedProfiles(remoteAddr);
651 HILOGI("ret: %{public}d", ret);
652 return NapiAsyncWorkRet(ret);
653 };
654 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
655 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
656 asyncWork->Run();
657 return asyncWork->GetRet();
658 }
659
DisconnectAllowedProfiles(napi_env env,napi_callback_info info)660 napi_value DisconnectAllowedProfiles(napi_env env, napi_callback_info info)
661 {
662 HILOGI("enter");
663 std::string remoteAddr = INVALID_MAC_ADDRESS;
664 auto checkRet = CheckDeviceAsyncParam(env, info, remoteAddr);
665 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet == napi_ok, BT_ERR_INVALID_PARAM);
666
667 auto func = [remoteAddr]() {
668 BluetoothHost *host = &BluetoothHost::GetDefaultHost();
669 int32_t ret = host->DisconnectAllowedProfiles(remoteAddr);
670 HILOGI("ret: %{public}d", ret);
671 return NapiAsyncWorkRet(ret);
672 };
673 auto asyncWork = NapiAsyncWorkFactory::CreateAsyncWork(env, info, func, ASYNC_WORK_NO_NEED_CALLBACK);
674 NAPI_BT_ASSERT_RETURN_UNDEF(env, asyncWork, BT_ERR_INTERNAL_ERROR);
675 asyncWork->Run();
676 return asyncWork->GetRet();
677 }
678
GetRemoteProductId(napi_env env,napi_callback_info info)679 napi_value GetRemoteProductId(napi_env env, napi_callback_info info)
680 {
681 HILOGD("start");
682 std::string remoteAddr = INVALID_MAC_ADDRESS;
683 bool checkRet = CheckDeivceIdParam(env, info, remoteAddr);
684 NAPI_BT_ASSERT_RETURN_UNDEF(env, checkRet, BT_ERR_INVALID_PARAM);
685
686 BluetoothRemoteDevice remoteDevice = BluetoothRemoteDevice(remoteAddr);
687 std::string productId;
688 int32_t err = remoteDevice.GetDeviceProductId(productId);
689
690 napi_value result = nullptr;
691 napi_create_string_utf8(env, productId.c_str(), productId.size(), &result);
692 NAPI_BT_ASSERT_RETURN(env, err == BT_NO_ERROR, err, result);
693 HILOGI("GetRemoteProductId :%{public}s", productId.c_str());
694 return result;
695 }
696
697 #endif
698
ConnectionPropertyValueInit(napi_env env,napi_value exports)699 napi_value ConnectionPropertyValueInit(napi_env env, napi_value exports)
700 {
701 HILOGD("enter");
702 napi_value scanModeObj = ScanModeInit(env);
703 napi_value bondStateObj = BondStateInit(env);
704 #ifdef BLUETOOTH_API_SINCE_10
705 napi_value bluetoothTransportObject = BluetoothTransportInit(env);
706 napi_value pinTypeObject = PinTypeInit(env);
707 #endif
708 napi_property_descriptor exportProperties[] = {
709 DECLARE_NAPI_PROPERTY("ScanMode", scanModeObj),
710 DECLARE_NAPI_PROPERTY("BondState", bondStateObj),
711 #ifdef BLUETOOTH_API_SINCE_10
712 DECLARE_NAPI_PROPERTY("BluetoothTransport", bluetoothTransportObject),
713 DECLARE_NAPI_PROPERTY("PinType", pinTypeObject),
714 #endif
715 };
716 napi_define_properties(env, exports, sizeof(exportProperties) / sizeof(*exportProperties), exportProperties);
717 return exports;
718 }
719
ScanModeInit(napi_env env)720 napi_value ScanModeInit(napi_env env)
721 {
722 HILOGD("enter");
723 napi_value scanMode = nullptr;
724 napi_create_object(env, &scanMode);
725 SetNamedPropertyByInteger(env, scanMode, static_cast<int>(ScanMode::SCAN_MODE_NONE), "SCAN_MODE_NONE");
726 SetNamedPropertyByInteger(
727 env, scanMode, static_cast<int>(ScanMode::SCAN_MODE_CONNECTABLE), "SCAN_MODE_CONNECTABLE");
728 SetNamedPropertyByInteger(
729 env, scanMode, static_cast<int>(ScanMode::SCAN_MODE_GENERAL_DISCOVERABLE), "SCAN_MODE_GENERAL_DISCOVERABLE");
730 SetNamedPropertyByInteger(
731 env, scanMode, static_cast<int>(ScanMode::SCAN_MODE_LIMITED_DISCOVERABLE), "SCAN_MODE_LIMITED_DISCOVERABLE");
732 SetNamedPropertyByInteger(env,
733 scanMode,
734 static_cast<int>(ScanMode::SCAN_MODE_CONNECTABLE_GENERAL_DISCOVERABLE),
735 "SCAN_MODE_CONNECTABLE_GENERAL_DISCOVERABLE");
736 SetNamedPropertyByInteger(env,
737 scanMode,
738 static_cast<int>(ScanMode::SCAN_MODE_CONNECTABLE_LIMITED_DISCOVERABLE),
739 "SCAN_MODE_CONNECTABLE_LIMITED_DISCOVERABLE");
740 return scanMode;
741 }
742
BondStateInit(napi_env env)743 napi_value BondStateInit(napi_env env)
744 {
745 HILOGD("enter");
746 napi_value bondState = nullptr;
747 napi_create_object(env, &bondState);
748 SetNamedPropertyByInteger(env, bondState, static_cast<int>(BondState::BOND_STATE_INVALID), "BOND_STATE_INVALID");
749 SetNamedPropertyByInteger(env, bondState, static_cast<int>(BondState::BOND_STATE_BONDING), "BOND_STATE_BONDING");
750 SetNamedPropertyByInteger(env, bondState, static_cast<int>(BondState::BOND_STATE_BONDED), "BOND_STATE_BONDED");
751 return bondState;
752 }
753
754 #ifdef BLUETOOTH_API_SINCE_10
BluetoothTransportInit(napi_env env)755 napi_value BluetoothTransportInit(napi_env env)
756 {
757 HILOGD("enter");
758 napi_value bluetoothTransport = nullptr;
759 napi_create_object(env, &bluetoothTransport);
760 SetNamedPropertyByInteger(
761 env, bluetoothTransport, static_cast<int>(BluetoothTransport::TRANSPORT_BR_EDR), "TRANSPORT_BR_EDR");
762 SetNamedPropertyByInteger(
763 env, bluetoothTransport, static_cast<int>(BluetoothTransport::TRANSPORT_LE), "TRANSPORT_LE");
764 return bluetoothTransport;
765 }
766
PinTypeInit(napi_env env)767 napi_value PinTypeInit(napi_env env)
768 {
769 HILOGD("enter");
770 napi_value pinType = nullptr;
771 napi_create_object(env, &pinType);
772 SetNamedPropertyByInteger(
773 env, pinType, static_cast<int>(PinType::PIN_TYPE_ENTER_PIN_CODE), "PIN_TYPE_ENTER_PIN_CODE");
774 SetNamedPropertyByInteger(
775 env, pinType, static_cast<int>(PinType::PIN_TYPE_ENTER_PASSKEY), "PIN_TYPE_ENTER_PASSKEY");
776 SetNamedPropertyByInteger(
777 env, pinType, static_cast<int>(PinType::PIN_TYPE_CONFIRM_PASSKEY), "PIN_TYPE_CONFIRM_PASSKEY");
778 SetNamedPropertyByInteger(
779 env, pinType, static_cast<int>(PinType::PIN_TYPE_NO_PASSKEY_CONSENT), "PIN_TYPE_NO_PASSKEY_CONSENT");
780 SetNamedPropertyByInteger(
781 env, pinType, static_cast<int>(PinType::PIN_TYPE_NOTIFY_PASSKEY), "PIN_TYPE_NOTIFY_PASSKEY");
782 SetNamedPropertyByInteger(
783 env, pinType, static_cast<int>(PinType::PIN_TYPE_DISPLAY_PIN_CODE), "PIN_TYPE_DISPLAY_PIN_CODE");
784 SetNamedPropertyByInteger(env, pinType, static_cast<int>(PinType::PIN_TYPE_OOB_CONSENT), "PIN_TYPE_OOB_CONSENT");
785 SetNamedPropertyByInteger(
786 env, pinType, static_cast<int>(PinType::PIN_TYPE_PIN_16_DIGITS), "PIN_TYPE_PIN_16_DIGITS");
787 return pinType;
788 }
789 #endif
790
RegisterObserverToHost()791 void RegisterObserverToHost()
792 {
793 HILOGD("enter");
794 BluetoothHost &host = BluetoothHost::GetDefaultHost();
795 host.RegisterObserver(g_connectionObserver);
796 host.RegisterRemoteDeviceObserver(g_remoteDeviceObserver);
797 }
798 } // namespace Bluetooth
799 } // namespace OHOS