1 /* Output routines for GCC for ARM/Thumb
2 Copyright (C) 1996 Cygnus Software Technologies Ltd
3 The basis of this contribution was generated by
4 Richard Earnshaw, Advanced RISC Machines Ltd
6 This file is part of GNU CC.
8 GNU CC is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
13 GNU CC is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with GNU CC; see the file COPYING. If not, write to
20 the Free Software Foundation, 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, USA. */
27 #include "hard-reg-set.h"
30 #include "insn-flags.h"
31 #include "insn-attr.h"
37 int current_function_anonymous_args
= 0;
39 /* Used to parse -mstructure_size_boundary command line option. */
40 char * structure_size_string
= NULL
;
41 int arm_structure_size_boundary
= 32; /* Used to be 8 */
46 reload_memory_operand (op
, mode
)
48 enum machine_mode mode
;
50 int regno
= true_regnum (op
);
52 return (! CONSTANT_P (op
)
54 || (GET_CODE (op
) == REG
55 && REGNO (op
) >= FIRST_PSEUDO_REGISTER
)));
58 /* Return nonzero if op is suitable for the RHS of a cmp instruction. */
60 thumb_cmp_operand (op
, mode
)
62 enum machine_mode mode
;
64 return ((GET_CODE (op
) == CONST_INT
65 && (unsigned HOST_WIDE_INT
) (INTVAL (op
)) < 256)
66 || register_operand (op
, mode
));
70 thumb_shiftable_const (val
)
73 unsigned HOST_WIDE_INT x
= val
;
74 unsigned HOST_WIDE_INT mask
= 0xff;
77 for (i
= 0; i
< 25; i
++)
78 if ((val
& (mask
<< i
)) == val
)
85 thumb_trivial_epilogue ()
89 /* ??? If this function ever returns 1, we get a function without any
90 epilogue at all. It appears that the intent was to cause a "return"
91 insn to be emitted, but that does not happen. */
96 || current_function_outgoing_args_size
97 || current_function_pretend_args_size
)
100 for (regno
= 8; regno
< 13; regno
++)
101 if (regs_ever_live
[regno
] && ! call_used_regs
[regno
])
109 /* Routines for handling the constant pool */
110 /* This is unashamedly hacked from the version in sh.c, since the problem is
111 extremely similar. */
113 /* Thumb instructions cannot load a large constant into a register,
114 constants have to come from a pc relative load. The reference of a pc
115 relative load instruction must be less than 1k infront of the instruction.
116 This means that we often have to dump a constant inside a function, and
117 generate code to branch around it.
119 It is important to minimize this, since the branches will slow things
120 down and make things bigger.
122 Worst case code looks like:
138 We fix this by performing a scan before scheduling, which notices which
139 instructions need to have their operands fetched from the constant table
140 and builds the table.
145 scan, find an instruction which needs a pcrel move. Look forward, find the
146 last barrier which is within MAX_COUNT bytes of the requirement.
147 If there isn't one, make one. Process all the instructions between
148 the find and the barrier.
150 In the above example, we can tell that L3 is within 1k of L1, so
151 the first move can be shrunk from the 2 insn+constant sequence into
152 just 1 insn, and the constant moved to L3 to make:
163 Then the second move becomes the target for the shortening process.
169 rtx value
; /* Value in table */
170 HOST_WIDE_INT next_offset
;
171 enum machine_mode mode
; /* Mode of value */
174 /* The maximum number of constants that can fit into one pool, since
175 the pc relative range is 0...1020 bytes and constants are at least 4
178 #define MAX_POOL_SIZE (1020/4)
179 static pool_node pool_vector
[MAX_POOL_SIZE
];
180 static int pool_size
;
181 static rtx pool_vector_label
;
183 /* Add a constant to the pool and return its label. */
186 add_constant (x
, mode
)
188 enum machine_mode mode
;
192 HOST_WIDE_INT offset
;
194 if (mode
== SImode
&& GET_CODE (x
) == MEM
&& CONSTANT_P (XEXP (x
, 0))
195 && CONSTANT_POOL_ADDRESS_P (XEXP (x
, 0)))
196 x
= get_pool_constant (XEXP (x
, 0));
198 /* First see if we've already got it */
200 for (i
= 0; i
< pool_size
; i
++)
202 if (x
->code
== pool_vector
[i
].value
->code
203 && mode
== pool_vector
[i
].mode
)
205 if (x
->code
== CODE_LABEL
)
207 if (XINT (x
, 3) != XINT (pool_vector
[i
].value
, 3))
210 if (rtx_equal_p (x
, pool_vector
[i
].value
))
211 return pool_vector
[i
].next_offset
- GET_MODE_SIZE (mode
);
217 pool_vector
[pool_size
].next_offset
= GET_MODE_SIZE (mode
);
220 pool_vector_label
= gen_label_rtx ();
222 pool_vector
[pool_size
].next_offset
223 += (offset
= pool_vector
[pool_size
- 1].next_offset
);
225 pool_vector
[pool_size
].value
= x
;
226 pool_vector
[pool_size
].mode
= mode
;
231 /* Output the literal table */
239 scan
= emit_label_after (gen_label_rtx (), scan
);
240 scan
= emit_insn_after (gen_align_4 (), scan
);
241 scan
= emit_label_after (pool_vector_label
, scan
);
243 for (i
= 0; i
< pool_size
; i
++)
245 pool_node
*p
= pool_vector
+ i
;
247 switch (GET_MODE_SIZE (p
->mode
))
250 scan
= emit_insn_after (gen_consttable_4 (p
->value
), scan
);
254 scan
= emit_insn_after (gen_consttable_8 (p
->value
), scan
);
263 scan
= emit_insn_after (gen_consttable_end (), scan
);
264 scan
= emit_barrier_after (scan
);
268 /* Non zero if the src operand needs to be fixed up */
273 enum machine_mode mode
;
275 return ((CONSTANT_P (src
)
276 && (GET_CODE (src
) != CONST_INT
277 || ! (CONST_OK_FOR_LETTER_P (INTVAL (src
), 'I')
278 || CONST_OK_FOR_LETTER_P (INTVAL (src
), 'J')
280 && CONST_OK_FOR_LETTER_P (INTVAL (src
), 'K')))))
281 || (mode
== SImode
&& GET_CODE (src
) == MEM
282 && GET_CODE (XEXP (src
, 0)) == SYMBOL_REF
283 && CONSTANT_POOL_ADDRESS_P (XEXP (src
, 0))));
286 /* Find the last barrier less than MAX_COUNT bytes from FROM, or create one. */
288 #define MAX_COUNT_SI 1000
295 rtx found_barrier
= 0;
298 while (from
&& count
< MAX_COUNT_SI
)
300 if (GET_CODE (from
) == BARRIER
)
303 /* Count the length of this insn */
304 if (GET_CODE (from
) == INSN
305 && GET_CODE (PATTERN (from
)) == SET
306 && CONSTANT_P (SET_SRC (PATTERN (from
)))
307 && CONSTANT_POOL_ADDRESS_P (SET_SRC (PATTERN (from
))))
309 rtx src
= SET_SRC (PATTERN (from
));
313 count
+= get_attr_length (from
);
315 from
= NEXT_INSN (from
);
318 /* We didn't find a barrier in time to
319 dump our stuff, so we'll make one */
320 label
= gen_label_rtx ();
323 from
= PREV_INSN (from
);
325 from
= get_last_insn ();
327 /* Walk back to be just before any jump */
328 while (GET_CODE (from
) == JUMP_INSN
329 || GET_CODE (from
) == NOTE
330 || GET_CODE (from
) == CODE_LABEL
)
331 from
= PREV_INSN (from
);
333 from
= emit_jump_insn_after (gen_jump (label
), from
);
334 JUMP_LABEL (from
) = label
;
335 found_barrier
= emit_barrier_after (from
);
336 emit_label_after (label
, found_barrier
);
337 return found_barrier
;
340 /* Non zero if the insn is a move instruction which needs to be fixed. */
346 if (!INSN_DELETED_P (insn
)
347 && GET_CODE (insn
) == INSN
348 && GET_CODE (PATTERN (insn
)) == SET
)
350 rtx pat
= PATTERN (insn
);
351 rtx src
= SET_SRC (pat
);
352 rtx dst
= SET_DEST (pat
);
353 enum machine_mode mode
= GET_MODE (dst
);
356 return fixit (src
, mode
);
361 #ifdef DBX_DEBUGGING_INFO
363 /* Recursively search through all of the blocks in a function
364 checking to see if any of the variables created in that
365 function match the RTX called 'orig'. If they do then
366 replace them with the RTX called 'new'. */
369 replace_symbols_in_block (tree block
, rtx orig
, rtx
new)
371 for (; block
; block
= BLOCK_CHAIN (block
))
375 if (! TREE_USED (block
))
378 for (sym
= BLOCK_VARS (block
); sym
; sym
= TREE_CHAIN (sym
))
380 if ( (DECL_NAME (sym
) == 0 && TREE_CODE (sym
) != TYPE_DECL
)
381 || DECL_IGNORED_P (sym
)
382 || TREE_CODE (sym
) != VAR_DECL
383 || DECL_EXTERNAL (sym
)
384 || ! rtx_equal_p (DECL_RTL (sym
), orig
)
388 DECL_RTL (sym
) = new;
391 replace_symbols_in_block (BLOCK_SUBBLOCKS (block
), orig
, new);
401 for (insn
= first
; insn
; insn
= NEXT_INSN (insn
))
403 if (broken_move (insn
))
405 /* This is a broken move instruction, scan ahead looking for
406 a barrier to stick the constant table behind */
408 rtx barrier
= find_barrier (insn
);
410 /* Now find all the moves between the points and modify them */
411 for (scan
= insn
; scan
!= barrier
; scan
= NEXT_INSN (scan
))
413 if (broken_move (scan
))
415 /* This is a broken move instruction, add it to the pool */
416 rtx pat
= PATTERN (scan
);
417 rtx src
= SET_SRC (pat
);
418 rtx dst
= SET_DEST (pat
);
419 enum machine_mode mode
= GET_MODE (dst
);
420 HOST_WIDE_INT offset
;
424 /* If this is an HImode constant load, convert it into
425 an SImode constant load. Since the register is always
426 32 bits this is safe. We have to do this, since the
427 load pc-relative instruction only does a 32-bit load. */
431 if (GET_CODE (dst
) != REG
)
433 PUT_MODE (dst
, SImode
);
436 offset
= add_constant (src
, mode
);
437 newsrc
= gen_rtx (MEM
, mode
,
438 plus_constant (gen_rtx (LABEL_REF
,
443 /* Build a jump insn wrapper around the move instead
444 of an ordinary insn, because we want to have room for
445 the target label rtx in fld[7], which an ordinary
446 insn doesn't have. */
447 newinsn
= emit_jump_insn_after (gen_rtx (SET
, VOIDmode
,
449 JUMP_LABEL (newinsn
) = pool_vector_label
;
451 /* But it's still an ordinary insn */
452 PUT_CODE (newinsn
, INSN
);
454 #ifdef DBX_DEBUGGING_INFO
455 /* If debugging information is going to be emitted then we must
456 make sure that any refences to symbols which are removed by
457 the above code are also removed in the descriptions of the
458 function's variables. Failure to do this means that the
459 debugging information emitted could refer to symbols which
460 are not emited by output_constant_pool() because
461 mark_constant_pool() never sees them as being used. */
463 if (optimize
> 0 /* These are the tests used in output_constant_pool() */
464 && flag_expensive_optimizations
/* to decide if the constant pool will be marked. */
465 && write_symbols
== DBX_DEBUG
/* Only necessary if debugging info is being emitted. */
466 && GET_CODE (src
) == MEM
/* Only necessary for references to memory ... */
467 && GET_CODE (XEXP (src
, 0)) == SYMBOL_REF
) /* ... whose address is given by a symbol. */
469 replace_symbols_in_block (DECL_INITIAL (current_function_decl
), src
, newsrc
);
478 dump_table (barrier
);
484 /* Routines for generating rtl */
487 thumb_expand_movstrqi (operands
)
490 rtx out
= copy_to_mode_reg (SImode
, XEXP (operands
[0], 0));
491 rtx in
= copy_to_mode_reg (SImode
, XEXP (operands
[1], 0));
492 HOST_WIDE_INT len
= INTVAL (operands
[2]);
493 HOST_WIDE_INT offset
= 0;
497 emit_insn (gen_movmem12b (out
, in
));
502 emit_insn (gen_movmem8b (out
, in
));
507 rtx reg
= gen_reg_rtx (SImode
);
508 emit_insn (gen_movsi (reg
, gen_rtx (MEM
, SImode
, in
)));
509 emit_insn (gen_movsi (gen_rtx (MEM
, SImode
, out
), reg
));
515 rtx reg
= gen_reg_rtx (HImode
);
516 emit_insn (gen_movhi (reg
, gen_rtx (MEM
, HImode
,
517 plus_constant (in
, offset
))));
518 emit_insn (gen_movhi (gen_rtx (MEM
, HImode
, plus_constant (out
, offset
)),
525 rtx reg
= gen_reg_rtx (QImode
);
526 emit_insn (gen_movqi (reg
, gen_rtx (MEM
, QImode
,
527 plus_constant (in
, offset
))));
528 emit_insn (gen_movqi (gen_rtx (MEM
, QImode
, plus_constant (out
, offset
)),
534 /* Routines for reloading */
537 thumb_reload_out_si (operands
)
543 /* Return non-zero if FUNC must be entered in ARM mode. */
545 is_called_in_ARM_mode (func
)
548 if (TREE_CODE (func
) != FUNCTION_DECL
)
551 /* Ignore the problem about functions whoes address is taken. */
552 if (TARGET_CALLEE_INTERWORKING
&& TREE_PUBLIC (func
))
559 /* Routines for emitting code */
562 final_prescan_insn(insn
)
565 extern int *insn_addresses
;
567 if (flag_print_asm_name
)
568 fprintf (asm_out_file
, "%s 0x%04x\n", ASM_COMMENT_START
,
569 insn_addresses
[INSN_UID (insn
)]);
573 static void thumb_pushpop ( FILE *, int, int ); /* Forward declaration. */
579 number_of_first_bit_set (mask
)
585 (mask
& (1 << bit
)) == 0;
592 #define ARG_1_REGISTER 0
593 #define ARG_2_REGISTER 1
594 #define ARG_3_REGISTER 2
595 #define ARG_4_REGISTER 3
596 #define WORK_REGISTER 7
597 #define FRAME_POINTER 11
598 #define IP_REGISTER 12
599 #define STACK_POINTER STACK_POINTER_REGNUM
600 #define LINK_REGISTER 14
601 #define PROGRAM_COUNTER 15
603 /* Generate code to return from a thumb function. If
604 'reg_containing_return_addr' is -1, then the return address is
605 actually on the stack, at the stack pointer. */
607 thumb_exit (f
, reg_containing_return_addr
)
609 int reg_containing_return_addr
;
611 int regs_available_for_popping
;
619 int restore_a4
= FALSE
;
621 /* Compute the registers we need to pop. */
625 if (reg_containing_return_addr
== -1)
627 regs_to_pop
|= 1 << LINK_REGISTER
;
631 if (TARGET_BACKTRACE
)
633 /* Restore frame pointer and stack pointer. */
634 regs_to_pop
|= (1 << FRAME_POINTER
) | (1 << STACK_POINTER
);
638 /* If there is nothing to pop then just emit the BX instruction and return.*/
639 if (pops_needed
== 0)
641 asm_fprintf (f
, "\tbx\t%s\n", reg_names
[reg_containing_return_addr
]);
646 /* Otherwise if we are not supporting interworking and we have not created
647 a backtrace structure and the function was not entered in ARM mode then
648 just pop the return address straight into the PC. */
649 else if ( ! TARGET_THUMB_INTERWORK
650 && ! TARGET_BACKTRACE
651 && ! is_called_in_ARM_mode (current_function_decl
))
653 asm_fprintf (f
, "\tpop\t{pc}\n" );
658 /* Find out how many of the (return) argument registers we can corrupt. */
659 regs_available_for_popping
= 0;
662 /* If we can deduce the registers used from the function's return value.
663 This is more reliable that examining regs_ever_live[] because that
664 will be set if the register is ever used in the function, not just if
665 the register is used to hold a return value. */
667 if (current_function_return_rtx
!= 0)
668 mode
= GET_MODE (current_function_return_rtx
);
671 mode
= DECL_MODE (DECL_RESULT (current_function_decl
));
673 size
= GET_MODE_SIZE (mode
);
677 /* In a void function we can use any argument register.
678 In a function that returns a structure on the stack
679 we can use the second and third argument registers. */
680 if (mode
== VOIDmode
)
681 regs_available_for_popping
=
682 (1 << ARG_1_REGISTER
)
683 | (1 << ARG_2_REGISTER
)
684 | (1 << ARG_3_REGISTER
);
686 regs_available_for_popping
=
687 (1 << ARG_2_REGISTER
)
688 | (1 << ARG_3_REGISTER
);
690 else if (size
<= 4) regs_available_for_popping
=
691 (1 << ARG_2_REGISTER
)
692 | (1 << ARG_3_REGISTER
);
693 else if (size
<= 8) regs_available_for_popping
=
694 (1 << ARG_3_REGISTER
);
696 /* Match registers to be popped with registers into which we pop them. */
697 for (available
= regs_available_for_popping
,
698 required
= regs_to_pop
;
699 required
!= 0 && available
!= 0;
700 available
&= ~(available
& - available
),
701 required
&= ~(required
& - required
))
704 /* If we have any popping registers left over, remove them. */
706 regs_available_for_popping
&= ~ available
;
708 /* Otherwise if we need another popping register we can use
709 the fourth argument register. */
710 else if (pops_needed
)
712 /* If we have not found any free argument registers and
713 reg a4 contains the return address, we must move it. */
714 if (regs_available_for_popping
== 0
715 && reg_containing_return_addr
== ARG_4_REGISTER
)
717 asm_fprintf (f
, "\tmov\t%s, %s\n",
718 reg_names
[LINK_REGISTER
], reg_names
[ARG_4_REGISTER
]);
719 reg_containing_return_addr
= LINK_REGISTER
;
723 /* Register a4 is being used to hold part of the return value,
724 but we have dire need of a free, low register. */
727 asm_fprintf (f
, "\tmov\t%s, %s\n",
728 reg_names
[IP_REGISTER
], reg_names
[ARG_4_REGISTER
]);
731 if (reg_containing_return_addr
!= ARG_4_REGISTER
)
733 /* The fourth argument register is available. */
734 regs_available_for_popping
|= 1 << ARG_4_REGISTER
;
740 /* Pop as many registers as we can. */
741 thumb_pushpop (f
, regs_available_for_popping
, FALSE
);
743 /* Process the registers we popped. */
744 if (reg_containing_return_addr
== -1)
746 /* The return address was popped into the lowest numbered register. */
747 regs_to_pop
&= ~ (1 << LINK_REGISTER
);
749 reg_containing_return_addr
=
750 number_of_first_bit_set (regs_available_for_popping
);
752 /* Remove this register for the mask of available registers, so that
753 the return address will not be corrupted by futher pops. */
754 regs_available_for_popping
&= ~ (1 << reg_containing_return_addr
);
757 /* If we popped other registers then handle them here. */
758 if (regs_available_for_popping
)
762 /* Work out which register currently contains the frame pointer. */
763 frame_pointer
= number_of_first_bit_set (regs_available_for_popping
);
765 /* Move it into the correct place. */
766 asm_fprintf (f
, "\tmov\tfp, %s\n", reg_names
[frame_pointer
]);
768 /* (Temporarily) remove it from the mask of popped registers. */
769 regs_available_for_popping
&= ~ (1 << frame_pointer
);
770 regs_to_pop
&= ~ (1 << FRAME_POINTER
);
772 if (regs_available_for_popping
)
776 /* We popped the stack pointer as well, find the register that
778 stack_pointer
= number_of_first_bit_set (regs_available_for_popping
);
780 /* Move it into the stack register. */
781 asm_fprintf (f
, "\tmov\tsp, %s\n", reg_names
[stack_pointer
]);
783 /* At this point we have popped all necessary registers, so
784 do not worry about restoring regs_available_for_popping
785 to its correct value:
787 assert (pops_needed == 0)
788 assert (regs_available_for_popping == (1 << frame_pointer))
789 assert (regs_to_pop == (1 << STACK_POINTER)) */
793 /* Since we have just move the popped value into the frame
794 pointer, the popping register is available for reuse, and
795 we know that we still have the stack pointer left to pop. */
796 regs_available_for_popping
|= (1 << frame_pointer
);
800 /* If we still have registers left on the stack, but we no longer have
801 any registers into which we can pop them, then we must move the return
802 address into the link register and make available the register that
804 if (regs_available_for_popping
== 0 && pops_needed
> 0)
806 regs_available_for_popping
|= 1 << reg_containing_return_addr
;
808 asm_fprintf (f
, "\tmov\t%s, %s\n",
809 reg_names
[LINK_REGISTER
],
810 reg_names
[reg_containing_return_addr
]);
812 reg_containing_return_addr
= LINK_REGISTER
;
815 /* If we have registers left on the stack then pop some more.
816 We know that at most we will want to pop FP and SP. */
822 thumb_pushpop (f
, regs_available_for_popping
, FALSE
);
824 /* We have popped either FP or SP.
825 Move whichever one it is into the correct register. */
826 popped_into
= number_of_first_bit_set (regs_available_for_popping
);
827 move_to
= number_of_first_bit_set (regs_to_pop
);
829 asm_fprintf (f
, "\tmov\t%s, %s\n",
830 reg_names
[move_to
], reg_names
[popped_into
]);
832 regs_to_pop
&= ~ (1 << move_to
);
837 /* If we still have not popped everything then we must have only
838 had one register available to us and we are now popping the SP. */
843 thumb_pushpop (f
, regs_available_for_popping
, FALSE
);
845 popped_into
= number_of_first_bit_set (regs_available_for_popping
);
847 asm_fprintf (f
, "\tmov\tsp, %s\n", reg_names
[popped_into
]);
850 assert (regs_to_pop == (1 << STACK_POINTER))
851 assert (pops_needed == 1)
855 /* If necessary restore the a4 register. */
858 if (reg_containing_return_addr
!= LINK_REGISTER
)
860 asm_fprintf (f
, "\tmov\t%s, %s\n",
861 reg_names
[LINK_REGISTER
], reg_names
[ARG_4_REGISTER
]);
862 reg_containing_return_addr
= LINK_REGISTER
;
865 asm_fprintf (f
, "\tmov\t%s, %s\n",
866 reg_names
[ARG_4_REGISTER
], reg_names
[IP_REGISTER
]);
869 /* Return to caller. */
870 asm_fprintf (f
, "\tbx\t%s\n", reg_names
[reg_containing_return_addr
]);
873 /* Emit code to push or pop registers to or from the stack. */
875 thumb_pushpop (f
, mask
, push
)
881 int lo_mask
= mask
& 0xFF;
883 if (lo_mask
== 0 && ! push
&& (mask
& (1 << 15)))
885 /* Special case. Do not generate a POP PC statement here, do it in
892 asm_fprintf (f
, "\t%s\t{", push
? "push" : "pop");
894 /* Look at the low registers first. */
896 for (regno
= 0; regno
< 8; regno
++, lo_mask
>>= 1)
900 asm_fprintf (f
, reg_names
[regno
]);
902 if ((lo_mask
& ~1) != 0)
903 asm_fprintf (f
, ", ");
907 if (push
&& (mask
& (1 << 14)))
909 /* Catch pushing the LR. */
912 asm_fprintf (f
, ", ");
914 asm_fprintf (f
, reg_names
[14]);
916 else if (!push
&& (mask
& (1 << 15)))
918 /* Catch popping the PC. */
920 if (TARGET_THUMB_INTERWORK
|| TARGET_BACKTRACE
)
922 /* The PC is never poped directly, instead
923 it is popped into r3 and then BX is used. */
925 asm_fprintf (f
, "}\n");
934 asm_fprintf (f
, ", ");
936 asm_fprintf (f
, reg_names
[15]);
940 asm_fprintf (f
, "}\n");
943 /* Returns non-zero if the current function contains a far jump */
946 far_jump_used_p (void)
950 for (insn
= get_insns (); insn
; insn
= NEXT_INSN (insn
))
952 if (GET_CODE (insn
) == JUMP_INSN
953 /* Ignore tablejump patterns. */
954 && GET_CODE (PATTERN (insn
)) != ADDR_VEC
955 && GET_CODE (PATTERN (insn
)) != ADDR_DIFF_VEC
956 && get_attr_far_jump (insn
) == FAR_JUMP_YES
)
963 static int return_used_this_function
= 0;
969 int live_regs_mask
= 0;
971 return_used_this_function
= 1;
973 for (regno
= 0; regno
< 8; regno
++)
974 if (regs_ever_live
[regno
] && ! call_used_regs
[regno
])
975 live_regs_mask
|= 1 << regno
;
977 if (live_regs_mask
== 0)
979 if (leaf_function_p () && ! far_jump_used_p())
981 thumb_exit (asm_out_file
, 14);
983 else if ( TARGET_THUMB_INTERWORK
985 || is_called_in_ARM_mode (current_function_decl
))
987 thumb_exit (asm_out_file
, -1);
990 asm_fprintf (asm_out_file
, "\tpop\t{pc}\n");
994 asm_fprintf (asm_out_file
, "\tpop\t{");
996 for (regno
= 0; live_regs_mask
; regno
++, live_regs_mask
>>= 1)
997 if (live_regs_mask
& 1)
999 asm_fprintf (asm_out_file
, reg_names
[regno
]);
1000 if (live_regs_mask
& ~1)
1001 asm_fprintf (asm_out_file
, ", ");
1004 if ( TARGET_THUMB_INTERWORK
1006 || is_called_in_ARM_mode (current_function_decl
))
1008 asm_fprintf (asm_out_file
, "}\n");
1009 thumb_exit (asm_out_file
, -1);
1012 asm_fprintf (asm_out_file
, ", pc}\n");
1019 thumb_function_prologue (f
, frame_size
)
1023 int amount
= frame_size
+ current_function_outgoing_args_size
;
1024 int live_regs_mask
= 0;
1025 int high_regs_pushed
= 0;
1026 int store_arg_regs
= 0;
1029 if (is_called_in_ARM_mode (current_function_decl
))
1032 if (GET_CODE (DECL_RTL (current_function_decl
)) != MEM
)
1034 if (GET_CODE (XEXP (DECL_RTL (current_function_decl
), 0)) != SYMBOL_REF
)
1036 name
= XSTR (XEXP (DECL_RTL (current_function_decl
), 0), 0);
1038 /* Generate code sequence to switch us into Thumb mode. */
1039 /* The .code 32 directive has already been emitted by
1040 ASM_DECLARE_FUNCITON_NAME */
1041 asm_fprintf (f
, "\torr\tr12, pc, #1\n");
1042 asm_fprintf (f
, "\tbx\tr12\n");
1044 /* Generate a label, so that the debugger will notice the
1045 change in instruction sets. This label is also used by
1046 the assembler to bypass the ARM code when this function
1047 is called from a Thumb encoded function elsewhere in the
1048 same file. Hence the definition of STUB_NAME here must
1049 agree with the definition in gas/config/tc-arm.c */
1051 #define STUB_NAME ".real_start_of"
1053 asm_fprintf (f
, "\t.code\t16\n");
1054 asm_fprintf (f
, "\t.globl %s%U%s\n", STUB_NAME
, name
);
1055 asm_fprintf (f
, "\t.thumb_func\n");
1056 asm_fprintf (f
, "%s%U%s:\n", STUB_NAME
, name
);
1059 if (current_function_anonymous_args
&& current_function_pretend_args_size
)
1062 if (current_function_pretend_args_size
)
1066 asm_fprintf (f
, "\tpush\t{");
1067 for (regno
= 4 - current_function_pretend_args_size
/ 4 ; regno
< 4;
1069 asm_fprintf (f
, "%s%s", reg_names
[regno
], regno
== 3 ? "" : ", ");
1070 asm_fprintf (f
, "}\n");
1073 asm_fprintf (f
, "\tsub\t%Rsp, %Rsp, #%d\n",
1074 current_function_pretend_args_size
);
1077 for (regno
= 0; regno
< 8; regno
++)
1078 if (regs_ever_live
[regno
] && ! call_used_regs
[regno
])
1079 live_regs_mask
|= 1 << regno
;
1081 if (live_regs_mask
|| ! leaf_function_p () || far_jump_used_p())
1082 live_regs_mask
|= 1 << 14;
1084 if (TARGET_BACKTRACE
)
1088 int work_register
= 0;
1091 /* We have been asked to create a stack backtrace structure.
1092 The code looks like this:
1096 0 sub SP, #16 Reserve space for 4 registers.
1097 2 push {R7} Get a work register.
1098 4 add R7, SP, #20 Get the stack pointer before the push.
1099 6 str R7, [SP, #8] Store the stack pointer (before reserving the space).
1100 8 mov R7, PC Get hold of the start of this code plus 12.
1101 10 str R7, [SP, #16] Store it.
1102 12 mov R7, FP Get hold of the current frame pointer.
1103 14 str R7, [SP, #4] Store it.
1104 16 mov R7, LR Get hold of the current return address.
1105 18 str R7, [SP, #12] Store it.
1106 20 add R7, SP, #16 Point at the start of the backtrace structure.
1107 22 mov FP, R7 Put this value into the frame pointer. */
1109 if ((live_regs_mask
& 0xFF) == 0)
1111 /* See if the a4 register is free. */
1113 if (regs_ever_live
[ 3 ] == 0)
1115 else /* We must push a register of our own */
1116 live_regs_mask
|= (1 << 7);
1119 if (work_register
== 0)
1121 /* Select a register from the list that will be pushed to use as our work register. */
1123 for (work_register
= 8; work_register
--;)
1124 if ((1 << work_register
) & live_regs_mask
)
1128 name
= reg_names
[ work_register
];
1130 asm_fprintf (f
, "\tsub\tsp, sp, #16\t@ Create stack backtrace structure\n");
1133 thumb_pushpop (f
, live_regs_mask
, 1);
1135 for (offset
= 0, work_register
= 1 << 15; work_register
; work_register
>>= 1)
1136 if (work_register
& live_regs_mask
)
1139 asm_fprintf (f
, "\tadd\t%s, sp, #%d\n",
1140 name
, offset
+ 16 + current_function_pretend_args_size
);
1142 asm_fprintf (f
, "\tstr\t%s, [sp, #%d]\n", name
, offset
+ 4);
1144 /* Make sure that the instruction fetching the PC is in the right place
1145 to calculate "start of backtrace creation code + 12". */
1149 asm_fprintf (f
, "\tmov\t%s, pc\n", name
);
1150 asm_fprintf (f
, "\tstr\t%s, [sp, #%d]\n", name
, offset
+ 12);
1151 asm_fprintf (f
, "\tmov\t%s, fp\n", name
);
1152 asm_fprintf (f
, "\tstr\t%s, [sp, #%d]\n", name
, offset
);
1156 asm_fprintf (f
, "\tmov\t%s, fp\n", name
);
1157 asm_fprintf (f
, "\tstr\t%s, [sp, #%d]\n", name
, offset
);
1158 asm_fprintf (f
, "\tmov\t%s, pc\n", name
);
1159 asm_fprintf (f
, "\tstr\t%s, [sp, #%d]\n", name
, offset
+ 12);
1162 asm_fprintf (f
, "\tmov\t%s, lr\n", name
);
1163 asm_fprintf (f
, "\tstr\t%s, [sp, #%d]\n", name
, offset
+ 8);
1164 asm_fprintf (f
, "\tadd\t%s, sp, #%d\n", name
, offset
+ 12);
1165 asm_fprintf (f
, "\tmov\tfp, %s\t\t@ Backtrace structure created\n", name
);
1167 else if (live_regs_mask
)
1168 thumb_pushpop (f
, live_regs_mask
, 1);
1170 for (regno
= 8; regno
< 13; regno
++)
1172 if (regs_ever_live
[regno
] && ! call_used_regs
[regno
])
1176 if (high_regs_pushed
)
1178 int pushable_regs
= 0;
1179 int mask
= live_regs_mask
& 0xff;
1182 for (next_hi_reg
= 12; next_hi_reg
> 7; next_hi_reg
--)
1184 if (regs_ever_live
[next_hi_reg
] && ! call_used_regs
[next_hi_reg
])
1188 pushable_regs
= mask
;
1190 if (pushable_regs
== 0)
1192 /* desperation time -- this probably will never happen */
1193 if (regs_ever_live
[3] || ! call_used_regs
[3])
1194 asm_fprintf (f
, "\tmov\t%s, %s\n", reg_names
[12], reg_names
[3]);
1198 while (high_regs_pushed
> 0)
1200 for (regno
= 7; regno
>= 0; regno
--)
1202 if (mask
& (1 << regno
))
1204 asm_fprintf (f
, "\tmov\t%s, %s\n", reg_names
[regno
],
1205 reg_names
[next_hi_reg
]);
1207 if (high_regs_pushed
)
1208 for (next_hi_reg
--; next_hi_reg
> 7; next_hi_reg
--)
1210 if (regs_ever_live
[next_hi_reg
]
1211 && ! call_used_regs
[next_hi_reg
])
1216 mask
&= ~ ((1 << regno
) - 1);
1221 thumb_pushpop (f
, mask
, 1);
1224 if (pushable_regs
== 0 && (regs_ever_live
[3] || ! call_used_regs
[3]))
1225 asm_fprintf (f
, "\tmov\t%s, %s\n", reg_names
[3], reg_names
[12]);
1230 thumb_expand_prologue ()
1232 HOST_WIDE_INT amount
= (get_frame_size ()
1233 + current_function_outgoing_args_size
);
1240 for (regno
= 0; regno
< 8; regno
++)
1241 if (regs_ever_live
[regno
] && ! call_used_regs
[regno
])
1242 live_regs_mask
|= 1 << regno
;
1245 emit_insn (gen_addsi3 (stack_pointer_rtx
, stack_pointer_rtx
,
1246 GEN_INT (-amount
)));
1251 if ((live_regs_mask
& 0xff) == 0) /* Very unlikely */
1252 emit_insn (gen_movsi (spare
= gen_rtx (REG
, SImode
, 12),
1253 reg
= gen_rtx (REG
, SImode
, 4)));
1256 for (regno
= 0; regno
< 8; regno
++)
1257 if (live_regs_mask
& (1 << regno
))
1259 reg
= gen_rtx (REG
, SImode
, regno
);
1262 emit_insn (gen_movsi (reg
, GEN_INT (-amount
)));
1263 emit_insn (gen_addsi3 (stack_pointer_rtx
, stack_pointer_rtx
, reg
));
1264 if ((live_regs_mask
& 0xff) == 0)
1265 emit_insn (gen_movsi (reg
, spare
));
1269 if (frame_pointer_needed
)
1271 if (current_function_outgoing_args_size
)
1273 rtx offset
= GEN_INT (current_function_outgoing_args_size
);
1275 if (current_function_outgoing_args_size
< 1024)
1276 emit_insn (gen_addsi3 (frame_pointer_rtx
, stack_pointer_rtx
,
1280 emit_insn (gen_movsi (frame_pointer_rtx
, offset
));
1281 emit_insn (gen_addsi3 (frame_pointer_rtx
, frame_pointer_rtx
,
1282 stack_pointer_rtx
));
1286 emit_insn (gen_movsi (frame_pointer_rtx
, stack_pointer_rtx
));
1289 /* if (profile_flag || profile_block_flag) */
1290 emit_insn (gen_blockage ());
1294 thumb_expand_epilogue ()
1296 HOST_WIDE_INT amount
= (get_frame_size ()
1297 + current_function_outgoing_args_size
);
1303 emit_insn (gen_addsi3 (stack_pointer_rtx
, stack_pointer_rtx
,
1307 rtx reg
= gen_rtx (REG
, SImode
, 3); /* Always free in the epilogue */
1309 emit_insn (gen_movsi (reg
, GEN_INT (amount
)));
1310 emit_insn (gen_addsi3 (stack_pointer_rtx
, stack_pointer_rtx
, reg
));
1312 /* if (profile_flag || profile_block_flag) */
1313 emit_insn (gen_blockage ());
1318 thumb_function_epilogue (f
, frame_size
)
1322 /* ??? Probably not safe to set this here, since it assumes that a
1323 function will be emitted as assembly immediately after we generate
1324 RTL for it. This does not happen for inline functions. */
1325 return_used_this_function
= 0;
1326 #if 0 /* TODO : comment not really needed */
1327 fprintf (f
, "%s THUMB Epilogue\n", ASM_COMMENT_START
);
1331 /* The bits which aren't usefully expanded as rtl. */
1333 thumb_unexpanded_epilogue ()
1336 int live_regs_mask
= 0;
1337 int high_regs_pushed
= 0;
1338 int leaf_function
= leaf_function_p ();
1341 if (return_used_this_function
)
1344 for (regno
= 0; regno
< 8; regno
++)
1345 if (regs_ever_live
[regno
] && ! call_used_regs
[regno
])
1346 live_regs_mask
|= 1 << regno
;
1348 for (regno
= 8; regno
< 13; regno
++)
1350 if (regs_ever_live
[regno
] && ! call_used_regs
[regno
])
1351 high_regs_pushed
++;
1354 /* The prolog may have pushed some high registers to use as
1355 work registers. eg the testuite file:
1356 gcc/testsuite/gcc/gcc.c-torture/execute/complex-2.c
1357 compiles to produce:
1358 push {r4, r5, r6, r7, lr}
1362 as part of the prolog. We have to undo that pushing here. */
1364 if (high_regs_pushed
)
1366 int mask
= live_regs_mask
;
1372 /* If we can deduce the registers used from the function's return value.
1373 This is more reliable that examining regs_ever_live[] because that
1374 will be set if the register is ever used in the function, not just if
1375 the register is used to hold a return value. */
1377 if (current_function_return_rtx
!= 0)
1379 mode
= GET_MODE (current_function_return_rtx
);
1384 mode
= DECL_MODE (DECL_RESULT (current_function_decl
));
1387 size
= GET_MODE_SIZE (mode
);
1389 /* Unless we are returning a type of size > 12 register r3 is available. */
1395 /* Oh dear! We have no low registers into which we can pop high registers! */
1397 fatal ("No low registers available for popping high registers");
1400 for (next_hi_reg
= 8; next_hi_reg
< 13; next_hi_reg
++)
1401 if (regs_ever_live
[next_hi_reg
] && ! call_used_regs
[next_hi_reg
])
1404 while (high_regs_pushed
)
1406 /* Find low register(s) into which the high register(s) can be popped. */
1407 for (regno
= 0; regno
< 8; regno
++)
1409 if (mask
& (1 << regno
))
1411 if (high_regs_pushed
== 0)
1415 mask
&= (2 << regno
) - 1; /* A noop if regno == 8 */
1417 /* Pop the values into the low register(s). */
1418 thumb_pushpop (asm_out_file
, mask
, 0);
1420 /* Move the value(s) into the high registers. */
1421 for (regno
= 0; regno
< 8; regno
++)
1423 if (mask
& (1 << regno
))
1425 asm_fprintf (asm_out_file
, "\tmov\t%s, %s\n",
1426 reg_names
[next_hi_reg
], reg_names
[regno
]);
1427 for (next_hi_reg
++; next_hi_reg
< 13; next_hi_reg
++)
1428 if (regs_ever_live
[next_hi_reg
] &&
1429 ! call_used_regs
[next_hi_reg
])
1436 had_to_push_lr
= (live_regs_mask
|| ! leaf_function
|| far_jump_used_p());
1438 if (TARGET_BACKTRACE
&& ((live_regs_mask
& 0xFF) == 0) && regs_ever_live
[ ARG_4_REGISTER
] != 0)
1440 /* The stack backtrace structure creation code had to
1441 push R7 in order to get a work register, so we pop
1444 live_regs_mask
|= (1 << WORK_REGISTER
);
1447 if (current_function_pretend_args_size
== 0 || TARGET_BACKTRACE
)
1450 && ! is_called_in_ARM_mode (current_function_decl
))
1451 live_regs_mask
|= 1 << PROGRAM_COUNTER
;
1453 /* Either no argument registers were pushed or a backtrace
1454 structure was created which includes an adjusted stack
1455 pointer, so just pop everything. */
1458 thumb_pushpop (asm_out_file
, live_regs_mask
, FALSE
);
1460 /* We have either just popped the return address into the
1461 PC or it is was kept in LR for the entire function or
1462 it is still on the stack because we do not want to
1463 return by doing a pop {pc}. */
1465 if ((live_regs_mask
& (1 << PROGRAM_COUNTER
)) == 0)
1466 thumb_exit (asm_out_file
,
1468 && is_called_in_ARM_mode (current_function_decl
)) ? -1 : LINK_REGISTER
);
1472 /* Pop everything but the return address. */
1473 live_regs_mask
&= ~ (1 << PROGRAM_COUNTER
);
1476 thumb_pushpop (asm_out_file
, live_regs_mask
, FALSE
);
1480 /* Get the return address into a temporary register. */
1481 thumb_pushpop (asm_out_file
, 1 << ARG_4_REGISTER
, 0);
1484 /* Remove the argument registers that were pushed onto the stack. */
1485 asm_fprintf (asm_out_file
, "\tadd\t%s, %s, #%d\n",
1486 reg_names
[STACK_POINTER
],
1487 reg_names
[STACK_POINTER
],
1488 current_function_pretend_args_size
);
1490 thumb_exit (asm_out_file
, had_to_push_lr
? ARG_4_REGISTER
: LINK_REGISTER
);
1496 /* Handle the case of a double word load into a low register from
1497 a computed memory address. The computed address may involve a
1498 register which is overwritten by the load. */
1501 thumb_load_double_from_address (operands
)
1510 if (GET_CODE (operands
[0]) != REG
)
1511 fatal ("thumb_load_double_from_address: destination is not a register");
1513 if (GET_CODE (operands
[1]) != MEM
)
1514 fatal ("thumb_load_double_from_address: source is not a computed memory address");
1516 /* Get the memory address. */
1518 addr
= XEXP (operands
[1], 0);
1520 /* Work out how the memory address is computed. */
1522 switch (GET_CODE (addr
))
1525 operands
[2] = gen_rtx (MEM
, SImode
, plus_constant (XEXP (operands
[1], 0), 4));
1527 if (REGNO (operands
[0]) == REGNO (addr
))
1529 output_asm_insn ("ldr\t%H0, %2\t\t%@ created by thumb_load_double_from_address", operands
);
1530 output_asm_insn ("ldr\t%0, %1\t\t%@ created by thumb_load_double_from_address", operands
);
1534 output_asm_insn ("ldr\t%0, %1\t\t%@ created by thumb_load_double_from_address", operands
);
1535 output_asm_insn ("ldr\t%H0, %2\t\t%@ created by thumb_load_double_from_address", operands
);
1540 /* Compute <address> + 4 for the high order load. */
1542 operands
[2] = gen_rtx (MEM
, SImode
, plus_constant (XEXP (operands
[1], 0), 4));
1544 output_asm_insn ("ldr\t%0, %1\t\t%@ created by thumb_load_double_from_address", operands
);
1545 output_asm_insn ("ldr\t%H0, %2\t\t%@ created by thumb_load_double_from_address", operands
);
1549 arg1
= XEXP (addr
, 0);
1550 arg2
= XEXP (addr
, 1);
1552 if (CONSTANT_P (arg1
))
1553 base
= arg2
, offset
= arg1
;
1555 base
= arg1
, offset
= arg2
;
1557 if (GET_CODE (base
) != REG
)
1558 fatal ("thumb_load_double_from_address: base is not a register");
1560 /* Catch the case of <address> = <reg> + <reg> */
1562 if (GET_CODE (offset
) == REG
)
1564 int reg_offset
= REGNO (offset
);
1565 int reg_base
= REGNO (base
);
1566 int reg_dest
= REGNO (operands
[0]);
1568 /* Add the base and offset registers together into the higher destination register. */
1570 fprintf (asm_out_file
, "\tadd\t%s, %s, %s\t\t%s created by thumb_load_double_from_address",
1571 reg_names
[ reg_dest
+ 1 ],
1572 reg_names
[ reg_base
],
1573 reg_names
[ reg_offset
],
1576 /* Load the lower destination register from the address in the higher destination register. */
1578 fprintf (asm_out_file
, "\tldr\t%s, [%s, #0]\t\t%s created by thumb_load_double_from_address",
1579 reg_names
[ reg_dest
],
1580 reg_names
[ reg_dest
+ 1],
1583 /* Load the higher destination register from its own address plus 4. */
1585 fprintf (asm_out_file
, "\tldr\t%s, [%s, #4]\t\t%s created by thumb_load_double_from_address",
1586 reg_names
[ reg_dest
+ 1 ],
1587 reg_names
[ reg_dest
+ 1 ],
1592 /* Compute <address> + 4 for the high order load. */
1594 operands
[2] = gen_rtx (MEM
, SImode
, plus_constant (XEXP (operands
[1], 0), 4));
1596 /* If the computed address is held in the low order register
1597 then load the high order register first, otherwise always
1598 load the low order register first. */
1600 if (REGNO (operands
[0]) == REGNO (base
))
1602 output_asm_insn ("ldr\t%H0, %2\t\t%@ created by thumb_load_double_from_address", operands
);
1603 output_asm_insn ("ldr\t%0, %1\t\t%@ created by thumb_load_double_from_address", operands
);
1607 output_asm_insn ("ldr\t%0, %1\t\t%@ created by thumb_load_double_from_address", operands
);
1608 output_asm_insn ("ldr\t%H0, %2\t\t%@ created by thumb_load_double_from_address", operands
);
1614 /* With no registers to worry about we can just load the value directly. */
1615 operands
[2] = gen_rtx (MEM
, SImode
, plus_constant (XEXP (operands
[1], 0), 4));
1617 output_asm_insn ("ldr\t%H0, %2\t\t%@ created by thumb_load_double_from_address", operands
);
1618 output_asm_insn ("ldr\t%0, %1\t\t%@ created by thumb_load_double_from_address", operands
);
1622 debug_rtx (operands
[1]);
1623 fatal ("thumb_load_double_from_address: Unhandled address calculation");
1631 output_move_mem_multiple (n
, operands
)
1640 if (REGNO (operands
[2]) > REGNO (operands
[3]))
1643 operands
[2] = operands
[3];
1646 output_asm_insn ("ldmia\t%1!, {%2, %3}", operands
);
1647 output_asm_insn ("stmia\t%0!, {%2, %3}", operands
);
1651 if (REGNO (operands
[2]) > REGNO (operands
[3]))
1654 operands
[2] = operands
[3];
1657 if (REGNO (operands
[3]) > REGNO (operands
[4]))
1660 operands
[3] = operands
[4];
1663 if (REGNO (operands
[2]) > REGNO (operands
[3]))
1666 operands
[2] = operands
[3];
1669 output_asm_insn ("ldmia\t%1!, {%2, %3, %4}", operands
);
1670 output_asm_insn ("stmia\t%0!, {%2, %3, %4}", operands
);
1682 thumb_epilogue_size ()
1684 return 42; /* The answer to .... */
1687 static char *conds
[] =
1689 "eq", "ne", "cs", "cc", "mi", "pl", "vs", "vc",
1690 "hi", "ls", "ge", "lt", "gt", "le"
1694 thumb_condition_code (x
, invert
)
1700 switch (GET_CODE (x
))
1702 case EQ
: val
= 0; break;
1703 case NE
: val
= 1; break;
1704 case GEU
: val
= 2; break;
1705 case LTU
: val
= 3; break;
1706 case GTU
: val
= 8; break;
1707 case LEU
: val
= 9; break;
1708 case GE
: val
= 10; break;
1709 case LT
: val
= 11; break;
1710 case GT
: val
= 12; break;
1711 case LE
: val
= 13; break;
1716 return conds
[val
^ invert
];
1720 thumb_print_operand (f
, x
, code
)
1730 fputs (ASM_COMMENT_START
, f
);
1734 fputs (USER_LABEL_PREFIX
, f
);
1739 fputs (thumb_condition_code (x
, 1), f
);
1744 fputs (thumb_condition_code (x
, 0), f
);
1747 /* An explanation of the 'Q', 'R' and 'H' register operands:
1749 In a pair of registers containing a DI or DF value the 'Q'
1750 operand returns the register number of the register containing
1751 the least signficant part of the value. The 'R' operand returns
1752 the register number of the register containing the most
1753 significant part of the value.
1755 The 'H' operand returns the higher of the two register numbers.
1756 On a run where WORDS_BIG_ENDIAN is true the 'H' operand is the
1757 same as the 'Q' operand, since the most signficant part of the
1758 value is held in the lower number register. The reverse is true
1759 on systems where WORDS_BIG_ENDIAN is false.
1761 The purpose of these operands is to distinguish between cases
1762 where the endian-ness of the values is important (for example
1763 when they are added together), and cases where the endian-ness
1764 is irrelevant, but the order of register operations is important.
1765 For example when loading a value from memory into a register
1766 pair, the endian-ness does not matter. Provided that the value
1767 from the lower memory address is put into the lower numbered
1768 register, and the value from the higher address is put into the
1769 higher numbered register, the load will work regardless of whether
1770 the value being loaded is big-wordian or little-wordian. The
1771 order of the two register loads can matter however, if the address
1772 of the memory location is actually held in one of the registers
1773 being overwritten by the load. */
1777 fputs (reg_names
[REGNO (x
) + (WORDS_BIG_ENDIAN
? 1 : 0)], f
);
1783 fputs (reg_names
[REGNO (x
) + (WORDS_BIG_ENDIAN
? 0 : 1)], f
);
1789 fputs (reg_names
[REGNO (x
) + 1], f
);
1796 if (GET_CODE (x
) == REG
)
1797 fputs (reg_names
[REGNO (x
)], f
);
1798 else if (GET_CODE (x
) == MEM
)
1799 output_address (XEXP (x
, 0));
1800 else if (GET_CODE (x
) == CONST_INT
)
1803 output_addr_const (f
, x
);
1809 #ifdef AOF_ASSEMBLER
1810 int arm_text_section_count
= 1;
1813 aof_text_section (in_readonly
)
1816 static char buf
[100];
1819 sprintf (buf
, "\tCODE16\n\tAREA |C$$code%d|, CODE, READONLY",
1820 arm_text_section_count
++);
1824 static int arm_data_section_count
= 1;
1829 static char buf
[100];
1830 sprintf (buf
, "\tAREA |C$$data%d|, DATA", arm_data_section_count
++);
1834 /* The AOF thumb assembler is religiously strict about declarations of
1835 imported and exported symbols, so that it is impossible to declare a
1836 function as imported near the begining of the file, and then to export
1837 it later on. It is, however, possible to delay the decision until all
1838 the functions in the file have been compiled. To get around this, we
1839 maintain a list of the imports and exports, and delete from it any that
1840 are subsequently defined. At the end of compilation we spit the
1841 remainder of the list out before the END directive. */
1845 struct import
*next
;
1849 static struct import
*imports_list
= NULL
;
1852 thumb_aof_add_import (name
)
1857 for (new = imports_list
; new; new = new->next
)
1858 if (new->name
== name
)
1861 new = (struct import
*) xmalloc (sizeof (struct import
));
1862 new->next
= imports_list
;
1868 thumb_aof_delete_import (name
)
1871 struct import
**old
;
1873 for (old
= &imports_list
; *old
; old
= & (*old
)->next
)
1875 if ((*old
)->name
== name
)
1877 *old
= (*old
)->next
;
1884 thumb_aof_dump_imports (f
)
1887 while (imports_list
)
1889 fprintf (f
, "\tIMPORT\t");
1890 assemble_name (f
, imports_list
->name
);
1892 imports_list
= imports_list
->next
;
1897 /* Decide whether a type should be returned in memory (true)
1898 or in a register (false). This is called by the macro
1899 RETURN_IN_MEMORY. */
1902 thumb_return_in_memory (type
)
1905 if (! AGGREGATE_TYPE_P (type
))
1907 /* All simple types are returned in registers. */
1911 else if (int_size_in_bytes (type
) > 4)
1913 /* All structures/unions bigger than one word are returned in memory. */
1917 else if (TREE_CODE (type
) == RECORD_TYPE
)
1921 /* For a struct the APCS says that we must return in a register if
1922 every addressable element has an offset of zero. For practical
1923 purposes this means that the structure can have at most one non-
1924 bit-field element and that this element must be the first one in
1927 /* Find the first field, ignoring non FIELD_DECL things which will
1928 have been created by C++. */
1929 for (field
= TYPE_FIELDS (type
);
1930 field
&& TREE_CODE (field
) != FIELD_DECL
;
1931 field
= TREE_CHAIN (field
))
1935 return 0; /* An empty structure. Allowed by an extension to ANSI C. */
1937 /* Now check the remaining fields, if any. */
1938 for (field
= TREE_CHAIN (field
); field
; field
= TREE_CHAIN (field
))
1940 if (TREE_CODE (field
) != FIELD_DECL
)
1943 if (! DECL_BIT_FIELD_TYPE (field
))
1949 else if (TREE_CODE (type
) == UNION_TYPE
)
1953 /* Unions can be returned in registers if every element is
1954 integral, or can be returned in an integer register. */
1956 for (field
= TYPE_FIELDS (type
);
1958 field
= TREE_CHAIN (field
))
1960 if (TREE_CODE (field
) != FIELD_DECL
)
1963 if (RETURN_IN_MEMORY (TREE_TYPE (field
)))
1969 /* XXX Not sure what should be done for other aggregates, so put them in
1974 void thumb_override_options()
1976 if (structure_size_string
!= NULL
)
1978 int size
= strtol (structure_size_string
, NULL
, 0);
1980 if (size
== 8 || size
== 32)
1981 arm_structure_size_boundary
= size
;
1983 warning ("Structure size boundary can only be set to 8 or 32");