10 years, 5 months ago.

u-blox 5 GPS RS232

Hi,

I've connected my mbed to a u-blox 5 GPS shield, which includes a Navilock NL550ERS chip for levelshifting to RS232 standard. To go back on TTL for the Mbed, I'm using a MAX 232.

I'd like to just read the data the u-blox is permantly sending. Therefore, I need to set up the UART2 interface for p28 and p27. Further, I need to set up a baudrate of 38400.

In the code below, I tried to initialize UART2, refering to

https://developer.mbed.org/users/AjK/notebook/getting-closer-to-the-hardware/

and

https://sites.google.com/site/johnkneenmicrocontrollers/sci_rs232/sci_1768

I tried both methods for setting the baudrate without success. Printing the "characters" to a terminal there's always the same character (look at the picture). If I unplug the GPS device, it still happens the same on the terminal, which is very confusing.

Anyone for help?

#define IER_RBR         0x01
#define IER_RLS         0x04
#include "mbed.h"

Serial pc(USBTX, USBRX); // tx, rx
uint8_t                     UART2RcvOutIndex;
uint8_t                     UART2RcvInIndex;

void uart_init(int baudrate);
 
int main() {
char c;
pc.baud(9600);
uart_init(38400);

while(1)
{
    c=(char)LPC_UART2->RBR; 
    pc.printf("%c\n", c);
}

void uart_init(int baudrate)
{
        uint32_t fdiv;
        LPC_SC->PCONP |= (1<<24);               // power-up UART2 
        LPC_SC->PCLKSEL1    &= ~(3UL << 18);
        LPC_SC->PCLKSEL1    |=  (1UL << 18); // PCLK = CCLK

        LPC_PINCON->PINSEL0 |= ((1<<22) | (1<<20));  // enable RxD2 P0.11, TxD2 P0.10
        
        LPC_UART2->LCR = 0x80;                  // enable access to baudrate divisors
        fdiv = ((SystemCoreClock/4) / (16 * baudrate)); //baud rate
    
       // LPC_UART3->FDR = 0x58;  //DivAddVal = 5, MULVAL=8 doesn't work don't know why
        LPC_UART2->DLM = fdiv / 256;                                                    
        LPC_UART2->DLL =fdiv % 256;
        LPC_UART2->LCR = 0x03;                  // disable baudrate divisor access, 8 bits, no parity, 1 stop bit
        LPC_UART2->FCR = 0x07;                  // enable and reset TX and RX FIFO
        LPC_UART2->IER = (IER_RBR|IER_RLS);     // enable interrupts on RBR and RLS, no THRE for now (someone better enable interrupts!)
        UART2RcvOutIndex = 0;                   // need to rewind the receive queue indices
        UART2RcvInIndex = 0;
        NVIC_EnableIRQ(UART2_IRQn);             // now turn on the IRQ handler  
        LPC_UART2->IER = 0x01; 

 }   

/media/uploads/abcSepp/received_data.png

1 Answer

10 years, 5 months ago.

You get the same character constantly because your while loop is sitting there reading the last byte received and outputting it to the PC over and over again rather than waiting for a new byte to arrive.

You need to either check for new data or use the receive interrupt to tell you there is new data available.

Also you have a fundamental design issue, you are getting data in at 38400 and then for each byte you get you send two bytes out on a serial port at 9600. The output isn't going to keep up which means if you get more than 16 bytes in a row the UART buffer will overflow and data will get lost.

Also this may be a silly question but why are you doing this the hard way? If this is a learning project then that's fine but if all you want to do is get data from the GPS then do it the easy way.

Serial gps(p28,p27); // use the serial port class rather than bare metal.
Serial pc(USBTX, USBRX);

onGPSrx() {
  while (gps.readable())
    pc.putc(gps.getc());
}

main () {
  gps.baud(38400);
  pc.baud(115200); // output port as fast or faster than the input port in order to avoid needing to use software buffers
  gps.attach(onGPSrx);
  while (1) { // loop forever.
    wait(1);
  }
}