DataAvailable Question

I first used a serial port in RB 5.5 to read electric submeters. It has always been half-diplex - send a request and process the reply. Now I have been tasked to update the program so they can use a mesh network to read the meters. The mesh provider suggests that the old way will take a long time and that we should change to a full duplex model where we send out a bunch of requests and the replies come back in a random order depending on how many hops in the mesh are needed. The solution I am considering is to use the DataAvailable event to append the buffer to a string property (Responses) of my Connection class . Then a timer would process the data. As part of that process, it would remove the first reply from Responses. I am concerned that Responses could be corrupted if DataAvailable fired while Responses is being shortened.

My thought is to set a Busy property True just before removing the first 102 bytes from Responses, then setting Busy False immediately after. DataAvailable would then say If not Busy then Responses = Responses + me.ReadAll. My concern is that the Busy property might not be changed until the event completes and thus would do nothing.

It looks like your replies are all 102 bytes? In that case in the data avalaible event handler I would use lookahead to get the number of bytes available and if > 102 read the first 102 bytes into a reply and add that to an array. The replies would then be discrete and could be processed while receiving more replies

I agree with Wayne. In DataAvailable, simply snip off complete messages and append them to an array. In a Timer, process the first message in the array and exit (so you’re not blocking the DataAvailable events). Note that in DataAvailable you can have several different states:

  • an incomplete message
  • a complete message
  • a complete message and a partial message
  • more than one message

You’ll have to code to handle any of the above.

This needs more emphasis: SerialConnection.LookAhead

DataAvailable means that data was just appended to the internal buffer. Use LookAhead() to peek at the buffer and Read() to remove bytes from it.

Great answers. Thank you all. My first thought was that it would be a nightmare whenever a random extra byte appeared before a good reply. But when that happens, I will be able to determine the start position of the first byte of the message and get the missing bytes from the next item in the array.