1 /* Definitions for GCC. Part of the machine description for CRIS.
2 Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
3 Free Software Foundation, Inc.
4 Contributed by Axis Communications. Written by Hans-Peter Nilsson.
6 This file is part of GCC.
8 GCC 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 GCC 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 GCC; see the file COPYING. If not, write to
20 the Free Software Foundation, 51 Franklin Street, Fifth Floor,
21 Boston, MA 02110-1301, USA. */
25 #include "coretypes.h"
29 #include "hard-reg-set.h"
31 #include "insn-config.h"
32 #include "conditions.h"
33 #include "insn-attr.h"
45 #include "target-def.h"
49 /* Usable when we have an amount to add or subtract, and want the
50 optimal size of the insn. */
51 #define ADDITIVE_SIZE_MODIFIER(size) \
52 ((size) <= 63 ? "q" : (size) <= 255 ? "u.b" : (size) <= 65535 ? "u.w" : ".d")
54 #define ASSERT_PLT_UNSPEC(x) \
55 CRIS_ASSERT (XINT (x, 1) == CRIS_UNSPEC_PLT \
56 && ((GET_CODE (XVECEXP (x, 0, 0)) == SYMBOL_REF) \
57 || GET_CODE (XVECEXP (x, 0, 0)) == LABEL_REF))
59 #define LOSE_AND_RETURN(msgid, x) \
62 cris_operand_lossage (msgid, x); \
66 enum cris_retinsn_type
67 { CRIS_RETINSN_UNKNOWN = 0, CRIS_RETINSN_RET, CRIS_RETINSN_JUMP };
69 /* Per-function machine data. */
70 struct machine_function GTY(())
72 int needs_return_address_on_stack;
74 /* This is the number of registers we save in the prologue due to
78 enum cris_retinsn_type return_type;
81 /* This little fix suppresses the 'u' or 's' when '%e' in assembly
83 static char cris_output_insn_is_bound = 0;
85 /* This one suppresses printing out the "rPIC+" in
86 "rPIC+sym:GOTOFF+offset" when doing PIC. For a PLT symbol, it
87 suppresses outputting it as [rPIC+sym:GOTPLT] and outputs similarly
88 just the "sym:GOTOFF" part. */
89 static int cris_pic_sympart_only = 0;
91 /* In code for output macros, this is how we know whether e.g. constant
92 goes in code or in a static initializer. */
93 static int in_code = 0;
95 /* Fix for reg_overlap_mentioned_p. */
96 static int cris_reg_overlap_mentioned_p (rtx, rtx);
98 static void cris_print_base (rtx, FILE *);
100 static void cris_print_index (rtx, FILE *);
102 static void cris_output_addr_const (FILE *, rtx);
104 static struct machine_function * cris_init_machine_status (void);
106 static rtx cris_struct_value_rtx (tree, int);
108 static void cris_setup_incoming_varargs (CUMULATIVE_ARGS *, enum machine_mode,
109 tree type, int *, int);
111 static int cris_initial_frame_pointer_offset (void);
113 static int saved_regs_mentioned (rtx);
115 static void cris_operand_lossage (const char *, rtx);
117 static int cris_reg_saved_in_regsave_area (unsigned int, bool);
119 static void cris_asm_output_mi_thunk
120 (FILE *, tree, HOST_WIDE_INT, HOST_WIDE_INT, tree);
122 static void cris_file_start (void);
123 static void cris_init_libfuncs (void);
125 static bool cris_rtx_costs (rtx, int, int, int *);
126 static int cris_address_cost (rtx);
127 static bool cris_pass_by_reference (CUMULATIVE_ARGS *, enum machine_mode,
129 static int cris_arg_partial_bytes (CUMULATIVE_ARGS *, enum machine_mode,
131 static tree cris_md_asm_clobbers (tree, tree, tree);
133 static bool cris_handle_option (size_t, const char *, int);
135 /* This is the parsed result of the "-max-stack-stackframe=" option. If
136 it (still) is zero, then there was no such option given. */
137 int cris_max_stackframe = 0;
139 /* This is the parsed result of the "-march=" option, if given. */
140 int cris_cpu_version = CRIS_DEFAULT_CPU_VERSION;
142 #undef TARGET_ASM_ALIGNED_HI_OP
143 #define TARGET_ASM_ALIGNED_HI_OP "\t.word\t"
144 #undef TARGET_ASM_ALIGNED_SI_OP
145 #define TARGET_ASM_ALIGNED_SI_OP "\t.dword\t"
146 #undef TARGET_ASM_ALIGNED_DI_OP
147 #define TARGET_ASM_ALIGNED_DI_OP "\t.quad\t"
149 /* We need to define these, since the 2byte, 4byte, 8byte op:s are only
150 available in ELF. These "normal" pseudos do not have any alignment
151 constraints or side-effects. */
152 #undef TARGET_ASM_UNALIGNED_HI_OP
153 #define TARGET_ASM_UNALIGNED_HI_OP TARGET_ASM_ALIGNED_HI_OP
155 #undef TARGET_ASM_UNALIGNED_SI_OP
156 #define TARGET_ASM_UNALIGNED_SI_OP TARGET_ASM_ALIGNED_SI_OP
158 #undef TARGET_ASM_UNALIGNED_DI_OP
159 #define TARGET_ASM_UNALIGNED_DI_OP TARGET_ASM_ALIGNED_DI_OP
161 #undef TARGET_ASM_OUTPUT_MI_THUNK
162 #define TARGET_ASM_OUTPUT_MI_THUNK cris_asm_output_mi_thunk
163 #undef TARGET_ASM_CAN_OUTPUT_MI_THUNK
164 #define TARGET_ASM_CAN_OUTPUT_MI_THUNK default_can_output_mi_thunk_no_vcall
166 #undef TARGET_ASM_FILE_START
167 #define TARGET_ASM_FILE_START cris_file_start
169 #undef TARGET_INIT_LIBFUNCS
170 #define TARGET_INIT_LIBFUNCS cris_init_libfuncs
172 #undef TARGET_RTX_COSTS
173 #define TARGET_RTX_COSTS cris_rtx_costs
174 #undef TARGET_ADDRESS_COST
175 #define TARGET_ADDRESS_COST cris_address_cost
177 #undef TARGET_PROMOTE_FUNCTION_ARGS
178 #define TARGET_PROMOTE_FUNCTION_ARGS hook_bool_tree_true
179 #undef TARGET_STRUCT_VALUE_RTX
180 #define TARGET_STRUCT_VALUE_RTX cris_struct_value_rtx
181 #undef TARGET_SETUP_INCOMING_VARARGS
182 #define TARGET_SETUP_INCOMING_VARARGS cris_setup_incoming_varargs
183 #undef TARGET_PASS_BY_REFERENCE
184 #define TARGET_PASS_BY_REFERENCE cris_pass_by_reference
185 #undef TARGET_ARG_PARTIAL_BYTES
186 #define TARGET_ARG_PARTIAL_BYTES cris_arg_partial_bytes
187 #undef TARGET_MD_ASM_CLOBBERS
188 #define TARGET_MD_ASM_CLOBBERS cris_md_asm_clobbers
189 #undef TARGET_DEFAULT_TARGET_FLAGS
190 #define TARGET_DEFAULT_TARGET_FLAGS (TARGET_DEFAULT | CRIS_SUBTARGET_DEFAULT)
191 #undef TARGET_HANDLE_OPTION
192 #define TARGET_HANDLE_OPTION cris_handle_option
194 struct gcc_target targetm = TARGET_INITIALIZER;
196 /* Helper for cris_load_multiple_op and cris_ret_movem_op. */
199 cris_movem_load_rest_p (rtx op, int offs)
201 unsigned int reg_count = XVECLEN (op, 0) - offs;
207 unsigned int regno = 0;
209 /* Perform a quick check so we don't blow up below. FIXME: Adjust for
210 other than (MEM reg). */
212 || GET_CODE (XVECEXP (op, 0, offs)) != SET
213 || GET_CODE (SET_DEST (XVECEXP (op, 0, offs))) != REG
214 || GET_CODE (SET_SRC (XVECEXP (op, 0, offs))) != MEM)
217 /* Check a possible post-inc indicator. */
218 if (GET_CODE (SET_SRC (XVECEXP (op, 0, offs + 1))) == PLUS)
220 rtx reg = XEXP (SET_SRC (XVECEXP (op, 0, offs + 1)), 0);
221 rtx inc = XEXP (SET_SRC (XVECEXP (op, 0, offs + 1)), 1);
227 || !REG_P (SET_DEST (XVECEXP (op, 0, offs + 1)))
228 || REGNO (reg) != REGNO (SET_DEST (XVECEXP (op, 0, offs + 1)))
229 || GET_CODE (inc) != CONST_INT
230 || INTVAL (inc) != (HOST_WIDE_INT) reg_count * 4)
237 /* FIXME: These two only for pre-v32. */
239 regno = reg_count - 1;
241 elt = XVECEXP (op, 0, offs);
242 src_addr = XEXP (SET_SRC (elt), 0);
244 if (GET_CODE (elt) != SET
245 || GET_CODE (SET_DEST (elt)) != REG
246 || GET_MODE (SET_DEST (elt)) != SImode
247 || REGNO (SET_DEST (elt)) != regno
248 || GET_CODE (SET_SRC (elt)) != MEM
249 || GET_MODE (SET_SRC (elt)) != SImode
250 || !memory_address_p (SImode, src_addr))
253 for (setno = 1; i < XVECLEN (op, 0); setno++, i++)
255 rtx elt = XVECEXP (op, 0, i);
258 if (GET_CODE (elt) != SET
259 || GET_CODE (SET_DEST (elt)) != REG
260 || GET_MODE (SET_DEST (elt)) != SImode
261 || REGNO (SET_DEST (elt)) != regno
262 || GET_CODE (SET_SRC (elt)) != MEM
263 || GET_MODE (SET_SRC (elt)) != SImode
264 || GET_CODE (XEXP (SET_SRC (elt), 0)) != PLUS
265 || ! rtx_equal_p (XEXP (XEXP (SET_SRC (elt), 0), 0), src_addr)
266 || GET_CODE (XEXP (XEXP (SET_SRC (elt), 0), 1)) != CONST_INT
267 || INTVAL (XEXP (XEXP (SET_SRC (elt), 0), 1)) != setno * 4)
274 /* Worker function for predicate for the parallel contents in a movem
278 cris_store_multiple_op_p (rtx op)
280 int reg_count = XVECLEN (op, 0);
291 /* Perform a quick check so we don't blow up below. FIXME: Adjust for
292 other than (MEM reg) and (MEM (PLUS reg const)). */
296 elt = XVECEXP (op, 0, 0);
298 if (GET_CODE (elt) != SET)
301 dest = SET_DEST (elt);
303 if (GET_CODE (SET_SRC (elt)) != REG
304 || GET_CODE (dest) != MEM)
307 dest_addr = XEXP (dest, 0);
309 /* Check a possible post-inc indicator. */
310 if (GET_CODE (SET_SRC (XVECEXP (op, 0, 1))) == PLUS)
312 rtx reg = XEXP (SET_SRC (XVECEXP (op, 0, 1)), 0);
313 rtx inc = XEXP (SET_SRC (XVECEXP (op, 0, 1)), 1);
319 || !REG_P (SET_DEST (XVECEXP (op, 0, 1)))
320 || REGNO (reg) != REGNO (SET_DEST (XVECEXP (op, 0, 1)))
321 || GET_CODE (inc) != CONST_INT
322 /* Support increment by number of registers, and by the offset
323 of the destination, if it has the form (MEM (PLUS reg
325 || !((REG_P (dest_addr)
326 && REGNO (dest_addr) == REGNO (reg)
327 && INTVAL (inc) == (HOST_WIDE_INT) reg_count * 4)
328 || (GET_CODE (dest_addr) == PLUS
329 && REG_P (XEXP (dest_addr, 0))
330 && REGNO (XEXP (dest_addr, 0)) == REGNO (reg)
331 && GET_CODE (XEXP (dest_addr, 1)) == CONST_INT
332 && INTVAL (XEXP (dest_addr, 1)) == INTVAL (inc))))
340 /* FIXME: These two only for pre-v32. */
342 regno = reg_count - 1;
344 if (GET_CODE (elt) != SET
345 || GET_CODE (SET_SRC (elt)) != REG
346 || GET_MODE (SET_SRC (elt)) != SImode
347 || REGNO (SET_SRC (elt)) != (unsigned int) regno
348 || GET_CODE (SET_DEST (elt)) != MEM
349 || GET_MODE (SET_DEST (elt)) != SImode)
352 if (REG_P (dest_addr))
354 dest_base = dest_addr;
357 else if (GET_CODE (dest_addr) == PLUS
358 && REG_P (XEXP (dest_addr, 0))
359 && GET_CODE (XEXP (dest_addr, 1)) == CONST_INT)
361 dest_base = XEXP (dest_addr, 0);
362 offset = INTVAL (XEXP (dest_addr, 1));
367 for (setno = 1; i < XVECLEN (op, 0); setno++, i++)
369 rtx elt = XVECEXP (op, 0, i);
372 if (GET_CODE (elt) != SET
373 || GET_CODE (SET_SRC (elt)) != REG
374 || GET_MODE (SET_SRC (elt)) != SImode
375 || REGNO (SET_SRC (elt)) != (unsigned int) regno
376 || GET_CODE (SET_DEST (elt)) != MEM
377 || GET_MODE (SET_DEST (elt)) != SImode
378 || GET_CODE (XEXP (SET_DEST (elt), 0)) != PLUS
379 || ! rtx_equal_p (XEXP (XEXP (SET_DEST (elt), 0), 0), dest_base)
380 || GET_CODE (XEXP (XEXP (SET_DEST (elt), 0), 1)) != CONST_INT
381 || INTVAL (XEXP (XEXP (SET_DEST (elt), 0), 1)) != setno * 4 + offset)
388 /* The CONDITIONAL_REGISTER_USAGE worker. */
391 cris_conditional_register_usage (void)
393 /* FIXME: This isn't nice. We should be able to use that register for
394 something else if the PIC table isn't needed. */
396 fixed_regs[PIC_OFFSET_TABLE_REGNUM]
397 = call_used_regs[PIC_OFFSET_TABLE_REGNUM] = 1;
399 if (TARGET_HAS_MUL_INSNS)
400 fixed_regs[CRIS_MOF_REGNUM] = 0;
402 /* On early versions, we must use the 16-bit condition-code register,
403 which has another name. */
404 if (cris_cpu_version < 8)
405 reg_names[CRIS_CC0_REGNUM] = "ccr";
408 /* Return current_function_uses_pic_offset_table. For use in cris.md,
409 since some generated files do not include function.h. */
412 cris_cfun_uses_pic_table (void)
414 return current_function_uses_pic_offset_table;
417 /* Given an rtx, return the text string corresponding to the CODE of X.
418 Intended for use in the assembly language output section of a
424 cris_output_insn_is_bound = 0;
425 switch (GET_CODE (x))
436 /* This function is for retrieving a part of an instruction name for
437 an operator, for immediate output. If that ever happens for
438 MULT, we need to apply TARGET_MUL_BUG in the caller. Make sure
440 internal_error ("MULT case in cris_op_str");
476 /* Used to control the sign/zero-extend character for the 'e' modifier.
478 cris_output_insn_is_bound = 1;
483 return "Unknown operator";
488 /* Emit an error message when we're in an asm, and a fatal error for
489 "normal" insns. Formatted output isn't easily implemented, since we
490 use output_operand_lossage to output the actual message and handle the
491 categorization of the error. */
494 cris_operand_lossage (const char *msgid, rtx op)
497 output_operand_lossage ("%s", msgid);
500 /* Print an index part of an address to file. */
503 cris_print_index (rtx index, FILE *file)
505 rtx inner = XEXP (index, 0);
507 /* Make the index "additive" unless we'll output a negative number, in
508 which case the sign character is free (as in free beer). */
509 if (GET_CODE (index) != CONST_INT || INTVAL (index) >= 0)
513 fprintf (file, "$%s.b", reg_names[REGNO (index)]);
514 else if (CONSTANT_P (index))
515 cris_output_addr_const (file, index);
516 else if (GET_CODE (index) == MULT)
518 fprintf (file, "$%s.",
519 reg_names[REGNO (XEXP (index, 0))]);
521 putc (INTVAL (XEXP (index, 1)) == 2 ? 'w' : 'd', file);
523 else if (GET_CODE (index) == SIGN_EXTEND &&
524 GET_CODE (inner) == MEM)
526 rtx inner_inner = XEXP (inner, 0);
528 if (GET_CODE (inner_inner) == POST_INC)
530 fprintf (file, "[$%s+].",
531 reg_names[REGNO (XEXP (inner_inner, 0))]);
532 putc (GET_MODE (inner) == HImode ? 'w' : 'b', file);
536 fprintf (file, "[$%s].", reg_names[REGNO (inner_inner)]);
538 putc (GET_MODE (inner) == HImode ? 'w' : 'b', file);
541 else if (GET_CODE (index) == MEM)
543 if (GET_CODE (inner) == POST_INC)
544 fprintf (file, "[$%s+].d", reg_names[REGNO (XEXP (inner, 0))]);
546 fprintf (file, "[$%s].d", reg_names[REGNO (inner)]);
549 cris_operand_lossage ("unexpected index-type in cris_print_index",
553 /* Print a base rtx of an address to file. */
556 cris_print_base (rtx base, FILE *file)
559 fprintf (file, "$%s", reg_names[REGNO (base)]);
560 else if (GET_CODE (base) == POST_INC)
561 fprintf (file, "$%s+", reg_names[REGNO (XEXP (base, 0))]);
563 cris_operand_lossage ("unexpected base-type in cris_print_base",
567 /* Usable as a guard in expressions. */
570 cris_fatal (char *arg)
572 internal_error (arg);
574 /* We'll never get here; this is just to appease compilers. */
578 /* Return nonzero if REGNO is an ordinary register that *needs* to be
579 saved together with other registers, possibly by a MOVEM instruction,
580 or is saved for target-independent reasons. There may be
581 target-dependent reasons to save the register anyway; this is just a
582 wrapper for a complicated conditional. */
585 cris_reg_saved_in_regsave_area (unsigned int regno, bool got_really_used)
588 (((regs_ever_live[regno]
589 && !call_used_regs[regno])
590 || (regno == PIC_OFFSET_TABLE_REGNUM
592 /* It is saved anyway, if there would be a gap. */
594 && regs_ever_live[regno + 1]
595 && !call_used_regs[regno + 1]))))
596 && (regno != FRAME_POINTER_REGNUM || !frame_pointer_needed)
597 && regno != CRIS_SRP_REGNUM)
598 || (current_function_calls_eh_return
599 && (regno == EH_RETURN_DATA_REGNO (0)
600 || regno == EH_RETURN_DATA_REGNO (1)
601 || regno == EH_RETURN_DATA_REGNO (2)
602 || regno == EH_RETURN_DATA_REGNO (3)));
605 /* Return nonzero if there are regs mentioned in the insn that are not all
606 in the call_used regs. This is part of the decision whether an insn
607 can be put in the epilogue. */
610 saved_regs_mentioned (rtx x)
616 /* Mainly stolen from refers_to_regno_p in rtlanal.c. */
624 return !call_used_regs[i];
627 /* If this is a SUBREG of a hard reg, we can see exactly which
628 registers are being modified. Otherwise, handle normally. */
629 i = REGNO (SUBREG_REG (x));
630 return !call_used_regs[i];
636 fmt = GET_RTX_FORMAT (code);
637 for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
641 if (saved_regs_mentioned (XEXP (x, i)))
644 else if (fmt[i] == 'E')
647 for (j = XVECLEN (x, i) - 1; j >=0; j--)
648 if (saved_regs_mentioned (XEXP (x, i)))
656 /* The PRINT_OPERAND worker. */
659 cris_print_operand (FILE *file, rtx x, int code)
663 /* Size-strings corresponding to MULT expressions. */
664 static const char *const mults[] = { "BAD:0", ".b", ".w", "BAD:3", ".d" };
666 /* New code entries should just be added to the switch below. If
667 handling is finished, just return. If handling was just a
668 modification of the operand, the modified operand should be put in
669 "operand", and then do a break to let default handling
670 (zero-modifier) output the operand. */
675 /* Print the unsigned supplied integer as if it were signed
676 and < 0, i.e print 255 or 65535 as -1, 254, 65534 as -2, etc. */
677 if (GET_CODE (x) != CONST_INT
678 || ! CONST_OK_FOR_LETTER_P (INTVAL (x), 'O'))
679 LOSE_AND_RETURN ("invalid operand for 'b' modifier", x);
680 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
681 INTVAL (x)| (INTVAL (x) <= 255 ? ~255 : ~65535));
685 /* Print assembler code for operator. */
686 fprintf (file, "%s", cris_op_str (operand));
690 /* Print the operand without the PIC register. */
691 if (! flag_pic || ! CONSTANT_P (x) || ! cris_gotless_symbol (x))
692 LOSE_AND_RETURN ("invalid operand for 'v' modifier", x);
693 cris_pic_sympart_only++;
694 cris_output_addr_const (file, x);
695 cris_pic_sympart_only--;
700 /* A movem modifier working on a parallel; output the register
704 if (GET_CODE (x) != PARALLEL)
705 LOSE_AND_RETURN ("invalid operand for 'o' modifier", x);
707 /* The second item can be (set reg (plus reg const)) to denote a
710 = (GET_CODE (SET_SRC (XVECEXP (x, 0, 1))) == PLUS
712 : XVECLEN (x, 0) - 1);
714 fprintf (file, "$%s", reg_names [regno]);
720 /* A similar movem modifier; output the memory operand. */
723 if (GET_CODE (x) != PARALLEL)
724 LOSE_AND_RETURN ("invalid operand for 'O' modifier", x);
726 /* The lowest mem operand is in the first item, but perhaps it
727 needs to be output as postincremented. */
728 addr = GET_CODE (SET_SRC (XVECEXP (x, 0, 0))) == MEM
729 ? XEXP (SET_SRC (XVECEXP (x, 0, 0)), 0)
730 : XEXP (SET_DEST (XVECEXP (x, 0, 0)), 0);
732 /* The second item can be a (set reg (plus reg const)) to denote
734 if (GET_CODE (SET_SRC (XVECEXP (x, 0, 1))) == PLUS)
736 /* It's a post-increment, if the address is a naked (reg). */
738 addr = gen_rtx_POST_INC (SImode, addr);
741 /* Otherwise, it's a side-effect; RN=RN+M. */
742 fprintf (file, "[$%s=$%s%s%d]",
743 reg_names [REGNO (SET_DEST (XVECEXP (x, 0, 1)))],
744 reg_names [REGNO (XEXP (addr, 0))],
745 INTVAL (XEXP (addr, 1)) < 0 ? "" : "+",
746 (int) INTVAL (XEXP (addr, 1)));
750 output_address (addr);
755 /* Print the PIC register. Applied to a GOT-less PIC symbol for
757 if (! flag_pic || ! CONSTANT_P (x) || ! cris_gotless_symbol (x))
758 LOSE_AND_RETURN ("invalid operand for 'P' modifier", x);
759 fprintf (file, "$%s", reg_names [PIC_OFFSET_TABLE_REGNUM]);
763 /* Adjust a power of two to its log2. */
764 if (GET_CODE (x) != CONST_INT || exact_log2 (INTVAL (x)) < 0 )
765 LOSE_AND_RETURN ("invalid operand for 'p' modifier", x);
766 fprintf (file, "%d", exact_log2 (INTVAL (x)));
770 /* For an integer, print 'b' or 'w' if <= 255 or <= 65535
771 respectively. This modifier also terminates the inhibiting
772 effects of the 'x' modifier. */
773 cris_output_insn_is_bound = 0;
774 if (GET_MODE (x) == VOIDmode && GET_CODE (x) == CONST_INT)
778 if (INTVAL (x) <= 255)
780 else if (INTVAL (x) <= 65535)
790 /* For a non-integer, print the size of the operand. */
791 putc ((GET_MODE (x) == SImode || GET_MODE (x) == SFmode)
792 ? 'd' : GET_MODE (x) == HImode ? 'w'
793 : GET_MODE (x) == QImode ? 'b'
794 /* If none of the above, emit an erroneous size letter. */
800 /* Const_int: print b for -127 <= x <= 255,
801 w for -32768 <= x <= 65535, else die. */
802 if (GET_CODE (x) != CONST_INT
803 || INTVAL (x) < -32768 || INTVAL (x) > 65535)
804 LOSE_AND_RETURN ("invalid operand for 'z' modifier", x);
805 putc (INTVAL (x) >= -128 && INTVAL (x) <= 255 ? 'b' : 'w', file);
809 /* Output a 'nop' if there's nothing for the delay slot.
810 This method stolen from the sparc files. */
811 if (dbr_sequence_length () == 0)
812 fputs ("\n\tnop", file);
816 /* Output directive for alignment padded with "nop" insns.
817 Optimizing for size, it's plain 4-byte alignment, otherwise we
818 align the section to a cache-line (32 bytes) and skip at max 2
819 bytes, i.e. we skip if it's the last insn on a cache-line. The
820 latter is faster by a small amount (for two test-programs 99.6%
821 and 99.9%) and larger by a small amount (ditto 100.1% and
822 100.2%). This is supposed to be the simplest yet performance-
823 wise least intrusive way to make sure the immediately following
824 (supposed) muls/mulu insn isn't located at the end of a
828 ? ".p2alignw 2,0x050f\n\t"
829 : ".p2alignw 5,0x050f,2\n\t", file);
833 /* Print high (most significant) part of something. */
834 switch (GET_CODE (operand))
837 /* If we're having 64-bit HOST_WIDE_INTs, the whole (DImode)
838 value is kept here, and so may be other than 0 or -1. */
839 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
840 INTVAL (operand_subword (operand, 1, 0, DImode)));
844 /* High part of a long long constant. */
845 if (GET_MODE (operand) == VOIDmode)
847 fprintf (file, HOST_WIDE_INT_PRINT_HEX, CONST_DOUBLE_HIGH (x));
851 LOSE_AND_RETURN ("invalid operand for 'H' modifier", x);
854 /* Print reg + 1. Check that there's not an attempt to print
855 high-parts of registers like stack-pointer or higher. */
856 if (REGNO (operand) > STACK_POINTER_REGNUM - 2)
857 LOSE_AND_RETURN ("bad register", operand);
858 fprintf (file, "$%s", reg_names[REGNO (operand) + 1]);
862 /* Adjust memory address to high part. */
864 rtx adj_mem = operand;
866 = GET_MODE_BITSIZE (GET_MODE (operand)) / BITS_PER_UNIT;
868 /* Adjust so we can use two SImode in DImode.
869 Calling adj_offsettable_operand will make sure it is an
870 offsettable address. Don't do this for a postincrement
871 though; it should remain as it was. */
872 if (GET_CODE (XEXP (adj_mem, 0)) != POST_INC)
874 = adjust_address (adj_mem, GET_MODE (adj_mem), size / 2);
876 output_address (XEXP (adj_mem, 0));
881 LOSE_AND_RETURN ("invalid operand for 'H' modifier", x);
885 /* Strip the MEM expression. */
886 operand = XEXP (operand, 0);
890 /* Print 's' if operand is SIGN_EXTEND or 'u' if ZERO_EXTEND unless
891 cris_output_insn_is_bound is nonzero. */
892 if (GET_CODE (operand) != SIGN_EXTEND
893 && GET_CODE (operand) != ZERO_EXTEND
894 && GET_CODE (operand) != CONST_INT)
895 LOSE_AND_RETURN ("invalid operand for 'e' modifier", x);
897 if (cris_output_insn_is_bound)
899 cris_output_insn_is_bound = 0;
903 putc (GET_CODE (operand) == SIGN_EXTEND
904 || (GET_CODE (operand) == CONST_INT && INTVAL (operand) < 0)
909 /* Print the size letter of the inner element. We can do it by
910 calling ourselves with the 's' modifier. */
911 if (GET_CODE (operand) != SIGN_EXTEND && GET_CODE (operand) != ZERO_EXTEND)
912 LOSE_AND_RETURN ("invalid operand for 'm' modifier", x);
913 cris_print_operand (file, XEXP (operand, 0), 's');
917 /* Print the least significant part of operand. */
918 if (GET_CODE (operand) == CONST_DOUBLE)
920 fprintf (file, HOST_WIDE_INT_PRINT_HEX, CONST_DOUBLE_LOW (x));
923 else if (HOST_BITS_PER_WIDE_INT > 32 && GET_CODE (operand) == CONST_INT)
925 fprintf (file, HOST_WIDE_INT_PRINT_HEX,
926 INTVAL (x) & ((unsigned int) 0x7fffffff * 2 + 1));
929 /* Otherwise the least significant part equals the normal part,
930 so handle it normally. */
934 /* When emitting an add for the high part of a DImode constant, we
935 want to use addq for 0 and adds.w for -1. */
936 if (GET_CODE (operand) != CONST_INT)
937 LOSE_AND_RETURN ("invalid operand for 'A' modifier", x);
938 fprintf (file, INTVAL (operand) < 0 ? "adds.w" : "addq");
942 /* If this is a GOT symbol, print it as :GOT regardless of -fpic. */
943 if (flag_pic && CONSTANT_P (operand) && cris_got_symbol (operand))
945 cris_output_addr_const (file, operand);
946 fprintf (file, ":GOT");
952 /* When emitting an sub for the high part of a DImode constant, we
953 want to use subq for 0 and subs.w for -1. */
954 if (GET_CODE (operand) != CONST_INT)
955 LOSE_AND_RETURN ("invalid operand for 'D' modifier", x);
956 fprintf (file, INTVAL (operand) < 0 ? "subs.w" : "subq");
960 /* Print the operand as the index-part of an address.
961 Easiest way out is to use cris_print_index. */
962 cris_print_index (operand, file);
966 /* Print the size letter for an operand to a MULT, which must be a
967 const_int with a suitable value. */
968 if (GET_CODE (operand) != CONST_INT || INTVAL (operand) > 4)
969 LOSE_AND_RETURN ("invalid operand for 'T' modifier", x);
970 fprintf (file, "%s", mults[INTVAL (operand)]);
974 /* No code, print as usual. */
978 LOSE_AND_RETURN ("invalid operand modifier letter", x);
981 /* Print an operand as without a modifier letter. */
982 switch (GET_CODE (operand))
985 if (REGNO (operand) > 15
986 && REGNO (operand) != CRIS_MOF_REGNUM
987 && REGNO (operand) != CRIS_SRP_REGNUM
988 && REGNO (operand) != CRIS_CC0_REGNUM)
989 internal_error ("internal error: bad register: %d", REGNO (operand));
990 fprintf (file, "$%s", reg_names[REGNO (operand)]);
994 output_address (XEXP (operand, 0));
998 if (GET_MODE (operand) == VOIDmode)
999 /* A long long constant. */
1000 output_addr_const (file, operand);
1003 /* Only single precision is allowed as plain operands the
1004 moment. FIXME: REAL_VALUE_FROM_CONST_DOUBLE isn't
1009 /* FIXME: Perhaps check overflow of the "single". */
1010 REAL_VALUE_FROM_CONST_DOUBLE (r, operand);
1011 REAL_VALUE_TO_TARGET_SINGLE (r, l);
1013 fprintf (file, "0x%lx", l);
1018 ASSERT_PLT_UNSPEC (operand);
1022 cris_output_addr_const (file, operand);
1028 /* For a (MULT (reg X) const_int) we output "rX.S". */
1029 int i = GET_CODE (XEXP (operand, 1)) == CONST_INT
1030 ? INTVAL (XEXP (operand, 1)) : INTVAL (XEXP (operand, 0));
1031 rtx reg = GET_CODE (XEXP (operand, 1)) == CONST_INT
1032 ? XEXP (operand, 0) : XEXP (operand, 1);
1034 if (GET_CODE (reg) != REG
1035 || (GET_CODE (XEXP (operand, 0)) != CONST_INT
1036 && GET_CODE (XEXP (operand, 1)) != CONST_INT))
1037 LOSE_AND_RETURN ("unexpected multiplicative operand", x);
1039 cris_print_base (reg, file);
1040 fprintf (file, ".%c",
1041 i == 0 || (i == 1 && GET_CODE (operand) == MULT) ? 'b'
1043 : (i == 2 && GET_CODE (operand) == MULT) || i == 1 ? 'w'
1049 /* No need to handle all strange variants, let output_addr_const
1051 if (CONSTANT_P (operand))
1053 cris_output_addr_const (file, operand);
1057 LOSE_AND_RETURN ("unexpected operand", x);
1061 /* The PRINT_OPERAND_ADDRESS worker. */
1064 cris_print_operand_address (FILE *file, rtx x)
1066 /* All these were inside MEM:s so output indirection characters. */
1069 if (CONSTANT_ADDRESS_P (x))
1070 cris_output_addr_const (file, x);
1071 else if (BASE_OR_AUTOINCR_P (x))
1072 cris_print_base (x, file);
1073 else if (GET_CODE (x) == PLUS)
1081 cris_print_base (x1, file);
1082 cris_print_index (x2, file);
1084 else if (BASE_P (x2))
1086 cris_print_base (x2, file);
1087 cris_print_index (x1, file);
1090 LOSE_AND_RETURN ("unrecognized address", x);
1092 else if (GET_CODE (x) == MEM)
1094 /* A DIP. Output more indirection characters. */
1096 cris_print_base (XEXP (x, 0), file);
1100 LOSE_AND_RETURN ("unrecognized address", x);
1105 /* The RETURN_ADDR_RTX worker.
1106 We mark that the return address is used, either by EH or
1107 __builtin_return_address, for use by the function prologue and
1108 epilogue. FIXME: This isn't optimal; we just use the mark in the
1109 prologue and epilogue to say that the return address is to be stored
1110 in the stack frame. We could return SRP for leaf-functions and use the
1111 initial-value machinery. */
1114 cris_return_addr_rtx (int count, rtx frameaddr ATTRIBUTE_UNUSED)
1116 cfun->machine->needs_return_address_on_stack = 1;
1118 /* The return-address is stored just above the saved frame-pointer (if
1119 present). Apparently we can't eliminate from the frame-pointer in
1120 that direction, so use the incoming args (maybe pretended) pointer. */
1122 ? gen_rtx_MEM (Pmode, plus_constant (virtual_incoming_args_rtx, -4))
1126 /* Accessor used in cris.md:return because cfun->machine isn't available
1130 cris_return_address_on_stack (void)
1132 return regs_ever_live[CRIS_SRP_REGNUM]
1133 || cfun->machine->needs_return_address_on_stack;
1136 /* Accessor used in cris.md:return because cfun->machine isn't available
1140 cris_return_address_on_stack_for_return (void)
1142 return cfun->machine->return_type == CRIS_RETINSN_RET ? false
1143 : cris_return_address_on_stack ();
1146 /* This used to be the INITIAL_FRAME_POINTER_OFFSET worker; now only
1147 handles FP -> SP elimination offset. */
1150 cris_initial_frame_pointer_offset (void)
1154 /* Initial offset is 0 if we don't have a frame pointer. */
1156 bool got_really_used = current_function_uses_pic_offset_table;
1158 /* And 4 for each register pushed. */
1159 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1160 if (cris_reg_saved_in_regsave_area (regno, got_really_used))
1163 /* And then, last, we add the locals allocated. */
1164 offs += get_frame_size ();
1166 /* And more; the accumulated args size. */
1167 offs += current_function_outgoing_args_size;
1169 /* Then round it off, in case we use aligned stack. */
1170 if (TARGET_STACK_ALIGN)
1171 offs = TARGET_ALIGN_BY_32 ? (offs + 3) & ~3 : (offs + 1) & ~1;
1176 /* The INITIAL_ELIMINATION_OFFSET worker.
1177 Calculate the difference between imaginary registers such as frame
1178 pointer and the stack pointer. Used to eliminate the frame pointer
1179 and imaginary arg pointer. */
1182 cris_initial_elimination_offset (int fromreg, int toreg)
1185 = cris_initial_frame_pointer_offset ();
1187 /* We should be able to use regs_ever_live and related prologue
1188 information here, or alpha should not as well. */
1189 bool return_address_on_stack = cris_return_address_on_stack ();
1191 /* Here we act as if the frame-pointer were needed. */
1192 int ap_fp_offset = 4 + (return_address_on_stack ? 4 : 0);
1194 if (fromreg == ARG_POINTER_REGNUM
1195 && toreg == FRAME_POINTER_REGNUM)
1196 return ap_fp_offset;
1198 /* Between the frame pointer and the stack are only "normal" stack
1199 variables and saved registers. */
1200 if (fromreg == FRAME_POINTER_REGNUM
1201 && toreg == STACK_POINTER_REGNUM)
1202 return fp_sp_offset;
1204 /* We need to balance out the frame pointer here. */
1205 if (fromreg == ARG_POINTER_REGNUM
1206 && toreg == STACK_POINTER_REGNUM)
1207 return ap_fp_offset + fp_sp_offset - 4;
1212 /* This function looks into the pattern to see how this insn affects
1215 Used when to eliminate test insns before a condition-code user,
1216 such as a "scc" insn or a conditional branch. This includes
1217 checking if the entities that cc was updated by, are changed by the
1220 Currently a jumble of the old peek-inside-the-insn and the newer
1221 check-cc-attribute methods. */
1224 cris_notice_update_cc (rtx exp, rtx insn)
1226 /* Check if user specified "-mcc-init" as a bug-workaround. FIXME:
1227 TARGET_CCINIT does not work; we must set CC_REVERSED as below.
1228 Several testcases will otherwise fail, for example
1229 gcc.c-torture/execute/20000217-1.c -O0 and -O1. */
1236 /* Slowly, we're converting to using attributes to control the setting
1237 of condition-code status. */
1238 switch (get_attr_cc (insn))
1241 /* Even if it is "none", a setting may clobber a previous
1242 cc-value, so check. */
1243 if (GET_CODE (exp) == SET)
1245 if (cc_status.value1
1246 && modified_in_p (cc_status.value1, insn))
1247 cc_status.value1 = 0;
1249 if (cc_status.value2
1250 && modified_in_p (cc_status.value2, insn))
1251 cc_status.value2 = 0;
1260 /* Which means, for:
1265 CC is (reg) and (...) - unless (...) is 0, then CC does not change.
1266 CC_NO_OVERFLOW unless (...) is reg or mem.
1275 (set (reg1) (mem (bdap/biap)))
1276 (set (reg2) (bdap/biap))):
1277 CC is (reg1) and (mem (reg2))
1280 (set (mem (bdap/biap)) (reg1)) [or 0]
1281 (set (reg2) (bdap/biap))):
1284 (where reg and mem includes strict_low_parts variants thereof)
1286 For all others, assume CC is clobbered.
1287 Note that we do not have to care about setting CC_NO_OVERFLOW,
1288 since the overflow flag is set to 0 (i.e. right) for
1289 instructions where it does not have any sane sense, but where
1290 other flags have meanings. (This includes shifts; the carry is
1293 Note that there are other parallel constructs we could match,
1294 but we don't do that yet. */
1296 if (GET_CODE (exp) == SET)
1298 /* FIXME: Check when this happens. It looks like we should
1299 actually do a CC_STATUS_INIT here to be safe. */
1300 if (SET_DEST (exp) == pc_rtx)
1303 /* Record CC0 changes, so we do not have to output multiple
1305 if (SET_DEST (exp) == cc0_rtx)
1307 cc_status.value1 = SET_SRC (exp);
1308 cc_status.value2 = 0;
1310 /* Handle flags for the special btstq on one bit. */
1311 if (GET_CODE (SET_SRC (exp)) == ZERO_EXTRACT
1312 && XEXP (SET_SRC (exp), 1) == const1_rtx)
1314 if (GET_CODE (XEXP (SET_SRC (exp), 0)) == CONST_INT)
1316 cc_status.flags = CC_INVERTED;
1318 /* A one-bit btstq. */
1319 cc_status.flags = CC_Z_IN_NOT_N;
1322 cc_status.flags = 0;
1324 if (GET_CODE (SET_SRC (exp)) == COMPARE)
1326 if (!REG_P (XEXP (SET_SRC (exp), 0))
1327 && XEXP (SET_SRC (exp), 1) != const0_rtx)
1328 /* For some reason gcc will not canonicalize compare
1329 operations, reversing the sign by itself if
1330 operands are in wrong order. */
1331 /* (But NOT inverted; eq is still eq.) */
1332 cc_status.flags = CC_REVERSED;
1334 /* This seems to be overlooked by gcc. FIXME: Check again.
1335 FIXME: Is it really safe? */
1337 = gen_rtx_MINUS (GET_MODE (SET_SRC (exp)),
1338 XEXP (SET_SRC (exp), 0),
1339 XEXP (SET_SRC (exp), 1));
1343 else if (REG_P (SET_DEST (exp))
1344 || (GET_CODE (SET_DEST (exp)) == STRICT_LOW_PART
1345 && REG_P (XEXP (SET_DEST (exp), 0))))
1347 /* A register is set; normally CC is set to show that no
1348 test insn is needed. Catch the exceptions. */
1350 /* If not to cc0, then no "set"s in non-natural mode give
1352 if (GET_MODE_SIZE (GET_MODE (SET_DEST (exp))) > UNITS_PER_WORD
1353 || GET_MODE_CLASS (GET_MODE (SET_DEST (exp))) == MODE_FLOAT)
1355 /* ... except add:s and sub:s in DImode. */
1356 if (GET_MODE (SET_DEST (exp)) == DImode
1357 && (GET_CODE (SET_SRC (exp)) == PLUS
1358 || GET_CODE (SET_SRC (exp)) == MINUS))
1360 cc_status.flags = 0;
1361 cc_status.value1 = SET_DEST (exp);
1362 cc_status.value2 = SET_SRC (exp);
1364 if (cris_reg_overlap_mentioned_p (cc_status.value1,
1366 cc_status.value2 = 0;
1368 /* Add and sub may set V, which gets us
1369 unoptimizable results in "gt" and "le" condition
1371 cc_status.flags |= CC_NO_OVERFLOW;
1376 else if (SET_SRC (exp) == const0_rtx)
1378 /* There's no CC0 change when clearing a register or
1379 memory. Just check for overlap. */
1380 if (cc_status.value1
1381 && modified_in_p (cc_status.value1, insn))
1382 cc_status.value1 = 0;
1384 if (cc_status.value2
1385 && modified_in_p (cc_status.value2, insn))
1386 cc_status.value2 = 0;
1392 cc_status.flags = 0;
1393 cc_status.value1 = SET_DEST (exp);
1394 cc_status.value2 = SET_SRC (exp);
1396 if (cris_reg_overlap_mentioned_p (cc_status.value1,
1398 cc_status.value2 = 0;
1400 /* Some operations may set V, which gets us
1401 unoptimizable results in "gt" and "le" condition
1403 if (GET_CODE (SET_SRC (exp)) == PLUS
1404 || GET_CODE (SET_SRC (exp)) == MINUS
1405 || GET_CODE (SET_SRC (exp)) == NEG)
1406 cc_status.flags |= CC_NO_OVERFLOW;
1411 else if (GET_CODE (SET_DEST (exp)) == MEM
1412 || (GET_CODE (SET_DEST (exp)) == STRICT_LOW_PART
1413 && GET_CODE (XEXP (SET_DEST (exp), 0)) == MEM))
1415 /* When SET to MEM, then CC is not changed (except for
1417 if (cc_status.value1
1418 && modified_in_p (cc_status.value1, insn))
1419 cc_status.value1 = 0;
1421 if (cc_status.value2
1422 && modified_in_p (cc_status.value2, insn))
1423 cc_status.value2 = 0;
1428 else if (GET_CODE (exp) == PARALLEL)
1430 if (GET_CODE (XVECEXP (exp, 0, 0)) == SET
1431 && GET_CODE (XVECEXP (exp, 0, 1)) == SET
1432 && REG_P (XEXP (XVECEXP (exp, 0, 1), 0)))
1434 if (REG_P (XEXP (XVECEXP (exp, 0, 0), 0))
1435 && GET_CODE (XEXP (XVECEXP (exp, 0, 0), 1)) == MEM)
1437 /* For "move.S [rx=ry+o],rz", say CC reflects
1438 value1=rz and value2=[rx] */
1439 cc_status.value1 = XEXP (XVECEXP (exp, 0, 0), 0);
1441 = replace_equiv_address (XEXP (XVECEXP (exp, 0, 0), 1),
1442 XEXP (XVECEXP (exp, 0, 1), 0));
1443 cc_status.flags = 0;
1445 /* Huh? A side-effect cannot change the destination
1447 if (cris_reg_overlap_mentioned_p (cc_status.value1,
1449 internal_error ("internal error: sideeffect-insn affecting main effect");
1452 else if ((REG_P (XEXP (XVECEXP (exp, 0, 0), 1))
1453 || XEXP (XVECEXP (exp, 0, 0), 1) == const0_rtx)
1454 && GET_CODE (XEXP (XVECEXP (exp, 0, 0), 0)) == MEM)
1456 /* For "move.S rz,[rx=ry+o]" and "clear.S [rx=ry+o]",
1457 say flags are not changed, except for overlap. */
1458 if (cc_status.value1
1459 && modified_in_p (cc_status.value1, insn))
1460 cc_status.value1 = 0;
1462 if (cc_status.value2
1463 && modified_in_p (cc_status.value2, insn))
1464 cc_status.value2 = 0;
1473 internal_error ("Unknown cc_attr value");
1479 /* Return != 0 if the return sequence for the current function is short,
1480 like "ret" or "jump [sp+]". Prior to reloading, we can't tell if
1481 registers must be saved, so return 0 then. */
1484 cris_simple_epilogue (void)
1487 unsigned int reglimit = STACK_POINTER_REGNUM;
1488 bool got_really_used = current_function_uses_pic_offset_table;
1490 if (! reload_completed
1491 || frame_pointer_needed
1492 || get_frame_size () != 0
1493 || current_function_pretend_args_size
1494 || current_function_args_size
1495 || current_function_outgoing_args_size
1496 || current_function_calls_eh_return
1498 /* If we're not supposed to emit prologue and epilogue, we must
1499 not emit return-type instructions. */
1500 || !TARGET_PROLOGUE_EPILOGUE)
1503 /* No simple epilogue if there are saved registers. */
1504 for (regno = 0; regno < reglimit; regno++)
1505 if (cris_reg_saved_in_regsave_area (regno, got_really_used))
1511 /* Expand a return insn (just one insn) marked as using SRP or stack
1512 slot depending on parameter ON_STACK. */
1515 cris_expand_return (bool on_stack)
1517 /* FIXME: emit a parallel with a USE for SRP or the stack-slot, to
1518 tell "ret" from "jump [sp+]". Some, but not all, other parts of
1519 GCC expect just (return) to do the right thing when optimizing, so
1520 we do that until they're fixed. Currently, all return insns in a
1521 function must be the same (not really a limiting factor) so we need
1522 to check that it doesn't change half-way through. */
1523 emit_jump_insn (gen_rtx_RETURN (VOIDmode));
1525 CRIS_ASSERT (cfun->machine->return_type != CRIS_RETINSN_RET || !on_stack);
1526 CRIS_ASSERT (cfun->machine->return_type != CRIS_RETINSN_JUMP || on_stack);
1528 cfun->machine->return_type
1529 = on_stack ? CRIS_RETINSN_JUMP : CRIS_RETINSN_RET;
1532 /* Compute a (partial) cost for rtx X. Return true if the complete
1533 cost has been computed, and false if subexpressions should be
1534 scanned. In either case, *TOTAL contains the cost result. */
1537 cris_rtx_costs (rtx x, int code, int outer_code, int *total)
1543 HOST_WIDE_INT val = INTVAL (x);
1546 else if (val < 32 && val >= -32)
1548 /* Eight or 16 bits are a word and cycle more expensive. */
1549 else if (val <= 32767 && val >= -32768)
1551 /* A 32 bit constant (or very seldom, unsigned 16 bits) costs
1552 another word. FIXME: This isn't linear to 16 bits. */
1564 /* For PIC, we need a prefix (if it isn't already there),
1565 and the PIC register. For a global PIC symbol, we also
1566 need a read of the GOT. */
1569 if (cris_got_symbol (x))
1579 if (x != CONST0_RTX (GET_MODE (x) == VOIDmode ? DImode : GET_MODE (x)))
1582 /* Make 0.0 cheap, else test-insns will not be used. */
1587 /* Identify values that are no powers of two. Powers of 2 are
1588 taken care of already and those values should not be changed. */
1589 if (GET_CODE (XEXP (x, 1)) != CONST_INT
1590 || exact_log2 (INTVAL (XEXP (x, 1)) < 0))
1592 /* If we have a multiply insn, then the cost is between
1593 1 and 2 "fast" instructions. */
1594 if (TARGET_HAS_MUL_INSNS)
1596 *total = COSTS_N_INSNS (1) + COSTS_N_INSNS (1) / 2;
1600 /* Estimate as 4 + 4 * #ofbits. */
1601 *total = COSTS_N_INSNS (132);
1610 if (GET_CODE (XEXP (x, 1)) != CONST_INT
1611 || exact_log2 (INTVAL (XEXP (x, 1)) < 0))
1613 /* Estimate this as 4 + 8 * #of bits. */
1614 *total = COSTS_N_INSNS (260);
1620 if (GET_CODE (XEXP (x, 1)) == CONST_INT
1621 /* Two constants may actually happen before optimization. */
1622 && GET_CODE (XEXP (x, 0)) != CONST_INT
1623 && !CONST_OK_FOR_LETTER_P (INTVAL (XEXP (x, 1)), 'I'))
1625 *total = (rtx_cost (XEXP (x, 0), outer_code) + 2
1626 + 2 * GET_MODE_NUNITS (GET_MODE (XEXP (x, 0))));
1631 case ZERO_EXTEND: case SIGN_EXTEND:
1632 *total = rtx_cost (XEXP (x, 0), outer_code);
1640 /* The ADDRESS_COST worker. */
1643 cris_address_cost (rtx x)
1645 /* The metric to use for the cost-macros is unclear.
1646 The metric used here is (the number of cycles needed) / 2,
1647 where we consider equal a cycle for a word of code and a cycle to
1650 /* The cheapest addressing modes get 0, since nothing extra is needed. */
1651 if (BASE_OR_AUTOINCR_P (x))
1654 /* An indirect mem must be a DIP. This means two bytes extra for code,
1655 and 4 bytes extra for memory read, i.e. (2 + 4) / 2. */
1656 if (GET_CODE (x) == MEM)
1659 /* Assume (2 + 4) / 2 for a single constant; a dword, since it needs
1660 an extra DIP prefix and 4 bytes of constant in most cases.
1661 For PIC and a symbol with a GOT entry, we double the cost since we
1662 add a [rPIC+...] offset. A GOT-less symbol uses a BDAP prefix
1663 equivalent to the DIP prefix for non-PIC, hence the same cost. */
1665 return flag_pic && cris_got_symbol (x) ? 2 * (2 + 4) / 2 : (2 + 4) / 2;
1667 /* Handle BIAP and BDAP prefixes. */
1668 if (GET_CODE (x) == PLUS)
1670 rtx tem1 = XEXP (x, 0);
1671 rtx tem2 = XEXP (x, 1);
1673 /* A BIAP is 2 extra bytes for the prefix insn, nothing more. We
1674 recognize the typical MULT which is always in tem1 because of
1675 insn canonicalization. */
1676 if ((GET_CODE (tem1) == MULT && BIAP_INDEX_P (tem1))
1680 /* A BDAP (quick) is 2 extra bytes. Any constant operand to the
1681 PLUS is always found in tem2. */
1682 if (GET_CODE (tem2) == CONST_INT
1683 && INTVAL (tem2) < 128 && INTVAL (tem2) >= -128)
1686 /* A BDAP -32768 .. 32767 is like BDAP quick, but with 2 extra
1688 if (GET_CODE (tem2) == CONST_INT
1689 && CONST_OK_FOR_LETTER_P (INTVAL (tem2), 'L'))
1692 /* A BDAP with some other constant is 2 bytes extra. */
1693 if (CONSTANT_P (tem2))
1694 return (2 + 2 + 2) / 2;
1696 /* BDAP with something indirect should have a higher cost than
1697 BIAP with register. FIXME: Should it cost like a MEM or more? */
1698 /* Don't need to check it, it's the only one left.
1699 FIXME: There was a REG test missing, perhaps there are others.
1701 return (2 + 2 + 2) / 2;
1704 /* What else? Return a high cost. It matters only for valid
1705 addressing modes. */
1709 /* Check various objections to the side-effect. Used in the test-part
1710 of an anonymous insn describing an insn with a possible side-effect.
1711 Returns nonzero if the implied side-effect is ok.
1714 ops : An array of rtx:es. lreg, rreg, rval,
1715 The variables multop and other_op are indexes into this,
1716 or -1 if they are not applicable.
1717 lreg : The register that gets assigned in the side-effect.
1718 rreg : One register in the side-effect expression
1719 rval : The other register, or an int.
1720 multop : An integer to multiply rval with.
1721 other_op : One of the entities of the main effect,
1722 whose mode we must consider. */
1725 cris_side_effect_mode_ok (enum rtx_code code, rtx *ops,
1726 int lreg, int rreg, int rval,
1727 int multop, int other_op)
1729 /* Find what value to multiply with, for rx =ry + rz * n. */
1730 int mult = multop < 0 ? 1 : INTVAL (ops[multop]);
1732 rtx reg_rtx = ops[rreg];
1733 rtx val_rtx = ops[rval];
1735 /* The operands may be swapped. Canonicalize them in reg_rtx and
1736 val_rtx, where reg_rtx always is a reg (for this constraint to
1738 if (! BASE_P (reg_rtx))
1739 reg_rtx = val_rtx, val_rtx = ops[rreg];
1741 /* Don't forget to check that reg_rtx really is a reg. If it isn't,
1742 we have no business. */
1743 if (! BASE_P (reg_rtx))
1746 /* Don't do this when -mno-split. */
1747 if (!TARGET_SIDE_EFFECT_PREFIXES)
1750 /* The mult expression may be hidden in lreg. FIXME: Add more
1751 commentary about that. */
1752 if (GET_CODE (val_rtx) == MULT)
1754 mult = INTVAL (XEXP (val_rtx, 1));
1755 val_rtx = XEXP (val_rtx, 0);
1759 /* First check the "other operand". */
1762 if (GET_MODE_SIZE (GET_MODE (ops[other_op])) > UNITS_PER_WORD)
1765 /* Check if the lvalue register is the same as the "other
1766 operand". If so, the result is undefined and we shouldn't do
1767 this. FIXME: Check again. */
1768 if ((BASE_P (ops[lreg])
1769 && BASE_P (ops[other_op])
1770 && REGNO (ops[lreg]) == REGNO (ops[other_op]))
1771 || rtx_equal_p (ops[other_op], ops[lreg]))
1775 /* Do not accept frame_pointer_rtx as any operand. */
1776 if (ops[lreg] == frame_pointer_rtx || ops[rreg] == frame_pointer_rtx
1777 || ops[rval] == frame_pointer_rtx
1778 || (other_op >= 0 && ops[other_op] == frame_pointer_rtx))
1782 && ! BASE_P (val_rtx))
1785 /* Do not allow rx = rx + n if a normal add or sub with same size
1787 if (rtx_equal_p (ops[lreg], reg_rtx)
1788 && GET_CODE (val_rtx) == CONST_INT
1789 && (INTVAL (val_rtx) <= 63 && INTVAL (val_rtx) >= -63))
1792 /* Check allowed cases, like [r(+)?].[bwd] and const.
1793 A symbol is not allowed with PIC. */
1794 if (CONSTANT_P (val_rtx))
1795 return flag_pic == 0 || cris_symbol (val_rtx) == 0;
1797 if (GET_CODE (val_rtx) == MEM
1798 && BASE_OR_AUTOINCR_P (XEXP (val_rtx, 0)))
1801 if (GET_CODE (val_rtx) == SIGN_EXTEND
1802 && GET_CODE (XEXP (val_rtx, 0)) == MEM
1803 && BASE_OR_AUTOINCR_P (XEXP (XEXP (val_rtx, 0), 0)))
1806 /* If we got here, it's not a valid addressing mode. */
1809 else if (code == MULT
1810 || (code == PLUS && BASE_P (val_rtx)))
1812 /* Do not allow rx = rx + ry.S, since it doesn't give better code. */
1813 if (rtx_equal_p (ops[lreg], reg_rtx)
1814 || (mult == 1 && rtx_equal_p (ops[lreg], val_rtx)))
1817 /* Do not allow bad multiply-values. */
1818 if (mult != 1 && mult != 2 && mult != 4)
1821 /* Only allow r + ... */
1822 if (! BASE_P (reg_rtx))
1825 /* If we got here, all seems ok.
1826 (All checks need to be done above). */
1830 /* If we get here, the caller got its initial tests wrong. */
1831 internal_error ("internal error: cris_side_effect_mode_ok with bad operands");
1834 /* The function reg_overlap_mentioned_p in CVS (still as of 2001-05-16)
1835 does not handle the case where the IN operand is strict_low_part; it
1836 does handle it for X. Test-case in Axis-20010516. This function takes
1837 care of that for THIS port. FIXME: strict_low_part is going away
1841 cris_reg_overlap_mentioned_p (rtx x, rtx in)
1843 /* The function reg_overlap_mentioned now handles when X is
1844 strict_low_part, but not when IN is a STRICT_LOW_PART. */
1845 if (GET_CODE (in) == STRICT_LOW_PART)
1848 return reg_overlap_mentioned_p (x, in);
1851 /* The TARGET_ASM_NAMED_SECTION worker.
1852 We just dispatch to the functions for ELF and a.out. */
1855 cris_target_asm_named_section (const char *name, unsigned int flags,
1859 default_no_named_section (name, flags, decl);
1861 default_elf_asm_named_section (name, flags, decl);
1864 /* The LEGITIMATE_PIC_OPERAND_P worker. */
1867 cris_legitimate_pic_operand (rtx x)
1869 /* The PIC representation of a symbol with a GOT entry will be (for
1870 example; relocations differ):
1871 sym => [rPIC+sym:GOT]
1872 and for a GOT-less symbol it will be (for example, relocation differ):
1873 sym => rPIC+sym:GOTOFF
1874 so only a symbol with a GOT is by itself a valid operand, and it
1875 can't be a sum of a symbol and an offset. */
1876 return ! cris_symbol (x) || cris_got_symbol (x);
1879 /* Return nonzero if there's a SYMBOL_REF or LABEL_REF hiding inside this
1885 switch (GET_CODE (x))
1892 if (XINT (x, 1) == CRIS_UNSPEC_GOT || XINT (x, 1) != CRIS_UNSPEC_PLT)
1894 /* A PLT reference. */
1895 ASSERT_PLT_UNSPEC (x);
1899 return cris_symbol (XEXP (x, 0));
1903 return cris_symbol (XEXP (x, 0)) || cris_symbol (XEXP (x, 1));
1910 fatal_insn ("unrecognized supposed constant", x);
1916 /* Return nonzero if there's a SYMBOL_REF or LABEL_REF hiding inside this
1917 CONSTANT_P, and the symbol does not need a GOT entry. Also set
1918 current_function_uses_pic_offset_table if we're generating PIC and ever
1919 see something that would need one. */
1922 cris_gotless_symbol (rtx x)
1924 CRIS_ASSERT (flag_pic);
1926 switch (GET_CODE (x))
1929 if (XINT (x, 1) == CRIS_UNSPEC_GOT)
1931 if (XINT (x, 1) != CRIS_UNSPEC_PLT)
1933 ASSERT_PLT_UNSPEC (x);
1938 current_function_uses_pic_offset_table = 1;
1939 return SYMBOL_REF_LOCAL_P (x);
1942 /* We don't set current_function_uses_pic_offset_table for
1943 LABEL_REF:s in here, since they are almost always originating
1944 from some branch. The only time it does not come from a label is
1945 when GCC does something like __builtin_setjmp. Then we get the
1946 LABEL_REF from the movsi expander, so we mark it there as a
1951 return cris_gotless_symbol (XEXP (x, 0));
1956 int x0 = cris_gotless_symbol (XEXP (x, 0)) != 0;
1957 int x1 = cris_gotless_symbol (XEXP (x, 1)) != 0;
1959 /* One and only one of them must be a local symbol. Neither must
1960 be some other, more general kind of symbol. */
1963 && ! (x0 == 0 && cris_symbol (XEXP (x, 0)))
1964 && ! (x1 == 0 && cris_symbol (XEXP (x, 1)));
1972 fatal_insn ("unrecognized supposed constant", x);
1978 /* Return nonzero if there's a SYMBOL_REF or LABEL_REF hiding inside this
1979 CONSTANT_P, and the symbol needs a GOT entry. */
1982 cris_got_symbol (rtx x)
1984 CRIS_ASSERT (flag_pic);
1986 switch (GET_CODE (x))
1989 if (XINT (x, 1) == CRIS_UNSPEC_GOT)
1991 ASSERT_PLT_UNSPEC (x);
1996 current_function_uses_pic_offset_table = 1;
1997 return ! SYMBOL_REF_LOCAL_P (x);
2000 return cris_got_symbol (XEXP (x, 0));
2003 /* A LABEL_REF is never visible as a symbol outside the local
2007 /* Nope, can't access the GOT for "symbol + offset". */
2015 fatal_insn ("unrecognized supposed constant in cris_global_pic_symbol",
2022 /* TARGET_HANDLE_OPTION worker. We just store the values into local
2023 variables here. Checks for correct semantics are in
2024 cris_override_options. */
2027 cris_handle_option (size_t code, const char *arg, int value ATTRIBUTE_UNUSED)
2035 + MASK_ALIGN_BY_32);
2038 case OPT_mno_etrax100:
2042 + MASK_ALIGN_BY_32);
2048 |= (MASK_STACK_ALIGN
2051 + MASK_ALIGN_BY_32);
2057 |= (MASK_STACK_ALIGN
2065 &= ~(MASK_STACK_ALIGN
2074 CRIS_SUBTARGET_HANDLE_OPTION(code, arg, value);
2079 /* The OVERRIDE_OPTIONS worker.
2080 As is the norm, this also parses -mfoo=bar type parameters. */
2083 cris_override_options (void)
2085 if (cris_max_stackframe_str)
2087 cris_max_stackframe = atoi (cris_max_stackframe_str);
2089 /* Do some sanity checking. */
2090 if (cris_max_stackframe < 0 || cris_max_stackframe > 0x20000000)
2091 internal_error ("-max-stackframe=%d is not usable, not between 0 and %d",
2092 cris_max_stackframe, 0x20000000);
2095 /* Let "-metrax4" and "-metrax100" change the cpu version. */
2096 if (TARGET_SVINTO && cris_cpu_version < CRIS_CPU_SVINTO)
2097 cris_cpu_version = CRIS_CPU_SVINTO;
2098 else if (TARGET_ETRAX4_ADD && cris_cpu_version < CRIS_CPU_ETRAX4)
2099 cris_cpu_version = CRIS_CPU_ETRAX4;
2101 /* Parse -march=... and its synonym, the deprecated -mcpu=... */
2105 = (*cris_cpu_str == 'v' ? atoi (cris_cpu_str + 1) : -1);
2107 if (strcmp ("etrax4", cris_cpu_str) == 0)
2108 cris_cpu_version = 3;
2110 if (strcmp ("svinto", cris_cpu_str) == 0
2111 || strcmp ("etrax100", cris_cpu_str) == 0)
2112 cris_cpu_version = 8;
2114 if (strcmp ("ng", cris_cpu_str) == 0
2115 || strcmp ("etrax100lx", cris_cpu_str) == 0)
2116 cris_cpu_version = 10;
2118 if (cris_cpu_version < 0 || cris_cpu_version > 10)
2119 error ("unknown CRIS version specification in -march= or -mcpu= : %s",
2122 /* Set the target flags. */
2123 if (cris_cpu_version >= CRIS_CPU_ETRAX4)
2124 target_flags |= MASK_ETRAX4_ADD;
2126 /* If this is Svinto or higher, align for 32 bit accesses. */
2127 if (cris_cpu_version >= CRIS_CPU_SVINTO)
2129 |= (MASK_SVINTO | MASK_ALIGN_BY_32
2130 | MASK_STACK_ALIGN | MASK_CONST_ALIGN
2133 /* Note that we do not add new flags when it can be completely
2134 described with a macro that uses -mcpu=X. So
2135 TARGET_HAS_MUL_INSNS is (cris_cpu_version >= CRIS_CPU_NG). */
2141 = (*cris_tune_str == 'v' ? atoi (cris_tune_str + 1) : -1);
2143 if (strcmp ("etrax4", cris_tune_str) == 0)
2146 if (strcmp ("svinto", cris_tune_str) == 0
2147 || strcmp ("etrax100", cris_tune_str) == 0)
2150 if (strcmp ("ng", cris_tune_str) == 0
2151 || strcmp ("etrax100lx", cris_tune_str) == 0)
2154 if (cris_tune < 0 || cris_tune > 10)
2155 error ("unknown CRIS cpu version specification in -mtune= : %s",
2158 if (cris_tune >= CRIS_CPU_SVINTO)
2159 /* We have currently nothing more to tune than alignment for
2162 |= (MASK_STACK_ALIGN | MASK_CONST_ALIGN
2163 | MASK_DATA_ALIGN | MASK_ALIGN_BY_32);
2168 /* Use error rather than warning, so invalid use is easily
2169 detectable. Still change to the values we expect, to avoid
2173 error ("-fPIC and -fpic are not supported in this configuration");
2177 /* Turn off function CSE. We need to have the addresses reach the
2178 call expanders to get PLT-marked, as they could otherwise be
2179 compared against zero directly or indirectly. After visiting the
2180 call expanders they will then be cse:ed, as the call expanders
2181 force_reg the addresses, effectively forcing flag_no_function_cse
2183 flag_no_function_cse = 1;
2186 if (write_symbols == DWARF2_DEBUG && ! TARGET_ELF)
2188 warning (0, "that particular -g option is invalid with -maout and -melinux");
2189 write_symbols = DBX_DEBUG;
2192 /* Set the per-function-data initializer. */
2193 init_machine_status = cris_init_machine_status;
2196 /* The TARGET_ASM_OUTPUT_MI_THUNK worker. */
2199 cris_asm_output_mi_thunk (FILE *stream,
2200 tree thunkdecl ATTRIBUTE_UNUSED,
2201 HOST_WIDE_INT delta,
2202 HOST_WIDE_INT vcall_offset ATTRIBUTE_UNUSED,
2206 fprintf (stream, "\tadd%s " HOST_WIDE_INT_PRINT_DEC ",$%s\n",
2207 ADDITIVE_SIZE_MODIFIER (delta), delta,
2208 reg_names[CRIS_FIRST_ARG_REG]);
2210 fprintf (stream, "\tsub%s " HOST_WIDE_INT_PRINT_DEC ",$%s\n",
2211 ADDITIVE_SIZE_MODIFIER (-delta), -delta,
2212 reg_names[CRIS_FIRST_ARG_REG]);
2216 const char *name = XSTR (XEXP (DECL_RTL (funcdecl), 0), 0);
2218 name = (* targetm.strip_name_encoding) (name);
2219 fprintf (stream, "add.d ");
2220 assemble_name (stream, name);
2221 fprintf (stream, "%s,$pc\n", CRIS_PLT_PCOFFSET_SUFFIX);
2225 fprintf (stream, "jump ");
2226 assemble_name (stream, XSTR (XEXP (DECL_RTL (funcdecl), 0), 0));
2227 fprintf (stream, "\n");
2231 /* Boilerplate emitted at start of file.
2233 NO_APP *only at file start* means faster assembly. It also means
2234 comments are not allowed. In some cases comments will be output
2235 for debugging purposes. Make sure they are allowed then.
2237 We want a .file directive only if TARGET_ELF. */
2239 cris_file_start (void)
2241 /* These expressions can vary at run time, so we cannot put
2242 them into TARGET_INITIALIZER. */
2243 targetm.file_start_app_off = !(TARGET_PDEBUG || flag_print_asm_name);
2244 targetm.file_start_file_directive = TARGET_ELF;
2246 default_file_start ();
2249 /* Rename the function calls for integer multiply and divide. */
2251 cris_init_libfuncs (void)
2253 set_optab_libfunc (smul_optab, SImode, "__Mul");
2254 set_optab_libfunc (sdiv_optab, SImode, "__Div");
2255 set_optab_libfunc (udiv_optab, SImode, "__Udiv");
2256 set_optab_libfunc (smod_optab, SImode, "__Mod");
2257 set_optab_libfunc (umod_optab, SImode, "__Umod");
2260 /* The INIT_EXPANDERS worker sets the per-function-data initializer and
2264 cris_init_expanders (void)
2266 /* Nothing here at the moment. */
2269 /* Zero initialization is OK for all current fields. */
2271 static struct machine_function *
2272 cris_init_machine_status (void)
2274 return ggc_alloc_cleared (sizeof (struct machine_function));
2277 /* Split a 2 word move (DI or presumably DF) into component parts.
2278 Originally a copy of gen_split_move_double in m32r.c. */
2281 cris_split_movdx (rtx *operands)
2283 enum machine_mode mode = GET_MODE (operands[0]);
2284 rtx dest = operands[0];
2285 rtx src = operands[1];
2288 /* We used to have to handle (SUBREG (MEM)) here, but that should no
2289 longer happen; after reload there are no SUBREGs any more, and we're
2290 only called after reload. */
2291 CRIS_ASSERT (GET_CODE (dest) != SUBREG && GET_CODE (src) != SUBREG);
2294 if (GET_CODE (dest) == REG)
2296 int dregno = REGNO (dest);
2298 /* Reg-to-reg copy. */
2299 if (GET_CODE (src) == REG)
2301 int sregno = REGNO (src);
2303 int reverse = (dregno == sregno + 1);
2305 /* We normally copy the low-numbered register first. However, if
2306 the first register operand 0 is the same as the second register of
2307 operand 1, we must copy in the opposite order. */
2308 emit_insn (gen_rtx_SET (VOIDmode,
2309 operand_subword (dest, reverse, TRUE, mode),
2310 operand_subword (src, reverse, TRUE, mode)));
2312 emit_insn (gen_rtx_SET (VOIDmode,
2313 operand_subword (dest, !reverse, TRUE, mode),
2314 operand_subword (src, !reverse, TRUE, mode)));
2316 /* Constant-to-reg copy. */
2317 else if (GET_CODE (src) == CONST_INT || GET_CODE (src) == CONST_DOUBLE)
2320 split_double (src, &words[0], &words[1]);
2321 emit_insn (gen_rtx_SET (VOIDmode,
2322 operand_subword (dest, 0, TRUE, mode),
2325 emit_insn (gen_rtx_SET (VOIDmode,
2326 operand_subword (dest, 1, TRUE, mode),
2329 /* Mem-to-reg copy. */
2330 else if (GET_CODE (src) == MEM)
2332 /* If the high-address word is used in the address, we must load it
2333 last. Otherwise, load it first. */
2334 rtx addr = XEXP (src, 0);
2336 = (refers_to_regno_p (dregno, dregno + 1, addr, NULL) != 0);
2338 /* The original code implies that we can't do
2339 move.x [rN+],rM move.x [rN],rM+1
2340 when rN is dead, because of REG_NOTES damage. That is
2341 consistent with what I've seen, so don't try it.
2343 We have two different cases here; if the addr is POST_INC,
2344 just pass it through, otherwise add constants. */
2346 if (GET_CODE (addr) == POST_INC)
2348 emit_insn (gen_rtx_SET (VOIDmode,
2349 operand_subword (dest, 0, TRUE, mode),
2350 change_address (src, SImode, addr)));
2351 emit_insn (gen_rtx_SET (VOIDmode,
2352 operand_subword (dest, 1, TRUE, mode),
2353 change_address (src, SImode, addr)));
2357 /* Make sure we don't get any other addresses with
2358 embedded postincrements. They should be stopped in
2359 GO_IF_LEGITIMATE_ADDRESS, but we're here for your
2361 if (side_effects_p (addr))
2362 fatal_insn ("unexpected side-effects in address", addr);
2364 emit_insn (gen_rtx_SET
2366 operand_subword (dest, reverse, TRUE, mode),
2369 plus_constant (addr,
2370 reverse * UNITS_PER_WORD))));
2371 emit_insn (gen_rtx_SET
2373 operand_subword (dest, ! reverse, TRUE, mode),
2376 plus_constant (addr,
2382 internal_error ("Unknown src");
2384 /* Reg-to-mem copy or clear mem. */
2385 else if (GET_CODE (dest) == MEM
2386 && (GET_CODE (src) == REG
2387 || src == const0_rtx
2388 || src == CONST0_RTX (DFmode)))
2390 rtx addr = XEXP (dest, 0);
2392 if (GET_CODE (addr) == POST_INC)
2394 emit_insn (gen_rtx_SET (VOIDmode,
2395 change_address (dest, SImode, addr),
2396 operand_subword (src, 0, TRUE, mode)));
2397 emit_insn (gen_rtx_SET (VOIDmode,
2398 change_address (dest, SImode, addr),
2399 operand_subword (src, 1, TRUE, mode)));
2403 /* Make sure we don't get any other addresses with embedded
2404 postincrements. They should be stopped in
2405 GO_IF_LEGITIMATE_ADDRESS, but we're here for your safety. */
2406 if (side_effects_p (addr))
2407 fatal_insn ("unexpected side-effects in address", addr);
2409 emit_insn (gen_rtx_SET
2411 change_address (dest, SImode, addr),
2412 operand_subword (src, 0, TRUE, mode)));
2414 emit_insn (gen_rtx_SET
2416 change_address (dest, SImode,
2417 plus_constant (addr,
2419 operand_subword (src, 1, TRUE, mode)));
2424 internal_error ("Unknown dest");
2431 /* The expander for the prologue pattern name. */
2434 cris_expand_prologue (void)
2437 int size = get_frame_size ();
2438 /* Shorten the used name for readability. */
2439 int cfoa_size = current_function_outgoing_args_size;
2440 int last_movem_reg = -1;
2443 int return_address_on_stack = cris_return_address_on_stack ();
2444 int got_really_used = current_function_uses_pic_offset_table;
2445 int n_movem_regs = 0;
2446 int pretend = current_function_pretend_args_size;
2448 /* Don't do anything if no prologues or epilogues are wanted. */
2449 if (!TARGET_PROLOGUE_EPILOGUE)
2452 CRIS_ASSERT (size >= 0);
2454 /* Align the size to what's best for the CPU model. */
2455 if (TARGET_STACK_ALIGN)
2456 size = TARGET_ALIGN_BY_32 ? (size + 3) & ~3 : (size + 1) & ~1;
2460 /* See also cris_setup_incoming_varargs where
2461 cfun->machine->stdarg_regs is set. There are other setters of
2462 current_function_pretend_args_size than stdarg handling, like
2463 for an argument passed with parts in R13 and stack. We must
2464 not store R13 into the pretend-area for that case, as GCC does
2465 that itself. "Our" store would be marked as redundant and GCC
2466 will attempt to remove it, which will then be flagged as an
2467 internal error; trying to remove a frame-related insn. */
2468 int stdarg_regs = cfun->machine->stdarg_regs;
2470 framesize += pretend;
2472 for (regno = CRIS_FIRST_ARG_REG + CRIS_MAX_ARGS_IN_REGS - 1;
2474 regno--, pretend -= 4, stdarg_regs--)
2476 insn = emit_insn (gen_rtx_SET (VOIDmode,
2478 plus_constant (stack_pointer_rtx,
2480 /* FIXME: When dwarf2 frame output and unless asynchronous
2481 exceptions, make dwarf2 bundle together all stack
2482 adjustments like it does for registers between stack
2484 RTX_FRAME_RELATED_P (insn) = 1;
2486 mem = gen_rtx_MEM (SImode, stack_pointer_rtx);
2487 set_mem_alias_set (mem, get_varargs_alias_set ());
2488 insn = emit_move_insn (mem, gen_rtx_raw_REG (SImode, regno));
2490 /* Note the absence of RTX_FRAME_RELATED_P on the above insn:
2491 the value isn't restored, so we don't want to tell dwarf2
2492 that it's been stored to stack, else EH handling info would
2496 /* For other setters of current_function_pretend_args_size, we
2497 just adjust the stack by leaving the remaining size in
2498 "pretend", handled below. */
2501 /* Save SRP if not a leaf function. */
2502 if (return_address_on_stack)
2504 insn = emit_insn (gen_rtx_SET (VOIDmode,
2506 plus_constant (stack_pointer_rtx,
2509 RTX_FRAME_RELATED_P (insn) = 1;
2511 mem = gen_rtx_MEM (SImode, stack_pointer_rtx);
2512 set_mem_alias_set (mem, get_frame_alias_set ());
2513 insn = emit_move_insn (mem, gen_rtx_raw_REG (SImode, CRIS_SRP_REGNUM));
2514 RTX_FRAME_RELATED_P (insn) = 1;
2518 /* Set up the frame pointer, if needed. */
2519 if (frame_pointer_needed)
2521 insn = emit_insn (gen_rtx_SET (VOIDmode,
2523 plus_constant (stack_pointer_rtx,
2526 RTX_FRAME_RELATED_P (insn) = 1;
2528 mem = gen_rtx_MEM (SImode, stack_pointer_rtx);
2529 set_mem_alias_set (mem, get_frame_alias_set ());
2530 insn = emit_move_insn (mem, frame_pointer_rtx);
2531 RTX_FRAME_RELATED_P (insn) = 1;
2533 insn = emit_move_insn (frame_pointer_rtx, stack_pointer_rtx);
2534 RTX_FRAME_RELATED_P (insn) = 1;
2539 /* Between frame-pointer and saved registers lie the area for local
2540 variables. If we get here with "pretended" size remaining, count
2541 it into the general stack size. */
2544 /* Get a contiguous sequence of registers, starting with R0, that need
2546 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
2548 if (cris_reg_saved_in_regsave_area (regno, got_really_used))
2552 /* Check if movem may be used for registers so far. */
2553 if (regno == last_movem_reg + 1)
2554 /* Yes, update next expected register. */
2555 last_movem_reg = regno;
2558 /* We cannot use movem for all registers. We have to flush
2559 any movem:ed registers we got so far. */
2560 if (last_movem_reg != -1)
2563 = (n_movem_regs == 1) ? 1 : last_movem_reg + 1;
2565 /* It is a win to use a side-effect assignment for
2566 64 <= size <= 128. But side-effect on movem was
2567 not usable for CRIS v0..3. Also only do it if
2568 side-effects insns are allowed. */
2569 if ((last_movem_reg + 1) * 4 + size >= 64
2570 && (last_movem_reg + 1) * 4 + size <= 128
2571 && (cris_cpu_version >= CRIS_CPU_SVINTO || n_saved == 1)
2572 && TARGET_SIDE_EFFECT_PREFIXES)
2575 = gen_rtx_MEM (SImode,
2576 plus_constant (stack_pointer_rtx,
2577 -(n_saved * 4 + size)));
2578 set_mem_alias_set (mem, get_frame_alias_set ());
2580 = cris_emit_movem_store (mem, GEN_INT (n_saved),
2581 -(n_saved * 4 + size),
2587 = gen_rtx_SET (VOIDmode,
2589 plus_constant (stack_pointer_rtx,
2590 -(n_saved * 4 + size)));
2591 insn = emit_insn (insn);
2592 RTX_FRAME_RELATED_P (insn) = 1;
2594 mem = gen_rtx_MEM (SImode, stack_pointer_rtx);
2595 set_mem_alias_set (mem, get_frame_alias_set ());
2596 insn = cris_emit_movem_store (mem, GEN_INT (n_saved),
2600 framesize += n_saved * 4 + size;
2601 last_movem_reg = -1;
2605 insn = emit_insn (gen_rtx_SET (VOIDmode,
2607 plus_constant (stack_pointer_rtx,
2609 RTX_FRAME_RELATED_P (insn) = 1;
2611 mem = gen_rtx_MEM (SImode, stack_pointer_rtx);
2612 set_mem_alias_set (mem, get_frame_alias_set ());
2613 insn = emit_move_insn (mem, gen_rtx_raw_REG (SImode, regno));
2614 RTX_FRAME_RELATED_P (insn) = 1;
2616 framesize += 4 + size;
2622 /* Check after, if we could movem all registers. This is the normal case. */
2623 if (last_movem_reg != -1)
2626 = (n_movem_regs == 1) ? 1 : last_movem_reg + 1;
2628 /* Side-effect on movem was not usable for CRIS v0..3. Also only
2629 do it if side-effects insns are allowed. */
2630 if ((last_movem_reg + 1) * 4 + size >= 64
2631 && (last_movem_reg + 1) * 4 + size <= 128
2632 && (cris_cpu_version >= CRIS_CPU_SVINTO || n_saved == 1)
2633 && TARGET_SIDE_EFFECT_PREFIXES)
2636 = gen_rtx_MEM (SImode,
2637 plus_constant (stack_pointer_rtx,
2638 -(n_saved * 4 + size)));
2639 set_mem_alias_set (mem, get_frame_alias_set ());
2640 insn = cris_emit_movem_store (mem, GEN_INT (n_saved),
2641 -(n_saved * 4 + size), true);
2646 = gen_rtx_SET (VOIDmode,
2648 plus_constant (stack_pointer_rtx,
2649 -(n_saved * 4 + size)));
2650 insn = emit_insn (insn);
2651 RTX_FRAME_RELATED_P (insn) = 1;
2653 mem = gen_rtx_MEM (SImode, stack_pointer_rtx);
2654 set_mem_alias_set (mem, get_frame_alias_set ());
2655 insn = cris_emit_movem_store (mem, GEN_INT (n_saved), 0, true);
2658 framesize += n_saved * 4 + size;
2659 /* We have to put outgoing argument space after regs. */
2662 insn = emit_insn (gen_rtx_SET (VOIDmode,
2664 plus_constant (stack_pointer_rtx,
2666 RTX_FRAME_RELATED_P (insn) = 1;
2667 framesize += cfoa_size;
2670 else if ((size + cfoa_size) > 0)
2672 insn = emit_insn (gen_rtx_SET (VOIDmode,
2674 plus_constant (stack_pointer_rtx,
2675 -(cfoa_size + size))));
2676 RTX_FRAME_RELATED_P (insn) = 1;
2677 framesize += size + cfoa_size;
2680 /* Set up the PIC register, if it is used. */
2681 if (got_really_used)
2684 = gen_rtx_UNSPEC (SImode, gen_rtvec (1, const0_rtx), CRIS_UNSPEC_GOT);
2685 emit_move_insn (pic_offset_table_rtx, got);
2687 /* FIXME: This is a cover-up for flow2 messing up; it doesn't
2688 follow exceptional paths and tries to delete the GOT load as
2689 unused, if it isn't used on the non-exceptional paths. Other
2690 ports have similar or other cover-ups, or plain bugs marking
2691 the GOT register load as maybe-dead. To see this, remove the
2692 line below and try libsupc++/vec.cc or a trivial
2693 "static void y (); void x () {try {y ();} catch (...) {}}". */
2694 emit_insn (gen_rtx_USE (VOIDmode, pic_offset_table_rtx));
2697 if (cris_max_stackframe && framesize > cris_max_stackframe)
2698 warning (0, "stackframe too big: %d bytes", framesize);
2701 /* The expander for the epilogue pattern. */
2704 cris_expand_epilogue (void)
2707 int size = get_frame_size ();
2708 int last_movem_reg = -1;
2709 int argspace_offset = current_function_outgoing_args_size;
2710 int pretend = current_function_pretend_args_size;
2712 bool return_address_on_stack = cris_return_address_on_stack ();
2713 /* A reference may have been optimized out
2714 (like the abort () in fde_split in unwind-dw2-fde.c, at least 3.2.1)
2715 so check that it's still used. */
2716 int got_really_used = current_function_uses_pic_offset_table;
2717 int n_movem_regs = 0;
2719 if (!TARGET_PROLOGUE_EPILOGUE)
2722 /* Align byte count of stack frame. */
2723 if (TARGET_STACK_ALIGN)
2724 size = TARGET_ALIGN_BY_32 ? (size + 3) & ~3 : (size + 1) & ~1;
2726 /* Check how many saved regs we can movem. They start at r0 and must
2729 regno < FIRST_PSEUDO_REGISTER;
2731 if (cris_reg_saved_in_regsave_area (regno, got_really_used))
2735 if (regno == last_movem_reg + 1)
2736 last_movem_reg = regno;
2741 /* If there was only one register that really needed to be saved
2742 through movem, don't use movem. */
2743 if (n_movem_regs == 1)
2744 last_movem_reg = -1;
2746 /* Now emit "normal" move insns for all regs higher than the movem
2748 for (regno = FIRST_PSEUDO_REGISTER - 1;
2749 regno > last_movem_reg;
2751 if (cris_reg_saved_in_regsave_area (regno, got_really_used))
2753 if (argspace_offset)
2755 /* There is an area for outgoing parameters located before
2756 the saved registers. We have to adjust for that. */
2757 emit_insn (gen_rtx_SET (VOIDmode,
2759 plus_constant (stack_pointer_rtx,
2761 /* Make sure we only do this once. */
2762 argspace_offset = 0;
2765 mem = gen_rtx_MEM (SImode, gen_rtx_POST_INC (SImode,
2766 stack_pointer_rtx));
2767 set_mem_alias_set (mem, get_frame_alias_set ());
2768 emit_move_insn (gen_rtx_raw_REG (SImode, regno), mem);
2771 /* If we have any movem-restore, do it now. */
2772 if (last_movem_reg != -1)
2774 if (argspace_offset)
2776 emit_insn (gen_rtx_SET (VOIDmode,
2778 plus_constant (stack_pointer_rtx,
2780 argspace_offset = 0;
2783 mem = gen_rtx_MEM (SImode,
2784 gen_rtx_POST_INC (SImode, stack_pointer_rtx));
2785 set_mem_alias_set (mem, get_frame_alias_set ());
2786 emit_insn (cris_gen_movem_load (mem, GEN_INT (last_movem_reg + 1), 0));
2789 /* If we don't clobber all of the allocated stack area (we've already
2790 deallocated saved registers), GCC might want to schedule loads from
2791 the stack to *after* the stack-pointer restore, which introduces an
2792 interrupt race condition. This happened for the initial-value
2793 SRP-restore for g++.dg/eh/registers1.C (noticed by inspection of
2794 other failure for that test). It also happened for the stack slot
2795 for the return value in (one version of)
2796 linux/fs/dcache.c:__d_lookup, at least with "-O2
2797 -fno-omit-frame-pointer". */
2799 /* Restore frame pointer if necessary. */
2800 if (frame_pointer_needed)
2802 emit_insn (gen_cris_frame_deallocated_barrier ());
2804 emit_move_insn (stack_pointer_rtx, frame_pointer_rtx);
2805 mem = gen_rtx_MEM (SImode, gen_rtx_POST_INC (SImode,
2806 stack_pointer_rtx));
2807 set_mem_alias_set (mem, get_frame_alias_set ());
2808 emit_move_insn (frame_pointer_rtx, mem);
2810 else if ((size + argspace_offset) != 0)
2812 emit_insn (gen_cris_frame_deallocated_barrier ());
2814 /* If there was no frame-pointer to restore sp from, we must
2815 explicitly deallocate local variables. */
2817 /* Handle space for outgoing parameters that hasn't been handled
2819 size += argspace_offset;
2821 emit_insn (gen_rtx_SET (VOIDmode,
2823 plus_constant (stack_pointer_rtx, size)));
2826 /* If this function has no pushed register parameters
2827 (stdargs/varargs), and if it is not a leaf function, then we have
2828 the return address on the stack. */
2829 if (return_address_on_stack && pretend == 0)
2831 if (current_function_calls_eh_return)
2834 rtx srpreg = gen_rtx_raw_REG (SImode, CRIS_SRP_REGNUM);
2835 mem = gen_rtx_MEM (SImode,
2836 gen_rtx_POST_INC (SImode,
2837 stack_pointer_rtx));
2838 set_mem_alias_set (mem, get_frame_alias_set ());
2839 emit_move_insn (srpreg, mem);
2841 emit_insn (gen_addsi3 (stack_pointer_rtx,
2843 gen_rtx_raw_REG (SImode,
2844 CRIS_STACKADJ_REG)));
2845 cris_expand_return (false);
2848 cris_expand_return (true);
2853 /* If we pushed some register parameters, then adjust the stack for
2857 /* If SRP is stored on the way, we need to restore it first. */
2858 if (return_address_on_stack)
2861 rtx srpreg = gen_rtx_raw_REG (SImode, CRIS_SRP_REGNUM);
2862 mem = gen_rtx_MEM (SImode,
2863 gen_rtx_POST_INC (SImode,
2864 stack_pointer_rtx));
2865 set_mem_alias_set (mem, get_frame_alias_set ());
2866 emit_move_insn (srpreg, mem);
2869 emit_insn (gen_rtx_SET (VOIDmode,
2871 plus_constant (stack_pointer_rtx, pretend)));
2874 /* Perform the "physical" unwinding that the EH machinery calculated. */
2875 if (current_function_calls_eh_return)
2876 emit_insn (gen_addsi3 (stack_pointer_rtx,
2878 gen_rtx_raw_REG (SImode,
2879 CRIS_STACKADJ_REG)));
2880 cris_expand_return (false);
2883 /* Worker function for generating movem from mem for load_multiple. */
2886 cris_gen_movem_load (rtx src, rtx nregs_rtx, int nprefix)
2888 int nregs = INTVAL (nregs_rtx);
2892 rtx srcreg = XEXP (src, 0);
2893 unsigned int regno = nregs - 1;
2896 if (GET_CODE (srcreg) == POST_INC)
2897 srcreg = XEXP (srcreg, 0);
2899 CRIS_ASSERT (REG_P (srcreg));
2901 /* Don't use movem for just one insn. The insns are equivalent except
2902 for the pipeline hazard (on v32); movem does not forward the loaded
2903 registers so there's a three cycles penalty for their use. */
2905 return gen_movsi (gen_rtx_REG (SImode, 0), src);
2907 vec = rtvec_alloc (nprefix + nregs
2908 + (GET_CODE (XEXP (src, 0)) == POST_INC));
2910 if (GET_CODE (XEXP (src, 0)) == POST_INC)
2912 RTVEC_ELT (vec, nprefix + 1)
2913 = gen_rtx_SET (VOIDmode, srcreg, plus_constant (srcreg, nregs * 4));
2917 src = replace_equiv_address (src, srcreg);
2918 RTVEC_ELT (vec, nprefix)
2919 = gen_rtx_SET (VOIDmode, gen_rtx_REG (SImode, regno), src);
2922 for (i = 1; i < nregs; i++, eltno++)
2924 RTVEC_ELT (vec, nprefix + eltno)
2925 = gen_rtx_SET (VOIDmode, gen_rtx_REG (SImode, regno),
2926 adjust_address_nv (src, SImode, i * 4));
2930 return gen_rtx_PARALLEL (VOIDmode, vec);
2933 /* Worker function for generating movem to mem. If FRAME_RELATED, notes
2934 are added that the dwarf2 machinery understands. */
2937 cris_emit_movem_store (rtx dest, rtx nregs_rtx, int increment,
2940 int nregs = INTVAL (nregs_rtx);
2945 rtx destreg = XEXP (dest, 0);
2946 unsigned int regno = nregs - 1;
2949 if (GET_CODE (destreg) == POST_INC)
2950 increment += nregs * 4;
2952 if (GET_CODE (destreg) == POST_INC || GET_CODE (destreg) == PLUS)
2953 destreg = XEXP (destreg, 0);
2955 CRIS_ASSERT (REG_P (destreg));
2957 /* Don't use movem for just one insn. The insns are equivalent except
2958 for the pipeline hazard (on v32); movem does not forward the loaded
2959 registers so there's a three cycles penalty for use. */
2962 rtx mov = gen_rtx_SET (VOIDmode, dest, gen_rtx_REG (SImode, 0));
2966 insn = emit_insn (mov);
2968 RTX_FRAME_RELATED_P (insn) = 1;
2972 /* If there was a request for a side-effect, create the ordinary
2974 vec = rtvec_alloc (2);
2976 RTVEC_ELT (vec, 0) = mov;
2977 RTVEC_ELT (vec, 1) = gen_rtx_SET (VOIDmode, destreg,
2978 plus_constant (destreg, increment));
2981 RTX_FRAME_RELATED_P (mov) = 1;
2982 RTX_FRAME_RELATED_P (RTVEC_ELT (vec, 1)) = 1;
2987 vec = rtvec_alloc (nregs + (increment != 0 ? 1 : 0));
2989 = gen_rtx_SET (VOIDmode,
2990 replace_equiv_address (dest,
2991 plus_constant (destreg,
2993 gen_rtx_REG (SImode, regno));
2996 /* The dwarf2 info wants this mark on each component in a parallel
2997 that's part of the prologue (though it's optional on the first
3000 RTX_FRAME_RELATED_P (RTVEC_ELT (vec, 0)) = 1;
3005 = gen_rtx_SET (VOIDmode, destreg,
3006 plus_constant (destreg,
3008 ? increment : nregs * 4));
3012 RTX_FRAME_RELATED_P (RTVEC_ELT (vec, 1)) = 1;
3014 /* Don't call adjust_address_nv on a post-incremented address if
3016 if (GET_CODE (XEXP (dest, 0)) == POST_INC)
3017 dest = replace_equiv_address (dest, destreg);
3020 for (i = 1; i < nregs; i++, eltno++)
3022 RTVEC_ELT (vec, eltno)
3023 = gen_rtx_SET (VOIDmode, adjust_address_nv (dest, SImode, i * 4),
3024 gen_rtx_REG (SImode, regno));
3026 RTX_FRAME_RELATED_P (RTVEC_ELT (vec, eltno)) = 1;
3031 insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, vec));
3033 /* Because dwarf2out.c handles the insns in a parallel as a sequence,
3034 we need to keep the stack adjustment separate, after the
3035 MEM-setters. Else the stack-adjustment in the second component of
3036 the parallel would be mishandled; the offsets for the SETs that
3037 follow it would be wrong. We prepare for this by adding a
3038 REG_FRAME_RELATED_EXPR with the MEM-setting parts in a SEQUENCE
3039 followed by the increment. Note that we have FRAME_RELATED_P on
3040 all the SETs, including the original stack adjustment SET in the
3046 rtx seq = gen_rtx_SEQUENCE (VOIDmode, rtvec_alloc (nregs + 1));
3047 XVECEXP (seq, 0, 0) = XVECEXP (PATTERN (insn), 0, 0);
3048 for (i = 1; i < nregs; i++)
3049 XVECEXP (seq, 0, i) = XVECEXP (PATTERN (insn), 0, i + 1);
3050 XVECEXP (seq, 0, nregs) = XVECEXP (PATTERN (insn), 0, 1);
3052 = gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR, seq,
3056 RTX_FRAME_RELATED_P (insn) = 1;
3062 /* Use from within code, from e.g. PRINT_OPERAND and
3063 PRINT_OPERAND_ADDRESS. Macros used in output_addr_const need to emit
3064 different things depending on whether code operand or constant is
3068 cris_output_addr_const (FILE *file, rtx x)
3071 output_addr_const (file, x);
3075 /* Worker function for ASM_OUTPUT_SYMBOL_REF. */
3078 cris_asm_output_symbol_ref (FILE *file, rtx x)
3080 if (flag_pic && in_code > 0)
3082 const char *origstr = XSTR (x, 0);
3085 str = (* targetm.strip_name_encoding) (origstr);
3087 if (cris_gotless_symbol (x))
3089 if (! cris_pic_sympart_only)
3090 fprintf (file, "$%s+", reg_names [PIC_OFFSET_TABLE_REGNUM]);
3091 assemble_name (file, str);
3092 fprintf (file, ":GOTOFF");
3094 else if (cris_got_symbol (x))
3096 CRIS_ASSERT (!cris_pic_sympart_only);
3098 fprintf (file, "[$%s+", reg_names [PIC_OFFSET_TABLE_REGNUM]);
3099 assemble_name (file, XSTR (x, 0));
3102 fprintf (file, ":GOT16]");
3104 fprintf (file, ":GOT]");
3107 LOSE_AND_RETURN ("unexpected PIC symbol", x);
3110 if (! current_function_uses_pic_offset_table)
3111 output_operand_lossage ("PIC register isn't set up");
3114 assemble_name (file, XSTR (x, 0));
3117 /* Worker function for ASM_OUTPUT_LABEL_REF. */
3120 cris_asm_output_label_ref (FILE *file, char *buf)
3122 if (flag_pic && in_code > 0)
3124 if (! cris_pic_sympart_only)
3125 fprintf (file, "$%s+", reg_names [PIC_OFFSET_TABLE_REGNUM]);
3126 assemble_name (file, buf);
3128 fprintf (file, ":GOTOFF");
3131 if (! current_function_uses_pic_offset_table)
3132 internal_error ("emitting PIC operand, but PIC register isn't set up");
3135 assemble_name (file, buf);
3138 /* Worker function for OUTPUT_ADDR_CONST_EXTRA. */
3141 cris_output_addr_const_extra (FILE *file, rtx x)
3143 switch (GET_CODE (x))
3145 const char *origstr;
3149 ASSERT_PLT_UNSPEC (x);
3150 x = XVECEXP (x, 0, 0);
3151 origstr = XSTR (x, 0);
3152 str = (* targetm.strip_name_encoding) (origstr);
3153 if (cris_pic_sympart_only)
3155 assemble_name (file, str);
3156 fprintf (file, ":PLTG");
3160 CRIS_ASSERT (!TARGET_AVOID_GOTPLT);
3162 fprintf (file, "[$%s+", reg_names [PIC_OFFSET_TABLE_REGNUM]);
3163 assemble_name (file, XSTR (x, 0));
3166 fprintf (file, ":GOTPLT16]");
3168 fprintf (file, ":GOTPLT]");
3177 /* Worker function for TARGET_STRUCT_VALUE_RTX. */
3180 cris_struct_value_rtx (tree fntype ATTRIBUTE_UNUSED,
3181 int incoming ATTRIBUTE_UNUSED)
3183 return gen_rtx_REG (Pmode, CRIS_STRUCT_VALUE_REGNUM);
3186 /* Worker function for TARGET_SETUP_INCOMING_VARARGS. */
3189 cris_setup_incoming_varargs (CUMULATIVE_ARGS *ca,
3190 enum machine_mode mode ATTRIBUTE_UNUSED,
3191 tree type ATTRIBUTE_UNUSED,
3192 int *pretend_arg_size,
3195 if (ca->regs < CRIS_MAX_ARGS_IN_REGS)
3197 int stdarg_regs = CRIS_MAX_ARGS_IN_REGS - ca->regs;
3198 cfun->machine->stdarg_regs = stdarg_regs;
3199 *pretend_arg_size = stdarg_regs * 4;
3203 fprintf (asm_out_file,
3204 "\n; VA:: ANSI: %d args before, anon @ #%d, %dtime\n",
3205 ca->regs, *pretend_arg_size, second_time);
3208 /* Return true if TYPE must be passed by invisible reference.
3209 For cris, we pass <= 8 bytes by value, others by reference. */
3212 cris_pass_by_reference (CUMULATIVE_ARGS *ca ATTRIBUTE_UNUSED,
3213 enum machine_mode mode, tree type,
3214 bool named ATTRIBUTE_UNUSED)
3216 return (targetm.calls.must_pass_in_stack (mode, type)
3217 || CRIS_FUNCTION_ARG_SIZE (mode, type) > 8);
3222 cris_arg_partial_bytes (CUMULATIVE_ARGS *ca, enum machine_mode mode,
3223 tree type, bool named ATTRIBUTE_UNUSED)
3225 if (ca->regs == CRIS_MAX_ARGS_IN_REGS - 1
3226 && !targetm.calls.must_pass_in_stack (mode, type)
3227 && CRIS_FUNCTION_ARG_SIZE (mode, type) > 4
3228 && CRIS_FUNCTION_ARG_SIZE (mode, type) <= 8)
3229 return UNITS_PER_WORD;
3234 /* Worker function for TARGET_MD_ASM_CLOBBERS. */
3237 cris_md_asm_clobbers (tree outputs, tree inputs, tree in_clobbers)
3239 HARD_REG_SET mof_set;
3243 CLEAR_HARD_REG_SET (mof_set);
3244 SET_HARD_REG_BIT (mof_set, CRIS_MOF_REGNUM);
3246 /* For the time being, all asms clobber condition codes. Revisit when
3247 there's a reasonable use for inputs/outputs that mention condition
3250 = tree_cons (NULL_TREE,
3251 build_string (strlen (reg_names[CRIS_CC0_REGNUM]),
3252 reg_names[CRIS_CC0_REGNUM]),
3255 for (t = outputs; t != NULL; t = TREE_CHAIN (t))
3257 tree val = TREE_VALUE (t);
3259 /* The constraint letter for the singleton register class of MOF
3260 is 'h'. If it's mentioned in the constraints, the asm is
3261 MOF-aware and adding it to the clobbers would cause it to have
3262 impossible constraints. */
3263 if (strchr (TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (t))),
3265 || decl_overlaps_hard_reg_set_p (val, mof_set))
3269 for (t = inputs; t != NULL; t = TREE_CHAIN (t))
3271 tree val = TREE_VALUE (t);
3273 if (strchr (TREE_STRING_POINTER (TREE_VALUE (TREE_PURPOSE (t))),
3275 || decl_overlaps_hard_reg_set_p (val, mof_set))
3279 return tree_cons (NULL_TREE,
3280 build_string (strlen (reg_names[CRIS_MOF_REGNUM]),
3281 reg_names[CRIS_MOF_REGNUM]),
3286 /* Various small functions to replace macros. Only called from a
3287 debugger. They might collide with gcc functions or system functions,
3288 so only emit them when '#if 1' above. */
3290 enum rtx_code Get_code (rtx);
3295 return GET_CODE (x);
3298 const char *Get_mode (rtx);
3303 return GET_MODE_NAME (GET_MODE (x));
3306 rtx Xexp (rtx, int);
3314 rtx Xvecexp (rtx, int, int);
3317 Xvecexp (rtx x, int n, int m)
3319 return XVECEXP (x, n, m);
3322 int Get_rtx_len (rtx);
3327 return GET_RTX_LENGTH (GET_CODE (x));
3330 /* Use upper-case to distinguish from local variables that are sometimes
3331 called next_insn and prev_insn. */
3333 rtx Next_insn (rtx);
3336 Next_insn (rtx insn)
3338 return NEXT_INSN (insn);
3341 rtx Prev_insn (rtx);
3344 Prev_insn (rtx insn)
3346 return PREV_INSN (insn);
3350 #include "gt-cris.h"
3354 * eval: (c-set-style "gnu")
3355 * indent-tabs-mode: t