Skip to content

Commit

Permalink
Merge pull request #6511 from MaskRay/master
Browse files Browse the repository at this point in the history
fix SIGFPE caused by integer division overflow `sinteger_t.min / (-1)` in constant folding
  • Loading branch information
MartinNowak committed Feb 11, 2017
2 parents 307a7b9 + a4cedfa commit 4f1425c
Show file tree
Hide file tree
Showing 2 changed files with 37 additions and 2 deletions.
18 changes: 16 additions & 2 deletions src/constfold.d
Original file line number Diff line number Diff line change
Expand Up @@ -433,6 +433,20 @@ extern (C++) UnionExp Div(Loc loc, Type type, Expression e1, Expression e2)
e2.error("divide by 0");
n2 = 1;
}
if (n2 == -1 && !type.isunsigned())
{
// Check for int.min / -1
if (n1 == 0xFFFFFFFF80000000UL && type.toBasetype().ty != Tint64)
{
e2.error("integer overflow: int.min / -1");
n2 = 1;
}
else if (n1 == 0x8000000000000000L) // long.min / -1
{
e2.error("integer overflow: long.min / -1");
n2 = 1;
}
}
if (e1.type.isunsigned() || e2.type.isunsigned())
n = (cast(dinteger_t)n1) / (cast(dinteger_t)n2);
else
Expand Down Expand Up @@ -486,12 +500,12 @@ extern (C++) UnionExp Mod(Loc loc, Type type, Expression e1, Expression e2)
// Check for int.min % -1
if (n1 == 0xFFFFFFFF80000000UL && type.toBasetype().ty != Tint64)
{
e2.error("integer overflow: int.min % -1");
e2.error("integer overflow: int.min %% -1");
n2 = 1;
}
else if (n1 == 0x8000000000000000L) // long.min % -1
{
e2.error("integer overflow: long.min % -1");
e2.error("integer overflow: long.min %% -1");
n2 = 1;
}
}
Expand Down
21 changes: 21 additions & 0 deletions test/fail_compilation/test4682.d
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
/*
TEST_OUTPUT:
----
fail_compilation/test4682.d(18): Error: integer overflow: int.min / -1
fail_compilation/test4682.d(18): Error: integer overflow: int.min / -1
fail_compilation/test4682.d(18): Error: integer overflow: int.min / -1
fail_compilation/test4682.d(19): Error: integer overflow: long.min / -1
fail_compilation/test4682.d(19): Error: integer overflow: long.min / -1
fail_compilation/test4682.d(19): Error: integer overflow: long.min / -1
fail_compilation/test4682.d(20): Error: integer overflow: int.min % -1
fail_compilation/test4682.d(20): Error: integer overflow: int.min % -1
fail_compilation/test4682.d(20): Error: integer overflow: int.min % -1
fail_compilation/test4682.d(21): Error: integer overflow: long.min % -1
fail_compilation/test4682.d(21): Error: integer overflow: long.min % -1
fail_compilation/test4682.d(21): Error: integer overflow: long.min % -1
----
*/
auto a = int.min / -1;
auto b = long.min / -1;
auto c = int.min % -1;
auto d = long.min % -1;

0 comments on commit 4f1425c

Please sign in to comment.