]> git.ipfire.org Git - thirdparty/Python/cpython.git/commitdiff
- Issues #2588, #2589: Fix potential integer underflow and overflow
authorMatthias Klose <doko@ubuntu.com>
Wed, 12 Nov 2008 07:08:51 +0000 (07:08 +0000)
committerMatthias Klose <doko@ubuntu.com>
Wed, 12 Nov 2008 07:08:51 +0000 (07:08 +0000)
  conditions in the PyOS_vsnprintf C API function. CVE-2008-3144.

Misc/NEWS
Python/mysnprintf.c

index bf3f7462eb1f743da029915e71553bd58d307f7d..32dd128f0156c9cca069d9613e2765138b1458af 100644 (file)
--- a/Misc/NEWS
+++ b/Misc/NEWS
@@ -27,6 +27,9 @@ Core and builtins
 - Issue #2586: Fix CVE-2008-1721, zlib crash from
   zlib.decompressobj().flush(val) when val is not positive.
 
+- Issues #2588, #2589: Fix potential integer underflow and overflow
+  conditions in the PyOS_vsnprintf C API function. CVE-2008-3144.
+
 Extension Modules
 -----------------
 
index 4d3770d894359b14a78680051cf58c78bdfe8972..3173863c466f6aa16b3e1f682ee46de63f152c47 100644 (file)
@@ -54,18 +54,28 @@ int
 PyOS_vsnprintf(char *str, size_t size, const char  *format, va_list va)
 {
        int len;  /* # bytes written, excluding \0 */
-#ifndef HAVE_SNPRINTF
+#ifdef HAVE_SNPRINTF
+#define _PyOS_vsnprintf_EXTRA_SPACE 1
+#else
+#define _PyOS_vsnprintf_EXTRA_SPACE 512
        char *buffer;
 #endif
        assert(str != NULL);
        assert(size > 0);
        assert(format != NULL);
+       /* We take a size_t as input but return an int.  Sanity check
+        * our input so that it won't cause an overflow in the
+         * vsnprintf return value or the buffer malloc size.  */
+       if (size > INT_MAX - _PyOS_vsnprintf_EXTRA_SPACE) {
+               len = -666;
+               goto Done;
+       }
 
 #ifdef HAVE_SNPRINTF
        len = vsnprintf(str, size, format, va);
 #else
        /* Emulate it. */
-       buffer = PyMem_MALLOC(size + 512);
+       buffer = PyMem_MALLOC(size + _PyOS_vsnprintf_EXTRA_SPACE);
        if (buffer == NULL) {
                len = -666;
                goto Done;
@@ -75,7 +85,7 @@ PyOS_vsnprintf(char *str, size_t size, const char  *format, va_list va)
        if (len < 0)
                /* ignore the error */;
 
-       else if ((size_t)len >= size + 512)
+       else if ((size_t)len >= size + _PyOS_vsnprintf_EXTRA_SPACE)
                Py_FatalError("Buffer overflow in PyOS_snprintf/PyOS_vsnprintf");
 
        else {
@@ -86,8 +96,10 @@ PyOS_vsnprintf(char *str, size_t size, const char  *format, va_list va)
                str[to_copy] = '\0';
        }
        PyMem_FREE(buffer);
-Done:
 #endif
-       str[size-1] = '\0';
+Done:
+       if (size > 0)
+               str[size-1] = '\0';
        return len;
+#undef _PyOS_vsnprintf_EXTRA_SPACE
 }