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]

[patch] for PR17474


Hello,

when strength reduction in ivopts was rewriting memory accesses of
form

(*base_1)->field = ...

It took a duplicate of the ssa name that was base of the reference as
the base of the new INDIRECT_REF reference (so that the aliasing info is
preserved).  The problem is that this pointer has wrong type, i.e.
struct something * instead typeof (field) *, which somehow persuaded dom
to fold this reference back to structure field access, however with a
wrong offset (this might be a bug in maybe_fold_offset_to_component_ref,
I am not really sure).

This patch makes the base variable be of the right type, thus fixing
the misscompilation.

Bootstrapped & regtested on i686.

Zdenek

	PR tree-optimization/17474
	* tree-flow.h (create_subfield_ptr_name): Declare.
	* tree-ssa-loop-ivopts.c (rewrite_address_base): Use
	create_subfield_ptr_name.
	* tree-ssanames.c (create_subfield_ptr_name): New function.

Index: tree-flow.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-flow.h,v
retrieving revision 2.46
diff -c -3 -p -r2.46 tree-flow.h
*** tree-flow.h	16 Sep 2004 21:29:38 -0000	2.46
--- tree-flow.h	19 Sep 2004 21:40:03 -0000
*************** extern void rewrite_ssa_into_ssa (void);
*** 594,599 ****
--- 594,600 ----
  
  void compute_global_livein (bitmap, bitmap);
  tree duplicate_ssa_name (tree, tree);
+ tree create_subfield_ptr_name (tree, tree);
  
  /* In tree-ssa-ccp.c  */
  bool fold_stmt (tree *);
Index: tree-ssa-loop-ivopts.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-ssa-loop-ivopts.c,v
retrieving revision 2.11
diff -c -3 -p -r2.11 tree-ssa-loop-ivopts.c
*** tree-ssa-loop-ivopts.c	17 Sep 2004 21:54:42 -0000	2.11
--- tree-ssa-loop-ivopts.c	19 Sep 2004 21:40:05 -0000
*************** unshare_and_remove_ssa_names (tree ref)
*** 3826,3868 ****
  static void
  rewrite_address_base (block_stmt_iterator *bsi, tree *op, tree with)
  {
!   tree var = get_base_address (*op), new_var, new_name, copy, name;
!   tree orig;
  
!   if (!var || TREE_CODE (with) != SSA_NAME)
      goto do_rewrite;
  
!   if (TREE_CODE (var) == INDIRECT_REF)
!     var = TREE_OPERAND (var, 0);
!   if (TREE_CODE (var) == SSA_NAME)
!     {
!       name = var;
!       var = SSA_NAME_VAR (var);
!     }
!   else if (DECL_P (var))
!     name = NULL_TREE;
!   else
      goto do_rewrite;
-     
-   if (var_ann (var)->type_mem_tag)
-     var = var_ann (var)->type_mem_tag;
  
!   /* We need to add a memory tag for the variable.  But we do not want
!      to add it to the temporary used for the computations, since this leads
!      to problems in redundancy elimination when there are common parts
!      in two computations referring to the different arrays.  So we copy
!      the variable to a new temporary.  */
!   copy = build2 (MODIFY_EXPR, void_type_node, NULL_TREE, with);
!   if (name)
!     new_name = duplicate_ssa_name (name, copy);
!   else
!     {
!       new_var = create_tmp_var (TREE_TYPE (with), "ruatmp");
!       add_referenced_tmp_var (new_var);
!       var_ann (new_var)->type_mem_tag = var;
!       new_name = make_ssa_name (new_var, copy);
!     }
!   TREE_OPERAND (copy, 0) = new_name;
    bsi_insert_before (bsi, copy, BSI_SAME_STMT);
    with = new_name;
  
--- 3855,3873 ----
  static void
  rewrite_address_base (block_stmt_iterator *bsi, tree *op, tree with)
  {
!   tree new_name, copy, orig;
  
!   if (TREE_CODE (with) != SSA_NAME)
      goto do_rewrite;
  
!   /* Copy the address to the new temporary variable with the aliasing
!      information copied from the memory reference.  */
!   new_name = create_subfield_ptr_name (*op, NULL_TREE);
!   if (!new_name)
      goto do_rewrite;
  
!   copy = build2 (MODIFY_EXPR, void_type_node, new_name, with);
!   SSA_NAME_DEF_STMT (new_name) = copy;
    bsi_insert_before (bsi, copy, BSI_SAME_STMT);
    with = new_name;
  
Index: tree-ssanames.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/tree-ssanames.c,v
retrieving revision 2.14
diff -c -3 -p -r2.14 tree-ssanames.c
*** tree-ssanames.c	18 Sep 2004 07:31:30 -0000	2.14
--- tree-ssanames.c	19 Sep 2004 21:40:05 -0000
*************** duplicate_ssa_name (tree name, tree stmt
*** 294,299 ****
--- 294,346 ----
    return new_name;
  }
  
+ /* Create and return a ssa name defined by statement STMT.  The aliasing
+    information of new ssa name is set up using the fact that it will
+    be used to address memory location FIELD.  */
+ 
+ tree
+ create_subfield_ptr_name (tree field, tree stmt)
+ {
+   tree new_name, new_var, old_name, old_var, type_mem_tag, type;
+  
+   old_var = get_base_address (field);
+ 
+   if (!old_var)
+     return NULL_TREE;
+   if (TREE_CODE (old_var) == INDIRECT_REF)
+     old_var = TREE_OPERAND (old_var, 0);
+   if (TREE_CODE (old_var) == SSA_NAME)
+     {
+       old_name = old_var;
+       old_var = SSA_NAME_VAR (old_var);
+     }
+   else if (DECL_P (old_var))
+     old_name = NULL_TREE;
+   else
+     return NULL_TREE;
+ 
+   type_mem_tag = var_ann (old_var)->type_mem_tag;
+   if (!type_mem_tag)
+     type_mem_tag = old_var;
+ 
+   type = build_pointer_type (TREE_TYPE (field));
+   new_var = create_tmp_var (type, "cspntmp");
+   add_referenced_tmp_var (new_var);
+   var_ann (new_var)->type_mem_tag = type_mem_tag;
+ 
+   if (old_name)
+     {
+       /* We use duplicate_ssa_name to copy the aliasing information
+ 	 from old_name.  A bit hacky.  */
+       new_name = duplicate_ssa_name (old_name, stmt);
+       SSA_NAME_VAR (new_name) = new_var;
+       TREE_TYPE (new_name) = type;
+     }
+   else
+     new_name = make_ssa_name (new_var, stmt);
+ 
+   return new_name;
+ }
  
  /* Release all the SSA_NAMEs created by STMT.  */
  


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