XBee API mode library

Committer:
yamaguch
Date:
Thu Mar 21 06:51:31 2013 +0000
Revision:
17:2f728fd13bc0
Parent:
16:cdfcb63b2c4b
rewrote to use rtos Semaphore only

Who changed what in which revision?

UserRevisionLine numberNew contents of line
yamaguch 0:0232a97b3883 1 /*
yamaguch 8:776b8dc51932 2 Copyright (c) 2013, Senio Networks, Inc.
yamaguch 0:0232a97b3883 3
yamaguch 0:0232a97b3883 4 Permission is hereby granted, free of charge, to any person obtaining a copy
yamaguch 0:0232a97b3883 5 of this software and associated documentation files (the "Software"), to deal
yamaguch 0:0232a97b3883 6 in the Software without restriction, including without limitation the rights
yamaguch 0:0232a97b3883 7 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
yamaguch 0:0232a97b3883 8 copies of the Software, and to permit persons to whom the Software is
yamaguch 0:0232a97b3883 9 furnished to do so, subject to the following conditions:
yamaguch 0:0232a97b3883 10
yamaguch 0:0232a97b3883 11 The above copyright notice and this permission notice shall be included in
yamaguch 0:0232a97b3883 12 all copies or substantial portions of the Software.
yamaguch 0:0232a97b3883 13
yamaguch 0:0232a97b3883 14 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
yamaguch 0:0232a97b3883 15 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
yamaguch 0:0232a97b3883 16 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
yamaguch 0:0232a97b3883 17 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
yamaguch 0:0232a97b3883 18 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
yamaguch 0:0232a97b3883 19 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
yamaguch 0:0232a97b3883 20 THE SOFTWARE.
yamaguch 0:0232a97b3883 21 */
yamaguch 0:0232a97b3883 22
yamaguch 0:0232a97b3883 23 #include "XBee.h"
yamaguch 0:0232a97b3883 24 #include <stdarg.h>
yamaguch 0:0232a97b3883 25
yamaguch 17:2f728fd13bc0 26 #define LOCK() NVIC_DisableIRQ(UARTx_IRQn[_serial.index])
yamaguch 17:2f728fd13bc0 27 #define UNLOCK() NVIC_EnableIRQ(UARTx_IRQn[_serial.index])
yamaguch 17:2f728fd13bc0 28 #define INDEX(n) ((n) % BUFSIZE)
yamaguch 17:2f728fd13bc0 29 #define SIZE(b, i) (b[i] << 8 | b[INDEX(i + 1)])
yamaguch 17:2f728fd13bc0 30
yamaguch 16:cdfcb63b2c4b 31 const IRQn_Type UARTx_IRQn[] = {UART0_IRQn, UART1_IRQn, UART2_IRQn, UART3_IRQn};
yamaguch 16:cdfcb63b2c4b 32
yamaguch 0:0232a97b3883 33 void XBee::sendCommand(const char *command, int8_t param, bool queue) {
yamaguch 0:0232a97b3883 34 sendCommand(command, (uint64_t) param, queue);
yamaguch 0:0232a97b3883 35 }
yamaguch 0:0232a97b3883 36
yamaguch 0:0232a97b3883 37 void XBee::sendCommand(const char *command, int16_t param, bool queue) {
yamaguch 0:0232a97b3883 38 sendCommand(command, (uint64_t) param, queue);
yamaguch 0:0232a97b3883 39 }
yamaguch 0:0232a97b3883 40
yamaguch 0:0232a97b3883 41 void XBee::sendCommand(const char *command, int32_t param, bool queue) {
yamaguch 0:0232a97b3883 42 sendCommand(command, (uint64_t) param, queue);
yamaguch 0:0232a97b3883 43 }
yamaguch 0:0232a97b3883 44
yamaguch 0:0232a97b3883 45 void XBee::sendCommand(const char *command, int64_t param, bool queue) {
yamaguch 0:0232a97b3883 46 sendCommand(command, (uint64_t) param, queue);
yamaguch 0:0232a97b3883 47 }
yamaguch 0:0232a97b3883 48
yamaguch 0:0232a97b3883 49 void XBee::sendCommand(const char *command, uint8_t param, bool queue) {
yamaguch 0:0232a97b3883 50 sendCommand(command, (uint64_t) param, queue);
yamaguch 0:0232a97b3883 51 }
yamaguch 0:0232a97b3883 52
yamaguch 0:0232a97b3883 53 void XBee::sendCommand(const char *command, uint16_t param, bool queue) {
yamaguch 0:0232a97b3883 54 sendCommand(command, (uint64_t) param, queue);
yamaguch 0:0232a97b3883 55 }
yamaguch 0:0232a97b3883 56
yamaguch 0:0232a97b3883 57 void XBee::sendCommand(const char *command, uint32_t param, bool queue) {
yamaguch 0:0232a97b3883 58 sendCommand(command, (uint64_t) param, queue);
yamaguch 0:0232a97b3883 59 }
yamaguch 0:0232a97b3883 60
yamaguch 0:0232a97b3883 61 void XBee::sendCommand(const char *command, uint64_t param, bool queue) {
yamaguch 0:0232a97b3883 62 uint8_t param_buf[8] = {
yamaguch 0:0232a97b3883 63 (uint8_t) (param >> 56), (uint8_t) (param >> 48),
yamaguch 0:0232a97b3883 64 (uint8_t) (param >> 40), (uint8_t) (param >> 32),
yamaguch 0:0232a97b3883 65 (uint8_t) (param >> 24), (uint8_t) (param >> 16),
yamaguch 0:0232a97b3883 66 (uint8_t) (param >> 8), (uint8_t) param
yamaguch 0:0232a97b3883 67 };
yamaguch 0:0232a97b3883 68
yamaguch 0:0232a97b3883 69 int n = 0;
yamaguch 0:0232a97b3883 70 while (n < 7 && param_buf[n] == 0) n++;
yamaguch 0:0232a97b3883 71
yamaguch 0:0232a97b3883 72 sendCommand(command, param_buf + n, 8 - n, queue);
yamaguch 0:0232a97b3883 73 }
yamaguch 0:0232a97b3883 74
yamaguch 0:0232a97b3883 75 void XBee::sendCommand(const char *command, const char *param, bool queue) {
yamaguch 0:0232a97b3883 76 sendCommand(command, (uint8_t *) param, strlen(param), queue);
yamaguch 0:0232a97b3883 77 }
yamaguch 0:0232a97b3883 78
yamaguch 0:0232a97b3883 79 void XBee::sendCommand(const char *command, const uint8_t *param, int param_length, bool queue) {
yamaguch 0:0232a97b3883 80 char buf[param_length + 4];
yamaguch 0:0232a97b3883 81
yamaguch 0:0232a97b3883 82 createAtRequest(frame_id, command, param, param_length, queue, buf, sizeof(buf));
yamaguch 0:0232a97b3883 83 sendFrame(buf, param_length + 4);
yamaguch 0:0232a97b3883 84 frame_id = frame_id % 255 + 1;
yamaguch 0:0232a97b3883 85 }
yamaguch 0:0232a97b3883 86
yamaguch 0:0232a97b3883 87 void XBee::sendRemoteCommand(const char *command, int8_t param) {
yamaguch 0:0232a97b3883 88 sendRemoteCommand(command, (uint64_t) param);
yamaguch 0:0232a97b3883 89 }
yamaguch 0:0232a97b3883 90
yamaguch 0:0232a97b3883 91 void XBee::sendRemoteCommand(const char *command, int16_t param) {
yamaguch 0:0232a97b3883 92 sendRemoteCommand(command, (uint64_t) param);
yamaguch 0:0232a97b3883 93 }
yamaguch 0:0232a97b3883 94
yamaguch 0:0232a97b3883 95 void XBee::sendRemoteCommand(const char *command, int32_t param) {
yamaguch 0:0232a97b3883 96 sendRemoteCommand(command, (uint64_t) param);
yamaguch 0:0232a97b3883 97 }
yamaguch 0:0232a97b3883 98
yamaguch 0:0232a97b3883 99 void XBee::sendRemoteCommand(const char *command, int64_t param) {
yamaguch 0:0232a97b3883 100 sendRemoteCommand(command, (uint64_t) param);
yamaguch 0:0232a97b3883 101 }
yamaguch 0:0232a97b3883 102
yamaguch 0:0232a97b3883 103 void XBee::sendRemoteCommand(const char *command, uint8_t param) {
yamaguch 0:0232a97b3883 104 sendRemoteCommand(command, (uint64_t) param);
yamaguch 0:0232a97b3883 105 }
yamaguch 0:0232a97b3883 106
yamaguch 0:0232a97b3883 107 void XBee::sendRemoteCommand(const char *command, uint16_t param) {
yamaguch 0:0232a97b3883 108 sendRemoteCommand(command, (uint64_t) param);
yamaguch 0:0232a97b3883 109 }
yamaguch 0:0232a97b3883 110
yamaguch 0:0232a97b3883 111 void XBee::sendRemoteCommand(const char *command, uint32_t param) {
yamaguch 0:0232a97b3883 112 sendRemoteCommand(command, (uint64_t) param);
yamaguch 0:0232a97b3883 113 }
yamaguch 0:0232a97b3883 114
yamaguch 0:0232a97b3883 115 void XBee::sendRemoteCommand(const char *command, uint64_t param) {
yamaguch 0:0232a97b3883 116 uint8_t param_buf[8] = {
yamaguch 0:0232a97b3883 117 (uint8_t) (param >> 56), (uint8_t) (param >> 48),
yamaguch 0:0232a97b3883 118 (uint8_t) (param >> 40), (uint8_t) (param >> 32),
yamaguch 0:0232a97b3883 119 (uint8_t) (param >> 24), (uint8_t) (param >> 16),
yamaguch 0:0232a97b3883 120 (uint8_t) (param >> 8), (uint8_t) param
yamaguch 0:0232a97b3883 121 };
yamaguch 0:0232a97b3883 122
yamaguch 0:0232a97b3883 123 int n = 0;
yamaguch 0:0232a97b3883 124 while (n < 7 && param_buf[n] == 0) n++;
yamaguch 0:0232a97b3883 125
yamaguch 0:0232a97b3883 126 sendRemoteCommand(command, param_buf + n, 8 - n);
yamaguch 0:0232a97b3883 127 }
yamaguch 0:0232a97b3883 128
yamaguch 0:0232a97b3883 129 void XBee::sendRemoteCommand(const char *command, const char *param) {
yamaguch 0:0232a97b3883 130 sendRemoteCommand(command, (uint8_t *) param, strlen(param));
yamaguch 0:0232a97b3883 131 }
yamaguch 0:0232a97b3883 132
yamaguch 0:0232a97b3883 133 void XBee::sendRemoteCommand(const char *command, const uint8_t *param, int param_length, char options) {
yamaguch 0:0232a97b3883 134 char buf[param_length + 15];
yamaguch 0:0232a97b3883 135
yamaguch 0:0232a97b3883 136 createRemoteAtRequest(frame_id, command, param, param_length, options, buf, sizeof(buf));
yamaguch 0:0232a97b3883 137 sendFrame(buf, param_length + 15);
yamaguch 0:0232a97b3883 138 frame_id = frame_id % 255 + 1;
yamaguch 0:0232a97b3883 139 }
yamaguch 0:0232a97b3883 140
yamaguch 10:3da24a020e67 141 bool XBee::send(const char *data, int length) {
yamaguch 10:3da24a020e67 142 return send(data, length, sendConfirmation);
yamaguch 10:3da24a020e67 143 }
yamaguch 10:3da24a020e67 144
yamaguch 10:3da24a020e67 145 bool XBee::send(const char *data, int length, float timeout) {
yamaguch 0:0232a97b3883 146 if (length == 0)
yamaguch 0:0232a97b3883 147 length = strlen(data);
yamaguch 0:0232a97b3883 148
yamaguch 0:0232a97b3883 149 char buf[length + 14];
yamaguch 0:0232a97b3883 150
yamaguch 0:0232a97b3883 151 createTxRequest(frame_id, data, length, buf, sizeof(buf));
yamaguch 0:0232a97b3883 152 sendFrame(buf, length + 14);
yamaguch 3:8453df14bd30 153
yamaguch 16:cdfcb63b2c4b 154 bool ret = true;
yamaguch 10:3da24a020e67 155 if (timeout > 0) {
yamaguch 10:3da24a020e67 156 int index = seekFor(ZigBeeTransmitStatus, frame_id, timeout);
yamaguch 0:0232a97b3883 157 if (index != -1) {
yamaguch 0:0232a97b3883 158 char delivery;
yamaguch 0:0232a97b3883 159 scan(index, DeliveryStatus, &delivery);
yamaguch 16:cdfcb63b2c4b 160 this->buf[INDEX(index + 2)] = None;
yamaguch 16:cdfcb63b2c4b 161 //::printf("index = %02X, out = %02X, in = %02X\n", index, out, in);
yamaguch 16:cdfcb63b2c4b 162 if (index == out) {
yamaguch 16:cdfcb63b2c4b 163 LOCK();
yamaguch 16:cdfcb63b2c4b 164 int size = SIZE(this->buf, out);
yamaguch 16:cdfcb63b2c4b 165 out = INDEX(out + 2 + size);
yamaguch 16:cdfcb63b2c4b 166 free += (2 + size);
yamaguch 16:cdfcb63b2c4b 167 UNLOCK();
yamaguch 16:cdfcb63b2c4b 168 }
yamaguch 16:cdfcb63b2c4b 169 ret = (delivery == 0);
yamaguch 10:3da24a020e67 170 } else
yamaguch 16:cdfcb63b2c4b 171 ret = false;
yamaguch 0:0232a97b3883 172 }
yamaguch 16:cdfcb63b2c4b 173
yamaguch 16:cdfcb63b2c4b 174 frame_id = frame_id % 255 + 1;
yamaguch 16:cdfcb63b2c4b 175 return ret;
yamaguch 0:0232a97b3883 176 }
yamaguch 0:0232a97b3883 177
yamaguch 10:3da24a020e67 178 void XBee::setSendConfirmation(float sendConfirmation) {
yamaguch 10:3da24a020e67 179 this->sendConfirmation = sendConfirmation;
yamaguch 0:0232a97b3883 180 }
yamaguch 0:0232a97b3883 181
yamaguch 0:0232a97b3883 182 int XBee::printf(const char *format, ...) {
yamaguch 0:0232a97b3883 183 va_list argv;
yamaguch 0:0232a97b3883 184 va_start(argv, format);
yamaguch 0:0232a97b3883 185 char buf[256];
yamaguch 0:0232a97b3883 186 int length = vsnprintf(buf, sizeof buf, format, argv);
yamaguch 10:3da24a020e67 187 return length > 0 && send(buf, length) ? length : -1;
yamaguch 0:0232a97b3883 188 }
yamaguch 0:0232a97b3883 189
yamaguch 0:0232a97b3883 190 void XBee::send(char c) {
yamaguch 10:3da24a020e67 191 while (!writeable()) wait(0.001);
yamaguch 0:0232a97b3883 192 putc(c);
yamaguch 0:0232a97b3883 193 }
yamaguch 0:0232a97b3883 194
yamaguch 0:0232a97b3883 195 void XBee::send2(char c) {
yamaguch 0:0232a97b3883 196 switch (c) {
yamaguch 0:0232a97b3883 197 case 0x7E:
yamaguch 0:0232a97b3883 198 case 0x7D:
yamaguch 0:0232a97b3883 199 case 0x11:
yamaguch 0:0232a97b3883 200 case 0x13:
yamaguch 0:0232a97b3883 201 send(ESCAPE);
yamaguch 0:0232a97b3883 202 send(c ^ 0x20);
yamaguch 0:0232a97b3883 203 break;
yamaguch 0:0232a97b3883 204 default:
yamaguch 0:0232a97b3883 205 send(c);
yamaguch 0:0232a97b3883 206 }
yamaguch 0:0232a97b3883 207 }
yamaguch 0:0232a97b3883 208
yamaguch 0:0232a97b3883 209 void XBee::sendFrame(const char *frame, int length) {
yamaguch 0:0232a97b3883 210 char checksum = 255;
yamaguch 0:0232a97b3883 211
yamaguch 0:0232a97b3883 212 send(PREAMBLE);
yamaguch 0:0232a97b3883 213
yamaguch 17:2f728fd13bc0 214 if (api == 2) {
yamaguch 0:0232a97b3883 215 send2((length >> 8) & 255);
yamaguch 0:0232a97b3883 216 send2(length & 255);
yamaguch 0:0232a97b3883 217 for (int i = 0; i < length; i++) {
yamaguch 0:0232a97b3883 218 send2(frame[i]);
yamaguch 0:0232a97b3883 219 checksum -= frame[i];
yamaguch 0:0232a97b3883 220 }
yamaguch 0:0232a97b3883 221 send2(checksum);
yamaguch 0:0232a97b3883 222 } else {
yamaguch 0:0232a97b3883 223 send((length >> 8) & 255);
yamaguch 0:0232a97b3883 224 send(length & 255);
yamaguch 0:0232a97b3883 225 for (int i = 0; i < length; i++) {
yamaguch 0:0232a97b3883 226 send(frame[i]);
yamaguch 0:0232a97b3883 227 checksum -= frame[i];
yamaguch 0:0232a97b3883 228 }
yamaguch 0:0232a97b3883 229 send(checksum);
yamaguch 0:0232a97b3883 230 }
yamaguch 0:0232a97b3883 231 }
yamaguch 0:0232a97b3883 232
yamaguch 0:0232a97b3883 233 int XBee::createTxRequest(char frame_id, const char *data, int data_length, char *buf, int buf_size) {
yamaguch 0:0232a97b3883 234 if (data_length + 14 > buf_size) return -1;
yamaguch 0:0232a97b3883 235
yamaguch 0:0232a97b3883 236 buf[0] = 0x10; // frame type
yamaguch 0:0232a97b3883 237 buf[1] = frame_id;
yamaguch 0:0232a97b3883 238 for (int i = 0; i < 8; i++) buf[i + 2] = destination64[i];
yamaguch 0:0232a97b3883 239 buf[10] = destination16[0]; // 16 bit dest address
yamaguch 0:0232a97b3883 240 buf[11] = destination16[1]; // 16 bit dest address
yamaguch 0:0232a97b3883 241 buf[12] = 0;
yamaguch 0:0232a97b3883 242 buf[13] = 0;
yamaguch 0:0232a97b3883 243 for (int i = 0; i < data_length; i++) buf[i + 14] = data[i];
yamaguch 0:0232a97b3883 244
yamaguch 0:0232a97b3883 245 return data_length + 14;
yamaguch 0:0232a97b3883 246 }
yamaguch 0:0232a97b3883 247
yamaguch 0:0232a97b3883 248 int XBee::createAtRequest(char frame_id, const char *command, const uint8_t *param, int param_length, bool queue, char *buf, int buf_size) {
yamaguch 0:0232a97b3883 249 if (param_length + 4 > buf_size) return -1;
yamaguch 0:0232a97b3883 250
yamaguch 0:0232a97b3883 251 buf[0] = queue ? 0x09 : 0x08; // frame type
yamaguch 0:0232a97b3883 252 buf[1] = frame_id;
yamaguch 0:0232a97b3883 253 buf[2] = command[0];
yamaguch 0:0232a97b3883 254 buf[3] = command[1];
yamaguch 0:0232a97b3883 255 for (int i = 0; i < param_length; i++) buf[i + 4] = param[i];
yamaguch 0:0232a97b3883 256
yamaguch 0:0232a97b3883 257 return param_length + 4;
yamaguch 0:0232a97b3883 258 }
yamaguch 0:0232a97b3883 259
yamaguch 0:0232a97b3883 260 int XBee::createRemoteAtRequest(char frame_id, const char *command, const uint8_t *param, int param_length, char options, char *buf, int buf_size) {
yamaguch 0:0232a97b3883 261 if (param_length + 4 > buf_size) return -1;
yamaguch 0:0232a97b3883 262
yamaguch 0:0232a97b3883 263 buf[0] = 0x17; // frame type
yamaguch 0:0232a97b3883 264 buf[1] = frame_id;
yamaguch 0:0232a97b3883 265 memcpy(buf + 2, destination64, 8);
yamaguch 0:0232a97b3883 266 buf[10] = destination16[0];
yamaguch 0:0232a97b3883 267 buf[11] = destination16[1];
yamaguch 0:0232a97b3883 268 buf[12] = options;
yamaguch 0:0232a97b3883 269 buf[13] = command[0];
yamaguch 0:0232a97b3883 270 buf[14] = command[1];
yamaguch 0:0232a97b3883 271 for (int i = 0; i < param_length; i++) buf[i + 15] = param[i];
yamaguch 0:0232a97b3883 272
yamaguch 0:0232a97b3883 273 return param_length + 15;
yamaguch 0:0232a97b3883 274 }