[PATCH] Restore bitfield comparison optimization (PR middle-end/37248)

H.J. Lu hjl.tools@gmail.com
Fri Dec 5 22:50:00 GMT 2008


On Fri, Dec 5, 2008 at 8:27 AM, Jakub Jelinek <jakub@redhat.com> wrote:
> Hi!
>
> After discussions on IRC how to solve this, I'm proposing to restore
> this optimization similarly how it has been restored for 4.3,
> as trunk still generates BIT_FIELD_REFs with struct/union bases
> anyway (in SRA) and so the compiler supports them anyway.
>
> The only difference from 4.4 here is that BIT_FIELD_REF_UNSIGNED
> is gone, so we have to make sure the type on the BIT_FIELD_REF is
> the right width and signedness (but it usually is even without
> build_nonstandard_integer_type, because optimize_bit_field_compare
> uses types with TYPE_PRECISION the same as TYPE_SIZE.
>
> Bootstrapped/regtested on x86_64-linux (2 extra patches are needed),
> ok for trunk?
>
> 2008-12-05  Jakub Jelinek  <jakub@redhat.com>
>
>        PR middle-end/37248
>        * fold-const.c (make_bit_field_ref): Change bitpos and bitsize
>        arguments to HOST_WIDE_INT.  If type has different signedness
>        than unsignedp or different precision from bitsize, create
>        the right type for BIT_FIELD_REF and cast to type.
>        (fold_truthop): Change first_bit and end_bit to HOST_WIDE_INT.
>
>        Revert:
>        2008-03-05  Richard Guenther  <rguenther@suse.de>
>        PR c++/35336
>        * fold-const.c (fold_truthop): Remove code generating
>        BIT_FIELD_REFs of structure bases.
>        (fold_binary): Likewise.
>        (make_bit_field_ref): Remove.
>        (optimize_bit_field_compare): Remove.
>        (all_ones_mask_p): Remove.
>
>        * gcc.target/i386/pr37248-1.c: New test.
>        * gcc.target/i386/pr37248-2.c: New test.
>        * gcc.target/i386/pr37248-3.c: New test.
>


> --- gcc/testsuite/gcc.target/i386/pr37248-2.c.jj        2008-12-04 15:37:38.000000000 +0100
> +++ gcc/testsuite/gcc.target/i386/pr37248-2.c   2008-12-04 15:28:18.000000000 +0100
> @@ -0,0 +1,23 @@
> +/* PR middle-end/37248 */
> +/* { dg-do compile } */
> +/* { dg-options "-O2 -fdump-tree-optimized" } */
> +
> +struct S
> +{
> +  unsigned char a : 1;
> +  unsigned char b : 1;
> +  unsigned char c : 1;
> +  unsigned int d : 26;
> +  unsigned char e : 1;
> +  unsigned char f : 1;
> +  unsigned char g : 1;
> +} s;
> +
> +int
> +foo (struct S x)
> +{
> +  return x.a && x.g && x.b && x.f && x.c && x.e;
> +}
> +
> +/* { dg-final { scan-tree-dump "& 3758096391\[^\n\t\]*== 3758096391" "optimized" } } */
> +/* { dg-final { cleanup-tree-dump "optimized" } } */
> --- gcc/testsuite/gcc.target/i386/pr37248-3.c.jj        2008-12-04 15:40:39.000000000 +0100
> +++ gcc/testsuite/gcc.target/i386/pr37248-3.c   2008-12-04 15:39:12.000000000 +0100
> @@ -0,0 +1,25 @@
> +/* PR middle-end/37248 */
> +/* { dg-do compile } */
> +/* { dg-options "-O2 -fdump-tree-optimized" } */
> +
> +struct S
> +{
> +  unsigned char a : 1;
> +  unsigned char b : 1;
> +  unsigned char c : 1;
> +  unsigned int d : 6;
> +  unsigned int e : 14;
> +  unsigned int f : 6;
> +  unsigned char g : 1;
> +  unsigned char h : 1;
> +  unsigned char i : 1;
> +} s;
> +
> +int
> +foo (struct S x)
> +{
> +  return x.a && x.i && x.b && x.h && x.c && x.g && x.e == 131;
> +}
> +
> +/* { dg-final { scan-tree-dump "& 3766484487\[^\n\t\]*== 3758163463" "optimized" } } */
> +/* { dg-final { cleanup-tree-dump "optimized" } } */
>

I got

+FAIL: gcc.target/i386/pr37248-2.c scan-tree-dump optimized "& 3758096391[^
+FAIL: gcc.target/i386/pr37248-3.c scan-tree-dump optimized "& 3766484487[^

on Fedora 9/ia32. I saw

;; Function foo (foo)

Analyzing Edge Insertions.
foo (struct S x)
{
<bb 2>:
  return (BIT_FIELD_REF <x, 32, 0> & 0x0e0000007) == 0x0e0000007;

}

0x0e0000007 is the same as 3758096391


-- 
H.J.



More information about the Gcc-patches mailing list