Patchwork Fix gnat.dg/aliasing2.adb regression

login
register
mail settings
Submitter Eric Botcazou
Date Nov. 29, 2010, 7:27 p.m.
Message ID <201011292027.49783.ebotcazou@adacore.com>
Download mbox | patch
Permalink /patch/73484/
State New
Headers show

Comments

Eric Botcazou - Nov. 29, 2010, 7:27 p.m.
> Sooo - can you check sth along the above instead?

OK, I acted boldly and tested the complete change. :-)  Bootstrapped/regtested 
and LTO-bootstrapped (for C/Ada) on x86_64-suse-linux, OK for mainline?


2010-11-29  Eric Botcazou  <ebotcazou@adacore.com>

	* tree.c (build_range_type_1): Do not SET_TYPE_STRUCTURAL_EQUALITY.
	(build_array_type_1): Do not consider TYPE_STRUCTURAL_EQUALITY_P and
	TYPE_CANONICAL for the index type.
Eric Botcazou - Nov. 29, 2010, 8:24 p.m.
> OK, I acted boldly and tested the complete change. :-) 
> Bootstrapped/regtested and LTO-bootstrapped (for C/Ada) on
> x86_64-suse-linux, OK for mainline?

There was a new C++ failure among the existing ones:

eric@atlantis:~/build/gcc/native32> gcc/xgcc -Bgcc -S vla9.C
vla9.C: In function 'void f(double*, int)':
vla9.C:13:44: internal compiler error: canonical types differ for identical 
types double [(((unsigned int)(((int)ny) + -0x000000001)) + 1)] and double 
[(((unsigned int)(((int)ny) + -0x000000001)) + 1)]
Please submit a full bug report,
with preprocessed source if appropriate.
See <http://gcc.gnu.org/bugs.html> for instructions.

#ifdef ENABLE_CHECKING
      if (USE_CANONICAL_TYPES)
	{
	  bool result = structural_comptypes (t1, t2, strict);
	  
	  if (result && TYPE_CANONICAL (t1) != TYPE_CANONICAL (t2))
	    /* The two types are structurally equivalent, but their
	       canonical types were different. This is a failure of the
	       canonical type propagation code.*/
	    internal_error 
	      ("canonical types differ for identical types %T and %T", 
	       t1, t2);
	  else if (!result && TYPE_CANONICAL (t1) == TYPE_CANONICAL (t2))
	    /* Two types are structurally different, but the canonical
	       types are the same. This means we were over-eager in
	       assigning canonical types. */
	    internal_error 
	      ("same canonical type node for different types %T and %T",
	       t1, t2);
	  
	  return result;
	}
Richard Guenther - Nov. 30, 2010, 11 a.m.
On Mon, Nov 29, 2010 at 9:24 PM, Eric Botcazou <ebotcazou@adacore.com> wrote:
>> OK, I acted boldly and tested the complete change. :-)
>> Bootstrapped/regtested and LTO-bootstrapped (for C/Ada) on
>> x86_64-suse-linux, OK for mainline?
>
> There was a new C++ failure among the existing ones:
>
> eric@atlantis:~/build/gcc/native32> gcc/xgcc -Bgcc -S vla9.C
> vla9.C: In function 'void f(double*, int)':
> vla9.C:13:44: internal compiler error: canonical types differ for identical
> types double [(((unsigned int)(((int)ny) + -0x000000001)) + 1)] and double
> [(((unsigned int)(((int)ny) + -0x000000001)) + 1)]
> Please submit a full bug report,
> with preprocessed source if appropriate.
> See <http://gcc.gnu.org/bugs.html> for instructions.

Hm.  So it seems that the C++ frontend relies on
TYPE_STRUCTURAL_EQUALITY here (probably rightfully so at
least for templates and [] when looking at its comp_array_types).

Bah, looks like the patch is wrong then, unless we start unifying
non-INTEGER_CST range types by for example using
operand_equal_p for TYPE_MIN/MAX_VALUE in type_hash_eq.

But I guess that's nothing for stage3.

So your original patch is ok.

Thanks for trying,
Richard.

> #ifdef ENABLE_CHECKING
>      if (USE_CANONICAL_TYPES)
>        {
>          bool result = structural_comptypes (t1, t2, strict);
>
>          if (result && TYPE_CANONICAL (t1) != TYPE_CANONICAL (t2))
>            /* The two types are structurally equivalent, but their
>               canonical types were different. This is a failure of the
>               canonical type propagation code.*/
>            internal_error
>              ("canonical types differ for identical types %T and %T",
>               t1, t2);
>          else if (!result && TYPE_CANONICAL (t1) == TYPE_CANONICAL (t2))
>            /* Two types are structurally different, but the canonical
>               types are the same. This means we were over-eager in
>               assigning canonical types. */
>            internal_error
>              ("same canonical type node for different types %T and %T",
>               t1, t2);
>
>          return result;
>        }
>
> --
> Eric Botcazou
>

Patch

Index: tree.c
===================================================================
--- tree.c	(revision 167201)
+++ tree.c	(working copy)
@@ -7096,6 +7096,7 @@  static tree
 build_range_type_1 (tree type, tree lowval, tree highval, bool shared)
 {
   tree itype = make_node (INTEGER_TYPE);
+  hashval_t hashcode = 0;
 
   TREE_TYPE (itype) = type;
 
@@ -7109,24 +7110,17 @@  build_range_type_1 (tree type, tree lowv
   TYPE_ALIGN (itype) = TYPE_ALIGN (type);
   TYPE_USER_ALIGN (itype) = TYPE_USER_ALIGN (type);
 
-  if ((TYPE_MIN_VALUE (itype)
-       && TREE_CODE (TYPE_MIN_VALUE (itype)) != INTEGER_CST)
+  if (!shared
+      || (TYPE_MIN_VALUE (itype)
+	  && TREE_CODE (TYPE_MIN_VALUE (itype)) != INTEGER_CST)
       || (TYPE_MAX_VALUE (itype)
 	  && TREE_CODE (TYPE_MAX_VALUE (itype)) != INTEGER_CST))
-    {
-      /* Since we cannot reliably merge this type, we need to compare it using
-	 structural equality checks.  */
-      SET_TYPE_STRUCTURAL_EQUALITY (itype);
-      return itype;
-    }
+    return itype;
 
-  if (shared)
-    {
-      hashval_t hash = iterative_hash_expr (TYPE_MIN_VALUE (itype), 0);
-      hash = iterative_hash_expr (TYPE_MAX_VALUE (itype), hash);
-      hash = iterative_hash_hashval_t (TYPE_HASH (type), hash);
-      itype = type_hash_canon (hash, itype);
-    }
+  hashcode = iterative_hash_expr (TYPE_MIN_VALUE (itype), hashcode);
+  hashcode = iterative_hash_expr (TYPE_MAX_VALUE (itype), hashcode);
+  hashcode = iterative_hash_hashval_t (TYPE_HASH (type), hashcode);
+  itype = type_hash_canon (hashcode, itype);
 
   return itype;
 }
@@ -7250,16 +7244,11 @@  build_array_type_1 (tree elt_type, tree
 
   if (TYPE_CANONICAL (t) == t)
     {
-      if (TYPE_STRUCTURAL_EQUALITY_P (elt_type)
-	  || (index_type && TYPE_STRUCTURAL_EQUALITY_P (index_type)))
+      if (TYPE_STRUCTURAL_EQUALITY_P (elt_type))
 	SET_TYPE_STRUCTURAL_EQUALITY (t);
-      else if (TYPE_CANONICAL (elt_type) != elt_type
-	       || (index_type && TYPE_CANONICAL (index_type) != index_type))
+      else if (TYPE_CANONICAL (elt_type) != elt_type)
 	TYPE_CANONICAL (t)
-	  = build_array_type_1 (TYPE_CANONICAL (elt_type),
-				index_type
-				? TYPE_CANONICAL (index_type) : NULL_TREE,
-				shared);
+	  = build_array_type_1 (TYPE_CANONICAL (elt_type), index_type, shared);
     }
 
   return t;