[Python-Dev] gcc 4.2 exposes signed integer overflows
Tim Peters
tim.peters at gmail.com
Mon Aug 28 04:32:52 CEST 2006
[Anthony Baxter]
> Regardless of whether we consider gcc's behaviour to be correct or not,
It is correct, but more to the point it's, umm, /there/ ;-)
> I do agree we need a fix for this in 2.5 final. That should also be backported to
> release24-maint for the 2.4.4 release, and maybe release23-maint, as Barry
> recently started talking about cutting a 2.3.6.
>
> Can I nominate Tim, with his terrifying knowledge of C compiler esoterica, as
> the person to pick the best fix?
It's a bitch. Changing to
if (y == -1 && x < 0 && (unsigned long)x == -(unsigned long)x)
is the obvious fix, but violates our "no warnings" policy: the MS
compiler warns about applying unary minus to an unsigned operand -- it
"looks insane" to /their/ compiler writers ;-). Elegant patch below
-- LOL.
Would be nice if someone verified it worked on a box where it matters.
Would also be nice if people checked to see whether their compiler(s)
warn about something else now.
IIndex: Objects/intobject.c
===================================================================
--- Objects/intobject.c (revision 51618)
+++ Objects/intobject.c (working copy)
@@ -564,8 +564,14 @@
"integer division or modulo by zero");
return DIVMOD_ERROR;
}
- /* (-sys.maxint-1)/-1 is the only overflow case. */
- if (y == -1 && x < 0 && x == -x)
+ /* (-sys.maxint-1)/-1 is the only overflow case. x is the most
+ * negative long iff x < 0 and, on a 2's-complement box, x == -x.
+ * However, -x is undefined (by C) if x /is/ the most negative long
+ * (it's a signed overflow case), and some compilers care. So we cast
+ * x to unsigned long first. However, then other compilers warn about
+ * applying unary minus to an unsigned operand. Hence the weird "0-".
+ */
+ if (y == -1 && x < 0 && (unsigned long)x == 0-(unsigned long)x)
return DIVMOD_OVERFLOW;
xdivy = x / y;
xmody = x - xdivy * y;
More information about the Python-Dev
mailing list