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 "module_update_kits_impl.h"
17
18 #include "if_system_ability_manager.h"
19 #include "iservice_registry.h"
20 #include "log/log.h"
21 #include "module_constants.h"
22 #include "module_error_code.h"
23 #include "module_update_load_callback.h"
24 #include "module_update_proxy.h"
25 #include "service_control.h"
26 #include "system_ability_definition.h"
27 #include "sys_installer_callback.h"
28
29 namespace OHOS {
30 namespace SysInstaller {
31 using namespace Updater;
32
33 namespace {
34 constexpr int LOAD_SA_TIMEOUT_MS = 3;
35 static volatile std::atomic_long g_request(0);
36 }
37
GetInstance()38 ModuleUpdateKits &ModuleUpdateKits::GetInstance()
39 {
40 return DelayedRefSingleton<ModuleUpdateKitsImpl>::GetInstance();
41 }
42
ModuleUpdateKitsImpl()43 ModuleUpdateKitsImpl::ModuleUpdateKitsImpl() {}
44
~ModuleUpdateKitsImpl()45 ModuleUpdateKitsImpl::~ModuleUpdateKitsImpl() {}
46
ResetService(const wptr<IRemoteObject> & remote)47 void ModuleUpdateKitsImpl::ResetService(const wptr<IRemoteObject>& remote)
48 {
49 LOG(INFO) << "Remote is dead, reset service instance";
50
51 std::lock_guard<std::mutex> lock(moduleUpdateLock_);
52 if (moduleUpdate_ != nullptr) {
53 sptr<IRemoteObject> object = moduleUpdate_->AsObject();
54 if ((object != nullptr) && (remote == object)) {
55 object->RemoveDeathRecipient(deathRecipient_);
56 moduleUpdate_ = nullptr;
57 }
58 }
59 }
60
GetService()61 sptr<IModuleUpdate> ModuleUpdateKitsImpl::GetService()
62 {
63 std::lock_guard<std::mutex> lock(moduleUpdateLock_);
64 if (moduleUpdate_ != nullptr) {
65 return moduleUpdate_;
66 }
67
68 sptr<ISystemAbilityManager> samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
69 if (samgr == nullptr) {
70 LOG(ERROR) << "Get samgr object failed";
71 return nullptr;
72 }
73 sptr<IRemoteObject> object = samgr->GetSystemAbility(MODULE_UPDATE_SERVICE_ID);
74 if (object == nullptr) {
75 LOG(ERROR) << "Get module update object from samgr failed";
76 return nullptr;
77 }
78
79 if (deathRecipient_ == nullptr) {
80 deathRecipient_ = new DeathRecipient();
81 }
82
83 if ((object->IsProxyObject()) && (!object->AddDeathRecipient(deathRecipient_))) {
84 LOG(ERROR) << "Failed to add death recipient";
85 }
86
87 LOG(INFO) << "get remote object ok";
88 moduleUpdate_ = iface_cast<IModuleUpdate>(object);
89 if (moduleUpdate_ == nullptr) {
90 LOG(ERROR) << "module update object iface_cast failed";
91 return nullptr;
92 }
93 return moduleUpdate_;
94 }
95
OnRemoteDied(const wptr<IRemoteObject> & remote)96 void ModuleUpdateKitsImpl::DeathRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
97 {
98 DelayedRefSingleton<ModuleUpdateKitsImpl>::GetInstance().ResetService(remote);
99 }
100
InstallModulePackage(const std::string & pkgPath)101 int32_t ModuleUpdateKitsImpl::InstallModulePackage(const std::string &pkgPath)
102 {
103 LOG(INFO) << "InstallModulePackage " << pkgPath;
104 auto moduleUpdate = GetService();
105 if (moduleUpdate == nullptr) {
106 LOG(ERROR) << "Get moduleUpdate failed";
107 return ModuleErrorCode::ERR_SERVICE_NOT_FOUND;
108 }
109 return moduleUpdate->InstallModulePackage(pkgPath);
110 }
111
UninstallModulePackage(const std::string & hmpName)112 int32_t ModuleUpdateKitsImpl::UninstallModulePackage(const std::string &hmpName)
113 {
114 LOG(INFO) << "UninstallModulePackage " << hmpName;
115 auto moduleUpdate = GetService();
116 if (moduleUpdate == nullptr) {
117 LOG(ERROR) << "Get moduleUpdate failed";
118 return ModuleErrorCode::ERR_SERVICE_NOT_FOUND;
119 }
120 return moduleUpdate->UninstallModulePackage(hmpName);
121 }
122
GetModulePackageInfo(const std::string & hmpName,std::list<ModulePackageInfo> & modulePackageInfos)123 int32_t ModuleUpdateKitsImpl::GetModulePackageInfo(const std::string &hmpName,
124 std::list<ModulePackageInfo> &modulePackageInfos)
125 {
126 LOG(INFO) << "GetModulePackageInfo";
127 auto moduleUpdate = GetService();
128 if (moduleUpdate == nullptr) {
129 LOG(ERROR) << "Get moduleUpdate failed";
130 return ModuleErrorCode::ERR_SERVICE_NOT_FOUND;
131 }
132 return moduleUpdate->GetModulePackageInfo(hmpName, modulePackageInfos);
133 }
134
ExitModuleUpdate()135 int32_t ModuleUpdateKitsImpl::ExitModuleUpdate()
136 {
137 LOG(INFO) << "ExitModuleUpdate, g_request = " << g_request;
138 auto moduleUpdate = GetService();
139 if (moduleUpdate == nullptr) {
140 LOG(ERROR) << "Get moduleUpdate failed";
141 return ModuleErrorCode::ERR_SERVICE_NOT_FOUND;
142 }
143 if (--g_request <= 0) {
144 return moduleUpdate->ExitModuleUpdate();
145 }
146 return 0;
147 }
148
Init()149 int32_t ModuleUpdateKitsImpl::Init()
150 {
151 std::lock_guard<std::mutex> lock(moduleUpdateLock_);
152 if (moduleUpdate_ != nullptr) {
153 LOG(INFO) << "already init";
154 return 0;
155 }
156
157 LOG(INFO) << "InitModuleUpdate Init start";
158 sptr<ModuleUpdateLoadCallback> loadCallback_ = new ModuleUpdateLoadCallback();
159 sptr<ISystemAbilityManager> sm = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
160 if (sm == nullptr) {
161 LOG(ERROR) << "GetSystemAbilityManager samgr object null";
162 return -1;
163 }
164 LOG(INFO) << "InitModuleUpdate Init GetSystemAbilityManager done";
165 int32_t result = sm->LoadSystemAbility(MODULE_UPDATE_SERVICE_ID, loadCallback_);
166 if (result != ERR_OK) {
167 LOG(ERROR) << "systemAbilityId " << MODULE_UPDATE_SERVICE_ID <<
168 " load failed, result code:" << result;
169 return -1;
170 }
171
172 LOG(INFO) << "InitModuleUpdate Init Load done";
173 std::unique_lock<std::mutex> callbackLock(serviceMutex_);
174 serviceCv_.wait_for(callbackLock, std::chrono::seconds(LOAD_SA_TIMEOUT_MS));
175 return 0;
176 }
177
InitModuleUpdate()178 int32_t ModuleUpdateKitsImpl::InitModuleUpdate()
179 {
180 InitUpdaterLogger("ModuleUpdaterClient", MODULE_UPDATE_LOG_FILE, "", "");
181 LOG(INFO) << "InitModuleUpdate";
182 int ret = Init();
183 if (ret != 0) {
184 LOG(ERROR) << "Init failed";
185 return ret;
186 }
187
188 auto updateService = GetService();
189 if (updateService == nullptr) {
190 LOG(ERROR) << "Get updateService failed";
191 return -1;
192 }
193 g_request++;
194 return ModuleErrorCode::MODULE_UPDATE_SUCCESS;
195 }
196
GetHmpVersionInfo()197 std::vector<HmpVersionInfo> ModuleUpdateKitsImpl::GetHmpVersionInfo()
198 {
199 LOG(INFO) << "GetHmpVersionInfo";
200 std::vector<HmpVersionInfo> versionInfo {};
201 auto moduleUpdate = GetService();
202 if (moduleUpdate == nullptr) {
203 LOG(ERROR) << "Get moduleUpdate failed";
204 return versionInfo;
205 }
206 versionInfo = moduleUpdate->GetHmpVersionInfo();
207 return versionInfo;
208 }
209
StartUpdateHmpPackage(const std::string & path,sptr<ISysInstallerCallbackFunc> callback)210 int32_t ModuleUpdateKitsImpl::StartUpdateHmpPackage(const std::string &path,
211 sptr<ISysInstallerCallbackFunc> callback)
212 {
213 LOG(INFO) << "StartUpdateHmpPackage";
214 if (callback == nullptr) {
215 LOG(ERROR) << "callback null";
216 return ModuleErrorCode::ERR_SERVICE_PARA_ERROR;
217 }
218
219 auto moduleUpdate = GetService();
220 if (moduleUpdate == nullptr) {
221 LOG(ERROR) << "Get moduleUpdate failed";
222 return ModuleErrorCode::ERR_SERVICE_NOT_FOUND;
223 }
224
225 if (updateCallBack_ == nullptr) {
226 updateCallBack_ = new SysInstallerCallback(callback);
227 }
228
229 return moduleUpdate->StartUpdateHmpPackage(path, updateCallBack_);
230 }
231
GetHmpUpdateResult()232 std::vector<HmpUpdateInfo> ModuleUpdateKitsImpl::GetHmpUpdateResult()
233 {
234 LOG(INFO) << "GetHmpUpdateResult";
235 std::vector<HmpUpdateInfo> updateInfo {};
236 auto moduleUpdate = GetService();
237 if (moduleUpdate == nullptr) {
238 LOG(ERROR) << "Get moduleUpdate failed";
239 return updateInfo;
240 }
241 updateInfo = moduleUpdate->GetHmpUpdateResult();
242 return updateInfo;
243 }
244
LoadServiceSuccess()245 void ModuleUpdateKitsImpl::LoadServiceSuccess()
246 {
247 serviceCv_.notify_all();
248 }
249
LoadServiceFail()250 void ModuleUpdateKitsImpl::LoadServiceFail()
251 {
252 serviceCv_.notify_all();
253 }
254 }
255 } // namespace OHOS
256