Fix GPS week rollover handling in RTCM3 decoder#767
Fix GPS week rollover handling in RTCM3 decoder#767gary7530 wants to merge 2 commits intortklibexplorer:mainfrom
Conversation
src/rtkcmn.c
Outdated
| (void)time2gpst(utc2gpst(timeget()),&w); | ||
| if (w<1560) w=1560; /* use 2009/12/1 if time is earlier than 2009/12/1 */ | ||
| return week+(w-week+1)/1024*1024; | ||
| return week+(w-week+512)/1024*1024; |
There was a problem hiding this comment.
Well spotted, this looks correct. Fwiw using +511 rather than +512 would have a 2-complement split.
| tt=timediff(gpst2time(eph.week,eph.toes),rtcm->time); | ||
| if (tt<-302400.0) eph.week++; | ||
| else if (tt>=302400.0) eph.week--; | ||
| rtcm->time=gpst2time(eph.week,eph.toes); |
There was a problem hiding this comment.
Note sure about setting the rtcm->time to the eph time. adjgpsweek() also uses timeget(). Might be best to leave that.
The further adjustment to the eph.week might be to handle the rtcm->time being different to timeget() used in adjgpsweek(), handling half a week difference here. If this code is not broken then I suggest not changing it as there are a lot of complex code paths here e.g. replying data etc. Could you split these 'simplifications' out and just include the fix to adjgpsweek().
There was a problem hiding this comment.
The reason for changing rtcm->time to use the ephemeris time is that in the original code, when timeget() and the ephemeris time differ by more than two weeks, it causes incorrect behavior. Using the eph time avoids this issue.
There was a problem hiding this comment.
With adjgpsweek() improved wouldn't that make eph.weeks consistent with timeget(). Can't see why the other eph.week adjustment was needed, and with that removed it should not be an issue even if the eph time is weeks off timeget() or rtcm->time? Still seems best to initialize the rtcm->time using timeget() as that is used everywhere else. So suggest:
eph.week=adjgpsweek(week);
if (rtcm->time.time==0) rtcm->time=utc2gpst(timeget());
There was a problem hiding this comment.
Sorry, my situation is a bit special — I’m actually running RTKLIB on an ESP32. On this platform, every time the ESP32 boots, timeget() starts counting from the firmware’s compile time.
Because of that, when rtcm->time is initialized using timeget(), RTKLIB works correctly during the current week and the following week, but by the second week it encounters a week rollover error.
To fix this, I changed the code to set rtcm->time using the ephemeris time (after correction with adjgpsweek()), instead of relying on timeget().
|
I will close this Pull Request and open a new one with just the fix for adjgpsweek(). |
|
PR #775 adds support for message 1013 which does have the time and that might be a better option for initializing the real time clock on a disconnected device if the rtcm stream is the only option. Fwiw the esp-idf includes a sntp client integrated with the time functions and that might be a quick option for the esp32. For my own esp32 loggers they support the DS3231 RTC when they need to be ready to go, and also synchronise their time when interacting with clients and servers, the web interface sends the web client time and when data is pushed to a server the server responds with the time (better option as it is trusted and there is a round trip time for better estimate), and it also caches data in the flash including the time, and it synchronises these rough real times to the esp32 64-bit system tick counter - there is a lot of code dedicated to the time! |
Pull Request Description:
Summary
This PR fixes the GPS week rollover handling in the RTCM3 decoder by replacing local time-based calculations with ephemeris time.
Changes Made
1. RTCM3 Decoder (
src/rtcm3.c)decode_type1019()(GPS)decode_type1041()(IRNSS)decode_type1044()(QZSS)decode_type1045()(Galileo F/NAV)decode_type1046()(Galileo I/NAV)decode_type1042()(BeiDou)2. Common Functions (
src/rtkcmn.c)adjgpsweek()function by changing the week adjustment calculation from(w-week+1)/1024*1024to(w-week+512)/1024*1024