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: [PATCH] Fix PR14495 (2/2)


> +   /* Remove dead edges from SWITCH_EXPR optimization.  This leaves the
> +      CFG in a broken state and requires a cfg_cleanup run.  */
> +   for (i = 0; VEC_iterate (edge, to_remove_edges, i, e); ++i)
> +     remove_edge (e);
> +   /* Update SWITCH_EXPR case label vector.  */
> +   for (i = 0; VEC_iterate (switch_update, to_update_switch_stmts, i, su);
> ++i) +     SWITCH_LABELS (su->stmt) = su->vec;
> +
> +   if (VEC_length (edge, to_remove_edges) > 0)
> +     free_dominance_info (CDI_DOMINATORS);
> +
> +   VEC_free (edge, heap, to_remove_edges);
> +   VEC_free (switch_update, heap, to_update_switch_stmts);
> +
>     /* ASSERT_EXPRs must be removed before finalizing jump threads
>        as finalizing jump threads calls the CFG cleanup code which
>        does not properly handle ASSERT_EXPRs.  */

I think there is an ordering problem: the CFG is broken at this point (and 
dominance info is correctly wiped) and it will be rebuilt a few lines below
by the call to finalize_jump_threads.

However there is this line in-between

  /* If we exposed any new variables, go ahead and put them into
     SSA form now, before we handle jump threading.  This simplifies
     interactions between rewriting of _DECL nodes into SSA form
     and rewriting SSA_NAME nodes into SSA form after block
     duplication and CFG manipulation.  */
  update_ssa (TODO_update_ssa);

and the first thing update_ssa does is

  /* Ensure that the dominance information is up-to-date.  */
  calculate_dominance_info (CDI_DOMINATORS);

but the CFG is still broken so calculate_dominance_info may abort.

Ada testcase attached, to be compiled at O2 -gnatp on x86.  BB 18 has no 
predecessor after VRP2.

-- 
Eric Botcazou
with GNAT.Dynamic_Tables;

package Q is

   procedure Add_Str_To_Name_Buffer (S : String);

   Names_Low_Bound : constant := 300_000_000;
   Names_High_Bound : constant := 399_999_999;
   type Name_Id is range Names_Low_Bound .. Names_High_Bound;
   No_Name : constant Name_Id := Names_Low_Bound;
   function Name_Find return Name_Id;

   type File_Name_Type is new Name_Id;
   No_File : constant File_Name_Type := File_Name_Type (No_Name);

   type Language_Index is new Natural;

   No_Language_Index          : constant Language_Index := 0;
   Ada_Language_Index         : constant Language_Index := 1;
   C_Language_Index           : constant Language_Index := 2;

   Last_Language_Index : Language_Index := No_Language_Index;

   type Spec_Or_Body is (Specification, Body_Part);

   type File_Name_Data is record
      Name : File_Name_Type := No_File;
   end record;

   type File_Names_Data is array (Spec_Or_Body) of File_Name_Data;

   type Unit_Data is record
      Name       : Name_Id;
      File_Names : File_Names_Data;
   end record;

   package Unit_Table is new GNAT.Dynamic_Tables
     (Table_Component_Type => Unit_Data,
      Table_Index_Type     => Natural,
      Table_Low_Bound      => 1,
      Table_Initial        => 100,
      Table_Increment      => 100);

   type Project_Tree_Ref is access all Unit_Table.Instance;

   procedure Set (Suffix : File_Name_Type);

end Q;
with Q; use Q;

package P is

   procedure Look_For_Sources (In_Tree : Project_Tree_Ref);

end P;
package body P is

   function Suffix_For (Language : Language_Index) return File_Name_Type is
   begin
      case Language is
         when Ada_Language_Index =>
            Add_Str_To_Name_Buffer (".adb");
         when C_Language_Index =>
            Add_Str_To_Name_Buffer (".c");
         when others =>
            return No_File;
      end case;
      return Name_Find;
   end;

   procedure Look_For_Sources (In_Tree : Project_Tree_Ref) is
      Excluded : File_Name_Type := Name_Find;
      Unit     : Unit_Data;
   begin
      while Excluded /= No_File loop
         For_Each_Unit:
         for Index in Unit_Table.First .. Unit_Table.Last (In_Tree.all)
         loop
            Unit := In_Tree.Table (Index);
            for Kind in Spec_Or_Body'Range loop
               if Unit.File_Names (Kind).Name = Excluded then
                  exit For_Each_Unit;
               end if;
            Excluded := Unit.File_Names (Kind).Name;
            end loop;
         end loop For_Each_Unit;
      end loop;

      for Lang in Ada_Language_Index + 1 .. Last_Language_Index loop
         Set (Suffix_For (Lang));
      end loop;
   end;

end P;

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