I was trying to generate a graph file with -fdump-ipa-tmipa-blocks-details-vops-graph, but the .dot file was corrupted. It looks like the header bits printed in start_graph_dump() are not dumped because we are predicating the calls to clean_graph_dump_file->start_graph_dump by:

          && cfun && (cfun->curr_properties & PROP_cfg))

The problem is that for IPA passes (well at least for tmipa) cfun is NULL so we don't initialize the dump file, but later we go through each function (setting cfun appropriately) and dump the corresponding graphs somewhere in:

    do_per_function (execute_function_dump, NULL);

I have fixed this by adding a bit in opt_pass to keep track of if a graph .DOT file has been initialized, and initialize it if not. I suppose we could move initialization of the graph file further down, but that seemed a bit more tedious given all the places where we dump.

OK?
commit c5715cee17a20918375277ee602a5f0706138aba
Author: Aldy Hernandez <al...@redhat.com>
Date:   Mon Dec 16 12:37:01 2013 -0800

        * passes.c (execute_function_dump): Set graph_dump_initialized
        appropriately.
        (pass_init_dump_file): Similarly.
        (execute_one_pass): Pass new argument to do_per_function.
        * tree-pass.h (class opt_pass): New field graph_dump_initialized.

diff --git a/gcc/passes.c b/gcc/passes.c
index f30f159..bc7bf06 100644
--- a/gcc/passes.c
+++ b/gcc/passes.c
@@ -1640,8 +1640,10 @@ do_per_function_toporder (void (*callback) (void *data), 
void *data)
 /* Helper function to perform function body dump.  */
 
 static void
-execute_function_dump (void *data ATTRIBUTE_UNUSED)
+execute_function_dump (void *data)
 {
+  opt_pass *pass = (opt_pass *)data;
+
   if (dump_file && current_function_decl)
     {
       if (cfun->curr_properties & PROP_trees)
@@ -1655,7 +1657,14 @@ execute_function_dump (void *data ATTRIBUTE_UNUSED)
 
       if ((cfun->curr_properties & PROP_cfg)
          && (dump_flags & TDF_GRAPH))
-       print_graph_cfg (dump_file_name, cfun);
+       {
+         if (!pass->graph_dump_initialized)
+           {
+             clean_graph_dump_file (dump_file_name);
+             pass->graph_dump_initialized = true;
+           }
+         print_graph_cfg (dump_file_name, cfun);
+       }
     }
 }
 
@@ -1936,6 +1945,7 @@ verify_curr_properties (void *data)
 bool
 pass_init_dump_file (opt_pass *pass)
 {
+  pass->graph_dump_initialized = false;
   /* If a dump file name is present, open it if enabled.  */
   if (pass->static_pass_number != -1)
     {
@@ -1950,7 +1960,10 @@ pass_init_dump_file (opt_pass *pass)
       if (initializing_dump
          && dump_file && (dump_flags & TDF_GRAPH)
          && cfun && (cfun->curr_properties & PROP_cfg))
-       clean_graph_dump_file (dump_file_name);
+       {
+         clean_graph_dump_file (dump_file_name);
+         pass->graph_dump_initialized = true;
+       }
       timevar_pop (TV_DUMP);
       return initializing_dump;
     }
@@ -2230,7 +2243,7 @@ execute_one_pass (opt_pass *pass)
 
   verify_interpass_invariants ();
   if (dump_file)
-    do_per_function (execute_function_dump, NULL);
+    do_per_function (execute_function_dump, pass);
   if (pass->type == IPA_PASS)
     {
       struct cgraph_node *node;
diff --git a/gcc/tree-pass.h b/gcc/tree-pass.h
index b7b43de..d23181a 100644
--- a/gcc/tree-pass.h
+++ b/gcc/tree-pass.h
@@ -114,6 +114,11 @@ public:
   /* Static pass number, used as a fragment of the dump file name.  */
   int static_pass_number;
 
+  /* When a given dump file is being initialized, this flag is set to
+     true if the corresponding TDF_graph dump file has also been
+     initialized.  */
+  bool graph_dump_initialized;
+
 protected:
   gcc::context *m_ctxt;
 };

Reply via email to