11#include <stddef.h>
22#include <stdarg.h>
3- #include <string.h>
43#include <stdio.h>
5- #include <stdbool.h>
64#include <stdlib.h>
75#include <ti/sprintf.h>
86
97#define SINK (char *__restrict)0xE40000
108
119int boot_vsnprintf (char * __restrict buffer , size_t count , const char * __restrict format , va_list args ) {
12- int str_len = boot_vsprintf (SINK , format , args );
10+ va_list args_copy ;
11+ va_copy (args_copy , args );
12+ int str_len = boot_vsprintf (SINK , format , args_copy );
13+ va_end (args_copy );
14+
1315 if (buffer == NULL || count == 0 ) {
1416 return str_len ;
1517 }
16- if ((size_t )str_len >= count || str_len <= 0 ) {
17- // won't fit or invalid formatting
18+ // str_len == 0 can take this fast path
19+ if ((size_t )str_len >= count || str_len < 0 || str_len == 0 ) {
20+ // won't fit, invalid formatting, or empty string
1821 * buffer = '\0' ;
1922 return str_len ;
2023 }
@@ -32,18 +35,30 @@ int boot_snprintf(char *__restrict buffer, size_t count, const char *__restrict
3235__attribute__((weak , alias ("boot_snprintf" ))) int snprintf (char * __restrict buffer , size_t count , const char * __restrict format , ...);
3336
3437int boot_vasprintf (char * * __restrict p_buffer , const char * __restrict format , va_list args ) {
35- int ret = -1 ;
3638 * p_buffer = NULL ;
37- int str_len = boot_vsprintf (SINK , format , args );
39+ va_list args_copy ;
40+ va_copy (args_copy , args );
41+ int str_len = boot_vsprintf (SINK , format , args_copy );
42+ va_end (args_copy );
43+
3844 if (str_len < 0 ) {
3945 // formatting error
4046 return str_len ;
4147 }
4248 size_t buffer_size = (size_t )str_len + 1 ;
43- * p_buffer = malloc (buffer_size );
44- if (* p_buffer != NULL ) {
45- ret = boot_vsprintf (* p_buffer , format , args );
49+ char * buffer = malloc (buffer_size );
50+ if (buffer == NULL ) {
51+ // malloc failure
52+ return -1 ;
53+ }
54+ va_copy (args_copy , args );
55+ int ret = boot_vsprintf (buffer , format , args_copy );
56+ va_end (args_copy );
57+ if (ret < 0 ) {
58+ free (buffer );
59+ return ret ;
4660 }
61+ * p_buffer = buffer ;
4762 return ret ;
4863}
4964__attribute__((weak , alias ("boot_vasprintf" ))) int vasprintf (char * * __restrict p_buffer , const char * __restrict format , va_list args );
0 commit comments