This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[PATCH][LTO] Allow bootstrapping lto, break whopr (ugh)


This patch allows me to bootstrap with BOOT_CFLAGS including -flto
until the comparison which fails.  The key element of the patch and
all what should be required to fix bootstrapping is the
gimple_get_alias_set change - but that doesn't work because of
lto/41071.  I tried to fix that and it went smooth until running
the testsuite which shows whopr is confused about all the main
variant stuff (the original fix was just to
LTO_REGISTER_TYPE_AND_FIXUP_SUBTREE both the TYPE_MAIN_VARIANT
and TYPE_NEXT_VARIANT (which in turn required the compar_type_names_p
change).  With the extra hacks the whopr fails are down to a few
hundred (ugh).

Does anyone remember why we have to hack around the TYPE_MAIN/NEXT_VARIANT
stuff (we do so in free-lang-data, but new next-variants are introduced
before streaming out again during ltrans - it's not enough to stream
out NULLs here either)?

I will probably try (just because I am a masochist) to properly
deal with this variant list and not fix them up during free-lang-data
(which should hopefully uncover the problems with -flto as well).

But - I guess you guys tried that already?

Anyway, the following patch bootstraps ok and tests with zero extra
-flto fails.  It fixes bootstrap with -flto on i?86 for me, building
all of stage3 fine.

Thanks,
Richard.

2009-08-15  Richard Guenther  <rguenther@suse.de>

	PR lto/41071
	* gimple.c (compare_type_names_p): Do not look at the
	types main variant.
	(gimple_register_type): Always register the main variant first.
	(gimple_get_alias_set): Pointers to CV qualified variants
	have the same alias-set as unqualified variants.

	lto/
	* lto.c (lto_fixup_type): Register and replace the types
	main variant, zero its next variant.

Index: gcc/gimple.c
===================================================================
*** gcc/gimple.c.orig	2009-08-15 15:25:24.000000000 +0200
--- gcc/gimple.c	2009-08-15 16:36:36.000000000 +0200
*************** lookup_type_pair (tree t1, tree t2, htab
*** 3185,3192 ****
  static bool
  compare_type_names_p (tree t1, tree t2)
  {
-   tree variant1 = TYPE_MAIN_VARIANT (t1);
-   tree variant2 = TYPE_MAIN_VARIANT (t2);
    tree name1 = TYPE_NAME (t1);
    tree name2 = TYPE_NAME (t2);
  
--- 3185,3190 ----
*************** compare_type_names_p (tree t1, tree t2)
*** 3215,3228 ****
    if (name1 == name2)
      return true;
  
-   /* If either type has a variant type, compare that.  This finds
-      the case where a struct is typedef'ed in one module but referred
-      to as 'struct foo' in the other; here, the main type for one is
-      'foo', and for the other 'foo_t', but the variants have the same
-      name 'foo'.  */
-   if (variant1 != t1 || variant2 != t2)
-     return compare_type_names_p (variant1, variant2);
- 
    return false;
  }
  
--- 3213,3218 ----
*************** gimple_register_type (tree t)
*** 3907,3912 ****
--- 3897,3907 ----
        print_generic_stmt (stderr, t, 0);
      }
  
+   /* Always register the main variant first.  It is the one we want to
+      canonicalize to - otherwise that somehow breaks whopr.  */
+   if (TYPE_MAIN_VARIANT (t) != t)
+     gimple_register_type (TYPE_MAIN_VARIANT (t));
+ 
    slot = htab_find_slot (gimple_types, t, INSERT);
    if (*slot)
      {
*************** gimple_get_alias_set (tree t)
*** 4183,4188 ****
--- 4178,4213 ----
        if (t1 != t)
  	return get_alias_set (t1);
      }
+   else if (POINTER_TYPE_P (t))
+     {
+       tree t1;
+ 
+       /* Unfortunately, there is no canonical form of a pointer type.
+ 	 In particular, if we have `typedef int I', then `int *', and
+ 	 `I *' are different types.  So, we have to pick a canonical
+ 	 representative.  We do this below.
+ 
+ 	 Technically, this approach is actually more conservative that
+ 	 it needs to be.  In particular, `const int *' and `int *'
+ 	 should be in different alias sets, according to the C and C++
+ 	 standard, since their types are not the same, and so,
+ 	 technically, an `int **' and `const int **' cannot point at
+ 	 the same thing.
+ 
+ 	 But, the standard is wrong.  In particular, this code is
+ 	 legal C++:
+ 
+ 	 int *ip;
+ 	 int **ipp = &ip;
+ 	 const int* const* cipp = ipp;
+ 	 And, it doesn't make sense for that to be legal unless you
+ 	 can dereference IPP and CIPP.  So, we ignore cv-qualifiers on
+ 	 the pointed-to types.  This issue has been reported to the
+ 	 C++ committee.  */
+       t1 = build_type_no_quals (t);
+       if (t1 != t)
+ 	return get_alias_set (t1);
+     }
  
    return -1;
  }
Index: gcc/lto/lto.c
===================================================================
*** gcc/lto/lto.c.orig	2009-08-15 15:25:13.000000000 +0200
--- gcc/lto/lto.c	2009-08-15 16:35:28.000000000 +0200
*************** lto_fixup_type (tree t, void *data)
*** 1215,1222 ****
    LTO_FIXUP_SUBTREE (t->type.minval);
    LTO_FIXUP_SUBTREE (t->type.maxval);
  
!   LTO_FIXUP_SUBTREE (TYPE_NEXT_VARIANT (t));
!   LTO_FIXUP_SUBTREE (TYPE_MAIN_VARIANT (t));
  
    /* Accessor is for derived node types only. */
    LTO_FIXUP_SUBTREE (t->type.binfo);
--- 1215,1223 ----
    LTO_FIXUP_SUBTREE (t->type.minval);
    LTO_FIXUP_SUBTREE (t->type.maxval);
  
!   LTO_REGISTER_TYPE_AND_FIXUP_SUBTREE (TYPE_MAIN_VARIANT (t));
!   /* FIXME lto.  We are not good in preserving the list of variant types.  */
!   TYPE_NEXT_VARIANT (t) = NULL_TREE;
  
    /* Accessor is for derived node types only. */
    LTO_FIXUP_SUBTREE (t->type.binfo);


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]