diff options
author | Martin v. Löwis <martin@v.loewis.de> | 2007-12-04 22:10:37 (GMT) |
---|---|---|
committer | Martin v. Löwis <martin@v.loewis.de> | 2007-12-04 22:10:37 (GMT) |
commit | d1a1d1ed802187cd1a9a8a95ac5d758c7acffee6 (patch) | |
tree | 17489e6ea4df32ba3b3bbda6e4b31155a460f265 /Objects | |
parent | 0fbab7ff8d2efd92e222fcc13c0aff0998c3c158 (diff) | |
download | cpython-d1a1d1ed802187cd1a9a8a95ac5d758c7acffee6.zip cpython-d1a1d1ed802187cd1a9a8a95ac5d758c7acffee6.tar.gz cpython-d1a1d1ed802187cd1a9a8a95ac5d758c7acffee6.tar.bz2 |
Remove PyInt_CheckExact. Add PyLong_AsLongAndOverflow.
Diffstat (limited to 'Objects')
-rw-r--r-- | Objects/exceptions.c | 10 | ||||
-rw-r--r-- | Objects/frameobject.c | 18 | ||||
-rw-r--r-- | Objects/listobject.c | 6 | ||||
-rw-r--r-- | Objects/longobject.c | 24 |
4 files changed, 47 insertions, 11 deletions
diff --git a/Objects/exceptions.c b/Objects/exceptions.c index cbcda7b..9655733 100644 --- a/Objects/exceptions.c +++ b/Objects/exceptions.c @@ -929,6 +929,10 @@ SyntaxError_str(PySyntaxErrorObject *self) { int have_lineno = 0; char *filename = 0; + /* Below, we always ignore overflow errors, just printing -1. + Still, we cannot allow an OverflowError to be raised, so + we need to call PyLong_AsLongAndOverflow. */ + int overflow; /* XXX -- do all the additional formatting with filename and lineno here */ @@ -936,7 +940,7 @@ SyntaxError_str(PySyntaxErrorObject *self) if (self->filename && PyUnicode_Check(self->filename)) { filename = PyUnicode_AsString(self->filename); } - have_lineno = (self->lineno != NULL) && PyInt_CheckExact(self->lineno); + have_lineno = (self->lineno != NULL) && PyLong_CheckExact(self->lineno); if (!filename && !have_lineno) return PyObject_Str(self->msg ? self->msg : Py_None); @@ -945,7 +949,7 @@ SyntaxError_str(PySyntaxErrorObject *self) return PyUnicode_FromFormat("%S (%s, line %ld)", self->msg ? self->msg : Py_None, my_basename(filename), - PyLong_AsLong(self->lineno)); + PyLong_AsLongAndOverflow(self->lineno, &overflow)); else if (filename) return PyUnicode_FromFormat("%S (%s)", self->msg ? self->msg : Py_None, @@ -953,7 +957,7 @@ SyntaxError_str(PySyntaxErrorObject *self) else /* only have_lineno */ return PyUnicode_FromFormat("%S (line %ld)", self->msg ? self->msg : Py_None, - PyLong_AsLong(self->lineno)); + PyLong_AsLongAndOverflow(self->lineno, &overflow)); } static PyMemberDef SyntaxError_members[] = { diff --git a/Objects/frameobject.c b/Objects/frameobject.c index 0e6d9f8..266cbd2 100644 --- a/Objects/frameobject.c +++ b/Objects/frameobject.c @@ -66,6 +66,8 @@ static int frame_setlineno(PyFrameObject *f, PyObject* p_new_lineno) { int new_lineno = 0; /* The new value of f_lineno */ + long l_new_lineno; + int overflow; int new_lasti = 0; /* The new value of f_lasti */ int new_iblock = 0; /* The new value of f_iblock */ unsigned char *code = NULL; /* The bytecode for the frame... */ @@ -88,7 +90,7 @@ frame_setlineno(PyFrameObject *f, PyObject* p_new_lineno) unsigned char setup_op = 0; /* (ditto) */ /* f_lineno must be an integer. */ - if (!PyInt_CheckExact(p_new_lineno)) { + if (!PyLong_CheckExact(p_new_lineno)) { PyErr_SetString(PyExc_ValueError, "lineno must be an integer"); return -1; @@ -104,7 +106,19 @@ frame_setlineno(PyFrameObject *f, PyObject* p_new_lineno) } /* Fail if the line comes before the start of the code block. */ - new_lineno = (int) PyLong_AsLong(p_new_lineno); + l_new_lineno = PyLong_AsLongAndOverflow(p_new_lineno, &overflow); + if (overflow +#if SIZEOF_LONG > SIZEOF_INT + || l_new_lineno > INT_MAX + || l_new_lineno < INT_MIN +#endif + ) { + PyErr_SetString(PyExc_ValueError, + "lineno out of range"); + return -1; + } + new_lineno = (int)l_new_lineno; + if (new_lineno < f->f_code->co_firstlineno) { PyErr_Format(PyExc_ValueError, "line %d comes before the current code block", diff --git a/Objects/listobject.c b/Objects/listobject.c index 59674bf..18d3b90 100644 --- a/Objects/listobject.c +++ b/Objects/listobject.c @@ -925,7 +925,7 @@ islt(PyObject *x, PyObject *y, PyObject *compare) Py_DECREF(args); if (res == NULL) return -1; - if (!PyInt_CheckExact(res)) { + if (!PyLong_CheckExact(res)) { PyErr_Format(PyExc_TypeError, "comparison function must return int, not %.200s", res->ob_type->tp_name); @@ -934,6 +934,10 @@ islt(PyObject *x, PyObject *y, PyObject *compare) } i = PyLong_AsLong(res); Py_DECREF(res); + if (i == -1 && PyErr_Occurred()) { + /* Overflow in long conversion. */ + return -1; + } return i < 0; } diff --git a/Objects/longobject.c b/Objects/longobject.c index 1e20485..cf7cb47 100644 --- a/Objects/longobject.c +++ b/Objects/longobject.c @@ -299,7 +299,7 @@ PyLong_FromDouble(double dval) Returns -1 and sets an error condition if overflow occurs. */ long -PyLong_AsLong(PyObject *vv) +PyLong_AsLongAndOverflow(PyObject *vv, int *overflow) { /* This version by Tim Peters */ register PyLongObject *v; @@ -309,6 +309,7 @@ PyLong_AsLong(PyObject *vv) int sign; int do_decref = 0; /* if nb_int was called */ + *overflow = 0; if (vv == NULL) { PyErr_BadInternalCall(); return -1; @@ -358,8 +359,7 @@ PyLong_AsLong(PyObject *vv) prev = x; x = (x << PyLong_SHIFT) + v->ob_digit[i]; if ((x >> PyLong_SHIFT) != prev) { - PyErr_SetString(PyExc_OverflowError, - "Python int too large to convert to C long"); + *overflow = Py_Size(v) > 0 ? 1 : -1; goto exit; } } @@ -373,8 +373,8 @@ PyLong_AsLong(PyObject *vv) res = LONG_MIN; } else { - PyErr_SetString(PyExc_OverflowError, - "Python int too large to convert to C long"); + *overflow = Py_Size(v) > 0 ? 1 : -1; + /* res is already set to -1 */ } } exit: @@ -384,6 +384,20 @@ PyLong_AsLong(PyObject *vv) return res; } +long +PyLong_AsLong(PyObject *obj) +{ + int overflow; + long result = PyLong_AsLongAndOverflow(obj, &overflow); + if (overflow) { + /* XXX: could be cute and give a different + message for overflow == -1 */ + PyErr_SetString(PyExc_OverflowError, + "Python int too large to convert to C long"); + } + return result; +} + int _PyLong_FitsInLong(PyObject *vv) { |