1 /*
2 * Copyright (c) 2018, The OpenThread Authors.
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * 3. Neither the name of the copyright holder nor the
13 * names of its contributors may be used to endorse or promote products
14 * derived from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
20 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26 * POSSIBILITY OF SUCH DAMAGE.
27 */
28
29 /**
30 * @file
31 * This file includes definitions for command line parser.
32 */
33
34 #ifndef PARSE_CMD_LINE_HPP_
35 #define PARSE_CMD_LINE_HPP_
36
37 #include <stdint.h>
38 #include <string.h>
39
40 #include <openthread/error.h>
41 #include <openthread/instance.h>
42 #include <openthread/ip6.h>
43 #include <openthread/nat64.h>
44
45 namespace ot {
46 namespace Utils {
47 namespace CmdLineParser {
48
49 /**
50 * @addtogroup utils-parse-cmd-line
51 *
52 * @brief
53 * This module includes definitions for command line parser.
54 *
55 * @{
56 */
57
58 /**
59 * Parses a string as a `uint8_t` value.
60 *
61 * The number in string is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
62 *
63 * @param[in] aString The string to parse.
64 * @param[out] aUint8 A reference to an `uint8_t` variable to output the parsed value.
65 *
66 * @retval kErrorNone The string was parsed successfully.
67 * @retval kErrorInvalidArgs The string does not contain valid number (e.g., value out of range).
68 */
69 otError ParseAsUint8(const char *aString, uint8_t &aUint8);
70
71 /**
72 * Parses a string as a `uint16_t` value.
73 *
74 * The number in string is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
75 *
76 * @param[in] aString The string to parse.
77 * @param[out] aUint16 A reference to an `uint16_t` variable to output the parsed value.
78 *
79 * @retval kErrorNone The string was parsed successfully.
80 * @retval kErrorInvalidArgs The string does not contain valid number (e.g., value out of range).
81 */
82 otError ParseAsUint16(const char *aString, uint16_t &aUint16);
83
84 /**
85 * Parses a string as a `uint32_t` value.
86 *
87 * The number in string is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
88 *
89 * @param[in] aString The string to parse.
90 * @param[out] aUint32 A reference to an `uint32_t` variable to output the parsed value.
91 *
92 * @retval kErrorNone The string was parsed successfully.
93 * @retval kErrorInvalidArgs The string does not contain valid number (e.g., value out of range).
94 */
95 otError ParseAsUint32(const char *aString, uint32_t &aUint32);
96
97 /**
98 * Parses a string as a `uint64_t` value.
99 *
100 * The number in string is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
101 *
102 * @param[in] aString The string to parse.
103 * @param[out] aUint64 A reference to an `uint64_t` variable to output the parsed value.
104 *
105 * @retval kErrorNone The string was parsed successfully.
106 * @retval kErrorInvalidArgs The string does not contain valid number (e.g., value out of range).
107 */
108 otError ParseAsUint64(const char *aString, uint64_t &aUint64);
109
110 /**
111 * Parses a string as a `int8_t` value.
112 *
113 * The number in string is parsed as decimal or hex format (if contains `0x` or `0X` prefix). The string can start with
114 * `+`/`-` sign.
115 *
116 * @param[in] aString The string to parse.
117 * @param[out] aInt8 A reference to an `int8_t` variable to output the parsed value.
118 *
119 * @retval kErrorNone The string was parsed successfully.
120 * @retval kErrorInvalidArgs The string does not contain valid number (e.g., value out of range).
121 */
122 otError ParseAsInt8(const char *aString, int8_t &aInt8);
123
124 /**
125 * Parses a string as a `int16_t` value.
126 *
127 * The number in string is parsed as decimal or hex format (if contains `0x` or `0X` prefix). The string can start with
128 * `+`/`-` sign.
129 *
130 * @param[in] aString The string to parse.
131 * @param[out] aInt16 A reference to an `int16_t` variable to output the parsed value.
132 *
133 * @retval kErrorNone The string was parsed successfully.
134 * @retval kErrorInvalidArgs The string does not contain valid number (e.g., value out of range).
135 */
136 otError ParseAsInt16(const char *aString, int16_t &aInt16);
137
138 /**
139 * Parses a string as a `int32_t` value.
140 *
141 * The number in string is parsed as decimal or hex format (if contains `0x` or `0X` prefix). The string can start with
142 * `+`/`-` sign.
143 *
144 * @param[in] aString The string to parse.
145 * @param[out] aInt32 A reference to an `int32_t` variable to output the parsed value.
146 *
147 * @retval kErrorNone The string was parsed successfully.
148 * @retval kErrorInvalidArgs The string does not contain valid number (e.g., value out of range).
149 */
150 otError ParseAsInt32(const char *aString, int32_t &aInt32);
151
152 /**
153 * Parses a string as a `bool` value.
154 *
155 * Zero value is treated as `false`, non-zero value as `true`.
156 *
157 * @param[in] aString The string to parse.
158 * @param[out] aBool A reference to a `bool` variable to output the parsed value.
159 *
160 * @retval kErrorNone The string was parsed successfully.
161 * @retval kErrorInvalidArgs The string does not contain valid number.
162 */
163 otError ParseAsBool(const char *aString, bool &aBool);
164
165 #if OPENTHREAD_FTD || OPENTHREAD_MTD
166 /**
167 * Parses a string as an IPv6 address.
168 *
169 *
170 * @param[in] aString The string to parse.
171 * @param[out] aAddress A reference to an `otIp6Address` to output the parsed IPv6 address.
172 *
173 * @retval kErrorNone The string was parsed successfully.
174 * @retval kErrorInvalidArgs The string does not contain valid IPv6 address.
175 */
176 otError ParseAsIp6Address(const char *aString, otIp6Address &aAddress);
177
178 /**
179 * Parses a string as an IPv4 address.
180 *
181 * @param[in] aString The string to parse.
182 * @param[out] aAddress A reference to an `otIp6Address` to output the parsed IPv6 address.
183 *
184 * @retval kErrorNone The string was parsed successfully.
185 * @retval kErrorInvalidArgs The string does not contain valid IPv4 address.
186 */
187 otError ParseAsIp4Address(const char *aString, otIp4Address &aAddress);
188
189 /**
190 * Parses a string as an IPv6 prefix.
191 *
192 * The string is parsed as `{IPv6Address}/{PrefixLength}`.
193 *
194 * @param[in] aString The string to parse.
195 * @param[out] aPrefix A reference to an `otIp6Prefix` to output the parsed IPv6 prefix.
196 *
197 * @retval kErrorNone The string was parsed successfully.
198 * @retval kErrorInvalidArgs The string does not contain a valid IPv6 prefix.
199 */
200 otError ParseAsIp6Prefix(const char *aString, otIp6Prefix &aPrefix);
201 #endif // OPENTHREAD_FTD || OPENTHREAD_MTD
202
203 /**
204 * Parses a hex string into a byte array of fixed expected size.
205 *
206 * Returns `kErrorNone` only when the hex string contains exactly @p aSize bytes (after parsing). If
207 * there are fewer or more bytes in hex string that @p aSize, the parsed bytes (up to @p aSize) are copied into the
208 * `aBuffer` and `kErrorInvalidArgs` is returned.
209 *
210 * Correctly handles hex strings with even or odd length. For example, "AABBCCDD" (with even length) is
211 * parsed as {0xaa, 0xbb, 0xcc, 0xdd} and "123" (with odd length) is parsed as {0x01, 0x23}.
212 *
213 * @param[in] aString The string to parse.
214 * @param[out] aBuffer A pointer to a buffer to output the parsed byte sequence.
215 * @param[in] aSize The expected size of byte sequence (number of bytes after parsing).
216 *
217 * @retval kErrorNone The string was parsed successfully.
218 * @retval kErrorInvalidArgs The string does not contain valid hex bytes and/or not @p aSize bytes.
219 */
220 otError ParseAsHexString(const char *aString, uint8_t *aBuffer, uint16_t aSize);
221
222 /**
223 * This template function parses a hex string into a a given fixed size array.
224 *
225 * Returns `kErrorNone` only when the hex string contains exactly @p kBufferSize bytes (after parsing).
226 * If there are fewer or more bytes in hex string that @p kBufferSize, the parsed bytes (up to @p kBufferSize) are
227 * copied into the `aBuffer` and `kErrorInvalidArgs` is returned.
228 *
229 * Correctly handles hex strings with even or odd length. For example, "AABBCCDD" (with even length) is
230 * parsed as {0xaa, 0xbb, 0xcc, 0xdd} and "123" (with odd length) is parsed as {0x01, 0x23}.
231 *
232 * @tparam kBufferSize The byte array size (number of bytes).
233 *
234 * @param[in] aString The string to parse.
235 * @param[out] aBuffer A reference to a byte array to output the parsed byte sequence.
236 *
237 * @retval kErrorNone The string was parsed successfully.
238 * @retval kErrorInvalidArgs The string does not contain valid hex bytes and/or not @p aSize bytes.
239 */
ParseAsHexString(const char * aString,uint8_t (& aBuffer)[kBufferSize])240 template <uint16_t kBufferSize> static otError ParseAsHexString(const char *aString, uint8_t (&aBuffer)[kBufferSize])
241 {
242 return ParseAsHexString(aString, aBuffer, kBufferSize);
243 }
244
245 /**
246 * Parses a hex string into a byte array.
247 *
248 * Verifies that the parsed hex string bytes fit in @p aBuffer with its given @p aSize.
249 *
250 * Correctly handles hex strings with even or odd length. For example, "AABBCCDD" (with even length) is
251 * parsed as {0xaa, 0xbb, 0xcc, 0xdd} and "123" (with odd length) is parsed as {0x01, 0x23}.
252 *
253 * @param[in] aString The string to parse.
254 * @param[in,out] aSize On entry indicates the number of bytes in @p aBuffer (max size of @p aBuffer).
255 * On exit provides number of bytes parsed and copied into @p aBuffer.
256 * @param[out] aBuffer A pointer to a buffer to output the parsed byte sequence.
257 *
258 * @retval kErrorNone The string was parsed successfully.
259 * @retval kErrorInvalidArgs The string does not contain valid format or too many bytes.
260 */
261 otError ParseAsHexString(const char *aString, uint16_t &aSize, uint8_t *aBuffer);
262
263 /**
264 * Parses a segment of a hex string up to a given size.
265 *
266 * Allows a longer hex string to be parsed and read in smaller segments into a given buffer. If the
267 * entire hex string bytes can fit in the given @p aBuffer with its @p aSize, they are copied into @p aBuffer and
268 * function returns `kErrorNone`. Otherwise, @p aSize bytes are read and copied and function returns `kErrorPending`
269 * to indicate that there are more bytes to parse. The @p aString is also updated to skip over the parsed segment.
270 *
271 * Correctly handles hex strings with even or odd length. For example, "AABBCCDD" (with even length) is
272 * parsed as {0xaa, 0xbb, 0xcc, 0xdd} and "123" (with odd length) is parsed as {0x01, 0x23}.
273 *
274 * @param[in,out] aString A reference to string to parse. On successful parse, updated to skip parsed digits.
275 * @param[in,out] aSize On entry indicates the segment size (number of bytes in @p aBuffer).
276 * On exit provides number of bytes parsed and copied into @p aBuffer.
277 * @param[out] aBuffer A pointer to a buffer to output the parsed byte sequence.
278 *
279 * @retval kErrorNone The string was parsed successfully to the end of string.
280 * @retval kErrorPending The string segment was parsed successfully, but there are additional bytes remaining
281 * to be parsed.
282 * @retval kErrorInvalidArgs The string does not contain valid format hex digits.
283 */
284 otError ParseAsHexStringSegment(const char *&aString, uint16_t &aSize, uint8_t *aBuffer);
285
286 /**
287 * Represents a single argument from an argument list.
288 */
289 class Arg
290 {
291 public:
292 /**
293 * Clears the argument.
294 */
Clear(void)295 void Clear(void) { mString = nullptr; }
296
297 /**
298 * Indicates whether or not the argument is empty (i.e., reached the end of argument list).
299 *
300 * @retval TRUE The argument is empty.
301 * @retval FALSE The argument is not empty.
302 */
IsEmpty(void) const303 bool IsEmpty(void) const { return (mString == nullptr); }
304
305 /**
306 * Returns the length (number of characters) in the argument C string.
307 *
308 * @returns The argument string length if argument is not empty, zero otherwise.
309 */
310 uint16_t GetLength(void) const;
311
312 /**
313 * Gets the argument as a C string.
314 *
315 * @returns A pointer to the argument as a C string, or `nullptr` if argument is empty.
316 */
GetCString(void) const317 const char *GetCString(void) const { return mString; }
318
319 /**
320 * Gets the argument as C string.
321 *
322 * @returns A pointer to the argument as a C string, or `nullptr` if argument is empty.
323 */
GetCString(void)324 char *GetCString(void) { return mString; }
325
326 /**
327 * Sets the argument with a given C string.
328 *
329 * @param[in] aString A pointer to the new C string.
330 */
SetCString(char * aString)331 void SetCString(char *aString) { mString = aString; }
332
333 /**
334 * Overload the operator `==` to evaluate whether the argument is equal to a given C string.
335 *
336 * If the argument is empty (`IsEmpty()` is `true`) then comparing it using operator `==` with any C string will
337 * return false.
338 *
339 * @param[in] aString The C string to compare with (MUST not be `nullptr`).
340 *
341 * @retval TRUE If the argument is not empty and is equal to @p aString.
342 * @retval FALSE If the argument is not equal to @p aString, or if the argument is empty.
343 */
344 bool operator==(const char *aString) const;
345
346 /**
347 * Overload the operator `!=` to evaluate whether the argument is unequal to a given C string.
348 *
349 * @param[in] aString The C string to compare with (MUST not be `nullptr`).
350 *
351 * @retval TRUE If the argument is not equal to @p aString, or if the argument is empty.
352 * @retval FALSE If the argument is not empty and equal to @p aString.
353 */
operator !=(const char * aString) const354 bool operator!=(const char *aString) const { return !(*this == aString); }
355
356 /**
357 * Parses the argument as a `uint8_t` value.
358 *
359 * The number is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
360 *
361 * @param[out] aUint8 A reference to an `uint8_t` variable to output the parsed value.
362 *
363 * @retval kErrorNone The argument was parsed successfully.
364 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number (e.g., value out of range).
365 */
ParseAsUint8(uint8_t & aUint8) const366 otError ParseAsUint8(uint8_t &aUint8) const { return CmdLineParser::ParseAsUint8(mString, aUint8); }
367
368 /**
369 * Parses the argument as a `uint16_t` value.
370 *
371 * The number is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
372 *
373 * @param[out] aUint16 A reference to an `uint16_t` variable to output the parsed value.
374 *
375 * @retval kErrorNone The argument was parsed successfully.
376 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number (e.g., value out of range).
377 */
ParseAsUint16(uint16_t & aUint16) const378 otError ParseAsUint16(uint16_t &aUint16) const { return CmdLineParser::ParseAsUint16(mString, aUint16); }
379
380 /**
381 * Parses the argument as a `uint32_t` value.
382 *
383 * The number is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
384 *
385 * @param[out] aUint32 A reference to an `uint32_t` variable to output the parsed value.
386 *
387 * @retval kErrorNone The argument was parsed successfully.
388 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number (e.g., value out of range).
389 */
ParseAsUint32(uint32_t & aUint32) const390 otError ParseAsUint32(uint32_t &aUint32) const { return CmdLineParser::ParseAsUint32(mString, aUint32); }
391
392 /**
393 * Parses the argument as a `uint64_t` value.
394 *
395 * The number is parsed as decimal or hex format (if contains `0x` or `0X` prefix).
396 *
397 * @param[out] aUint64 A reference to an `uint64_t` variable to output the parsed value.
398 *
399 * @retval kErrorNone The argument was parsed successfully.
400 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number (e.g., value out of range).
401 */
ParseAsUint64(uint64_t & aUint64) const402 otError ParseAsUint64(uint64_t &aUint64) const { return CmdLineParser::ParseAsUint64(mString, aUint64); }
403
404 /**
405 * Parses the argument as a `int8_t` value.
406 *
407 * The number is parsed as decimal or hex format (if contains `0x` or `0X` prefix). The string can start with
408 * `+`/`-` sign.
409 *
410 * @param[out] aInt8 A reference to an `int8_t` variable to output the parsed value.
411 *
412 * @retval kErrorNone The argument was parsed successfully.
413 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number (e.g., value out of range).
414 */
ParseAsInt8(int8_t & aInt8) const415 otError ParseAsInt8(int8_t &aInt8) const { return CmdLineParser::ParseAsInt8(mString, aInt8); }
416
417 /**
418 * Parses the argument as a `int16_t` value.
419 *
420 * The number is parsed as decimal or hex format (if contains `0x` or `0X` prefix). The string can start with
421 * `+`/`-` sign.
422 *
423 * @param[out] aInt16 A reference to an `int16_t` variable to output the parsed value.
424 *
425 * @retval kErrorNone The argument was parsed successfully.
426 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number (e.g., value out of range).
427 */
ParseAsInt16(int16_t & aInt16) const428 otError ParseAsInt16(int16_t &aInt16) const { return CmdLineParser::ParseAsInt16(mString, aInt16); }
429
430 /**
431 * Parses the argument as a `int32_t` value.
432 *
433 * The number is parsed as decimal or hex format (if contains `0x` or `0X` prefix). The string can start with
434 * `+`/`-` sign.
435 *
436 * @param[out] aInt32 A reference to an `int32_t` variable to output the parsed value.
437 *
438 * @retval kErrorNone The argument was parsed successfully.
439 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number (e.g., value out of range).
440 */
ParseAsInt32(int32_t & aInt32) const441 otError ParseAsInt32(int32_t &aInt32) const { return CmdLineParser::ParseAsInt32(mString, aInt32); }
442
443 /**
444 * Parses the argument as a `bool` value.
445 *
446 * Zero value is treated as `false`, non-zero value as `true`.
447 *
448 * @param[out] aBool A reference to a `bool` variable to output the parsed value.
449 *
450 * @retval kErrorNone The argument was parsed successfully.
451 * @retval kErrorInvalidArgs The argument is empty or does not contain valid number.
452 */
ParseAsBool(bool & aBool) const453 otError ParseAsBool(bool &aBool) const { return CmdLineParser::ParseAsBool(mString, aBool); }
454
455 #if OPENTHREAD_FTD || OPENTHREAD_MTD
456 /**
457 * Parses the argument as an IPv6 address.
458 *
459 * @param[out] aAddress A reference to an `otIp6Address` to output the parsed IPv6 address.
460 *
461 * @retval kErrorNone The argument was parsed successfully.
462 * @retval kErrorInvalidArgs The argument is empty or does not contain valid IPv6 address.
463 */
ParseAsIp6Address(otIp6Address & aAddress) const464 otError ParseAsIp6Address(otIp6Address &aAddress) const
465 {
466 return CmdLineParser::ParseAsIp6Address(mString, aAddress);
467 }
468
469 /**
470 * Parses the argument as an IPv4 address.
471 *
472 * @param[out] aAddress A reference to an `otIp4Address` to output the parsed IPv4 address.
473 *
474 * @retval kErrorNone The argument was parsed successfully.
475 * @retval kErrorInvalidArgs The argument is empty or does not contain valid IPv4 address.
476 */
ParseAsIp4Address(otIp4Address & aAddress) const477 otError ParseAsIp4Address(otIp4Address &aAddress) const
478 {
479 return CmdLineParser::ParseAsIp4Address(mString, aAddress);
480 }
481
482 /**
483 * Parses the argument as an IPv6 prefix.
484 *
485 * The string is parsed as `{IPv6Address}/{PrefixLength}`.
486 *
487 * @param[out] aPrefix A reference to an `otIp6Prefix` to output the parsed IPv6 prefix.
488 *
489 * @retval kErrorNone The argument was parsed successfully.
490 * @retval kErrorInvalidArgs The argument is empty or does not contain a valid IPv6 prefix.
491 */
ParseAsIp6Prefix(otIp6Prefix & aPrefix) const492 otError ParseAsIp6Prefix(otIp6Prefix &aPrefix) const { return CmdLineParser::ParseAsIp6Prefix(mString, aPrefix); }
493
494 #endif // OPENTHREAD_FTD || OPENTHREAD_MTD
495
496 /**
497 * Parses the argument as a specified value type.
498 *
499 * @tparam Type The value type.
500 *
501 * @param[out] aValue A reference to output the parsed value.
502 *
503 * @retval kErrorNone The argument was parsed successfully.
504 * @retval kErrorInvalidArgs The argument is empty or does not contain a valid value.
505 */
506 template <typename Type> otError ParseAs(Type &aValue) const;
507
508 /**
509 * Parses the argument as a hex string into a byte array of fixed expected size.
510 *
511 * Returns `kErrorNone` only when the hex string contains exactly @p aSize bytes (after parsing). If
512 * there are fewer or more bytes in hex string that @p aSize, the parsed bytes (up to @p aSize) are copied into the
513 * `aBuffer` and `kErrorInvalidArgs` is returned.
514 *
515 * @param[out] aBuffer A pointer to a buffer to output the parsed byte sequence.
516 * @param[in] aSize The expected size of byte sequence (number of bytes after parsing).
517 *
518 * @retval kErrorNone The argument was parsed successfully.
519 * @retval kErrorInvalidArgs The argument is empty or does not contain valid hex bytes and/or not @p aSize bytes.
520 */
ParseAsHexString(uint8_t * aBuffer,uint16_t aSize) const521 otError ParseAsHexString(uint8_t *aBuffer, uint16_t aSize) const
522 {
523 return CmdLineParser::ParseAsHexString(mString, aBuffer, aSize);
524 }
525
526 /**
527 * Parses the argument as a hex string into a a given fixed size array.
528 *
529 * Returns `kErrorNone` only when the hex string contains exactly @p kBufferSize bytes (after parsing).
530 * If there are fewer or more bytes in hex string that @p kBufferSize, the parsed bytes (up to @p kBufferSize) are
531 * copied into the `aBuffer` and `kErrorInvalidArgs` is returned.
532 *
533 * @tparam kBufferSize The byte array size (number of bytes).
534 *
535 * @param[out] aBuffer A reference to a byte array to output the parsed byte sequence.
536 *
537 * @retval kErrorNone The argument was parsed successfully.
538 * @retval kErrorInvalidArgs The argument is empty or does not contain valid hex bytes and/or not @p aSize bytes.
539 */
ParseAsHexString(uint8_t (& aBuffer)[kBufferSize])540 template <uint16_t kBufferSize> otError ParseAsHexString(uint8_t (&aBuffer)[kBufferSize])
541 {
542 return ParseAsHexString(aBuffer, kBufferSize);
543 }
544
545 /**
546 * Parses the argument as a hex string into a byte array.
547 *
548 * Verifies that the parsed hex string bytes fit in @p aBuffer with its given @p aSize.
549 *
550 * @param[in,out] aSize On entry indicates the number of bytes in @p aBuffer (max size of @p aBuffer).
551 * On exit provides number of bytes parsed and copied into @p aBuffer.
552 * @param[out] aBuffer A pointer to a buffer to output the parsed byte sequence.
553 *
554 * @retval kErrorNone The argument was parsed successfully.
555 * @retval kErrorInvalidArgs The argument does not contain valid format or too many bytes.
556 */
ParseAsHexString(uint16_t & aSize,uint8_t * aBuffer)557 otError ParseAsHexString(uint16_t &aSize, uint8_t *aBuffer)
558 {
559 return CmdLineParser::ParseAsHexString(mString, aSize, aBuffer);
560 }
561
562 /**
563 * Copies the argument string pointers from an `Arg` array to a C string array.
564 *
565 * @note this method only copies the string pointer value (i.e., `GetString()` pointer) from `aArgs` array to the
566 * @p aStrings array (the content of strings are not copied).
567 *
568 * @param[in] aArgs An `Arg` array.
569 * @param[out] aStrings An `char *` array to populate with the argument string pointers. The @p aString array
570 * MUST contain at least same number of entries as in @p aArgs array.
571 */
572 static void CopyArgsToStringArray(Arg aArgs[], char *aStrings[]);
573
574 /**
575 * Returns the length of argument array, i.e. number of consecutive non-empty arguments.
576 *
577 * @param[in] aArgs An `Arg` array.
578 *
579 * @returns Number of non-empty arguments in the array.
580 */
581 static uint8_t GetArgsLength(Arg aArgs[]);
582
583 private:
584 char *mString;
585 };
586
587 /**
588 * Parses a given command line string and breaks it into an argument list.
589 *
590 * May change the input @p aCommandString, it will put a '\0' by the end of each argument, and @p aArgs
591 * will point to the arguments in the input @p aCommandString. Backslash ('\') can be used to escape separators
592 * (' ', '\t', '\r', '\n') and the backslash itself.
593 *
594 * As the arguments are parsed, the @p aArgs array entries are populated. Any remaining @p aArgs entries in the array
595 * will be cleared and marked as empty. So the number of arguments can be determined by going through @p aArgs array
596 * entries till we get to an empty `Arg` (i.e., `Arg::IsEmpty()` returns `true).
597 *
598 * Ensures that the last entry in @p aArgs array is always used to indicate the end (always marked as
599 * empty), so the @p aArgs array should have one more entry than the desired max number of arguments.
600 *
601 * @param[in] aCommandString A null-terminated input string.
602 * @param[out] aArgs The argument array.
603 * @param[in] aArgsMaxLength The max length of @p aArgs array.
604 *
605 * @retval OT_ERROR_NONE The command line parsed successfully and @p aArgs array is populated.
606 * @retval OT_ERROR_INVALID_ARGS Too many arguments in @p aCommandString and could not fit in @p aArgs array.
607 */
608 otError ParseCmd(char *aCommandString, Arg aArgs[], uint8_t aArgsMaxLength);
609
ParseCmd(char * aCommandString,Arg (& aArgs)[kLength])610 template <uint8_t kLength> inline otError ParseCmd(char *aCommandString, Arg (&aArgs)[kLength])
611 {
612 return ParseCmd(aCommandString, aArgs, kLength);
613 }
614
615 //- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
616 // Specializations of `Arg::ParseAs<Type>()` method.
617
ParseAs(uint8_t & aValue) const618 template <> inline otError Arg::ParseAs(uint8_t &aValue) const { return ParseAsUint8(aValue); }
619
ParseAs(uint16_t & aValue) const620 template <> inline otError Arg::ParseAs(uint16_t &aValue) const { return ParseAsUint16(aValue); }
621
ParseAs(uint32_t & aValue) const622 template <> inline otError Arg::ParseAs(uint32_t &aValue) const { return ParseAsUint32(aValue); }
623
ParseAs(uint64_t & aValue) const624 template <> inline otError Arg::ParseAs(uint64_t &aValue) const { return ParseAsUint64(aValue); }
625
ParseAs(bool & aValue) const626 template <> inline otError Arg::ParseAs(bool &aValue) const { return ParseAsBool(aValue); }
627
ParseAs(int8_t & aValue) const628 template <> inline otError Arg::ParseAs(int8_t &aValue) const { return ParseAsInt8(aValue); }
629
ParseAs(int16_t & aValue) const630 template <> inline otError Arg::ParseAs(int16_t &aValue) const { return ParseAsInt16(aValue); }
631
ParseAs(int32_t & aValue) const632 template <> inline otError Arg::ParseAs(int32_t &aValue) const { return ParseAsInt32(aValue); }
633
ParseAs(const char * & aValue) const634 template <> inline otError Arg::ParseAs(const char *&aValue) const
635 {
636 return IsEmpty() ? OT_ERROR_INVALID_ARGS : (aValue = GetCString(), OT_ERROR_NONE);
637 }
638
639 #if OPENTHREAD_FTD || OPENTHREAD_MTD
640
ParseAs(otIp6Address & aValue) const641 template <> inline otError Arg::ParseAs(otIp6Address &aValue) const { return ParseAsIp6Address(aValue); }
642
ParseAs(otIp6Prefix & aValue) const643 template <> inline otError Arg::ParseAs(otIp6Prefix &aValue) const { return ParseAsIp6Prefix(aValue); }
644
645 #endif
646
647 /**
648 * @}
649 */
650
651 } // namespace CmdLineParser
652 } // namespace Utils
653 } // namespace ot
654
655 #endif // PARSE_CMD_LINE_HPP_
656