Useless conditional branches

2010-03-02 Thread Alain Ketterlin


It looks like gcc sometimes produces "useless" conditional branches.
I've found code like this:

  xor%edx,%edx
  ; code with no effect on edx (see full code below)
  test   %edx,%edx
  jne

The branch on the last line is never taken. Why does gcc generate such
code sequences? Is this patched at runtime, or something? Am I missing
something obvious here?

I append the function's complete code below. There is another
suspicious branch at 0xb31cd8 (never taken, for less obvious
reasons---edx is never zero at that point).

I have found hundreds such occurrences across the CPU2006 suite. Does
anybody have any idea why this happens? Is there any specific
optimization to enable or disable to avoid such dead edges? Thanks in
advance for any remark/idea/...


This code is from 416.gamess (from SPEC CPU2006), function "formf",
compiled with "gcc version 4.4.1 (Ubuntu 4.4.1-4ubuntu9)" (from a
stock ubuntu 9.10), with options "-g -O3 -march=native
-fno-optimize-sibling-calls". 416.gamess is compiled with gfortran,
but the same thing happens with C or C++ programs. The same also
happens at lower optimization levels (-01), but less frequently.

uname -m gives "x86_64", and /proc/cpuinfo contains:

vendor_id   : GenuineIntel
cpu family  : 6
model   : 23
model name  : Intel(R) Core(TM)2 Duo CPU P8700  @ 2.53GHz
[...]
flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov
pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe syscall nx
lm constant_tsc arch_perfmon pebs bts rep_good pni dtes64 monitor
ds_cpl vmx smx est tm2 ssse3 cx16 xtpr pdcm sse4_1 xsave lahf_lm ida
tpr_shadow vnmi flexpriority

Here is an objdump disassembly of the code, broken into basic-blocks:

00b31c60 :
  b31c60: push   %rbx
  b31c61: xor%edx,%edx
  b31c63: mov%rsi,%rbx
  b31c66: mov$0x2,%r9d
  b31c6c: mov$0xa,%r8d
  b31c72: mov$0x6,%esi
  b31c77: mov$0xe,%ecx
  b31c7c: test   %edx,%edx
  b31c7e: jneb31cda 

  b31c80: mov$0x3ff8,%r11
  b31c8a: mov$0xbfe0,%r10
  b31c94: mov%r11,(%rdi)
  b31c97: movq   $0x0,0x40(%rdi)
  b31c9f: movq   $0x0,0x20(%rdi)
  b31ca7: mov%r10,0x60(%rdi)
  b31cab: xor%eax,%eax
  b31cad: nopl   (%rax)

  b31cb0: inc%edx
  b31cb2: movq   $0x0,0x10(%rdi,%rax,8)
  b31cbb: movq   $0x0,0x50(%rdi,%rax,8)
  b31cc4: movq   $0x0,0x30(%rdi,%rax,8)
  b31ccd: movq   $0x0,0x70(%rdi,%rax,8)
  b31cd6: test   %edx,%edx
  b31cd8: je b31c80 

  b31cda: cmp$0x2,%edx
  b31cdd: jneb31d18 

  b31cdf: mov$0xbfe0,%r11
  b31ce9: mov$0xbfe0,%r10
  b31cf3: mov%r11,(%rdi,%r9,8)
  b31cf7: mov$0x2,%eax
  b31cfc: movq   $0x0,(%rdi,%r8,8)
  b31d04: movq   $0x0,(%rdi,%rsi,8)
  b31d0c: mov%r10,(%rdi,%rcx,8)
  b31d10: jmpb31cb0 

  b31d12: nopw   0x0(%rax,%rax,1)

  b31d18: movslq %edx,%rax
  b31d1b: cmp$0x1,%edx
  b31d1e: movq   $0x0,(%rdi,%rax,8)
  b31d26: movq   $0x0,0x40(%rdi,%rax,8)
  b31d2f: movq   $0x0,0x20(%rdi,%rax,8)
  b31d38: movq   $0x0,0x60(%rdi,%rax,8)
  b31d41: jneb31cb0 

  b31d47: movq   $0x0,0x50(%rdi,%rax,8)
  b31d50: movq   $0x0,0x30(%rdi,%rax,8)
  b31d59: mov$0x3fe0,%r9
  b31d63: mov$0xbff8,%r8
  b31d6d: mov%r9,0x10(%rdi,%rax,8)
  b31d72: mov%r8,0x70(%rdi,%rax,8)
  b31d77: mov$0xd0f838,%edx
  b31d7c: mov$0xd0f7b0,%esi
  b31d81: mov%rbx,%rdi
  b31d84: xor%eax,%eax
  b31d86: callq  977b20 
  b31d8b: mov$0x3fe0,%rsi
  b31d95: mov$0x3fe0,%rcx
  b31d9f: mov%rsi,(%rbx)
  b31da2: mov%rcx,0x60(%rbx)
  b31da6: mov$0xbfe0,%rdx
  b31db0: mov$0xbfe0,%rax
  b31dba: mov%rdx,0x18(%rbx)
  b31dbe: mov%rax,0x78(%rbx)
  b31dc2: pop%rbx
  b31dc3: retq

Let me know if more detail is needed.

-- Alain.


gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Peter Kourzanov

Hi guys,

  I have the following variation on Duff's device that seems to 
mis-compile on all GCC versions I can access within a minute (that 
is gcc-3.{3,4}, gcc-4.{1,2,3,4} on x86 and gcc-4.3.2 on x86_64). The 
symptoms are as follows:

$ gcc-4.4 -o duffbug duffbug.c ; ./duffbug
{ he��3)
{ hello world ! }

  As you can observe in the difference between duff4_works() and 
duff4_fails(), apparently due to for-loop initializer being externalized
vs. specified as the first for-loop expression. It doesn't matter if the
'case 0' is  labeling the for-loop, or the first statement in the 
for-loop in case of duff4_works() of course. However, older gcc-3.x do
give a warning though if the 'case 0' labels the first statement for 
duff4_fails(), since the first expression in the for-loop is then
inaccessible. All gcc-4.x versions don't warn, even when supplied with
the -Wall flag (which is wrong, hence this *first* bug):

$ gcc-4.4 -Wall -o duffbug duffbug.c ; ./duffbug
$ gcc-3.4 -Wall -o duffbug duffbug.c ; ./duffbug
duffbug.c: In function `duff4_fails':
duffbug.c:28: warning: unreachable code at beginning of switch statement

  I think the compiler is generating wrong code for duff4_fails() when
'case 0' labels the for-loop. It somehow skips the first for-loop
expression, just as if 'case 0' pointed to the first statement in the
for-loop (hence this *second* bug). Haven't checked the assembly
though...

Kind regards,

Pjotr Kourzanov
#include 

int duff4_works(char * dst,const char * src,const size_t n)
{
  const size_t rem=n % 4, a=rem + (!rem)*4;
  char * d=dst+=a;
  const char * s=src+=a;
  dst+=n;
  
switch (rem) {
case 0:  for(/* gcc bug? dst+=n*/;d

Re: Useless conditional branches

2010-03-02 Thread Piotr Wyderski
Alain Ketterlin wrote:

> I've found code like this:
>
>  xor    %edx,%edx
>  ; code with no effect on edx (see full code below)
>  test   %edx,%edx
>  jne    

I have experienced similar sequences where your
"code with no effect" was a lot of SSE instructions,
so I can confirm that the problem exists.

Best regards
Piotr Wyderski


Re: Useless conditional branches

2010-03-02 Thread Andrew Haley
On 03/02/2010 08:55 AM, Alain Ketterlin wrote:
> 
> It looks like gcc sometimes produces "useless" conditional branches.
> I've found code like this:
> 
>   xor%edx,%edx
>   ; code with no effect on edx (see full code below)
>   test   %edx,%edx
>   jne
> 
> The branch on the last line is never taken. Why does gcc generate such
> code sequences? Is this patched at runtime, or something? Am I missing
> something obvious here?

> Let me know if more detail is needed.

We really need a test case, with source, that illustrates the problem.
When we have that, we can treat is as a missed-optimization bug.

Andrew.


Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Andrew Haley
On 03/02/2010 09:38 AM, Peter Kourzanov wrote:

>   I have the following variation on Duff's device that seems to 
> mis-compile on all GCC versions I can access within a minute (that 
> is gcc-3.{3,4}, gcc-4.{1,2,3,4} on x86 and gcc-4.3.2 on x86_64). The 
> symptoms are as follows:
> 
> $ gcc-4.4 -o duffbug duffbug.c ; ./duffbug
> { he��3)
> { hello world ! }
> 
>   As you can observe in the difference between duff4_works() and 
> duff4_fails(), apparently due to for-loop initializer being externalized
> vs. specified as the first for-loop expression. It doesn't matter if the
> 'case 0' is  labeling the for-loop, or the first statement in the 
> for-loop in case of duff4_works() of course. However, older gcc-3.x do
> give a warning though if the 'case 0' labels the first statement for 
> duff4_fails(), since the first expression in the for-loop is then
> inaccessible. All gcc-4.x versions don't warn, even when supplied with
> the -Wall flag (which is wrong, hence this *first* bug):

So, your claim is that gcc should warn about the for loop initializer
being unreachable.  is that correct?

> $ gcc-4.4 -Wall -o duffbug duffbug.c ; ./duffbug
> $ gcc-3.4 -Wall -o duffbug duffbug.c ; ./duffbug
> duffbug.c: In function `duff4_fails':
> duffbug.c:28: warning: unreachable code at beginning of switch statement
> 
>   I think the compiler is generating wrong code for duff4_fails() when
> 'case 0' labels the for-loop. It somehow skips the first for-loop
> expression, just as if 'case 0' pointed to the first statement in the
> for-loop (hence this *second* bug). Haven't checked the assembly
> though...

I don't understand.  In what way is the code gcc generates wrong?

int duff4_fails(char * dst,const char * src,const size_t n)
{
  const size_t rem=n % 4, a=rem + (!rem)*4;
  char * d=dst+=a;
  const char * s=src+=a;
  /* gcc bug? dst+=n; */
  
switch (rem) {
case 0:  for(dst+=n;d dst.  Therefore the loop
exits.

Andrew.



Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Richard Guenther
On Tue, Mar 2, 2010 at 10:38 AM, Peter Kourzanov
 wrote:
>
> Hi guys,
>
>  I have the following variation on Duff's device that seems to
> mis-compile on all GCC versions I can access within a minute (that
> is gcc-3.{3,4}, gcc-4.{1,2,3,4} on x86 and gcc-4.3.2 on x86_64). The
> symptoms are as follows:
>
> $ gcc-4.4 -o duffbug duffbug.c ; ./duffbug
> { he��3)
> { hello world ! }
>
>  As you can observe in the difference between duff4_works() and
> duff4_fails(), apparently due to for-loop initializer being externalized
> vs. specified as the first for-loop expression. It doesn't matter if the
> 'case 0' is  labeling the for-loop, or the first statement in the
> for-loop in case of duff4_works() of course. However, older gcc-3.x do
> give a warning though if the 'case 0' labels the first statement for
> duff4_fails(), since the first expression in the for-loop is then
> inaccessible. All gcc-4.x versions don't warn, even when supplied with
> the -Wall flag (which is wrong, hence this *first* bug):
>
> $ gcc-4.4 -Wall -o duffbug duffbug.c ; ./duffbug
> $ gcc-3.4 -Wall -o duffbug duffbug.c ; ./duffbug
> duffbug.c: In function `duff4_fails':
> duffbug.c:28: warning: unreachable code at beginning of switch statement
>
>  I think the compiler is generating wrong code for duff4_fails() when
> 'case 0' labels the for-loop. It somehow skips the first for-loop
> expression, just as if 'case 0' pointed to the first statement in the
> for-loop (hence this *second* bug). Haven't checked the assembly
> though...

The routines are not equivalent.  in _works you unconditionally
do dst += n while in _fails you only do it for rem == 0.

Richard.

> Kind regards,
>
> Pjotr Kourzanov
>


Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Pjotr Kourzanov
On Tue, 2010-03-02 at 10:24 +, Andrew Haley wrote: 
> On 03/02/2010 09:38 AM, Peter Kourzanov wrote:
> 
> >   I have the following variation on Duff's device that seems to 
> > mis-compile on all GCC versions I can access within a minute (that 
> > is gcc-3.{3,4}, gcc-4.{1,2,3,4} on x86 and gcc-4.3.2 on x86_64). The 
> > symptoms are as follows:
> > 
> > $ gcc-4.4 -o duffbug duffbug.c ; ./duffbug
> > { he��3)
> > { hello world ! }
> > 
> >   As you can observe in the difference between duff4_works() and 
> > duff4_fails(), apparently due to for-loop initializer being externalized
> > vs. specified as the first for-loop expression. It doesn't matter if the
> > 'case 0' is  labeling the for-loop, or the first statement in the 
> > for-loop in case of duff4_works() of course. However, older gcc-3.x do
> > give a warning though if the 'case 0' labels the first statement for 
> > duff4_fails(), since the first expression in the for-loop is then
> > inaccessible. All gcc-4.x versions don't warn, even when supplied with
> > the -Wall flag (which is wrong, hence this *first* bug):
> 
> So, your claim is that gcc should warn about the for loop initializer
> being unreachable.  is that correct?

Exactly. Just like what gcc-3.x does, even without the -Wall flag.

> 
> > $ gcc-4.4 -Wall -o duffbug duffbug.c ; ./duffbug
> > $ gcc-3.4 -Wall -o duffbug duffbug.c ; ./duffbug
> > duffbug.c: In function `duff4_fails':
> > duffbug.c:28: warning: unreachable code at beginning of switch statement
> > 
> >   I think the compiler is generating wrong code for duff4_fails() when
> > 'case 0' labels the for-loop. It somehow skips the first for-loop
> > expression, just as if 'case 0' pointed to the first statement in the
> > for-loop (hence this *second* bug). Haven't checked the assembly
> > though...
> 
> I don't understand.  In what way is the code gcc generates wrong?
> 
> int duff4_fails(char * dst,const char * src,const size_t n)
> {
>   const size_t rem=n % 4, a=rem + (!rem)*4;
>   char * d=dst+=a;
>   const char * s=src+=a;
>   /* gcc bug? dst+=n; */
>   
> switch (rem) {
> case 0:  for(dst+=n;d /*case 0:*/   d[-4]=s[-4];
> case 3:   d[-3]=s[-3];
> case 2:   d[-2]=s[-2];
> case 1:   d[-1]=s[-1];
> }
> }
>   return 0;
> }
> The first time around the loop the initializer (d+=n) is jumped around, so
> d == dst.  At the end of the loop, d+=4, so d > dst.  Therefore the loop
> exits.

  And its wrong since it shouldn't jump around the initializer.  The
following two snippets exhibit the same behaviour:

> case 0:  for(dst+=n;d /*case 0:*/   d[-4]=s[-4];

> /*case 0:*/  for(dst+=n;d case 0:   d[-4]=s[-4];

  Which is wrong IMHO.

Kind regards,

Pjotr



Re: Useless conditional branches

2010-03-02 Thread Alain Ketterlin

Andrew Haley wrote:

On 03/02/2010 08:55 AM, Alain Ketterlin wrote:

It looks like gcc sometimes produces "useless" conditional branches.
I've found code like this:

  xor%edx,%edx
  ; code with no effect on edx (see full code below)
  test   %edx,%edx
  jne

The branch on the last line is never taken. Why does gcc generate such
code sequences? Is this patched at runtime, or something? Am I missing
something obvious here?



We really need a test case, with source, that illustrates the problem.
When we have that, we can treat is as a missed-optimization bug.


Sure. I can provide a list of functions from the SPEC CPU2006 where it 
happens. Here is the list for 403.gcc, at -01 and -03 (the CPU2006 gcc 
is based on gcc-3.2, according to SPEC, so probably different from the 
actual code base).


=== 403.gcc (-O1)
FUN init_builtins 0x43582f BLOCK 0x43582f
FUN cpp_finish_options 0x435a39 BLOCK 0x435a52
FUN life_analysis 0x4be8f7 BLOCK 0x4beb79
FUN optimize_mode_switching 0x580b9a BLOCK 0x580ea4
=== 403.gcc (-O3)
FUN start_function 0x413af0 BLOCK 0x41410e
FUN init_builtins 0x442640 BLOCK 0x442640
FUN cpp_finish_options 0x442ec0 BLOCK 0x442f28
FUN can_combine_p 0x4770f0 BLOCK 0x477196
FUN gen_rtx 0x4bf440 BLOCK 0x4bf5a8
FUN expand_shift 0x4ca5a0 BLOCK 0x4ca6ce
FUN life_analysis 0x4edbc0 BLOCK 0x4ee03d
FUN htab_create 0x6a1940 BLOCK 0x6a1940
FUN htab_expand 0x6a1aa0 BLOCK 0x6a1aa0
FUN htab_try_create 0x6a1ee0 BLOCK 0x6a1ee0

(the addresses may be meaningless, but if both addresses are equal it 
means that the problem appears on the entry block). I can't guarantee 
this list is exhaustive.


My full list for CPU2006 programs is a bit too long to post on the 
mailing list (around a thousand lines). I can send it by mail (is a list 
of function names enough?).


I'll try to extract a minimal example if you want and/or have no access 
to CPU2006. Give me one or two days.


-- Alain.


Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Pjotr Kourzanov
On Tue, 2010-03-02 at 11:27 +0100, Richard Guenther wrote: 
> On Tue, Mar 2, 2010 at 10:38 AM, Peter Kourzanov
>  wrote:
> >
> > Hi guys,
> >
> >  I have the following variation on Duff's device that seems to
> > mis-compile on all GCC versions I can access within a minute (that
> > is gcc-3.{3,4}, gcc-4.{1,2,3,4} on x86 and gcc-4.3.2 on x86_64). The
> > symptoms are as follows:
> >
> > $ gcc-4.4 -o duffbug duffbug.c ; ./duffbug
> > { he��3)
> > { hello world ! }
> >
> >  As you can observe in the difference between duff4_works() and
> > duff4_fails(), apparently due to for-loop initializer being externalized
> > vs. specified as the first for-loop expression. It doesn't matter if the
> > 'case 0' is  labeling the for-loop, or the first statement in the
> > for-loop in case of duff4_works() of course. However, older gcc-3.x do
> > give a warning though if the 'case 0' labels the first statement for
> > duff4_fails(), since the first expression in the for-loop is then
> > inaccessible. All gcc-4.x versions don't warn, even when supplied with
> > the -Wall flag (which is wrong, hence this *first* bug):
> >
> > $ gcc-4.4 -Wall -o duffbug duffbug.c ; ./duffbug
> > $ gcc-3.4 -Wall -o duffbug duffbug.c ; ./duffbug
> > duffbug.c: In function `duff4_fails':
> > duffbug.c:28: warning: unreachable code at beginning of switch statement
> >
> >  I think the compiler is generating wrong code for duff4_fails() when
> > 'case 0' labels the for-loop. It somehow skips the first for-loop
> > expression, just as if 'case 0' pointed to the first statement in the
> > for-loop (hence this *second* bug). Haven't checked the assembly
> > though...
> 
> The routines are not equivalent.  in _works you unconditionally
> do dst += n while in _fails you only do it for rem == 0.

That's right. And about missing warning?

> 
> Richard.
> 
> > Kind regards,
> >
> > Pjotr Kourzanov
> >
> 




Re: Useless conditional branches

2010-03-02 Thread Richard Guenther
On Tue, Mar 2, 2010 at 10:55 AM, Andrew Haley  wrote:
> On 03/02/2010 08:55 AM, Alain Ketterlin wrote:
>>
>> It looks like gcc sometimes produces "useless" conditional branches.
>> I've found code like this:
>>
>>   xor    %edx,%edx
>>   ; code with no effect on edx (see full code below)
>>   test   %edx,%edx
>>   jne    
>>
>> The branch on the last line is never taken. Why does gcc generate such
>> code sequences? Is this patched at runtime, or something? Am I missing
>> something obvious here?
>
>> Let me know if more detail is needed.
>
> We really need a test case, with source, that illustrates the problem.
> When we have that, we can treat is as a missed-optimization bug.

I can't reproduce it with 4.3 nor 4.5 but indeed 4.4 has this interesting
code sequence.  It looks like a missed jump threading opportunity.

Richard.

> Andrew.
>


Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Andrew Haley
On 03/02/2010 10:34 AM, Pjotr Kourzanov wrote:

>> int duff4_fails(char * dst,const char * src,const size_t n)
>> {
>>   const size_t rem=n % 4, a=rem + (!rem)*4;
>>   char * d=dst+=a;
>>   const char * s=src+=a;
>>   /* gcc bug? dst+=n; */
>>   
>> switch (rem) {
>> case 0:  for(dst+=n;d> /*case 0:*/  d[-4]=s[-4];
>> case 3:  d[-3]=s[-3];
>> case 2:  d[-2]=s[-2];
>> case 1:  d[-1]=s[-1];
>>}
>> }
>>  return 0;
>> }
>> The first time around the loop the initializer (d+=n) is jumped around, so
>> d == dst.  At the end of the loop, d+=4, so d > dst.  Therefore the loop
>> exits.
> 
>   And its wrong since it shouldn't jump around the initializer.

Sure it should.  On entry to that loop, rem == 3.

Andrew.


Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Andreas Schwab
Peter Kourzanov  writes:

>   I think the compiler is generating wrong code for duff4_fails() when
> 'case 0' labels the for-loop. It somehow skips the first for-loop
> expression,

If rem != 0 you jump over the init expression, so it is never executed.

Andreas.

-- 
Andreas Schwab, sch...@redhat.com
GPG Key fingerprint = D4E8 DBE3 3813 BB5D FA84  5EC7 45C6 250E 6F00 984E
"And now for something completely different."


Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Pjotr Kourzanov
On Tue, 2010-03-02 at 10:47 +, Andrew Haley wrote: 
> On 03/02/2010 10:34 AM, Pjotr Kourzanov wrote:
> 
> >> int duff4_fails(char * dst,const char * src,const size_t n)
> >> {
> >>   const size_t rem=n % 4, a=rem + (!rem)*4;
> >>   char * d=dst+=a;
> >>   const char * s=src+=a;
> >>   /* gcc bug? dst+=n; */
> >>   
> >> switch (rem) {
> >> case 0:  for(dst+=n;d >> /*case 0:*/d[-4]=s[-4];
> >> case 3:d[-3]=s[-3];
> >> case 2:d[-2]=s[-2];
> >> case 1:d[-1]=s[-1];
> >>  }
> >> }
> >>return 0;
> >> }
> >> The first time around the loop the initializer (d+=n) is jumped around, so
> >> d == dst.  At the end of the loop, d+=4, so d > dst.  Therefore the loop
> >> exits.
> > 
> >   And its wrong since it shouldn't jump around the initializer.
> 
> Sure it should.  On entry to that loop, rem == 3.

  I agree, this is one of the places where referential transparency
breaks in C. I wouldn't have expected that the compiler could or 
would put the first expression before the switch in this case:

switch (rem) {
  for(dst+=n;d 
> Andrew.
> 




Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Richard Guenther
On Tue, Mar 2, 2010 at 12:00 PM, Pjotr Kourzanov
 wrote:
> On Tue, 2010-03-02 at 10:47 +, Andrew Haley wrote:
>> On 03/02/2010 10:34 AM, Pjotr Kourzanov wrote:
>>
>> >> int duff4_fails(char * dst,const char * src,const size_t n)
>> >> {
>> >>   const size_t rem=n % 4, a=rem + (!rem)*4;
>> >>   char * d=dst+=a;
>> >>   const char * s=src+=a;
>> >>   /* gcc bug? dst+=n; */
>> >>
>> >>     switch (rem) {
>> >>     case 0:  for(dst+=n;d> >>     /*case 0:*/    d[-4]=s[-4];
>> >>     case 3:        d[-3]=s[-3];
>> >>     case 2:        d[-2]=s[-2];
>> >>     case 1:        d[-1]=s[-1];
>> >>          }
>> >>     }
>> >>    return 0;
>> >> }
>> >> The first time around the loop the initializer (d+=n) is jumped around, so
>> >> d == dst.  At the end of the loop, d+=4, so d > dst.  Therefore the loop
>> >> exits.
>> >
>> >   And its wrong since it shouldn't jump around the initializer.
>>
>> Sure it should.  On entry to that loop, rem == 3.
>
>  I agree, this is one of the places where referential transparency
> breaks in C. I wouldn't have expected that the compiler could or
> would put the first expression before the switch in this case:
>
> switch (rem) {
>  for(dst+=n;d case 0: d[-4]=s[-4]; ...
> }}
>
> However, the warning is still due, since a combination of a switch with a
> for loop results in code that is completely ignored, i.e., is inaccessible.
> As I said, gcc-3.x used to issue a warning for this one...

Neither 2.95 nor 3.3.6 or 3.4.6 warn for me.

Richard.

>>
>> Andrew.
>>
>
>
>


Re: a gcc plugin to show cfg graphically when debug gcc

2010-03-02 Thread Martin Jambor
Hi,

On Thu, Feb 25, 2010 at 11:48:44AM +0100, Richard Guenther wrote:
> I've been using the attached in debug sessions a lot (and I have
> similar patch for the cgraph). 

I'd be interested in that, can you post it as well?

I meant to write something like that for myself a few times but in the
end I always managed without it somehow.

Thanks,

Martin

> I've been wanting to transform
> this into a gdb python script but sofar didn't get along to do it ...
> 
> The nice thing with using dot is that it listens to file changes
> and so with xlib output you get a nice cfg "movie" when invoking
> the generation function when hitting a breakpoint.
> 
> Richard.


Re: gcc miscompiling duff's device (probaby two different bugs)

2010-03-02 Thread Peter Kourzanov
On Tue, 2010-03-02 at 12:26 +0100, Richard Guenther wrote: 
> On Tue, Mar 2, 2010 at 12:00 PM, Pjotr Kourzanov
>  wrote:
> > On Tue, 2010-03-02 at 10:47 +, Andrew Haley wrote:
> >> On 03/02/2010 10:34 AM, Pjotr Kourzanov wrote:
> >>
> >> >> int duff4_fails(char * dst,const char * src,const size_t n)
> >> >> {
> >> >>   const size_t rem=n % 4, a=rem + (!rem)*4;
> >> >>   char * d=dst+=a;
> >> >>   const char * s=src+=a;
> >> >>   /* gcc bug? dst+=n; */
> >> >>
> >> >> switch (rem) {
> >> >> case 0:  for(dst+=n;d >> >> /*case 0:*/d[-4]=s[-4];
> >> >> case 3:d[-3]=s[-3];
> >> >> case 2:d[-2]=s[-2];
> >> >> case 1:d[-1]=s[-1];
> >> >>  }
> >> >> }
> >> >>return 0;
> >> >> }
> >> >> The first time around the loop the initializer (d+=n) is jumped around, 
> >> >> so
> >> >> d == dst.  At the end of the loop, d+=4, so d > dst.  Therefore the loop
> >> >> exits.
> >> >
> >> >   And its wrong since it shouldn't jump around the initializer.
> >>
> >> Sure it should.  On entry to that loop, rem == 3.
> >
> >  I agree, this is one of the places where referential transparency
> > breaks in C. I wouldn't have expected that the compiler could or
> > would put the first expression before the switch in this case:
> >
> > switch (rem) {
> >  for(dst+=n;d > case 0: d[-4]=s[-4]; ...
> > }}
> >
> > However, the warning is still due, since a combination of a switch with a
> > for loop results in code that is completely ignored, i.e., is inaccessible.
> > As I said, gcc-3.x used to issue a warning for this one...
> 
> Neither 2.95 nor 3.3.6 or 3.4.6 warn for me.

That's weird. I am having:

gcc-3.3 (GCC) 3.3.6 (Ubuntu 1:3.3.6-15ubuntu6)
Configured with: ../src/configure -v --enable-languages=c,c++
--prefix=/usr --mandir=/usr/share/man --infodir=/usr/share/info
--with-gxx-include-dir=/usr/include/c++/3.3 --enable-shared
--enable-__cxa_atexit --with-system-zlib --enable-nls
--without-included-gettext --enable-clocale=gnu --enable-debug
i486-linux-gnu
Thread model: posix
gcc-3.4 (GCC) 3.4.6 (Ubuntu 3.4.6-8ubuntu2)
Configured with: ../src/configure -v --enable-languages=c,f77
--prefix=/usr --libexecdir=/usr/lib
--with-gxx-include-dir=/usr/include/c++/3.4 --enable-shared
--with-system-zlib --enable-nls --without-included-gettext
--program-suffix=-3.4 --enable-__cxa_atexit --with-tune=pentium4
i486-linux-gnu
Thread model: posix

Are you sure you test the following variant?

switch (rem) { 
for(dst+=n;d 
> Richard.
> 
> >>
> >> Andrew.
> >>
> >
> >
> >
> 




GUPC: A GCC frontend for UPC

2010-03-02 Thread Gary Funck
A GCC front-end (and runtime) for UPC (Unified Parallel C) is available
via the following GCC branch: svn://svn/gcc/branches/gupc.

The GUPC project is described here: http://gcc.gnu.org/projects/gupc.html.

Over the course of this year, we plan to work with the GCC
development community with the goal to merge UPC support
into the GCC mainline (perhaps in the GCC 4.6 release).

We appreciate any/all feedback and suggestions.

Thanks,
- The GUPC development team



gcc-4.4-20100302 is now available

2010-03-02 Thread gccadmin
Snapshot gcc-4.4-20100302 is now available on
  ftp://gcc.gnu.org/pub/gcc/snapshots/4.4-20100302/
and on various mirrors, see http://gcc.gnu.org/mirrors.html for details.

This snapshot has been generated from the GCC 4.4 SVN branch
with the following options: svn://gcc.gnu.org/svn/gcc/branches/gcc-4_4-branch 
revision 157179

You'll find:

gcc-4.4-20100302.tar.bz2  Complete GCC (includes all of below)

gcc-core-4.4-20100302.tar.bz2 C front end and core compiler

gcc-ada-4.4-20100302.tar.bz2  Ada front end and runtime

gcc-fortran-4.4-20100302.tar.bz2  Fortran front end and runtime

gcc-g++-4.4-20100302.tar.bz2  C++ front end and runtime

gcc-java-4.4-20100302.tar.bz2 Java front end and runtime

gcc-objc-4.4-20100302.tar.bz2 Objective-C front end and runtime

gcc-testsuite-4.4-20100302.tar.bz2The GCC testsuite

Diffs from 4.4-20100223 are available in the diffs/ subdirectory.

When a particular snapshot is ready for public consumption the LATEST-4.4
link is updated and a message is sent to the gcc list.  Please do not use
a snapshot before it has been announced that way.


Bootstraping i686-linux gcc on x86_64-linux fails during libgcc stage1 on trunk

2010-03-02 Thread Laurent GUERBY
Hi,

I'm trying to build a fully 32 bits GCC on a x86_64-linux 64 bits debian
system which has all the 32 bits libraries installed (this is for the
GCC compile farm testers).

I've played with various things including --with-ld= and putting a fake
"ld" script in PATH but something is hardcoding "/usr/bin/ld" and at the
end of stage1 it always fails to link libgcc, after having successfully
built a 32 bits cc1 & friends.

crti.o & friends in 32 bits are in /usr/lib32 on this system.

What am I doing wrong? Is there a way to tell libgcc build to
use ld the right way?

Thanks in advance,

Laurent

$ CC="gcc -m32"
$ export CC
$ ../trunk/configure --prefix=/n/100/guerby/install-trunk
--enable-languages=c --enable-__cxa_atexit --disable-nls
--enable-threads=posix --with-mpfr=/opt/cfarm/mpfr-2.4.2-32
--with-gmp=/opt/cfarm/gmp-4.2.4-32 --with-mpc=/opt/cfarm/mpc-0.8-32
--build=i686-linux-gnu --host=i686-linux-gnu --target=i686-linux-gnu
--disable-multilib
$ make
...
/home/guerby/build/./gcc/xgcc -B/home/guerby/build/./gcc/
-B/n/100/guerby/install-trunk/i686-linux-gnu/bin/
-B/n/100/guerby/install-trunk/i686-linux-gnu/lib/
-isystem /n/100/guerby/install-trunk/i686-linux-gnu/include
-isystem /n/100/guerby/install-trunk/i686-linux-gnu/sys-include-O2
-g -O2 -DIN_GCC   -W -Wall -Wwrite-strings -Wcast-qual
-Wstrict-prototypes -Wmissing-prototypes -Wold-style-definition
-isystem ./include  -fPIC -g -DHAVE_GTHR_DEFAULT -DIN_LIBGCC2
-D__GCC_FLOAT_NOT_NEEDED  -shared -nodefaultlibs
-Wl,--soname=libgcc_s.so.1 -Wl,--version-script=libgcc.map
-o ./libgcc_s.so.1.tmp -g -O2 -B./ _muldi3_s.o _negdi2_s.o _lshrdi3_s.o
_ashldi3_s.o _ashrdi3_s.o _cmpdi2_s.o _ucmpdi2_s.o _clear_cache_s.o
_enable_execute_stack_s.o _trampoline_s.o __main_s.o _absvsi2_s.o
_absvdi2_s.o _addvsi3_s.o _addvdi3_s.o _subvsi3_s.o _subvdi3_s.o
_mulvsi3_s.o _mulvdi3_s.o _negvsi2_s.o _negvdi2_s.o _ctors_s.o
_ffssi2_s.o _ffsdi2_s.o _clz_s.o _clzsi2_s.o _clzdi2_s.o _ctzsi2_s.o
_ctzdi2_s.o _popcount_tab_s.o _popcountsi2_s.o _popcountdi2_s.o
_paritysi2_s.o _paritydi2_s.o _powisf2_s.o _powidf2_s.o _powixf2_s.o
_powitf2_s.o _mulsc3_s.o _muldc3_s.o _mulxc3_s.o _multc3_s.o _divsc3_s.o
_divdc3_s.o _divxc3_s.o _divtc3_s.o _bswapsi2_s.o _bswapdi2_s.o
_fixunssfsi_s.o _fixunsdfsi_s.o _fixunsxfsi_s.o _fixsfdi_s.o
_fixdfdi_s.o _fixxfdi_s.o _fixunssfdi_s.o _fixunsdfdi_s.o
_fixunsxfdi_s.o _floatdisf_s.o _floatdidf_s.o _floatdixf_s.o
_floatundisf_s.o _floatundidf_s.o _floatundixf_s.o _divdi3_s.o
_moddi3_s.o _udivdi3_s.o _umoddi3_s.o _udiv_w_sdiv_s.o _udivmoddi4_s.o
addtf3_s.o divtf3_s.o eqtf2_s.o getf2_s.o letf2_s.o multf3_s.o
negtf2_s.o subtf3_s.o unordtf2_s.o fixtfsi_s.o fixunstfsi_s.o
floatsitf_s.o floatunsitf_s.o fixtfdi_s.o fixunstfdi_s.o floatditf_s.o
floatunditf_s.o extendsftf2_s.o extenddftf2_s.o extendxftf2_s.o
trunctfsf2_s.o trunctfdf2_s.o trunctfxf2_s.o tf-signs_s.o unwind-dw2_s.o
unwind-dw2-fde-glibc_s.o unwind-sjlj_s.o gthr-gnat_s.o unwind-c_s.o
emutls_s.o -lc && rm -f ./libgcc_s.so && if [ -f ./libgcc_s.so.1 ]; then
mv -f ./libgcc_s.so.1 ./libgcc_s.so.1.backup; else true; fi &&
mv ./libgcc_s.so.1.tmp ./libgcc_s.so.1 && ln -s
libgcc_s.so.1 ./libgcc_s.so
/usr/bin/ld: skipping incompatible /usr/bin/../lib/libc.so when
searching for -lc
/usr/bin/ld: skipping incompatible /usr/bin/../lib/libc.a when searching
for -lc
/usr/bin/ld: i386:x86-64 architecture of input file `/usr/lib/crti.o' is
incompatible with i386 output
/usr/bin/ld: i386:x86-64 architecture of input file `/usr/lib/crtn.o' is
incompatible with i386 output
collect2: ld returned 1 exit status
make[3]: *** [libgcc_s.so] Error 1
make[3]: Leaving directory `/home/guerby/build/i686-linux-gnu/libgcc'
make[2]: *** [all-stage1-target-libgcc] Error 2
make[2]: Leaving directory `/home/guerby/build'
make[1]: *** [stage1-bubble] Error 2
make[1]: Leaving directory `/home/guerby/build'
make: *** [bootstrap] Error 2
$ file gcc/cc1
build/gcc/cc1: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV),
dynamically linked (uses shared libs), for GNU/Linux 2.6.8, not stripped





Re: Bootstraping i686-linux gcc on x86_64-linux fails during libgcc stage1 on trunk

2010-03-02 Thread Joseph S. Myers
On Wed, 3 Mar 2010, Laurent GUERBY wrote:

> $ ../trunk/configure --prefix=/n/100/guerby/install-trunk
> --enable-languages=c --enable-__cxa_atexit --disable-nls
> --enable-threads=posix --with-mpfr=/opt/cfarm/mpfr-2.4.2-32
> --with-gmp=/opt/cfarm/gmp-4.2.4-32 --with-mpc=/opt/cfarm/mpc-0.8-32
> --build=i686-linux-gnu --host=i686-linux-gnu --target=i686-linux-gnu
> --disable-multilib

The logic to use lib32 on Debian/Ubuntu is only in t-linux64, so you need 
to build --enable-targets=all for this to work.  (I don't know whether 
--enable-targets=all --disable-multilib works; it doesn't really make 
logical sense, but might in fact cause the MULTILIB_OSDIRNAMES 
configuration to take effect with none of the rest of the multilib 
configuration.)

-- 
Joseph S. Myers
jos...@codesourcery.com


Re: Bootstraping i686-linux gcc on x86_64-linux fails during libgcc stage1 on trunk

2010-03-02 Thread H.J. Lu
On Tue, Mar 2, 2010 at 4:18 PM, Laurent GUERBY  wrote:
> Hi,
>
> I'm trying to build a fully 32 bits GCC on a x86_64-linux 64 bits debian
> system which has all the 32 bits libraries installed (this is for the
> GCC compile farm testers).
>
> I've played with various things including --with-ld= and putting a fake
> "ld" script in PATH but something is hardcoding "/usr/bin/ld" and at the
> end of stage1 it always fails to link libgcc, after having successfully
> built a 32 bits cc1 & friends.
>
> crti.o & friends in 32 bits are in /usr/lib32 on this system.
>
> What am I doing wrong? Is there a way to tell libgcc build to
> use ld the right way?
>

I don't know about Debian. I can bootstap ia32 gcc trunk on Fedora/x86-64
with

# CC="gcc -m32" CXX="g++ -m32" ../src-trunk/configure \
--enable-clocale=gnu --with-system-zlib --enable-shared --with-d
emangler-in-ld --with-fpmath=sse i686-linux

CC="gcc -m32" CXX="g++ -m32" is the key.

-- 
H.J.


Idea for Google Summer Code : C Compiler for EFI Byte Code implement in gcc

2010-03-02 Thread b95705030


Hello all,

I am highly interestd in implementing C compiler for EFI Byte Code in  
gcc and participate in Google Summer Code.


EFI is a much larger, more complex,OS-like replacement for the older BIOS
firmware interface present in all IBM PC-compatible personal computers.
and the EFI specification provides for a processor-independent device  
driver environment(like virtualmachine), called EFI Byte Code or EBC.


Intel(R) C Compiler for EFI Byte Code, the only one C compiler for EFI  
Byte Code

(http://sx.intel.com/p-553-intel-c-compiler-for-efi-byte-code.aspx)
is not open source, and also a pay software.

So i am wondering whether this kind of idea is valuable to the gcc  
community?  or are there any other related ideas is more valuable?



thanks

  yi-hong