1 /*
2 * Copyright (c) 2021-2022 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 "ui_mgr_service.h"
17
18 #include <atomic>
19
20 #include "if_system_ability_manager.h"
21 #include "ipc_skeleton.h"
22 #include "string_ex.h"
23 #include "system_ability_definition.h"
24 #include "ui_service_mgr_errors.h"
25
26 #include "ui_service_hilog.h"
27 namespace OHOS {
28 namespace Ace {
29 namespace {
30 constexpr int32_t UI_MGR_SERVICE_SA_ID = 7001;
31 const bool REGISTER_RESULT = SystemAbility::MakeAndRegisterAbility(DelayedSingleton<UIMgrService>::GetInstance().get());
32 } // namespace
33
34 // UiservicePluginDialog UIMgrService::dialogPlugin_;
35
UIMgrService()36 UIMgrService::UIMgrService()
37 : SystemAbility(UI_MGR_SERVICE_SA_ID, true), eventLoop_(nullptr), handler_(nullptr),
38 state_(UIServiceRunningState::STATE_NOT_START)
39 {}
40
~UIMgrService()41 UIMgrService::~UIMgrService()
42 {
43 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
44 callbackMap_.clear();
45 }
46
Dump(int32_t fd,const std::vector<std::u16string> & args)47 int32_t UIMgrService::Dump(int32_t fd, const std::vector<std::u16string>& args)
48 {
49 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
50 dprintf(fd, "total callbacks: %u\n", callbackMap_.size());
51 if (!callbackMap_.empty()) {
52 dprintf(fd, "callback keys: \n");
53 }
54 for (const auto& callback : callbackMap_) {
55 dprintf(fd, " %s\n", callback.first.c_str());
56 }
57 return UI_SERVICE_NO_ERROR;
58 }
59
OnStart()60 void UIMgrService::OnStart()
61 {
62 if (state_ == UIServiceRunningState::STATE_RUNNING) {
63 return;
64 }
65 if (!Init()) {
66 return;
67 }
68 state_ = UIServiceRunningState::STATE_RUNNING;
69 eventLoop_->Run();
70
71 /* Publish service maybe failed, so we need call this function at the last,
72 * so it can't affect the TDD test program */
73 bool ret = Publish(DelayedSingleton<UIMgrService>::GetInstance().get());
74 if (!ret) {
75 return;
76 }
77 HILOG_INFO("Ace UImanager service OnStart");
78 }
79
Init()80 bool UIMgrService::Init()
81 {
82 eventLoop_ = AppExecFwk::EventRunner::Create("UIMgrService");
83 if (eventLoop_ == nullptr) {
84 return false;
85 }
86
87 handler_ = std::make_shared<AppExecFwk::EventHandler>(eventLoop_);
88 if (handler_ == nullptr) {
89 return false;
90 }
91 HILOG_INFO("Ace UIservice init success");
92 return true;
93 }
94
OnStop()95 void UIMgrService::OnStop()
96 {
97 eventLoop_->Stop();
98 eventLoop_.reset();
99 handler_.reset();
100 state_ = UIServiceRunningState::STATE_NOT_START;
101 HILOG_INFO("Ace UImanager service stop");
102 }
103
QueryServiceState() const104 UIServiceRunningState UIMgrService::QueryServiceState() const
105 {
106 return state_;
107 }
108
RegisterCallBack(const AAFwk::Want & want,const sptr<IUIService> & uiService)109 int32_t UIMgrService::RegisterCallBack(const AAFwk::Want& want, const sptr<IUIService>& uiService)
110 {
111 if (uiService == nullptr) {
112 return UI_SERVICE_IS_NULL;
113 }
114 if (handler_ == nullptr) {
115 return UI_SERVICE_HANDLER_IS_NULL;
116 }
117 std::function<void()> registerFunc = std::bind(&UIMgrService::HandleRegister, shared_from_this(), want, uiService);
118 bool ret = handler_->PostTask(registerFunc);
119 if (!ret) {
120 return UI_SERVICE_POST_TASK_FAILED;
121 }
122 HILOG_INFO("UIServices register CallBack success");
123 return NO_ERROR;
124 }
125
UnregisterCallBack(const AAFwk::Want & want)126 int32_t UIMgrService::UnregisterCallBack(const AAFwk::Want& want)
127 {
128 if (handler_ == nullptr) {
129 return UI_SERVICE_HANDLER_IS_NULL;
130 }
131 std::function<void()> unregisterFunc = std::bind(&UIMgrService::HandleUnregister, shared_from_this(), want);
132 bool ret = handler_->PostTask(unregisterFunc);
133 if (!ret) {
134 return UI_SERVICE_POST_TASK_FAILED;
135 }
136 HILOG_INFO("UIServices unregister CallBack success");
137 return NO_ERROR;
138 }
139
Push(const AAFwk::Want & want,const std::string & name,const std::string & jsonPath,const std::string & data,const std::string & extraData)140 int32_t UIMgrService::Push(const AAFwk::Want& want, const std::string& name, const std::string& jsonPath,
141 const std::string& data, const std::string& extraData)
142 {
143 std::map<std::string, sptr<IUIService>> callbackMap;
144 {
145 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
146 callbackMap = std::map<std::string, sptr<IUIService>>(callbackMap_);
147 }
148 for (auto iter = callbackMap.begin(); iter != callbackMap.end(); ++iter) {
149 sptr<IUIService> uiService = iter->second;
150 if (uiService == nullptr) {
151 return UI_SERVICE_IS_NULL;
152 }
153 uiService->OnPushCallBack(want, name, jsonPath, data, extraData);
154 }
155 return NO_ERROR;
156 }
157
Request(const AAFwk::Want & want,const std::string & name,const std::string & data)158 int32_t UIMgrService::Request(const AAFwk::Want& want, const std::string& name, const std::string& data)
159 {
160 std::map<std::string, sptr<IUIService>> callbackMap;
161 {
162 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
163 callbackMap = std::map<std::string, sptr<IUIService>>(callbackMap_);
164 }
165 for (auto iter = callbackMap.begin(); iter != callbackMap.end(); ++iter) {
166 sptr<IUIService> uiService = iter->second;
167 if (uiService == nullptr) {
168 return UI_SERVICE_IS_NULL;
169 }
170 uiService->OnRequestCallBack(want, name, data);
171 }
172 return NO_ERROR;
173 }
174
ReturnRequest(const AAFwk::Want & want,const std::string & source,const std::string & data,const std::string & extraData)175 int32_t UIMgrService::ReturnRequest(
176 const AAFwk::Want& want, const std::string& source, const std::string& data, const std::string& extraData)
177 {
178 std::map<std::string, sptr<IUIService>> callbackMap;
179 {
180 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
181 callbackMap = std::map<std::string, sptr<IUIService>>(callbackMap_);
182 }
183 for (auto iter = callbackMap.begin(); iter != callbackMap.end(); ++iter) {
184 sptr<IUIService> uiService = iter->second;
185 if (uiService == nullptr) {
186 return UI_SERVICE_IS_NULL;
187 }
188 uiService->OnReturnRequest(want, source, data, extraData);
189 }
190 return NO_ERROR;
191 }
192
HandleRegister(const AAFwk::Want & want,const sptr<IUIService> & uiService)193 int32_t UIMgrService::HandleRegister(const AAFwk::Want& want, const sptr<IUIService>& uiService)
194 {
195 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
196 std::string keyStr = GetCallBackKeyStr(want);
197 bool exist = CheckCallBackFromMap(keyStr);
198 if (exist) {
199 callbackMap_.erase(keyStr);
200 }
201 callbackMap_.emplace(keyStr, uiService);
202 return NO_ERROR;
203 }
204
HandleUnregister(const AAFwk::Want & want)205 int32_t UIMgrService::HandleUnregister(const AAFwk::Want& want)
206 {
207 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
208 std::string keyStr = GetCallBackKeyStr(want);
209 bool exist = CheckCallBackFromMap(keyStr);
210 if (!exist) {
211 return NO_CALLBACK_FOR_KEY;
212 }
213 callbackMap_.erase(keyStr);
214 return NO_ERROR;
215 }
216
GetCallBackKeyStr(const AAFwk::Want & want)217 std::string UIMgrService::GetCallBackKeyStr(const AAFwk::Want& want)
218 {
219 AppExecFwk::ElementName element = want.GetElement();
220 std::string bundleName = element.GetBundleName();
221 std::string keyStr = bundleName;
222 return keyStr;
223 }
224
CheckCallBackFromMap(const std::string & key)225 bool UIMgrService::CheckCallBackFromMap(const std::string& key)
226 {
227 std::lock_guard<std::recursive_mutex> lock(uiMutex_);
228 auto it = callbackMap_.find(key);
229 if (it == callbackMap_.end()) {
230 return false;
231 }
232 return true;
233 }
234 } // namespace Ace
235 } // namespace OHOS
236