123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565 |
- /* Copyright (c) 2017-2020, The Linux Foundation. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following
- * disclaimer in the documentation and/or other materials provided
- * with the distribution.
- * * Neither the name of The Linux Foundation, nor the names of its
- * contributors may be used to endorse or promote products derived
- * from this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
- * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
- * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
- * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
- * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
- * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
- * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
- * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
- * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
- * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- *
- */
- #define LOG_NDEBUG 0
- #define LOG_TAG "LocSvc_GnssAPIClient"
- #define SINGLE_SHOT_MIN_TRACKING_INTERVAL_MSEC (590 * 60 * 60 * 1000) // 590 hours
- #include <inttypes.h>
- #include <log_util.h>
- #include <loc_cfg.h>
- #include "LocationUtil.h"
- #include "GnssAPIClient.h"
- #include <LocContext.h>
- namespace android {
- namespace hardware {
- namespace gnss {
- namespace V1_1 {
- namespace implementation {
- using ::android::hardware::gnss::V1_0::IGnss;
- using ::android::hardware::gnss::V1_0::IGnssCallback;
- using ::android::hardware::gnss::V1_0::IGnssNiCallback;
- using ::android::hardware::gnss::V1_0::GnssLocation;
- static void convertGnssSvStatus(GnssSvNotification& in, IGnssCallback::GnssSvStatus& out);
- GnssAPIClient::GnssAPIClient(const sp<IGnssCallback>& gpsCb,
- const sp<IGnssNiCallback>& niCb) :
- LocationAPIClientBase(),
- mGnssCbIface(nullptr),
- mGnssNiCbIface(nullptr),
- mControlClient(new LocationAPIControlClient()),
- mLocationCapabilitiesMask(0),
- mLocationCapabilitiesCached(false)
- {
- LOC_LOGD("%s]: (%p %p)", __FUNCTION__, &gpsCb, &niCb);
- // set default LocationOptions.
- memset(&mTrackingOptions, 0, sizeof(TrackingOptions));
- mTrackingOptions.size = sizeof(TrackingOptions);
- mTrackingOptions.minInterval = 1000;
- mTrackingOptions.minDistance = 0;
- mTrackingOptions.mode = GNSS_SUPL_MODE_STANDALONE;
- gnssUpdateCallbacks(gpsCb, niCb);
- }
- GnssAPIClient::~GnssAPIClient()
- {
- LOC_LOGD("%s]: ()", __FUNCTION__);
- if (mControlClient) {
- delete mControlClient;
- mControlClient = nullptr;
- }
- }
- // for GpsInterface
- void GnssAPIClient::gnssUpdateCallbacks(const sp<IGnssCallback>& gpsCb,
- const sp<IGnssNiCallback>& niCb)
- {
- LOC_LOGD("%s]: (%p %p)", __FUNCTION__, &gpsCb, &niCb);
- mMutex.lock();
- mGnssCbIface = gpsCb;
- mGnssNiCbIface = niCb;
- mMutex.unlock();
- LocationCallbacks locationCallbacks;
- memset(&locationCallbacks, 0, sizeof(LocationCallbacks));
- locationCallbacks.size = sizeof(LocationCallbacks);
- locationCallbacks.trackingCb = nullptr;
- if (mGnssCbIface != nullptr) {
- locationCallbacks.trackingCb = [this](Location location) {
- onTrackingCb(location);
- };
- }
- locationCallbacks.batchingCb = nullptr;
- locationCallbacks.geofenceBreachCb = nullptr;
- locationCallbacks.geofenceStatusCb = nullptr;
- locationCallbacks.gnssLocationInfoCb = nullptr;
- locationCallbacks.gnssNiCb = nullptr;
- loc_core::ContextBase* context =
- loc_core::LocContext::getLocContext(loc_core::LocContext::mLocationHalName);
- if (mGnssNiCbIface != nullptr && !context->hasAgpsExtendedCapabilities()) {
- LOC_LOGD("Registering NI CB");
- locationCallbacks.gnssNiCb = [this](uint32_t id, GnssNiNotification gnssNiNotification) {
- onGnssNiCb(id, gnssNiNotification);
- };
- }
- locationCallbacks.gnssSvCb = nullptr;
- if (mGnssCbIface != nullptr) {
- locationCallbacks.gnssSvCb = [this](GnssSvNotification gnssSvNotification) {
- onGnssSvCb(gnssSvNotification);
- };
- }
- locationCallbacks.gnssNmeaCb = nullptr;
- if (mGnssCbIface != nullptr) {
- locationCallbacks.gnssNmeaCb = [this](GnssNmeaNotification gnssNmeaNotification) {
- onGnssNmeaCb(gnssNmeaNotification);
- };
- }
- locationCallbacks.gnssMeasurementsCb = nullptr;
- locAPISetCallbacks(locationCallbacks);
- }
- bool GnssAPIClient::gnssStart()
- {
- LOC_LOGD("%s]: ()", __FUNCTION__);
- bool retVal = true;
- locAPIStartTracking(mTrackingOptions);
- return retVal;
- }
- bool GnssAPIClient::gnssStop()
- {
- LOC_LOGD("%s]: ()", __FUNCTION__);
- bool retVal = true;
- locAPIStopTracking();
- return retVal;
- }
- bool GnssAPIClient::gnssSetPositionMode(IGnss::GnssPositionMode mode,
- IGnss::GnssPositionRecurrence recurrence, uint32_t minIntervalMs,
- uint32_t preferredAccuracyMeters, uint32_t preferredTimeMs,
- GnssPowerMode powerMode, uint32_t timeBetweenMeasurement)
- {
- LOC_LOGD("%s]: (%d %d %d %d %d %d %d)", __FUNCTION__,
- (int)mode, recurrence, minIntervalMs, preferredAccuracyMeters,
- preferredTimeMs, (int)powerMode, timeBetweenMeasurement);
- bool retVal = true;
- memset(&mTrackingOptions, 0, sizeof(TrackingOptions));
- mTrackingOptions.size = sizeof(TrackingOptions);
- mTrackingOptions.minInterval = minIntervalMs;
- if (IGnss::GnssPositionMode::MS_ASSISTED == mode ||
- IGnss::GnssPositionRecurrence::RECURRENCE_SINGLE == recurrence) {
- // We set a very large interval to simulate SINGLE mode. Once we report a fix,
- // the caller should take the responsibility to stop the session.
- // For MSA, we always treat it as SINGLE mode.
- mTrackingOptions.minInterval = SINGLE_SHOT_MIN_TRACKING_INTERVAL_MSEC;
- }
- if (mode == IGnss::GnssPositionMode::STANDALONE)
- mTrackingOptions.mode = GNSS_SUPL_MODE_STANDALONE;
- else if (mode == IGnss::GnssPositionMode::MS_BASED)
- mTrackingOptions.mode = GNSS_SUPL_MODE_MSB;
- else if (mode == IGnss::GnssPositionMode::MS_ASSISTED)
- mTrackingOptions.mode = GNSS_SUPL_MODE_MSA;
- else {
- LOC_LOGD("%s]: invalid GnssPositionMode: %d", __FUNCTION__, (int)mode);
- retVal = false;
- }
- if (GNSS_POWER_MODE_INVALID != powerMode) {
- mTrackingOptions.powerMode = powerMode;
- mTrackingOptions.tbm = timeBetweenMeasurement;
- }
- locAPIUpdateTrackingOptions(mTrackingOptions);
- return retVal;
- }
- // for GpsNiInterface
- void GnssAPIClient::gnssNiRespond(int32_t notifId,
- IGnssNiCallback::GnssUserResponseType userResponse)
- {
- LOC_LOGD("%s]: (%d %d)", __FUNCTION__, notifId, static_cast<int>(userResponse));
- GnssNiResponse data;
- switch (userResponse) {
- case IGnssNiCallback::GnssUserResponseType::RESPONSE_ACCEPT:
- data = GNSS_NI_RESPONSE_ACCEPT;
- break;
- case IGnssNiCallback::GnssUserResponseType::RESPONSE_DENY:
- data = GNSS_NI_RESPONSE_DENY;
- break;
- case IGnssNiCallback::GnssUserResponseType::RESPONSE_NORESP:
- data = GNSS_NI_RESPONSE_NO_RESPONSE;
- break;
- default:
- data = GNSS_NI_RESPONSE_IGNORE;
- break;
- }
- locAPIGnssNiResponse(notifId, data);
- }
- // these apis using LocationAPIControlClient
- void GnssAPIClient::gnssDeleteAidingData(IGnss::GnssAidingData aidingDataFlags)
- {
- LOC_LOGD("%s]: (%02hx)", __FUNCTION__, aidingDataFlags);
- if (mControlClient == nullptr) {
- return;
- }
- GnssAidingData data;
- memset(&data, 0, sizeof (GnssAidingData));
- data.sv.svTypeMask = GNSS_AIDING_DATA_SV_TYPE_GPS_BIT |
- GNSS_AIDING_DATA_SV_TYPE_GLONASS_BIT |
- GNSS_AIDING_DATA_SV_TYPE_QZSS_BIT |
- GNSS_AIDING_DATA_SV_TYPE_BEIDOU_BIT |
- GNSS_AIDING_DATA_SV_TYPE_GALILEO_BIT;
- data.posEngineMask = STANDARD_POSITIONING_ENGINE;
- if (aidingDataFlags == IGnss::GnssAidingData::DELETE_ALL)
- data.deleteAll = true;
- else {
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_EPHEMERIS)
- data.sv.svMask |= GNSS_AIDING_DATA_SV_EPHEMERIS_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_ALMANAC)
- data.sv.svMask |= GNSS_AIDING_DATA_SV_ALMANAC_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_POSITION)
- data.common.mask |= GNSS_AIDING_DATA_COMMON_POSITION_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_TIME)
- data.common.mask |= GNSS_AIDING_DATA_COMMON_TIME_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_IONO)
- data.sv.svMask |= GNSS_AIDING_DATA_SV_IONOSPHERE_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_UTC)
- data.common.mask |= GNSS_AIDING_DATA_COMMON_UTC_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_HEALTH)
- data.sv.svMask |= GNSS_AIDING_DATA_SV_HEALTH_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_SVDIR)
- data.sv.svMask |= GNSS_AIDING_DATA_SV_DIRECTION_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_SVSTEER)
- data.sv.svMask |= GNSS_AIDING_DATA_SV_STEER_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_SADATA)
- data.sv.svMask |= GNSS_AIDING_DATA_SV_SA_DATA_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_RTI)
- data.common.mask |= GNSS_AIDING_DATA_COMMON_RTI_BIT;
- if (aidingDataFlags & IGnss::GnssAidingData::DELETE_CELLDB_INFO)
- data.common.mask |= GNSS_AIDING_DATA_COMMON_CELLDB_BIT;
- }
- mControlClient->locAPIGnssDeleteAidingData(data);
- }
- void GnssAPIClient::gnssEnable(LocationTechnologyType techType)
- {
- LOC_LOGD("%s]: (%0d)", __FUNCTION__, techType);
- if (mControlClient == nullptr) {
- return;
- }
- mControlClient->locAPIEnable(techType);
- }
- void GnssAPIClient::gnssDisable()
- {
- LOC_LOGD("%s]: ()", __FUNCTION__);
- if (mControlClient == nullptr) {
- return;
- }
- mControlClient->locAPIDisable();
- }
- void GnssAPIClient::gnssConfigurationUpdate(const GnssConfig& gnssConfig)
- {
- LOC_LOGD("%s]: (%02x)", __FUNCTION__, gnssConfig.flags);
- if (mControlClient == nullptr) {
- return;
- }
- mControlClient->locAPIGnssUpdateConfig(gnssConfig);
- }
- void GnssAPIClient::requestCapabilities() {
- // only send capablities if it's already cached, otherwise the first time LocationAPI
- // is initialized, capabilities will be sent by LocationAPI
- if (mLocationCapabilitiesCached) {
- onCapabilitiesCb(mLocationCapabilitiesMask);
- }
- }
- // callbacks
- void GnssAPIClient::onCapabilitiesCb(LocationCapabilitiesMask capabilitiesMask)
- {
- LOC_LOGD("%s]: (%" PRIu64 ")", __FUNCTION__, capabilitiesMask);
- mLocationCapabilitiesMask = capabilitiesMask;
- mLocationCapabilitiesCached = true;
- mMutex.lock();
- auto gnssCbIface(mGnssCbIface);
- mMutex.unlock();
- if (gnssCbIface != nullptr) {
- uint32_t data = 0;
- if ((capabilitiesMask & LOCATION_CAPABILITIES_TIME_BASED_TRACKING_BIT) ||
- (capabilitiesMask & LOCATION_CAPABILITIES_TIME_BASED_BATCHING_BIT) ||
- (capabilitiesMask & LOCATION_CAPABILITIES_DISTANCE_BASED_TRACKING_BIT) ||
- (capabilitiesMask & LOCATION_CAPABILITIES_DISTANCE_BASED_BATCHING_BIT))
- data |= IGnssCallback::Capabilities::SCHEDULING;
- if (capabilitiesMask & LOCATION_CAPABILITIES_GEOFENCE_BIT)
- data |= IGnssCallback::Capabilities::GEOFENCING;
- if (capabilitiesMask & LOCATION_CAPABILITIES_GNSS_MEASUREMENTS_BIT)
- data |= IGnssCallback::Capabilities::MEASUREMENTS;
- if (capabilitiesMask & LOCATION_CAPABILITIES_GNSS_MSB_BIT)
- data |= IGnssCallback::Capabilities::MSB;
- if (capabilitiesMask & LOCATION_CAPABILITIES_GNSS_MSA_BIT)
- data |= IGnssCallback::Capabilities::MSA;
- auto r = gnssCbIface->gnssSetCapabilitesCb(data);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssSetCapabilitesCb description=%s",
- __func__, r.description().c_str());
- }
- }
- if (gnssCbIface != nullptr) {
- IGnssCallback::GnssSystemInfo gnssInfo = { .yearOfHw = 2015 };
- if (capabilitiesMask & LOCATION_CAPABILITIES_GNSS_MEASUREMENTS_BIT) {
- gnssInfo.yearOfHw++; // 2016
- if (capabilitiesMask & LOCATION_CAPABILITIES_DEBUG_NMEA_BIT) {
- gnssInfo.yearOfHw++; // 2017
- if (capabilitiesMask & LOCATION_CAPABILITIES_CONSTELLATION_ENABLEMENT_BIT ||
- capabilitiesMask & LOCATION_CAPABILITIES_AGPM_BIT) {
- gnssInfo.yearOfHw++; // 2018
- }
- }
- }
- LOC_LOGV("%s:%d] set_system_info_cb (%d)", __FUNCTION__, __LINE__, gnssInfo.yearOfHw);
- auto r = gnssCbIface->gnssSetSystemInfoCb(gnssInfo);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssSetSystemInfoCb description=%s",
- __func__, r.description().c_str());
- }
- }
- }
- void GnssAPIClient::onTrackingCb(Location location)
- {
- LOC_LOGD("%s]: (flags: %02x)", __FUNCTION__, location.flags);
- mMutex.lock();
- auto gnssCbIface(mGnssCbIface);
- mMutex.unlock();
- if (gnssCbIface != nullptr) {
- GnssLocation gnssLocation;
- convertGnssLocation(location, gnssLocation);
- auto r = gnssCbIface->gnssLocationCb(gnssLocation);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssLocationCb description=%s",
- __func__, r.description().c_str());
- }
- }
- }
- void GnssAPIClient::onGnssNiCb(uint32_t id, GnssNiNotification gnssNiNotification)
- {
- LOC_LOGD("%s]: (id: %d)", __FUNCTION__, id);
- mMutex.lock();
- auto gnssNiCbIface(mGnssNiCbIface);
- mMutex.unlock();
- if (gnssNiCbIface == nullptr) {
- LOC_LOGE("%s]: mGnssNiCbIface is nullptr", __FUNCTION__);
- return;
- }
- IGnssNiCallback::GnssNiNotification notificationGnss = {};
- notificationGnss.notificationId = id;
- if (gnssNiNotification.type == GNSS_NI_TYPE_VOICE)
- notificationGnss.niType = IGnssNiCallback::GnssNiType::VOICE;
- else if (gnssNiNotification.type == GNSS_NI_TYPE_SUPL)
- notificationGnss.niType = IGnssNiCallback::GnssNiType::UMTS_SUPL;
- else if (gnssNiNotification.type == GNSS_NI_TYPE_CONTROL_PLANE)
- notificationGnss.niType = IGnssNiCallback::GnssNiType::UMTS_CTRL_PLANE;
- else if (gnssNiNotification.type == GNSS_NI_TYPE_EMERGENCY_SUPL)
- notificationGnss.niType = IGnssNiCallback::GnssNiType::EMERGENCY_SUPL;
- if (gnssNiNotification.options & GNSS_NI_OPTIONS_NOTIFICATION_BIT)
- notificationGnss.notifyFlags |= IGnssNiCallback::GnssNiNotifyFlags::NEED_NOTIFY;
- if (gnssNiNotification.options & GNSS_NI_OPTIONS_VERIFICATION_BIT)
- notificationGnss.notifyFlags |= IGnssNiCallback::GnssNiNotifyFlags::NEED_VERIFY;
- if (gnssNiNotification.options & GNSS_NI_OPTIONS_PRIVACY_OVERRIDE_BIT)
- notificationGnss.notifyFlags |= IGnssNiCallback::GnssNiNotifyFlags::PRIVACY_OVERRIDE;
- notificationGnss.timeoutSec = gnssNiNotification.timeout;
- if (gnssNiNotification.timeoutResponse == GNSS_NI_RESPONSE_ACCEPT)
- notificationGnss.defaultResponse = IGnssNiCallback::GnssUserResponseType::RESPONSE_ACCEPT;
- else if (gnssNiNotification.timeoutResponse == GNSS_NI_RESPONSE_DENY)
- notificationGnss.defaultResponse = IGnssNiCallback::GnssUserResponseType::RESPONSE_DENY;
- else if (gnssNiNotification.timeoutResponse == GNSS_NI_RESPONSE_NO_RESPONSE ||
- gnssNiNotification.timeoutResponse == GNSS_NI_RESPONSE_IGNORE)
- notificationGnss.defaultResponse = IGnssNiCallback::GnssUserResponseType::RESPONSE_NORESP;
- notificationGnss.requestorId = gnssNiNotification.requestor;
- notificationGnss.notificationMessage = gnssNiNotification.message;
- if (gnssNiNotification.requestorEncoding == GNSS_NI_ENCODING_TYPE_NONE)
- notificationGnss.requestorIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_NONE;
- else if (gnssNiNotification.requestorEncoding == GNSS_NI_ENCODING_TYPE_GSM_DEFAULT)
- notificationGnss.requestorIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_SUPL_GSM_DEFAULT;
- else if (gnssNiNotification.requestorEncoding == GNSS_NI_ENCODING_TYPE_UTF8)
- notificationGnss.requestorIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_SUPL_UTF8;
- else if (gnssNiNotification.requestorEncoding == GNSS_NI_ENCODING_TYPE_UCS2)
- notificationGnss.requestorIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_SUPL_UCS2;
- if (gnssNiNotification.messageEncoding == GNSS_NI_ENCODING_TYPE_NONE)
- notificationGnss.notificationIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_NONE;
- else if (gnssNiNotification.messageEncoding == GNSS_NI_ENCODING_TYPE_GSM_DEFAULT)
- notificationGnss.notificationIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_SUPL_GSM_DEFAULT;
- else if (gnssNiNotification.messageEncoding == GNSS_NI_ENCODING_TYPE_UTF8)
- notificationGnss.notificationIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_SUPL_UTF8;
- else if (gnssNiNotification.messageEncoding == GNSS_NI_ENCODING_TYPE_UCS2)
- notificationGnss.notificationIdEncoding =
- IGnssNiCallback::GnssNiEncodingType::ENC_SUPL_UCS2;
- gnssNiCbIface->niNotifyCb(notificationGnss);
- }
- void GnssAPIClient::onGnssSvCb(GnssSvNotification gnssSvNotification)
- {
- LOC_LOGD("%s]: (count: %zu)", __FUNCTION__, gnssSvNotification.count);
- mMutex.lock();
- auto gnssCbIface(mGnssCbIface);
- mMutex.unlock();
- if (gnssCbIface != nullptr) {
- IGnssCallback::GnssSvStatus svStatus;
- convertGnssSvStatus(gnssSvNotification, svStatus);
- auto r = gnssCbIface->gnssSvStatusCb(svStatus);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssSvStatusCb description=%s",
- __func__, r.description().c_str());
- }
- }
- }
- void GnssAPIClient::onGnssNmeaCb(GnssNmeaNotification gnssNmeaNotification)
- {
- mMutex.lock();
- auto gnssCbIface(mGnssCbIface);
- mMutex.unlock();
- if (gnssCbIface != nullptr) {
- const std::string s(gnssNmeaNotification.nmea);
- std::stringstream ss(s);
- std::string each;
- while(std::getline(ss, each, '\n')) {
- each += '\n';
- android::hardware::hidl_string nmeaString;
- nmeaString.setToExternal(each.c_str(), each.length());
- auto r = gnssCbIface->gnssNmeaCb(
- static_cast<V1_0::GnssUtcTime>(gnssNmeaNotification.timestamp), nmeaString);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssNmeaCb nmea=%s length=%zu description=%s", __func__,
- gnssNmeaNotification.nmea, gnssNmeaNotification.length,
- r.description().c_str());
- }
- }
- }
- }
- void GnssAPIClient::onStartTrackingCb(LocationError error)
- {
- LOC_LOGD("%s]: (%d)", __FUNCTION__, error);
- mMutex.lock();
- auto gnssCbIface(mGnssCbIface);
- mMutex.unlock();
- if (error == LOCATION_ERROR_SUCCESS && gnssCbIface != nullptr) {
- auto r = gnssCbIface->gnssStatusCb(IGnssCallback::GnssStatusValue::ENGINE_ON);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssStatusCb ENGINE_ON description=%s",
- __func__, r.description().c_str());
- }
- r = gnssCbIface->gnssStatusCb(IGnssCallback::GnssStatusValue::SESSION_BEGIN);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssStatusCb SESSION_BEGIN description=%s",
- __func__, r.description().c_str());
- }
- }
- }
- void GnssAPIClient::onStopTrackingCb(LocationError error)
- {
- LOC_LOGD("%s]: (%d)", __FUNCTION__, error);
- mMutex.lock();
- auto gnssCbIface(mGnssCbIface);
- mMutex.unlock();
- if (error == LOCATION_ERROR_SUCCESS && gnssCbIface != nullptr) {
- auto r = gnssCbIface->gnssStatusCb(IGnssCallback::GnssStatusValue::SESSION_END);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssStatusCb SESSION_END description=%s",
- __func__, r.description().c_str());
- }
- r = gnssCbIface->gnssStatusCb(IGnssCallback::GnssStatusValue::ENGINE_OFF);
- if (!r.isOk()) {
- LOC_LOGE("%s] Error from gnssStatusCb ENGINE_OFF description=%s",
- __func__, r.description().c_str());
- }
- }
- }
- static void convertGnssSvStatus(GnssSvNotification& in, IGnssCallback::GnssSvStatus& out)
- {
- memset(&out, 0, sizeof(IGnssCallback::GnssSvStatus));
- out.numSvs = in.count;
- if (out.numSvs > static_cast<uint32_t>(V1_0::GnssMax::SVS_COUNT)) {
- LOC_LOGW("%s]: Too many satellites %u. Clamps to %d.",
- __FUNCTION__, out.numSvs, V1_0::GnssMax::SVS_COUNT);
- out.numSvs = static_cast<uint32_t>(V1_0::GnssMax::SVS_COUNT);
- }
- for (size_t i = 0; i < out.numSvs; i++) {
- IGnssCallback::GnssSvInfo& info = out.gnssSvList[i];
- convertGnssSvid(in.gnssSvs[i], info.svid);
- convertGnssConstellationType(in.gnssSvs[i].type, info.constellation);
- info.cN0Dbhz = in.gnssSvs[i].cN0Dbhz;
- info.elevationDegrees = in.gnssSvs[i].elevation;
- info.azimuthDegrees = in.gnssSvs[i].azimuth;
- info.carrierFrequencyHz = in.gnssSvs[i].carrierFrequencyHz;
- info.svFlag = static_cast<uint8_t>(IGnssCallback::GnssSvFlags::NONE);
- if (in.gnssSvs[i].gnssSvOptionsMask & GNSS_SV_OPTIONS_HAS_EPHEMER_BIT)
- info.svFlag |= IGnssCallback::GnssSvFlags::HAS_EPHEMERIS_DATA;
- if (in.gnssSvs[i].gnssSvOptionsMask & GNSS_SV_OPTIONS_HAS_ALMANAC_BIT)
- info.svFlag |= IGnssCallback::GnssSvFlags::HAS_ALMANAC_DATA;
- if (in.gnssSvs[i].gnssSvOptionsMask & GNSS_SV_OPTIONS_USED_IN_FIX_BIT)
- info.svFlag |= IGnssCallback::GnssSvFlags::USED_IN_FIX;
- if (in.gnssSvs[i].gnssSvOptionsMask & GNSS_SV_OPTIONS_HAS_CARRIER_FREQUENCY_BIT)
- info.svFlag |= IGnssCallback::GnssSvFlags::HAS_CARRIER_FREQUENCY;
- }
- }
- } // namespace implementation
- } // namespace V1_1
- } // namespace gnss
- } // namespace hardware
- } // namespace android
|