[PATCH] Emit DWARF5 DW_AT_reference and DW_AT_rvalue_reference

Jason Merrill jason@redhat.com
Tue Nov 1 18:44:00 GMT 2016


On Tue, Nov 1, 2016 at 2:04 PM, Jason Merrill <jason@redhat.com> wrote:
> On Tue, Nov 1, 2016 at 9:56 AM, Jakub Jelinek <jakub@redhat.com> wrote:
>> On Mon, Oct 31, 2016 at 09:56:28AM -0400, Jason Merrill wrote:
>>> >Or by changing get_qualified_die (in particular check_base_type) to use a
>>> >langhook, we could at least for DW_AT_{reference,rvalue_reference} just use
>>> >equate_type_number_to_die/lookup_type_die reliably (DW_AT_endianity issue
>>> >remains).
>>>
>>> Yeah, I think that adding a langhook is the right way to go.  The generic
>>> code clobbering C++ qualifiers is a frequent headache.
>>
>> I've tried to implement that, but am getting some TYPE_CANONICAL differences
>> because of that, and am really lost what the problem is and how to fix it.
>> Furthermore, I bet the exception specification also should be considered in
>> that langhook.
>
> Yes.  I'll take a look.

This patch on top of yours passes regtest and seems to DTRT with your
testcase on brief inspection.
-------------- next part --------------
commit d11a8a96689cc81c71fc48b16653aff2227b6fff
Author: Jason Merrill <jason@redhat.com>
Date:   Tue Nov 1 14:13:00 2016 -0400

    fix

diff --git a/gcc/cp/cp-objcp-common.h b/gcc/cp/cp-objcp-common.h
index 986821d..0ef7e1e 100644
--- a/gcc/cp/cp-objcp-common.h
+++ b/gcc/cp/cp-objcp-common.h
@@ -135,8 +135,6 @@ extern void cp_common_init_ts (void);
 #define LANG_HOOKS_DECL_DWARF_ATTRIBUTE cp_decl_dwarf_attribute
 #undef LANG_HOOKS_TYPE_DWARF_ATTRIBUTE
 #define LANG_HOOKS_TYPE_DWARF_ATTRIBUTE cp_type_dwarf_attribute
-#undef LANG_HOOKS_CHECK_BASE_TYPE
-#define LANG_HOOKS_CHECK_BASE_TYPE cp_check_base_type
 #undef LANG_HOOKS_OMP_PREDETERMINED_SHARING
 #define LANG_HOOKS_OMP_PREDETERMINED_SHARING cxx_omp_predetermined_sharing
 #undef LANG_HOOKS_OMP_CLAUSE_DEFAULT_CTOR
diff --git a/gcc/cp/tree.c b/gcc/cp/tree.c
index ac15d67..4dc6e22 100644
--- a/gcc/cp/tree.c
+++ b/gcc/cp/tree.c
@@ -1980,7 +1980,8 @@ static bool
 cp_check_qualified_type (const_tree cand, const_tree base, int type_quals,
 			 cp_ref_qualifier rqual, tree raises)
 {
-  return (check_qualified_type (cand, base, type_quals)
+  return (TYPE_QUALS (cand) == type_quals
+	  && check_base_type (cand, base)
 	  && comp_except_specs (raises, TYPE_RAISES_EXCEPTIONS (cand),
 				ce_exact)
 	  && type_memfn_rqual (cand) == rqual);
@@ -4080,9 +4081,7 @@ cp_build_type_attribute_variant (tree type, tree attributes)
 }
 
 /* Return TRUE if TYPE1 and TYPE2 are identical for type hashing purposes.
-   Called only after doing all language independent checks.  Only
-   to check TYPE_RAISES_EXCEPTIONS for FUNCTION_TYPE, the rest is already
-   compared in type_hash_eq.  */
+   Called only after doing all language independent checks.  */
 
 bool
 cxx_type_hash_eq (const_tree typea, const_tree typeb)
@@ -4090,6 +4089,8 @@ cxx_type_hash_eq (const_tree typea, const_tree typeb)
   gcc_assert (TREE_CODE (typea) == FUNCTION_TYPE
 	      || TREE_CODE (typea) == METHOD_TYPE);
 
+  if (type_memfn_rqual (typea) != type_memfn_rqual (typeb))
+    return false;
   return comp_except_specs (TYPE_RAISES_EXCEPTIONS (typea),
 			    TYPE_RAISES_EXCEPTIONS (typeb), ce_exact);
 }
diff --git a/gcc/dwarf2out.c b/gcc/dwarf2out.c
index c823fdb..21b5380 100644
--- a/gcc/dwarf2out.c
+++ b/gcc/dwarf2out.c
@@ -12336,12 +12336,14 @@ modified_type_die (tree type, int cv_quals, bool reverse,
       if (TREE_CODE (type) == FUNCTION_TYPE
 	  || TREE_CODE (type) == METHOD_TYPE)
 	{
-	  /* For function/method types, can't use type_main_variant here,
+	  /* For function/method types, can't just use type_main_variant here,
 	     because that can have different ref-qualifiers for C++,
 	     but try to canonicalize.  */
-	  for (tree t = TYPE_MAIN_VARIANT (type); t; t = TYPE_NEXT_VARIANT (t))
-	    if (check_qualified_type (t, type, TYPE_QUALS (type)))
-	      type = t;
+	  tree main = TYPE_MAIN_VARIANT (type);
+	  for (tree t = main; t; t = TYPE_NEXT_VARIANT (t))
+	    if (check_base_type (t, main)
+		&& check_lang_type (t, type))
+	      return lookup_type_die (t);
 	  return lookup_type_die (type);
 	}
       else if (TREE_CODE (type) != VECTOR_TYPE
diff --git a/gcc/hooks.c b/gcc/hooks.c
index 24f6c99..3995786 100644
--- a/gcc/hooks.c
+++ b/gcc/hooks.c
@@ -293,12 +293,6 @@ hook_bool_tree_tree_true (tree, tree)
 }
 
 bool
-hook_bool_const_tree_const_tree_true (const_tree, const_tree)
-{
-  return true;
-}
-
-bool
 hook_bool_tree_bool_false (tree, bool)
 {
   return false;
diff --git a/gcc/hooks.h b/gcc/hooks.h
index 7965603..a1d6776 100644
--- a/gcc/hooks.h
+++ b/gcc/hooks.h
@@ -59,7 +59,6 @@ extern bool hook_bool_rtx_mode_int_int_intp_bool_false (rtx, machine_mode,
 							int, int, int *, bool);
 extern bool hook_bool_tree_tree_false (tree, tree);
 extern bool hook_bool_tree_tree_true (tree, tree);
-extern bool hook_bool_const_tree_const_tree_true (const_tree, const_tree);
 extern bool hook_bool_tree_bool_false (tree, bool);
 extern bool hook_bool_wint_wint_uint_bool_true (const widest_int &,
 						const widest_int &,
diff --git a/gcc/langhooks-def.h b/gcc/langhooks-def.h
index bb7b97a..5c330f0 100644
--- a/gcc/langhooks-def.h
+++ b/gcc/langhooks-def.h
@@ -188,7 +188,6 @@ extern tree lhd_make_node (enum tree_code);
 #define LANG_HOOKS_GET_DEBUG_TYPE	NULL
 #define LANG_HOOKS_GET_FIXED_POINT_TYPE_INFO NULL
 #define LANG_HOOKS_TYPE_DWARF_ATTRIBUTE	lhd_type_dwarf_attribute
-#define LANG_HOOKS_CHECK_BASE_TYPE	hook_bool_const_tree_const_tree_true
 
 #define LANG_HOOKS_FOR_TYPES_INITIALIZER { \
   LANG_HOOKS_MAKE_TYPE, \
@@ -212,8 +211,7 @@ extern tree lhd_make_node (enum tree_code);
   LANG_HOOKS_ENUM_UNDERLYING_BASE_TYPE, \
   LANG_HOOKS_GET_DEBUG_TYPE, \
   LANG_HOOKS_GET_FIXED_POINT_TYPE_INFO, \
-  LANG_HOOKS_TYPE_DWARF_ATTRIBUTE, \
-  LANG_HOOKS_CHECK_BASE_TYPE \
+  LANG_HOOKS_TYPE_DWARF_ATTRIBUTE \
 }
 
 /* Declaration hooks.  */
diff --git a/gcc/langhooks.h b/gcc/langhooks.h
index c8bbd24..150227c 100644
--- a/gcc/langhooks.h
+++ b/gcc/langhooks.h
@@ -120,7 +120,7 @@ struct lang_hooks_for_types
   /* Return TRUE if TYPE1 and TYPE2 are identical for type hashing purposes.
      Called only after doing all language independent checks.
      At present, this function is only called when both TYPE1 and TYPE2 are
-     FUNCTION_TYPEs.  */
+     FUNCTION_TYPE or METHOD_TYPE.  */
   bool (*type_hash_eq) (const_tree, const_tree);
 
   /* Return TRUE if TYPE uses a hidden descriptor and fills in information
@@ -166,10 +166,6 @@ struct lang_hooks_for_types
   /* Returns -1 if dwarf ATTR shouldn't be added for TYPE, or the attribute
      value otherwise.  */
   int (*type_dwarf_attribute) (const_tree, int);
-
-  /* Return TRUE iff unqualified CAND and BASE types are equivalent for
-     check_qualified_type purposes.  */
-  bool (*check_base_type) (const_tree, const_tree);
 };
 
 /* Language hooks related to decls and the symbol table.  */
diff --git a/gcc/tree.c b/gcc/tree.c
index 825376c..434aff1 100644
--- a/gcc/tree.c
+++ b/gcc/tree.c
@@ -6497,6 +6497,21 @@ set_type_quals (tree type, int type_quals)
   TYPE_ADDR_SPACE (type) = DECODE_QUAL_ADDR_SPACE (type_quals);
 }
 
+/* Returns true iff CAND and BASE have equivalent language-specific
+   qualifiers.  */
+
+bool
+check_lang_type (const_tree cand, const_tree base)
+{
+  if (lang_hooks.types.type_hash_eq == NULL)
+    return true;
+  /* type_hash_eq currently only applies to these types.  */
+  if (TREE_CODE (cand) != FUNCTION_TYPE
+      && TREE_CODE (cand) != METHOD_TYPE)
+    return true;
+  return lang_hooks.types.type_hash_eq (cand, base);
+}
+
 /* Returns true iff unqualified CAND and BASE are equivalent.  */
 
 bool
@@ -6507,7 +6522,6 @@ check_base_type (const_tree cand, const_tree base)
 	  && TYPE_CONTEXT (cand) == TYPE_CONTEXT (base)
 	  /* Check alignment.  */
 	  && TYPE_ALIGN (cand) == TYPE_ALIGN (base)
-	  && lang_hooks.types.check_base_type (cand, base)
 	  && attribute_list_equal (TYPE_ATTRIBUTES (cand),
 				   TYPE_ATTRIBUTES (base)));
 }
@@ -6518,7 +6532,8 @@ bool
 check_qualified_type (const_tree cand, const_tree base, int type_quals)
 {
   return (TYPE_QUALS (cand) == type_quals
-	  && check_base_type (cand, base));
+	  && check_base_type (cand, base)
+	  && check_lang_type (cand, base));
 }
 
 /* Returns true iff CAND is equivalent to BASE with ALIGN.  */
@@ -6533,7 +6548,8 @@ check_aligned_type (const_tree cand, const_tree base, unsigned int align)
 	  /* Check alignment.  */
 	  && TYPE_ALIGN (cand) == align
 	  && attribute_list_equal (TYPE_ATTRIBUTES (cand),
-				   TYPE_ATTRIBUTES (base)));
+				   TYPE_ATTRIBUTES (base))
+	  && check_lang_type (cand, base));
 }
 
 /* This function checks to see if TYPE matches the size one of the built-in 
diff --git a/gcc/tree.h b/gcc/tree.h
index c494f23..fb4f033 100644
--- a/gcc/tree.h
+++ b/gcc/tree.h
@@ -4210,6 +4210,11 @@ extern tree merge_dllimport_decl_attributes (tree, tree);
 /* Handle a "dllimport" or "dllexport" attribute.  */
 extern tree handle_dll_attribute (tree *, tree, tree, int, bool *);
 
+/* Returns true iff CAND and BASE have equivalent language-specific
+   qualifiers.  */
+
+extern bool check_lang_type (const_tree cand, const_tree base);
+
 /* Returns true iff unqualified CAND and BASE are equivalent.  */
 
 extern bool check_base_type (const_tree cand, const_tree base);


More information about the Gcc-patches mailing list