blob: 21fea1c910cb0c7afc311dc69d49398e8acb22c2 [file] [log] [blame]
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001/*
2 * Copyright (C) 2008 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
Lifu Tang30f95a72016-01-07 23:20:38 -080017#define LOG_TAG "GnssLocationProvider"
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080018
Mike Lockwoodb8d90332010-10-18 17:59:48 -040019#define LOG_NDEBUG 0
Danke Xie22d1f9f2009-08-18 18:28:45 -040020
gomo48f1a642017-11-10 20:35:46 -080021#include <android/hardware/gnss/1.0/IGnss.h>
Wyatt Rileyfb840922017-11-08 15:07:58 -080022#include <android/hardware/gnss/1.1/IGnss.h>
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070023
gomo48f1a642017-11-10 20:35:46 -080024#include <android/hardware/gnss/1.0/IGnssMeasurement.h>
25#include <android/hardware/gnss/1.1/IGnssMeasurement.h>
Steven Morelandc95dca82017-08-01 10:18:40 -070026#include <nativehelper/JNIHelp.h>
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080027#include "jni.h"
Mike Lockwood8f5a8002010-04-07 09:05:26 -040028#include "hardware_legacy/power.h"
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080029#include "utils/Log.h"
30#include "utils/misc.h"
Mike Lockwoodf602d362010-06-20 14:28:16 -070031#include "android_runtime/AndroidRuntime.h"
Ruben Brunk87eac992013-09-09 17:44:59 -070032#include "android_runtime/Log.h"
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080033
destradaa931a37f2014-08-12 16:36:59 -070034#include <arpa/inet.h>
Lifu Tang38bce792016-02-24 17:17:38 -080035#include <limits>
destradaa96a14702014-06-05 11:36:30 -070036#include <linux/in.h>
37#include <linux/in6.h>
Lifu Tang38bce792016-02-24 17:17:38 -080038#include <pthread.h>
39#include <string.h>
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070040#include <cinttypes>
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080041
Mike Lockwoodf602d362010-06-20 14:28:16 -070042static jobject mCallbacksObj = NULL;
43
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080044static jmethodID method_reportLocation;
45static jmethodID method_reportStatus;
46static jmethodID method_reportSvStatus;
Mike Lockwoode3635c92009-05-11 08:38:02 -040047static jmethodID method_reportAGpsStatus;
Mike Lockwoodb16e7802009-08-06 09:26:02 -040048static jmethodID method_reportNmea;
Mike Lockwood04598b62010-04-14 17:17:24 -040049static jmethodID method_setEngineCapabilities;
Lifu Tang9363b942016-02-16 18:07:00 -080050static jmethodID method_setGnssYearOfHardware;
Wyatt Rileyd87cf912017-12-05 09:31:52 -080051static jmethodID method_setGnssHardwareModelName;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080052static jmethodID method_xtraDownloadRequest;
Danke Xie22d1f9f2009-08-18 18:28:45 -040053static jmethodID method_reportNiNotification;
Yu-Han Yange7baef32018-02-09 13:58:17 -080054static jmethodID method_requestLocation;
Miguel Torroja1e84da82010-07-27 07:02:24 +020055static jmethodID method_requestRefLocation;
56static jmethodID method_requestSetID;
Mike Lockwood9b9fb5c2011-06-29 15:09:40 -040057static jmethodID method_requestUtcTime;
Jaikumar Ganesh8ce470d2013-04-03 12:22:18 -070058static jmethodID method_reportGeofenceTransition;
59static jmethodID method_reportGeofenceStatus;
60static jmethodID method_reportGeofenceAddStatus;
61static jmethodID method_reportGeofenceRemoveStatus;
62static jmethodID method_reportGeofencePauseStatus;
63static jmethodID method_reportGeofenceResumeStatus;
destradaaea8a8a62014-06-23 18:19:03 -070064static jmethodID method_reportMeasurementData;
destradaa4b3e3932014-07-21 18:01:47 -070065static jmethodID method_reportNavigationMessages;
Wyatt Rileycf879db2017-01-12 13:57:38 -080066static jmethodID method_reportLocationBatch;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080067
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -080068/*
69 * Save a pointer to JavaVm to attach/detach threads executing
70 * callback methods that need to make JNI calls.
71 */
72static JavaVM* sJvm;
73
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070074using android::OK;
75using android::sp;
gomo25208882017-04-15 02:05:25 -070076using android::wp;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070077using android::status_t;
78using android::String16;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080079
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070080using android::hardware::Return;
81using android::hardware::Void;
82using android::hardware::hidl_vec;
gomo25208882017-04-15 02:05:25 -070083using android::hardware::hidl_death_recipient;
Wyatt Rileyfb840922017-11-08 15:07:58 -080084using android::hardware::gnss::V1_0::GnssLocation;
85using android::hardware::gnss::V1_0::GnssLocationFlags;
Wyatt Riley46ac9562018-03-02 20:16:58 -080086
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070087using android::hardware::gnss::V1_0::IAGnss;
88using android::hardware::gnss::V1_0::IAGnssCallback;
89using android::hardware::gnss::V1_0::IAGnssCallback;
90using android::hardware::gnss::V1_0::IAGnssRil;
91using android::hardware::gnss::V1_0::IAGnssRilCallback;
Wyatt Rileycf879db2017-01-12 13:57:38 -080092using android::hardware::gnss::V1_0::IGnssBatching;
93using android::hardware::gnss::V1_0::IGnssBatchingCallback;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070094using android::hardware::gnss::V1_0::IGnssConfiguration;
95using android::hardware::gnss::V1_0::IGnssDebug;
96using android::hardware::gnss::V1_0::IGnssGeofenceCallback;
97using android::hardware::gnss::V1_0::IGnssGeofencing;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -070098using android::hardware::gnss::V1_0::IGnssNavigationMessage;
99using android::hardware::gnss::V1_0::IGnssNavigationMessageCallback;
100using android::hardware::gnss::V1_0::IGnssNi;
101using android::hardware::gnss::V1_0::IGnssNiCallback;
102using android::hardware::gnss::V1_0::IGnssXtra;
103using android::hardware::gnss::V1_0::IGnssXtraCallback;
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800104
Wyatt Rileyfb840922017-11-08 15:07:58 -0800105using android::hardware::gnss::V1_1::IGnssCallback;
Wyatt Riley46ac9562018-03-02 20:16:58 -0800106
107using android::hidl::base::V1_0::IBase;
108
109using IGnss_V1_0 = android::hardware::gnss::V1_0::IGnss;
110using IGnss_V1_1 = android::hardware::gnss::V1_1::IGnss;
111using IGnssMeasurement_V1_0 = android::hardware::gnss::V1_0::IGnssMeasurement;
112using IGnssMeasurement_V1_1 = android::hardware::gnss::V1_1::IGnssMeasurement;
113using IGnssMeasurementCallback_V1_0 = android::hardware::gnss::V1_0::IGnssMeasurementCallback;
114using IGnssMeasurementCallback_V1_1 = android::hardware::gnss::V1_1::IGnssMeasurementCallback;
115
Wyatt Rileyfb840922017-11-08 15:07:58 -0800116
gomo25208882017-04-15 02:05:25 -0700117struct GnssDeathRecipient : virtual public hidl_death_recipient
118{
119 // hidl_death_recipient interface
120 virtual void serviceDied(uint64_t cookie, const wp<IBase>& who) override {
Wyatt Rileyfb840922017-11-08 15:07:58 -0800121 // TODO(b/37460011): implement a better death recovery mechanism without
gomo25208882017-04-15 02:05:25 -0700122 // crashing system server process as described in go//treble-gnss-death
123 LOG_ALWAYS_FATAL("Abort due to IGNSS hidl service failure,"
124 " restarting system server");
125 }
126};
Wyatt Rileyf6527ae2016-05-23 15:23:12 -0700127
Wyatt Riley4cbcb412018-01-23 18:07:05 -0800128// Must match the value from GnssMeasurement.java
129static const uint32_t ADR_STATE_HALF_CYCLE_REPORTED = (1<<4);
130
gomo25208882017-04-15 02:05:25 -0700131sp<GnssDeathRecipient> gnssHalDeathRecipient = nullptr;
Wyatt Riley46ac9562018-03-02 20:16:58 -0800132sp<IGnss_V1_0> gnssHal = nullptr;
gomo48f1a642017-11-10 20:35:46 -0800133sp<IGnss_V1_1> gnssHal_V1_1 = nullptr;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700134sp<IGnssXtra> gnssXtraIface = nullptr;
135sp<IAGnssRil> agnssRilIface = nullptr;
136sp<IGnssGeofencing> gnssGeofencingIface = nullptr;
137sp<IAGnss> agnssIface = nullptr;
Wyatt Rileycf879db2017-01-12 13:57:38 -0800138sp<IGnssBatching> gnssBatchingIface = nullptr;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700139sp<IGnssDebug> gnssDebugIface = nullptr;
140sp<IGnssConfiguration> gnssConfigurationIface = nullptr;
141sp<IGnssNi> gnssNiIface = nullptr;
gomo48f1a642017-11-10 20:35:46 -0800142sp<IGnssMeasurement_V1_0> gnssMeasurementIface = nullptr;
143sp<IGnssMeasurement_V1_1> gnssMeasurementIface_V1_1 = nullptr;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700144sp<IGnssNavigationMessage> gnssNavigationMessageIface = nullptr;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800145
Mike Lockwood8f5a8002010-04-07 09:05:26 -0400146#define WAKE_LOCK_NAME "GPS"
147
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800148namespace android {
149
Lifu Tang120480f2016-02-07 18:08:19 -0800150template<class T>
151class JavaMethodHelper {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700152 public:
153 // Helper function to call setter on a Java object.
154 static void callJavaMethod(
Lifu Tang120480f2016-02-07 18:08:19 -0800155 JNIEnv* env,
156 jclass clazz,
157 jobject object,
158 const char* method_name,
159 T value);
destradaaea8a8a62014-06-23 18:19:03 -0700160
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700161 private:
Lifu Tang120480f2016-02-07 18:08:19 -0800162 static const char *const signature_;
163};
Lifu Tange5a0e212016-01-25 18:02:17 -0800164
Lifu Tang120480f2016-02-07 18:08:19 -0800165template<class T>
166void JavaMethodHelper<T>::callJavaMethod(
167 JNIEnv* env,
168 jclass clazz,
169 jobject object,
170 const char* method_name,
171 T value) {
172 jmethodID method = env->GetMethodID(clazz, method_name, signature_);
173 env->CallVoidMethod(object, method, value);
174}
destradaaea8a8a62014-06-23 18:19:03 -0700175
Lifu Tang120480f2016-02-07 18:08:19 -0800176class JavaObject {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700177 public:
178 JavaObject(JNIEnv* env, const char* class_name);
Wyatt Rileycf879db2017-01-12 13:57:38 -0800179 JavaObject(JNIEnv* env, const char* class_name, const char * sz_arg_1);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700180 virtual ~JavaObject();
Lifu Tang120480f2016-02-07 18:08:19 -0800181
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700182 template<class T>
183 void callSetter(const char* method_name, T value);
184 template<class T>
185 void callSetter(const char* method_name, T* value, size_t size);
186 jobject get();
Lifu Tang120480f2016-02-07 18:08:19 -0800187
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700188 private:
189 JNIEnv* env_;
190 jclass clazz_;
191 jobject object_;
Lifu Tang120480f2016-02-07 18:08:19 -0800192};
193
194JavaObject::JavaObject(JNIEnv* env, const char* class_name) : env_(env) {
195 clazz_ = env_->FindClass(class_name);
196 jmethodID ctor = env->GetMethodID(clazz_, "<init>", "()V");
197 object_ = env_->NewObject(clazz_, ctor);
198}
199
Wyatt Rileycf879db2017-01-12 13:57:38 -0800200JavaObject::JavaObject(JNIEnv* env, const char* class_name, const char * sz_arg_1) : env_(env) {
201 clazz_ = env_->FindClass(class_name);
202 jmethodID ctor = env->GetMethodID(clazz_, "<init>", "(Ljava/lang/String;)V");
203 object_ = env_->NewObject(clazz_, ctor, env->NewStringUTF(sz_arg_1));
204}
205
Lifu Tang120480f2016-02-07 18:08:19 -0800206JavaObject::~JavaObject() {
207 env_->DeleteLocalRef(clazz_);
208}
209
210template<class T>
211void JavaObject::callSetter(const char* method_name, T value) {
212 JavaMethodHelper<T>::callJavaMethod(
213 env_, clazz_, object_, method_name, value);
214}
215
216template<>
217void JavaObject::callSetter(
218 const char* method_name, uint8_t* value, size_t size) {
219 jbyteArray array = env_->NewByteArray(size);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700220 env_->SetByteArrayRegion(array, 0, size, reinterpret_cast<jbyte*>(value));
Lifu Tang120480f2016-02-07 18:08:19 -0800221 jmethodID method = env_->GetMethodID(
222 clazz_,
223 method_name,
224 "([B)V");
225 env_->CallVoidMethod(object_, method, array);
Lifu Tangfe427f22016-10-08 02:57:53 -0700226 env_->DeleteLocalRef(array);
Lifu Tang120480f2016-02-07 18:08:19 -0800227}
228
229jobject JavaObject::get() {
230 return object_;
231}
232
233// Define Java method signatures for all known types.
Lifu Tang120480f2016-02-07 18:08:19 -0800234template<>
235const char *const JavaMethodHelper<uint8_t>::signature_ = "(B)V";
236template<>
237const char *const JavaMethodHelper<int8_t>::signature_ = "(B)V";
238template<>
239const char *const JavaMethodHelper<int16_t>::signature_ = "(S)V";
240template<>
241const char *const JavaMethodHelper<uint16_t>::signature_ = "(S)V";
242template<>
Lifu Tang9363b942016-02-16 18:07:00 -0800243const char *const JavaMethodHelper<int32_t>::signature_ = "(I)V";
244template<>
245const char *const JavaMethodHelper<uint32_t>::signature_ = "(I)V";
Lifu Tang120480f2016-02-07 18:08:19 -0800246template<>
247const char *const JavaMethodHelper<int64_t>::signature_ = "(J)V";
248template<>
249const char *const JavaMethodHelper<float>::signature_ = "(F)V";
250template<>
251const char *const JavaMethodHelper<double>::signature_ = "(D)V";
252template<>
253const char *const JavaMethodHelper<bool>::signature_ = "(Z)V";
254
255#define SET(setter, value) object.callSetter("set" # setter, (value))
Lifu Tangccb44882016-03-09 19:32:29 -0800256
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700257static inline jboolean boolToJbool(bool value) {
258 return value ? JNI_TRUE : JNI_FALSE;
259}
Lifu Tang120480f2016-02-07 18:08:19 -0800260
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700261static void checkAndClearExceptionFromCallback(JNIEnv* env, const char* methodName) {
262 if (env->ExceptionCheck()) {
263 ALOGE("An exception was thrown by callback '%s'.", methodName);
264 LOGE_EX(env);
265 env->ExceptionClear();
266 }
267}
destradaaea8a8a62014-06-23 18:19:03 -0700268
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800269class ScopedJniThreadAttach {
270public:
271 ScopedJniThreadAttach() {
272 /*
273 * attachResult will also be JNI_OK if the thead was already attached to
274 * JNI before the call to AttachCurrentThread().
275 */
276 jint attachResult = sJvm->AttachCurrentThread(&mEnv, nullptr);
277 LOG_ALWAYS_FATAL_IF(attachResult != JNI_OK, "Unable to attach thread. Error %d",
278 attachResult);
279 }
280
281 ~ScopedJniThreadAttach() {
282 jint detachResult = sJvm->DetachCurrentThread();
283 /*
284 * Return if the thread was already detached. Log error for any other
285 * failure.
286 */
287 if (detachResult == JNI_EDETACHED) {
288 return;
289 }
290
291 LOG_ALWAYS_FATAL_IF(detachResult != JNI_OK, "Unable to detach thread. Error %d",
292 detachResult);
293 }
294
295 JNIEnv* getEnv() {
296 /*
297 * Checking validity of mEnv in case the thread was detached elsewhere.
298 */
299 LOG_ALWAYS_FATAL_IF(AndroidRuntime::getJNIEnv() != mEnv);
300 return mEnv;
301 }
302
303private:
304 JNIEnv* mEnv = nullptr;
305};
306
307thread_local std::unique_ptr<ScopedJniThreadAttach> tJniThreadAttacher;
308
309static JNIEnv* getJniEnv() {
310 JNIEnv* env = AndroidRuntime::getJNIEnv();
311
312 /*
313 * If env is nullptr, the thread is not already attached to
314 * JNI. It is attached below and the destructor for ScopedJniThreadAttach
315 * will detach it on thread exit.
316 */
317 if (env == nullptr) {
318 tJniThreadAttacher.reset(new ScopedJniThreadAttach());
319 env = tJniThreadAttacher->getEnv();
320 }
321
322 return env;
323}
324
Wyatt Rileyfb840922017-11-08 15:07:58 -0800325static jobject translateLocation(JNIEnv* env, const GnssLocation& location) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800326 JavaObject object(env, "android/location/Location", "gps");
327
328 uint16_t flags = static_cast<uint32_t>(location.gnssLocationFlags);
Wyatt Rileyfb840922017-11-08 15:07:58 -0800329 if (flags & GnssLocationFlags::HAS_LAT_LONG) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800330 SET(Latitude, location.latitudeDegrees);
331 SET(Longitude, location.longitudeDegrees);
332 }
Wyatt Rileyfb840922017-11-08 15:07:58 -0800333 if (flags & GnssLocationFlags::HAS_ALTITUDE) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800334 SET(Altitude, location.altitudeMeters);
335 }
Wyatt Rileyfb840922017-11-08 15:07:58 -0800336 if (flags & GnssLocationFlags::HAS_SPEED) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800337 SET(Speed, location.speedMetersPerSec);
338 }
Wyatt Rileyfb840922017-11-08 15:07:58 -0800339 if (flags & GnssLocationFlags::HAS_BEARING) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800340 SET(Bearing, location.bearingDegrees);
341 }
Wyatt Rileyfb840922017-11-08 15:07:58 -0800342 if (flags & GnssLocationFlags::HAS_HORIZONTAL_ACCURACY) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800343 SET(Accuracy, location.horizontalAccuracyMeters);
344 }
Wyatt Rileyfb840922017-11-08 15:07:58 -0800345 if (flags & GnssLocationFlags::HAS_VERTICAL_ACCURACY) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800346 SET(VerticalAccuracyMeters, location.verticalAccuracyMeters);
347 }
Wyatt Rileyfb840922017-11-08 15:07:58 -0800348 if (flags & GnssLocationFlags::HAS_SPEED_ACCURACY) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800349 SET(SpeedAccuracyMetersPerSecond, location.speedAccuracyMetersPerSecond);
350 }
Wyatt Rileyfb840922017-11-08 15:07:58 -0800351 if (flags & GnssLocationFlags::HAS_BEARING_ACCURACY) {
Wyatt Riley5d229832017-02-10 17:06:00 -0800352 SET(BearingAccuracyDegrees, location.bearingAccuracyDegrees);
353 }
354 SET(Time, location.timestamp);
355
356 return object.get();
357}
358
Yu-Han Yange7baef32018-02-09 13:58:17 -0800359static GnssLocation createGnssLocation(
360 jint gnssLocationFlags,
361 jdouble latitudeDegrees,
362 jdouble longitudeDegrees,
363 jdouble altitudeMeters,
364 jfloat speedMetersPerSec,
365 jfloat bearingDegrees,
366 jfloat horizontalAccuracyMeters,
367 jfloat verticalAccuracyMeters,
368 jfloat speedAccuracyMetersPerSecond,
369 jfloat bearingAccuracyDegrees,
370 jlong timestamp) {
371 GnssLocation location;
372 location.gnssLocationFlags = static_cast<uint16_t>(gnssLocationFlags);
373 location.latitudeDegrees = static_cast<double>(latitudeDegrees);
374 location.longitudeDegrees = static_cast<double>(longitudeDegrees);
375 location.altitudeMeters = static_cast<double>(altitudeMeters);
376 location.speedMetersPerSec = static_cast<float>(speedMetersPerSec);
377 location.bearingDegrees = static_cast<float>(bearingDegrees);
378 location.horizontalAccuracyMeters = static_cast<float>(horizontalAccuracyMeters);
379 location.verticalAccuracyMeters = static_cast<float>(verticalAccuracyMeters);
380 location.speedAccuracyMetersPerSecond = static_cast<float>(speedAccuracyMetersPerSecond);
381 location.bearingAccuracyDegrees = static_cast<float>(bearingAccuracyDegrees);
382 location.timestamp = static_cast<uint64_t>(timestamp);
383
384 return location;
385}
386
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700387/*
388 * GnssCallback class implements the callback methods for IGnss interface.
389 */
390struct GnssCallback : public IGnssCallback {
Wyatt Rileyfb840922017-11-08 15:07:58 -0800391 Return<void> gnssLocationCb(const GnssLocation& location) override;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700392 Return<void> gnssStatusCb(const IGnssCallback::GnssStatusValue status) override;
393 Return<void> gnssSvStatusCb(const IGnssCallback::GnssSvStatus& svStatus) override;
394 Return<void> gnssNmeaCb(int64_t timestamp, const android::hardware::hidl_string& nmea) override;
395 Return<void> gnssSetCapabilitesCb(uint32_t capabilities) override;
396 Return<void> gnssAcquireWakelockCb() override;
397 Return<void> gnssReleaseWakelockCb() override;
398 Return<void> gnssRequestTimeCb() override;
Yu-Han Yang21988932018-01-23 15:07:37 -0800399 Return<void> gnssRequestLocationCb(const bool independentFromGnss) override;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700400 Return<void> gnssSetSystemInfoCb(const IGnssCallback::GnssSystemInfo& info) override;
Lifu Tang38bce792016-02-24 17:17:38 -0800401
Wyatt Rileyfb840922017-11-08 15:07:58 -0800402 // New in 1.1
403 Return<void> gnssNameCb(const android::hardware::hidl_string& name) override;
404
Wyatt Riley26465d22018-02-12 13:44:24 -0800405 // TODO(b/73306084): Reconsider allocation cost vs threadsafety on these statics
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700406 static const char* sNmeaString;
407 static size_t sNmeaStringLength;
408};
409
Wyatt Rileyfb840922017-11-08 15:07:58 -0800410Return<void> GnssCallback::gnssNameCb(const android::hardware::hidl_string& name) {
411 ALOGD("%s: name=%s\n", __func__, name.c_str());
412
Wyatt Rileyfb840922017-11-08 15:07:58 -0800413 JNIEnv* env = getJniEnv();
Wyatt Rileyd87cf912017-12-05 09:31:52 -0800414 jstring jstringName = env->NewStringUTF(name.c_str());
415 env->CallVoidMethod(mCallbacksObj, method_setGnssHardwareModelName, jstringName);
Wyatt Rileyfb840922017-11-08 15:07:58 -0800416 checkAndClearExceptionFromCallback(env, __FUNCTION__);
Wyatt Rileyd87cf912017-12-05 09:31:52 -0800417
Wyatt Rileyfb840922017-11-08 15:07:58 -0800418 return Void();
419}
420
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700421const char* GnssCallback::sNmeaString = nullptr;
422size_t GnssCallback::sNmeaStringLength = 0;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700423
Wyatt Rileyfb840922017-11-08 15:07:58 -0800424Return<void> GnssCallback::gnssLocationCb(const GnssLocation& location) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800425 JNIEnv* env = getJniEnv();
Wyatt Riley5d229832017-02-10 17:06:00 -0800426
427 jobject jLocation = translateLocation(env, location);
428 bool hasLatLong = (static_cast<uint32_t>(location.gnssLocationFlags) &
Wyatt Rileyfb840922017-11-08 15:07:58 -0800429 GnssLocationFlags::HAS_LAT_LONG) != 0;
Wyatt Riley5d229832017-02-10 17:06:00 -0800430
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700431 env->CallVoidMethod(mCallbacksObj,
432 method_reportLocation,
Wyatt Riley5d229832017-02-10 17:06:00 -0800433 boolToJbool(hasLatLong),
434 jLocation);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700435 checkAndClearExceptionFromCallback(env, __FUNCTION__);
Wyatt Riley26465d22018-02-12 13:44:24 -0800436 env->DeleteLocalRef(jLocation);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700437 return Void();
438}
439
440Return<void> GnssCallback::gnssStatusCb(const IGnssCallback::GnssStatusValue status) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800441 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700442 env->CallVoidMethod(mCallbacksObj, method_reportStatus, status);
443 checkAndClearExceptionFromCallback(env, __FUNCTION__);
444 return Void();
445}
446
447Return<void> GnssCallback::gnssSvStatusCb(const IGnssCallback::GnssSvStatus& svStatus) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800448 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700449
Wyatt Riley26465d22018-02-12 13:44:24 -0800450 uint32_t listSize = svStatus.numSvs;
451 if (listSize > static_cast<uint32_t>(
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700452 android::hardware::gnss::V1_0::GnssMax::SVS_COUNT)) {
Wyatt Riley26465d22018-02-12 13:44:24 -0800453 ALOGD("Too many satellites %u. Clamps to %u.", listSize,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700454 static_cast<uint32_t>(android::hardware::gnss::V1_0::GnssMax::SVS_COUNT));
Wyatt Riley26465d22018-02-12 13:44:24 -0800455 listSize = static_cast<uint32_t>(android::hardware::gnss::V1_0::GnssMax::SVS_COUNT);
Lifu Tang38bce792016-02-24 17:17:38 -0800456 }
457
Wyatt Riley26465d22018-02-12 13:44:24 -0800458 jintArray svidWithFlagArray = env->NewIntArray(listSize);
459 jfloatArray cn0Array = env->NewFloatArray(listSize);
460 jfloatArray elevArray = env->NewFloatArray(listSize);
461 jfloatArray azimArray = env->NewFloatArray(listSize);
462 jfloatArray carrierFreqArray = env->NewFloatArray(listSize);
463
464 jint* svidWithFlags = env->GetIntArrayElements(svidWithFlagArray, 0);
465 jfloat* cn0s = env->GetFloatArrayElements(cn0Array, 0);
466 jfloat* elev = env->GetFloatArrayElements(elevArray, 0);
467 jfloat* azim = env->GetFloatArrayElements(azimArray, 0);
468 jfloat* carrierFreq = env->GetFloatArrayElements(carrierFreqArray, 0);
469
470 /*
471 * Read GNSS SV info.
472 */
473 for (size_t i = 0; i < listSize; ++i) {
474 enum ShiftWidth: uint8_t {
475 SVID_SHIFT_WIDTH = 8,
476 CONSTELLATION_TYPE_SHIFT_WIDTH = 4
477 };
478
479 const IGnssCallback::GnssSvInfo& info = svStatus.gnssSvList.data()[i];
480 svidWithFlags[i] = (info.svid << SVID_SHIFT_WIDTH) |
481 (static_cast<uint32_t>(info.constellation) << CONSTELLATION_TYPE_SHIFT_WIDTH) |
482 static_cast<uint32_t>(info.svFlag);
483 cn0s[i] = info.cN0Dbhz;
484 elev[i] = info.elevationDegrees;
485 azim[i] = info.azimuthDegrees;
486 carrierFreq[i] = info.carrierFrequencyHz;
Lifu Tang9363b942016-02-16 18:07:00 -0800487 }
destradaaea8a8a62014-06-23 18:19:03 -0700488
Wyatt Riley26465d22018-02-12 13:44:24 -0800489 env->ReleaseIntArrayElements(svidWithFlagArray, svidWithFlags, 0);
490 env->ReleaseFloatArrayElements(cn0Array, cn0s, 0);
491 env->ReleaseFloatArrayElements(elevArray, elev, 0);
492 env->ReleaseFloatArrayElements(azimArray, azim, 0);
493 env->ReleaseFloatArrayElements(carrierFreqArray, carrierFreq, 0);
494
495 env->CallVoidMethod(mCallbacksObj, method_reportSvStatus,
496 static_cast<jint>(listSize), svidWithFlagArray, cn0Array, elevArray, azimArray,
497 carrierFreqArray);
498
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700499 checkAndClearExceptionFromCallback(env, __FUNCTION__);
500 return Void();
destradaaea8a8a62014-06-23 18:19:03 -0700501}
502
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700503Return<void> GnssCallback::gnssNmeaCb(
504 int64_t timestamp, const ::android::hardware::hidl_string& nmea) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800505 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700506 /*
507 * The Java code will call back to read these values.
508 * We do this to avoid creating unnecessary String objects.
509 */
510 sNmeaString = nmea.c_str();
511 sNmeaStringLength = nmea.size();
512
513 env->CallVoidMethod(mCallbacksObj, method_reportNmea, timestamp);
514 checkAndClearExceptionFromCallback(env, __FUNCTION__);
515 return Void();
516}
517
518Return<void> GnssCallback::gnssSetCapabilitesCb(uint32_t capabilities) {
519 ALOGD("%s: %du\n", __func__, capabilities);
520
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800521 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700522 env->CallVoidMethod(mCallbacksObj, method_setEngineCapabilities, capabilities);
523 checkAndClearExceptionFromCallback(env, __FUNCTION__);
524 return Void();
525}
526
527Return<void> GnssCallback::gnssAcquireWakelockCb() {
528 acquire_wake_lock(PARTIAL_WAKE_LOCK, WAKE_LOCK_NAME);
529 return Void();
530}
531
532Return<void> GnssCallback::gnssReleaseWakelockCb() {
533 release_wake_lock(WAKE_LOCK_NAME);
534 return Void();
535}
536
537Return<void> GnssCallback::gnssRequestTimeCb() {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800538 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700539 env->CallVoidMethod(mCallbacksObj, method_requestUtcTime);
540 checkAndClearExceptionFromCallback(env, __FUNCTION__);
541 return Void();
542}
543
Yu-Han Yang21988932018-01-23 15:07:37 -0800544Return<void> GnssCallback::gnssRequestLocationCb(const bool independentFromGnss) {
Yu-Han Yange7baef32018-02-09 13:58:17 -0800545 JNIEnv* env = getJniEnv();
546 env->CallVoidMethod(mCallbacksObj, method_requestLocation, boolToJbool(independentFromGnss));
547 checkAndClearExceptionFromCallback(env, __FUNCTION__);
Yu-Han Yang21988932018-01-23 15:07:37 -0800548 return Void();
549}
550
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700551Return<void> GnssCallback::gnssSetSystemInfoCb(const IGnssCallback::GnssSystemInfo& info) {
552 ALOGD("%s: yearOfHw=%d\n", __func__, info.yearOfHw);
553
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800554 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700555 env->CallVoidMethod(mCallbacksObj, method_setGnssYearOfHardware,
556 info.yearOfHw);
557 checkAndClearExceptionFromCallback(env, __FUNCTION__);
558 return Void();
559}
560
561class GnssXtraCallback : public IGnssXtraCallback {
562 Return<void> downloadRequestCb() override;
563};
564
565/*
566 * GnssXtraCallback class implements the callback methods for the IGnssXtra
567 * interface.
568 */
569Return<void> GnssXtraCallback::downloadRequestCb() {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800570 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700571 env->CallVoidMethod(mCallbacksObj, method_xtraDownloadRequest);
572 checkAndClearExceptionFromCallback(env, __FUNCTION__);
573 return Void();
574}
575
576/*
577 * GnssGeofenceCallback class implements the callback methods for the
578 * IGnssGeofence interface.
579 */
580struct GnssGeofenceCallback : public IGnssGeofenceCallback {
581 // Methods from ::android::hardware::gps::V1_0::IGnssGeofenceCallback follow.
582 Return<void> gnssGeofenceTransitionCb(
583 int32_t geofenceId,
Wyatt Rileyfb840922017-11-08 15:07:58 -0800584 const GnssLocation& location,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700585 GeofenceTransition transition,
586 hardware::gnss::V1_0::GnssUtcTime timestamp) override;
587 Return<void> gnssGeofenceStatusCb(
588 GeofenceAvailability status,
Wyatt Rileyfb840922017-11-08 15:07:58 -0800589 const GnssLocation& location) override;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700590 Return<void> gnssGeofenceAddCb(int32_t geofenceId,
591 GeofenceStatus status) override;
592 Return<void> gnssGeofenceRemoveCb(int32_t geofenceId,
593 GeofenceStatus status) override;
594 Return<void> gnssGeofencePauseCb(int32_t geofenceId,
595 GeofenceStatus status) override;
596 Return<void> gnssGeofenceResumeCb(int32_t geofenceId,
597 GeofenceStatus status) override;
598};
599
600Return<void> GnssGeofenceCallback::gnssGeofenceTransitionCb(
601 int32_t geofenceId,
Wyatt Rileyfb840922017-11-08 15:07:58 -0800602 const GnssLocation& location,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700603 GeofenceTransition transition,
604 hardware::gnss::V1_0::GnssUtcTime timestamp) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800605 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700606
Wyatt Riley5d229832017-02-10 17:06:00 -0800607 jobject jLocation = translateLocation(env, location);
608
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700609 env->CallVoidMethod(mCallbacksObj,
610 method_reportGeofenceTransition,
611 geofenceId,
Wyatt Riley5d229832017-02-10 17:06:00 -0800612 jLocation,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700613 transition,
614 timestamp);
615
616 checkAndClearExceptionFromCallback(env, __FUNCTION__);
Wyatt Riley26465d22018-02-12 13:44:24 -0800617 env->DeleteLocalRef(jLocation);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700618 return Void();
619}
620
621Return<void> GnssGeofenceCallback::gnssGeofenceStatusCb(
622 GeofenceAvailability status,
Wyatt Rileyfb840922017-11-08 15:07:58 -0800623 const GnssLocation& location) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800624 JNIEnv* env = getJniEnv();
Wyatt Riley5d229832017-02-10 17:06:00 -0800625
626 jobject jLocation = translateLocation(env, location);
627
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700628 env->CallVoidMethod(mCallbacksObj,
629 method_reportGeofenceStatus,
630 status,
Wyatt Riley5d229832017-02-10 17:06:00 -0800631 jLocation);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700632 checkAndClearExceptionFromCallback(env, __FUNCTION__);
Wyatt Riley26465d22018-02-12 13:44:24 -0800633 env->DeleteLocalRef(jLocation);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700634 return Void();
635}
636
637Return<void> GnssGeofenceCallback::gnssGeofenceAddCb(int32_t geofenceId,
638 GeofenceStatus status) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800639 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700640 if (status != IGnssGeofenceCallback::GeofenceStatus::OPERATION_SUCCESS) {
641 ALOGE("%s: Error in adding a Geofence: %d\n", __func__, status);
642 }
643
644 env->CallVoidMethod(mCallbacksObj,
645 method_reportGeofenceAddStatus,
646 geofenceId,
647 status);
648 checkAndClearExceptionFromCallback(env, __FUNCTION__);
649 return Void();
650}
651
652Return<void> GnssGeofenceCallback::gnssGeofenceRemoveCb(int32_t geofenceId,
653 GeofenceStatus status) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800654 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700655 if (status != IGnssGeofenceCallback::GeofenceStatus::OPERATION_SUCCESS) {
656 ALOGE("%s: Error in removing a Geofence: %d\n", __func__, status);
657 }
658
659 env->CallVoidMethod(mCallbacksObj,
660 method_reportGeofenceRemoveStatus,
661 geofenceId, status);
662 checkAndClearExceptionFromCallback(env, __FUNCTION__);
663 return Void();
664}
665
666Return<void> GnssGeofenceCallback::gnssGeofencePauseCb(int32_t geofenceId,
667 GeofenceStatus status) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800668 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700669 if (status != IGnssGeofenceCallback::GeofenceStatus::OPERATION_SUCCESS) {
670 ALOGE("%s: Error in pausing Geofence: %d\n", __func__, status);
671 }
672
673 env->CallVoidMethod(mCallbacksObj,
674 method_reportGeofencePauseStatus,
675 geofenceId, status);
676 checkAndClearExceptionFromCallback(env, __FUNCTION__);
677 return Void();
678}
679
680Return<void> GnssGeofenceCallback::gnssGeofenceResumeCb(int32_t geofenceId,
681 GeofenceStatus status) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800682 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700683 if (status != IGnssGeofenceCallback::GeofenceStatus::OPERATION_SUCCESS) {
684 ALOGE("%s: Error in resuming Geofence: %d\n", __func__, status);
685 }
686
687 env->CallVoidMethod(mCallbacksObj,
688 method_reportGeofenceResumeStatus,
689 geofenceId, status);
690 checkAndClearExceptionFromCallback(env, __FUNCTION__);
691 return Void();
692}
693
694/*
695 * GnssNavigationMessageCallback interface implements the callback methods
696 * required by the IGnssNavigationMessage interface.
697 */
698struct GnssNavigationMessageCallback : public IGnssNavigationMessageCallback {
699 /*
700 * Methods from ::android::hardware::gps::V1_0::IGnssNavigationMessageCallback
701 * follow.
702 */
703 Return<void> gnssNavigationMessageCb(
704 const IGnssNavigationMessageCallback::GnssNavigationMessage& message) override;
705};
706
707Return<void> GnssNavigationMessageCallback::gnssNavigationMessageCb(
708 const IGnssNavigationMessageCallback::GnssNavigationMessage& message) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800709 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700710
711 size_t dataLength = message.data.size();
712
713 std::vector<uint8_t> navigationData = message.data;
714 uint8_t* data = &(navigationData[0]);
715 if (dataLength == 0 || data == NULL) {
716 ALOGE("Invalid Navigation Message found: data=%p, length=%zd", data,
717 dataLength);
718 return Void();
719 }
720
721 JavaObject object(env, "android/location/GnssNavigationMessage");
722 SET(Type, static_cast<int32_t>(message.type));
723 SET(Svid, static_cast<int32_t>(message.svid));
724 SET(MessageId, static_cast<int32_t>(message.messageId));
725 SET(SubmessageId, static_cast<int32_t>(message.submessageId));
726 object.callSetter("setData", data, dataLength);
727 SET(Status, static_cast<int32_t>(message.status));
728
729 jobject navigationMessage = object.get();
730 env->CallVoidMethod(mCallbacksObj,
731 method_reportNavigationMessages,
732 navigationMessage);
Wyatt Rileycf879db2017-01-12 13:57:38 -0800733 checkAndClearExceptionFromCallback(env, __FUNCTION__);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700734 env->DeleteLocalRef(navigationMessage);
735 return Void();
736}
737
738/*
739 * GnssMeasurementCallback implements the callback methods required for the
740 * GnssMeasurement interface.
741 */
Wyatt Riley46ac9562018-03-02 20:16:58 -0800742struct GnssMeasurementCallback : public IGnssMeasurementCallback_V1_1 {
743 Return<void> gnssMeasurementCb(const IGnssMeasurementCallback_V1_1::GnssData& data) override;
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800744 Return<void> GnssMeasurementCb(const IGnssMeasurementCallback_V1_0::GnssData& data) override;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700745 private:
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800746 void translateGnssMeasurement_V1_0(
747 JNIEnv* env, const IGnssMeasurementCallback_V1_0::GnssMeasurement* measurement,
Wyatt Riley46ac9562018-03-02 20:16:58 -0800748 JavaObject& object);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700749 jobjectArray translateGnssMeasurements(
750 JNIEnv* env,
Wyatt Riley46ac9562018-03-02 20:16:58 -0800751 const IGnssMeasurementCallback_V1_1::GnssMeasurement* measurements_v1_1,
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800752 const IGnssMeasurementCallback_V1_0::GnssMeasurement* measurements_v1_0,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700753 size_t count);
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800754 jobject translateGnssClock(
Wyatt Riley46ac9562018-03-02 20:16:58 -0800755 JNIEnv* env, const IGnssMeasurementCallback_V1_0::GnssClock* clock);
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700756 void setMeasurementData(JNIEnv* env, jobject clock, jobjectArray measurementArray);
757};
758
759
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800760Return<void> GnssMeasurementCallback::gnssMeasurementCb(
Wyatt Riley46ac9562018-03-02 20:16:58 -0800761 const IGnssMeasurementCallback_V1_1::GnssData& data) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800762 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700763
764 jobject clock;
765 jobjectArray measurementArray;
766
767 clock = translateGnssClock(env, &data.clock);
Wyatt Riley46ac9562018-03-02 20:16:58 -0800768
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700769 measurementArray = translateGnssMeasurements(
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800770 env, data.measurements.data(), NULL, data.measurements.size());
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700771 setMeasurementData(env, clock, measurementArray);
772
773 env->DeleteLocalRef(clock);
774 env->DeleteLocalRef(measurementArray);
775 return Void();
776}
777
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800778Return<void> GnssMeasurementCallback::GnssMeasurementCb(
779 const IGnssMeasurementCallback_V1_0::GnssData& data) {
780 JNIEnv* env = getJniEnv();
Lifu Tang120480f2016-02-07 18:08:19 -0800781
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800782 jobject clock;
783 jobjectArray measurementArray;
784
785 clock = translateGnssClock(env, &data.clock);
786 measurementArray = translateGnssMeasurements(
787 env, NULL, data.measurements.data(), data.measurementCount);
788 setMeasurementData(env, clock, measurementArray);
789
790 env->DeleteLocalRef(clock);
791 env->DeleteLocalRef(measurementArray);
792 return Void();
793}
794
795// preallocate object as: JavaObject object(env, "android/location/GnssMeasurement");
796void GnssMeasurementCallback::translateGnssMeasurement_V1_0(
797 JNIEnv* env, const IGnssMeasurementCallback_V1_0::GnssMeasurement* measurement,
Wyatt Riley46ac9562018-03-02 20:16:58 -0800798 JavaObject& object) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700799 uint32_t flags = static_cast<uint32_t>(measurement->flags);
Mike Cailean96635bd2016-03-24 19:34:16 -0700800
801 SET(Svid, static_cast<int32_t>(measurement->svid));
Lifu Tang76a620f2016-02-26 19:53:01 -0800802 SET(ConstellationType, static_cast<int32_t>(measurement->constellation));
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700803 SET(TimeOffsetNanos, measurement->timeOffsetNs);
Lifu Tang76a620f2016-02-26 19:53:01 -0800804 SET(State, static_cast<int32_t>(measurement->state));
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700805 SET(ReceivedSvTimeNanos, measurement->receivedSvTimeInNs);
Lifu Tang76a620f2016-02-26 19:53:01 -0800806 SET(ReceivedSvTimeUncertaintyNanos,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700807 measurement->receivedSvTimeUncertaintyInNs);
808 SET(Cn0DbHz, measurement->cN0DbHz);
809 SET(PseudorangeRateMetersPerSecond, measurement->pseudorangeRateMps);
Lifu Tang76a620f2016-02-26 19:53:01 -0800810 SET(PseudorangeRateUncertaintyMetersPerSecond,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700811 measurement->pseudorangeRateUncertaintyMps);
Lifu Tang76a620f2016-02-26 19:53:01 -0800812 SET(AccumulatedDeltaRangeState,
Wyatt Riley4cbcb412018-01-23 18:07:05 -0800813 (static_cast<int32_t>(measurement->accumulatedDeltaRangeState) &
814 !ADR_STATE_HALF_CYCLE_REPORTED)); // Half Cycle state not reported from Hardware in V1_0
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700815 SET(AccumulatedDeltaRangeMeters, measurement->accumulatedDeltaRangeM);
Lifu Tang76a620f2016-02-26 19:53:01 -0800816 SET(AccumulatedDeltaRangeUncertaintyMeters,
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700817 measurement->accumulatedDeltaRangeUncertaintyM);
818
819 if (flags & static_cast<uint32_t>(GnssMeasurementFlags::HAS_CARRIER_FREQUENCY)) {
820 SET(CarrierFrequencyHz, measurement->carrierFrequencyHz);
821 }
822
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800823 // Intentionally not copying deprecated fields of carrierCycles,
824 // carrierPhase, carrierPhaseUncertainty
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700825
826 SET(MultipathIndicator, static_cast<int32_t>(measurement->multipathIndicator));
827
828 if (flags & static_cast<uint32_t>(GnssMeasurementFlags::HAS_SNR)) {
829 SET(SnrInDb, measurement->snrDb);
830 }
Lifu Tang120480f2016-02-07 18:08:19 -0800831
gomo4402af62017-01-11 13:20:13 -0800832 if (flags & static_cast<uint32_t>(GnssMeasurementFlags::HAS_AUTOMATIC_GAIN_CONTROL)) {
gomo127ba322017-01-15 20:26:48 -0800833 SET(AutomaticGainControlLevelInDb, measurement->agcLevelDb);
gomo4402af62017-01-11 13:20:13 -0800834 }
Lifu Tang120480f2016-02-07 18:08:19 -0800835}
836
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700837jobject GnssMeasurementCallback::translateGnssClock(
Wyatt Riley46ac9562018-03-02 20:16:58 -0800838 JNIEnv* env, const IGnssMeasurementCallback_V1_0::GnssClock* clock) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700839 JavaObject object(env, "android/location/GnssClock");
840
841 uint32_t flags = static_cast<uint32_t>(clock->gnssClockFlags);
842 if (flags & static_cast<uint32_t>(GnssClockFlags::HAS_LEAP_SECOND)) {
843 SET(LeapSecond, static_cast<int32_t>(clock->leapSecond));
844 }
845
846 if (flags & static_cast<uint32_t>(GnssClockFlags::HAS_TIME_UNCERTAINTY)) {
847 SET(TimeUncertaintyNanos, clock->timeUncertaintyNs);
848 }
849
850 if (flags & static_cast<uint32_t>(GnssClockFlags::HAS_FULL_BIAS)) {
851 SET(FullBiasNanos, clock->fullBiasNs);
852 }
853
854 if (flags & static_cast<uint32_t>(GnssClockFlags::HAS_BIAS)) {
855 SET(BiasNanos, clock->biasNs);
856 }
857
858 if (flags & static_cast<uint32_t>(GnssClockFlags::HAS_BIAS_UNCERTAINTY)) {
859 SET(BiasUncertaintyNanos, clock->biasUncertaintyNs);
860 }
861
862 if (flags & static_cast<uint32_t>(GnssClockFlags::HAS_DRIFT)) {
863 SET(DriftNanosPerSecond, clock->driftNsps);
864 }
865
866 if (flags & static_cast<uint32_t>(GnssClockFlags::HAS_DRIFT_UNCERTAINTY)) {
867 SET(DriftUncertaintyNanosPerSecond, clock->driftUncertaintyNsps);
868 }
869
870 SET(TimeNanos, clock->timeNs);
871 SET(HardwareClockDiscontinuityCount, clock->hwClockDiscontinuityCount);
872
873 return object.get();
874}
875
876jobjectArray GnssMeasurementCallback::translateGnssMeasurements(JNIEnv* env,
Wyatt Riley46ac9562018-03-02 20:16:58 -0800877 const IGnssMeasurementCallback_V1_1::GnssMeasurement* measurements_v1_1,
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800878 const IGnssMeasurementCallback_V1_0::GnssMeasurement* measurements_v1_0,
879 size_t count) {
Lifu Tang120480f2016-02-07 18:08:19 -0800880 if (count == 0) {
destradaaea8a8a62014-06-23 18:19:03 -0700881 return NULL;
882 }
883
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700884 jclass gnssMeasurementClass = env->FindClass("android/location/GnssMeasurement");
Lifu Tang818aa2c2016-02-01 01:52:00 -0800885 jobjectArray gnssMeasurementArray = env->NewObjectArray(
Lifu Tang120480f2016-02-07 18:08:19 -0800886 count,
Lifu Tang818aa2c2016-02-01 01:52:00 -0800887 gnssMeasurementClass,
destradaaea8a8a62014-06-23 18:19:03 -0700888 NULL /* initialElement */);
889
Lifu Tang120480f2016-02-07 18:08:19 -0800890 for (uint16_t i = 0; i < count; ++i) {
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800891 JavaObject object(env, "android/location/GnssMeasurement");
Wyatt Riley46ac9562018-03-02 20:16:58 -0800892 if (measurements_v1_1 != NULL) {
893 translateGnssMeasurement_V1_0(env, &(measurements_v1_1[i].v1_0), object);
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800894
Wyatt Riley4cbcb412018-01-23 18:07:05 -0800895 // Set the V1_1 flag, and mark that new field has valid information for Java Layer
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800896 SET(AccumulatedDeltaRangeState,
Wyatt Riley4cbcb412018-01-23 18:07:05 -0800897 (static_cast<int32_t>(measurements_v1_1[i].accumulatedDeltaRangeState) |
898 ADR_STATE_HALF_CYCLE_REPORTED));
Wyatt Rileybb9bc842018-02-14 08:46:00 -0800899 } else {
900 translateGnssMeasurement_V1_0(env, &(measurements_v1_0[i]), object);
901 }
902
903 env->SetObjectArrayElement(gnssMeasurementArray, i, object.get());
destradaaea8a8a62014-06-23 18:19:03 -0700904 }
905
Lifu Tang818aa2c2016-02-01 01:52:00 -0800906 env->DeleteLocalRef(gnssMeasurementClass);
907 return gnssMeasurementArray;
destradaaea8a8a62014-06-23 18:19:03 -0700908}
909
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700910void GnssMeasurementCallback::setMeasurementData(JNIEnv* env, jobject clock,
911 jobjectArray measurementArray) {
912 jclass gnssMeasurementsEventClass =
913 env->FindClass("android/location/GnssMeasurementsEvent");
914 jmethodID gnssMeasurementsEventCtor =
915 env->GetMethodID(
916 gnssMeasurementsEventClass,
917 "<init>",
918 "(Landroid/location/GnssClock;[Landroid/location/GnssMeasurement;)V");
Lifu Tange5a0e212016-01-25 18:02:17 -0800919
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700920 jobject gnssMeasurementsEvent = env->NewObject(gnssMeasurementsEventClass,
921 gnssMeasurementsEventCtor,
922 clock,
923 measurementArray);
Lifu Tang120480f2016-02-07 18:08:19 -0800924
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700925 env->CallVoidMethod(mCallbacksObj, method_reportMeasurementData,
926 gnssMeasurementsEvent);
Lifu Tange5a0e212016-01-25 18:02:17 -0800927 checkAndClearExceptionFromCallback(env, __FUNCTION__);
Lifu Tang818aa2c2016-02-01 01:52:00 -0800928 env->DeleteLocalRef(gnssMeasurementsEventClass);
929 env->DeleteLocalRef(gnssMeasurementsEvent);
destradaaea8a8a62014-06-23 18:19:03 -0700930}
931
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700932/*
933 * GnssNiCallback implements callback methods required by the IGnssNi interface.
934 */
935struct GnssNiCallback : public IGnssNiCallback {
936 Return<void> niNotifyCb(const IGnssNiCallback::GnssNiNotification& notification)
937 override;
destradaaea8a8a62014-06-23 18:19:03 -0700938};
939
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700940Return<void> GnssNiCallback::niNotifyCb(
941 const IGnssNiCallback::GnssNiNotification& notification) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800942 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700943 jstring requestorId = env->NewStringUTF(notification.requestorId.c_str());
944 jstring text = env->NewStringUTF(notification.notificationMessage.c_str());
945
946 if (requestorId && text) {
947 env->CallVoidMethod(mCallbacksObj, method_reportNiNotification,
948 notification.notificationId, notification.niType,
949 notification.notifyFlags, notification.timeoutSec,
950 notification.defaultResponse, requestorId, text,
951 notification.requestorIdEncoding,
952 notification.notificationIdEncoding);
953 } else {
954 ALOGE("%s: OOM Error\n", __func__);
955 }
956
957 if (requestorId) {
958 env->DeleteLocalRef(requestorId);
959 }
960
961 if (text) {
962 env->DeleteLocalRef(text);
963 }
964 checkAndClearExceptionFromCallback(env, __FUNCTION__);
965 return Void();
966}
967
968/*
969 * AGnssCallback implements callback methods required by the IAGnss interface.
970 */
971struct AGnssCallback : public IAGnssCallback {
972 // Methods from ::android::hardware::gps::V1_0::IAGnssCallback follow.
973 Return<void> agnssStatusIpV6Cb(
974 const IAGnssCallback::AGnssStatusIpV6& agps_status) override;
975
976 Return<void> agnssStatusIpV4Cb(
977 const IAGnssCallback::AGnssStatusIpV4& agps_status) override;
978 private:
979 jbyteArray convertToIpV4(uint32_t ip);
980};
981
982Return<void> AGnssCallback::agnssStatusIpV6Cb(
983 const IAGnssCallback::AGnssStatusIpV6& agps_status) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -0800984 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -0700985 jbyteArray byteArray = NULL;
986 bool isSupported = false;
987
988 byteArray = env->NewByteArray(16);
989 if (byteArray != NULL) {
990 env->SetByteArrayRegion(byteArray, 0, 16,
991 (const jbyte*)(agps_status.ipV6Addr.data()));
992 isSupported = true;
993 } else {
994 ALOGE("Unable to allocate byte array for IPv6 address.");
995 }
996
997 IF_ALOGD() {
998 // log the IP for reference in case there is a bogus value pushed by HAL
999 char str[INET6_ADDRSTRLEN];
1000 inet_ntop(AF_INET6, agps_status.ipV6Addr.data(), str, INET6_ADDRSTRLEN);
1001 ALOGD("AGPS IP is v6: %s", str);
1002 }
1003
1004 jsize byteArrayLength = byteArray != NULL ? env->GetArrayLength(byteArray) : 0;
1005 ALOGV("Passing AGPS IP addr: size %d", byteArrayLength);
1006 env->CallVoidMethod(mCallbacksObj, method_reportAGpsStatus,
1007 agps_status.type, agps_status.status, byteArray);
1008
1009 checkAndClearExceptionFromCallback(env, __FUNCTION__);
1010
1011 if (byteArray) {
1012 env->DeleteLocalRef(byteArray);
1013 }
1014
1015 return Void();
1016}
1017
1018Return<void> AGnssCallback::agnssStatusIpV4Cb(
1019 const IAGnssCallback::AGnssStatusIpV4& agps_status) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -08001020 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001021 jbyteArray byteArray = NULL;
1022
1023 uint32_t ipAddr = agps_status.ipV4Addr;
1024 byteArray = convertToIpV4(ipAddr);
1025
1026 IF_ALOGD() {
1027 /*
1028 * log the IP for reference in case there is a bogus value pushed by
1029 * HAL.
1030 */
1031 char str[INET_ADDRSTRLEN];
1032 inet_ntop(AF_INET, &ipAddr, str, INET_ADDRSTRLEN);
1033 ALOGD("AGPS IP is v4: %s", str);
1034 }
1035
1036 jsize byteArrayLength =
1037 byteArray != NULL ? env->GetArrayLength(byteArray) : 0;
1038 ALOGV("Passing AGPS IP addr: size %d", byteArrayLength);
1039 env->CallVoidMethod(mCallbacksObj, method_reportAGpsStatus,
1040 agps_status.type, agps_status.status, byteArray);
1041
1042 checkAndClearExceptionFromCallback(env, __FUNCTION__);
1043
1044 if (byteArray) {
1045 env->DeleteLocalRef(byteArray);
1046 }
1047 return Void();
1048}
1049
1050jbyteArray AGnssCallback::convertToIpV4(uint32_t ip) {
1051 if (INADDR_NONE == ip) {
1052 return NULL;
1053 }
1054
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -08001055 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001056 jbyteArray byteArray = env->NewByteArray(4);
1057 if (byteArray == NULL) {
1058 ALOGE("Unable to allocate byte array for IPv4 address");
1059 return NULL;
1060 }
1061
1062 jbyte ipv4[4];
1063 ALOGV("Converting IPv4 address byte array (net_order) %x", ip);
1064 memcpy(ipv4, &ip, sizeof(ipv4));
1065 env->SetByteArrayRegion(byteArray, 0, 4, (const jbyte*)ipv4);
1066 return byteArray;
1067}
1068
1069/*
1070 * AGnssRilCallback implements the callback methods required by the AGnssRil
1071 * interface.
1072 */
1073struct AGnssRilCallback : IAGnssRilCallback {
Hridya Valsarajub39eb402017-01-11 08:07:40 -08001074 Return<void> requestSetIdCb(uint32_t setIdFlag) override;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001075 Return<void> requestRefLocCb() override;
1076};
1077
Hridya Valsarajub39eb402017-01-11 08:07:40 -08001078Return<void> AGnssRilCallback::requestSetIdCb(uint32_t setIdFlag) {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -08001079 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001080 env->CallVoidMethod(mCallbacksObj, method_requestSetID, setIdFlag);
1081 checkAndClearExceptionFromCallback(env, __FUNCTION__);
1082 return Void();
1083}
1084
1085Return<void> AGnssRilCallback::requestRefLocCb() {
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -08001086 JNIEnv* env = getJniEnv();
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001087 env->CallVoidMethod(mCallbacksObj, method_requestRefLocation);
1088 checkAndClearExceptionFromCallback(env, __FUNCTION__);
1089 return Void();
1090}
1091
Wyatt Rileycf879db2017-01-12 13:57:38 -08001092/*
1093 * GnssBatchingCallback interface implements the callback methods
1094 * required by the IGnssBatching interface.
1095 */
1096struct GnssBatchingCallback : public IGnssBatchingCallback {
1097 /*
1098 * Methods from ::android::hardware::gps::V1_0::IGnssBatchingCallback
1099 * follow.
1100 */
1101 Return<void> gnssLocationBatchCb(
Wyatt Rileyfb840922017-11-08 15:07:58 -08001102 const ::android::hardware::hidl_vec<GnssLocation> & locations)
Wyatt Rileycf879db2017-01-12 13:57:38 -08001103 override;
Wyatt Rileycf879db2017-01-12 13:57:38 -08001104};
1105
1106Return<void> GnssBatchingCallback::gnssLocationBatchCb(
Wyatt Rileyfb840922017-11-08 15:07:58 -08001107 const ::android::hardware::hidl_vec<GnssLocation> & locations) {
Wyatt Rileycf879db2017-01-12 13:57:38 -08001108 JNIEnv* env = getJniEnv();
1109
1110 jobjectArray jLocations = env->NewObjectArray(locations.size(),
1111 env->FindClass("android/location/Location"), nullptr);
1112
1113 for (uint16_t i = 0; i < locations.size(); ++i) {
Wyatt Riley5d229832017-02-10 17:06:00 -08001114 jobject jLocation = translateLocation(env, locations[i]);
Wyatt Rileycf879db2017-01-12 13:57:38 -08001115 env->SetObjectArrayElement(jLocations, i, jLocation);
1116 env->DeleteLocalRef(jLocation);
1117 }
1118
1119 env->CallVoidMethod(mCallbacksObj, method_reportLocationBatch, jLocations);
1120 checkAndClearExceptionFromCallback(env, __FUNCTION__);
1121
1122 env->DeleteLocalRef(jLocations);
1123
1124 return Void();
1125}
1126
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001127static void android_location_GnssLocationProvider_class_init_native(JNIEnv* env, jclass clazz) {
Yu-Han Yang6d317352018-03-15 11:53:01 -07001128 gnssHal_V1_1 = IGnss_V1_1::getService();
1129 if (gnssHal_V1_1 == nullptr) {
1130 ALOGD("gnssHal 1.1 was null, trying 1.0");
1131 gnssHal = IGnss_V1_0::getService();
1132 } else {
1133 gnssHal = gnssHal_V1_1;
1134 }
1135}
1136
1137static void android_location_GnssLocationProvider_init_once(JNIEnv* env, jclass clazz) {
Wyatt Riley5d229832017-02-10 17:06:00 -08001138 method_reportLocation = env->GetMethodID(clazz, "reportLocation",
1139 "(ZLandroid/location/Location;)V");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001140 method_reportStatus = env->GetMethodID(clazz, "reportStatus", "(I)V");
Wyatt Riley26465d22018-02-12 13:44:24 -08001141 method_reportSvStatus = env->GetMethodID(clazz, "reportSvStatus", "(I[I[F[F[F[F)V");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001142 method_reportAGpsStatus = env->GetMethodID(clazz, "reportAGpsStatus", "(II[B)V");
1143 method_reportNmea = env->GetMethodID(clazz, "reportNmea", "(J)V");
1144 method_setEngineCapabilities = env->GetMethodID(clazz, "setEngineCapabilities", "(I)V");
1145 method_setGnssYearOfHardware = env->GetMethodID(clazz, "setGnssYearOfHardware", "(I)V");
Wyatt Rileyd87cf912017-12-05 09:31:52 -08001146 method_setGnssHardwareModelName = env->GetMethodID(clazz, "setGnssHardwareModelName",
1147 "(Ljava/lang/String;)V");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001148 method_xtraDownloadRequest = env->GetMethodID(clazz, "xtraDownloadRequest", "()V");
1149 method_reportNiNotification = env->GetMethodID(clazz, "reportNiNotification",
1150 "(IIIIILjava/lang/String;Ljava/lang/String;II)V");
Yu-Han Yange7baef32018-02-09 13:58:17 -08001151 method_requestLocation = env->GetMethodID(clazz, "requestLocation", "(Z)V");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001152 method_requestRefLocation = env->GetMethodID(clazz, "requestRefLocation", "()V");
1153 method_requestSetID = env->GetMethodID(clazz, "requestSetID", "(I)V");
1154 method_requestUtcTime = env->GetMethodID(clazz, "requestUtcTime", "()V");
1155 method_reportGeofenceTransition = env->GetMethodID(clazz, "reportGeofenceTransition",
Wyatt Riley5d229832017-02-10 17:06:00 -08001156 "(ILandroid/location/Location;IJ)V");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001157 method_reportGeofenceStatus = env->GetMethodID(clazz, "reportGeofenceStatus",
Wyatt Riley5d229832017-02-10 17:06:00 -08001158 "(ILandroid/location/Location;)V");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001159 method_reportGeofenceAddStatus = env->GetMethodID(clazz, "reportGeofenceAddStatus",
1160 "(II)V");
1161 method_reportGeofenceRemoveStatus = env->GetMethodID(clazz, "reportGeofenceRemoveStatus",
1162 "(II)V");
1163 method_reportGeofenceResumeStatus = env->GetMethodID(clazz, "reportGeofenceResumeStatus",
1164 "(II)V");
1165 method_reportGeofencePauseStatus = env->GetMethodID(clazz, "reportGeofencePauseStatus",
1166 "(II)V");
1167 method_reportMeasurementData = env->GetMethodID(
1168 clazz,
1169 "reportMeasurementData",
1170 "(Landroid/location/GnssMeasurementsEvent;)V");
1171 method_reportNavigationMessages = env->GetMethodID(
1172 clazz,
1173 "reportNavigationMessage",
1174 "(Landroid/location/GnssNavigationMessage;)V");
Wyatt Rileycf879db2017-01-12 13:57:38 -08001175 method_reportLocationBatch = env->GetMethodID(
1176 clazz,
1177 "reportLocationBatch",
1178 "([Landroid/location/Location;)V");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001179
Hridya Valsarajub5b6ffe2017-01-05 15:13:34 -08001180 /*
1181 * Save a pointer to JVM.
1182 */
1183 jint jvmStatus = env->GetJavaVM(&sJvm);
1184 if (jvmStatus != JNI_OK) {
1185 LOG_ALWAYS_FATAL("Unable to get Java VM. Error: %d", jvmStatus);
1186 }
1187
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001188 if (gnssHal != nullptr) {
gomo25208882017-04-15 02:05:25 -07001189 gnssHalDeathRecipient = new GnssDeathRecipient();
1190 hardware::Return<bool> linked = gnssHal->linkToDeath(
1191 gnssHalDeathRecipient, /*cookie*/ 0);
1192 if (!linked.isOk()) {
1193 ALOGE("Transaction error in linking to GnssHAL death: %s",
1194 linked.description().c_str());
1195 } else if (!linked) {
1196 ALOGW("Unable to link to GnssHal death notifications");
1197 } else {
1198 ALOGD("Link to death notification successful");
1199 }
1200
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001201 auto gnssXtra = gnssHal->getExtensionXtra();
1202 if (!gnssXtra.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001203 ALOGD("Unable to get a handle to Xtra");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001204 } else {
1205 gnssXtraIface = gnssXtra;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001206 }
1207
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001208 auto gnssRil = gnssHal->getExtensionAGnssRil();
1209 if (!gnssRil.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001210 ALOGD("Unable to get a handle to AGnssRil");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001211 } else {
1212 agnssRilIface = gnssRil;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001213 }
1214
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001215 auto gnssAgnss = gnssHal->getExtensionAGnss();
1216 if (!gnssAgnss.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001217 ALOGD("Unable to get a handle to AGnss");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001218 } else {
1219 agnssIface = gnssAgnss;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001220 }
1221
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001222 auto gnssNavigationMessage = gnssHal->getExtensionGnssNavigationMessage();
1223 if (!gnssNavigationMessage.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001224 ALOGD("Unable to get a handle to GnssNavigationMessage");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001225 } else {
1226 gnssNavigationMessageIface = gnssNavigationMessage;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001227 }
1228
gomo48f1a642017-11-10 20:35:46 -08001229 if (gnssHal_V1_1 != nullptr) {
1230 auto gnssMeasurement = gnssHal_V1_1->getExtensionGnssMeasurement_1_1();
1231 if (!gnssMeasurement.isOk()) {
1232 ALOGD("Unable to get a handle to GnssMeasurement");
1233 } else {
1234 gnssMeasurementIface_V1_1 = gnssMeasurement;
1235 gnssMeasurementIface = gnssMeasurementIface_V1_1;
1236 }
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001237 } else {
gomo48f1a642017-11-10 20:35:46 -08001238 auto gnssMeasurement_V1_0 = gnssHal->getExtensionGnssMeasurement();
1239 if (!gnssMeasurement_V1_0.isOk()) {
1240 ALOGD("Unable to get a handle to GnssMeasurement");
1241 } else {
1242 gnssMeasurementIface = gnssMeasurement_V1_0;
1243 }
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001244 }
1245
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001246 auto gnssDebug = gnssHal->getExtensionGnssDebug();
1247 if (!gnssDebug.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001248 ALOGD("Unable to get a handle to GnssDebug");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001249 } else {
1250 gnssDebugIface = gnssDebug;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001251 }
1252
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001253 auto gnssNi = gnssHal->getExtensionGnssNi();
1254 if (!gnssNi.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001255 ALOGD("Unable to get a handle to GnssNi");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001256 } else {
1257 gnssNiIface = gnssNi;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001258 }
1259
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001260 auto gnssConfiguration = gnssHal->getExtensionGnssConfiguration();
1261 if (!gnssConfiguration.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001262 ALOGD("Unable to get a handle to GnssConfiguration");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001263 } else {
1264 gnssConfigurationIface = gnssConfiguration;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001265 }
1266
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001267 auto gnssGeofencing = gnssHal->getExtensionGnssGeofencing();
1268 if (!gnssGeofencing.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001269 ALOGD("Unable to get a handle to GnssGeofencing");
Martijn Coenen3a3a4ac2017-01-04 12:57:47 +01001270 } else {
1271 gnssGeofencingIface = gnssGeofencing;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001272 }
Wyatt Rileycf879db2017-01-12 13:57:38 -08001273
1274 auto gnssBatching = gnssHal->getExtensionGnssBatching();
1275 if (!gnssBatching.isOk()) {
1276 ALOGD("Unable to get a handle to gnssBatching");
1277 } else {
1278 gnssBatchingIface = gnssBatching;
1279 }
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001280 } else {
1281 ALOGE("Unable to get GPS service\n");
1282 }
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001283}
1284
1285static jboolean android_location_GnssLocationProvider_is_supported(
1286 JNIEnv* /* env */, jclass /* clazz */) {
1287 return (gnssHal != nullptr) ? JNI_TRUE : JNI_FALSE;
1288}
1289
1290static jboolean android_location_GnssLocationProvider_is_agps_ril_supported(
1291 JNIEnv* /* env */, jclass /* clazz */) {
1292 return (agnssRilIface != nullptr) ? JNI_TRUE : JNI_FALSE;
1293}
1294
1295static jboolean android_location_gpsLocationProvider_is_gnss_configuration_supported(
1296 JNIEnv* /* env */, jclass /* jclazz */) {
1297 return (gnssConfigurationIface != nullptr) ? JNI_TRUE : JNI_FALSE;
1298}
1299
1300static jboolean android_location_GnssLocationProvider_init(JNIEnv* env, jobject obj) {
1301 /*
1302 * This must be set before calling into the HAL library.
1303 */
1304 if (!mCallbacksObj)
1305 mCallbacksObj = env->NewGlobalRef(obj);
1306
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001307 /*
1308 * Fail if the main interface fails to initialize
1309 */
1310 if (gnssHal == nullptr) {
1311 ALOGE("Unable to Initialize GNSS HAL\n");
1312 return JNI_FALSE;
1313 }
1314
Wyatt Rileyfb840922017-11-08 15:07:58 -08001315 sp<IGnssCallback> gnssCbIface = new GnssCallback();
1316
1317 Return<bool> result = false;
gomo48f1a642017-11-10 20:35:46 -08001318 if (gnssHal_V1_1 != nullptr) {
1319 result = gnssHal_V1_1->setCallback_1_1(gnssCbIface);
Wyatt Rileyfb840922017-11-08 15:07:58 -08001320 } else {
1321 result = gnssHal->setCallback(gnssCbIface);
1322 }
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001323 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001324 ALOGE("SetCallback for Gnss Interface fails\n");
1325 return JNI_FALSE;
1326 }
1327
1328 sp<IGnssXtraCallback> gnssXtraCbIface = new GnssXtraCallback();
1329 if (gnssXtraIface == nullptr) {
1330 ALOGE("Unable to initialize GNSS Xtra interface\n");
Hridya Valsarajue8650322016-12-05 20:23:21 -08001331 } else {
1332 result = gnssXtraIface->setCallback(gnssXtraCbIface);
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001333 if (!result.isOk() || !result) {
Hridya Valsarajue8650322016-12-05 20:23:21 -08001334 gnssXtraIface = nullptr;
Wyatt Rileyfb840922017-11-08 15:07:58 -08001335 ALOGI("SetCallback for Gnss Xtra Interface fails\n");
Hridya Valsarajue8650322016-12-05 20:23:21 -08001336 }
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001337 }
1338
1339 sp<IAGnssCallback> aGnssCbIface = new AGnssCallback();
1340 if (agnssIface != nullptr) {
1341 agnssIface->setCallback(aGnssCbIface);
1342 } else {
Wyatt Rileyfb840922017-11-08 15:07:58 -08001343 ALOGI("Unable to Initialize AGnss interface\n");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001344 }
1345
1346 sp<IGnssGeofenceCallback> gnssGeofencingCbIface = new GnssGeofenceCallback();
1347 if (gnssGeofencingIface != nullptr) {
1348 gnssGeofencingIface->setCallback(gnssGeofencingCbIface);
1349 } else {
Wyatt Rileyfb840922017-11-08 15:07:58 -08001350 ALOGI("Unable to initialize GNSS Geofencing interface\n");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001351 }
1352
1353 sp<IGnssNiCallback> gnssNiCbIface = new GnssNiCallback();
Hridya Valsaraju388e9682017-03-08 10:57:06 -08001354 if (gnssNiIface != nullptr) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001355 gnssNiIface->setCallback(gnssNiCbIface);
1356 } else {
Wyatt Rileyfb840922017-11-08 15:07:58 -08001357 ALOGI("Unable to initialize GNSS NI interface\n");
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001358 }
1359
Jaekyun Seokf9038ad2017-11-13 15:03:21 +09001360 sp<IAGnssRilCallback> aGnssRilCbIface = new AGnssRilCallback();
1361 if (agnssRilIface != nullptr) {
1362 agnssRilIface->setCallback(aGnssRilCbIface);
1363 } else {
1364 ALOGI("Unable to Initialize AGnss Ril interface\n");
1365 }
1366
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001367 return JNI_TRUE;
1368}
1369
1370static void android_location_GnssLocationProvider_cleanup(JNIEnv* /* env */, jobject /* obj */) {
1371 if (gnssHal != nullptr) {
1372 gnssHal->cleanup();
1373 }
1374}
1375
1376static jboolean android_location_GnssLocationProvider_set_position_mode(JNIEnv* /* env */,
1377 jobject /* obj */, jint mode, jint recurrence, jint min_interval, jint preferred_accuracy,
gomo48f1a642017-11-10 20:35:46 -08001378 jint preferred_time, jboolean low_power_mode) {
1379 Return<bool> result = false;
1380 if (gnssHal_V1_1 != nullptr) {
Wyatt Riley46ac9562018-03-02 20:16:58 -08001381 result = gnssHal_V1_1->setPositionMode_1_1(static_cast<IGnss_V1_0::GnssPositionMode>(mode),
1382 static_cast<IGnss_V1_0::GnssPositionRecurrence>(recurrence),
1383 min_interval,
1384 preferred_accuracy,
1385 preferred_time,
1386 low_power_mode);
gomo48f1a642017-11-10 20:35:46 -08001387 } else if (gnssHal != nullptr) {
Wyatt Riley46ac9562018-03-02 20:16:58 -08001388 result = gnssHal->setPositionMode(static_cast<IGnss_V1_0::GnssPositionMode>(mode),
1389 static_cast<IGnss_V1_0::GnssPositionRecurrence>(recurrence),
1390 min_interval,
1391 preferred_accuracy,
1392 preferred_time);
gomo48f1a642017-11-10 20:35:46 -08001393 }
1394 if (!result.isOk()) {
1395 ALOGE("%s: GNSS setPositionMode failed\n", __func__);
1396 return JNI_FALSE;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001397 } else {
gomo48f1a642017-11-10 20:35:46 -08001398 return result;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001399 }
1400}
1401
1402static jboolean android_location_GnssLocationProvider_start(JNIEnv* /* env */, jobject /* obj */) {
1403 if (gnssHal != nullptr) {
1404 auto result = gnssHal->start();
Steven Morelandd002a8b2017-01-03 17:18:24 -08001405 if (!result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001406 return JNI_FALSE;
1407 } else {
1408 return result;
1409 }
1410 } else {
1411 return JNI_FALSE;
1412 }
1413}
1414
1415static jboolean android_location_GnssLocationProvider_stop(JNIEnv* /* env */, jobject /* obj */) {
1416 if (gnssHal != nullptr) {
1417 auto result = gnssHal->stop();
Steven Morelandd002a8b2017-01-03 17:18:24 -08001418 if (!result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001419 return JNI_FALSE;
1420 } else {
1421 return result;
1422 }
1423 } else {
1424 return JNI_FALSE;
1425 }
1426}
1427static void android_location_GnssLocationProvider_delete_aiding_data(JNIEnv* /* env */,
1428 jobject /* obj */,
1429 jint flags) {
1430 if (gnssHal != nullptr) {
Wyatt Riley46ac9562018-03-02 20:16:58 -08001431 auto result = gnssHal->deleteAidingData(static_cast<IGnss_V1_0::GnssAidingData>(flags));
Steven Morelandd002a8b2017-01-03 17:18:24 -08001432 if (!result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001433 ALOGE("Error in deleting aiding data");
1434 }
1435 }
1436}
1437
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001438static void android_location_GnssLocationProvider_agps_set_reference_location_cellid(
1439 JNIEnv* /* env */, jobject /* obj */, jint type, jint mcc, jint mnc, jint lac, jint cid) {
1440 IAGnssRil::AGnssRefLocation location;
1441
1442 if (agnssRilIface == nullptr) {
1443 ALOGE("No AGPS RIL interface in agps_set_reference_location_cellid");
1444 return;
1445 }
1446
1447 switch (static_cast<IAGnssRil::AGnssRefLocationType>(type)) {
1448 case IAGnssRil::AGnssRefLocationType::GSM_CELLID:
1449 case IAGnssRil::AGnssRefLocationType::UMTS_CELLID:
1450 location.type = static_cast<IAGnssRil::AGnssRefLocationType>(type);
1451 location.cellID.mcc = mcc;
1452 location.cellID.mnc = mnc;
1453 location.cellID.lac = lac;
1454 location.cellID.cid = cid;
1455 break;
1456 default:
1457 ALOGE("Neither a GSM nor a UMTS cellid (%s:%d).", __FUNCTION__, __LINE__);
1458 return;
1459 break;
1460 }
1461
1462 agnssRilIface->setRefLocation(location);
1463}
1464
1465static void android_location_GnssLocationProvider_agps_set_id(JNIEnv *env, jobject /* obj */,
1466 jint type, jstring setid_string) {
1467 if (agnssRilIface == nullptr) {
1468 ALOGE("no AGPS RIL interface in agps_set_id");
1469 return;
1470 }
1471
1472 const char *setid = env->GetStringUTFChars(setid_string, NULL);
1473 agnssRilIface->setSetId((IAGnssRil::SetIDType)type, setid);
1474 env->ReleaseStringUTFChars(setid_string, setid);
1475}
1476
1477static jint android_location_GnssLocationProvider_read_nmea(JNIEnv* env, jobject /* obj */,
1478 jbyteArray nmeaArray, jint buffer_size) {
1479 // this should only be called from within a call to reportNmea
1480 jbyte* nmea = reinterpret_cast<jbyte *>(env->GetPrimitiveArrayCritical(nmeaArray, 0));
1481 int length = GnssCallback::sNmeaStringLength;
1482 if (length > buffer_size)
1483 length = buffer_size;
1484 memcpy(nmea, GnssCallback::sNmeaString, length);
1485 env->ReleasePrimitiveArrayCritical(nmeaArray, nmea, JNI_ABORT);
1486 return (jint) length;
1487}
1488
1489static void android_location_GnssLocationProvider_inject_time(JNIEnv* /* env */, jobject /* obj */,
1490 jlong time, jlong timeReference, jint uncertainty) {
1491 if (gnssHal != nullptr) {
1492 auto result = gnssHal->injectTime(time, timeReference, uncertainty);
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001493 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001494 ALOGE("%s: Gnss injectTime() failed", __func__);
1495 }
1496 }
1497}
1498
Yu-Han Yange7baef32018-02-09 13:58:17 -08001499static void android_location_GnssLocationProvider_inject_best_location(
1500 JNIEnv*,
1501 jobject,
1502 jint gnssLocationFlags,
1503 jdouble latitudeDegrees,
1504 jdouble longitudeDegrees,
1505 jdouble altitudeMeters,
1506 jfloat speedMetersPerSec,
1507 jfloat bearingDegrees,
1508 jfloat horizontalAccuracyMeters,
1509 jfloat verticalAccuracyMeters,
1510 jfloat speedAccuracyMetersPerSecond,
1511 jfloat bearingAccuracyDegrees,
1512 jlong timestamp) {
1513 if (gnssHal_V1_1 != nullptr) {
1514 GnssLocation location = createGnssLocation(
1515 gnssLocationFlags,
1516 latitudeDegrees,
1517 longitudeDegrees,
1518 altitudeMeters,
1519 speedMetersPerSec,
1520 bearingDegrees,
1521 horizontalAccuracyMeters,
1522 verticalAccuracyMeters,
1523 speedAccuracyMetersPerSecond,
1524 bearingAccuracyDegrees,
1525 timestamp);
1526 auto result = gnssHal_V1_1->injectBestLocation(location);
1527 if (!result.isOk() || !result) {
1528 ALOGE("%s: Gnss injectBestLocation() failed.", __func__);
1529 }
1530 } else {
1531 ALOGE("%s: injectBestLocation() is called but gnssHal_V1_1 is not available.", __func__);
1532 }
1533}
1534
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001535static void android_location_GnssLocationProvider_inject_location(JNIEnv* /* env */,
1536 jobject /* obj */, jdouble latitude, jdouble longitude, jfloat accuracy) {
1537 if (gnssHal != nullptr) {
1538 auto result = gnssHal->injectLocation(latitude, longitude, accuracy);
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001539 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001540 ALOGE("%s: Gnss injectLocation() failed", __func__);
1541 }
1542 }
1543}
1544
1545static jboolean android_location_GnssLocationProvider_supports_xtra(
1546 JNIEnv* /* env */, jobject /* obj */) {
1547 return (gnssXtraIface != nullptr) ? JNI_TRUE : JNI_FALSE;
1548}
1549
1550static void android_location_GnssLocationProvider_inject_xtra_data(JNIEnv* env, jobject /* obj */,
1551 jbyteArray data, jint length) {
1552 if (gnssXtraIface == nullptr) {
1553 ALOGE("XTRA Interface not supported");
1554 return;
1555 }
1556
1557 jbyte* bytes = reinterpret_cast<jbyte *>(env->GetPrimitiveArrayCritical(data, 0));
1558 gnssXtraIface->injectXtraData(std::string((const char*)bytes, length));
1559 env->ReleasePrimitiveArrayCritical(data, bytes, JNI_ABORT);
1560}
1561
1562static void android_location_GnssLocationProvider_agps_data_conn_open(
1563 JNIEnv* env, jobject /* obj */, jstring apn, jint apnIpType) {
1564 if (agnssIface == nullptr) {
1565 ALOGE("no AGPS interface in agps_data_conn_open");
1566 return;
1567 }
1568 if (apn == NULL) {
1569 jniThrowException(env, "java/lang/IllegalArgumentException", NULL);
1570 return;
1571 }
1572
1573 const char *apnStr = env->GetStringUTFChars(apn, NULL);
1574
1575 auto result = agnssIface->dataConnOpen(apnStr, static_cast<IAGnss::ApnIpType>(apnIpType));
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001576 if (!result.isOk() || !result){
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001577 ALOGE("%s: Failed to set APN and its IP type", __func__);
1578 }
1579 env->ReleaseStringUTFChars(apn, apnStr);
1580}
1581
1582static void android_location_GnssLocationProvider_agps_data_conn_closed(JNIEnv* /* env */,
1583 jobject /* obj */) {
1584 if (agnssIface == nullptr) {
1585 ALOGE("%s: AGPS interface not supported", __func__);
1586 return;
1587 }
1588
1589 auto result = agnssIface->dataConnClosed();
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001590 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001591 ALOGE("%s: Failed to close AGnss data connection", __func__);
1592 }
1593}
1594
1595static void android_location_GnssLocationProvider_agps_data_conn_failed(JNIEnv* /* env */,
1596 jobject /* obj */) {
1597 if (agnssIface == nullptr) {
1598 ALOGE("%s: AGPS interface not supported", __func__);
1599 return;
1600 }
1601
1602 auto result = agnssIface->dataConnFailed();
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001603 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001604 ALOGE("%s: Failed to notify unavailability of AGnss data connection", __func__);
1605 }
1606}
1607
1608static void android_location_GnssLocationProvider_set_agps_server(JNIEnv* env, jobject /* obj */,
1609 jint type, jstring hostname, jint port) {
1610 if (agnssIface == nullptr) {
1611 ALOGE("no AGPS interface in set_agps_server");
1612 return;
1613 }
1614
1615 const char *c_hostname = env->GetStringUTFChars(hostname, NULL);
1616 auto result = agnssIface->setServer(static_cast<IAGnssCallback::AGnssType>(type),
1617 c_hostname,
1618 port);
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001619 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001620 ALOGE("%s: Failed to set AGnss host name and port", __func__);
1621 }
1622
1623 env->ReleaseStringUTFChars(hostname, c_hostname);
1624}
1625
1626static void android_location_GnssLocationProvider_send_ni_response(JNIEnv* /* env */,
1627 jobject /* obj */, jint notifId, jint response) {
1628 if (gnssNiIface == nullptr) {
1629 ALOGE("no NI interface in send_ni_response");
1630 return;
1631 }
1632
1633 gnssNiIface->respond(notifId, static_cast<IGnssNiCallback::GnssUserResponseType>(response));
1634}
1635
1636static jstring android_location_GnssLocationProvider_get_internal_state(JNIEnv* env,
1637 jobject /* obj */) {
1638 jstring result = NULL;
1639 /*
1640 * TODO(b/33089503) : Create a jobject to represent GnssDebug.
1641 */
Wyatt Riley268c6e02017-03-29 10:21:46 -07001642
1643 std::stringstream internalState;
1644
1645 if (gnssDebugIface == nullptr) {
1646 internalState << "Gnss Debug Interface not available" << std::endl;
1647 } else {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001648 IGnssDebug::DebugData data;
1649 gnssDebugIface->getDebugData([&data](const IGnssDebug::DebugData& debugData) {
1650 data = debugData;
1651 });
1652
Wyatt Riley268c6e02017-03-29 10:21:46 -07001653 internalState << "Gnss Location Data:: ";
1654 if (!data.position.valid) {
1655 internalState << "not valid";
1656 } else {
1657 internalState << "LatitudeDegrees: " << data.position.latitudeDegrees
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001658 << ", LongitudeDegrees: " << data.position.longitudeDegrees
1659 << ", altitudeMeters: " << data.position.altitudeMeters
gomo4402af62017-01-11 13:20:13 -08001660 << ", speedMetersPerSecond: " << data.position.speedMetersPerSec
1661 << ", bearingDegrees: " << data.position.bearingDegrees
Wyatt Riley268c6e02017-03-29 10:21:46 -07001662 << ", horizontalAccuracyMeters: "
1663 << data.position.horizontalAccuracyMeters
gomo4402af62017-01-11 13:20:13 -08001664 << ", verticalAccuracyMeters: " << data.position.verticalAccuracyMeters
Wyatt Riley268c6e02017-03-29 10:21:46 -07001665 << ", speedAccuracyMetersPerSecond: "
1666 << data.position.speedAccuracyMetersPerSecond
gomo4402af62017-01-11 13:20:13 -08001667 << ", bearingAccuracyDegrees: " << data.position.bearingAccuracyDegrees
Wyatt Riley268c6e02017-03-29 10:21:46 -07001668 << ", ageSeconds: " << data.position.ageSeconds;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001669 }
Wyatt Riley268c6e02017-03-29 10:21:46 -07001670 internalState << std::endl;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001671
Wyatt Riley268c6e02017-03-29 10:21:46 -07001672 internalState << "Gnss Time Data:: timeEstimate: " << data.time.timeEstimate
1673 << ", timeUncertaintyNs: " << data.time.timeUncertaintyNs
1674 << ", frequencyUncertaintyNsPerSec: "
1675 << data.time.frequencyUncertaintyNsPerSec << std::endl;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001676
1677 if (data.satelliteDataArray.size() != 0) {
Wyatt Riley268c6e02017-03-29 10:21:46 -07001678 internalState << "Satellite Data for " << data.satelliteDataArray.size()
1679 << " satellites:: " << std::endl;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001680 }
1681
Wyatt Riley77ca4f82017-06-30 18:13:44 -07001682 internalState << "constellation: 1=GPS, 2=SBAS, 3=GLO, 4=QZSS, 5=BDS, 6=GAL; "
1683 << "ephemerisType: 0=Eph, 1=Alm, 2=?; "
1684 << "ephemerisSource: 0=Demod, 1=Supl, 2=Server, 3=?; "
1685 << "ephemerisHealth: 0=Good, 1=Bad, 2=?" << std::endl;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001686 for (size_t i = 0; i < data.satelliteDataArray.size(); i++) {
1687 internalState << "svid: " << data.satelliteDataArray[i].svid
1688 << ", constellation: "
1689 << static_cast<uint32_t>(data.satelliteDataArray[i].constellation)
1690 << ", ephemerisType: "
1691 << static_cast<uint32_t>(data.satelliteDataArray[i].ephemerisType)
Wyatt Riley268c6e02017-03-29 10:21:46 -07001692 << ", ephemerisSource: "
1693 << static_cast<uint32_t>(data.satelliteDataArray[i].ephemerisSource)
1694 << ", ephemerisHealth: "
1695 << static_cast<uint32_t>(data.satelliteDataArray[i].ephemerisHealth)
1696 << ", serverPredictionIsAvailable: "
1697 << data.satelliteDataArray[i].serverPredictionIsAvailable
1698 << ", serverPredictionAgeSeconds: "
1699 << data.satelliteDataArray[i].serverPredictionAgeSeconds
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001700 << ", ephemerisAgeSeconds: "
1701 << data.satelliteDataArray[i].ephemerisAgeSeconds << std::endl;
1702 }
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001703 }
Wyatt Riley268c6e02017-03-29 10:21:46 -07001704
1705 result = env->NewStringUTF(internalState.str().c_str());
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001706 return result;
1707}
1708
1709static void android_location_GnssLocationProvider_update_network_state(JNIEnv* env,
1710 jobject /* obj */,
1711 jboolean connected,
1712 jint type,
1713 jboolean roaming,
1714 jboolean available,
1715 jstring extraInfo,
1716 jstring apn) {
1717 if (agnssRilIface != nullptr) {
1718 auto result = agnssRilIface->updateNetworkState(connected,
1719 static_cast<IAGnssRil::NetworkType>(type),
1720 roaming);
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001721 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001722 ALOGE("updateNetworkState failed");
1723 }
1724
1725 const char *c_apn = env->GetStringUTFChars(apn, NULL);
1726 result = agnssRilIface->updateNetworkAvailability(available, c_apn);
Hridya Valsarajuf6423ba2017-02-28 09:40:48 -08001727 if (!result.isOk() || !result) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001728 ALOGE("updateNetworkAvailability failed");
1729 }
1730
1731 env->ReleaseStringUTFChars(apn, c_apn);
1732 } else {
1733 ALOGE("AGnssRilInterface does not exist");
1734 }
1735}
1736
1737static jboolean android_location_GnssLocationProvider_is_geofence_supported(
1738 JNIEnv* /* env */, jobject /* obj */) {
1739 return (gnssGeofencingIface != nullptr) ? JNI_TRUE : JNI_FALSE;
1740}
1741
1742static jboolean android_location_GnssLocationProvider_add_geofence(JNIEnv* /* env */,
1743 jobject /* obj */, jint geofenceId, jdouble latitude, jdouble longitude, jdouble radius,
1744 jint last_transition, jint monitor_transition, jint notification_responsiveness,
1745 jint unknown_timer) {
1746 if (gnssGeofencingIface != nullptr) {
1747 auto result = gnssGeofencingIface->addGeofence(
1748 geofenceId, latitude, longitude, radius,
1749 static_cast<IGnssGeofenceCallback::GeofenceTransition>(last_transition),
1750 monitor_transition, notification_responsiveness, unknown_timer);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001751 return boolToJbool(result.isOk());
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001752 } else {
1753 ALOGE("Geofence Interface not available");
1754 }
1755 return JNI_FALSE;
1756}
1757
1758static jboolean android_location_GnssLocationProvider_remove_geofence(JNIEnv* /* env */,
1759 jobject /* obj */, jint geofenceId) {
1760 if (gnssGeofencingIface != nullptr) {
1761 auto result = gnssGeofencingIface->removeGeofence(geofenceId);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001762 return boolToJbool(result.isOk());
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001763 } else {
1764 ALOGE("Geofence interface not available");
1765 }
1766 return JNI_FALSE;
1767}
1768
1769static jboolean android_location_GnssLocationProvider_pause_geofence(JNIEnv* /* env */,
1770 jobject /* obj */, jint geofenceId) {
1771 if (gnssGeofencingIface != nullptr) {
1772 auto result = gnssGeofencingIface->pauseGeofence(geofenceId);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001773 return boolToJbool(result.isOk());
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001774 } else {
1775 ALOGE("Geofence interface not available");
1776 }
1777 return JNI_FALSE;
1778}
1779
1780static jboolean android_location_GnssLocationProvider_resume_geofence(JNIEnv* /* env */,
1781 jobject /* obj */, jint geofenceId, jint monitor_transition) {
1782 if (gnssGeofencingIface != nullptr) {
1783 auto result = gnssGeofencingIface->resumeGeofence(geofenceId, monitor_transition);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001784 return boolToJbool(result.isOk());
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001785 } else {
1786 ALOGE("Geofence interface not available");
1787 }
1788 return JNI_FALSE;
1789}
1790
Lifu Tang30f95a72016-01-07 23:20:38 -08001791static jboolean android_location_GnssLocationProvider_is_measurement_supported(
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001792 JNIEnv* env, jclass clazz) {
1793 if (gnssMeasurementIface != nullptr) {
destradaaea8a8a62014-06-23 18:19:03 -07001794 return JNI_TRUE;
1795 }
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001796
destradaaea8a8a62014-06-23 18:19:03 -07001797 return JNI_FALSE;
1798}
1799
Lifu Tang30f95a72016-01-07 23:20:38 -08001800static jboolean android_location_GnssLocationProvider_start_measurement_collection(
gomo48f1a642017-11-10 20:35:46 -08001801 JNIEnv* /* env */,
1802 jobject /* obj */,
1803 jboolean enableFullTracking) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001804 if (gnssMeasurementIface == nullptr) {
1805 ALOGE("GNSS Measurement interface is not available.");
destradaaea8a8a62014-06-23 18:19:03 -07001806 return JNI_FALSE;
1807 }
1808
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001809 sp<GnssMeasurementCallback> cbIface = new GnssMeasurementCallback();
gomo48f1a642017-11-10 20:35:46 -08001810 IGnssMeasurement_V1_0::GnssMeasurementStatus result =
1811 IGnssMeasurement_V1_0::GnssMeasurementStatus::ERROR_GENERIC;;
1812 if (gnssMeasurementIface_V1_1 != nullptr) {
1813 result = gnssMeasurementIface_V1_1->setCallback_1_1(cbIface,
1814 enableFullTracking);
1815 } else {
1816 if (enableFullTracking == JNI_TRUE) {
1817 // full tracking mode not supported in 1.0 HAL
1818 return JNI_FALSE;
1819 }
1820 result = gnssMeasurementIface->setCallback(cbIface);
1821 }
1822
1823 if (result != IGnssMeasurement_V1_0::GnssMeasurementStatus::SUCCESS) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001824 ALOGE("An error has been found on GnssMeasurementInterface::init, status=%d",
1825 static_cast<int32_t>(result));
destradaaea8a8a62014-06-23 18:19:03 -07001826 return JNI_FALSE;
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001827 } else {
1828 ALOGD("gnss measurement infc has been enabled");
destradaaea8a8a62014-06-23 18:19:03 -07001829 }
1830
1831 return JNI_TRUE;
1832}
1833
Lifu Tang30f95a72016-01-07 23:20:38 -08001834static jboolean android_location_GnssLocationProvider_stop_measurement_collection(
destradaaea8a8a62014-06-23 18:19:03 -07001835 JNIEnv* env,
1836 jobject obj) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001837 if (gnssMeasurementIface == nullptr) {
destradaaea8a8a62014-06-23 18:19:03 -07001838 ALOGE("Measurement interface not available");
1839 return JNI_FALSE;
1840 }
1841
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001842 auto result = gnssMeasurementIface->close();
Steven Morelandd002a8b2017-01-03 17:18:24 -08001843 return boolToJbool(result.isOk());
destradaaea8a8a62014-06-23 18:19:03 -07001844}
1845
Lifu Tang30f95a72016-01-07 23:20:38 -08001846static jboolean android_location_GnssLocationProvider_is_navigation_message_supported(
destradaa4b3e3932014-07-21 18:01:47 -07001847 JNIEnv* env,
1848 jclass clazz) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001849 if (gnssNavigationMessageIface != nullptr) {
destradaa4b3e3932014-07-21 18:01:47 -07001850 return JNI_TRUE;
1851 }
1852 return JNI_FALSE;
1853}
1854
Lifu Tang30f95a72016-01-07 23:20:38 -08001855static jboolean android_location_GnssLocationProvider_start_navigation_message_collection(
destradaa4b3e3932014-07-21 18:01:47 -07001856 JNIEnv* env,
1857 jobject obj) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001858 if (gnssNavigationMessageIface == nullptr) {
destradaa4b3e3932014-07-21 18:01:47 -07001859 ALOGE("Navigation Message interface is not available.");
1860 return JNI_FALSE;
1861 }
1862
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001863 sp<IGnssNavigationMessageCallback> gnssNavigationMessageCbIface =
1864 new GnssNavigationMessageCallback();
1865 IGnssNavigationMessage::GnssNavigationMessageStatus result =
1866 gnssNavigationMessageIface->setCallback(gnssNavigationMessageCbIface);
1867
1868 if (result != IGnssNavigationMessage::GnssNavigationMessageStatus::SUCCESS) {
1869 ALOGE("An error has been found in %s: %d", __FUNCTION__, static_cast<int32_t>(result));
destradaa4b3e3932014-07-21 18:01:47 -07001870 return JNI_FALSE;
1871 }
1872
1873 return JNI_TRUE;
1874}
1875
Lifu Tang30f95a72016-01-07 23:20:38 -08001876static jboolean android_location_GnssLocationProvider_stop_navigation_message_collection(
destradaa4b3e3932014-07-21 18:01:47 -07001877 JNIEnv* env,
1878 jobject obj) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001879 if (gnssNavigationMessageIface == nullptr) {
destradaa4b3e3932014-07-21 18:01:47 -07001880 ALOGE("Navigation Message interface is not available.");
1881 return JNI_FALSE;
1882 }
1883
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001884 auto result = gnssNavigationMessageIface->close();
Steven Morelandd002a8b2017-01-03 17:18:24 -08001885 return boolToJbool(result.isOk());
destradaa4b3e3932014-07-21 18:01:47 -07001886}
1887
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001888static jboolean android_location_GnssLocationProvider_set_emergency_supl_pdn(JNIEnv*,
1889 jobject,
1890 jint emergencySuplPdn) {
1891 if (gnssConfigurationIface == nullptr) {
1892 ALOGE("no GNSS configuration interface available");
1893 return JNI_FALSE;
Tsuwei Chen52617bb2014-08-25 11:49:11 -07001894 }
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001895
1896 auto result = gnssConfigurationIface->setEmergencySuplPdn(emergencySuplPdn);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001897 if (result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001898 return result;
1899 } else {
1900 return JNI_FALSE;
1901 }
1902}
1903
1904static jboolean android_location_GnssLocationProvider_set_supl_version(JNIEnv*,
1905 jobject,
1906 jint version) {
1907 if (gnssConfigurationIface == nullptr) {
1908 ALOGE("no GNSS configuration interface available");
1909 return JNI_FALSE;
1910 }
1911 auto result = gnssConfigurationIface->setSuplVersion(version);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001912 if (result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001913 return result;
1914 } else {
1915 return JNI_FALSE;
1916 }
1917}
1918
1919static jboolean android_location_GnssLocationProvider_set_supl_es(JNIEnv*,
1920 jobject,
1921 jint suplEs) {
1922 if (gnssConfigurationIface == nullptr) {
1923 ALOGE("no GNSS configuration interface available");
1924 return JNI_FALSE;
1925 }
1926
1927 auto result = gnssConfigurationIface->setSuplEs(suplEs);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001928 if (result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001929 return result;
1930 } else {
1931 return JNI_FALSE;
1932 }
1933}
1934
1935static jboolean android_location_GnssLocationProvider_set_supl_mode(JNIEnv*,
1936 jobject,
1937 jint mode) {
1938 if (gnssConfigurationIface == nullptr) {
1939 ALOGE("no GNSS configuration interface available");
1940 return JNI_FALSE;
1941 }
1942
1943 auto result = gnssConfigurationIface->setSuplMode(mode);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001944 if (result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001945 return result;
1946 } else {
1947 return JNI_FALSE;
1948 }
1949}
1950
1951static jboolean android_location_GnssLocationProvider_set_gps_lock(JNIEnv*,
1952 jobject,
1953 jint gpsLock) {
1954 if (gnssConfigurationIface == nullptr) {
1955 ALOGE("no GNSS configuration interface available");
1956 return JNI_FALSE;
1957 }
1958
1959 auto result = gnssConfigurationIface->setGpsLock(gpsLock);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001960 if (result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001961 return result;
1962 } else {
1963 return JNI_FALSE;
1964 }
1965}
1966
1967static jboolean android_location_GnssLocationProvider_set_lpp_profile(JNIEnv*,
1968 jobject,
1969 jint lppProfile) {
1970 if (gnssConfigurationIface == nullptr) {
1971 ALOGE("no GNSS configuration interface available");
1972 return JNI_FALSE;
1973 }
1974
1975 auto result = gnssConfigurationIface->setLppProfile(lppProfile);
1976
Steven Morelandd002a8b2017-01-03 17:18:24 -08001977 if (result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001978 return result;
1979 } else {
1980 return JNI_FALSE;
1981 }
1982}
1983
1984static jboolean android_location_GnssLocationProvider_set_gnss_pos_protocol_select(JNIEnv*,
1985 jobject,
1986 jint gnssPosProtocol) {
1987 if (gnssConfigurationIface == nullptr) {
1988 ALOGE("no GNSS configuration interface available");
1989 return JNI_FALSE;
1990 }
1991
1992 auto result = gnssConfigurationIface->setGlonassPositioningProtocol(gnssPosProtocol);
Steven Morelandd002a8b2017-01-03 17:18:24 -08001993 if (result.isOk()) {
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07001994 return result;
1995 } else {
1996 return JNI_FALSE;
1997 }
Tsuwei Chen52617bb2014-08-25 11:49:11 -07001998}
1999
Wyatt Rileycf879db2017-01-12 13:57:38 -08002000static jint android_location_GnssLocationProvider_get_batch_size(JNIEnv*, jclass) {
2001 if (gnssBatchingIface == nullptr) {
2002 return 0; // batching not supported, size = 0
2003 }
2004 auto result = gnssBatchingIface->getBatchSize();
2005 if (result.isOk()) {
2006 return static_cast<jint>(result);
2007 } else {
2008 return 0; // failure in binder, don't support batching
2009 }
2010}
2011
2012static jboolean android_location_GnssLocationProvider_init_batching(JNIEnv*, jclass) {
2013 if (gnssBatchingIface == nullptr) {
2014 return JNI_FALSE; // batching not supported
2015 }
2016 sp<IGnssBatchingCallback> gnssBatchingCbIface = new GnssBatchingCallback();
2017
2018 return static_cast<jboolean>(gnssBatchingIface->init(gnssBatchingCbIface));
2019}
2020
2021static void android_location_GnssLocationProvider_cleanup_batching(JNIEnv*, jclass) {
2022 if (gnssBatchingIface == nullptr) {
2023 return; // batching not supported
2024 }
2025 gnssBatchingIface->cleanup();
2026}
2027
2028static jboolean android_location_GnssLocationProvider_start_batch(JNIEnv*, jclass,
2029 jlong periodNanos, jboolean wakeOnFifoFull) {
2030 if (gnssBatchingIface == nullptr) {
2031 return JNI_FALSE; // batching not supported
2032 }
2033
2034 IGnssBatching::Options options;
2035 options.periodNanos = periodNanos;
2036 if (wakeOnFifoFull) {
2037 options.flags = static_cast<uint8_t>(IGnssBatching::Flag::WAKEUP_ON_FIFO_FULL);
2038 } else {
2039 options.flags = 0;
2040 }
2041
2042 return static_cast<jboolean>(gnssBatchingIface->start(options));
2043}
2044
2045static void android_location_GnssLocationProvider_flush_batch(JNIEnv*, jclass) {
2046 if (gnssBatchingIface == nullptr) {
2047 return; // batching not supported
2048 }
2049
2050 gnssBatchingIface->flush();
2051}
2052
2053static jboolean android_location_GnssLocationProvider_stop_batch(JNIEnv*, jclass) {
2054 if (gnssBatchingIface == nullptr) {
2055 return JNI_FALSE; // batching not supported
2056 }
2057
2058 return gnssBatchingIface->stop();
2059}
2060
Daniel Micay76f6a862015-09-19 17:31:01 -04002061static const JNINativeMethod sMethods[] = {
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002062 /* name, signature, funcPtr */
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002063 {"class_init_native", "()V", reinterpret_cast<void *>(
2064 android_location_GnssLocationProvider_class_init_native)},
2065 {"native_is_supported", "()Z", reinterpret_cast<void *>(
2066 android_location_GnssLocationProvider_is_supported)},
destradaaef752b62015-04-17 13:10:47 -07002067 {"native_is_agps_ril_supported", "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002068 reinterpret_cast<void *>(android_location_GnssLocationProvider_is_agps_ril_supported)},
destradaaef752b62015-04-17 13:10:47 -07002069 {"native_is_gnss_configuration_supported", "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002070 reinterpret_cast<void *>(
2071 android_location_gpsLocationProvider_is_gnss_configuration_supported)},
Yu-Han Yang6d317352018-03-15 11:53:01 -07002072 {"native_init_once", "()V", reinterpret_cast<void *>(
2073 android_location_GnssLocationProvider_init_once)},
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002074 {"native_init", "()Z", reinterpret_cast<void *>(android_location_GnssLocationProvider_init)},
2075 {"native_cleanup", "()V", reinterpret_cast<void *>(
2076 android_location_GnssLocationProvider_cleanup)},
destradaaea8a8a62014-06-23 18:19:03 -07002077 {"native_set_position_mode",
gomo48f1a642017-11-10 20:35:46 -08002078 "(IIIIIZ)Z",
2079 reinterpret_cast<void*>(android_location_GnssLocationProvider_set_position_mode)},
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002080 {"native_start", "()Z", reinterpret_cast<void*>(android_location_GnssLocationProvider_start)},
2081 {"native_stop", "()Z", reinterpret_cast<void*>(android_location_GnssLocationProvider_stop)},
destradaaea8a8a62014-06-23 18:19:03 -07002082 {"native_delete_aiding_data",
2083 "(I)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002084 reinterpret_cast<void*>(android_location_GnssLocationProvider_delete_aiding_data)},
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002085 {"native_read_nmea", "([BI)I", reinterpret_cast<void *>(
2086 android_location_GnssLocationProvider_read_nmea)},
2087 {"native_inject_time", "(JJI)V", reinterpret_cast<void *>(
2088 android_location_GnssLocationProvider_inject_time)},
Yu-Han Yange7baef32018-02-09 13:58:17 -08002089 {"native_inject_best_location",
2090 "(IDDDFFFFFFJ)V",
2091 reinterpret_cast<void *>(android_location_GnssLocationProvider_inject_best_location)},
destradaaea8a8a62014-06-23 18:19:03 -07002092 {"native_inject_location",
2093 "(DDF)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002094 reinterpret_cast<void *>(android_location_GnssLocationProvider_inject_location)},
2095 {"native_supports_xtra", "()Z", reinterpret_cast<void *>(
2096 android_location_GnssLocationProvider_supports_xtra)},
destradaaea8a8a62014-06-23 18:19:03 -07002097 {"native_inject_xtra_data",
2098 "([BI)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002099 reinterpret_cast<void *>(android_location_GnssLocationProvider_inject_xtra_data)},
destradaaea8a8a62014-06-23 18:19:03 -07002100 {"native_agps_data_conn_open",
2101 "(Ljava/lang/String;I)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002102 reinterpret_cast<void *>(android_location_GnssLocationProvider_agps_data_conn_open)},
destradaaea8a8a62014-06-23 18:19:03 -07002103 {"native_agps_data_conn_closed",
2104 "()V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002105 reinterpret_cast<void *>(android_location_GnssLocationProvider_agps_data_conn_closed)},
destradaaea8a8a62014-06-23 18:19:03 -07002106 {"native_agps_data_conn_failed",
2107 "()V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002108 reinterpret_cast<void *>(android_location_GnssLocationProvider_agps_data_conn_failed)},
destradaaea8a8a62014-06-23 18:19:03 -07002109 {"native_agps_set_id",
2110 "(ILjava/lang/String;)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002111 reinterpret_cast<void *>(android_location_GnssLocationProvider_agps_set_id)},
destradaaea8a8a62014-06-23 18:19:03 -07002112 {"native_agps_set_ref_location_cellid",
2113 "(IIIII)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002114 reinterpret_cast<void *>(
2115 android_location_GnssLocationProvider_agps_set_reference_location_cellid)},
destradaaea8a8a62014-06-23 18:19:03 -07002116 {"native_set_agps_server",
2117 "(ILjava/lang/String;I)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002118 reinterpret_cast<void *>(android_location_GnssLocationProvider_set_agps_server)},
destradaaea8a8a62014-06-23 18:19:03 -07002119 {"native_send_ni_response",
2120 "(II)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002121 reinterpret_cast<void *>(android_location_GnssLocationProvider_send_ni_response)},
destradaaea8a8a62014-06-23 18:19:03 -07002122 {"native_get_internal_state",
2123 "()Ljava/lang/String;",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002124 reinterpret_cast<void *>(android_location_GnssLocationProvider_get_internal_state)},
destradaaea8a8a62014-06-23 18:19:03 -07002125 {"native_update_network_state",
2126 "(ZIZZLjava/lang/String;Ljava/lang/String;)V",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002127 reinterpret_cast<void *>(android_location_GnssLocationProvider_update_network_state)},
destradaaea8a8a62014-06-23 18:19:03 -07002128 {"native_is_geofence_supported",
2129 "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002130 reinterpret_cast<void *>(android_location_GnssLocationProvider_is_geofence_supported)},
destradaaea8a8a62014-06-23 18:19:03 -07002131 {"native_add_geofence",
2132 "(IDDDIIII)Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002133 reinterpret_cast<void *>(android_location_GnssLocationProvider_add_geofence)},
destradaaea8a8a62014-06-23 18:19:03 -07002134 {"native_remove_geofence",
2135 "(I)Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002136 reinterpret_cast<void *>(android_location_GnssLocationProvider_remove_geofence)},
2137 {"native_pause_geofence", "(I)Z", reinterpret_cast<void *>(
2138 android_location_GnssLocationProvider_pause_geofence)},
destradaaea8a8a62014-06-23 18:19:03 -07002139 {"native_resume_geofence",
2140 "(II)Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002141 reinterpret_cast<void *>(android_location_GnssLocationProvider_resume_geofence)},
destradaaea8a8a62014-06-23 18:19:03 -07002142 {"native_is_measurement_supported",
2143 "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002144 reinterpret_cast<void *>(
2145 android_location_GnssLocationProvider_is_measurement_supported)},
destradaaea8a8a62014-06-23 18:19:03 -07002146 {"native_start_measurement_collection",
gomo48f1a642017-11-10 20:35:46 -08002147 "(Z)Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002148 reinterpret_cast<void *>(
2149 android_location_GnssLocationProvider_start_measurement_collection)},
destradaaea8a8a62014-06-23 18:19:03 -07002150 {"native_stop_measurement_collection",
2151 "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002152 reinterpret_cast<void *>(
2153 android_location_GnssLocationProvider_stop_measurement_collection)},
destradaa4b3e3932014-07-21 18:01:47 -07002154 {"native_is_navigation_message_supported",
2155 "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002156 reinterpret_cast<void *>(
2157 android_location_GnssLocationProvider_is_navigation_message_supported)},
destradaa4b3e3932014-07-21 18:01:47 -07002158 {"native_start_navigation_message_collection",
2159 "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002160 reinterpret_cast<void *>(
2161 android_location_GnssLocationProvider_start_navigation_message_collection)},
destradaa4b3e3932014-07-21 18:01:47 -07002162 {"native_stop_navigation_message_collection",
2163 "()Z",
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002164 reinterpret_cast<void *>(
2165 android_location_GnssLocationProvider_stop_navigation_message_collection)},
2166 {"native_set_supl_es",
2167 "(I)Z",
2168 reinterpret_cast<void *>(android_location_GnssLocationProvider_set_supl_es)},
2169 {"native_set_supl_version",
2170 "(I)Z",
2171 reinterpret_cast<void *>(android_location_GnssLocationProvider_set_supl_version)},
2172 {"native_set_supl_mode",
2173 "(I)Z",
2174 reinterpret_cast<void *>(android_location_GnssLocationProvider_set_supl_mode)},
2175 {"native_set_lpp_profile",
2176 "(I)Z",
2177 reinterpret_cast<void *>(android_location_GnssLocationProvider_set_lpp_profile)},
2178 {"native_set_gnss_pos_protocol_select",
2179 "(I)Z",
2180 reinterpret_cast<void *>(
2181 android_location_GnssLocationProvider_set_gnss_pos_protocol_select)},
2182 {"native_set_gps_lock",
2183 "(I)Z",
2184 reinterpret_cast<void *>(android_location_GnssLocationProvider_set_gps_lock)},
2185 {"native_set_emergency_supl_pdn",
2186 "(I)Z",
2187 reinterpret_cast<void *>(android_location_GnssLocationProvider_set_emergency_supl_pdn)},
Wyatt Rileycf879db2017-01-12 13:57:38 -08002188 {"native_get_batch_size",
2189 "()I",
2190 reinterpret_cast<void *>(android_location_GnssLocationProvider_get_batch_size)},
2191 {"native_init_batching",
2192 "()Z",
2193 reinterpret_cast<void *>(android_location_GnssLocationProvider_init_batching)},
2194 {"native_start_batch",
2195 "(JZ)Z",
2196 reinterpret_cast<void *>(android_location_GnssLocationProvider_start_batch)},
2197 {"native_flush_batch",
2198 "()V",
2199 reinterpret_cast<void *>(android_location_GnssLocationProvider_flush_batch)},
2200 {"native_stop_batch",
2201 "()Z",
2202 reinterpret_cast<void *>(android_location_GnssLocationProvider_stop_batch)},
2203 {"native_init_batching",
2204 "()Z",
2205 reinterpret_cast<void *>(android_location_GnssLocationProvider_init_batching)},
2206 {"native_cleanup_batching",
2207 "()V",
2208 reinterpret_cast<void *>(android_location_GnssLocationProvider_cleanup_batching)},
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002209};
2210
Hridya Valsaraju2ea29602016-09-13 08:38:09 -07002211int register_android_server_location_GnssLocationProvider(JNIEnv* env) {
destradaaea8a8a62014-06-23 18:19:03 -07002212 return jniRegisterNativeMethods(
2213 env,
Lifu Tang30f95a72016-01-07 23:20:38 -08002214 "com/android/server/location/GnssLocationProvider",
destradaaea8a8a62014-06-23 18:19:03 -07002215 sMethods,
2216 NELEM(sMethods));
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08002217}
2218
2219} /* namespace android */