• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2024 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 "dtbschedmgr_device_info_storage.h"
17 
18 #include <chrono>
19 #include <thread>
20 
21 #include "distributed_device_node_listener.h"
22 #include "distributed_sched_service.h"
23 #include "dtbschedmgr_log.h"
24 #include "ipc_object_proxy.h"
25 #include "ipc_skeleton.h"
26 #include "iservice_registry.h"
27 #include "system_ability_definition.h"
28 
29 using namespace std;
30 namespace OHOS {
31 namespace DistributedSchedule {
32 using namespace std::chrono_literals;
33 using namespace DistributedHardware;
34 
35 namespace {
36 constexpr int32_t RETRY_TIMES = 30;
37 constexpr int32_t CONNECT_SOFTBUS_RETRY_TIMES = 60;
38 const std::string TAG = "DtbschedmgrDeviceInfoStorage";
39 }
40 
41 IMPLEMENT_SINGLE_INSTANCE(DtbschedmgrDeviceInfoStorage);
42 
Init()43 bool DtbschedmgrDeviceInfoStorage::Init()
44 {
45     if (initHandler_ == nullptr) {
46         auto deviceInfoStorageRunner = AppExecFwk::EventRunner::Create("DmsDeviceInfoStorageManager");
47         initHandler_ = std::make_shared<AppExecFwk::EventHandler>(deviceInfoStorageRunner);
48     }
49 
50     auto func = [this]() {
51         HILOGI("begin connect softbus");
52         for (int32_t retryTimes = 0; retryTimes <= CONNECT_SOFTBUS_RETRY_TIMES; retryTimes++) {
53             if (ConnectSoftbus()) {
54                 return;
55             }
56             HILOGE("retry connect softbus %{public}d times", retryTimes);
57             std::this_thread::sleep_for(1s);
58         }
59         HILOGE("connect softbus 60times * 30s, error!!");
60     };
61     if (!initHandler_->PostTask(func)) {
62         HILOGE("Init handler postTask failed");
63         return false;
64     }
65     return true;
66 }
67 
ConnectSoftbus()68 bool DtbschedmgrDeviceInfoStorage::ConnectSoftbus()
69 {
70     ClearAllDevices();
71     bool isReady = WaitForDnetworkReady();
72     if (!isReady) {
73         HILOGE("ConnectSoftbus wait Dnetwork failed!");
74         return false;
75     }
76     std::shared_ptr<DnetworkAdapter> dnetworkAdapter = DnetworkAdapter::GetInstance();
77     if (dnetworkAdapter == nullptr) {
78         HILOGE("DnetworkAdapter::GetInstance() null");
79         return false;
80     }
81     if (!InitNetworkIdManager(dnetworkAdapter)) {
82         HILOGE("InitNetworkIdManager failed");
83         return false;
84     }
85     HILOGI("ConnectSoftbus success");
86     return true;
87 }
88 
InitNetworkIdManager(std::shared_ptr<DnetworkAdapter> dnetworkAdapter)89 bool DtbschedmgrDeviceInfoStorage::InitNetworkIdManager(std::shared_ptr<DnetworkAdapter> dnetworkAdapter)
90 {
91     if (networkIdMgrHandler_ == nullptr) {
92         auto runner = AppExecFwk::EventRunner::Create("DmsNetworkIdManager");
93         networkIdMgrHandler_ = std::make_shared<AppExecFwk::EventHandler>(runner);
94     }
95 
96     deviceNodeListener_ = std::make_shared<DistributedDeviceNodeListener>();
97     if (!dnetworkAdapter->AddDeviceChangeListener(deviceNodeListener_)) {
98         deviceNodeListener_ = nullptr;
99         HILOGE("AddDeviceChangeListener failed!");
100         return false;
101     }
102     return true;
103 }
104 
Stop()105 void DtbschedmgrDeviceInfoStorage::Stop()
106 {
107     ClearAllDevices();
108     if (deviceNodeListener_ != nullptr) {
109         DnetworkAdapter::GetInstance()->RemoveDeviceChangeListener(deviceNodeListener_);
110         deviceNodeListener_ = nullptr;
111     }
112 }
113 
WaitForDnetworkReady()114 bool DtbschedmgrDeviceInfoStorage::WaitForDnetworkReady()
115 {
116     auto samgr = SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager();
117     if (samgr == nullptr) {
118         HILOGE("WaitForDnetworkReady failed to get samgr!");
119         return false;
120     }
121     int32_t retryTimeout = RETRY_TIMES;
122     do {
123         auto dnetwork = samgr->CheckSystemAbility(DISTRIBUTED_HARDWARE_DEVICEMANAGER_SA_ID);
124         if (dnetwork != nullptr) {
125             IPCObjectProxy* proxy = reinterpret_cast<IPCObjectProxy*>(dnetwork.GetRefPtr());
126             // make sure the proxy is not dead
127             if (proxy != nullptr && !proxy->IsObjectDead()) {
128                 return true;
129             }
130         }
131         HILOGI("Waiting for dnentwork service...");
132         std::this_thread::sleep_for(1s);
133         if (--retryTimeout <= 0) {
134             HILOGI("Waiting for dnentwork service timeout(30)s");
135             return false;
136         }
137     } while (true);
138     return false;
139 }
140 
RegisterUuidNetworkIdMap(const std::string & networkId)141 void DtbschedmgrDeviceInfoStorage::RegisterUuidNetworkIdMap(const std::string& networkId)
142 {
143     std::string uuid = DnetworkAdapter::GetInstance()->GetUuidByNetworkId(networkId);
144     if (uuid.empty()) {
145         HILOGE("GetUuidByNetworkId return an empty uuid!");
146         return;
147     }
148     {
149         std::lock_guard<std::mutex> autoLock(uuidNetworkIdLock_);
150         uuidNetworkIdMap_[uuid] = networkId;
151     }
152 }
153 
UnregisterUuidNetworkIdMap(const std::string & networkId)154 void DtbschedmgrDeviceInfoStorage::UnregisterUuidNetworkIdMap(const std::string& networkId)
155 {
156     std::string uuid = DnetworkAdapter::GetInstance()->GetUuidByNetworkId(networkId);
157     if (uuid.empty()) {
158         HILOGE("GetUuidByNetworkId return an empty uuid");
159         return;
160     }
161     {
162         std::lock_guard<std::mutex> autoLock(uuidNetworkIdLock_);
163         uuidNetworkIdMap_.erase(uuid);
164     }
165 }
166 
GetDeviceIdSet(std::set<std::string> & deviceIdSet)167 void DtbschedmgrDeviceInfoStorage::GetDeviceIdSet(std::set<std::string>& deviceIdSet)
168 {
169     deviceIdSet.clear();
170     lock_guard<mutex> autoLock(deviceLock_);
171     for (const auto& device : remoteDevices_) {
172         deviceIdSet.emplace(device.first);
173     }
174 }
175 
UpdateDeviceInfoStorage(const std::vector<DmDeviceInfo> & dmDeviceInfoList)176 void DtbschedmgrDeviceInfoStorage::UpdateDeviceInfoStorage(
177     const std::vector<DmDeviceInfo>& dmDeviceInfoList)
178 {
179     for (const auto& dmDeviceInfo : dmDeviceInfoList) {
180         auto deviceInfo = std::make_shared<DmsDeviceInfo>(
181             dmDeviceInfo.deviceName, dmDeviceInfo.deviceTypeId, dmDeviceInfo.networkId);
182         std::string networkId = deviceInfo->GetNetworkId();
183         RegisterUuidNetworkIdMap(networkId);
184         {
185             HILOGI("remoteDevices networkId = %{public}s", DnetworkAdapter::AnonymizeNetworkId(networkId).c_str());
186             lock_guard<mutex> autoLock(deviceLock_);
187             remoteDevices_[networkId] = deviceInfo;
188         }
189     }
190 }
191 
GetLocalDeviceId(std::string & networkId)192 bool DtbschedmgrDeviceInfoStorage::GetLocalDeviceId(std::string& networkId)
193 {
194     return GetLocalDeviceFromDnet(networkId);
195 }
196 
GetLocalUdid(std::string & udid)197 bool DtbschedmgrDeviceInfoStorage::GetLocalUdid(std::string& udid)
198 {
199     return GetLocalDeviceUdid(udid);
200 }
201 
GetLocalDeviceFromDnet(std::string & networkId)202 bool DtbschedmgrDeviceInfoStorage::GetLocalDeviceFromDnet(std::string& networkId)
203 {
204     auto dnetworkAdapter = DnetworkAdapter::GetInstance();
205     if (dnetworkAdapter == nullptr) {
206         HILOGE("GetLocalDeviceFromDnet dnetworkAdapter null");
207         return false;
208     }
209     DmDeviceInfo dmDeviceInfo;
210     if (!dnetworkAdapter->GetLocalBasicInfo(dmDeviceInfo)) {
211         HILOGE("GetLocalBasicInfo error");
212         return false;
213     }
214     networkId = dmDeviceInfo.networkId;
215     HILOGI("get local networkId from DnetworkAdapter, networkId = %{public}s",
216         DnetworkAdapter::AnonymizeNetworkId(networkId).c_str());
217     return true;
218 }
219 
GetLocalDeviceUdid(std::string & udid)220 bool DtbschedmgrDeviceInfoStorage::GetLocalDeviceUdid(std::string& udid)
221 {
222     auto dnetworkAdapter = DnetworkAdapter::GetInstance();
223     if (dnetworkAdapter == nullptr) {
224         HILOGE("GetLocalDeviceFromDnet dnetworkAdapter null");
225         return false;
226     }
227     DmDeviceInfo dmDeviceInfo;
228     if (!dnetworkAdapter->GetLocalBasicInfo(dmDeviceInfo)) {
229         HILOGE("GetLocalBasicInfo error");
230         return false;
231     }
232     udid = GetUuidByNetworkId(dmDeviceInfo.networkId);
233     HILOGI("GetLocalDeviceUdid = %{public}s", DnetworkAdapter::AnonymizeNetworkId(udid).c_str());
234     return true;
235 }
236 
ClearAllDevices()237 void DtbschedmgrDeviceInfoStorage::ClearAllDevices()
238 {
239     lock_guard<mutex> autoLock(deviceLock_);
240     remoteDevices_.clear();
241 }
242 
GetDeviceInfoById(const string & networkId)243 std::shared_ptr<DmsDeviceInfo> DtbschedmgrDeviceInfoStorage::GetDeviceInfoById(const string& networkId)
244 {
245     lock_guard<mutex> autoLock(deviceLock_);
246     auto iter = remoteDevices_.find(networkId);
247     if (iter == remoteDevices_.end()) {
248         return nullptr;
249     }
250     return iter->second;
251 }
252 
GetUuidByNetworkId(const std::string & networkId)253 std::string DtbschedmgrDeviceInfoStorage::GetUuidByNetworkId(const std::string& networkId)
254 {
255     if (networkId.empty()) {
256         HILOGW("GetUuidByNetworkId networkId empty!");
257         return "";
258     }
259     {
260         std::lock_guard<std::mutex> autoLock(uuidNetworkIdLock_);
261         auto iter = uuidNetworkIdMap_.begin();
262         while (iter != uuidNetworkIdMap_.end()) {
263             if (iter->second == networkId) {
264                 return iter->first;
265             } else {
266                 ++iter;
267             }
268         }
269     }
270     std::string uuid = DnetworkAdapter::GetInstance()->GetUuidByNetworkId(networkId);
271     return uuid;
272 }
273 
GetUdidByNetworkId(const std::string & networkId)274 std::string DtbschedmgrDeviceInfoStorage::GetUdidByNetworkId(const std::string& networkId)
275 {
276     if (networkId.empty()) {
277         HILOGW("GetUdidByNetworkId networkId empty!");
278         return "";
279     }
280     std::string udid = DnetworkAdapter::GetInstance()->GetUdidByNetworkId(networkId);
281     return udid;
282 }
283 
GetNetworkIdByUuid(const std::string & uuid)284 std::string DtbschedmgrDeviceInfoStorage::GetNetworkIdByUuid(const std::string& uuid)
285 {
286     if (uuid.empty()) {
287         HILOGW("GetNetworkIdByUuid uuid empty!");
288         return "";
289     }
290     {
291         std::lock_guard<std::mutex> autoLock(uuidNetworkIdLock_);
292         auto iter = uuidNetworkIdMap_.find(uuid);
293         if (iter != uuidNetworkIdMap_.end()) {
294             return iter->second;
295         }
296         return "";
297     }
298 }
DeviceOnlineNotify(const std::shared_ptr<DmsDeviceInfo> devInfo)299 void DtbschedmgrDeviceInfoStorage::DeviceOnlineNotify(const std::shared_ptr<DmsDeviceInfo> devInfo)
300 {
301     if (devInfo == nullptr) {
302         HILOGE("DeviceOnlineNotify devInfo null");
303         return;
304     }
305 
306     if (networkIdMgrHandler_ == nullptr) {
307         HILOGE("networkIdMgrHandler null");
308         return;
309     }
310     auto nodeOnline = [this, devInfo]() {
311         std::string networkId = devInfo->GetNetworkId();
312         RegisterUuidNetworkIdMap(networkId);
313         std::string uuid = GetUuidByNetworkId(networkId);
314         HILOGI("networkId = %{public}s, uuid = %{public}s, deviceName = %{public}s",
315             DnetworkAdapter::AnonymizeNetworkId(networkId).c_str(),
316             DnetworkAdapter::AnonymizeNetworkId(uuid).c_str(), devInfo->GetDeviceName().c_str());
317         {
318             lock_guard<mutex> autoLock(deviceLock_);
319             remoteDevices_[networkId] = devInfo;
320         }
321         DistributedSchedService::GetInstance().DeviceOnlineNotify(networkId);
322     };
323     if (!networkIdMgrHandler_->PostTask(nodeOnline)) {
324         HILOGE("DeviceOnlineNotify handler postTask failed");
325     }
326 }
327 
DeviceOfflineNotify(const std::string & networkId)328 void DtbschedmgrDeviceInfoStorage::DeviceOfflineNotify(const std::string& networkId)
329 {
330     if (networkId.empty()) {
331         HILOGE("DeviceOfflineNotify networkId empty");
332         return;
333     }
334     HILOGD("DeviceOfflineNotify networkId = %{public}s",
335         DnetworkAdapter::AnonymizeNetworkId(networkId).c_str());
336     if (networkIdMgrHandler_ == nullptr) {
337         HILOGE("DeviceOfflineNotify networkIdMgrHandler null");
338         return;
339     }
340     auto nodeOffline = [this, networkId]() {
341         std::string uuid = GetUuidByNetworkId(networkId);
342         HILOGI("DeviceOfflineNotify process networkId = %{public}s, uuid = %{public}s",
343             DnetworkAdapter::AnonymizeNetworkId(networkId).c_str(), DnetworkAdapter::AnonymizeNetworkId(uuid).c_str());
344         DistributedSchedService::GetInstance().DeviceOfflineNotify(networkId);
345         UnregisterUuidNetworkIdMap(networkId);
346         lock_guard<mutex> autoLock(deviceLock_);
347         remoteDevices_.erase(networkId);
348     };
349     if (!networkIdMgrHandler_->PostTask(nodeOffline)) {
350         HILOGE("DeviceOfflineNotify handler postTask failed");
351     }
352 }
353 
OnDeviceInfoChanged(const std::string & deviceId)354 void DtbschedmgrDeviceInfoStorage::OnDeviceInfoChanged(const std::string& deviceId)
355 {
356     HILOGI("OnDeviceInfoChanged called");
357 }
358 
OnRemoteDied(const wptr<IRemoteObject> & remote)359 void DnetServiceDeathRecipient::OnRemoteDied(const wptr<IRemoteObject>& remote)
360 {
361     HILOGI("OnRemoteDied dnetwork service died");
362     DtbschedmgrDeviceInfoStorage::GetInstance().Init();
363 }
364 }
365 }
366