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]

[C++ PATCH] move class lookup fns


this patch moves the direct class member lookup functions from search.c to name-lookup.c. I'll be morphing them into a saner data representation.

These are the functions that look only in a specified class. The hierarchy searching functions remain in search.c

This is a direct transplant with no change of functionality, so that future diffs don't have extraneous churn.

Applied to trunk.

nathan
--
Nathan Sidwell
2017-08-23  Nathan Sidwell  <nathan@acm.org>

	* cp-tree.h (lookup_field_1, lookup_fnfields_slot,
	lookup_fnfields_slot_nolazy, lookup_all_conversions): Move
	declatations to ...
	* name-lookup.h (lookup_field_1, lookup_fnfields_slot,
	lookup_fnfields_slot_nolazy, lookup_all_conversions): ... here.
	* search.c (lookup_conversion_operator,
	lookup_fnfields_slot_nolazy, lookup_field_1, lookup_fnfields_slot,
	lookup_all_conversions): Move to ...
	* name-lookup.c (lookup_conversion_operator,
	lookup_fnfields_slot_nolazy, lookup_field_1, lookup_fnfields_slot,
	lookup_all_conversions): ... here.

Index: cp-tree.h
===================================================================
--- cp-tree.h	(revision 251316)
+++ cp-tree.h	(working copy)
@@ -6563,11 +6563,7 @@ extern tree lookup_base
 extern tree dcast_base_hint			(tree, tree);
 extern int accessible_p				(tree, tree, bool);
 extern int accessible_in_template_p		(tree, tree);
-extern tree lookup_field_1			(tree, tree, bool);
 extern tree lookup_field			(tree, tree, int, bool);
-extern tree lookup_fnfields_slot		(tree, tree);
-extern tree lookup_fnfields_slot_nolazy		(tree, tree);
-extern tree lookup_all_conversions		(tree);
 extern tree lookup_fnfields			(tree, tree, int);
 extern tree lookup_member			(tree, tree, int, bool,
 						 tsubst_flags_t,
Index: name-lookup.c
===================================================================
--- name-lookup.c	(revision 251313)
+++ name-lookup.c	(working copy)
@@ -1089,6 +1089,258 @@ lookup_arg_dependent (tree name, tree fn
   return fns;
 }
 
+/* Return the conversion operators in CLASS_TYPE corresponding to
+   "operator TYPE ()".  Only CLASS_TYPE itself is searched; this
+   routine does not scan the base classes of CLASS_TYPE.  */
+
+static tree
+lookup_conversion_operator (tree class_type, tree type)
+{
+  tree tpls = NULL_TREE;
+
+  if (TYPE_HAS_CONVERSION (class_type))
+    {
+      tree fns;
+      vec<tree, va_gc> *methods = CLASSTYPE_METHOD_VEC (class_type);
+
+      for (int i = CLASSTYPE_FIRST_CONVERSION_SLOT;
+	   vec_safe_iterate (methods, i, &fns); ++i)
+	{
+	  /* All the conversion operators come near the beginning of
+	     the class.  Therefore, if FN is not a conversion
+	     operator, there is no matching conversion operator in
+	     CLASS_TYPE.  */
+	  tree fn = OVL_FIRST (fns);
+	  if (!DECL_CONV_FN_P (fn))
+	    break;
+
+	  if (TREE_CODE (fn) == TEMPLATE_DECL)
+	    /* All the templated conversion functions are on the same
+	       slot, so remember it.  */
+	    tpls = fns;
+	  else if (same_type_p (DECL_CONV_FN_TYPE (fn), type))
+	    return fns;
+	}
+    }
+
+  return tpls;
+}
+
+/* TYPE is a class type. Return the member functions in the method
+   vector with name NAME.  Does not lazily declare implicitly-declared
+   member functions.  */
+
+tree
+lookup_fnfields_slot_nolazy (tree type, tree name)
+{
+  vec<tree, va_gc> *method_vec = CLASSTYPE_METHOD_VEC (type);
+  if (!method_vec)
+    return NULL_TREE;
+
+  if (IDENTIFIER_CONV_OP_P (name))
+    return lookup_conversion_operator (type, TREE_TYPE (name));
+
+  /* Skip the conversion operators.  */
+  int i;
+  tree fns;
+  for (i = CLASSTYPE_FIRST_CONVERSION_SLOT;
+       vec_safe_iterate (method_vec, i, &fns);
+       ++i)
+    if (!DECL_CONV_FN_P (OVL_FIRST (fns)))
+      break;
+
+  /* If the type is complete, use binary search.  */
+  if (COMPLETE_TYPE_P (type))
+    {
+      int lo;
+      int hi;
+
+      lo = i;
+      hi = method_vec->length ();
+      while (lo < hi)
+	{
+	  i = (lo + hi) / 2;
+
+	  fns = (*method_vec)[i];
+	  tree fn_name = OVL_NAME (fns);
+	  if (fn_name > name)
+	    hi = i;
+	  else if (fn_name < name)
+	    lo = i + 1;
+	  else
+	    return fns;
+	}
+    }
+  else
+    for (; vec_safe_iterate (method_vec, i, &fns); ++i)
+      {
+	if (OVL_NAME (fns) == name)
+	  return fns;
+      }
+
+  return NULL_TREE;
+}
+
+/* Do a 1-level search for NAME as a member of TYPE.  The caller must
+   figure out whether it can access this field.  (Since it is only one
+   level, this is reasonable.)  */
+
+tree
+lookup_field_1 (tree type, tree name, bool want_type)
+{
+  tree field;
+
+  gcc_assert (identifier_p (name) && RECORD_OR_UNION_TYPE_P (type));
+
+  if (CLASSTYPE_SORTED_FIELDS (type))
+    {
+      tree *fields = &CLASSTYPE_SORTED_FIELDS (type)->elts[0];
+      int lo = 0, hi = CLASSTYPE_SORTED_FIELDS (type)->len;
+      int i;
+
+      while (lo < hi)
+	{
+	  i = (lo + hi) / 2;
+
+	  if (DECL_NAME (fields[i]) > name)
+	    hi = i;
+	  else if (DECL_NAME (fields[i]) < name)
+	    lo = i + 1;
+	  else
+	    {
+	      field = NULL_TREE;
+
+	      /* We might have a nested class and a field with the
+		 same name; we sorted them appropriately via
+		 field_decl_cmp, so just look for the first or last
+		 field with this name.  */
+	      if (want_type)
+		{
+		  do
+		    field = fields[i--];
+		  while (i >= lo && DECL_NAME (fields[i]) == name);
+		  if (!DECL_DECLARES_TYPE_P (field))
+		    field = NULL_TREE;
+		}
+	      else
+		{
+		  do
+		    field = fields[i++];
+		  while (i < hi && DECL_NAME (fields[i]) == name);
+		}
+
+	      if (field)
+	      	{
+	      	  field = strip_using_decl (field);
+	      	  if (is_overloaded_fn (field))
+	      	    field = NULL_TREE;
+	      	}
+
+	      return field;
+	    }
+	}
+      return NULL_TREE;
+    }
+
+  field = TYPE_FIELDS (type);
+
+  for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
+    {
+      tree decl = field;
+
+      if (DECL_DECLARES_FUNCTION_P (decl))
+	/* Functions are kep separately, at the moment.  */
+	continue;
+
+      gcc_assert (DECL_P (field));
+      if (DECL_NAME (field) == NULL_TREE
+	  && ANON_AGGR_TYPE_P (TREE_TYPE (field)))
+	{
+	  tree temp = lookup_field_1 (TREE_TYPE (field), name, want_type);
+	  if (temp)
+	    return temp;
+	}
+
+      if (TREE_CODE (decl) == USING_DECL
+	  && DECL_NAME (decl) == name)
+	{
+	  decl = strip_using_decl (decl);
+	  if (is_overloaded_fn (decl))
+	    continue;
+	}
+
+      if (DECL_NAME (decl) == name
+	  && (!want_type || DECL_DECLARES_TYPE_P (decl)))
+	return decl;
+    }
+
+  /* We used to special-case vptr_identifier.  Make sure it's not
+     special any more.  */
+  gcc_assert (name != vptr_identifier || !TYPE_VFIELD (type));
+
+  return NULL_TREE;
+}
+
+/* TYPE is a class type. Return the overloads in
+   the method vector with name NAME.  Lazily create ctors etc.  */
+
+tree
+lookup_fnfields_slot (tree type, tree name)
+{
+  type = complete_type (type);
+
+  if (COMPLETE_TYPE_P (type))
+    {
+      if (IDENTIFIER_CTOR_P (name))
+	{
+	  if (CLASSTYPE_LAZY_DEFAULT_CTOR (type))
+	    lazily_declare_fn (sfk_constructor, type);
+	  if (CLASSTYPE_LAZY_COPY_CTOR (type))
+	    lazily_declare_fn (sfk_copy_constructor, type);
+	  if (CLASSTYPE_LAZY_MOVE_CTOR (type))
+	    lazily_declare_fn (sfk_move_constructor, type);
+	}
+      else if (name == cp_assignment_operator_id (NOP_EXPR))
+	{
+	  if (CLASSTYPE_LAZY_COPY_ASSIGN (type))
+	    lazily_declare_fn (sfk_copy_assignment, type);
+	  if (CLASSTYPE_LAZY_MOVE_ASSIGN (type))
+	    lazily_declare_fn (sfk_move_assignment, type);
+	}
+      else if (IDENTIFIER_DTOR_P (name))
+	{
+	  if (CLASSTYPE_LAZY_DESTRUCTOR (type))
+	    lazily_declare_fn (sfk_destructor, type);
+	}
+    }
+
+  return lookup_fnfields_slot_nolazy (type, name);
+}
+
+/* Collect all the conversion operators of KLASS.  */
+
+tree
+lookup_all_conversions (tree klass)
+{
+  tree lkp = NULL_TREE;
+
+  if (vec<tree, va_gc> *methods = CLASSTYPE_METHOD_VEC (klass))
+    {
+      tree ovl;
+      for (int idx = CLASSTYPE_FIRST_CONVERSION_SLOT;
+	   methods->iterate (idx, &ovl); ++idx)
+	{
+	  if (!DECL_CONV_FN_P (OVL_FIRST (ovl)))
+	    /* There are no more conversion functions.  */
+	    break;
+
+	  lkp = lookup_add (ovl, lkp);
+	}
+    }
+
+  return lkp;
+}
+
 /* Compute the chain index of a binding_entry given the HASH value of its
    name and the total COUNT of chains.  COUNT is assumed to be a power
    of 2.  */
@@ -3319,7 +3571,7 @@ do_pushdecl_with_scope (tree x, cp_bindi
   current_function_decl = function_decl;
   return x;
 }
- 
+
 /* Inject X into the local scope just before the function parms.  */
 
 tree
Index: name-lookup.h
===================================================================
--- name-lookup.h	(revision 251313)
+++ name-lookup.h	(working copy)
@@ -319,6 +319,10 @@ extern void pop_decl_namespace (void);
 extern void do_namespace_alias (tree, tree);
 extern tree do_class_using_decl (tree, tree);
 extern tree lookup_arg_dependent (tree, tree, vec<tree, va_gc> *);
+extern tree lookup_field_1			(tree, tree, bool);
+extern tree lookup_fnfields_slot		(tree, tree);
+extern tree lookup_fnfields_slot_nolazy		(tree, tree);
+extern tree lookup_all_conversions		(tree);
 extern tree innermost_non_namespace_value (tree);
 extern cxx_binding *outer_binding (tree, cxx_binding *, bool);
 extern void cp_emit_debug_info_for_using (tree, tree);
Index: search.c
===================================================================
--- search.c	(revision 251315)
+++ search.c	(working copy)
@@ -353,106 +353,6 @@ dcast_base_hint (tree subtype, tree targ
    Otherwise, return a DECL with the indicated name.  If WANT_TYPE is
    true, type declarations are preferred.  */
 
-/* Do a 1-level search for NAME as a member of TYPE.  The caller must
-   figure out whether it can access this field.  (Since it is only one
-   level, this is reasonable.)  */
-
-tree
-lookup_field_1 (tree type, tree name, bool want_type)
-{
-  tree field;
-
-  gcc_assert (identifier_p (name) && RECORD_OR_UNION_TYPE_P (type));
-
-  if (CLASSTYPE_SORTED_FIELDS (type))
-    {
-      tree *fields = &CLASSTYPE_SORTED_FIELDS (type)->elts[0];
-      int lo = 0, hi = CLASSTYPE_SORTED_FIELDS (type)->len;
-      int i;
-
-      while (lo < hi)
-	{
-	  i = (lo + hi) / 2;
-
-	  if (DECL_NAME (fields[i]) > name)
-	    hi = i;
-	  else if (DECL_NAME (fields[i]) < name)
-	    lo = i + 1;
-	  else
-	    {
-	      field = NULL_TREE;
-
-	      /* We might have a nested class and a field with the
-		 same name; we sorted them appropriately via
-		 field_decl_cmp, so just look for the first or last
-		 field with this name.  */
-	      if (want_type)
-		{
-		  do
-		    field = fields[i--];
-		  while (i >= lo && DECL_NAME (fields[i]) == name);
-		  if (!DECL_DECLARES_TYPE_P (field))
-		    field = NULL_TREE;
-		}
-	      else
-		{
-		  do
-		    field = fields[i++];
-		  while (i < hi && DECL_NAME (fields[i]) == name);
-		}
-
-	      if (field)
-	      	{
-	      	  field = strip_using_decl (field);
-	      	  if (is_overloaded_fn (field))
-	      	    field = NULL_TREE;
-	      	}
-
-	      return field;
-	    }
-	}
-      return NULL_TREE;
-    }
-
-  field = TYPE_FIELDS (type);
-
-  for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
-    {
-      tree decl = field;
-
-      if (DECL_DECLARES_FUNCTION_P (decl))
-	/* Functions are kep separately, at the moment.  */
-	continue;
-
-      gcc_assert (DECL_P (field));
-      if (DECL_NAME (field) == NULL_TREE
-	  && ANON_AGGR_TYPE_P (TREE_TYPE (field)))
-	{
-	  tree temp = lookup_field_1 (TREE_TYPE (field), name, want_type);
-	  if (temp)
-	    return temp;
-	}
-
-      if (TREE_CODE (decl) == USING_DECL
-	  && DECL_NAME (decl) == name)
-	{
-	  decl = strip_using_decl (decl);
-	  if (is_overloaded_fn (decl))
-	    continue;
-	}
-
-      if (DECL_NAME (decl) == name
-	  && (!want_type || DECL_DECLARES_TYPE_P (decl)))
-	return decl;
-    }
-
-  /* We used to special-case vptr_identifier.  Make sure it's not
-     special any more.  */
-  gcc_assert (name != vptr_identifier || !TYPE_VFIELD (type));
-
-  return NULL_TREE;
-}
-
 /* Return the FUNCTION_DECL, RECORD_TYPE, UNION_TYPE, or
    NAMESPACE_DECL corresponding to the innermost non-block scope.  */
 
@@ -1454,158 +1354,6 @@ lookup_fnfields (tree xbasetype, tree na
   return rval;
 }
 
-/* Return the conversion operators in CLASS_TYPE corresponding to
-   "operator TYPE ()".  Only CLASS_TYPE itself is searched; this
-   routine does not scan the base classes of CLASS_TYPE.  */
-
-static tree
-lookup_conversion_operator (tree class_type, tree type)
-{
-  tree tpls = NULL_TREE;
-
-  if (TYPE_HAS_CONVERSION (class_type))
-    {
-      tree fns;
-      vec<tree, va_gc> *methods = CLASSTYPE_METHOD_VEC (class_type);
-
-      for (int i = CLASSTYPE_FIRST_CONVERSION_SLOT;
-	   vec_safe_iterate (methods, i, &fns); ++i)
-	{
-	  /* All the conversion operators come near the beginning of
-	     the class.  Therefore, if FN is not a conversion
-	     operator, there is no matching conversion operator in
-	     CLASS_TYPE.  */
-	  tree fn = OVL_FIRST (fns);
-	  if (!DECL_CONV_FN_P (fn))
-	    break;
-
-	  if (TREE_CODE (fn) == TEMPLATE_DECL)
-	    /* All the templated conversion functions are on the same
-	       slot, so remember it.  */
-	    tpls = fns;
-	  else if (same_type_p (DECL_CONV_FN_TYPE (fn), type))
-	    return fns;
-	}
-    }
-
-  return tpls;
-}
-
-/* TYPE is a class type. Return the member functions in the method
-   vector with name NAME.  Does not lazily declare implicitly-declared
-   member functions.  */
-
-tree
-lookup_fnfields_slot_nolazy (tree type, tree name)
-{
-  vec<tree, va_gc> *method_vec = CLASSTYPE_METHOD_VEC (type);
-  if (!method_vec)
-    return NULL_TREE;
-
-  if (IDENTIFIER_CONV_OP_P (name))
-    return lookup_conversion_operator (type, TREE_TYPE (name));
-
-  /* Skip the conversion operators.  */
-  int i;
-  tree fns;
-  for (i = CLASSTYPE_FIRST_CONVERSION_SLOT;
-       vec_safe_iterate (method_vec, i, &fns);
-       ++i)
-    if (!DECL_CONV_FN_P (OVL_FIRST (fns)))
-      break;
-
-  /* If the type is complete, use binary search.  */
-  if (COMPLETE_TYPE_P (type))
-    {
-      int lo;
-      int hi;
-
-      lo = i;
-      hi = method_vec->length ();
-      while (lo < hi)
-	{
-	  i = (lo + hi) / 2;
-
-	  fns = (*method_vec)[i];
-	  tree fn_name = OVL_NAME (fns);
-	  if (fn_name > name)
-	    hi = i;
-	  else if (fn_name < name)
-	    lo = i + 1;
-	  else
-	    return fns;
-	}
-    }
-  else
-    for (; vec_safe_iterate (method_vec, i, &fns); ++i)
-      {
-	if (OVL_NAME (fns) == name)
-	  return fns;
-      }
-
-  return NULL_TREE;
-}
-
-/* TYPE is a class type. Return the overloads in
-   the method vector with name NAME.  Lazily create ctors etc.  */
-
-tree
-lookup_fnfields_slot (tree type, tree name)
-{
-  type = complete_type (type);
-
-  if (COMPLETE_TYPE_P (type))
-    {
-      if (IDENTIFIER_CTOR_P (name))
-	{
-	  if (CLASSTYPE_LAZY_DEFAULT_CTOR (type))
-	    lazily_declare_fn (sfk_constructor, type);
-	  if (CLASSTYPE_LAZY_COPY_CTOR (type))
-	    lazily_declare_fn (sfk_copy_constructor, type);
-	  if (CLASSTYPE_LAZY_MOVE_CTOR (type))
-	    lazily_declare_fn (sfk_move_constructor, type);
-	}
-      else if (name == cp_assignment_operator_id (NOP_EXPR))
-	{
-	  if (CLASSTYPE_LAZY_COPY_ASSIGN (type))
-	    lazily_declare_fn (sfk_copy_assignment, type);
-	  if (CLASSTYPE_LAZY_MOVE_ASSIGN (type))
-	    lazily_declare_fn (sfk_move_assignment, type);
-	}
-      else if (IDENTIFIER_DTOR_P (name))
-	{
-	  if (CLASSTYPE_LAZY_DESTRUCTOR (type))
-	    lazily_declare_fn (sfk_destructor, type);
-	}
-    }
-
-  return lookup_fnfields_slot_nolazy (type, name);
-}
-
-/* Collect all the conversion operators of KLASS.  */
-
-tree
-lookup_all_conversions (tree klass)
-{
-  tree lkp = NULL_TREE;
-
-  if (vec<tree, va_gc> *methods = CLASSTYPE_METHOD_VEC (klass))
-    {
-      tree ovl;
-      for (int idx = CLASSTYPE_FIRST_CONVERSION_SLOT;
-	   methods->iterate (idx, &ovl); ++idx)
-	{
-	  if (!DECL_CONV_FN_P (OVL_FIRST (ovl)))
-	    /* There are no more conversion functions.  */
-	    break;
-
-	  lkp = lookup_add (ovl, lkp);
-	}
-    }
-
-  return lkp;
-}
-
 /* DECL is the result of a qualified name lookup.  QUALIFYING_SCOPE is
    the class or namespace used to qualify the name.  CONTEXT_CLASS is
    the class corresponding to the object in which DECL will be used.

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