Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Database - getAccumulatedDeltaRangeMeters() support isn't reported correctly #478

Closed
barbeau opened this issue Jan 28, 2021 · 7 comments
Closed
Labels
Milestone

Comments

@barbeau
Copy link
Owner

barbeau commented Jan 28, 2021

Describe the bug
First reported at https://groups.google.com/g/gpstest_android/c/JkaiUnPdi-Q/m/sO0f-lnDAQAJ.

Apparently the support for getAccumulatedDeltaRangeMeters() for RTK / carrier phase measurements isn't being captured correctly.

From the above post:

looking at the list of phones you compiled has both " Navigation messages" and " Carrier phase (getAccumulatedDeltaRangeMeters())" columns and for the Pixel 4 it shows "Not Supported" for the first when they do output CP messages and the Mi 10 Lite shows "Supported" for the second and it doesn"t, or rather they are showing 0.0.

This is a little tricky to support without having access to many physical devices, so I could certainly use help testing if others have devices. Here's the current logic we're using:

    /**
     * Returns true if carrier phase uncertainty is supported for this GNSS measurement, false if it is not
     * @param gnssMeasurement
     * @return true if carrier phase uncertainty is supported for this GNSS measurement, false if it is not
     */
    public static boolean isCarrierPhaseUncertaintySupported(GnssMeasurement gnssMeasurement) {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
            return gnssMeasurement.getAccumulatedDeltaRangeState() != GnssMeasurement.ADR_STATE_UNKNOWN;
        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            return gnssMeasurement.hasCarrierFrequencyHz();
        } else {
            return false;
        }
    }

Seems like at a minimum we need to check getAccumulatedDeltaRangeMeters() and make sure the value isn't 0.0, and maybe look at all measurements instead of just one.

See also https://groups.google.com/g/gpstest_android/c/_D70pKZduFQ.

To Reproduce
Steps to reproduce the behavior:

  1. Go to "Share" and "Device" tab
  2. Upload device characteristics to the device database - https://bit.ly/gpstest-device-database

Expected behavior
Devices that support getAccumulatedDeltaRangeMeters() should show up as SUPPORTED, and those that do not should show up as NOT_SUPPORTED

Observed behavior
See above quote - some devices aren't showing up right

App, Device and Android version:

See above - Pixel 4, Mi 10 Lite

@barbeau barbeau added the bug label Jan 28, 2021
@barbeau barbeau added this to the v3.9 milestone Jan 28, 2021
@barbeau barbeau changed the title Database - getAccumulatedDeltaRangeMeters() isn't reported correctly Database - getAccumulatedDeltaRangeMeters() support isn't reported correctly Jan 28, 2021
@barbeau
Copy link
Owner Author

barbeau commented Jan 28, 2021

Oh, there is also a bug in the above code for Android <= O - gnssMeasurement.hasCarrierFrequencyHz() should be gnssMeasurement.hasCarrierPhase().

@webvan1999
Copy link

Thanks for starting the issue that I mentioned in the Google Group.
Checking for 0.0 would work to filter out my Mi 10. I have a Redmi 9 handy that is single-band and has ADR but it looks like the data is garbage so that wouldn't help :-( I'll do more testing to check that.

Also would it be possible to show ADR Support (and maybe specify somewhere that it matters because it's a requirement for post-processing via RTP or PPP) in the Email feedback form and not only the Database feedback where the user can't see what's being sent as far as I can tell ?

@barbeau
Copy link
Owner Author

barbeau commented Jan 28, 2021

Checking for 0.0 would work to filter out my Mi 10

👍

I have a Redmi 9 handy that is single-band and has ADR but it looks like the data is garbage so that wouldn't help :-( I'll do more testing to check that.

I'm wondering if I should also be more strict and instead of:

gnssMeasurement.getAccumulatedDeltaRangeState() != GnssMeasurement.ADR_STATE_UNKNOWN

...change to:

gnssMeasurement.getAccumulatedDeltaRangeState() == GnssMeasurement.ADR_STATE_VALID

I was originally assuming that if the device reported any state other than unknown it has some knowledge of ADR and therefore supported it, but maybe that's not strict enough.

Any idea if that would fix the Redmi 9 issue?

Also would it be possible to show ADR Support (and maybe specify somewhere that it matters because it's a requirement for post-processing via RTP or PPP) in the Email feedback form and not only the Database feedback where the user can't see what's being sent as far as I can tell ?

Sure - could you open an issue for including it in Email feedback? I have #313 open for an eventual in-app UI for device capabilities but that's a larger lift.

@barbeau
Copy link
Owner Author

barbeau commented Jan 28, 2021

I'm going to go with the above for now (see new logic in 70d8ec5).

I'll try to get another release out soon with this so you and others can test.

@barbeau
Copy link
Owner Author

barbeau commented Jan 28, 2021

I looked at my logs and don't see "ADR_STATE_VALID" or even "VALID", are you seeing that elsewhere ?

@webvan1999 These are device states returned by the GnssMeasurement API in Android, specifically from getAccumulatedDeltaRangeState():
https://developer.android.com/reference/android/location/GnssMeasurement#getAccumulatedDeltaRangeState()

Those docs say:

Value is either 0 or a combination of ADR_STATE_VALID, ADR_STATE_RESET, ADR_STATE_CYCLE_SLIP, ADR_STATE_HALF_CYCLE_RESOLVED, and ADR_STATE_HALF_CYCLE_REPORTED

0 is also equal to GnssMeasurement.ADR_STATE_UNKNOWN

getAccumulatedDeltaRangeMeters() docs:
https://developer.android.com/reference/android/location/GnssMeasurement#getAccumulatedDeltaRangeMeters()

...say:

Gets the accumulated delta range since the last channel reset, in meters.

The error estimate for this value is getAccumulatedDeltaRangeUncertaintyMeters().

The availability of the value is represented by getAccumulatedDeltaRangeState().

So you won't see these ADR_* values output in logs, but they are used within the app to determine the state surrounding ADR.

Looking at GnssLogger closer, they use the value 1 (which is what the constant ADR_STATE_VALID equals) to determine if the ADR should be used for positioning, so the approach I'm now using seems right:
https://github.com/google/gps-measurement-tools/blob/978de59bfdf082b7afbea52c008226402fc846d6/GNSSLogger/pseudorange/src/main/java/com/google/location/lbs/gnss/gps/pseudorange/PseudorangePositionVelocityFromRealTimeEvents.java#L142

@barbeau
Copy link
Owner Author

barbeau commented Feb 14, 2021

Re-opening - on a closer look at the ADR_* constants, it looks like this is actually a bitmask, so more than one enum value can be represented at the same time. I think the GnssLogger open-source code is old at this point and was used when some of the newer ADR values introduced in API 28 didn't yet exist. As a result, at the time they could just check if the state was equal to 1, but this no longer works with newer devices >= API 28. So we need to check if the LSB is set for this to work right on newer devices instead of checking equal to 1.

@barbeau barbeau reopened this Feb 14, 2021
@barbeau
Copy link
Owner Author

barbeau commented Feb 22, 2021

I've opened a PR on the Google GnssLogger as well to fix the ADR state bug there:
google/gps-measurement-tools#29

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

2 participants