diff --git a/src/include/ngspice/stringutil.h b/src/include/ngspice/stringutil.h index cc7d2e1e1..bb372b6bd 100644 --- a/src/include/ngspice/stringutil.h +++ b/src/include/ngspice/stringutil.h @@ -24,6 +24,12 @@ char * gettok(char **s); char * gettok_instance(char **); char * gettok_char(char **s, char p, bool inc_p, bool nested); +#ifdef __GNUC__ +extern char *tprintf(const char *fmt, ...) __attribute__ ((format (__printf__, 1, 2))); +#else +extern char *tprintf(const char *fmt, ...); +#endif + #ifdef CIDER /* cider integration */ diff --git a/src/misc/string.c b/src/misc/string.c index 1166597b5..237f99bec 100644 --- a/src/misc/string.c +++ b/src/misc/string.c @@ -10,6 +10,9 @@ Copyright 1990 Regents of the University of California. All rights reserved. #include "ngspice/stringutil.h" #include "ngspice/dstring.h" +#include + + int prefix(register char *p, register char *s) { @@ -49,6 +52,45 @@ copy_substring(const char *str, const char *end) return(p); } + +char* +tprintf(const char *fmt, ...) +{ + char buf[1024]; + char *p = buf; + int size = sizeof(buf); + + va_list args; + + for (;;) { + + int nchars; + + va_start(args, fmt); + + nchars = vsnprintf(p, (size_t) size, fmt, args); + + va_end(args); + + if (nchars == -1) { // compatibility to old implementations + size *= 2; + } else if (size < nchars + 1) { + size = nchars + 1; + } else { + break; + } + + if (p == buf) + p = TMALLOC(char, size); + else + p = TREALLOC(char, p, size); + } + + + return (p == buf) ? copy(p) : p; +} + + /* Determine whether sub is a substring of str. */ /* Like strstr( ) XXX */