jcs
/subtext
/amendments
/583
util: Fix truncated termination in snprintf, handle 0 length
jcs made amendment 583 9 months ago
--- util.c Wed Jan 24 09:19:14 2024
+++ util.c Thu Feb 1 17:37:17 2024
@@ -1724,17 +1724,17 @@ static struct format {
int precision;
} default_format;
-int bounded_vfprintf(FILE *fp, const char *fmt, va_list arg);
+short bounded_vfprintf(FILE *fp, const char *fmt, va_list arg);
static int nullio(FILE *fp, int i);
-int
+short
bounded_vfprintf(FILE *fp, const char *fmt, va_list arg)
{
register int c, i, nwritten = 0;
register unsigned long n;
register char *s;
#define VFPRINTF_BUFLEN 512
- char buf[VFPRINTF_BUFLEN], *digits, *t;
+ static char buf[VFPRINTF_BUFLEN], *digits, *t;
struct format F;
for (c = *fmt; c; c = *++fmt) {
@@ -2010,7 +2010,7 @@ done:
return(nwritten);
}
-int
+short
snprintf(char *s, size_t size, const char *fmt, ...)
{
return(vsnprintf(s, size, fmt, __va(fmt)));
@@ -2022,20 +2022,32 @@ nullio(FILE *fp, int i)
return(EOF);
}
-int
+short
vsnprintf(char *s, size_t size, const char *fmt, void *p)
{
FILE f;
int n;
+ unsigned char zb;
memset(&f, 0, sizeof(f));
f.refnum = -1;
- f.ptr = (unsigned char *) s;
+ f.ptr = (unsigned char *)s;
f.cnt = size;
f.proc = nullio;
f.dirty = 1;
- if ((n = bounded_vfprintf(&f, fmt, p)) >= 0)
- s[n] = 0;
+ if (size == 0)
+ zb = s[0];
+
+ if ((n = bounded_vfprintf(&f, fmt, p)) >= 0) {
+ if (n < size)
+ s[n] = 0;
+ else
+ s[size - 1] = 0;
+ }
+
+ if (size == 0)
+ s[0] = zb;
+
return(n);
}
--- util.h Tue Nov 14 16:44:25 2023
+++ util.h Thu Feb 1 17:37:30 2024
@@ -161,7 +161,7 @@ size_t strlcat(char *dst, const char *src, size_t dsiz
size_t strlcpy(char *dst, const char *src, size_t dsize);
char * strndup(const char *str, size_t maxlen);
char * strsep(char **stringp, const char *delim);
-int snprintf(char *s, size_t size, const char *fmt, ...);
-int vsnprintf(char *s, size_t size, const char *fmt, void *p);
+short snprintf(char *s, size_t size, const char *fmt, ...);
+short vsnprintf(char *s, size_t size, const char *fmt, void *p);
#endif