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 #ifndef BASE_SERVICE_KITS_IMPL_H
17 #define BASE_SERVICE_KITS_IMPL_H
18
19 #include <mutex>
20
21 #include "iremote_object.h"
22
23 #include "common_death_recipient.h"
24 #include "load_sa_service.h"
25 #include "update_define.h"
26
27 namespace OHOS::UpdateEngine {
28 #define RETURN_FAIL_WHEN_SERVICE_NULL(service) \
29 if ((service) == nullptr) { \
30 ENGINE_LOGE("Service is null"); \
31 return INT_CALL_IPC_ERR; \
32 }
33
34 template <typename SERVICE> class BaseServiceKitsImpl {
35 public:
36 explicit BaseServiceKitsImpl(int32_t systemAbilityId, bool isNeedAddDeathRecipient = true)
37 : systemAbilityId_(systemAbilityId), isNeedAddDeathRecipient_(isNeedAddDeathRecipient) {}
38 virtual ~BaseServiceKitsImpl();
39
40 protected:
41 sptr<SERVICE> GetService();
42 void ResetRemoteService();
RegisterCallback()43 virtual void RegisterCallback(){};
44 virtual void ResetService(const wptr<IRemoteObject> &remote);
45
46 protected:
47 std::recursive_mutex remoteServerLock_;
48 sptr<SERVICE> remoteServer_ = nullptr;
49 sptr<IRemoteObject::DeathRecipient> deathRecipient_ = nullptr;
50 int32_t systemAbilityId_;
51
52 private:
53 void AddDeathRecipient(const sptr<IRemoteObject> &object);
54
55 private:
56 bool isNeedAddDeathRecipient_ = true;
57 };
58
~BaseServiceKitsImpl()59 template <typename SERVICE> BaseServiceKitsImpl<SERVICE>::~BaseServiceKitsImpl()
60 {
61 ENGINE_LOGI("BaseServiceKitsImpl desConstructor");
62 std::lock_guard<std::recursive_mutex> lock(remoteServerLock_);
63 if (isNeedAddDeathRecipient_ && remoteServer_ != nullptr && deathRecipient_ != nullptr) {
64 sptr<IRemoteObject> object = remoteServer_->AsObject();
65 if (object != nullptr) {
66 bool removeResult = object->RemoveDeathRecipient(deathRecipient_);
67 ENGINE_LOGI("RemoveDeathRecipient result is %{public}s", removeResult ? "success" : "error");
68 }
69 }
70 deathRecipient_ = nullptr;
71 remoteServer_ = nullptr;
72 }
73
GetService()74 template <typename SERVICE> sptr<SERVICE> BaseServiceKitsImpl<SERVICE>::GetService()
75 {
76 std::lock_guard<std::recursive_mutex> lock(remoteServerLock_);
77 if (remoteServer_ != nullptr) {
78 return remoteServer_;
79 }
80 ENGINE_LOGI("GetService recreate service instance");
81 sptr<ISystemAbilityManager> manager = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
82 ENGINE_CHECK(manager != nullptr, return nullptr, "manager is nullptr");
83 sptr<IRemoteObject> object = manager->CheckSystemAbility(systemAbilityId_);
84 if (object == nullptr) {
85 ENGINE_CHECK(LoadSaService::GetInstance()->TryLoadSa(systemAbilityId_), return nullptr, "TryLoadSa fail");
86 object = manager->GetSystemAbility(systemAbilityId_);
87 ENGINE_CHECK(object != nullptr, return nullptr, "Get remote object from samgr failed");
88 }
89 AddDeathRecipient(object);
90 remoteServer_ = iface_cast<SERVICE>(object);
91 ENGINE_CHECK(remoteServer_ != nullptr, return nullptr, "service iface_cast failed");
92 RegisterCallback();
93 return remoteServer_;
94 }
95
AddDeathRecipient(const sptr<IRemoteObject> & object)96 template <typename SERVICE> void BaseServiceKitsImpl<SERVICE>::AddDeathRecipient(const sptr<IRemoteObject> &object)
97 {
98 if (isNeedAddDeathRecipient_ && object != nullptr) {
99 if (deathRecipient_ == nullptr) {
100 auto resetCallback = [this](const wptr<IRemoteObject> &remote) { this->ResetService(remote); };
101 deathRecipient_ = new CommonDeathRecipient(resetCallback);
102 }
103 if ((object->IsProxyObject()) && (!object->AddDeathRecipient(deathRecipient_))) {
104 ENGINE_LOGE("Failed to add death recipient");
105 }
106 }
107 }
108
ResetRemoteService()109 template <typename SERVICE> void BaseServiceKitsImpl<SERVICE>::ResetRemoteService()
110 {
111 ENGINE_LOGI("ResetRemoteService, do ResetService");
112 std::lock_guard<std::recursive_mutex> lock(remoteServerLock_);
113 if (remoteServer_ != nullptr) {
114 remoteServer_ = nullptr;
115 }
116 }
117
ResetService(const wptr<IRemoteObject> & remote)118 template <typename SERVICE> void BaseServiceKitsImpl<SERVICE>::ResetService(const wptr<IRemoteObject> &remote)
119 {
120 ENGINE_LOGI("Remote is dead, do ResetService");
121 std::lock_guard<std::recursive_mutex> lock(remoteServerLock_);
122 if (deathRecipient_ != nullptr && remote != nullptr) {
123 remote->RemoveDeathRecipient(deathRecipient_);
124 }
125 remoteServer_ = nullptr;
126 deathRecipient_ = nullptr;
127 }
128 }
129 #endif // BASE_SERVICE_KITS_IMPL_H
130