bug-gnulib
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: bug#36370: 27.0.50; XFIXNAT called on negative numbers


From: Bruno Haible
Subject: Re: bug#36370: 27.0.50; XFIXNAT called on negative numbers
Date: Fri, 28 Jun 2019 21:11:11 +0200
User-agent: KMail/5.1.3 (Linux/4.4.0-151-generic; KDE/5.18.0; x86_64; ; )

Pip Cet wrote:
> Sorry, can't reproduce that here. I'm sure the changes I need to make
> are obvious once I've found them, but can you let me know your gcc
> version?

I reproduce this with GCC versions 5.4.0, 6.5.0, 7.4.0, 8.3.0, and 9.1.0.
1. Take the files foo.c and bar.c from
   <https://lists.gnu.org/archive/html/bug-gnulib/2019-06/msg00096.html>
2. Compile and disassemble:
    gcc -O2 -m32 -flto foo.c bar.c -shared -o libfoo.so && objdump 
--disassemble 
libfoo.so
   Observe that f_assume pushes an immediate $0 argument on the stack for the
   function call.
3. Enable the second 'assume' definition instead of the first one.
4. Compile and disassemble:
    gcc -O2 -m32 -flto foo.c bar.c -shared -o libfoo.so && objdump 
--disassemble 
libfoo.so
   Observe that f_assume is now an alias of f_generic, that pushes a
   computed value as argument on the stack for the function call (push %eax).

> Sorry to be pedantic, but do you disagree that it is better in these
> cases, or in general?

I disagree that it is better in general.

You're apparently setting out a high goal for the 'assume' macro:
(1) that the programmer may call it with an expression that involves
    function calls,
(2) that the generated code will never include these function calls,
    because the generated code with the 'assume' invocation should be
    optimized at least as well as the generated code without the
    'assume' invocation.

I'm adding certain quality criteria:
  - It is not "good" if a construct behaves unpredictably, that is,
    if it hard to document precisely how it will behave. (*)
  - It is not "good" if the behaviour with no LTO is different from
    the behaviour with LTO.

The implementation with the __builtin_constant, while attaining the
goals (1) and (2), does not satisfy the two quality criteria.

I believe the only way to attain the goals and the quality criteria
is, as you suggested, to ask the GCC people to add a __builtin_assume
built-in.

> >   1. The new 'assume' is worse when -flto is in use.
> 
> Maybe. Even if it is, though, that's a GCC limitation which I consider
> likely to be fixable

Yes, *maybe* the GCC people can change the semantics of __builtin_constant_p
so that it is effectively computed at link-time, rather than when a single
compilation unit gets compiled. Or maybe not. I don't know...

> It's way too easy to do something like
> 
> eassume(ptr->field >= 0 && f(ptr));
> 
> when what you mean is
> 
> eassume(ptr->field >= 0);
> eassume(f(ptr));

I argue that it's unnatural if the two don't behave exactly the same.
Like everyone expects that
  x = foo ? yes : no;
is equivalent to
  if (foo) x = yes; else x = no;
And everyone expects that
  if (A && B) { ... }
is equivalent to
  if (A) if (B) { ... }

Bruno

(*) My favourite example of this principle is tail-recursion elimination.




reply via email to

[Prev in Thread] Current Thread [Next in Thread]