1f857971dSopenharmony_ci/* 2f857971dSopenharmony_ci * Copyright (c) 2022-2023 Huawei Device Co., Ltd. 3f857971dSopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License"); 4f857971dSopenharmony_ci * you may not use this file except in compliance with the License. 5f857971dSopenharmony_ci * You may obtain a copy of the License at 6f857971dSopenharmony_ci * 7f857971dSopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0 8f857971dSopenharmony_ci * 9f857971dSopenharmony_ci * Unless required by applicable law or agreed to in writing, software 10f857971dSopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS, 11f857971dSopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12f857971dSopenharmony_ci * See the License for the specific language governing permissions and 13f857971dSopenharmony_ci * limitations under the License. 14f857971dSopenharmony_ci */ 15f857971dSopenharmony_ci 16f857971dSopenharmony_ci#ifdef DEVICE_STATUS_SENSOR_ENABLE 17f857971dSopenharmony_ci#include "devicestatus_algorithm_manager.h" 18f857971dSopenharmony_ci 19f857971dSopenharmony_ci#include <cerrno> 20f857971dSopenharmony_ci#include <string> 21f857971dSopenharmony_ci 22f857971dSopenharmony_ci#include <linux/netlink.h> 23f857971dSopenharmony_ci#include <sys/epoll.h> 24f857971dSopenharmony_ci#include <sys/timerfd.h> 25f857971dSopenharmony_ci#include <unistd.h> 26f857971dSopenharmony_ci 27f857971dSopenharmony_ci#include "devicestatus_common.h" 28f857971dSopenharmony_ci#include "devicestatus_define.h" 29f857971dSopenharmony_ci 30f857971dSopenharmony_ci#undef LOG_TAG 31f857971dSopenharmony_ci#define LOG_TAG "AlgoMgr" 32f857971dSopenharmony_ci 33f857971dSopenharmony_cinamespace OHOS { 34f857971dSopenharmony_cinamespace Msdp { 35f857971dSopenharmony_cinamespace DeviceStatus { 36f857971dSopenharmony_ci 37f857971dSopenharmony_cibool AlgoMgr::StartSensor(Type type) 38f857971dSopenharmony_ci{ 39f857971dSopenharmony_ci CALL_DEBUG_ENTER; 40f857971dSopenharmony_ci int32_t sensorType = GetSensorTypeId(type); 41f857971dSopenharmony_ci if (sensorType == RET_ERR) { 42f857971dSopenharmony_ci FI_HILOGE("Failed to get sensorType"); 43f857971dSopenharmony_ci return false; 44f857971dSopenharmony_ci } 45f857971dSopenharmony_ci if (!CheckSensorTypeId(sensorType)) { 46f857971dSopenharmony_ci FI_HILOGE("Sensor type mismatch"); 47f857971dSopenharmony_ci return false; 48f857971dSopenharmony_ci } 49f857971dSopenharmony_ci 50f857971dSopenharmony_ci SENSOR_DATA_CB.Init(); 51f857971dSopenharmony_ci if (!SENSOR_DATA_CB.RegisterCallbackSensor(sensorType)) { 52f857971dSopenharmony_ci FI_HILOGE("Failed to register callback sensor"); 53f857971dSopenharmony_ci return false; 54f857971dSopenharmony_ci } 55f857971dSopenharmony_ci 56f857971dSopenharmony_ci return true; 57f857971dSopenharmony_ci} 58f857971dSopenharmony_ci 59f857971dSopenharmony_ciErrCode AlgoMgr::RegisterCallback(std::shared_ptr<MsdpAlgoCallback> callback) 60f857971dSopenharmony_ci{ 61f857971dSopenharmony_ci CALL_DEBUG_ENTER; 62f857971dSopenharmony_ci std::lock_guard lock(mutex_); 63f857971dSopenharmony_ci switch (algoType_) { 64f857971dSopenharmony_ci case Type::TYPE_ABSOLUTE_STILL: { 65f857971dSopenharmony_ci if (still_ != nullptr) { 66f857971dSopenharmony_ci still_->RegisterCallback(callback); 67f857971dSopenharmony_ci } 68f857971dSopenharmony_ci break; 69f857971dSopenharmony_ci } 70f857971dSopenharmony_ci case Type::TYPE_HORIZONTAL_POSITION: { 71f857971dSopenharmony_ci if (horizontalPosition_ != nullptr) { 72f857971dSopenharmony_ci horizontalPosition_->RegisterCallback(callback); 73f857971dSopenharmony_ci } 74f857971dSopenharmony_ci break; 75f857971dSopenharmony_ci } 76f857971dSopenharmony_ci case Type::TYPE_VERTICAL_POSITION: { 77f857971dSopenharmony_ci if (verticalPosition_ != nullptr) { 78f857971dSopenharmony_ci verticalPosition_->RegisterCallback(callback); 79f857971dSopenharmony_ci } 80f857971dSopenharmony_ci break; 81f857971dSopenharmony_ci } 82f857971dSopenharmony_ci default: { 83f857971dSopenharmony_ci FI_HILOGE("Unsupported algorithm type"); 84f857971dSopenharmony_ci return RET_ERR; 85f857971dSopenharmony_ci } 86f857971dSopenharmony_ci } 87f857971dSopenharmony_ci return RET_OK; 88f857971dSopenharmony_ci} 89f857971dSopenharmony_ci 90f857971dSopenharmony_ciErrCode AlgoMgr::UnregisterCallback() 91f857971dSopenharmony_ci{ 92f857971dSopenharmony_ci CALL_DEBUG_ENTER; 93f857971dSopenharmony_ci return RET_OK; 94f857971dSopenharmony_ci} 95f857971dSopenharmony_ci 96f857971dSopenharmony_cibool AlgoMgr::CheckSensorTypeId(int32_t sensorTypeId) 97f857971dSopenharmony_ci{ 98f857971dSopenharmony_ci int32_t count = -1; 99f857971dSopenharmony_ci SensorInfo *sensorInfo = nullptr; 100f857971dSopenharmony_ci int32_t ret = GetAllSensors(&sensorInfo, &count); 101f857971dSopenharmony_ci if (ret != 0) { 102f857971dSopenharmony_ci FI_HILOGE("Get all sensors failed"); 103f857971dSopenharmony_ci return false; 104f857971dSopenharmony_ci } 105f857971dSopenharmony_ci SensorInfo *pt = sensorInfo + count; 106f857971dSopenharmony_ci for (SensorInfo *ps = sensorInfo; ps < pt; ++ps) { 107f857971dSopenharmony_ci if (ps->sensorTypeId == sensorTypeId) { 108f857971dSopenharmony_ci FI_HILOGI("Get sensor sensorTypeId: %{public}d", sensorTypeId); 109f857971dSopenharmony_ci return true; 110f857971dSopenharmony_ci } 111f857971dSopenharmony_ci } 112f857971dSopenharmony_ci FI_HILOGE("Get sensor failed"); 113f857971dSopenharmony_ci return false; 114f857971dSopenharmony_ci} 115f857971dSopenharmony_ci 116f857971dSopenharmony_ciint32_t AlgoMgr::GetSensorTypeId(Type type) 117f857971dSopenharmony_ci{ 118f857971dSopenharmony_ci FI_HILOGI("Get sensor type: %{public}d", type); 119f857971dSopenharmony_ci switch (type) { 120f857971dSopenharmony_ci case Type::TYPE_ABSOLUTE_STILL: { 121f857971dSopenharmony_ci return SensorTypeId::SENSOR_TYPE_ID_ACCELEROMETER; 122f857971dSopenharmony_ci } 123f857971dSopenharmony_ci case Type::TYPE_HORIZONTAL_POSITION: { 124f857971dSopenharmony_ci return SensorTypeId::SENSOR_TYPE_ID_ACCELEROMETER; 125f857971dSopenharmony_ci } 126f857971dSopenharmony_ci case Type::TYPE_VERTICAL_POSITION: { 127f857971dSopenharmony_ci return SensorTypeId::SENSOR_TYPE_ID_ACCELEROMETER; 128f857971dSopenharmony_ci } 129f857971dSopenharmony_ci default: { 130f857971dSopenharmony_ci FI_HILOGW("GetSensorTypeId failed"); 131f857971dSopenharmony_ci break; 132f857971dSopenharmony_ci } 133f857971dSopenharmony_ci } 134f857971dSopenharmony_ci return RET_ERR; 135f857971dSopenharmony_ci} 136f857971dSopenharmony_ci 137f857971dSopenharmony_ciErrCode AlgoMgr::Enable(Type type) 138f857971dSopenharmony_ci{ 139f857971dSopenharmony_ci CALL_DEBUG_ENTER; 140f857971dSopenharmony_ci if (!StartSensor(type)) { 141f857971dSopenharmony_ci FI_HILOGE("sensor init failed"); 142f857971dSopenharmony_ci return RET_ERR; 143f857971dSopenharmony_ci } 144f857971dSopenharmony_ci std::lock_guard lock(mutex_); 145f857971dSopenharmony_ci switch (type) { 146f857971dSopenharmony_ci case Type::TYPE_ABSOLUTE_STILL: { 147f857971dSopenharmony_ci if (still_ == nullptr) { 148f857971dSopenharmony_ci FI_HILOGE("still_ is nullptr"); 149f857971dSopenharmony_ci still_ = std::make_shared<AlgoAbsoluteStill>(); 150f857971dSopenharmony_ci still_->Init(type); 151f857971dSopenharmony_ci callAlgoNums_[type] = 0; 152f857971dSopenharmony_ci } 153f857971dSopenharmony_ci callAlgoNums_[type]++; 154f857971dSopenharmony_ci break; 155f857971dSopenharmony_ci } 156f857971dSopenharmony_ci case Type::TYPE_HORIZONTAL_POSITION: { 157f857971dSopenharmony_ci if (horizontalPosition_ == nullptr) { 158f857971dSopenharmony_ci FI_HILOGE("horizontalPosition_ is nullptr"); 159f857971dSopenharmony_ci horizontalPosition_ = std::make_shared<AlgoHorizontal>(); 160f857971dSopenharmony_ci horizontalPosition_->Init(type); 161f857971dSopenharmony_ci callAlgoNums_[type] = 0; 162f857971dSopenharmony_ci } 163f857971dSopenharmony_ci callAlgoNums_[type]++; 164f857971dSopenharmony_ci break; 165f857971dSopenharmony_ci } 166f857971dSopenharmony_ci case Type::TYPE_VERTICAL_POSITION: { 167f857971dSopenharmony_ci if (verticalPosition_ == nullptr) { 168f857971dSopenharmony_ci FI_HILOGE("verticalPosition_ is nullptr"); 169f857971dSopenharmony_ci verticalPosition_ = std::make_shared<AlgoVertical>(); 170f857971dSopenharmony_ci verticalPosition_->Init(type); 171f857971dSopenharmony_ci callAlgoNums_[type] = 0; 172f857971dSopenharmony_ci } 173f857971dSopenharmony_ci callAlgoNums_[type]++; 174f857971dSopenharmony_ci break; 175f857971dSopenharmony_ci } 176f857971dSopenharmony_ci default: { 177f857971dSopenharmony_ci FI_HILOGE("Unsupported algorithm type"); 178f857971dSopenharmony_ci return RET_ERR; 179f857971dSopenharmony_ci } 180f857971dSopenharmony_ci } 181f857971dSopenharmony_ci algoType_ = type; 182f857971dSopenharmony_ci return RET_OK; 183f857971dSopenharmony_ci} 184f857971dSopenharmony_ci 185f857971dSopenharmony_ciErrCode AlgoMgr::Disable(Type type) 186f857971dSopenharmony_ci{ 187f857971dSopenharmony_ci CALL_DEBUG_ENTER; 188f857971dSopenharmony_ci std::lock_guard lock(mutex_); 189f857971dSopenharmony_ci callAlgoNums_[type]--; 190f857971dSopenharmony_ci FI_HILOGI("callAlgoNums_:%{public}d", callAlgoNums_[type]); 191f857971dSopenharmony_ci if (callAlgoNums_[type] != 0) { 192f857971dSopenharmony_ci FI_HILOGE("callAlgoNums_[type] is not zero"); 193f857971dSopenharmony_ci return RET_ERR; 194f857971dSopenharmony_ci } 195f857971dSopenharmony_ci switch (type) { 196f857971dSopenharmony_ci case Type::TYPE_ABSOLUTE_STILL: { 197f857971dSopenharmony_ci if (still_ != nullptr) { 198f857971dSopenharmony_ci FI_HILOGD("still_ is not nullptr"); 199f857971dSopenharmony_ci still_->Unsubscribe(type); 200f857971dSopenharmony_ci still_ = nullptr; 201f857971dSopenharmony_ci } 202f857971dSopenharmony_ci break; 203f857971dSopenharmony_ci } 204f857971dSopenharmony_ci case Type::TYPE_HORIZONTAL_POSITION: { 205f857971dSopenharmony_ci if (horizontalPosition_ != nullptr) { 206f857971dSopenharmony_ci FI_HILOGD("horizontalPosition_ is not nullptr"); 207f857971dSopenharmony_ci horizontalPosition_->Unsubscribe(type); 208f857971dSopenharmony_ci horizontalPosition_ = nullptr; 209f857971dSopenharmony_ci } 210f857971dSopenharmony_ci break; 211f857971dSopenharmony_ci } 212f857971dSopenharmony_ci case Type::TYPE_VERTICAL_POSITION: { 213f857971dSopenharmony_ci if (verticalPosition_ != nullptr) { 214f857971dSopenharmony_ci FI_HILOGD("verticalPosition_ is not nullptr"); 215f857971dSopenharmony_ci verticalPosition_->Unsubscribe(type); 216f857971dSopenharmony_ci verticalPosition_ = nullptr; 217f857971dSopenharmony_ci } 218f857971dSopenharmony_ci break; 219f857971dSopenharmony_ci } 220f857971dSopenharmony_ci default: { 221f857971dSopenharmony_ci FI_HILOGE("Unsupported algorithm type"); 222f857971dSopenharmony_ci break; 223f857971dSopenharmony_ci } 224f857971dSopenharmony_ci } 225f857971dSopenharmony_ci callAlgoNums_.erase(type); 226f857971dSopenharmony_ci UnregisterSensor(type); 227f857971dSopenharmony_ci return RET_OK; 228f857971dSopenharmony_ci} 229f857971dSopenharmony_ci 230f857971dSopenharmony_ciErrCode AlgoMgr::DisableCount(Type type) 231f857971dSopenharmony_ci{ 232f857971dSopenharmony_ci CALL_DEBUG_ENTER; 233f857971dSopenharmony_ci return RET_OK; 234f857971dSopenharmony_ci} 235f857971dSopenharmony_ci 236f857971dSopenharmony_ciErrCode AlgoMgr::UnregisterSensor(Type type) 237f857971dSopenharmony_ci{ 238f857971dSopenharmony_ci CALL_DEBUG_ENTER; 239f857971dSopenharmony_ci int32_t sensorType = GetSensorTypeId(type); 240f857971dSopenharmony_ci if (sensorType == RET_ERR) { 241f857971dSopenharmony_ci FI_HILOGE("Failed to get sensorType"); 242f857971dSopenharmony_ci return false; 243f857971dSopenharmony_ci } 244f857971dSopenharmony_ci if (!SENSOR_DATA_CB.UnregisterCallbackSensor(sensorType)) { 245f857971dSopenharmony_ci FI_HILOGE("Failed to unregister callback sensor"); 246f857971dSopenharmony_ci return false; 247f857971dSopenharmony_ci } 248f857971dSopenharmony_ci return true; 249f857971dSopenharmony_ci} 250f857971dSopenharmony_ci 251f857971dSopenharmony_ciextern "C" IMsdp *Create(void) 252f857971dSopenharmony_ci{ 253f857971dSopenharmony_ci CALL_DEBUG_ENTER; 254f857971dSopenharmony_ci return new (std::nothrow) AlgoMgr(); 255f857971dSopenharmony_ci} 256f857971dSopenharmony_ci 257f857971dSopenharmony_ciextern "C" void Destroy(const IMsdp* algorithm) 258f857971dSopenharmony_ci{ 259f857971dSopenharmony_ci CALL_DEBUG_ENTER; 260f857971dSopenharmony_ci if (algorithm != nullptr) { 261f857971dSopenharmony_ci FI_HILOGD("algorithm is not nullptr"); 262f857971dSopenharmony_ci delete algorithm; 263f857971dSopenharmony_ci } 264f857971dSopenharmony_ci} 265f857971dSopenharmony_ci} // namespace DeviceStatus 266f857971dSopenharmony_ci} // namespace Msdp 267f857971dSopenharmony_ci} // namespace OHOS 268f857971dSopenharmony_ci#endif // DEVICE_STATUS_SENSOR_ENABLE 269