This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
Re: __builtin_expect (setjmp (buf) == 0, 1)) generates broken code
On Wed, Mar 19, 2003 at 12:40:59PM -0800, Zack Weinberg wrote:
> Geoff Keating <geoffk at geoffk dot org> writes:
>
> >> The question is, what's broken here. Is this combination of setjmp
> >> with __builtin_expect valid in the first place? If so, how could
> >> this be fixed?
> >
> > Yes, it's invalid. The C standard is pretty clear on the places that
> > you can put setjmp, and this isn't one of them (see C99 7.13.1.1
> > paragraph 4), for exactly this sort of reason.
>
> I don't agree -- __builtin_expect is a special case, it should have no
> effect on code generation other than to tag the surrounding if
> construct with a probability estimate. Wherever we fail to achieve
> that, it's a bug.
I agree with Zack here. __builtin_expect is not part of the C99 standard
and thus it is up to us how we define it. And IMHO it should just set
branch probablity, nothing else.
FYI, while:
if (__builtin_expect (setjmp (b) == 0, 1))
bar ();
doesn't work,
if (__builtin_expect (setjmp (b), 0) == 0)
bar ();
seems to work just fine, which leads to another thing:
int baz (void);
void bar (void);
void foo (void)
{
if (__builtin_expect (baz (), 0) == 0)
bar ();
}
vs.
int baz (void);
void bar (void);
void foo (void)
{
if (__builtin_expect (baz () == 0, 1))
bar ();
}
(this time no messing with functions returning twice etc.), generates
the exact same assembly when optimizing on IA-32, x86-64, IA-64, sparc -m32,
but generates worse code for the second variant on s390, s390x, sparc -m64.
When __builtin_expect makes the code worse rather then better is somewhat
disturbing (but the first form really cannot be used everywhere, it requires
that first builtin expect argument is integral type and the expected
return value is constant).
Jakub