Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

reading uart using pic18f

Status
Not open for further replies.
when the length of data received is not specified, during that time the rcif bit is set and never returned to 0 causing the program to go in infinite loop.....so how can i come out of the infinite loop.??
 

I must admit that I don't quite understand your comment but I suspect that you are going about this the wrong way.
The RCxIF bit will be set when a value has been received and is available in the RCREGx buffer. Once you have read the received value, the RCxIF bit will be cleared and will stay clear until the next value is received. If there is "no next value" because you have received the last value, then the RCxIF bit will stay at 0.
If you don't know the length of the data to be received then there needs to be some other means to know when it is complete. For text strings, this is typically the '\n' character which indicates a 'newline'. In the examples you have given, this would seem to be the most appropriate way to tell the transmission has completed. However you, as the designer, have the knowledge to determine the best way.
You asked about implementing a timeout and the suggestion was to use a timer which will generate an interrupt if a character is not received soon enough. Assuming that you are using an interrupt to also receive the characters, the code could look like the following pseudo-code:
Code:
volatile char rx_buffer[100];
volatile char *rx_ptr;
volatile int rx_complete;
volatile int rx_timeout;

uart_rx_interrupt()
{
    *rx_ptr = RCREGx;  // Receives the character and resets the RCxIF bit
    if(*rx_ptr++ == '\n')      // Do this if we are checking for the '\n' character here
    { rx_complete = true; }  // '\n' seen so set a flag
    TMRx0H = 0;
    TMRx0L= 0;  // Reset the timer counter as we have received a character
}

timer_x_interrupt()
{
    rx_timeout = true;  // Flag the timeout
   _TMRxON = 0;   // Turn off the timer
   _TMRxIF = 0;    // Clear the timer IF bit
}


main()
{
....
    rx_ptr = rx_buffer;
    rx_complete = false;
    rx_timout - false;
....
    while(!rx_complete && !rx_timeout);  // Wait until the complete message has been received or the timeout occurs
    if(rx_timeout)
    {
        // Handle the incomplete received string
    }
    if(rx_complete)
    {
        // Process the received string
    }
}
Of course you will need to implement this using whatever coding practices are required for your compiler and MCU and you can alter the 'while' condition to whatever suits (I've written this as blocking within an outer main loop but it could actually be the main loop and the other tests are simply part of the main loop processing).
Also there is no error checking which should be added.
There are *MANY* variations and alternatives that could be used - this is just one way of doing this.
No infinite loops (except the main loop which is always infinite), no 'hanging' on failed receptions etc and also notification when the received string completes.
Susan
 

i will try to see if it works
 

how about using a ring/circular buffer to read uart??
 

Circular buffers are always a possibility. As I said, there are *many* variations and alternatives.
It really comes down to the ob you need to do. For example, if you know that you can fully process each in-coming string before the next arrives, then a simple linear buffer might be the way to go as it is easier to program and you don't need a pointer to the last read character. However if the next message might be started before the current message is processed, then a circular buffer is a good option (as long as the buffer is big enough for multiple messages) at the cost additional pointers and code (e.g. the need to check for/process a 'wrap around' on each pointer increment).
All of this is getting a bit ahead of the game right now - have you got the basics working such as correctly reading the incoming characters?
(BTW - for other readers, there is also a parallel forum thread on this subject at https://www.microchip.com/forums/m1032189.aspx which also has a link back to this thread to try to stop duplication of advice and wasted effort.)
Susan
 

Status
Not open for further replies.

Similar threads

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top