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 #include "intell_voice_trigger_manager_impl.h"
16
17 #include <dlfcn.h>
18
19 #include "hdf_base.h"
20 #include "intell_voice_log.h"
21 #include "intell_voice_trigger_adapter_impl.h"
22
23 #undef HDF_LOG_TAG
24 #define HDF_LOG_TAG "TriggerManagerImpl"
25
26 using namespace OHOS::HDI::IntelligentVoice::Trigger::V1_0;
27
28 namespace OHOS {
29 namespace IntelligentVoice {
30 namespace Trigger {
IntellVoiceTriggerManagerImplGetInstance(void)31 extern "C" IIntellVoiceTriggerManager *IntellVoiceTriggerManagerImplGetInstance(void)
32 {
33 return new (std::nothrow) IntellVoiceTriggerManagerImpl();
34 }
35
LoadVendorLib()36 int32_t IntellVoiceTriggerManagerImpl::LoadVendorLib()
37 {
38 std::string error;
39 const char *vendorLibPath = HDF_LIBRARY_FULL_PATH("libvendor_intell_voice_trigger");
40 triggerManagerPriv_.handle = dlopen(vendorLibPath, RTLD_LAZY);
41 if (triggerManagerPriv_.handle == nullptr) {
42 error = dlerror();
43 INTELLIGENT_VOICE_LOGE("load path%{public}s, dlopen err=%{public}s", vendorLibPath, error.c_str());
44 return HDF_FAILURE;
45 }
46
47 (void)dlerror(); // clear existing error
48
49 triggerManagerPriv_.getTriggerManagerHalInst = reinterpret_cast<GetTriggerManagerHalInstFunc>(dlsym(
50 triggerManagerPriv_.handle, "GetIntellVoiceTriggerHalInst"));
51 if (triggerManagerPriv_.getTriggerManagerHalInst == nullptr) {
52 error = dlerror();
53 INTELLIGENT_VOICE_LOGE("dlsym GetIntellVoiceEngineManagerHalInst err=%{public}s", error.c_str());
54 dlclose(triggerManagerPriv_.handle);
55 triggerManagerPriv_.handle = nullptr;
56 return HDF_FAILURE;
57 }
58
59 INTELLIGENT_VOICE_LOGI("load vendor lib success");
60 return HDF_SUCCESS;
61 }
62
UnloadVendorLib()63 void IntellVoiceTriggerManagerImpl::UnloadVendorLib()
64 {
65 if (triggerManagerPriv_.handle != nullptr) {
66 dlclose(triggerManagerPriv_.handle);
67 triggerManagerPriv_.handle = nullptr;
68 }
69 }
70
IntellVoiceTriggerManagerImpl()71 IntellVoiceTriggerManagerImpl::IntellVoiceTriggerManagerImpl()
72 {
73 if (LoadVendorLib() == static_cast<int32_t>(HDF_SUCCESS)) {
74 inst_ = triggerManagerPriv_.getTriggerManagerHalInst();
75 if (inst_ == nullptr) {
76 INTELLIGENT_VOICE_LOGE("failed to get trigger manager hal inst");
77 }
78 }
79 }
80
~IntellVoiceTriggerManagerImpl()81 IntellVoiceTriggerManagerImpl::~IntellVoiceTriggerManagerImpl()
82 {
83 UnloadVendorLib();
84 inst_ = nullptr;
85 halAdapters_.clear();
86 }
87
LoadAdapter(const IntellVoiceTriggerAdapterDsecriptor & descriptor,sptr<IIntellVoiceTriggerAdapter> & adapter)88 int32_t IntellVoiceTriggerManagerImpl::LoadAdapter(const IntellVoiceTriggerAdapterDsecriptor &descriptor,
89 sptr<IIntellVoiceTriggerAdapter> &adapter)
90 {
91 std::lock_guard<std::mutex> lock(mutex_);
92
93 if (inst_ == nullptr) {
94 INTELLIGENT_VOICE_LOGE("inst is nullptr");
95 return HDF_FAILURE;
96 }
97
98 auto it = halAdapters_.find(descriptor.adapterName);
99 if (it != halAdapters_.end()) {
100 INTELLIGENT_VOICE_LOGW("adapter %{public}s already exist", descriptor.adapterName.c_str());
101 inst_->UnloadAdapter(descriptor);
102 it->second = nullptr;
103 halAdapters_.erase(it);
104 }
105
106 std::unique_ptr<ITrigger> triggerAdapterDevice = nullptr;
107 int32_t ret = inst_->LoadAdapter(descriptor, triggerAdapterDevice);
108 if (triggerAdapterDevice == nullptr) {
109 INTELLIGENT_VOICE_LOGE("get adapter device from hal failed, ret:%{public}d", ret);
110 return HDF_FAILURE;
111 }
112
113 adapter = sptr<IIntellVoiceTriggerAdapter>(new (std::nothrow) IntellVoiceTriggerAdapterImpl(
114 std::move(triggerAdapterDevice)));
115 if (adapter == nullptr) {
116 INTELLIGENT_VOICE_LOGE("new adapter failed");
117 return HDF_ERR_MALLOC_FAIL;
118 }
119
120 halAdapters_[descriptor.adapterName] = adapter;
121 return HDF_SUCCESS;
122 }
123
UnloadAdapter(const IntellVoiceTriggerAdapterDsecriptor & descriptor)124 int32_t IntellVoiceTriggerManagerImpl::UnloadAdapter(const IntellVoiceTriggerAdapterDsecriptor &descriptor)
125 {
126 std::lock_guard<std::mutex> lock(mutex_);
127 if (inst_ == nullptr) {
128 INTELLIGENT_VOICE_LOGE("inst is nullptr");
129 return HDF_FAILURE;
130 }
131
132 auto adapter = halAdapters_.find(descriptor.adapterName);
133 if (adapter == halAdapters_.end()) {
134 INTELLIGENT_VOICE_LOGE("there is no %{public}s adapter", descriptor.adapterName.c_str());
135 return HDF_ERR_INVALID_OBJECT;
136 }
137
138 int32_t ret = inst_->UnloadAdapter(descriptor);
139 adapter->second = nullptr;
140 halAdapters_.erase(adapter);
141 return ret;
142 }
143 }
144 }
145 }