Experiment of serial command protocol

Dependencies:   RingBuffer SerialInterfaceProtocol duinotech_16x2_LCD mbed

You can edit this area

Committer:
rba90
Date:
Thu Jun 16 03:52:01 2016 +0000
Revision:
3:0c4aa3cec685
Parent:
2:54932809c7b2
1. Update definition for checksum; 2. Add more examples of SIP

Who changed what in which revision?

UserRevisionLine numberNew contents of line
rba90 0:2ba6a9f316b6 1 #include "CommandPacket.h"
rba90 0:2ba6a9f316b6 2 #include "mbed.h"
rba90 0:2ba6a9f316b6 3
rba90 0:2ba6a9f316b6 4 #define CHECKSUM_DEBUG
rba90 0:2ba6a9f316b6 5
rba90 0:2ba6a9f316b6 6 uint8_t generate_checksum(uint8_t *data, uint8_t length, uint8_t offset)
rba90 0:2ba6a9f316b6 7 {
rba90 0:2ba6a9f316b6 8 uint8_t s = 0;
rba90 0:2ba6a9f316b6 9
rba90 0:2ba6a9f316b6 10 if (data)
rba90 0:2ba6a9f316b6 11 {
rba90 0:2ba6a9f316b6 12 // take the sum of all data bytes preceding checksum field
rba90 0:2ba6a9f316b6 13 for(uint8_t i = 0; i < length; i++)
rba90 0:2ba6a9f316b6 14 {
rba90 0:2ba6a9f316b6 15 s += data[i + offset];
rba90 0:2ba6a9f316b6 16 }
rba90 0:2ba6a9f316b6 17
rba90 0:2ba6a9f316b6 18 // calculate two's complement of the remainder
rba90 0:2ba6a9f316b6 19 s = 0xff - s + 1;
rba90 0:2ba6a9f316b6 20 }
rba90 0:2ba6a9f316b6 21
rba90 0:2ba6a9f316b6 22 return s;
rba90 0:2ba6a9f316b6 23 }
rba90 0:2ba6a9f316b6 24
rba90 0:2ba6a9f316b6 25 uint8_t hexchar_to_uint8(uint8_t ch)
rba90 0:2ba6a9f316b6 26 {
rba90 0:2ba6a9f316b6 27 uint8_t val = 0;
rba90 0:2ba6a9f316b6 28
rba90 0:2ba6a9f316b6 29 if (ch >= '0' && ch <= '9')
rba90 0:2ba6a9f316b6 30 {
rba90 0:2ba6a9f316b6 31 val = ch - '0';
rba90 0:2ba6a9f316b6 32 }
rba90 0:2ba6a9f316b6 33 else if (ch >= 'A' && ch <= 'F')
rba90 0:2ba6a9f316b6 34 {
rba90 0:2ba6a9f316b6 35 val = ch - 'A';
rba90 0:2ba6a9f316b6 36 val += 10;
rba90 0:2ba6a9f316b6 37 }
rba90 0:2ba6a9f316b6 38 else if (ch >= 'a' && ch <= 'f')
rba90 0:2ba6a9f316b6 39 {
rba90 0:2ba6a9f316b6 40 val = ch - 'a';
rba90 0:2ba6a9f316b6 41 val += 10;
rba90 0:2ba6a9f316b6 42 }
rba90 0:2ba6a9f316b6 43
rba90 0:2ba6a9f316b6 44 return val;
rba90 0:2ba6a9f316b6 45 }
rba90 2:54932809c7b2 46
rba90 0:2ba6a9f316b6 47
rba90 0:2ba6a9f316b6 48 bool CommandPacket::verify()
rba90 0:2ba6a9f316b6 49 {
rba90 3:0c4aa3cec685 50 return checksum == generate_checksum();
rba90 0:2ba6a9f316b6 51 }
rba90 0:2ba6a9f316b6 52
rba90 0:2ba6a9f316b6 53 CommandPacket::CommandPacket()
rba90 0:2ba6a9f316b6 54 {
rba90 0:2ba6a9f316b6 55 // reset internal error number
rba90 0:2ba6a9f316b6 56 errno = NO_ERROR;
rba90 0:2ba6a9f316b6 57
rba90 0:2ba6a9f316b6 58 // set public variables
rba90 0:2ba6a9f316b6 59 sflag = '<';
rba90 0:2ba6a9f316b6 60 command = 0x0;
rba90 0:2ba6a9f316b6 61 length = 0x0;
rba90 0:2ba6a9f316b6 62 memset(payload, 0x0, sizeof(payload));
rba90 0:2ba6a9f316b6 63 checksum = 0x0;
rba90 0:2ba6a9f316b6 64 eflag = '>';
rba90 0:2ba6a9f316b6 65 }
rba90 0:2ba6a9f316b6 66
rba90 0:2ba6a9f316b6 67 const char *CommandPacket::getErrorString() const
rba90 0:2ba6a9f316b6 68 {
rba90 0:2ba6a9f316b6 69 return errorString[errno];
rba90 0:2ba6a9f316b6 70 }
rba90 2:54932809c7b2 71
rba90 2:54932809c7b2 72 int CommandPacket::serialize(uint8_t *output)
rba90 2:54932809c7b2 73 {
rba90 2:54932809c7b2 74 // create buffer for payload
rba90 2:54932809c7b2 75 uint8_t buffer[length * 2];
rba90 2:54932809c7b2 76 memset(buffer, 0x0, sizeof(buffer));
rba90 2:54932809c7b2 77
rba90 2:54932809c7b2 78 for (int i = 0; i < length; i++)
rba90 2:54932809c7b2 79 {
rba90 2:54932809c7b2 80 sprintf((char *) (buffer + i * 2), "%02X", payload[i]);
rba90 2:54932809c7b2 81 }
rba90 2:54932809c7b2 82
rba90 2:54932809c7b2 83 // assume the user provide output buffer large enough
rba90 2:54932809c7b2 84 sprintf((char *) output, "%c%02X%02X%s%02X%c",
rba90 2:54932809c7b2 85 sflag,
rba90 2:54932809c7b2 86 command,
rba90 2:54932809c7b2 87 length,
rba90 2:54932809c7b2 88 (char *) buffer,
rba90 3:0c4aa3cec685 89 generate_checksum(),
rba90 2:54932809c7b2 90 eflag
rba90 2:54932809c7b2 91 );
rba90 2:54932809c7b2 92
rba90 2:54932809c7b2 93 return length;
rba90 2:54932809c7b2 94 }
rba90 3:0c4aa3cec685 95
rba90 3:0c4aa3cec685 96 uint8_t CommandPacket::generate_checksum()
rba90 3:0c4aa3cec685 97 {
rba90 3:0c4aa3cec685 98 // checksum is defined by the sum of all characters between sflag and checksum field
rba90 3:0c4aa3cec685 99 uint8_t s = 0;
rba90 3:0c4aa3cec685 100
rba90 3:0c4aa3cec685 101 // include command
rba90 3:0c4aa3cec685 102 s += command;
rba90 3:0c4aa3cec685 103
rba90 3:0c4aa3cec685 104 // include length
rba90 3:0c4aa3cec685 105 s += length;
rba90 3:0c4aa3cec685 106
rba90 3:0c4aa3cec685 107 // include payload
rba90 3:0c4aa3cec685 108 for (int i = 0; i < length; i++)
rba90 3:0c4aa3cec685 109 {
rba90 3:0c4aa3cec685 110 s += payload[i];
rba90 3:0c4aa3cec685 111 }
rba90 3:0c4aa3cec685 112
rba90 3:0c4aa3cec685 113 // calculate two's complement of the remainder
rba90 3:0c4aa3cec685 114 s = 0xff - s + 1;
rba90 3:0c4aa3cec685 115
rba90 3:0c4aa3cec685 116 return s;
rba90 3:0c4aa3cec685 117 }
rba90 2:54932809c7b2 118
rba90 2:54932809c7b2 119