• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 "ipc_server_stub.h"
17 
18 #include <algorithm>
19 #include <thread>
20 
21 #include "if_system_ability_manager.h"
22 #include "ipc_skeleton.h"
23 #include "ipc_types.h"
24 #include "iservice_registry.h"
25 #include "string_ex.h"
26 #include "system_ability_definition.h"
27 
28 #include "device_manager_errno.h"
29 #include "device_manager_log.h"
30 
31 #include "ipc_server_adapter.h"
32 #include "ipc_cmd_register.h"
33 
34 namespace OHOS {
35 namespace DistributedHardware {
36 IMPLEMENT_SINGLE_INSTANCE(IpcServerStub);
37 
38 const bool REGISTER_RESULT = SystemAbility::MakeAndRegisterAbility(&IpcServerStub::GetInstance());
39 
IpcServerStub()40 IpcServerStub::IpcServerStub() : SystemAbility(DISTRIBUTED_HARDWARE_DEVICEMANAGER_SA_ID, true)
41 {
42     registerToService_ = false;
43     state_ = ServiceRunningState::STATE_NOT_START;
44 }
45 
OnStart()46 void IpcServerStub::OnStart()
47 {
48     DMLOG(DM_LOG_INFO, "IpcServerStub::OnStart start");
49     if (state_ == ServiceRunningState::STATE_RUNNING) {
50         DMLOG(DM_LOG_DEBUG, "IpcServerStub has already started.");
51         return;
52     }
53     if (!Init()) {
54         DMLOG(DM_LOG_ERROR, "failed to init IpcServerStub");
55         return;
56     }
57     state_ = ServiceRunningState::STATE_RUNNING;
58 }
59 
Init()60 bool IpcServerStub::Init()
61 {
62     DMLOG(DM_LOG_INFO, "IpcServerStub::Init ready to init.");
63     if (!registerToService_) {
64         bool ret = Publish(this);
65         if (!ret) {
66             DMLOG(DM_LOG_ERROR, "IpcServerStub::Init Publish failed!");
67             return false;
68         }
69         registerToService_ = true;
70     }
71 
72     std::thread {
73         [] {
74             IpcServerAdapter::GetInstance().ModuleInit();
75         }
76     }.detach();
77     return true;
78 }
79 
OnStop()80 void IpcServerStub::OnStop()
81 {
82     DMLOG(DM_LOG_INFO, "IpcServerStub::OnStop ready to stop service.");
83     state_ = ServiceRunningState::STATE_NOT_START;
84     registerToService_ = false;
85 }
86 
OnRemoteRequest(uint32_t code,MessageParcel & data,MessageParcel & reply,MessageOption & option)87 int32_t IpcServerStub::OnRemoteRequest(uint32_t code,
88     MessageParcel &data, MessageParcel &reply, MessageOption &option)
89 {
90     DMLOG(DM_LOG_INFO, "code = %u, flags= %d.", code, option.GetFlags());
91     auto remoteDescriptor = data.ReadInterfaceToken();
92     if (GetDescriptor() != remoteDescriptor) {
93         DMLOG(DM_LOG_ERROR, "ReadInterfaceToken fail!");
94         return DEVICEMANAGER_FAILED;
95     }
96     int32_t ret = DEVICEMANAGER_OK;
97     ret = IpcCmdRegister::GetInstance().OnIpcCmd(code, data, reply);
98     if (ret == DEVICEMANAGER_IPC_NOT_REGISTER_FUNC) {
99         DMLOG(DM_LOG_WARN, "unsupport code: %d", code);
100         return IPCObjectStub::OnRemoteRequest(code, data, reply, option);
101     }
102     return ret;
103 }
104 
SendCmd(int32_t cmdCode,std::shared_ptr<IpcReq> req,std::shared_ptr<IpcRsp> rsp)105 int32_t IpcServerStub::SendCmd(int32_t cmdCode, std::shared_ptr<IpcReq> req, std::shared_ptr<IpcRsp> rsp)
106 {
107     return DEVICEMANAGER_OK;
108 }
109 
QueryServiceState() const110 ServiceRunningState IpcServerStub::QueryServiceState() const
111 {
112     return state_;
113 }
114 
RegisterDeviceManagerListener(std::string & pkgName,sptr<IRemoteObject> listener)115 int32_t IpcServerStub::RegisterDeviceManagerListener(std::string &pkgName, sptr<IRemoteObject> listener)
116 {
117     if (pkgName.empty() || listener == nullptr) {
118         DMLOG(DM_LOG_ERROR, "Error: parameter invalid");
119         return DEVICEMANAGER_NULLPTR;
120     }
121 
122     DMLOG(DM_LOG_INFO, "In, pkgName: %s", pkgName.c_str());
123     std::lock_guard<std::mutex> autoLock(listenerLock_);
124     auto iter = dmListener_.find(pkgName);
125     if (iter != dmListener_.end()) {
126         DMLOG(DM_LOG_INFO, "RegisterDeviceManagerListener: listener already exists");
127         return DEVICEMANAGER_OK;
128     }
129 
130     sptr<AppDeathRecipient> appRecipient = sptr<AppDeathRecipient>(new AppDeathRecipient());
131     if (!listener->AddDeathRecipient(appRecipient)) {
132         DMLOG(DM_LOG_ERROR, "RegisterDeviceManagerListener: AddDeathRecipient Failed");
133     }
134     dmListener_[pkgName] = listener;
135     appRecipient_[pkgName] = appRecipient;
136     return DEVICEMANAGER_OK;
137 }
138 
UnRegisterDeviceManagerListener(std::string & pkgName)139 int32_t IpcServerStub::UnRegisterDeviceManagerListener(std::string &pkgName)
140 {
141     if (pkgName.empty()) {
142         DMLOG(DM_LOG_ERROR, "Error: parameter invalid");
143         return DEVICEMANAGER_NULLPTR;
144     }
145 
146     DMLOG(DM_LOG_INFO, "In, pkgName: %s", pkgName.c_str());
147     std::lock_guard<std::mutex> autoLock(listenerLock_);
148     auto listenerIter = dmListener_.find(pkgName);
149     if (listenerIter == dmListener_.end()) {
150         DMLOG(DM_LOG_INFO, "UnRegisterDeviceManagerListener: listener not exists");
151         return DEVICEMANAGER_OK;
152     }
153 
154     auto recipientIter = appRecipient_.find(pkgName);
155     if (recipientIter == appRecipient_.end()) {
156         DMLOG(DM_LOG_INFO, "UnRegisterDeviceManagerListener: appRecipient not exists");
157         dmListener_.erase(pkgName);
158         return DEVICEMANAGER_OK;
159     }
160 
161     auto listener = listenerIter->second;
162     auto appRecipient = recipientIter->second;
163     listener->RemoveDeathRecipient(appRecipient);
164     appRecipient_.erase(pkgName);
165     dmListener_.erase(pkgName);
166     return DEVICEMANAGER_OK;
167 }
168 
GetDmListener()169 const std::map<std::string, sptr<IRemoteObject>> &IpcServerStub::GetDmListener()
170 {
171     return dmListener_;
172 }
173 
GetDmListener(std::string pkgName) const174 const sptr<IpcRemoteBroker> IpcServerStub::GetDmListener(std::string pkgName) const
175 {
176     if (pkgName.empty()) {
177         DMLOG(DM_LOG_ERROR, "Error: parameter invalid");
178         return nullptr;
179     }
180     auto iter = dmListener_.find(pkgName);
181     if (iter == dmListener_.end()) {
182         return nullptr;
183     }
184     auto remote = iter->second;
185     sptr<IpcRemoteBroker> dmListener = iface_cast<IpcRemoteBroker>(remote);
186     return dmListener;
187 }
188 
OnRemoteDied(const wptr<IRemoteObject> & remote)189 void AppDeathRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
190 {
191     DMLOG(DM_LOG_WARN, "AppDeathRecipient: OnRemoteDied");
192     std::map<std::string, sptr<IRemoteObject>> listeners = IpcServerStub::GetInstance().GetDmListener();
193     std::string pkgName;
194     for (auto iter : listeners) {
195         if (iter.second == remote.promote()) {
196             pkgName = iter.first;
197             break;
198         }
199     }
200     if (pkgName.empty()) {
201         DMLOG(DM_LOG_ERROR, "AppDeathRecipient: OnRemoteDied, no pkgName matched");
202         return;
203     }
204     DMLOG(DM_LOG_INFO, "AppDeathRecipient: OnRemoteDied for %s", pkgName.c_str());
205     IpcServerStub::GetInstance().UnRegisterDeviceManagerListener(pkgName);
206 }
207 } // namespace DistributedHardware
208 } // namespace OHOS
209