• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2020 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "stdio.h"
17 #include <stdarg.h>
18 #include <securec.h>
19 #include "fcntl.h"
20 #include "unistd.h"
21 #include <log.h>
22 
23 #ifndef LOSCFG_BASE_CORE_HILOG
24 #include <stdatomic.h>
25 #include "hilog_trace.h"
26 #endif
27 
28 typedef int SecInt32;
29 typedef unsigned int SecUnsignedInt32;
30 typedef long long SecInt64;
31 typedef unsigned long long SecUnsignedInt64;
32 
33 #ifndef LOSCFG_BASE_CORE_HILOG
34 static RegisterFunc g_registerFunc = NULL;
35 static atomic_int g_hiLogGetIdCallCount = 0;
36 #endif
37 
38 #define SECUREC_BUFFER_SIZE 256
39 
40 #define SECUREC_MAX_PRECISION SECUREC_BUFFER_SIZE
41 /* max. # bytes in multibyte char  ,see MB_LEN_MAX */
42 #define SECUREC_MB_LEN 16
43 
44 /* state definitions */
45 #define SECUREC_FLAG_SIGN 0x00001U
46 #define SECUREC_FLAG_SIGN_SPACE 0x00002U
47 #define SECUREC_FLAG_LEFT 0x00004U
48 #define SECUREC_FLAG_LEADZERO 0x00008U
49 #define SECUREC_FLAG_LONG 0x00010U
50 #define SECUREC_FLAG_SHORT 0x00020U
51 #define SECUREC_FLAG_SIGNED 0x00040U
52 #define SECUREC_FLAG_ALTERNATE 0x00080U
53 #define SECUREC_FLAG_NEGATIVE 0x00100U
54 #define SECUREC_FLAG_FORCE_OCTAL 0x00200U
55 #define SECUREC_FLAG_LONG_DOUBLE 0x00400U
56 #define SECUREC_FLAG_WIDECHAR 0x00800U
57 #define SECUREC_FLAG_LONGLONG 0x01000U
58 #define SECUREC_FLAG_CHAR 0x02000U
59 #define SECUREC_FLAG_POINTER 0x04000U
60 #define SECUREC_FLAG_I64 0x08000U
61 #define SECUREC_FLAG_PTRDIFF 0x10000U
62 #define SECUREC_FLAG_SIZE 0x20000U
63 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
64 #define SECUREC_FLAG_INTMAX 0x40000U
65 #endif
66 
67 
68 typedef enum {
69     STAT_NORMAL,
70     STAT_PERCENT,
71     STAT_FLAG,
72     STAT_WIDTH,
73     STAT_DOT,
74     STAT_PRECIS,
75     STAT_SIZE,
76     STAT_TYPE,
77     STAT_INVALID
78 } SecFmtState;
79 
80 #define SECUREC_PRINTF_TRUNCATE (-2)
81 typedef struct {
82     int count;
83     char *cur;
84 } SecPrintfStream;
85 #define SECUREC_ERROR_INVALID_PARAMTER(msg) printf("%s invalid argument\n", msg)
86 #define SECUREC_ERROR_INVALID_RANGE(msg) printf("%s invalid dest buffer size\n", msg)
87 #define SECUREC_ERROR_BUFFER_OVERLAP(msg) printf("%s buffer overlap\n", msg)
88 
89 // Log type
90 #define LOG_BUF_SIZE (1024)
91 #define MAX_DOMAIN_TAG_SIZE 64
92 #define IOV_SIZE (3)
93 #define HILOG_IOV_SIZE 4
94 #define HITRACE_BUF_SIZE 128
95 #define MAX_INIT_RETRIES (500)
96 #define DOMAIN_MIN 0x0D000000
97 #define DOMAIN_MAX 0x0E000000
98 
99 #define SECUREC_FLOAT_BUFSIZE (309 + 40)     /* max float point value */
100 #define SECUREC_FLOAT_BUFSIZE_LB (4932 + 40) /* max long double value */
101 
102 #define SECUREC_INT_MAX 2147483647
103 
104 #define SECUREC_MUL10(x) ((((x) << 2) + (x)) << 1)
105 #define SECUREC_INT_MAX_DIV_TEN 21474836
106 #define SECUREC_MUL10_ADD_BEYOND_MAX(val) (((val) > SECUREC_INT_MAX_DIV_TEN))
107 
108 #ifdef SECUREC_STACK_SIZE_LESS_THAN_1K
109 #define SECUREC_FMT_STR_LEN (8)
110 #else
111 #define SECUREC_FMT_STR_LEN (16)
112 #endif
113 
114 #ifndef SECUREC_PUTC
115 #define SECUREC_PUTC(_c, _stream) ((--(_stream)->count >= 0) ? (*(_stream)->cur++ = (char)(_c)) : EOF)
116 #endif
117 /* to clear e835 */
118 #ifndef SECUREC_PUTC_ZERO
119 #define SECUREC_PUTC_ZERO(_stream) ((--(_stream)->count >= 0) ? ((*(_stream)->cur++ = (char)('\0'))) : EOF)
120 #endif
121 
122 #ifndef SECUREC_MALLOC
123 #define SECUREC_MALLOC(x) malloc((size_t)(x))
124 #endif
125 
126 #ifndef SECUREC_FREE
127 #define SECUREC_FREE(x) free((void *)(x))
128 #endif
129 
130 typedef char SecChar;
131 #define SECUREC_CHAR(x) x
132 /* put a char to output */
133 #define SECUREC_PUTC(_c, _stream) ((--(_stream)->count >= 0) ? (*(_stream)->cur++ = (char)(_c)) : EOF)
134 /* to clear e835 */
135 
136 #define SECUREC_PUTC_ZERO(_stream) ((--(_stream)->count >= 0) ? ((*(_stream)->cur++ = (char)('\0'))) : EOF)
137 
SecPutWcharStrEndingZero(SecPrintfStream * str,int zeroNum)138 int SecPutWcharStrEndingZero(SecPrintfStream *str, int zeroNum)
139 {
140     int succeed = 0;
141     int i;
142 
143     for (i = 0; i < zeroNum && (SECUREC_PUTC_ZERO(str) != EOF); ++i) {
144     }
145     if (i == zeroNum) {
146         succeed = 1;
147     }
148     return succeed;
149 }
150 
SecWriteMultiChar(char ch,int num,SecPrintfStream * f,int * pnumwritten)151 void SecWriteMultiChar(char ch, int num, SecPrintfStream *f, int *pnumwritten)
152 {
153     int count = num;
154     while (count-- > 0) {
155         if (SECUREC_PUTC(ch, f) == EOF) {
156             *pnumwritten = -1;
157             break;
158         } else {
159             ++(*pnumwritten);
160         }
161     }
162 }
163 
SecWriteString(const char * string,int len,SecPrintfStream * f,int * pnumwritten)164 void SecWriteString(const char *string, int len, SecPrintfStream *f, int *pnumwritten)
165 {
166     const char *str = string;
167     int count = len;
168     while (count-- > 0) {
169         if (SECUREC_PUTC(*str, f) == EOF) {
170             *pnumwritten = -1;
171             break;
172         } else {
173             ++(*pnumwritten);
174             ++str;
175         }
176     }
177 }
178 
179 #ifndef LOSCFG_BASE_CORE_HILOG
HiLogRegisterGetIdFun(RegisterFunc registerFunc)180 int HiLogRegisterGetIdFun(RegisterFunc registerFunc)
181 {
182     if (g_registerFunc != NULL) {
183         return -1;
184     }
185     g_registerFunc = registerFunc;
186     return 0;
187 }
188 
HiLogUnregisterGetIdFun(RegisterFunc registerFunc)189 void HiLogUnregisterGetIdFun(RegisterFunc registerFunc)
190 {
191     if (g_registerFunc != registerFunc) {
192         return;
193     }
194 
195     g_registerFunc = NULL;
196     while (atomic_load(&g_hiLogGetIdCallCount) != 0) {
197         /* do nothing, just wait current callback return */
198     }
199 
200     return;
201 }
202 #endif
203 
204 #define SECUREC_WRITE_MULTI_CHAR SecWriteMultiChar
205 #define SECUREC_WRITE_STRING SecWriteString
206 
207 typedef struct {
208     unsigned int flags;
209     int fldWidth;
210     int precision;
211     int bufferIsWide; /* flag for buffer contains wide chars */
212     int dynWidth;     /* %*   1 width from variable parameter ;0 not */
213     int dynPrecision; /* %.*  1 precision from variable parameter ;0 not */
214 } SecFormatAttr;
215 
216 typedef union {
217     char *str; /* not a null terminated  string */
218     wchar_t *wStr;
219 } SecFormatBuf;
220 
221 typedef union {
222     char str[SECUREC_BUFFER_SIZE + 1];
223 #ifdef SECUREC_FOR_WCHAR
224     wchar_t wStr[SECUREC_BUFFER_SIZE + 1];
225 #endif
226 } SecBuffer;
227 
228 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
229 /* to clear e506 warning */
SecIsSameSize(size_t sizeA,size_t sizeB)230 static int SecIsSameSize(size_t sizeA, size_t sizeB)
231 {
232     return sizeA == sizeB;
233 }
234 #endif
235 #define SECUREC_WHILE_ZERO while (0)
236 
237 #define SECUREC_SPECIAL(_val, Base) case Base:                                      \
238         do {                                        \
239             *--formatBuf.str = digits[_val % Base]; \
240         } while ((_val /= Base) != 0)
241 
242 #define SECUREC_SAFE_WRITE_PREFIX(src, txtLen, _stream, outChars) \
243     do {                                                          \
244         for (ii = 0; ii < txtLen; ++ii) {                         \
245             *((SecChar *)(void *)(_stream->cur)) = *(src);        \
246             _stream->cur += sizeof(SecChar);                      \
247             ++(src);                                              \
248         }                                                         \
249         _stream->count -= txtLen * (int)(sizeof(SecChar));        \
250         *(outChars) = *(outChars) + (txtLen);                     \
251     }                                                             \
252     SECUREC_WHILE_ZERO
253 #define MOBILE_NUMBER_LENGTH 12
254 #define SECUREC_SAFE_WRITE_STR(src, txtLen, _stream, outChars)                                    \
255     do {                                                                                          \
256         if (txtLen < MOBILE_NUMBER_LENGTH) {                                                      \
257             for (ii = 0; ii < txtLen; ++ii) {                                                     \
258                 *((SecChar *)(void *)(_stream->cur)) = *(src);                                    \
259                 _stream->cur += sizeof(SecChar);                                                  \
260                 ++(src);                                                                          \
261             }                                                                                     \
262         } else {                                                                                  \
263             (void)memcpy_s(_stream->cur, ((size_t)(unsigned int)txtLen * (sizeof(SecChar))), src, \
264                 ((size_t)(unsigned int)txtLen * (sizeof(SecChar))));                              \
265             _stream->cur += (size_t)(unsigned int)txtLen * (sizeof(SecChar));                     \
266         }                                                                                         \
267         _stream->count -= txtLen * (int)(sizeof(SecChar));                                        \
268         *(outChars) = *(outChars) + (txtLen);                                                     \
269     }                                                                                             \
270     SECUREC_WHILE_ZERO
271 
272 #define SECUREC_SAFE_WRITE_CHAR(_ch, _stream, outChars) do {                                                     \
273         *((SecChar *)(void *)(_stream->cur)) = (SecChar)_ch; \
274         _stream->cur += sizeof(SecChar);                     \
275         _stream->count -= (int)(sizeof(SecChar));            \
276         *(outChars) = *(outChars) + 1;                       \
277     }                                                        \
278     SECUREC_WHILE_ZERO
279 
280 #define SECUREC_SAFE_PADDING(padChar, padLen, _stream, outChars)     \
281     do {                                                             \
282         for (ii = 0; ii < padLen; ++ii) {                            \
283             *((SecChar *)(void *)(_stream->cur)) = (SecChar)padChar; \
284             _stream->cur += sizeof(SecChar);                         \
285         }                                                            \
286         _stream->count -= padLen * (int)(sizeof(SecChar));           \
287         *(outChars) = *(outChars) + (padLen);                        \
288     }                                                                \
289     SECUREC_WHILE_ZERO
290 
291 /* The count variable can be reduced to 0, and the external function complements the \0 terminator. */
292 #define SECUREC_IS_REST_BUF_ENOUGH(needLen) ((int)(stream->count - (int)needLen * (int)(sizeof(SecChar))) >= 0)
293 
294 #define SECUREC_FMT_STATE_OFFSET 256
295 #ifdef SECUREC_FOR_WCHAR
296 #define SECUREC_FMT_TYPE(c, fmtTable) \
297     ((((unsigned int)(int)(c)) <= (unsigned int)(int)SECUREC_CHAR('~')) ? (fmtTable[(unsigned char)(c)]) : 0)
298 #define SECUREC_DECODE_STATE(c, fmtTable, laststate)                                               \
299     (SecFmtState)(((fmtTable[(SECUREC_FMT_TYPE(c, fmtTable)) * ((unsigned char)STAT_INVALID + 1) + \
300         (unsigned char)(laststate) + SECUREC_FMT_STATE_OFFSET])))
301 #else
302 #define SECUREC_DECODE_STATE(c, fmtTable, laststate)                                             \
303     (SecFmtState)((fmtTable[(fmtTable[(unsigned char)(c)]) * ((unsigned char)STAT_INVALID + 1) + \
304         (unsigned char)(laststate) + SECUREC_FMT_STATE_OFFSET]))
305 #endif
306 
SecDecodeFlags(SecChar ch,SecFormatAttr * attr)307 static void SecDecodeFlags(SecChar ch, SecFormatAttr *attr)
308 {
309     switch (ch) {
310         case SECUREC_CHAR(' '):
311             attr->flags |= SECUREC_FLAG_SIGN_SPACE;
312             break;
313         case SECUREC_CHAR('+'):
314             attr->flags |= SECUREC_FLAG_SIGN;
315             break;
316         case SECUREC_CHAR('-'):
317             attr->flags |= SECUREC_FLAG_LEFT;
318             break;
319         case SECUREC_CHAR('0'):
320             attr->flags |= SECUREC_FLAG_LEADZERO; /* add zero th the front */
321             break;
322         case SECUREC_CHAR('#'):
323             attr->flags |= SECUREC_FLAG_ALTERNATE; /* output %x with 0x */
324             break;
325         default:
326             break;
327     }
328     return;
329 }
330 
SecDecodeSize(SecChar ch,SecFormatAttr * attr,const SecChar ** format)331 static int SecDecodeSize(SecChar ch, SecFormatAttr *attr, const SecChar **format)
332 {
333     switch (ch) {
334 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
335         case SECUREC_CHAR('j'):
336             attr->flags |= SECUREC_FLAG_INTMAX;
337             break;
338 #endif
339         case SECUREC_CHAR('q'): /* fall-through */ /* FALLTHRU */
340         case SECUREC_CHAR('L'):
341             attr->flags |= SECUREC_FLAG_LONGLONG | SECUREC_FLAG_LONG_DOUBLE;
342             break;
343         case SECUREC_CHAR('l'):
344             if (**format == SECUREC_CHAR('l')) {
345                 ++(*format);
346                 attr->flags |= SECUREC_FLAG_LONGLONG; /* long long */
347             } else {
348                 attr->flags |= SECUREC_FLAG_LONG; /* long int or wchar_t */
349             }
350             break;
351         case SECUREC_CHAR('t'):
352             attr->flags |= SECUREC_FLAG_PTRDIFF;
353             break;
354 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
355         case SECUREC_CHAR('z'):
356             attr->flags |= SECUREC_FLAG_SIZE;
357             break;
358         case SECUREC_CHAR('Z'):
359             attr->flags |= SECUREC_FLAG_SIZE;
360             break;
361 #endif
362 
363         case SECUREC_CHAR('I'):
364 #ifdef SECUREC_ON_64BITS
365             attr->flags |= SECUREC_FLAG_I64; /* %I  to  INT64 */
366 #endif
367             if ((**format == SECUREC_CHAR('6')) && (*((*format) + 1) == SECUREC_CHAR('4'))) {
368                 (*format) += 2;
369                 attr->flags |= SECUREC_FLAG_I64; /* %I64  to  INT64 */
370             } else if ((**format == SECUREC_CHAR('3')) && (*((*format) + 1) == SECUREC_CHAR('2'))) {
371                 (*format) += 2;
372                 attr->flags &= ~SECUREC_FLAG_I64; /* %I64  to  INT32 */
373             } else if ((**format == SECUREC_CHAR('d')) || (**format == SECUREC_CHAR('i')) ||
374                 (**format == SECUREC_CHAR('o')) || (**format == SECUREC_CHAR('u')) || (**format == SECUREC_CHAR('x')) ||
375                 (**format == SECUREC_CHAR('X'))) {
376                 /* do nothing */
377             } else {
378                 /* Compatibility  code for "%I" just print I */
379                 return -1;
380             }
381             break;
382 
383         case SECUREC_CHAR('h'):
384             if (**format == SECUREC_CHAR('h'))
385                 attr->flags |= SECUREC_FLAG_CHAR; /* char */
386             else
387                 attr->flags |= SECUREC_FLAG_SHORT; /* short int */
388             break;
389 
390         case SECUREC_CHAR('w'):
391             attr->flags |= SECUREC_FLAG_WIDECHAR; /* wide char */
392             break;
393         default:
394             break;
395     }
396 
397     return 0;
398 }
399 
SecDecodeTypeC(SecFormatAttr * attr,unsigned int cValue,SecFormatBuf * formatBuf,SecBuffer * buffer)400 static int SecDecodeTypeC(SecFormatAttr *attr, unsigned int cValue, SecFormatBuf *formatBuf, SecBuffer *buffer)
401 {
402     int textLen;
403     wchar_t wchar;
404 
405 #if (defined(SECUREC_COMPATIBLE_LINUX_FORMAT)) && !(defined(__hpux)) && !(defined(SECUREC_ON_SOLARIS))
406     attr->flags &= ~SECUREC_FLAG_LEADZERO;
407 #endif
408 
409 #ifdef SECUREC_FOR_WCHAR
410     attr->bufferIsWide = 1;
411     wchar = (wchar_t)cValue;
412     if (attr->flags & SECUREC_FLAG_SHORT) {
413         /* multibyte character to wide  character */
414         char tempchar[2];
415         tempchar[0] = (char)(wchar & 0x00ff);
416         tempchar[1] = '\0';
417 
418         if (mbtowc(buffer->wStr, tempchar, sizeof(tempchar)) < 0) {
419             return -1;
420         }
421     } else {
422         buffer->wStr[0] = wchar;
423     }
424     formatBuf->wStr = buffer->wStr;
425     textLen = 1; /* only 1 wide character */
426 #else
427     attr->bufferIsWide = 0;
428     if (attr->flags & (SECUREC_FLAG_LONG | SECUREC_FLAG_WIDECHAR)) {
429         wchar = (wchar_t)cValue;
430         /* wide  character  to multibyte character */
431         // SECUREC_MASK_MSVC_CRT_WARNING
432         textLen = wctomb(buffer->str, wchar);
433         // SECUREC_END_MASK_MSVC_CRT_WARNING
434         if (textLen < 0) {
435             return -1;
436         }
437     } else {
438         /* get  multibyte character from argument */
439         unsigned short temp;
440         temp = (unsigned short)cValue;
441         buffer->str[0] = (char)temp;
442         textLen = 1;
443     }
444     formatBuf->str = buffer->str;
445 #endif
446 
447     return textLen;
448 }
449 
SecDecodeTypeS(SecFormatAttr * attr,char * argPtr,SecFormatBuf * formatBuf)450 static int SecDecodeTypeS(SecFormatAttr *attr, char *argPtr, SecFormatBuf *formatBuf)
451 {
452     /* literal string to print null ptr, define it on stack rather than const text area
453        is to avoid gcc warning with pointing const text with variable */
454     static char strNullString[8] = "(null)";
455     static wchar_t wStrNullString[8] = { L'(', L'n', L'u', L'l', L'l', L')', L'\0', L'\0' };
456 
457     int finalPrecision;
458     char *strEnd = NULL;
459     wchar_t *wStrEnd = NULL;
460     int textLen;
461 
462 #if (defined(SECUREC_COMPATIBLE_LINUX_FORMAT)) && (!defined(SECUREC_ON_UNIX))
463     attr->flags &= ~SECUREC_FLAG_LEADZERO;
464 #endif
465     finalPrecision = (attr->precision == -1) ? SECUREC_INT_MAX : attr->precision;
466     formatBuf->str = argPtr;
467 
468 #ifdef SECUREC_FOR_WCHAR
469 #if defined(SECUREC_COMPATIBLE_LINUX_FORMAT)
470     if (!(attr->flags & SECUREC_FLAG_LONG)) {
471         attr->flags |= SECUREC_FLAG_SHORT;
472     }
473 #endif
474     if (attr->flags & SECUREC_FLAG_SHORT) {
475         if (formatBuf->str == NULL) { /* NULL passed, use special string */
476             formatBuf->str = strNullString;
477         }
478         strEnd = formatBuf->str;
479         for (textLen = 0; textLen < finalPrecision && *strEnd; textLen++) {
480             ++strEnd;
481         }
482         /* textLen now contains length in multibyte chars */
483     } else {
484         if (formatBuf->wStr == NULL) { /* NULL passed, use special string */
485             formatBuf->wStr = wStrNullString;
486         }
487         attr->bufferIsWide = 1;
488         wStrEnd = formatBuf->wStr;
489         while (finalPrecision-- && *wStrEnd) {
490             ++wStrEnd;
491         }
492         textLen = (int)(wStrEnd - formatBuf->wStr); /* in wchar_ts */
493         /* textLen now contains length in wide chars */
494     }
495 #else /* SECUREC_FOR_WCHAR */
496     if (attr->flags & (SECUREC_FLAG_LONG | SECUREC_FLAG_WIDECHAR)) {
497         if (formatBuf->wStr == NULL) { /* NULL passed, use special string */
498             formatBuf->wStr = wStrNullString;
499         }
500         attr->bufferIsWide = 1;
501         wStrEnd = formatBuf->wStr;
502         while (finalPrecision-- && *wStrEnd) {
503             ++wStrEnd;
504         }
505         textLen = (int)(wStrEnd - formatBuf->wStr);
506     } else {
507         if (formatBuf->str == NULL) { /* meet NULL, use special string */
508             formatBuf->str = strNullString;
509         }
510 
511         if (finalPrecision == SECUREC_INT_MAX) {
512             /* precision NOT assigned */
513             /* The strlen performance is high when the string length is greater than 32 */
514             textLen = (int)strlen(formatBuf->str);
515         } else {
516             /* precision assigned */
517             strEnd = formatBuf->str;
518             while (finalPrecision-- && *strEnd) {
519                 ++strEnd;
520             }
521             textLen = (int)(strEnd - formatBuf->str); /* length of the string */
522         }
523     }
524 
525 #endif /* SECUREC_FOR_WCHAR */
526     return textLen;
527 }
528 
529 #define PUBLIC_FLAG_LEN (8)
530 #define PRIVATE_FLAG_LEN (9)
531 #define PUBLIC_FLAG "{public}"
532 #define PRIVATE_FLAG "{private}"
533 #define bool _Bool
534 static int HILOG_TRUE = 1;
535 static int HILOG_FALSE = 0;
536 
HiLogSecOutputS(SecPrintfStream * stream,bool isDebugMode,const char * cformat,va_list arglist)537 int HiLogSecOutputS(SecPrintfStream *stream, bool isDebugMode, const char *cformat, va_list arglist)
538 {
539     const SecChar *format = cformat;
540 
541     char *floatBuf = NULL;
542     SecFormatBuf formatBuf;
543     static const char *itoaUpperDigits = "0123456789ABCDEFX";
544     static const char *itoaLowerDigits = "0123456789abcdefx";
545     const char *digits = itoaUpperDigits;
546     int ii = 0;
547 
548     unsigned int radix;
549     int charsOut; /* characters written */
550 
551     int prefixLen = 0;
552     int padding = 0;
553 
554     int textLen;        /* length of the text */
555     int bufferSize = 0; /* size of formatBuf.str */
556     int noOutput = 0;
557 
558     SecFmtState state;
559     SecFmtState laststate;
560 
561     SecChar prefix[2] = { 0 };
562     SecChar ch; /* currently read character */
563     static char PRIVACY_STRING[] = "<private>";
564     static wchar_t WPRIVACY_STRING[] = { L'<', L'p', L'r', L'i', L'v', L'a', L't', L'e', L'>', L'\0'};
565     bool isPrivacy = HILOG_TRUE;
566 
567     static const unsigned char fmtCharTable[337] = {
568         /* type 0:    nospecial meanin;
569            1:   '%';
570            2:    '.'
571            3:    '*'
572            4:    '0'
573            5:    '1' ... '9'
574            6:    ' ', '+', '-', '#'
575            7:     'h', 'l', 'L', 'F', 'w' , 'N','z','q','t','j'
576            8:     'd','o','u','i','x','X','e','f','g'
577          */
578         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
579         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
580         0x06, 0x00, 0x00, 0x06, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x03, 0x06, 0x00, 0x06, 0x02, 0x00,
581         0x04, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
582         0x00, 0x00, 0x00, 0x08, 0x00, 0x08, 0x08, 0x08, 0x00, 0x07, 0x00, 0x00, 0x07, 0x00, 0x07, 0x00,
583         0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00,
584         0x00, 0x00, 0x00, 0x08, 0x08, 0x08, 0x08, 0x08, 0x07, 0x08, 0x07, 0x00, 0x07, 0x00, 0x00, 0x08,
585         0x08, 0x07, 0x00, 0x08, 0x07, 0x08, 0x00, 0x07, 0x08, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00,
586         /* fill zero  for normal char 128 byte for 0x80 - 0xff */
587         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
588         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
589         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
590         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
591         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
592         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
593         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
594         0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
595         /* state  0: normal
596            1: percent
597            2: flag
598            3: width
599            4: dot
600            5: precis
601            6: size
602            7: type
603            8: invalid
604          */
605         0x00, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x00, 0x00, 0x01, 0x00, 0x08, 0x08, 0x08, 0x08, 0x08,
606         0x01, 0x00, 0x00, 0x04, 0x04, 0x04, 0x08, 0x08, 0x08, 0x00, 0x00, 0x00, 0x03, 0x03, 0x08, 0x05,
607         0x08, 0x08, 0x00, 0x00, 0x00, 0x02, 0x02, 0x03, 0x05, 0x05, 0x08, 0x00, 0x00, 0x00, 0x03, 0x03,
608         0x03, 0x05, 0x05, 0x08, 0x00, 0x00, 0x00, 0x02, 0x02, 0x02, 0x08, 0x08, 0x08, 0x00, 0x00, 0x00,
609         0x06, 0x06, 0x06, 0x06, 0x06, 0x06, 0x00, 0x00, 0x00, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x00,
610         0x00
611     };
612 
613     SecFormatAttr formatAttr;
614     SecBuffer buffer;
615     formatAttr.flags = 0;
616     formatAttr.bufferIsWide = 0; /* flag for buffer contains wide chars */
617     formatAttr.fldWidth = 0;
618     formatAttr.precision = 0;
619     formatAttr.dynWidth = 0;
620     formatAttr.dynPrecision = 0;
621 
622     charsOut = 0;
623     textLen = 0;
624     state = STAT_NORMAL; /* starting state */
625     formatBuf.str = NULL;
626 
627     /* loop each format character */
628     /* remove format != NULL */
629     while ((ch = *format++) != SECUREC_CHAR('\0') && charsOut >= 0) {
630         laststate = state;
631         state = SECUREC_DECODE_STATE(ch, fmtCharTable, laststate);
632 
633         switch (state) {
634             case STAT_NORMAL:
635 
636             NORMAL_CHAR:
637 
638                 /* normal state, write character */
639                 if (SECUREC_IS_REST_BUF_ENOUGH(1 /* only one char */)) {
640                     SECUREC_SAFE_WRITE_CHAR(ch, stream, &charsOut); /* char * cast to wchar * */
641                 } else {
642 #ifdef SECUREC_FOR_WCHAR
643                     SECUREC_WRITE_CHAR(ch, stream, &charsOut);
644 #else
645                     /* optimize function call to code */
646                     charsOut = -1;
647                     stream->count = -1;
648 #endif
649                 }
650 
651                 continue;
652 
653             case STAT_PERCENT:
654                 /* set default values */
655                 prefixLen = 0;
656                 noOutput = 0;
657                 formatAttr.flags = 0;
658                 formatAttr.fldWidth = 0;
659                 formatAttr.precision = -1;
660                 formatAttr.bufferIsWide = 0;
661                 isPrivacy = HILOG_TRUE;
662                 if (0 == strncmp(format, PUBLIC_FLAG, PUBLIC_FLAG_LEN)) {
663                     isPrivacy = HILOG_FALSE;
664                     format += PUBLIC_FLAG_LEN;
665                     break;
666                 }
667                 if (0 == strncmp(format, PRIVATE_FLAG, PRIVATE_FLAG_LEN)) {
668                     isPrivacy = HILOG_TRUE;
669                     format += PRIVATE_FLAG_LEN;
670                     break;
671                 }
672 
673                 if (*format == SECUREC_CHAR('%')) {
674                     isPrivacy = HILOG_FALSE;
675                 }
676 
677                 break;
678 
679             case STAT_FLAG:
680                 /* set flag based on which flag character */
681                 SecDecodeFlags(ch, &formatAttr);
682                 break;
683 
684             case STAT_WIDTH:
685                 /* update width value */
686                 if (ch == SECUREC_CHAR('*')) {
687                     /* get width */
688                     formatAttr.fldWidth = (int)va_arg(arglist, int);
689                     if (formatAttr.fldWidth < 0) {
690                         formatAttr.flags |= SECUREC_FLAG_LEFT;
691                         formatAttr.fldWidth = -formatAttr.fldWidth;
692                     }
693                     formatAttr.dynWidth = 1;
694                 } else {
695                     if (laststate != STAT_WIDTH) {
696                         formatAttr.fldWidth = 0;
697                     }
698                     if (SECUREC_MUL10_ADD_BEYOND_MAX(formatAttr.fldWidth)) {
699                         return -1;
700                     }
701                     formatAttr.fldWidth =
702                         (int)SECUREC_MUL10((unsigned int)formatAttr.fldWidth) + (ch - SECUREC_CHAR('0'));
703                     formatAttr.dynWidth = 0;
704                 }
705                 break;
706 
707             case STAT_DOT:
708                 formatAttr.precision = 0;
709                 break;
710 
711             case STAT_PRECIS:
712                 /* update precison value */
713                 if (ch == SECUREC_CHAR('*')) {
714                     /* get precision from arg list */
715                     formatAttr.precision = (int)va_arg(arglist, int);
716                     if (formatAttr.precision < 0) {
717                         formatAttr.precision = -1;
718                     }
719                     formatAttr.dynPrecision = 1;
720                 } else {
721                     /* add digit to current precision */
722                     if (SECUREC_MUL10_ADD_BEYOND_MAX(formatAttr.precision)) {
723                         return -1;
724                     }
725                     formatAttr.precision =
726                         (int)SECUREC_MUL10((unsigned int)formatAttr.precision) + (ch - SECUREC_CHAR('0'));
727                     formatAttr.dynPrecision = 0;
728                 }
729                 break;
730 
731             case STAT_SIZE:
732                 /* read a size specifier, set the formatAttr.flags based on it */
733                 if (SecDecodeSize(ch, &formatAttr, &format) != 0) {
734                     /* Compatibility  code for "%I" just print I */
735                     state = STAT_NORMAL;
736                     goto NORMAL_CHAR;
737                 }
738                 break;
739 
740             case STAT_TYPE:
741 
742                 switch (ch) {
743                     case SECUREC_CHAR('C'):
744                         /* wide char */
745                         if (!(formatAttr.flags & (SECUREC_FLAG_SHORT | SECUREC_FLAG_LONG | SECUREC_FLAG_WIDECHAR))) {
746 #ifdef SECUREC_FOR_WCHAR
747                             formatAttr.flags |= SECUREC_FLAG_SHORT;
748 #else
749                             formatAttr.flags |= SECUREC_FLAG_WIDECHAR;
750 #endif
751                         }
752                         /* fall-through */
753                         /* FALLTHRU */
754                     case SECUREC_CHAR('c'): {
755                         unsigned int cValue = (unsigned int)va_arg(arglist, int);
756                         textLen = SecDecodeTypeC(&formatAttr, cValue, &formatBuf, &buffer);
757                         if (textLen < 0) {
758                             noOutput = 1;
759                         }
760                     } break;
761                     case SECUREC_CHAR('S'): /* wide char string */
762 #ifndef SECUREC_FOR_WCHAR
763                         if (!(formatAttr.flags & (SECUREC_FLAG_SHORT | SECUREC_FLAG_LONG | SECUREC_FLAG_WIDECHAR))) {
764                             formatAttr.flags |= SECUREC_FLAG_WIDECHAR;
765                         }
766 #else
767                         if (!(formatAttr.flags & (SECUREC_FLAG_SHORT | SECUREC_FLAG_LONG | SECUREC_FLAG_WIDECHAR))) {
768                             formatAttr.flags |= SECUREC_FLAG_SHORT;
769                         }
770 #endif
771                         /* fall-through */
772                         /* FALLTHRU */
773                     case SECUREC_CHAR('s'): {
774                         char *argPtr = (char *)va_arg(arglist, char *);
775                         textLen = SecDecodeTypeS(&formatAttr, argPtr, &formatBuf);
776                     } break;
777 
778                     case SECUREC_CHAR('n'):
779                         /* higher risk disable it */
780                         return -1;
781 
782                     case SECUREC_CHAR('E'): /* fall-through */ /* FALLTHRU */
783                     case SECUREC_CHAR('F'): /* fall-through */ /* FALLTHRU */
784                     case SECUREC_CHAR('G'): /* fall-through */ /* FALLTHRU */
785                     case SECUREC_CHAR('A'): /* fall-through */ /* FALLTHRU */
786                         /* convert format char to lower , use Explicit conversion to clean up compilation warning */
787                         ch = (SecChar)(ch + ((SecChar)(SECUREC_CHAR('a')) - (SECUREC_CHAR('A'))));
788                         /* fall-through */
789                         /* FALLTHRU */
790                     case SECUREC_CHAR('e'): /* fall-through */ /* FALLTHRU */
791                     case SECUREC_CHAR('f'): /* fall-through */ /* FALLTHRU */
792                     case SECUREC_CHAR('g'): /* fall-through */ /* FALLTHRU */
793                     case SECUREC_CHAR('a'): {
794                         /* floating point conversion */
795                         formatBuf.str = buffer.str; /* output buffer for float string with default size */
796 
797                         /* compute the precision value */
798                         if (formatAttr.precision < 0) {
799                             formatAttr.precision = 6;
800                         } else if (formatAttr.precision == 0 && ch == SECUREC_CHAR('g')) {
801                             formatAttr.precision = 1;
802                         }
803 
804                         /* calc buffer size to store long double value */
805                         if (formatAttr.flags & SECUREC_FLAG_LONG_DOUBLE) {
806                             if (formatAttr.precision > (SECUREC_INT_MAX - SECUREC_FLOAT_BUFSIZE_LB)) {
807                                 noOutput = 1;
808                                 break;
809                             }
810                             bufferSize = SECUREC_FLOAT_BUFSIZE_LB + formatAttr.precision;
811                         } else {
812                             if (formatAttr.precision > (SECUREC_INT_MAX - SECUREC_FLOAT_BUFSIZE)) {
813                                 noOutput = 1;
814                                 break;
815                             }
816                             bufferSize = SECUREC_FLOAT_BUFSIZE + formatAttr.precision;
817                         }
818                         if (formatAttr.fldWidth > bufferSize) {
819                             bufferSize = formatAttr.fldWidth;
820                         }
821 
822                         if (bufferSize >= SECUREC_BUFFER_SIZE) {
823                             /* the current vlaue of SECUREC_BUFFER_SIZE could NOT store the formatted float string */
824                             /* size include '+' and '\0' */
825                             floatBuf = (char *)SECUREC_MALLOC(((size_t)(unsigned int)bufferSize + (size_t)2));
826                             if (floatBuf != NULL) {
827                                 formatBuf.str = floatBuf;
828                             } else {
829                                 noOutput = 1;
830                                 break;
831                             }
832                         }
833 
834                         {
835                             /* add following code to call system sprintf API for float number */
836                             const SecChar *pFltFmt = format - 2; /* point to the position before 'f' or 'g' */
837                             int k = 0;
838                             int fltFmtStrLen;
839                             char fltFmtBuf[SECUREC_FMT_STR_LEN];
840                             char *fltFmtStr = fltFmtBuf;
841                             char *fltFmtHeap = NULL; /* to clear warning */
842 
843                             while (SECUREC_CHAR('%') != *pFltFmt && SECUREC_CHAR('}') != *pFltFmt) { /* must meet '%' */
844                                 --pFltFmt;
845                             }
846 
847                             fltFmtStrLen = (int)((format - pFltFmt) + 1); /* with ending terminator */
848                             if (fltFmtStrLen > SECUREC_FMT_STR_LEN) {
849                                 /* if SECUREC_FMT_STR_LEN is NOT enough, alloc a new buffer */
850                                 fltFmtHeap = (char *)SECUREC_MALLOC((size_t)((unsigned int)fltFmtStrLen));
851                                 if (fltFmtHeap == NULL) {
852                                     noOutput = 1;
853                                     break;
854                                 } else {
855                                     if (SECUREC_CHAR('%') != *pFltFmt) {
856                                         fltFmtHeap[0] = '%';
857                                         ++k;
858                                     }
859                                     for (; k < fltFmtStrLen - 1; ++k) {
860                                         /* convert wchar to char */
861                                         fltFmtHeap[k] = (char)(pFltFmt[k]); /* copy the format string */
862                                     }
863                                     fltFmtHeap[k] = '\0';
864 
865                                     fltFmtStr = fltFmtHeap;
866                                 }
867                             } else {
868                                 if (SECUREC_CHAR('%') != *pFltFmt) {
869                                     fltFmtBuf[0] = '%';
870                                     ++k;
871                                 }
872                                 /* purpose of the repeat code is to solve the tool alarm  Redundant_Null_Check */
873                                 for (; k < fltFmtStrLen - 1; ++k) {
874                                     /* convert wchar to char */
875                                     fltFmtBuf[k] = (char)(pFltFmt[k]); /* copy the format string */
876                                 }
877                                 fltFmtBuf[k] = '\0';
878                             }
879 
880 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
881                             if (formatAttr.flags & SECUREC_FLAG_LONG_DOUBLE) {
882                                 long double tmp = (long double)va_arg(arglist, long double);
883                                 /* call system sprintf to format float value */
884                                 if (formatAttr.dynWidth && formatAttr.dynPrecision) {
885                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr,
886                                         formatAttr.fldWidth, formatAttr.precision, tmp);
887                                 } else if (formatAttr.dynWidth) {
888                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr,
889                                         formatAttr.fldWidth, tmp);
890                                 } else if (formatAttr.dynPrecision) {
891                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr,
892                                         formatAttr.precision, tmp);
893                                 } else {
894                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr, tmp);
895                                 }
896                             } else
897 #endif
898                             {
899                                 double tmp = (double)va_arg(arglist, double);
900                                 if (formatAttr.dynWidth && formatAttr.dynPrecision) {
901                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr,
902                                         formatAttr.fldWidth, formatAttr.precision, tmp);
903                                 } else if (formatAttr.dynWidth) {
904                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr,
905                                         formatAttr.fldWidth, tmp);
906                                 } else if (formatAttr.dynPrecision) {
907                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr,
908                                         formatAttr.precision, tmp);
909                                 } else {
910                                     textLen = sprintf_s(formatBuf.str, SECUREC_BUFFER_SIZE + 1, (char *)fltFmtStr, tmp);
911                                 }
912                             }
913 
914                             if (fltFmtHeap != NULL) {
915                                 /* if buffer is alloced on heap, free it */
916                                 SECUREC_FREE(fltFmtHeap);
917                                 fltFmtHeap = NULL;
918                             }
919                             if (textLen < 0) {
920                                 /* bufferSize is large enough,just validation the return value */
921                                 noOutput = 1;
922                                 break;
923                             }
924 
925                             formatAttr.fldWidth =
926                                 textLen;          /* no padding ,this variable to calculate amount of padding */
927                             prefixLen = 0;        /* no padding ,this variable to  calculate amount of padding */
928                             formatAttr.flags = 0; /* clear all internal formatAttr.flags */
929                             break;
930                         }
931                     }
932 
933                     case SECUREC_CHAR('p'):
934                         /* print a pointer */
935 #if defined(SECUREC_COMPATIBLE_WIN_FORMAT)
936                         formatAttr.flags &= ~SECUREC_FLAG_LEADZERO;
937 #else
938                         formatAttr.flags |= SECUREC_FLAG_POINTER;
939 #endif
940 
941 #ifdef SECUREC_ON_64BITS
942                         formatAttr.flags |= SECUREC_FLAG_I64; /* converting an int64 */
943 #else
944                         formatAttr.flags |= SECUREC_FLAG_LONG; /* converting a long */
945 #endif
946 
947 #if (defined(SECUREC_COMPATIBLE_LINUX_FORMAT) || defined(SECUREC_VXWORKS_PLATFORM)) && (!defined(SECUREC_ON_UNIX))
948 
949 #if defined(SECUREC_VXWORKS_PLATFORM)
950                         formatAttr.precision = 1;
951 #else
952                         formatAttr.precision = 0;
953 #endif
954                         formatAttr.flags |= SECUREC_FLAG_ALTERNATE; /* "0x" is not default prefix in UNIX */
955                         digits = itoaLowerDigits;
956                         goto OUTPUT_HEX;
957 #else
958                                                                /* not linux vxwoks */
959 #if defined(_AIX) || defined(SECUREC_ON_SOLARIS)
960                         formatAttr.precision = 1;
961 #else
962                         formatAttr.precision = 2 * sizeof(void *);
963 #endif
964 
965 #endif
966 
967 #if defined(SECUREC_ON_UNIX)
968                         digits = itoaLowerDigits;
969                         goto OUTPUT_HEX;
970 #endif
971 
972                         /* fall-through */
973                         /* FALLTHRU */
974                     case SECUREC_CHAR('X'):
975                         /* unsigned upper hex output */
976                         digits = itoaUpperDigits;
977                         goto OUTPUT_HEX;
978 
979                     case SECUREC_CHAR('x'):
980                         /* unsigned lower hex output */
981                         digits = itoaLowerDigits;
982 
983                     OUTPUT_HEX:
984                         radix = 16;
985                         if (formatAttr.flags & SECUREC_FLAG_ALTERNATE) {
986                             /* alternate form means '0x' prefix */
987                             prefix[0] = SECUREC_CHAR('0');
988                             prefix[1] = (SecChar)(digits[16]); /* 'x' or 'X' */
989 
990 #if (defined(SECUREC_COMPATIBLE_LINUX_FORMAT) || defined(SECUREC_VXWORKS_PLATFORM))
991                             if (ch == 'p') {
992                                 prefix[1] = SECUREC_CHAR('x');
993                             }
994 #endif
995 #if defined(_AIX) || defined(SECUREC_ON_SOLARIS)
996                             if (ch == 'p') {
997                                 prefixLen = 0;
998                             } else {
999                                 prefixLen = 2;
1000                             }
1001 #else
1002                             prefixLen = 2;
1003 #endif
1004                         }
1005                         goto OUTPUT_INT;
1006                     case SECUREC_CHAR('i'): /* fall-through */ /* FALLTHRU */
1007                     case SECUREC_CHAR('d'): /* fall-through */ /* FALLTHRU */
1008                         /* signed decimal output */
1009                         formatAttr.flags |= SECUREC_FLAG_SIGNED;
1010                         /* fall-through */
1011                         /* FALLTHRU */
1012                     case SECUREC_CHAR('u'):
1013                         radix = 10;
1014                         goto OUTPUT_INT;
1015                     case SECUREC_CHAR('o'):
1016                         /* unsigned octal output */
1017                         radix = 8;
1018                         if (formatAttr.flags & SECUREC_FLAG_ALTERNATE) {
1019                             /* alternate form means force a leading 0 */
1020                             formatAttr.flags |= SECUREC_FLAG_FORCE_OCTAL;
1021                         }
1022                     OUTPUT_INT : {
1023                         SecUnsignedInt64 number = 0; /* number to convert */
1024                         SecInt64 l;                  /* temp long value */
1025                         unsigned char tch;
1026 #if defined(SECUREC_VXWORKS_VERSION_5_4) && !defined(SECUREC_ON_64BITS)
1027                         SecUnsignedInt32 digit = 0; /* ascii value of digit */
1028                         SecUnsignedInt32 quotientHigh = 0;
1029                         SecUnsignedInt32 quotientLow = 0;
1030 #endif
1031 
1032                         /* read argument into variable l */
1033                         if (formatAttr.flags & SECUREC_FLAG_I64) {
1034                             l = (SecInt64)va_arg(arglist, SecInt64);
1035                         } else if (formatAttr.flags & SECUREC_FLAG_LONGLONG) {
1036                             l = (SecInt64)va_arg(arglist, SecInt64);
1037                         } else
1038 #ifdef SECUREC_ON_64BITS
1039                             if (formatAttr.flags & SECUREC_FLAG_LONG) {
1040                             l = (long)va_arg(arglist, long);
1041                         } else
1042 #endif /* SECUREC_ON_64BITS */
1043                             if (formatAttr.flags & SECUREC_FLAG_CHAR) {
1044                             if (formatAttr.flags & SECUREC_FLAG_SIGNED) {
1045                                 l = (char)va_arg(arglist, int); /* sign extend */
1046                                 if (l >= 128) {                 /* on some platform, char is always unsigned */
1047                                     SecUnsignedInt64 tmpL = (SecUnsignedInt64)l;
1048                                     formatAttr.flags |= SECUREC_FLAG_NEGATIVE;
1049                                     tch = (unsigned char)(~(tmpL));
1050                                     l = tch + 1;
1051                                 }
1052                             } else {
1053                                 l = (unsigned char)va_arg(arglist, int); /* zero-extend */
1054                             }
1055                         } else if (formatAttr.flags & SECUREC_FLAG_SHORT) {
1056                             if (formatAttr.flags & SECUREC_FLAG_SIGNED) {
1057                                 l = (short)va_arg(arglist, int); /* sign extend */
1058                             } else {
1059                                 l = (unsigned short)va_arg(arglist, int); /* zero-extend */
1060                             }
1061                         }
1062 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
1063                         else if (formatAttr.flags & SECUREC_FLAG_PTRDIFF) {
1064                             l = (ptrdiff_t)va_arg(arglist, ptrdiff_t); /* sign extend */
1065                         } else if (formatAttr.flags & SECUREC_FLAG_SIZE) {
1066                             if (formatAttr.flags & SECUREC_FLAG_SIGNED) {
1067                                 /* No suitable macros were found to handle the branch */
1068                                 if (SecIsSameSize(sizeof(size_t), sizeof(long))) {
1069                                     l = va_arg(arglist, long); /* sign extend */
1070                                 } else if (SecIsSameSize(sizeof(size_t), sizeof(long long))) {
1071                                     l = va_arg(arglist, long long); /* sign extend */
1072                                 } else {
1073                                     l = va_arg(arglist, int); /* sign extend */
1074                                 }
1075                             } else {
1076                                 l = (SecInt64)(size_t)va_arg(arglist, size_t); /* sign extend */
1077                             }
1078                         } else if (formatAttr.flags & SECUREC_FLAG_INTMAX) {
1079                             if (formatAttr.flags & SECUREC_FLAG_SIGNED) {
1080                                 l = va_arg(arglist, SecInt64); /* sign extend */
1081                             } else {
1082                                 l = (SecInt64)(SecUnsignedInt64)va_arg(arglist, SecUnsignedInt64); /* sign extend */
1083                             }
1084                         }
1085 #endif
1086                         else {
1087                             if (formatAttr.flags & SECUREC_FLAG_SIGNED) {
1088                                 l = va_arg(arglist, int); /* sign extend */
1089                             } else {
1090                                 l = (unsigned int)va_arg(arglist, int); /* zero-extend */
1091                             }
1092                         }
1093 
1094                         /* check for negative; copy into number */
1095                         if ((formatAttr.flags & SECUREC_FLAG_SIGNED) && l < 0) {
1096                             number = (SecUnsignedInt64)(-l);
1097                             formatAttr.flags |= SECUREC_FLAG_NEGATIVE;
1098                         } else {
1099                             number = (SecUnsignedInt64)l;
1100                         }
1101 
1102                         if (((formatAttr.flags & SECUREC_FLAG_I64) == 0) &&
1103 #ifdef SECUREC_COMPATIBLE_LINUX_FORMAT
1104                             ((formatAttr.flags & SECUREC_FLAG_INTMAX) == 0) &&
1105 #endif
1106 #ifdef SECUREC_ON_64BITS
1107                             ((formatAttr.flags & SECUREC_FLAG_PTRDIFF) == 0) &&
1108                             ((formatAttr.flags & SECUREC_FLAG_SIZE) == 0) &&
1109 #if !defined(SECUREC_COMPATIBLE_WIN_FORMAT) /* on window 64 system sizeof long is 32bit */
1110                             ((formatAttr.flags & SECUREC_FLAG_LONG) == 0) &&
1111 #endif
1112 #endif
1113                             ((formatAttr.flags & SECUREC_FLAG_LONGLONG) == 0)) {
1114 
1115                             number &= 0xffffffff;
1116                         }
1117 
1118                         /* check precision value for default */
1119                         if (formatAttr.precision < 0) {
1120                             formatAttr.precision = 1; /* default precision */
1121                         } else {
1122 #if defined(SECUREC_COMPATIBLE_WIN_FORMAT)
1123                             formatAttr.flags &= ~SECUREC_FLAG_LEADZERO;
1124 #else
1125                             if (!(formatAttr.flags & SECUREC_FLAG_POINTER)) {
1126                                 formatAttr.flags &= ~SECUREC_FLAG_LEADZERO;
1127                             }
1128 #endif
1129                             if (formatAttr.precision > SECUREC_MAX_PRECISION) {
1130                                 formatAttr.precision = SECUREC_MAX_PRECISION;
1131                             }
1132                         }
1133 
1134                         /* Check if data is 0; if so, turn off hex prefix,if 'p',add 0x prefix,else not add prefix */
1135                         if (number == 0) {
1136 #if !(defined(SECUREC_VXWORKS_PLATFORM) || defined(__hpux))
1137                             prefixLen = 0;
1138 #else
1139                             if ((ch == 'p') && (formatAttr.flags & SECUREC_FLAG_ALTERNATE))
1140                                 prefixLen = 2;
1141                             else
1142                                 prefixLen = 0;
1143 #endif
1144                         }
1145 
1146                         /* Convert data to ASCII */
1147                         formatBuf.str = &buffer.str[SECUREC_BUFFER_SIZE];
1148 
1149                         if (number > 0) {
1150 #ifdef SECUREC_ON_64BITS
1151                             switch (radix) {
1152                                 /* the compiler will optimize each one */
1153                                 SECUREC_SPECIAL(number, 10);
1154                                 break;
1155                                 SECUREC_SPECIAL(number, 16);
1156                                 break;
1157                                 SECUREC_SPECIAL(number, 8);
1158                                 break;
1159                                 default:
1160                                     break;
1161                             }
1162 #else /* for 32 bits system */
1163                             if (number <= 0xFFFFFFFFUL) {
1164                                 /* in most case, the value to be converted is small value */
1165                                 SecUnsignedInt32 n32Tmp = (SecUnsignedInt32)number;
1166                                 switch (radix) {
1167                                     SECUREC_SPECIAL(n32Tmp, 16);
1168                                     break;
1169                                     SECUREC_SPECIAL(n32Tmp, 8);
1170                                     break;
1171 
1172 #ifdef _AIX
1173                                     /* the compiler will optimize div 10 */
1174                                     SECUREC_SPECIAL(n32Tmp, 10);
1175                                     break;
1176 #else
1177                                     case 10: {
1178                                         /* fast div 10 */
1179                                         SecUnsignedInt32 q;
1180                                         SecUnsignedInt32 r;
1181                                         do {
1182                                             *--formatBuf.str = digits[n32Tmp % 10];
1183                                             q = (n32Tmp >> 1) + (n32Tmp >> 2);
1184                                             q = q + (q >> 4);
1185                                             q = q + (q >> 8);
1186                                             q = q + (q >> 16);
1187                                             q = q >> 3;
1188                                             r = n32Tmp - (((q << 2) + q) << 1);
1189                                             n32Tmp = (r > 9) ? (q + 1) : q;
1190                                         } while (n32Tmp != 0);
1191                                     } break;
1192 #endif
1193                                     default:
1194                                         break;
1195                                 } /* end switch */
1196                             } else {
1197                                 /* the value to be converted is greater than 4G */
1198 #if defined(SECUREC_VXWORKS_VERSION_5_4)
1199                                 do {
1200                                     if (0 != SecU64Div32((SecUnsignedInt32)((number >> 16) >> 16),
1201                                         (SecUnsignedInt32)number, (SecUnsignedInt32)radix, &quotientHigh, &quotientLow,
1202                                         &digit)) {
1203                                         noOutput = 1;
1204                                         break;
1205                                     }
1206                                     *--formatBuf.str = digits[digit];
1207 
1208                                     number = (SecUnsignedInt64)quotientHigh;
1209                                     number = (number << 32) + quotientLow;
1210                                 } while (number != 0);
1211 #else
1212                                 switch (radix) {
1213                                     /* the compiler will optimize div 10 */
1214                                     SECUREC_SPECIAL(number, 10);
1215                                     break;
1216                                     SECUREC_SPECIAL(number, 16);
1217                                     break;
1218                                     SECUREC_SPECIAL(number, 8);
1219                                     break;
1220                                     default:
1221                                         break;
1222                                 }
1223 #endif
1224                             }
1225 #endif
1226                         } /* END if (number > 0) */
1227                         /* compute length of number,.if textLen > 0, then formatBuf.str must be in buffer.str */
1228                         textLen = (int)((char *)&buffer.str[SECUREC_BUFFER_SIZE] - formatBuf.str);
1229                         if (formatAttr.precision > textLen) {
1230                             for (ii = 0; ii < formatAttr.precision - textLen; ++ii) {
1231                                 *--formatBuf.str = '0';
1232                             }
1233                             textLen = formatAttr.precision;
1234                         }
1235 
1236                         /* Force a leading zero if FORCEOCTAL flag set */
1237                         if ((formatAttr.flags & SECUREC_FLAG_FORCE_OCTAL) &&
1238                             (textLen == 0 || formatBuf.str[0] != '0')) {
1239                             *--formatBuf.str = '0';
1240                             ++textLen; /* add a zero */
1241                         }
1242                     } break;
1243                     default:
1244                         break;
1245                 }
1246 
1247                 if (noOutput == 0) {
1248                     if (formatAttr.flags & SECUREC_FLAG_SIGNED) {
1249                         if (formatAttr.flags & SECUREC_FLAG_NEGATIVE) {
1250                             /* prefix is a '-' */
1251                             prefix[0] = SECUREC_CHAR('-');
1252                             prefixLen = 1;
1253                         } else if (formatAttr.flags & SECUREC_FLAG_SIGN) {
1254                             /* prefix is '+' */
1255                             prefix[0] = SECUREC_CHAR('+');
1256                             prefixLen = 1;
1257                         } else if (formatAttr.flags & SECUREC_FLAG_SIGN_SPACE) {
1258                             /* prefix is ' ' */
1259                             prefix[0] = SECUREC_CHAR(' ');
1260                             prefixLen = 1;
1261                         }
1262                     }
1263 
1264 #if defined(SECUREC_COMPATIBLE_LINUX_FORMAT) && (!defined(SECUREC_ON_UNIX))
1265                     if ((formatAttr.flags & SECUREC_FLAG_POINTER) && (0 == textLen)) {
1266                         formatAttr.flags &= ~SECUREC_FLAG_LEADZERO;
1267                         formatBuf.str = &buffer.str[SECUREC_BUFFER_SIZE - 1];
1268                         *formatBuf.str-- = '\0';
1269                         *formatBuf.str-- = ')';
1270                         *formatBuf.str-- = 'l';
1271                         *formatBuf.str-- = 'i';
1272                         *formatBuf.str-- = 'n';
1273                         *formatBuf.str = '(';
1274                         textLen = 5;
1275                     }
1276 #endif
1277 
1278                     /* calculate amount of padding */
1279                     padding = (formatAttr.fldWidth - textLen) - prefixLen;
1280 
1281                     /* put out the padding, prefix, and text, in the correct order */
1282 
1283                     if (!(formatAttr.flags & (SECUREC_FLAG_LEFT | SECUREC_FLAG_LEADZERO)) && padding > 0) {
1284                         /* pad on left with blanks */
1285                         if (SECUREC_IS_REST_BUF_ENOUGH(padding)) {
1286                             /* char * cast to wchar * */
1287                             SECUREC_SAFE_PADDING(SECUREC_CHAR(' '), padding, stream, &charsOut);
1288                         } else {
1289                             SECUREC_WRITE_MULTI_CHAR(SECUREC_CHAR(' '), padding, stream, &charsOut);
1290                         }
1291                     }
1292 
1293 
1294                     /* write prefix */
1295                     if (prefixLen > 0) {
1296                         SecChar *pPrefix = prefix;
1297                         if (SECUREC_IS_REST_BUF_ENOUGH(prefixLen)) {
1298                             /* max prefix len is 2, use loop copy */ /* char * cast to wchar * */
1299                             SECUREC_SAFE_WRITE_PREFIX(pPrefix, prefixLen, stream, &charsOut);
1300                         } else {
1301                             SECUREC_WRITE_STRING(prefix, prefixLen, stream, &charsOut);
1302                         }
1303                     }
1304 
1305                     if ((formatAttr.flags & SECUREC_FLAG_LEADZERO) && !(formatAttr.flags & SECUREC_FLAG_LEFT) &&
1306                         padding > 0) {
1307                         /* write leading zeros */
1308                         if (SECUREC_IS_REST_BUF_ENOUGH(padding)) {
1309                             /* char * cast to wchar * */
1310                             SECUREC_SAFE_PADDING(SECUREC_CHAR('0'), padding, stream, &charsOut);
1311                         } else {
1312                             SECUREC_WRITE_MULTI_CHAR(SECUREC_CHAR('0'), padding, stream, &charsOut);
1313                         }
1314                     }
1315 
1316                     /* write text */
1317 #ifndef SECUREC_FOR_WCHAR
1318                     if (!isDebugMode && isPrivacy) {
1319                         if (formatAttr.bufferIsWide) {
1320                             formatBuf.wStr = WPRIVACY_STRING;
1321                             textLen = sizeof(WPRIVACY_STRING) / sizeof(wchar_t) - 1;
1322                         } else {
1323                             formatBuf.str = PRIVACY_STRING;
1324                             textLen = strlen(PRIVACY_STRING);
1325                         }
1326                     }
1327                     if (formatAttr.bufferIsWide && (textLen > 0)) {
1328                         wchar_t *p = formatBuf.wStr;
1329                         int count = textLen;
1330                         while (count--) {
1331                             char tmpBuf[SECUREC_MB_LEN + 1];
1332                             // SECUREC_MASK_MSVC_CRT_WARNING
1333                             int retVal = wctomb(tmpBuf, *p++);
1334                             // SECUREC_END_MASK_MSVC_CRT_WARNING
1335                             if (retVal <= 0) {
1336                                 charsOut = -1;
1337                                 break;
1338                             }
1339                             SECUREC_WRITE_STRING(tmpBuf, retVal, stream, &charsOut);
1340                         }
1341                     } else {
1342                         if (SECUREC_IS_REST_BUF_ENOUGH(textLen)) {
1343                             SECUREC_SAFE_WRITE_STR(formatBuf.str, textLen, stream, &charsOut);
1344                         } else {
1345                             SECUREC_WRITE_STRING(formatBuf.str, textLen, stream, &charsOut);
1346                         }
1347                     }
1348 #else /* SECUREC_FOR_WCHAR */
1349                     if (formatAttr.bufferIsWide == 0 && textLen > 0) {
1350                         int count = textLen;
1351                         char *p = formatBuf.str;
1352 
1353                         while (count > 0) {
1354                             wchar_t wchar = L'\0';
1355                             int retVal = mbtowc(&wchar, p, (size_t)MB_CUR_MAX);
1356                             if (retVal <= 0) {
1357                                 charsOut = -1;
1358                                 break;
1359                             }
1360                             SECUREC_WRITE_CHAR(wchar, stream, &charsOut);
1361                             p += retVal;
1362                             count -= retVal;
1363                         }
1364                     } else {
1365                         if (SECUREC_IS_REST_BUF_ENOUGH(textLen)) {
1366                             SECUREC_SAFE_WRITE_STR(formatBuf.wStr, textLen, stream,
1367                                 &charsOut); /* char * cast to wchar * */
1368                         } else {
1369                             SECUREC_WRITE_STRING(formatBuf.wStr, textLen, stream, &charsOut);
1370                         }
1371                     }
1372 #endif /* SECUREC_FOR_WCHAR */
1373 
1374                     if (charsOut >= 0 && (formatAttr.flags & SECUREC_FLAG_LEFT) && padding > 0) {
1375                         /* pad on right with blanks */
1376                         if (SECUREC_IS_REST_BUF_ENOUGH(padding)) {
1377                             /* char * cast to wchar * */
1378                             SECUREC_SAFE_PADDING(SECUREC_CHAR(' '), padding, stream, &charsOut);
1379                         } else {
1380                             SECUREC_WRITE_MULTI_CHAR(SECUREC_CHAR(' '), padding, stream, &charsOut);
1381                         }
1382                     }
1383 
1384                     /* we're done! */
1385                 }
1386                 if (floatBuf != NULL) {
1387                     SECUREC_FREE(floatBuf);
1388                     floatBuf = NULL;
1389                 }
1390                 break;
1391             case STAT_INVALID:
1392                 return -1;
1393             default:
1394                 return -1; /* input format is wrong, directly return */
1395         }
1396     }
1397 
1398     if (state != STAT_NORMAL && state != STAT_TYPE) {
1399         return -1;
1400     }
1401 
1402     return charsOut; /* the number of characters written */
1403 } /* arglist must not be declare as const */
1404 
1405 
HiLogSecVsnprintfImpl(char * string,size_t count,bool isDebugMode,const char * format,va_list arglist)1406 int HiLogSecVsnprintfImpl(char *string, size_t count, bool isDebugMode, const char *format, va_list arglist)
1407 {
1408     SecPrintfStream str;
1409     int retVal;
1410 
1411     str.count = (int)count; /* this count include \0 character */
1412     str.cur = string;
1413 
1414     retVal = HiLogSecOutputS(&str, isDebugMode, format, arglist);
1415     if ((retVal >= 0) && (SECUREC_PUTC_ZERO(&str) != EOF)) {
1416         return (retVal);
1417     } else if (str.count < 0) {
1418         /* the buffer was too small; we return truncation */
1419         string[count - 1] = 0;
1420         return SECUREC_PRINTF_TRUNCATE;
1421     }
1422 
1423     return -1;
1424 }
1425 
1426 
HiLog_Printf(char * strDest,size_t destMax,size_t count,bool isDebugMode,const char * format,va_list arglist)1427 int HiLog_Printf(char *strDest, size_t destMax, size_t count, bool isDebugMode, const char *format, va_list arglist)
1428 {
1429     int retVal;
1430 
1431     if (format == NULL || strDest == NULL || destMax == 0 || destMax > SECUREC_STRING_MAX_LEN ||
1432         (count > (SECUREC_STRING_MAX_LEN - 1) && count != (size_t)-1)) {
1433         if (strDest != NULL && destMax > 0) {
1434             strDest[0] = '\0';
1435         }
1436         SECUREC_ERROR_INVALID_PARAMTER("hilog_printf");
1437         return -1;
1438     }
1439 
1440     if (destMax > count) {
1441         retVal = HiLogSecVsnprintfImpl(strDest, count + 1, isDebugMode, format, arglist);
1442         if (retVal == SECUREC_PRINTF_TRUNCATE) { /* lsd add to keep dest buffer not destroyed 2014.2.18 */
1443             /* the string has been truncated, return  -1 */
1444             return -1; /* to skip error handler,  return strlen(strDest) or -1 */
1445         }
1446     } else { /* destMax <= count */
1447         retVal = HiLogSecVsnprintfImpl(strDest, destMax, isDebugMode, format, arglist);
1448 #ifdef SECUREC_COMPATIBLE_WIN_FORMAT
1449         if (retVal == SECUREC_PRINTF_TRUNCATE && count == (size_t)-1) {
1450             return -1;
1451         }
1452 #endif
1453     }
1454 
1455     if (retVal < 0) {
1456         strDest[0] = '\0'; /* empty the dest strDest */
1457 
1458         if (retVal == SECUREC_PRINTF_TRUNCATE) {
1459             /* Buffer too small */
1460             SECUREC_ERROR_INVALID_RANGE("hilog_printf");
1461         }
1462 
1463         SECUREC_ERROR_INVALID_PARAMTER("hilog_printf");
1464         return -1;
1465     }
1466 
1467     return retVal;
1468 }
1469 
1470 #define HILOG_DRIVER "/dev/hilog"
1471 static char g_logLevelInfo[HILOG_LEVEL_MAX] = {
1472     'N', // "NONE"
1473     'N', // "NONE"
1474     'N', // "NONE"
1475     'D', // "DEBUG"
1476     'I', // "INFO"
1477     'W', // "WARN"
1478     'E', // "ERROR"
1479     'F'  // "FATAL"
1480 };
1481 
1482 #ifdef LOSCFG_BASE_CORE_HILOG
1483 extern int HiLogWriteInternal(const char *buffer, size_t bufLen);
1484 #else
1485 static int g_hilogFd = -1;
1486 #endif
1487 
HiLogPrintArgs(LogType bufID,LogLevel prio,unsigned int domain,const char * tag,const char * fmt,va_list ap)1488 int HiLogPrintArgs(LogType bufID, LogLevel prio, unsigned int domain, const char *tag, const char *fmt, va_list ap)
1489 {
1490     int ret;
1491     char buf[LOG_BUF_SIZE] = {0};
1492     bool isDebugMode = 1;
1493     unsigned int bufLen;
1494 
1495 #ifdef OHOS_RELEASE
1496     isDebugMode = 0;
1497 #endif
1498     if (snprintf_s(buf, sizeof(buf), sizeof(buf) - 1, "%c %05X/%s: ", g_logLevelInfo[prio], (domain & DOMAIN_FILTER),
1499         tag) == -1) {
1500         return 0;
1501     }
1502 
1503     bufLen = strlen(buf);
1504     if (bufLen >= MAX_DOMAIN_TAG_SIZE) {
1505         return 0;
1506     }
1507 
1508 #ifndef LOSCFG_BASE_CORE_HILOG
1509     /* print traceid */
1510     if (g_registerFunc != NULL) {
1511         char *logBuf = buf;
1512         int traceBufLen = 0;
1513         uint64_t chainId = 0;
1514         uint32_t flag = 0;
1515         uint64_t spanId = 0;
1516         uint64_t parentSpanId = 0;
1517         int ret = -1;  /* default value -1: invalid trace id */
1518         atomic_fetch_add_explicit(&g_hiLogGetIdCallCount, 1, memory_order_relaxed);
1519         RegisterFunc func = g_registerFunc;
1520         if (g_registerFunc != NULL) {
1521             ret = func(&chainId, &flag, &spanId, &parentSpanId);
1522         }
1523         atomic_fetch_sub_explicit(&g_hiLogGetIdCallCount, 1, memory_order_relaxed);
1524         if (ret == 0) {  /* 0: trace id with span id */
1525             traceBufLen = snprintf_s(logBuf, LOG_BUF_SIZE, LOG_BUF_SIZE - 1, "[%llx, %llx, %llx] ",
1526                 (unsigned long long)chainId, (unsigned long long)spanId, (unsigned long long)parentSpanId);
1527         } else if (ret != -1) {  /* trace id without span id, -1: invalid trace id */
1528             traceBufLen = snprintf_s(logBuf, LOG_BUF_SIZE, LOG_BUF_SIZE - 1, "[%llx] ",
1529                 (unsigned long long)chainId);
1530         }
1531         if (traceBufLen > 0) {
1532             logBuf += traceBufLen;
1533         } else {
1534             traceBufLen = 0;
1535         }
1536     }
1537 #endif
1538 
1539     HiLog_Printf(buf + bufLen, LOG_BUF_SIZE - bufLen, LOG_BUF_SIZE - bufLen - 1, isDebugMode, fmt, ap);
1540 
1541 #ifdef LOSCFG_BASE_CORE_HILOG
1542     ret = HiLogWriteInternal(buf, strlen(buf) + 1);
1543 #else
1544     if (g_hilogFd == -1) {
1545         g_hilogFd = open(HILOG_DRIVER, O_WRONLY | O_CLOEXEC);
1546     }
1547     if (g_hilogFd == -1) {
1548         return 0;
1549     }
1550     ret = write(g_hilogFd, buf, strlen(buf) + 1);
1551 #endif
1552     return ret;
1553 }
1554 
HiLogPrint(LogType bufID,LogLevel prio,unsigned int domain,const char * tag,const char * fmt,...)1555 int HiLogPrint(LogType bufID, LogLevel prio, unsigned int domain, const char *tag, const char *fmt, ...)
1556 {
1557     int ret;
1558     va_list ap;
1559     va_start(ap, fmt);
1560     ret = HiLogPrintArgs(bufID, prio, domain, tag, fmt, ap);
1561     va_end(ap);
1562     return ret;
1563 }
1564 
FlushHilog(void)1565 int FlushHilog(void)
1566 {
1567     int ret;
1568 #define FLUSH_LOG_WRITE_LEN 3
1569     char buf[FLUSH_LOG_WRITE_LEN] = {0x07, 0x07, '\0'};
1570 #ifdef LOSCFG_BASE_CORE_HILOG
1571     ret = HiLogWriteInternal(buf, strlen(buf) + 1);
1572 #else
1573     if (g_hilogFd == -1) {
1574         g_hilogFd = open(HILOG_DRIVER, O_WRONLY);
1575     }
1576     if (g_hilogFd == -1) {
1577         return 0;
1578     }
1579     ret = write(g_hilogFd, buf, strlen(buf) + 1);
1580 #endif
1581     return ret;
1582 }