Marco Zecchini
/
Example_RTOS
Rtos API example
Embed:
(wiki syntax)
Show/hide line numbers
mbed_trace.c
00001 /* 00002 * Copyright (c) 2014-2015 ARM Limited. All rights reserved. 00003 * SPDX-License-Identifier: Apache-2.0 00004 * Licensed under the Apache License, Version 2.0 (the License); you may 00005 * not use this file except in compliance with the License. 00006 * You may obtain a copy of the License at 00007 * 00008 * http://www.apache.org/licenses/LICENSE-2.0 00009 * 00010 * Unless required by applicable law or agreed to in writing, software 00011 * distributed under the License is distributed on an AS IS BASIS, WITHOUT 00012 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 00013 * See the License for the specific language governing permissions and 00014 * limitations under the License. 00015 */ 00016 #include <stdio.h> 00017 #include <string.h> 00018 #include <stdarg.h> 00019 00020 #ifdef MBED_CONF_MBED_TRACE_ENABLE 00021 #undef MBED_CONF_MBED_TRACE_ENABLE 00022 #endif 00023 #define MBED_CONF_MBED_TRACE_ENABLE 1 00024 #ifndef MBED_CONF_MBED_TRACE_FEA_IPV6 00025 #define MBED_CONF_MBED_TRACE_FEA_IPV6 1 00026 #endif 00027 00028 #include "mbed-trace/mbed_trace.h" 00029 #if MBED_CONF_MBED_TRACE_FEA_IPV6 == 1 00030 #include "mbed-client-libservice/ip6string.h" 00031 #include "mbed-client-libservice/common_functions.h" 00032 #endif 00033 00034 #if defined(YOTTA_CFG_MBED_TRACE_MEM) 00035 #define MBED_TRACE_MEM_INCLUDE YOTTA_CFG_MBED_TRACE_MEM_INCLUDE 00036 #define MBED_TRACE_MEM_ALLOC YOTTA_CFG_MBED_TRACE_MEM_ALLOC 00037 #define MBED_TRACE_MEM_FREE YOTTA_CFG_MBED_TRACE_MEM_FREE 00038 #else /* YOTTA_CFG_MEMLIB */ 00039 // Default options 00040 #ifndef MBED_TRACE_MEM_INCLUDE 00041 #define MBED_TRACE_MEM_INCLUDE <stdlib.h> 00042 #endif 00043 #include MBED_TRACE_MEM_INCLUDE 00044 #ifndef MBED_TRACE_MEM_ALLOC 00045 #define MBED_TRACE_MEM_ALLOC malloc 00046 #endif 00047 #ifndef MBED_TRACE_MEM_FREE 00048 #define MBED_TRACE_MEM_FREE free 00049 #endif 00050 #endif /* YOTTA_CFG_MEMLIB */ 00051 00052 #define VT100_COLOR_ERROR "\x1b[31m" 00053 #define VT100_COLOR_WARN "\x1b[33m" 00054 #define VT100_COLOR_INFO "\x1b[39m" 00055 #define VT100_COLOR_DEBUG "\x1b[90m" 00056 00057 /** default max trace line size in bytes */ 00058 #ifdef MBED_TRACE_LINE_LENGTH 00059 #define DEFAULT_TRACE_LINE_LENGTH MBED_TRACE_LINE_LENGTH 00060 #elif defined YOTTA_CFG_MBED_TRACE_LINE_LENGTH 00061 #warning YOTTA_CFG_MBED_TRACE_LINE_LENGTH is deprecated and will be removed in the future! Use MBED_TRACE_LINE_LENGTH instead. 00062 #define DEFAULT_TRACE_LINE_LENGTH YOTTA_CFG_MBED_TRACE_LINE_LENGTH 00063 #else 00064 #define DEFAULT_TRACE_LINE_LENGTH 1024 00065 #endif 00066 00067 /** default max temporary buffer size in bytes, used in 00068 trace_ipv6, trace_ipv6_prefix and trace_array */ 00069 #ifdef MBED_TRACE_TMP_LINE_LENGTH 00070 #define DEFAULT_TRACE_TMP_LINE_LEN MBED_TRACE_TMP_LINE_LENGTH 00071 #elif defined YOTTA_CFG_MBED_TRACE_TMP_LINE_LEN 00072 #warning The YOTTA_CFG_MBED_TRACE_TMP_LINE_LEN flag is deprecated and will be removed in the future! Use MBED_TRACE_TMP_LINE_LENGTH instead. 00073 #define DEFAULT_TRACE_TMP_LINE_LEN YOTTA_CFG_MBED_TRACE_TMP_LINE_LEN 00074 #elif defined YOTTA_CFG_MTRACE_TMP_LINE_LEN 00075 #warning The YOTTA_CFG_MTRACE_TMP_LINE_LEN flag is deprecated and will be removed in the future! Use MBED_TRACE_TMP_LINE_LENGTH instead. 00076 #define DEFAULT_TRACE_TMP_LINE_LEN YOTTA_CFG_MTRACE_TMP_LINE_LEN 00077 #else 00078 #define DEFAULT_TRACE_TMP_LINE_LEN 128 00079 #endif 00080 00081 /** default max filters (include/exclude) length in bytes */ 00082 #ifdef MBED_TRACE_FILTER_LENGTH 00083 #define DEFAULT_TRACE_FILTER_LENGTH MBED_TRACE_FILTER_LENGTH 00084 #else 00085 #define DEFAULT_TRACE_FILTER_LENGTH 24 00086 #endif 00087 00088 /** default trace configuration bitmask */ 00089 #ifdef MBED_TRACE_CONFIG 00090 #define DEFAULT_TRACE_CONFIG MBED_TRACE_CONFIG 00091 #else 00092 #define DEFAULT_TRACE_CONFIG TRACE_MODE_COLOR | TRACE_ACTIVE_LEVEL_ALL | TRACE_CARRIAGE_RETURN 00093 #endif 00094 00095 /** default print function, just redirect str to printf */ 00096 static void mbed_trace_realloc( char **buffer, int *length_ptr, int new_length); 00097 static void mbed_trace_default_print(const char *str); 00098 static void mbed_trace_reset_tmp(void); 00099 00100 typedef struct trace_s { 00101 /** trace configuration bits */ 00102 uint8_t trace_config; 00103 /** exclude filters list, related group name */ 00104 char *filters_exclude; 00105 /** include filters list, related group name */ 00106 char *filters_include; 00107 /** Filters length */ 00108 int filters_length; 00109 /** trace line */ 00110 char *line; 00111 /** trace line length */ 00112 int line_length; 00113 /** temporary data */ 00114 char *tmp_data; 00115 /** temporary data array length */ 00116 int tmp_data_length; 00117 /** temporary data pointer */ 00118 char *tmp_data_ptr; 00119 00120 /** prefix function, which can be used to put time to the trace line */ 00121 char *(*prefix_f)(size_t); 00122 /** suffix function, which can be used to some string to the end of trace line */ 00123 char *(*suffix_f)(void); 00124 /** print out function. Can be redirect to flash for example. */ 00125 void (*printf)(const char *); 00126 /** print out function for TRACE_LEVEL_CMD */ 00127 void (*cmd_printf)(const char *); 00128 /** mutex wait function which can be called to lock against a mutex. */ 00129 void (*mutex_wait_f)(void); 00130 /** mutex release function which must be used to release the mutex locked by mutex_wait_f. */ 00131 void (*mutex_release_f)(void); 00132 /** number of times the mutex has been locked */ 00133 int mutex_lock_count; 00134 } trace_t; 00135 00136 static trace_t m_trace = { 00137 .trace_config = DEFAULT_TRACE_CONFIG, 00138 .filters_exclude = 0, 00139 .filters_include = 0, 00140 .filters_length = DEFAULT_TRACE_FILTER_LENGTH, 00141 .line = 0, 00142 .line_length = DEFAULT_TRACE_LINE_LENGTH, 00143 .tmp_data = 0, 00144 .tmp_data_length = DEFAULT_TRACE_TMP_LINE_LEN, 00145 .prefix_f = 0, 00146 .suffix_f = 0, 00147 .printf = mbed_trace_default_print, 00148 .cmd_printf = 0, 00149 .mutex_wait_f = 0, 00150 .mutex_release_f = 0, 00151 .mutex_lock_count = 0 00152 }; 00153 00154 int mbed_trace_init(void) 00155 { 00156 if (m_trace.line == NULL) { 00157 m_trace.line = MBED_TRACE_MEM_ALLOC(m_trace.line_length); 00158 } 00159 00160 if (m_trace.tmp_data == NULL) { 00161 m_trace.tmp_data = MBED_TRACE_MEM_ALLOC(m_trace.tmp_data_length); 00162 } 00163 m_trace.tmp_data_ptr = m_trace.tmp_data; 00164 00165 if (m_trace.filters_exclude == NULL) { 00166 m_trace.filters_exclude = MBED_TRACE_MEM_ALLOC(m_trace.filters_length); 00167 } 00168 if (m_trace.filters_include == NULL) { 00169 m_trace.filters_include = MBED_TRACE_MEM_ALLOC(m_trace.filters_length); 00170 } 00171 00172 if (m_trace.line == NULL || 00173 m_trace.tmp_data == NULL || 00174 m_trace.filters_exclude == NULL || 00175 m_trace.filters_include == NULL) { 00176 //memory allocation fail 00177 mbed_trace_free(); 00178 return -1; 00179 } 00180 memset(m_trace.tmp_data, 0, m_trace.tmp_data_length); 00181 memset(m_trace.filters_exclude, 0, m_trace.filters_length); 00182 memset(m_trace.filters_include, 0, m_trace.filters_length); 00183 memset(m_trace.line, 0, m_trace.line_length); 00184 00185 return 0; 00186 } 00187 void mbed_trace_free(void) 00188 { 00189 // release memory 00190 MBED_TRACE_MEM_FREE(m_trace.line); 00191 MBED_TRACE_MEM_FREE(m_trace.tmp_data); 00192 MBED_TRACE_MEM_FREE(m_trace.filters_exclude); 00193 MBED_TRACE_MEM_FREE(m_trace.filters_include); 00194 00195 // reset to default values 00196 m_trace.trace_config = DEFAULT_TRACE_CONFIG; 00197 m_trace.filters_exclude = 0; 00198 m_trace.filters_include = 0; 00199 m_trace.filters_length = DEFAULT_TRACE_FILTER_LENGTH; 00200 m_trace.line = 0; 00201 m_trace.line_length = DEFAULT_TRACE_LINE_LENGTH; 00202 m_trace.tmp_data = 0; 00203 m_trace.tmp_data_length = DEFAULT_TRACE_TMP_LINE_LEN; 00204 m_trace.prefix_f = 0; 00205 m_trace.suffix_f = 0; 00206 m_trace.printf = mbed_trace_default_print; 00207 m_trace.cmd_printf = 0; 00208 m_trace.mutex_wait_f = 0; 00209 m_trace.mutex_release_f = 0; 00210 m_trace.mutex_lock_count = 0; 00211 } 00212 static void mbed_trace_realloc( char **buffer, int *length_ptr, int new_length) 00213 { 00214 MBED_TRACE_MEM_FREE(*buffer); 00215 *buffer = MBED_TRACE_MEM_ALLOC(new_length); 00216 *length_ptr = new_length; 00217 } 00218 void mbed_trace_buffer_sizes(int lineLength, int tmpLength) 00219 { 00220 if( lineLength > 0 ) { 00221 mbed_trace_realloc( &(m_trace.line), &m_trace.line_length, lineLength ); 00222 } 00223 if( tmpLength > 0 ) { 00224 mbed_trace_realloc( &(m_trace.tmp_data), &m_trace.tmp_data_length, tmpLength); 00225 mbed_trace_reset_tmp(); 00226 } 00227 } 00228 void mbed_trace_config_set(uint8_t config) 00229 { 00230 m_trace.trace_config = config; 00231 } 00232 uint8_t mbed_trace_config_get(void) 00233 { 00234 return m_trace.trace_config; 00235 } 00236 void mbed_trace_prefix_function_set(char *(*pref_f)(size_t)) 00237 { 00238 m_trace.prefix_f = pref_f; 00239 } 00240 void mbed_trace_suffix_function_set(char *(*suffix_f)(void)) 00241 { 00242 m_trace.suffix_f = suffix_f; 00243 } 00244 void mbed_trace_print_function_set(void (*printf)(const char *)) 00245 { 00246 m_trace.printf = printf; 00247 } 00248 void mbed_trace_cmdprint_function_set(void (*printf)(const char *)) 00249 { 00250 m_trace.cmd_printf = printf; 00251 } 00252 void mbed_trace_mutex_wait_function_set(void (*mutex_wait_f)(void)) 00253 { 00254 m_trace.mutex_wait_f = mutex_wait_f; 00255 } 00256 void mbed_trace_mutex_release_function_set(void (*mutex_release_f)(void)) 00257 { 00258 m_trace.mutex_release_f = mutex_release_f; 00259 } 00260 void mbed_trace_exclude_filters_set(char *filters) 00261 { 00262 if (filters) { 00263 (void)strncpy(m_trace.filters_exclude, filters, m_trace.filters_length); 00264 } else { 00265 m_trace.filters_exclude[0] = 0; 00266 } 00267 } 00268 const char *mbed_trace_exclude_filters_get(void) 00269 { 00270 return m_trace.filters_exclude; 00271 } 00272 const char *mbed_trace_include_filters_get(void) 00273 { 00274 return m_trace.filters_include; 00275 } 00276 void mbed_trace_include_filters_set(char *filters) 00277 { 00278 if (filters) { 00279 (void)strncpy(m_trace.filters_include, filters, m_trace.filters_length); 00280 } else { 00281 m_trace.filters_include[0] = 0; 00282 } 00283 } 00284 static int8_t mbed_trace_skip(int8_t dlevel, const char *grp) 00285 { 00286 if (dlevel >= 0 && grp != 0) { 00287 // filter debug prints only when dlevel is >0 and grp is given 00288 00289 /// @TODO this could be much better.. 00290 if (m_trace.filters_exclude[0] != '\0' && 00291 strstr(m_trace.filters_exclude, grp) != 0) { 00292 //grp was in exclude list 00293 return 1; 00294 } 00295 if (m_trace.filters_include[0] != '\0' && 00296 strstr(m_trace.filters_include, grp) == 0) { 00297 //grp was in include list 00298 return 1; 00299 } 00300 } 00301 return 0; 00302 } 00303 static void mbed_trace_default_print(const char *str) 00304 { 00305 puts(str); 00306 } 00307 void mbed_tracef(uint8_t dlevel, const char *grp, const char *fmt, ...) 00308 { 00309 va_list ap; 00310 va_start(ap, fmt); 00311 mbed_vtracef(dlevel, grp, fmt, ap); 00312 va_end(ap); 00313 } 00314 void mbed_vtracef(uint8_t dlevel, const char* grp, const char *fmt, va_list ap) 00315 { 00316 if ( m_trace.mutex_wait_f ) { 00317 m_trace.mutex_wait_f(); 00318 m_trace.mutex_lock_count++; 00319 } 00320 00321 if (NULL == m_trace.line) { 00322 goto end; 00323 } 00324 00325 m_trace.line[0] = 0; //by default trace is empty 00326 00327 if (mbed_trace_skip(dlevel, grp) || fmt == 0 || grp == 0 || !m_trace.printf) { 00328 //return tmp data pointer back to the beginning 00329 mbed_trace_reset_tmp(); 00330 goto end; 00331 } 00332 if ((m_trace.trace_config & TRACE_MASK_LEVEL) & dlevel) { 00333 bool color = (m_trace.trace_config & TRACE_MODE_COLOR) != 0; 00334 bool plain = (m_trace.trace_config & TRACE_MODE_PLAIN) != 0; 00335 bool cr = (m_trace.trace_config & TRACE_CARRIAGE_RETURN) != 0; 00336 00337 int retval = 0, bLeft = m_trace.line_length; 00338 char *ptr = m_trace.line; 00339 if (plain == true || dlevel == TRACE_LEVEL_CMD) { 00340 //add trace data 00341 retval = vsnprintf(ptr, bLeft, fmt, ap); 00342 if (dlevel == TRACE_LEVEL_CMD && m_trace.cmd_printf) { 00343 m_trace.cmd_printf(m_trace.line); 00344 m_trace.cmd_printf("\n"); 00345 } else { 00346 //print out whole data 00347 m_trace.printf(m_trace.line); 00348 } 00349 } else { 00350 if (color) { 00351 if (cr) { 00352 retval = snprintf(ptr, bLeft, "\r\x1b[2K"); 00353 if (retval >= bLeft) { 00354 retval = 0; 00355 } 00356 if (retval > 0) { 00357 ptr += retval; 00358 bLeft -= retval; 00359 } 00360 } 00361 if (bLeft > 0) { 00362 //include color in ANSI/VT100 escape code 00363 switch (dlevel) { 00364 case (TRACE_LEVEL_ERROR): 00365 retval = snprintf(ptr, bLeft, "%s", VT100_COLOR_ERROR); 00366 break; 00367 case (TRACE_LEVEL_WARN): 00368 retval = snprintf(ptr, bLeft, "%s", VT100_COLOR_WARN); 00369 break; 00370 case (TRACE_LEVEL_INFO): 00371 retval = snprintf(ptr, bLeft, "%s", VT100_COLOR_INFO); 00372 break; 00373 case (TRACE_LEVEL_DEBUG): 00374 retval = snprintf(ptr, bLeft, "%s", VT100_COLOR_DEBUG); 00375 break; 00376 default: 00377 color = 0; //avoid unneeded color-terminate code 00378 retval = 0; 00379 break; 00380 } 00381 if (retval >= bLeft) { 00382 retval = 0; 00383 } 00384 if (retval > 0 && color) { 00385 ptr += retval; 00386 bLeft -= retval; 00387 } 00388 } 00389 00390 } 00391 if (bLeft > 0 && m_trace.prefix_f) { 00392 //find out length of body 00393 size_t sz = 0; 00394 va_list ap2; 00395 va_copy(ap2, ap); 00396 sz = vsnprintf(NULL, 0, fmt, ap2) + retval + (retval ? 4 : 0); 00397 va_end(ap2); 00398 //add prefix string 00399 retval = snprintf(ptr, bLeft, "%s", m_trace.prefix_f(sz)); 00400 if (retval >= bLeft) { 00401 retval = 0; 00402 } 00403 if (retval > 0) { 00404 ptr += retval; 00405 bLeft -= retval; 00406 } 00407 } 00408 if (bLeft > 0) { 00409 //add group tag 00410 switch (dlevel) { 00411 case (TRACE_LEVEL_ERROR): 00412 retval = snprintf(ptr, bLeft, "[ERR ][%-4s]: ", grp); 00413 break; 00414 case (TRACE_LEVEL_WARN): 00415 retval = snprintf(ptr, bLeft, "[WARN][%-4s]: ", grp); 00416 break; 00417 case (TRACE_LEVEL_INFO): 00418 retval = snprintf(ptr, bLeft, "[INFO][%-4s]: ", grp); 00419 break; 00420 case (TRACE_LEVEL_DEBUG): 00421 retval = snprintf(ptr, bLeft, "[DBG ][%-4s]: ", grp); 00422 break; 00423 default: 00424 retval = snprintf(ptr, bLeft, " "); 00425 break; 00426 } 00427 if (retval >= bLeft) { 00428 retval = 0; 00429 } 00430 if (retval > 0) { 00431 ptr += retval; 00432 bLeft -= retval; 00433 } 00434 } 00435 if (retval > 0 && bLeft > 0) { 00436 //add trace text 00437 retval = vsnprintf(ptr, bLeft, fmt, ap); 00438 if (retval >= bLeft) { 00439 retval = 0; 00440 } 00441 if (retval > 0) { 00442 ptr += retval; 00443 bLeft -= retval; 00444 } 00445 } 00446 00447 if (retval > 0 && bLeft > 0 && m_trace.suffix_f) { 00448 //add suffix string 00449 retval = snprintf(ptr, bLeft, "%s", m_trace.suffix_f()); 00450 if (retval >= bLeft) { 00451 retval = 0; 00452 } 00453 if (retval > 0) { 00454 ptr += retval; 00455 bLeft -= retval; 00456 } 00457 } 00458 00459 if (retval > 0 && bLeft > 0 && color) { 00460 //add zero color VT100 when color mode 00461 retval = snprintf(ptr, bLeft, "\x1b[0m"); 00462 if (retval >= bLeft) { 00463 retval = 0; 00464 } 00465 if (retval > 0) { 00466 // not used anymore 00467 //ptr += retval; 00468 //bLeft -= retval; 00469 } 00470 } 00471 //print out whole data 00472 m_trace.printf(m_trace.line); 00473 } 00474 //return tmp data pointer back to the beginning 00475 mbed_trace_reset_tmp(); 00476 } 00477 00478 end: 00479 if ( m_trace.mutex_release_f ) { 00480 // Store the mutex lock count to temp variable so that it won't get 00481 // clobbered during last loop iteration when mutex gets released 00482 int count = m_trace.mutex_lock_count; 00483 m_trace.mutex_lock_count = 0; 00484 // Since the helper functions (eg. mbed_trace_array) are used like this: 00485 // mbed_tracef(TRACE_LEVEL_INFO, "grp", "%s", mbed_trace_array(some_array)) 00486 // The helper function MUST acquire the mutex if it modifies any buffers. However 00487 // it CANNOT unlock the mutex because that would allow another thread to acquire 00488 // the mutex after helper function unlocks it and before mbed_tracef acquires it 00489 // for itself. This means that here we have to unlock the mutex as many times 00490 // as it was acquired by trace function and any possible helper functions. 00491 do { 00492 m_trace.mutex_release_f(); 00493 } while (--count > 0); 00494 } 00495 } 00496 static void mbed_trace_reset_tmp(void) 00497 { 00498 m_trace.tmp_data_ptr = m_trace.tmp_data; 00499 } 00500 const char *mbed_trace_last(void) 00501 { 00502 return m_trace.line; 00503 } 00504 /* Helping functions */ 00505 #define tmp_data_left() m_trace.tmp_data_length-(m_trace.tmp_data_ptr-m_trace.tmp_data) 00506 #if MBED_CONF_MBED_TRACE_FEA_IPV6 == 1 00507 char *mbed_trace_ipv6(const void *addr_ptr) 00508 { 00509 /** Acquire mutex. It is released before returning from mbed_vtracef. */ 00510 if ( m_trace.mutex_wait_f ) { 00511 m_trace.mutex_wait_f(); 00512 m_trace.mutex_lock_count++; 00513 } 00514 char *str = m_trace.tmp_data_ptr; 00515 if (str == NULL) { 00516 return ""; 00517 } 00518 if (tmp_data_left() < 41) { 00519 return ""; 00520 } 00521 if (addr_ptr == NULL) { 00522 return "<null>"; 00523 } 00524 str[0] = 0; 00525 m_trace.tmp_data_ptr += ip6tos(addr_ptr, str) + 1; 00526 return str; 00527 } 00528 char *mbed_trace_ipv6_prefix(const uint8_t *prefix, uint8_t prefix_len) 00529 { 00530 /** Acquire mutex. It is released before returning from mbed_vtracef. */ 00531 if ( m_trace.mutex_wait_f ) { 00532 m_trace.mutex_wait_f(); 00533 m_trace.mutex_lock_count++; 00534 } 00535 char *str = m_trace.tmp_data_ptr; 00536 if (str == NULL) { 00537 return ""; 00538 } 00539 if (tmp_data_left() < 45) { 00540 return ""; 00541 } 00542 00543 if ((prefix_len != 0 && prefix == NULL) || prefix_len > 128) { 00544 return "<err>"; 00545 } 00546 00547 m_trace.tmp_data_ptr += ip6_prefix_tos(prefix, prefix_len, str) + 1; 00548 return str; 00549 } 00550 #endif //MBED_CONF_MBED_TRACE_FEA_IPV6 00551 char *mbed_trace_array(const uint8_t *buf, uint16_t len) 00552 { 00553 /** Acquire mutex. It is released before returning from mbed_vtracef. */ 00554 if ( m_trace.mutex_wait_f ) { 00555 m_trace.mutex_wait_f(); 00556 m_trace.mutex_lock_count++; 00557 } 00558 int i, bLeft = tmp_data_left(); 00559 char *str, *wptr; 00560 str = m_trace.tmp_data_ptr; 00561 if (len == 0 || str == NULL || bLeft == 0) { 00562 return ""; 00563 } 00564 if (buf == NULL) { 00565 return "<null>"; 00566 } 00567 wptr = str; 00568 wptr[0] = 0; 00569 const uint8_t *ptr = buf; 00570 char overflow = 0; 00571 for (i = 0; i < len; i++) { 00572 if (bLeft <= 3) { 00573 overflow = 1; 00574 break; 00575 } 00576 int retval = snprintf(wptr, bLeft, "%02x:", *ptr++); 00577 if (retval <= 0 || retval > bLeft) { 00578 break; 00579 } 00580 bLeft -= retval; 00581 wptr += retval; 00582 } 00583 if (wptr > str) { 00584 if( overflow ) { 00585 // replace last character as 'star', 00586 // which indicate buffer len is not enough 00587 *(wptr - 1) = '*'; 00588 } else { 00589 //null to replace last ':' character 00590 *(wptr - 1) = 0; 00591 } 00592 } 00593 m_trace.tmp_data_ptr = wptr; 00594 return str; 00595 }
Generated on Sun Jul 17 2022 08:25:27 by 1.7.2