23#define UPRINTF_S16_FMT "%d"
24#define UPRINTF_U16_FMT "%u"
26#define UPRINTF_S16_DIGITS 5
28#ifndef UPRINTF_S32_FMT
29# if __LONG_WIDTH__ == 64 || __EMSCRIPTEN__
30# define UPRINTF_S32_FMT "%d"
31# elif __LONG_WIDTH__ == 32 || defined( __WATCOMC__ ) || defined( __BORLANDC__ ) || _MSC_VER <= 1200
32# define UPRINTF_S32_FMT "%ld"
36#ifndef UPRINTF_U32_FMT
37# if __LONG_WIDTH__ == 64 || __EMSCRIPTEN__
38# define UPRINTF_U32_FMT "%u"
39# elif __LONG_WIDTH__ == 32 || defined( __WATCOMC__ ) || defined( __BORLANDC__ ) || _MSC_VER <= 1200
40# define UPRINTF_U32_FMT "%lu"
44#ifndef UPRINTF_X32_FMT
45# if __LONG_WIDTH__ == 64 || __EMSCRIPTEN__
46# define UPRINTF_X32_FMT "%x"
47# elif __LONG_WIDTH__ == 32 || defined( __WATCOMC__ ) || defined( __BORLANDC__ ) || _MSC_VER <= 1200
48# define UPRINTF_X32_FMT "%lx"
54#define NEWLINE_STR "\n"
59#ifndef UPRINTF_BUFFER_SZ_MAX
60# define UPRINTF_BUFFER_SZ_MAX 1024
64# define platform_file FILE*
67#ifndef platform_fprintf
68# define platform_fprintf fprintf
71#ifndef platform_vfprintf
72# define platform_vfprintf vfprintf
76# define platform_fopen fopen
79#ifndef platform_fflush
80# define platform_fflush fflush
83#ifndef platform_fclose
84# define platform_fclose fclose
91# define LOG_ERR_TARGET g_log_file
92# define LOG_STD_TARGET g_log_file
94# define LOG_ERR_TARGET stderr
95# define LOG_STD_TARGET stdout
100# define SIZE_T_FMT "%lu"
101# define SSIZE_T_FMT "%ld"
102# define OFF_T_FMT "%lld"
103# elif defined( _WIN64 )
104# define SIZE_T_FMT "%I64u"
105# define SSIZE_T_FMT "%I64d"
106# define OFF_T_FMT "%I32d"
108# define SIZE_T_FMT "%lu"
109# define SSIZE_T_FMT "%ld"
110# define OFF_T_FMT "%lu"
113# define SIZE_T_FMT "%u"
114# define SSIZE_T_FMT "%d"
115# define OFF_T_FMT "%lu"
118#ifdef MAUG_OS_DOS_REAL
119# define UPRINTF_MS_FMT UPRINTF_U16_FMT
121# define UPRINTF_MS_FMT UPRINTF_U32_FMT
124#if !defined( DEBUG_THRESHOLD )
125# define DEBUG_THRESHOLD 1
137#if defined( MAUG_OS_NDS )
143static void _internal_debug_printf(
144 const char* src_file,
int line,
int level,
const char* fmt, ...
147 char buffer[UPRINTF_BUFFER_SZ_MAX + 1];
148 char line_buffer[11] = { 0 };
150 if( level >= DEBUG_THRESHOLD ) {
151 va_start( argp, fmt );
152 vsnprintf( buffer, UPRINTF_BUFFER_SZ_MAX, fmt, argp );
154 snprintf( line_buffer, 10,
"%d", line );
155 nocashMessage( src_file );
156 nocashMessage(
" (" );
157 nocashMessage( line_buffer );
158 nocashMessage(
"): " );
159 nocashMessage( buffer );
160 nocashMessage(
"\n" );
164#define debug_printf( lvl, ... ) \
165 _internal_debug_printf( __FILE__, __LINE__, lvl, __VA_ARGS__ )
167static void error_printf(
const char* fmt, ... ) {
169 char buffer[UPRINTF_BUFFER_SZ_MAX + 1];
171 va_start( argp, fmt );
172 vsnprintf( buffer, UPRINTF_BUFFER_SZ_MAX, fmt, argp );
175 nocashMessage( buffer );
176 nocashMessage(
"\n" );
179# define size_printf( lvl, name, sz ) debug_printf( lvl, name " size is " SIZE_T_FMT " bytes", (sz) );
182#elif defined( UPRINTF_ANCIENT_C )
187#ifdef RETROFLAT_API_WINCE
189static void debug_printf(
int level,
const char* fmt, ... ) {
193static void error_printf(
const char* fmt, ... ) {
199static void debug_printf(
int level,
const char* fmt, ... ) {
202 if( level >= DEBUG_THRESHOLD ) {
203 va_start( argp, fmt );
204 vprintf( fmt, argp );
210static void error_printf(
const char* fmt, ... ) {
213 va_start( argp, fmt );
214 vprintf( fmt, argp );
221# define size_printf( lvl, name, sz ) debug_printf( lvl, name " size is " SIZE_T_FMT " bytes", (sz) );
223# define size_multi_printf( lvl, name, sz, max ) debug_printf( lvl, "single " name " size is " SIZE_T_FMT " bytes, " name " array size is " SIZE_T_FMT " bytes", (sz), ((sz) * (max)) );
226#elif defined( UPRINTF_LOG )
229# ifdef NO_DEBUG_LINE_NUMBER
230# define LINE_NUMBER() 0
232# define LINE_NUMBER() __LINE__
235# define internal_debug_printf( lvl, ... ) if( NULL != LOG_ERR_TARGET && lvl >= DEBUG_THRESHOLD ) { platform_fprintf( LOG_STD_TARGET, "(%d) " __FILE__ ": %d: ", lvl, LINE_NUMBER() ); platform_fprintf( LOG_STD_TARGET, __VA_ARGS__ ); platform_fprintf( LOG_STD_TARGET, NEWLINE_STR ); platform_fflush( LOG_STD_TARGET ); }
237# define internal_error_printf( ... ) if( NULL != LOG_ERR_TARGET ) { platform_fprintf( LOG_ERR_TARGET, "(E) " __FILE__ ": %d: ", LINE_NUMBER() ); platform_fprintf( LOG_ERR_TARGET, __VA_ARGS__ ); platform_fprintf( LOG_ERR_TARGET, NEWLINE_STR ); platform_fflush( LOG_ERR_TARGET ); }
239# define debug_printf( lvl, ... ) internal_debug_printf( lvl, __VA_ARGS__ )
241# define error_printf( ... ) internal_error_printf( __VA_ARGS__ )
243# define size_printf( lvl, name, sz ) internal_debug_printf( lvl, name " size is " SIZE_T_FMT " bytes", (sz) );
245# define size_multi_printf( lvl, name, sz, max ) internal_debug_printf( lvl, "single " name " size is " SIZE_T_FMT " bytes, " name " array size is " SIZE_T_FMT " bytes", (sz), ((sz) * (max)) );
253# define debug_printf( ... )
254# define error_printf( ... )
255# define size_printf( ... )
256# define size_multi_printf( ... )
264# define logging_init() g_log_file = platform_fopen( LOG_FILE_NAME, "w" );
265# define logging_shutdown() platform_fclose( g_log_file );
267# if defined( UPRINTF_C )
268platform_file g_log_file = NULL;
270extern platform_file g_log_file;
275# define logging_init()
276# define logging_shutdown()
280#define maug_bufcat( c, buf, buf_idx, buf_sz, cleanup ) \
281 buf[buf_idx++] = c; \
282 if( buf_idx >= buf_sz ) { goto cleanup; }
284#define maug_bufpad( pad_c, pad_sz, i, buf, buf_idx, buf_sz, cleanup ) \
286 while( i < pad_sz ) { \
287 maug_bufcat( pad_c, buffer, buffer_idx, buffer_sz, cleanup ); \
291int maug_digits(
long int num,
int base );
293int maug_zdigits(
size_t num,
int base );
295#define maug_xtoa( num, base, rem, dest, dest_idx, digits, digits_done, pad ) \
296 dest_idx += digits; \
297 while( 0 != num ) { \
300 dest[--dest_idx] = (9 < rem) ? \
309 while( digits_done < digits ) { \
310 dest[--dest_idx] = '0'; \
317#define maug_hctoi( c ) \
318 ('9' > (c) ? (c) - '0' : 'a' > (c) ? 10 + (c) - 'A' : 10 + (c) - 'a')
320int maug_is_num(
const char* str,
size_t str_sz, uint8_t base, uint8_t sign );
322int maug_is_float(
const char* str,
size_t str_sz );
324int maug_itoa(
long int num,
char* dest,
int dest_sz,
int base );
326int maug_utoa( uint32_t num,
char* dest,
int dest_sz,
int base );
328int maug_ztoa(
size_t num,
char* dest,
int dest_sz,
int base );
337uint32_t
maug_atou32(
const char* buffer,
size_t buffer_sz, uint8_t base );
348float maug_atof(
const char* buffer,
size_t buffer_sz );
350void maug_str_upper(
char* line,
size_t line_sz );
352void maug_str_lower(
char* line,
size_t line_sz );
355 size_t idx,
const char* line,
size_t line_sz,
char* out,
size_t out_sz );
358 size_t idx,
const char* line,
size_t line_sz, int16_t* out );
361 char* buffer,
int buffer_sz,
const char* fmt, va_list vargs );
363void maug_snprintf(
char* buffer,
int buffer_sz,
const char* fmt, ... );
365void maug_printf(
const char* fmt, ... );
371uint32_t g_maug_printf_line = 0;
372int g_maug_uprintf_threshold = DEBUG_THRESHOLD;
374int maug_is_num(
const char* str,
size_t str_sz, uint8_t base, uint8_t sign ) {
378 str_sz = maug_strlen( str );
381 for( i = 0 ; str_sz > i ; i++ ) {
383 if( sign && 0 == i &&
'-' == str[i] ) {
385 }
else if(
'0' > str[i] ||
'9' < str[i] ) {
393int maug_is_float(
const char* str,
size_t str_sz ) {
397 str_sz = maug_strlen( str );
400 for( i = 0 ; str_sz > i ; i++ ) {
401 if( (
'0' > str[i] ||
'9' < str[i]) &&
'.' != str[i] ) {
409int maug_digits(
long int num,
int base ) {
436int maug_zdigits(
size_t num,
int base ) {
458int maug_itoa(
long int num,
char* dest,
int dest_sz,
int base ) {
465 digits = maug_digits( num, base );
466 assert( (0 == num && 1 == digits) || (0 != num && 0 < digits) );
467 assert( digits < dest_sz );
473 }
else if( 0 > num ) {
478 maug_xtoa( num, base, rem, dest, dest_idx, digits, digits_done, pad );
481 dest[dest_idx] =
'-';
491int maug_utoa( uint32_t num,
char* dest,
int dest_sz,
int base ) {
497 digits = maug_digits( num, base );
498 assert( (0 == num && 1 == digits) || (0 != num && 0 < digits) );
499 assert( digits < dest_sz );
507 maug_xtoa( num, base, rem, dest, dest_idx, digits, digits_done, pad );
515int maug_ztoa(
size_t num,
char* dest,
int dest_sz,
int base ) {
521 digits = maug_zdigits( num, base );
522 assert( (0 == num && 1 == digits) || (0 != num && 0 < digits) );
523 assert( digits < dest_sz );
531 maug_xtoa( num, base, rem, dest, dest_idx, digits, digits_done, pad );
539uint32_t
maug_atou32(
const char* buffer,
size_t buffer_sz, uint8_t base ) {
541 uint32_t u32_out = 0;
543 if( 0 == buffer_sz ) {
544 buffer_sz = maug_strlen( buffer );
547 for( i = 0 ; buffer_sz > i ; i++ ) {
548 if( base > 10 &&
'a' <= buffer[i] ) {
550 u32_out += (buffer[i] -
'a') + 10;
551 }
else if( base > 10 &&
'A' <= buffer[i] ) {
553 u32_out += (buffer[i] -
'A') + 10;
554 }
else if(
'0' <= buffer[i] ) {
556 u32_out += (buffer[i] -
'0');
567int32_t
maug_atos32(
const char* buffer,
size_t buffer_sz ) {
572 if( 0 == buffer_sz ) {
573 buffer_sz = maug_strlen( buffer );
576 for( i = 0 ; buffer_sz > i ; i++ ) {
577 if(
'-' == buffer[i] && 0 == i ) {
579 }
else if(
'0' <= buffer[i] &&
'9' >= buffer[i] ) {
581 s32_out += (buffer[i] -
'0');
596float maug_atof(
const char* buffer,
size_t buffer_sz ) {
601 if( 0 == buffer_sz ) {
602 buffer_sz = maug_strlen( buffer );
605 for( i = 0 ; buffer_sz > i ; i++ ) {
606 if(
'0' <= buffer[i] &&
'9' >= buffer[i] ) {
610 float_out += (buffer[i] -
'0');
613 float_out += ((buffer[i] -
'0') * dec_sz);
616 }
else if(
'.' == buffer[i] ) {
629void maug_str_upper(
char* line,
size_t line_sz ) {
632 for( i = 0 ; line_sz > i ; i++ ) {
633 if( 0x61 <= line[i] && 0x7a >= line[i] ) {
641void maug_str_lower(
char* line,
size_t line_sz ) {
644 for( i = 0 ; line_sz > i ; i++ ) {
645 if( 0x41 <= line[i] && 0x5a >= line[i] ) {
654 size_t idx,
const char* line,
size_t line_sz,
char* out,
size_t out_sz
662 line_sz = maug_strlen( line );
666 for( i_in = 0 ; line_sz >= i_in ; i_in++ ) {
667 if(
'\n' == line[i_in] ||
' ' == line[i_in] ||
'\0' == line[i_in] ) {
670 if( idx_iter > idx ) {
674 assert( i_out < out_sz );
678 }
else if( idx_iter == idx ) {
679 if( i_out + 1 >= out_sz ) {
681 "token " SIZE_T_FMT
" would exceed buffer sz: " SIZE_T_FMT,
686 out[i_out++] = line[i_in];
690 error_printf(
"token " SIZE_T_FMT
" not available in line!", idx );
700 size_t idx,
const char* line,
size_t line_sz, int16_t* out
703 char out_str[UPRINTF_S16_DIGITS + 1];
705 maug_mzero( out_str, UPRINTF_S16_DIGITS + 1 );
707 retval = maug_tok_str(
708 idx, line, line_sz, out_str, UPRINTF_S16_DIGITS + 1 );
709 maug_cleanup_if_not_ok();
722 char* buffer,
int buffer_sz,
const char* fmt, va_list vargs
731 int spec_is_long = 0;
733 for( i = 0 ;
'\0' != fmt[i] ; i++ ) {
745 spec.s = va_arg( vargs,
char* );
749 while(
'\0' != spec.s[j] ) {
750 maug_bufcat( spec.s[j++], buffer, buffer_idx,
751 buffer_sz, cleanup );
757 spec.u = va_arg( vargs, uint32_t );
759 spec.u = va_arg( vargs,
unsigned int );
763 pad_len -= maug_digits( spec.d, 10 );
764 maug_bufpad( pad_char, pad_len, j,
765 buffer, buffer_idx, buffer_sz, cleanup );
768 buffer_idx += maug_utoa(
769 spec.d, &(buffer[buffer_idx]), buffer_sz - buffer_idx, 10 );
774 spec.d = va_arg( vargs,
long int );
776 spec.d = va_arg( vargs,
int );
780 pad_len -= maug_digits( spec.d, 10 );
781 maug_bufpad( pad_char, pad_len, j,
782 buffer, buffer_idx, buffer_sz, cleanup );
785 buffer_idx += maug_itoa(
786 spec.d, &(buffer[buffer_idx]), buffer_sz - buffer_idx, 10 );
790 spec.z = va_arg( vargs,
size_t );
793 pad_len -= maug_zdigits( spec.z, 10 );
794 maug_bufpad( pad_char, pad_len, j,
795 buffer, buffer_idx, buffer_sz, cleanup );
798 buffer_idx += maug_ztoa(
799 spec.z, &(buffer[buffer_idx]), buffer_sz - buffer_idx, 10 );
803 spec.d = va_arg( vargs,
int );
806 pad_len -= maug_digits( spec.d, 16 );
807 maug_bufpad( pad_char, pad_len, j,
808 buffer, buffer_idx, buffer_sz, cleanup );
811 buffer_idx += maug_utoa(
812 spec.d, &(buffer[buffer_idx]), buffer_sz - buffer_idx, 16 );
816 spec.c = va_arg( vargs,
int );
820 maug_bufpad( pad_char, pad_len, j,
821 buffer, buffer_idx, buffer_sz, cleanup );
824 maug_bufcat( spec.c, buffer, buffer_idx,
825 buffer_sz, cleanup );
831 maug_bufcat(
'%', buffer, buffer_idx, buffer_sz, cleanup );
857 pad_len += (c -
'0');
861 }
else if(
'%' != c ) {
867 maug_bufcat( c, buffer, buffer_idx,
868 buffer_sz, cleanup );
875 maug_bufcat(
'\0', buffer, buffer_idx,
876 buffer_sz, cleanup );
885void maug_snprintf(
char* buffer,
int buffer_sz,
const char* fmt, ... ) {
888 va_start( vargs, fmt );
889 maug_vsnprintf( buffer, buffer_sz, fmt, vargs );
895void maug_printf(
const char* fmt, ... ) {
896 char buffer[UPRINTF_BUFFER_SZ_MAX];
899 va_start( vargs, fmt );
900 maug_vsnprintf( buffer, UPRINTF_BUFFER_SZ_MAX, fmt, vargs );
908#ifndef RETROFLAT_API_WINCE
910void maug_debug_printf(
911 FILE* out, uint8_t flags,
const char* src_name,
size_t line, int16_t lvl,
924 if( lvl >= g_maug_uprintf_threshold ) {
925 platform_fprintf( out,
"(%d) %s : " SIZE_T_FMT
": ",
926 lvl, src_name, line );
928 va_start( vargs, fmt );
929 platform_vfprintf( out, fmt, vargs );
932 platform_fprintf( out, NEWLINE_STR );
933 platform_fflush( out );
941extern uint32_t g_maug_printf_line;
int MERROR_RETVAL
Return type indicating function returns a value from this list.
Definition merror.h:19
#define maug_mzero(ptr, sz)
Zero the block of memory pointed to by ptr.
Definition mmem.h:62
uint32_t maug_atou32(const char *buffer, size_t buffer_sz, uint8_t base)
int32_t maug_atos32(const char *buffer, size_t buffer_sz)