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: Move variably_modified_type_p to tree-inline.c


On Tue, Oct 22, 2002 at 05:48:34PM -0700, Mark Mitchell wrote:
> 
> 
> --On Tuesday, October 22, 2002 03:51:16 PM -0700 Zack Weinberg 
> <zack@codesourcery.com> wrote:
> 
> >This is phase one of a fix for PR 6994.
> 
> Cool.  This patch is OK.  While you're there, would you fix my typo:
> 
> +     elements are.  (Note that the VLA case has alredy been checked
> 
> That's "already".
> 
> This good go in c-common.c; the notion of "variably modified type" is
> C99-ism.  But then we have to increase the horrible damage that was
> done to tree-inline.c.  So, I think you should just put it in tree.c;
> it's really a property of types; nothing specific to do with inlining.
> 
> You can certainly move it there without re-bootstrapping.

Okay.  Here is the patch I just applied.

zw

	* langhooks.h (struct lang_hooks_for_tree_inlining): Add
	var_mod_type_p.
	* langhooks-def.h: Default for tree_inlining.var_mod_type_p is
	hook_tree_bool_false.

	* tree.c (variably_modified_type_p): Moved here from
	cp/tree.c.  Use lang_hooks.tree_inlining.var_mod_type_p for
	language-specific cases.  Due to this, must weaken some 'if
	and only if' checks to merely 'if'.
	* tree.h: Prototype variably_modified_type_p.

	* tree-inline.c (walk_tree): #undef WALK_SUBTREE_TAIL at end.

cp:
	* cp-lang.c (cp_var_mod_type_p): New: C++ hook for
	variably_modified_type_p.
	* cp-tree.h: Remove prototype of variably_modified_type_p.
	* tree.c (variably_modified_type_p): Remove; now implemented
	in language-independent code.

===================================================================
Index: langhooks-def.h
--- langhooks-def.h	22 Aug 2002 00:42:40 -0000	1.37
+++ langhooks-def.h	23 Oct 2002 17:00:48 -0000
@@ -140,6 +140,8 @@ tree lhd_tree_inlining_convert_parm_for_
   lhd_tree_inlining_copy_res_decl_for_inlining
 #define LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P \
   lhd_tree_inlining_anon_aggr_type_p
+#define LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P \
+  hook_tree_bool_false
 #define LANG_HOOKS_TREE_INLINING_START_INLINING \
   lhd_tree_inlining_start_inlining
 #define LANG_HOOKS_TREE_INLINING_END_INLINING \
@@ -156,6 +158,7 @@ tree lhd_tree_inlining_convert_parm_for_
   LANG_HOOKS_TREE_INLINING_AUTO_VAR_IN_FN_P, \
   LANG_HOOKS_TREE_INLINING_COPY_RES_DECL_FOR_INLINING, \
   LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P, \
+  LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P, \
   LANG_HOOKS_TREE_INLINING_START_INLINING, \
   LANG_HOOKS_TREE_INLINING_END_INLINING, \
   LANG_HOOKS_TREE_INLINING_CONVERT_PARM_FOR_INLINING \
===================================================================
Index: langhooks.h
--- langhooks.h	22 Sep 2002 14:09:34 -0000	1.47
+++ langhooks.h	23 Oct 2002 17:00:49 -0000
@@ -50,6 +50,7 @@ struct lang_hooks_for_tree_inlining
 							  void *, int *,
 							  void *));
   int (*anon_aggr_type_p) PARAMS ((union tree_node *));
+  bool (*var_mod_type_p) PARAMS ((union tree_node *));
   int (*start_inlining) PARAMS ((union tree_node *));
   void (*end_inlining) PARAMS ((union tree_node *));
   union tree_node *(*convert_parm_for_inlining) PARAMS ((union tree_node *,
===================================================================
Index: tree-inline.c
--- tree-inline.c	14 Oct 2002 18:12:11 -0000	1.32
+++ tree-inline.c	23 Oct 2002 17:00:49 -0000
@@ -1647,6 +1647,7 @@ walk_tree (tp, func, data, htab_)
   return NULL_TREE;
 
 #undef WALK_SUBTREE
+#undef WALK_SUBTREE_TAIL
 }
 
 /* Like walk_tree, but does not walk duplicate nodes more than
===================================================================
Index: tree.c
--- tree.c	14 Oct 2002 10:36:41 -0000	1.277
+++ tree.c	23 Oct 2002 17:00:50 -0000
@@ -4151,6 +4151,65 @@ int_fits_type_p (c, type)
     }
 }
 
+/* Returns true if T is, contains, or refers to a type with variable
+   size.  This concept is more general than that of C99 'variably
+   modified types': in C99, a struct type is never variably modified
+   because a VLA may not appear as a structure member.  However, in
+   GNU C code like:
+    
+     struct S { int i[f()]; };
+
+   is valid, and other languages may define similar constructs.  */
+
+bool
+variably_modified_type_p (type)
+     tree type;
+{
+  /* If TYPE itself has variable size, it is variably modified.  
+
+     We do not yet have a representation of the C99 '[*]' syntax.
+     When a representation is chosen, this function should be modified
+     to test for that case as well.  */
+  if (TYPE_SIZE (type) 
+      && TYPE_SIZE (type) != error_mark_node
+      && TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
+    return true;
+
+  /* If TYPE is a pointer or reference, it is variably modified if 
+     the type pointed to is variably modified.  */
+  if ((TREE_CODE (type) == POINTER_TYPE
+       || TREE_CODE (type) == REFERENCE_TYPE)
+      && variably_modified_type_p (TREE_TYPE (type)))
+    return true;
+  
+  /* If TYPE is an array, it is variably modified if the array
+     elements are.  (Note that the VLA case has already been checked
+     above.)  */
+  if (TREE_CODE (type) == ARRAY_TYPE
+      && variably_modified_type_p (TREE_TYPE (type)))
+    return true;
+
+  /* If TYPE is a function type, it is variably modified if any of the
+     parameters or the return type are variably modified.  */
+  if (TREE_CODE (type) == FUNCTION_TYPE
+      || TREE_CODE (type) == METHOD_TYPE)
+    {
+      tree parm;
+
+      if (variably_modified_type_p (TREE_TYPE (type)))
+	return true;
+      for (parm = TYPE_ARG_TYPES (type); 
+	   parm && parm != void_list_node; 
+	   parm = TREE_CHAIN (parm))
+	if (variably_modified_type_p (TREE_VALUE (parm)))
+	  return true;
+    }
+
+  /* The current language may have other cases to check, but in general,
+     all other types are not variably modified.  */
+  return (*lang_hooks.tree_inlining.var_mod_type_p) (type);
+}
+
 /* Given a DECL or TYPE, return the scope in which it was declared, or
    NULL_TREE if there is no containing scope.  */
 
===================================================================
Index: tree.h
--- tree.h	14 Oct 2002 10:36:41 -0000	1.359
+++ tree.h	23 Oct 2002 17:00:51 -0000
@@ -2909,6 +2909,7 @@ struct obstack;
 /* In tree.c */
 extern int really_constant_p		PARAMS ((tree));
 extern int int_fits_type_p		PARAMS ((tree, tree));
+extern bool variably_modified_type_p    PARAMS ((tree));
 extern int tree_log2			PARAMS ((tree));
 extern int tree_floor_log2		PARAMS ((tree));
 extern int simple_cst_equal		PARAMS ((tree, tree));
===================================================================
Index: cp/cp-lang.c
--- cp/cp-lang.c	13 Sep 2002 00:22:58 -0000	1.41
+++ cp/cp-lang.c	23 Oct 2002 17:01:12 -0000
@@ -32,6 +32,7 @@ static HOST_WIDE_INT cxx_get_alias_set P
 static bool ok_to_generate_alias_set_for_type PARAMS ((tree));
 static bool cxx_warn_unused_global_decl PARAMS ((tree));
 static tree cp_expr_size PARAMS ((tree));
+static bool cp_var_mod_type_p PARAMS ((tree));
 
 #undef LANG_HOOKS_NAME
 #define LANG_HOOKS_NAME "GNU C++"
@@ -126,6 +127,8 @@ static tree cp_expr_size PARAMS ((tree))
   cp_convert_parm_for_inlining
 #undef LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P
 #define LANG_HOOKS_TREE_INLINING_ANON_AGGR_TYPE_P anon_aggr_type_p
+#undef LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P
+#define LANG_HOOKS_TREE_INLINING_VAR_MOD_TYPE_P cp_var_mod_type_p
 #undef LANG_HOOKS_TREE_INLINING_START_INLINING
 #define LANG_HOOKS_TREE_INLINING_START_INLINING cp_start_inlining
 #undef LANG_HOOKS_TREE_INLINING_END_INLINING
@@ -310,3 +313,21 @@ cp_expr_size (exp)
     /* Use the default code.  */
     return lhd_expr_size (exp);
 }
+
+/* Returns true if T is a variably modified type, in the sense of C99.
+   This routine needs only check cases that cannot be handled by the
+   language-independent logic in tree-inline.c.  */
+
+static bool
+cp_var_mod_type_p (tree type)
+{
+  /* If TYPE is a pointer-to-member, it is variably modified if either
+     the class or the member are variably modified.  */
+  if (TYPE_PTRMEM_P (type) || TYPE_PTRMEMFUNC_P (type))
+    return (variably_modified_type_p (TYPE_PTRMEM_CLASS_TYPE (type))
+	    || variably_modified_type_p (TYPE_PTRMEM_POINTED_TO_TYPE (type)));
+
+  /* All other types are not variably modified.  */
+  return false;
+}
+
===================================================================
Index: cp/cp-tree.h
--- cp/cp-tree.h	21 Oct 2002 08:40:24 -0000	1.761
+++ cp/cp-tree.h	23 Oct 2002 17:01:14 -0000
@@ -4191,7 +4191,6 @@ extern tree cxx_unsave_expr_now			PARAMS
 extern tree cxx_maybe_build_cleanup		PARAMS ((tree));
 extern void init_tree			        PARAMS ((void));
 extern int pod_type_p				PARAMS ((tree));
-extern bool variably_modified_type_p            (tree);
 extern int zero_init_p				PARAMS ((tree));
 extern tree canonical_type_variant              PARAMS ((tree));
 extern void unshare_base_binfos			PARAMS ((tree));
===================================================================
Index: cp/tree.c
--- cp/tree.c	11 Oct 2002 19:55:21 -0000	1.304
+++ cp/tree.c	23 Oct 2002 17:01:14 -0000
@@ -1958,72 +1958,6 @@ pod_type_p (t)
   return 1;
 }
 
-/* Returns true if T is a variably modified type, in the sense of
-   C99.
-
-   In C99, a struct type is never variably modified because a VLA may
-   not appear as a structure member.  However, in GNU C code like:
-    
-     struct S { int i[f()]; };
-
-   is valid.  Even though GNU C++ does not allow that, this function
-   may sometimes be used in the C front end, so it treats any type
-   with variable size in the same way that C99 treats VLAs.
-
-   In particular, a variably modified type is one that involves a type
-   with variable size.  */
-
-bool
-variably_modified_type_p (tree type)
-{
-  /* If TYPE itself has variable size, it is variably modified.  
-
-     We do not yet have a representation of the C99 '[*]' syntax.
-     When a representation is chosen, this function should be modified
-     to test for that case as well.  */
-  if (TYPE_SIZE (type) 
-      && TYPE_SIZE (type) != error_mark_node
-      && TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
-    return true;
-
-  /* If TYPE is a pointer or reference, it is variably modified if and
-     only if the type pointed to is variably modified.  */
-  if (TYPE_PTR_P (type)
-      || TREE_CODE (type) == REFERENCE_TYPE)
-    return variably_modified_type_p (TREE_TYPE (type));
-  
-  /* If TYPE is an array, it is variably modified if the array
-     elements are.  (Note that the VLA case has alredy been checked
-     above).  */
-  if (TREE_CODE (type) == ARRAY_TYPE)
-    return variably_modified_type_p (TREE_TYPE (type));
-
-  /* If TYPE is a pointer-to-member, it is variably modified if either
-     the class or the member are variably modified.  */
-  if (TYPE_PTRMEM_P (type) || TYPE_PTRMEMFUNC_P (type))
-    return (variably_modified_type_p (TYPE_PTRMEM_CLASS_TYPE (type))
-	    || variably_modified_type_p (TYPE_PTRMEM_POINTED_TO_TYPE (type)));
-
-  /* If TYPE Is a function type, it is variably modified if any of the
-     parameters or the return type are variably modified.  */
-  if (TREE_CODE (type) == FUNCTION_TYPE
-      || TREE_CODE (type) == METHOD_TYPE)
-    {
-      tree parm;
-
-      if (variably_modified_type_p (TREE_TYPE (type)))
-	return true;
-      for (parm = TYPE_ARG_TYPES (type); 
-	   parm && parm != void_list_node; 
-	   parm = TREE_CHAIN (parm))
-	if (variably_modified_type_p (TREE_VALUE (parm)))
-	  return true;
-    }
-
-  /* All other types are not variably modified.  */
-  return false;
-}
-
 /* Returns 1 iff zero initialization of type T means actually storing
    zeros in it.  */
 


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