diff options
author | Simon Howard | 2015-07-11 03:38:49 -0400 |
---|---|---|
committer | Mike Swanson | 2015-08-24 14:19:04 -0700 |
commit | 7d884d24adff82c020c2663c9142b38ee189ddef (patch) | |
tree | 7c6fac776353330aefa9d20d074293097e615bac | |
parent | 7c192af0d17f3f45d4208bc15cb1225b811aab74 (diff) | |
download | chocolate-doom-7d884d24adff82c020c2663c9142b38ee189ddef.tar.gz chocolate-doom-7d884d24adff82c020c2663c9142b38ee189ddef.tar.bz2 chocolate-doom-7d884d24adff82c020c2663c9142b38ee189ddef.zip |
doom: Avoid overflow for spawn angle calculation.
Integer overflow is undefined and this breaks when using Clang with
-O2 optimization turned on. This fixes #572 (thanks to David Majnemer
for insight into fixing this bug).
-rw-r--r-- | src/doom/g_game.c | 17 |
1 files changed, 8 insertions, 9 deletions
diff --git a/src/doom/g_game.c b/src/doom/g_game.c index bc582a52..3001e039 100644 --- a/src/doom/g_game.c +++ b/src/doom/g_game.c @@ -1168,26 +1168,26 @@ G_CheckSpot fixed_t xa, ya; signed int an; - an = (ANG45 * ((signed int) mthing->angle / 45)); - // Right-shifting a negative signed integer is implementation-defined, - // so divide instead. - an /= 1 << ANGLETOFINESHIFT; + // This calculation overflows in Vanilla Doom, but here we deliberately + // avoid integer overflow as it is undefined behavior, so the value of + // 'an' will always be positive. + an = (ANG45 >> ANGLETOFINESHIFT) * ((signed int) mthing->angle / 45); switch (an) { - case -4096: + case 4096: // -4096: xa = finetangent[2048]; // finecosine[-4096] ya = finetangent[0]; // finesine[-4096] break; - case -3072: + case 5120: // -3072: xa = finetangent[3072]; // finecosine[-3072] ya = finetangent[1024]; // finesine[-3072] break; - case -2048: + case 6144: // -2048: xa = finesine[0]; // finecosine[-2048] ya = finetangent[2048]; // finesine[-2048] break; - case -1024: + case 7168: // -1024: xa = finesine[1024]; // finecosine[-1024] ya = finetangent[3072]; // finesine[-1024] break; @@ -1195,7 +1195,6 @@ G_CheckSpot case 1024: case 2048: case 3072: - case 4096: xa = finecosine[an]; ya = finesine[an]; break; |