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

feature: add support for satellite data (GSA, GSV) #187

Merged
merged 2 commits into from
Apr 11, 2021
Merged

Conversation

tkurki
Copy link
Member

@tkurki tkurki commented Jan 12, 2021

No description provided.

@tkurki tkurki changed the title [WIP] feature: add GSV support [WIP] feature: add support for satellite data (GSA, GSV) Jan 12, 2021
@Hakansv
Copy link
Contributor

Hakansv commented Jan 13, 2021

I've tried the GSV from branch sats-in-view and it's not working. No GPGSV is read.
It may be due to my device, AirMar TD100, is following the NMEA0183 spec. to not repeat info from 1:st message in subsequent massages.

My GSV looks like this. (For test: TCP; signalk.stupan.se port: 10112)

$GPGSV,3,1,10,8,13,62,35,13,50,277,39,18,18,324,33,5,53,228,38*48
$GPGSV,,2,,7,43,71,39,30,73,107,38,27,13,26,34,15,14,289,37*7F
$GPGSV,,3,,14,33,150,40,28,26,155,37*44

Following the recommendation in the note below from the specification for GSV: (probably older than 4.11)

So
if (parts[SATS_IN_VIEW] === '') {
will delete session.gsvData and return 0 for all gsvData.nextSentenceNumber > 1.

Notes: 1 (from spec 4.11) Satellite information may require the transmission of multiple sentences all containing identical field formats when sending a complete message. The first field specifies the total number of sentences, minimum value 1. The second field identifies the order of this sentence (sentence number), minimum value 1. For efficiency it is recommended that null fields be used in the additional sentences when the data is unchanged from the first sentence.

@tkurki
Copy link
Member Author

tkurki commented Jan 13, 2021

Thanks, fixed to work without repeated fields.

@Hakansv
Copy link
Contributor

Hakansv commented Jan 13, 2021

@tkurki
Yes, now it works fine.
The function "session.gsvData" was a nice tool to combine several sentences. I didn't noticed before.

  • I noticed you've changed the path from navigation.gnss. satellites
    to "navigation.satellitesInview.satellitesInview" for number of satellites.
    And the new "navigation.satellitesInview.satellites" for satellites constellation.
  • I suppose elevation and azimuth units would be changed to radians? If so I personally find three or four significant precision to be enough.
  • The satellites list in the "Data Browser" do occupy some significant space. But not much to deal with I suppose?

When these new paths are agreed to update the SK specification we will adapt it into O code as well.

Thanks.
Håkan

@Hakansv
Copy link
Contributor

Hakansv commented Jan 17, 2021

@tkurki
Please an advice how to parse this data

One level of object is no problem:

{"path":"navigation.position",
"value":
 {"longitude":11.074966666666667,
  "latitude":57.7099}
  },

The we code:

if (update_path == _T("navigation.position")) {
		double lat = value[_T("latitude")].AsDouble();
		double lon = value[_T("longitude")].AsDouble();

But...
Nested objects like this I can't figure out:

{"path":"navigation.satellitesInView",
  "value":{"satellitesInView":11,
	"satellites":{
		"2":{"elevation":"41", "azimuth":"284", "SNR":"37"},
		"3":{"elevation":"11", "azimuth":"124", "SNR":"29"},
		"4":{"elevation":"42", "azimuth":"77", "SNR":"33"},
		"5":{"elevation":"9", "azimuth":"298", "SNR":"37"},
		"6":{"elevation":"42","azimuth":"222","SNR":"39"},
		"7":{"elevation":"37","azimuth":"174","SNR":"40"},
		"9":{"elevation":"80","azimuth":"115","SNR":"38"},
		"16":{"elevation":"18","azimuth":"70","SNR":"35"},
		"26":{"elevation":"17","azimuth":"38","SNR":"30"},
		"29":{"elevation":"11","azimuth":"348","SNR":"35"},
		"30":{"elevation":"9","azimuth":"193","SNR":"31"}
		}
 }

This one is easy and works fine:
double m_SK_SatsInView = (value["satellitesInView"].AsInt());

But how can I parse the satellites: value and like "elevation": value?
If I ask for (value["satellites"] I get the result {11} e.g. the size of "satellites":
If i could get the whole "satellites" as a string it will be fine but I haven't succeed.
Any advise?

@Hakansv
Copy link
Contributor

Hakansv commented Jan 19, 2021

@tkurki
I couldn't get the structure:
"satellites":{
"2":{"elevation":"41", "azimuth":"284", "SNR":"37"},
to work with OCPN where I've to divide a 12 message group to three groups of four messages, like the GPGSV does it. But then I need all four constellations combined in the array. So I changed my copy of your GSV.js to get the structure as of the pict below instead:
Do you have any trouble with that? See: My SK
With these changes all instruments and satellite data are fine also in OCPN using SK data.
My edited GSV.js attached.

Håkan

bild

GSV .js.txt

@Hakansv
Copy link
Contributor

Hakansv commented Jan 19, 2021

@tkurki
My latest edits to GSV.js can be shown here: My Git
With this it works fine in OCPN but changes to names or other are easily adapted since no O release is yet performed. We are working on a new Android release though.

bild

@tkurki
Copy link
Member Author

tkurki commented Jan 19, 2021

Yes. I'll update my code soonish.

@Hakansv
Copy link
Contributor

Hakansv commented Jan 21, 2021

OK, good. I can PR my changes if you want?

@tkurki
Copy link
Member Author

tkurki commented Jan 27, 2021

I force pushed a slightly modified version of what you had. I don't want to loose precision by rounding, even if it does not really matter in this case, and numbers should be numbers. I also changed the count field to count, as the path is already satellitesInView and it felt stupid repeating that.

@Hakansv
Copy link
Contributor

Hakansv commented Jan 27, 2021

@tkurki
I do agree on the changes.
I'll update the OCPN code accordingly and PR that for next release.
Many thanks for your support.
Håkan

@Hakansv
Copy link
Contributor

Hakansv commented Jan 27, 2021

@tkurki
Now also tested in SK and OCPN. Works like a charm

@Hakansv
Copy link
Contributor

Hakansv commented Feb 1, 2021

@tkurki
For me this is ready to merge.
Next step or at once?
The use of different satellite systems, apart from GPS, are now in stable use by new GNSS devices. OCPN will implement this in it's "GNSS Status" graphical instrument. (The one shown above). For that we need the GSV TalkerID. For NMEA0183 GSV in OCPN it's not a problem. It would be nice if the same info is available also from SK?
Something like the talkerID insert in the code snippet below. But I don't don't know if that info is available in SK?

const gsvData = session.gsvData || (session.gsvData = {
    nextSentenceNumber: 1,
    numberOfSentences: Number(parts[NUMBER_OF_SENTENCES]),
    count: Number(parts[SATS_IN_VIEW]),
    talkerID: String(Is there a function to get the GSV TalkerID? Possible values: "GP", "GA", "GB", "GI", "GL", "GQ" else ""
    satellites: []

ref:
NMEA talker mnemonics

@tkurki
Copy link
Member Author

tkurki commented Feb 6, 2021

Next steps:

Add support for multiple gnss systems

  • this should not be NMEA0183 specific, as we must support also N2K data and in theory non-NMEA sats data

Check that this is in line with what we already have in the specification

Add support for the same stuff in n2k-signalk

@tkurki
Copy link
Member Author

tkurki commented Feb 6, 2021

NMEA0183 using talker ID to identify the GNSS systems fits very badly with how Signal K is using talker id. SK has the concept of a source, that translates roughly to a sensor. In N2K it is a device on the N2K bus, in 0183 it is a talker. So in data from 0183 the source is a combination of a (connection) label/id (assigned in the SK server UI by the user) and the talker ID.

{
  "updates": [
    {
      "source": {
        "sentence": "GSV",
        "talker": "GP"
      },
...

Data with differerent talker IDs therefore look like data from two different devices.

I am not sure how to solve this. One way would be to add a configurable option to a NMEA0183 connection, that would tell the parser to use a generated talker id, like GNSS, that is distinct from all real 0183 talker ids being four characters.

A place where this fails is data log files, where the connection label/id is not stored at all. That we can solve by including the label id in the data logs and a bit of defensive coding for backwards compatibility in playback.

That leaves the problems

  • identifying the gnss system in the delta
  • allowing coexistence of satsinview data from different gnss systems for the same source in the full model. in practice this is not possible without adding something dynamic to the path, like we do for multiple batteries and engines (propulsion)

One totally new avenue would be to create a new mechanism, where this kind of metadata about a sensor would end up under sources, under the source. One problem with that approach (in addition to the fact that I think there is no such mechanism now) is that it is server global, and won't work in system to system communications.

ping @sbender9 - do we have something that puts this kind of data under sources?

@Hakansv
Copy link
Contributor

Hakansv commented Feb 6, 2021

The TalkerID, for GSV, is nothing else than a satellite system pointer. That is; "for what satellite system are the constellation data in the message referring to." So GSV is sent from the receiver in up to six groups divided per sat system. All in one second. The talkerID is the group divider. So, apart from most other NMEA messages, the GSV-TalkerID is essential and unique info. For other messages like e.g. xxRMC we don't need to care about the TalkerID to use the messaged data.

The GSV TalkerID info belongs to every single message and can't be stored anywhere else. I understand this doesn't comply with the SK way of handling the TalkerID. It's the same for OCPN where we until now don't care about the TalkerID to use the info. The NMEA0183 specification for this seems also a to be a "quick" solution apart from how they normally handle data info.

So my question is still if SK could implement the TalkerID info for the GSV message beside the "count" path? The value for "count" is actually the number of sats for the "TalkerID"-system.

How the N2k specification handle this I don't know but it would be in some similar way. Satellite constellation data would belong to a single satellite system in the same way for every GNSS receiver.

@tkurki
Copy link
Member Author

tkurki commented Feb 6, 2021

I understand and I am not saying that SK is correct, just saying how it is.

Supporting only NMEA0183 in a NMEA0183 specific way is not a good option. Let's try to find out more about how this is in N2K.

@Hakansv
Copy link
Contributor

Hakansv commented Feb 6, 2021

Very good.
The N2k spec is of course not available in the same way as NMEA0183 but you guys may have more experience. But I'll see if Google is friend here as well.

@tkurki
Copy link
Member Author

tkurki commented Feb 7, 2021

@Hakansv
Copy link
Contributor

Hakansv commented Feb 7, 2021

The PGN 129793 would be closest: (But search for e.g. Galileo and there are three more PGNs
"Order":14,
"Id":"gnssType",
"Name":"GNSS type",
"BitLength":4,
"BitOffset":188,
"BitStart":4,
"Type":"Lookup table",
"Signed":false,
"EnumValues":[
{"name":"undefined","value":"0"},
{"name":"GPS","value":"1"},
{"name":"GLONASS","value":"2"},
{"name":"GPS+GLONASS","value":"3"},
{"name":"Loran-C","value":"4"},
{"name":"Chayka","value":"5"},
{"name":"integrated","value":"6"},
{"name":"surveyed","value":"7"},
{"name":"Galileo","value":"8"}]},

But Canboat PGN's are missing a few GNSS types:
From here
bild

@Hakansv
Copy link
Contributor

Hakansv commented Feb 7, 2021

Sorry, correction! PGN would be 129029. The one above is for AIS.
Maybe we could ask for data with PGN 129029?

@Hakansv
Copy link
Contributor

Hakansv commented Apr 9, 2021

@tkurki
From a OCPN point of view this could be merged as is. The satellite system info from TalkerID could wait until a specification for that is established.
Thanks
Håkan

@tkurki tkurki merged commit 7ee86ea into master Apr 11, 2021
@tkurki tkurki deleted the sats-in-view branch April 11, 2021 18:04
@tkurki tkurki changed the title [WIP] feature: add support for satellite data (GSA, GSV) feature: add support for satellite data (GSA, GSV) Apr 11, 2021
@tkurki
Copy link
Member Author

tkurki commented Apr 11, 2021

Published in version 3.10.0.

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

Successfully merging this pull request may close these issues.

None yet

2 participants