mbed library sources. Supersedes mbed-src.

Dependents:   Nucleo_Hello_Encoder BLE_iBeaconScan AM1805_DEMO DISCO-F429ZI_ExportTemplate1 ... more

Committer:
AnnaBridge
Date:
Wed Feb 20 22:31:08 2019 +0000
Revision:
189:f392fc9709a3
Parent:
188:bcfe06ba3d64
mbed library release version 165

Who changed what in which revision?

UserRevisionLine numberNew contents of line
AnnaBridge 167:e84263d55307 1 /* Copyright (c) 2017 ARM Limited
AnnaBridge 189:f392fc9709a3 2 * SPDX-License-Identifier: Apache-2.0
AnnaBridge 167:e84263d55307 3 *
AnnaBridge 167:e84263d55307 4 * Licensed under the Apache License, Version 2.0 (the "License");
AnnaBridge 167:e84263d55307 5 * you may not use this file except in compliance with the License.
AnnaBridge 167:e84263d55307 6 * You may obtain a copy of the License at
AnnaBridge 167:e84263d55307 7 *
AnnaBridge 167:e84263d55307 8 * http://www.apache.org/licenses/LICENSE-2.0
AnnaBridge 167:e84263d55307 9 *
AnnaBridge 167:e84263d55307 10 * Unless required by applicable law or agreed to in writing, software
AnnaBridge 167:e84263d55307 11 * distributed under the License is distributed on an "AS IS" BASIS,
AnnaBridge 167:e84263d55307 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
AnnaBridge 167:e84263d55307 13 * See the License for the specific language governing permissions and
AnnaBridge 167:e84263d55307 14 * limitations under the License.
AnnaBridge 167:e84263d55307 15 *
AnnaBridge 167:e84263d55307 16 * @section DESCRIPTION
AnnaBridge 167:e84263d55307 17 *
AnnaBridge 167:e84263d55307 18 * Parser for the AT command syntax
AnnaBridge 167:e84263d55307 19 *
AnnaBridge 167:e84263d55307 20 */
AnnaBridge 167:e84263d55307 21
AnnaBridge 167:e84263d55307 22 #include "ATCmdParser.h"
AnnaBridge 167:e84263d55307 23 #include "mbed_poll.h"
AnnaBridge 167:e84263d55307 24 #include "mbed_debug.h"
AnnaBridge 189:f392fc9709a3 25 #include <stdio.h>
AnnaBridge 189:f392fc9709a3 26 #include <stdlib.h>
AnnaBridge 189:f392fc9709a3 27 #include <string.h>
AnnaBridge 167:e84263d55307 28
AnnaBridge 167:e84263d55307 29 #ifdef LF
AnnaBridge 167:e84263d55307 30 #undef LF
AnnaBridge 167:e84263d55307 31 #define LF 10
AnnaBridge 167:e84263d55307 32 #else
AnnaBridge 167:e84263d55307 33 #define LF 10
AnnaBridge 167:e84263d55307 34 #endif
AnnaBridge 167:e84263d55307 35
AnnaBridge 167:e84263d55307 36 #ifdef CR
AnnaBridge 167:e84263d55307 37 #undef CR
AnnaBridge 167:e84263d55307 38 #define CR 13
AnnaBridge 167:e84263d55307 39 #else
AnnaBridge 167:e84263d55307 40 #define CR 13
AnnaBridge 167:e84263d55307 41 #endif
AnnaBridge 167:e84263d55307 42
AnnaBridge 189:f392fc9709a3 43 namespace mbed {
AnnaBridge 189:f392fc9709a3 44
AnnaBridge 167:e84263d55307 45 // getc/putc handling with timeouts
AnnaBridge 167:e84263d55307 46 int ATCmdParser::putc(char c)
AnnaBridge 167:e84263d55307 47 {
AnnaBridge 167:e84263d55307 48 pollfh fhs;
AnnaBridge 167:e84263d55307 49 fhs.fh = _fh;
AnnaBridge 167:e84263d55307 50 fhs.events = POLLOUT;
AnnaBridge 167:e84263d55307 51
AnnaBridge 167:e84263d55307 52 int count = poll(&fhs, 1, _timeout);
AnnaBridge 167:e84263d55307 53 if (count > 0 && (fhs.revents & POLLOUT)) {
AnnaBridge 167:e84263d55307 54 return _fh->write(&c, 1) == 1 ? 0 : -1;
AnnaBridge 167:e84263d55307 55 } else {
AnnaBridge 167:e84263d55307 56 return -1;
AnnaBridge 167:e84263d55307 57 }
AnnaBridge 167:e84263d55307 58 }
AnnaBridge 167:e84263d55307 59
AnnaBridge 167:e84263d55307 60 int ATCmdParser::getc()
AnnaBridge 167:e84263d55307 61 {
AnnaBridge 167:e84263d55307 62 pollfh fhs;
AnnaBridge 167:e84263d55307 63 fhs.fh = _fh;
AnnaBridge 167:e84263d55307 64 fhs.events = POLLIN;
AnnaBridge 167:e84263d55307 65
AnnaBridge 167:e84263d55307 66 int count = poll(&fhs, 1, _timeout);
AnnaBridge 167:e84263d55307 67 if (count > 0 && (fhs.revents & POLLIN)) {
AnnaBridge 167:e84263d55307 68 unsigned char ch;
AnnaBridge 167:e84263d55307 69 return _fh->read(&ch, 1) == 1 ? ch : -1;
AnnaBridge 167:e84263d55307 70 } else {
AnnaBridge 167:e84263d55307 71 return -1;
AnnaBridge 167:e84263d55307 72 }
AnnaBridge 167:e84263d55307 73 }
AnnaBridge 167:e84263d55307 74
AnnaBridge 167:e84263d55307 75 void ATCmdParser::flush()
AnnaBridge 167:e84263d55307 76 {
AnnaBridge 167:e84263d55307 77 while (_fh->readable()) {
AnnaBridge 167:e84263d55307 78 unsigned char ch;
AnnaBridge 167:e84263d55307 79 _fh->read(&ch, 1);
AnnaBridge 167:e84263d55307 80 }
AnnaBridge 167:e84263d55307 81 }
AnnaBridge 167:e84263d55307 82
AnnaBridge 167:e84263d55307 83
AnnaBridge 167:e84263d55307 84 // read/write handling with timeouts
AnnaBridge 167:e84263d55307 85 int ATCmdParser::write(const char *data, int size)
AnnaBridge 167:e84263d55307 86 {
AnnaBridge 167:e84263d55307 87 int i = 0;
AnnaBridge 187:0387e8f68319 88 for (; i < size; i++) {
AnnaBridge 167:e84263d55307 89 if (putc(data[i]) < 0) {
AnnaBridge 167:e84263d55307 90 return -1;
AnnaBridge 167:e84263d55307 91 }
AnnaBridge 167:e84263d55307 92 }
AnnaBridge 167:e84263d55307 93 return i;
AnnaBridge 167:e84263d55307 94 }
AnnaBridge 167:e84263d55307 95
AnnaBridge 167:e84263d55307 96 int ATCmdParser::read(char *data, int size)
AnnaBridge 167:e84263d55307 97 {
AnnaBridge 167:e84263d55307 98 int i = 0;
AnnaBridge 187:0387e8f68319 99 for (; i < size; i++) {
AnnaBridge 167:e84263d55307 100 int c = getc();
AnnaBridge 167:e84263d55307 101 if (c < 0) {
AnnaBridge 167:e84263d55307 102 return -1;
AnnaBridge 167:e84263d55307 103 }
AnnaBridge 167:e84263d55307 104 data[i] = c;
AnnaBridge 167:e84263d55307 105 }
AnnaBridge 167:e84263d55307 106 return i;
AnnaBridge 167:e84263d55307 107 }
AnnaBridge 167:e84263d55307 108
AnnaBridge 167:e84263d55307 109
AnnaBridge 167:e84263d55307 110 // printf/scanf handling
AnnaBridge 189:f392fc9709a3 111 int ATCmdParser::vprintf(const char *format, std::va_list args)
AnnaBridge 167:e84263d55307 112 {
AnnaBridge 167:e84263d55307 113
AnnaBridge 167:e84263d55307 114 if (vsprintf(_buffer, format, args) < 0) {
AnnaBridge 167:e84263d55307 115 return false;
AnnaBridge 167:e84263d55307 116 }
AnnaBridge 167:e84263d55307 117
AnnaBridge 167:e84263d55307 118 int i = 0;
AnnaBridge 187:0387e8f68319 119 for (; _buffer[i]; i++) {
AnnaBridge 167:e84263d55307 120 if (putc(_buffer[i]) < 0) {
AnnaBridge 167:e84263d55307 121 return -1;
AnnaBridge 167:e84263d55307 122 }
AnnaBridge 167:e84263d55307 123 }
AnnaBridge 167:e84263d55307 124 return i;
AnnaBridge 167:e84263d55307 125 }
AnnaBridge 167:e84263d55307 126
AnnaBridge 189:f392fc9709a3 127 int ATCmdParser::vscanf(const char *format, std::va_list args)
AnnaBridge 167:e84263d55307 128 {
AnnaBridge 167:e84263d55307 129 // Since format is const, we need to copy it into our buffer to
AnnaBridge 167:e84263d55307 130 // add the line's null terminator and clobber value-matches with asterisks.
AnnaBridge 167:e84263d55307 131 //
AnnaBridge 167:e84263d55307 132 // We just use the beginning of the buffer to avoid unnecessary allocations.
AnnaBridge 167:e84263d55307 133 int i = 0;
AnnaBridge 167:e84263d55307 134 int offset = 0;
AnnaBridge 167:e84263d55307 135
AnnaBridge 167:e84263d55307 136 while (format[i]) {
AnnaBridge 187:0387e8f68319 137 if (format[i] == '%' && format[i + 1] != '%' && format[i + 1] != '*') {
AnnaBridge 167:e84263d55307 138 _buffer[offset++] = '%';
AnnaBridge 167:e84263d55307 139 _buffer[offset++] = '*';
AnnaBridge 167:e84263d55307 140 i++;
AnnaBridge 167:e84263d55307 141 } else {
AnnaBridge 167:e84263d55307 142 _buffer[offset++] = format[i++];
AnnaBridge 167:e84263d55307 143 }
AnnaBridge 167:e84263d55307 144 }
AnnaBridge 167:e84263d55307 145
AnnaBridge 167:e84263d55307 146 // Scanf has very poor support for catching errors
AnnaBridge 167:e84263d55307 147 // fortunately, we can abuse the %n specifier to determine
AnnaBridge 167:e84263d55307 148 // if the entire string was matched.
AnnaBridge 167:e84263d55307 149 _buffer[offset++] = '%';
AnnaBridge 167:e84263d55307 150 _buffer[offset++] = 'n';
AnnaBridge 167:e84263d55307 151 _buffer[offset++] = 0;
AnnaBridge 167:e84263d55307 152
AnnaBridge 167:e84263d55307 153 // To workaround scanf's lack of error reporting, we actually
AnnaBridge 167:e84263d55307 154 // make two passes. One checks the validity with the modified
AnnaBridge 167:e84263d55307 155 // format string that only stores the matched characters (%n).
AnnaBridge 167:e84263d55307 156 // The other reads in the actual matched values.
AnnaBridge 167:e84263d55307 157 //
AnnaBridge 167:e84263d55307 158 // We keep trying the match until we succeed or some other error
AnnaBridge 167:e84263d55307 159 // derails us.
AnnaBridge 167:e84263d55307 160 int j = 0;
AnnaBridge 167:e84263d55307 161
AnnaBridge 167:e84263d55307 162 while (true) {
AnnaBridge 167:e84263d55307 163 // Ran out of space
AnnaBridge 187:0387e8f68319 164 if (j + 1 >= _buffer_size - offset) {
AnnaBridge 167:e84263d55307 165 return false;
AnnaBridge 167:e84263d55307 166 }
AnnaBridge 184:08ed48f1de7f 167 // Receive next character
AnnaBridge 167:e84263d55307 168 int c = getc();
AnnaBridge 167:e84263d55307 169 if (c < 0) {
AnnaBridge 167:e84263d55307 170 return -1;
AnnaBridge 167:e84263d55307 171 }
AnnaBridge 167:e84263d55307 172 _buffer[offset + j++] = c;
AnnaBridge 167:e84263d55307 173 _buffer[offset + j] = 0;
AnnaBridge 167:e84263d55307 174
AnnaBridge 167:e84263d55307 175 // Check for match
AnnaBridge 167:e84263d55307 176 int count = -1;
AnnaBridge 187:0387e8f68319 177 sscanf(_buffer + offset, _buffer, &count);
AnnaBridge 167:e84263d55307 178
AnnaBridge 167:e84263d55307 179 // We only succeed if all characters in the response are matched
AnnaBridge 167:e84263d55307 180 if (count == j) {
AnnaBridge 167:e84263d55307 181 // Store the found results
AnnaBridge 187:0387e8f68319 182 vsscanf(_buffer + offset, format, args);
AnnaBridge 167:e84263d55307 183 return j;
AnnaBridge 167:e84263d55307 184 }
AnnaBridge 167:e84263d55307 185 }
AnnaBridge 167:e84263d55307 186 }
AnnaBridge 167:e84263d55307 187
AnnaBridge 167:e84263d55307 188
AnnaBridge 167:e84263d55307 189 // Command parsing with line handling
AnnaBridge 189:f392fc9709a3 190 bool ATCmdParser::vsend(const char *command, std::va_list args)
AnnaBridge 167:e84263d55307 191 {
AnnaBridge 167:e84263d55307 192 // Create and send command
AnnaBridge 167:e84263d55307 193 if (vsprintf(_buffer, command, args) < 0) {
AnnaBridge 167:e84263d55307 194 return false;
AnnaBridge 167:e84263d55307 195 }
AnnaBridge 167:e84263d55307 196
AnnaBridge 167:e84263d55307 197 for (int i = 0; _buffer[i]; i++) {
AnnaBridge 167:e84263d55307 198 if (putc(_buffer[i]) < 0) {
AnnaBridge 167:e84263d55307 199 return false;
AnnaBridge 167:e84263d55307 200 }
AnnaBridge 167:e84263d55307 201 }
AnnaBridge 167:e84263d55307 202
AnnaBridge 167:e84263d55307 203 // Finish with newline
AnnaBridge 167:e84263d55307 204 for (size_t i = 0; _output_delimiter[i]; i++) {
AnnaBridge 167:e84263d55307 205 if (putc(_output_delimiter[i]) < 0) {
AnnaBridge 167:e84263d55307 206 return false;
AnnaBridge 167:e84263d55307 207 }
AnnaBridge 167:e84263d55307 208 }
AnnaBridge 167:e84263d55307 209
AnnaBridge 167:e84263d55307 210 debug_if(_dbg_on, "AT> %s\n", _buffer);
AnnaBridge 167:e84263d55307 211 return true;
AnnaBridge 167:e84263d55307 212 }
AnnaBridge 167:e84263d55307 213
AnnaBridge 189:f392fc9709a3 214 bool ATCmdParser::vrecv(const char *response, std::va_list args)
AnnaBridge 167:e84263d55307 215 {
AnnaBridge 167:e84263d55307 216 restart:
AnnaBridge 167:e84263d55307 217 _aborted = false;
AnnaBridge 167:e84263d55307 218 // Iterate through each line in the expected response
AnnaBridge 188:bcfe06ba3d64 219 // response being NULL means we just want to check for OOBs
AnnaBridge 188:bcfe06ba3d64 220 while (!response || response[0]) {
AnnaBridge 167:e84263d55307 221 // Since response is const, we need to copy it into our buffer to
AnnaBridge 167:e84263d55307 222 // add the line's null terminator and clobber value-matches with asterisks.
AnnaBridge 167:e84263d55307 223 //
AnnaBridge 167:e84263d55307 224 // We just use the beginning of the buffer to avoid unnecessary allocations.
AnnaBridge 167:e84263d55307 225 int i = 0;
AnnaBridge 167:e84263d55307 226 int offset = 0;
AnnaBridge 167:e84263d55307 227 bool whole_line_wanted = false;
AnnaBridge 167:e84263d55307 228
AnnaBridge 188:bcfe06ba3d64 229 while (response && response[i]) {
AnnaBridge 187:0387e8f68319 230 if (response[i] == '%' && response[i + 1] != '%' && response[i + 1] != '*') {
AnnaBridge 167:e84263d55307 231 _buffer[offset++] = '%';
AnnaBridge 167:e84263d55307 232 _buffer[offset++] = '*';
AnnaBridge 167:e84263d55307 233 i++;
AnnaBridge 167:e84263d55307 234 } else {
AnnaBridge 167:e84263d55307 235 _buffer[offset++] = response[i++];
AnnaBridge 167:e84263d55307 236 // Find linebreaks, taking care not to be fooled if they're in a %[^\n] conversion specification
AnnaBridge 187:0387e8f68319 237 if (response[i - 1] == '\n' && !(i >= 3 && response[i - 3] == '[' && response[i - 2] == '^')) {
AnnaBridge 167:e84263d55307 238 whole_line_wanted = true;
AnnaBridge 167:e84263d55307 239 break;
AnnaBridge 167:e84263d55307 240 }
AnnaBridge 167:e84263d55307 241 }
AnnaBridge 167:e84263d55307 242 }
AnnaBridge 167:e84263d55307 243
AnnaBridge 167:e84263d55307 244 // Scanf has very poor support for catching errors
AnnaBridge 167:e84263d55307 245 // fortunately, we can abuse the %n specifier to determine
AnnaBridge 167:e84263d55307 246 // if the entire string was matched.
AnnaBridge 167:e84263d55307 247 _buffer[offset++] = '%';
AnnaBridge 167:e84263d55307 248 _buffer[offset++] = 'n';
AnnaBridge 167:e84263d55307 249 _buffer[offset++] = 0;
AnnaBridge 167:e84263d55307 250
AnnaBridge 167:e84263d55307 251 debug_if(_dbg_on, "AT? %s\n", _buffer);
AnnaBridge 167:e84263d55307 252 // To workaround scanf's lack of error reporting, we actually
AnnaBridge 167:e84263d55307 253 // make two passes. One checks the validity with the modified
AnnaBridge 167:e84263d55307 254 // format string that only stores the matched characters (%n).
AnnaBridge 167:e84263d55307 255 // The other reads in the actual matched values.
AnnaBridge 167:e84263d55307 256 //
AnnaBridge 167:e84263d55307 257 // We keep trying the match until we succeed or some other error
AnnaBridge 167:e84263d55307 258 // derails us.
AnnaBridge 167:e84263d55307 259 int j = 0;
AnnaBridge 167:e84263d55307 260
AnnaBridge 167:e84263d55307 261 while (true) {
AnnaBridge 188:bcfe06ba3d64 262 // If just peeking for OOBs, and at start of line, check
AnnaBridge 188:bcfe06ba3d64 263 // readability
AnnaBridge 188:bcfe06ba3d64 264 if (!response && j == 0 && !_fh->readable()) {
AnnaBridge 188:bcfe06ba3d64 265 return false;
AnnaBridge 188:bcfe06ba3d64 266 }
AnnaBridge 167:e84263d55307 267 // Receive next character
AnnaBridge 167:e84263d55307 268 int c = getc();
AnnaBridge 167:e84263d55307 269 if (c < 0) {
AnnaBridge 167:e84263d55307 270 debug_if(_dbg_on, "AT(Timeout)\n");
AnnaBridge 167:e84263d55307 271 return false;
AnnaBridge 167:e84263d55307 272 }
AnnaBridge 167:e84263d55307 273 // Simplify newlines (borrowed from retarget.cpp)
AnnaBridge 167:e84263d55307 274 if ((c == CR && _in_prev != LF) ||
AnnaBridge 187:0387e8f68319 275 (c == LF && _in_prev != CR)) {
AnnaBridge 167:e84263d55307 276 _in_prev = c;
AnnaBridge 167:e84263d55307 277 c = '\n';
AnnaBridge 167:e84263d55307 278 } else if ((c == CR && _in_prev == LF) ||
AnnaBridge 167:e84263d55307 279 (c == LF && _in_prev == CR)) {
AnnaBridge 167:e84263d55307 280 _in_prev = c;
AnnaBridge 167:e84263d55307 281 // onto next character
AnnaBridge 167:e84263d55307 282 continue;
AnnaBridge 167:e84263d55307 283 } else {
AnnaBridge 167:e84263d55307 284 _in_prev = c;
AnnaBridge 167:e84263d55307 285 }
AnnaBridge 167:e84263d55307 286 _buffer[offset + j++] = c;
AnnaBridge 167:e84263d55307 287 _buffer[offset + j] = 0;
AnnaBridge 167:e84263d55307 288
AnnaBridge 167:e84263d55307 289 // Check for oob data
AnnaBridge 167:e84263d55307 290 for (struct oob *oob = _oobs; oob; oob = oob->next) {
AnnaBridge 167:e84263d55307 291 if ((unsigned)j == oob->len && memcmp(
AnnaBridge 187:0387e8f68319 292 oob->prefix, _buffer + offset, oob->len) == 0) {
AnnaBridge 167:e84263d55307 293 debug_if(_dbg_on, "AT! %s\n", oob->prefix);
AnnaBridge 188:bcfe06ba3d64 294 _oob_cb_count++;
AnnaBridge 167:e84263d55307 295 oob->cb();
AnnaBridge 167:e84263d55307 296
AnnaBridge 167:e84263d55307 297 if (_aborted) {
AnnaBridge 167:e84263d55307 298 debug_if(_dbg_on, "AT(Aborted)\n");
AnnaBridge 167:e84263d55307 299 return false;
AnnaBridge 167:e84263d55307 300 }
AnnaBridge 167:e84263d55307 301 // oob may have corrupted non-reentrant buffer,
AnnaBridge 167:e84263d55307 302 // so we need to set it up again
AnnaBridge 167:e84263d55307 303 goto restart;
AnnaBridge 167:e84263d55307 304 }
AnnaBridge 167:e84263d55307 305 }
AnnaBridge 167:e84263d55307 306
AnnaBridge 167:e84263d55307 307 // Check for match
AnnaBridge 167:e84263d55307 308 int count = -1;
AnnaBridge 167:e84263d55307 309 if (whole_line_wanted && c != '\n') {
AnnaBridge 167:e84263d55307 310 // Don't attempt scanning until we get delimiter if they included it in format
AnnaBridge 167:e84263d55307 311 // This allows recv("Foo: %s\n") to work, and not match with just the first character of a string
AnnaBridge 167:e84263d55307 312 // (scanf does not itself match whitespace in its format string, so \n is not significant to it)
AnnaBridge 188:bcfe06ba3d64 313 } else if (response) {
AnnaBridge 187:0387e8f68319 314 sscanf(_buffer + offset, _buffer, &count);
AnnaBridge 167:e84263d55307 315 }
AnnaBridge 167:e84263d55307 316
AnnaBridge 167:e84263d55307 317 // We only succeed if all characters in the response are matched
AnnaBridge 167:e84263d55307 318 if (count == j) {
AnnaBridge 187:0387e8f68319 319 debug_if(_dbg_on, "AT= %s\n", _buffer + offset);
AnnaBridge 167:e84263d55307 320 // Reuse the front end of the buffer
AnnaBridge 167:e84263d55307 321 memcpy(_buffer, response, i);
AnnaBridge 167:e84263d55307 322 _buffer[i] = 0;
AnnaBridge 167:e84263d55307 323
AnnaBridge 167:e84263d55307 324 // Store the found results
AnnaBridge 187:0387e8f68319 325 vsscanf(_buffer + offset, _buffer, args);
AnnaBridge 167:e84263d55307 326
AnnaBridge 167:e84263d55307 327 // Jump to next line and continue parsing
AnnaBridge 167:e84263d55307 328 response += i;
AnnaBridge 167:e84263d55307 329 break;
AnnaBridge 167:e84263d55307 330 }
AnnaBridge 167:e84263d55307 331
AnnaBridge 167:e84263d55307 332 // Clear the buffer when we hit a newline or ran out of space
AnnaBridge 167:e84263d55307 333 // running out of space usually means we ran into binary data
AnnaBridge 187:0387e8f68319 334 if (c == '\n' || j + 1 >= _buffer_size - offset) {
AnnaBridge 187:0387e8f68319 335 debug_if(_dbg_on, "AT< %s", _buffer + offset);
AnnaBridge 167:e84263d55307 336 j = 0;
AnnaBridge 167:e84263d55307 337 }
AnnaBridge 167:e84263d55307 338 }
AnnaBridge 167:e84263d55307 339 }
AnnaBridge 167:e84263d55307 340
AnnaBridge 167:e84263d55307 341 return true;
AnnaBridge 167:e84263d55307 342 }
AnnaBridge 167:e84263d55307 343
AnnaBridge 167:e84263d55307 344 // Mapping to vararg functions
AnnaBridge 167:e84263d55307 345 int ATCmdParser::printf(const char *format, ...)
AnnaBridge 167:e84263d55307 346 {
AnnaBridge 189:f392fc9709a3 347 std::va_list args;
AnnaBridge 167:e84263d55307 348 va_start(args, format);
AnnaBridge 167:e84263d55307 349 int res = vprintf(format, args);
AnnaBridge 167:e84263d55307 350 va_end(args);
AnnaBridge 167:e84263d55307 351 return res;
AnnaBridge 167:e84263d55307 352 }
AnnaBridge 167:e84263d55307 353
AnnaBridge 167:e84263d55307 354 int ATCmdParser::scanf(const char *format, ...)
AnnaBridge 167:e84263d55307 355 {
AnnaBridge 189:f392fc9709a3 356 std::va_list args;
AnnaBridge 167:e84263d55307 357 va_start(args, format);
AnnaBridge 167:e84263d55307 358 int res = vscanf(format, args);
AnnaBridge 167:e84263d55307 359 va_end(args);
AnnaBridge 167:e84263d55307 360 return res;
AnnaBridge 167:e84263d55307 361 }
AnnaBridge 167:e84263d55307 362
AnnaBridge 167:e84263d55307 363 bool ATCmdParser::send(const char *command, ...)
AnnaBridge 167:e84263d55307 364 {
AnnaBridge 189:f392fc9709a3 365 std::va_list args;
AnnaBridge 167:e84263d55307 366 va_start(args, command);
AnnaBridge 167:e84263d55307 367 bool res = vsend(command, args);
AnnaBridge 167:e84263d55307 368 va_end(args);
AnnaBridge 167:e84263d55307 369 return res;
AnnaBridge 167:e84263d55307 370 }
AnnaBridge 167:e84263d55307 371
AnnaBridge 167:e84263d55307 372 bool ATCmdParser::recv(const char *response, ...)
AnnaBridge 167:e84263d55307 373 {
AnnaBridge 189:f392fc9709a3 374 std::va_list args;
AnnaBridge 167:e84263d55307 375 va_start(args, response);
AnnaBridge 167:e84263d55307 376 bool res = vrecv(response, args);
AnnaBridge 167:e84263d55307 377 va_end(args);
AnnaBridge 167:e84263d55307 378 return res;
AnnaBridge 167:e84263d55307 379 }
AnnaBridge 167:e84263d55307 380
AnnaBridge 167:e84263d55307 381 // oob registration
AnnaBridge 167:e84263d55307 382 void ATCmdParser::oob(const char *prefix, Callback<void()> cb)
AnnaBridge 167:e84263d55307 383 {
AnnaBridge 167:e84263d55307 384 struct oob *oob = new struct oob;
AnnaBridge 167:e84263d55307 385 oob->len = strlen(prefix);
AnnaBridge 167:e84263d55307 386 oob->prefix = prefix;
AnnaBridge 167:e84263d55307 387 oob->cb = cb;
AnnaBridge 167:e84263d55307 388 oob->next = _oobs;
AnnaBridge 167:e84263d55307 389 _oobs = oob;
AnnaBridge 167:e84263d55307 390 }
AnnaBridge 167:e84263d55307 391
AnnaBridge 167:e84263d55307 392 void ATCmdParser::abort()
AnnaBridge 167:e84263d55307 393 {
AnnaBridge 167:e84263d55307 394 _aborted = true;
AnnaBridge 167:e84263d55307 395 }
AnnaBridge 176:447f873cad2f 396
AnnaBridge 176:447f873cad2f 397 bool ATCmdParser::process_oob()
AnnaBridge 176:447f873cad2f 398 {
AnnaBridge 188:bcfe06ba3d64 399 int pre_count = _oob_cb_count;
AnnaBridge 188:bcfe06ba3d64 400 recv(NULL);
AnnaBridge 188:bcfe06ba3d64 401 return _oob_cb_count != pre_count;
AnnaBridge 176:447f873cad2f 402 }
AnnaBridge 176:447f873cad2f 403
AnnaBridge 189:f392fc9709a3 404 }
AnnaBridge 176:447f873cad2f 405