mikalhart / TinyGPSPlus

A new, customizable Arduino NMEA parsing library
http://arduiniana.org
1.1k stars 495 forks source link

Leap seconds and inaccurate time report #125

Open PiotrFabian opened 1 year ago

PiotrFabian commented 1 year ago

Hello, I used this library in a GPS synchronized clock project. The assumption was to display the time with a resolution of 0.1 seconds and an error of no more than 50 milliseconds. The clock has its own DS3231 module which provides accurate time for at least 24 hours after synchronization. The clock is in a room where there is no GPS signal. Synchronization therefore requires moving the clock near a window and manually initiating synchronization. Of course, the synchronization procedure waits until a valid GPS signal is available and then sets up the DS3231 with millisecond accuracy (using the PPS output from the GPS module). But there is a problem: the time given by the GPS after turning on and catching a fix is often three seconds ahead. Exactly three seconds. After several minutes, the time is corrected to the correct value. This is due to leap seconds and delayed accounting for the correction as I read at gpsd.gitlab.io/gpsd/NMEA.html. Under the given assumptions (error not exceeding 50 ms), a deviation of 3000 ms is of course unacceptable. Is there any way to detect whether the reported time includes leap seconds correction or not? Currently, I just leave the clock by the window for 20 minutes and then start syncing. Regards Piotr

svdrummer commented 1 year ago

As this is not a Tiny Gps issue, may I suggest you look at the following link which has options and discussions. In particular GMT vs UTC conversion. https://news.ycombinator.com/item?id=27944776 (Google search)

PiotrFabian commented 1 year ago

Thank you for your answer. It seems that the problem is difficult to solve. First, I looked in the TinyGPSPlus library for a flag informing that the given time is correct. It turned out that the isValid() function informing about the correct location does not tell about the correctness of the time. It happened many times that despite receiving the correct coordinates, the time was incorrect. It would be enough for me to know whether the seconds correction was included or not. But I don't think it can be determined. With the assumed method of using the clock (it is taken outside the house once a day and synchronized with GPS), it probably makes the most sense to check the time difference between the DS3231 and the GPS. If the difference is in the range from 2900 ms to 3100 ms, it means that the GPS time is not corrected. And if it is in the range from -100 ms to +100 ms, then the correction is included.

Here is a snippet of data received from GPS. At the beginning of each line I have included timestamp from DS3231 (valid UTC time). The moment when the GPS time was corrected is visible: the seconds jump back by three. There is no information that this happened. So the problem is unsolvable with such receivers...

13:28:35,06/08/2023,$GPGLL,,,,,132838.00,V,N49 13:28:36,06/08/2023,$GPRMC,132839.00,V,,,,,,,060823,,,N70 13:28:36,06/08/2023,$GPVTG,,,,,,,,,N30 13:28:36,06/08/2023,$GPGGA,132839.00,,,,,0,03,4.89,,,,,,52 13:28:36,06/08/2023,$GPGSA,A,1,31,03,28,,,,,,,,,,4.99,4.89,1.000B 13:28:36,06/08/2023,$GPGSV,2,1,06,01,28,159,27,03,70,082,34,07,,,17,17,24,250,40 13:28:36,06/08/2023,$GPGSV,2,2,06,28,18,039,30,31,36,066,3677 13:28:36,06/08/2023,$GPGLL,,,,,132839.00,V,N48 13:28:37,06/08/2023,$GPRMC,132837.00,V,,,,,,,060823,,,N7E 13:28:37,06/08/2023,$GPVTG,,,,,,,,,N30 13:28:37,06/08/2023,$GPGGA,132837.00,,,,,0,03,4.90,,,,,,54 13:28:37,06/08/2023,$GPGSA,A,1,31,03,28,,,,,,,,,,5.00,4.90,1.0002 13:28:37,06/08/2023,$GPGSV,2,1,07,01,28,159,28,03,70,082,34,07,,,15,17,24,250,4C 13:28:37,06/08/2023,$GPGSV,2,2,07,20,,,20,28,18,039,30,31,36,066,3676 13:28:37,06/08/2023,$GPGLL,,,,,132837.00,V,N46 13:28:38,06/08/2023,$GPRMC,132838.00,V,,,,,,,060823,,,N71 13:28:38,06/08/2023,$GPVTG,,,,,,,,,N30 13:28:38,06/08/2023,$GPGGA,132838.00,,,,,0,03,4.90,,,,,,5B

PiotrFabian commented 1 year ago

I've completed the first version of the GPS-synchronized clock using, among other things, the TinyGPSPlus library. Here is a short video showing how this clock works: (https://youtu.be/agQMkFr3lfo) I encountered another problem, this time related to this library. I had problems with refreshing the LED display, composed of eight 8x8 matrices (as in the video). Every few tenths of a second the refresh slowed down, it looked like something was getting stuck. At first I thought it was the fault of too slow processor (Arduino Nano). However, it turned out that the SoftwareSerial library that TinyGPSPlus uses is the cause of the problems. The LED display is connected to the hardware SPI interface. However, regardless of whether SPI was supported by hardware or software, it was not possible to get a smooth display. Only removing the start of the serial interface (ss.begin()) solved the problem. In the current version of the clock, I run the SoftwareSerial object only for a short while when I need to read data from the GPS. For the rest of the time, the PPS signal from GPS is enough. Time is counted by DS3231 after initial synchronization with GPS.

cyberman54 commented 1 year ago

Use a realtime OS for your project, like FreeRTOS. Segregate time critical tasks like refreshing the display and driving the serial interface in RTOS tasks. Use a state engine for control.

Your issue seems not related to TinyGPS, since TinyGPS is just an NMEA payload parser - no more, no less.