1 /* $NetBSD: snprintf.c,v 1.5 2020/05/25 20:47:35 christos Exp $ */ 2 3 4 #ifndef HAVE_VPRINTF 5 #include "choke-me: no vprintf and no snprintf" 6 choke me. 7 #endif 8 9 #if defined(HAVE_STDARG_H) 10 # include <stdarg.h> 11 # ifndef VA_START 12 # define VA_START(a, f) va_start(a, f) 13 # define VA_END(a) va_end(a) 14 # endif /* VA_START */ 15 # define SNV_USING_STDARG_H 16 17 #elif defined(HAVE_VARARGS_H) 18 # include <varargs.h> 19 # ifndef VA_START 20 # define VA_START(a, f) va_start(a) 21 # define VA_END(a) va_end(a) 22 # endif /* VA_START */ 23 # undef SNV_USING_STDARG_H 24 25 #else 26 # include "must-have-stdarg-or-varargs" 27 choke me. 28 #endif 29 30 static int 31 snprintf(char *str, size_t n, char const *fmt, ...) 32 { 33 va_list ap; 34 int rval; 35 36 #ifdef VSPRINTF_CHARSTAR 37 char *rp; 38 VA_START(ap, fmt); 39 rp = vsprintf(str, fmt, ap); 40 VA_END(ap); 41 rval = strlen(rp); 42 43 #else 44 VA_START(ap, fmt); 45 rval = vsprintf(str, fmt, ap); 46 VA_END(ap); 47 #endif 48 49 if (rval > n) { 50 fprintf(stderr, "snprintf buffer overrun %d > %d\n", rval, (int)n); 51 abort(); 52 } 53 return rval; 54 } 55 56 static int 57 vsnprintf( char *str, size_t n, char const *fmt, va_list ap ) 58 { 59 #ifdef VSPRINTF_CHARSTAR 60 return (strlen(vsprintf(str, fmt, ap))); 61 #else 62 return (vsprintf(str, fmt, ap)); 63 #endif 64 } 65