On 20/11/2019 14:46, Martin Liška wrote: > On 11/20/19 3:37 PM, Matthew Malcomson wrote: >> Hi Martin, >> >> Thanks for the review, > > You're welcome. > >> I'll get working on your comments now, but since I really enjoyed >> finding this bug in ./configure when I hit it I thought I'd answer this >> right away. > > Heh :) > >> >> >> On 20/11/2019 14:02, Martin Liška wrote: >>> On 11/7/19 7:37 PM, Matthew Malcomson wrote: >>>> >>>> diff --git a/config/bootstrap-hwasan.mk b/config/bootstrap-hwasan.mk >>>> index >>>> 4f60bed3fd6e98b47a3a38aea6eba2a7c320da25..91989f4bb1db6ccff564383777757b896645e541 >>>> >>>> >>>> 100644 >>>> --- a/config/bootstrap-hwasan.mk >>>> +++ b/config/bootstrap-hwasan.mk >>>> @@ -1,7 +1,11 @@ >>>> # This option enables -fsanitize=hwaddress for stage2 and stage3. >>>> +# We need to disable random frame tags for bootstrap since the >>>> autoconf check >>>> +# for which direction the stack is growing has UB that a random frame >>>> tag >>>> +# breaks. Running with a random frame tag gives approx. 50% chance of >>>> +# bootstrap comparison diff in libiberty/alloca.c. >>> >>> Here I would like to see what's exactly the problem. I would expect ASAN >>> will >>> have exactly the same problem? Can you please isolate it and file a bug. >>> I bet >>> a configure script should not expose an undefined behavior. >>> >> >> The configure problem is this snippet below: >> >> >> find_stack_direction () >> { >> static char *addr = 0; >> auto char dummy; >> if (addr == 0) >> { >> addr = &dummy; >> return find_stack_direction (); >> } >> else >> return (&dummy > addr) ? 1 : -1; >> } >> main () >> { >> exit (find_stack_direction() < 0); >> } >> >> >> configure uses this to determine the direction that the stack grows. >> >> `find_stack_direction` compares the address of two different objects and >> uses that to make a decision. >> >> With HWASAN random frame tags the answer to the comparison is mostly >> determined by what random tag was assigned to the object in each frame, >> rather than the memory layout of the stack -- which means this configure >> test program can end up getting different answers on different runs. >> >> This is not a problem for ASAN since ASAN does not store tags in the >> pointers of variables. >> >> >> You're right -- I should file a bug on that for configure. >> >> For reference the UB clause in the standard is 6.5.8 #5 (relational >> operators) where there's a sentence at the end saying "In all other >> cases, the behaviour is undefined". Essentially, this program is >> comparing the address of two different objects on the stack, and that's >> not allowed. > > Well, to be honest, this is quite cute violation of the standard. I would > have written exactly the same code for the stack direction direction. I > understand > that a top byte will (a.k.a. tag) make the randomness. > > Do you have an idea how can we rewrite the check? > Thanks, > Martin >
I don't have much of a plan. The most promising lead I have is that libiberty/alloca.c has a similar functionality but with macros to account for a special case. Instead of just using '&' it uses a macro `ADDRESS_FUNCTION`. I can use that macro to ensure the libiberty/alloca.c function could handle tags, but I'm not sure that architecture specific conditions will neatly fit into autoconf.