This only happens for me with a valgrind from SVN. valgrind 3.10.1 seems fine. Compile the following program with gcc 4.9.1 and the undefined sanitizer: gcc -g -O0 -fsanitize=undefined -o t t.c #include <stdlib.h> int main (int argc, char **argv) { long l1 = atol (argv[1]); long l2 = atol (argv[2]); long l3 = l1 - l2; return l3 > 0; } Run standalone: ./t 444 433 Run under valgrind: $ ./vg-in-place -q /tmp/t 444 433 t.c:8:8: runtime error: signed integer overflow: 444 - 433 cannot be represented in type 'long int' Disassembly of main: 0x00000000004007d0 <+122>: mov %rax,-0x20(%rbp) 0x00000000004007d4 <+126>: mov -0x18(%rbp),%rax 0x00000000004007d8 <+130>: sub -0x20(%rbp),%rax 0x00000000004007dc <+134>: mov %rax,%rbx 0x00000000004007df <+137>: jno 0x4007f6 <main+160> Where main+160 jumps over the call to __ubsan_handle_sub_overflow Generated VEX: ==== SB 1768 (evchecks 85512) [tid 1] 0x4007d0 main+122 /tmp/t+0x4007d0 ------------------------ Front end ------------------------ 0x4007D0: movq %rax,-32(%rbp) ------ IMark(0x4007D0, 4, 0) ------ t0 = Add64(GET:I64(56),0xFFFFFFFFFFFFFFE0:I64) STle(t0) = GET:I64(16) PUT(184) = 0x4007D4:I64 0x4007D4: movq -24(%rbp),%rax ------ IMark(0x4007D4, 4, 0) ------ t1 = Add64(GET:I64(56),0xFFFFFFFFFFFFFFE8:I64) PUT(16) = LDle:I64(t1) PUT(184) = 0x4007D8:I64 0x4007D8: subq -32(%rbp),%rax ------ IMark(0x4007D8, 4, 0) ------ t5 = Add64(GET:I64(56),0xFFFFFFFFFFFFFFE0:I64) t4 = GET:I64(16) t3 = LDle:I64(t5) t2 = Sub64(t4,t3) PUT(144) = 0x8:I64 PUT(152) = t4 PUT(160) = t3 PUT(16) = t2 PUT(184) = 0x4007DC:I64 0x4007DC: movq %rax,%rbx ------ IMark(0x4007DC, 3, 0) ------ PUT(40) = GET:I64(16) PUT(184) = 0x4007DF:I64 0x4007DF: jno-8 0x4007F6 ------ IMark(0x4007DF, 2, 0) ------ if (64to1(amd64g_calculate_condition[mcx=0x13]{0x3815f0a0}(0x0:I64,GET:I64(144),GET:I64(152),GET:I64(160),GET:I64(168)):I64)) { PUT(184) = 0x4007E1:I64; exit-Boring } PUT(184) = 0x4007F6:I64 PUT(184) = GET:I64(184); exit-Boring GuestBytes 4007D0 17 48 89 45 E0 48 8B 45 E8 48 2B 45 E0 48 89 C3 71 15 00018FF3 VexExpansionRatio 17 401 235 :10
Looks like VEX svn r2965 caused this regression.
Bug found by sewardj: diff --git a/priv/guest_amd64_helpers.c b/priv/guest_amd64_helpers.c index 2887b08..8111583 100644 --- a/priv/guest_amd64_helpers.c +++ b/priv/guest_amd64_helpers.c @@ -1036,7 +1036,7 @@ IRExpr* guest_amd64_spechelper ( const HChar* function_name, binop(Iop_Xor64, cc_dep1, binop(Iop_Sub64, cc_dep1, cc_dep2))), - mkU8(64)); + mkU8(63)); } if (isU64(cc_op, AMD64G_CC_OP_SUBQ) && isU64(cond, AMD64CondNO)) { /* No action. Never yet found a test case. */ With that the above testcase and my original one work again when building with gcc -fsanitize-undefined and running under valgrind.
Thanks for chasing that down. Patch lgtm; +1 to land.
VEX svn r3147