Mercurial > hg > CbC > CbC_gcc
comparison gcc/var-tracking.c @ 132:d34655255c78
update gcc-8.2
author | mir3636 |
---|---|
date | Thu, 25 Oct 2018 10:21:07 +0900 |
parents | 84e7813d76e9 |
children | 1830386684a0 |
comparison
equal
deleted
inserted
replaced
130:e108057fa461 | 132:d34655255c78 |
---|---|
1 /* Variable tracking routines for the GNU compiler. | 1 /* Variable tracking routines for the GNU compiler. |
2 Copyright (C) 2002-2017 Free Software Foundation, Inc. | 2 Copyright (C) 2002-2018 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 | 6 GCC is free software; you can redistribute it and/or modify it |
7 under the terms of the GNU General Public License as published by | 7 under the terms of the GNU General Public License as published by |
113 #include "cselib.h" | 113 #include "cselib.h" |
114 #include "params.h" | 114 #include "params.h" |
115 #include "tree-pretty-print.h" | 115 #include "tree-pretty-print.h" |
116 #include "rtl-iter.h" | 116 #include "rtl-iter.h" |
117 #include "fibonacci_heap.h" | 117 #include "fibonacci_heap.h" |
118 #include "print-rtl.h" | |
118 | 119 |
119 typedef fibonacci_heap <long, basic_block_def> bb_heap_t; | 120 typedef fibonacci_heap <long, basic_block_def> bb_heap_t; |
120 typedef fibonacci_node <long, basic_block_def> bb_heap_node_t; | 121 typedef fibonacci_node <long, basic_block_def> bb_heap_node_t; |
121 | 122 |
122 /* var-tracking.c assumes that tree code with the same value as VALUE rtx code | 123 /* var-tracking.c assumes that tree code with the same value as VALUE rtx code |
388 }; | 389 }; |
389 | 390 |
390 /* Pointer to the BB's information specific to variable tracking pass. */ | 391 /* Pointer to the BB's information specific to variable tracking pass. */ |
391 #define VTI(BB) ((variable_tracking_info *) (BB)->aux) | 392 #define VTI(BB) ((variable_tracking_info *) (BB)->aux) |
392 | 393 |
393 /* Macro to access MEM_OFFSET as an HOST_WIDE_INT. Evaluates MEM twice. */ | 394 /* Return MEM_OFFSET (MEM) as a HOST_WIDE_INT, or 0 if we can't. */ |
394 #define INT_MEM_OFFSET(mem) (MEM_OFFSET_KNOWN_P (mem) ? MEM_OFFSET (mem) : 0) | 395 |
396 static inline HOST_WIDE_INT | |
397 int_mem_offset (const_rtx mem) | |
398 { | |
399 HOST_WIDE_INT offset; | |
400 if (MEM_OFFSET_KNOWN_P (mem) && MEM_OFFSET (mem).is_constant (&offset)) | |
401 return offset; | |
402 return 0; | |
403 } | |
395 | 404 |
396 #if CHECKING_P && (GCC_VERSION >= 2007) | 405 #if CHECKING_P && (GCC_VERSION >= 2007) |
397 | 406 |
398 /* Access VAR's Ith part's offset, checking that it's not a one-part | 407 /* Access VAR's Ith part's offset, checking that it's not a one-part |
399 variable. */ | 408 variable. */ |
664 static bool variable_different_p (variable *, variable *); | 673 static bool variable_different_p (variable *, variable *); |
665 static bool dataflow_set_different (dataflow_set *, dataflow_set *); | 674 static bool dataflow_set_different (dataflow_set *, dataflow_set *); |
666 static void dataflow_set_destroy (dataflow_set *); | 675 static void dataflow_set_destroy (dataflow_set *); |
667 | 676 |
668 static bool track_expr_p (tree, bool); | 677 static bool track_expr_p (tree, bool); |
669 static bool same_variable_part_p (rtx, tree, HOST_WIDE_INT); | |
670 static void add_uses_1 (rtx *, void *); | 678 static void add_uses_1 (rtx *, void *); |
671 static void add_stores (rtx, const_rtx, void *); | 679 static void add_stores (rtx, const_rtx, void *); |
672 static bool compute_bb_dataflow (basic_block); | 680 static bool compute_bb_dataflow (basic_block); |
673 static bool vt_find_locations (void); | 681 static bool vt_find_locations (void); |
674 | 682 |
695 static void delete_variable_part (dataflow_set *, rtx, | 703 static void delete_variable_part (dataflow_set *, rtx, |
696 decl_or_value, HOST_WIDE_INT); | 704 decl_or_value, HOST_WIDE_INT); |
697 static void emit_notes_in_bb (basic_block, dataflow_set *); | 705 static void emit_notes_in_bb (basic_block, dataflow_set *); |
698 static void vt_emit_notes (void); | 706 static void vt_emit_notes (void); |
699 | 707 |
700 static bool vt_get_decl_and_offset (rtx, tree *, HOST_WIDE_INT *); | |
701 static void vt_add_function_parameters (void); | 708 static void vt_add_function_parameters (void); |
702 static bool vt_initialize (void); | 709 static bool vt_initialize (void); |
703 static void vt_finalize (void); | 710 static void vt_finalize (void); |
704 | 711 |
705 /* Callback for stack_adjust_offset_pre_post, called via for_each_inc_dec. */ | 712 /* Callback for stack_adjust_offset_pre_post, called via for_each_inc_dec. */ |
909 | 916 |
910 /* Compute a CFA-based value for an ADJUSTMENT made to stack_pointer_rtx | 917 /* Compute a CFA-based value for an ADJUSTMENT made to stack_pointer_rtx |
911 or hard_frame_pointer_rtx. */ | 918 or hard_frame_pointer_rtx. */ |
912 | 919 |
913 static inline rtx | 920 static inline rtx |
914 compute_cfa_pointer (HOST_WIDE_INT adjustment) | 921 compute_cfa_pointer (poly_int64 adjustment) |
915 { | 922 { |
916 return plus_constant (Pmode, cfa_base_rtx, adjustment + cfa_base_offset); | 923 return plus_constant (Pmode, cfa_base_rtx, adjustment + cfa_base_offset); |
917 } | 924 } |
918 | 925 |
919 /* Adjustment for hard_frame_pointer_rtx to cfa base reg, | 926 /* Adjustment for hard_frame_pointer_rtx to cfa base reg, |
920 or -1 if the replacement shouldn't be done. */ | 927 or -1 if the replacement shouldn't be done. */ |
921 static HOST_WIDE_INT hard_frame_pointer_adjustment = -1; | 928 static poly_int64 hard_frame_pointer_adjustment = -1; |
922 | 929 |
923 /* Data for adjust_mems callback. */ | 930 /* Data for adjust_mems callback. */ |
924 | 931 |
925 struct adjust_mem_data | 932 struct adjust_mem_data |
926 { | 933 { |
956 case PLUS: | 963 case PLUS: |
957 case MINUS: | 964 case MINUS: |
958 case MULT: | 965 case MULT: |
959 break; | 966 break; |
960 case ASHIFT: | 967 case ASHIFT: |
968 if (GET_MODE (XEXP (x, 1)) != VOIDmode) | |
969 { | |
970 enum machine_mode mode = GET_MODE (subreg); | |
971 rtx op1 = XEXP (x, 1); | |
972 enum machine_mode op1_mode = GET_MODE (op1); | |
973 if (GET_MODE_PRECISION (as_a <scalar_int_mode> (mode)) | |
974 < GET_MODE_PRECISION (as_a <scalar_int_mode> (op1_mode))) | |
975 { | |
976 poly_uint64 byte = subreg_lowpart_offset (mode, op1_mode); | |
977 if (GET_CODE (op1) == SUBREG || GET_CODE (op1) == CONCAT) | |
978 { | |
979 if (!simplify_subreg (mode, op1, op1_mode, byte)) | |
980 return false; | |
981 } | |
982 else if (!validate_subreg (mode, op1_mode, op1, byte)) | |
983 return false; | |
984 } | |
985 } | |
961 iter.substitute (XEXP (x, 0)); | 986 iter.substitute (XEXP (x, 0)); |
962 break; | 987 break; |
963 default: | 988 default: |
964 return false; | 989 return false; |
965 } | 990 } |
1008 struct adjust_mem_data *amd = (struct adjust_mem_data *) data; | 1033 struct adjust_mem_data *amd = (struct adjust_mem_data *) data; |
1009 rtx mem, addr = loc, tem; | 1034 rtx mem, addr = loc, tem; |
1010 machine_mode mem_mode_save; | 1035 machine_mode mem_mode_save; |
1011 bool store_save; | 1036 bool store_save; |
1012 scalar_int_mode tem_mode, tem_subreg_mode; | 1037 scalar_int_mode tem_mode, tem_subreg_mode; |
1038 poly_int64 size; | |
1013 switch (GET_CODE (loc)) | 1039 switch (GET_CODE (loc)) |
1014 { | 1040 { |
1015 case REG: | 1041 case REG: |
1016 /* Don't do any sp or fp replacements outside of MEM addresses | 1042 /* Don't do any sp or fp replacements outside of MEM addresses |
1017 on the LHS. */ | 1043 on the LHS. */ |
1021 && !frame_pointer_needed | 1047 && !frame_pointer_needed |
1022 && cfa_base_rtx) | 1048 && cfa_base_rtx) |
1023 return compute_cfa_pointer (amd->stack_adjust); | 1049 return compute_cfa_pointer (amd->stack_adjust); |
1024 else if (loc == hard_frame_pointer_rtx | 1050 else if (loc == hard_frame_pointer_rtx |
1025 && frame_pointer_needed | 1051 && frame_pointer_needed |
1026 && hard_frame_pointer_adjustment != -1 | 1052 && maybe_ne (hard_frame_pointer_adjustment, -1) |
1027 && cfa_base_rtx) | 1053 && cfa_base_rtx) |
1028 return compute_cfa_pointer (hard_frame_pointer_adjustment); | 1054 return compute_cfa_pointer (hard_frame_pointer_adjustment); |
1029 gcc_checking_assert (loc != virtual_incoming_args_rtx); | 1055 gcc_checking_assert (loc != virtual_incoming_args_rtx); |
1030 return loc; | 1056 return loc; |
1031 case MEM: | 1057 case MEM: |
1052 if (!amd->store) | 1078 if (!amd->store) |
1053 mem = avoid_constant_pool_reference (mem); | 1079 mem = avoid_constant_pool_reference (mem); |
1054 return mem; | 1080 return mem; |
1055 case PRE_INC: | 1081 case PRE_INC: |
1056 case PRE_DEC: | 1082 case PRE_DEC: |
1057 addr = gen_rtx_PLUS (GET_MODE (loc), XEXP (loc, 0), | 1083 size = GET_MODE_SIZE (amd->mem_mode); |
1058 gen_int_mode (GET_CODE (loc) == PRE_INC | 1084 addr = plus_constant (GET_MODE (loc), XEXP (loc, 0), |
1059 ? GET_MODE_SIZE (amd->mem_mode) | 1085 GET_CODE (loc) == PRE_INC ? size : -size); |
1060 : -GET_MODE_SIZE (amd->mem_mode), | |
1061 GET_MODE (loc))); | |
1062 /* FALLTHRU */ | 1086 /* FALLTHRU */ |
1063 case POST_INC: | 1087 case POST_INC: |
1064 case POST_DEC: | 1088 case POST_DEC: |
1065 if (addr == loc) | 1089 if (addr == loc) |
1066 addr = XEXP (loc, 0); | 1090 addr = XEXP (loc, 0); |
1067 gcc_assert (amd->mem_mode != VOIDmode && amd->mem_mode != BLKmode); | 1091 gcc_assert (amd->mem_mode != VOIDmode && amd->mem_mode != BLKmode); |
1068 addr = simplify_replace_fn_rtx (addr, old_rtx, adjust_mems, data); | 1092 addr = simplify_replace_fn_rtx (addr, old_rtx, adjust_mems, data); |
1069 tem = gen_rtx_PLUS (GET_MODE (loc), XEXP (loc, 0), | 1093 size = GET_MODE_SIZE (amd->mem_mode); |
1070 gen_int_mode ((GET_CODE (loc) == PRE_INC | 1094 tem = plus_constant (GET_MODE (loc), XEXP (loc, 0), |
1071 || GET_CODE (loc) == POST_INC) | 1095 (GET_CODE (loc) == PRE_INC |
1072 ? GET_MODE_SIZE (amd->mem_mode) | 1096 || GET_CODE (loc) == POST_INC) ? size : -size); |
1073 : -GET_MODE_SIZE (amd->mem_mode), | |
1074 GET_MODE (loc))); | |
1075 store_save = amd->store; | 1097 store_save = amd->store; |
1076 amd->store = false; | 1098 amd->store = false; |
1077 tem = simplify_replace_fn_rtx (tem, old_rtx, adjust_mems, data); | 1099 tem = simplify_replace_fn_rtx (tem, old_rtx, adjust_mems, data); |
1078 amd->store = store_save; | 1100 amd->store = store_save; |
1079 amd->side_effects.safe_push (gen_rtx_SET (XEXP (loc, 0), tem)); | 1101 amd->side_effects.safe_push (gen_rtx_SET (XEXP (loc, 0), tem)); |
1116 GET_MODE (SUBREG_REG (loc)), | 1138 GET_MODE (SUBREG_REG (loc)), |
1117 SUBREG_BYTE (loc)); | 1139 SUBREG_BYTE (loc)); |
1118 if (tem == NULL_RTX) | 1140 if (tem == NULL_RTX) |
1119 tem = gen_rtx_raw_SUBREG (GET_MODE (loc), addr, SUBREG_BYTE (loc)); | 1141 tem = gen_rtx_raw_SUBREG (GET_MODE (loc), addr, SUBREG_BYTE (loc)); |
1120 finish_subreg: | 1142 finish_subreg: |
1121 if (MAY_HAVE_DEBUG_INSNS | 1143 if (MAY_HAVE_DEBUG_BIND_INSNS |
1122 && GET_CODE (tem) == SUBREG | 1144 && GET_CODE (tem) == SUBREG |
1123 && (GET_CODE (SUBREG_REG (tem)) == PLUS | 1145 && (GET_CODE (SUBREG_REG (tem)) == PLUS |
1124 || GET_CODE (SUBREG_REG (tem)) == MINUS | 1146 || GET_CODE (SUBREG_REG (tem)) == MINUS |
1125 || GET_CODE (SUBREG_REG (tem)) == MULT | 1147 || GET_CODE (SUBREG_REG (tem)) == MULT |
1126 || GET_CODE (SUBREG_REG (tem)) == ASHIFT) | 1148 || GET_CODE (SUBREG_REG (tem)) == ASHIFT) |
1328 static inline onepart_enum | 1350 static inline onepart_enum |
1329 dv_onepart_p (decl_or_value dv) | 1351 dv_onepart_p (decl_or_value dv) |
1330 { | 1352 { |
1331 tree decl; | 1353 tree decl; |
1332 | 1354 |
1333 if (!MAY_HAVE_DEBUG_INSNS) | 1355 if (!MAY_HAVE_DEBUG_BIND_INSNS) |
1334 return NOT_ONEPART; | 1356 return NOT_ONEPART; |
1335 | 1357 |
1336 if (dv_is_value_p (dv)) | 1358 if (dv_is_value_p (dv)) |
1337 return ONEPART_VALUE; | 1359 return ONEPART_VALUE; |
1338 | 1360 |
1841 if (!node) | 1863 if (!node) |
1842 attrs_list_insert (&set->regs[REGNO (loc)], dv, offset, loc); | 1864 attrs_list_insert (&set->regs[REGNO (loc)], dv, offset, loc); |
1843 set_variable_part (set, loc, dv, offset, initialized, set_src, iopt); | 1865 set_variable_part (set, loc, dv, offset, initialized, set_src, iopt); |
1844 } | 1866 } |
1845 | 1867 |
1868 /* Return true if we should track a location that is OFFSET bytes from | |
1869 a variable. Store the constant offset in *OFFSET_OUT if so. */ | |
1870 | |
1871 static bool | |
1872 track_offset_p (poly_int64 offset, HOST_WIDE_INT *offset_out) | |
1873 { | |
1874 HOST_WIDE_INT const_offset; | |
1875 if (!offset.is_constant (&const_offset) | |
1876 || !IN_RANGE (const_offset, 0, MAX_VAR_PARTS - 1)) | |
1877 return false; | |
1878 *offset_out = const_offset; | |
1879 return true; | |
1880 } | |
1881 | |
1882 /* Return the offset of a register that track_offset_p says we | |
1883 should track. */ | |
1884 | |
1885 static HOST_WIDE_INT | |
1886 get_tracked_reg_offset (rtx loc) | |
1887 { | |
1888 HOST_WIDE_INT offset; | |
1889 if (!track_offset_p (REG_OFFSET (loc), &offset)) | |
1890 gcc_unreachable (); | |
1891 return offset; | |
1892 } | |
1893 | |
1846 /* Set the register to contain REG_EXPR (LOC), REG_OFFSET (LOC). */ | 1894 /* Set the register to contain REG_EXPR (LOC), REG_OFFSET (LOC). */ |
1847 | 1895 |
1848 static void | 1896 static void |
1849 var_reg_set (dataflow_set *set, rtx loc, enum var_init_status initialized, | 1897 var_reg_set (dataflow_set *set, rtx loc, enum var_init_status initialized, |
1850 rtx set_src) | 1898 rtx set_src) |
1851 { | 1899 { |
1852 tree decl = REG_EXPR (loc); | 1900 tree decl = REG_EXPR (loc); |
1853 HOST_WIDE_INT offset = REG_OFFSET (loc); | 1901 HOST_WIDE_INT offset = get_tracked_reg_offset (loc); |
1854 | 1902 |
1855 var_reg_decl_set (set, loc, initialized, | 1903 var_reg_decl_set (set, loc, initialized, |
1856 dv_from_decl (decl), offset, set_src, INSERT); | 1904 dv_from_decl (decl), offset, set_src, INSERT); |
1857 } | 1905 } |
1858 | 1906 |
1894 static void | 1942 static void |
1895 var_reg_delete_and_set (dataflow_set *set, rtx loc, bool modify, | 1943 var_reg_delete_and_set (dataflow_set *set, rtx loc, bool modify, |
1896 enum var_init_status initialized, rtx set_src) | 1944 enum var_init_status initialized, rtx set_src) |
1897 { | 1945 { |
1898 tree decl = REG_EXPR (loc); | 1946 tree decl = REG_EXPR (loc); |
1899 HOST_WIDE_INT offset = REG_OFFSET (loc); | 1947 HOST_WIDE_INT offset = get_tracked_reg_offset (loc); |
1900 attrs *node, *next; | 1948 attrs *node, *next; |
1901 attrs **nextp; | 1949 attrs **nextp; |
1902 | 1950 |
1903 decl = var_debug_decl (decl); | 1951 decl = var_debug_decl (decl); |
1904 | 1952 |
1935 var_reg_delete (dataflow_set *set, rtx loc, bool clobber) | 1983 var_reg_delete (dataflow_set *set, rtx loc, bool clobber) |
1936 { | 1984 { |
1937 attrs **nextp = &set->regs[REGNO (loc)]; | 1985 attrs **nextp = &set->regs[REGNO (loc)]; |
1938 attrs *node, *next; | 1986 attrs *node, *next; |
1939 | 1987 |
1940 if (clobber) | 1988 HOST_WIDE_INT offset; |
1989 if (clobber && track_offset_p (REG_OFFSET (loc), &offset)) | |
1941 { | 1990 { |
1942 tree decl = REG_EXPR (loc); | 1991 tree decl = REG_EXPR (loc); |
1943 HOST_WIDE_INT offset = REG_OFFSET (loc); | |
1944 | 1992 |
1945 decl = var_debug_decl (decl); | 1993 decl = var_debug_decl (decl); |
1946 | 1994 |
1947 clobber_variable_part (set, NULL, dv_from_decl (decl), offset, NULL); | 1995 clobber_variable_part (set, NULL, dv_from_decl (decl), offset, NULL); |
1948 } | 1996 } |
2125 change. */ | 2173 change. */ |
2126 | 2174 |
2127 static rtx | 2175 static rtx |
2128 vt_canonicalize_addr (dataflow_set *set, rtx oloc) | 2176 vt_canonicalize_addr (dataflow_set *set, rtx oloc) |
2129 { | 2177 { |
2130 HOST_WIDE_INT ofst = 0; | 2178 poly_int64 ofst = 0, term; |
2131 machine_mode mode = GET_MODE (oloc); | 2179 machine_mode mode = GET_MODE (oloc); |
2132 rtx loc = oloc; | 2180 rtx loc = oloc; |
2133 rtx x; | 2181 rtx x; |
2134 bool retry = true; | 2182 bool retry = true; |
2135 | 2183 |
2136 while (retry) | 2184 while (retry) |
2137 { | 2185 { |
2138 while (GET_CODE (loc) == PLUS | 2186 while (GET_CODE (loc) == PLUS |
2139 && GET_CODE (XEXP (loc, 1)) == CONST_INT) | 2187 && poly_int_rtx_p (XEXP (loc, 1), &term)) |
2140 { | 2188 { |
2141 ofst += INTVAL (XEXP (loc, 1)); | 2189 ofst += term; |
2142 loc = XEXP (loc, 0); | 2190 loc = XEXP (loc, 0); |
2143 } | 2191 } |
2144 | 2192 |
2145 /* Alignment operations can't normally be combined, so just | 2193 /* Alignment operations can't normally be combined, so just |
2146 canonicalize the base and we're done. We'll normally have | 2194 canonicalize the base and we're done. We'll normally have |
2161 loc = get_addr_from_local_cache (set, loc); | 2209 loc = get_addr_from_local_cache (set, loc); |
2162 else | 2210 else |
2163 loc = get_addr_from_global_cache (loc); | 2211 loc = get_addr_from_global_cache (loc); |
2164 | 2212 |
2165 /* Consolidate plus_constants. */ | 2213 /* Consolidate plus_constants. */ |
2166 while (ofst && GET_CODE (loc) == PLUS | 2214 while (maybe_ne (ofst, 0) |
2167 && GET_CODE (XEXP (loc, 1)) == CONST_INT) | 2215 && GET_CODE (loc) == PLUS |
2216 && poly_int_rtx_p (XEXP (loc, 1), &term)) | |
2168 { | 2217 { |
2169 ofst += INTVAL (XEXP (loc, 1)); | 2218 ofst += term; |
2170 loc = XEXP (loc, 0); | 2219 loc = XEXP (loc, 0); |
2171 } | 2220 } |
2172 | 2221 |
2173 retry = false; | 2222 retry = false; |
2174 } | 2223 } |
2180 loc = x; | 2229 loc = x; |
2181 } | 2230 } |
2182 } | 2231 } |
2183 | 2232 |
2184 /* Add OFST back in. */ | 2233 /* Add OFST back in. */ |
2185 if (ofst) | 2234 if (maybe_ne (ofst, 0)) |
2186 { | 2235 { |
2187 /* Don't build new RTL if we can help it. */ | 2236 /* Don't build new RTL if we can help it. */ |
2188 if (GET_CODE (oloc) == PLUS | 2237 if (strip_offset (oloc, &term) == loc && known_eq (term, ofst)) |
2189 && XEXP (oloc, 0) == loc | |
2190 && INTVAL (XEXP (oloc, 1)) == ofst) | |
2191 return oloc; | 2238 return oloc; |
2192 | 2239 |
2193 loc = plus_constant (mode, loc, ofst); | 2240 loc = plus_constant (mode, loc, ofst); |
2194 } | 2241 } |
2195 | 2242 |
2334 static void | 2381 static void |
2335 var_mem_set (dataflow_set *set, rtx loc, enum var_init_status initialized, | 2382 var_mem_set (dataflow_set *set, rtx loc, enum var_init_status initialized, |
2336 rtx set_src) | 2383 rtx set_src) |
2337 { | 2384 { |
2338 tree decl = MEM_EXPR (loc); | 2385 tree decl = MEM_EXPR (loc); |
2339 HOST_WIDE_INT offset = INT_MEM_OFFSET (loc); | 2386 HOST_WIDE_INT offset = int_mem_offset (loc); |
2340 | 2387 |
2341 var_mem_decl_set (set, loc, initialized, | 2388 var_mem_decl_set (set, loc, initialized, |
2342 dv_from_decl (decl), offset, set_src, INSERT); | 2389 dv_from_decl (decl), offset, set_src, INSERT); |
2343 } | 2390 } |
2344 | 2391 |
2352 static void | 2399 static void |
2353 var_mem_delete_and_set (dataflow_set *set, rtx loc, bool modify, | 2400 var_mem_delete_and_set (dataflow_set *set, rtx loc, bool modify, |
2354 enum var_init_status initialized, rtx set_src) | 2401 enum var_init_status initialized, rtx set_src) |
2355 { | 2402 { |
2356 tree decl = MEM_EXPR (loc); | 2403 tree decl = MEM_EXPR (loc); |
2357 HOST_WIDE_INT offset = INT_MEM_OFFSET (loc); | 2404 HOST_WIDE_INT offset = int_mem_offset (loc); |
2358 | 2405 |
2359 clobber_overlapping_mems (set, loc); | 2406 clobber_overlapping_mems (set, loc); |
2360 decl = var_debug_decl (decl); | 2407 decl = var_debug_decl (decl); |
2361 | 2408 |
2362 if (initialized == VAR_INIT_STATUS_UNKNOWN) | 2409 if (initialized == VAR_INIT_STATUS_UNKNOWN) |
2373 | 2420 |
2374 static void | 2421 static void |
2375 var_mem_delete (dataflow_set *set, rtx loc, bool clobber) | 2422 var_mem_delete (dataflow_set *set, rtx loc, bool clobber) |
2376 { | 2423 { |
2377 tree decl = MEM_EXPR (loc); | 2424 tree decl = MEM_EXPR (loc); |
2378 HOST_WIDE_INT offset = INT_MEM_OFFSET (loc); | 2425 HOST_WIDE_INT offset = int_mem_offset (loc); |
2379 | 2426 |
2380 clobber_overlapping_mems (set, loc); | 2427 clobber_overlapping_mems (set, loc); |
2381 decl = var_debug_decl (decl); | 2428 decl = var_debug_decl (decl); |
2382 if (clobber) | 2429 if (clobber) |
2383 clobber_variable_part (set, NULL, dv_from_decl (decl), offset, NULL); | 2430 clobber_variable_part (set, NULL, dv_from_decl (decl), offset, NULL); |
3488 else if (XINT (x, i) < XINT (y, i)) | 3535 else if (XINT (x, i) < XINT (y, i)) |
3489 return -1; | 3536 return -1; |
3490 else | 3537 else |
3491 return 1; | 3538 return 1; |
3492 | 3539 |
3540 case 'p': | |
3541 r = compare_sizes_for_sort (SUBREG_BYTE (x), SUBREG_BYTE (y)); | |
3542 if (r != 0) | |
3543 return r; | |
3544 break; | |
3545 | |
3493 case 'V': | 3546 case 'V': |
3494 case 'E': | 3547 case 'E': |
3495 /* Compare the vector length first. */ | 3548 /* Compare the vector length first. */ |
3496 if (XVECLEN (x, i) == XVECLEN (y, i)) | 3549 if (XVECLEN (x, i) == XVECLEN (y, i)) |
3497 /* Compare the vectors elements. */; | 3550 /* Compare the vectors elements. */; |
4616 VALUE_RECURSED_INTO (val) = true; | 4669 VALUE_RECURSED_INTO (val) = true; |
4617 | 4670 |
4618 for (node = var->var_part[0].loc_chain; node; node = node->next) | 4671 for (node = var->var_part[0].loc_chain; node; node = node->next) |
4619 if (MEM_P (node->loc) | 4672 if (MEM_P (node->loc) |
4620 && MEM_EXPR (node->loc) == expr | 4673 && MEM_EXPR (node->loc) == expr |
4621 && INT_MEM_OFFSET (node->loc) == 0) | 4674 && int_mem_offset (node->loc) == 0) |
4622 { | 4675 { |
4623 where = node; | 4676 where = node; |
4624 break; | 4677 break; |
4625 } | 4678 } |
4626 else if (GET_CODE (node->loc) == VALUE | 4679 else if (GET_CODE (node->loc) == VALUE |
4681 for (loc = var->var_part[0].loc_chain; loc; loc = loc->next) | 4734 for (loc = var->var_part[0].loc_chain; loc; loc = loc->next) |
4682 { | 4735 { |
4683 /* We want to remove dying MEMs that don't refer to DECL. */ | 4736 /* We want to remove dying MEMs that don't refer to DECL. */ |
4684 if (GET_CODE (loc->loc) == MEM | 4737 if (GET_CODE (loc->loc) == MEM |
4685 && (MEM_EXPR (loc->loc) != decl | 4738 && (MEM_EXPR (loc->loc) != decl |
4686 || INT_MEM_OFFSET (loc->loc) != 0) | 4739 || int_mem_offset (loc->loc) != 0) |
4687 && mem_dies_at_call (loc->loc)) | 4740 && mem_dies_at_call (loc->loc)) |
4688 break; | 4741 break; |
4689 /* We want to move here MEMs that do refer to DECL. */ | 4742 /* We want to move here MEMs that do refer to DECL. */ |
4690 else if (GET_CODE (loc->loc) == VALUE | 4743 else if (GET_CODE (loc->loc) == VALUE |
4691 && find_mem_expr_in_1pdv (decl, loc->loc, | 4744 && find_mem_expr_in_1pdv (decl, loc->loc, |
4725 } | 4778 } |
4726 } | 4779 } |
4727 | 4780 |
4728 if (GET_CODE (loc->loc) != MEM | 4781 if (GET_CODE (loc->loc) != MEM |
4729 || (MEM_EXPR (loc->loc) == decl | 4782 || (MEM_EXPR (loc->loc) == decl |
4730 && INT_MEM_OFFSET (loc->loc) == 0) | 4783 && int_mem_offset (loc->loc) == 0) |
4731 || !mem_dies_at_call (loc->loc)) | 4784 || !mem_dies_at_call (loc->loc)) |
4732 { | 4785 { |
4733 if (old_loc != loc->loc && emit_notes) | 4786 if (old_loc != loc->loc && emit_notes) |
4734 { | 4787 { |
4735 if (old_loc == var->var_part[0].cur_loc) | 4788 if (old_loc == var->var_part[0].cur_loc) |
4852 regs_invalidated_by_call); | 4905 regs_invalidated_by_call); |
4853 | 4906 |
4854 EXECUTE_IF_SET_IN_HARD_REG_SET (invalidated_regs, 0, r, hrsi) | 4907 EXECUTE_IF_SET_IN_HARD_REG_SET (invalidated_regs, 0, r, hrsi) |
4855 var_regno_delete (set, r); | 4908 var_regno_delete (set, r); |
4856 | 4909 |
4857 if (MAY_HAVE_DEBUG_INSNS) | 4910 if (MAY_HAVE_DEBUG_BIND_INSNS) |
4858 { | 4911 { |
4859 set->traversed_vars = set->vars; | 4912 set->traversed_vars = set->vars; |
4860 shared_hash_htab (set->vars) | 4913 shared_hash_htab (set->vars) |
4861 ->traverse <dataflow_set *, dataflow_set_preserve_mem_locs> (set); | 4914 ->traverse <dataflow_set *, dataflow_set_preserve_mem_locs> (set); |
4862 set->traversed_vars = set->vars; | 4915 set->traversed_vars = set->vars; |
5168 { | 5221 { |
5169 if (handled_component_p (realdecl) | 5222 if (handled_component_p (realdecl) |
5170 || (TREE_CODE (realdecl) == MEM_REF | 5223 || (TREE_CODE (realdecl) == MEM_REF |
5171 && TREE_CODE (TREE_OPERAND (realdecl, 0)) == ADDR_EXPR)) | 5224 && TREE_CODE (TREE_OPERAND (realdecl, 0)) == ADDR_EXPR)) |
5172 { | 5225 { |
5173 HOST_WIDE_INT bitsize, bitpos, maxsize; | 5226 HOST_WIDE_INT bitsize, bitpos; |
5174 bool reverse; | 5227 bool reverse; |
5175 tree innerdecl | 5228 tree innerdecl |
5176 = get_ref_base_and_extent (realdecl, &bitpos, &bitsize, | 5229 = get_ref_base_and_extent_hwi (realdecl, &bitpos, |
5177 &maxsize, &reverse); | 5230 &bitsize, &reverse); |
5178 if (!DECL_P (innerdecl) | 5231 if (!innerdecl |
5232 || !DECL_P (innerdecl) | |
5179 || DECL_IGNORED_P (innerdecl) | 5233 || DECL_IGNORED_P (innerdecl) |
5180 /* Do not track declarations for parts of tracked record | 5234 /* Do not track declarations for parts of tracked record |
5181 parameters since we want to track them as a whole. */ | 5235 parameters since we want to track them as a whole. */ |
5182 || tracked_record_parameter_p (innerdecl) | 5236 || tracked_record_parameter_p (innerdecl) |
5183 || TREE_STATIC (innerdecl) | 5237 || TREE_STATIC (innerdecl) |
5184 || bitsize <= 0 | 5238 || bitsize == 0 |
5185 || bitpos + bitsize > 256 | 5239 || bitpos + bitsize > 256) |
5186 || bitsize != maxsize) | |
5187 return 0; | 5240 return 0; |
5188 else | 5241 else |
5189 realdecl = expr; | 5242 realdecl = expr; |
5190 } | 5243 } |
5191 else | 5244 else |
5223 if ((GET_MODE (decl_rtl) == BLKmode | 5276 if ((GET_MODE (decl_rtl) == BLKmode |
5224 || AGGREGATE_TYPE_P (TREE_TYPE (realdecl))) | 5277 || AGGREGATE_TYPE_P (TREE_TYPE (realdecl))) |
5225 && !tracked_record_parameter_p (realdecl)) | 5278 && !tracked_record_parameter_p (realdecl)) |
5226 return 0; | 5279 return 0; |
5227 if (MEM_SIZE_KNOWN_P (decl_rtl) | 5280 if (MEM_SIZE_KNOWN_P (decl_rtl) |
5228 && MEM_SIZE (decl_rtl) > MAX_VAR_PARTS) | 5281 && maybe_gt (MEM_SIZE (decl_rtl), MAX_VAR_PARTS)) |
5229 return 0; | 5282 return 0; |
5230 } | 5283 } |
5231 | 5284 |
5232 DECL_CHANGED (expr) = 0; | 5285 DECL_CHANGED (expr) = 0; |
5233 DECL_CHANGED (realdecl) = 0; | 5286 DECL_CHANGED (realdecl) = 0; |
5236 | 5289 |
5237 /* Determine whether a given LOC refers to the same variable part as | 5290 /* Determine whether a given LOC refers to the same variable part as |
5238 EXPR+OFFSET. */ | 5291 EXPR+OFFSET. */ |
5239 | 5292 |
5240 static bool | 5293 static bool |
5241 same_variable_part_p (rtx loc, tree expr, HOST_WIDE_INT offset) | 5294 same_variable_part_p (rtx loc, tree expr, poly_int64 offset) |
5242 { | 5295 { |
5243 tree expr2; | 5296 tree expr2; |
5244 HOST_WIDE_INT offset2; | 5297 poly_int64 offset2; |
5245 | 5298 |
5246 if (! DECL_P (expr)) | 5299 if (! DECL_P (expr)) |
5247 return false; | 5300 return false; |
5248 | 5301 |
5249 if (REG_P (loc)) | 5302 if (REG_P (loc)) |
5252 offset2 = REG_OFFSET (loc); | 5305 offset2 = REG_OFFSET (loc); |
5253 } | 5306 } |
5254 else if (MEM_P (loc)) | 5307 else if (MEM_P (loc)) |
5255 { | 5308 { |
5256 expr2 = MEM_EXPR (loc); | 5309 expr2 = MEM_EXPR (loc); |
5257 offset2 = INT_MEM_OFFSET (loc); | 5310 offset2 = int_mem_offset (loc); |
5258 } | 5311 } |
5259 else | 5312 else |
5260 return false; | 5313 return false; |
5261 | 5314 |
5262 if (! expr2 || ! DECL_P (expr2)) | 5315 if (! expr2 || ! DECL_P (expr2)) |
5263 return false; | 5316 return false; |
5264 | 5317 |
5265 expr = var_debug_decl (expr); | 5318 expr = var_debug_decl (expr); |
5266 expr2 = var_debug_decl (expr2); | 5319 expr2 = var_debug_decl (expr2); |
5267 | 5320 |
5268 return (expr == expr2 && offset == offset2); | 5321 return (expr == expr2 && known_eq (offset, offset2)); |
5269 } | 5322 } |
5270 | 5323 |
5271 /* LOC is a REG or MEM that we would like to track if possible. | 5324 /* LOC is a REG or MEM that we would like to track if possible. |
5272 If EXPR is null, we don't know what expression LOC refers to, | 5325 If EXPR is null, we don't know what expression LOC refers to, |
5273 otherwise it refers to EXPR + OFFSET. STORE_REG_P is true if | 5326 otherwise it refers to EXPR + OFFSET. STORE_REG_P is true if |
5277 is something we can track. When returning true, store the mode of | 5330 is something we can track. When returning true, store the mode of |
5278 the lowpart we can track in *MODE_OUT (if nonnull) and its offset | 5331 the lowpart we can track in *MODE_OUT (if nonnull) and its offset |
5279 from EXPR in *OFFSET_OUT (if nonnull). */ | 5332 from EXPR in *OFFSET_OUT (if nonnull). */ |
5280 | 5333 |
5281 static bool | 5334 static bool |
5282 track_loc_p (rtx loc, tree expr, HOST_WIDE_INT offset, bool store_reg_p, | 5335 track_loc_p (rtx loc, tree expr, poly_int64 offset, bool store_reg_p, |
5283 machine_mode *mode_out, HOST_WIDE_INT *offset_out) | 5336 machine_mode *mode_out, HOST_WIDE_INT *offset_out) |
5284 { | 5337 { |
5285 machine_mode mode; | 5338 machine_mode mode; |
5286 | 5339 |
5287 if (expr == NULL || !track_expr_p (expr, true)) | 5340 if (expr == NULL || !track_expr_p (expr, true)) |
5311 hard register. */ | 5364 hard register. */ |
5312 if ((paradoxical_subreg_p (mode, DECL_MODE (expr)) | 5365 if ((paradoxical_subreg_p (mode, DECL_MODE (expr)) |
5313 || (store_reg_p | 5366 || (store_reg_p |
5314 && !COMPLEX_MODE_P (DECL_MODE (expr)) | 5367 && !COMPLEX_MODE_P (DECL_MODE (expr)) |
5315 && hard_regno_nregs (REGNO (loc), DECL_MODE (expr)) == 1)) | 5368 && hard_regno_nregs (REGNO (loc), DECL_MODE (expr)) == 1)) |
5316 && offset + byte_lowpart_offset (DECL_MODE (expr), mode) == 0) | 5369 && known_eq (offset + byte_lowpart_offset (DECL_MODE (expr), mode), 0)) |
5317 { | 5370 { |
5318 mode = DECL_MODE (expr); | 5371 mode = DECL_MODE (expr); |
5319 offset = 0; | 5372 offset = 0; |
5320 } | 5373 } |
5321 | 5374 |
5322 if (offset < 0 || offset >= MAX_VAR_PARTS) | 5375 HOST_WIDE_INT const_offset; |
5376 if (!track_offset_p (offset, &const_offset)) | |
5323 return false; | 5377 return false; |
5324 | 5378 |
5325 if (mode_out) | 5379 if (mode_out) |
5326 *mode_out = mode; | 5380 *mode_out = mode; |
5327 if (offset_out) | 5381 if (offset_out) |
5328 *offset_out = offset; | 5382 *offset_out = const_offset; |
5329 return true; | 5383 return true; |
5330 } | 5384 } |
5331 | 5385 |
5332 /* Return the MODE lowpart of LOC, or null if LOC is not something we | 5386 /* Return the MODE lowpart of LOC, or null if LOC is not something we |
5333 want to track. When returning nonnull, make sure that the attributes | 5387 want to track. When returning nonnull, make sure that the attributes |
5334 on the returned value are updated. */ | 5388 on the returned value are updated. */ |
5335 | 5389 |
5336 static rtx | 5390 static rtx |
5337 var_lowpart (machine_mode mode, rtx loc) | 5391 var_lowpart (machine_mode mode, rtx loc) |
5338 { | 5392 { |
5339 unsigned int offset, reg_offset, regno; | 5393 unsigned int regno; |
5340 | 5394 |
5341 if (GET_MODE (loc) == mode) | 5395 if (GET_MODE (loc) == mode) |
5342 return loc; | 5396 return loc; |
5343 | 5397 |
5344 if (!REG_P (loc) && !MEM_P (loc)) | 5398 if (!REG_P (loc) && !MEM_P (loc)) |
5345 return NULL; | 5399 return NULL; |
5346 | 5400 |
5347 offset = byte_lowpart_offset (mode, GET_MODE (loc)); | 5401 poly_uint64 offset = byte_lowpart_offset (mode, GET_MODE (loc)); |
5348 | 5402 |
5349 if (MEM_P (loc)) | 5403 if (MEM_P (loc)) |
5350 return adjust_address_nv (loc, mode, offset); | 5404 return adjust_address_nv (loc, mode, offset); |
5351 | 5405 |
5352 reg_offset = subreg_lowpart_offset (mode, GET_MODE (loc)); | 5406 poly_uint64 reg_offset = subreg_lowpart_offset (mode, GET_MODE (loc)); |
5353 regno = REGNO (loc) + subreg_regno_offset (REGNO (loc), GET_MODE (loc), | 5407 regno = REGNO (loc) + subreg_regno_offset (REGNO (loc), GET_MODE (loc), |
5354 reg_offset, mode); | 5408 reg_offset, mode); |
5355 return gen_rtx_REG_offset (loc, mode, regno, offset); | 5409 return gen_rtx_REG_offset (loc, mode, regno, offset); |
5356 } | 5410 } |
5357 | 5411 |
5520 | 5574 |
5521 if (!expr) | 5575 if (!expr) |
5522 return MO_CLOBBER; | 5576 return MO_CLOBBER; |
5523 else if (target_for_debug_bind (var_debug_decl (expr))) | 5577 else if (target_for_debug_bind (var_debug_decl (expr))) |
5524 return MO_CLOBBER; | 5578 return MO_CLOBBER; |
5525 else if (track_loc_p (loc, expr, INT_MEM_OFFSET (loc), | 5579 else if (track_loc_p (loc, expr, int_mem_offset (loc), |
5526 false, modep, NULL) | 5580 false, modep, NULL) |
5527 /* Multi-part variables shouldn't refer to one-part | 5581 /* Multi-part variables shouldn't refer to one-part |
5528 variable names such as VALUEs (never happens) or | 5582 variable names such as VALUEs (never happens) or |
5529 DEBUG_EXPRs (only happens in the presence of debug | 5583 DEBUG_EXPRs (only happens in the presence of debug |
5530 insns). */ | 5584 insns). */ |
5531 && (!MAY_HAVE_DEBUG_INSNS | 5585 && (!MAY_HAVE_DEBUG_BIND_INSNS |
5532 || !rtx_debug_expr_p (XEXP (loc, 0)))) | 5586 || !rtx_debug_expr_p (XEXP (loc, 0)))) |
5533 return MO_USE; | 5587 return MO_USE; |
5534 else | 5588 else |
5535 return MO_CLOBBER; | 5589 return MO_CLOBBER; |
5536 } | 5590 } |
5924 || GET_CODE (expr) == CLOBBER) | 5978 || GET_CODE (expr) == CLOBBER) |
5925 { | 5979 { |
5926 mo.type = MO_CLOBBER; | 5980 mo.type = MO_CLOBBER; |
5927 mo.u.loc = loc; | 5981 mo.u.loc = loc; |
5928 if (GET_CODE (expr) == SET | 5982 if (GET_CODE (expr) == SET |
5929 && SET_DEST (expr) == loc | 5983 && (SET_DEST (expr) == loc |
5984 || (GET_CODE (SET_DEST (expr)) == STRICT_LOW_PART | |
5985 && XEXP (SET_DEST (expr), 0) == loc)) | |
5930 && !unsuitable_loc (SET_SRC (expr)) | 5986 && !unsuitable_loc (SET_SRC (expr)) |
5931 && find_use_val (loc, mode, cui)) | 5987 && find_use_val (loc, mode, cui)) |
5932 { | 5988 { |
5933 gcc_checking_assert (type == MO_VAL_SET); | 5989 gcc_checking_assert (type == MO_VAL_SET); |
5934 mo.u.loc = gen_rtx_SET (loc, SET_SRC (expr)); | 5990 mo.u.loc = gen_rtx_SET (loc, SET_SRC (expr)); |
6015 else | 6071 else |
6016 { | 6072 { |
6017 rtx xexpr = gen_rtx_SET (loc, src); | 6073 rtx xexpr = gen_rtx_SET (loc, src); |
6018 if (same_variable_part_p (SET_SRC (xexpr), | 6074 if (same_variable_part_p (SET_SRC (xexpr), |
6019 MEM_EXPR (loc), | 6075 MEM_EXPR (loc), |
6020 INT_MEM_OFFSET (loc))) | 6076 int_mem_offset (loc))) |
6021 mo.type = MO_COPY; | 6077 mo.type = MO_COPY; |
6022 else | 6078 else |
6023 mo.type = MO_SET; | 6079 mo.type = MO_SET; |
6024 mo.u.loc = xexpr; | 6080 mo.u.loc = xexpr; |
6025 } | 6081 } |
6054 preserve_value (v); | 6110 preserve_value (v); |
6055 goto log_and_return; | 6111 goto log_and_return; |
6056 } | 6112 } |
6057 | 6113 |
6058 if (loc == stack_pointer_rtx | 6114 if (loc == stack_pointer_rtx |
6059 && hard_frame_pointer_adjustment != -1 | 6115 && maybe_ne (hard_frame_pointer_adjustment, -1) |
6060 && preserve) | 6116 && preserve) |
6061 cselib_set_value_sp_based (v); | 6117 cselib_set_value_sp_based (v); |
6062 | 6118 |
6063 nloc = replace_expr_with_values (oloc); | 6119 nloc = replace_expr_with_values (oloc); |
6064 if (nloc) | 6120 if (nloc) |
6691 | 6747 |
6692 dataflow_set_init (&old_out); | 6748 dataflow_set_init (&old_out); |
6693 dataflow_set_copy (&old_out, out); | 6749 dataflow_set_copy (&old_out, out); |
6694 dataflow_set_copy (out, in); | 6750 dataflow_set_copy (out, in); |
6695 | 6751 |
6696 if (MAY_HAVE_DEBUG_INSNS) | 6752 if (MAY_HAVE_DEBUG_BIND_INSNS) |
6697 local_get_addr_cache = new hash_map<rtx, rtx>; | 6753 local_get_addr_cache = new hash_map<rtx, rtx>; |
6698 | 6754 |
6699 FOR_EACH_VEC_ELT (VTI (bb)->mos, i, mo) | 6755 FOR_EACH_VEC_ELT (VTI (bb)->mos, i, mo) |
6700 { | 6756 { |
6701 rtx_insn *insn = mo->insn; | 6757 rtx_insn *insn = mo->insn; |
6973 out->stack_adjust += mo->u.adjust; | 7029 out->stack_adjust += mo->u.adjust; |
6974 break; | 7030 break; |
6975 } | 7031 } |
6976 } | 7032 } |
6977 | 7033 |
6978 if (MAY_HAVE_DEBUG_INSNS) | 7034 if (MAY_HAVE_DEBUG_BIND_INSNS) |
6979 { | 7035 { |
6980 delete local_get_addr_cache; | 7036 delete local_get_addr_cache; |
6981 local_get_addr_cache = NULL; | 7037 local_get_addr_cache = NULL; |
6982 | 7038 |
6983 dataflow_set_equiv_regs (out); | 7039 dataflow_set_equiv_regs (out); |
7060 = shared_hash_htab (VTI (bb)->out.vars)->elements (); | 7116 = shared_hash_htab (VTI (bb)->out.vars)->elements (); |
7061 } | 7117 } |
7062 else | 7118 else |
7063 oldinsz = oldoutsz = 0; | 7119 oldinsz = oldoutsz = 0; |
7064 | 7120 |
7065 if (MAY_HAVE_DEBUG_INSNS) | 7121 if (MAY_HAVE_DEBUG_BIND_INSNS) |
7066 { | 7122 { |
7067 dataflow_set *in = &VTI (bb)->in, *first_out = NULL; | 7123 dataflow_set *in = &VTI (bb)->in, *first_out = NULL; |
7068 bool first = true, adjust = false; | 7124 bool first = true, adjust = false; |
7069 | 7125 |
7070 /* Calculate the IN set as the intersection of | 7126 /* Calculate the IN set as the intersection of |
7121 htabsz += shared_hash_htab (VTI (bb)->in.vars)->size () | 7177 htabsz += shared_hash_htab (VTI (bb)->in.vars)->size () |
7122 + shared_hash_htab (VTI (bb)->out.vars)->size (); | 7178 + shared_hash_htab (VTI (bb)->out.vars)->size (); |
7123 | 7179 |
7124 if (htabmax && htabsz > htabmax) | 7180 if (htabmax && htabsz > htabmax) |
7125 { | 7181 { |
7126 if (MAY_HAVE_DEBUG_INSNS) | 7182 if (MAY_HAVE_DEBUG_BIND_INSNS) |
7127 inform (DECL_SOURCE_LOCATION (cfun->decl), | 7183 inform (DECL_SOURCE_LOCATION (cfun->decl), |
7128 "variable tracking size limit exceeded with " | 7184 "variable tracking size limit exceeded with " |
7129 "-fvar-tracking-assignments, retrying without"); | 7185 "-fvar-tracking-assignments, retrying without"); |
7130 else | 7186 else |
7131 inform (DECL_SOURCE_LOCATION (cfun->decl), | 7187 inform (DECL_SOURCE_LOCATION (cfun->decl), |
7181 } | 7237 } |
7182 } | 7238 } |
7183 } | 7239 } |
7184 } | 7240 } |
7185 | 7241 |
7186 if (success && MAY_HAVE_DEBUG_INSNS) | 7242 if (success && MAY_HAVE_DEBUG_BIND_INSNS) |
7187 FOR_EACH_BB_FN (bb, cfun) | 7243 FOR_EACH_BB_FN (bb, cfun) |
7188 gcc_assert (VTI (bb)->flooded); | 7244 gcc_assert (VTI (bb)->flooded); |
7189 | 7245 |
7190 free (bb_order); | 7246 free (bb_order); |
7191 delete worklist; | 7247 delete worklist; |
8570 vt_expand_loc (rtx loc, variable_table_type *vars) | 8626 vt_expand_loc (rtx loc, variable_table_type *vars) |
8571 { | 8627 { |
8572 struct expand_loc_callback_data data; | 8628 struct expand_loc_callback_data data; |
8573 rtx result; | 8629 rtx result; |
8574 | 8630 |
8575 if (!MAY_HAVE_DEBUG_INSNS) | 8631 if (!MAY_HAVE_DEBUG_BIND_INSNS) |
8576 return loc; | 8632 return loc; |
8577 | 8633 |
8578 INIT_ELCD (data, vars); | 8634 INIT_ELCD (data, vars); |
8579 | 8635 |
8580 result = cselib_expand_value_rtx_cb (loc, scratch_regs, EXPR_DEPTH, | 8636 result = cselib_expand_value_rtx_cb (loc, scratch_regs, EXPR_DEPTH, |
8625 rtx note_vl; | 8681 rtx note_vl; |
8626 int i, j, n_var_parts; | 8682 int i, j, n_var_parts; |
8627 bool complete; | 8683 bool complete; |
8628 enum var_init_status initialized = VAR_INIT_STATUS_UNINITIALIZED; | 8684 enum var_init_status initialized = VAR_INIT_STATUS_UNINITIALIZED; |
8629 HOST_WIDE_INT last_limit; | 8685 HOST_WIDE_INT last_limit; |
8630 tree type_size_unit; | |
8631 HOST_WIDE_INT offsets[MAX_VAR_PARTS]; | 8686 HOST_WIDE_INT offsets[MAX_VAR_PARTS]; |
8632 rtx loc[MAX_VAR_PARTS]; | 8687 rtx loc[MAX_VAR_PARTS]; |
8633 tree decl; | 8688 tree decl; |
8634 location_chain *lc; | 8689 location_chain *lc; |
8635 | 8690 |
8647 var->var_part[i].cur_loc = var->var_part[i].loc_chain->loc; | 8702 var->var_part[i].cur_loc = var->var_part[i].loc_chain->loc; |
8648 for (i = 0; i < var->n_var_parts; i++) | 8703 for (i = 0; i < var->n_var_parts; i++) |
8649 { | 8704 { |
8650 machine_mode mode, wider_mode; | 8705 machine_mode mode, wider_mode; |
8651 rtx loc2; | 8706 rtx loc2; |
8652 HOST_WIDE_INT offset; | 8707 HOST_WIDE_INT offset, size, wider_size; |
8653 | 8708 |
8654 if (i == 0 && var->onepart) | 8709 if (i == 0 && var->onepart) |
8655 { | 8710 { |
8656 gcc_checking_assert (var->n_var_parts == 1); | 8711 gcc_checking_assert (var->n_var_parts == 1); |
8657 offset = 0; | 8712 offset = 0; |
8702 } | 8757 } |
8703 loc[n_var_parts] = loc2; | 8758 loc[n_var_parts] = loc2; |
8704 mode = GET_MODE (var->var_part[i].cur_loc); | 8759 mode = GET_MODE (var->var_part[i].cur_loc); |
8705 if (mode == VOIDmode && var->onepart) | 8760 if (mode == VOIDmode && var->onepart) |
8706 mode = DECL_MODE (decl); | 8761 mode = DECL_MODE (decl); |
8707 last_limit = offsets[n_var_parts] + GET_MODE_SIZE (mode); | 8762 /* We ony track subparts of constant-sized objects, since at present |
8763 there's no representation for polynomial pieces. */ | |
8764 if (!GET_MODE_SIZE (mode).is_constant (&size)) | |
8765 { | |
8766 complete = false; | |
8767 continue; | |
8768 } | |
8769 last_limit = offsets[n_var_parts] + size; | |
8708 | 8770 |
8709 /* Attempt to merge adjacent registers or memory. */ | 8771 /* Attempt to merge adjacent registers or memory. */ |
8710 for (j = i + 1; j < var->n_var_parts; j++) | 8772 for (j = i + 1; j < var->n_var_parts; j++) |
8711 if (last_limit <= VAR_PART_OFFSET (var, j)) | 8773 if (last_limit <= VAR_PART_OFFSET (var, j)) |
8712 break; | 8774 break; |
8713 if (j < var->n_var_parts | 8775 if (j < var->n_var_parts |
8714 && GET_MODE_WIDER_MODE (mode).exists (&wider_mode) | 8776 && GET_MODE_WIDER_MODE (mode).exists (&wider_mode) |
8777 && GET_MODE_SIZE (wider_mode).is_constant (&wider_size) | |
8715 && var->var_part[j].cur_loc | 8778 && var->var_part[j].cur_loc |
8716 && mode == GET_MODE (var->var_part[j].cur_loc) | 8779 && mode == GET_MODE (var->var_part[j].cur_loc) |
8717 && (REG_P (loc[n_var_parts]) || MEM_P (loc[n_var_parts])) | 8780 && (REG_P (loc[n_var_parts]) || MEM_P (loc[n_var_parts])) |
8718 && last_limit == (var->onepart ? 0 : VAR_PART_OFFSET (var, j)) | 8781 && last_limit == (var->onepart ? 0 : VAR_PART_OFFSET (var, j)) |
8719 && (loc2 = vt_expand_loc (var->var_part[j].cur_loc, vars)) | 8782 && (loc2 = vt_expand_loc (var->var_part[j].cur_loc, vars)) |
8720 && GET_CODE (loc[n_var_parts]) == GET_CODE (loc2)) | 8783 && GET_CODE (loc[n_var_parts]) == GET_CODE (loc2)) |
8721 { | 8784 { |
8722 rtx new_loc = NULL; | 8785 rtx new_loc = NULL; |
8786 poly_int64 offset2; | |
8723 | 8787 |
8724 if (REG_P (loc[n_var_parts]) | 8788 if (REG_P (loc[n_var_parts]) |
8725 && hard_regno_nregs (REGNO (loc[n_var_parts]), mode) * 2 | 8789 && hard_regno_nregs (REGNO (loc[n_var_parts]), mode) * 2 |
8726 == hard_regno_nregs (REGNO (loc[n_var_parts]), wider_mode) | 8790 == hard_regno_nregs (REGNO (loc[n_var_parts]), wider_mode) |
8727 && end_hard_regno (mode, REGNO (loc[n_var_parts])) | 8791 && end_hard_regno (mode, REGNO (loc[n_var_parts])) |
8742 } | 8806 } |
8743 } | 8807 } |
8744 else if (MEM_P (loc[n_var_parts]) | 8808 else if (MEM_P (loc[n_var_parts]) |
8745 && GET_CODE (XEXP (loc2, 0)) == PLUS | 8809 && GET_CODE (XEXP (loc2, 0)) == PLUS |
8746 && REG_P (XEXP (XEXP (loc2, 0), 0)) | 8810 && REG_P (XEXP (XEXP (loc2, 0), 0)) |
8747 && CONST_INT_P (XEXP (XEXP (loc2, 0), 1))) | 8811 && poly_int_rtx_p (XEXP (XEXP (loc2, 0), 1), &offset2)) |
8748 { | 8812 { |
8749 if ((REG_P (XEXP (loc[n_var_parts], 0)) | 8813 poly_int64 end1 = size; |
8750 && rtx_equal_p (XEXP (loc[n_var_parts], 0), | 8814 rtx base1 = strip_offset_and_add (XEXP (loc[n_var_parts], 0), |
8751 XEXP (XEXP (loc2, 0), 0)) | 8815 &end1); |
8752 && INTVAL (XEXP (XEXP (loc2, 0), 1)) | 8816 if (rtx_equal_p (base1, XEXP (XEXP (loc2, 0), 0)) |
8753 == GET_MODE_SIZE (mode)) | 8817 && known_eq (end1, offset2)) |
8754 || (GET_CODE (XEXP (loc[n_var_parts], 0)) == PLUS | |
8755 && CONST_INT_P (XEXP (XEXP (loc[n_var_parts], 0), 1)) | |
8756 && rtx_equal_p (XEXP (XEXP (loc[n_var_parts], 0), 0), | |
8757 XEXP (XEXP (loc2, 0), 0)) | |
8758 && INTVAL (XEXP (XEXP (loc[n_var_parts], 0), 1)) | |
8759 + GET_MODE_SIZE (mode) | |
8760 == INTVAL (XEXP (XEXP (loc2, 0), 1)))) | |
8761 new_loc = adjust_address_nv (loc[n_var_parts], | 8818 new_loc = adjust_address_nv (loc[n_var_parts], |
8762 wider_mode, 0); | 8819 wider_mode, 0); |
8763 } | 8820 } |
8764 | 8821 |
8765 if (new_loc) | 8822 if (new_loc) |
8766 { | 8823 { |
8767 loc[n_var_parts] = new_loc; | 8824 loc[n_var_parts] = new_loc; |
8768 mode = wider_mode; | 8825 mode = wider_mode; |
8769 last_limit = offsets[n_var_parts] + GET_MODE_SIZE (mode); | 8826 last_limit = offsets[n_var_parts] + wider_size; |
8770 i = j; | 8827 i = j; |
8771 } | 8828 } |
8772 } | 8829 } |
8773 ++n_var_parts; | 8830 ++n_var_parts; |
8774 } | 8831 } |
8775 type_size_unit = TYPE_SIZE_UNIT (TREE_TYPE (decl)); | 8832 poly_uint64 type_size_unit |
8776 if ((unsigned HOST_WIDE_INT) last_limit < TREE_INT_CST_LOW (type_size_unit)) | 8833 = tree_to_poly_uint64 (TYPE_SIZE_UNIT (TREE_TYPE (decl))); |
8834 if (maybe_lt (poly_uint64 (last_limit), type_size_unit)) | |
8777 complete = false; | 8835 complete = false; |
8778 | 8836 |
8779 if (! flag_var_tracking_uninit) | 8837 if (! flag_var_tracking_uninit) |
8780 initialized = VAR_INIT_STATUS_INITIALIZED; | 8838 initialized = VAR_INIT_STATUS_INITIALIZED; |
8781 | 8839 |
8816 else | 8874 else |
8817 { | 8875 { |
8818 /* Make sure that the call related notes come first. */ | 8876 /* Make sure that the call related notes come first. */ |
8819 while (NEXT_INSN (insn) | 8877 while (NEXT_INSN (insn) |
8820 && NOTE_P (insn) | 8878 && NOTE_P (insn) |
8821 && ((NOTE_KIND (insn) == NOTE_INSN_VAR_LOCATION | 8879 && NOTE_KIND (insn) == NOTE_INSN_VAR_LOCATION |
8822 && NOTE_DURING_CALL_P (insn)) | 8880 && NOTE_DURING_CALL_P (insn)) |
8823 || NOTE_KIND (insn) == NOTE_INSN_CALL_ARG_LOCATION)) | |
8824 insn = NEXT_INSN (insn); | 8881 insn = NEXT_INSN (insn); |
8825 if (NOTE_P (insn) | 8882 if (NOTE_P (insn) |
8826 && ((NOTE_KIND (insn) == NOTE_INSN_VAR_LOCATION | 8883 && NOTE_KIND (insn) == NOTE_INSN_VAR_LOCATION |
8827 && NOTE_DURING_CALL_P (insn)) | 8884 && NOTE_DURING_CALL_P (insn)) |
8828 || NOTE_KIND (insn) == NOTE_INSN_CALL_ARG_LOCATION)) | |
8829 note = emit_note_after (NOTE_INSN_VAR_LOCATION, insn); | 8885 note = emit_note_after (NOTE_INSN_VAR_LOCATION, insn); |
8830 else | 8886 else |
8831 note = emit_note_before (NOTE_INSN_VAR_LOCATION, insn); | 8887 note = emit_note_before (NOTE_INSN_VAR_LOCATION, insn); |
8832 } | 8888 } |
8833 NOTE_VAR_LOCATION (note) = note_vl; | 8889 NOTE_VAR_LOCATION (note) = note_vl; |
9005 variable_table_type *htab = shared_hash_htab (vars); | 9061 variable_table_type *htab = shared_hash_htab (vars); |
9006 | 9062 |
9007 if (!changed_variables->elements ()) | 9063 if (!changed_variables->elements ()) |
9008 return; | 9064 return; |
9009 | 9065 |
9010 if (MAY_HAVE_DEBUG_INSNS) | 9066 if (MAY_HAVE_DEBUG_BIND_INSNS) |
9011 process_changed_values (htab); | 9067 process_changed_values (htab); |
9012 | 9068 |
9013 data.insn = insn; | 9069 data.insn = insn; |
9014 data.where = where; | 9070 data.where = where; |
9015 data.vars = htab; | 9071 data.vars = htab; |
9166 case MO_CALL: | 9222 case MO_CALL: |
9167 dataflow_set_clear_at_call (set, insn); | 9223 dataflow_set_clear_at_call (set, insn); |
9168 emit_notes_for_changes (insn, EMIT_NOTE_AFTER_CALL_INSN, set->vars); | 9224 emit_notes_for_changes (insn, EMIT_NOTE_AFTER_CALL_INSN, set->vars); |
9169 { | 9225 { |
9170 rtx arguments = mo->u.loc, *p = &arguments; | 9226 rtx arguments = mo->u.loc, *p = &arguments; |
9171 rtx_note *note; | |
9172 while (*p) | 9227 while (*p) |
9173 { | 9228 { |
9174 XEXP (XEXP (*p, 0), 1) | 9229 XEXP (XEXP (*p, 0), 1) |
9175 = vt_expand_loc (XEXP (XEXP (*p, 0), 1), | 9230 = vt_expand_loc (XEXP (XEXP (*p, 0), 1), |
9176 shared_hash_htab (set->vars)); | 9231 shared_hash_htab (set->vars)); |
9177 /* If expansion is successful, keep it in the list. */ | 9232 /* If expansion is successful, keep it in the list. */ |
9178 if (XEXP (XEXP (*p, 0), 1)) | 9233 if (XEXP (XEXP (*p, 0), 1)) |
9179 p = &XEXP (*p, 1); | 9234 { |
9235 XEXP (XEXP (*p, 0), 1) | |
9236 = copy_rtx_if_shared (XEXP (XEXP (*p, 0), 1)); | |
9237 p = &XEXP (*p, 1); | |
9238 } | |
9180 /* Otherwise, if the following item is data_value for it, | 9239 /* Otherwise, if the following item is data_value for it, |
9181 drop it too too. */ | 9240 drop it too too. */ |
9182 else if (XEXP (*p, 1) | 9241 else if (XEXP (*p, 1) |
9183 && REG_P (XEXP (XEXP (*p, 0), 0)) | 9242 && REG_P (XEXP (XEXP (*p, 0), 0)) |
9184 && MEM_P (XEXP (XEXP (XEXP (*p, 1), 0), 0)) | 9243 && MEM_P (XEXP (XEXP (XEXP (*p, 1), 0), 0)) |
9190 *p = XEXP (XEXP (*p, 1), 1); | 9249 *p = XEXP (XEXP (*p, 1), 1); |
9191 /* Just drop this item. */ | 9250 /* Just drop this item. */ |
9192 else | 9251 else |
9193 *p = XEXP (*p, 1); | 9252 *p = XEXP (*p, 1); |
9194 } | 9253 } |
9195 note = emit_note_after (NOTE_INSN_CALL_ARG_LOCATION, insn); | 9254 add_reg_note (insn, REG_CALL_ARG_LOCATION, arguments); |
9196 NOTE_VAR_LOCATION (note) = arguments; | |
9197 } | 9255 } |
9198 break; | 9256 break; |
9199 | 9257 |
9200 case MO_USE: | 9258 case MO_USE: |
9201 { | 9259 { |
9489 | 9547 |
9490 /* Enable emitting notes by functions (mainly by set_variable_part and | 9548 /* Enable emitting notes by functions (mainly by set_variable_part and |
9491 delete_variable_part). */ | 9549 delete_variable_part). */ |
9492 emit_notes = true; | 9550 emit_notes = true; |
9493 | 9551 |
9494 if (MAY_HAVE_DEBUG_INSNS) | 9552 if (MAY_HAVE_DEBUG_BIND_INSNS) |
9495 { | 9553 dropped_values = new variable_table_type (cselib_get_next_uid () * 2); |
9496 dropped_values = new variable_table_type (cselib_get_next_uid () * 2); | |
9497 } | |
9498 | 9554 |
9499 dataflow_set_init (&cur); | 9555 dataflow_set_init (&cur); |
9500 | 9556 |
9501 FOR_EACH_BB_FN (bb, cfun) | 9557 FOR_EACH_BB_FN (bb, cfun) |
9502 { | 9558 { |
9503 /* Emit the notes for changes of variable locations between two | 9559 /* Emit the notes for changes of variable locations between two |
9504 subsequent basic blocks. */ | 9560 subsequent basic blocks. */ |
9505 emit_notes_for_differences (BB_HEAD (bb), &cur, &VTI (bb)->in); | 9561 emit_notes_for_differences (BB_HEAD (bb), &cur, &VTI (bb)->in); |
9506 | 9562 |
9507 if (MAY_HAVE_DEBUG_INSNS) | 9563 if (MAY_HAVE_DEBUG_BIND_INSNS) |
9508 local_get_addr_cache = new hash_map<rtx, rtx>; | 9564 local_get_addr_cache = new hash_map<rtx, rtx>; |
9509 | 9565 |
9510 /* Emit the notes for the changes in the basic block itself. */ | 9566 /* Emit the notes for the changes in the basic block itself. */ |
9511 emit_notes_in_bb (bb, &cur); | 9567 emit_notes_in_bb (bb, &cur); |
9512 | 9568 |
9513 if (MAY_HAVE_DEBUG_INSNS) | 9569 if (MAY_HAVE_DEBUG_BIND_INSNS) |
9514 delete local_get_addr_cache; | 9570 delete local_get_addr_cache; |
9515 local_get_addr_cache = NULL; | 9571 local_get_addr_cache = NULL; |
9516 | 9572 |
9517 /* Free memory occupied by the in hash table, we won't need it | 9573 /* Free memory occupied by the in hash table, we won't need it |
9518 again. */ | 9574 again. */ |
9524 ->traverse <variable_table_type *, emit_notes_for_differences_1> | 9580 ->traverse <variable_table_type *, emit_notes_for_differences_1> |
9525 (shared_hash_htab (empty_shared_hash)); | 9581 (shared_hash_htab (empty_shared_hash)); |
9526 | 9582 |
9527 dataflow_set_destroy (&cur); | 9583 dataflow_set_destroy (&cur); |
9528 | 9584 |
9529 if (MAY_HAVE_DEBUG_INSNS) | 9585 if (MAY_HAVE_DEBUG_BIND_INSNS) |
9530 delete dropped_values; | 9586 delete dropped_values; |
9531 dropped_values = NULL; | 9587 dropped_values = NULL; |
9532 | 9588 |
9533 emit_notes = false; | 9589 emit_notes = false; |
9534 } | 9590 } |
9535 | 9591 |
9536 /* If there is a declaration and offset associated with register/memory RTL | 9592 /* If there is a declaration and offset associated with register/memory RTL |
9537 assign declaration to *DECLP and offset to *OFFSETP, and return true. */ | 9593 assign declaration to *DECLP and offset to *OFFSETP, and return true. */ |
9538 | 9594 |
9539 static bool | 9595 static bool |
9540 vt_get_decl_and_offset (rtx rtl, tree *declp, HOST_WIDE_INT *offsetp) | 9596 vt_get_decl_and_offset (rtx rtl, tree *declp, poly_int64 *offsetp) |
9541 { | 9597 { |
9542 if (REG_P (rtl)) | 9598 if (REG_P (rtl)) |
9543 { | 9599 { |
9544 if (REG_ATTRS (rtl)) | 9600 if (REG_ATTRS (rtl)) |
9545 { | 9601 { |
9561 break; | 9617 break; |
9562 if (!decl) | 9618 if (!decl) |
9563 decl = REG_EXPR (reg); | 9619 decl = REG_EXPR (reg); |
9564 if (REG_EXPR (reg) != decl) | 9620 if (REG_EXPR (reg) != decl) |
9565 break; | 9621 break; |
9566 if (REG_OFFSET (reg) < offset) | 9622 HOST_WIDE_INT this_offset; |
9567 offset = REG_OFFSET (reg); | 9623 if (!track_offset_p (REG_OFFSET (reg), &this_offset)) |
9624 break; | |
9625 offset = MIN (offset, this_offset); | |
9568 } | 9626 } |
9569 | 9627 |
9570 if (i == len) | 9628 if (i == len) |
9571 { | 9629 { |
9572 *declp = decl; | 9630 *declp = decl; |
9577 else if (MEM_P (rtl)) | 9635 else if (MEM_P (rtl)) |
9578 { | 9636 { |
9579 if (MEM_ATTRS (rtl)) | 9637 if (MEM_ATTRS (rtl)) |
9580 { | 9638 { |
9581 *declp = MEM_EXPR (rtl); | 9639 *declp = MEM_EXPR (rtl); |
9582 *offsetp = INT_MEM_OFFSET (rtl); | 9640 *offsetp = int_mem_offset (rtl); |
9583 return true; | 9641 return true; |
9584 } | 9642 } |
9585 } | 9643 } |
9586 return false; | 9644 return false; |
9587 } | 9645 } |
9606 { | 9664 { |
9607 rtx decl_rtl = DECL_RTL_IF_SET (parm); | 9665 rtx decl_rtl = DECL_RTL_IF_SET (parm); |
9608 rtx incoming = DECL_INCOMING_RTL (parm); | 9666 rtx incoming = DECL_INCOMING_RTL (parm); |
9609 tree decl; | 9667 tree decl; |
9610 machine_mode mode; | 9668 machine_mode mode; |
9611 HOST_WIDE_INT offset; | 9669 poly_int64 offset; |
9612 dataflow_set *out; | 9670 dataflow_set *out; |
9613 decl_or_value dv; | 9671 decl_or_value dv; |
9672 bool incoming_ok = true; | |
9614 | 9673 |
9615 if (TREE_CODE (parm) != PARM_DECL) | 9674 if (TREE_CODE (parm) != PARM_DECL) |
9616 return; | 9675 return; |
9617 | 9676 |
9618 if (!decl_rtl || !incoming) | 9677 if (!decl_rtl || !incoming) |
9623 | 9682 |
9624 /* If there is a DRAP register or a pseudo in internal_arg_pointer, | 9683 /* If there is a DRAP register or a pseudo in internal_arg_pointer, |
9625 rewrite the incoming location of parameters passed on the stack | 9684 rewrite the incoming location of parameters passed on the stack |
9626 into MEMs based on the argument pointer, so that incoming doesn't | 9685 into MEMs based on the argument pointer, so that incoming doesn't |
9627 depend on a pseudo. */ | 9686 depend on a pseudo. */ |
9687 poly_int64 incoming_offset = 0; | |
9628 if (MEM_P (incoming) | 9688 if (MEM_P (incoming) |
9629 && (XEXP (incoming, 0) == crtl->args.internal_arg_pointer | 9689 && (strip_offset (XEXP (incoming, 0), &incoming_offset) |
9630 || (GET_CODE (XEXP (incoming, 0)) == PLUS | 9690 == crtl->args.internal_arg_pointer)) |
9631 && XEXP (XEXP (incoming, 0), 0) | |
9632 == crtl->args.internal_arg_pointer | |
9633 && CONST_INT_P (XEXP (XEXP (incoming, 0), 1))))) | |
9634 { | 9691 { |
9635 HOST_WIDE_INT off = -FIRST_PARM_OFFSET (current_function_decl); | 9692 HOST_WIDE_INT off = -FIRST_PARM_OFFSET (current_function_decl); |
9636 if (GET_CODE (XEXP (incoming, 0)) == PLUS) | |
9637 off += INTVAL (XEXP (XEXP (incoming, 0), 1)); | |
9638 incoming | 9693 incoming |
9639 = replace_equiv_address_nv (incoming, | 9694 = replace_equiv_address_nv (incoming, |
9640 plus_constant (Pmode, | 9695 plus_constant (Pmode, |
9641 arg_pointer_rtx, off)); | 9696 arg_pointer_rtx, |
9697 off + incoming_offset)); | |
9642 } | 9698 } |
9643 | 9699 |
9644 #ifdef HAVE_window_save | 9700 #ifdef HAVE_window_save |
9645 /* DECL_INCOMING_RTL uses the INCOMING_REGNO of parameter registers. | 9701 /* DECL_INCOMING_RTL uses the INCOMING_REGNO of parameter registers. |
9646 If the target machine has an explicit window save instruction, the | 9702 If the target machine has an explicit window save instruction, the |
9699 } | 9755 } |
9700 #endif | 9756 #endif |
9701 | 9757 |
9702 if (!vt_get_decl_and_offset (incoming, &decl, &offset)) | 9758 if (!vt_get_decl_and_offset (incoming, &decl, &offset)) |
9703 { | 9759 { |
9760 incoming_ok = false; | |
9704 if (MEM_P (incoming)) | 9761 if (MEM_P (incoming)) |
9705 { | 9762 { |
9706 /* This means argument is passed by invisible reference. */ | 9763 /* This means argument is passed by invisible reference. */ |
9707 offset = 0; | 9764 offset = 0; |
9708 decl = parm; | 9765 decl = parm; |
9729 if (decl != get_spill_slot_decl (false)) | 9786 if (decl != get_spill_slot_decl (false)) |
9730 return; | 9787 return; |
9731 offset = 0; | 9788 offset = 0; |
9732 } | 9789 } |
9733 | 9790 |
9734 if (!track_loc_p (incoming, parm, offset, false, &mode, &offset)) | 9791 HOST_WIDE_INT const_offset; |
9792 if (!track_loc_p (incoming, parm, offset, false, &mode, &const_offset)) | |
9735 return; | 9793 return; |
9736 | 9794 |
9737 out = &VTI (ENTRY_BLOCK_PTR_FOR_FN (cfun))->out; | 9795 out = &VTI (ENTRY_BLOCK_PTR_FOR_FN (cfun))->out; |
9738 | 9796 |
9739 dv = dv_from_decl (parm); | 9797 dv = dv_from_decl (parm); |
9750 | 9808 |
9751 /* ??? We shouldn't ever hit this, but it may happen because | 9809 /* ??? We shouldn't ever hit this, but it may happen because |
9752 arguments passed by invisible reference aren't dealt with | 9810 arguments passed by invisible reference aren't dealt with |
9753 above: incoming-rtl will have Pmode rather than the | 9811 above: incoming-rtl will have Pmode rather than the |
9754 expected mode for the type. */ | 9812 expected mode for the type. */ |
9755 if (offset) | 9813 if (const_offset) |
9756 return; | 9814 return; |
9757 | 9815 |
9758 lowpart = var_lowpart (mode, incoming); | 9816 lowpart = var_lowpart (mode, incoming); |
9759 if (!lowpart) | 9817 if (!lowpart) |
9760 return; | 9818 return; |
9765 /* ??? Float-typed values in memory are not handled by | 9823 /* ??? Float-typed values in memory are not handled by |
9766 cselib. */ | 9824 cselib. */ |
9767 if (val) | 9825 if (val) |
9768 { | 9826 { |
9769 preserve_value (val); | 9827 preserve_value (val); |
9770 set_variable_part (out, val->val_rtx, dv, offset, | 9828 set_variable_part (out, val->val_rtx, dv, const_offset, |
9771 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); | 9829 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); |
9772 dv = dv_from_value (val->val_rtx); | 9830 dv = dv_from_value (val->val_rtx); |
9773 } | 9831 } |
9774 | 9832 |
9775 if (MEM_P (incoming)) | 9833 if (MEM_P (incoming)) |
9786 | 9844 |
9787 if (REG_P (incoming)) | 9845 if (REG_P (incoming)) |
9788 { | 9846 { |
9789 incoming = var_lowpart (mode, incoming); | 9847 incoming = var_lowpart (mode, incoming); |
9790 gcc_assert (REGNO (incoming) < FIRST_PSEUDO_REGISTER); | 9848 gcc_assert (REGNO (incoming) < FIRST_PSEUDO_REGISTER); |
9791 attrs_list_insert (&out->regs[REGNO (incoming)], dv, offset, | 9849 attrs_list_insert (&out->regs[REGNO (incoming)], dv, const_offset, |
9792 incoming); | 9850 incoming); |
9793 set_variable_part (out, incoming, dv, offset, | 9851 set_variable_part (out, incoming, dv, const_offset, |
9794 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); | 9852 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); |
9795 if (dv_is_value_p (dv)) | 9853 if (dv_is_value_p (dv)) |
9796 { | 9854 { |
9797 record_entry_value (CSELIB_VAL_PTR (dv_as_value (dv)), incoming); | 9855 record_entry_value (CSELIB_VAL_PTR (dv_as_value (dv)), incoming); |
9798 if (TREE_CODE (TREE_TYPE (parm)) == REFERENCE_TYPE | 9856 if (TREE_CODE (TREE_TYPE (parm)) == REFERENCE_TYPE |
9816 } | 9874 } |
9817 else if (GET_CODE (incoming) == PARALLEL && !dv_onepart_p (dv)) | 9875 else if (GET_CODE (incoming) == PARALLEL && !dv_onepart_p (dv)) |
9818 { | 9876 { |
9819 int i; | 9877 int i; |
9820 | 9878 |
9879 /* The following code relies on vt_get_decl_and_offset returning true for | |
9880 incoming, which might not be always the case. */ | |
9881 if (!incoming_ok) | |
9882 return; | |
9821 for (i = 0; i < XVECLEN (incoming, 0); i++) | 9883 for (i = 0; i < XVECLEN (incoming, 0); i++) |
9822 { | 9884 { |
9823 rtx reg = XEXP (XVECEXP (incoming, 0, i), 0); | 9885 rtx reg = XEXP (XVECEXP (incoming, 0, i), 0); |
9824 offset = REG_OFFSET (reg); | 9886 /* vt_get_decl_and_offset has already checked that the offset |
9887 is a valid variable part. */ | |
9888 const_offset = get_tracked_reg_offset (reg); | |
9825 gcc_assert (REGNO (reg) < FIRST_PSEUDO_REGISTER); | 9889 gcc_assert (REGNO (reg) < FIRST_PSEUDO_REGISTER); |
9826 attrs_list_insert (&out->regs[REGNO (reg)], dv, offset, reg); | 9890 attrs_list_insert (&out->regs[REGNO (reg)], dv, const_offset, reg); |
9827 set_variable_part (out, reg, dv, offset, | 9891 set_variable_part (out, reg, dv, const_offset, |
9828 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); | 9892 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); |
9829 } | 9893 } |
9830 } | 9894 } |
9831 else if (MEM_P (incoming)) | 9895 else if (MEM_P (incoming)) |
9832 { | 9896 { |
9833 incoming = var_lowpart (mode, incoming); | 9897 incoming = var_lowpart (mode, incoming); |
9834 set_variable_part (out, incoming, dv, offset, | 9898 set_variable_part (out, incoming, dv, const_offset, |
9835 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); | 9899 VAR_INIT_STATUS_INITIALIZED, NULL, INSERT); |
9836 } | 9900 } |
9837 } | 9901 } |
9838 | 9902 |
9839 /* Insert function parameters to IN and OUT sets of ENTRY_BLOCK. */ | 9903 /* Insert function parameters to IN and OUT sets of ENTRY_BLOCK. */ |
9843 { | 9907 { |
9844 tree parm; | 9908 tree parm; |
9845 | 9909 |
9846 for (parm = DECL_ARGUMENTS (current_function_decl); | 9910 for (parm = DECL_ARGUMENTS (current_function_decl); |
9847 parm; parm = DECL_CHAIN (parm)) | 9911 parm; parm = DECL_CHAIN (parm)) |
9848 if (!POINTER_BOUNDS_P (parm)) | 9912 vt_add_function_parameter (parm); |
9849 vt_add_function_parameter (parm); | |
9850 | 9913 |
9851 if (DECL_HAS_VALUE_EXPR_P (DECL_RESULT (current_function_decl))) | 9914 if (DECL_HAS_VALUE_EXPR_P (DECL_RESULT (current_function_decl))) |
9852 { | 9915 { |
9853 tree vexpr = DECL_VALUE_EXPR (DECL_RESULT (current_function_decl)); | 9916 tree vexpr = DECL_VALUE_EXPR (DECL_RESULT (current_function_decl)); |
9854 | 9917 |
9884 || !fixed_regs[REGNO (cfa_base_rtx)]) | 9947 || !fixed_regs[REGNO (cfa_base_rtx)]) |
9885 { | 9948 { |
9886 cfa_base_rtx = NULL_RTX; | 9949 cfa_base_rtx = NULL_RTX; |
9887 return; | 9950 return; |
9888 } | 9951 } |
9889 if (!MAY_HAVE_DEBUG_INSNS) | 9952 if (!MAY_HAVE_DEBUG_BIND_INSNS) |
9890 return; | 9953 return; |
9891 | 9954 |
9892 /* Tell alias analysis that cfa_base_rtx should share | 9955 /* Tell alias analysis that cfa_base_rtx should share |
9893 find_base_term value with stack pointer or hard frame pointer. */ | 9956 find_base_term value with stack pointer or hard frame pointer. */ |
9894 if (!frame_pointer_needed) | 9957 if (!frame_pointer_needed) |
9900 VOIDmode, get_insns ()); | 9963 VOIDmode, get_insns ()); |
9901 preserve_value (val); | 9964 preserve_value (val); |
9902 cselib_preserve_cfa_base_value (val, REGNO (cfa_base_rtx)); | 9965 cselib_preserve_cfa_base_value (val, REGNO (cfa_base_rtx)); |
9903 } | 9966 } |
9904 | 9967 |
9968 /* Reemit INSN, a MARKER_DEBUG_INSN, as a note. */ | |
9969 | |
9970 static rtx_insn * | |
9971 reemit_marker_as_note (rtx_insn *insn) | |
9972 { | |
9973 gcc_checking_assert (DEBUG_MARKER_INSN_P (insn)); | |
9974 | |
9975 enum insn_note kind = INSN_DEBUG_MARKER_KIND (insn); | |
9976 | |
9977 switch (kind) | |
9978 { | |
9979 case NOTE_INSN_BEGIN_STMT: | |
9980 case NOTE_INSN_INLINE_ENTRY: | |
9981 { | |
9982 rtx_insn *note = NULL; | |
9983 if (cfun->debug_nonbind_markers) | |
9984 { | |
9985 note = emit_note_before (kind, insn); | |
9986 NOTE_MARKER_LOCATION (note) = INSN_LOCATION (insn); | |
9987 } | |
9988 delete_insn (insn); | |
9989 return note; | |
9990 } | |
9991 | |
9992 default: | |
9993 gcc_unreachable (); | |
9994 } | |
9995 } | |
9996 | |
9905 /* Allocate and initialize the data structures for variable tracking | 9997 /* Allocate and initialize the data structures for variable tracking |
9906 and parse the RTL to get the micro operations. */ | 9998 and parse the RTL to get the micro operations. */ |
9907 | 9999 |
9908 static bool | 10000 static bool |
9909 vt_initialize (void) | 10001 vt_initialize (void) |
9910 { | 10002 { |
9911 basic_block bb; | 10003 basic_block bb; |
9912 HOST_WIDE_INT fp_cfa_offset = -1; | 10004 poly_int64 fp_cfa_offset = -1; |
9913 | 10005 |
9914 alloc_aux_for_blocks (sizeof (variable_tracking_info)); | 10006 alloc_aux_for_blocks (sizeof (variable_tracking_info)); |
9915 | 10007 |
9916 empty_shared_hash = shared_hash_pool.allocate (); | 10008 empty_shared_hash = shared_hash_pool.allocate (); |
9917 empty_shared_hash->refcount = 1; | 10009 empty_shared_hash->refcount = 1; |
9926 dataflow_set_init (&VTI (bb)->in); | 10018 dataflow_set_init (&VTI (bb)->in); |
9927 dataflow_set_init (&VTI (bb)->out); | 10019 dataflow_set_init (&VTI (bb)->out); |
9928 VTI (bb)->permp = NULL; | 10020 VTI (bb)->permp = NULL; |
9929 } | 10021 } |
9930 | 10022 |
9931 if (MAY_HAVE_DEBUG_INSNS) | 10023 if (MAY_HAVE_DEBUG_BIND_INSNS) |
9932 { | 10024 { |
9933 cselib_init (CSELIB_RECORD_MEMORY | CSELIB_PRESERVE_CONSTANTS); | 10025 cselib_init (CSELIB_RECORD_MEMORY | CSELIB_PRESERVE_CONSTANTS); |
9934 scratch_regs = BITMAP_ALLOC (NULL); | 10026 scratch_regs = BITMAP_ALLOC (NULL); |
9935 preserved_values.create (256); | 10027 preserved_values.create (256); |
9936 global_get_addr_cache = new hash_map<rtx, rtx>; | 10028 global_get_addr_cache = new hash_map<rtx, rtx>; |
9939 { | 10031 { |
9940 scratch_regs = NULL; | 10032 scratch_regs = NULL; |
9941 global_get_addr_cache = NULL; | 10033 global_get_addr_cache = NULL; |
9942 } | 10034 } |
9943 | 10035 |
9944 if (MAY_HAVE_DEBUG_INSNS) | 10036 if (MAY_HAVE_DEBUG_BIND_INSNS) |
9945 { | 10037 { |
9946 rtx reg, expr; | 10038 rtx reg, expr; |
9947 int ofst; | 10039 int ofst; |
9948 cselib_val *val; | 10040 cselib_val *val; |
9949 | 10041 |
10022 elim = eliminate_regs (reg, VOIDmode, NULL_RTX); | 10114 elim = eliminate_regs (reg, VOIDmode, NULL_RTX); |
10023 if (elim != reg) | 10115 if (elim != reg) |
10024 { | 10116 { |
10025 if (GET_CODE (elim) == PLUS) | 10117 if (GET_CODE (elim) == PLUS) |
10026 { | 10118 { |
10027 fp_cfa_offset -= INTVAL (XEXP (elim, 1)); | 10119 fp_cfa_offset -= rtx_to_poly_int64 (XEXP (elim, 1)); |
10028 elim = XEXP (elim, 0); | 10120 elim = XEXP (elim, 0); |
10029 } | 10121 } |
10030 if (elim != hard_frame_pointer_rtx) | 10122 if (elim != hard_frame_pointer_rtx) |
10031 fp_cfa_offset = -1; | 10123 fp_cfa_offset = -1; |
10032 } | 10124 } |
10069 { | 10161 { |
10070 rtx_insn *insn; | 10162 rtx_insn *insn; |
10071 HOST_WIDE_INT pre, post = 0; | 10163 HOST_WIDE_INT pre, post = 0; |
10072 basic_block first_bb, last_bb; | 10164 basic_block first_bb, last_bb; |
10073 | 10165 |
10074 if (MAY_HAVE_DEBUG_INSNS) | 10166 if (MAY_HAVE_DEBUG_BIND_INSNS) |
10075 { | 10167 { |
10076 cselib_record_sets_hook = add_with_sets; | 10168 cselib_record_sets_hook = add_with_sets; |
10077 if (dump_file && (dump_flags & TDF_DETAILS)) | 10169 if (dump_file && (dump_flags & TDF_DETAILS)) |
10078 fprintf (dump_file, "first value: %i\n", | 10170 fprintf (dump_file, "first value: %i\n", |
10079 cselib_get_next_uid ()); | 10171 cselib_get_next_uid ()); |
10096 /* Add the micro-operations to the vector. */ | 10188 /* Add the micro-operations to the vector. */ |
10097 FOR_BB_BETWEEN (bb, first_bb, last_bb->next_bb, next_bb) | 10189 FOR_BB_BETWEEN (bb, first_bb, last_bb->next_bb, next_bb) |
10098 { | 10190 { |
10099 HOST_WIDE_INT offset = VTI (bb)->out.stack_adjust; | 10191 HOST_WIDE_INT offset = VTI (bb)->out.stack_adjust; |
10100 VTI (bb)->out.stack_adjust = VTI (bb)->in.stack_adjust; | 10192 VTI (bb)->out.stack_adjust = VTI (bb)->in.stack_adjust; |
10101 for (insn = BB_HEAD (bb); insn != NEXT_INSN (BB_END (bb)); | 10193 |
10102 insn = NEXT_INSN (insn)) | 10194 rtx_insn *next; |
10195 FOR_BB_INSNS_SAFE (bb, insn, next) | |
10103 { | 10196 { |
10104 if (INSN_P (insn)) | 10197 if (INSN_P (insn)) |
10105 { | 10198 { |
10106 if (!frame_pointer_needed) | 10199 if (!frame_pointer_needed) |
10107 { | 10200 { |
10114 mo.insn = insn; | 10207 mo.insn = insn; |
10115 if (dump_file && (dump_flags & TDF_DETAILS)) | 10208 if (dump_file && (dump_flags & TDF_DETAILS)) |
10116 log_op_type (PATTERN (insn), bb, insn, | 10209 log_op_type (PATTERN (insn), bb, insn, |
10117 MO_ADJUST, dump_file); | 10210 MO_ADJUST, dump_file); |
10118 VTI (bb)->mos.safe_push (mo); | 10211 VTI (bb)->mos.safe_push (mo); |
10119 VTI (bb)->out.stack_adjust += pre; | |
10120 } | 10212 } |
10121 } | 10213 } |
10122 | 10214 |
10123 cselib_hook_called = false; | 10215 cselib_hook_called = false; |
10124 adjust_insn (bb, insn); | 10216 adjust_insn (bb, insn); |
10125 if (MAY_HAVE_DEBUG_INSNS) | 10217 |
10218 if (!frame_pointer_needed && pre) | |
10219 VTI (bb)->out.stack_adjust += pre; | |
10220 | |
10221 if (DEBUG_MARKER_INSN_P (insn)) | |
10222 { | |
10223 reemit_marker_as_note (insn); | |
10224 continue; | |
10225 } | |
10226 | |
10227 if (MAY_HAVE_DEBUG_BIND_INSNS) | |
10126 { | 10228 { |
10127 if (CALL_P (insn)) | 10229 if (CALL_P (insn)) |
10128 prepare_call_arguments (bb, insn); | 10230 prepare_call_arguments (bb, insn); |
10129 cselib_process_insn (insn); | 10231 cselib_process_insn (insn); |
10130 if (dump_file && (dump_flags & TDF_DETAILS)) | 10232 if (dump_file && (dump_flags & TDF_DETAILS)) |
10131 { | 10233 { |
10132 print_rtl_single (dump_file, insn); | 10234 if (dump_flags & TDF_SLIM) |
10235 dump_insn_slim (dump_file, insn); | |
10236 else | |
10237 print_rtl_single (dump_file, insn); | |
10133 dump_cselib_table (dump_file); | 10238 dump_cselib_table (dump_file); |
10134 } | 10239 } |
10135 } | 10240 } |
10136 if (!cselib_hook_called) | 10241 if (!cselib_hook_called) |
10137 add_with_sets (insn, 0, 0); | 10242 add_with_sets (insn, 0, 0); |
10148 MO_ADJUST, dump_file); | 10253 MO_ADJUST, dump_file); |
10149 VTI (bb)->mos.safe_push (mo); | 10254 VTI (bb)->mos.safe_push (mo); |
10150 VTI (bb)->out.stack_adjust += post; | 10255 VTI (bb)->out.stack_adjust += post; |
10151 } | 10256 } |
10152 | 10257 |
10153 if (fp_cfa_offset != -1 | 10258 if (maybe_ne (fp_cfa_offset, -1) |
10154 && hard_frame_pointer_adjustment == -1 | 10259 && known_eq (hard_frame_pointer_adjustment, -1) |
10155 && fp_setter_insn (insn)) | 10260 && fp_setter_insn (insn)) |
10156 { | 10261 { |
10157 vt_init_cfa_base (); | 10262 vt_init_cfa_base (); |
10158 hard_frame_pointer_adjustment = fp_cfa_offset; | 10263 hard_frame_pointer_adjustment = fp_cfa_offset; |
10159 /* Disassociate sp from fp now. */ | 10264 /* Disassociate sp from fp now. */ |
10160 if (MAY_HAVE_DEBUG_INSNS) | 10265 if (MAY_HAVE_DEBUG_BIND_INSNS) |
10161 { | 10266 { |
10162 cselib_val *v; | 10267 cselib_val *v; |
10163 cselib_invalidate_rtx (stack_pointer_rtx); | 10268 cselib_invalidate_rtx (stack_pointer_rtx); |
10164 v = cselib_lookup (stack_pointer_rtx, Pmode, 1, | 10269 v = cselib_lookup (stack_pointer_rtx, Pmode, 1, |
10165 VOIDmode); | 10270 VOIDmode); |
10175 gcc_assert (offset == VTI (bb)->out.stack_adjust); | 10280 gcc_assert (offset == VTI (bb)->out.stack_adjust); |
10176 } | 10281 } |
10177 | 10282 |
10178 bb = last_bb; | 10283 bb = last_bb; |
10179 | 10284 |
10180 if (MAY_HAVE_DEBUG_INSNS) | 10285 if (MAY_HAVE_DEBUG_BIND_INSNS) |
10181 { | 10286 { |
10182 cselib_preserve_only_values (); | 10287 cselib_preserve_only_values (); |
10183 cselib_reset_table (cselib_get_next_uid ()); | 10288 cselib_reset_table (cselib_get_next_uid ()); |
10184 cselib_record_sets_hook = NULL; | 10289 cselib_record_sets_hook = NULL; |
10185 } | 10290 } |
10195 NOTE_INSN_DELETED_DEBUG_LABEL in the entire compilation | 10300 NOTE_INSN_DELETED_DEBUG_LABEL in the entire compilation |
10196 a unique label number. */ | 10301 a unique label number. */ |
10197 | 10302 |
10198 static int debug_label_num = 1; | 10303 static int debug_label_num = 1; |
10199 | 10304 |
10200 /* Get rid of all debug insns from the insn stream. */ | 10305 /* Remove from the insn stream a single debug insn used for |
10201 | 10306 variable tracking at assignments. */ |
10202 static void | 10307 |
10203 delete_debug_insns (void) | 10308 static inline void |
10309 delete_vta_debug_insn (rtx_insn *insn) | |
10310 { | |
10311 if (DEBUG_MARKER_INSN_P (insn)) | |
10312 { | |
10313 reemit_marker_as_note (insn); | |
10314 return; | |
10315 } | |
10316 | |
10317 tree decl = INSN_VAR_LOCATION_DECL (insn); | |
10318 if (TREE_CODE (decl) == LABEL_DECL | |
10319 && DECL_NAME (decl) | |
10320 && !DECL_RTL_SET_P (decl)) | |
10321 { | |
10322 PUT_CODE (insn, NOTE); | |
10323 NOTE_KIND (insn) = NOTE_INSN_DELETED_DEBUG_LABEL; | |
10324 NOTE_DELETED_LABEL_NAME (insn) | |
10325 = IDENTIFIER_POINTER (DECL_NAME (decl)); | |
10326 SET_DECL_RTL (decl, insn); | |
10327 CODE_LABEL_NUMBER (insn) = debug_label_num++; | |
10328 } | |
10329 else | |
10330 delete_insn (insn); | |
10331 } | |
10332 | |
10333 /* Remove from the insn stream all debug insns used for variable | |
10334 tracking at assignments. USE_CFG should be false if the cfg is no | |
10335 longer usable. */ | |
10336 | |
10337 void | |
10338 delete_vta_debug_insns (bool use_cfg) | |
10204 { | 10339 { |
10205 basic_block bb; | 10340 basic_block bb; |
10206 rtx_insn *insn, *next; | 10341 rtx_insn *insn, *next; |
10207 | 10342 |
10208 if (!MAY_HAVE_DEBUG_INSNS) | 10343 if (!MAY_HAVE_DEBUG_INSNS) |
10209 return; | 10344 return; |
10210 | 10345 |
10211 FOR_EACH_BB_FN (bb, cfun) | 10346 if (use_cfg) |
10212 { | 10347 FOR_EACH_BB_FN (bb, cfun) |
10213 FOR_BB_INSNS_SAFE (bb, insn, next) | 10348 { |
10349 FOR_BB_INSNS_SAFE (bb, insn, next) | |
10350 if (DEBUG_INSN_P (insn)) | |
10351 delete_vta_debug_insn (insn); | |
10352 } | |
10353 else | |
10354 for (insn = get_insns (); insn; insn = next) | |
10355 { | |
10356 next = NEXT_INSN (insn); | |
10214 if (DEBUG_INSN_P (insn)) | 10357 if (DEBUG_INSN_P (insn)) |
10215 { | 10358 delete_vta_debug_insn (insn); |
10216 tree decl = INSN_VAR_LOCATION_DECL (insn); | 10359 } |
10217 if (TREE_CODE (decl) == LABEL_DECL | |
10218 && DECL_NAME (decl) | |
10219 && !DECL_RTL_SET_P (decl)) | |
10220 { | |
10221 PUT_CODE (insn, NOTE); | |
10222 NOTE_KIND (insn) = NOTE_INSN_DELETED_DEBUG_LABEL; | |
10223 NOTE_DELETED_LABEL_NAME (insn) | |
10224 = IDENTIFIER_POINTER (DECL_NAME (decl)); | |
10225 SET_DECL_RTL (decl, insn); | |
10226 CODE_LABEL_NUMBER (insn) = debug_label_num++; | |
10227 } | |
10228 else | |
10229 delete_insn (insn); | |
10230 } | |
10231 } | |
10232 } | 10360 } |
10233 | 10361 |
10234 /* Run a fast, BB-local only version of var tracking, to take care of | 10362 /* Run a fast, BB-local only version of var tracking, to take care of |
10235 information that we don't do global analysis on, such that not all | 10363 information that we don't do global analysis on, such that not all |
10236 information is lost. If SKIPPED holds, we're skipping the global | 10364 information is lost. If SKIPPED holds, we're skipping the global |
10239 | 10367 |
10240 static void | 10368 static void |
10241 vt_debug_insns_local (bool skipped ATTRIBUTE_UNUSED) | 10369 vt_debug_insns_local (bool skipped ATTRIBUTE_UNUSED) |
10242 { | 10370 { |
10243 /* ??? Just skip it all for now. */ | 10371 /* ??? Just skip it all for now. */ |
10244 delete_debug_insns (); | 10372 delete_vta_debug_insns (true); |
10245 } | 10373 } |
10246 | 10374 |
10247 /* Free the data structures needed for variable tracking. */ | 10375 /* Free the data structures needed for variable tracking. */ |
10248 | 10376 |
10249 static void | 10377 static void |
10274 attrs_pool.release (); | 10402 attrs_pool.release (); |
10275 var_pool.release (); | 10403 var_pool.release (); |
10276 location_chain_pool.release (); | 10404 location_chain_pool.release (); |
10277 shared_hash_pool.release (); | 10405 shared_hash_pool.release (); |
10278 | 10406 |
10279 if (MAY_HAVE_DEBUG_INSNS) | 10407 if (MAY_HAVE_DEBUG_BIND_INSNS) |
10280 { | 10408 { |
10281 if (global_get_addr_cache) | 10409 if (global_get_addr_cache) |
10282 delete global_get_addr_cache; | 10410 delete global_get_addr_cache; |
10283 global_get_addr_cache = NULL; | 10411 global_get_addr_cache = NULL; |
10284 loc_exp_dep_pool.release (); | 10412 loc_exp_dep_pool.release (); |
10304 static inline unsigned int | 10432 static inline unsigned int |
10305 variable_tracking_main_1 (void) | 10433 variable_tracking_main_1 (void) |
10306 { | 10434 { |
10307 bool success; | 10435 bool success; |
10308 | 10436 |
10309 if (flag_var_tracking_assignments < 0 | 10437 /* We won't be called as a separate pass if flag_var_tracking is not |
10438 set, but final may call us to turn debug markers into notes. */ | |
10439 if ((!flag_var_tracking && MAY_HAVE_DEBUG_INSNS) | |
10440 || flag_var_tracking_assignments < 0 | |
10310 /* Var-tracking right now assumes the IR doesn't contain | 10441 /* Var-tracking right now assumes the IR doesn't contain |
10311 any pseudos at this point. */ | 10442 any pseudos at this point. */ |
10312 || targetm.no_register_allocation) | 10443 || targetm.no_register_allocation) |
10313 { | 10444 { |
10314 delete_debug_insns (); | 10445 delete_vta_debug_insns (true); |
10315 return 0; | 10446 return 0; |
10316 } | 10447 } |
10317 | 10448 |
10318 if (n_basic_blocks_for_fn (cfun) > 500 && | 10449 if (!flag_var_tracking) |
10319 n_edges_for_fn (cfun) / n_basic_blocks_for_fn (cfun) >= 20) | 10450 return 0; |
10451 | |
10452 if (n_basic_blocks_for_fn (cfun) > 500 | |
10453 && n_edges_for_fn (cfun) / n_basic_blocks_for_fn (cfun) >= 20) | |
10320 { | 10454 { |
10321 vt_debug_insns_local (true); | 10455 vt_debug_insns_local (true); |
10322 return 0; | 10456 return 0; |
10323 } | 10457 } |
10324 | 10458 |
10334 | 10468 |
10335 if (!success && flag_var_tracking_assignments > 0) | 10469 if (!success && flag_var_tracking_assignments > 0) |
10336 { | 10470 { |
10337 vt_finalize (); | 10471 vt_finalize (); |
10338 | 10472 |
10339 delete_debug_insns (); | 10473 delete_vta_debug_insns (true); |
10340 | 10474 |
10341 /* This is later restored by our caller. */ | 10475 /* This is later restored by our caller. */ |
10342 flag_var_tracking_assignments = 0; | 10476 flag_var_tracking_assignments = 0; |
10343 | 10477 |
10344 success = vt_initialize (); | 10478 success = vt_initialize (); |