feat: 更新GPS功能,添加自定义位置支持,调整权限和配置,移除旧服务
This commit is contained in:
66
gps/Android.bp
Normal file
66
gps/Android.bp
Normal file
@@ -0,0 +1,66 @@
|
|||||||
|
// Copyright (C) 2023 The Android Open Source Project
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
|
||||||
|
cc_library_shared {
|
||||||
|
name: "libredroid_gps_jni",
|
||||||
|
|
||||||
|
srcs: [
|
||||||
|
"com_android_server_location_GnssLocationProvider.cpp",
|
||||||
|
],
|
||||||
|
|
||||||
|
cflags: [
|
||||||
|
"-Wall",
|
||||||
|
"-Werror",
|
||||||
|
"-Wextra",
|
||||||
|
"-std=c++17",
|
||||||
|
],
|
||||||
|
|
||||||
|
shared_libs: [
|
||||||
|
"libandroid_runtime",
|
||||||
|
"libbinder",
|
||||||
|
"libcutils",
|
||||||
|
"liblog",
|
||||||
|
"libnativehelper",
|
||||||
|
"libutils",
|
||||||
|
"libhardware",
|
||||||
|
"libhardware_legacy",
|
||||||
|
"libhidlbase",
|
||||||
|
"libhidltransport",
|
||||||
|
"android.hardware.gnss@1.0",
|
||||||
|
"android.hardware.gnss@1.1",
|
||||||
|
"android.hardware.gnss@2.0",
|
||||||
|
"android.hardware.gnss@2.1",
|
||||||
|
"android.hardware.gnss-V1-ndk",
|
||||||
|
],
|
||||||
|
|
||||||
|
static_libs: [
|
||||||
|
"libc++fs",
|
||||||
|
],
|
||||||
|
|
||||||
|
header_libs: [
|
||||||
|
"jni_headers",
|
||||||
|
"libandroid_runtime_headers",
|
||||||
|
],
|
||||||
|
|
||||||
|
include_dirs: [
|
||||||
|
"frameworks/base/services/core/jni",
|
||||||
|
"frameworks/base/core/jni",
|
||||||
|
],
|
||||||
|
|
||||||
|
vendor: true,
|
||||||
|
|
||||||
|
compile_multilib: "both",
|
||||||
|
|
||||||
|
relative_install_path: "hw",
|
||||||
|
}
|
||||||
196
gps/BUILD_GUIDE.md
Normal file
196
gps/BUILD_GUIDE.md
Normal file
@@ -0,0 +1,196 @@
|
|||||||
|
# Redroid 自定义GPS位置构建指南
|
||||||
|
|
||||||
|
本指南详细说明如何构建和使用Redroid的自定义GPS位置功能。
|
||||||
|
|
||||||
|
## 📋 修改的文件列表
|
||||||
|
|
||||||
|
### 1. 核心实现文件
|
||||||
|
- `gps/com_android_server_location_GnssLocationProvider.cpp` - 主要的JNI实现
|
||||||
|
- `gps/Android.bp` - 编译配置文件(新增)
|
||||||
|
- `gps/init.redroid.gps.sh` - GPS初始化脚本
|
||||||
|
|
||||||
|
### 2. 集成配置文件
|
||||||
|
- `vendor.mk` - 添加GPS JNI库到产品包
|
||||||
|
- `redroid.legacy.rc` - 调整GPS目录权限
|
||||||
|
|
||||||
|
## 🔧 构建步骤
|
||||||
|
|
||||||
|
### 1. 准备源码
|
||||||
|
确保所有修改的文件都在正确的位置:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
vendor/redroid/
|
||||||
|
├── gps/
|
||||||
|
│ ├── com_android_server_location_GnssLocationProvider.cpp
|
||||||
|
│ ├── Android.bp
|
||||||
|
│ └── init.redroid.gps.sh
|
||||||
|
├── vendor.mk
|
||||||
|
└── redroid.legacy.rc
|
||||||
|
```
|
||||||
|
|
||||||
|
### 2. 编译系统
|
||||||
|
在Android源码根目录执行:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 设置环境
|
||||||
|
source build/envsetup.sh
|
||||||
|
|
||||||
|
# 选择目标(根据你的设备调整)
|
||||||
|
lunch aosp_arm64-eng
|
||||||
|
|
||||||
|
# 编译GPS JNI库
|
||||||
|
m libredroid_gps_jni
|
||||||
|
|
||||||
|
# 或者编译整个vendor模块
|
||||||
|
m vendor-redroid
|
||||||
|
```
|
||||||
|
|
||||||
|
### 3. 验证编译结果
|
||||||
|
检查编译输出:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 检查生成的库文件
|
||||||
|
ls -la out/target/product/*/vendor/lib*/hw/libredroid_gps_jni.so
|
||||||
|
```
|
||||||
|
|
||||||
|
## 🚀 部署和使用
|
||||||
|
|
||||||
|
### 1. 系统启动
|
||||||
|
当Android系统启动时,`redroid.legacy.rc`会自动:
|
||||||
|
- 创建`/data/vendor/gps`目录
|
||||||
|
- 执行`init.redroid.gps.sh`脚本
|
||||||
|
- 设置正确的权限
|
||||||
|
|
||||||
|
### 2. 默认位置
|
||||||
|
系统会创建默认的GPS位置文件:
|
||||||
|
```bash
|
||||||
|
/data/vendor/gps/custom_location.txt
|
||||||
|
```
|
||||||
|
|
||||||
|
默认坐标(杭州):`30.281026,120.019348`
|
||||||
|
|
||||||
|
### 3. 自定义位置
|
||||||
|
修改GPS位置只需编辑文件:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 使用adb连接设备
|
||||||
|
adb shell
|
||||||
|
|
||||||
|
# 修改GPS位置(例如:北京天安门)
|
||||||
|
echo "39.904989,116.405285" > /data/vendor/gps/custom_location.txt
|
||||||
|
|
||||||
|
# 或者使用adb push
|
||||||
|
echo "39.904989,116.405285" > custom_location.txt
|
||||||
|
adb push custom_location.txt /data/vendor/gps/
|
||||||
|
```
|
||||||
|
|
||||||
|
### 4. 实时生效
|
||||||
|
- 修改文件后,新的GPS位置会在下次位置请求时自动生效
|
||||||
|
- 无需重启系统或GPS服务
|
||||||
|
- 系统会检测文件修改时间并自动加载新坐标
|
||||||
|
|
||||||
|
## 📍 支持的坐标格式
|
||||||
|
|
||||||
|
### 逗号分隔格式
|
||||||
|
```
|
||||||
|
纬度,经度
|
||||||
|
39.904989,116.405285
|
||||||
|
```
|
||||||
|
|
||||||
|
### 空格分隔格式
|
||||||
|
```
|
||||||
|
纬度 经度
|
||||||
|
39.904989 116.405285
|
||||||
|
```
|
||||||
|
|
||||||
|
### 坐标范围
|
||||||
|
- 纬度:-90° 到 +90°
|
||||||
|
- 经度:-180° 到 +180°
|
||||||
|
|
||||||
|
## 🧪 测试验证
|
||||||
|
|
||||||
|
### 1. 查看日志
|
||||||
|
```bash
|
||||||
|
# 查看GPS相关日志
|
||||||
|
adb logcat | grep -i gnss
|
||||||
|
adb logcat | grep -i "custom.*gps"
|
||||||
|
|
||||||
|
# 期望看到的日志:
|
||||||
|
# I/GnssLocationProviderJni: Custom GPS location loaded: lat=39.904989, lon=116.405285
|
||||||
|
# I/GnssLocationProviderJni: Using custom GPS location: lat=39.904989, lon=116.405285
|
||||||
|
```
|
||||||
|
|
||||||
|
### 2. 使用GPS应用
|
||||||
|
- 打开地图应用(如Google Maps)
|
||||||
|
- 启用位置服务
|
||||||
|
- 应该显示自定义的GPS位置
|
||||||
|
|
||||||
|
### 3. 验证位置变更
|
||||||
|
```bash
|
||||||
|
# 修改位置
|
||||||
|
echo "31.239666,121.499809" > /data/vendor/gps/custom_location.txt
|
||||||
|
|
||||||
|
# 在地图应用中观察位置变化
|
||||||
|
```
|
||||||
|
|
||||||
|
## 🔍 故障排除
|
||||||
|
|
||||||
|
### 编译错误
|
||||||
|
1. 确保Android编译环境正确设置
|
||||||
|
2. 检查依赖库是否存在
|
||||||
|
3. 验证Android.bp语法
|
||||||
|
|
||||||
|
### 运行时错误
|
||||||
|
1. 检查文件权限:
|
||||||
|
```bash
|
||||||
|
ls -la /data/vendor/gps/
|
||||||
|
```
|
||||||
|
|
||||||
|
2. 验证文件格式:
|
||||||
|
```bash
|
||||||
|
cat /data/vendor/gps/custom_location.txt
|
||||||
|
```
|
||||||
|
|
||||||
|
3. 查看详细日志:
|
||||||
|
```bash
|
||||||
|
adb logcat -v threadtime | grep -E "(Gnss|GPS)"
|
||||||
|
```
|
||||||
|
|
||||||
|
### 权限问题
|
||||||
|
如果遇到权限错误:
|
||||||
|
```bash
|
||||||
|
# 重新设置权限
|
||||||
|
adb shell
|
||||||
|
chown system:system /data/vendor/gps/custom_location.txt
|
||||||
|
chmod 644 /data/vendor/gps/custom_location.txt
|
||||||
|
```
|
||||||
|
|
||||||
|
## 📱 兼容性
|
||||||
|
|
||||||
|
### Android版本
|
||||||
|
- 支持Android 8.0+(API 26+)
|
||||||
|
- 测试过的版本:Android 11、12、13
|
||||||
|
|
||||||
|
### 架构支持
|
||||||
|
- ARM64
|
||||||
|
- ARM32
|
||||||
|
- x86_64(通过Android.bp的compile_multilib配置)
|
||||||
|
|
||||||
|
## 🔄 回退到默认GPS
|
||||||
|
|
||||||
|
如果要禁用自定义GPS功能:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 删除自定义位置文件
|
||||||
|
rm /data/vendor/gps/custom_location.txt
|
||||||
|
|
||||||
|
# 系统会自动回退到默认GPS行为
|
||||||
|
```
|
||||||
|
|
||||||
|
## 📞 技术支持
|
||||||
|
|
||||||
|
如果遇到问题,请提供:
|
||||||
|
1. Android版本和设备信息
|
||||||
|
2. 完整的logcat日志
|
||||||
|
3. 文件权限和内容截图
|
||||||
|
4. 具体的错误现象描述
|
||||||
1231
gps/com_android_server_location_GnssLocationProvider.cpp
Normal file
1231
gps/com_android_server_location_GnssLocationProvider.cpp
Normal file
File diff suppressed because it is too large
Load Diff
@@ -1,69 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
// package {
|
|
||||||
// // See: http://go/android-license-faq
|
|
||||||
// // A large-scale-change added 'default_applicable_licenses' to import
|
|
||||||
// // all of the 'license_kinds' from "hardware_interfaces_license"
|
|
||||||
// // to get the below license kinds:
|
|
||||||
// // SPDX-license-identifier-Apache-2.0
|
|
||||||
// default_applicable_licenses: ["hardware_interfaces_license"],
|
|
||||||
// }
|
|
||||||
|
|
||||||
cc_binary {
|
|
||||||
name: "android.hardware.gnss-service",
|
|
||||||
relative_install_path: "hw",
|
|
||||||
// init_rc: [
|
|
||||||
// "gnss-xxx-service.rc",
|
|
||||||
// ],
|
|
||||||
vintf_fragments: [
|
|
||||||
"gnss-xxx.xml",
|
|
||||||
"gnss-xxx@2.1-service.xml",
|
|
||||||
],
|
|
||||||
vendor: true,
|
|
||||||
cflags: [
|
|
||||||
"-Wall",
|
|
||||||
"-Wextra",
|
|
||||||
],
|
|
||||||
shared_libs: [
|
|
||||||
"libbase",
|
|
||||||
"libcutils",
|
|
||||||
"libbinder_ndk",
|
|
||||||
"libhidlbase",
|
|
||||||
"libutils",
|
|
||||||
"liblog",
|
|
||||||
"android.hardware.gnss@2.1",
|
|
||||||
"android.hardware.gnss@2.0",
|
|
||||||
"android.hardware.gnss@1.1",
|
|
||||||
"android.hardware.gnss@1.0",
|
|
||||||
"android.hardware.gnss.measurement_corrections@1.1",
|
|
||||||
"android.hardware.gnss.measurement_corrections@1.0",
|
|
||||||
"android.hardware.gnss.visibility_control@1.0",
|
|
||||||
"android.hardware.gnss-V1-ndk_platform",
|
|
||||||
],
|
|
||||||
srcs: [
|
|
||||||
"Gnss.cpp",
|
|
||||||
"GnssHidlHal.cpp",
|
|
||||||
"GnssPowerIndication.cpp",
|
|
||||||
"GnssPsds.cpp",
|
|
||||||
"GnssConfiguration.cpp",
|
|
||||||
"GnssMeasurementInterface.cpp",
|
|
||||||
"service.cpp",
|
|
||||||
],
|
|
||||||
static_libs: [
|
|
||||||
"android.hardware.gnss@common-default-lib2",
|
|
||||||
],
|
|
||||||
}
|
|
||||||
@@ -1,91 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssAidl"
|
|
||||||
|
|
||||||
#include "Gnss.h"
|
|
||||||
#include <log/log.h>
|
|
||||||
#include "GnssConfiguration.h"
|
|
||||||
#include "GnssMeasurementInterface.h"
|
|
||||||
#include "GnssPsds.h"
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
std::shared_ptr<IGnssCallback> Gnss::sGnssCallback = nullptr;
|
|
||||||
|
|
||||||
ndk::ScopedAStatus Gnss::setCallback(const std::shared_ptr<IGnssCallback>& callback) {
|
|
||||||
ALOGD("Gnss::setCallback");
|
|
||||||
if (callback == nullptr) {
|
|
||||||
ALOGE("%s: Null callback ignored", __func__);
|
|
||||||
return ndk::ScopedAStatus::fromExceptionCode(STATUS_INVALID_OPERATION);
|
|
||||||
}
|
|
||||||
|
|
||||||
sGnssCallback = callback;
|
|
||||||
|
|
||||||
int capabilities = (int)(IGnssCallback::CAPABILITY_SATELLITE_BLOCKLIST |
|
|
||||||
IGnssCallback::CAPABILITY_SATELLITE_PVT |
|
|
||||||
IGnssCallback::CAPABILITY_CORRELATION_VECTOR);
|
|
||||||
|
|
||||||
auto status = sGnssCallback->gnssSetCapabilitiesCb(capabilities);
|
|
||||||
if (!status.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback.gnssSetCapabilities", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus Gnss::close() {
|
|
||||||
ALOGD("Gnss::close");
|
|
||||||
sGnssCallback = nullptr;
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus Gnss::getExtensionPsds(std::shared_ptr<IGnssPsds>* iGnssPsds) {
|
|
||||||
ALOGD("Gnss::getExtensionPsds");
|
|
||||||
*iGnssPsds = SharedRefBase::make<GnssPsds>();
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus Gnss::getExtensionGnssConfiguration(
|
|
||||||
std::shared_ptr<IGnssConfiguration>* iGnssConfiguration) {
|
|
||||||
ALOGD("Gnss::getExtensionGnssConfiguration");
|
|
||||||
if (mGnssConfiguration == nullptr) {
|
|
||||||
mGnssConfiguration = SharedRefBase::make<GnssConfiguration>();
|
|
||||||
}
|
|
||||||
*iGnssConfiguration = mGnssConfiguration;
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus Gnss::getExtensionGnssPowerIndication(
|
|
||||||
std::shared_ptr<IGnssPowerIndication>* iGnssPowerIndication) {
|
|
||||||
ALOGD("Gnss::getExtensionGnssPowerIndication");
|
|
||||||
if (mGnssPowerIndication == nullptr) {
|
|
||||||
mGnssPowerIndication = SharedRefBase::make<GnssPowerIndication>();
|
|
||||||
}
|
|
||||||
|
|
||||||
*iGnssPowerIndication = mGnssPowerIndication;
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus Gnss::getExtensionGnssMeasurement(
|
|
||||||
std::shared_ptr<IGnssMeasurementInterface>* iGnssMeasurement) {
|
|
||||||
ALOGD("Gnss::getExtensionGnssMeasurement");
|
|
||||||
|
|
||||||
*iGnssMeasurement = SharedRefBase::make<GnssMeasurementInterface>();
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,48 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnss.h>
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssConfiguration.h>
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssMeasurementInterface.h>
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssPowerIndication.h>
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssPsds.h>
|
|
||||||
#include "GnssConfiguration.h"
|
|
||||||
#include "GnssPowerIndication.h"
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
class Gnss : public BnGnss {
|
|
||||||
public:
|
|
||||||
ndk::ScopedAStatus setCallback(const std::shared_ptr<IGnssCallback>& callback) override;
|
|
||||||
ndk::ScopedAStatus close() override;
|
|
||||||
ndk::ScopedAStatus getExtensionPsds(std::shared_ptr<IGnssPsds>* iGnssPsds) override;
|
|
||||||
ndk::ScopedAStatus getExtensionGnssConfiguration(
|
|
||||||
std::shared_ptr<IGnssConfiguration>* iGnssConfiguration) override;
|
|
||||||
ndk::ScopedAStatus getExtensionGnssPowerIndication(
|
|
||||||
std::shared_ptr<IGnssPowerIndication>* iGnssPowerIndication) override;
|
|
||||||
ndk::ScopedAStatus getExtensionGnssMeasurement(
|
|
||||||
std::shared_ptr<IGnssMeasurementInterface>* iGnssMeasurement) override;
|
|
||||||
|
|
||||||
std::shared_ptr<GnssConfiguration> mGnssConfiguration;
|
|
||||||
std::shared_ptr<GnssPowerIndication> mGnssPowerIndication;
|
|
||||||
|
|
||||||
private:
|
|
||||||
static std::shared_ptr<IGnssCallback> sGnssCallback;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,52 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssConfigurationAidl"
|
|
||||||
|
|
||||||
#include "GnssConfiguration.h"
|
|
||||||
#include <log/log.h>
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
ndk::ScopedAStatus GnssConfiguration::setBlocklist(const vector<BlocklistedSource>& sourceList) {
|
|
||||||
ALOGD("GnssConfiguration::setBlocklist");
|
|
||||||
std::unique_lock<std::recursive_mutex> lock(mMutex);
|
|
||||||
mBlocklistedConstellationSet.clear();
|
|
||||||
mBlocklistedSourceSet.clear();
|
|
||||||
for (const auto& source : sourceList) {
|
|
||||||
if (source.svid == 0) {
|
|
||||||
// Wildcard blocklist, i.e., blocklist entire constellation.
|
|
||||||
mBlocklistedConstellationSet.insert(source.constellation);
|
|
||||||
} else {
|
|
||||||
mBlocklistedSourceSet.insert(source);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool GnssConfiguration::isBlocklistedV2_1(const GnssSvInfoV2_1& gnssSvInfo) const {
|
|
||||||
std::unique_lock<std::recursive_mutex> lock(mMutex);
|
|
||||||
if (mBlocklistedConstellationSet.find(static_cast<GnssConstellationType>(
|
|
||||||
gnssSvInfo.v2_0.constellation)) != mBlocklistedConstellationSet.end()) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
BlocklistedSource source = {
|
|
||||||
.constellation = static_cast<GnssConstellationType>(gnssSvInfo.v2_0.constellation),
|
|
||||||
.svid = gnssSvInfo.v2_0.v1_0.svid};
|
|
||||||
return (mBlocklistedSourceSet.find(source) != mBlocklistedSourceSet.end());
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,72 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssConfiguration.h>
|
|
||||||
#include <android/hardware/gnss/2.1/IGnssCallback.h>
|
|
||||||
#include <mutex>
|
|
||||||
#include <unordered_set>
|
|
||||||
#include <vector>
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
struct BlocklistedSourceHash {
|
|
||||||
inline int operator()(const BlocklistedSource& source) const {
|
|
||||||
return int(source.constellation) * 1000 + int(source.svid);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct BlocklistedSourceEqual {
|
|
||||||
inline bool operator()(const BlocklistedSource& s1, const BlocklistedSource& s2) const {
|
|
||||||
return (s1.constellation == s2.constellation) && (s1.svid == s2.svid);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
using GnssSvInfoV2_1 = ::android::hardware::gnss::V2_1::IGnssCallback::GnssSvInfo;
|
|
||||||
using std::vector;
|
|
||||||
using BlocklistedSourceSet =
|
|
||||||
std::unordered_set<BlocklistedSource, BlocklistedSourceHash, BlocklistedSourceEqual>;
|
|
||||||
using BlocklistedConstellationSet =
|
|
||||||
std::unordered_set<android::hardware::gnss::GnssConstellationType>;
|
|
||||||
|
|
||||||
struct GnssConfiguration : public BnGnssConfiguration {
|
|
||||||
public:
|
|
||||||
ndk::ScopedAStatus setSuplVersion(int) override { return ndk::ScopedAStatus::ok(); }
|
|
||||||
|
|
||||||
ndk::ScopedAStatus setSuplMode(int) override { return ndk::ScopedAStatus::ok(); }
|
|
||||||
|
|
||||||
ndk::ScopedAStatus setLppProfile(int) override { return ndk::ScopedAStatus::ok(); }
|
|
||||||
|
|
||||||
ndk::ScopedAStatus setGlonassPositioningProtocol(int) override {
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus setEmergencySuplPdn(bool) override { return ndk::ScopedAStatus::ok(); }
|
|
||||||
|
|
||||||
ndk::ScopedAStatus setEsExtensionSec(int) override { return ndk::ScopedAStatus::ok(); }
|
|
||||||
|
|
||||||
ndk::ScopedAStatus setBlocklist(const vector<BlocklistedSource>& blocklist) override;
|
|
||||||
|
|
||||||
bool isBlocklistedV2_1(const GnssSvInfoV2_1& gnssSvInfo) const;
|
|
||||||
|
|
||||||
private:
|
|
||||||
BlocklistedSourceSet mBlocklistedSourceSet;
|
|
||||||
BlocklistedConstellationSet mBlocklistedConstellationSet;
|
|
||||||
mutable std::recursive_mutex mMutex;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,65 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssHidlHal"
|
|
||||||
|
|
||||||
#include "GnssHidlHal.h"
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
using GnssSvInfo = ::android::hardware::gnss::V2_1::IGnssCallback::GnssSvInfo;
|
|
||||||
|
|
||||||
GnssHidlHal::GnssHidlHal(const std::shared_ptr<Gnss>& gnssAidl) : mGnssAidl(gnssAidl) {
|
|
||||||
Gnss* iGnss = mGnssAidl.get();
|
|
||||||
std::shared_ptr<IGnssConfiguration> iGnssConfiguration;
|
|
||||||
auto status = iGnss->getExtensionGnssConfiguration(&iGnssConfiguration);
|
|
||||||
if (!status.isOk()) {
|
|
||||||
ALOGE("Failed to getExtensionGnssConfiguration.");
|
|
||||||
} else {
|
|
||||||
mGnssConfigurationAidl = iGnss->mGnssConfiguration;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::shared_ptr<IGnssPowerIndication> iGnssPowerIndication;
|
|
||||||
status = iGnss->getExtensionGnssPowerIndication(&iGnssPowerIndication);
|
|
||||||
if (!status.isOk()) {
|
|
||||||
ALOGE("Failed to getExtensionGnssPowerIndication.");
|
|
||||||
} else {
|
|
||||||
mGnssPowerIndicationAidl = iGnss->mGnssPowerIndication;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
hidl_vec<GnssSvInfo> GnssHidlHal::filterBlocklistedSatellitesV2_1(
|
|
||||||
hidl_vec<GnssSvInfo> gnssSvInfoList) {
|
|
||||||
if (mGnssConfigurationAidl == nullptr) {
|
|
||||||
ALOGE("Handle to AIDL GnssConfiguration is not available.");
|
|
||||||
return gnssSvInfoList;
|
|
||||||
}
|
|
||||||
for (uint32_t i = 0; i < gnssSvInfoList.size(); i++) {
|
|
||||||
if (mGnssConfigurationAidl->isBlocklistedV2_1(gnssSvInfoList[i])) {
|
|
||||||
ALOGD("Blocklisted constellation: %d, svid: %d",
|
|
||||||
(int)gnssSvInfoList[i].v2_0.constellation, gnssSvInfoList[i].v2_0.v1_0.svid);
|
|
||||||
gnssSvInfoList[i].v2_0.v1_0.svFlag &= ~static_cast<uint8_t>(
|
|
||||||
::android::hardware::gnss::V1_0::IGnssCallback::GnssSvFlags::USED_IN_FIX);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return gnssSvInfoList;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssHidlHal::notePowerConsumption() {
|
|
||||||
mGnssPowerIndicationAidl->notePowerConsumption();
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,42 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "Gnss.h"
|
|
||||||
#include "GnssConfiguration.h"
|
|
||||||
#include "v2_1/GnssTemplate.h"
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
class GnssHidlHal : public ::android::hardware::gnss::common::implementation::GnssTemplate<
|
|
||||||
::android::hardware::gnss::V2_1::IGnss> {
|
|
||||||
public:
|
|
||||||
GnssHidlHal(const std::shared_ptr<Gnss>& gnssAidl);
|
|
||||||
|
|
||||||
private:
|
|
||||||
hidl_vec<::android::hardware::gnss::V2_1::IGnssCallback::GnssSvInfo>
|
|
||||||
filterBlocklistedSatellitesV2_1(
|
|
||||||
hidl_vec<::android::hardware::gnss::V2_1::IGnssCallback::GnssSvInfo> gnssSvInfoList)
|
|
||||||
override;
|
|
||||||
void notePowerConsumption() override;
|
|
||||||
|
|
||||||
std::shared_ptr<Gnss> mGnssAidl;
|
|
||||||
std::shared_ptr<GnssConfiguration> mGnssConfigurationAidl;
|
|
||||||
std::shared_ptr<GnssPowerIndication> mGnssPowerIndicationAidl;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,94 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssMeasIfaceAidl"
|
|
||||||
|
|
||||||
#include "GnssMeasurementInterface.h"
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnss.h>
|
|
||||||
#include <log/log.h>
|
|
||||||
#include "Utils.h"
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
using Utils = ::android::hardware::gnss::common::Utils;
|
|
||||||
|
|
||||||
std::shared_ptr<IGnssMeasurementCallback> GnssMeasurementInterface::sCallback = nullptr;
|
|
||||||
|
|
||||||
GnssMeasurementInterface::GnssMeasurementInterface() : mMinIntervalMillis(1000) {}
|
|
||||||
|
|
||||||
GnssMeasurementInterface::~GnssMeasurementInterface() {
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus GnssMeasurementInterface::setCallback(
|
|
||||||
const std::shared_ptr<IGnssMeasurementCallback>& callback, const bool enableFullTracking,
|
|
||||||
const bool enableCorrVecOutputs) {
|
|
||||||
ALOGD("setCallback: enableFullTracking: %d enableCorrVecOutputs: %d", (int)enableFullTracking,
|
|
||||||
(int)enableCorrVecOutputs);
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback = callback;
|
|
||||||
|
|
||||||
if (mIsActive) {
|
|
||||||
ALOGW("GnssMeasurement callback already set. Resetting the callback...");
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
start(enableCorrVecOutputs);
|
|
||||||
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus GnssMeasurementInterface::close() {
|
|
||||||
ALOGD("close");
|
|
||||||
stop();
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback = nullptr;
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssMeasurementInterface::start(const bool enableCorrVecOutputs) {
|
|
||||||
ALOGD("start");
|
|
||||||
mIsActive = true;
|
|
||||||
mThread = std::thread([this, enableCorrVecOutputs]() {
|
|
||||||
while (mIsActive == true) {
|
|
||||||
auto measurement = Utils::getMockMeasurement(enableCorrVecOutputs);
|
|
||||||
this->reportMeasurement(measurement);
|
|
||||||
|
|
||||||
std::this_thread::sleep_for(std::chrono::milliseconds(mMinIntervalMillis));
|
|
||||||
}
|
|
||||||
});
|
|
||||||
mThread.detach();
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssMeasurementInterface::stop() {
|
|
||||||
ALOGD("stop");
|
|
||||||
mIsActive = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssMeasurementInterface::reportMeasurement(const GnssData& data) {
|
|
||||||
ALOGD("reportMeasurement()");
|
|
||||||
std::shared_ptr<IGnssMeasurementCallback> callbackCopy;
|
|
||||||
{
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
if (sCallback == nullptr) {
|
|
||||||
ALOGE("%s: GnssMeasurement::sCallback is null.", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
callbackCopy = sCallback;
|
|
||||||
}
|
|
||||||
callbackCopy->gnssMeasurementCb(data);
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,52 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssMeasurementCallback.h>
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssMeasurementInterface.h>
|
|
||||||
#include <atomic>
|
|
||||||
#include <mutex>
|
|
||||||
#include <thread>
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
struct GnssMeasurementInterface : public BnGnssMeasurementInterface {
|
|
||||||
public:
|
|
||||||
GnssMeasurementInterface();
|
|
||||||
~GnssMeasurementInterface();
|
|
||||||
ndk::ScopedAStatus setCallback(const std::shared_ptr<IGnssMeasurementCallback>& callback,
|
|
||||||
const bool enableFullTracking,
|
|
||||||
const bool enableCorrVecOutputs) override;
|
|
||||||
ndk::ScopedAStatus close() override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
void start(const bool enableCorrVecOutputs);
|
|
||||||
void stop();
|
|
||||||
void reportMeasurement(const GnssData&);
|
|
||||||
|
|
||||||
std::atomic<long> mMinIntervalMillis;
|
|
||||||
std::atomic<bool> mIsActive;
|
|
||||||
std::thread mThread;
|
|
||||||
|
|
||||||
// Guarded by mMutex
|
|
||||||
static std::shared_ptr<IGnssMeasurementCallback> sCallback;
|
|
||||||
|
|
||||||
// Synchronization lock for sCallback
|
|
||||||
mutable std::mutex mMutex;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,68 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssPowerIndicationAidl"
|
|
||||||
|
|
||||||
#include "GnssPowerIndication.h"
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnss.h>
|
|
||||||
#include <log/log.h>
|
|
||||||
#include <utils/SystemClock.h>
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
std::shared_ptr<IGnssPowerIndicationCallback> GnssPowerIndication::sCallback = nullptr;
|
|
||||||
|
|
||||||
ndk::ScopedAStatus GnssPowerIndication::setCallback(
|
|
||||||
const std::shared_ptr<IGnssPowerIndicationCallback>& callback) {
|
|
||||||
ALOGD("setCallback");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback = callback;
|
|
||||||
sCallback->setCapabilitiesCb(IGnssPowerIndicationCallback::CAPABILITY_TOTAL |
|
|
||||||
IGnssPowerIndicationCallback::CAPABILITY_SINGLEBAND_TRACKING |
|
|
||||||
IGnssPowerIndicationCallback::CAPABILITY_MULTIBAND_TRACKING |
|
|
||||||
IGnssPowerIndicationCallback::CAPABILITY_SINGLEBAND_ACQUISITION |
|
|
||||||
IGnssPowerIndicationCallback::CAPABILITY_MULTIBAND_ACQUISITION |
|
|
||||||
IGnssPowerIndicationCallback::CAPABILITY_OTHER_MODES);
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus GnssPowerIndication::requestGnssPowerStats() {
|
|
||||||
ALOGD("requestGnssPowerStats");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
|
|
||||||
ElapsedRealtime elapsedRealtime = {
|
|
||||||
.flags = ElapsedRealtime::HAS_TIMESTAMP_NS | ElapsedRealtime::HAS_TIME_UNCERTAINTY_NS,
|
|
||||||
.timestampNs = ::android::elapsedRealtimeNano(),
|
|
||||||
.timeUncertaintyNs = 1000,
|
|
||||||
};
|
|
||||||
GnssPowerStats gnssPowerStats = {
|
|
||||||
.elapsedRealtime = elapsedRealtime,
|
|
||||||
.totalEnergyMilliJoule = 1.500e+3 + numLocationReported * 22.0,
|
|
||||||
.singlebandTrackingModeEnergyMilliJoule = 0.0,
|
|
||||||
.multibandTrackingModeEnergyMilliJoule = 1.28e+2 + numLocationReported * 4.0,
|
|
||||||
.singlebandAcquisitionModeEnergyMilliJoule = 0.0,
|
|
||||||
.multibandAcquisitionModeEnergyMilliJoule = 3.65e+2 + numLocationReported * 15.0,
|
|
||||||
.otherModesEnergyMilliJoule = {1.232e+2, 3.234e+3},
|
|
||||||
};
|
|
||||||
sCallback->gnssPowerStatsCb(gnssPowerStats);
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssPowerIndication::notePowerConsumption() {
|
|
||||||
numLocationReported++;
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,41 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssPowerIndication.h>
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
struct GnssPowerIndication : public BnGnssPowerIndication {
|
|
||||||
public:
|
|
||||||
ndk::ScopedAStatus setCallback(
|
|
||||||
const std::shared_ptr<IGnssPowerIndicationCallback>& callback) override;
|
|
||||||
ndk::ScopedAStatus requestGnssPowerStats() override;
|
|
||||||
|
|
||||||
void notePowerConsumption();
|
|
||||||
|
|
||||||
private:
|
|
||||||
// Guarded by mMutex
|
|
||||||
static std::shared_ptr<IGnssPowerIndicationCallback> sCallback;
|
|
||||||
|
|
||||||
// Synchronization lock for sCallback
|
|
||||||
mutable std::mutex mMutex;
|
|
||||||
|
|
||||||
int numLocationReported;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,44 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssPsdsAidl"
|
|
||||||
|
|
||||||
#include "GnssPsds.h"
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnss.h>
|
|
||||||
#include <log/log.h>
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
std::shared_ptr<IGnssPsdsCallback> GnssPsds::sCallback = nullptr;
|
|
||||||
|
|
||||||
ndk::ScopedAStatus GnssPsds::setCallback(const std::shared_ptr<IGnssPsdsCallback>& callback) {
|
|
||||||
ALOGD("setCallback");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback = callback;
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
ndk::ScopedAStatus GnssPsds::injectPsdsData(PsdsType psdsType,
|
|
||||||
const std::vector<uint8_t>& psdsData) {
|
|
||||||
ALOGD("injectPsdsData. psdsType: %d, psdsData: %d bytes", static_cast<int>(psdsType),
|
|
||||||
static_cast<int>(psdsData.size()));
|
|
||||||
if (psdsData.size() > 0) {
|
|
||||||
return ndk::ScopedAStatus::ok();
|
|
||||||
} else {
|
|
||||||
return ndk::ScopedAStatus::fromServiceSpecificError(IGnss::ERROR_INVALID_ARGUMENT);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,37 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssPsds.h>
|
|
||||||
|
|
||||||
namespace aidl::android::hardware::gnss {
|
|
||||||
|
|
||||||
struct GnssPsds : public BnGnssPsds {
|
|
||||||
public:
|
|
||||||
ndk::ScopedAStatus setCallback(const std::shared_ptr<IGnssPsdsCallback>& callback) override;
|
|
||||||
ndk::ScopedAStatus injectPsdsData(PsdsType psdsType,
|
|
||||||
const std::vector<uint8_t>& psdsData) override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
// Guarded by mMutex
|
|
||||||
static std::shared_ptr<IGnssPsdsCallback> sCallback;
|
|
||||||
|
|
||||||
// Synchronization lock for sCallback
|
|
||||||
mutable std::mutex mMutex;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace aidl::android::hardware::gnss
|
|
||||||
@@ -1,4 +0,0 @@
|
|||||||
service gnss /vendor/bin/hw/android.hardware.gnss-service
|
|
||||||
class hal
|
|
||||||
user nobody
|
|
||||||
group nobody
|
|
||||||
@@ -1,9 +0,0 @@
|
|||||||
<manifest version="1.0" type="device">
|
|
||||||
<hal format="aidl">
|
|
||||||
<name>android.hardware.gnss</name>
|
|
||||||
<interface>
|
|
||||||
<name>IGnss</name>
|
|
||||||
<instance>default</instance>
|
|
||||||
</interface>
|
|
||||||
</hal>
|
|
||||||
</manifest>
|
|
||||||
@@ -1,12 +0,0 @@
|
|||||||
<manifest version="1.0" type="device">
|
|
||||||
<hal format="hidl">
|
|
||||||
<name>android.hardware.gnss</name>
|
|
||||||
<transport>hwbinder</transport>
|
|
||||||
<version>2.1</version>
|
|
||||||
<version>1.1</version>
|
|
||||||
<interface>
|
|
||||||
<name>IGnss</name>
|
|
||||||
<instance>default</instance>
|
|
||||||
</interface>
|
|
||||||
</hal>
|
|
||||||
</manifest>
|
|
||||||
@@ -1,58 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright 2020, The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "Gnss-main"
|
|
||||||
|
|
||||||
#include <android-base/logging.h>
|
|
||||||
#include <android/binder_manager.h>
|
|
||||||
#include <android/binder_process.h>
|
|
||||||
#include <hidl/HidlSupport.h>
|
|
||||||
#include <hidl/HidlTransportSupport.h>
|
|
||||||
#include <log/log.h>
|
|
||||||
#include <pthread.h>
|
|
||||||
#include "Gnss.h"
|
|
||||||
#include "GnssHidlHal.h"
|
|
||||||
|
|
||||||
using aidl::android::hardware::gnss::Gnss;
|
|
||||||
using aidl::android::hardware::gnss::GnssHidlHal;
|
|
||||||
using ::android::OK;
|
|
||||||
using ::android::sp;
|
|
||||||
using ::android::hardware::configureRpcThreadpool;
|
|
||||||
using ::android::hardware::joinRpcThreadpool;
|
|
||||||
using ::android::hardware::gnss::V2_1::IGnss;
|
|
||||||
|
|
||||||
int main() {
|
|
||||||
ABinderProcess_setThreadPoolMaxThreadCount(1);
|
|
||||||
ABinderProcess_startThreadPool();
|
|
||||||
|
|
||||||
std::shared_ptr<Gnss> gnssAidl = ndk::SharedRefBase::make<Gnss>();
|
|
||||||
const std::string instance = std::string() + Gnss::descriptor + "/default";
|
|
||||||
binder_status_t status =
|
|
||||||
AServiceManager_addService(gnssAidl->asBinder().get(), instance.c_str());
|
|
||||||
CHECK(status == STATUS_OK);
|
|
||||||
|
|
||||||
sp<IGnss> gnss = new GnssHidlHal(gnssAidl);
|
|
||||||
configureRpcThreadpool(1, true /* will join */);
|
|
||||||
if (gnss->registerAsService() != OK) {
|
|
||||||
ALOGE("Could not register gnss 2.1 service.");
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
joinRpcThreadpool();
|
|
||||||
ABinderProcess_joinThreadPool();
|
|
||||||
|
|
||||||
return EXIT_FAILURE; // should not reach
|
|
||||||
}
|
|
||||||
@@ -1,7 +0,0 @@
|
|||||||
wyattriley@google.com
|
|
||||||
gomo@google.com
|
|
||||||
smalkos@google.com
|
|
||||||
yuhany@google.com
|
|
||||||
|
|
||||||
# VTS team
|
|
||||||
yim@google.com
|
|
||||||
@@ -1,57 +0,0 @@
|
|||||||
//
|
|
||||||
// Copyright (C) 2019 The Android Open Source Project
|
|
||||||
//
|
|
||||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
// you may not use this file except in compliance with the License.
|
|
||||||
// You may obtain a copy of the License at
|
|
||||||
//
|
|
||||||
// http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
//
|
|
||||||
// Unless required by applicable law or agreed to in writing, software
|
|
||||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
// See the License for the specific language governing permissions and
|
|
||||||
// limitations under the License.
|
|
||||||
//
|
|
||||||
|
|
||||||
// package {
|
|
||||||
// // See: http://go/android-license-faq
|
|
||||||
// // A large-scale-change added 'default_applicable_licenses' to import
|
|
||||||
// // all of the 'license_kinds' from "hardware_interfaces_license"
|
|
||||||
// // to get the below license kinds:
|
|
||||||
// // SPDX-license-identifier-Apache-2.0
|
|
||||||
// default_applicable_licenses: ["hardware_interfaces_license"],
|
|
||||||
// }
|
|
||||||
|
|
||||||
cc_library_static {
|
|
||||||
name: "android.hardware.gnss@common-default-lib2",
|
|
||||||
vendor_available: true,
|
|
||||||
relative_install_path: "hw",
|
|
||||||
cflags: [
|
|
||||||
"-Wall",
|
|
||||||
"-Wextra",
|
|
||||||
"-Werror",
|
|
||||||
],
|
|
||||||
srcs: [
|
|
||||||
"v2_1/GnssAntennaInfo.cpp",
|
|
||||||
"v2_1/GnssConfiguration.cpp",
|
|
||||||
"v2_1/GnssDebug.cpp",
|
|
||||||
"v2_1/GnssMeasurement.cpp",
|
|
||||||
"v2_1/GnssMeasurementCorrections.cpp",
|
|
||||||
"MockLocation.cpp",
|
|
||||||
"Utils.cpp",
|
|
||||||
"NmeaFixInfo.cpp",
|
|
||||||
],
|
|
||||||
export_include_dirs: ["include"],
|
|
||||||
shared_libs: [
|
|
||||||
"libcutils",
|
|
||||||
"libhidlbase",
|
|
||||||
"libutils",
|
|
||||||
"android.hardware.gnss@1.0",
|
|
||||||
"android.hardware.gnss@2.0",
|
|
||||||
"android.hardware.gnss@2.1",
|
|
||||||
"android.hardware.gnss.measurement_corrections@1.1",
|
|
||||||
"android.hardware.gnss.measurement_corrections@1.0",
|
|
||||||
"android.hardware.gnss-V1-ndk_platform",
|
|
||||||
],
|
|
||||||
}
|
|
||||||
@@ -1,27 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "MockLocation.h"
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::common {
|
|
||||||
|
|
||||||
float gMockLatitudeDegrees{37.4219999};
|
|
||||||
float gMockLongitudeDegrees{-122.0840575};
|
|
||||||
float gMockAltitudeMeters{1.60062531};
|
|
||||||
float gMockBearingDegrees{0};
|
|
||||||
float gMockSpeedMetersPerSec{0};
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::common
|
|
||||||
@@ -1,273 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "NmeaFixInfo"
|
|
||||||
|
|
||||||
#include <Constants.h>
|
|
||||||
#include <NmeaFixInfo.h>
|
|
||||||
#include <Utils.h>
|
|
||||||
#include <log/log.h>
|
|
||||||
#include <sys/stat.h>
|
|
||||||
#include <sys/types.h>
|
|
||||||
#include <unistd.h>
|
|
||||||
#include <utils/SystemClock.h>
|
|
||||||
#include <limits>
|
|
||||||
#include <sstream>
|
|
||||||
#include <string>
|
|
||||||
#include <vector>
|
|
||||||
|
|
||||||
namespace android {
|
|
||||||
namespace hardware {
|
|
||||||
namespace gnss {
|
|
||||||
namespace common {
|
|
||||||
|
|
||||||
NmeaFixInfo::NmeaFixInfo() : hasGMCRecord(false), hasGGARecord(false) {}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getAltitudeMeters() const {
|
|
||||||
return altitudeMeters;
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::checkAndConvertToFloat(const std::string& sentence) {
|
|
||||||
if (sentence.empty()) {
|
|
||||||
return std::numeric_limits<float>::quiet_NaN();
|
|
||||||
}
|
|
||||||
return std::stof(sentence);
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getBearingAccuracyDegrees() const {
|
|
||||||
// Current NMEA doesn't contains beaing accuracy inforamtion
|
|
||||||
return kMockBearingAccuracyDegrees;
|
|
||||||
}
|
|
||||||
float NmeaFixInfo::getBearingDegrees() const {
|
|
||||||
return bearingDegrees;
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getHorizontalAccuracyMeters() const {
|
|
||||||
// Current NMEA doesn't contains horizontal accuracy inforamtion
|
|
||||||
return kMockHorizontalAccuracyMeters;
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getLatDeg() const {
|
|
||||||
return latDeg;
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getLngDeg() const {
|
|
||||||
return lngDeg;
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getSpeedAccuracyMetersPerSecond() const {
|
|
||||||
// Current NMEA doesn't contains speed accuracy inforamtion
|
|
||||||
return kMockSpeedAccuracyMetersPerSecond;
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getSpeedMetersPerSec() const {
|
|
||||||
return speedMetersPerSec;
|
|
||||||
}
|
|
||||||
|
|
||||||
int64_t NmeaFixInfo::getTimestamp() const {
|
|
||||||
return timestamp;
|
|
||||||
}
|
|
||||||
|
|
||||||
float NmeaFixInfo::getVerticalAccuracyMeters() const {
|
|
||||||
// Current NMEA doesn't contains vertical accuracy inforamtion
|
|
||||||
return kMockVerticalAccuracyMeters;
|
|
||||||
}
|
|
||||||
|
|
||||||
int64_t NmeaFixInfo::nmeaPartsToTimestamp(const std::string& timeStr, const std::string& dateStr) {
|
|
||||||
/**
|
|
||||||
* In NMEA format, the full time can only get from the $GPRMC record, see
|
|
||||||
* the following example:
|
|
||||||
* $GPRMC,213204.00,A,3725.371240,N,12205.589239,W,000.0,000.0,290819,,,A*49
|
|
||||||
* the datetime is stored in two parts, 213204 and 290819, which means
|
|
||||||
* 2019/08/29 21:32:04, however for in unix the year starts from 1900, we
|
|
||||||
* need to add the offset.
|
|
||||||
*/
|
|
||||||
struct tm tm;
|
|
||||||
const int32_t unixYearOffset = 100;
|
|
||||||
tm.tm_mday = std::stoi(dateStr.substr(0, 2).c_str());
|
|
||||||
tm.tm_mon = std::stoi(dateStr.substr(2, 2).c_str()) - 1;
|
|
||||||
tm.tm_year = std::stoi(dateStr.substr(4, 2).c_str()) + unixYearOffset;
|
|
||||||
tm.tm_hour = std::stoi(timeStr.substr(0, 2).c_str());
|
|
||||||
tm.tm_min = std::stoi(timeStr.substr(2, 2).c_str());
|
|
||||||
tm.tm_sec = std::stoi(timeStr.substr(4, 2).c_str());
|
|
||||||
return static_cast<int64_t>(mktime(&tm) - timezone);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool NmeaFixInfo::isValidFix() const {
|
|
||||||
return hasGMCRecord && hasGGARecord;
|
|
||||||
}
|
|
||||||
|
|
||||||
void NmeaFixInfo::parseGGALine(const std::vector<std::string>& sentenceValues) {
|
|
||||||
if (sentenceValues.size() == 0 || sentenceValues[0].compare(GPGA_RECORD_TAG) != 0) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// LatDeg, need covert to degree, if it is 'N', should be negative value
|
|
||||||
this->latDeg = std::stof(sentenceValues[2].substr(0, 2)) +
|
|
||||||
(std::stof(sentenceValues[2].substr(2)) / 60.0);
|
|
||||||
if (sentenceValues[3].compare("N") != 0) {
|
|
||||||
this->latDeg *= -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
// LngDeg, need covert to degree, if it is 'E', should be negative value
|
|
||||||
this->lngDeg = std::stof(sentenceValues[4].substr(0, 3)) +
|
|
||||||
std::stof(sentenceValues[4].substr(3)) / 60.0;
|
|
||||||
if (sentenceValues[5].compare("E") != 0) {
|
|
||||||
this->lngDeg *= -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
this->altitudeMeters = std::stof(sentenceValues[9]);
|
|
||||||
|
|
||||||
this->hDop = sentenceValues[8].empty() ? std::numeric_limits<float>::quiet_NaN()
|
|
||||||
: std::stof(sentenceValues[8]);
|
|
||||||
this->hasGGARecord = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void NmeaFixInfo::parseRMCLine(const std::vector<std::string>& sentenceValues) {
|
|
||||||
if (sentenceValues.size() == 0 || sentenceValues[0].compare(GPRMC_RECORD_TAG) != 0) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
this->speedMetersPerSec = checkAndConvertToFloat(sentenceValues[7]);
|
|
||||||
this->bearingDegrees = checkAndConvertToFloat(sentenceValues[8]);
|
|
||||||
this->timestamp = nmeaPartsToTimestamp(sentenceValues[1], sentenceValues[9]);
|
|
||||||
this->hasGMCRecord = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/** invalid the current NmeaFixInfo */
|
|
||||||
void NmeaFixInfo::reset() {
|
|
||||||
this->altitudeMeters = 0;
|
|
||||||
this->bearingDegrees = 0;
|
|
||||||
this->fixId = 0;
|
|
||||||
this->hasGMCRecord = false;
|
|
||||||
this->hasGGARecord = false;
|
|
||||||
this->latDeg = 0;
|
|
||||||
this->lngDeg = 0;
|
|
||||||
this->hDop = 0;
|
|
||||||
this->vDop = 0;
|
|
||||||
this->satelliteCount = 0;
|
|
||||||
this->speedMetersPerSec = 0;
|
|
||||||
this->timestamp = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void NmeaFixInfo::splitStr(const std::string& line, const char& delimiter,
|
|
||||||
std::vector<std::string>& out) {
|
|
||||||
std::istringstream iss(line);
|
|
||||||
std::string item;
|
|
||||||
while (std::getline(iss, item, delimiter)) {
|
|
||||||
out.push_back(item);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
NmeaFixInfo& NmeaFixInfo::operator=(const NmeaFixInfo& rhs) {
|
|
||||||
if (this == &rhs) return *this;
|
|
||||||
this->altitudeMeters = rhs.altitudeMeters;
|
|
||||||
this->bearingDegrees = rhs.bearingDegrees;
|
|
||||||
this->fixId = rhs.fixId;
|
|
||||||
this->hasGMCRecord = rhs.hasGMCRecord;
|
|
||||||
this->hasGGARecord = rhs.hasGGARecord;
|
|
||||||
this->hDop = rhs.hDop;
|
|
||||||
this->vDop = rhs.vDop;
|
|
||||||
this->latDeg = rhs.latDeg;
|
|
||||||
this->lngDeg = rhs.lngDeg;
|
|
||||||
this->satelliteCount = rhs.satelliteCount;
|
|
||||||
this->speedMetersPerSec = rhs.speedMetersPerSec;
|
|
||||||
this->timestamp = rhs.timestamp;
|
|
||||||
|
|
||||||
return *this;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parses the input string in NMEA format and convert to GnssLocation.
|
|
||||||
* Currently version only cares about $GPGGA and $GPRMC records. but we
|
|
||||||
* can easily extend to other types supported by NMEA if needed.
|
|
||||||
*/
|
|
||||||
std::unique_ptr<V2_0::GnssLocation> NmeaFixInfo::getLocationFromInputStr(
|
|
||||||
const std::string& inputStr) {
|
|
||||||
std::vector<std::string> nmeaRecords;
|
|
||||||
splitStr(inputStr, LINE_SEPARATOR, nmeaRecords);
|
|
||||||
NmeaFixInfo nmeaFixInfo;
|
|
||||||
NmeaFixInfo candidateFixInfo;
|
|
||||||
uint32_t fixId = 0;
|
|
||||||
double lastTimeStamp = 0;
|
|
||||||
for (const auto& line : nmeaRecords) {
|
|
||||||
if (line.compare(0, strlen(GPGA_RECORD_TAG), GPGA_RECORD_TAG) != 0 &&
|
|
||||||
line.compare(0, strlen(GPRMC_RECORD_TAG), GPRMC_RECORD_TAG) != 0) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
std::vector<std::string> sentenceValues;
|
|
||||||
splitStr(line, COMMA_SEPARATOR, sentenceValues);
|
|
||||||
if (sentenceValues.size() < MIN_COL_NUM) {
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
double currentTimeStamp = std::stof(sentenceValues[1]);
|
|
||||||
// If see a new timestamp, report correct location.
|
|
||||||
if ((currentTimeStamp - lastTimeStamp) > TIMESTAMP_EPSILON &&
|
|
||||||
candidateFixInfo.isValidFix()) {
|
|
||||||
nmeaFixInfo = candidateFixInfo;
|
|
||||||
candidateFixInfo.reset();
|
|
||||||
fixId++;
|
|
||||||
}
|
|
||||||
if (line.compare(0, strlen(GPGA_RECORD_TAG), GPGA_RECORD_TAG) == 0) {
|
|
||||||
candidateFixInfo.fixId = fixId;
|
|
||||||
candidateFixInfo.parseGGALine(sentenceValues);
|
|
||||||
} else if (line.compare(0, strlen(GPRMC_RECORD_TAG), GPRMC_RECORD_TAG) == 0) {
|
|
||||||
candidateFixInfo.parseRMCLine(sentenceValues);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (candidateFixInfo.isValidFix()) {
|
|
||||||
nmeaFixInfo = candidateFixInfo;
|
|
||||||
candidateFixInfo.reset();
|
|
||||||
}
|
|
||||||
if (!nmeaFixInfo.isValidFix()) {
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
return nmeaFixInfo.toGnssLocation();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Parses the input string in NMEA format and convert to GnssLocation.
|
|
||||||
*/
|
|
||||||
std::unique_ptr<V2_0::GnssLocation> NmeaFixInfo::toGnssLocation() const {
|
|
||||||
const V2_0::ElapsedRealtime currentOsTimestamp = {
|
|
||||||
.flags = V2_0::ElapsedRealtimeFlags::HAS_TIMESTAMP_NS |
|
|
||||||
V2_0::ElapsedRealtimeFlags::HAS_TIME_UNCERTAINTY_NS,
|
|
||||||
.timestampNs = static_cast<uint64_t>(::android::elapsedRealtimeNano()),
|
|
||||||
// This is an hardcoded value indicating a 1ms of uncertainty between the two clocks.
|
|
||||||
// In an actual implementation provide an estimate of the synchronization uncertainty
|
|
||||||
// or don't set the field.
|
|
||||||
.timeUncertaintyNs = 1000000};
|
|
||||||
|
|
||||||
V1_0::GnssLocation locationV1 = {
|
|
||||||
.gnssLocationFlags = 0xFF,
|
|
||||||
.latitudeDegrees = this->getLatDeg(),
|
|
||||||
.longitudeDegrees = this->getLngDeg(),
|
|
||||||
.altitudeMeters = this->getAltitudeMeters(),
|
|
||||||
.speedMetersPerSec = this->getSpeedMetersPerSec(),
|
|
||||||
.bearingDegrees = this->getBearingDegrees(),
|
|
||||||
.horizontalAccuracyMeters = this->getHorizontalAccuracyMeters(),
|
|
||||||
.verticalAccuracyMeters = this->getVerticalAccuracyMeters(),
|
|
||||||
.speedAccuracyMetersPerSecond = this->getSpeedAccuracyMetersPerSecond(),
|
|
||||||
.bearingAccuracyDegrees = this->getBearingAccuracyDegrees(),
|
|
||||||
.timestamp = this->getTimestamp()};
|
|
||||||
|
|
||||||
V2_0::GnssLocation locationV2 = {.v1_0 = locationV1, .elapsedRealtime = currentOsTimestamp};
|
|
||||||
|
|
||||||
return std::make_unique<V2_0::GnssLocation>(locationV2);
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace common
|
|
||||||
} // namespace gnss
|
|
||||||
} // namespace hardware
|
|
||||||
} // namespace android
|
|
||||||
@@ -1,405 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include <Constants.h>
|
|
||||||
#include <MockLocation.h>
|
|
||||||
#include <Utils.h>
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnss.h>
|
|
||||||
#include <utils/SystemClock.h>
|
|
||||||
|
|
||||||
namespace android {
|
|
||||||
namespace hardware {
|
|
||||||
namespace gnss {
|
|
||||||
namespace common {
|
|
||||||
|
|
||||||
using aidl::android::hardware::gnss::ElapsedRealtime;
|
|
||||||
using aidl::android::hardware::gnss::GnssClock;
|
|
||||||
using aidl::android::hardware::gnss::GnssData;
|
|
||||||
using aidl::android::hardware::gnss::GnssMeasurement;
|
|
||||||
using aidl::android::hardware::gnss::IGnss;
|
|
||||||
using aidl::android::hardware::gnss::IGnssMeasurementCallback;
|
|
||||||
using aidl::android::hardware::gnss::SatellitePvt;
|
|
||||||
|
|
||||||
using GnssSvFlags = V1_0::IGnssCallback::GnssSvFlags;
|
|
||||||
using GnssMeasurementFlagsV1_0 = V1_0::IGnssMeasurementCallback::GnssMeasurementFlags;
|
|
||||||
using GnssMeasurementFlagsV2_1 = V2_1::IGnssMeasurementCallback::GnssMeasurementFlags;
|
|
||||||
using GnssMeasurementStateV2_0 = V2_0::IGnssMeasurementCallback::GnssMeasurementState;
|
|
||||||
using ElapsedRealtimeFlags = V2_0::ElapsedRealtimeFlags;
|
|
||||||
using GnssConstellationTypeV2_0 = V2_0::GnssConstellationType;
|
|
||||||
using IGnssMeasurementCallbackV2_0 = V2_0::IGnssMeasurementCallback;
|
|
||||||
using GnssSignalType = V2_1::GnssSignalType;
|
|
||||||
|
|
||||||
using GnssDataV2_0 = V2_0::IGnssMeasurementCallback::GnssData;
|
|
||||||
using GnssDataV2_1 = V2_1::IGnssMeasurementCallback::GnssData;
|
|
||||||
using GnssSvInfoV1_0 = V1_0::IGnssCallback::GnssSvInfo;
|
|
||||||
using GnssSvInfoV2_0 = V2_0::IGnssCallback::GnssSvInfo;
|
|
||||||
using GnssSvInfoV2_1 = V2_1::IGnssCallback::GnssSvInfo;
|
|
||||||
using GnssAntennaInfo = ::android::hardware::gnss::V2_1::IGnssAntennaInfoCallback::GnssAntennaInfo;
|
|
||||||
using Row = V2_1::IGnssAntennaInfoCallback::Row;
|
|
||||||
using Coord = V2_1::IGnssAntennaInfoCallback::Coord;
|
|
||||||
|
|
||||||
GnssDataV2_1 Utils::getMockMeasurementV2_1() {
|
|
||||||
GnssDataV2_0 gnssDataV2_0 = Utils::getMockMeasurementV2_0();
|
|
||||||
V2_1::IGnssMeasurementCallback::GnssMeasurement gnssMeasurementV2_1 = {
|
|
||||||
.v2_0 = gnssDataV2_0.measurements[0],
|
|
||||||
.flags = (uint32_t)(GnssMeasurementFlagsV2_1::HAS_CARRIER_FREQUENCY |
|
|
||||||
GnssMeasurementFlagsV2_1::HAS_CARRIER_PHASE |
|
|
||||||
GnssMeasurementFlagsV2_1::HAS_FULL_ISB |
|
|
||||||
GnssMeasurementFlagsV2_1::HAS_FULL_ISB_UNCERTAINTY |
|
|
||||||
GnssMeasurementFlagsV2_1::HAS_SATELLITE_ISB |
|
|
||||||
GnssMeasurementFlagsV2_1::HAS_SATELLITE_ISB_UNCERTAINTY),
|
|
||||||
.fullInterSignalBiasNs = 30.0,
|
|
||||||
.fullInterSignalBiasUncertaintyNs = 250.0,
|
|
||||||
.satelliteInterSignalBiasNs = 20.0,
|
|
||||||
.satelliteInterSignalBiasUncertaintyNs = 150.0,
|
|
||||||
.basebandCN0DbHz = 25.0,
|
|
||||||
};
|
|
||||||
GnssSignalType referenceSignalTypeForIsb = {
|
|
||||||
.constellation = GnssConstellationTypeV2_0::GPS,
|
|
||||||
.carrierFrequencyHz = 1.59975e+09,
|
|
||||||
.codeType = "C",
|
|
||||||
};
|
|
||||||
V2_1::IGnssMeasurementCallback::GnssClock gnssClockV2_1 = {
|
|
||||||
.v1_0 = gnssDataV2_0.clock,
|
|
||||||
.referenceSignalTypeForIsb = referenceSignalTypeForIsb,
|
|
||||||
};
|
|
||||||
hidl_vec<V2_1::IGnssMeasurementCallback::GnssMeasurement> measurements(1);
|
|
||||||
measurements[0] = gnssMeasurementV2_1;
|
|
||||||
GnssDataV2_1 gnssDataV2_1 = {
|
|
||||||
.measurements = measurements,
|
|
||||||
.clock = gnssClockV2_1,
|
|
||||||
.elapsedRealtime = gnssDataV2_0.elapsedRealtime,
|
|
||||||
};
|
|
||||||
return gnssDataV2_1;
|
|
||||||
}
|
|
||||||
|
|
||||||
GnssDataV2_0 Utils::getMockMeasurementV2_0() {
|
|
||||||
V1_0::IGnssMeasurementCallback::GnssMeasurement measurement_1_0 = {
|
|
||||||
.flags = (uint32_t)GnssMeasurementFlagsV1_0::HAS_CARRIER_FREQUENCY,
|
|
||||||
.svid = (int16_t)6,
|
|
||||||
.constellation = V1_0::GnssConstellationType::UNKNOWN,
|
|
||||||
.timeOffsetNs = 0.0,
|
|
||||||
.receivedSvTimeInNs = 8195997131077,
|
|
||||||
.receivedSvTimeUncertaintyInNs = 15,
|
|
||||||
.cN0DbHz = 30.0,
|
|
||||||
.pseudorangeRateMps = -484.13739013671875,
|
|
||||||
.pseudorangeRateUncertaintyMps = 1.0379999876022339,
|
|
||||||
.accumulatedDeltaRangeState = (uint32_t)V1_0::IGnssMeasurementCallback::
|
|
||||||
GnssAccumulatedDeltaRangeState::ADR_STATE_UNKNOWN,
|
|
||||||
.accumulatedDeltaRangeM = 0.0,
|
|
||||||
.accumulatedDeltaRangeUncertaintyM = 0.0,
|
|
||||||
.carrierFrequencyHz = 1.59975e+09,
|
|
||||||
.multipathIndicator =
|
|
||||||
V1_0::IGnssMeasurementCallback::GnssMultipathIndicator::INDICATOR_UNKNOWN};
|
|
||||||
V1_1::IGnssMeasurementCallback::GnssMeasurement measurement_1_1 = {.v1_0 = measurement_1_0};
|
|
||||||
V2_0::IGnssMeasurementCallback::GnssMeasurement measurement_2_0 = {
|
|
||||||
.v1_1 = measurement_1_1,
|
|
||||||
.codeType = "C",
|
|
||||||
.state = GnssMeasurementStateV2_0::STATE_CODE_LOCK |
|
|
||||||
GnssMeasurementStateV2_0::STATE_BIT_SYNC |
|
|
||||||
GnssMeasurementStateV2_0::STATE_SUBFRAME_SYNC |
|
|
||||||
GnssMeasurementStateV2_0::STATE_TOW_DECODED |
|
|
||||||
GnssMeasurementStateV2_0::STATE_GLO_STRING_SYNC |
|
|
||||||
GnssMeasurementStateV2_0::STATE_GLO_TOD_DECODED,
|
|
||||||
.constellation = GnssConstellationTypeV2_0::GLONASS,
|
|
||||||
};
|
|
||||||
|
|
||||||
hidl_vec<IGnssMeasurementCallbackV2_0::GnssMeasurement> measurements(1);
|
|
||||||
measurements[0] = measurement_2_0;
|
|
||||||
V1_0::IGnssMeasurementCallback::GnssClock clock = {.timeNs = 2713545000000,
|
|
||||||
.fullBiasNs = -1226701900521857520,
|
|
||||||
.biasNs = 0.59689998626708984,
|
|
||||||
.biasUncertaintyNs = 47514.989972114563,
|
|
||||||
.driftNsps = -51.757811607455452,
|
|
||||||
.driftUncertaintyNsps = 310.64968328491528,
|
|
||||||
.hwClockDiscontinuityCount = 1};
|
|
||||||
|
|
||||||
V2_0::ElapsedRealtime timestamp = {
|
|
||||||
.flags = ElapsedRealtimeFlags::HAS_TIMESTAMP_NS |
|
|
||||||
ElapsedRealtimeFlags::HAS_TIME_UNCERTAINTY_NS,
|
|
||||||
.timestampNs = static_cast<uint64_t>(::android::elapsedRealtimeNano()),
|
|
||||||
// This is an hardcoded value indicating a 1ms of uncertainty between the two clocks.
|
|
||||||
// In an actual implementation provide an estimate of the synchronization uncertainty
|
|
||||||
// or don't set the field.
|
|
||||||
.timeUncertaintyNs = 1000000};
|
|
||||||
|
|
||||||
GnssDataV2_0 gnssData = {
|
|
||||||
.measurements = measurements, .clock = clock, .elapsedRealtime = timestamp};
|
|
||||||
return gnssData;
|
|
||||||
}
|
|
||||||
|
|
||||||
GnssData Utils::getMockMeasurement(const bool enableCorrVecOutputs) {
|
|
||||||
aidl::android::hardware::gnss::GnssSignalType signalType = {
|
|
||||||
.constellation = aidl::android::hardware::gnss::GnssConstellationType::GLONASS,
|
|
||||||
.carrierFrequencyHz = 1.59975e+09,
|
|
||||||
.codeType = aidl::android::hardware::gnss::GnssSignalType::CODE_TYPE_C,
|
|
||||||
};
|
|
||||||
GnssMeasurement measurement = {
|
|
||||||
.flags = GnssMeasurement::HAS_AUTOMATIC_GAIN_CONTROL |
|
|
||||||
GnssMeasurement::HAS_CARRIER_FREQUENCY | GnssMeasurement::HAS_CARRIER_PHASE |
|
|
||||||
GnssMeasurement::HAS_CARRIER_PHASE_UNCERTAINTY |
|
|
||||||
GnssMeasurement::HAS_FULL_ISB | GnssMeasurement::HAS_FULL_ISB_UNCERTAINTY |
|
|
||||||
GnssMeasurement::HAS_SATELLITE_ISB |
|
|
||||||
GnssMeasurement::HAS_SATELLITE_ISB_UNCERTAINTY |
|
|
||||||
GnssMeasurement::HAS_SATELLITE_PVT,
|
|
||||||
.svid = 13,
|
|
||||||
.signalType = signalType,
|
|
||||||
.receivedSvTimeInNs = 8195997131077,
|
|
||||||
.receivedSvTimeUncertaintyInNs = 15,
|
|
||||||
.antennaCN0DbHz = 30.0,
|
|
||||||
.basebandCN0DbHz = 26.5,
|
|
||||||
.agcLevelDb = 2.3,
|
|
||||||
.pseudorangeRateMps = -484.13739013671875,
|
|
||||||
.pseudorangeRateUncertaintyMps = 1.0379999876022339,
|
|
||||||
.accumulatedDeltaRangeState = GnssMeasurement::ADR_STATE_UNKNOWN,
|
|
||||||
.accumulatedDeltaRangeM = 1.52,
|
|
||||||
.accumulatedDeltaRangeUncertaintyM = 2.43,
|
|
||||||
.multipathIndicator = aidl::android::hardware::gnss::GnssMultipathIndicator::UNKNOWN,
|
|
||||||
.state = GnssMeasurement::STATE_CODE_LOCK | GnssMeasurement::STATE_BIT_SYNC |
|
|
||||||
GnssMeasurement::STATE_SUBFRAME_SYNC | GnssMeasurement::STATE_TOW_DECODED |
|
|
||||||
GnssMeasurement::STATE_GLO_STRING_SYNC |
|
|
||||||
GnssMeasurement::STATE_GLO_TOD_DECODED,
|
|
||||||
.fullInterSignalBiasNs = 21.5,
|
|
||||||
.fullInterSignalBiasUncertaintyNs = 792.0,
|
|
||||||
.satelliteInterSignalBiasNs = 233.9,
|
|
||||||
.satelliteInterSignalBiasUncertaintyNs = 921.2,
|
|
||||||
.satellitePvt = {.flags = SatellitePvt::HAS_POSITION_VELOCITY_CLOCK_INFO |
|
|
||||||
SatellitePvt::HAS_IONO | SatellitePvt::HAS_TROPO,
|
|
||||||
.satPosEcef = {.posXMeters = 10442993.1153328,
|
|
||||||
.posYMeters = -19926932.8051666,
|
|
||||||
.posZMeters = -12034295.0216203,
|
|
||||||
.ureMeters = 1000.2345678},
|
|
||||||
.satVelEcef = {.velXMps = -478.667183715732,
|
|
||||||
.velYMps = 1580.68371984114,
|
|
||||||
.velZMps = -3030.52994449997,
|
|
||||||
.ureRateMps = 10.2345678},
|
|
||||||
.satClockInfo = {.satHardwareCodeBiasMeters = 1.396983861923e-09,
|
|
||||||
.satTimeCorrectionMeters = -7113.08964331,
|
|
||||||
.satClkDriftMps = 0},
|
|
||||||
.ionoDelayMeters = 3.069949602639317e-08,
|
|
||||||
.tropoDelayMeters = 3.882265204404031},
|
|
||||||
.correlationVectors = {}};
|
|
||||||
|
|
||||||
GnssClock clock = {.gnssClockFlags = GnssClock::HAS_FULL_BIAS | GnssClock::HAS_BIAS |
|
|
||||||
GnssClock::HAS_BIAS_UNCERTAINTY | GnssClock::HAS_DRIFT |
|
|
||||||
GnssClock::HAS_DRIFT_UNCERTAINTY,
|
|
||||||
.timeNs = 35854545000000,
|
|
||||||
.fullBiasNs = -234621900521857520,
|
|
||||||
.biasNs = 0.2352389998626708984,
|
|
||||||
.biasUncertaintyNs = 274.989972114563,
|
|
||||||
.driftNsps = -124.3742360,
|
|
||||||
.driftUncertaintyNsps = 239.6234285828,
|
|
||||||
.hwClockDiscontinuityCount = 999};
|
|
||||||
|
|
||||||
ElapsedRealtime timestamp = {
|
|
||||||
.flags = ElapsedRealtime::HAS_TIMESTAMP_NS | ElapsedRealtime::HAS_TIME_UNCERTAINTY_NS,
|
|
||||||
.timestampNs = ::android::elapsedRealtimeNano(),
|
|
||||||
// This is an hardcoded value indicating a 1ms of uncertainty between the two clocks.
|
|
||||||
// In an actual implementation provide an estimate of the synchronization uncertainty
|
|
||||||
// or don't set the field.
|
|
||||||
.timeUncertaintyNs = 1020400};
|
|
||||||
|
|
||||||
if (enableCorrVecOutputs) {
|
|
||||||
aidl::android::hardware::gnss::CorrelationVector correlationVector1 = {
|
|
||||||
.frequencyOffsetMps = 10,
|
|
||||||
.samplingWidthM = 30,
|
|
||||||
.samplingStartM = 0,
|
|
||||||
.magnitude = {0, 5000, 10000, 5000, 0, 0, 3000, 0}};
|
|
||||||
aidl::android::hardware::gnss::CorrelationVector correlationVector2 = {
|
|
||||||
.frequencyOffsetMps = 20,
|
|
||||||
.samplingWidthM = 30,
|
|
||||||
.samplingStartM = -10,
|
|
||||||
.magnitude = {0, 3000, 5000, 3000, 0, 0, 1000, 0}};
|
|
||||||
measurement.correlationVectors = {correlationVector1, correlationVector2};
|
|
||||||
measurement.flags |= GnssMeasurement::HAS_CORRELATION_VECTOR;
|
|
||||||
}
|
|
||||||
|
|
||||||
GnssData gnssData = {
|
|
||||||
.measurements = {measurement}, .clock = clock, .elapsedRealtime = timestamp};
|
|
||||||
return gnssData;
|
|
||||||
}
|
|
||||||
|
|
||||||
V2_0::GnssLocation Utils::getMockLocationV2_0() {
|
|
||||||
const V2_0::ElapsedRealtime timestamp = {
|
|
||||||
.flags = V2_0::ElapsedRealtimeFlags::HAS_TIMESTAMP_NS |
|
|
||||||
V2_0::ElapsedRealtimeFlags::HAS_TIME_UNCERTAINTY_NS,
|
|
||||||
.timestampNs = static_cast<uint64_t>(::android::elapsedRealtimeNano()),
|
|
||||||
// This is an hardcoded value indicating a 1ms of uncertainty between the two clocks.
|
|
||||||
// In an actual implementation provide an estimate of the synchronization uncertainty
|
|
||||||
// or don't set the field.
|
|
||||||
.timeUncertaintyNs = 1000000};
|
|
||||||
|
|
||||||
V2_0::GnssLocation location = {.v1_0 = Utils::getMockLocationV1_0(),
|
|
||||||
.elapsedRealtime = timestamp};
|
|
||||||
return location;
|
|
||||||
}
|
|
||||||
|
|
||||||
V1_0::GnssLocation Utils::getMockLocationV1_0() {
|
|
||||||
V1_0::GnssLocation location = {
|
|
||||||
.gnssLocationFlags = 0xFF,
|
|
||||||
.latitudeDegrees = gMockLatitudeDegrees,
|
|
||||||
.longitudeDegrees = gMockLongitudeDegrees,
|
|
||||||
.altitudeMeters = gMockAltitudeMeters,
|
|
||||||
.speedMetersPerSec = gMockSpeedMetersPerSec,
|
|
||||||
.bearingDegrees = gMockBearingDegrees,
|
|
||||||
.horizontalAccuracyMeters = kMockHorizontalAccuracyMeters,
|
|
||||||
.verticalAccuracyMeters = kMockVerticalAccuracyMeters,
|
|
||||||
.speedAccuracyMetersPerSecond = kMockSpeedAccuracyMetersPerSecond,
|
|
||||||
.bearingAccuracyDegrees = kMockBearingAccuracyDegrees,
|
|
||||||
.timestamp =
|
|
||||||
static_cast<int64_t>(kMockTimestamp + ::android::elapsedRealtimeNano() / 1e6)};
|
|
||||||
return location;
|
|
||||||
}
|
|
||||||
|
|
||||||
hidl_vec<GnssSvInfoV2_1> Utils::getMockSvInfoListV2_1() {
|
|
||||||
GnssSvInfoV1_0 gnssSvInfoV1_0 = Utils::getMockSvInfoV1_0(3, V1_0::GnssConstellationType::GPS,
|
|
||||||
32.5, 59.1, 166.5, kGpsL1FreqHz);
|
|
||||||
GnssSvInfoV2_0 gnssSvInfoV2_0 =
|
|
||||||
Utils::getMockSvInfoV2_0(gnssSvInfoV1_0, V2_0::GnssConstellationType::GPS);
|
|
||||||
hidl_vec<GnssSvInfoV2_1> gnssSvInfoList = {
|
|
||||||
Utils::getMockSvInfoV2_1(gnssSvInfoV2_0, 27.5),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(5, V1_0::GnssConstellationType::GPS, 27.0,
|
|
||||||
29.0, 56.5, kGpsL1FreqHz),
|
|
||||||
V2_0::GnssConstellationType::GPS),
|
|
||||||
22.0),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(17, V1_0::GnssConstellationType::GPS, 30.5,
|
|
||||||
71.0, 77.0, kGpsL5FreqHz),
|
|
||||||
V2_0::GnssConstellationType::GPS),
|
|
||||||
25.5),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(26, V1_0::GnssConstellationType::GPS, 24.1,
|
|
||||||
28.0, 253.0, kGpsL5FreqHz),
|
|
||||||
V2_0::GnssConstellationType::GPS),
|
|
||||||
19.1),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(5, V1_0::GnssConstellationType::GLONASS,
|
|
||||||
20.5, 11.5, 116.0, kGloG1FreqHz),
|
|
||||||
V2_0::GnssConstellationType::GLONASS),
|
|
||||||
15.5),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(17, V1_0::GnssConstellationType::GLONASS,
|
|
||||||
21.5, 28.5, 186.0, kGloG1FreqHz),
|
|
||||||
V2_0::GnssConstellationType::GLONASS),
|
|
||||||
16.5),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(18, V1_0::GnssConstellationType::GLONASS,
|
|
||||||
28.3, 38.8, 69.0, kGloG1FreqHz),
|
|
||||||
V2_0::GnssConstellationType::GLONASS),
|
|
||||||
25.3),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(10, V1_0::GnssConstellationType::GLONASS,
|
|
||||||
25.0, 66.0, 247.0, kGloG1FreqHz),
|
|
||||||
V2_0::GnssConstellationType::GLONASS),
|
|
||||||
20.0),
|
|
||||||
getMockSvInfoV2_1(
|
|
||||||
getMockSvInfoV2_0(getMockSvInfoV1_0(3, V1_0::GnssConstellationType::UNKNOWN,
|
|
||||||
22.0, 35.0, 112.0, kIrnssL5FreqHz),
|
|
||||||
V2_0::GnssConstellationType::IRNSS),
|
|
||||||
19.7),
|
|
||||||
};
|
|
||||||
return gnssSvInfoList;
|
|
||||||
}
|
|
||||||
|
|
||||||
GnssSvInfoV2_1 Utils::getMockSvInfoV2_1(GnssSvInfoV2_0 gnssSvInfoV2_0, float basebandCN0DbHz) {
|
|
||||||
GnssSvInfoV2_1 gnssSvInfoV2_1 = {
|
|
||||||
.v2_0 = gnssSvInfoV2_0,
|
|
||||||
.basebandCN0DbHz = basebandCN0DbHz,
|
|
||||||
};
|
|
||||||
return gnssSvInfoV2_1;
|
|
||||||
}
|
|
||||||
|
|
||||||
GnssSvInfoV2_0 Utils::getMockSvInfoV2_0(GnssSvInfoV1_0 gnssSvInfoV1_0,
|
|
||||||
V2_0::GnssConstellationType type) {
|
|
||||||
GnssSvInfoV2_0 gnssSvInfoV2_0 = {
|
|
||||||
.v1_0 = gnssSvInfoV1_0,
|
|
||||||
.constellation = type,
|
|
||||||
};
|
|
||||||
return gnssSvInfoV2_0;
|
|
||||||
}
|
|
||||||
|
|
||||||
GnssSvInfoV1_0 Utils::getMockSvInfoV1_0(int16_t svid, V1_0::GnssConstellationType type,
|
|
||||||
float cN0DbHz, float elevationDegrees, float azimuthDegrees,
|
|
||||||
float carrierFrequencyHz) {
|
|
||||||
GnssSvInfoV1_0 svInfo = {.svid = svid,
|
|
||||||
.constellation = type,
|
|
||||||
.cN0Dbhz = cN0DbHz,
|
|
||||||
.elevationDegrees = elevationDegrees,
|
|
||||||
.azimuthDegrees = azimuthDegrees,
|
|
||||||
.carrierFrequencyHz = carrierFrequencyHz,
|
|
||||||
.svFlag = GnssSvFlags::USED_IN_FIX | GnssSvFlags::HAS_EPHEMERIS_DATA |
|
|
||||||
GnssSvFlags::HAS_ALMANAC_DATA |
|
|
||||||
GnssSvFlags::HAS_CARRIER_FREQUENCY};
|
|
||||||
return svInfo;
|
|
||||||
}
|
|
||||||
|
|
||||||
hidl_vec<GnssAntennaInfo> Utils::getMockAntennaInfos() {
|
|
||||||
GnssAntennaInfo mockAntennaInfo_1 = {
|
|
||||||
.carrierFrequencyMHz = kGpsL1FreqHz * 1e-6,
|
|
||||||
.phaseCenterOffsetCoordinateMillimeters = Coord{.x = 1,
|
|
||||||
.xUncertainty = 0.1,
|
|
||||||
.y = 2,
|
|
||||||
.yUncertainty = 0.1,
|
|
||||||
.z = 3,
|
|
||||||
.zUncertainty = 0.1},
|
|
||||||
.phaseCenterVariationCorrectionMillimeters =
|
|
||||||
{
|
|
||||||
Row{hidl_vec<double>{1, -1, 5, -2, 3, -1}},
|
|
||||||
Row{hidl_vec<double>{-2, 3, 2, 0, 1, 2}},
|
|
||||||
Row{hidl_vec<double>{1, 3, 2, -1, -3, 5}},
|
|
||||||
},
|
|
||||||
.phaseCenterVariationCorrectionUncertaintyMillimeters =
|
|
||||||
{
|
|
||||||
Row{hidl_vec<double>{0.1, 0.2, 0.4, 0.1, 0.2, 0.3}},
|
|
||||||
Row{hidl_vec<double>{0.3, 0.2, 0.3, 0.6, 0.1, 0.1}},
|
|
||||||
Row{hidl_vec<double>{0.1, 0.1, 0.4, 0.2, 0.5, 0.3}},
|
|
||||||
},
|
|
||||||
.signalGainCorrectionDbi =
|
|
||||||
{
|
|
||||||
Row{hidl_vec<double>{2, -3, 1, -3, 0, -4}},
|
|
||||||
Row{hidl_vec<double>{1, 0, -4, 1, 3, -2}},
|
|
||||||
Row{hidl_vec<double>{3, -2, 0, -2, 3, 0}},
|
|
||||||
},
|
|
||||||
.signalGainCorrectionUncertaintyDbi =
|
|
||||||
{
|
|
||||||
Row{hidl_vec<double>{0.3, 0.1, 0.2, 0.6, 0.1, 0.3}},
|
|
||||||
Row{hidl_vec<double>{0.1, 0.1, 0.5, 0.2, 0.3, 0.1}},
|
|
||||||
Row{hidl_vec<double>{0.2, 0.4, 0.2, 0.1, 0.1, 0.2}},
|
|
||||||
},
|
|
||||||
};
|
|
||||||
|
|
||||||
GnssAntennaInfo mockAntennaInfo_2 = {
|
|
||||||
.carrierFrequencyMHz = kGpsL5FreqHz * 1e-6,
|
|
||||||
.phaseCenterOffsetCoordinateMillimeters = Coord{.x = 5,
|
|
||||||
.xUncertainty = 0.1,
|
|
||||||
.y = 6,
|
|
||||||
.yUncertainty = 0.1,
|
|
||||||
.z = 7,
|
|
||||||
.zUncertainty = 0.1},
|
|
||||||
};
|
|
||||||
|
|
||||||
hidl_vec<GnssAntennaInfo> mockAntennaInfos = {
|
|
||||||
mockAntennaInfo_1,
|
|
||||||
mockAntennaInfo_2,
|
|
||||||
};
|
|
||||||
return mockAntennaInfos;
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace common
|
|
||||||
} // namespace gnss
|
|
||||||
} // namespace hardware
|
|
||||||
} // namespace android
|
|
||||||
@@ -1,42 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef android_hardware_gnss_common_Constants_H_
|
|
||||||
#define android_hardware_gnss_common_Constants_H_
|
|
||||||
|
|
||||||
#include <cstdint>
|
|
||||||
|
|
||||||
namespace android {
|
|
||||||
namespace hardware {
|
|
||||||
namespace gnss {
|
|
||||||
namespace common {
|
|
||||||
|
|
||||||
const float kMockHorizontalAccuracyMeters = 5;
|
|
||||||
const float kMockVerticalAccuracyMeters = 5;
|
|
||||||
const float kMockSpeedAccuracyMetersPerSecond = 1;
|
|
||||||
const float kMockBearingAccuracyDegrees = 90;
|
|
||||||
const int64_t kMockTimestamp = 1519930775453L;
|
|
||||||
const float kGpsL1FreqHz = 1575.42 * 1e6;
|
|
||||||
const float kGpsL5FreqHz = 1176.45 * 1e6;
|
|
||||||
const float kGloG1FreqHz = 1602.0 * 1e6;
|
|
||||||
const float kIrnssL5FreqHz = 1176.45 * 1e6;
|
|
||||||
|
|
||||||
} // namespace common
|
|
||||||
} // namespace gnss
|
|
||||||
} // namespace hardware
|
|
||||||
} // namespace android
|
|
||||||
|
|
||||||
#endif // android_hardware_gnss_common_Constants_H_
|
|
||||||
@@ -1,38 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef android_hardware_gnss_common_MockLocation_H_
|
|
||||||
#define android_hardware_gnss_common_MockLocation_H_
|
|
||||||
|
|
||||||
#include <cstdint>
|
|
||||||
|
|
||||||
namespace android {
|
|
||||||
namespace hardware {
|
|
||||||
namespace gnss {
|
|
||||||
namespace common {
|
|
||||||
|
|
||||||
extern float gMockLatitudeDegrees;
|
|
||||||
extern float gMockLongitudeDegrees;
|
|
||||||
extern float gMockAltitudeMeters;
|
|
||||||
extern float gMockBearingDegrees;
|
|
||||||
extern float gMockSpeedMetersPerSec;
|
|
||||||
|
|
||||||
} // namespace common
|
|
||||||
} // namespace gnss
|
|
||||||
} // namespace hardware
|
|
||||||
} // namespace android
|
|
||||||
|
|
||||||
#endif // android_hardware_gnss_common_MockLocation_H_
|
|
||||||
@@ -1,88 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <Constants.h>
|
|
||||||
#include <android/hardware/gnss/1.0/IGnss.h>
|
|
||||||
#include <android/hardware/gnss/2.0/IGnss.h>
|
|
||||||
#include <hidl/Status.h>
|
|
||||||
#include <ctime>
|
|
||||||
#include <string>
|
|
||||||
namespace android {
|
|
||||||
namespace hardware {
|
|
||||||
namespace gnss {
|
|
||||||
namespace common {
|
|
||||||
|
|
||||||
constexpr char GPGA_RECORD_TAG[] = "$GPGGA";
|
|
||||||
constexpr char GPRMC_RECORD_TAG[] = "$GPRMC";
|
|
||||||
constexpr char LINE_SEPARATOR = '\n';
|
|
||||||
constexpr char COMMA_SEPARATOR = ',';
|
|
||||||
constexpr double TIMESTAMP_EPSILON = 0.001;
|
|
||||||
constexpr int MIN_COL_NUM = 13;
|
|
||||||
|
|
||||||
/** Helper class to parse and store the GNSS fix details information. */
|
|
||||||
class NmeaFixInfo {
|
|
||||||
private:
|
|
||||||
float altitudeMeters;
|
|
||||||
float bearingDegrees;
|
|
||||||
uint32_t fixId;
|
|
||||||
bool hasGMCRecord;
|
|
||||||
bool hasGGARecord;
|
|
||||||
float hDop;
|
|
||||||
float vDop;
|
|
||||||
float latDeg;
|
|
||||||
float lngDeg;
|
|
||||||
uint32_t satelliteCount;
|
|
||||||
float speedMetersPerSec;
|
|
||||||
int64_t timestamp;
|
|
||||||
|
|
||||||
public:
|
|
||||||
static std::unique_ptr<V2_0::GnssLocation> getLocationFromInputStr(const std::string& inputStr);
|
|
||||||
|
|
||||||
private:
|
|
||||||
static void splitStr(const std::string& line, const char& delimiter,
|
|
||||||
std::vector<std::string>& out);
|
|
||||||
static float checkAndConvertToFloat(const std::string& sentence);
|
|
||||||
static int64_t nmeaPartsToTimestamp(const std::string& timeStr, const std::string& dateStr);
|
|
||||||
|
|
||||||
NmeaFixInfo();
|
|
||||||
void parseGGALine(const std::vector<std::string>& sentenceValues);
|
|
||||||
void parseRMCLine(const std::vector<std::string>& sentenceValues);
|
|
||||||
std::unique_ptr<V2_0::GnssLocation> toGnssLocation() const;
|
|
||||||
|
|
||||||
// Getters
|
|
||||||
float getAltitudeMeters() const;
|
|
||||||
float getBearingAccuracyDegrees() const;
|
|
||||||
float getBearingDegrees() const;
|
|
||||||
uint32_t getFixId() const;
|
|
||||||
float getHorizontalAccuracyMeters() const;
|
|
||||||
float getLatDeg() const;
|
|
||||||
float getLngDeg() const;
|
|
||||||
float getSpeedAccuracyMetersPerSecond() const;
|
|
||||||
float getSpeedMetersPerSec() const;
|
|
||||||
int64_t getTimestamp() const;
|
|
||||||
float getVerticalAccuracyMeters() const;
|
|
||||||
|
|
||||||
bool isValidFix() const;
|
|
||||||
void reset();
|
|
||||||
NmeaFixInfo& operator=(const NmeaFixInfo& rhs);
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace common
|
|
||||||
} // namespace gnss
|
|
||||||
} // namespace hardware
|
|
||||||
} // namespace android
|
|
||||||
@@ -1,57 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef android_hardware_gnss_common_default_Utils_H_
|
|
||||||
#define android_hardware_gnss_common_default_Utils_H_
|
|
||||||
|
|
||||||
#include <aidl/android/hardware/gnss/BnGnssMeasurementInterface.h>
|
|
||||||
#include <android/hardware/gnss/1.0/IGnss.h>
|
|
||||||
#include <android/hardware/gnss/2.0/IGnss.h>
|
|
||||||
#include <android/hardware/gnss/2.1/IGnss.h>
|
|
||||||
|
|
||||||
using ::android::hardware::hidl_vec;
|
|
||||||
|
|
||||||
namespace android {
|
|
||||||
namespace hardware {
|
|
||||||
namespace gnss {
|
|
||||||
namespace common {
|
|
||||||
|
|
||||||
struct Utils {
|
|
||||||
static aidl::android::hardware::gnss::GnssData getMockMeasurement(
|
|
||||||
const bool enableCorrVecOutputs);
|
|
||||||
static V2_0::IGnssMeasurementCallback::GnssData getMockMeasurementV2_0();
|
|
||||||
static V2_1::IGnssMeasurementCallback::GnssData getMockMeasurementV2_1();
|
|
||||||
static V2_0::GnssLocation getMockLocationV2_0();
|
|
||||||
static V1_0::GnssLocation getMockLocationV1_0();
|
|
||||||
static hidl_vec<V2_1::IGnssCallback::GnssSvInfo> getMockSvInfoListV2_1();
|
|
||||||
static V2_1::IGnssCallback::GnssSvInfo getMockSvInfoV2_1(
|
|
||||||
V2_0::IGnssCallback::GnssSvInfo gnssSvInfoV2_0, float basebandCN0DbHz);
|
|
||||||
static V2_0::IGnssCallback::GnssSvInfo getMockSvInfoV2_0(
|
|
||||||
V1_0::IGnssCallback::GnssSvInfo gnssSvInfoV1_0, V2_0::GnssConstellationType type);
|
|
||||||
static V1_0::IGnssCallback::GnssSvInfo getMockSvInfoV1_0(int16_t svid,
|
|
||||||
V1_0::GnssConstellationType type,
|
|
||||||
float cN0DbHz, float elevationDegrees,
|
|
||||||
float azimuthDegrees,
|
|
||||||
float carrierFrequencyHz);
|
|
||||||
static hidl_vec<V2_1::IGnssAntennaInfoCallback::GnssAntennaInfo> getMockAntennaInfos();
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace common
|
|
||||||
} // namespace gnss
|
|
||||||
} // namespace hardware
|
|
||||||
} // namespace android
|
|
||||||
|
|
||||||
#endif // android_hardware_gnss_common_default_Utils_H_
|
|
||||||
@@ -1,54 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <android/hardware/gnss/2.1/IGnssAntennaInfo.h>
|
|
||||||
|
|
||||||
#include <mutex>
|
|
||||||
#include <thread>
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V2_1::implementation {
|
|
||||||
|
|
||||||
struct GnssAntennaInfo : public ::android::hardware::gnss::V2_1::IGnssAntennaInfo {
|
|
||||||
GnssAntennaInfo();
|
|
||||||
~GnssAntennaInfo();
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V2_1::IGnssAntennaInfo follow.
|
|
||||||
Return<GnssAntennaInfoStatus> setCallback(
|
|
||||||
const sp<::android::hardware::gnss::V2_1::IGnssAntennaInfoCallback>& callback) override;
|
|
||||||
Return<void> close() override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
void start();
|
|
||||||
void stop();
|
|
||||||
void reportAntennaInfo(
|
|
||||||
const hidl_vec<
|
|
||||||
::android::hardware::gnss::V2_1::IGnssAntennaInfoCallback::GnssAntennaInfo>&
|
|
||||||
antennaInfo) const;
|
|
||||||
|
|
||||||
// Guarded by mMutex
|
|
||||||
static sp<::android::hardware::gnss::V2_1::IGnssAntennaInfoCallback> sCallback;
|
|
||||||
|
|
||||||
std::atomic<long> mMinIntervalMillis;
|
|
||||||
std::atomic<bool> mIsActive;
|
|
||||||
std::thread mThread;
|
|
||||||
|
|
||||||
// Synchronization lock for sCallback
|
|
||||||
mutable std::mutex mMutex;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V2_1::implementation
|
|
||||||
@@ -1,82 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <android/hardware/gnss/2.1/IGnssCallback.h>
|
|
||||||
#include <android/hardware/gnss/2.1/IGnssConfiguration.h>
|
|
||||||
#include <hidl/MQDescriptor.h>
|
|
||||||
#include <hidl/Status.h>
|
|
||||||
#include <mutex>
|
|
||||||
#include <unordered_set>
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V2_1::implementation {
|
|
||||||
|
|
||||||
struct BlacklistedSourceHashV2_1 {
|
|
||||||
inline int operator()(
|
|
||||||
const ::android::hardware::gnss::V2_1::IGnssConfiguration::BlacklistedSource& source)
|
|
||||||
const {
|
|
||||||
return int(source.constellation) * 1000 + int(source.svid);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct BlacklistedSourceEqualV2_1 {
|
|
||||||
inline bool operator()(
|
|
||||||
const ::android::hardware::gnss::V2_1::IGnssConfiguration::BlacklistedSource& s1,
|
|
||||||
const ::android::hardware::gnss::V2_1::IGnssConfiguration::BlacklistedSource& s2)
|
|
||||||
const {
|
|
||||||
return (s1.constellation == s2.constellation) && (s1.svid == s2.svid);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
using BlacklistedSourceSetV2_1 =
|
|
||||||
std::unordered_set<::android::hardware::gnss::V2_1::IGnssConfiguration::BlacklistedSource,
|
|
||||||
BlacklistedSourceHashV2_1, BlacklistedSourceEqualV2_1>;
|
|
||||||
using BlacklistedConstellationSetV2_1 = std::unordered_set<V2_0::GnssConstellationType>;
|
|
||||||
|
|
||||||
struct GnssConfiguration : public IGnssConfiguration {
|
|
||||||
// Methods from ::android::hardware::gnss::V1_0::IGnssConfiguration follow.
|
|
||||||
Return<bool> setSuplEs(bool enabled) override;
|
|
||||||
Return<bool> setSuplVersion(uint32_t version) override;
|
|
||||||
Return<bool> setSuplMode(hidl_bitfield<SuplMode> mode) override;
|
|
||||||
Return<bool> setGpsLock(hidl_bitfield<GpsLock> lock) override;
|
|
||||||
Return<bool> setLppProfile(hidl_bitfield<LppProfile> lppProfile) override;
|
|
||||||
Return<bool> setGlonassPositioningProtocol(hidl_bitfield<GlonassPosProtocol> protocol) override;
|
|
||||||
Return<bool> setEmergencySuplPdn(bool enable) override;
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V1_1::IGnssConfiguration follow.
|
|
||||||
Return<bool> setBlacklist(
|
|
||||||
const hidl_vec<V1_1::IGnssConfiguration::BlacklistedSource>& blacklist) override;
|
|
||||||
|
|
||||||
std::recursive_mutex& getMutex() const;
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V2_0::IGnssConfiguration follow.
|
|
||||||
Return<bool> setEsExtensionSec(uint32_t emergencyExtensionSeconds) override;
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V2_1::IGnssConfiguration follow.
|
|
||||||
Return<bool> setBlacklist_2_1(
|
|
||||||
const hidl_vec<V2_1::IGnssConfiguration::BlacklistedSource>& blacklist) override;
|
|
||||||
|
|
||||||
Return<bool> isBlacklistedV2_1(const V2_1::IGnssCallback::GnssSvInfo& gnssSvInfo) const;
|
|
||||||
|
|
||||||
private:
|
|
||||||
mutable std::recursive_mutex mMutex;
|
|
||||||
|
|
||||||
BlacklistedSourceSetV2_1 mBlacklistedSourceSet;
|
|
||||||
BlacklistedConstellationSetV2_1 mBlacklistedConstellationSet;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V2_1::implementation
|
|
||||||
@@ -1,33 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2018 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <android/hardware/gnss/1.0/IGnssDebug.h>
|
|
||||||
#include <hidl/Status.h>
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V1_1::implementation {
|
|
||||||
|
|
||||||
/* Interface for GNSS Debug support. */
|
|
||||||
struct GnssDebug : public V1_0::IGnssDebug {
|
|
||||||
/*
|
|
||||||
* Methods from ::android::hardware::gnss::V1_0::IGnssDebug follow.
|
|
||||||
* These declarations were generated from IGnssDebug.hal.
|
|
||||||
*/
|
|
||||||
Return<void> getDebugData(V1_0::IGnssDebug::getDebugData_cb _hidl_cb) override;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V1_1::implementation
|
|
||||||
@@ -1,68 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <android/hardware/gnss/2.1/IGnssMeasurement.h>
|
|
||||||
#include <hidl/MQDescriptor.h>
|
|
||||||
#include <hidl/Status.h>
|
|
||||||
#include <atomic>
|
|
||||||
#include <mutex>
|
|
||||||
#include <thread>
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V2_1::implementation {
|
|
||||||
|
|
||||||
struct GnssMeasurement : public IGnssMeasurement {
|
|
||||||
GnssMeasurement();
|
|
||||||
~GnssMeasurement();
|
|
||||||
// Methods from V1_0::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> setCallback(
|
|
||||||
const sp<V1_0::IGnssMeasurementCallback>& callback) override;
|
|
||||||
Return<void> close() override;
|
|
||||||
|
|
||||||
// Methods from V1_1::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> setCallback_1_1(
|
|
||||||
const sp<V1_1::IGnssMeasurementCallback>& callback, bool enableFullTracking) override;
|
|
||||||
|
|
||||||
// Methods from V2_0::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> setCallback_2_0(
|
|
||||||
const sp<V2_0::IGnssMeasurementCallback>& callback, bool enableFullTracking) override;
|
|
||||||
|
|
||||||
// Methods from V2_1::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> setCallback_2_1(
|
|
||||||
const sp<V2_1::IGnssMeasurementCallback>& callback, bool enableFullTracking) override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
void start();
|
|
||||||
void stop();
|
|
||||||
void reportMeasurement(const V2_0::IGnssMeasurementCallback::GnssData&);
|
|
||||||
void reportMeasurement(const V2_1::IGnssMeasurementCallback::GnssData&);
|
|
||||||
|
|
||||||
// Guarded by mMutex
|
|
||||||
static sp<V2_1::IGnssMeasurementCallback> sCallback_2_1;
|
|
||||||
|
|
||||||
// Guarded by mMutex
|
|
||||||
static sp<V2_0::IGnssMeasurementCallback> sCallback_2_0;
|
|
||||||
|
|
||||||
std::atomic<long> mMinIntervalMillis;
|
|
||||||
std::atomic<bool> mIsActive;
|
|
||||||
std::thread mThread;
|
|
||||||
|
|
||||||
// Synchronization lock for sCallback_2_1 and sCallback_2_0
|
|
||||||
mutable std::mutex mMutex;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V2_1::implementation
|
|
||||||
@@ -1,37 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <android/hardware/gnss/measurement_corrections/1.1/IMeasurementCorrections.h>
|
|
||||||
#include <hidl/MQDescriptor.h>
|
|
||||||
#include <hidl/Status.h>
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::measurement_corrections::V1_1::implementation {
|
|
||||||
|
|
||||||
struct GnssMeasurementCorrections : public IMeasurementCorrections {
|
|
||||||
GnssMeasurementCorrections();
|
|
||||||
~GnssMeasurementCorrections();
|
|
||||||
|
|
||||||
// Methods from V1_0::IMeasurementCorrections follow.
|
|
||||||
Return<bool> setCorrections(const V1_0::MeasurementCorrections& corrections) override;
|
|
||||||
Return<bool> setCallback(const sp<V1_0::IMeasurementCorrectionsCallback>& callback) override;
|
|
||||||
|
|
||||||
// Methods from V1_1::IMeasurementCorrections follow.
|
|
||||||
Return<bool> setCorrections_1_1(const V1_1::MeasurementCorrections& corrections) override;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::measurement_corrections::V1_1::implementation
|
|
||||||
@@ -1,779 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <android/hardware/gnss/2.1/IGnss.h>
|
|
||||||
#include <errno.h>
|
|
||||||
#include <fcntl.h>
|
|
||||||
#include <hidl/MQDescriptor.h>
|
|
||||||
#include <hidl/Status.h>
|
|
||||||
#include <log/log.h>
|
|
||||||
#include <sys/epoll.h>
|
|
||||||
#include <atomic>
|
|
||||||
#include <mutex>
|
|
||||||
#include <string>
|
|
||||||
#include <thread>
|
|
||||||
#include <utils/SystemClock.h>
|
|
||||||
|
|
||||||
#include <cutils/properties.h>
|
|
||||||
|
|
||||||
#include "GnssAntennaInfo.h"
|
|
||||||
#include "GnssConfiguration.h"
|
|
||||||
#include "GnssDebug.h"
|
|
||||||
#include "GnssMeasurement.h"
|
|
||||||
#include "GnssMeasurementCorrections.h"
|
|
||||||
#include "MockLocation.h"
|
|
||||||
#include "NmeaFixInfo.h"
|
|
||||||
#include "Utils.h"
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::common::implementation {
|
|
||||||
|
|
||||||
constexpr int INPUT_BUFFER_SIZE = 128;
|
|
||||||
constexpr char CMD_GET_LOCATION[] = "CMD_GET_LOCATION";
|
|
||||||
constexpr char GNSS_PATH[] = "/data/vendor/gps/gnss";
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
struct GnssTemplate : public T_IGnss {
|
|
||||||
GnssTemplate();
|
|
||||||
~GnssTemplate();
|
|
||||||
// Methods from V1_0::IGnss follow.
|
|
||||||
Return<bool> setCallback(const sp<V1_0::IGnssCallback>& callback) override;
|
|
||||||
Return<bool> start() override;
|
|
||||||
Return<bool> stop() override;
|
|
||||||
Return<void> cleanup() override;
|
|
||||||
Return<bool> injectTime(int64_t timeMs, int64_t timeReferenceMs,
|
|
||||||
int32_t uncertaintyMs) override;
|
|
||||||
Return<bool> injectLocation(double latitudeDegrees, double longitudeDegrees,
|
|
||||||
float accuracyMeters) override;
|
|
||||||
Return<void> deleteAidingData(V1_0::IGnss::GnssAidingData aidingDataFlags) override;
|
|
||||||
Return<bool> setPositionMode(V1_0::IGnss::GnssPositionMode mode,
|
|
||||||
V1_0::IGnss::GnssPositionRecurrence recurrence,
|
|
||||||
uint32_t minIntervalMs, uint32_t preferredAccuracyMeters,
|
|
||||||
uint32_t preferredTimeMs) override;
|
|
||||||
Return<sp<V1_0::IAGnssRil>> getExtensionAGnssRil() override;
|
|
||||||
Return<sp<V1_0::IGnssGeofencing>> getExtensionGnssGeofencing() override;
|
|
||||||
Return<sp<V1_0::IAGnss>> getExtensionAGnss() override;
|
|
||||||
Return<sp<V1_0::IGnssNi>> getExtensionGnssNi() override;
|
|
||||||
Return<sp<V1_0::IGnssMeasurement>> getExtensionGnssMeasurement() override;
|
|
||||||
Return<sp<V1_0::IGnssNavigationMessage>> getExtensionGnssNavigationMessage() override;
|
|
||||||
Return<sp<V1_0::IGnssXtra>> getExtensionXtra() override;
|
|
||||||
Return<sp<V1_0::IGnssConfiguration>> getExtensionGnssConfiguration() override;
|
|
||||||
Return<sp<V1_0::IGnssDebug>> getExtensionGnssDebug() override;
|
|
||||||
Return<sp<V1_0::IGnssBatching>> getExtensionGnssBatching() override;
|
|
||||||
|
|
||||||
// Methods from V1_1::IGnss follow.
|
|
||||||
Return<bool> setCallback_1_1(const sp<V1_1::IGnssCallback>& callback) override;
|
|
||||||
Return<bool> setPositionMode_1_1(V1_0::IGnss::GnssPositionMode mode,
|
|
||||||
V1_0::IGnss::GnssPositionRecurrence recurrence,
|
|
||||||
uint32_t minIntervalMs, uint32_t preferredAccuracyMeters,
|
|
||||||
uint32_t preferredTimeMs, bool lowPowerMode) override;
|
|
||||||
Return<sp<V1_1::IGnssConfiguration>> getExtensionGnssConfiguration_1_1() override;
|
|
||||||
Return<sp<V1_1::IGnssMeasurement>> getExtensionGnssMeasurement_1_1() override;
|
|
||||||
Return<bool> injectBestLocation(const V1_0::GnssLocation& location) override;
|
|
||||||
|
|
||||||
// Methods from V2_0::IGnss follow.
|
|
||||||
Return<bool> setCallback_2_0(const sp<V2_0::IGnssCallback>& callback) override;
|
|
||||||
Return<sp<V2_0::IGnssConfiguration>> getExtensionGnssConfiguration_2_0() override;
|
|
||||||
Return<sp<V2_0::IGnssDebug>> getExtensionGnssDebug_2_0() override;
|
|
||||||
Return<sp<V2_0::IAGnss>> getExtensionAGnss_2_0() override;
|
|
||||||
Return<sp<V2_0::IAGnssRil>> getExtensionAGnssRil_2_0() override;
|
|
||||||
Return<sp<V2_0::IGnssMeasurement>> getExtensionGnssMeasurement_2_0() override;
|
|
||||||
Return<sp<measurement_corrections::V1_0::IMeasurementCorrections>>
|
|
||||||
getExtensionMeasurementCorrections() override;
|
|
||||||
Return<sp<visibility_control::V1_0::IGnssVisibilityControl>> getExtensionVisibilityControl()
|
|
||||||
override;
|
|
||||||
Return<sp<V2_0::IGnssBatching>> getExtensionGnssBatching_2_0() override;
|
|
||||||
Return<bool> injectBestLocation_2_0(const V2_0::GnssLocation& location) override;
|
|
||||||
|
|
||||||
// Methods from V2_1::IGnss follow.
|
|
||||||
Return<bool> setCallback_2_1(const sp<V2_1::IGnssCallback>& callback) override;
|
|
||||||
Return<sp<V2_1::IGnssMeasurement>> getExtensionGnssMeasurement_2_1() override;
|
|
||||||
Return<sp<V2_1::IGnssConfiguration>> getExtensionGnssConfiguration_2_1() override;
|
|
||||||
Return<sp<measurement_corrections::V1_1::IMeasurementCorrections>>
|
|
||||||
getExtensionMeasurementCorrections_1_1() override;
|
|
||||||
Return<sp<V2_1::IGnssAntennaInfo>> getExtensionGnssAntennaInfo() override;
|
|
||||||
|
|
||||||
Return<void> debug(const hidl_handle& fd, const hidl_vec<hidl_string>& options) override;
|
|
||||||
|
|
||||||
private:
|
|
||||||
std::unique_ptr<V2_0::GnssLocation> getLocationFromHW();
|
|
||||||
void reportLocation(const V2_0::GnssLocation&) const;
|
|
||||||
void reportLocation(const V1_0::GnssLocation&) const;
|
|
||||||
void reportSvStatus(const hidl_vec<V2_1::IGnssCallback::GnssSvInfo>&) const;
|
|
||||||
void reportGnssStatusValue(const V1_0::IGnssCallback::GnssStatusValue) const;
|
|
||||||
|
|
||||||
Return<void> help(const hidl_handle& fd);
|
|
||||||
Return<void> setLocation(const hidl_handle& fd, const hidl_vec<hidl_string>& options);
|
|
||||||
|
|
||||||
static sp<V2_1::IGnssCallback> sGnssCallback_2_1;
|
|
||||||
static sp<V2_0::IGnssCallback> sGnssCallback_2_0;
|
|
||||||
static sp<V1_1::IGnssCallback> sGnssCallback_1_1;
|
|
||||||
static sp<V1_0::IGnssCallback> sGnssCallback_1_0;
|
|
||||||
|
|
||||||
std::atomic<long> mMinIntervalMs;
|
|
||||||
sp<V2_1::implementation::GnssConfiguration> mGnssConfiguration;
|
|
||||||
std::atomic<bool> mIsActive;
|
|
||||||
std::atomic<bool> mHardwareModeChecked;
|
|
||||||
std::atomic<int> mGnssFd;
|
|
||||||
std::thread mThread;
|
|
||||||
|
|
||||||
mutable std::mutex mMutex;
|
|
||||||
virtual hidl_vec<V2_1::IGnssCallback::GnssSvInfo> filterBlocklistedSatellitesV2_1(
|
|
||||||
hidl_vec<V2_1::IGnssCallback::GnssSvInfo> gnssSvInfoList);
|
|
||||||
virtual void notePowerConsumption();
|
|
||||||
};
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
sp<V2_1::IGnssCallback> GnssTemplate<T_IGnss>::sGnssCallback_2_1 = nullptr;
|
|
||||||
template <class T_IGnss>
|
|
||||||
sp<V2_0::IGnssCallback> GnssTemplate<T_IGnss>::sGnssCallback_2_0 = nullptr;
|
|
||||||
template <class T_IGnss>
|
|
||||||
sp<V1_1::IGnssCallback> GnssTemplate<T_IGnss>::sGnssCallback_1_1 = nullptr;
|
|
||||||
template <class T_IGnss>
|
|
||||||
sp<V1_0::IGnssCallback> GnssTemplate<T_IGnss>::sGnssCallback_1_0 = nullptr;
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
GnssTemplate<T_IGnss>::GnssTemplate()
|
|
||||||
: mMinIntervalMs(1000),
|
|
||||||
mGnssConfiguration{new V2_1::implementation::GnssConfiguration()},
|
|
||||||
mHardwareModeChecked(false),
|
|
||||||
mGnssFd(-1) {}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
GnssTemplate<T_IGnss>::~GnssTemplate() {
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
std::unique_ptr<V2_0::GnssLocation> GnssTemplate<T_IGnss>::getLocationFromHW() {
|
|
||||||
float latitudeDegrees = gMockLatitudeDegrees;
|
|
||||||
float longitudeDegrees = gMockLongitudeDegrees;
|
|
||||||
float altitudeMeters = gMockAltitudeMeters;
|
|
||||||
float speedMetersPerSec = gMockSpeedMetersPerSec;
|
|
||||||
float bearingDegrees = gMockBearingDegrees;
|
|
||||||
float horizontalAccuracyMeters = kMockHorizontalAccuracyMeters;
|
|
||||||
float verticalAccuracyMeters = kMockVerticalAccuracyMeters;
|
|
||||||
float speedAccuracyMetersPerSecond = kMockSpeedAccuracyMetersPerSecond;
|
|
||||||
float bearingAccuracyDegrees = kMockBearingAccuracyDegrees;
|
|
||||||
int64_t timestamp = static_cast<int64_t>(time(NULL)) - 1;
|
|
||||||
|
|
||||||
const char * gnss_dev_path = GNSS_PATH;
|
|
||||||
int gnss_fd = open(gnss_dev_path, O_RDONLY);
|
|
||||||
if (gnss_fd != -1) {
|
|
||||||
int bytes_read = -1;
|
|
||||||
std::string inputStr = "";
|
|
||||||
char inputBuffer[INPUT_BUFFER_SIZE];
|
|
||||||
while (true) {
|
|
||||||
memset(inputBuffer, 0, INPUT_BUFFER_SIZE);
|
|
||||||
bytes_read = read(gnss_fd, &inputBuffer, INPUT_BUFFER_SIZE);
|
|
||||||
if (bytes_read <= 0) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
inputStr += std::string(inputBuffer, bytes_read);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::istringstream iss(inputStr);
|
|
||||||
std::string item;
|
|
||||||
while (std::getline(iss, item, LINE_SEPARATOR)) {
|
|
||||||
if (item.compare(0, strlen("LatitudeDegrees="), "LatitudeDegrees=") == 0) {
|
|
||||||
latitudeDegrees = std::stof(item.substr(strlen("LatitudeDegrees=")));
|
|
||||||
} else if (item.compare(0, strlen("LongitudeDegrees="), "LongitudeDegrees=") == 0) {
|
|
||||||
longitudeDegrees = std::stof(item.substr(strlen("LongitudeDegrees=")));
|
|
||||||
} else if (item.compare(0, strlen("AltitudeMeters="), "AltitudeMeters=") == 0) {
|
|
||||||
altitudeMeters = std::stof(item.substr(strlen("AltitudeMeters=")));
|
|
||||||
} else if (item.compare(0, strlen("SpeedMetersPerSec="), "SpeedMetersPerSec=") == 0) {
|
|
||||||
speedMetersPerSec = std::stof(item.substr(strlen("SpeedMetersPerSec=")));
|
|
||||||
} else if (item.compare(0, strlen("BearingDegrees="), "BearingDegrees=") == 0) {
|
|
||||||
bearingDegrees = std::stof(item.substr(strlen("BearingDegrees=")));
|
|
||||||
} else if (item.compare(0, strlen("HorizontalAccuracyMeters="), "HorizontalAccuracyMeters=") == 0) {
|
|
||||||
horizontalAccuracyMeters = std::stof(item.substr(strlen("HorizontalAccuracyMeters=")));
|
|
||||||
} else if (item.compare(0, strlen("VerticalAccuracyMeters="), "VerticalAccuracyMeters=") == 0) {
|
|
||||||
verticalAccuracyMeters = std::stof(item.substr(strlen("VerticalAccuracyMeters=")));
|
|
||||||
} else if (item.compare(0, strlen("SpeedAccuracyMetersPerSecond="), "SpeedAccuracyMetersPerSecond=") == 0) {
|
|
||||||
speedAccuracyMetersPerSecond = std::stof(item.substr(strlen("SpeedAccuracyMetersPerSecond=")));
|
|
||||||
} else if (item.compare(0, strlen("BearingAccuracyDegrees="), "BearingAccuracyDegrees=") == 0) {
|
|
||||||
bearingAccuracyDegrees = std::stof(item.substr(strlen("BearingAccuracyDegrees=")));
|
|
||||||
} else if (item.compare(0, strlen("Timestamp="), "Timestamp=") == 0) {
|
|
||||||
timestamp = std::stol(item.substr(strlen("Timestamp=")));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
close(gnss_fd);
|
|
||||||
} else {
|
|
||||||
ALOGW("Failed to open %s errno: %d", gnss_dev_path, errno);
|
|
||||||
}
|
|
||||||
|
|
||||||
const V2_0::ElapsedRealtime currentOsTimestamp = {
|
|
||||||
.flags = V2_0::ElapsedRealtimeFlags::HAS_TIMESTAMP_NS |
|
|
||||||
V2_0::ElapsedRealtimeFlags::HAS_TIME_UNCERTAINTY_NS,
|
|
||||||
.timestampNs = static_cast<uint64_t>(::android::elapsedRealtimeNano()),
|
|
||||||
// This is an hardcoded value indicating a 1ms of uncertainty between the two clocks.
|
|
||||||
// In an actual implementation provide an estimate of the synchronization uncertainty
|
|
||||||
// or don't set the field.
|
|
||||||
.timeUncertaintyNs = 1000000};
|
|
||||||
|
|
||||||
V1_0::GnssLocation locationV1 = {
|
|
||||||
.gnssLocationFlags = 0xFF,
|
|
||||||
.latitudeDegrees = latitudeDegrees,
|
|
||||||
.longitudeDegrees = longitudeDegrees,
|
|
||||||
.altitudeMeters = altitudeMeters,
|
|
||||||
.speedMetersPerSec = speedMetersPerSec,
|
|
||||||
.bearingDegrees = bearingDegrees,
|
|
||||||
.horizontalAccuracyMeters = horizontalAccuracyMeters,
|
|
||||||
.verticalAccuracyMeters = verticalAccuracyMeters,
|
|
||||||
.speedAccuracyMetersPerSecond = speedAccuracyMetersPerSecond,
|
|
||||||
.bearingAccuracyDegrees = bearingAccuracyDegrees,
|
|
||||||
.timestamp = timestamp};
|
|
||||||
|
|
||||||
V2_0::GnssLocation locationV2 = {.v1_0 = locationV1, .elapsedRealtime = currentOsTimestamp};
|
|
||||||
|
|
||||||
return std::make_unique<V2_0::GnssLocation>(locationV2);
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::start() {
|
|
||||||
if (mIsActive) {
|
|
||||||
ALOGW("Gnss has started. Restarting...");
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
mIsActive = true;
|
|
||||||
this->reportGnssStatusValue(V1_0::IGnssCallback::GnssStatusValue::SESSION_BEGIN);
|
|
||||||
mThread = std::thread([this]() {
|
|
||||||
while (mIsActive == true) {
|
|
||||||
auto svStatus = filterBlocklistedSatellitesV2_1(Utils::getMockSvInfoListV2_1());
|
|
||||||
this->reportSvStatus(svStatus);
|
|
||||||
auto currentLocation = getLocationFromHW();
|
|
||||||
notePowerConsumption();
|
|
||||||
if (currentLocation != nullptr) {
|
|
||||||
this->reportLocation(*currentLocation);
|
|
||||||
} else {
|
|
||||||
if (sGnssCallback_2_1 != nullptr || sGnssCallback_2_0 != nullptr) {
|
|
||||||
const auto location = Utils::getMockLocationV2_0();
|
|
||||||
this->reportLocation(location);
|
|
||||||
} else {
|
|
||||||
const auto location = Utils::getMockLocationV1_0();
|
|
||||||
this->reportLocation(location);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
std::this_thread::sleep_for(std::chrono::milliseconds(mMinIntervalMs));
|
|
||||||
}
|
|
||||||
});
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
hidl_vec<V2_1::IGnssCallback::GnssSvInfo> GnssTemplate<T_IGnss>::filterBlocklistedSatellitesV2_1(
|
|
||||||
hidl_vec<V2_1::IGnssCallback::GnssSvInfo> gnssSvInfoList) {
|
|
||||||
ALOGD("GnssTemplate::filterBlocklistedSatellitesV2_1");
|
|
||||||
for (uint32_t i = 0; i < gnssSvInfoList.size(); i++) {
|
|
||||||
if (mGnssConfiguration->isBlacklistedV2_1(gnssSvInfoList[i])) {
|
|
||||||
gnssSvInfoList[i].v2_0.v1_0.svFlag &=
|
|
||||||
~static_cast<uint8_t>(V1_0::IGnssCallback::GnssSvFlags::USED_IN_FIX);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return gnssSvInfoList;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
void GnssTemplate<T_IGnss>::notePowerConsumption() {
|
|
||||||
ALOGD("GnssTemplate::notePowerConsumption");
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::stop() {
|
|
||||||
ALOGD("stop");
|
|
||||||
mIsActive = false;
|
|
||||||
this->reportGnssStatusValue(V1_0::IGnssCallback::GnssStatusValue::SESSION_END);
|
|
||||||
if (mThread.joinable()) {
|
|
||||||
mThread.join();
|
|
||||||
}
|
|
||||||
if (mGnssFd != -1) {
|
|
||||||
close(mGnssFd);
|
|
||||||
mGnssFd = -1;
|
|
||||||
mHardwareModeChecked = false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V1_0::IGnss follow.
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::setCallback(const sp<V1_0::IGnssCallback>& callback) {
|
|
||||||
if (callback == nullptr) {
|
|
||||||
ALOGE("%s: Null callback ignored", __func__);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
sGnssCallback_1_0 = callback;
|
|
||||||
|
|
||||||
uint32_t capabilities = 0x0 | V1_0::IGnssCallback::Capabilities::MEASUREMENTS |
|
|
||||||
V1_0::IGnssCallback::Capabilities::SCHEDULING;
|
|
||||||
auto ret = sGnssCallback_1_0->gnssSetCapabilitesCb(capabilities);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
V2_1::IGnssCallback::GnssSystemInfo gnssInfo = {.yearOfHw = 2018};
|
|
||||||
|
|
||||||
ret = sGnssCallback_1_0->gnssSetSystemInfoCb(gnssInfo);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<void> GnssTemplate<T_IGnss>::cleanup() {
|
|
||||||
sGnssCallback_2_1 = nullptr;
|
|
||||||
sGnssCallback_2_0 = nullptr;
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::injectTime(int64_t, int64_t, int32_t) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::injectLocation(double, double, float) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<void> GnssTemplate<T_IGnss>::deleteAidingData(V1_0::IGnss::GnssAidingData) {
|
|
||||||
// TODO implement
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::setPositionMode(V1_0::IGnss::GnssPositionMode,
|
|
||||||
V1_0::IGnss::GnssPositionRecurrence,
|
|
||||||
uint32_t minIntervalMs, uint32_t, uint32_t) {
|
|
||||||
mMinIntervalMs = minIntervalMs;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IAGnssRil>> GnssTemplate<T_IGnss>::getExtensionAGnssRil() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IAGnssRil>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssGeofencing>> GnssTemplate<T_IGnss>::getExtensionGnssGeofencing() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IGnssGeofencing>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IAGnss>> GnssTemplate<T_IGnss>::getExtensionAGnss() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IAGnss>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssNi>> GnssTemplate<T_IGnss>::getExtensionGnssNi() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IGnssNi>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssMeasurement>> GnssTemplate<T_IGnss>::getExtensionGnssMeasurement() {
|
|
||||||
ALOGD("Gnss::getExtensionGnssMeasurement");
|
|
||||||
return new V2_1::implementation::GnssMeasurement();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssNavigationMessage>>
|
|
||||||
GnssTemplate<T_IGnss>::getExtensionGnssNavigationMessage() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IGnssNavigationMessage>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssXtra>> GnssTemplate<T_IGnss>::getExtensionXtra() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IGnssXtra>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssConfiguration>> GnssTemplate<T_IGnss>::getExtensionGnssConfiguration() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IGnssConfiguration>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssDebug>> GnssTemplate<T_IGnss>::getExtensionGnssDebug() {
|
|
||||||
return new V1_1::implementation::GnssDebug();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_0::IGnssBatching>> GnssTemplate<T_IGnss>::getExtensionGnssBatching() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_0::IGnssBatching>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V1_1::IGnss follow.
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::setCallback_1_1(const sp<V1_1::IGnssCallback>& callback) {
|
|
||||||
if (callback == nullptr) {
|
|
||||||
ALOGE("%s: Null callback ignored", __func__);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
sGnssCallback_1_1 = callback;
|
|
||||||
|
|
||||||
uint32_t capabilities = 0x0;
|
|
||||||
auto ret = sGnssCallback_1_1->gnssSetCapabilitesCb(capabilities);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
V2_1::IGnssCallback::GnssSystemInfo gnssInfo = {.yearOfHw = 2018};
|
|
||||||
|
|
||||||
ret = sGnssCallback_1_1->gnssSetSystemInfoCb(gnssInfo);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
auto gnssName = "Google Mock GNSS Implementation v2.1";
|
|
||||||
ret = sGnssCallback_1_1->gnssNameCb(gnssName);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::setPositionMode_1_1(V1_0::IGnss::GnssPositionMode,
|
|
||||||
V1_0::IGnss::GnssPositionRecurrence,
|
|
||||||
uint32_t minIntervalMs, uint32_t, uint32_t,
|
|
||||||
bool) {
|
|
||||||
mMinIntervalMs = minIntervalMs;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_1::IGnssConfiguration>> GnssTemplate<T_IGnss>::getExtensionGnssConfiguration_1_1() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_1::IGnssConfiguration>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V1_1::IGnssMeasurement>> GnssTemplate<T_IGnss>::getExtensionGnssMeasurement_1_1() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V1_1::IGnssMeasurement>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::injectBestLocation(const V1_0::GnssLocation&) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V2_0::IGnss follow.
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::setCallback_2_0(const sp<V2_0::IGnssCallback>& callback) {
|
|
||||||
ALOGD("Gnss::setCallback_2_0");
|
|
||||||
if (callback == nullptr) {
|
|
||||||
ALOGE("%s: Null callback ignored", __func__);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
sGnssCallback_2_0 = callback;
|
|
||||||
|
|
||||||
using Capabilities = V2_0::IGnssCallback::Capabilities;
|
|
||||||
const auto capabilities = Capabilities::MEASUREMENTS | Capabilities::MEASUREMENT_CORRECTIONS |
|
|
||||||
Capabilities::LOW_POWER_MODE | Capabilities::SATELLITE_BLACKLIST;
|
|
||||||
auto ret = sGnssCallback_2_0->gnssSetCapabilitiesCb_2_0(capabilities);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
V1_1::IGnssCallback::GnssSystemInfo gnssInfo = {.yearOfHw = 2019};
|
|
||||||
|
|
||||||
ret = sGnssCallback_2_0->gnssSetSystemInfoCb(gnssInfo);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
auto gnssName = "Google Mock GNSS Implementation v2.1";
|
|
||||||
ret = sGnssCallback_2_0->gnssNameCb(gnssName);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_0::IGnssConfiguration>> GnssTemplate<T_IGnss>::getExtensionGnssConfiguration_2_0() {
|
|
||||||
ALOGD("Gnss::getExtensionGnssConfiguration_2_0");
|
|
||||||
return mGnssConfiguration;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_0::IGnssDebug>> GnssTemplate<T_IGnss>::getExtensionGnssDebug_2_0() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V2_0::IGnssDebug>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_0::IAGnss>> GnssTemplate<T_IGnss>::getExtensionAGnss_2_0() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V2_0::IAGnss>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_0::IAGnssRil>> GnssTemplate<T_IGnss>::getExtensionAGnssRil_2_0() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V2_0::IAGnssRil>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_0::IGnssMeasurement>> GnssTemplate<T_IGnss>::getExtensionGnssMeasurement_2_0() {
|
|
||||||
ALOGD("Gnss::getExtensionGnssMeasurement_2_0");
|
|
||||||
return new V2_1::implementation::GnssMeasurement();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<measurement_corrections::V1_0::IMeasurementCorrections>>
|
|
||||||
GnssTemplate<T_IGnss>::getExtensionMeasurementCorrections() {
|
|
||||||
ALOGD("Gnss::getExtensionMeasurementCorrections()");
|
|
||||||
return new measurement_corrections::V1_1::implementation::GnssMeasurementCorrections();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<visibility_control::V1_0::IGnssVisibilityControl>>
|
|
||||||
GnssTemplate<T_IGnss>::getExtensionVisibilityControl() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<visibility_control::V1_0::IGnssVisibilityControl>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_0::IGnssBatching>> GnssTemplate<T_IGnss>::getExtensionGnssBatching_2_0() {
|
|
||||||
// TODO implement
|
|
||||||
return ::android::sp<V2_0::IGnssBatching>{};
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::injectBestLocation_2_0(const V2_0::GnssLocation&) {
|
|
||||||
// TODO(b/124012850): Implement function.
|
|
||||||
return bool{};
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V2_1::IGnss follow.
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<bool> GnssTemplate<T_IGnss>::setCallback_2_1(const sp<V2_1::IGnssCallback>& callback) {
|
|
||||||
ALOGD("Gnss::setCallback_2_1");
|
|
||||||
if (callback == nullptr) {
|
|
||||||
ALOGE("%s: Null callback ignored", __func__);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
sGnssCallback_2_1 = callback;
|
|
||||||
|
|
||||||
using Capabilities = V2_1::IGnssCallback::Capabilities;
|
|
||||||
const auto capabilities = Capabilities::MEASUREMENTS | Capabilities::MEASUREMENT_CORRECTIONS |
|
|
||||||
Capabilities::LOW_POWER_MODE | Capabilities::SATELLITE_BLACKLIST |
|
|
||||||
Capabilities::ANTENNA_INFO;
|
|
||||||
auto ret = sGnssCallback_2_1->gnssSetCapabilitiesCb_2_1(capabilities);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
V1_1::IGnssCallback::GnssSystemInfo gnssInfo = {.yearOfHw = 2020};
|
|
||||||
|
|
||||||
ret = sGnssCallback_2_1->gnssSetSystemInfoCb(gnssInfo);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
auto gnssName = "Android Mock GNSS Implementation v2.1";
|
|
||||||
ret = sGnssCallback_2_1->gnssNameCb(gnssName);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_1::IGnssMeasurement>> GnssTemplate<T_IGnss>::getExtensionGnssMeasurement_2_1() {
|
|
||||||
ALOGD("Gnss::getExtensionGnssMeasurement_2_1");
|
|
||||||
return new V2_1::implementation::GnssMeasurement();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_1::IGnssConfiguration>> GnssTemplate<T_IGnss>::getExtensionGnssConfiguration_2_1() {
|
|
||||||
ALOGD("Gnss::getExtensionGnssConfiguration_2_1");
|
|
||||||
return mGnssConfiguration;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<measurement_corrections::V1_1::IMeasurementCorrections>>
|
|
||||||
GnssTemplate<T_IGnss>::getExtensionMeasurementCorrections_1_1() {
|
|
||||||
ALOGD("Gnss::getExtensionMeasurementCorrections_1_1()");
|
|
||||||
return new measurement_corrections::V1_1::implementation::GnssMeasurementCorrections();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<sp<V2_1::IGnssAntennaInfo>> GnssTemplate<T_IGnss>::getExtensionGnssAntennaInfo() {
|
|
||||||
ALOGD("Gnss::getExtensionGnssAntennaInfo");
|
|
||||||
return new V2_1::implementation::GnssAntennaInfo();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
void GnssTemplate<T_IGnss>::reportGnssStatusValue(
|
|
||||||
const V1_0::IGnssCallback::GnssStatusValue gnssStatusValue) const {
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
if (sGnssCallback_2_1 == nullptr) {
|
|
||||||
ALOGE("%s: sGnssCallback v2.1 is null.", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
auto ret = sGnssCallback_2_1->gnssStatusCb(gnssStatusValue);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
void GnssTemplate<T_IGnss>::reportSvStatus(
|
|
||||||
const hidl_vec<V2_1::IGnssCallback::GnssSvInfo>& svInfoList) const {
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
// TODO(skz): update this to call 2_0 callback if non-null
|
|
||||||
if (sGnssCallback_2_1 == nullptr) {
|
|
||||||
ALOGE("%s: sGnssCallback v2.1 is null.", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
auto ret = sGnssCallback_2_1->gnssSvStatusCb_2_1(svInfoList);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
void GnssTemplate<T_IGnss>::reportLocation(const V1_0::GnssLocation& location) const {
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
if (sGnssCallback_1_1 != nullptr) {
|
|
||||||
auto ret = sGnssCallback_1_1->gnssLocationCb(location);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback v1.1", __func__);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (sGnssCallback_1_0 == nullptr) {
|
|
||||||
ALOGE("%s: No non-null callback", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
auto ret = sGnssCallback_1_0->gnssLocationCb(location);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback v1.0", __func__);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
void GnssTemplate<T_IGnss>::reportLocation(const V2_0::GnssLocation& location) const {
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
if (sGnssCallback_2_1 != nullptr) {
|
|
||||||
auto ret = sGnssCallback_2_1->gnssLocationCb_2_0(location);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback v2.1", __func__);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (sGnssCallback_2_0 == nullptr) {
|
|
||||||
ALOGE("%s: No non-null callback", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
auto ret = sGnssCallback_2_0->gnssLocationCb_2_0(location);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback v2.0", __func__);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<void> GnssTemplate<T_IGnss>::setLocation(const hidl_handle& fd,
|
|
||||||
const hidl_vec<hidl_string>& options) {
|
|
||||||
auto lat = gMockLatitudeDegrees;
|
|
||||||
auto lon = gMockLongitudeDegrees;
|
|
||||||
auto ele = gMockAltitudeMeters;
|
|
||||||
auto bea = gMockBearingDegrees;
|
|
||||||
auto spd = gMockSpeedMetersPerSec;
|
|
||||||
|
|
||||||
for (size_t i = 1; i < options.size(); ++i) {
|
|
||||||
std::string option = options[i];
|
|
||||||
if (option.rfind("lat=", 0) == 0) {
|
|
||||||
option = option.substr(4);
|
|
||||||
lat = stof(option);
|
|
||||||
} else if (option.rfind("lon=", 0) == 0) {
|
|
||||||
option = option.substr(4);
|
|
||||||
lon = stof(option);
|
|
||||||
} else if (option.rfind("ele=", 0) == 0) {
|
|
||||||
option = option.substr(4);
|
|
||||||
ele = stof(option);
|
|
||||||
} else if (option.rfind("bea=", 0) == 0) {
|
|
||||||
option = option.substr(4);
|
|
||||||
bea = stof(option);
|
|
||||||
} else if (option.rfind("spd=", 0) == 0) {
|
|
||||||
option = option.substr(4);
|
|
||||||
spd = stof(option);
|
|
||||||
} else {
|
|
||||||
dprintf(fd->data[0], "unsupported location argument: %s\n", option.c_str());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
gMockLatitudeDegrees = lat;
|
|
||||||
gMockLongitudeDegrees = lon;
|
|
||||||
gMockAltitudeMeters = ele;
|
|
||||||
gMockBearingDegrees = bea;
|
|
||||||
gMockSpeedMetersPerSec = spd;
|
|
||||||
|
|
||||||
dprintf(fd->data[0], "mock location updated to lat=%f lon=%f ele=%f bea=%f spd=%f\n",
|
|
||||||
gMockLatitudeDegrees, gMockLongitudeDegrees, gMockAltitudeMeters, gMockBearingDegrees,
|
|
||||||
gMockSpeedMetersPerSec);
|
|
||||||
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<void> GnssTemplate<T_IGnss>::help(const hidl_handle& fd) {
|
|
||||||
dprintf(fd->data[0],
|
|
||||||
"invalid option for Gnss HAL; valid options are:\n"
|
|
||||||
"location [lat=..] [lon=..] [ele=..] [bea=..] [spd=..]\n");
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
template <class T_IGnss>
|
|
||||||
Return<void> GnssTemplate<T_IGnss>::debug(const hidl_handle& fd,
|
|
||||||
const hidl_vec<hidl_string>& options) {
|
|
||||||
if (fd == nullptr || fd->numFds == 0) {
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (options.size() == 0) {
|
|
||||||
return help(fd);
|
|
||||||
} else if (options[0] == "location") {
|
|
||||||
return setLocation(fd, options);
|
|
||||||
} else {
|
|
||||||
return help(fd);
|
|
||||||
}
|
|
||||||
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::common::implementation
|
|
||||||
@@ -1,101 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2020 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssAntennaInfo"
|
|
||||||
|
|
||||||
#include "v2_1/GnssAntennaInfo.h"
|
|
||||||
#include "Utils.h"
|
|
||||||
|
|
||||||
#include <log/log.h>
|
|
||||||
|
|
||||||
using ::android::hardware::gnss::common::Utils;
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V2_1::implementation {
|
|
||||||
|
|
||||||
sp<IGnssAntennaInfoCallback> GnssAntennaInfo::sCallback = nullptr;
|
|
||||||
|
|
||||||
GnssAntennaInfo::GnssAntennaInfo() : mMinIntervalMillis(1000) {}
|
|
||||||
|
|
||||||
GnssAntennaInfo::~GnssAntennaInfo() {
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V2_1::IGnssAntennaInfo follow.
|
|
||||||
Return<GnssAntennaInfo::GnssAntennaInfoStatus> GnssAntennaInfo::setCallback(
|
|
||||||
const sp<IGnssAntennaInfoCallback>& callback) {
|
|
||||||
ALOGD("setCallback");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback = callback;
|
|
||||||
|
|
||||||
if (mIsActive) {
|
|
||||||
ALOGW("GnssAntennaInfo callback already set. Resetting the callback...");
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
start();
|
|
||||||
|
|
||||||
return GnssAntennaInfoStatus::SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<void> GnssAntennaInfo::close() {
|
|
||||||
ALOGD("close");
|
|
||||||
stop();
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback = nullptr;
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Private methods
|
|
||||||
void GnssAntennaInfo::start() {
|
|
||||||
ALOGD("start");
|
|
||||||
mIsActive = true;
|
|
||||||
mThread = std::thread([this]() {
|
|
||||||
while (mIsActive == true) {
|
|
||||||
if (sCallback != nullptr) {
|
|
||||||
auto antennaInfos = Utils::getMockAntennaInfos();
|
|
||||||
this->reportAntennaInfo(antennaInfos);
|
|
||||||
}
|
|
||||||
|
|
||||||
/** For mock implementation this is good. On real device, we should only report
|
|
||||||
antennaInfo at start and when there is a configuration change. **/
|
|
||||||
std::this_thread::sleep_for(std::chrono::milliseconds(mMinIntervalMillis));
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssAntennaInfo::stop() {
|
|
||||||
ALOGD("stop");
|
|
||||||
mIsActive = false;
|
|
||||||
if (mThread.joinable()) {
|
|
||||||
mThread.join();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssAntennaInfo::reportAntennaInfo(
|
|
||||||
const hidl_vec<IGnssAntennaInfoCallback::GnssAntennaInfo>& antennaInfo) const {
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
|
|
||||||
if (sCallback == nullptr) {
|
|
||||||
ALOGE("%s: No non-null callback", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
auto ret = sCallback->gnssAntennaInfoCb(antennaInfo);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V2_1::implementation
|
|
||||||
@@ -1,101 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssConfiguration"
|
|
||||||
|
|
||||||
#include "v2_1/GnssConfiguration.h"
|
|
||||||
#include <log/log.h>
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V2_1::implementation {
|
|
||||||
|
|
||||||
using GnssSvInfoV2_1 = V2_1::IGnssCallback::GnssSvInfo;
|
|
||||||
using BlacklistedSourceV2_1 = V2_1::IGnssConfiguration::BlacklistedSource;
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V1_0::IGnssConfiguration follow.
|
|
||||||
Return<bool> GnssConfiguration::setSuplEs(bool enable) {
|
|
||||||
ALOGD("setSuplEs enable: %d", enable);
|
|
||||||
// Method deprecated in 2.0 and not expected to be called by the framework.
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssConfiguration::setSuplVersion(uint32_t) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssConfiguration::setSuplMode(hidl_bitfield<SuplMode>) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssConfiguration::setGpsLock(hidl_bitfield<GpsLock> gpsLock) {
|
|
||||||
ALOGD("setGpsLock gpsLock: %hhu", static_cast<GpsLock>(gpsLock));
|
|
||||||
// Method deprecated in 2.0 and not expected to be called by the framework.
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssConfiguration::setLppProfile(hidl_bitfield<LppProfile>) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssConfiguration::setGlonassPositioningProtocol(hidl_bitfield<GlonassPosProtocol>) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssConfiguration::setEmergencySuplPdn(bool) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V1_1::IGnssConfiguration follow.
|
|
||||||
Return<bool> GnssConfiguration::setBlacklist(
|
|
||||||
const hidl_vec<V1_1::IGnssConfiguration::BlacklistedSource>&) {
|
|
||||||
// TODO (b/122463906): Reuse 1.1 implementation.
|
|
||||||
return bool{};
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V2_0::IGnssConfiguration follow.
|
|
||||||
Return<bool> GnssConfiguration::setEsExtensionSec(uint32_t emergencyExtensionSeconds) {
|
|
||||||
ALOGD("setEsExtensionSec emergencyExtensionSeconds: %d", emergencyExtensionSeconds);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V2_1::IGnssConfiguration follow.
|
|
||||||
Return<bool> GnssConfiguration::setBlacklist_2_1(
|
|
||||||
const hidl_vec<BlacklistedSourceV2_1>& sourceList) {
|
|
||||||
std::unique_lock<std::recursive_mutex> lock(mMutex);
|
|
||||||
mBlacklistedConstellationSet.clear();
|
|
||||||
mBlacklistedSourceSet.clear();
|
|
||||||
for (auto source : sourceList) {
|
|
||||||
if (source.svid == 0) {
|
|
||||||
// Wildcard blacklist, i.e., blacklist entire constellation.
|
|
||||||
mBlacklistedConstellationSet.insert(source.constellation);
|
|
||||||
} else {
|
|
||||||
mBlacklistedSourceSet.insert(source);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssConfiguration::isBlacklistedV2_1(const GnssSvInfoV2_1& gnssSvInfo) const {
|
|
||||||
std::unique_lock<std::recursive_mutex> lock(mMutex);
|
|
||||||
if (mBlacklistedConstellationSet.find(gnssSvInfo.v2_0.constellation) !=
|
|
||||||
mBlacklistedConstellationSet.end()) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
BlacklistedSourceV2_1 source = {.constellation = gnssSvInfo.v2_0.constellation,
|
|
||||||
.svid = gnssSvInfo.v2_0.v1_0.svid};
|
|
||||||
return (mBlacklistedSourceSet.find(source) != mBlacklistedSourceSet.end());
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V2_1::implementation
|
|
||||||
@@ -1,55 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2016 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssDebug"
|
|
||||||
|
|
||||||
#include <log/log.h>
|
|
||||||
|
|
||||||
#include "Constants.h"
|
|
||||||
#include "MockLocation.h"
|
|
||||||
#include "v2_1/GnssDebug.h"
|
|
||||||
|
|
||||||
using namespace ::android::hardware::gnss::common;
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V1_1::implementation {
|
|
||||||
|
|
||||||
// Methods from ::android::hardware::gnss::V1_0::IGnssDebug follow.
|
|
||||||
Return<void> GnssDebug::getDebugData(V1_0::IGnssDebug::getDebugData_cb _hidl_cb) {
|
|
||||||
PositionDebug positionDebug = {
|
|
||||||
.valid = true,
|
|
||||||
.latitudeDegrees = gMockLatitudeDegrees,
|
|
||||||
.longitudeDegrees = gMockLongitudeDegrees,
|
|
||||||
.altitudeMeters = gMockAltitudeMeters,
|
|
||||||
.speedMetersPerSec = gMockSpeedMetersPerSec,
|
|
||||||
.bearingDegrees = gMockBearingDegrees,
|
|
||||||
.horizontalAccuracyMeters = kMockHorizontalAccuracyMeters,
|
|
||||||
.verticalAccuracyMeters = kMockVerticalAccuracyMeters,
|
|
||||||
.speedAccuracyMetersPerSecond = kMockSpeedAccuracyMetersPerSecond,
|
|
||||||
.bearingAccuracyDegrees = kMockBearingAccuracyDegrees,
|
|
||||||
.ageSeconds = 0.99};
|
|
||||||
|
|
||||||
TimeDebug timeDebug = {.timeEstimate = kMockTimestamp,
|
|
||||||
.timeUncertaintyNs = 1000,
|
|
||||||
.frequencyUncertaintyNsPerSec = 5.0e4};
|
|
||||||
|
|
||||||
DebugData data = {.position = positionDebug, .time = timeDebug};
|
|
||||||
|
|
||||||
_hidl_cb(data);
|
|
||||||
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V1_1::implementation
|
|
||||||
@@ -1,143 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssMeasurement"
|
|
||||||
|
|
||||||
#include "v2_1/GnssMeasurement.h"
|
|
||||||
#include <log/log.h>
|
|
||||||
#include "Utils.h"
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::V2_1::implementation {
|
|
||||||
|
|
||||||
using common::Utils;
|
|
||||||
|
|
||||||
sp<V2_1::IGnssMeasurementCallback> GnssMeasurement::sCallback_2_1 = nullptr;
|
|
||||||
sp<V2_0::IGnssMeasurementCallback> GnssMeasurement::sCallback_2_0 = nullptr;
|
|
||||||
|
|
||||||
GnssMeasurement::GnssMeasurement() : mMinIntervalMillis(1000) {}
|
|
||||||
|
|
||||||
GnssMeasurement::~GnssMeasurement() {
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V1_0::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> GnssMeasurement::setCallback(
|
|
||||||
const sp<V1_0::IGnssMeasurementCallback>&) {
|
|
||||||
// TODO implement
|
|
||||||
return V1_0::IGnssMeasurement::GnssMeasurementStatus{};
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<void> GnssMeasurement::close() {
|
|
||||||
ALOGD("close");
|
|
||||||
stop();
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback_2_1 = nullptr;
|
|
||||||
sCallback_2_0 = nullptr;
|
|
||||||
return Void();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V1_1::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> GnssMeasurement::setCallback_1_1(
|
|
||||||
const sp<V1_1::IGnssMeasurementCallback>&, bool) {
|
|
||||||
// TODO implement
|
|
||||||
return V1_0::IGnssMeasurement::GnssMeasurementStatus{};
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V2_0::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> GnssMeasurement::setCallback_2_0(
|
|
||||||
const sp<V2_0::IGnssMeasurementCallback>& callback, bool) {
|
|
||||||
ALOGD("setCallback_2_0");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback_2_0 = callback;
|
|
||||||
|
|
||||||
if (mIsActive) {
|
|
||||||
ALOGW("GnssMeasurement callback already set. Resetting the callback...");
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
start();
|
|
||||||
|
|
||||||
return V1_0::IGnssMeasurement::GnssMeasurementStatus::SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V2_1::IGnssMeasurement follow.
|
|
||||||
Return<V1_0::IGnssMeasurement::GnssMeasurementStatus> GnssMeasurement::setCallback_2_1(
|
|
||||||
const sp<V2_1::IGnssMeasurementCallback>& callback, bool) {
|
|
||||||
ALOGD("setCallback_2_1");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
sCallback_2_1 = callback;
|
|
||||||
|
|
||||||
if (mIsActive) {
|
|
||||||
ALOGW("GnssMeasurement callback already set. Resetting the callback...");
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
start();
|
|
||||||
|
|
||||||
return V1_0::IGnssMeasurement::GnssMeasurementStatus::SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssMeasurement::start() {
|
|
||||||
ALOGD("start");
|
|
||||||
mIsActive = true;
|
|
||||||
mThread = std::thread([this]() {
|
|
||||||
while (mIsActive == true) {
|
|
||||||
if (sCallback_2_1 != nullptr) {
|
|
||||||
auto measurement = Utils::getMockMeasurementV2_1();
|
|
||||||
this->reportMeasurement(measurement);
|
|
||||||
} else {
|
|
||||||
auto measurement = Utils::getMockMeasurementV2_0();
|
|
||||||
this->reportMeasurement(measurement);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::this_thread::sleep_for(std::chrono::milliseconds(mMinIntervalMillis));
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssMeasurement::stop() {
|
|
||||||
ALOGD("stop");
|
|
||||||
mIsActive = false;
|
|
||||||
if (mThread.joinable()) {
|
|
||||||
mThread.join();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssMeasurement::reportMeasurement(const V2_0::IGnssMeasurementCallback::GnssData& data) {
|
|
||||||
ALOGD("reportMeasurement()");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
if (sCallback_2_0 == nullptr) {
|
|
||||||
ALOGE("%s: GnssMeasurement::sCallback_2_0 is null.", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
auto ret = sCallback_2_0->gnssMeasurementCb_2_0(data);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void GnssMeasurement::reportMeasurement(const V2_1::IGnssMeasurementCallback::GnssData& data) {
|
|
||||||
ALOGD("reportMeasurement()");
|
|
||||||
std::unique_lock<std::mutex> lock(mMutex);
|
|
||||||
if (sCallback_2_1 == nullptr) {
|
|
||||||
ALOGE("%s: GnssMeasurement::sCallback_2_1 is null.", __func__);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
auto ret = sCallback_2_1->gnssMeasurementCb_2_1(data);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::V2_1::implementation
|
|
||||||
@@ -1,103 +0,0 @@
|
|||||||
/*
|
|
||||||
* Copyright (C) 2019 The Android Open Source Project
|
|
||||||
*
|
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
* you may not use this file except in compliance with the License.
|
|
||||||
* You may obtain a copy of the License at
|
|
||||||
*
|
|
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
*
|
|
||||||
* Unless required by applicable law or agreed to in writing, software
|
|
||||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
* See the License for the specific language governing permissions and
|
|
||||||
* limitations under the License.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define LOG_TAG "GnssMeasurementCorrections"
|
|
||||||
|
|
||||||
#include "v2_1/GnssMeasurementCorrections.h"
|
|
||||||
#include <log/log.h>
|
|
||||||
|
|
||||||
namespace android::hardware::gnss::measurement_corrections::V1_1::implementation {
|
|
||||||
|
|
||||||
GnssMeasurementCorrections::GnssMeasurementCorrections() {}
|
|
||||||
|
|
||||||
GnssMeasurementCorrections::~GnssMeasurementCorrections() {}
|
|
||||||
|
|
||||||
// Methods from V1_0::IMeasurementCorrections follow.
|
|
||||||
Return<bool> GnssMeasurementCorrections::setCorrections(
|
|
||||||
const V1_0::MeasurementCorrections& corrections) {
|
|
||||||
ALOGD("setCorrections");
|
|
||||||
ALOGD("corrections = lat: %f, lng: %f, alt: %f, hUnc: %f, vUnc: %f, toa: %llu, "
|
|
||||||
"satCorrections.size: %d",
|
|
||||||
corrections.latitudeDegrees, corrections.longitudeDegrees, corrections.altitudeMeters,
|
|
||||||
corrections.horizontalPositionUncertaintyMeters,
|
|
||||||
corrections.verticalPositionUncertaintyMeters,
|
|
||||||
static_cast<unsigned long long>(corrections.toaGpsNanosecondsOfWeek),
|
|
||||||
static_cast<int>(corrections.satCorrections.size()));
|
|
||||||
for (auto singleSatCorrection : corrections.satCorrections) {
|
|
||||||
ALOGD("singleSatCorrection = flags: %d, constellation: %d, svid: %d, cfHz: %f, probLos: %f,"
|
|
||||||
" epl: %f, eplUnc: %f",
|
|
||||||
static_cast<int>(singleSatCorrection.singleSatCorrectionFlags),
|
|
||||||
static_cast<int>(singleSatCorrection.constellation),
|
|
||||||
static_cast<int>(singleSatCorrection.svid), singleSatCorrection.carrierFrequencyHz,
|
|
||||||
singleSatCorrection.probSatIsLos, singleSatCorrection.excessPathLengthMeters,
|
|
||||||
singleSatCorrection.excessPathLengthUncertaintyMeters);
|
|
||||||
ALOGD("reflecting plane = lat: %f, lng: %f, alt: %f, azm: %f",
|
|
||||||
singleSatCorrection.reflectingPlane.latitudeDegrees,
|
|
||||||
singleSatCorrection.reflectingPlane.longitudeDegrees,
|
|
||||||
singleSatCorrection.reflectingPlane.altitudeMeters,
|
|
||||||
singleSatCorrection.reflectingPlane.azimuthDegrees);
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
Return<bool> GnssMeasurementCorrections::setCallback(
|
|
||||||
const sp<V1_0::IMeasurementCorrectionsCallback>& callback) {
|
|
||||||
using Capabilities = V1_0::IMeasurementCorrectionsCallback::Capabilities;
|
|
||||||
auto ret =
|
|
||||||
callback->setCapabilitiesCb(Capabilities::LOS_SATS | Capabilities::EXCESS_PATH_LENGTH |
|
|
||||||
Capabilities::REFLECTING_PLANE);
|
|
||||||
if (!ret.isOk()) {
|
|
||||||
ALOGE("%s: Unable to invoke callback", __func__);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Methods from V1_1::IMeasurementCorrections follow.
|
|
||||||
Return<bool> GnssMeasurementCorrections::setCorrections_1_1(
|
|
||||||
const V1_1::MeasurementCorrections& corrections) {
|
|
||||||
ALOGD("setCorrections_1_1");
|
|
||||||
ALOGD("corrections = lat: %f, lng: %f, alt: %f, hUnc: %f, vUnc: %f, toa: %llu,"
|
|
||||||
"satCorrections.size: %d, hasEnvironmentBearing: %d, environmentBearingDeg: %f,"
|
|
||||||
"environmentBearingUncDeg: %f",
|
|
||||||
corrections.v1_0.latitudeDegrees, corrections.v1_0.longitudeDegrees,
|
|
||||||
corrections.v1_0.altitudeMeters, corrections.v1_0.horizontalPositionUncertaintyMeters,
|
|
||||||
corrections.v1_0.verticalPositionUncertaintyMeters,
|
|
||||||
static_cast<unsigned long long>(corrections.v1_0.toaGpsNanosecondsOfWeek),
|
|
||||||
static_cast<int>(corrections.v1_0.satCorrections.size()),
|
|
||||||
corrections.hasEnvironmentBearing, corrections.environmentBearingDegrees,
|
|
||||||
corrections.environmentBearingUncertaintyDegrees);
|
|
||||||
for (auto singleSatCorrection : corrections.satCorrections) {
|
|
||||||
ALOGD("singleSatCorrection = flags: %d, constellation: %d, svid: %d, cfHz: %f, probLos: %f,"
|
|
||||||
" epl: %f, eplUnc: %f",
|
|
||||||
static_cast<int>(singleSatCorrection.v1_0.singleSatCorrectionFlags),
|
|
||||||
static_cast<int>(singleSatCorrection.constellation),
|
|
||||||
static_cast<int>(singleSatCorrection.v1_0.svid),
|
|
||||||
singleSatCorrection.v1_0.carrierFrequencyHz, singleSatCorrection.v1_0.probSatIsLos,
|
|
||||||
singleSatCorrection.v1_0.excessPathLengthMeters,
|
|
||||||
singleSatCorrection.v1_0.excessPathLengthUncertaintyMeters);
|
|
||||||
ALOGD("reflecting plane = lat: %f, lng: %f, alt: %f, azm: %f",
|
|
||||||
singleSatCorrection.v1_0.reflectingPlane.latitudeDegrees,
|
|
||||||
singleSatCorrection.v1_0.reflectingPlane.longitudeDegrees,
|
|
||||||
singleSatCorrection.v1_0.reflectingPlane.altitudeMeters,
|
|
||||||
singleSatCorrection.v1_0.reflectingPlane.azimuthDegrees);
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace android::hardware::gnss::measurement_corrections::V1_1::implementation
|
|
||||||
@@ -1,10 +1,28 @@
|
|||||||
#!/vendor/bin/sh
|
#!/vendor/bin/sh
|
||||||
|
|
||||||
|
# Create GPS data directory if it doesn't exist
|
||||||
|
if [ ! -d /data/vendor/gps ]; then
|
||||||
|
mkdir -p /data/vendor/gps
|
||||||
|
chmod 755 /data/vendor/gps
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Create legacy gnss file for compatibility
|
||||||
if [ ! -f /data/vendor/gps/gnss ]; then
|
if [ ! -f /data/vendor/gps/gnss ]; then
|
||||||
echo "LatitudeDegrees=30.281026818001678" > /data/vendor/gps/gnss
|
echo "LatitudeDegrees=30.281026818001678" > /data/vendor/gps/gnss
|
||||||
echo "LongitudeDegrees=120.01934876982831" >> /data/vendor/gps/gnss
|
echo "LongitudeDegrees=120.01934876982831" >> /data/vendor/gps/gnss
|
||||||
echo "AltitudeMeters=1.60062531" >> /data/vendor/gps/gnss
|
echo "AltitudeMeters=1.60062531" >> /data/vendor/gps/gnss
|
||||||
echo "BearingDegrees=0" >> /data/vendor/gps/gnss
|
echo "BearingDegrees=0" >> /data/vendor/gps/gnss
|
||||||
echo "SpeedMetersPerSec=0" >> /data/vendor/gps/gnss
|
echo "SpeedMetersPerSec=0" >> /data/vendor/gps/gnss
|
||||||
chmod 777 /data/vendor/gps/gnss
|
chmod 644 /data/vendor/gps/gnss
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
# Create custom location file for new JNI implementation
|
||||||
|
# This file uses simple "latitude,longitude" format
|
||||||
|
if [ ! -f /data/vendor/gps/custom_location.txt ]; then
|
||||||
|
echo "30.281026,120.019348" > /data/vendor/gps/custom_location.txt
|
||||||
|
chmod 644 /data/vendor/gps/custom_location.txt
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Set proper ownership and permissions
|
||||||
|
chown -R system:system /data/vendor/gps/
|
||||||
|
chmod 644 /data/vendor/gps/*
|
||||||
|
|||||||
82
gps/set_gps_location.sh
Normal file
82
gps/set_gps_location.sh
Normal file
@@ -0,0 +1,82 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# Redroid GPS位置设置脚本
|
||||||
|
# 用法: ./set_gps_location.sh <纬度> <经度>
|
||||||
|
# 示例: ./set_gps_location.sh 39.904989 116.405285
|
||||||
|
|
||||||
|
if [ $# -ne 2 ]; then
|
||||||
|
echo "用法: $0 <纬度> <经度>"
|
||||||
|
echo ""
|
||||||
|
echo "示例位置:"
|
||||||
|
echo " 北京天安门: $0 39.904989 116.405285"
|
||||||
|
echo " 上海外滩: $0 31.239666 121.499809"
|
||||||
|
echo " 广州塔: $0 23.109831 113.324504"
|
||||||
|
echo " 深圳地王: $0 22.544249 114.095298"
|
||||||
|
echo " 杭州西湖: $0 30.281026 120.019348"
|
||||||
|
echo ""
|
||||||
|
echo "坐标范围:"
|
||||||
|
echo " 纬度: -90 到 90"
|
||||||
|
echo " 经度: -180 到 180"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
LATITUDE=$1
|
||||||
|
LONGITUDE=$2
|
||||||
|
|
||||||
|
# 验证纬度范围
|
||||||
|
if (( $(echo "$LATITUDE < -90.0 || $LATITUDE > 90.0" | bc -l) )); then
|
||||||
|
echo "错误: 纬度必须在 -90 到 90 之间"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 验证经度范围
|
||||||
|
if (( $(echo "$LONGITUDE < -180.0 || $LONGITUDE > 180.0" | bc -l) )); then
|
||||||
|
echo "错误: 经度必须在 -180 到 180 之间"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
GPS_FILE="/data/vendor/gps/custom_location.txt"
|
||||||
|
|
||||||
|
echo "设置GPS位置为: 纬度 $LATITUDE, 经度 $LONGITUDE"
|
||||||
|
|
||||||
|
# 检查设备连接
|
||||||
|
if ! adb devices | grep -q "device$"; then
|
||||||
|
echo "错误: 未找到连接的Android设备"
|
||||||
|
echo "请确保:"
|
||||||
|
echo "1. 设备已连接并启用USB调试"
|
||||||
|
echo "2. 已授权计算机的USB调试请求"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 创建临时文件
|
||||||
|
TEMP_FILE=$(mktemp)
|
||||||
|
echo "$LATITUDE,$LONGITUDE" > "$TEMP_FILE"
|
||||||
|
|
||||||
|
# 推送到设备
|
||||||
|
echo "正在更新GPS位置文件..."
|
||||||
|
adb push "$TEMP_FILE" "$GPS_FILE"
|
||||||
|
|
||||||
|
if [ $? -eq 0 ]; then
|
||||||
|
echo "✅ GPS位置更新成功!"
|
||||||
|
|
||||||
|
# 设置正确权限
|
||||||
|
adb shell "chown system:system $GPS_FILE"
|
||||||
|
adb shell "chmod 644 $GPS_FILE"
|
||||||
|
|
||||||
|
# 验证文件内容
|
||||||
|
echo "📍 当前GPS位置:"
|
||||||
|
adb shell "cat $GPS_FILE"
|
||||||
|
|
||||||
|
echo ""
|
||||||
|
echo "💡 提示:"
|
||||||
|
echo "- 新位置将在下次GPS请求时生效"
|
||||||
|
echo "- 打开地图应用验证位置是否正确"
|
||||||
|
echo "- 查看日志: adb logcat | grep -i 'custom.*gps'"
|
||||||
|
|
||||||
|
else
|
||||||
|
echo "❌ GPS位置更新失败"
|
||||||
|
echo "请检查设备权限和连接状态"
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 清理临时文件
|
||||||
|
rm -f "$TEMP_FILE"
|
||||||
@@ -57,10 +57,10 @@ on post-fs-data
|
|||||||
|
|
||||||
# GPS
|
# GPS
|
||||||
on post-fs-data
|
on post-fs-data
|
||||||
mkdir /data/vendor/gps 0751 root root
|
mkdir /data/vendor/gps 0755 system system
|
||||||
exec -- /system/bin/sh /vendor/bin/hw/init.redroid.gps.sh
|
exec -- /system/bin/sh /vendor/bin/hw/init.redroid.gps.sh
|
||||||
|
|
||||||
service gnss /vendor/bin/hw/android.hardware.gnss-service
|
# service gnss /vendor/bin/hw/android.hardware.gnss-service
|
||||||
class hal
|
# class hal
|
||||||
user nobody
|
# user nobody
|
||||||
group nobody
|
# group nobody
|
||||||
@@ -45,7 +45,10 @@ PRODUCT_COPY_FILES += \
|
|||||||
# gps config
|
# gps config
|
||||||
######################
|
######################
|
||||||
PRODUCT_PACKAGES += \
|
PRODUCT_PACKAGES += \
|
||||||
android.hardware.gnss-service
|
libredroid_gps_jni
|
||||||
|
|
||||||
|
# PRODUCT_PACKAGES += \
|
||||||
|
# android.hardware.gnss-service
|
||||||
|
|
||||||
PRODUCT_COPY_FILES += \
|
PRODUCT_COPY_FILES += \
|
||||||
vendor/redroid/gps/init.redroid.gps.sh:$(TARGET_COPY_OUT_VENDOR)/bin/hw/init.redroid.gps.sh \
|
vendor/redroid/gps/init.redroid.gps.sh:$(TARGET_COPY_OUT_VENDOR)/bin/hw/init.redroid.gps.sh \
|
||||||
|
|||||||
Reference in New Issue
Block a user