GPS hw: report ppe/spe report with combined report

When DRE/PPE are also running in the system, in addition to
reporitng the combined final output, add the support to
report the unmodified SPE/PPE report received from the engine

Change-Id: Icb636824da32b175030dfcd2b270ac8b500ff75b
CRs-fixed: 2487580
This commit is contained in:
Wei Chen 2019-07-18 15:50:55 -07:00 committed by Yingjie Wang
parent 5ee0b62e8c
commit 1a1232c594
9 changed files with 206 additions and 43 deletions

View file

@ -103,12 +103,8 @@ public:
}
};
typedef std::function<void(const UlpLocation& ulpLocation,
const GpsLocationExtended& locationExtended,
enum loc_sess_status status,
LocPosTechMask techMask,
bool fromEngineHub)>
GnssAdapterReportPositionEventCb;
typedef std::function<void(int count, EngineLocationInfo* locationArr)>
GnssAdapterReportEnginePositionsEventCb;
typedef std::function<void(const GnssSvNotification& svNotify,
bool fromEngineHub)>
@ -119,9 +115,10 @@ typedef std::function<void(const GnssAidingDataSvMask& svDataMask)>
// potential parameters: message queue: MsgTask * msgTask;
// callback function to report back dr and ppe position and sv report
typedef EngineHubProxyBase* (getEngHubProxyFn)(const MsgTask * msgTask,
typedef EngineHubProxyBase* (getEngHubProxyFn)(
const MsgTask * msgTask,
IOsObserver* osObserver,
GnssAdapterReportPositionEventCb positionEventCb,
GnssAdapterReportEnginePositionsEventCb positionEventCb,
GnssAdapterReportSvEventCb svEventCb,
GnssAdapterReqAidingDataCb reqAidingDataCb);

View file

@ -81,7 +81,6 @@ void LocAdapterBase::
const GpsLocationExtended& locationExtended,
enum loc_sess_status status,
LocPosTechMask loc_technology_mask,
bool /*fromEngineHub*/,
GnssDataNotification* pDataNotify,
int msInWeek)
{

View file

@ -151,9 +151,13 @@ public:
const GpsLocationExtended& locationExtended,
enum loc_sess_status status,
LocPosTechMask loc_technology_mask,
bool fromEngineHub = false,
GnssDataNotification* pDataNotify = nullptr,
int msInWeek = -1);
virtual void reportEnginePositionsEvent(unsigned int count,
EngineLocationInfo* locationArr) {
(void)count;
(void)locationArr;
}
virtual void reportSvEvent(const GnssSvNotification& svNotify,
bool fromEngineHub=false);
virtual void reportDataEvent(const GnssDataNotification& dataNotify, int msInWeek);

View file

@ -345,7 +345,6 @@ void LocApiBase::reportPosition(UlpLocation& location,
TO_ALL_LOCADAPTERS(
mLocAdapters[i]->reportPositionEvent(location, locationExtended,
status, loc_technology_mask,
false,
pDataNotify, msInWeek)
);
}

View file

@ -485,6 +485,16 @@ GnssAdapter::convertLocationInfo(GnssLocationInfoNotification& out,
out.flags |= GNSS_LOCATION_INFO_CALIBRATION_STATUS_BIT;
out.calibrationStatus = locationExtended.calibrationStatus;
}
if (GPS_LOCATION_EXTENDED_HAS_OUTPUT_ENG_TYPE & locationExtended.flags) {
out.flags |= GNSS_LOCATION_INFO_OUTPUT_ENG_TYPE_BIT;
out.locOutputEngType = locationExtended.locOutputEngType;
}
if (GPS_LOCATION_EXTENDED_HAS_OUTPUT_ENG_MASK & locationExtended.flags) {
out.flags |= GNSS_LOCATION_INFO_OUTPUT_ENG_MASK_BIT;
out.locOutputEngMask = locationExtended.locOutputEngMask;
}
}
@ -3051,32 +3061,23 @@ GnssAdapter::reportPositionEvent(const UlpLocation& ulpLocation,
const GpsLocationExtended& locationExtended,
enum loc_sess_status status,
LocPosTechMask techMask,
bool fromEngineHub,
GnssDataNotification* pDataNotify,
int msInWeek)
{
// if this event is called from QMI LOC API, then send report to engine hub
// this position is from QMI LOC API, then send report to engine hub
// if sending is successful, we return as we will wait for final report from engine hub
// if the position is called from engine hub, then send it out directly
if (!fromEngineHub) {
// report QMI position (both propagated and unpropagated) to engine hub,
// and engine hub will be distributing it to the registered plugins
if (true == initEngHubProxy()){
mEngHubProxy->gnssReportPosition(ulpLocation, locationExtended, status);
return;
}
if (true == ulpLocation.unpropagatedPosition) {
return;
}
// engine hub is loaded, do not report qmi position to client as
// final position report should come from engine hub
if (true == initEngHubProxy()){
return;
}
}
// for all other cases:
// case 1: fix is from engine hub, queue the msg
// case 2: fix is not from engine hub, e.g. from QMI, and it is not an
// Fix is from QMI, and it is not an
// unpropagated position and engine hub is not loaded, queue the msg
// when message is queued, the position can be dispatched to requesting client
struct MsgReportPosition : public LocMsg {
@ -3133,6 +3134,35 @@ GnssAdapter::reportPositionEvent(const UlpLocation& ulpLocation,
pDataNotify, msInWeek));
}
void
GnssAdapter::reportEnginePositionsEvent(unsigned int count,
EngineLocationInfo* locationArr)
{
struct MsgReportEnginePositions : public LocMsg {
GnssAdapter& mAdapter;
unsigned int mCount;
EngineLocationInfo mEngLocInfo[LOC_OUTPUT_ENGINE_COUNT];
inline MsgReportEnginePositions(GnssAdapter& adapter,
unsigned int count,
EngineLocationInfo* locationArr) :
LocMsg(),
mAdapter(adapter),
mCount(count) {
if (mCount > LOC_OUTPUT_ENGINE_COUNT) {
mCount = LOC_OUTPUT_ENGINE_COUNT;
}
if (mCount > 0) {
memcpy(mEngLocInfo, locationArr, sizeof(EngineLocationInfo)*mCount);
}
}
inline virtual void proc() const {
mAdapter.reportEnginePositions(mCount, mEngLocInfo);
}
};
sendMsg(new MsgReportEnginePositions(*this, count, locationArr));
}
bool
GnssAdapter::needReportForGnssClient(const UlpLocation& ulpLocation,
enum loc_sess_status status,
@ -3190,6 +3220,17 @@ GnssAdapter::reportPosition(const UlpLocation& ulpLocation,
(reportToGnssClient && !isFlpClient(it->second))) {
if (nullptr != it->second.gnssLocationInfoCb) {
it->second.gnssLocationInfoCb(locationInfo);
} else if ((nullptr != it->second.engineLocationsInfoCb) &&
(false == initEngHubProxy())) {
// if engine hub is disabled, this is SPE fix from modem
// we need to mark one copy marked as fused and one copy marked as PPE
// and dispatch it to the engineLocationsInfoCb
GnssLocationInfoNotification engLocationsInfo[2];
engLocationsInfo[0] = locationInfo;
engLocationsInfo[0].locOutputEngType = LOC_OUTPUT_ENGINE_FUSED;
engLocationsInfo[0].flags |= GNSS_LOCATION_INFO_OUTPUT_ENG_TYPE_BIT;
engLocationsInfo[1] = locationInfo;
it->second.engineLocationsInfoCb(2, engLocationsInfo);
} else if (nullptr != it->second.trackingCb) {
it->second.trackingCb(locationInfo.location);
}
@ -3237,6 +3278,48 @@ GnssAdapter::reportPosition(const UlpLocation& ulpLocation,
}
}
void
GnssAdapter::reportEnginePositions(unsigned int count,
const EngineLocationInfo* locationArr)
{
bool needReportEnginePositions = false;
for (auto it=mClientData.begin(); it != mClientData.end(); ++it) {
if (nullptr != it->second.engineLocationsInfoCb) {
needReportEnginePositions = true;
break;
}
}
GnssLocationInfoNotification locationInfo[LOC_OUTPUT_ENGINE_COUNT] = {};
for (unsigned int i = 0; i < count; i++) {
const EngineLocationInfo* engLocation = (locationArr+i);
// if it is fused/default location, call reportPosition maintain legacy behavior
if ((GPS_LOCATION_EXTENDED_HAS_OUTPUT_ENG_TYPE & engLocation->locationExtended.flags) &&
(LOC_OUTPUT_ENGINE_FUSED == engLocation->locationExtended.locOutputEngType)) {
reportPosition(engLocation->location,
engLocation->locationExtended,
engLocation->sessionStatus,
engLocation->location.tech_mask);
}
if (needReportEnginePositions) {
convertLocationInfo(locationInfo[i], engLocation->locationExtended);
convertLocation(locationInfo[i].location,
engLocation->location,
engLocation->locationExtended,
engLocation->location.tech_mask);
}
}
if (needReportEnginePositions) {
for (auto it=mClientData.begin(); it != mClientData.end(); ++it) {
if (nullptr != it->second.engineLocationsInfoCb) {
it->second.engineLocationsInfoCb(count, locationInfo);
}
}
}
}
void
GnssAdapter::reportSvEvent(const GnssSvNotification& svNotify,
bool fromEngineHub)
@ -4920,15 +5003,10 @@ GnssAdapter::initEngHubProxy() {
// prepare the callback functions
// callback function for engine hub to report back position event
GnssAdapterReportPositionEventCb reportPositionEventCb =
[this](const UlpLocation& ulpLocation,
const GpsLocationExtended& locationExtended,
enum loc_sess_status status,
LocPosTechMask techMask,
bool fromEngineHub) {
GnssAdapterReportEnginePositionsEventCb reportPositionEventCb =
[this](int count, EngineLocationInfo* locationArr) {
// report from engine hub on behalf of PPE will be treated as fromUlp
reportPositionEvent(ulpLocation, locationExtended, status,
techMask, fromEngineHub);
reportEnginePositionsEvent(count, locationArr);
};
// callback function for engine hub to report back sv event

View file

@ -351,9 +351,11 @@ public:
const GpsLocationExtended& locationExtended,
enum loc_sess_status status,
LocPosTechMask techMask,
bool fromEngineHub = false,
GnssDataNotification* pDataNotify = nullptr,
int msInWeek = -1);
virtual void reportEnginePositionsEvent(unsigned int count,
EngineLocationInfo* locationArr);
virtual void reportSvEvent(const GnssSvNotification& svNotify,
bool fromEngineHub=false);
virtual void reportNmeaEvent(const char* nmea, size_t length);
@ -386,6 +388,8 @@ public:
const GpsLocationExtended &locationExtended,
enum loc_sess_status status,
LocPosTechMask techMask);
void reportEnginePositions(unsigned int count,
const EngineLocationInfo* locationArr);
void reportSv(GnssSvNotification& svNotify);
void reportNmea(const char* nmea, size_t length);
void reportData(GnssDataNotification& dataNotify);

View file

@ -85,6 +85,7 @@ static bool isGnssClient(LocationCallbacks& locationCallbacks)
return (locationCallbacks.gnssNiCb != nullptr ||
locationCallbacks.trackingCb != nullptr ||
locationCallbacks.gnssLocationInfoCb != nullptr ||
locationCallbacks.engineLocationsInfoCb != nullptr ||
locationCallbacks.gnssMeasurementsCb != nullptr);
}

View file

@ -175,6 +175,8 @@ typedef enum {
GNSS_LOCATION_INFO_NUM_SV_USED_IN_POSITION_BIT = (1<<24), // number of SV used in position
GNSS_LOCATION_INFO_CALIBRATION_CONFIDENCE_BIT = (1<<25), // valid sensor cal confidence
GNSS_LOCATION_INFO_CALIBRATION_STATUS_BIT = (1<<26), // valid sensor cal status
GNSS_LOCATION_INFO_OUTPUT_ENG_TYPE_BIT = (1<<27), // valid output engine type
GNSS_LOCATION_INFO_OUTPUT_ENG_MASK_BIT = (1<<28), // valid output engine mask
} GnssLocationInfoFlagBits;
typedef enum {
@ -646,6 +648,13 @@ typedef enum {
GNSS_LOC_MAX_NUMBER_OF_SIGNAL_TYPES = 20 /**< Maximum number of signal types */
} Gnss_LocSignalEnumType;
typedef uint32_t PositioningEngineMask;
typedef enum {
STANDARD_POSITIONING_ENGINE = (1 << 0),
DEAD_RECKONING_ENGINE = (1 << 1),
PRECISE_POSITIONING_ENGINE = (1 << 2)
} PositioningEngineBits;
typedef uint64_t GnssDataMask;
typedef enum {
// Jammer Indicator is available
@ -731,15 +740,35 @@ typedef struct {
LocationSpoofMask spoofMask;
} Location;
typedef enum {
LOC_REQ_ENGINE_FUSED_BIT = (1<<0),
LOC_REQ_ENGINE_SPE_BIT = (1<<1),
LOC_REQ_ENGINE_PPE_BIT = (1<<2),
} LocReqEngineTypeMask;
typedef enum {
LOC_OUTPUT_ENGINE_FUSED = 0,
/** This is the GNSS fix from modem */
LOC_OUTPUT_ENGINE_SPE = 1,
/** This is the GNSS fix with correction PPP/RTK correction */
LOC_OUTPUT_ENGINE_PPE = 2,
LOC_OUTPUT_ENGINE_COUNT,
} LocOutputEngineType;
struct LocationOptions {
uint32_t size; // set to sizeof(LocationOptions)
uint32_t minInterval; // in milliseconds
uint32_t minDistance; // in meters. if minDistance > 0, gnssSvCallback/gnssNmeaCallback/
// gnssMeasurementsCallback may not be called
GnssSuplMode mode; // Standalone/MS-Based/MS-Assisted
// behavior when this field is 0:
// if engine hub is running, this will be fused fix,
// if engine hub is not running, this will be SPE fix
LocReqEngineTypeMask locReqEngTypeMask;
inline LocationOptions() :
size(0), minInterval(0), minDistance(0), mode(GNSS_SUPL_MODE_STANDALONE) {}
size(0), minInterval(0), minDistance(0), mode(GNSS_SUPL_MODE_STANDALONE),
locReqEngTypeMask((LocReqEngineTypeMask)0) {}
};
typedef enum {
@ -764,9 +793,11 @@ struct TrackingOptions : LocationOptions {
inline TrackingOptions(const LocationOptions& options) :
LocationOptions(options), powerMode(GNSS_POWER_MODE_INVALID), tbm(0) {}
inline void setLocationOptions(const LocationOptions& options) {
size = sizeof(TrackingOptions);
minInterval = options.minInterval;
minDistance = options.minDistance;
mode = options.mode;
locReqEngTypeMask = options.locReqEngTypeMask;
}
inline LocationOptions getLocationOptions() {
LocationOptions locOption;
@ -774,6 +805,7 @@ struct TrackingOptions : LocationOptions {
locOption.minDistance = minDistance;
locOption.minInterval = minInterval;
locOption.mode = mode;
locOption.locReqEngTypeMask = locReqEngTypeMask;
return locOption;
}
};
@ -997,6 +1029,16 @@ typedef struct {
uint8_t calibrationConfidence; // Sensor calibration confidence percent,
// in range of [0, 100]
DrCalibrationStatusMask calibrationStatus; // Sensor calibration status
// location engine type. When the fix. when the type is set to
// LOC_ENGINE_SRC_FUSED, the fix is the propagated/aggregated
// reports from all engines running on the system (e.g.:
// DR/SPE/PPE) based proprietary algorithm. To check which
// location engine contributes to the fused output, check for
// locOutputEngMask.
LocOutputEngineType locOutputEngType;
// when loc output eng type is set to fused, this field
// indicates the set of engines contribute to the fix.
PositioningEngineMask locOutputEngMask;
} GnssLocationInfoNotification;
typedef struct {
@ -1317,6 +1359,20 @@ typedef std::function<void(
GnssLocationInfoNotification gnssLocationInfoNotification
)> gnssLocationInfoCallback;
/* Gives default combined location information from all engines and
location information individually from selected engines.
This callback is only used when there are multiple engines
running in the system.
optional can be NULL
engineLocationsInfoCallback is called only during a tracking session
broadcasted to all clients, no matter if a session has started by client */
typedef std::function<void(
uint32_t count,
GnssLocationInfoNotification* engineLocationInfoNotification
)> engineLocationsInfoCallback;
/* Used for addGeofences API, optional can be NULL
geofenceBreachCallback is called when any number of geofences have a state change */
typedef std::function<void(
@ -1403,6 +1459,7 @@ typedef struct {
gnssMeasurementsCallback gnssMeasurementsCb; // optional
batchingStatusCallback batchingStatusCb; // optional
locationSystemInfoCallback locationSystemInfoCb; // optional
engineLocationsInfoCallback engineLocationsInfoCb; // optional
} LocationCallbacks;
#endif /* LOCATIONDATATYPES_H */

View file

@ -385,6 +385,13 @@ typedef uint64_t GpsLocationExtendedFlags;
#define GPS_LOCATION_EXTENDED_HAS_CALIBRATION_CONFIDENCE 0x800000000
/** GpsLocationExtended has sensor calibration status */
#define GPS_LOCATION_EXTENDED_HAS_CALIBRATION_STATUS 0x1000000000
/** GpsLocationExtended has the engine type that produced this
* position, the bit mask will only be set when there are two
* or more position engines running in the system */
#define GPS_LOCATION_EXTENDED_HAS_OUTPUT_ENG_TYPE 0x2000000000
/** GpsLocationExtended has the engine mask that indicates the
* set of engines contribute to the fix. */
#define GPS_LOCATION_EXTENDED_HAS_OUTPUT_ENG_MASK 0x4000000000
typedef uint32_t LocNavSolutionMask;
/* Bitmask to specify whether SBAS ionospheric correction is used */
@ -798,6 +805,16 @@ typedef struct {
/** Sensor calibration confidence percent. Range: 0 - 100 */
uint8_t calibrationConfidence;
DrCalibrationStatusMask calibrationStatus;
/* location engine type. When the fix. when the type is set to
LOC_ENGINE_SRC_FUSED, the fix is the propagated/aggregated
reports from all engines running on the system (e.g.:
DR/SPE/PPE) based proprietary algorithm. To check which
location engine contributes to the fused output, check for
locOutputEngMask. */
LocOutputEngineType locOutputEngType;
/* when loc output eng type is set to fused, this field
indicates the set of engines contribute to the fix. */
PositioningEngineMask locOutputEngMask;
} GpsLocationExtended;
enum loc_sess_status {
@ -806,6 +823,13 @@ enum loc_sess_status {
LOC_SESS_FAILURE
};
// struct that contains complete position info from engine
typedef struct {
UlpLocation location;
GpsLocationExtended locationExtended;
enum loc_sess_status sessionStatus;
} EngineLocationInfo;
// Nmea sentence types mask
typedef uint32_t NmeaSentenceTypesMask;
#define LOC_NMEA_MASK_GGA_V02 ((NmeaSentenceTypesMask)0x00000001) /**< Enable GGA type */