mirror of
https://github.com/python/cpython.git
synced 2025-07-29 06:05:00 +00:00
Part of bug #1523610: fix miscalculation of buffer length.
Also add a guard against NULL in converttuple and add a test case (that previously would have crashed).
This commit is contained in:
parent
0619a329e8
commit
5f135787ec
3 changed files with 39 additions and 3 deletions
|
@ -233,8 +233,25 @@ class LongLong_TestCase(unittest.TestCase):
|
||||||
|
|
||||||
self.failUnlessEqual(VERY_LARGE & ULLONG_MAX, getargs_K(VERY_LARGE))
|
self.failUnlessEqual(VERY_LARGE & ULLONG_MAX, getargs_K(VERY_LARGE))
|
||||||
|
|
||||||
|
|
||||||
|
class Tuple_TestCase(unittest.TestCase):
|
||||||
|
def test_tuple(self):
|
||||||
|
from _testcapi import getargs_tuple
|
||||||
|
|
||||||
|
ret = getargs_tuple(1, (2, 3))
|
||||||
|
self.assertEquals(ret, (1,2,3))
|
||||||
|
|
||||||
|
# make sure invalid tuple arguments are handled correctly
|
||||||
|
class seq:
|
||||||
|
def __len__(self):
|
||||||
|
return 2
|
||||||
|
def __getitem__(self, n):
|
||||||
|
raise ValueError
|
||||||
|
self.assertRaises(TypeError, getargs_tuple, 1, seq())
|
||||||
|
|
||||||
|
|
||||||
def test_main():
|
def test_main():
|
||||||
tests = [Signed_TestCase, Unsigned_TestCase]
|
tests = [Signed_TestCase, Unsigned_TestCase, Tuple_TestCase]
|
||||||
try:
|
try:
|
||||||
from _testcapi import getargs_L, getargs_K
|
from _testcapi import getargs_L, getargs_K
|
||||||
except ImportError:
|
except ImportError:
|
||||||
|
|
|
@ -294,6 +294,16 @@ test_L_code(PyObject *self)
|
||||||
|
|
||||||
#endif /* ifdef HAVE_LONG_LONG */
|
#endif /* ifdef HAVE_LONG_LONG */
|
||||||
|
|
||||||
|
/* Test tuple argument processing */
|
||||||
|
static PyObject *
|
||||||
|
getargs_tuple(PyObject *self, PyObject *args)
|
||||||
|
{
|
||||||
|
int a, b, c;
|
||||||
|
if (!PyArg_ParseTuple(args, "i(ii)", &a, &b, &c))
|
||||||
|
return NULL;
|
||||||
|
return Py_BuildValue("iii", a, b, c);
|
||||||
|
}
|
||||||
|
|
||||||
/* Functions to call PyArg_ParseTuple with integer format codes,
|
/* Functions to call PyArg_ParseTuple with integer format codes,
|
||||||
and return the result.
|
and return the result.
|
||||||
*/
|
*/
|
||||||
|
@ -707,6 +717,7 @@ static PyMethodDef TestMethods[] = {
|
||||||
{"test_null_strings", (PyCFunction)test_null_strings, METH_NOARGS},
|
{"test_null_strings", (PyCFunction)test_null_strings, METH_NOARGS},
|
||||||
{"test_string_from_format", (PyCFunction)test_string_from_format, METH_NOARGS},
|
{"test_string_from_format", (PyCFunction)test_string_from_format, METH_NOARGS},
|
||||||
|
|
||||||
|
{"getargs_tuple", getargs_tuple, METH_VARARGS},
|
||||||
{"getargs_b", getargs_b, METH_VARARGS},
|
{"getargs_b", getargs_b, METH_VARARGS},
|
||||||
{"getargs_B", getargs_B, METH_VARARGS},
|
{"getargs_B", getargs_B, METH_VARARGS},
|
||||||
{"getargs_H", getargs_H, METH_VARARGS},
|
{"getargs_H", getargs_H, METH_VARARGS},
|
||||||
|
|
|
@ -351,8 +351,8 @@ seterror(int iarg, const char *msg, int *levels, const char *fname,
|
||||||
"argument %d", iarg);
|
"argument %d", iarg);
|
||||||
i = 0;
|
i = 0;
|
||||||
p += strlen(p);
|
p += strlen(p);
|
||||||
while (levels[i] > 0 && (int)(p-buf) < 220) {
|
while (levels[i] > 0 && i < 32 && (int)(p-buf) < 220) {
|
||||||
PyOS_snprintf(p, sizeof(buf) - (buf - p),
|
PyOS_snprintf(p, sizeof(buf) - (p - buf),
|
||||||
", item %d", levels[i]-1);
|
", item %d", levels[i]-1);
|
||||||
p += strlen(p);
|
p += strlen(p);
|
||||||
i++;
|
i++;
|
||||||
|
@ -439,6 +439,13 @@ converttuple(PyObject *arg, const char **p_format, va_list *p_va, int flags,
|
||||||
char *msg;
|
char *msg;
|
||||||
PyObject *item;
|
PyObject *item;
|
||||||
item = PySequence_GetItem(arg, i);
|
item = PySequence_GetItem(arg, i);
|
||||||
|
if (item == NULL) {
|
||||||
|
PyErr_Clear();
|
||||||
|
levels[0] = i+1;
|
||||||
|
levels[1] = 0;
|
||||||
|
strncpy(msgbuf, "is not retrievable", bufsize);
|
||||||
|
return msgbuf;
|
||||||
|
}
|
||||||
msg = convertitem(item, &format, p_va, flags, levels+1,
|
msg = convertitem(item, &format, p_va, flags, levels+1,
|
||||||
msgbuf, bufsize, freelist);
|
msgbuf, bufsize, freelist);
|
||||||
/* PySequence_GetItem calls tp->sq_item, which INCREFs */
|
/* PySequence_GetItem calls tp->sq_item, which INCREFs */
|
||||||
|
@ -1509,6 +1516,7 @@ vgetargskeywords(PyObject *args, PyObject *keywords, const char *format,
|
||||||
else {
|
else {
|
||||||
msg = skipitem(&format, p_va, flags);
|
msg = skipitem(&format, p_va, flags);
|
||||||
if (msg) {
|
if (msg) {
|
||||||
|
levels[0] = 0;
|
||||||
seterror(i+1, msg, levels, fname, message);
|
seterror(i+1, msg, levels, fname, message);
|
||||||
return cleanreturn(0, freelist);
|
return cleanreturn(0, freelist);
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue