Options
Processing Received Strings
Hi all I am having trouble with a certain system below is an example of the string being received (in netlinx string format)
"02,85,'UNIT-5 ALARM',03"
After the above string there is a whole heap of other junk that I dont want, also the above string wont always be the same, there are other types of alarms ect so the char length will vary.
What I want to do is use 85h as my starting delimeter then store all char's to a variable until 03h is received, is it possible, im sure it is, im just not seeing it.
Any help would be much appreciated, thanks guys
"02,85,'UNIT-5 ALARM',03"
After the above string there is a whole heap of other junk that I dont want, also the above string wont always be the same, there are other types of alarms ect so the char length will vary.
What I want to do is use 85h as my starting delimeter then store all char's to a variable until 03h is received, is it possible, im sure it is, im just not seeing it.
Any help would be much appreciated, thanks guys
0
Comments
I love protocols that use a start and end character. First, tokenize your buffer by using something like
sToken=REMOVE_STRING(sBuffer, 3, 1) ;
This will give you a string ending with the 03, and remove it from the original buffer. Chances are more than likely that it's going to start with 02, but if it doesn't, simply do a FIND for the 02, and lop the extra off the token with something like this:
sToken = RIGHT_STRING(sToken, (LENGTH_STRING(sToken) - FIND_STRING(sToken, 2, 1))) ;
That will give you everything after the 02 and including the terminating 03. You can break it down further as necessary.
Just another way to skin the cat
Jeff
I would initially just look for ETX ( 3 ) and then once that's found I would check if a STX also preceded it. Otherwise I'd ignore the RX but dump the content if I don't receive the ETX after a specified time. I almost always use a while just in case more then 1 complete string is ever received and WTF even if it isn't possible there's no real difference between using the if or while in this case.
Plus if you're new to parsing or even if you aren't send_string 0's are your friend. So use them and comment them out when the bugs are worked out.
I usually use this code for these situations; I don't like using CREATE_BUFFER related commands.
(Previously defined)
DEFINE_CONSTANT
INTEGER MAX_STRING_SIZE = 50 // or the size near a normal feedback packet from the device
INTEGER MAX_BUFFER_SIZE = 200 // something a bit larger, in case multiple packets arrive
CHAR STX[] = "$02"
CHAR ETX[] = "$03"
DEFINE_VARIABLE
CHAR Device_RX[MAX_STRING_SIZE ]
CHAR Device_Buffer[MAX_BUFFER_SIZE ]
DATA_EVENT[Device]
{
STACK_VAR INTEGER Buf_Len,RX_Len
STACK_VAR INTEGER stx_pos,etx_pos
STACK_VAR CHAR sData[MAX_STRING_SIZE]
Device_RX = Data.Text
Buf_Len = LENGTH_STRING(Device_Buffer)
Rx_Len = LENGTH_STRING(Device_RX)
IF (Buf_Len + Rx_Len < MAX_BUFFER_SIZE) Device_Buffer= "Device_Buffer,Device_RX"
ELSE Device_Buffer= "RIGHT_STRING(Device_Buffer,MAX_BUFFER_SIZE-Rx_Len ),Device_RX"
// This essentially makes a buffer that shifts older data making space for new data if it is full
// Parsing
stx_pos = FIND_STRING(sData,STX,1)
IF(stx_pos)
{
sData = REMOVE_STRING(Device_Buffer,ETX,stx_pos+1)
etx_pos = LENGTH_STRING(sData)
WHILE(etx_pos)
{
... (Parse and process)
// loop back to while
stx_pos = FIND_STRING(sData,STX,1)
IF(stx_pos)
{
sData = REMOVE_STRING(Device_Buffer,ETX,stx_pos+1)
etx_pos = LENGTH_STRING(sData)
}
ELSE etx_pos = 0 // exits while loop if there is no STX
}
This code should give all of the necessary positions to parse and work with any feedback
The circular buffer protects agains garbage, noise and data corruption by always renewing the data, and will never become "locked" since it naturally cleans itself when new data overwrites old data. This also allows for truncated packets to be processed after completing a packet - even if it is truncated among several different packets
The while loop ensures that all pckets are processed, even if multiple processable strings arrive in a single packet, as somebody pointed out before.
finally, the REMOVE_STRING and position for STX and ETX are done twice to avoid making multiple string searches in the while loop, as the code with the while posted before did. This is to optimize cpu cycle efficiency, since in large programs each cpu cycle counts for not bogging down a program....