OLD | NEW |
1 /* RTL dead code elimination. | 1 /* RTL dead code elimination. |
2 Copyright (C) 2005, 2006, 2007, 2008, 2009 Free Software Foundation, Inc. | 2 Copyright (C) 2005, 2006, 2007, 2008, 2009 Free Software Foundation, Inc. |
3 | 3 |
4 This file is part of GCC. | 4 This file is part of GCC. |
5 | 5 |
6 GCC is free software; you can redistribute it and/or modify it under | 6 GCC is free software; you can redistribute it and/or modify it under |
7 the terms of the GNU General Public License as published by the Free | 7 the terms of the GNU General Public License as published by the Free |
8 Software Foundation; either version 3, or (at your option) any later | 8 Software Foundation; either version 3, or (at your option) any later |
9 version. | 9 version. |
10 | 10 |
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY | 11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY |
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or | 12 WARRANTY; without even the implied warranty of MERCHANTABILITY or |
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | 13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License |
14 for more details. | 14 for more details. |
15 | 15 |
16 You should have received a copy of the GNU General Public License | 16 You should have received a copy of the GNU General Public License |
17 along with GCC; see the file COPYING3. If not see | 17 along with GCC; see the file COPYING3. If not see |
18 <http://www.gnu.org/licenses/>. */ | 18 <http://www.gnu.org/licenses/>. */ |
19 | 19 |
20 #include "config.h" | 20 #include "config.h" |
21 #include "system.h" | 21 #include "system.h" |
22 #include "coretypes.h" | 22 #include "coretypes.h" |
23 #include "hashtab.h" | 23 #include "hashtab.h" |
24 #include "tm.h" | 24 #include "tm.h" |
25 #include "rtl.h" | 25 #include "rtl.h" |
26 #include "tree.h" | 26 #include "tree.h" |
27 #include "regs.h" | 27 #include "regs.h" |
28 #include "hard-reg-set.h" | 28 #include "hard-reg-set.h" |
29 #include "flags.h" | 29 #include "flags.h" |
| 30 #include "except.h" |
30 #include "df.h" | 31 #include "df.h" |
31 #include "cselib.h" | 32 #include "cselib.h" |
32 #include "dce.h" | 33 #include "dce.h" |
33 #include "timevar.h" | 34 #include "timevar.h" |
34 #include "tree-pass.h" | 35 #include "tree-pass.h" |
35 #include "dbgcnt.h" | 36 #include "dbgcnt.h" |
36 #include "tm_p.h" | 37 #include "tm_p.h" |
37 | 38 |
38 DEF_VEC_I(int); | |
39 DEF_VEC_ALLOC_I(int,heap); | |
40 | |
41 | 39 |
42 /* ------------------------------------------------------------------------- | 40 /* ------------------------------------------------------------------------- |
43 Core mark/delete routines | 41 Core mark/delete routines |
44 ------------------------------------------------------------------------- */ | 42 ------------------------------------------------------------------------- */ |
45 | 43 |
46 /* True if we are invoked while the df engine is running; in this case, | 44 /* True if we are invoked while the df engine is running; in this case, |
47 we don't want to reenter it. */ | 45 we don't want to reenter it. */ |
48 static bool df_in_progress = false; | 46 static bool df_in_progress = false; |
49 | 47 |
50 /* Instructions that have been marked but whose dependencies have not | 48 /* Instructions that have been marked but whose dependencies have not |
(...skipping 23 matching lines...) Expand all Loading... |
74 /* The UNSPEC case was added here because the ia-64 claims that | 72 /* The UNSPEC case was added here because the ia-64 claims that |
75 USEs do not work after reload and generates UNSPECS rather | 73 USEs do not work after reload and generates UNSPECS rather |
76 than USEs. Since dce is run after reload we need to avoid | 74 than USEs. Since dce is run after reload we need to avoid |
77 deleting these even if they are dead. If it turns out that | 75 deleting these even if they are dead. If it turns out that |
78 USEs really do work after reload, the ia-64 should be | 76 USEs really do work after reload, the ia-64 should be |
79 changed, and the UNSPEC case can be removed. */ | 77 changed, and the UNSPEC case can be removed. */ |
80 case UNSPEC: | 78 case UNSPEC: |
81 return false; | 79 return false; |
82 | 80 |
83 default: | 81 default: |
84 if (volatile_refs_p (body)) | 82 return !volatile_refs_p (body); |
85 » return false; | |
86 | |
87 if (flag_non_call_exceptions && may_trap_p (body)) | |
88 » return false; | |
89 | |
90 return true; | |
91 } | 83 } |
92 } | 84 } |
93 | 85 |
94 | 86 |
95 /* Return true if INSN is a normal instruction that can be deleted by | 87 /* Return true if INSN is a normal instruction that can be deleted by |
96 the DCE pass. */ | 88 the DCE pass. */ |
97 | 89 |
98 static bool | 90 static bool |
99 deletable_insn_p (rtx insn, bool fast, bitmap arg_stores) | 91 deletable_insn_p (rtx insn, bool fast, bitmap arg_stores) |
100 { | 92 { |
101 rtx body, x; | 93 rtx body, x; |
102 int i; | 94 int i; |
103 | 95 |
104 if (CALL_P (insn) | 96 if (CALL_P (insn) |
105 /* We cannot delete calls inside of the recursive dce because | 97 /* We cannot delete calls inside of the recursive dce because |
106 this may cause basic blocks to be deleted and this messes up | 98 this may cause basic blocks to be deleted and this messes up |
107 the rest of the stack of optimization passes. */ | 99 the rest of the stack of optimization passes. */ |
108 && (!df_in_progress) | 100 && (!df_in_progress) |
109 /* We cannot delete pure or const sibling calls because it is | 101 /* We cannot delete pure or const sibling calls because it is |
110 hard to see the result. */ | 102 hard to see the result. */ |
111 && (!SIBLING_CALL_P (insn)) | 103 && (!SIBLING_CALL_P (insn)) |
112 /* We can delete dead const or pure calls as long as they do not | 104 /* We can delete dead const or pure calls as long as they do not |
113 infinite loop. */ | 105 infinite loop. */ |
114 && (RTL_CONST_OR_PURE_CALL_P (insn) | 106 && (RTL_CONST_OR_PURE_CALL_P (insn) |
115 && !RTL_LOOPING_CONST_OR_PURE_CALL_P (insn))) | 107 && !RTL_LOOPING_CONST_OR_PURE_CALL_P (insn))) |
116 return find_call_stack_args (insn, false, fast, arg_stores); | 108 return find_call_stack_args (insn, false, fast, arg_stores); |
117 | 109 |
| 110 /* Don't delete jumps, notes and the like. */ |
118 if (!NONJUMP_INSN_P (insn)) | 111 if (!NONJUMP_INSN_P (insn)) |
119 return false; | 112 return false; |
120 | 113 |
| 114 /* Don't delete insns that can throw. */ |
| 115 if (!insn_nothrow_p (insn)) |
| 116 return false; |
| 117 |
121 body = PATTERN (insn); | 118 body = PATTERN (insn); |
122 switch (GET_CODE (body)) | 119 switch (GET_CODE (body)) |
123 { | 120 { |
124 case USE: | 121 case USE: |
| 122 case VAR_LOCATION: |
125 return false; | 123 return false; |
126 | 124 |
127 case CLOBBER: | 125 case CLOBBER: |
128 if (fast) | 126 if (fast) |
129 { | 127 { |
130 /* A CLOBBER of a dead pseudo register serves no purpose. | 128 /* A CLOBBER of a dead pseudo register serves no purpose. |
131 That is not necessarily true for hard registers until | 129 That is not necessarily true for hard registers until |
132 after reload. */ | 130 after reload. */ |
133 x = XEXP (body, 0); | 131 x = XEXP (body, 0); |
134 return REG_P (x) && (!HARD_REGISTER_P (x) || reload_completed); | 132 return REG_P (x) && (!HARD_REGISTER_P (x) || reload_completed); |
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
345 | 343 |
346 for (defs = DF_REF_CHAIN (*use_rec); defs; defs = defs->next) | 344 for (defs = DF_REF_CHAIN (*use_rec); defs; defs = defs->next) |
347 if (! DF_REF_IS_ARTIFICIAL (defs->ref)) | 345 if (! DF_REF_IS_ARTIFICIAL (defs->ref)) |
348 break; | 346 break; |
349 | 347 |
350 set = single_set (DF_REF_INSN (defs->ref)); | 348 set = single_set (DF_REF_INSN (defs->ref)); |
351 off += INTVAL (XEXP (SET_SRC (set), 1)); | 349 off += INTVAL (XEXP (SET_SRC (set), 1)); |
352 } | 350 } |
353 for (byte = off; byte < off + INTVAL (MEM_SIZE (mem)); byte++) | 351 for (byte = off; byte < off + INTVAL (MEM_SIZE (mem)); byte++) |
354 { | 352 { |
355 » gcc_assert (!bitmap_bit_p (sp_bytes, byte - min_sp_off)); | 353 » if (!bitmap_set_bit (sp_bytes, byte - min_sp_off)) |
356 » bitmap_set_bit (sp_bytes, byte - min_sp_off); | 354 » gcc_unreachable (); |
357 } | 355 } |
358 } | 356 } |
359 | 357 |
360 /* Walk backwards, looking for argument stores. The search stops | 358 /* Walk backwards, looking for argument stores. The search stops |
361 when seeing another call, sp adjustment or memory store other than | 359 when seeing another call, sp adjustment or memory store other than |
362 argument store. */ | 360 argument store. */ |
363 ret = false; | 361 ret = false; |
364 for (insn = PREV_INSN (call_insn); insn; insn = prev_insn) | 362 for (insn = PREV_INSN (call_insn); insn; insn = prev_insn) |
365 { | 363 { |
366 rtx set, mem, addr; | 364 rtx set, mem, addr; |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
433 break; | 431 break; |
434 } | 432 } |
435 | 433 |
436 if (GET_MODE_SIZE (GET_MODE (mem)) == 0) | 434 if (GET_MODE_SIZE (GET_MODE (mem)) == 0) |
437 break; | 435 break; |
438 | 436 |
439 for (byte = off; byte < off + GET_MODE_SIZE (GET_MODE (mem)); byte++) | 437 for (byte = off; byte < off + GET_MODE_SIZE (GET_MODE (mem)); byte++) |
440 { | 438 { |
441 if (byte < min_sp_off | 439 if (byte < min_sp_off |
442 || byte >= max_sp_off | 440 || byte >= max_sp_off |
443 » || !bitmap_bit_p (sp_bytes, byte - min_sp_off)) | 441 » || !bitmap_clear_bit (sp_bytes, byte - min_sp_off)) |
444 break; | 442 break; |
445 bitmap_clear_bit (sp_bytes, byte - min_sp_off); | |
446 } | 443 } |
447 | 444 |
448 if (!deletable_insn_p (insn, fast, NULL)) | 445 if (!deletable_insn_p (insn, fast, NULL)) |
449 break; | 446 break; |
450 | 447 |
451 if (do_mark) | 448 if (do_mark) |
452 mark_insn (insn, fast); | 449 mark_insn (insn, fast); |
453 else | 450 else |
454 bitmap_set_bit (arg_stores, INSN_UID (insn)); | 451 bitmap_set_bit (arg_stores, INSN_UID (insn)); |
455 | 452 |
(...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
618 | 615 |
619 static void | 616 static void |
620 mark_artificial_uses (void) | 617 mark_artificial_uses (void) |
621 { | 618 { |
622 basic_block bb; | 619 basic_block bb; |
623 struct df_link *defs; | 620 struct df_link *defs; |
624 df_ref *use_rec; | 621 df_ref *use_rec; |
625 | 622 |
626 FOR_ALL_BB (bb) | 623 FOR_ALL_BB (bb) |
627 { | 624 { |
628 for (use_rec = df_get_artificial_uses (bb->index); | 625 for (use_rec = df_get_artificial_uses (bb->index); |
629 *use_rec; use_rec++) | 626 *use_rec; use_rec++) |
630 for (defs = DF_REF_CHAIN (*use_rec); defs; defs = defs->next) | 627 for (defs = DF_REF_CHAIN (*use_rec); defs; defs = defs->next) |
631 if (! DF_REF_IS_ARTIFICIAL (defs->ref)) | 628 if (! DF_REF_IS_ARTIFICIAL (defs->ref)) |
632 mark_insn (DF_REF_INSN (defs->ref), false); | 629 mark_insn (DF_REF_INSN (defs->ref), false); |
633 } | 630 } |
634 } | 631 } |
635 | 632 |
636 | 633 |
637 /* Mark every instruction that defines a register value that INSN uses. */ | 634 /* Mark every instruction that defines a register value that INSN uses. */ |
638 | 635 |
639 static void | 636 static void |
640 mark_reg_dependencies (rtx insn) | 637 mark_reg_dependencies (rtx insn) |
641 { | 638 { |
642 struct df_link *defs; | 639 struct df_link *defs; |
643 df_ref *use_rec; | 640 df_ref *use_rec; |
644 | 641 |
| 642 if (DEBUG_INSN_P (insn)) |
| 643 return; |
| 644 |
645 for (use_rec = DF_INSN_USES (insn); *use_rec; use_rec++) | 645 for (use_rec = DF_INSN_USES (insn); *use_rec; use_rec++) |
646 { | 646 { |
647 df_ref use = *use_rec; | 647 df_ref use = *use_rec; |
648 if (dump_file) | 648 if (dump_file) |
649 { | 649 { |
650 fprintf (dump_file, "Processing use of "); | 650 fprintf (dump_file, "Processing use of "); |
651 print_simple_rtl (dump_file, DF_REF_REG (use)); | 651 print_simple_rtl (dump_file, DF_REF_REG (use)); |
652 fprintf (dump_file, " in insn %d:\n", INSN_UID (insn)); | 652 fprintf (dump_file, " in insn %d:\n", INSN_UID (insn)); |
653 } | 653 } |
654 for (defs = DF_REF_CHAIN (use); defs; defs = defs->next) | 654 for (defs = DF_REF_CHAIN (use); defs; defs = defs->next) |
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
731 gate_ud_dce (void) | 731 gate_ud_dce (void) |
732 { | 732 { |
733 return optimize > 1 && flag_dce | 733 return optimize > 1 && flag_dce |
734 && dbg_cnt (dce_ud); | 734 && dbg_cnt (dce_ud); |
735 } | 735 } |
736 | 736 |
737 struct rtl_opt_pass pass_ud_rtl_dce = | 737 struct rtl_opt_pass pass_ud_rtl_dce = |
738 { | 738 { |
739 { | 739 { |
740 RTL_PASS, | 740 RTL_PASS, |
741 "dce", /* name */ | 741 "ud dce", /* name */ |
742 gate_ud_dce, /* gate */ | 742 gate_ud_dce, /* gate */ |
743 rest_of_handle_ud_dce, /* execute */ | 743 rest_of_handle_ud_dce, /* execute */ |
744 NULL, /* sub */ | 744 NULL, /* sub */ |
745 NULL, /* next */ | 745 NULL, /* next */ |
746 0, /* static_pass_number */ | 746 0, /* static_pass_number */ |
747 TV_DCE, /* tv_id */ | 747 TV_DCE, /* tv_id */ |
748 0, /* properties_required */ | 748 0, /* properties_required */ |
749 0, /* properties_provided */ | 749 0, /* properties_provided */ |
750 0, /* properties_destroyed */ | 750 0, /* properties_destroyed */ |
751 0, /* todo_flags_start */ | 751 0, /* todo_flags_start */ |
752 TODO_dump_func | | 752 TODO_dump_func | |
753 TODO_df_finish | TODO_verify_rtl_sharing | | 753 TODO_df_finish | TODO_verify_rtl_sharing | |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
818 { | 818 { |
819 start += sb; | 819 start += sb; |
820 len = lb - sb; | 820 len = lb - sb; |
821 } | 821 } |
822 | 822 |
823 if (bitmap_bit_p (au, dregno)) | 823 if (bitmap_bit_p (au, dregno)) |
824 { | 824 { |
825 mark_insn (insn, true); | 825 mark_insn (insn, true); |
826 goto quickexit; | 826 goto quickexit; |
827 } | 827 } |
828 » | 828 |
829 last = start + len; | 829 last = start + len; |
830 while (start < last) | 830 while (start < last) |
831 if (bitmap_bit_p (local_live, start++)) | 831 if (bitmap_bit_p (local_live, start++)) |
832 { | 832 { |
833 mark_insn (insn, true); | 833 mark_insn (insn, true); |
834 goto quickexit; | 834 goto quickexit; |
835 } | 835 } |
836 } | 836 } |
837 » | 837 |
838 quickexit: | 838 quickexit: |
839 » | 839 |
840 /* No matter if the instruction is needed or not, we remove | 840 /* No matter if the instruction is needed or not, we remove |
841 any regno in the defs from the live set. */ | 841 any regno in the defs from the live set. */ |
842 df_byte_lr_simulate_defs (insn, local_live); | 842 df_byte_lr_simulate_defs (insn, local_live); |
843 | 843 |
844 /* On the other hand, we do not allow the dead uses to set | 844 /* On the other hand, we do not allow the dead uses to set |
845 anything in local_live. */ | 845 anything in local_live. */ |
846 if (marked_insn_p (insn)) | 846 if (marked_insn_p (insn)) |
847 df_byte_lr_simulate_uses (insn, local_live); | 847 df_byte_lr_simulate_uses (insn, local_live); |
848 | 848 |
849 if (dump_file) | 849 if (dump_file) |
850 { | 850 { |
851 » fprintf (dump_file, "finished processing insn %d live out = ", | 851 » fprintf (dump_file, "finished processing insn %d live out = ", |
852 INSN_UID (insn)); | 852 INSN_UID (insn)); |
853 df_print_byte_regset (dump_file, local_live); | 853 df_print_byte_regset (dump_file, local_live); |
854 } | 854 } |
855 } | 855 } |
856 | 856 |
857 df_byte_lr_simulate_artificial_refs_at_top (bb, local_live); | 857 df_byte_lr_simulate_artificial_refs_at_top (bb, local_live); |
858 | 858 |
859 block_changed = !bitmap_equal_p (local_live, DF_BYTE_LR_IN (bb)); | 859 block_changed = !bitmap_equal_p (local_live, DF_BYTE_LR_IN (bb)); |
860 if (block_changed) | 860 if (block_changed) |
861 bitmap_copy (DF_BYTE_LR_IN (bb), local_live); | 861 bitmap_copy (DF_BYTE_LR_IN (bb), local_live); |
862 BITMAP_FREE (local_live); | 862 BITMAP_FREE (local_live); |
863 return block_changed; | 863 return block_changed; |
864 } | 864 } |
865 | 865 |
866 | 866 |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
906 bool needed = false; | 906 bool needed = false; |
907 | 907 |
908 /* The insn is needed if there is someone who uses the output. */ | 908 /* The insn is needed if there is someone who uses the output. */ |
909 for (def_rec = DF_INSN_DEFS (insn); *def_rec; def_rec++) | 909 for (def_rec = DF_INSN_DEFS (insn); *def_rec; def_rec++) |
910 if (bitmap_bit_p (local_live, DF_REF_REGNO (*def_rec)) | 910 if (bitmap_bit_p (local_live, DF_REF_REGNO (*def_rec)) |
911 || bitmap_bit_p (au, DF_REF_REGNO (*def_rec))) | 911 || bitmap_bit_p (au, DF_REF_REGNO (*def_rec))) |
912 { | 912 { |
913 needed = true; | 913 needed = true; |
914 break; | 914 break; |
915 } | 915 } |
916 » | 916 |
917 if (needed) | 917 if (needed) |
918 mark_insn (insn, true); | 918 mark_insn (insn, true); |
919 » | 919 |
920 /* No matter if the instruction is needed or not, we remove | 920 /* No matter if the instruction is needed or not, we remove |
921 any regno in the defs from the live set. */ | 921 any regno in the defs from the live set. */ |
922 df_simulate_defs (insn, local_live); | 922 df_simulate_defs (insn, local_live); |
923 | 923 |
924 /* On the other hand, we do not allow the dead uses to set | 924 /* On the other hand, we do not allow the dead uses to set |
925 anything in local_live. */ | 925 anything in local_live. */ |
926 if (marked_insn_p (insn)) | 926 if (marked_insn_p (insn)) |
927 df_simulate_uses (insn, local_live); | 927 df_simulate_uses (insn, local_live); |
928 } | 928 } |
929 | 929 |
930 df_simulate_finalize_backwards (bb, local_live); | 930 df_simulate_finalize_backwards (bb, local_live); |
931 | 931 |
932 block_changed = !bitmap_equal_p (local_live, DF_LR_IN (bb)); | 932 block_changed = !bitmap_equal_p (local_live, DF_LR_IN (bb)); |
933 if (block_changed) | 933 if (block_changed) |
934 bitmap_copy (DF_LR_IN (bb), local_live); | 934 bitmap_copy (DF_LR_IN (bb), local_live); |
935 | 935 |
936 BITMAP_FREE (local_live); | 936 BITMAP_FREE (local_live); |
937 return block_changed; | 937 return block_changed; |
938 } | 938 } |
939 | 939 |
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
979 basic_block bb = BASIC_BLOCK (index); | 979 basic_block bb = BASIC_BLOCK (index); |
980 bool local_changed; | 980 bool local_changed; |
981 | 981 |
982 if (index < NUM_FIXED_BLOCKS) | 982 if (index < NUM_FIXED_BLOCKS) |
983 { | 983 { |
984 bitmap_set_bit (processed, index); | 984 bitmap_set_bit (processed, index); |
985 continue; | 985 continue; |
986 } | 986 } |
987 | 987 |
988 if (byte_level) | 988 if (byte_level) |
989 » local_changed | 989 » local_changed |
990 = byte_dce_process_block (bb, bitmap_bit_p (redo_out, index), | 990 = byte_dce_process_block (bb, bitmap_bit_p (redo_out, index), |
991 bb_has_eh_pred (bb) ? au_eh : au); | 991 bb_has_eh_pred (bb) ? au_eh : au); |
992 else | 992 else |
993 » local_changed | 993 » local_changed |
994 = dce_process_block (bb, bitmap_bit_p (redo_out, index), | 994 = dce_process_block (bb, bitmap_bit_p (redo_out, index), |
995 bb_has_eh_pred (bb) ? au_eh : au); | 995 bb_has_eh_pred (bb) ? au_eh : au); |
996 bitmap_set_bit (processed, index); | 996 bitmap_set_bit (processed, index); |
997 » | 997 |
998 if (local_changed) | 998 if (local_changed) |
999 { | 999 { |
1000 edge e; | 1000 edge e; |
1001 edge_iterator ei; | 1001 edge_iterator ei; |
1002 FOR_EACH_EDGE (e, ei, bb->preds) | 1002 FOR_EACH_EDGE (e, ei, bb->preds) |
1003 if (bitmap_bit_p (processed, e->src->index)) | 1003 if (bitmap_bit_p (processed, e->src->index)) |
1004 /* Be tricky about when we need to iterate the | 1004 /* Be tricky about when we need to iterate the |
1005 analysis. We only have redo the analysis if the | 1005 analysis. We only have redo the analysis if the |
1006 bitmaps change at the top of a block that is the | 1006 bitmaps change at the top of a block that is the |
1007 entry to a loop. */ | 1007 entry to a loop. */ |
1008 global_changed = true; | 1008 global_changed = true; |
1009 else | 1009 else |
1010 bitmap_set_bit (redo_out, e->src->index); | 1010 bitmap_set_bit (redo_out, e->src->index); |
1011 } | 1011 } |
1012 } | 1012 } |
1013 | 1013 |
1014 if (global_changed) | 1014 if (global_changed) |
1015 { | 1015 { |
1016 /* Turn off the RUN_DCE flag to prevent recursive calls to | 1016 /* Turn off the RUN_DCE flag to prevent recursive calls to |
1017 dce. */ | 1017 dce. */ |
1018 int old_flag = df_clear_flags (DF_LR_RUN_DCE); | 1018 int old_flag = df_clear_flags (DF_LR_RUN_DCE); |
1019 | 1019 |
1020 /* So something was deleted that requires a redo. Do it on | 1020 /* So something was deleted that requires a redo. Do it on |
1021 the cheap. */ | 1021 the cheap. */ |
1022 delete_unmarked_insns (); | 1022 delete_unmarked_insns (); |
1023 sbitmap_zero (marked); | 1023 sbitmap_zero (marked); |
1024 bitmap_clear (processed); | 1024 bitmap_clear (processed); |
1025 bitmap_clear (redo_out); | 1025 bitmap_clear (redo_out); |
1026 » | 1026 |
1027 /* We do not need to rescan any instructions. We only need | 1027 /* We do not need to rescan any instructions. We only need |
1028 to redo the dataflow equations for the blocks that had a | 1028 to redo the dataflow equations for the blocks that had a |
1029 change at the top of the block. Then we need to redo the | 1029 change at the top of the block. Then we need to redo the |
1030 » iteration. */ | 1030 » iteration. */ |
1031 if (byte_level) | 1031 if (byte_level) |
1032 df_analyze_problem (df_byte_lr, all_blocks, postorder, n_blocks); | 1032 df_analyze_problem (df_byte_lr, all_blocks, postorder, n_blocks); |
1033 else | 1033 else |
1034 df_analyze_problem (df_lr, all_blocks, postorder, n_blocks); | 1034 df_analyze_problem (df_lr, all_blocks, postorder, n_blocks); |
1035 | 1035 |
1036 if (old_flag & DF_LR_RUN_DCE) | 1036 if (old_flag & DF_LR_RUN_DCE) |
1037 df_set_flags (DF_LR_RUN_DCE); | 1037 df_set_flags (DF_LR_RUN_DCE); |
1038 | 1038 |
1039 prescan_insns_for_dce (true); | 1039 prescan_insns_for_dce (true); |
1040 } | 1040 } |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1083 vectors for any other problems than LR. */ | 1083 vectors for any other problems than LR. */ |
1084 | 1084 |
1085 void | 1085 void |
1086 run_fast_df_dce (void) | 1086 run_fast_df_dce (void) |
1087 { | 1087 { |
1088 if (flag_dce) | 1088 if (flag_dce) |
1089 { | 1089 { |
1090 /* If dce is able to delete something, it has to happen | 1090 /* If dce is able to delete something, it has to happen |
1091 immediately. Otherwise there will be problems handling the | 1091 immediately. Otherwise there will be problems handling the |
1092 eq_notes. */ | 1092 eq_notes. */ |
1093 enum df_changeable_flags old_flags | 1093 int old_flags = |
1094 » = df_clear_flags (DF_DEFER_INSN_RESCAN + DF_NO_INSN_RESCAN); | 1094 » df_clear_flags (DF_DEFER_INSN_RESCAN + DF_NO_INSN_RESCAN); |
1095 | 1095 |
1096 df_in_progress = true; | 1096 df_in_progress = true; |
1097 rest_of_handle_fast_dce (); | 1097 rest_of_handle_fast_dce (); |
1098 df_in_progress = false; | 1098 df_in_progress = false; |
1099 | 1099 |
1100 df_set_flags (old_flags); | 1100 df_set_flags (old_flags); |
1101 } | 1101 } |
1102 } | 1102 } |
1103 | 1103 |
1104 | 1104 |
1105 /* Run a fast DCE pass. */ | 1105 /* Run a fast DCE pass. */ |
(...skipping 10 matching lines...) Expand all Loading... |
1116 gate_fast_dce (void) | 1116 gate_fast_dce (void) |
1117 { | 1117 { |
1118 return optimize > 0 && flag_dce | 1118 return optimize > 0 && flag_dce |
1119 && dbg_cnt (dce_fast); | 1119 && dbg_cnt (dce_fast); |
1120 } | 1120 } |
1121 | 1121 |
1122 struct rtl_opt_pass pass_fast_rtl_dce = | 1122 struct rtl_opt_pass pass_fast_rtl_dce = |
1123 { | 1123 { |
1124 { | 1124 { |
1125 RTL_PASS, | 1125 RTL_PASS, |
1126 "dce", /* name */ | 1126 "rtl dce", /* name */ |
1127 gate_fast_dce, /* gate */ | 1127 gate_fast_dce, /* gate */ |
1128 rest_of_handle_fast_dce, /* execute */ | 1128 rest_of_handle_fast_dce, /* execute */ |
1129 NULL, /* sub */ | 1129 NULL, /* sub */ |
1130 NULL, /* next */ | 1130 NULL, /* next */ |
1131 0, /* static_pass_number */ | 1131 0, /* static_pass_number */ |
1132 TV_DCE, /* tv_id */ | 1132 TV_DCE, /* tv_id */ |
1133 0, /* properties_required */ | 1133 0, /* properties_required */ |
1134 0, /* properties_provided */ | 1134 0, /* properties_provided */ |
1135 0, /* properties_destroyed */ | 1135 0, /* properties_destroyed */ |
1136 0, /* todo_flags_start */ | 1136 0, /* todo_flags_start */ |
(...skipping 16 matching lines...) Expand all Loading... |
1153 TV_DCE, /* tv_id */ | 1153 TV_DCE, /* tv_id */ |
1154 0, /* properties_required */ | 1154 0, /* properties_required */ |
1155 0, /* properties_provided */ | 1155 0, /* properties_provided */ |
1156 0, /* properties_destroyed */ | 1156 0, /* properties_destroyed */ |
1157 0, /* todo_flags_start */ | 1157 0, /* todo_flags_start */ |
1158 TODO_dump_func | | 1158 TODO_dump_func | |
1159 TODO_df_finish | TODO_verify_rtl_sharing | | 1159 TODO_df_finish | TODO_verify_rtl_sharing | |
1160 TODO_ggc_collect /* todo_flags_finish */ | 1160 TODO_ggc_collect /* todo_flags_finish */ |
1161 } | 1161 } |
1162 }; | 1162 }; |
OLD | NEW |