CmdMessenger 3.0 CmdMessenger is a messaging library for the Arduino Platform. It has uses the serial port as its transport layer

- Main Page
- Classes
- Files

- File List

D:/My Documents/Github/Arduino-Code-and-Libraries/Libraries/CmdMessenger/CmdMessenger.h

    00001 /*
    00002   CmdMessenger - library that provides command based messaging
    00003
    00004     Permission is hereby granted, free of charge, to any person obtaining
    00005     a copy of this software and associated documentation files (the
    00006     "Software"), to deal in the Software without restriction, including
    00007     without limitation the rights to use, copy, modify, merge, publish,
    00008     distribute, sublicense, and/or sell copies of the Software, and to
    00009     permit persons to whom the Software is furnished to do so, subject to
    00010     the following conditions:
    00011
    00012     The above copyright notice and this permission notice shall be
    00013     included in all copies or substantial portions of the Software.
    00014
    00015     THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
    00016     EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
    00017     MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
    00018     NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
    00019     LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
    00020     OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
    00021     WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
    00022
    00023
    00024  */
    00025
    00026 #ifndef CmdMessenger_h
    00027 #define CmdMessenger_h
    00028
    00029 #include <inttypes.h>
    00030 #if ARDUINO >= 100
    00031 #include <Arduino.h>
    00032 #else
    00033 #include <WProgram.h>
    00034 #endif
    00035
    00036 //#include "Stream.h"
    00037
    00038 extern "C"
    00039 {
    00040   // callback functions always follow the signature: void cmd(void);
    00041   typedef void (*messengerCallbackFunction) (void);
    00042 }
    00043
    00044 #define MAXCALLBACKS        50   // The maximum number of commands   (default: 50)
    00045 #define MESSENGERBUFFERSIZE 64   // The maximum length of the buffer (default: 64)
    00046 #define DEFAULT_TIMEOUT     5000 // Time out on unanswered messages. (default: 5s)
    00047
    00048 // Message States
    00049 enum
    00050 {
    00051   kProccesingMessage,            // Message is being received, not reached command separator
    00052   kEndOfMessage,                 // Message is fully received, reached command separator
    00053   kProcessingArguments,          // Message is received, arguments are being read parsed
    00054 };
    00055
    00056 class CmdMessenger
    00057 {
    00058 private:
    00059
    00060   // **** Private variables ***
    00061
    00062   bool    startCommand;            // Indicates if sending of a command is underway
    00063   uint8_t lastCommandId;            // ID of last received command
    00064   uint8_t bufferIndex;              // Index where to write data in buffer
    00065   uint8_t bufferLength;             // Is set to MESSENGERBUFFERSIZE
    00066   uint8_t bufferLastIndex;          // The last index of the buffer
    00067   char ArglastChar;                 // Bookkeeping of argument escape char
    00068   char CmdlastChar;                 // Bookkeeping of command escape char
    00069   bool pauseProcessing;             // pauses processing of new commands, during sending
    00070   bool print_newlines;              // Indicates if \r\n should be added after send command
    00071   char buffer[MESSENGERBUFFERSIZE]; // Buffer that holds the data
    00072   uint8_t messageState;             // Current state of message processing
    00073   bool dumped;                      // Indicates if last argument has been externally read
    00074   bool ArgOk;                       // Indicated if last fetched argument could be read
    00075   char *current;                    // Pointer to current buffer position
    00076   char *last;                       // Pointer to previous buffer position
    00077   char prevChar;                    // Previous char (needed for unescaping)
    00078   Stream *comms;                    // Serial data stream
    00079
    00080   char command_separator;           // Character indicating end of command (default: ';')
    00081   char field_separator;             // Character indicating end of argument (default: ',')
    00082   char escape_character;            // Character indicating escaping of special chars
    00083
    00084   messengerCallbackFunction default_callback;            // default callback function
    00085   messengerCallbackFunction callbackList[MAXCALLBACKS];  // list of attached callback functions
    00086
    00087   // ****** Private functions ******
    00088
    00089   // **** Initialize ****
    00090
    00091   void init (Stream & comms, const char fld_separator, const char cmd_separator, const char esc_character);
    00092   void reset ();
    00093
    00094   // **** Command processing ****
    00095
    00096   uint8_t processAndCallBack (int serialByte);
    00097   uint8_t processLine (int serialByte);
    00098   void handleMessage ();
    00099
    00100   bool blockedTillReply (int timeout = DEFAULT_TIMEOUT, int ackCmdId = 1);
    00101   bool CheckForAck (int AckCommand);
    00102   bool processAndWaitForAck (int serialByte, int AckCommand);
    00103
    00104   // **** Command sending ****
    00105
    00109   template < class T >
    00110     void writeBin (const T & value)
    00111   {
    00112     const byte *bytePointer = (const byte *) (const void *) &value;
    00113     for (unsigned int i = 0; i < sizeof (value); i++)
    00114       {
    00115         printEsc (*bytePointer);
    00116         *bytePointer++;
    00117       }
    00118   }
    00119
    00120   // **** Command receiving ****
    00121
    00122   int findNext (char *str, char delim);
    00123
    00127   template < class T >
    00128     T readBin (char *str)
    00129   {
    00130     T value;
    00131     unescape (str);
    00132     byte *bytePointer = (byte *) (const void *) &value;
    00133     for (unsigned int i = 0; i < sizeof (value); i++)
    00134       {
    00135         *bytePointer = str[i];
    00136         *bytePointer++;
    00137       }
    00138     return value;
    00139   }
    00140
    00141   // **** Escaping tools ****
    00142
    00143   char *split_r (char *str, const char delim, char **nextp);
    00144   bool isEscaped (char *currChar, const char escapeChar, char *lastChar);
    00145
    00146   void printEsc (char *str);
    00147   void printEsc (char str);
    00148
    00149 public:
    00150
    00151   // ****** Public functions ******
    00152
    00153   // **** Initialization ****
    00154
    00155   CmdMessenger (Stream & comms, const char fld_separator = ',',
    00156                 const char cmd_separator = ';',
    00157                 const char esc_character = '/');
    00158
    00159   void printLfCr (bool addNewLine=true);
    00160   void attach (messengerCallbackFunction newFunction);
    00161   void attach (byte msgId, messengerCallbackFunction newFunction);
    00162
    00163   // **** Command processing ****
    00164
    00165   void feedinSerialData ();
    00166   bool next ();
    00167   bool available ();
    00168
    00169   uint8_t CommandID ();
    00170
    00171   // ****  Command sending ****
    00172
    00177   template < class T >
    00178     bool sendCmd (int cmdId, T arg, bool reqAc = false, int ackCmdId = 1,
    00179                   int timeout = DEFAULT_TIMEOUT)
    00180   {
    00181     if (!startCommand) {
    00182         sendCmdStart (cmdId);
    00183         sendCmdArg (arg);
    00184         return sendCmdEnd (reqAc, ackCmdId, timeout);
    00185     }
    00186   }
    00187
    00192   template < class T >
    00193     bool sendBinCmd (int cmdId, T arg, bool reqAc = false, int ackCmdId = 1,
    00194                      int timeout = DEFAULT_TIMEOUT)
    00195   {
    00196     if (!startCommand) {
    00197         sendCmdStart (cmdId);
    00198         sendCmdBinArg (arg);
    00199         return sendCmdEnd (reqAc, ackCmdId, timeout);
    00200     }
    00201   }
    00202
    00203   // **** Command sending with multiple arguments ****
    00204
    00205   void sendCmdStart (int cmdId);
    00206   void sendCmdEscArg (char *arg);
    00207   void sendCmdfArg (char *fmt, ...);
    00208   bool sendCmdEnd (bool reqAc = false, int ackCmdId = 1, int timeout = DEFAULT_TIMEOUT);
    00209
    00214   template < class T > void sendCmdArg (T arg)
    00215   {
    00216     if (startCommand)
    00217       {
    00218         comms->print (field_separator);
    00219         comms->print (arg);
    00220       }
    00221   }
    00222
    00227   template < class T > void sendCmdArg (T arg, int n)
    00228   {
    00229     if (startCommand)
    00230       {
    00231         comms->print (field_separator);
    00232         comms->print (arg, n);
    00233       }
    00234   }
    00235
    00240   template < class T > void sendCmdBinArg (T arg)
    00241   {
    00242     if (startCommand)
    00243       {
    00244         comms->print (field_separator);
    00245         writeBin (arg);
    00246       }
    00247   }
    00248
    00249   // **** Command receiving ****
    00250   bool readBoolArg();
    00251   int readIntArg ();
    00252   char readCharArg ();
    00253   float readFloatArg ();
    00254   char *readStringArg ();
    00255   void copyStringArg (char *string, uint8_t size);
    00256   uint8_t compareStringArg (char *string);
    00257
    00261   template < class T > T readBinArg ()
    00262   {
    00263     if (next ())
    00264       {
    00265         dumped = true;
    00266         return readBin < T > (current);
    00267       }
    00268   }
    00269
    00270   // **** Escaping tools ****
    00271
    00272   void unescape (char *fromChar);
    00273 };
    00274 #endif