1 # DP: Some fixes for ARM from Philip Blundell
3 Tue Jul 27 18:42:12 1999 Bernd Schmidt <bernds@cygnus.co.uk>
5 * reload1.c (reload_reg_free_for_value_p): RELOAD_OTHER reloads with
6 an earlyclobbered output conflict with RELOAD_INPUT reloads.
8 Tue Jul 27 18:42:12 1999 Bernd Schmidt <bernds@cygnus.co.uk>
10 * reload1.c (reload_reg_free_for_value_p): If two reloads overlap in
11 their lifetimes, and one of them has an output, they conflict.
13 Fri Jul 16 10:29:48 1999 Philip Blundell <pb@nexus.co.uk>
15 * config/arm/arm.c (legitimize_pic_address): Handle LABEL_REF
17 (arm_poke_function_name): Avoid warning.
18 * config/arm/arm.h (LEGITIMATE_CONSTANT_P): Allow anything when
20 (GO_IF_LEGITIMATE_INDEX): Fix handling of HImode values.
21 (LEGITIMATE_PIC_OPERAND): Disallow references to labels.
22 * config/arm/linux-elf.h (MULTILIB_DEFAULTS): Define.
23 (SUBTARGET_EXTRA_LINK_SPEC): Provide alternative definition for
24 use with new binutils.
25 * config/arm/linux-elf26.h (MULTILIB_DEFAULTS): Define.
26 * config/arm/t-linux (EXTRA_MULTILIB_PARTS): Define.
27 (MULTILIB_OPTIONS, MULTILIB_DIRNAMES): Multilib for hard/soft
30 * function.c (rtx_equal_for_addressof_p): New function.
31 (purge_addressof_1): Use it instead of rtx_equal_p.
33 --- gcc/function.c 1999/05/20 22:26:35 1.90.4.1
34 +++ gcc/function.c 1999/07/16 09:30:04
35 @@ -3042,6 +3042,105 @@
36 extracted by usage MEM with narrower mode. */
37 static rtx purge_addressof_replacements;
39 +/* Return 1 if X and Y are identical-looking rtx's.
40 + This is the Lisp function EQUAL for rtx arguments. */
43 +rtx_equal_for_addressof_p (x, y)
48 + register enum rtx_code code;
53 + if (x == 0 || y == 0)
56 + code = GET_CODE (x);
57 + /* Rtx's of different codes cannot be equal. */
58 + if (code != GET_CODE (y))
61 + /* (MULT:SI x y) and (MULT:HI x y) are NOT equivalent.
62 + (REG:SI x) and (REG:HI x) are NOT equivalent.
63 + But (MEM:SI x) and (MEM:HI x) are equivalent for our purposes. */
65 + if (code != MEM && (GET_MODE (x) != GET_MODE (y)))
68 + /* REG, LABEL_REF, and SYMBOL_REF can be compared nonrecursively. */
71 + return REGNO (x) == REGNO (y);
72 + else if (code == LABEL_REF)
73 + return XEXP (x, 0) == XEXP (y, 0);
74 + else if (code == SYMBOL_REF)
75 + return XSTR (x, 0) == XSTR (y, 0);
76 + else if (code == SCRATCH || code == CONST_DOUBLE)
79 + /* Compare the elements. If any pair of corresponding elements
80 + fail to match, return 0 for the whole things. */
82 + fmt = GET_RTX_FORMAT (code);
83 + for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
88 + if (XWINT (x, i) != XWINT (y, i))
94 + if (XINT (x, i) != XINT (y, i))
100 + /* Two vectors must have the same length. */
101 + if (XVECLEN (x, i) != XVECLEN (y, i))
104 + /* And the corresponding elements must match. */
105 + for (j = 0; j < XVECLEN (x, i); j++)
106 + if (rtx_equal_p (XVECEXP (x, i, j), XVECEXP (y, i, j)) == 0)
111 + if (rtx_equal_p (XEXP (x, i), XEXP (y, i)) == 0)
117 + if (strcmp (XSTR (x, i), XSTR (y, i)))
122 + /* These are just backpointers, so they don't matter. */
128 + /* It is believed that rtx's at this level will never
129 + contain anything but integers and other rtx's,
130 + except for within LABEL_REFs and SYMBOL_REFs. */
138 /* Helper function for purge_addressof. See if the rtx expression at *LOC
139 in INSN needs to be changed. If FORCE, always put any ADDRESSOFs into
141 @@ -3122,7 +3221,7 @@
142 for (tem = purge_bitfield_addressof_replacements;
144 tem = XEXP (XEXP (tem, 1), 1))
145 - if (rtx_equal_p (x, XEXP (tem, 0)))
146 + if (rtx_equal_for_addressof_p (x, XEXP (tem, 0)))
148 *loc = XEXP (XEXP (tem, 1), 0);
150 @@ -3132,7 +3231,7 @@
151 for (tem = purge_addressof_replacements;
153 tem = XEXP (XEXP (tem, 1), 1))
154 - if (rtx_equal_p (XEXP (x, 0), XEXP (tem, 0)))
155 + if (rtx_equal_for_addressof_p (XEXP (x, 0), XEXP (tem, 0)))
157 rtx z = XEXP (XEXP (tem, 1), 0);
159 --- gcc/config/arm/arm.c 1999/06/19 06:34:36 1.43.4.5
160 +++ gcc/config/arm/arm.c 1999/07/16 09:27:53
161 @@ -1528,7 +1528,20 @@ legitimize_pic_address (orig, mode, reg)
162 return gen_rtx_PLUS (Pmode, base, offset);
164 else if (GET_CODE (orig) == LABEL_REF)
165 - current_function_uses_pic_offset_table = 1;
167 + current_function_uses_pic_offset_table = 1;
171 + rtx pic_ref, address = gen_reg_rtx (Pmode);
173 + emit_insn (gen_pic_load_addr (address, orig));
174 + pic_ref = gen_rtx_PLUS (Pmode, pic_offset_table_rtx,
176 + emit_move_insn (address, pic_ref);
183 @@ -5445,7 +5458,7 @@ arm_poke_function_name (stream, name)
186 length = strlen (name);
187 - alignlength = (length + 1) + 3 & ~3;
188 + alignlength = ((length + 1) + 3) & ~3;
190 ASM_OUTPUT_ASCII (stream, name, length + 1);
191 ASM_OUTPUT_ALIGN (stream, 2);
192 --- gcc/config/arm/arm.h 1999/06/19 05:37:07 1.34.4.3
193 +++ gcc/config/arm/arm.h 1999/07/16 09:28:04
194 @@ -1378,9 +1378,11 @@ do { \
196 On the ARM, allow any integer (invalid ones are removed later by insn
197 patterns), nice doubles and symbol_refs which refer to the function's
198 - constant pool XXX. */
199 -#define LEGITIMATE_CONSTANT_P(X) (! label_mentioned_p (X))
202 + When generating PIC code, allow anything. */
203 +#define LEGITIMATE_CONSTANT_P(X) (flag_pic || ! label_mentioned_p (X))
205 /* Symbols in the text segment can be accessed without indirecting via the
206 constant pool; it may take an extra binary operation, but this is still
207 faster than indirecting via memory. Don't do this when not optimizing,
208 @@ -1495,9 +1497,8 @@ do \
209 && INTVAL (op) <= 31) \
212 - /* NASTY: Since this limits the addressing of unsigned byte loads */ \
213 range = ((MODE) == HImode || (MODE) == QImode) \
214 - ? (arm_arch4 ? 256 : 4095) : 4096; \
215 + ? (((MODE) == HImode && arm_arch4) ? 256 : 4095) : 4096; \
216 if (code == CONST_INT && INTVAL (INDEX) < range \
217 && INTVAL (INDEX) > -range) \
219 @@ -1813,12 +1814,13 @@ extern int arm_pic_register;
221 #define FINALIZE_PIC arm_finalize_pic ()
223 -/* We can't directly access anything that contains a symbol,
224 +/* We can't directly access anything that contains a symbol or label,
225 nor can we indirect via the constant pool. */
226 #define LEGITIMATE_PIC_OPERAND_P(X) \
227 - (! symbol_mentioned_p (X) \
228 + (! symbol_mentioned_p (X) && ! label_mentioned_p (X) \
229 && (! CONSTANT_POOL_ADDRESS_P (X) \
230 - || ! symbol_mentioned_p (get_pool_constant (X))))
231 + || (! symbol_mentioned_p (get_pool_constant (X))) \
232 + && (! label_mentioned_p (get_pool_constant (X)))))
234 /* We need to know when we are making a constant pool; this determines
235 whether data needs to be in the GOT or can be referenced via a GOT
236 --- gcc/config/arm/arm.md 1999/06/02 06:43:14 1.27.4.2
237 +++ gcc/config/arm/arm.md 1999/07/16 09:28:31
238 @@ -2627,7 +2627,8 @@
239 : preserve_subexpressions_p ()));
242 - if (CONSTANT_P (operands[1]) && flag_pic)
243 + if ((CONSTANT_P (operands[1]) || symbol_mentioned_p (operands[1])
244 + || label_mentioned_p (operands[1])) && flag_pic)
245 operands[1] = legitimize_pic_address (operands[1], SImode,
248 --- gcc/config/arm/linux-elf.h 1999/03/31 10:25:34 1.7
249 +++ gcc/config/arm/linux-elf.h 1999/07/16 09:28:33
250 @@ -28,10 +28,16 @@ Boston, MA 02111-1307, USA. */
251 /* Default is to use APCS-32 mode. */
252 #ifndef SUBTARGET_DEFAULT_APCS26
253 #define TARGET_DEFAULT (ARM_FLAG_APCS_32 | ARM_FLAG_SHORT_BYTE)
255 #define SUBTARGET_EXTRA_LINK_SPEC \
256 + " %{mapcs-26:-m armelf_linux26} %{!mapcs-26:-m armelf_linux} -p"
258 +#define SUBTARGET_EXTRA_LINK_SPEC \
259 " %{mapcs-26:-m elf32arm26} %{!mapcs-26:-m elf32arm}"
261 #define SUBTARGET_EXTRA_ASM_SPEC \
262 " %{mapcs-26:-mapcs-26} %(!mapcs-26:-mapcs-32}"
263 +#define MULTILIB_DEFAULTS { "mlittle-endian", "mhard-float", "mapcs-32", "mno-thumb-interwork" }
266 /* This was defined in linux.h. Define it here also. */
267 --- gcc/config/arm/linux-elf26.h 1998/12/16 21:01:40 1.2
268 +++ gcc/config/arm/linux-elf26.h 1999/07/16 09:28:33
269 @@ -29,4 +29,6 @@ Boston, MA 02111-1307, USA. */
271 #define TARGET_DEFAULT (ARM_FLAG_SHORT_BYTE)
273 +#define MULTILIB_DEFAULTS { "mlittle-endian", "mhard-float", "mapcs-26", "mno-thumb-interwork" }
275 #include "arm/linux-elf.h"
276 --- gcc/config/arm/t-linux 1999/03/26 15:30:20 1.5
277 +++ gcc/config/arm/t-linux 1999/07/16 09:28:33
278 @@ -13,10 +13,15 @@ LIBGCC1 = libgcc1-asm.a
279 LIB1ASMSRC = arm/lib1funcs.asm
280 LIB1ASMFUNCS = _udivsi3 _divsi3 _umodsi3 _modsi3 _dvmd_lnx
282 +MULTILIB_OPTIONS = mhard-float/msoft-float
283 +MULTILIB_DIRNAMES = hard-float soft-float
285 # If you want to build both APCS variants as multilib options this is how
287 -#MULTILIB_OPTIONS = mapcs-32/apcs-26
288 -#MULTILIB_DIRNAMES = apcs-32 apcs-26
289 +#MULTILIB_OPTIONS += mapcs-32/mapcs-26
290 +#MULTILIB_DIRNAMES += apcs-32 apcs-26
292 +EXTRA_MULTILIB_PARTS = crtbegin.o crtend.o
294 LIBGCC = stmp-multilib
295 INSTALL_LIBGCC = install-multilib
296 --- gcc/jump.c 1999/05/31 13:30:06 1.59.4.2
297 +++ gcc/jump.c 1999/07/30 10:14:30
299 static rtx delete_unreferenced_labels PROTO((rtx));
300 static void delete_noop_moves PROTO((rtx));
301 static int calculate_can_reach_end PROTO((rtx, int, int));
302 -static int duplicate_loop_exit_test PROTO((rtx));
303 +static int duplicate_loop_exit_test PROTO((rtx, int));
304 static void find_cross_jump PROTO((rtx, rtx, int, rtx *, rtx *));
305 static void do_cross_jump PROTO((rtx, rtx, rtx));
306 static int jump_back_p PROTO((rtx, rtx));
308 && simplejump_p (temp1))
310 temp = PREV_INSN (insn);
311 - if (duplicate_loop_exit_test (insn))
312 + if (duplicate_loop_exit_test (insn, after_regscan))
315 next = NEXT_INSN (temp);
316 @@ -2544,8 +2544,9 @@
317 values of regno_first_uid and regno_last_uid. */
320 -duplicate_loop_exit_test (loop_start)
321 +duplicate_loop_exit_test (loop_start, after_regscan)
325 rtx insn, set, reg, p, link;
327 @@ -2658,6 +2659,9 @@
328 reg_map[REGNO (reg)] = gen_reg_rtx (GET_MODE (reg));
333 + reg_scan_update (exitcode, lastexit, max_reg);
335 /* Now copy each insn. */
336 for (insn = exitcode; insn != lastexit; insn = NEXT_INSN (insn))
337 --- gcc/reload1.c 1999/07/07 01:05:39 1.145.4.1
338 +++ gcc/reload1.c 1999/07/30 10:15:23
339 @@ -5281,7 +5281,7 @@
340 if (! reload_in[i] || ! rtx_equal_p (reload_in[i], value)
341 || reload_out[i] || out)
345 switch (reload_when_needed[i])
347 case RELOAD_FOR_OTHER_ADDRESS:
348 @@ -5360,6 +5360,11 @@
349 if (! reload_in[i] || rtx_equal_p (reload_in[i], value))
351 time2 = MAX_RECOG_OPERANDS * 4 + 4;
352 + /* Earlyclobbered outputs must conflict with inputs. */
353 + for (j = 0; j < n_earlyclobbers; j++)
354 + if (reload_out[i] == reload_earlyclobbers[j])
355 + time2 = MAX_RECOG_OPERANDS * 4 + 3;
360 @@ -5375,7 +5380,8 @@
363 && (! reload_in[i] || reload_out[i]
364 - || ! rtx_equal_p (reload_in[i], value)))
365 + || ! rtx_equal_p (reload_in[i], value)
367 || (out && reload_out_reg[reloadnum]
368 && time2 >= MAX_RECOG_OPERANDS * 4 + 3))