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]

Re: Calculate TYPE_CANONICAL only for types that can be accessed in memory


> Now we have it spelled out 4 times ... makes sense to create a new
> macro for it?  (though I cannot think of a good name...
> UNACCESSIBLE_TYPE_P ()?)

Yep, actually I already made that version of patch yesterday but then got
hooked by beers.  This is better version (also with more sensible comments).
I will commit it at afternoon if you have no further comments.


	* lto.c (hash_canonical_type): Be sure we hash only types that
	need alias set.
	(gimple_register_canonical_type_1): Do not produce canonical
	types for types that do not need alias sets.
	* tree.c (gimple_canonical_types_compatible_p): Sanity check that
	we do not try to compute canonical type for type that does not need
	alias set.
	(verify_type): Drop FIXME for METHOD_TYPE, update FIXME for
	FUNCITON_TYPE.
	* tree.h (type_with_alias_set_p): New.
Index: lto/lto.c
===================================================================
--- lto/lto.c	(revision 223508)
+++ lto/lto.c	(working copy)
@@ -309,6 +309,12 @@ hash_canonical_type (tree type)
 {
   inchash::hash hstate;
 
+  /* We compute alias sets only for types that needs them.
+     Be sure we do not recurse to something else as we can not hash incomplete
+     types in a way they would have same hash value as compatible complete
+     types.  */
+  gcc_checking_assert (type_with_alias_set_p (type));
+
   /* Combine a few common features of types so that types are grouped into
      smaller sets; when searching for existing matching types to merge,
      only existing types having the same features as the new type will be
@@ -493,7 +495,7 @@ gimple_register_canonical_type_1 (tree t
 static void
 gimple_register_canonical_type (tree t)
 {
-  if (TYPE_CANONICAL (t))
+  if (TYPE_CANONICAL (t) || !type_with_alias_set_p (t))
     return;
 
   gimple_register_canonical_type_1 (t, hash_canonical_type (t));
Index: tree.c
===================================================================
--- tree.c	(revision 223508)
+++ tree.c	(working copy)
@@ -12720,6 +12720,23 @@ gimple_canonical_types_compatible_p (con
   if (t1 == NULL_TREE || t2 == NULL_TREE)
     return false;
 
+  /* We consider complete types always compatible with incomplete type.
+     This does not make sense for canonical type calculation and thus we
+     need to ensure that we are never called on it.
+
+     FIXME: For more correctness the function probably should have three modes
+	1) mode assuming that types are complete mathcing their structure
+	2) mode allowing incomplete types but producing equivalence classes
+	   and thus ignoring all info from complete types
+	3) mode allowing incomplete types to match complete but checking
+	   compatibility between complete types.
+
+     1 and 2 can be used for canonical type calculation. 3 is the real
+     definition of type compatibility that can be used i.e. for warnings during
+     declaration merging.  */
+
+  gcc_assert (!trust_type_canonical
+	      || (type_with_alias_set_p (t1) && type_with_alias_set_p (t2)));
   /* If the types have been previously registered and found equal
      they still are.  */
   if (TYPE_CANONICAL (t1) && TYPE_CANONICAL (t2)
@@ -12939,10 +12953,9 @@ verify_type (const_tree t)
   /* Method and function types can not be used to address memory and thus
      TYPE_CANONICAL really matters only for determining useless conversions.
 
-     FIXME: C++ FE does not agree with gimple_canonical_types_compatible_p
-     here.  gimple_canonical_types_compatible_p calls comp_type_attributes
-     while for C++ FE the attributes does not make difference.  */
-  else if (TREE_CODE (t) == FUNCTION_TYPE || TREE_CODE (t) == METHOD_TYPE)
+     FIXME: C++ FE produce declarations of builtin functions that are not
+     compatible with main variants.  */
+  else if (TREE_CODE (t) == FUNCTION_TYPE)
     ;
   else if (t != ct
 	   /* FIXME: gimple_canonical_types_compatible_p can not compare types
Index: tree.h
===================================================================
--- tree.h	(revision 223508)
+++ tree.h	(working copy)
@@ -5090,6 +5090,26 @@ int_bit_position (const_tree field)
 	  + wi::to_offset (DECL_FIELD_BIT_OFFSET (field))).to_shwi ();
 }
 
+/* Return true if it makes sense to consider alias set for a type T.  */
+
+inline bool
+type_with_alias_set_p (const_tree t)
+{
+  /* Function and method types are never accessed as memory locations.  */
+  if (TREE_CODE (t) == FUNCTION_TYPE || TREE_CODE (t) == METHOD_TYPE)
+    return false;
+
+  if (COMPLETE_TYPE_P (t))
+    return true;
+
+  /* Incomplete types can not be accessed in general except for arrays
+     where we can fetch its element despite we have no array bounds.  */
+  if (TREE_CODE (t) == ARRAY_TYPE && COMPLETE_TYPE_P (TREE_TYPE (t)))
+    return true;
+
+  return false;
+}
+
 extern void gt_ggc_mx (tree &);
 extern void gt_pch_nx (tree &);
 extern void gt_pch_nx (tree &, gt_pointer_operator, void *);


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