1/*
2 * Copyright (C) 2021 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 "im_common_event_manager.h"
17
18#include <utility>
19
20#include "full_ime_info_manager.h"
21#include "global.h"
22#include "ime_info_inquirer.h"
23#include "ipc_skeleton.h"
24#include "iservice_registry.h"
25#include "itypes_util.h"
26#include "message_handler.h"
27#include "os_account_adapter.h"
28#include "system_ability_definition.h"
29
30namespace OHOS {
31namespace MiscServices {
32using namespace MessageID;
33sptr<ImCommonEventManager> ImCommonEventManager::instance_;
34std::mutex ImCommonEventManager::instanceLock_;
35using namespace OHOS::EventFwk;
36constexpr const char *COMMON_EVENT_INPUT_PANEL_STATUS_CHANGED = "usual.event.imf.input_panel_status_changed";
37constexpr const char *COMMON_EVENT_PARAM_USER_ID = "userId";
38constexpr const char *COMMON_EVENT_PARAM_PANEL_STATE = "panelState";
39constexpr const char *COMMON_EVENT_PARAM_PANEL_RECT = "panelRect";
40ImCommonEventManager::ImCommonEventManager()
41{
42}
43
44ImCommonEventManager::~ImCommonEventManager()
45{
46}
47
48sptr<ImCommonEventManager> ImCommonEventManager::GetInstance()
49{
50    if (instance_ == nullptr) {
51        std::lock_guard<std::mutex> autoLock(instanceLock_);
52        if (instance_ == nullptr) {
53            IMSA_HILOGI("instance_ is nullptr.");
54            instance_ = new ImCommonEventManager();
55        }
56    }
57    return instance_;
58}
59
60bool ImCommonEventManager::SubscribeEvent()
61{
62    EventFwk::MatchingSkills matchingSkills;
63    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_USER_SWITCHED);
64    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_USER_REMOVED);
65    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_PACKAGE_ADDED);
66    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_PACKAGE_CHANGED);
67    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_PACKAGE_REMOVED);
68    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_BUNDLE_SCAN_FINISHED);
69    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_USER_STOPPED);
70    matchingSkills.AddEvent(CommonEventSupport::COMMON_EVENT_BOOT_COMPLETED);
71
72    EventFwk::CommonEventSubscribeInfo subscriberInfo(matchingSkills);
73
74    std::shared_ptr<EventSubscriber> subscriber = std::make_shared<EventSubscriber>(subscriberInfo);
75    auto abilityManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
76    if (abilityManager == nullptr) {
77        IMSA_HILOGE("SubscribeEvent abilityManager is nullptr!");
78        return false;
79    }
80    sptr<ISystemAbilityStatusChange> listener = new (std::nothrow) SystemAbilityStatusChangeListener([subscriber]() {
81        bool subscribeResult = EventFwk::CommonEventManager::SubscribeCommonEvent(subscriber);
82        IMSA_HILOGI("SubscribeCommonEvent ret: %{public}d", subscribeResult);
83    });
84    if (listener == nullptr) {
85        IMSA_HILOGE("SubscribeEvent listener is nullptr!");
86        return false;
87    }
88    int32_t ret = abilityManager->SubscribeSystemAbility(COMMON_EVENT_SERVICE_ID, listener);
89    if (ret != ERR_OK) {
90        IMSA_HILOGE("SubscribeEvent SubscribeSystemAbility failed. ret: %{public}d", ret);
91        return false;
92    }
93    return true;
94}
95
96bool ImCommonEventManager::SubscribeKeyboardEvent(KeyHandle handle)
97{
98    IMSA_HILOGI("ImCommonEventManager::SubscribeKeyboardEvent start.");
99    auto abilityManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
100    if (abilityManager == nullptr) {
101        IMSA_HILOGE("SubscribeKeyboardEvent abilityManager is nullptr!");
102        return false;
103    }
104    sptr<ISystemAbilityStatusChange> listener = new (std::nothrow) SystemAbilityStatusChangeListener([handle]() {
105        int32_t ret = KeyboardEvent::GetInstance().AddKeyEventMonitor(handle);
106        IMSA_HILOGI("SubscribeKeyboardEvent add monitor: %{public}s.",
107            ret == ErrorCode::NO_ERROR ? "success" : "failed");
108    });
109    if (listener == nullptr) {
110        IMSA_HILOGE("listener is nullptr!");
111        return false;
112    }
113    int32_t ret = abilityManager->SubscribeSystemAbility(MULTIMODAL_INPUT_SERVICE_ID, listener);
114    if (ret != ERR_OK) {
115        IMSA_HILOGE("failed to SubscribeSystemAbility, ret: %{public}d!", ret);
116        return false;
117    }
118    return true;
119}
120
121bool ImCommonEventManager::SubscribeWindowManagerService(const Handler &handler)
122{
123    IMSA_HILOGI("start.");
124    auto abilityManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
125    if (abilityManager == nullptr) {
126        IMSA_HILOGE("abilityManager is nullptr!");
127        return false;
128    }
129    sptr<ISystemAbilityStatusChange> listener = new (std::nothrow) SystemAbilityStatusChangeListener([handler]() {
130        if (handler != nullptr) {
131            handler();
132        }
133    });
134    if (listener == nullptr) {
135        IMSA_HILOGE("failed to create listener!");
136        return false;
137    }
138    int32_t ret = abilityManager->SubscribeSystemAbility(WINDOW_MANAGER_SERVICE_ID, listener);
139    if (ret != ERR_OK) {
140        IMSA_HILOGE("subscribe system ability failed, ret: %{public}d", ret);
141        return false;
142    }
143    return true;
144}
145
146bool ImCommonEventManager::SubscribeMemMgrService(const Handler &handler)
147{
148    auto abilityManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
149    if (abilityManager == nullptr) {
150        IMSA_HILOGE("abilityManager is nullptr!");
151        return false;
152    }
153    sptr<ISystemAbilityStatusChange> listener = new (std::nothrow) SystemAbilityStatusChangeListener([handler]() {
154        if (handler != nullptr) {
155            handler();
156        }
157    });
158    if (listener == nullptr) {
159        IMSA_HILOGE("failed to create listener!");
160        return false;
161    }
162    int32_t ret = abilityManager->SubscribeSystemAbility(MEMORY_MANAGER_SA_ID, listener);
163    if (ret != ERR_OK) {
164        IMSA_HILOGE("subscribe system ability failed, ret: %{public}d", ret);
165        return false;
166    }
167    return true;
168}
169
170bool ImCommonEventManager::SubscribeAccountManagerService(Handler handler)
171{
172    auto abilityManager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
173    if (abilityManager == nullptr) {
174        IMSA_HILOGE("abilityManager is nullptr!");
175        return false;
176    }
177    sptr<ISystemAbilityStatusChange> listener = new (std::nothrow) SystemAbilityStatusChangeListener([handler]() {
178        if (handler != nullptr) {
179            handler();
180        }
181    });
182    if (listener == nullptr) {
183        IMSA_HILOGE("failed to create listener!");
184        return false;
185    }
186    int32_t ret = abilityManager->SubscribeSystemAbility(SUBSYS_ACCOUNT_SYS_ABILITY_ID_BEGIN, listener);
187    if (ret != ERR_OK) {
188        IMSA_HILOGE("subscribe system ability failed, ret: %{public}d", ret);
189        return false;
190    }
191    return true;
192}
193
194bool ImCommonEventManager::UnsubscribeEvent()
195{
196    return true;
197}
198
199ImCommonEventManager::EventSubscriber::EventSubscriber(const EventFwk::CommonEventSubscribeInfo &subscribeInfo)
200    : EventFwk::CommonEventSubscriber(subscribeInfo)
201{
202    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_USER_SWITCHED] =
203        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
204            return that->StartUser(data);
205        };
206    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_USER_STOPPED] =
207        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
208            return that->StopUser(data);
209        };
210    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_USER_REMOVED] =
211        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
212            return that->RemoveUser(data);
213        };
214    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_PACKAGE_REMOVED] =
215        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
216            return that->RemovePackage(data);
217        };
218    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_BUNDLE_SCAN_FINISHED] =
219        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
220            return that->OnBundleScanFinished(data);
221        };
222    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_PACKAGE_ADDED] =
223        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
224            return that->AddPackage(data);
225        };
226    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_PACKAGE_CHANGED] =
227        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
228            return that->ChangePackage(data);
229        };
230    EventManagerFunc_[CommonEventSupport::COMMON_EVENT_BOOT_COMPLETED] =
231        [] (EventSubscriber *that, const EventFwk::CommonEventData &data) {
232            return that->HandleBootCompleted(data);
233        };
234}
235
236void ImCommonEventManager::EventSubscriber::OnReceiveEvent(const EventFwk::CommonEventData &data)
237{
238    auto const &want = data.GetWant();
239    std::string action = want.GetAction();
240    IMSA_HILOGI("ImCommonEventManager::action: %{public}s!", action.c_str());
241    auto iter = EventManagerFunc_.find(action);
242    if (iter != EventManagerFunc_.end()) {
243        EventManagerFunc_[action] (this, data);
244    }
245}
246
247void ImCommonEventManager::EventSubscriber::StopUser(const CommonEventData &data)
248{
249    HandleUserEvent(MessageID::MSG_ID_USER_STOP, data);
250}
251
252void ImCommonEventManager::EventSubscriber::StartUser(const CommonEventData &data)
253{
254    HandleUserEvent(MessageID::MSG_ID_USER_START, data);
255}
256
257void ImCommonEventManager::EventSubscriber::RemoveUser(const CommonEventData &data)
258{
259    HandleUserEvent(MessageID::MSG_ID_USER_REMOVED, data);
260}
261
262void ImCommonEventManager::EventSubscriber::HandleUserEvent(int32_t messageId, const EventFwk::CommonEventData &data)
263{
264    auto userId = data.GetCode();
265    MessageParcel *parcel = new (std::nothrow) MessageParcel();
266    if (parcel == nullptr) {
267        return;
268    }
269    IMSA_HILOGD("userId:%{public}d, messageId:%{public}d", userId, messageId);
270    parcel->WriteInt32(userId);
271    Message *msg = new (std::nothrow) Message(messageId, parcel);
272    if (msg == nullptr) {
273        delete parcel;
274        return;
275    }
276    MessageHandler::Instance()->SendMessage(msg);
277}
278
279void ImCommonEventManager::EventSubscriber::OnBundleScanFinished(const EventFwk::CommonEventData &data)
280{
281    IMSA_HILOGI("ImCommonEventManager start.");
282    auto parcel = new (std::nothrow) MessageParcel();
283    if (parcel == nullptr) {
284        IMSA_HILOGE("failed to create MessageParcel!");
285        return;
286    }
287    auto msg = new (std::nothrow) Message(MessageID::MSG_ID_BUNDLE_SCAN_FINISHED, parcel);
288    if (msg == nullptr) {
289        IMSA_HILOGE("failed to create Message!");
290        delete parcel;
291        return;
292    }
293    MessageHandler::Instance()->SendMessage(msg);
294}
295
296void ImCommonEventManager::EventSubscriber::RemovePackage(const CommonEventData &data)
297{
298    HandlePackageEvent(MessageID::MSG_ID_PACKAGE_REMOVED, data);
299}
300
301void ImCommonEventManager::EventSubscriber::AddPackage(const EventFwk::CommonEventData &data)
302{
303    HandlePackageEvent(MessageID::MSG_ID_PACKAGE_ADDED, data);
304}
305
306void ImCommonEventManager::EventSubscriber::ChangePackage(const EventFwk::CommonEventData &data)
307{
308    HandlePackageEvent(MessageID::MSG_ID_PACKAGE_CHANGED, data);
309}
310
311void ImCommonEventManager::EventSubscriber::HandlePackageEvent(int32_t messageId, const EventFwk::CommonEventData &data)
312{
313    auto const &want = data.GetWant();
314    auto element = want.GetElement();
315    std::string bundleName = element.GetBundleName();
316    int32_t userId = want.GetIntParam("userId", OsAccountAdapter::INVALID_USER_ID);
317    if (userId == OsAccountAdapter::INVALID_USER_ID) {
318        IMSA_HILOGE("invalid user id, messageId:%{public}d", messageId);
319        return;
320    }
321    IMSA_HILOGD(
322        "messageId:%{public}d, bundleName:%{public}s, userId:%{public}d", messageId, bundleName.c_str(), userId);
323    if (messageId == MessageID::MSG_ID_PACKAGE_REMOVED) {
324        if (!FullImeInfoManager::GetInstance().Has(userId, bundleName)) {
325            return;
326        }
327    } else {
328        if (!ImeInfoInquirer::GetInstance().IsInputMethod(userId, bundleName)) {
329            return;
330        }
331    }
332    MessageParcel *parcel = new (std::nothrow) MessageParcel();
333    if (parcel == nullptr) {
334        IMSA_HILOGE("parcel is nullptr!");
335        return;
336    }
337    if (!ITypesUtil::Marshal(*parcel, userId, bundleName)) {
338        IMSA_HILOGE("Failed to write message parcel!");
339        delete parcel;
340        return;
341    }
342    Message *msg = new (std::nothrow) Message(messageId, parcel);
343    if (msg == nullptr) {
344        IMSA_HILOGE("failed to create Message!");
345        delete parcel;
346        return;
347    }
348    MessageHandler::Instance()->SendMessage(msg);
349}
350
351void ImCommonEventManager::EventSubscriber::HandleBootCompleted(const EventFwk::CommonEventData &data)
352{
353    Message *msg = new (std::nothrow) Message(MessageID::MSG_ID_BOOT_COMPLETED, nullptr);
354    if (msg == nullptr) {
355        return;
356    }
357    MessageHandler::Instance()->SendMessage(msg);
358}
359
360ImCommonEventManager::SystemAbilityStatusChangeListener::SystemAbilityStatusChangeListener(std::function<void()> func)
361    : func_(std::move(func))
362{
363}
364
365void ImCommonEventManager::SystemAbilityStatusChangeListener::OnAddSystemAbility(int32_t systemAbilityId,
366    const std::string &deviceId)
367{
368    IMSA_HILOGD("systemAbilityId: %{public}d.", systemAbilityId);
369    if (systemAbilityId != COMMON_EVENT_SERVICE_ID && systemAbilityId != MULTIMODAL_INPUT_SERVICE_ID &&
370        systemAbilityId != WINDOW_MANAGER_SERVICE_ID && systemAbilityId != SUBSYS_ACCOUNT_SYS_ABILITY_ID_BEGIN &&
371        systemAbilityId != MEMORY_MANAGER_SA_ID) {
372        return;
373    }
374    if (func_ != nullptr) {
375        func_();
376    }
377}
378
379void ImCommonEventManager::SystemAbilityStatusChangeListener::OnRemoveSystemAbility(int32_t systemAbilityId,
380    const std::string &deviceId)
381{
382}
383
384int32_t ImCommonEventManager::PublishPanelStatusChangeEvent(
385    int32_t userId, const InputWindowStatus &status, const ImeWindowInfo &info)
386{
387    EventFwk::CommonEventPublishInfo publicInfo;
388    publicInfo.SetOrdered(false);
389    AAFwk::Want want;
390    want.SetAction(COMMON_EVENT_INPUT_PANEL_STATUS_CHANGED);
391    bool visible = (status == InputWindowStatus::SHOW);
392    std::vector<int32_t> panelRect = { info.windowInfo.left, info.windowInfo.top,
393        static_cast<int32_t>(info.windowInfo.width), static_cast<int32_t>(info.windowInfo.height) };
394    want.SetParam(COMMON_EVENT_PARAM_USER_ID, userId);
395    want.SetParam(COMMON_EVENT_PARAM_PANEL_STATE, visible);
396    want.SetParam(COMMON_EVENT_PARAM_PANEL_RECT, panelRect);
397    EventFwk::CommonEventData data;
398    data.SetWant(want);
399    return EventFwk::CommonEventManager::NewPublishCommonEvent(data, publicInfo);
400}
401} // namespace MiscServices
402} // namespace OHOS