diff --git a/frameworks/js/napi/include/sensor_napi_utils.h b/frameworks/js/napi/include/sensor_napi_utils.h index 1b5ce939f644d65ea47bb6140789a2ab684d7631..d1a715ccd5eab330035f69d9ee7aa85bb56dc670 100644 --- a/frameworks/js/napi/include/sensor_napi_utils.h +++ b/frameworks/js/napi/include/sensor_napi_utils.h @@ -41,7 +41,7 @@ bool GetNativeFloat(const napi_env &env, const napi_value &value, float &number) napi_value GetNapiInt32(const napi_env &env, int32_t number); bool GetStringValue(const napi_env &env, const napi_value &value, string &result); void EmitAsyncCallbackWork(sptr asyncCallbackInfo); -void EmitUvEventLoop(sptr asyncCallbackInfo); +void EmitUvEventLoop(sptr asyncCallbackInfo, std::shared_ptr cb); void EmitPromiseWork(sptr asyncCallbackInfo); bool ConvertToFailData(const napi_env &env, sptr asyncCallbackInfo, napi_value result[2]); bool ConvertToGeomagneticData(const napi_env &env, sptr asyncCallbackInfo, napi_value result[2]); diff --git a/frameworks/js/napi/src/sensor_js.cpp b/frameworks/js/napi/src/sensor_js.cpp index e8945a0fd8684548229bce006425626e7cfb2134..df7b31f2a465296470a71c1ed870b4287bf140dc 100644 --- a/frameworks/js/napi/src/sensor_js.cpp +++ b/frameworks/js/napi/src/sensor_js.cpp @@ -75,33 +75,26 @@ static bool CheckSubscribe(SensorDescription sensorDesc) return iter != g_onCallbackInfos.end(); } -static bool copySensorData(sptr callbackInfo, SensorEvent *event) +static bool CopySensorData(SensorEvent *event, std::shared_ptr cb) { - CHKPF(callbackInfo); CHKPF(event); + CHKPF(cb); int32_t sensorTypeId = event->sensorTypeId; - callbackInfo->data.sensorData.sensorTypeId = sensorTypeId; - callbackInfo->data.sensorData.dataLength = event->dataLen; - callbackInfo->data.sensorData.timestamp = event->timestamp; - callbackInfo->data.sensorData.sensorAccuracy = event->option; + cb->sensorTypeId = sensorTypeId; + cb->dataLength = event->dataLen; + cb->timestamp = event->timestamp; + cb->sensorAccuracy = event->option; CHKPF(event->data); if (event->dataLen < sizeof(float)) { SEN_HILOGE("Event dataLen less than float size"); return false; } - auto data = reinterpret_cast(event->data); - if (sensorTypeId == SENSOR_TYPE_ID_WEAR_DETECTION && callbackInfo->type == SUBSCRIBE_CALLBACK) { - std::lock_guard onBodyLock(g_bodyMutex); - g_bodyState = *data; - callbackInfo->data.sensorData.data[0] = - (fabs(g_bodyState - BODY_STATE_EXCEPT) < THRESHOLD) ? true : false; - return true; - } - if (sizeof(callbackInfo->data.sensorData.data) < event->dataLen) { - SEN_HILOGE("callbackInfo space is insufficient"); + if (sizeof(cb->data) < event->dataLen) { + SEN_HILOGE("cb space is insufficient"); return false; } - if (memcpy_s(callbackInfo->data.sensorData.data, sizeof(callbackInfo->data.sensorData.data), + auto data = reinterpret_cast(event->data); + if (memcpy_s(cb->data, sizeof(cb->data), data, event->dataLen) != EOK) { SEN_HILOGE("Copy data failed"); return false; @@ -123,13 +116,20 @@ static void EmitSubscribeCallback(SensorEvent *event) return; } std::lock_guard subscribeLock(g_mutex); + std::shared_ptr cb = std::make_shared(); + if (!CopySensorData(event, cb)) { + SEN_HILOGE("Copy sensor data failed"); + return; + } + auto data = reinterpret_cast(event->data); auto callbacks = g_subscribeCallbacks[{event->deviceId, event->sensorTypeId, event->sensorId, event->location}]; for (auto &callback : callbacks) { - if (!copySensorData(callback, event)) { - SEN_HILOGE("Copy sensor data failed"); - continue; + if (event->sensorTypeId == SENSOR_TYPE_ID_WEAR_DETECTION && callback->type == SUBSCRIBE_CALLBACK) { + std::lock_guard onBodyLock(g_bodyMutex); + g_bodyState = *data; + cb->data[0] = (fabs(g_bodyState - BODY_STATE_EXCEPT) < THRESHOLD) ? true : false; } - EmitUvEventLoop(callback); + EmitUvEventLoop(callback, cb); } } @@ -140,13 +140,14 @@ static void EmitOnCallback(SensorEvent *event) return; } std::lock_guard onCallbackLock(g_onMutex); + std::shared_ptr cb = std::make_shared(); + if (!CopySensorData(event, cb)) { + SEN_HILOGE("Copy sensor data failed"); + return; + } auto onCallbackInfos = g_onCallbackInfos[{event->deviceId, event->sensorTypeId, event->sensorId, event->location}]; for (auto &onCallbackInfo : onCallbackInfos) { - if (!copySensorData(onCallbackInfo, event)) { - SEN_HILOGE("Copy sensor data failed"); - continue; - } - EmitUvEventLoop(onCallbackInfo); + EmitUvEventLoop(onCallbackInfo, cb); } } @@ -158,16 +159,17 @@ static void EmitOnceCallback(SensorEvent *event) if (iter == g_onceCallbackInfos.end()) { return; } + std::shared_ptr cb = std::make_shared(); + if (!CopySensorData(event, cb)) { + SEN_HILOGE("Copy sensor data failed"); + return; + } auto &onceCallbackInfos = iter->second; while (!onceCallbackInfos.empty()) { auto onceCallbackInfo = onceCallbackInfos.front(); auto beginIter = onceCallbackInfos.begin(); onceCallbackInfos.erase(beginIter); - if (!copySensorData(onceCallbackInfo, event)) { - SEN_HILOGE("Copy sensor data failed"); - continue; - } - EmitUvEventLoop(std::move(onceCallbackInfo)); + EmitUvEventLoop(std::move(onceCallbackInfo), cb); } g_onceCallbackInfos.erase({event->deviceId, event->sensorTypeId, event->sensorId, event->location}); @@ -201,9 +203,10 @@ void PlugDataCallbackImpl(SensorStatusEvent *plugEvent) CALL_LOG_ENTER; CHKPV(plugEvent); std::lock_guard plugCallbackLock(g_plugMutex); + std::shared_ptr cb = std::make_shared(); for (auto& callback : g_plugCallbackInfo) { UpdatePlugInfo(plugEvent, callback); - EmitUvEventLoop(callback); + EmitUvEventLoop(callback, cb); } } @@ -1810,7 +1813,8 @@ napi_value GetBodyState(napi_env env, napi_callback_info info) std::lock_guard onBodyLock(g_bodyMutex); asyncCallbackInfo->data.sensorData.data[0] = (fabs(g_bodyState - BODY_STATE_EXCEPT) < THRESHOLD) ? true : false; - EmitUvEventLoop(asyncCallbackInfo); + std::shared_ptr cb = std::make_shared(); + EmitUvEventLoop(asyncCallbackInfo, cb); return nullptr; } diff --git a/frameworks/js/napi/src/sensor_napi_utils.cpp b/frameworks/js/napi/src/sensor_napi_utils.cpp index 20adf402d3345e29afc6bdff49a42e39b994a4c8..35712581ea81316b6f35436a198962d371a2f42b 100644 --- a/frameworks/js/napi/src/sensor_napi_utils.cpp +++ b/frameworks/js/napi/src/sensor_napi_utils.cpp @@ -193,8 +193,6 @@ std::map> g_sensorAttributeList = { std::map g_convertfuncList = { {FAIL, ConvertToFailData}, - {ON_CALLBACK, ConvertToSensorData}, - {ONCE_CALLBACK, ConvertToSensorData}, {GET_GEOMAGNETIC_FIELD, ConvertToGeomagneticData}, {GET_ALTITUDE, ConvertToNumber}, {GET_GEOMAGNETIC_DIP, ConvertToNumber}, @@ -207,7 +205,6 @@ std::map g_convertfuncList = { {GET_SENSOR_LIST, ConvertToSensorInfos}, {GET_SINGLE_SENSOR, ConvertToSingleSensor}, {GET_BODY_STATE, ConvertToBodyData}, - {SUBSCRIBE_CALLBACK, ConvertToSensorData}, {SUBSCRIBE_COMPASS, ConvertToCompass}, {SENSOR_STATE_CHANGE, ConvertToSensorState}, }; @@ -365,34 +362,41 @@ bool ConvertToSensorState(const napi_env &env, sptr asyncCall return true; } -bool ConvertToSensorData(const napi_env &env, sptr asyncCallbackInfo, napi_value result[2]) +bool ConvertToSensorData(const napi_env &env, sptr asyncCallbackInfo, napi_value result[2], + std::shared_ptr data) { CHKPF(asyncCallbackInfo); - int32_t sensorTypeId = asyncCallbackInfo->data.sensorData.sensorTypeId; + CHKPF(data); + int32_t sensorTypeId = data->sensorTypeId; std::lock_guard sensorAttrListLock(g_sensorAttrListMutex); CHKNCF(env, (g_sensorAttributeList.find(sensorTypeId) != g_sensorAttributeList.end()), "Invalid sensor type"); if (sensorTypeId == SENSOR_TYPE_ID_WEAR_DETECTION && asyncCallbackInfo->type == SUBSCRIBE_CALLBACK) { - return ConvertToBodyData(env, asyncCallbackInfo, result); + CHKNRF(env, napi_create_object(env, &result[1]), "napi_create_object"); + napi_value status = nullptr; + CHKNRF(env, napi_get_boolean(env, data->data[0], &status), + "napi_get_boolean"); + CHKNRF(env, napi_set_named_property(env, result[1], "value", status), "napi_set_named_property"); + return true; } size_t size = g_sensorAttributeList[sensorTypeId].size(); - uint32_t dataLength = asyncCallbackInfo->data.sensorData.dataLength / sizeof(float); + uint32_t dataLength = data->dataLength / sizeof(float); CHKNCF(env, (size <= dataLength), "Data length mismatch"); CHKNRF(env, napi_create_object(env, &result[1]), "napi_create_object"); napi_value message = nullptr; auto sensorAttributes = g_sensorAttributeList[sensorTypeId]; for (uint32_t i = 0; i < size; ++i) { - CHKNRF(env, napi_create_double(env, asyncCallbackInfo->data.sensorData.data[i], &message), + CHKNRF(env, napi_create_double(env, data->data[i], &message), "napi_create_double"); CHKNRF(env, napi_set_named_property(env, result[1], sensorAttributes[i].c_str(), message), "napi_set_named_property"); message = nullptr; } - CHKNRF(env, napi_create_int64(env, asyncCallbackInfo->data.sensorData.timestamp, &message), + CHKNRF(env, napi_create_int64(env, data->timestamp, &message), "napi_create_int64"); CHKNRF(env, napi_set_named_property(env, result[1], "timestamp", message), "napi_set_named_property"); message = nullptr; - CHKNRF(env, napi_create_int32(env, asyncCallbackInfo->data.sensorData.sensorAccuracy, &message), + CHKNRF(env, napi_create_int32(env, data->sensorAccuracy, &message), "napi_create_int32"); CHKNRF(env, napi_set_named_property(env, result[1], "accuracy", message), "napi_set_named_property"); return true; @@ -553,20 +557,14 @@ void DeleteWork(uv_work_t *work) work = nullptr; } -void EmitUvEventLoop(sptr asyncCallbackInfo) +void EmitUvEventLoop(sptr asyncCallbackInfo, std::shared_ptr cb) { CHKPV(asyncCallbackInfo); - uv_loop_s *loop(nullptr); - CHKCV((napi_get_uv_event_loop(asyncCallbackInfo->env, &loop) == napi_ok), "napi_get_uv_event_loop fail"); - CHKPV(loop); - uv_work_t *work = new(std::nothrow) uv_work_t; - CHKPV(work); + CHKPV(cb); asyncCallbackInfo->IncStrongRef(nullptr); - work->data = asyncCallbackInfo.GetRefPtr(); - int32_t ret = uv_queue_work_with_qos(loop, work, [] (uv_work_t *work) { }, [] (uv_work_t *work, int status) { - CHKPV(work); - sptr asyncCallbackInfo(static_cast(work->data)); - DeleteWork(work); + auto event = asyncCallbackInfo.GetRefPtr(); + auto task = [event, cb]() { + sptr asyncCallbackInfo(static_cast(event)); /** * After the asynchronous task is created, the asyncCallbackInfo reference count is reduced * to 0 destruction, so you need to add 1 to the asyncCallbackInfo reference count when the @@ -593,14 +591,19 @@ void EmitUvEventLoop(sptr asyncCallbackInfo) } napi_value callResult = nullptr; napi_value result[2] = {0}; - if (!(g_convertfuncList.find(asyncCallbackInfo->type) != g_convertfuncList.end())) { - SEN_HILOGE("asyncCallbackInfo type is invalid"); - napi_throw_error(env, nullptr, "asyncCallbackInfo type is invalid"); - ReleaseCallback(asyncCallbackInfo); - napi_close_handle_scope(asyncCallbackInfo->env, scope); - return; + if (asyncCallbackInfo->type == ON_CALLBACK || asyncCallbackInfo->type == ONCE_CALLBACK || + asyncCallbackInfo->type == SUBSCRIBE_CALLBACK) { + ConvertToSensorData(env, asyncCallbackInfo, result, cb); + } else { + if (!(g_convertfuncList.find(asyncCallbackInfo->type) != g_convertfuncList.end())) { + SEN_HILOGE("asyncCallbackInfo type is invalid"); + napi_throw_error(env, nullptr, "asyncCallbackInfo type is invalid"); + ReleaseCallback(asyncCallbackInfo); + napi_close_handle_scope(asyncCallbackInfo->env, scope); + return; + } + g_convertfuncList[asyncCallbackInfo->type](env, asyncCallbackInfo, result); } - g_convertfuncList[asyncCallbackInfo->type](env, asyncCallbackInfo, result); if (napi_call_function(env, nullptr, callback, 1, &result[1], &callResult) != napi_ok) { SEN_HILOGE("napi_call_function callback fail"); napi_throw_error(env, nullptr, "napi_call_function callback fail"); @@ -610,11 +613,11 @@ void EmitUvEventLoop(sptr asyncCallbackInfo) } ReleaseCallback(asyncCallbackInfo); napi_close_handle_scope(asyncCallbackInfo->env, scope); - }, uv_qos_default); - if (ret != 0) { - SEN_HILOGE("uv_queue_work_with_qos fail"); + }; + auto ret = napi_send_event(asyncCallbackInfo->env, task, napi_eprio_immediate); + if (ret != napi_ok) { + SEN_HILOGE("Failed to SendEvent, ret:%{public}d", ret); asyncCallbackInfo->DecStrongRef(nullptr); - DeleteWork(work); } }