• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 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 #ifdef FEATURE_NETWORK_SUPPORT
17 #include "network_ability.h"
18 #include <file_ex.h>
19 #include <thread>
20 #include "ability_connect_callback_stub.h"
21 #include "ability_manager_client.h"
22 #include "ipc_skeleton.h"
23 #include "iservice_registry.h"
24 #include "system_ability_definition.h"
25 #include "want_agent_helper.h"
26 
27 #include "common_utils.h"
28 #include "location_config_manager.h"
29 #include "location_dumper.h"
30 #include "location_log.h"
31 #include "location_sa_load_manager.h"
32 #include "network_callback_host.h"
33 #include "locationhub_ipc_interface_code.h"
34 #include "location_log_event_ids.h"
35 #include "common_hisysevent.h"
36 #include "location_data_rdb_manager.h"
37 #include "hook_utils.h"
38 #include "permission_manager.h"
39 
40 #ifdef LOCATION_HICOLLIE_ENABLE
41 #include "xcollie/xcollie.h"
42 #include "xcollie/xcollie_define.h"
43 #endif
44 
45 namespace OHOS {
46 namespace Location {
47 const uint32_t EVENT_REPORT_MOCK_LOCATION = 0x0100;
48 const uint32_t EVENT_RESTART_ALL_LOCATION_REQUEST = 0x0200;
49 const uint32_t EVENT_STOP_ALL_LOCATION_REQUEST = 0x0300;
50 const uint32_t EVENT_DISCONNECT_SERVICES = 0x0400;
51 const uint32_t EVENT_INTERVAL_UNITE = 1000;
52 const uint32_t DELAY_RESTART_MS = 500;
53 const uint32_t DELAY_DINCONNECT_MS = 5 * 1000;
54 constexpr uint32_t WAIT_MS = 100;
55 const int MAX_RETRY_COUNT = 5;
56 const std::string UNLOAD_NETWORK_TASK = "network_sa_unload";
57 const std::string DISCONNECT_NETWORK_TASK = "disconnect_network_ability";
58 const uint32_t RETRY_INTERVAL_OF_UNLOAD_SA = 4 * 60 * EVENT_INTERVAL_UNITE;
59 const int TIMEOUT_WATCHDOG = 60; // s
60 const bool REGISTER_RESULT = NetworkAbility::MakeAndRegisterAbility(
61     NetworkAbility::GetInstance());
62 
NetworkAbility()63 NetworkAbility::NetworkAbility() : SystemAbility(LOCATION_NETWORK_LOCATING_SA_ID, true)
64 {
65     SetAbility(NETWORK_ABILITY);
66 #ifndef TDD_CASES_ENABLED
67     networkHandler_ =
68         std::make_shared<NetworkHandler>(AppExecFwk::EventRunner::Create(true, AppExecFwk::ThreadMode::FFRT));
69 #endif
70     LBSLOGI(NETWORK, "ability constructed.");
71 }
72 
~NetworkAbility()73 NetworkAbility::~NetworkAbility()
74 {
75     std::unique_lock<ffrt::mutex> uniqueLock(connMutex_);
76     conn_ = nullptr;
77 }
78 
OnStart()79 void NetworkAbility::OnStart()
80 {
81     if (state_ == ServiceRunningState::STATE_RUNNING) {
82         LBSLOGI(NETWORK, "ability has already started.");
83         return;
84     }
85     if (!Init()) {
86         LBSLOGE(NETWORK, "failed to init ability");
87         OnStop();
88         return;
89     }
90     state_ = ServiceRunningState::STATE_RUNNING;
91     LBSLOGI(NETWORK, "OnStart start ability success.");
92 }
93 
OnStop()94 void NetworkAbility::OnStop()
95 {
96     state_ = ServiceRunningState::STATE_NOT_START;
97     registerToAbility_ = false;
98     LBSLOGI(NETWORK, "OnStop ability stopped.");
99 }
100 
GetInstance()101 NetworkAbility* NetworkAbility::GetInstance()
102 {
103     static NetworkAbility data;
104     return &data;
105 }
106 
Init()107 bool NetworkAbility::Init()
108 {
109     if (!registerToAbility_) {
110         if (!Publish(AsObject())) {
111             LBSLOGE(NETWORK, "Init Publish failed!");
112             return false;
113         }
114         registerToAbility_ = true;
115     }
116     return true;
117 }
118 
119 class AbilityConnection : public AAFwk::AbilityConnectionStub {
120 public:
OnAbilityConnectDone(const AppExecFwk::ElementName & element,const sptr<IRemoteObject> & remoteObject,int resultCode)121     void OnAbilityConnectDone(
122         const AppExecFwk::ElementName& element, const sptr<IRemoteObject>& remoteObject, int resultCode) override
123     {
124         std::string uri = element.GetURI();
125         LBSLOGD(NETWORK, "Connected uri is %{public}s, result is %{public}d.", uri.c_str(), resultCode);
126         if (resultCode != ERR_OK) {
127             return;
128         }
129         NetworkAbility::GetInstance()->NotifyConnected(remoteObject);
130     }
131 
OnAbilityDisconnectDone(const AppExecFwk::ElementName & element,int)132     void OnAbilityDisconnectDone(const AppExecFwk::ElementName& element, int) override
133     {
134         std::string uri = element.GetURI();
135         LBSLOGD(NETWORK, "Disconnected uri is %{public}s.", uri.c_str());
136         NetworkAbility::GetInstance()->NotifyDisConnected();
137     }
138 };
139 
ConnectNlpService()140 bool NetworkAbility::ConnectNlpService()
141 {
142     LBSLOGD(NETWORK, "start ConnectNlpService");
143     if (!IsConnect()) {
144         AAFwk::Want connectionWant;
145         std::string serviceName;
146         bool result = LocationConfigManager::GetInstance()->GetNlpServiceName(serviceName);
147         if (!result || serviceName.empty()) {
148             LBSLOGE(NETWORK, "get service name failed!");
149             return false;
150         }
151         std::string abilityName;
152         bool res = LocationConfigManager::GetInstance()->GetNlpAbilityName(abilityName);
153         if (!res || abilityName.empty()) {
154             LBSLOGE(NETWORK, "get service name failed!");
155             return false;
156         }
157         connectionWant.SetElementName(serviceName, abilityName);
158         std::unique_lock<ffrt::mutex> lock(connMutex_, std::defer_lock);
159         connMutex_.lock();
160         conn_ = sptr<AAFwk::IAbilityConnection>(new (std::nothrow) AbilityConnection());
161         if (conn_ == nullptr) {
162             LBSLOGE(NETWORK, "get connection failed!");
163             connMutex_.unlock();
164             return false;
165         }
166         int32_t ret = AAFwk::AbilityManagerClient::GetInstance()->ConnectAbility(connectionWant, conn_, -1);
167         connMutex_.unlock();
168         if (ret != ERR_OK) {
169             LBSLOGE(NETWORK, "Connect cloud service failed, ret = %{public}d", ret);
170             return false;
171         }
172         std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
173         auto waitStatus = connectCondition_.wait_for(
174             uniqueLock, std::chrono::seconds(CONNECT_TIME_OUT), [this]() { return nlpServiceProxy_ != nullptr; });
175         if (!waitStatus) {
176             WriteLocationInnerEvent(NLP_SERVICE_TIMEOUT, {});
177             LBSLOGE(NETWORK, "Connect cloudService timeout!");
178             return false;
179         }
180     }
181     RegisterNlpServiceDeathRecipient();
182     return true;
183 }
184 
ReConnectNlpService()185 bool NetworkAbility::ReConnectNlpService()
186 {
187     int retryCount = 0;
188     if (IsConnect()) {
189         LBSLOGI(NETWORK, "Connect success!");
190         return true;
191     }
192     while (retryCount < MAX_RETRY_COUNT) {
193         retryCount++;
194         bool ret = ConnectNlpService();
195         if (ret) {
196             LBSLOGI(NETWORK, "Connect success!");
197             return true;
198         }
199         std::this_thread::sleep_for(std::chrono::milliseconds(WAIT_MS));
200     }
201     return false;
202 }
203 
ResetServiceProxy()204 bool NetworkAbility::ResetServiceProxy()
205 {
206     if (networkHandler_ == nullptr) {
207         return false;
208     }
209     networkHandler_->SendHighPriorityEvent(EVENT_DISCONNECT_SERVICES, 0, 0);
210     return true;
211 }
212 
ClearServiceProxy()213 void NetworkAbility::ClearServiceProxy()
214 {
215     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
216     nlpServiceProxy_ = nullptr;
217 }
218 
NotifyConnected(const sptr<IRemoteObject> & remoteObject)219 void NetworkAbility::NotifyConnected(const sptr<IRemoteObject>& remoteObject)
220 {
221     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
222     nlpServiceProxy_ = remoteObject;
223     connectCondition_.notify_all();
224 }
225 
NotifyDisConnected()226 void NetworkAbility::NotifyDisConnected()
227 {
228     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
229     connectCondition_.notify_all();
230 }
231 
SendLocationRequest(WorkRecord & workrecord)232 LocationErrCode NetworkAbility::SendLocationRequest(WorkRecord &workrecord)
233 {
234     LocationRequest(workrecord);
235     return ERRCODE_SUCCESS;
236 }
237 
SetEnable(bool state)238 LocationErrCode NetworkAbility::SetEnable(bool state)
239 {
240     LBSLOGD(NETWORK, "SetEnable: %{public}d", state);
241     int nlpEnableState  = LocationConfigManager::GetInstance()->GetNlpEnableState();
242     if (!nlpEnableState) {
243         LBSLOGE(NETWORK, "nlpEnableState false");
244         state = false;
245     }
246     if (networkHandler_ == nullptr) {
247         LBSLOGE(NETWORK, "%{public}s networkHandler is nullptr", __func__);
248         return ERRCODE_SERVICE_UNAVAILABLE;
249     }
250     auto event = state ? AppExecFwk::InnerEvent::Get(EVENT_RESTART_ALL_LOCATION_REQUEST, 0) :
251         AppExecFwk::InnerEvent::Get(EVENT_STOP_ALL_LOCATION_REQUEST, 0);
252     networkHandler_->SendHighPriorityEvent(event);
253     return ERRCODE_SUCCESS;
254 }
255 
CancelIdleState()256 bool NetworkAbility::CancelIdleState()
257 {
258     SystemAbilityState state = GetAbilityState();
259     if (state != SystemAbilityState::IDLE) {
260         return true;
261     }
262     bool ret = CancelIdle();
263     if (!ret) {
264         LBSLOGE(NETWORK, "%{public}s cancel idle failed!", __func__);
265         return false;
266     }
267     return true;
268 }
269 
UnloadNetworkSystemAbility()270 void NetworkAbility::UnloadNetworkSystemAbility()
271 {
272     if (networkHandler_ == nullptr) {
273         LBSLOGE(NETWORK, "%{public}s networkHandler is nullptr", __func__);
274         return;
275     }
276     networkHandler_->RemoveTask(UNLOAD_NETWORK_TASK);
277     auto task = [this]() {
278         if (CheckIfNetworkConnecting()) {
279             return;
280         }
281         SaLoadWithStatistic::UnInitLocationSa(LOCATION_NETWORK_LOCATING_SA_ID);
282     };
283     if (networkHandler_ != nullptr) {
284         networkHandler_->PostTask(task, UNLOAD_NETWORK_TASK, RETRY_INTERVAL_OF_UNLOAD_SA);
285     }
286 }
287 
CheckIfNetworkConnecting()288 bool NetworkAbility::CheckIfNetworkConnecting()
289 {
290     return IsMockEnabled() || !GetLocationMock().empty() || GetRequestNum() != 0;
291 }
292 
RequestRecord(WorkRecord & workRecord,bool isAdded)293 void NetworkAbility::RequestRecord(WorkRecord &workRecord, bool isAdded)
294 {
295     if (!IsConnect()) {
296         std::string serviceName;
297         bool result = LocationConfigManager::GetInstance()->GetNlpServiceName(serviceName);
298         if (!result || serviceName.empty()) {
299             LBSLOGE(NETWORK, "get service name failed!");
300             return;
301         }
302         if (!CommonUtils::CheckAppInstalled(serviceName)) { // app is not installed
303             LBSLOGE(NETWORK, "nlp service is not available.");
304             return;
305         } else if (!ReConnectNlpService()) {
306             LBSLOGE(NETWORK, "nlp service is not ready.");
307             return;
308         }
309     }
310     if (isAdded) {
311         int nlpEnableState  = LocationConfigManager::GetInstance()->GetNlpEnableState();
312         uint32_t tokenId = workRecord.GetTokenId(0);
313         uint32_t firstTokenId = workRecord.GetFirstTokenId(0);
314         bool ignoredSwtichPermission =
315             PermissionManager::CheckLocationSwitchIgnoredPermission(tokenId, firstTokenId);
316         if (!nlpEnableState && !ignoredSwtichPermission) { //  enter when enablestated & ignoredPermission all false
317             LBSLOGE(NETWORK, "enablestated and ignoredSwtichPermission both false");
318             return;
319         }
320         RequestNetworkLocation(workRecord);
321         if (networkHandler_ != nullptr) {
322             networkHandler_->RemoveTask(DISCONNECT_NETWORK_TASK);
323         }
324     } else {
325         RemoveNetworkLocation(workRecord);
326         if (networkHandler_ == nullptr) {
327             return;
328         }
329         networkHandler_->RemoveTask(DISCONNECT_NETWORK_TASK);
330         auto disconnectTask = [this]() {
331             auto networkAbility = NetworkAbility::GetInstance();
332             if (networkAbility == nullptr) {
333                 LBSLOGE(NETWORK, "OnRemoteDied: NetworkAbility is nullptr");
334                 return;
335             };
336             networkAbility->DisconnectAbilityConnect();
337         };
338         networkHandler_->PostTask(disconnectTask, DISCONNECT_NETWORK_TASK, DELAY_DINCONNECT_MS);
339     }
340 }
341 
DisconnectAbilityConnect()342 void NetworkAbility::DisconnectAbilityConnect()
343 {
344     std::unique_lock<ffrt::mutex> uniqueLock(connMutex_);
345     if (GetRequestNum() == 0 && conn_ != nullptr) {
346         LBSLOGI(NETWORK, "RequestRecord disconnect");
347         UnregisterNlpServiceDeathRecipient();
348         AAFwk::AbilityManagerClient::GetInstance()->DisconnectAbility(conn_);
349         conn_ = nullptr;
350         std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
351         nlpServiceProxy_ = nullptr;
352         LBSLOGD(NETWORK, "disconnect cloudService success!");
353     }
354 }
355 
RequestNetworkLocation(WorkRecord & workRecord)356 bool NetworkAbility::RequestNetworkLocation(WorkRecord &workRecord)
357 {
358     LBSLOGW(NETWORK, "start network location, uuid: %{public}s", workRecord.GetUuid(0).c_str());
359     sptr<NetworkCallbackHost> callback = new (std::nothrow) NetworkCallbackHost();
360     if (callback == nullptr) {
361         LBSLOGE(NETWORK, "can not get valid callback.");
362         return false;
363     }
364     HookUtils::ExecuteHookWhenAddNetworkRequest(workRecord.GetUuid(0));
365     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
366     if (nlpServiceProxy_ == nullptr) {
367         LBSLOGE(NETWORK, "nlpProxy is nullptr.");
368         return false;
369     }
370     MessageParcel data;
371 
372     MessageParcel reply;
373     MessageOption option;
374     data.WriteInterfaceToken(nlpServiceProxy_->GetInterfaceDescriptor());
375     data.WriteString16(Str8ToStr16(workRecord.GetUuid(0)));
376     data.WriteInt64(workRecord.GetTimeInterval(0) * MILLI_PER_SEC);
377     data.WriteInt32(workRecord.GetNlpRequestType(0));
378     data.WriteRemoteObject(callback->AsObject());
379     if (workRecord.GetName(0).size() == 0) {
380         data.WriteString16(Str8ToStr16(std::to_string(workRecord.GetUid(0)))); // uid
381     } else {
382         data.WriteString16(Str8ToStr16(workRecord.GetName(0))); // bundleName
383     }
384     int error = nlpServiceProxy_->SendRequest(REQUEST_NETWORK_LOCATION, data, reply, option);
385     if (error != ERR_OK) {
386         LBSLOGE(NETWORK, "SendRequest to cloud service failed. error = %{public}d", error);
387         return false;
388     }
389     return true;
390 }
391 
RemoveNetworkLocation(WorkRecord & workRecord)392 bool NetworkAbility::RemoveNetworkLocation(WorkRecord &workRecord)
393 {
394     HookUtils::ExecuteHookWhenRemoveNetworkRequest(workRecord.GetUuid(0));
395     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
396     if (nlpServiceProxy_ == nullptr) {
397         LBSLOGE(NETWORK, "nlpProxy is nullptr.");
398         return false;
399     }
400     LBSLOGW(NETWORK, "stop network location, uuid: %{public}s", workRecord.GetUuid(0).c_str());
401     MessageParcel data;
402     MessageParcel reply;
403     MessageOption option;
404     data.WriteInterfaceToken(nlpServiceProxy_->GetInterfaceDescriptor());
405     data.WriteString16(Str8ToStr16(workRecord.GetUuid(0)));
406     data.WriteString16(Str8ToStr16(workRecord.GetName(0))); // bundleName
407     int error = nlpServiceProxy_->SendRequest(REMOVE_NETWORK_LOCATION, data, reply, option);
408     if (error != ERR_OK) {
409         LBSLOGE(NETWORK, "SendRequest to cloud service failed.");
410         return false;
411     }
412     return true;
413 }
414 
EnableMock()415 LocationErrCode NetworkAbility::EnableMock()
416 {
417     if (!EnableLocationMock()) {
418         return LOCATION_ERRCODE_NOT_SUPPORTED;
419     }
420     return ERRCODE_SUCCESS;
421 }
422 
DisableMock()423 LocationErrCode NetworkAbility::DisableMock()
424 {
425     if (!DisableLocationMock()) {
426         return LOCATION_ERRCODE_NOT_SUPPORTED;
427     }
428     return ERRCODE_SUCCESS;
429 }
430 
IsMockEnabled()431 bool NetworkAbility::IsMockEnabled()
432 {
433     return IsLocationMocked();
434 }
435 
SetMocked(const int timeInterval,const std::vector<std::shared_ptr<Location>> & location)436 LocationErrCode NetworkAbility::SetMocked(const int timeInterval,
437     const std::vector<std::shared_ptr<Location>> &location)
438 {
439     if (!SetMockedLocations(timeInterval, location)) {
440         return LOCATION_ERRCODE_NOT_SUPPORTED;
441     }
442     return ERRCODE_SUCCESS;
443 }
444 
ProcessReportLocationMock()445 void NetworkAbility::ProcessReportLocationMock()
446 {
447     std::vector<std::shared_ptr<Location>> mockLocationArray = GetLocationMock();
448     if (mockLocationIndex_ < mockLocationArray.size()) {
449         ReportMockedLocation(mockLocationArray[mockLocationIndex_++]);
450         if (networkHandler_ != nullptr) {
451             networkHandler_->SendHighPriorityEvent(EVENT_REPORT_MOCK_LOCATION,
452                 0, GetTimeIntervalMock() * EVENT_INTERVAL_UNITE);
453         }
454     } else {
455         ClearLocationMock();
456         mockLocationIndex_ = 0;
457     }
458 }
459 
SendReportMockLocationEvent()460 void NetworkAbility::SendReportMockLocationEvent()
461 {
462     if (networkHandler_ == nullptr) {
463         return;
464     }
465     networkHandler_->SendHighPriorityEvent(EVENT_REPORT_MOCK_LOCATION, 0, 0);
466 }
467 
ReportMockedLocation(const std::shared_ptr<Location> location)468 int32_t NetworkAbility::ReportMockedLocation(const std::shared_ptr<Location> location)
469 {
470     if ((IsLocationMocked() && !location->GetIsFromMock()) ||
471         (!IsLocationMocked() && location->GetIsFromMock())) {
472         LBSLOGE(NETWORK, "location mock is enabled, do not report network location!");
473         return ERR_OK;
474     }
475     location->SetTimeSinceBoot(CommonUtils::GetSinceBootTime());
476     location->SetTimeStamp(CommonUtils::GetCurrentTimeStamp() * MICRO_PER_MILLI);
477     location->SetLocationSourceType(LocationSourceType::NETWORK_TYPE);
478     ReportLocationInfo(NETWORK_ABILITY, location);
479 #ifdef FEATURE_PASSIVE_SUPPORT
480     ReportLocationInfo(PASSIVE_ABILITY, location);
481 #endif
482     return ERR_OK;
483 }
484 
SaDumpInfo(std::string & result)485 void NetworkAbility::SaDumpInfo(std::string& result)
486 {
487     result += "Network Location enable status: false";
488     result += "\n";
489 }
490 
Dump(int32_t fd,const std::vector<std::u16string> & args)491 int32_t NetworkAbility::Dump(int32_t fd, const std::vector<std::u16string>& args)
492 {
493     std::vector<std::string> vecArgs;
494     std::transform(args.begin(), args.end(), std::back_inserter(vecArgs), [](const std::u16string &arg) {
495         return Str16ToStr8(arg);
496     });
497 
498     LocationDumper dumper;
499     std::string result;
500     dumper.NetWorkDump(SaDumpInfo, vecArgs, result);
501     if (!SaveStringToFd(fd, result)) {
502         LBSLOGE(NETWORK, "Network save string to fd failed!");
503         return ERR_OK;
504     }
505     return ERR_OK;
506 }
507 
SendMessage(uint32_t code,MessageParcel & data,MessageParcel & reply)508 void NetworkAbility::SendMessage(uint32_t code, MessageParcel &data, MessageParcel &reply)
509 {
510     if (networkHandler_ == nullptr) {
511         reply.WriteInt32(ERRCODE_SERVICE_UNAVAILABLE);
512         return;
513     }
514     switch (code) {
515         case static_cast<uint32_t>(NetworkInterfaceCode::SEND_LOCATION_REQUEST): {
516             std::unique_ptr<WorkRecord> workrecord = WorkRecord::Unmarshalling(data);
517             AppExecFwk::InnerEvent::Pointer event = AppExecFwk::InnerEvent::Get(code, workrecord);
518             if (networkHandler_->SendEvent(event)) {
519                 reply.WriteInt32(ERRCODE_SUCCESS);
520             } else {
521                 reply.WriteInt32(ERRCODE_SERVICE_UNAVAILABLE);
522             }
523             break;
524         }
525         case static_cast<uint32_t>(NetworkInterfaceCode::SET_MOCKED_LOCATIONS): {
526             if (!IsMockEnabled()) {
527                 reply.WriteInt32(LOCATION_ERRCODE_NOT_SUPPORTED);
528                 break;
529             }
530             int timeInterval = data.ReadInt32();
531             int locationSize = data.ReadInt32();
532             timeInterval = timeInterval < 0 ? 1 : timeInterval;
533             locationSize = locationSize > INPUT_ARRAY_LEN_MAX ? INPUT_ARRAY_LEN_MAX :
534                 locationSize;
535             std::shared_ptr<std::vector<std::shared_ptr<Location>>> vcLoc =
536                 std::make_shared<std::vector<std::shared_ptr<Location>>>();
537             for (int i = 0; i < locationSize; i++) {
538                 vcLoc->push_back(Location::UnmarshallingShared(data));
539             }
540             AppExecFwk::InnerEvent::Pointer event =
541                 AppExecFwk::InnerEvent::Get(code, vcLoc, timeInterval);
542             if (networkHandler_->SendEvent(event)) {
543                 reply.WriteInt32(ERRCODE_SUCCESS);
544             } else {
545                 reply.WriteInt32(ERRCODE_SERVICE_UNAVAILABLE);
546             }
547             break;
548         }
549         default:
550             break;
551     }
552 }
553 
RegisterNlpServiceDeathRecipient()554 void NetworkAbility::RegisterNlpServiceDeathRecipient()
555 {
556     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
557     if (nlpServiceProxy_ == nullptr) {
558         LBSLOGE(NETWORK, "%{public}s: nlpServiceProxy_ is nullptr", __func__);
559         return;
560     }
561     if (nlpServiceRecipient_ == nullptr) {
562         nlpServiceRecipient_ = sptr<NlpServiceDeathRecipient>(new (std::nothrow) NlpServiceDeathRecipient());
563     }
564     nlpServiceProxy_->AddDeathRecipient(nlpServiceRecipient_);
565     LBSLOGI(NETWORK, "%{public}s: success", __func__);
566 }
567 
UnregisterNlpServiceDeathRecipient()568 void NetworkAbility::UnregisterNlpServiceDeathRecipient()
569 {
570     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
571     LBSLOGI(NETWORK, "UnRegisterNLPServiceDeathRecipient enter");
572     if (nlpServiceProxy_ == nullptr) {
573         LBSLOGE(NETWORK, "%{public}s: nlpServiceProxy_ is nullptr", __func__);
574         return;
575     }
576     if (nlpServiceRecipient_ != nullptr) {
577         nlpServiceProxy_->RemoveDeathRecipient(nlpServiceRecipient_);
578         nlpServiceRecipient_ = nullptr;
579     }
580 }
581 
IsConnect()582 bool NetworkAbility::IsConnect()
583 {
584     std::unique_lock<ffrt::mutex> uniqueLock(nlpServiceMutex_);
585     return nlpServiceProxy_ != nullptr;
586 }
587 
RestartNlpRequests()588 void NetworkAbility::RestartNlpRequests()
589 {
590     if (GetRequestNum() > 0) {
591         if (networkHandler_ != nullptr) {
592             networkHandler_->SendHighPriorityEvent(EVENT_RESTART_ALL_LOCATION_REQUEST, 0, DELAY_RESTART_MS);
593             LBSLOGI(NETWORK, "CheckNetworkRequests needRecoverRequests");
594         }
595     }
596 }
597 
NetworkHandler(const std::shared_ptr<AppExecFwk::EventRunner> & runner)598 NetworkHandler::NetworkHandler(const std::shared_ptr<AppExecFwk::EventRunner>& runner) : EventHandler(runner)
599 {
600     InitNetworkEventProcessMap();
601 }
602 
~NetworkHandler()603 NetworkHandler::~NetworkHandler() {}
604 
InitNetworkEventProcessMap()605 void NetworkHandler::InitNetworkEventProcessMap()
606 {
607     if (networkEventProcessMap_.size() != 0) {
608         return;
609     }
610     networkEventProcessMap_[static_cast<uint32_t>(EVENT_REPORT_MOCK_LOCATION)] =
611         [this](const AppExecFwk::InnerEvent::Pointer& event) { HandleReportLocationMock(event); };
612     networkEventProcessMap_[static_cast<uint32_t>(EVENT_RESTART_ALL_LOCATION_REQUEST)] =
613         [this](const AppExecFwk::InnerEvent::Pointer& event) { HandleRestartAllLocationRequests(event); };
614     networkEventProcessMap_[static_cast<uint32_t>(EVENT_STOP_ALL_LOCATION_REQUEST)] =
615         [this](const AppExecFwk::InnerEvent::Pointer& event) { HandleStopAllLocationRequests(event); };
616     networkEventProcessMap_[static_cast<uint32_t>(EVENT_DISCONNECT_SERVICES)] =
617         [this](const AppExecFwk::InnerEvent::Pointer& event) { HandleClearServiceEvent(event); };
618     networkEventProcessMap_[static_cast<uint32_t>(NetworkInterfaceCode::SEND_LOCATION_REQUEST)] =
619         [this](const AppExecFwk::InnerEvent::Pointer& event) { HandleLocationRequest(event); };
620     networkEventProcessMap_[static_cast<uint32_t>(NetworkInterfaceCode::SET_MOCKED_LOCATIONS)] =
621         [this](const AppExecFwk::InnerEvent::Pointer& event) { HandleSetMocked(event); };
622 }
623 
ProcessEvent(const AppExecFwk::InnerEvent::Pointer & event)624 void NetworkHandler::ProcessEvent(const AppExecFwk::InnerEvent::Pointer& event)
625 {
626     uint32_t eventId = event->GetInnerEventId();
627     LBSLOGD(NETWORK, "ProcessEvent event:%{public}d", eventId);
628 
629     auto handleFunc = networkEventProcessMap_.find(eventId);
630     if (handleFunc != networkEventProcessMap_.end() && handleFunc->second != nullptr) {
631         auto memberFunc = handleFunc->second;
632 #ifdef LOCATION_HICOLLIE_ENABLE
633         int tid = gettid();
634         std::string moduleName = "NetworkHandler";
635         XCollieCallback callbackFunc = [moduleName, eventId, tid](void *) {
636             LBSLOGE(NETWORK, "TimeoutCallback tid:%{public}d moduleName:%{public}s excute eventId:%{public}u timeout.",
637                 tid, moduleName.c_str(), eventId);
638         };
639         std::string dfxInfo = moduleName + "_" + std::to_string(eventId) + "_" + std::to_string(tid);
640         int timerId = HiviewDFX::XCollie::GetInstance().SetTimer(dfxInfo, TIMEOUT_WATCHDOG, callbackFunc, nullptr,
641             HiviewDFX::XCOLLIE_FLAG_LOG|HiviewDFX::XCOLLIE_FLAG_RECOVERY);
642         memberFunc(event);
643         HiviewDFX::XCollie::GetInstance().CancelTimer(timerId);
644 #else
645         memberFunc(event);
646 #endif
647     }
648     auto networkAbility = NetworkAbility::GetInstance();
649     networkAbility->UnloadNetworkSystemAbility();
650 }
651 
HandleReportLocationMock(const AppExecFwk::InnerEvent::Pointer & event)652 void NetworkHandler::HandleReportLocationMock(const AppExecFwk::InnerEvent::Pointer& event)
653 {
654     auto networkAbility = NetworkAbility::GetInstance();
655     networkAbility->ProcessReportLocationMock();
656 }
657 
HandleRestartAllLocationRequests(const AppExecFwk::InnerEvent::Pointer & event)658 void NetworkHandler::HandleRestartAllLocationRequests(const AppExecFwk::InnerEvent::Pointer& event)
659 {
660     auto networkAbility = NetworkAbility::GetInstance();
661     networkAbility->RestartAllLocationRequests();
662 }
663 
HandleStopAllLocationRequests(const AppExecFwk::InnerEvent::Pointer & event)664 void NetworkHandler::HandleStopAllLocationRequests(const AppExecFwk::InnerEvent::Pointer& event)
665 {
666     auto networkAbility = NetworkAbility::GetInstance();
667     networkAbility->StopAllLocationRequests();
668 }
669 
HandleLocationRequest(const AppExecFwk::InnerEvent::Pointer & event)670 void NetworkHandler::HandleLocationRequest(const AppExecFwk::InnerEvent::Pointer& event)
671 {
672     std::unique_ptr<WorkRecord> workrecord = event->GetUniqueObject<WorkRecord>();
673     if (workrecord != nullptr) {
674         auto networkAbility = NetworkAbility::GetInstance();
675         networkAbility->LocationRequest(*workrecord);
676     }
677 }
678 
HandleClearServiceEvent(const AppExecFwk::InnerEvent::Pointer & event)679 void NetworkHandler::HandleClearServiceEvent(const AppExecFwk::InnerEvent::Pointer& event)
680 {
681     auto networkAbility = NetworkAbility::GetInstance();
682     networkAbility->ClearServiceProxy();
683 }
684 
HandleSetMocked(const AppExecFwk::InnerEvent::Pointer & event)685 void NetworkHandler::HandleSetMocked(const AppExecFwk::InnerEvent::Pointer& event)
686 {
687     auto networkAbility = NetworkAbility::GetInstance();
688     int timeInterval = event->GetParam();
689     auto vcLoc = event->GetSharedObject<std::vector<std::shared_ptr<Location>>>();
690     if (vcLoc != nullptr) {
691         std::vector<std::shared_ptr<Location>> mockLocations;
692         for (auto it = vcLoc->begin(); it != vcLoc->end(); ++it) {
693             mockLocations.push_back(*it);
694         }
695         networkAbility->SetMocked(timeInterval, mockLocations);
696     }
697 }
698 
NlpServiceDeathRecipient()699 NlpServiceDeathRecipient::NlpServiceDeathRecipient()
700 {
701 }
702 
~NlpServiceDeathRecipient()703 NlpServiceDeathRecipient::~NlpServiceDeathRecipient()
704 {
705 }
706 
OnRemoteDied(const wptr<IRemoteObject> & remote)707 void NlpServiceDeathRecipient::OnRemoteDied(const wptr<IRemoteObject> &remote)
708 {
709     auto networkAbility = NetworkAbility::GetInstance();
710     if (networkAbility == nullptr) {
711         LBSLOGE(NETWORK, "OnRemoteDied: NetworkAbility is nullptr");
712         return;
713     }
714     networkAbility->ResetServiceProxy();
715     networkAbility->RestartNlpRequests();
716 }
717 } // namespace Location
718 } // namespace OHOS
719 #endif // FEATURE_NETWORK_SUPPORT
720