Minor modref optimization and statistics fix

Jan Hubicka hubicka@ucw.cz
Wed Sep 23 13:16:28 GMT 2020


Hi,
this patch fixes bug in tracking memory stats and also I have noticed that while
the pass takes care to stop traking things when things are obviously out of hand
it still keeps summaries that have no useful info for loads or stores and also
many summaries are just copying const/pure attributes.  This patch thus also
adds logic to detect if summary is useful and drop it early otherwise.  This
reduces number of queries to the oracle and saves memory/lto streaming.

For cc1plus LTO build (configured with --disable-plugin
--enable-checking=release --with-build-config=lto) I now get:

Alias oracle query stats:
  refs_may_alias_p: 62488734 disambiguations, 72660949 queries
  ref_maybe_used_by_call_p: 128863 disambiguations, 63393551 queries
  call_may_clobber_ref_p: 16013 disambiguations, 21776 queries
  nonoverlapping_component_refs_p: 0 disambiguations, 37628 queries
  nonoverlapping_refs_since_match_p: 19397 disambiguations, 55370 must overlaps, 75516 queries
  aliasing_component_refs_p: 54741 disambiguations, 752198 queries
  TBAA oracle: 21632692 disambiguations 52565147 queries
               15656420 are in alias set 0
               10108172 queries asked about the same object
               124 queries asked about the same alias set
               0 access volatile
               3640460 are dependent in the DAG
               1527279 are aritificially in conflict with void *

Modref stats:
  modref use: 5712 disambiguations, 31221 queries
  modref clobber: 684316 disambiguations, 1010000 queries
  1779717 tbaa queries (1.762096 per modref query)

PTA query stats:
  pt_solution_includes: 947334 disambiguations, 13601373 queries
  pt_solutions_intersect: 1011662 disambiguations, 13139565 queries

The number of queries should change, but the number of disambiguations should
not.  However comparing with stats here
https://gcc.gnu.org/pipermail/gcc-patches/2020-September/554309.html
I see about 50% drop in clobber disambiguations. There is however same drop in
other alias oracle stats.  I suppose someting changed in meanwhile on mainline
because I was basing that on older tree.  I tried to proofread changes between
mainline and branch and they seem all quite obvious.

I get similar change on (with -O2):

Alias oracle query stats:                                                       
  refs_may_alias_p: 2051320 disambiguations, 2312132 queries                    
  ref_maybe_used_by_call_p: 7058 disambiguations, 2088222 queries               
  call_may_clobber_ref_p: 232 disambiguations, 232 queries                      
  nonoverlapping_component_refs_p: 0 disambiguations, 4339 queries              
  nonoverlapping_refs_since_match_p: 329 disambiguations, 10200 must overlaps, 10616 queries
  aliasing_component_refs_p: 857 disambiguations, 34639 queries                 
  TBAA oracle: 886768 disambiguations 1670635 queries                           
               131572 are in alias set 0                                        
               461689 queries asked about the same object                       
               0 queries asked about the same alias set                         
               0 access volatile                                                
               190291 are dependent in the DAG                                  
               315 are aritificially in conflict with void *                    
                                                                                
Modref stats:                                                                   
  modref use: 430 disambiguations, 1885 queries                                 
  modref clobber: 9657 disambiguations, 16076 queries                           
  19027 tbaa queries (1.183566 per modref query)                                
                                                                                
PTA query stats:                                                                
  pt_solution_includes: 311756 disambiguations, 524179 queries                  
  pt_solutions_intersect: 129689 disambiguations, 415878 queries                

In both cases the number of disambiguations should be same (queries are not
comparable). 

Bootstrapped/regtested x86_64-linux, comitted.

gcc/ChangeLog:

2020-09-23  Jan Hubicka  <hubicka@ucw.cz>

	* ipa-modref.c (modref_summary::lto_useful_p): New member function.
	(modref_summary::useful_p): New member function.
	(analyze_function): Drop useless summaries.
	(modref_write): Skip useless summaries.
	(pass_ipa_modref::execute): Drop useless summaries.
	* ipa-modref.h (struct GTY): Declare useful_p and lto_useful_p.
	* tree-ssa-alias.c (dump_alias_stats): Fix.
	(modref_may_conflict): Fix stats.

diff --git a/gcc/ipa-modref.c b/gcc/ipa-modref.c
index fe277d88a16..3e65159934e 100644
--- a/gcc/ipa-modref.c
+++ b/gcc/ipa-modref.c
@@ -106,6 +106,36 @@ modref_summary::~modref_summary ()
     ggc_delete (stores_lto);
 }
 
+/* Return true if lto summary is potentially useful for optimization.  */
+
+bool
+modref_summary::lto_useful_p (int ecf_flags)
+{
+  if (ecf_flags & (ECF_CONST | ECF_NOVOPS))
+    return false;
+  if (loads_lto && !loads_lto->every_base)
+    return true;
+  if (ecf_flags & ECF_PURE)
+    return false;
+  return stores_lto && !stores_lto->every_base;
+}
+
+/* Return true if summary is potentially useful for optimization.  */
+
+bool
+modref_summary::useful_p (int ecf_flags)
+{
+  if (ecf_flags & (ECF_CONST | ECF_NOVOPS))
+    return false;
+  if (lto_useful_p (ecf_flags))
+    return true;
+  if (loads && !loads->every_base)
+    return true;
+  if (ecf_flags & ECF_PURE)
+    return false;
+  return stores && !loads->every_base;
+}
+
 /* Dump records TT to OUT.  */
 
 static void
@@ -588,8 +618,10 @@ static void
 analyze_function (function *f, bool ipa)
 {
   if (dump_file)
-    fprintf (dump_file, "modref analyzing '%s' (ipa=%i)...\n",
-	     function_name (f), ipa);
+    fprintf (dump_file, "modref analyzing '%s' (ipa=%i)%s%s\n",
+	     function_name (f), ipa,
+	     TREE_READONLY (current_function_decl) ? " (const)" : "",
+	     DECL_PURE_P (current_function_decl) ? " (pure)" : "");
 
   /* Don't analyze this function if it's compiled with -fno-strict-aliasing.  */
   if (!flag_ipa_modref)
@@ -646,6 +678,7 @@ analyze_function (function *f, bool ipa)
 				    param_modref_max_refs);
     }
   summary->finished = false;
+  int ecf_flags = flags_from_decl_or_type (current_function_decl);
 
   /* Analyze each statement in each basic block of the function.  If the
      statement cannot be analyzed (for any reason), the entire function cannot
@@ -656,7 +689,8 @@ analyze_function (function *f, bool ipa)
       gimple_stmt_iterator si;
       for (si = gsi_after_labels (bb); !gsi_end_p (si); gsi_next (&si))
 	{
-	  if (!analyze_stmt (summary, gsi_stmt (si), ipa))
+	  if (!analyze_stmt (summary, gsi_stmt (si), ipa)
+	      || !summary->useful_p (ecf_flags))
 	    {
 	      cgraph_node *fnode = cgraph_node::get (current_function_decl);
 	      summaries->remove (fnode);
@@ -927,9 +961,11 @@ modref_write ()
     {
       symtab_node *snode = lto_symtab_encoder_deref (encoder, i);
       cgraph_node *cnode = dyn_cast <cgraph_node *> (snode);
+      modref_summary *r;
 
       if (cnode && cnode->definition && !cnode->alias
-	  && summaries->get (cnode))
+	  && (r = summaries->get (cnode))
+	  && r->lto_useful_p (flags_from_decl_or_type (cnode->decl)))
 	count++;
     }
   streamer_write_uhwi (ob, count);
@@ -944,7 +980,7 @@ modref_write ()
 
 	  modref_summary *r = summaries->get (cnode);
 
-	  if (!r)
+	  if (!r || !r->lto_useful_p (flags_from_decl_or_type (cnode->decl)))
 	    continue;
 
 	  streamer_write_uhwi (ob, lto_symtab_encoder_encode (encoder, cnode));
@@ -1233,7 +1269,7 @@ unsigned int pass_ipa_modref::execute (function *)
 
 	      if (dump_file)
 		fprintf (dump_file, "    Call to %s\n",
-			 cur->dump_name ());
+			 callee_edge->callee->dump_name ());
 
 	      /* We can not safely optimize based on summary of callee if it
 		 does not always bind to current def: it is possible that
@@ -1278,7 +1314,7 @@ unsigned int pass_ipa_modref::execute (function *)
 		      its_hopeless = true;
 		      if (dump_file && avail <= AVAIL_INTERPOSABLE)
 			fprintf (dump_file, "      Call target interposable"
-				 "or not available\n");
+				 " or not available\n");
 		      else if (dump_file)
 			fprintf (dump_file, "      No call target summary\n");
 		      break;
diff --git a/gcc/ipa-modref.h b/gcc/ipa-modref.h
index 6cccdfe7af3..152e7154aed 100644
--- a/gcc/ipa-modref.h
+++ b/gcc/ipa-modref.h
@@ -41,6 +41,8 @@ struct GTY(()) modref_summary
   modref_summary ();
   ~modref_summary ();
   void dump (FILE *);
+  bool useful_p (int ecf_flags);
+  bool lto_useful_p (int ecf_flags);
 };
 
 modref_summary *get_modref_function_summary (cgraph_node *func);
diff --git a/gcc/tree-ssa-alias.c b/gcc/tree-ssa-alias.c
index be4d4462fc5..18ff529b491 100644
--- a/gcc/tree-ssa-alias.c
+++ b/gcc/tree-ssa-alias.c
@@ -170,7 +170,7 @@ dump_alias_stats (FILE *s)
   fprintf (s, "  modref clobber: "
 	   HOST_WIDE_INT_PRINT_DEC" disambiguations, "
 	   HOST_WIDE_INT_PRINT_DEC" queries\n  "
-	   HOST_WIDE_INT_PRINT_DEC" tbaa querries (%f per modref querry)\n",
+	   HOST_WIDE_INT_PRINT_DEC" tbaa queries (%f per modref query)\n",
 	   alias_stats.modref_clobber_no_alias,
 	   alias_stats.modref_clobber_no_alias
 	   + alias_stats.modref_clobber_may_alias,
@@ -2448,9 +2448,9 @@ modref_may_conflict (modref_tree <alias_set_type> *tt, ao_ref *ref, bool tbaa_p)
 
       if (tbaa_p && flag_strict_aliasing)
 	{
+	  alias_stats.modref_tests++;
 	  if (!alias_sets_conflict_p (base_set, base_node->base))
 	    continue;
-	  alias_stats.modref_tests++;
 	  num_tests++;
 	}
       else
@@ -2465,9 +2465,9 @@ modref_may_conflict (modref_tree <alias_set_type> *tt, ao_ref *ref, bool tbaa_p)
 	    return true;
 	  if (!flag_strict_aliasing)
 	    return true;
+	  alias_stats.modref_tests++;
 	  if (alias_sets_conflict_p (ref_set, ref_node->ref))
 	    return true;
-	  alias_stats.modref_tests++;
 	  num_tests++;
 	  if (num_tests >= max_tests)
 	    return true;


More information about the Gcc-patches mailing list