• 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 #include "fusion_controller.h"
17 #include "system_ability_definition.h"
18 #include "common_utils.h"
19 #include "constant_definition.h"
20 #include "location_log.h"
21 #ifdef FEATURE_NETWORK_SUPPORT
22 #include "network_ability_proxy.h"
23 #endif
24 
25 namespace OHOS {
26 namespace Location {
27 const uint32_t FUSION_DEFAULT_FLAG = 0;
28 const uint32_t FUSION_BASE_FLAG = 1;
29 const uint32_t REPORT_FUSED_LOCATION_FLAG = FUSION_BASE_FLAG;
30 
31 #ifdef FEATURE_NETWORK_SUPPORT
32 const uint32_t QUICK_FIX_FLAG = FUSION_BASE_FLAG << 1;
33 const uint32_t NETWORK_SELF_REQUEST = 4;
34 #endif
35 const long NANOS_PER_MILLI = 1000000L;
36 const long MAX_LOCATION_COMPARISON_MS = 20 * SEC_TO_MILLI_SEC;
37 
ActiveFusionStrategies(int type)38 void FusionController::ActiveFusionStrategies(int type)
39 {
40     if (needReset_) {
41         fusedFlag_ = FUSION_DEFAULT_FLAG;
42         needReset_ = false;
43     }
44     switch (type) {
45         case SCENE_NAVIGATION:
46         case SCENE_TRAJECTORY_TRACKING:
47             break;
48         case PRIORITY_FAST_FIRST_FIX:
49             fusedFlag_ = fusedFlag_ | REPORT_FUSED_LOCATION_FLAG;
50             break;
51         default:
52             break;
53     }
54 }
55 
Process(std::string abilityName)56 void FusionController::Process(std::string abilityName)
57 {
58     needReset_ = true;
59     if (GNSS_ABILITY.compare(abilityName) != 0) {
60         return;
61     }
62     LBSLOGD(FUSION_CONTROLLER, "fused flag:%{public}u", fusedFlag_);
63 #ifdef FEATURE_NETWORK_SUPPORT
64     RequestQuickFix(fusedFlag_ & QUICK_FIX_FLAG);
65 #endif
66 }
67 
FuseResult(std::string abilityName,const std::unique_ptr<Location> & location)68 void FusionController::FuseResult(std::string abilityName, const std::unique_ptr<Location>& location)
69 {
70     if (GNSS_ABILITY.compare(abilityName) == 0) {
71 #ifdef FEATURE_NETWORK_SUPPORT
72         RequestQuickFix(false);
73 #endif
74     }
75 }
76 
77 #ifdef FEATURE_NETWORK_SUPPORT
RequestQuickFix(bool state)78 void FusionController::RequestQuickFix(bool state)
79 {
80     sptr<IRemoteObject> remoteObject = CommonUtils::GetRemoteObject(LOCATION_NETWORK_LOCATING_SA_ID);
81     if (remoteObject == nullptr) {
82         LBSLOGW(FUSION_CONTROLLER, "can not get network ability remote object");
83         return;
84     }
85     MessageParcel data;
86     MessageParcel reply;
87     MessageOption option;
88     if (!data.WriteInterfaceToken(NetworkAbilityProxy::GetDescriptor())) {
89         return;
90     }
91     data.WriteBool(state);
92     remoteObject->SendRequest(NETWORK_SELF_REQUEST, data, reply, option);
93 }
94 #endif
95 
chooseBestLocation(const std::unique_ptr<Location> & gnssLocation,const std::unique_ptr<Location> & networkLocation)96 std::unique_ptr<Location> FusionController::chooseBestLocation(const std::unique_ptr<Location>& gnssLocation,
97     const std::unique_ptr<Location>& networkLocation)
98 {
99     if (gnssLocation == nullptr && networkLocation == nullptr) {
100         return nullptr;
101     }
102     if (gnssLocation == nullptr) {
103         return std::make_unique<Location>(*networkLocation);
104     }
105     if (networkLocation == nullptr) {
106         return std::make_unique<Location>(*gnssLocation);
107     }
108     if (gnssLocation->GetTimeSinceBoot() / NANOS_PER_MILLI +
109         MAX_LOCATION_COMPARISON_MS < networkLocation->GetTimeSinceBoot() / NANOS_PER_MILLI) {
110         return std::make_unique<Location>(*networkLocation);
111     }
112     return std::make_unique<Location>(*gnssLocation);
113 }
114 
GetFuseLocation(std::string abilityName,const std::unique_ptr<Location> & location)115 std::unique_ptr<Location> FusionController::GetFuseLocation(std::string abilityName,
116     const std::unique_ptr<Location>& location)
117 {
118     LBSLOGD(FUSION_CONTROLLER, " GetFuseLocation enter");
119     if (GNSS_ABILITY.compare(abilityName) == 0) {
120         gnssLocation_ = std::make_unique<Location>(*location);
121     }
122     if (NETWORK_ABILITY.compare(abilityName) == 0) {
123         networkLocation_ = std::make_unique<Location>(*location);
124     }
125     auto bestLocation = chooseBestLocation(gnssLocation_, networkLocation_);
126     if (LocationEqual(bestLocation, fuseLocation_)) {
127         return nullptr;
128     }
129     if (bestLocation != nullptr) {
130         fuseLocation_ = std::make_unique<Location>(*bestLocation);
131     }
132     if (fuseLocation_ == nullptr) {
133         return nullptr;
134     } else {
135         return std::make_unique<Location>(*fuseLocation_);
136     }
137 }
138 
LocationEqual(const std::unique_ptr<Location> & bestLocation,const std::unique_ptr<Location> & fuseLocation)139 bool FusionController::LocationEqual(const std::unique_ptr<Location>& bestLocation,
140     const std::unique_ptr<Location>& fuseLocation)
141 {
142     if (fuseLocation_ == nullptr || bestLocation == nullptr) {
143         LBSLOGE(FUSION_CONTROLLER, "fuseLocation_ or fuseLocation is nullptr");
144         return false;
145     }
146     if (bestLocation->GetLatitude() == fuseLocation->GetLatitude() &&
147         bestLocation->GetLongitude() == fuseLocation->GetLongitude() &&
148         bestLocation->GetAltitude() == fuseLocation->GetAltitude() &&
149         bestLocation->GetAccuracy() == fuseLocation->GetAccuracy() &&
150         bestLocation->GetSpeed() == fuseLocation->GetSpeed() &&
151         bestLocation->GetDirection() == fuseLocation->GetDirection() &&
152         bestLocation->GetTimeStamp() == fuseLocation->GetTimeStamp() &&
153         bestLocation->GetTimeSinceBoot() == fuseLocation->GetTimeSinceBoot() &&
154         bestLocation->GetAdditions() == fuseLocation->GetAdditions() &&
155         bestLocation->GetAdditionSize() == fuseLocation->GetAdditionSize() &&
156         bestLocation->GetIsFromMock() == fuseLocation->GetIsFromMock() &&
157         bestLocation->GetSourceType() == fuseLocation->GetSourceType() &&
158         bestLocation->GetFloorNo() == fuseLocation->GetFloorNo() &&
159         bestLocation->GetFloorAccuracy() == fuseLocation->GetFloorAccuracy()) {
160         return true;
161     }
162     return false;
163 }
164 } // namespace Location
165 } // namespace OHOS