summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--ChangeLog7
-rw-r--r--src/conf.h6
-rw-r--r--src/main.c15
3 files changed, 25 insertions, 3 deletions
diff --git a/ChangeLog b/ChangeLog
index 84ad22e..efdf4ab 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,10 @@
+2007-08-14 Bernhard R. Link <brlink@debian.org>
+
+ * src/main.c (xvsprintf): limit memory allocation
+ to 200K when vsnprintf return -1. (i.e. on pre-1999
+ systems not distinguising fatal errors and too small
+ buffer).
+
2007-07-08 Bernhard R. Link <brlink@debian.org>
* src/manage.c (get_res_name, get_res_class): remove
diff --git a/src/conf.h b/src/conf.h
index d0322cc..8a62c20 100644
--- a/src/conf.h
+++ b/src/conf.h
@@ -123,4 +123,10 @@
#define DEFAULT_FONT "-*-fixed-bold-r-normal-*-15-*-*-*-c-*-*-*"
#define BACKUP_FONT "*"
+/* maximum xvsprintf result string length for systems with pre-C99 snprintf:
+ * on errors that are either permanent or cannot be distinguished from those
+ * as libc's snprintf might by returning -1 for too small buffers, at most
+ * the double of this value is tried before giving up */
+#define MAX_LEGACY_SNPRINTF_SIZE 102400
+
#endif /* !_ _RATPOISON_CONF_H */
diff --git a/src/main.c b/src/main.c
index 7c7b468..933decb 100644
--- a/src/main.c
+++ b/src/main.c
@@ -126,15 +126,24 @@ xvsprintf (char *fmt, va_list ap)
return buffer;
else if (nchars > -1)
size = nchars + 1;
- else
+ /* c99 says -1 is an error other than truncation,
+ * which thus will not go away with a larger buffer.
+ * To support older system but not making errors fatal
+ * (ratpoison will abort when trying to get too much memory otherwise),
+ * try to increase a bit but not too much: */
+ else if (size < MAX_LEGACY_SNPRINTF_SIZE)
size *= 2;
+ else
+ {
+ free(buffer);
+ break;
+ }
/* Resize the buffer and try again. */
buffer = (char *)xrealloc (buffer, size);
}
- /* Never gets here. */
- return NULL;
+ return xstrdup("<FAILURE>");
}
/* Return a new string based on fmt. */