Author Topic: How do you read and parse the GPS data  (Read 1582 times)

0 Members and 1 Guest are viewing this topic.

Offline Dadu@Topic starter

  • Contributor
  • Posts: 34
  • Country: in
How do you read and parse the GPS data
« on: February 06, 2023, 12:26:29 pm »
I am trying to understand the program logic on how the microcontroller read and Parse the GPS data. I have looked through a lot of code but I do not fully understand logic.

 I know microcontroller receive  character from GPS receiver via UART.  I do not understand when interrupts are activated and what is done in the interrupt service routine. Does each character is read and stored in buffer in the interrupt service routine when the interrupt is activated



 

Offline GromBeestje

  • Frequent Contributor
  • **
  • Posts: 276
  • Country: nl
Re: How do you read and parse the GPS data
« Reply #1 on: February 06, 2023, 06:49:00 pm »
Quote
I know microcontroller receive  character from GPS receiver via UART.  I do not understand when interrupts are activated and what is done in the interrupt service routine. Does each character is read and stored in buffer in the interrupt service routine when the interrupt is activated

Depends on the microcontroller capabilities and implementation.
In general, a GPS (GNSS) receiver sends characters over UART. As the receiver decides when it sends, and not the microcontroller, the microcontroller uses interrupts, to interrupts what is was doing, and receive what the GPS receiver sends. In this case, the ISR receives one byte from the UART and stores it somewhere in memory. Alternatively, it might do a DMA transfer. In this case, the UART peripheral in the microcontroller can receive the data from the GPS receiver and put it somewhere in memory.

When the data is received, it has to be inspected. A GPS receiver sends NMEA sentences. These sentences are ASCII data, terminated with \r\n characters. The received data has to be chopped up in these sentences. This could be done inside the interrupt handler or in the main loop. Regardless, one has to keep track of where in the buffer the read and write pointer are.

There are GPS receivers which communicate over other protocols such as I²C. In such case, the microcontroller is in charge of when communication happens.

Once a whole sentence has been found, it can be parsed with an NMEA parser. For this purpose I recommend https://github.com/kosma/minmea
 

Offline Dadu@Topic starter

  • Contributor
  • Posts: 34
  • Country: in
Re: How do you read and parse the GPS data
« Reply #2 on: February 08, 2023, 06:00:39 pm »
Quote


When the data is received, it has to be inspected. A GPS receiver sends NMEA sentences. These sentences are ASCII data, terminated with \r\n characters. The received data has to be chopped up in these sentences. This could be done inside the interrupt handler or in the main loop. Regardless, one has to keep track of where in the buffer the read and write pointer are.
I am trying to understand code given in link
https://www.electronicwings.com/arm7/gps-module-interfacing-with-lpc2148
Can you tell what is happening in the interrupt service routine?
 

Offline GromBeestje

  • Frequent Contributor
  • **
  • Posts: 276
  • Country: nl
Re: How do you read and parse the GPS data
« Reply #3 on: February 08, 2023, 07:01:35 pm »
Let's have a look.  This is accessing the registers of the microcontroller directly.
Using some code in a header file and linker script, making them appear as variables. Apart from that magic, I'll focus on the interrupt routine. This is called for every received character. This is a pretty limited parser which only looks for the GGA sentence. And in my opinion, it's rather awkward. Not a good reference to learn to understand.


When the interrupt is called, one character is received. This is read from the register and put in a local variable.
Code: [Select]
    received_char = U0RBR;

If the received character is a '$', this is the character that indicated the beginning of an NMEA sentence.
Code: [Select]
    if( received_char == '$' )
    {
        GGA_Index = 0;
        CommaCounter = 0;
        IsItGGAString = false;
    }


Then have a look at the end. I will explain a bit out of order, but I need to explain this part first to understand what is going on.
CGA is filled up from the end, and moved forwards.

So initially, it contains "\0\0\0"
The string the GNSS module transmits is "$GPGGA". The '$' was already eaten.
So for each character we get
Code: [Select]
"\0\0G"
"\0GP"
"GPG"
"PGG"
"GGA"
This looks rather awkward. Why would anyone write this?  Okay, they're ignoring the "GP" part... I get that, but why do it like this. This is code running on an ARM processor. No need to save 2 bytes of memory. If this code were running on something with an amount of RAM measured in bytes, such as a 8051 based MCU. This code is to run on a fairly old ARM chip, but still that chip got 32 kB of RAM, so there is no need to do such awkward code.

Code: [Select]
    else /* Store received character */
    {
        GGA[0] = GGA[1];
        GGA[1] = GGA[2];
        GGA[2] = received_char;
    }

Anyhow. After receiving this, we have  "GGA" in GGA, then we look at where we were. If we have this "GGA" in GGA, a condition variable IsItGGAString is set, and GGA is nulled.

Code: [Select]
else if( ( GGA[0] == 'G' ) && ( GGA[1] == 'G' ) && ( GGA[2] == 'A' ) ) /* If GGA string received */
{
IsItGGAString = true;
GGA[0] = GGA[1] = GGA[2] = 0;
}


Now IsItGGAString is set, we enter this part of the code.
This puts the data part of the string in GGA_String, and stored the location of the commas in GGA_Comma_Pointers

Code: [Select]
else if( IsItGGAString == true ) /* If $GPGGA string */
{
if ( received_char == ',' )
{
GGA_Comma_Pointers[CommaCounter++] = GGA_Index; /* Store locations of commas in the string in a buffer */
}
GGA_String[GGA_Index++] = received_char; /* Store the $GPGGA string in a buffer */
}


The rest of the parsing is done elsewhere in the code.

 
The following users thanked this post: Ed.Kloonk

Offline peter-h

  • Super Contributor
  • ***
  • Posts: 3670
  • Country: gb
  • Doing electronics since the 1960s...
Re: How do you read and parse the GPS data
« Reply #4 on: February 09, 2023, 10:15:47 am »
In general, I parse NMEA by looking for the start character, then loading a max # of x bytes into a buffer size x, or until the end character is seen, whichever occurs first. Then check the checksum. Then extract the required data.

Not all GPS units emit all possible NMEA strings; only some are common across them.
Z80 Z180 Z280 Z8 S8 8031 8051 H8/300 H8/500 80x86 90S1200 32F417
 


Share me

Digg  Facebook  SlashDot  Delicious  Technorati  Twitter  Google  Yahoo
Smf