diff -up sudo-1.8.6p3/common/lbuf.c.lbufexpandcode sudo-1.8.6p3/common/lbuf.c
--- sudo-1.8.6p3/common/lbuf.c.lbufexpandcode 2013-08-12 17:28:52.429562473 +0200
+++ sudo-1.8.6p3/common/lbuf.c 2013-08-12 17:29:21.486668465 +0200
@@ -77,6 +77,17 @@ lbuf_destroy(struct lbuf *lbuf)
debug_return;
}
+static void
+lbuf_expand(struct lbuf *lbuf, size_t extra)
+{
+ if (lbuf->len + extra + 1 >= lbuf->size) {
+ do {
+ lbuf->size += 256;
+ } while (lbuf->len + extra + 1 >= lbuf->size);
+ lbuf->buf = erealloc(lbuf->buf, lbuf->size);
+ }
+}
+
/*
* Parse the format and append strings, only %s and %% escapes are supported.
* Any characters in set are quoted with a backslash.
@@ -86,47 +97,40 @@ lbuf_append_quoted(struct lbuf *lbuf, co
{
va_list ap;
int len;
- char *cp, *s = NULL;
+ char *cp, *s;
debug_decl(lbuf_append_quoted, SUDO_DEBUG_UTIL)
va_start(ap, fmt);
while (*fmt != '\0') {
- len = 1;
if (fmt[0] == '%' && fmt[1] == 's') {
- s = va_arg(ap, char *);
- len = strlen(s);
- }
- /* Assume worst case that all chars must be escaped. */
- if (lbuf->len + (len * 2) + 1 >= lbuf->size) {
- do {
- lbuf->size += 256;
- } while (lbuf->len + len + 1 >= lbuf->size);
- lbuf->buf = erealloc(lbuf->buf, lbuf->size);
- }
- if (*fmt == '%') {
- if (*(++fmt) == 's') {
- while ((cp = strpbrk(s, set)) != NULL) {
- len = (int)(cp - s);
- memcpy(lbuf->buf + lbuf->len, s, len);
- lbuf->len += len;
- lbuf->buf[lbuf->len++] = '\\';
- lbuf->buf[lbuf->len++] = *cp;
- s = cp + 1;
- }
- if (*s != '\0') {
- len = strlen(s);
- memcpy(lbuf->buf + lbuf->len, s, len);
- lbuf->len += len;
- }
- fmt++;
- continue;
+ if ((s = va_arg(ap, char *)) == NULL)
+ goto done;
+ while ((cp = strpbrk(s, set)) != NULL) {
+ len = (int)(cp - s);
+ lbuf_expand(lbuf, len + 2);
+ memcpy(lbuf->buf + lbuf->len, s, len);
+ lbuf->len += len;
+ lbuf->buf[lbuf->len++] = '\\';
+ lbuf->buf[lbuf->len++] = *cp;
+ s = cp + 1;
}
+ if (*s != '\0') {
+ len = strlen(s);
+ lbuf_expand(lbuf, len);
+ memcpy(lbuf->buf + lbuf->len, s, len);
+ lbuf->len += len;
+ }
+ fmt += 2;
+ continue;
}
+ lbuf_expand(lbuf, 2);
if (strchr(set, *fmt) != NULL)
lbuf->buf[lbuf->len++] = '\\';
lbuf->buf[lbuf->len++] = *fmt++;
}
- lbuf->buf[lbuf->len] = '\0';
+done:
+ if (lbuf->size != 0)
+ lbuf->buf[lbuf->len] = '\0';
va_end(ap);
debug_return;
@@ -140,33 +144,27 @@ lbuf_append(struct lbuf *lbuf, const cha
{
va_list ap;
int len;
- char *s = NULL;
+ char *s;
debug_decl(lbuf_append, SUDO_DEBUG_UTIL)
va_start(ap, fmt);
while (*fmt != '\0') {
- len = 1;
if (fmt[0] == '%' && fmt[1] == 's') {
- s = va_arg(ap, char *);
+ if ((s = va_arg(ap, char *)) == NULL)
+ goto done;
len = strlen(s);
+ lbuf_expand(lbuf, len);
+ memcpy(lbuf->buf + lbuf->len, s, len);
+ lbuf->len += len;
+ fmt += 2;
+ continue;
}
- if (lbuf->len + len + 1 >= lbuf->size) {
- do {
- lbuf->size += 256;
- } while (lbuf->len + len + 1 >= lbuf->size);
- lbuf->buf = erealloc(lbuf->buf, lbuf->size);
- }
- if (*fmt == '%') {
- if (*(++fmt) == 's') {
- memcpy(lbuf->buf + lbuf->len, s, len);
- lbuf->len += len;
- fmt++;
- continue;
- }
- }
+ lbuf_expand(lbuf, 1);
lbuf->buf[lbuf->len++] = *fmt++;
}
- lbuf->buf[lbuf->len] = '\0';
+done:
+ if (lbuf->size != 0)
+ lbuf->buf[lbuf->len] = '\0';
va_end(ap);
debug_return;