PSOC UART RX

Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

cross mob
CaDu_3933941
Level 4
Level 4
50 replies posted 25 replies posted 10 replies posted

Hi all,

I am currently working in making a receiver for an RC car. I already configured the transmitter to send 2 bytes of data using the UART_PutArray function. Now I am trying to read these values on the receiver. The problem is that I do not know how to read more than one byte incoming from the transmitter into the receiver. Would anyone have any idea?

P.S these bytes of data are commands for moving forward and moving sideways.

Thanks

0 Likes
1 Solution
lock attach
Attachments are accessible only for community members.
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

So, I modified my sample and made a couple of projects.

=== transmitter ===

schematic

000-transmitter-schematic.JPG

ADC config

Note: In my experience, if I used Fee running, I got surprising value(s) time to time.

So I use Software trigger.

If you need to use a couple of ADCs, probably you need to use Hardware trigger for both ADCs

and feed trigger from another component like ControlReg to both socs.

001-ADC_config.JPG

main.c

======================

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

#define STR_LEN 32

char str[STR_LEN+1] ; /* print buffer */

void init_hardware(void)

{

    CyGlobalIntEnable ; /* Enable global interrupts */    

    UART_Terminal_Start() ;

    UART_Start() ;

    ADC_Start() ;

}

   

int main(void)

{

    uint16_t x, y ;

  

    init_hardware() ;

  

    for (;;) {

       ADC_StartConvert() ;

       ADC_IsEndConversion(ADC_WAIT_FOR_RESULT) ;

       x = ADC_GetResult16(0) ;

       y = ADC_GetResult16(1) ;

       snprintf(str, STR_LEN, "%04X,%04X\n", x, y) ;

       UART_PutString(str) ;

       CyDelay(50) ; /* 50ms, 20 samples / seconds */

    }

}

======================

=== receiver ===

Note: I use my "tty_utils" utility to make receiving easier.

schematic

002-receiver-schematic.JPG

main.c

===================

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

#include "tty_utils.h"

void SYS_INIT(void)

{

    UART_Terminal_Start() ;

    tty_init() ; /* UART_Start() was called inside this*/

}

   

int main(void)

{

    uint16_t x, y ;

   

    CyGlobalIntEnable ; /* Enable global interrupts */

    SYS_INIT() ;

   

    splash("Receiver Test") ;

    for (;;) {

        if (get_line()) { /* receiver got a line of data */

            sscanf(str, "%hX,%hX", &x, &y) ;

           snprintf(str, STR_BUF_LEN, "Received: %04X %04X\n", x, y) ;

           UART_Terminal_PutString(str) ;

         }

    }

}

===================

Note:

You need to change pins according to your system.

This time projects are compile-able, but have not been tested as I have only 1 CY8CKIT-059.

moto

View solution in original post

0 Likes
25 Replies
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

Can my sample be some help?

tty_utils a utility sample for CLI type program

moto

0 Likes
Len_CONSULTRON
Level 9
Level 9
Beta tester 500 solutions authored 1000 replies posted

CaDu,

It may seem strange that there is a PutArray() but not a Get Array() for the UART, all UART data for Tx or Rx is by one byte at a time.

Using the GetRxBufferSize() and GetByte() API calls, you could create your own GetArray() function.  I haven't tested it but here's the start of such a function.  Note:  This function is designed as a blocking function.  If you need a non-blocking type, it would have to be significantly rewritten.

    /*******************************************************************************

    * Function Name: UART_GetArray

    ********************************************************************************

    *

    * Summary:

    *  Reads UART RX data and fills the array with the desired byte count.

    *    If the desired byte count not received this function may hang.

    *    THIS IS A BLOCKING FUNCTION.

    *

    * Parameters:

    *  uint8 rx_array[]

    *  uint8 rx_count        desired count of received data.

    *                        This count cannot exceed the rx_array size.

    *

    * Return:

    *  Rx status.

    *    If Rx status is 0 then the rx_array contains the desired data

    *    If Rx status is not 0 then the rx_array may contain partial data.

    *

    * Reentrant:

    *  No.

    *

    *******************************************************************************/

uint8 UART_GetArray(uint8 rx_array[], uint8 rx_count)

{

uint8 incoming_cnt;  

uint16 rx_data;

uint8 rx_status = 0;

  

    for(incoming_cnt = 0;  incoming_cnt < rx_count; incoming_cnt++)

    {

        while(UART_GetRxBufferSize() == 0);    // There is no data available in the Rx Buffer, then loop

        // Rx data available

        rx_data = UART_GetByte();

        rx_array[incoming_cnt] = (uint8)(rx_data & 0xFF);    // strip out incoming data and put in array

        rx_status = rx_data >> 8;                    // strip out potential error status

        if(rx_status != 0) break;    // break out of for() if error occurred.

    }

    return(rx_status);

}

// code frag in application

#define SZ_OF_EXPECTED_RESPONSE 2

uint8 rcvd_data[SZ_OF_EXPECTED_RESPONSE];

void Your_App()

{

uint8 rx_error;

...

    rx_error = UART_GetArray(rcvd_data, sizeof(rcvd_data));

    if(rx_error) Fault_Recovery()

...

}

Because this is a blocking function, if you do not receive the requested number of bytes, the function will hang.  You can modify the code to have a max timeout to prevent a "hang".  This is probably preferred.

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes

Hi,

I will attempt this code and give you feedback on whether it worked.

0 Likes

Hey, the code did not work.

0 Likes

CaDu,

Sorry it didn't work.  Are you willing to share your project with the forum?  It's possible if we can reproduce the problem, we can solve it.

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes

Well the code I had written for the receiver was pretty much just what you gave me.

Another question, the Rx_GetBufferSize commands should return the number of bytes being sent correct? Because whenever I read it and send it to the UART to be reprinted, it returns a 1 (Which should actually be a 2).

0 Likes

CaDu,

Rx_GetBufferSize()  only returns the number of bytes received not transmitted.  If you transmit 2 bytes on one end using PutArray(), you will receive two bytes at the other end.  However, if you use Rx_GetBufferSize() often, you will get a count of 1 byte twice.  Remember, the UART component is a serial data device.  It sends one bit of one byte at a time.  If the other end (Rx-side) is constantly reading the incoming data, it will see ONE BYTE at a time therefore giving you the Rx_GetBufferSize() = 1.  To receive two bytes, you will see the Rx_GetBufferSize() = 1 twice.

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes

I am not reading the number of bytes at the receiver, I am reading them at the transmitter. That being said, how would I read the two bytes if RX is constantly replacing the current byte with another one?

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

> That being said, how would I read the two bytes if RX is constantly replacing the current byte with another one?

I thought my program can take care of that situation.

But meantime, I was wondering how we could detect separation of each data?

Isn't there any delimiter or time space between the 2-bytes data?

moto

0 Likes

There is no delimiter, I am sending the array from the transmitter with the following code:

#include "project.h"

#include<math.h>

#include <stdio.h>

char string[20];

uint8_t X;

uint8_t Y;

uint8_t Data_Out[3];

void init_hardware(void)

{

   

    CyGlobalIntEnable;

    UART_Start();

    ADC_SAR_0_Start();

    ADC_SAR_1_Start();     

  

   

}

int main(void)

{

   

    init_hardware() ;

    ADC_SAR_0_StartConvert();

    ADC_SAR_1_StartConvert();

   

       

    for(;;)

    {

       

        X=ADC_SAR_0_GetResult8();

        Y=ADC_SAR_1_GetResult8();

        Data_Out[0]=X;

        Data_Out[1]=Y;

       

        //UART_WriteTxData(X);

        UART_PutArray(Data_Out,2);

      

               

    }

}

Your code managed to read one of the bytes, but for some reason both elements were being populated with the same byte.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

So how fast must you send data?

Your transmitter loop seems to be very fast since it does not have any delay between UART_PutArray().

As my program is using PutString() to display the value, it won't be able to catch up with your transmitter.

And IMHO, dropping a byte or two would be quite popular with radio, so the receiver needs to have a chance to re-sync.

If by accident one byte is dropped, the values will be always Y,X, until next drop,  so I put delimiter X,Y,D.

As I wrote in my previous response, you are free to design any format.

But if you decide to send pure binary stream, which is continuous UART_PutArray(),

my poor capability can not come up with a solution to handle it correctly in the receiver side.

moto

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

If you don't mind modifying the line of your transmitter program

        UART_PutArray(Data_Out,2);

with

        snprintf(string, 20, "%04X,%04X\n", x, y) ;

        UART_PutString(string) ;

       CyDelay(100) ;

or

       snprintf(string, 20, "%04X,%04X\n", x, y) ;

      UART_PutArray(string, strlen(string)) ;

       CyDelay(100) ;

Then I think that the receiver part of my previous post should work (fingers crossed).

Note: Please use P3[6] and P3[7] as receiver's rx and tx.

moto

0 Likes
lock attach
Attachments are accessible only for community members.
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

So, I modified my sample and made a couple of projects.

=== transmitter ===

schematic

000-transmitter-schematic.JPG

ADC config

Note: In my experience, if I used Fee running, I got surprising value(s) time to time.

So I use Software trigger.

If you need to use a couple of ADCs, probably you need to use Hardware trigger for both ADCs

and feed trigger from another component like ControlReg to both socs.

001-ADC_config.JPG

main.c

======================

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

#define STR_LEN 32

char str[STR_LEN+1] ; /* print buffer */

void init_hardware(void)

{

    CyGlobalIntEnable ; /* Enable global interrupts */    

    UART_Terminal_Start() ;

    UART_Start() ;

    ADC_Start() ;

}

   

int main(void)

{

    uint16_t x, y ;

  

    init_hardware() ;

  

    for (;;) {

       ADC_StartConvert() ;

       ADC_IsEndConversion(ADC_WAIT_FOR_RESULT) ;

       x = ADC_GetResult16(0) ;

       y = ADC_GetResult16(1) ;

       snprintf(str, STR_LEN, "%04X,%04X\n", x, y) ;

       UART_PutString(str) ;

       CyDelay(50) ; /* 50ms, 20 samples / seconds */

    }

}

======================

=== receiver ===

Note: I use my "tty_utils" utility to make receiving easier.

schematic

002-receiver-schematic.JPG

main.c

===================

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

#include "tty_utils.h"

void SYS_INIT(void)

{

    UART_Terminal_Start() ;

    tty_init() ; /* UART_Start() was called inside this*/

}

   

int main(void)

{

    uint16_t x, y ;

   

    CyGlobalIntEnable ; /* Enable global interrupts */

    SYS_INIT() ;

   

    splash("Receiver Test") ;

    for (;;) {

        if (get_line()) { /* receiver got a line of data */

            sscanf(str, "%hX,%hX", &x, &y) ;

           snprintf(str, STR_BUF_LEN, "Received: %04X %04X\n", x, y) ;

           UART_Terminal_PutString(str) ;

         }

    }

}

===================

Note:

You need to change pins according to your system.

This time projects are compile-able, but have not been tested as I have only 1 CY8CKIT-059.

moto

0 Likes

The code I am currently trying is the following:

/* ========================================

*

* Copyright YOUR COMPANY, THE YEAR

* All Rights Reserved

* UNPUBLISHED, LICENSED SOFTWARE.

*

* CONFIDENTIAL AND PROPRIETARY INFORMATION

* WHICH IS THE PROPERTY OF your company.

*

* ========================================

*/

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

uint8_t Bytes_In[2];

uint8_t Data_In;

CY_ISR(RX_Handler){

   

    int i = 0;

   

    for(i=0; i<=1;i++){

        Bytes_In= UART_GetByte();

    }

   

    UART_ClearRxBuffer();

   

}

void SYS_INIT(void){

   

    UART_Start();

   

    UART_Terminal_Start();

   

    RX_ISR_Start();

       

}

int main(void)

{

    CyGlobalIntEnable; /* Enable global interrupts. */

    SYS_INIT();

   

    RX_ISR_StartEx(RX_Handler);

   

    UART_SetRxInterruptMode(UART_RX_STS_FIFO_NOTEMPTY);

   

    for(;;)

    {

                    

        UART_Terminal_WriteTxData(Bytes_In[1]);

       

        CyDelay(1000);

       

       

              

    }

}

/* [] END OF FILE */

0 Likes
lock attach
Attachments are accessible only for community members.
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

I modified your code for CY8CKIT-059.

Schematic

002-schematic.JPG

UART_Terminal

003-UART_Terminal_1.JPG

004-UART_Terminal_2.JPG

UART

005-UART_1.JPG

006-UART_2.JPG

Pins

007-Pins.JPG

main.c

===============

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

#define STR_LEN 32

#define NUM_TO_RECEIVE 2

uint8_t Bytes_In[NUM_TO_RECEIVE] ;

volatile int in_index = 0 ;

volatile int data_received = 0 ;

char str[STR_LEN+1] ; /* print buffer */

uint8_t Data_in ;

CY_ISR(RX_Handler)

{

    while(UART_GetRxBufferSize()) {

        Bytes_In[in_index] = UART_GetByte() ;

        in_index++ ;

        if (in_index >= NUM_TO_RECEIVE) {

            data_received = 1 ;

            in_index = 0 ;

            break ;

        }

    }

    UART_ReadRxStatus() ; // this clears interrupt flag

}

void SYS_INIT(void)

{

    UART_Terminal_Start() ;

    // UART_SetRxInterruptMode(UART_RX_STS_FIFO_NOTEMPTY); // this should come before StartEx()

     RX_ISR_StartEx(RX_Handler);

   

    UART_Start() ;

}

void cls(void)

{

    UART_Terminal_PutString("\033c") ; /* reset */

    CyDelay(100) ;

    UART_Terminal_PutString("\033[2J") ; /* clear screen */

    CyDelay(100) ;

}

void splash(void)

{

    cls() ;

    UART_Terminal_PutString("UART 2Bytes Test ") ;

    snprintf(str, STR_LEN, "(%s %s)\n", __DATE__, __TIME__) ;

    UART_Terminal_PutString(str) ;

}

   

int main(void)

{

    CyGlobalIntEnable ; /* Enable global interrupts */

     SYS_INIT() ;

   

    splash() ;

    for (;;) {

        if (data_received) {

            snprintf(str, STR_LEN, "%02X%02X\n", Bytes_In[0], Bytes_In[1]) ;

            UART_Terminal_PutString(str) ;

            data_received = 0 ;

        }

    }

}

===============

TeraTerm log UART (local echo on)

001-UART.JPG

TeraTerm log UART Terminal

000-UART_Terminal.JPG

moto

0 Likes

Hey, thank you, I tried the code, however it does not seem to be reading the incoming data from the joystick correctly.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

Hi,

> Hey, thank you, I tried the code,

> however it does not seem to be reading the incoming data from the joystick correctly.

I won't be surprised as I did not know the data format your joystick generates.

In case if you connect your joystick to my program, what was the outcome?

(Note: Please configure the baud rate etc to match the device)

And/or is there data format specification of the joystick? (at least model number/name?)

moto

0 Likes

The baud rate is the same, I just changed the code on mine since the top designs were the same. The Joystick is a simple potentiometer being read into an ADC and writeen into the UART. I am able to send the data by itself (instead of arrays). It is just that I need to send both X and Y values of the ADC readings.

0 Likes
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

So if I understand correct

(1) Transmitter

(1.1) Read 2 potentiometer values (X and Y) from ADC

(1.2) Write them to UART

(2) Receiver
(2.1) read 2 data from UART

...

Then what is the data you write to UART?

I think each value should be 12bit or so, right?

moto

0 Likes
lock attach
Attachments are accessible only for community members.
MotooTanaka
Level 9
Level 9
Distributor - Marubun (Japan)
First comment on blog Beta tester First comment on KBA

So I understand that this is a busy morning.. 😉

IMHO, you must define the format between transmitter and receiver.

Only sending stream of  binary data will be very difficult for the receiver to understand.

So in the following sample I assumed the transmitter format is

<Hex Value X>,<Hex Value Y>'\n'            i.e. "0120,1212\n"

This makes it easy for the receiver to detect the end of record, which is a new line char '\n'

(You can design any format as far as you can or are willing to manage.)

I modified my sample using my tty utils and added a transmitter emulator,

so the schematic is now

001-schematic.JPG

Pin list

002-pin.JPG

main.c

==========================

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

#include "tty_utils.h"

#define SEND_BUF_LEN 16

char send_buf[SEND_BUF_LEN] ;

int data_sent = 0 ;

void SYS_INIT(void)

{

UART_Terminal_Start() ;

    tty_init() ; /* UART_Start() was called inside this*/

   

    transmitter_Start() ;

}

   

int main(void)

{

    uint16_t t_x = 0 ;

    uint16_t t_y = 1023 ;

    uint16_t r_x, r_y ;

   

CyGlobalIntEnable ; /* Enable global interrupts */

SYS_INIT() ;

   

    splash("Receiver Test") ;

for (;;) {

    // emulate the transmitter   

        if (data_sent == 0) {

            t_x = (t_x + 1) % 2048 ; /* emulated ADC value */

            t_y = (t_y + 3) % 2048 ; /* emulated ADC value */

            snprintf(send_buf, SEND_BUF_LEN, "%04X,%04X\n", t_x, t_y) ;

            transmitter_PutString(send_buf) ;

            print("Transmitted: ") ;

            print(send_buf) ;

            data_sent = 1 ; /* since we use only 1 cpu here, let it wait */

             CyDelay(1000) ; /* to slower the terminal output */

        }

    // emulate the reciver   

        if (get_line()) { /* receiver got a line of data */

            sscanf(str, "%hX,%hX", &r_x, &r_y) ;

            snprintf(str, STR_BUF_LEN, "Received: %04X %04X\n", r_x, r_y) ;

            UART_Terminal_PutString(str) ;

            data_sent = 0 ;

        }

    }

}

==========================

Tera Term log

000-TeraTerm_log.JPG

I used CY8CKIT-059, to test this program connect

P3[7] and P1[6]

P3[6] and P1[7]

I hope this can be an idea for your issue.

moto

0 Likes

CaDu,

I see multiple problems with your code.

CY_ISR(RX_Handler){

    int i = 0;

 

    for(i=0; i<=1;i++){

        Bytes_In= UART_GetByte(); // Problem #1: You're assuming you will read two bytes from the UART Rx.  There is 100% chance with this routine you will receive

                                                           // exactly one byte of valid data and the other byte will be '\0' (null character).

                                                            // I think you are assuming that the two bytes you are sending by the transmitter will be received with one ISR from the Rx.

                                                            // If you process this correctly, you should receive two calls to this ISR.  One for each byte from the transmitter.

    }

    UART_ClearRxBuffer();               // Note:  This statement is most likely unnecessary.

}

int main(void)

{

    CyGlobalIntEnable; /* Enable global interrupts. */

     SYS_INIT();

    RX_ISR_StartEx(RX_Handler);

    UART_SetRxInterruptMode(UART_RX_STS_FIFO_NOTEMPTY);

  

    for(;;)

    {

        UART_Terminal_WriteTxData(Bytes_In[1]);          // Problem #2: Based on Problem #1, the '\0' byte would be the only one pushed to the Terminal.

        CyDelay(1000);

    }

}

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes

How about the following?:

Here I am setting it to interrupt on RX, which means that for every interrupt, the index will increase, and write that byte inside the the buffer.

* ========================================

*

* Copyright YOUR COMPANY, THE YEAR

* All Rights Reserved

* UNPUBLISHED, LICENSED SOFTWARE.

*

* CONFIDENTIAL AND PROPRIETARY INFORMATION

* WHICH IS THE PROPERTY OF your company.

*

* ========================================

*/

#include "project.h"

#include "stdio.h"

#include "stdlib.h"

#include "string.h"

#include "math.h"

#define MSG_LENGTH  2

int i = 0;

int status =1;

uint8_t Bytes_In[2];

uint8_t Bytes;

uint8_t Data_In;

uint8_t Buffer;

CY_ISR(RX_Handler){

    i = 0;

    Bytes_In=UART_GetByte();

    i++;

    if(i>=2) i = 0;

    RX_ISR_ClearPending();

}

void SYS_INIT(void){

    UART_Start();

    UART_Terminal_Start();

    RX_ISR_Start();

        

}

int main(void)

{

    CyGlobalIntEnable; /* Enable global interrupts. */

    SYS_INIT();

    RX_ISR_StartEx(RX_Handler);

    

  

    for(;;)

    {

    

        Buffer=UART_GetRxBufferSize();

    

        UART_Terminal_WriteTxData(Bytes_In[0]);

    

        //for(i=0;i<=1158000;i++);

      

    

    }

}

/* [] END OF FILE */

0 Likes

CaDu,

Your changes are better but still have a few issues.

uint8 new_byte = 0;     // This is a flag to the main() loop to know when a new byte comes in.

CY_ISR(RX_Handler){

    i = 0;

    Bytes_In=UART_GetByte();

// add this next code line

     new_byte = 1;          // indicate that a new byte is available.

// end of added code

    i++;

    if(i>=2) i = 0;

    RX_ISR_ClearPending();

}

#include "stdio.h"        // Add this line to allow snprintf() functions

char tstr[20];           // Temporary string allocation

int main(void)

{         

    CyGlobalIntEnable; /* Enable global interrupts. */

    SYS_INIT();

    RX_ISR_StartEx(RX_Handler);

    for(;;)

    {

        Buffer=UART_GetRxBufferSize();    // I'm not sure what this is used for.

// Replacement code for your WriteTxData().  Using bytes might dump unprintable characters to the terminal.

// The replacement will format the bytes into human-readable hex characters.

          if(new_byte > 0)

          {   // A new byte is available

               new_byte = 0;     // reset the new byte flag.

               if(i == 1)

               {  // print the first byte of two bytes

                    snprintf(tstr, sizeof(tstr), "%02X:", Bytes_In[0]);     // format the hex representation of the input byte.

                    UART_Terminal_PutString(tstr);     // dump the formatted string to the terminal.

               }

               else if(i > 1)

               {   // print the second byte of two bytes and place a CRLF to advance to a new line.

                    snprintf(tstr, sizeof(tstr), "%02X\n\r", Bytes_In[1]);     // format the hex representation of the input byte.

                    UART_Terminal_PutString(tstr);     // dump the formatted string to the terminal

               }

          }

     }

}

Question:  You are receiving a stream of data paired as two-bytes.    How do you know which byte you receive is the first byte and which the second?

Are you using a a two-byte burst then there is a delay in time at the Tx end?

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes

HI, about knowing which bit is the first, that I do not know how to specify yet.

0 Likes

CaDu,

In a stream of data where the order of data matters, you need to define a Start-Of-Header (SOH) and in some cases a End-Of-Header (EOH).

If the stream of data is ASCII bytes to a terminal, you may not need a SOH or EOH because as soon as you make the connection to both ends the stream shows up on the terminal.  The human brain then deciphers the beginning and end of data.

However in your case, you have a paired 2 bytes of data where knowing what is the first byte and the other the second byte.

There many ways to define a SOH and if needed a EOH.

One simple way is on the transmit end to place a time delay (let's call it 10ms) between the previous 2-byte set and the next 2-byte set.   Also on the transmit end, the 2-bytes of data have virtually no delay between the first and second bytes.

On the receiving end, you would need to look for the time gap (in this example 10ms).  This is the SOH synchronization point to know when you are about to receive the first byte.

Time delay

First Byte

Second Byte

Time delay

First Byte

Second Byte

Time delay

First Byte

Second Byte

Time delay

0x32

0x45

0xC2

0x02

0x22

0x28

In the above solution the time delay to the next set of data is the EOH to the just completed 2-byte set.

A second solution is by adding an addition byte in the data stream.  You have to determine with your data if there is a byte value that neither the first byte or second byte can NEVER be.  A possible example is the 0xFF byte.  This byte value would be the SOH also called the SYNC value.

If this is the case you can send the 3-byte data with the first byte being the SOH, the second being the first byte of data and the third being the second byte of data.

Every time you receive the SYNC value, this is the SOH and you know how to re-SYNC the data to know when to expect the first then the second bytes of data.  In this case the SOH is the implied EOH for the previous data set.  Additionally the data does'nt require a time delay and the bytes can be sent potentially faster.

SOH (SYNC)

First Byte

Second Byte

SOH (SYNC)

First Byte

Second Byte

SOH (SYNC)

First Byte

Second Byte

SOH (SYNC)

0xFF

0x32

0x45

0xFF

0xC2

0x02

0xFF

0x22

0x28

0xFF

As a last note, there are conditions in the data set where a specific EOH may be necessary.  Let's assume in your case it is not.

I hope this helps.  You express that the incoming data is "not correct" however you never provided examples of the incoming data along with what the expected data should be.  Therefore, moto and myself are making certain assumptions as best we can.

Len

Len
"Engineering is an Art. The Art of Compromise."
0 Likes