blob: f6f195d5f80d3af512f19cdea25ccc123eb562fa [file] [log] [blame]
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +08001/*
yang.lib06e0a82022-01-10 17:35:09 +08002 * Copyright (c) 2021-2022 Amlogic, Inc. All rights reserved.
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +08003 *
yang.lib06e0a82022-01-10 17:35:09 +08004 * SPDX-License-Identifier: MIT
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +08005 */
Xiaohu.Huang448314d2021-12-31 17:12:48 +08006#include "aml_printf.h"
xiaohu.huang9169c492022-11-18 16:30:06 +08007#include "aml_strnlen.h"
8#include "aml_isdigit.h"
9#include <stdarg.h>
10#include <stddef.h>
Xiaohu.Huang448314d2021-12-31 17:12:48 +080011#if (1 == CONFIG_ARM64)
xiaohu.huang1fd6f112022-05-24 11:02:05 +080012#include "serial.h"
Xiaohu.Huang448314d2021-12-31 17:12:48 +080013#else
xiaohu.huang1fd6f112022-05-24 11:02:05 +080014#include "uart.h"
Xiaohu.Huang448314d2021-12-31 17:12:48 +080015#endif
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +080016
bangzheng.liu207602f2023-04-12 16:06:47 +080017#if CONFIG_RISCV
18#define HAS_FLOAT 0
19#else
xiaohu.huang9169c492022-11-18 16:30:06 +080020#define HAS_FLOAT 1
bangzheng.liu207602f2023-04-12 16:06:47 +080021#endif
xiaohu.huang9169c492022-11-18 16:30:06 +080022#define MAX_BUFFER_LEN 512
23static char printbuffer[MAX_BUFFER_LEN];
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +080024
xiaohu.huang9169c492022-11-18 16:30:06 +080025#define ZEROPAD (1 << 0) /* Pad with zero */
26#define SIGN (1 << 1) /* Unsigned/signed long */
27#define PLUS (1 << 2) /* Show plus */
28#define SPACE (1 << 3) /* Spacer */
29#define LEFT (1 << 4) /* Left justified */
30#define HEX_PREP (1 << 5) /* 0x */
31#define UPPERCASE (1 << 6) /* 'ABCDEF' */
Xiaohu.Huangaa18c4c2021-11-16 17:26:41 +080032
xiaohu.huang9169c492022-11-18 16:30:06 +080033static char *digits = "0123456789abcdefghijklmnopqrstuvwxyz";
34static char *upper_digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
35
36static int skip_atoi(const char **s)
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +080037{
xiaohu.huang9169c492022-11-18 16:30:06 +080038 int i = 0;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +080039
xiaohu.huang9169c492022-11-18 16:30:06 +080040 while (isdigit(**s))
41 i = i * 10 + *((*s)++) - '0';
42
43 return i;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +080044}
45
xiaohu.huang9169c492022-11-18 16:30:06 +080046static char *number(char *str, long num, int base, int size, int precision, int type)
Xiaohu.Huangaa18c4c2021-11-16 17:26:41 +080047{
xiaohu.huang9169c492022-11-18 16:30:06 +080048 char c, sign, tmp[66];
49 char *dig = digits;
50 int i;
Xiaohu.Huangaa18c4c2021-11-16 17:26:41 +080051
xiaohu.huang9169c492022-11-18 16:30:06 +080052 if (type & UPPERCASE)
53 dig = upper_digits;
54 if (type & LEFT)
55 type &= ~ZEROPAD;
56 if (base < 2 || base > 36)
Xiaohu.Huangaa18c4c2021-11-16 17:26:41 +080057 return 0;
Xiaohu.Huangaa18c4c2021-11-16 17:26:41 +080058
xiaohu.huang9169c492022-11-18 16:30:06 +080059 c = (type & ZEROPAD) ? '0' : ' ';
60 sign = 0;
61 if (type & SIGN) {
62 if (num < 0) {
63 sign = '-';
64 num = -num;
65 size--;
66 } else if (type & PLUS) {
67 sign = '+';
68 size--;
69 } else if (type & SPACE) {
70 sign = ' ';
71 size--;
Xiaohu.Huangaa18c4c2021-11-16 17:26:41 +080072 }
73 }
xiaohu.huang9169c492022-11-18 16:30:06 +080074
75 if (type & HEX_PREP) {
76 if (base == 16)
77 size -= 2;
78 else if (base == 8)
79 size--;
80 }
81
82 i = 0;
83
84 if (num == 0)
85 tmp[i++] = '0';
86 else {
87 while (num != 0) {
88 tmp[i++] = dig[((unsigned long)num) % (unsigned int)base];
89 num = ((unsigned long)num) / (unsigned int)base;
90 }
91 }
92
93 if (i > precision)
94 precision = i;
95 size -= precision;
96 if (!(type & (ZEROPAD | LEFT)))
97 while (size-- > 0)
98 *str++ = ' ';
99 if (sign)
100 *str++ = sign;
101
102 if (type & HEX_PREP) {
103 if (base == 8)
104 *str++ = '0';
105 else if (base == 16) {
106 *str++ = '0';
107 *str++ = digits[33];
108 }
109 }
110
111 if (!(type & LEFT))
112 while (size-- > 0)
113 *str++ = c;
114 while (i < precision--)
115 *str++ = '0';
116 while (i-- > 0)
117 *str++ = tmp[i];
118 while (size-- > 0)
119 *str++ = ' ';
120
121 return str;
Xiaohu.Huangaa18c4c2021-11-16 17:26:41 +0800122}
123
xiaohu.huang9169c492022-11-18 16:30:06 +0800124static char *eaddr(char *str, unsigned char *addr, int size, int precision, int type)
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800125{
xiaohu.huang9169c492022-11-18 16:30:06 +0800126 char tmp[24];
127 char *dig = digits;
128 int i, len;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800129
xiaohu.huang9169c492022-11-18 16:30:06 +0800130 if (type & UPPERCASE)
131 dig = upper_digits;
132 len = 0;
133 for (i = 0; i < 6; i++) {
134 if (i != 0)
135 tmp[len++] = ':';
136 tmp[len++] = dig[addr[i] >> 4];
137 tmp[len++] = dig[addr[i] & 0x0F];
138 }
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800139
xiaohu.huang9169c492022-11-18 16:30:06 +0800140 if (!(type & LEFT))
141 while (len < size--)
142 *str++ = ' ';
143 for (i = 0; i < len; ++i)
144 *str++ = tmp[i];
145 while (len < size--)
146 *str++ = ' ';
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800147
xiaohu.huang9169c492022-11-18 16:30:06 +0800148 return str;
149}
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800150
xiaohu.huang9169c492022-11-18 16:30:06 +0800151static char *iaddr(char *str, unsigned char *addr, int size, int precision, int type)
152{
153 char tmp[24];
154 int i, n, len;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800155
xiaohu.huang9169c492022-11-18 16:30:06 +0800156 len = 0;
157 for (i = 0; i < 4; i++) {
158 if (i != 0)
159 tmp[len++] = '.';
160 n = addr[i];
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800161
xiaohu.huang9169c492022-11-18 16:30:06 +0800162 if (n == 0)
163 tmp[len++] = digits[0];
164 else {
165 if (n >= 100) {
166 tmp[len++] = digits[n / 100];
167 n = n % 100;
168 tmp[len++] = digits[n / 10];
169 n = n % 10;
170 } else if (n >= 10) {
171 tmp[len++] = digits[n / 10];
172 n = n % 10;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800173 }
174
xiaohu.huang9169c492022-11-18 16:30:06 +0800175 tmp[len++] = digits[n];
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800176 }
177 }
178
xiaohu.huang9169c492022-11-18 16:30:06 +0800179 if (!(type & LEFT))
180 while (len < size--)
181 *str++ = ' ';
182 for (i = 0; i < len; ++i)
183 *str++ = tmp[i];
184 while (len < size--)
185 *str++ = ' ';
186
187 return str;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800188}
xiaohu.huang1fd6f112022-05-24 11:02:05 +0800189
xiaohu.huang9169c492022-11-18 16:30:06 +0800190char *ecvtbuf(double arg, int ndigits, int *decpt, int *sign, char *buf);
191char *fcvtbuf(double arg, int ndigits, int *decpt, int *sign, char *buf);
192static void ee_bufcpy(char *d, char *s, int count);
193
194void ee_bufcpy(char *pd, char *ps, int count)
195{
196 char *pe = ps + count;
197
198 while (ps != pe)
199 *pd++ = *ps++;
200}
201
202static void parse_float(double value, char *buffer, char fmt, int precision)
203{
204 int decpt, sign, exp, pos;
205 char *digits = NULL;
206 char cvtbuf[80];
207 int capexp = 0;
208 int magnitude;
209
210 if (fmt == 'G' || fmt == 'E') {
211 capexp = 1;
212 fmt += 'a' - 'A';
213 }
214
215 if (fmt == 'g') {
216 digits = ecvtbuf(value, precision, &decpt, &sign, cvtbuf);
217 magnitude = decpt - 1;
218 if (magnitude < -4 || magnitude > precision - 1) {
219 fmt = 'e';
220 precision -= 1;
221 } else {
222 fmt = 'f';
223 precision -= decpt;
224 }
225 }
226
227 if (fmt == 'e') {
228 digits = ecvtbuf(value, precision + 1, &decpt, &sign, cvtbuf);
229
230 if (sign)
231 *buffer++ = '-';
232 *buffer++ = *digits;
233 if (precision > 0)
234 *buffer++ = '.';
235 ee_bufcpy(buffer, digits + 1, precision);
236 buffer += precision;
237 *buffer++ = capexp ? 'E' : 'e';
238
239 if (decpt == 0) {
240 if (value == 0.0)
241 exp = 0;
242 else
243 exp = -1;
244 } else
245 exp = decpt - 1;
246
247 if (exp < 0) {
248 *buffer++ = '-';
249 exp = -exp;
250 } else
251 *buffer++ = '+';
252
253 buffer[2] = (exp % 10) + '0';
254 exp = exp / 10;
255 buffer[1] = (exp % 10) + '0';
256 exp = exp / 10;
257 buffer[0] = (exp % 10) + '0';
258 buffer += 3;
259 } else if (fmt == 'f') {
260 digits = fcvtbuf(value, precision, &decpt, &sign, cvtbuf);
261 if (sign)
262 *buffer++ = '-';
263 if (*digits) {
264 if (decpt <= 0) {
265 *buffer++ = '0';
266 *buffer++ = '.';
267 for (pos = 0; pos < -decpt; pos++)
268 *buffer++ = '0';
269 while (*digits)
270 *buffer++ = *digits++;
271 } else {
272 pos = 0;
273 while (*digits) {
274 if (pos++ == decpt)
275 *buffer++ = '.';
276 *buffer++ = *digits++;
277 }
278 }
279 } else {
280 *buffer++ = '0';
281 if (precision > 0) {
282 *buffer++ = '.';
283 for (pos = 0; pos < precision; pos++)
284 *buffer++ = '0';
285 }
286 }
287 }
288
289 *buffer = '\0';
290}
291
292static void decimal_point(char *buffer)
293{
294 while (*buffer) {
295 if (*buffer == '.')
296 return;
297 if (*buffer == 'e' || *buffer == 'E')
298 break;
299 buffer++;
300 }
301
302 if (*buffer) {
303 int n = strnlen(buffer, 256);
304
305 while (n > 0) {
306 buffer[n + 1] = buffer[n];
307 n--;
308 }
309
310 *buffer = '.';
311 } else {
312 *buffer++ = '.';
313 *buffer = '\0';
314 }
315}
316
317static void cropzeros(char *buffer)
318{
319 char *stop;
320
321 while (*buffer && *buffer != '.')
322 buffer++;
323 if (*buffer++) {
324 while (*buffer && *buffer != 'e' && *buffer != 'E')
325 buffer++;
326 stop = buffer--;
327 while (*buffer == '0')
328 buffer--;
329 if (*buffer == '.')
330 buffer--;
331 while (buffer != stop)
332 *++buffer = 0;
333 }
334}
335
336static char *flt(char *str, double num, int size, int precision, char fmt, int flags)
337{
338 char tmp[80];
339 char c, sign;
340 int n, i;
341
342 // Left align means no zero padding
343 if (flags & LEFT)
344 flags &= ~ZEROPAD;
345
346 // Determine padding and sign char
347 c = (flags & ZEROPAD) ? '0' : ' ';
348 sign = 0;
349 if (flags & SIGN) {
350 if (num < 0.0) {
351 sign = '-';
352 num = -num;
353 size--;
354 } else if (flags & PLUS) {
355 sign = '+';
356 size--;
357 } else if (flags & SPACE) {
358 sign = ' ';
359 size--;
360 }
361 }
362
363 // Compute the precision value
364 if (precision < 0)
365 precision = 6; // Default precision: 6
366
367 // Convert floating point number to text
368 parse_float(num, tmp, fmt, precision);
369
370 if ((flags & HEX_PREP) && precision == 0)
371 decimal_point(tmp);
372 if (fmt == 'g' && !(flags & HEX_PREP))
373 cropzeros(tmp);
374
375 n = strnlen(tmp, 256);
376
377 // Output number with alignment and padding
378 size -= n;
379 if (!(flags & (ZEROPAD | LEFT)))
380 while (size-- > 0)
381 *str++ = ' ';
382 if (sign)
383 *str++ = sign;
384 if (!(flags & LEFT))
385 while (size-- > 0)
386 *str++ = c;
387 for (i = 0; i < n; i++)
388 *str++ = tmp[i];
389 while (size-- > 0)
390 *str++ = ' ';
391
392 return str;
393}
394
395int aml_vsprintf(char *buf, const char *fmt, va_list args)
396{
397 int len;
398 unsigned long num;
399 int i, base;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800400 char *str;
xiaohu.huang9169c492022-11-18 16:30:06 +0800401 char *s;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800402
xiaohu.huang9169c492022-11-18 16:30:06 +0800403 int flags; // Flags to number()
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800404
xiaohu.huang9169c492022-11-18 16:30:06 +0800405 int field_width; // Width of output field
406 int precision; // Min. # of digits for integers; max number of chars for from string
407 int qualifier; // 'h', 'l', or 'L' for integer fields
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800408
xiaohu.huang9169c492022-11-18 16:30:06 +0800409 for (str = buf; *fmt; fmt++) {
410 if (*fmt != '%') {
411 *str++ = *fmt;
412 continue;
413 }
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800414
xiaohu.huang9169c492022-11-18 16:30:06 +0800415 // Process flags
416 flags = 0;
417repeat:
418 fmt++; // This also skips first '%'
419 switch (*fmt) {
420 case '-':
421 flags |= LEFT;
422 goto repeat;
423 case '+':
424 flags |= PLUS;
425 goto repeat;
426 case ' ':
427 flags |= SPACE;
428 goto repeat;
429 case '#':
430 flags |= HEX_PREP;
431 goto repeat;
432 case '0':
433 flags |= ZEROPAD;
434 goto repeat;
435 }
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800436
xiaohu.huang9169c492022-11-18 16:30:06 +0800437 // Get field width
438 field_width = -1;
439 if (isdigit(*fmt))
440 field_width = skip_atoi(&fmt);
441 else if (*fmt == '*') {
442 fmt++;
443 field_width = va_arg(args, int);
444 if (field_width < 0) {
445 field_width = -field_width;
446 flags |= LEFT;
447 }
448 }
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800449
xiaohu.huang9169c492022-11-18 16:30:06 +0800450 // Get the precision
451 precision = -1;
452 if (*fmt == '.') {
453 ++fmt;
454 if (isdigit(*fmt))
455 precision = skip_atoi(&fmt);
456 else if (*fmt == '*') {
457 ++fmt;
458 precision = va_arg(args, int);
459 }
460 if (precision < 0)
461 precision = 0;
462 }
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800463
xiaohu.huang9169c492022-11-18 16:30:06 +0800464 // Get the conversion qualifier
465 qualifier = -1;
466 if (*fmt == 'l' || *fmt == 'L') {
467 qualifier = *fmt;
468 fmt++;
469 }
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800470
xiaohu.huang9169c492022-11-18 16:30:06 +0800471 // Default base
472 base = 10;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800473
xiaohu.huang9169c492022-11-18 16:30:06 +0800474 switch (*fmt) {
475 case 'c':
476 if (!(flags & LEFT))
477 while (--field_width > 0)
478 *str++ = ' ';
479 *str++ = (unsigned char)va_arg(args, int);
480 while (--field_width > 0)
481 *str++ = ' ';
482 continue;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800483
xiaohu.huang9169c492022-11-18 16:30:06 +0800484 case 's':
485 s = va_arg(args, char *);
486 if (!s)
487 s = "<NULL>";
488 len = strnlen(s, MAX_BUFFER_LEN - (str-buf) - 1);
489 if (!(flags & LEFT))
490 while (len < field_width--)
491 *str++ = ' ';
492 for (i = 0; i < len; ++i)
493 *str++ = *s++;
494 while (len < field_width--)
495 *str++ = ' ';
496 continue;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800497
xiaohu.huang9169c492022-11-18 16:30:06 +0800498 case 'p':
499 if (field_width == -1) {
500 field_width = 2 * sizeof(void *);
501 flags |= ZEROPAD;
502 }
503 str = number(str, (unsigned long)va_arg(args, void *), 16, field_width,
504 precision, flags);
505 continue;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800506
xiaohu.huang9169c492022-11-18 16:30:06 +0800507 case 'A':
508 flags |= UPPERCASE;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800509
xiaohu.huang9169c492022-11-18 16:30:06 +0800510 case 'a':
511 if (qualifier == 'l')
512 str = eaddr(str, va_arg(args, unsigned char *), field_width,
513 precision, flags);
514 else
515 str = iaddr(str, va_arg(args, unsigned char *), field_width,
516 precision, flags);
517 continue;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800518
xiaohu.huang9169c492022-11-18 16:30:06 +0800519 // Integer number formats - set up the flags and "break"
520 case 'o':
521 base = 8;
522 break;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800523
xiaohu.huang9169c492022-11-18 16:30:06 +0800524 case 'X':
525 flags |= UPPERCASE;
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800526
xiaohu.huang9169c492022-11-18 16:30:06 +0800527 case 'x':
528 base = 16;
529 break;
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800530
xiaohu.huang9169c492022-11-18 16:30:06 +0800531 case 'd':
532 case 'i':
533 flags |= SIGN;
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800534
xiaohu.huang9169c492022-11-18 16:30:06 +0800535 case 'u':
536 break;
537
538#if HAS_FLOAT
539 case 'f':
540 str = flt(str, va_arg(args, double), field_width, precision, *fmt,
541 flags | SIGN);
542 continue;
543
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800544#endif
xiaohu.huang9169c492022-11-18 16:30:06 +0800545
546 default:
547 if (*fmt != '%')
548 *str++ = '%';
549 if (*fmt)
550 *str++ = *fmt;
551 else
552 --fmt;
553 continue;
554 }
555
556 if (qualifier == 'l')
557 num = va_arg(args, unsigned long);
558 else if (flags & SIGN)
559 num = va_arg(args, int);
560 else
561 num = va_arg(args, unsigned int);
562
563 str = number(str, num, base, field_width, precision, flags);
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800564 }
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800565
xiaohu.huang9169c492022-11-18 16:30:06 +0800566 *str = '\0';
567 return str - buf;
bin.chenf2a61ab2022-01-07 17:29:02 +0800568}
569
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800570int printf(const char *fmt, ...)
571{
572 va_list args;
xiaohu.huang9169c492022-11-18 16:30:06 +0800573 char *p = printbuffer;
574 int n = 0;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800575
576 va_start(args, fmt);
xiaohu.huang9169c492022-11-18 16:30:06 +0800577 aml_vsprintf(printbuffer, fmt, args);
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800578 va_end(args);
xiaohu.huang9169c492022-11-18 16:30:06 +0800579
580 while (*p) {
581 if ('\n' == *p) {
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800582#if (1 == CONFIG_ARM64)
xiaohu.huang9169c492022-11-18 16:30:06 +0800583 vSerialPutChar(ConsoleSerial, '\r');
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800584#else
xiaohu.huang9169c492022-11-18 16:30:06 +0800585 vUartPutc('\r');
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800586#endif
xiaohu.huang9169c492022-11-18 16:30:06 +0800587 n++;
588 }
589#if (1 == CONFIG_ARM64)
590 vSerialPutChar(ConsoleSerial, *p);
591#else
592 vUartPutc(*p);
593#endif
594 n++;
595 p++;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800596 }
xiaohu.huang9169c492022-11-18 16:30:06 +0800597
598 return n;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800599}
600
xiaohu.huang9169c492022-11-18 16:30:06 +0800601int iprintf(const char *fmt, ...)
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800602{
xiaohu.huang9169c492022-11-18 16:30:06 +0800603 va_list args;
604 int n = 0;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800605
xiaohu.huang9169c492022-11-18 16:30:06 +0800606 va_start(args, fmt);
607 n = printf(fmt, args);
608 va_end(args);
609
610 return n;
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800611}
612
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800613int puts(const char *str)
614{
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800615#if (1 == CONFIG_ARM64)
xiaohu.huang9169c492022-11-18 16:30:06 +0800616 return vSerialPutString(ConsoleSerial, str);
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800617#else
xiaohu.huang9169c492022-11-18 16:30:06 +0800618 return vUartPuts(str);
Xiaohu.Huang448314d2021-12-31 17:12:48 +0800619#endif
Xiaohu.Huang60a7f2f2021-10-25 15:40:57 +0800620}