Building on gcc112 is stuck in msgfmt

2017-08-28 Thread Martin Liška
Hello.

I've just repeatedly seen stuck in build process:

make[5]: Entering directory 
`/home/marxin/Programming/gcc/objdir/powerpc64le-unknown-linux-gnu/libstdc++-v3/po'
msgfmt -o de.mo ../../../../libstdc++-v3/po/de.po

49__asm volatile ("sc; mfcr %0"
Missing separate debuginfos, use: debuginfo-install 
gettext-0.18.2.1-4.el7.ppc64le
(gdb) bt
#0  0x3fff85d8bac8 in sys_futex0 (val=-1, op=128, addr=0x3fff85db0520 
) at ../../../libgomp/config/linux/powerpc/futex.h:49
#1  futex_wait (val=-1, addr=0x3fff85db0520 ) at 
../../../libgomp/config/linux/powerpc/futex.h:62
#2  do_wait (val=-1, addr=) at 
../../../libgomp/config/linux/wait.h:67
#3  gomp_mutex_lock_slow (mutex=0x3fff85db0520 , 
oldval=) at ../../../libgomp/config/linux/mutex.c:63
#4  0x3fff85d98b04 in gomp_mutex_lock (mutex=0x3fff85db0520 
) at ../../../libgomp/config/linux/mutex.h:57
#5  goacc_register (disp=0x3fff85db0090 ) at 
../../../libgomp/oacc-init.c:74
#6  0x3fff85d983fc in goacc_host_init () at ../../../libgomp/oacc-host.c:265
#7  0x3fff85d99c88 in goacc_runtime_initialize () at 
../../../libgomp/oacc-init.c:657
#8  0x3fff85d7882c in initialize_env () at ../../../libgomp/env.c:1340
#9  0x3fff86525c74 in _dl_init_internal () from /lib64/ld64.so.2
#10 0x3fff865119cc in _dl_start_user () from /lib64/ld64.so.2

$ msgfmt --version
msgfmt (GNU gettext-tools) 0.18.2

Is it a known issue, has anybody spotted that as well?

Thanks,
Martin


GNU MPFR 3.1.6 Release Candidate

2017-08-28 Thread Vincent Lefevre
The release of GNU MPFR 3.1.6 ("canard à l'orange", patch level 6)
is imminent. Please help to make this release as good as possible
by downloading and testing this release candidate:

http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.tar.xz
http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.tar.bz2
http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.tar.gz
http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.zip

The SHA1 digests:
f21b4fd387ff8100a22d7b405761e327dcdee20d  mpfr-3.1.6-rc1.tar.bz2
aaa97d68cb740f1126c87f0fe4c4f9aff70e5447  mpfr-3.1.6-rc1.tar.gz
3a822d45edf871198a9cb5832b7f60e4c2aba9d0  mpfr-3.1.6-rc1.tar.xz
b49a991e85a09f97cf65a4375540f87a2b03e533  mpfr-3.1.6-rc1.zip

The SHA256 digests:
58da15a1604a1c3595109af79def6050256fe4b7406fe36e01573767298134c9  
mpfr-3.1.6-rc1.tar.bz2
5be1b8279b4514071c139a35f85369c6168a3da6f17bda98072ba9499b7c4d04  
mpfr-3.1.6-rc1.tar.gz
df943ffd58a46280599d83ce7583d83829d23e9c38b5d37244eec310d6c9bcf6  
mpfr-3.1.6-rc1.tar.xz
52dbe13dcba01989ae28eb4b5b26c3a25a220e3ebfc84d756968b68c4422d8ab  
mpfr-3.1.6-rc1.zip

The signatures:
http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.tar.xz.asc
http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.tar.bz2.asc
http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.tar.gz.asc
http://www.mpfr.org/mpfr-3.1.6/mpfr-3.1.6-rc1.zip.asc

Each tarball is signed by Vincent Lefèvre. This can be verified using
the DSA key ID 980C197698C3739D; this key can be retrieved with:

  gpg --recv-keys 980C197698C3739D

or by downloading it from .
The key fingerprint is:

  07F3 DBBE CC1A 3960 5078  094D 980C 1976 98C3 739D

The signatures can be verified with: gpg --verify 
You should check that the key fingerprint matches.

Changes from version 3.1.5 to version 3.1.6:
- Improved MPFR manual.
- Bug fixes (see  and ChangeLog file).
- Autotools: Under Linux, make sure that the old dtags (when supported)
  are used if LD_LIBRARY_PATH is defined; otherwise "make check" would
  check an installed, compatible MPFR library found in LD_LIBRARY_PATH
  instead of the one that has been built with "make".

Please send success and failure reports with "./config.guess" output
to .

If no problems are found, GNU MPFR 3.1.6 should be released
around 2017-09-07.

Regards,

-- 
Vincent Lefèvre  - Web: 
100% accessible validated (X)HTML - Blog: 
Work: CR INRIA - computer arithmetic / AriC project (LIP, ENS-Lyon)


Re: Building on gcc112 is stuck in msgfmt

2017-08-28 Thread Jeff Law
On 08/28/2017 01:16 AM, Martin Liška wrote:
> Hello.
> 
> I've just repeatedly seen stuck in build process:
> 
> make[5]: Entering directory 
> `/home/marxin/Programming/gcc/objdir/powerpc64le-unknown-linux-gnu/libstdc++-v3/po'
> msgfmt -o de.mo ../../../../libstdc++-v3/po/de.po
> 
> 49__asm volatile ("sc; mfcr %0"
> Missing separate debuginfos, use: debuginfo-install 
> gettext-0.18.2.1-4.el7.ppc64le
> (gdb) bt
> #0  0x3fff85d8bac8 in sys_futex0 (val=-1, op=128, addr=0x3fff85db0520 
> ) at ../../../libgomp/config/linux/powerpc/futex.h:49
> #1  futex_wait (val=-1, addr=0x3fff85db0520 ) at 
> ../../../libgomp/config/linux/powerpc/futex.h:62
> #2  do_wait (val=-1, addr=) at 
> ../../../libgomp/config/linux/wait.h:67
> #3  gomp_mutex_lock_slow (mutex=0x3fff85db0520 , 
> oldval=) at ../../../libgomp/config/linux/mutex.c:63
> #4  0x3fff85d98b04 in gomp_mutex_lock (mutex=0x3fff85db0520 
> ) at ../../../libgomp/config/linux/mutex.h:57
> #5  goacc_register (disp=0x3fff85db0090 ) at 
> ../../../libgomp/oacc-init.c:74
> #6  0x3fff85d983fc in goacc_host_init () at 
> ../../../libgomp/oacc-host.c:265
> #7  0x3fff85d99c88 in goacc_runtime_initialize () at 
> ../../../libgomp/oacc-init.c:657
> #8  0x3fff85d7882c in initialize_env () at ../../../libgomp/env.c:1340
> #9  0x3fff86525c74 in _dl_init_internal () from /lib64/ld64.so.2
> #10 0x3fff865119cc in _dl_start_user () from /lib64/ld64.so.2
> 
> $ msgfmt --version
> msgfmt (GNU gettext-tools) 0.18.2
> 
> Is it a known issue, has anybody spotted that as well?
Yea, my ppc64le builds from late last week are stumbling on this as
well.  Could well be an environment thing -- if I go into
/libstdc++-v3/po and "make", it works just fine.

jeff


Re: gcc torture test pr52286.c

2017-08-28 Thread Jeff Law
On 08/27/2017 09:33 PM, Paul S wrote:
> I've ported gcc to a 16 bit CPU and have all torture tests passing bar
> one, pr52286.c
> 
> The offending lines of code are
> 
>   long a, b = 0;
>   asm ("" : "=r" (a) : "0" (0));
I wouldn't use a matching constraint here.  Something like this is
probably closer to what you want:

asm ("" : "=r" (a) : "n" (0));

The "n" says accept any immediate integer constant with a compile time
known value.


In fact, I could probably argue that "0" (0) should generate an error as
a constraint -- it's meaningless in that you can't match a constant
integer input to any output.

Jeff


Re: gcc torture test pr52286.c

2017-08-28 Thread Michael Matz
Hi,

On Mon, 28 Aug 2017, Jeff Law wrote:

> >   long a, b = 0;
> >   asm ("" : "=r" (a) : "0" (0));
> I wouldn't use a matching constraint here.  Something like this is
> probably closer to what you want:
> 
> asm ("" : "=r" (a) : "n" (0));
> 
> The "n" says accept any immediate integer constant with a compile time
> known value.
> 
> In fact, I could probably argue that "0" (0) should generate an error as
> a constraint -- it's meaningless in that you can't match a constant
> integer input to any output.

Huh?  No.  The semantics are perfectly valid for this.  It says "put the 
output into a register, place that into variable 'a', put the input value 
into the same register".  Value is just that, an arbitrary rvalue (of 
correct type of course).  We accept any expression forms, as we should, 
including constants.

FWIW, the above is a "portable" way to get the value 0 into 'a' without 
the compiler knowing.


Ciao,
Michael.


Re: gcc torture test pr52286.c

2017-08-28 Thread Jeff Law
On 08/28/2017 11:33 AM, Michael Matz wrote:
> Hi,
> 
> On Mon, 28 Aug 2017, Jeff Law wrote:
> 
>>>   long a, b = 0;
>>>   asm ("" : "=r" (a) : "0" (0));
>> I wouldn't use a matching constraint here.  Something like this is
>> probably closer to what you want:
>>
>> asm ("" : "=r" (a) : "n" (0));
>>
>> The "n" says accept any immediate integer constant with a compile time
>> known value.
>>
>> In fact, I could probably argue that "0" (0) should generate an error as
>> a constraint -- it's meaningless in that you can't match a constant
>> integer input to any output.
> 
> Huh?  No.  The semantics are perfectly valid for this.  It says "put the 
> output into a register, place that into variable 'a', put the input value 
> into the same register".  Value is just that, an arbitrary rvalue (of 
> correct type of course).  We accept any expression forms, as we should, 
> including constants.
I can't remember matching constraints ever working that way.

REgister allocation and reloading will first try to allocate the two
objects to the same register and if that doesn't work it will emit
copies to ensure they are the same register.

But that doesn't work when one of the objects isn't a register.  There's
no allocno for the constant.  It's just that, a constant.




> 
> FWIW, the above is a "portable" way to get the value 0 into 'a' without 
> the compiler knowing.
?!?  Mine is just as portable and should actually work :-)



jeff


Re: gcc torture test pr52286.c

2017-08-28 Thread Michael Matz
Hi,

On Mon, 28 Aug 2017, Jeff Law wrote:

> I can't remember matching constraints ever working that way.

They do work exactly so.  These uses are all correct, though they place 
some random value into x:

  int x, y, z;
  y = z = init();
  asm ("" : "=r" (x) : "r" (y+z));
  asm ("" : "=r" (x) : "r" (z));
  asm ("" : "=r" (x) : "r" (42));

(are we still agreeing on this?  I'm having a problem understanding why 
you think the above wouldn't work)

>From that follows that also these are correct:

  asm ("" : "=r" (x) : "0" (y+z));
  asm ("" : "=r" (x) : "0" (z));
  asm ("" : "=r" (x) : "0" (42));

It follows from the above because "0" is exactly like "r" here, except 
that the concrete register to use is the same as for the first operand.

> REgister allocation and reloading will first try to allocate the two 
> objects to the same register and if that doesn't work it will emit 
> copies to ensure they are the same register.

Not quite.  Your use of "objects" muddles the issue.  It doesn't allocate 
two objects to the same register, it allocates the two _operands_ to the 
same register.  For output operands that's indeed an object (lvalue), for 
input operands it's rvalues, not objects.  It does indeed allocate both to 
the same register, possibly using copies.  If the rvalue happens to not be 
already in a register it makes it so by loading it into a, well, register.

> But that doesn't work when one of the objects isn't a register.  
> There's no allocno for the constant.  It's just that, a constant.

Which is a perfectly fine rvalue.  Input constraints never need lvalues 
(or objects).  Maybe you're confusing this all with one particularity that 
_if_ the input rvalue stems from an object and that object happens to be 
allocated to a hardreg (via an asm("regname") declaration) then this 
hardreg will be used as input register?  In that way some information 
from lvalues also flows into input operands, but it's not generally the 
case that they must be lvalues.

> > FWIW, the above is a "portable" way to get the value 0 into 'a' without 
> > the compiler knowing.
> ?!?  Mine is just as portable and should actually work :-)

Um, no?  FWIW this was your example:

  asm ("" : "=r" (a) : "n" (0));

So, we put 0 into an immedate operand before the asm.  After the asm we 
put some register into a.  How do you suggest that the immediate asm 
operand (which isn't mentioned in the asm template, in fact there are no 
operations at all) would be placed into that output register?  Answer: 
it isn't, the above places a random value into 'a'.


Ciao,
Michael.


Re: gcc torture test pr52286.c

2017-08-28 Thread Michael Matz
Hi,

On Mon, 28 Aug 2017, Paul S wrote:

> I've ported gcc to a 16 bit CPU and have all torture tests passing bar one,
> pr52286.c
> 
> The offending lines of code are
> 
>   long a, b = 0;
>   asm ("" : "=r" (a) : "0" (0));
> 
> 
> which should cause zero to be assigned to the "a" SI sized variable.
> 
> Inspecting the generated code revealed that zero was only being assigned to
> the lower 16 bit half of "a".
> 
> ldr2,0
> 
> I changed the inline asm statement to
> 
>   asm ("" : "=r" (a) : "0" (0L));

I think this really is the right fix for this testcase.  The testcase was 
obviously developed for sizeof(int)>2 targets.  The involved constant 
doesn't fit into int on those, but the #ifdef case for <=2 targets seems 
to have been an afterthought.  The asm would have needed the adjustment 
that you had to do now.

> so it seems that the "0" constraint on the input operand is affecting 
> the inferred mode of the output register operand ?

Or put another way, the required longness (two regs) of the output 
constraints isn't reflected back into the input constraint, yes.  For 
matching constraints the promoted types of the operands need to match, but 
nothing checks this :-/


Ciao,
Michael.


Re: gcc torture test pr52286.c

2017-08-28 Thread Michael Matz
Hi,

On Mon, 28 Aug 2017, Michael Matz wrote:

> On Mon, 28 Aug 2017, Jeff Law wrote:
> 
> > I can't remember matching constraints ever working that way.
> 
> They do work exactly so.

FWIW, I was momentarily worried that there once was a world where you were 
right.  If so (and I don't believe it) it was before gcc 2.95 ;-)


Ciao,
Michael.


Re: Building on gcc112 is stuck in msgfmt

2017-08-28 Thread Bill Seurer

On 08/28/2017 02:16 AM, Martin Liška wrote:

Hello.

I've just repeatedly seen stuck in build process:

make[5]: Entering directory 
`/home/marxin/Programming/gcc/objdir/powerpc64le-unknown-linux-gnu/libstdc++-v3/po'
msgfmt -o de.mo ../../../../libstdc++-v3/po/de.po

49__asm volatile ("sc; mfcr %0"
Missing separate debuginfos, use: debuginfo-install 
gettext-0.18.2.1-4.el7.ppc64le
(gdb) bt
#0  0x3fff85d8bac8 in sys_futex0 (val=-1, op=128, addr=0x3fff85db0520 
) at ../../../libgomp/config/linux/powerpc/futex.h:49
#1  futex_wait (val=-1, addr=0x3fff85db0520 ) at 
../../../libgomp/config/linux/powerpc/futex.h:62
#2  do_wait (val=-1, addr=) at 
../../../libgomp/config/linux/wait.h:67
#3  gomp_mutex_lock_slow (mutex=0x3fff85db0520 , 
oldval=) at ../../../libgomp/config/linux/mutex.c:63
#4  0x3fff85d98b04 in gomp_mutex_lock (mutex=0x3fff85db0520 
) at ../../../libgomp/config/linux/mutex.h:57
#5  goacc_register (disp=0x3fff85db0090 ) at 
../../../libgomp/oacc-init.c:74
#6  0x3fff85d983fc in goacc_host_init () at ../../../libgomp/oacc-host.c:265
#7  0x3fff85d99c88 in goacc_runtime_initialize () at 
../../../libgomp/oacc-init.c:657
#8  0x3fff85d7882c in initialize_env () at ../../../libgomp/env.c:1340
#9  0x3fff86525c74 in _dl_init_internal () from /lib64/ld64.so.2
#10 0x3fff865119cc in _dl_start_user () from /lib64/ld64.so.2

$ msgfmt --version
msgfmt (GNU gettext-tools) 0.18.2

Is it a known issue, has anybody spotted that as well?

Thanks,
Martin



I just did a build/test of current trunk (all languages, r251389) on a 
powerpc64le RHEL 7.3 system that has the same version of msgfmt and it 
went fine.

--

-Bill Seurer



Re: Building on gcc112 is stuck in msgfmt

2017-08-28 Thread Martin Liška

On 08/28/2017 04:06 PM, Jeff Law wrote:

On 08/28/2017 01:16 AM, Martin Liška wrote:

Hello.

I've just repeatedly seen stuck in build process:

make[5]: Entering directory 
`/home/marxin/Programming/gcc/objdir/powerpc64le-unknown-linux-gnu/libstdc++-v3/po'
msgfmt -o de.mo ../../../../libstdc++-v3/po/de.po

49__asm volatile ("sc; mfcr %0"
Missing separate debuginfos, use: debuginfo-install 
gettext-0.18.2.1-4.el7.ppc64le
(gdb) bt
#0  0x3fff85d8bac8 in sys_futex0 (val=-1, op=128, addr=0x3fff85db0520 
) at ../../../libgomp/config/linux/powerpc/futex.h:49
#1  futex_wait (val=-1, addr=0x3fff85db0520 ) at 
../../../libgomp/config/linux/powerpc/futex.h:62
#2  do_wait (val=-1, addr=) at 
../../../libgomp/config/linux/wait.h:67
#3  gomp_mutex_lock_slow (mutex=0x3fff85db0520 , 
oldval=) at ../../../libgomp/config/linux/mutex.c:63
#4  0x3fff85d98b04 in gomp_mutex_lock (mutex=0x3fff85db0520 
) at ../../../libgomp/config/linux/mutex.h:57
#5  goacc_register (disp=0x3fff85db0090 ) at 
../../../libgomp/oacc-init.c:74
#6  0x3fff85d983fc in goacc_host_init () at ../../../libgomp/oacc-host.c:265
#7  0x3fff85d99c88 in goacc_runtime_initialize () at 
../../../libgomp/oacc-init.c:657
#8  0x3fff85d7882c in initialize_env () at ../../../libgomp/env.c:1340
#9  0x3fff86525c74 in _dl_init_internal () from /lib64/ld64.so.2
#10 0x3fff865119cc in _dl_start_user () from /lib64/ld64.so.2

$ msgfmt --version
msgfmt (GNU gettext-tools) 0.18.2

Is it a known issue, has anybody spotted that as well?

Yea, my ppc64le builds from late last week are stumbling on this as
well.  Could well be an environment thing -- if I go into
/libstdc++-v3/po and "make", it works just fine.


I did the same with the same result. Note that I can see the same problem
on gcc110 machine :/

Martin



jeff





Re: gcc torture test pr52286.c

2017-08-28 Thread Paul S

Thanks Michael (and Jeff)

I shared your view about the mode of the output register not 
being reflected to the input until I saw


(asm_operands:SI ("") ("=r") 0 [
(reg:HI 30)
]

then I was unsure whether the input was affecting the output or 
the output mode wasn't being reflected to the input.


I had assumed that the r value in any assignment would be 
promoted to match the L object, but ...


In any case, I really wanted to ensure my changing the '0' to 
'0L' was really the proper fix and not just masking another issue.


Thanks again everyone... Paul.


On 29/08/17 04:01, Michael Matz wrote:

Hi,

On Mon, 28 Aug 2017, Paul S wrote:


I've ported gcc to a 16 bit CPU and have all torture tests passing bar one,
pr52286.c

The offending lines of code are

   long a, b = 0;
   asm ("" : "=r" (a) : "0" (0));


which should cause zero to be assigned to the "a" SI sized variable.

Inspecting the generated code revealed that zero was only being assigned to
the lower 16 bit half of "a".

ldr2,0

I changed the inline asm statement to

   asm ("" : "=r" (a) : "0" (0L));

I think this really is the right fix for this testcase.  The testcase was
obviously developed for sizeof(int)>2 targets.  The involved constant
doesn't fit into int on those, but the #ifdef case for <=2 targets seems
to have been an afterthought.  The asm would have needed the adjustment
that you had to do now.


so it seems that the "0" constraint on the input operand is affecting
the inferred mode of the output register operand ?

Or put another way, the required longness (two regs) of the output
constraints isn't reflected back into the input constraint, yes.  For
matching constraints the promoted types of the operands need to match, but
nothing checks this :-/


Ciao,
Michael.





Re: gcc torture test pr52286.c

2017-08-28 Thread Jeff Law
On 08/28/2017 11:56 AM, Michael Matz wrote:
> Hi,
> 
> On Mon, 28 Aug 2017, Jeff Law wrote:
> 
>> I can't remember matching constraints ever working that way.
> 
> They do work exactly so.  These uses are all correct, though they place 
> some random value into x:
Hmm, maybe I've spent too much time with .md files rather than looking
at how folks are using asms through the years.

> 
>   int x, y, z;
>   y = z = init();
>   asm ("" : "=r" (x) : "r" (y+z));
>   asm ("" : "=r" (x) : "r" (z));
>   asm ("" : "=r" (x) : "r" (42));

> 
> (are we still agreeing on this?  I'm having a problem understanding why 
> you think the above wouldn't work)
How do we represent the y+z case in particular.  Isn't that shoved into
a gimple temporary and ultimately a pseudo?


> 
> From that follows that also these are correct:
> 
>   asm ("" : "=r" (x) : "0" (y+z));
>   asm ("" : "=r" (x) : "0" (z));
>   asm ("" : "=r" (x) : "0" (42));
> 
> It follows from the above because "0" is exactly like "r" here, except 
> that the concrete register to use is the same as for the first operand
I'm surprised this actually works, but again, it may be because I don't
write a lot of asms and my md-fu isn't what it used to be.

> 
>> REgister allocation and reloading will first try to allocate the two 
>> objects to the same register and if that doesn't work it will emit 
>> copies to ensure they are the same register.
> 
> Not quite.  Your use of "objects" muddles the issue.  It doesn't allocate 
> two objects to the same register, it allocates the two _operands_ to the 
> same register.  For output operands that's indeed an object (lvalue), for 
> input operands it's rvalues, not objects.  It does indeed allocate both to 
> the same register, possibly using copies.  If the rvalue happens to not be 
> already in a register it makes it so by loading it into a, well, register.
I'll trust you on this -- I haven't gone in and looked at the code.
> 
>> But that doesn't work when one of the objects isn't a register.  
>> There's no allocno for the constant.  It's just that, a constant.
> 
> Which is a perfectly fine rvalue.  Input constraints never need lvalues 
> (or objects).  Maybe you're confusing this all with one particularity that 
> _if_ the input rvalue stems from an object and that object happens to be 
> allocated to a hardreg (via an asm("regname") declaration) then this 
> hardreg will be used as input register?  In that way some information 
> from lvalues also flows into input operands, but it's not generally the 
> case that they must be lvalues.
True.  I'm not thinking in terms of lvalues and rvalues, but in terms of
allocnos and pseudos that the allocators and reloaders operate on.

> 
>>> FWIW, the above is a "portable" way to get the value 0 into 'a' without 
>>> the compiler knowing.
>> ?!?  Mine is just as portable and should actually work :-)
> 
> Um, no?  FWIW this was your example:
> 
>   asm ("" : "=r" (a) : "n" (0));
> 
> So, we put 0 into an immedate operand before the asm.  After the asm we 
> put some register into a.  How do you suggest that the immediate asm 
> operand (which isn't mentioned in the asm template, in fact there are no 
> operations at all) would be placed into that output register?  Answer: 
> it isn't, the above places a random value into 'a'.
Ack.  Hmm, yea, I misunderstood part of this.  Hmm

Going back to pshortis issue, it's interesting how the size of the input
operand is being used to determine the mode of the matching output
operand.  That ought to be not-too-difficult to find within GCC...  With
any luck there'd be a useful comment in that code.

jeff

Jeff


operand_equal_p() and SSA_NAME

2017-08-28 Thread Martin Sebor

operand_equal_p() doesn't handle SSA_NAMEs and returns false for
operands in that form even when they have equal values (when both
are ADDR_EXPR of the same decl).  Yet the function is extensively
relied on in the middle end where I would expect it be beneficial
to have it handle SSA_NAMEs.  At a minimum, it would let some
tests succeed earlier rather than later, leading to better code.
One example is:

  char a[32];
  memcpy (&a[2], &a[4] - 2, 7);

which would be eliminated even without optimization if the function
did handle SSA_NAMEs.

When this handling of ADDR_EXPR is added, the internal call to
the recursive function returns true but the outermost call then
fails the "hash state" assertion.  With the assertion removed
the change then causes at least one test suite failure due to
a gimple validation check.  That suggests that the function
deliberately doesn't handle SSA_NAMEs but I don't understand
why.

If that is, in fact, intentional, can someone explain what
the rationale is?

Incidentally, I noticed that operand_equal_for_phi_arg_p() in
tree.c that calls operand_equal_p() takes care to avoid doing so
when either argument is an SSA_NAME, apparently as a (presumably
compile-time) optimization.  That seems to confirm that not
handling SSA_NAMEs is intentional (but doesn't explain it).
(As an aside, if operand_equal_p() is meant to return false
for SSA_NAMES and there is a use case for it doing so quickly
why not simply have it do what operand_equal_for_phi_arg_p does
as the first thing?)

Thanks
Martin


Re: operand_equal_p() and SSA_NAME

2017-08-28 Thread Andrew Pinski
On Mon, Aug 28, 2017 at 7:46 PM, Martin Sebor  wrote:
> operand_equal_p() doesn't handle SSA_NAMEs and returns false for
> operands in that form even when they have equal values (when both
> are ADDR_EXPR of the same decl).  Yet the function is extensively
> relied on in the middle end where I would expect it be beneficial
> to have it handle SSA_NAMEs.  At a minimum, it would let some
> tests succeed earlier rather than later, leading to better code.
> One example is:
>
>   char a[32];
>   memcpy (&a[2], &a[4] - 2, 7);
>
> which would be eliminated even without optimization if the function
> did handle SSA_NAMEs.


It does handle it via:
  /* If ARG0 and ARG1 are the same SAVE_EXPR, they are necessarily equal.
 We don't care about side effects in that case because the SAVE_EXPR
 takes care of that for us. In all other cases, two expressions are
 equal if they have no side effects.  If we have two identical
 expressions with side effects that should be treated the same due
 to the only side effects being identical SAVE_EXPR's, that will
 be detected in the recursive calls below.
 If we are taking an invariant address of two identical objects
 they are necessarily equal as well.  */
  if (arg0 == arg1 && ! (flags & OEP_ONLY_CONST)
  && (TREE_CODE (arg0) == SAVE_EXPR
  || (flags & OEP_MATCH_SIDE_EFFECTS)
  || (! TREE_SIDE_EFFECTS (arg0) && ! TREE_SIDE_EFFECTS (arg1
return 1;


That is SSA_NAMES are only equal to another SSA_NAME if it is self.
Otherwise it a different optimization pass job to get them to be
equal.
In this case most likely FRE or DOM.  If they are not doing the job,
you need to check why and not change operand_equal_p to look back it
the SSA_NAME's definition.

Thanks,
Andrew Pinski

>
> When this handling of ADDR_EXPR is added, the internal call to
> the recursive function returns true but the outermost call then
> fails the "hash state" assertion.  With the assertion removed
> the change then causes at least one test suite failure due to
> a gimple validation check.  That suggests that the function
> deliberately doesn't handle SSA_NAMEs but I don't understand
> why.
>
> If that is, in fact, intentional, can someone explain what
> the rationale is?
>
> Incidentally, I noticed that operand_equal_for_phi_arg_p() in
> tree.c that calls operand_equal_p() takes care to avoid doing so
> when either argument is an SSA_NAME, apparently as a (presumably
> compile-time) optimization.  That seems to confirm that not
> handling SSA_NAMEs is intentional (but doesn't explain it).
> (As an aside, if operand_equal_p() is meant to return false
> for SSA_NAMES and there is a use case for it doing so quickly
> why not simply have it do what operand_equal_for_phi_arg_p does
> as the first thing?)
>
> Thanks
> Martin


Re: operand_equal_p() and SSA_NAME

2017-08-28 Thread Jeff Law
On 08/28/2017 08:46 PM, Martin Sebor wrote:
> operand_equal_p() doesn't handle SSA_NAMEs and returns false for
> operands in that form even when they have equal values (when both
> are ADDR_EXPR of the same decl).  Yet the function is extensively
> relied on in the middle end where I would expect it be beneficial
> to have it handle SSA_NAMEs.  At a minimum, it would let some
> tests succeed earlier rather than later, leading to better code.
> One example is:
> 
>   char a[32];
>   memcpy (&a[2], &a[4] - 2, 7);
> 
> which would be eliminated even without optimization if the function
> did handle SSA_NAMEs.
> 
> When this handling of ADDR_EXPR is added, the internal call to
> the recursive function returns true but the outermost call then
> fails the "hash state" assertion.  With the assertion removed
> the change then causes at least one test suite failure due to
> a gimple validation check.  That suggests that the function
> deliberately doesn't handle SSA_NAMEs but I don't understand
> why.
> 
> If that is, in fact, intentional, can someone explain what
> the rationale is?
> 
> Incidentally, I noticed that operand_equal_for_phi_arg_p() in
> tree.c that calls operand_equal_p() takes care to avoid doing so
> when either argument is an SSA_NAME, apparently as a (presumably
> compile-time) optimization.  That seems to confirm that not
> handling SSA_NAMEs is intentional (but doesn't explain it).
> (As an aside, if operand_equal_p() is meant to return false
> for SSA_NAMES and there is a use case for it doing so quickly
> why not simply have it do what operand_equal_for_phi_arg_p does
> as the first thing?)
operand_equal_p was never designed to look back through the use-def
chains.  In fact, it pre-dates all the SSA work.

In general I'd think if you find yourself wanting operand_equal_p to
look backwards through the use-def chains, then more likely than not a
constant/copy propagation opportunity has been missed somewhere.

jeff


Re: operand_equal_p() and SSA_NAME

2017-08-28 Thread Jeff Law
On 08/28/2017 09:46 PM, Andrew Pinski wrote:
> On Mon, Aug 28, 2017 at 7:46 PM, Martin Sebor  wrote:
>> operand_equal_p() doesn't handle SSA_NAMEs and returns false for
>> operands in that form even when they have equal values (when both
>> are ADDR_EXPR of the same decl).  Yet the function is extensively
>> relied on in the middle end where I would expect it be beneficial
>> to have it handle SSA_NAMEs.  At a minimum, it would let some
>> tests succeed earlier rather than later, leading to better code.
>> One example is:
>>
>>   char a[32];
>>   memcpy (&a[2], &a[4] - 2, 7);
>>
>> which would be eliminated even without optimization if the function
>> did handle SSA_NAMEs.
> 
> 
> It does handle it via:
>   /* If ARG0 and ARG1 are the same SAVE_EXPR, they are necessarily equal.
>  We don't care about side effects in that case because the SAVE_EXPR
>  takes care of that for us. In all other cases, two expressions are
>  equal if they have no side effects.  If we have two identical
>  expressions with side effects that should be treated the same due
>  to the only side effects being identical SAVE_EXPR's, that will
>  be detected in the recursive calls below.
>  If we are taking an invariant address of two identical objects
>  they are necessarily equal as well.  */
>   if (arg0 == arg1 && ! (flags & OEP_ONLY_CONST)
>   && (TREE_CODE (arg0) == SAVE_EXPR
>   || (flags & OEP_MATCH_SIDE_EFFECTS)
>   || (! TREE_SIDE_EFFECTS (arg0) && ! TREE_SIDE_EFFECTS (arg1
> return 1;
> 
> 
> That is SSA_NAMES are only equal to another SSA_NAME if it is self.
> Otherwise it a different optimization pass job to get them to be
> equal.
Exactly.

> In this case most likely FRE or DOM.  If they are not doing the job,
> you need to check why and not change operand_equal_p to look back it
> the SSA_NAME's definition.
> 
Right.

Jeff