[chbot] HEX and ANSII ATMEGA and Delphi

Robin Gilks robin at gilks.org
Sun Oct 25 03:43:11 GMT 2020


> Wallace
>
> Have you considered Google Protocol buffers? They use an efficient 'on the
> wire' protocol, are very easy to work with and there are libraries you can
> use:
>
>    - For Pascal - https://github.com/lalexs75/protobuf-fpc
>    - For C - https://github.com/nanopb/nanopb
>
> I used protocol buffers very successfully to send data between 2 micros,
> the best part of it all was how easy it is to expand a message while
> maintaining backward compatibility.
>
> I also used a version of SLIP encoding in another project, also very easy
> to use and low overhead -> https://tools.ietf.org/html/rfc1055
>
> Stuart
>

I second the idea of using SLIP (although maybe adjusted to suit the
situation).
The last time I used it was I wanted to move large blocks of binary data
interleaved with printable data. The default is printable data, no special
processing required (other than a terminator).
The SLIP variant I came up with uses 4 printable characters for the FEND,
FESC, TFEND and TFESC of the protocol and the FEND was chosen to be a
character that does not normally appear in the stream (in my case '@').
This means it is all printable until I see a '@' whereupon its binary
until I see another '@' character. The 'escape' and 'transposed'
characters allow the '@' character to be embedded in the data (it is just
another binary character after all!!). Encoding is really simple:

// my slip delimiter characters
#define FEND     '@'       /** frame end       */
#define FESC     '#'       /** frame escape    */
#define TFEND    '$'       /** transposed fend */
#define TFESC    '%'       /** transposed fesc */

   offset = 0;
   output[offset++] = FEND;
   for (i = 0; i < length; i++)
   {
      if (input[i] == FEND)
      {
         output[i + offset++] = FESC;
         output[i + offset] = TFEND;
      }
      else if (input[i] == FESC)
      {
         output[i + offset++] = FESC;
         output[i + offset] = TFESC;
      }
      else
      {
         output[i + offset] = input[i];
      }
   }
   output [i + offset++] = '@'
// offset now tells you how much the data has grown by


Decoding could use a state machine where the states are SLIP_IDLE (not in
SLIP), SLIP_DATA (pass data from input to output) and SLIP_TRANSPOSE (seen
a FESC, decode the following transpose character).

>From what little I know of Delphi, I'd use an unsigned variable format
('word' I recall is unsigned 16 bits), pass over hex characters with a
non-hex character separator ('|' shouldn't confuse it!) and if you do want
a signed value then assigning to an equal sized signed variable is
equivalent to a cast (maybe use the 'as' keyword?).


-- 
Robin Gilks zl3rob/g8ecj
Internet: g8ecj at gilks.org    http://www.gilks.org






More information about the Chchrobotics mailing list