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.

Reception of a frame <STX>....<ETX> Using UART

Status
Not open for further replies.

treyz

Member level 5
Joined
Sep 26, 2012
Messages
93
Helped
0
Reputation
0
Reaction score
0
Trophy points
1,286
Activity points
2,065
Hi everyone

I am sending a stream of data from hypeterminal from a PC to a PIC 18F4680 via RS232.

Here the frame:
<STX><ADDR><DATAPAYLOAD=DATA+CHECKSUM><ETX<

Size.

STX = 0x02 (8-bit)
ADDR(8 or 9 bit, if ADDRESS is between 1 and 99,set the 9th bit at 1. If ADDRESS is at 0, clear the 9th bit)
DATA in 8-bit
CHECKSUM in 8-bit
ETX = 0x03(8-bit)

This is what the PIC should do:

- Receive the packet
- Check if the reception starts by 0x02,( if yes, check if ADDR is between 1 and 99 or at 0)
- Perform the checksum on <DATA>( Checksum = 2's complement)
- Wait for 0x03(ETX)

I wrote a piece of code,but I think I am confusing myself. Please Can I have some help?
 

Attachments

  • Frame.txt
    1.1 KB · Views: 121
Last edited:

Re: Reception of a frame <STX>....<ETX>

This is something I do all the time.

Your mistake is not knowing where the frame starts and stops. What you need to do is look at each byte as it arrives in the UART and compare it with <STX>. When <STX> is found start reading the following bytes into your array until the byte matches <ETX> or some error condition is detected such as too many bytes have arrived. This is an extract of my code, it is called upon a UART RX interrupt and I've removed some specific code dedicated to the work here. You should be able to work out the variable definitions. My WaitRx() function pulls a byte from the receive fifo.

Code:
void ByteFromNetwork()   
{
    BusRx = WaitRx();
    
    if(BusRx == STX) //start of a new transmission block?
    {
        BusRxPtr = 0;
        *BusRxBuffer = 0;
        return;
    }
    
    if(BusRx ==    ETX) //end of a transmission block    
    {
               <your code goes here>
        
        BusRxPtr = 0;
        BusRxBuffer[0] = 0;
    }
        
    if(BusRxPtr < 20) // prevent buffer overflow
    {
        BusRxBuffer[BusRxPtr++] = BusRx;
        BusRxBuffer[BusRxPtr] = 0;
    }
        
}

Brian.
 

Re: Reception of a frame <STX>....<ETX>

Hi

Thank you Brian for replying to me.
When you said "your code goes here",do you mean,my piece of code that I have showed you, or just the cheksum?
I am asking this because, I am already waiting for the transmission of reception of STX and ETX....
Please Can you tell me if my "checksum is right"?

Marc
 
Last edited:

Re: Reception of a frame <STX>....<ETX>

The <your code goes here> part is only reached when the whole data frame has been received, everything after <STX> up to <ETX> so at that point you can read each byte to verify the CRC and if Ok, use the data. For example if your frame was <STX> <0x12><0x34><0x56><CRC><ETX>, the contents of RxBuffe would be:
RxBuffer[0] = 0x12
RxBuffer[1] = 0x34
RxBuffer[2] = 0x56
RxBuffer[3] = CRC

Be careful with the data you send (including the CRC) because if it happes to be the same value as STX or ETX it will be seen as those by mistake. I convert all my data into it's ASCII equivalent before sending it.
Make sure the RxBuffer, or whatever you name it, is one byte bigger than the maximum length of your frame because that last section of code 'pushes' a zero terminator into the address beyond the end of the data.

Brian.
 

Re: Reception of a frame <STX>....<ETX>

Thank you for getting back to me again.

Yes I know,

I don't know the length of dat yet, that is why I have used aonther forever loop until we "break" it. i.e. from result[2] to result[j-1], and should be equals to zero otherwise there's an error.

Structure of data PAYLOAD:
result[0] = STX
result[1] = Address (?)
result[2] = data[0]
.
.
result[2+n] = data[n]
result[3+n] = ETX

In Result[], I have "data" and "checksum"..... I would like to sum <data>+<checksum>. Does it make sense?

Marc
 
Last edited:

Re: Reception of a frame <STX>....<ETX>

Hi

What do you think of this code? Is that better?
 

Attachments

  • Frame2.txt
    1.4 KB · Views: 104

Re: Reception of a frame <STX>....<ETX>

Hi,

Please, Can I have some help?
 

Re: Reception of a frame <STX>....<ETX>

It might work but I still have some concerns over the way you are doing it. For one thing, it's blocking code, in other words if the <ETX> never arrives the routine will hang forever.
Making the whole routine interrupt driven as in the example I gave will avoid this and allow the remainder of the program to run without being held up waiting for serial bytes.

One thng puzzles me, why do you "init_uart()" then later use "openUSART(....." with all the parameters, don't they do the same thing?

Brian.
 

Re: Reception of a frame <STX>....<ETX>

Hi Brian

Nice to hear from you again!
The delimiters(STX and ETX) will always be there. The most important things are <ADDR>,<DATA> and <CHECKSUM>.
Sorry about Init_uart, it might confuses you,( i have just used it when I was testing ma communication between my PIC and my PC) and about "openUSART", I am using it to send a words to my PC(hyperterminal),just in case of wrong checksum via USART. I am using the compiler c18 mpalad. This is what you have to do if you want to display something on "hyperterminal"

Marc
 
Last edited:

Status
Not open for further replies.

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top