Turn FUNCTION_ARG_PADDING into a target hook
[official-gcc.git] / gcc / config / iq2000 / iq2000.c
blob460e38d2df165d69c419efb07910fb8c5245e395
1 /* Subroutines used for code generation on Vitesse IQ2000 processors
2 Copyright (C) 2003-2017 Free Software Foundation, Inc.
4 This file is part of GCC.
6 GCC is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 3, or (at your option)
9 any later version.
11 GCC is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING3. If not see
18 <http://www.gnu.org/licenses/>. */
20 #include "config.h"
21 #include "system.h"
22 #include "coretypes.h"
23 #include "backend.h"
24 #include "target.h"
25 #include "rtl.h"
26 #include "tree.h"
27 #include "stringpool.h"
28 #include "attribs.h"
29 #include "df.h"
30 #include "memmodel.h"
31 #include "tm_p.h"
32 #include "optabs.h"
33 #include "regs.h"
34 #include "emit-rtl.h"
35 #include "recog.h"
36 #include "diagnostic-core.h"
37 #include "stor-layout.h"
38 #include "calls.h"
39 #include "varasm.h"
40 #include "output.h"
41 #include "insn-attr.h"
42 #include "explow.h"
43 #include "expr.h"
44 #include "langhooks.h"
45 #include "builtins.h"
47 /* This file should be included last. */
48 #include "target-def.h"
50 /* Enumeration for all of the relational tests, so that we can build
51 arrays indexed by the test type, and not worry about the order
52 of EQ, NE, etc. */
54 enum internal_test
56 ITEST_EQ,
57 ITEST_NE,
58 ITEST_GT,
59 ITEST_GE,
60 ITEST_LT,
61 ITEST_LE,
62 ITEST_GTU,
63 ITEST_GEU,
64 ITEST_LTU,
65 ITEST_LEU,
66 ITEST_MAX
69 struct constant;
72 /* Structure to be filled in by compute_frame_size with register
73 save masks, and offsets for the current function. */
75 struct iq2000_frame_info
77 long total_size; /* # bytes that the entire frame takes up. */
78 long var_size; /* # bytes that variables take up. */
79 long args_size; /* # bytes that outgoing arguments take up. */
80 long extra_size; /* # bytes of extra gunk. */
81 int gp_reg_size; /* # bytes needed to store gp regs. */
82 int fp_reg_size; /* # bytes needed to store fp regs. */
83 long mask; /* Mask of saved gp registers. */
84 long gp_save_offset; /* Offset from vfp to store gp registers. */
85 long fp_save_offset; /* Offset from vfp to store fp registers. */
86 long gp_sp_offset; /* Offset from new sp to store gp registers. */
87 long fp_sp_offset; /* Offset from new sp to store fp registers. */
88 int initialized; /* != 0 if frame size already calculated. */
89 int num_gp; /* Number of gp registers saved. */
90 } iq2000_frame_info;
92 struct GTY(()) machine_function
94 /* Current frame information, calculated by compute_frame_size. */
95 long total_size; /* # bytes that the entire frame takes up. */
96 long var_size; /* # bytes that variables take up. */
97 long args_size; /* # bytes that outgoing arguments take up. */
98 long extra_size; /* # bytes of extra gunk. */
99 int gp_reg_size; /* # bytes needed to store gp regs. */
100 int fp_reg_size; /* # bytes needed to store fp regs. */
101 long mask; /* Mask of saved gp registers. */
102 long gp_save_offset; /* Offset from vfp to store gp registers. */
103 long fp_save_offset; /* Offset from vfp to store fp registers. */
104 long gp_sp_offset; /* Offset from new sp to store gp registers. */
105 long fp_sp_offset; /* Offset from new sp to store fp registers. */
106 int initialized; /* != 0 if frame size already calculated. */
107 int num_gp; /* Number of gp registers saved. */
110 /* Global variables for machine-dependent things. */
112 /* List of all IQ2000 punctuation characters used by iq2000_print_operand. */
113 static char iq2000_print_operand_punct[256];
115 /* Which instruction set architecture to use. */
116 int iq2000_isa;
118 /* Local variables. */
120 /* The next branch instruction is a branch likely, not branch normal. */
121 static int iq2000_branch_likely;
123 /* Count of delay slots and how many are filled. */
124 static int dslots_load_total;
125 static int dslots_load_filled;
126 static int dslots_jump_total;
128 /* # of nops needed by previous insn. */
129 static int dslots_number_nops;
131 /* Number of 1/2/3 word references to data items (i.e., not jal's). */
132 static int num_refs[3];
134 /* Registers to check for load delay. */
135 static rtx iq2000_load_reg;
136 static rtx iq2000_load_reg2;
137 static rtx iq2000_load_reg3;
138 static rtx iq2000_load_reg4;
140 /* Mode used for saving/restoring general purpose registers. */
141 static machine_mode gpr_mode;
144 /* Initialize the GCC target structure. */
145 static struct machine_function* iq2000_init_machine_status (void);
146 static void iq2000_option_override (void);
147 static section *iq2000_select_rtx_section (machine_mode, rtx,
148 unsigned HOST_WIDE_INT);
149 static void iq2000_init_builtins (void);
150 static rtx iq2000_expand_builtin (tree, rtx, rtx, machine_mode, int);
151 static bool iq2000_return_in_memory (const_tree, const_tree);
152 static void iq2000_setup_incoming_varargs (cumulative_args_t,
153 machine_mode, tree, int *,
154 int);
155 static bool iq2000_rtx_costs (rtx, machine_mode, int, int, int *, bool);
156 static int iq2000_address_cost (rtx, machine_mode, addr_space_t,
157 bool);
158 static section *iq2000_select_section (tree, int, unsigned HOST_WIDE_INT);
159 static rtx iq2000_legitimize_address (rtx, rtx, machine_mode);
160 static bool iq2000_pass_by_reference (cumulative_args_t, machine_mode,
161 const_tree, bool);
162 static int iq2000_arg_partial_bytes (cumulative_args_t, machine_mode,
163 tree, bool);
164 static rtx iq2000_function_arg (cumulative_args_t,
165 machine_mode, const_tree, bool);
166 static void iq2000_function_arg_advance (cumulative_args_t,
167 machine_mode, const_tree, bool);
168 static pad_direction iq2000_function_arg_padding (machine_mode, const_tree);
169 static unsigned int iq2000_function_arg_boundary (machine_mode,
170 const_tree);
171 static void iq2000_va_start (tree, rtx);
172 static bool iq2000_legitimate_address_p (machine_mode, rtx, bool);
173 static bool iq2000_can_eliminate (const int, const int);
174 static void iq2000_asm_trampoline_template (FILE *);
175 static void iq2000_trampoline_init (rtx, tree, rtx);
176 static rtx iq2000_function_value (const_tree, const_tree, bool);
177 static rtx iq2000_libcall_value (machine_mode, const_rtx);
178 static void iq2000_print_operand (FILE *, rtx, int);
179 static void iq2000_print_operand_address (FILE *, machine_mode, rtx);
180 static bool iq2000_print_operand_punct_valid_p (unsigned char code);
181 static bool iq2000_hard_regno_mode_ok (unsigned int, machine_mode);
182 static bool iq2000_modes_tieable_p (machine_mode, machine_mode);
184 #undef TARGET_INIT_BUILTINS
185 #define TARGET_INIT_BUILTINS iq2000_init_builtins
186 #undef TARGET_EXPAND_BUILTIN
187 #define TARGET_EXPAND_BUILTIN iq2000_expand_builtin
188 #undef TARGET_ASM_SELECT_RTX_SECTION
189 #define TARGET_ASM_SELECT_RTX_SECTION iq2000_select_rtx_section
190 #undef TARGET_OPTION_OVERRIDE
191 #define TARGET_OPTION_OVERRIDE iq2000_option_override
192 #undef TARGET_RTX_COSTS
193 #define TARGET_RTX_COSTS iq2000_rtx_costs
194 #undef TARGET_ADDRESS_COST
195 #define TARGET_ADDRESS_COST iq2000_address_cost
196 #undef TARGET_ASM_SELECT_SECTION
197 #define TARGET_ASM_SELECT_SECTION iq2000_select_section
199 #undef TARGET_LEGITIMIZE_ADDRESS
200 #define TARGET_LEGITIMIZE_ADDRESS iq2000_legitimize_address
202 /* The assembler supports switchable .bss sections, but
203 iq2000_select_section doesn't yet make use of them. */
204 #undef TARGET_HAVE_SWITCHABLE_BSS_SECTIONS
205 #define TARGET_HAVE_SWITCHABLE_BSS_SECTIONS false
207 #undef TARGET_PRINT_OPERAND
208 #define TARGET_PRINT_OPERAND iq2000_print_operand
209 #undef TARGET_PRINT_OPERAND_ADDRESS
210 #define TARGET_PRINT_OPERAND_ADDRESS iq2000_print_operand_address
211 #undef TARGET_PRINT_OPERAND_PUNCT_VALID_P
212 #define TARGET_PRINT_OPERAND_PUNCT_VALID_P iq2000_print_operand_punct_valid_p
214 #undef TARGET_PROMOTE_FUNCTION_MODE
215 #define TARGET_PROMOTE_FUNCTION_MODE default_promote_function_mode_always_promote
216 #undef TARGET_PROMOTE_PROTOTYPES
217 #define TARGET_PROMOTE_PROTOTYPES hook_bool_const_tree_true
219 #undef TARGET_FUNCTION_VALUE
220 #define TARGET_FUNCTION_VALUE iq2000_function_value
221 #undef TARGET_LIBCALL_VALUE
222 #define TARGET_LIBCALL_VALUE iq2000_libcall_value
223 #undef TARGET_RETURN_IN_MEMORY
224 #define TARGET_RETURN_IN_MEMORY iq2000_return_in_memory
225 #undef TARGET_PASS_BY_REFERENCE
226 #define TARGET_PASS_BY_REFERENCE iq2000_pass_by_reference
227 #undef TARGET_CALLEE_COPIES
228 #define TARGET_CALLEE_COPIES hook_callee_copies_named
229 #undef TARGET_ARG_PARTIAL_BYTES
230 #define TARGET_ARG_PARTIAL_BYTES iq2000_arg_partial_bytes
231 #undef TARGET_FUNCTION_ARG
232 #define TARGET_FUNCTION_ARG iq2000_function_arg
233 #undef TARGET_FUNCTION_ARG_ADVANCE
234 #define TARGET_FUNCTION_ARG_ADVANCE iq2000_function_arg_advance
235 #undef TARGET_FUNCTION_ARG_PADDING
236 #define TARGET_FUNCTION_ARG_PADDING iq2000_function_arg_padding
237 #undef TARGET_FUNCTION_ARG_BOUNDARY
238 #define TARGET_FUNCTION_ARG_BOUNDARY iq2000_function_arg_boundary
240 #undef TARGET_SETUP_INCOMING_VARARGS
241 #define TARGET_SETUP_INCOMING_VARARGS iq2000_setup_incoming_varargs
242 #undef TARGET_STRICT_ARGUMENT_NAMING
243 #define TARGET_STRICT_ARGUMENT_NAMING hook_bool_CUMULATIVE_ARGS_true
245 #undef TARGET_EXPAND_BUILTIN_VA_START
246 #define TARGET_EXPAND_BUILTIN_VA_START iq2000_va_start
248 #undef TARGET_LRA_P
249 #define TARGET_LRA_P hook_bool_void_false
251 #undef TARGET_LEGITIMATE_ADDRESS_P
252 #define TARGET_LEGITIMATE_ADDRESS_P iq2000_legitimate_address_p
254 #undef TARGET_CAN_ELIMINATE
255 #define TARGET_CAN_ELIMINATE iq2000_can_eliminate
257 #undef TARGET_ASM_TRAMPOLINE_TEMPLATE
258 #define TARGET_ASM_TRAMPOLINE_TEMPLATE iq2000_asm_trampoline_template
259 #undef TARGET_TRAMPOLINE_INIT
260 #define TARGET_TRAMPOLINE_INIT iq2000_trampoline_init
262 #undef TARGET_HARD_REGNO_MODE_OK
263 #define TARGET_HARD_REGNO_MODE_OK iq2000_hard_regno_mode_ok
264 #undef TARGET_MODES_TIEABLE_P
265 #define TARGET_MODES_TIEABLE_P iq2000_modes_tieable_p
267 struct gcc_target targetm = TARGET_INITIALIZER;
269 /* Return nonzero if we split the address into high and low parts. */
272 iq2000_check_split (rtx address, machine_mode mode)
274 /* This is the same check used in simple_memory_operand.
275 We use it here because LO_SUM is not offsettable. */
276 if (GET_MODE_SIZE (mode) > (unsigned) UNITS_PER_WORD)
277 return 0;
279 if ((GET_CODE (address) == SYMBOL_REF)
280 || (GET_CODE (address) == CONST
281 && GET_CODE (XEXP (XEXP (address, 0), 0)) == SYMBOL_REF)
282 || GET_CODE (address) == LABEL_REF)
283 return 1;
285 return 0;
288 /* Return nonzero if REG is valid for MODE. */
291 iq2000_reg_mode_ok_for_base_p (rtx reg,
292 machine_mode mode ATTRIBUTE_UNUSED,
293 int strict)
295 return (strict
296 ? REGNO_MODE_OK_FOR_BASE_P (REGNO (reg), mode)
297 : GP_REG_OR_PSEUDO_NONSTRICT_P (REGNO (reg), mode));
300 /* Return a nonzero value if XINSN is a legitimate address for a
301 memory operand of the indicated MODE. STRICT is nonzero if this
302 function is called during reload. */
304 bool
305 iq2000_legitimate_address_p (machine_mode mode, rtx xinsn, bool strict)
307 if (TARGET_DEBUG_A_MODE)
309 GO_PRINTF2 ("\n========== legitimate_address_p, %sstrict\n",
310 strict ? "" : "not ");
311 GO_DEBUG_RTX (xinsn);
314 /* Check for constant before stripping off SUBREG, so that we don't
315 accept (subreg (const_int)) which will fail to reload. */
316 if (CONSTANT_ADDRESS_P (xinsn)
317 && ! (iq2000_check_split (xinsn, mode))
318 && ! (GET_CODE (xinsn) == CONST_INT && ! SMALL_INT (xinsn)))
319 return 1;
321 while (GET_CODE (xinsn) == SUBREG)
322 xinsn = SUBREG_REG (xinsn);
324 if (GET_CODE (xinsn) == REG
325 && iq2000_reg_mode_ok_for_base_p (xinsn, mode, strict))
326 return 1;
328 if (GET_CODE (xinsn) == LO_SUM)
330 rtx xlow0 = XEXP (xinsn, 0);
331 rtx xlow1 = XEXP (xinsn, 1);
333 while (GET_CODE (xlow0) == SUBREG)
334 xlow0 = SUBREG_REG (xlow0);
335 if (GET_CODE (xlow0) == REG
336 && iq2000_reg_mode_ok_for_base_p (xlow0, mode, strict)
337 && iq2000_check_split (xlow1, mode))
338 return 1;
341 if (GET_CODE (xinsn) == PLUS)
343 rtx xplus0 = XEXP (xinsn, 0);
344 rtx xplus1 = XEXP (xinsn, 1);
345 enum rtx_code code0;
346 enum rtx_code code1;
348 while (GET_CODE (xplus0) == SUBREG)
349 xplus0 = SUBREG_REG (xplus0);
350 code0 = GET_CODE (xplus0);
352 while (GET_CODE (xplus1) == SUBREG)
353 xplus1 = SUBREG_REG (xplus1);
354 code1 = GET_CODE (xplus1);
356 if (code0 == REG
357 && iq2000_reg_mode_ok_for_base_p (xplus0, mode, strict))
359 if (code1 == CONST_INT && SMALL_INT (xplus1)
360 && SMALL_INT_UNSIGNED (xplus1) /* No negative offsets */)
361 return 1;
365 if (TARGET_DEBUG_A_MODE)
366 GO_PRINTF ("Not a machine_mode mode, legitimate address\n");
368 /* The address was not legitimate. */
369 return 0;
372 /* Returns an operand string for the given instruction's delay slot,
373 after updating filled delay slot statistics.
375 We assume that operands[0] is the target register that is set.
377 In order to check the next insn, most of this functionality is moved
378 to FINAL_PRESCAN_INSN, and we just set the global variables that
379 it needs. */
381 const char *
382 iq2000_fill_delay_slot (const char *ret, enum delay_type type, rtx operands[],
383 rtx_insn *cur_insn)
385 rtx set_reg;
386 machine_mode mode;
387 rtx_insn *next_insn = cur_insn ? NEXT_INSN (cur_insn) : NULL;
388 int num_nops;
390 if (type == DELAY_LOAD || type == DELAY_FCMP)
391 num_nops = 1;
393 else
394 num_nops = 0;
396 /* Make sure that we don't put nop's after labels. */
397 next_insn = NEXT_INSN (cur_insn);
398 while (next_insn != 0
399 && (NOTE_P (next_insn) || LABEL_P (next_insn)))
400 next_insn = NEXT_INSN (next_insn);
402 dslots_load_total += num_nops;
403 if (TARGET_DEBUG_C_MODE
404 || type == DELAY_NONE
405 || operands == 0
406 || cur_insn == 0
407 || next_insn == 0
408 || LABEL_P (next_insn)
409 || (set_reg = operands[0]) == 0)
411 dslots_number_nops = 0;
412 iq2000_load_reg = 0;
413 iq2000_load_reg2 = 0;
414 iq2000_load_reg3 = 0;
415 iq2000_load_reg4 = 0;
417 return ret;
420 set_reg = operands[0];
421 if (set_reg == 0)
422 return ret;
424 while (GET_CODE (set_reg) == SUBREG)
425 set_reg = SUBREG_REG (set_reg);
427 mode = GET_MODE (set_reg);
428 dslots_number_nops = num_nops;
429 iq2000_load_reg = set_reg;
430 if (GET_MODE_SIZE (mode)
431 > (unsigned) (UNITS_PER_WORD))
432 iq2000_load_reg2 = gen_rtx_REG (SImode, REGNO (set_reg) + 1);
433 else
434 iq2000_load_reg2 = 0;
436 return ret;
439 /* Determine whether a memory reference takes one (based off of the GP
440 pointer), two (normal), or three (label + reg) instructions, and bump the
441 appropriate counter for -mstats. */
443 static void
444 iq2000_count_memory_refs (rtx op, int num)
446 int additional = 0;
447 int n_words = 0;
448 rtx addr, plus0, plus1;
449 enum rtx_code code0, code1;
450 int looping;
452 if (TARGET_DEBUG_B_MODE)
454 fprintf (stderr, "\n========== iq2000_count_memory_refs:\n");
455 debug_rtx (op);
458 /* Skip MEM if passed, otherwise handle movsi of address. */
459 addr = (GET_CODE (op) != MEM) ? op : XEXP (op, 0);
461 /* Loop, going through the address RTL. */
464 looping = FALSE;
465 switch (GET_CODE (addr))
467 case REG:
468 case CONST_INT:
469 case LO_SUM:
470 break;
472 case PLUS:
473 plus0 = XEXP (addr, 0);
474 plus1 = XEXP (addr, 1);
475 code0 = GET_CODE (plus0);
476 code1 = GET_CODE (plus1);
478 if (code0 == REG)
480 additional++;
481 addr = plus1;
482 looping = 1;
483 continue;
486 if (code0 == CONST_INT)
488 addr = plus1;
489 looping = 1;
490 continue;
493 if (code1 == REG)
495 additional++;
496 addr = plus0;
497 looping = 1;
498 continue;
501 if (code1 == CONST_INT)
503 addr = plus0;
504 looping = 1;
505 continue;
508 if (code0 == SYMBOL_REF || code0 == LABEL_REF || code0 == CONST)
510 addr = plus0;
511 looping = 1;
512 continue;
515 if (code1 == SYMBOL_REF || code1 == LABEL_REF || code1 == CONST)
517 addr = plus1;
518 looping = 1;
519 continue;
522 break;
524 case LABEL_REF:
525 n_words = 2; /* Always 2 words. */
526 break;
528 case CONST:
529 addr = XEXP (addr, 0);
530 looping = 1;
531 continue;
533 case SYMBOL_REF:
534 n_words = SYMBOL_REF_FLAG (addr) ? 1 : 2;
535 break;
537 default:
538 break;
541 while (looping);
543 if (n_words == 0)
544 return;
546 n_words += additional;
547 if (n_words > 3)
548 n_words = 3;
550 num_refs[n_words-1] += num;
553 /* Abort after printing out a specific insn. */
555 static void
556 abort_with_insn (rtx insn, const char * reason)
558 error (reason);
559 debug_rtx (insn);
560 fancy_abort (__FILE__, __LINE__, __FUNCTION__);
563 /* Return the appropriate instructions to move one operand to another. */
565 const char *
566 iq2000_move_1word (rtx operands[], rtx_insn *insn, int unsignedp)
568 const char *ret = 0;
569 rtx op0 = operands[0];
570 rtx op1 = operands[1];
571 enum rtx_code code0 = GET_CODE (op0);
572 enum rtx_code code1 = GET_CODE (op1);
573 machine_mode mode = GET_MODE (op0);
574 int subreg_offset0 = 0;
575 int subreg_offset1 = 0;
576 enum delay_type delay = DELAY_NONE;
578 while (code0 == SUBREG)
580 subreg_offset0 += subreg_regno_offset (REGNO (SUBREG_REG (op0)),
581 GET_MODE (SUBREG_REG (op0)),
582 SUBREG_BYTE (op0),
583 GET_MODE (op0));
584 op0 = SUBREG_REG (op0);
585 code0 = GET_CODE (op0);
588 while (code1 == SUBREG)
590 subreg_offset1 += subreg_regno_offset (REGNO (SUBREG_REG (op1)),
591 GET_MODE (SUBREG_REG (op1)),
592 SUBREG_BYTE (op1),
593 GET_MODE (op1));
594 op1 = SUBREG_REG (op1);
595 code1 = GET_CODE (op1);
598 /* For our purposes, a condition code mode is the same as SImode. */
599 if (mode == CCmode)
600 mode = SImode;
602 if (code0 == REG)
604 int regno0 = REGNO (op0) + subreg_offset0;
606 if (code1 == REG)
608 int regno1 = REGNO (op1) + subreg_offset1;
610 /* Do not do anything for assigning a register to itself */
611 if (regno0 == regno1)
612 ret = "";
614 else if (GP_REG_P (regno0))
616 if (GP_REG_P (regno1))
617 ret = "or\t%0,%%0,%1";
622 else if (code1 == MEM)
624 delay = DELAY_LOAD;
626 if (TARGET_STATS)
627 iq2000_count_memory_refs (op1, 1);
629 if (GP_REG_P (regno0))
631 /* For loads, use the mode of the memory item, instead of the
632 target, so zero/sign extend can use this code as well. */
633 switch (GET_MODE (op1))
635 default:
636 break;
637 case E_SFmode:
638 ret = "lw\t%0,%1";
639 break;
640 case E_SImode:
641 case E_CCmode:
642 ret = "lw\t%0,%1";
643 break;
644 case E_HImode:
645 ret = (unsignedp) ? "lhu\t%0,%1" : "lh\t%0,%1";
646 break;
647 case E_QImode:
648 ret = (unsignedp) ? "lbu\t%0,%1" : "lb\t%0,%1";
649 break;
654 else if (code1 == CONST_INT
655 || (code1 == CONST_DOUBLE
656 && GET_MODE (op1) == VOIDmode))
658 if (code1 == CONST_DOUBLE)
660 /* This can happen when storing constants into long long
661 bitfields. Just store the least significant word of
662 the value. */
663 operands[1] = op1 = GEN_INT (CONST_DOUBLE_LOW (op1));
666 if (INTVAL (op1) == 0)
668 if (GP_REG_P (regno0))
669 ret = "or\t%0,%%0,%z1";
671 else if (GP_REG_P (regno0))
673 if (SMALL_INT_UNSIGNED (op1))
674 ret = "ori\t%0,%%0,%x1\t\t\t# %1";
675 else if (SMALL_INT (op1))
676 ret = "addiu\t%0,%%0,%1\t\t\t# %1";
677 else
678 ret = "lui\t%0,%X1\t\t\t# %1\n\tori\t%0,%0,%x1";
682 else if (code1 == CONST_DOUBLE && mode == SFmode)
684 if (op1 == CONST0_RTX (SFmode))
686 if (GP_REG_P (regno0))
687 ret = "or\t%0,%%0,%.";
690 else
692 delay = DELAY_LOAD;
693 ret = "li.s\t%0,%1";
697 else if (code1 == LABEL_REF)
699 if (TARGET_STATS)
700 iq2000_count_memory_refs (op1, 1);
702 ret = "la\t%0,%a1";
705 else if (code1 == SYMBOL_REF || code1 == CONST)
707 if (TARGET_STATS)
708 iq2000_count_memory_refs (op1, 1);
710 ret = "la\t%0,%a1";
713 else if (code1 == PLUS)
715 rtx add_op0 = XEXP (op1, 0);
716 rtx add_op1 = XEXP (op1, 1);
718 if (GET_CODE (XEXP (op1, 1)) == REG
719 && GET_CODE (XEXP (op1, 0)) == CONST_INT)
720 add_op0 = XEXP (op1, 1), add_op1 = XEXP (op1, 0);
722 operands[2] = add_op0;
723 operands[3] = add_op1;
724 ret = "add%:\t%0,%2,%3";
727 else if (code1 == HIGH)
729 operands[1] = XEXP (op1, 0);
730 ret = "lui\t%0,%%hi(%1)";
734 else if (code0 == MEM)
736 if (TARGET_STATS)
737 iq2000_count_memory_refs (op0, 1);
739 if (code1 == REG)
741 int regno1 = REGNO (op1) + subreg_offset1;
743 if (GP_REG_P (regno1))
745 switch (mode)
747 case E_SFmode: ret = "sw\t%1,%0"; break;
748 case E_SImode: ret = "sw\t%1,%0"; break;
749 case E_HImode: ret = "sh\t%1,%0"; break;
750 case E_QImode: ret = "sb\t%1,%0"; break;
751 default: break;
756 else if (code1 == CONST_INT && INTVAL (op1) == 0)
758 switch (mode)
760 case E_SFmode: ret = "sw\t%z1,%0"; break;
761 case E_SImode: ret = "sw\t%z1,%0"; break;
762 case E_HImode: ret = "sh\t%z1,%0"; break;
763 case E_QImode: ret = "sb\t%z1,%0"; break;
764 default: break;
768 else if (code1 == CONST_DOUBLE && op1 == CONST0_RTX (mode))
770 switch (mode)
772 case E_SFmode: ret = "sw\t%.,%0"; break;
773 case E_SImode: ret = "sw\t%.,%0"; break;
774 case E_HImode: ret = "sh\t%.,%0"; break;
775 case E_QImode: ret = "sb\t%.,%0"; break;
776 default: break;
781 if (ret == 0)
783 abort_with_insn (insn, "Bad move");
784 return 0;
787 if (delay != DELAY_NONE)
788 return iq2000_fill_delay_slot (ret, delay, operands, insn);
790 return ret;
793 /* Provide the costs of an addressing mode that contains ADDR. */
795 static int
796 iq2000_address_cost (rtx addr, machine_mode mode, addr_space_t as,
797 bool speed)
799 switch (GET_CODE (addr))
801 case LO_SUM:
802 return 1;
804 case LABEL_REF:
805 return 2;
807 case CONST:
809 rtx offset = const0_rtx;
811 addr = eliminate_constant_term (XEXP (addr, 0), & offset);
812 if (GET_CODE (addr) == LABEL_REF)
813 return 2;
815 if (GET_CODE (addr) != SYMBOL_REF)
816 return 4;
818 if (! SMALL_INT (offset))
819 return 2;
822 /* Fall through. */
824 case SYMBOL_REF:
825 return SYMBOL_REF_FLAG (addr) ? 1 : 2;
827 case PLUS:
829 rtx plus0 = XEXP (addr, 0);
830 rtx plus1 = XEXP (addr, 1);
832 if (GET_CODE (plus0) != REG && GET_CODE (plus1) == REG)
833 plus0 = XEXP (addr, 1), plus1 = XEXP (addr, 0);
835 if (GET_CODE (plus0) != REG)
836 break;
838 switch (GET_CODE (plus1))
840 case CONST_INT:
841 return SMALL_INT (plus1) ? 1 : 2;
843 case CONST:
844 case SYMBOL_REF:
845 case LABEL_REF:
846 case HIGH:
847 case LO_SUM:
848 return iq2000_address_cost (plus1, mode, as, speed) + 1;
850 default:
851 break;
855 default:
856 break;
859 return 4;
862 /* Make normal rtx_code into something we can index from an array. */
864 static enum internal_test
865 map_test_to_internal_test (enum rtx_code test_code)
867 enum internal_test test = ITEST_MAX;
869 switch (test_code)
871 case EQ: test = ITEST_EQ; break;
872 case NE: test = ITEST_NE; break;
873 case GT: test = ITEST_GT; break;
874 case GE: test = ITEST_GE; break;
875 case LT: test = ITEST_LT; break;
876 case LE: test = ITEST_LE; break;
877 case GTU: test = ITEST_GTU; break;
878 case GEU: test = ITEST_GEU; break;
879 case LTU: test = ITEST_LTU; break;
880 case LEU: test = ITEST_LEU; break;
881 default: break;
884 return test;
887 /* Generate the code to do a TEST_CODE comparison on two integer values CMP0
888 and CMP1. P_INVERT is NULL or ptr if branch needs to reverse its test.
889 The return value RESULT is:
890 (reg:SI xx) The pseudo register the comparison is in
891 0 No register, generate a simple branch. */
894 gen_int_relational (enum rtx_code test_code, rtx result, rtx cmp0, rtx cmp1,
895 int *p_invert)
897 struct cmp_info
899 enum rtx_code test_code; /* Code to use in instruction (LT vs. LTU). */
900 int const_low; /* Low bound of constant we can accept. */
901 int const_high; /* High bound of constant we can accept. */
902 int const_add; /* Constant to add (convert LE -> LT). */
903 int reverse_regs; /* Reverse registers in test. */
904 int invert_const; /* != 0 if invert value if cmp1 is constant. */
905 int invert_reg; /* != 0 if invert value if cmp1 is register. */
906 int unsignedp; /* != 0 for unsigned comparisons. */
909 static struct cmp_info info[ (int)ITEST_MAX ] =
911 { XOR, 0, 65535, 0, 0, 0, 0, 0 }, /* EQ */
912 { XOR, 0, 65535, 0, 0, 1, 1, 0 }, /* NE */
913 { LT, -32769, 32766, 1, 1, 1, 0, 0 }, /* GT */
914 { LT, -32768, 32767, 0, 0, 1, 1, 0 }, /* GE */
915 { LT, -32768, 32767, 0, 0, 0, 0, 0 }, /* LT */
916 { LT, -32769, 32766, 1, 1, 0, 1, 0 }, /* LE */
917 { LTU, -32769, 32766, 1, 1, 1, 0, 1 }, /* GTU */
918 { LTU, -32768, 32767, 0, 0, 1, 1, 1 }, /* GEU */
919 { LTU, -32768, 32767, 0, 0, 0, 0, 1 }, /* LTU */
920 { LTU, -32769, 32766, 1, 1, 0, 1, 1 }, /* LEU */
923 enum internal_test test;
924 machine_mode mode;
925 struct cmp_info *p_info;
926 int branch_p;
927 int eqne_p;
928 int invert;
929 rtx reg;
930 rtx reg2;
932 test = map_test_to_internal_test (test_code);
933 gcc_assert (test != ITEST_MAX);
935 p_info = &info[(int) test];
936 eqne_p = (p_info->test_code == XOR);
938 mode = GET_MODE (cmp0);
939 if (mode == VOIDmode)
940 mode = GET_MODE (cmp1);
942 /* Eliminate simple branches. */
943 branch_p = (result == 0);
944 if (branch_p)
946 if (GET_CODE (cmp0) == REG || GET_CODE (cmp0) == SUBREG)
948 /* Comparisons against zero are simple branches. */
949 if (GET_CODE (cmp1) == CONST_INT && INTVAL (cmp1) == 0)
950 return 0;
952 /* Test for beq/bne. */
953 if (eqne_p)
954 return 0;
957 /* Allocate a pseudo to calculate the value in. */
958 result = gen_reg_rtx (mode);
961 /* Make sure we can handle any constants given to us. */
962 if (GET_CODE (cmp0) == CONST_INT)
963 cmp0 = force_reg (mode, cmp0);
965 if (GET_CODE (cmp1) == CONST_INT)
967 HOST_WIDE_INT value = INTVAL (cmp1);
969 if (value < p_info->const_low
970 || value > p_info->const_high)
971 cmp1 = force_reg (mode, cmp1);
974 /* See if we need to invert the result. */
975 invert = (GET_CODE (cmp1) == CONST_INT
976 ? p_info->invert_const : p_info->invert_reg);
978 if (p_invert != (int *)0)
980 *p_invert = invert;
981 invert = 0;
984 /* Comparison to constants, may involve adding 1 to change a LT into LE.
985 Comparison between two registers, may involve switching operands. */
986 if (GET_CODE (cmp1) == CONST_INT)
988 if (p_info->const_add != 0)
990 HOST_WIDE_INT new_const = INTVAL (cmp1) + p_info->const_add;
992 /* If modification of cmp1 caused overflow,
993 we would get the wrong answer if we follow the usual path;
994 thus, x > 0xffffffffU would turn into x > 0U. */
995 if ((p_info->unsignedp
996 ? (unsigned HOST_WIDE_INT) new_const >
997 (unsigned HOST_WIDE_INT) INTVAL (cmp1)
998 : new_const > INTVAL (cmp1))
999 != (p_info->const_add > 0))
1001 /* This test is always true, but if INVERT is true then
1002 the result of the test needs to be inverted so 0 should
1003 be returned instead. */
1004 emit_move_insn (result, invert ? const0_rtx : const_true_rtx);
1005 return result;
1007 else
1008 cmp1 = GEN_INT (new_const);
1012 else if (p_info->reverse_regs)
1014 rtx temp = cmp0;
1015 cmp0 = cmp1;
1016 cmp1 = temp;
1019 if (test == ITEST_NE && GET_CODE (cmp1) == CONST_INT && INTVAL (cmp1) == 0)
1020 reg = cmp0;
1021 else
1023 reg = (invert || eqne_p) ? gen_reg_rtx (mode) : result;
1024 convert_move (reg, gen_rtx_fmt_ee (p_info->test_code, mode, cmp0, cmp1), 0);
1027 if (test == ITEST_NE)
1029 convert_move (result, gen_rtx_GTU (mode, reg, const0_rtx), 0);
1030 if (p_invert != NULL)
1031 *p_invert = 0;
1032 invert = 0;
1035 else if (test == ITEST_EQ)
1037 reg2 = invert ? gen_reg_rtx (mode) : result;
1038 convert_move (reg2, gen_rtx_LTU (mode, reg, const1_rtx), 0);
1039 reg = reg2;
1042 if (invert)
1044 rtx one;
1046 one = const1_rtx;
1047 convert_move (result, gen_rtx_XOR (mode, reg, one), 0);
1050 return result;
1053 /* Emit the common code for doing conditional branches.
1054 operand[0] is the label to jump to.
1055 The comparison operands are saved away by cmp{si,di,sf,df}. */
1057 void
1058 gen_conditional_branch (rtx operands[], machine_mode mode)
1060 enum rtx_code test_code = GET_CODE (operands[0]);
1061 rtx cmp0 = operands[1];
1062 rtx cmp1 = operands[2];
1063 rtx reg;
1064 int invert;
1065 rtx label1, label2;
1067 invert = 0;
1068 reg = gen_int_relational (test_code, NULL_RTX, cmp0, cmp1, &invert);
1070 if (reg)
1072 cmp0 = reg;
1073 cmp1 = const0_rtx;
1074 test_code = NE;
1076 else if (GET_CODE (cmp1) == CONST_INT && INTVAL (cmp1) != 0)
1077 /* We don't want to build a comparison against a nonzero
1078 constant. */
1079 cmp1 = force_reg (mode, cmp1);
1081 /* Generate the branch. */
1082 label1 = gen_rtx_LABEL_REF (VOIDmode, operands[3]);
1083 label2 = pc_rtx;
1085 if (invert)
1087 label2 = label1;
1088 label1 = pc_rtx;
1091 emit_jump_insn (gen_rtx_SET (pc_rtx,
1092 gen_rtx_IF_THEN_ELSE (VOIDmode,
1093 gen_rtx_fmt_ee (test_code,
1094 VOIDmode,
1095 cmp0, cmp1),
1096 label1, label2)));
1099 /* Initialize CUM for a function FNTYPE. */
1101 void
1102 init_cumulative_args (CUMULATIVE_ARGS *cum, tree fntype,
1103 rtx libname ATTRIBUTE_UNUSED)
1105 static CUMULATIVE_ARGS zero_cum;
1106 tree param;
1107 tree next_param;
1109 if (TARGET_DEBUG_D_MODE)
1111 fprintf (stderr,
1112 "\ninit_cumulative_args, fntype = 0x%.8lx", (long) fntype);
1114 if (!fntype)
1115 fputc ('\n', stderr);
1117 else
1119 tree ret_type = TREE_TYPE (fntype);
1121 fprintf (stderr, ", fntype code = %s, ret code = %s\n",
1122 get_tree_code_name (TREE_CODE (fntype)),
1123 get_tree_code_name (TREE_CODE (ret_type)));
1127 *cum = zero_cum;
1129 /* Determine if this function has variable arguments. This is
1130 indicated by the last argument being 'void_type_mode' if there
1131 are no variable arguments. The standard IQ2000 calling sequence
1132 passes all arguments in the general purpose registers in this case. */
1134 for (param = fntype ? TYPE_ARG_TYPES (fntype) : 0;
1135 param != 0; param = next_param)
1137 next_param = TREE_CHAIN (param);
1138 if (next_param == 0 && TREE_VALUE (param) != void_type_node)
1139 cum->gp_reg_found = 1;
1143 /* Advance the argument of type TYPE and mode MODE to the next argument
1144 position in CUM. */
1146 static void
1147 iq2000_function_arg_advance (cumulative_args_t cum_v, machine_mode mode,
1148 const_tree type, bool named)
1150 CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
1152 if (TARGET_DEBUG_D_MODE)
1154 fprintf (stderr,
1155 "function_adv({gp reg found = %d, arg # = %2d, words = %2d}, %4s, ",
1156 cum->gp_reg_found, cum->arg_number, cum->arg_words,
1157 GET_MODE_NAME (mode));
1158 fprintf (stderr, "%p", (const void *) type);
1159 fprintf (stderr, ", %d )\n\n", named);
1162 cum->arg_number++;
1163 switch (mode)
1165 case E_VOIDmode:
1166 break;
1168 default:
1169 gcc_assert (GET_MODE_CLASS (mode) == MODE_COMPLEX_INT
1170 || GET_MODE_CLASS (mode) == MODE_COMPLEX_FLOAT);
1172 cum->gp_reg_found = 1;
1173 cum->arg_words += ((GET_MODE_SIZE (mode) + UNITS_PER_WORD - 1)
1174 / UNITS_PER_WORD);
1175 break;
1177 case E_BLKmode:
1178 cum->gp_reg_found = 1;
1179 cum->arg_words += ((int_size_in_bytes (type) + UNITS_PER_WORD - 1)
1180 / UNITS_PER_WORD);
1181 break;
1183 case E_SFmode:
1184 cum->arg_words ++;
1185 if (! cum->gp_reg_found && cum->arg_number <= 2)
1186 cum->fp_code += 1 << ((cum->arg_number - 1) * 2);
1187 break;
1189 case E_DFmode:
1190 cum->arg_words += 2;
1191 if (! cum->gp_reg_found && cum->arg_number <= 2)
1192 cum->fp_code += 2 << ((cum->arg_number - 1) * 2);
1193 break;
1195 case E_DImode:
1196 cum->gp_reg_found = 1;
1197 cum->arg_words += 2;
1198 break;
1200 case E_TImode:
1201 cum->gp_reg_found = 1;
1202 cum->arg_words += 4;
1203 break;
1205 case E_QImode:
1206 case E_HImode:
1207 case E_SImode:
1208 cum->gp_reg_found = 1;
1209 cum->arg_words ++;
1210 break;
1214 /* Return an RTL expression containing the register for the given mode MODE
1215 and type TYPE in CUM, or 0 if the argument is to be passed on the stack. */
1217 static rtx
1218 iq2000_function_arg (cumulative_args_t cum_v, machine_mode mode,
1219 const_tree type, bool named)
1221 CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
1222 rtx ret;
1223 int regbase = -1;
1224 int bias = 0;
1225 unsigned int *arg_words = &cum->arg_words;
1226 int struct_p = (type != 0
1227 && (TREE_CODE (type) == RECORD_TYPE
1228 || TREE_CODE (type) == UNION_TYPE
1229 || TREE_CODE (type) == QUAL_UNION_TYPE));
1231 if (TARGET_DEBUG_D_MODE)
1233 fprintf (stderr,
1234 "function_arg( {gp reg found = %d, arg # = %2d, words = %2d}, %4s, ",
1235 cum->gp_reg_found, cum->arg_number, cum->arg_words,
1236 GET_MODE_NAME (mode));
1237 fprintf (stderr, "%p", (const void *) type);
1238 fprintf (stderr, ", %d ) = ", named);
1242 cum->last_arg_fp = 0;
1243 switch (mode)
1245 case E_SFmode:
1246 regbase = GP_ARG_FIRST;
1247 break;
1249 case E_DFmode:
1250 cum->arg_words += cum->arg_words & 1;
1252 regbase = GP_ARG_FIRST;
1253 break;
1255 default:
1256 gcc_assert (GET_MODE_CLASS (mode) == MODE_COMPLEX_INT
1257 || GET_MODE_CLASS (mode) == MODE_COMPLEX_FLOAT);
1259 /* FALLTHRU */
1260 case E_BLKmode:
1261 if (type != NULL_TREE && TYPE_ALIGN (type) > (unsigned) BITS_PER_WORD)
1262 cum->arg_words += (cum->arg_words & 1);
1263 regbase = GP_ARG_FIRST;
1264 break;
1266 case E_VOIDmode:
1267 case E_QImode:
1268 case E_HImode:
1269 case E_SImode:
1270 regbase = GP_ARG_FIRST;
1271 break;
1273 case E_DImode:
1274 cum->arg_words += (cum->arg_words & 1);
1275 regbase = GP_ARG_FIRST;
1276 break;
1278 case E_TImode:
1279 cum->arg_words += (cum->arg_words & 3);
1280 regbase = GP_ARG_FIRST;
1281 break;
1284 if (*arg_words >= (unsigned) MAX_ARGS_IN_REGISTERS)
1286 if (TARGET_DEBUG_D_MODE)
1287 fprintf (stderr, "<stack>%s\n", struct_p ? ", [struct]" : "");
1289 ret = 0;
1291 else
1293 gcc_assert (regbase != -1);
1295 if (! type || TREE_CODE (type) != RECORD_TYPE
1296 || ! named || ! TYPE_SIZE_UNIT (type)
1297 || ! tree_fits_uhwi_p (TYPE_SIZE_UNIT (type)))
1298 ret = gen_rtx_REG (mode, regbase + *arg_words + bias);
1299 else
1301 tree field;
1303 for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
1304 if (TREE_CODE (field) == FIELD_DECL
1305 && TREE_CODE (TREE_TYPE (field)) == REAL_TYPE
1306 && TYPE_PRECISION (TREE_TYPE (field)) == BITS_PER_WORD
1307 && tree_fits_shwi_p (bit_position (field))
1308 && int_bit_position (field) % BITS_PER_WORD == 0)
1309 break;
1311 /* If the whole struct fits a DFmode register,
1312 we don't need the PARALLEL. */
1313 if (! field || mode == DFmode)
1314 ret = gen_rtx_REG (mode, regbase + *arg_words + bias);
1315 else
1317 unsigned int chunks;
1318 HOST_WIDE_INT bitpos;
1319 unsigned int regno;
1320 unsigned int i;
1322 /* ??? If this is a packed structure, then the last hunk won't
1323 be 64 bits. */
1324 chunks
1325 = tree_to_uhwi (TYPE_SIZE_UNIT (type)) / UNITS_PER_WORD;
1326 if (chunks + *arg_words + bias > (unsigned) MAX_ARGS_IN_REGISTERS)
1327 chunks = MAX_ARGS_IN_REGISTERS - *arg_words - bias;
1329 /* Assign_parms checks the mode of ENTRY_PARM, so we must
1330 use the actual mode here. */
1331 ret = gen_rtx_PARALLEL (mode, rtvec_alloc (chunks));
1333 bitpos = 0;
1334 regno = regbase + *arg_words + bias;
1335 field = TYPE_FIELDS (type);
1336 for (i = 0; i < chunks; i++)
1338 rtx reg;
1340 for (; field; field = DECL_CHAIN (field))
1341 if (TREE_CODE (field) == FIELD_DECL
1342 && int_bit_position (field) >= bitpos)
1343 break;
1345 if (field
1346 && int_bit_position (field) == bitpos
1347 && TREE_CODE (TREE_TYPE (field)) == REAL_TYPE
1348 && TYPE_PRECISION (TREE_TYPE (field)) == BITS_PER_WORD)
1349 reg = gen_rtx_REG (DFmode, regno++);
1350 else
1351 reg = gen_rtx_REG (word_mode, regno);
1353 XVECEXP (ret, 0, i)
1354 = gen_rtx_EXPR_LIST (VOIDmode, reg,
1355 GEN_INT (bitpos / BITS_PER_UNIT));
1357 bitpos += 64;
1358 regno++;
1363 if (TARGET_DEBUG_D_MODE)
1364 fprintf (stderr, "%s%s\n", reg_names[regbase + *arg_words + bias],
1365 struct_p ? ", [struct]" : "");
1368 /* We will be called with a mode of VOIDmode after the last argument
1369 has been seen. Whatever we return will be passed to the call
1370 insn. If we need any shifts for small structures, return them in
1371 a PARALLEL. */
1372 if (mode == VOIDmode)
1374 if (cum->num_adjusts > 0)
1375 ret = gen_rtx_PARALLEL ((machine_mode) cum->fp_code,
1376 gen_rtvec_v (cum->num_adjusts, cum->adjust));
1379 return ret;
1382 /* Implement TARGET_FUNCTION_ARG_PADDING. */
1384 static pad_direction
1385 iq2000_function_arg_padding (machine_mode mode, const_tree type)
1387 return (! BYTES_BIG_ENDIAN
1388 ? PAD_UPWARD
1389 : ((mode == BLKmode
1390 ? (type
1391 && TREE_CODE (TYPE_SIZE (type)) == INTEGER_CST
1392 && int_size_in_bytes (type) < (PARM_BOUNDARY / BITS_PER_UNIT))
1393 : (GET_MODE_BITSIZE (mode) < PARM_BOUNDARY
1394 && GET_MODE_CLASS (mode) == MODE_INT))
1395 ? PAD_DOWNWARD : PAD_UPWARD));
1398 static unsigned int
1399 iq2000_function_arg_boundary (machine_mode mode, const_tree type)
1401 return (type != NULL_TREE
1402 ? (TYPE_ALIGN (type) <= PARM_BOUNDARY
1403 ? PARM_BOUNDARY
1404 : TYPE_ALIGN (type))
1405 : (GET_MODE_ALIGNMENT (mode) <= PARM_BOUNDARY
1406 ? PARM_BOUNDARY
1407 : GET_MODE_ALIGNMENT (mode)));
1410 static int
1411 iq2000_arg_partial_bytes (cumulative_args_t cum_v, machine_mode mode,
1412 tree type ATTRIBUTE_UNUSED,
1413 bool named ATTRIBUTE_UNUSED)
1415 CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
1417 if (mode == DImode && cum->arg_words == MAX_ARGS_IN_REGISTERS - 1)
1419 if (TARGET_DEBUG_D_MODE)
1420 fprintf (stderr, "iq2000_arg_partial_bytes=%d\n", UNITS_PER_WORD);
1421 return UNITS_PER_WORD;
1424 return 0;
1427 /* Implement va_start. */
1429 static void
1430 iq2000_va_start (tree valist, rtx nextarg)
1432 int int_arg_words;
1433 /* Find out how many non-float named formals. */
1434 int gpr_save_area_size;
1435 /* Note UNITS_PER_WORD is 4 bytes. */
1436 int_arg_words = crtl->args.info.arg_words;
1438 if (int_arg_words < 8 )
1439 /* Adjust for the prologue's economy measure. */
1440 gpr_save_area_size = (8 - int_arg_words) * UNITS_PER_WORD;
1441 else
1442 gpr_save_area_size = 0;
1444 /* Everything is in the GPR save area, or in the overflow
1445 area which is contiguous with it. */
1446 nextarg = plus_constant (Pmode, nextarg, - gpr_save_area_size);
1447 std_expand_builtin_va_start (valist, nextarg);
1450 /* Allocate a chunk of memory for per-function machine-dependent data. */
1452 static struct machine_function *
1453 iq2000_init_machine_status (void)
1455 return ggc_cleared_alloc<machine_function> ();
1458 /* Detect any conflicts in the switches. */
1460 static void
1461 iq2000_option_override (void)
1463 target_flags &= ~MASK_GPOPT;
1465 iq2000_isa = IQ2000_ISA_DEFAULT;
1467 /* Identify the processor type. */
1469 iq2000_print_operand_punct['?'] = 1;
1470 iq2000_print_operand_punct['#'] = 1;
1471 iq2000_print_operand_punct['&'] = 1;
1472 iq2000_print_operand_punct['!'] = 1;
1473 iq2000_print_operand_punct['*'] = 1;
1474 iq2000_print_operand_punct['@'] = 1;
1475 iq2000_print_operand_punct['.'] = 1;
1476 iq2000_print_operand_punct['('] = 1;
1477 iq2000_print_operand_punct[')'] = 1;
1478 iq2000_print_operand_punct['['] = 1;
1479 iq2000_print_operand_punct[']'] = 1;
1480 iq2000_print_operand_punct['<'] = 1;
1481 iq2000_print_operand_punct['>'] = 1;
1482 iq2000_print_operand_punct['{'] = 1;
1483 iq2000_print_operand_punct['}'] = 1;
1484 iq2000_print_operand_punct['^'] = 1;
1485 iq2000_print_operand_punct['$'] = 1;
1486 iq2000_print_operand_punct['+'] = 1;
1487 iq2000_print_operand_punct['~'] = 1;
1489 /* Save GPR registers in word_mode sized hunks. word_mode hasn't been
1490 initialized yet, so we can't use that here. */
1491 gpr_mode = SImode;
1493 /* Function to allocate machine-dependent function status. */
1494 init_machine_status = iq2000_init_machine_status;
1497 /* The arg pointer (which is eliminated) points to the virtual frame pointer,
1498 while the frame pointer (which may be eliminated) points to the stack
1499 pointer after the initial adjustments. */
1501 HOST_WIDE_INT
1502 iq2000_debugger_offset (rtx addr, HOST_WIDE_INT offset)
1504 rtx offset2 = const0_rtx;
1505 rtx reg = eliminate_constant_term (addr, & offset2);
1507 if (offset == 0)
1508 offset = INTVAL (offset2);
1510 if (reg == stack_pointer_rtx || reg == frame_pointer_rtx
1511 || reg == hard_frame_pointer_rtx)
1513 HOST_WIDE_INT frame_size = (!cfun->machine->initialized)
1514 ? compute_frame_size (get_frame_size ())
1515 : cfun->machine->total_size;
1517 offset = offset - frame_size;
1520 return offset;
1523 /* If defined, a C statement to be executed just prior to the output of
1524 assembler code for INSN, to modify the extracted operands so they will be
1525 output differently.
1527 Here the argument OPVEC is the vector containing the operands extracted
1528 from INSN, and NOPERANDS is the number of elements of the vector which
1529 contain meaningful data for this insn. The contents of this vector are
1530 what will be used to convert the insn template into assembler code, so you
1531 can change the assembler output by changing the contents of the vector.
1533 We use it to check if the current insn needs a nop in front of it because
1534 of load delays, and also to update the delay slot statistics. */
1536 void
1537 final_prescan_insn (rtx_insn *insn, rtx opvec[] ATTRIBUTE_UNUSED,
1538 int noperands ATTRIBUTE_UNUSED)
1540 if (dslots_number_nops > 0)
1542 rtx pattern = PATTERN (insn);
1543 int length = get_attr_length (insn);
1545 /* Do we need to emit a NOP? */
1546 if (length == 0
1547 || (iq2000_load_reg != 0 && reg_mentioned_p (iq2000_load_reg, pattern))
1548 || (iq2000_load_reg2 != 0 && reg_mentioned_p (iq2000_load_reg2, pattern))
1549 || (iq2000_load_reg3 != 0 && reg_mentioned_p (iq2000_load_reg3, pattern))
1550 || (iq2000_load_reg4 != 0
1551 && reg_mentioned_p (iq2000_load_reg4, pattern)))
1552 fputs ("\tnop\n", asm_out_file);
1554 else
1555 dslots_load_filled ++;
1557 while (--dslots_number_nops > 0)
1558 fputs ("\tnop\n", asm_out_file);
1560 iq2000_load_reg = 0;
1561 iq2000_load_reg2 = 0;
1562 iq2000_load_reg3 = 0;
1563 iq2000_load_reg4 = 0;
1566 if ( (JUMP_P (insn)
1567 || CALL_P (insn)
1568 || (GET_CODE (PATTERN (insn)) == RETURN))
1569 && NEXT_INSN (PREV_INSN (insn)) == insn)
1571 rtx_insn *tmp = insn;
1572 while (NEXT_INSN (tmp)
1573 && NOTE_P (NEXT_INSN (tmp))
1574 && NOTE_KIND (NEXT_INSN (tmp)) == NOTE_INSN_CALL_ARG_LOCATION)
1575 tmp = NEXT_INSN (tmp);
1577 rtx_insn *nop_insn = emit_insn_after (gen_nop (), tmp);
1578 INSN_ADDRESSES_NEW (nop_insn, -1);
1581 if (TARGET_STATS
1582 && (JUMP_P (insn) || CALL_P (insn)))
1583 dslots_jump_total ++;
1586 /* Return the bytes needed to compute the frame pointer from the current
1587 stack pointer where SIZE is the # of var. bytes allocated.
1589 IQ2000 stack frames look like:
1591 Before call After call
1592 +-----------------------+ +-----------------------+
1593 high | | | |
1594 mem. | | | |
1595 | caller's temps. | | caller's temps. |
1596 | | | |
1597 +-----------------------+ +-----------------------+
1598 | | | |
1599 | arguments on stack. | | arguments on stack. |
1600 | | | |
1601 +-----------------------+ +-----------------------+
1602 | 4 words to save | | 4 words to save |
1603 | arguments passed | | arguments passed |
1604 | in registers, even | | in registers, even |
1605 SP->| if not passed. | VFP->| if not passed. |
1606 +-----------------------+ +-----------------------+
1608 | fp register save |
1610 +-----------------------+
1612 | gp register save |
1614 +-----------------------+
1616 | local variables |
1618 +-----------------------+
1620 | alloca allocations |
1622 +-----------------------+
1624 | GP save for V.4 abi |
1626 +-----------------------+
1628 | arguments on stack |
1630 +-----------------------+
1631 | 4 words to save |
1632 | arguments passed |
1633 | in registers, even |
1634 low SP->| if not passed. |
1635 memory +-----------------------+ */
1637 HOST_WIDE_INT
1638 compute_frame_size (HOST_WIDE_INT size)
1640 int regno;
1641 HOST_WIDE_INT total_size; /* # bytes that the entire frame takes up. */
1642 HOST_WIDE_INT var_size; /* # bytes that variables take up. */
1643 HOST_WIDE_INT args_size; /* # bytes that outgoing arguments take up. */
1644 HOST_WIDE_INT extra_size; /* # extra bytes. */
1645 HOST_WIDE_INT gp_reg_rounded; /* # bytes needed to store gp after rounding. */
1646 HOST_WIDE_INT gp_reg_size; /* # bytes needed to store gp regs. */
1647 HOST_WIDE_INT fp_reg_size; /* # bytes needed to store fp regs. */
1648 long mask; /* mask of saved gp registers. */
1650 gp_reg_size = 0;
1651 fp_reg_size = 0;
1652 mask = 0;
1653 extra_size = IQ2000_STACK_ALIGN ((0));
1654 var_size = IQ2000_STACK_ALIGN (size);
1655 args_size = IQ2000_STACK_ALIGN (crtl->outgoing_args_size);
1657 /* If a function dynamically allocates the stack and
1658 has 0 for STACK_DYNAMIC_OFFSET then allocate some stack space. */
1659 if (args_size == 0 && cfun->calls_alloca)
1660 args_size = 4 * UNITS_PER_WORD;
1662 total_size = var_size + args_size + extra_size;
1664 /* Calculate space needed for gp registers. */
1665 for (regno = GP_REG_FIRST; regno <= GP_REG_LAST; regno++)
1667 if (MUST_SAVE_REGISTER (regno))
1669 gp_reg_size += GET_MODE_SIZE (gpr_mode);
1670 mask |= 1L << (regno - GP_REG_FIRST);
1674 /* We need to restore these for the handler. */
1675 if (crtl->calls_eh_return)
1677 unsigned int i;
1679 for (i = 0; ; ++i)
1681 regno = EH_RETURN_DATA_REGNO (i);
1682 if (regno == (int) INVALID_REGNUM)
1683 break;
1684 gp_reg_size += GET_MODE_SIZE (gpr_mode);
1685 mask |= 1L << (regno - GP_REG_FIRST);
1689 gp_reg_rounded = IQ2000_STACK_ALIGN (gp_reg_size);
1690 total_size += gp_reg_rounded + IQ2000_STACK_ALIGN (fp_reg_size);
1692 /* The gp reg is caller saved, so there is no need for leaf routines
1693 (total_size == extra_size) to save the gp reg. */
1694 if (total_size == extra_size
1695 && ! profile_flag)
1696 total_size = extra_size = 0;
1698 total_size += IQ2000_STACK_ALIGN (crtl->args.pretend_args_size);
1700 /* Save other computed information. */
1701 cfun->machine->total_size = total_size;
1702 cfun->machine->var_size = var_size;
1703 cfun->machine->args_size = args_size;
1704 cfun->machine->extra_size = extra_size;
1705 cfun->machine->gp_reg_size = gp_reg_size;
1706 cfun->machine->fp_reg_size = fp_reg_size;
1707 cfun->machine->mask = mask;
1708 cfun->machine->initialized = reload_completed;
1709 cfun->machine->num_gp = gp_reg_size / UNITS_PER_WORD;
1711 if (mask)
1713 unsigned long offset;
1715 offset = (args_size + extra_size + var_size
1716 + gp_reg_size - GET_MODE_SIZE (gpr_mode));
1718 cfun->machine->gp_sp_offset = offset;
1719 cfun->machine->gp_save_offset = offset - total_size;
1721 else
1723 cfun->machine->gp_sp_offset = 0;
1724 cfun->machine->gp_save_offset = 0;
1727 cfun->machine->fp_sp_offset = 0;
1728 cfun->machine->fp_save_offset = 0;
1730 /* Ok, we're done. */
1731 return total_size;
1735 /* We can always eliminate to the frame pointer. We can eliminate to the
1736 stack pointer unless a frame pointer is needed. */
1738 bool
1739 iq2000_can_eliminate (const int from, const int to)
1741 return (from == RETURN_ADDRESS_POINTER_REGNUM
1742 && (! leaf_function_p ()
1743 || (to == GP_REG_FIRST + 31 && leaf_function_p ())))
1744 || (from != RETURN_ADDRESS_POINTER_REGNUM
1745 && (to == HARD_FRAME_POINTER_REGNUM
1746 || (to == STACK_POINTER_REGNUM
1747 && ! frame_pointer_needed)));
1750 /* Implement INITIAL_ELIMINATION_OFFSET. FROM is either the frame
1751 pointer, argument pointer, or return address pointer. TO is either
1752 the stack pointer or hard frame pointer. */
1755 iq2000_initial_elimination_offset (int from, int to ATTRIBUTE_UNUSED)
1757 int offset;
1759 compute_frame_size (get_frame_size ());
1760 if ((from) == FRAME_POINTER_REGNUM)
1761 (offset) = 0;
1762 else if ((from) == ARG_POINTER_REGNUM)
1763 (offset) = (cfun->machine->total_size);
1764 else if ((from) == RETURN_ADDRESS_POINTER_REGNUM)
1766 if (leaf_function_p ())
1767 (offset) = 0;
1768 else (offset) = cfun->machine->gp_sp_offset
1769 + ((UNITS_PER_WORD - (POINTER_SIZE / BITS_PER_UNIT))
1770 * (BYTES_BIG_ENDIAN != 0));
1772 else
1773 gcc_unreachable ();
1775 return offset;
1778 /* Common code to emit the insns (or to write the instructions to a file)
1779 to save/restore registers.
1780 Other parts of the code assume that IQ2000_TEMP1_REGNUM (aka large_reg)
1781 is not modified within save_restore_insns. */
1783 #define BITSET_P(VALUE,BIT) (((VALUE) & (1L << (BIT))) != 0)
1785 /* Emit instructions to load the value (SP + OFFSET) into IQ2000_TEMP2_REGNUM
1786 and return an rtl expression for the register. Write the assembly
1787 instructions directly to FILE if it is not null, otherwise emit them as
1788 rtl.
1790 This function is a subroutine of save_restore_insns. It is used when
1791 OFFSET is too large to add in a single instruction. */
1793 static rtx
1794 iq2000_add_large_offset_to_sp (HOST_WIDE_INT offset)
1796 rtx reg = gen_rtx_REG (Pmode, IQ2000_TEMP2_REGNUM);
1797 rtx offset_rtx = GEN_INT (offset);
1799 emit_move_insn (reg, offset_rtx);
1800 emit_insn (gen_addsi3 (reg, reg, stack_pointer_rtx));
1801 return reg;
1804 /* Make INSN frame related and note that it performs the frame-related
1805 operation DWARF_PATTERN. */
1807 static void
1808 iq2000_annotate_frame_insn (rtx_insn *insn, rtx dwarf_pattern)
1810 RTX_FRAME_RELATED_P (insn) = 1;
1811 REG_NOTES (insn) = alloc_EXPR_LIST (REG_FRAME_RELATED_EXPR,
1812 dwarf_pattern,
1813 REG_NOTES (insn));
1816 /* Emit a move instruction that stores REG in MEM. Make the instruction
1817 frame related and note that it stores REG at (SP + OFFSET). */
1819 static void
1820 iq2000_emit_frame_related_store (rtx mem, rtx reg, HOST_WIDE_INT offset)
1822 rtx dwarf_address = plus_constant (Pmode, stack_pointer_rtx, offset);
1823 rtx dwarf_mem = gen_rtx_MEM (GET_MODE (reg), dwarf_address);
1825 iq2000_annotate_frame_insn (emit_move_insn (mem, reg),
1826 gen_rtx_SET (dwarf_mem, reg));
1829 /* Emit instructions to save/restore registers, as determined by STORE_P. */
1831 static void
1832 save_restore_insns (int store_p)
1834 long mask = cfun->machine->mask;
1835 int regno;
1836 rtx base_reg_rtx;
1837 HOST_WIDE_INT base_offset;
1838 HOST_WIDE_INT gp_offset;
1839 HOST_WIDE_INT end_offset;
1841 gcc_assert (!frame_pointer_needed
1842 || BITSET_P (mask, HARD_FRAME_POINTER_REGNUM - GP_REG_FIRST));
1844 if (mask == 0)
1846 base_reg_rtx = 0, base_offset = 0;
1847 return;
1850 /* Save registers starting from high to low. The debuggers prefer at least
1851 the return register be stored at func+4, and also it allows us not to
1852 need a nop in the epilog if at least one register is reloaded in
1853 addition to return address. */
1855 /* Save GP registers if needed. */
1856 /* Pick which pointer to use as a base register. For small frames, just
1857 use the stack pointer. Otherwise, use a temporary register. Save 2
1858 cycles if the save area is near the end of a large frame, by reusing
1859 the constant created in the prologue/epilogue to adjust the stack
1860 frame. */
1862 gp_offset = cfun->machine->gp_sp_offset;
1863 end_offset
1864 = gp_offset - (cfun->machine->gp_reg_size
1865 - GET_MODE_SIZE (gpr_mode));
1867 if (gp_offset < 0 || end_offset < 0)
1868 internal_error
1869 ("gp_offset (%ld) or end_offset (%ld) is less than zero",
1870 (long) gp_offset, (long) end_offset);
1872 else if (gp_offset < 32768)
1873 base_reg_rtx = stack_pointer_rtx, base_offset = 0;
1874 else
1876 int regno;
1877 int reg_save_count = 0;
1879 for (regno = GP_REG_LAST; regno >= GP_REG_FIRST; regno--)
1880 if (BITSET_P (mask, regno - GP_REG_FIRST)) reg_save_count += 1;
1881 base_offset = gp_offset - ((reg_save_count - 1) * 4);
1882 base_reg_rtx = iq2000_add_large_offset_to_sp (base_offset);
1885 for (regno = GP_REG_LAST; regno >= GP_REG_FIRST; regno--)
1887 if (BITSET_P (mask, regno - GP_REG_FIRST))
1889 rtx reg_rtx;
1890 rtx mem_rtx
1891 = gen_rtx_MEM (gpr_mode,
1892 gen_rtx_PLUS (Pmode, base_reg_rtx,
1893 GEN_INT (gp_offset - base_offset)));
1895 reg_rtx = gen_rtx_REG (gpr_mode, regno);
1897 if (store_p)
1898 iq2000_emit_frame_related_store (mem_rtx, reg_rtx, gp_offset);
1899 else
1901 emit_move_insn (reg_rtx, mem_rtx);
1903 gp_offset -= GET_MODE_SIZE (gpr_mode);
1908 /* Expand the prologue into a bunch of separate insns. */
1910 void
1911 iq2000_expand_prologue (void)
1913 int regno;
1914 HOST_WIDE_INT tsize;
1915 int last_arg_is_vararg_marker = 0;
1916 tree fndecl = current_function_decl;
1917 tree fntype = TREE_TYPE (fndecl);
1918 tree fnargs = DECL_ARGUMENTS (fndecl);
1919 rtx next_arg_reg;
1920 int i;
1921 tree next_arg;
1922 tree cur_arg;
1923 CUMULATIVE_ARGS args_so_far_v;
1924 cumulative_args_t args_so_far;
1925 int store_args_on_stack = (iq2000_can_use_return_insn ());
1927 /* If struct value address is treated as the first argument. */
1928 if (aggregate_value_p (DECL_RESULT (fndecl), fndecl)
1929 && !cfun->returns_pcc_struct
1930 && targetm.calls.struct_value_rtx (TREE_TYPE (fndecl), 1) == 0)
1932 tree type = build_pointer_type (fntype);
1933 tree function_result_decl = build_decl (BUILTINS_LOCATION,
1934 PARM_DECL, NULL_TREE, type);
1936 DECL_ARG_TYPE (function_result_decl) = type;
1937 DECL_CHAIN (function_result_decl) = fnargs;
1938 fnargs = function_result_decl;
1941 /* For arguments passed in registers, find the register number
1942 of the first argument in the variable part of the argument list,
1943 otherwise GP_ARG_LAST+1. Note also if the last argument is
1944 the varargs special argument, and treat it as part of the
1945 variable arguments.
1947 This is only needed if store_args_on_stack is true. */
1948 INIT_CUMULATIVE_ARGS (args_so_far_v, fntype, NULL_RTX, 0, 0);
1949 args_so_far = pack_cumulative_args (&args_so_far_v);
1950 regno = GP_ARG_FIRST;
1952 for (cur_arg = fnargs; cur_arg != 0; cur_arg = next_arg)
1954 tree passed_type = DECL_ARG_TYPE (cur_arg);
1955 machine_mode passed_mode = TYPE_MODE (passed_type);
1956 rtx entry_parm;
1958 if (TREE_ADDRESSABLE (passed_type))
1960 passed_type = build_pointer_type (passed_type);
1961 passed_mode = Pmode;
1964 entry_parm = iq2000_function_arg (args_so_far, passed_mode,
1965 passed_type, true);
1967 iq2000_function_arg_advance (args_so_far, passed_mode,
1968 passed_type, true);
1969 next_arg = DECL_CHAIN (cur_arg);
1971 if (entry_parm && store_args_on_stack)
1973 if (next_arg == 0
1974 && DECL_NAME (cur_arg)
1975 && ((0 == strcmp (IDENTIFIER_POINTER (DECL_NAME (cur_arg)),
1976 "__builtin_va_alist"))
1977 || (0 == strcmp (IDENTIFIER_POINTER (DECL_NAME (cur_arg)),
1978 "va_alist"))))
1980 last_arg_is_vararg_marker = 1;
1981 break;
1983 else
1985 int words;
1987 gcc_assert (GET_CODE (entry_parm) == REG);
1989 /* Passed in a register, so will get homed automatically. */
1990 if (GET_MODE (entry_parm) == BLKmode)
1991 words = (int_size_in_bytes (passed_type) + 3) / 4;
1992 else
1993 words = (GET_MODE_SIZE (GET_MODE (entry_parm)) + 3) / 4;
1995 regno = REGNO (entry_parm) + words - 1;
1998 else
2000 regno = GP_ARG_LAST+1;
2001 break;
2005 /* In order to pass small structures by value in registers we need to
2006 shift the value into the high part of the register.
2007 iq2000_unction_arg has encoded a PARALLEL rtx, holding a vector of
2008 adjustments to be made as the next_arg_reg variable, so we split up
2009 the insns, and emit them separately. */
2010 next_arg_reg = iq2000_function_arg (args_so_far, VOIDmode,
2011 void_type_node, true);
2012 if (next_arg_reg != 0 && GET_CODE (next_arg_reg) == PARALLEL)
2014 rtvec adjust = XVEC (next_arg_reg, 0);
2015 int num = GET_NUM_ELEM (adjust);
2017 for (i = 0; i < num; i++)
2019 rtx pattern;
2021 pattern = RTVEC_ELT (adjust, i);
2022 if (GET_CODE (pattern) != SET
2023 || GET_CODE (SET_SRC (pattern)) != ASHIFT)
2024 abort_with_insn (pattern, "Insn is not a shift");
2025 PUT_CODE (SET_SRC (pattern), ASHIFTRT);
2027 emit_insn (pattern);
2031 tsize = compute_frame_size (get_frame_size ());
2033 /* If this function is a varargs function, store any registers that
2034 would normally hold arguments ($4 - $7) on the stack. */
2035 if (store_args_on_stack
2036 && (stdarg_p (fntype)
2037 || last_arg_is_vararg_marker))
2039 int offset = (regno - GP_ARG_FIRST) * UNITS_PER_WORD;
2040 rtx ptr = stack_pointer_rtx;
2042 for (; regno <= GP_ARG_LAST; regno++)
2044 if (offset != 0)
2045 ptr = gen_rtx_PLUS (Pmode, stack_pointer_rtx, GEN_INT (offset));
2046 emit_move_insn (gen_rtx_MEM (gpr_mode, ptr),
2047 gen_rtx_REG (gpr_mode, regno));
2049 offset += GET_MODE_SIZE (gpr_mode);
2053 if (tsize > 0)
2055 rtx tsize_rtx = GEN_INT (tsize);
2056 rtx adjustment_rtx, dwarf_pattern;
2057 rtx_insn *insn;
2059 if (tsize > 32767)
2061 adjustment_rtx = gen_rtx_REG (Pmode, IQ2000_TEMP1_REGNUM);
2062 emit_move_insn (adjustment_rtx, tsize_rtx);
2064 else
2065 adjustment_rtx = tsize_rtx;
2067 insn = emit_insn (gen_subsi3 (stack_pointer_rtx, stack_pointer_rtx,
2068 adjustment_rtx));
2070 dwarf_pattern = gen_rtx_SET (stack_pointer_rtx,
2071 plus_constant (Pmode, stack_pointer_rtx,
2072 -tsize));
2074 iq2000_annotate_frame_insn (insn, dwarf_pattern);
2076 save_restore_insns (1);
2078 if (frame_pointer_needed)
2080 rtx_insn *insn = 0;
2082 insn = emit_insn (gen_movsi (hard_frame_pointer_rtx,
2083 stack_pointer_rtx));
2085 if (insn)
2086 RTX_FRAME_RELATED_P (insn) = 1;
2090 if (flag_stack_usage_info)
2091 current_function_static_stack_size = cfun->machine->total_size;
2093 emit_insn (gen_blockage ());
2096 /* Expand the epilogue into a bunch of separate insns. */
2098 void
2099 iq2000_expand_epilogue (void)
2101 HOST_WIDE_INT tsize = cfun->machine->total_size;
2102 rtx tsize_rtx = GEN_INT (tsize);
2103 rtx tmp_rtx = (rtx)0;
2105 if (iq2000_can_use_return_insn ())
2107 emit_jump_insn (gen_return ());
2108 return;
2111 if (tsize > 32767)
2113 tmp_rtx = gen_rtx_REG (Pmode, IQ2000_TEMP1_REGNUM);
2114 emit_move_insn (tmp_rtx, tsize_rtx);
2115 tsize_rtx = tmp_rtx;
2118 if (tsize > 0)
2120 if (frame_pointer_needed)
2122 emit_insn (gen_blockage ());
2124 emit_insn (gen_movsi (stack_pointer_rtx, hard_frame_pointer_rtx));
2127 save_restore_insns (0);
2129 if (crtl->calls_eh_return)
2131 rtx eh_ofs = EH_RETURN_STACKADJ_RTX;
2132 emit_insn (gen_addsi3 (eh_ofs, eh_ofs, tsize_rtx));
2133 tsize_rtx = eh_ofs;
2136 emit_insn (gen_blockage ());
2138 if (tsize != 0 || crtl->calls_eh_return)
2140 emit_insn (gen_addsi3 (stack_pointer_rtx, stack_pointer_rtx,
2141 tsize_rtx));
2145 if (crtl->calls_eh_return)
2147 /* Perform the additional bump for __throw. */
2148 emit_move_insn (gen_rtx_REG (Pmode, HARD_FRAME_POINTER_REGNUM),
2149 stack_pointer_rtx);
2150 emit_use (gen_rtx_REG (Pmode, HARD_FRAME_POINTER_REGNUM));
2151 emit_jump_insn (gen_eh_return_internal ());
2153 else
2154 emit_jump_insn (gen_return_internal (gen_rtx_REG (Pmode,
2155 GP_REG_FIRST + 31)));
2158 void
2159 iq2000_expand_eh_return (rtx address)
2161 HOST_WIDE_INT gp_offset = cfun->machine->gp_sp_offset;
2162 rtx scratch;
2164 scratch = plus_constant (Pmode, stack_pointer_rtx, gp_offset);
2165 emit_move_insn (gen_rtx_MEM (GET_MODE (address), scratch), address);
2168 /* Return nonzero if this function is known to have a null epilogue.
2169 This allows the optimizer to omit jumps to jumps if no stack
2170 was created. */
2173 iq2000_can_use_return_insn (void)
2175 if (! reload_completed)
2176 return 0;
2178 if (df_regs_ever_live_p (31) || profile_flag)
2179 return 0;
2181 if (cfun->machine->initialized)
2182 return cfun->machine->total_size == 0;
2184 return compute_frame_size (get_frame_size ()) == 0;
2187 /* Choose the section to use for the constant rtx expression X that has
2188 mode MODE. */
2190 static section *
2191 iq2000_select_rtx_section (machine_mode mode, rtx x ATTRIBUTE_UNUSED,
2192 unsigned HOST_WIDE_INT align)
2194 /* For embedded applications, always put constants in read-only data,
2195 in order to reduce RAM usage. */
2196 return mergeable_constant_section (mode, align, 0);
2199 /* Choose the section to use for DECL. RELOC is true if its value contains
2200 any relocatable expression.
2202 Some of the logic used here needs to be replicated in
2203 ENCODE_SECTION_INFO in iq2000.h so that references to these symbols
2204 are done correctly. */
2206 static section *
2207 iq2000_select_section (tree decl, int reloc ATTRIBUTE_UNUSED,
2208 unsigned HOST_WIDE_INT align ATTRIBUTE_UNUSED)
2210 if (TARGET_EMBEDDED_DATA)
2212 /* For embedded applications, always put an object in read-only data
2213 if possible, in order to reduce RAM usage. */
2214 if ((TREE_CODE (decl) == VAR_DECL
2215 && TREE_READONLY (decl) && !TREE_SIDE_EFFECTS (decl)
2216 && DECL_INITIAL (decl)
2217 && (DECL_INITIAL (decl) == error_mark_node
2218 || TREE_CONSTANT (DECL_INITIAL (decl))))
2219 /* Deal with calls from output_constant_def_contents. */
2220 || TREE_CODE (decl) != VAR_DECL)
2221 return readonly_data_section;
2222 else
2223 return data_section;
2225 else
2227 /* For hosted applications, always put an object in small data if
2228 possible, as this gives the best performance. */
2229 if ((TREE_CODE (decl) == VAR_DECL
2230 && TREE_READONLY (decl) && !TREE_SIDE_EFFECTS (decl)
2231 && DECL_INITIAL (decl)
2232 && (DECL_INITIAL (decl) == error_mark_node
2233 || TREE_CONSTANT (DECL_INITIAL (decl))))
2234 /* Deal with calls from output_constant_def_contents. */
2235 || TREE_CODE (decl) != VAR_DECL)
2236 return readonly_data_section;
2237 else
2238 return data_section;
2241 /* Return register to use for a function return value with VALTYPE for function
2242 FUNC. */
2244 static rtx
2245 iq2000_function_value (const_tree valtype,
2246 const_tree fn_decl_or_type,
2247 bool outgoing ATTRIBUTE_UNUSED)
2249 int reg = GP_RETURN;
2250 machine_mode mode = TYPE_MODE (valtype);
2251 int unsignedp = TYPE_UNSIGNED (valtype);
2252 const_tree func = fn_decl_or_type;
2254 if (fn_decl_or_type
2255 && !DECL_P (fn_decl_or_type))
2256 fn_decl_or_type = NULL;
2258 /* Since we promote return types, we must promote the mode here too. */
2259 mode = promote_function_mode (valtype, mode, &unsignedp, func, 1);
2261 return gen_rtx_REG (mode, reg);
2264 /* Worker function for TARGET_LIBCALL_VALUE. */
2266 static rtx
2267 iq2000_libcall_value (machine_mode mode, const_rtx fun ATTRIBUTE_UNUSED)
2269 return gen_rtx_REG (((GET_MODE_CLASS (mode) != MODE_INT
2270 || GET_MODE_SIZE (mode) >= 4)
2271 ? mode : SImode),
2272 GP_RETURN);
2275 /* Worker function for FUNCTION_VALUE_REGNO_P.
2277 On the IQ2000, R2 and R3 are the only register thus used. */
2279 bool
2280 iq2000_function_value_regno_p (const unsigned int regno)
2282 return (regno == GP_RETURN);
2286 /* Return true when an argument must be passed by reference. */
2288 static bool
2289 iq2000_pass_by_reference (cumulative_args_t cum_v, machine_mode mode,
2290 const_tree type, bool named ATTRIBUTE_UNUSED)
2292 CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
2293 int size;
2295 /* We must pass by reference if we would be both passing in registers
2296 and the stack. This is because any subsequent partial arg would be
2297 handled incorrectly in this case. */
2298 if (cum && targetm.calls.must_pass_in_stack (mode, type))
2300 /* Don't pass the actual CUM to FUNCTION_ARG, because we would
2301 get double copies of any offsets generated for small structs
2302 passed in registers. */
2303 CUMULATIVE_ARGS temp;
2305 temp = *cum;
2306 if (iq2000_function_arg (pack_cumulative_args (&temp), mode, type, named)
2307 != 0)
2308 return 1;
2311 if (type == NULL_TREE || mode == DImode || mode == DFmode)
2312 return 0;
2314 size = int_size_in_bytes (type);
2315 return size == -1 || size > UNITS_PER_WORD;
2318 /* Return the length of INSN. LENGTH is the initial length computed by
2319 attributes in the machine-description file. */
2322 iq2000_adjust_insn_length (rtx_insn *insn, int length)
2324 /* A unconditional jump has an unfilled delay slot if it is not part
2325 of a sequence. A conditional jump normally has a delay slot. */
2326 if (simplejump_p (insn)
2327 || ( (JUMP_P (insn)
2328 || CALL_P (insn))))
2329 length += 4;
2331 return length;
2334 /* Output assembly instructions to perform a conditional branch.
2336 INSN is the branch instruction. OPERANDS[0] is the condition.
2337 OPERANDS[1] is the target of the branch. OPERANDS[2] is the target
2338 of the first operand to the condition. If TWO_OPERANDS_P is
2339 nonzero the comparison takes two operands; OPERANDS[3] will be the
2340 second operand.
2342 If INVERTED_P is nonzero we are to branch if the condition does
2343 not hold. If FLOAT_P is nonzero this is a floating-point comparison.
2345 LENGTH is the length (in bytes) of the sequence we are to generate.
2346 That tells us whether to generate a simple conditional branch, or a
2347 reversed conditional branch around a `jr' instruction. */
2349 char *
2350 iq2000_output_conditional_branch (rtx_insn *insn, rtx * operands,
2351 int two_operands_p, int float_p,
2352 int inverted_p, int length)
2354 static char buffer[200];
2355 /* The kind of comparison we are doing. */
2356 enum rtx_code code = GET_CODE (operands[0]);
2357 /* Nonzero if the opcode for the comparison needs a `z' indicating
2358 that it is a comparison against zero. */
2359 int need_z_p;
2360 /* A string to use in the assembly output to represent the first
2361 operand. */
2362 const char *op1 = "%z2";
2363 /* A string to use in the assembly output to represent the second
2364 operand. Use the hard-wired zero register if there's no second
2365 operand. */
2366 const char *op2 = (two_operands_p ? ",%z3" : ",%.");
2367 /* The operand-printing string for the comparison. */
2368 const char *comp = (float_p ? "%F0" : "%C0");
2369 /* The operand-printing string for the inverted comparison. */
2370 const char *inverted_comp = (float_p ? "%W0" : "%N0");
2372 /* Likely variants of each branch instruction annul the instruction
2373 in the delay slot if the branch is not taken. */
2374 iq2000_branch_likely = (final_sequence && INSN_ANNULLED_BRANCH_P (insn));
2376 if (!two_operands_p)
2378 /* To compute whether than A > B, for example, we normally
2379 subtract B from A and then look at the sign bit. But, if we
2380 are doing an unsigned comparison, and B is zero, we don't
2381 have to do the subtraction. Instead, we can just check to
2382 see if A is nonzero. Thus, we change the CODE here to
2383 reflect the simpler comparison operation. */
2384 switch (code)
2386 case GTU:
2387 code = NE;
2388 break;
2390 case LEU:
2391 code = EQ;
2392 break;
2394 case GEU:
2395 /* A condition which will always be true. */
2396 code = EQ;
2397 op1 = "%.";
2398 break;
2400 case LTU:
2401 /* A condition which will always be false. */
2402 code = NE;
2403 op1 = "%.";
2404 break;
2406 default:
2407 /* Not a special case. */
2408 break;
2412 /* Relative comparisons are always done against zero. But
2413 equality comparisons are done between two operands, and therefore
2414 do not require a `z' in the assembly language output. */
2415 need_z_p = (!float_p && code != EQ && code != NE);
2416 /* For comparisons against zero, the zero is not provided
2417 explicitly. */
2418 if (need_z_p)
2419 op2 = "";
2421 /* Begin by terminating the buffer. That way we can always use
2422 strcat to add to it. */
2423 buffer[0] = '\0';
2425 switch (length)
2427 case 4:
2428 case 8:
2429 /* Just a simple conditional branch. */
2430 if (float_p)
2431 sprintf (buffer, "b%s%%?\t%%Z2%%1",
2432 inverted_p ? inverted_comp : comp);
2433 else
2434 sprintf (buffer, "b%s%s%%?\t%s%s,%%1",
2435 inverted_p ? inverted_comp : comp,
2436 need_z_p ? "z" : "",
2437 op1,
2438 op2);
2439 return buffer;
2441 case 12:
2442 case 16:
2444 /* Generate a reversed conditional branch around ` j'
2445 instruction:
2447 .set noreorder
2448 .set nomacro
2449 bc l
2451 j target
2452 .set macro
2453 .set reorder
2456 Because we have to jump four bytes *past* the following
2457 instruction if this branch was annulled, we can't just use
2458 a label, as in the picture above; there's no way to put the
2459 label after the next instruction, as the assembler does not
2460 accept `.L+4' as the target of a branch. (We can't just
2461 wait until the next instruction is output; it might be a
2462 macro and take up more than four bytes. Once again, we see
2463 why we want to eliminate macros.)
2465 If the branch is annulled, we jump four more bytes that we
2466 would otherwise; that way we skip the annulled instruction
2467 in the delay slot. */
2469 const char *target
2470 = ((iq2000_branch_likely || length == 16) ? ".+16" : ".+12");
2471 char *c;
2473 c = strchr (buffer, '\0');
2474 /* Generate the reversed comparison. This takes four
2475 bytes. */
2476 if (float_p)
2477 sprintf (c, "b%s\t%%Z2%s",
2478 inverted_p ? comp : inverted_comp,
2479 target);
2480 else
2481 sprintf (c, "b%s%s\t%s%s,%s",
2482 inverted_p ? comp : inverted_comp,
2483 need_z_p ? "z" : "",
2484 op1,
2485 op2,
2486 target);
2487 strcat (c, "\n\tnop\n\tj\t%1");
2488 if (length == 16)
2489 /* The delay slot was unfilled. Since we're inside
2490 .noreorder, the assembler will not fill in the NOP for
2491 us, so we must do it ourselves. */
2492 strcat (buffer, "\n\tnop");
2493 return buffer;
2496 default:
2497 gcc_unreachable ();
2500 /* NOTREACHED */
2501 return 0;
2504 #define def_builtin(NAME, TYPE, CODE) \
2505 add_builtin_function ((NAME), (TYPE), (CODE), BUILT_IN_MD, \
2506 NULL, NULL_TREE)
2508 static void
2509 iq2000_init_builtins (void)
2511 tree void_ftype, void_ftype_int, void_ftype_int_int;
2512 tree void_ftype_int_int_int;
2513 tree int_ftype_int, int_ftype_int_int, int_ftype_int_int_int;
2514 tree int_ftype_int_int_int_int;
2516 /* func () */
2517 void_ftype
2518 = build_function_type_list (void_type_node, NULL_TREE);
2520 /* func (int) */
2521 void_ftype_int
2522 = build_function_type_list (void_type_node, integer_type_node, NULL_TREE);
2524 /* void func (int, int) */
2525 void_ftype_int_int
2526 = build_function_type_list (void_type_node,
2527 integer_type_node,
2528 integer_type_node,
2529 NULL_TREE);
2531 /* int func (int) */
2532 int_ftype_int
2533 = build_function_type_list (integer_type_node,
2534 integer_type_node, NULL_TREE);
2536 /* int func (int, int) */
2537 int_ftype_int_int
2538 = build_function_type_list (integer_type_node,
2539 integer_type_node,
2540 integer_type_node,
2541 NULL_TREE);
2543 /* void func (int, int, int) */
2544 void_ftype_int_int_int
2545 = build_function_type_list (void_type_node,
2546 integer_type_node,
2547 integer_type_node,
2548 integer_type_node,
2549 NULL_TREE);
2551 /* int func (int, int, int) */
2552 int_ftype_int_int_int
2553 = build_function_type_list (integer_type_node,
2554 integer_type_node,
2555 integer_type_node,
2556 integer_type_node,
2557 NULL_TREE);
2559 /* int func (int, int, int, int) */
2560 int_ftype_int_int_int_int
2561 = build_function_type_list (integer_type_node,
2562 integer_type_node,
2563 integer_type_node,
2564 integer_type_node,
2565 integer_type_node,
2566 NULL_TREE);
2568 def_builtin ("__builtin_ado16", int_ftype_int_int, IQ2000_BUILTIN_ADO16);
2569 def_builtin ("__builtin_ram", int_ftype_int_int_int_int, IQ2000_BUILTIN_RAM);
2570 def_builtin ("__builtin_chkhdr", void_ftype_int_int, IQ2000_BUILTIN_CHKHDR);
2571 def_builtin ("__builtin_pkrl", void_ftype_int_int, IQ2000_BUILTIN_PKRL);
2572 def_builtin ("__builtin_cfc0", int_ftype_int, IQ2000_BUILTIN_CFC0);
2573 def_builtin ("__builtin_cfc1", int_ftype_int, IQ2000_BUILTIN_CFC1);
2574 def_builtin ("__builtin_cfc2", int_ftype_int, IQ2000_BUILTIN_CFC2);
2575 def_builtin ("__builtin_cfc3", int_ftype_int, IQ2000_BUILTIN_CFC3);
2576 def_builtin ("__builtin_ctc0", void_ftype_int_int, IQ2000_BUILTIN_CTC0);
2577 def_builtin ("__builtin_ctc1", void_ftype_int_int, IQ2000_BUILTIN_CTC1);
2578 def_builtin ("__builtin_ctc2", void_ftype_int_int, IQ2000_BUILTIN_CTC2);
2579 def_builtin ("__builtin_ctc3", void_ftype_int_int, IQ2000_BUILTIN_CTC3);
2580 def_builtin ("__builtin_mfc0", int_ftype_int, IQ2000_BUILTIN_MFC0);
2581 def_builtin ("__builtin_mfc1", int_ftype_int, IQ2000_BUILTIN_MFC1);
2582 def_builtin ("__builtin_mfc2", int_ftype_int, IQ2000_BUILTIN_MFC2);
2583 def_builtin ("__builtin_mfc3", int_ftype_int, IQ2000_BUILTIN_MFC3);
2584 def_builtin ("__builtin_mtc0", void_ftype_int_int, IQ2000_BUILTIN_MTC0);
2585 def_builtin ("__builtin_mtc1", void_ftype_int_int, IQ2000_BUILTIN_MTC1);
2586 def_builtin ("__builtin_mtc2", void_ftype_int_int, IQ2000_BUILTIN_MTC2);
2587 def_builtin ("__builtin_mtc3", void_ftype_int_int, IQ2000_BUILTIN_MTC3);
2588 def_builtin ("__builtin_lur", void_ftype_int_int, IQ2000_BUILTIN_LUR);
2589 def_builtin ("__builtin_rb", void_ftype_int_int, IQ2000_BUILTIN_RB);
2590 def_builtin ("__builtin_rx", void_ftype_int_int, IQ2000_BUILTIN_RX);
2591 def_builtin ("__builtin_srrd", void_ftype_int, IQ2000_BUILTIN_SRRD);
2592 def_builtin ("__builtin_srwr", void_ftype_int_int, IQ2000_BUILTIN_SRWR);
2593 def_builtin ("__builtin_wb", void_ftype_int_int, IQ2000_BUILTIN_WB);
2594 def_builtin ("__builtin_wx", void_ftype_int_int, IQ2000_BUILTIN_WX);
2595 def_builtin ("__builtin_luc32l", void_ftype_int_int, IQ2000_BUILTIN_LUC32L);
2596 def_builtin ("__builtin_luc64", void_ftype_int_int, IQ2000_BUILTIN_LUC64);
2597 def_builtin ("__builtin_luc64l", void_ftype_int_int, IQ2000_BUILTIN_LUC64L);
2598 def_builtin ("__builtin_luk", void_ftype_int_int, IQ2000_BUILTIN_LUK);
2599 def_builtin ("__builtin_lulck", void_ftype_int, IQ2000_BUILTIN_LULCK);
2600 def_builtin ("__builtin_lum32", void_ftype_int_int, IQ2000_BUILTIN_LUM32);
2601 def_builtin ("__builtin_lum32l", void_ftype_int_int, IQ2000_BUILTIN_LUM32L);
2602 def_builtin ("__builtin_lum64", void_ftype_int_int, IQ2000_BUILTIN_LUM64);
2603 def_builtin ("__builtin_lum64l", void_ftype_int_int, IQ2000_BUILTIN_LUM64L);
2604 def_builtin ("__builtin_lurl", void_ftype_int_int, IQ2000_BUILTIN_LURL);
2605 def_builtin ("__builtin_mrgb", int_ftype_int_int_int, IQ2000_BUILTIN_MRGB);
2606 def_builtin ("__builtin_srrdl", void_ftype_int, IQ2000_BUILTIN_SRRDL);
2607 def_builtin ("__builtin_srulck", void_ftype_int, IQ2000_BUILTIN_SRULCK);
2608 def_builtin ("__builtin_srwru", void_ftype_int_int, IQ2000_BUILTIN_SRWRU);
2609 def_builtin ("__builtin_trapqfl", void_ftype, IQ2000_BUILTIN_TRAPQFL);
2610 def_builtin ("__builtin_trapqne", void_ftype, IQ2000_BUILTIN_TRAPQNE);
2611 def_builtin ("__builtin_traprel", void_ftype_int, IQ2000_BUILTIN_TRAPREL);
2612 def_builtin ("__builtin_wbu", void_ftype_int_int_int, IQ2000_BUILTIN_WBU);
2613 def_builtin ("__builtin_syscall", void_ftype, IQ2000_BUILTIN_SYSCALL);
2616 /* Builtin for ICODE having ARGCOUNT args in EXP where each arg
2617 has an rtx CODE. */
2619 static rtx
2620 expand_one_builtin (enum insn_code icode, rtx target, tree exp,
2621 enum rtx_code *code, int argcount)
2623 rtx pat;
2624 tree arg [5];
2625 rtx op [5];
2626 machine_mode mode [5];
2627 int i;
2629 mode[0] = insn_data[icode].operand[0].mode;
2630 for (i = 0; i < argcount; i++)
2632 arg[i] = CALL_EXPR_ARG (exp, i);
2633 op[i] = expand_normal (arg[i]);
2634 mode[i] = insn_data[icode].operand[i].mode;
2635 if (code[i] == CONST_INT && GET_CODE (op[i]) != CONST_INT)
2636 error ("argument %qd is not a constant", i + 1);
2637 if (code[i] == REG
2638 && ! (*insn_data[icode].operand[i].predicate) (op[i], mode[i]))
2639 op[i] = copy_to_mode_reg (mode[i], op[i]);
2642 if (insn_data[icode].operand[0].constraint[0] == '=')
2644 if (target == 0
2645 || GET_MODE (target) != mode[0]
2646 || ! (*insn_data[icode].operand[0].predicate) (target, mode[0]))
2647 target = gen_reg_rtx (mode[0]);
2649 else
2650 target = 0;
2652 switch (argcount)
2654 case 0:
2655 pat = GEN_FCN (icode) (target);
2656 break;
2657 case 1:
2658 if (target)
2659 pat = GEN_FCN (icode) (target, op[0]);
2660 else
2661 pat = GEN_FCN (icode) (op[0]);
2662 break;
2663 case 2:
2664 if (target)
2665 pat = GEN_FCN (icode) (target, op[0], op[1]);
2666 else
2667 pat = GEN_FCN (icode) (op[0], op[1]);
2668 break;
2669 case 3:
2670 if (target)
2671 pat = GEN_FCN (icode) (target, op[0], op[1], op[2]);
2672 else
2673 pat = GEN_FCN (icode) (op[0], op[1], op[2]);
2674 break;
2675 case 4:
2676 if (target)
2677 pat = GEN_FCN (icode) (target, op[0], op[1], op[2], op[3]);
2678 else
2679 pat = GEN_FCN (icode) (op[0], op[1], op[2], op[3]);
2680 break;
2681 default:
2682 gcc_unreachable ();
2685 if (! pat)
2686 return 0;
2687 emit_insn (pat);
2688 return target;
2691 /* Expand an expression EXP that calls a built-in function,
2692 with result going to TARGET if that's convenient
2693 (and in mode MODE if that's convenient).
2694 SUBTARGET may be used as the target for computing one of EXP's operands.
2695 IGNORE is nonzero if the value is to be ignored. */
2697 static rtx
2698 iq2000_expand_builtin (tree exp, rtx target, rtx subtarget ATTRIBUTE_UNUSED,
2699 machine_mode mode ATTRIBUTE_UNUSED,
2700 int ignore ATTRIBUTE_UNUSED)
2702 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
2703 int fcode = DECL_FUNCTION_CODE (fndecl);
2704 enum rtx_code code [5];
2706 code[0] = REG;
2707 code[1] = REG;
2708 code[2] = REG;
2709 code[3] = REG;
2710 code[4] = REG;
2711 switch (fcode)
2713 default:
2714 break;
2716 case IQ2000_BUILTIN_ADO16:
2717 return expand_one_builtin (CODE_FOR_ado16, target, exp, code, 2);
2719 case IQ2000_BUILTIN_RAM:
2720 code[1] = CONST_INT;
2721 code[2] = CONST_INT;
2722 code[3] = CONST_INT;
2723 return expand_one_builtin (CODE_FOR_ram, target, exp, code, 4);
2725 case IQ2000_BUILTIN_CHKHDR:
2726 return expand_one_builtin (CODE_FOR_chkhdr, target, exp, code, 2);
2728 case IQ2000_BUILTIN_PKRL:
2729 return expand_one_builtin (CODE_FOR_pkrl, target, exp, code, 2);
2731 case IQ2000_BUILTIN_CFC0:
2732 code[0] = CONST_INT;
2733 return expand_one_builtin (CODE_FOR_cfc0, target, exp, code, 1);
2735 case IQ2000_BUILTIN_CFC1:
2736 code[0] = CONST_INT;
2737 return expand_one_builtin (CODE_FOR_cfc1, target, exp, code, 1);
2739 case IQ2000_BUILTIN_CFC2:
2740 code[0] = CONST_INT;
2741 return expand_one_builtin (CODE_FOR_cfc2, target, exp, code, 1);
2743 case IQ2000_BUILTIN_CFC3:
2744 code[0] = CONST_INT;
2745 return expand_one_builtin (CODE_FOR_cfc3, target, exp, code, 1);
2747 case IQ2000_BUILTIN_CTC0:
2748 code[1] = CONST_INT;
2749 return expand_one_builtin (CODE_FOR_ctc0, target, exp, code, 2);
2751 case IQ2000_BUILTIN_CTC1:
2752 code[1] = CONST_INT;
2753 return expand_one_builtin (CODE_FOR_ctc1, target, exp, code, 2);
2755 case IQ2000_BUILTIN_CTC2:
2756 code[1] = CONST_INT;
2757 return expand_one_builtin (CODE_FOR_ctc2, target, exp, code, 2);
2759 case IQ2000_BUILTIN_CTC3:
2760 code[1] = CONST_INT;
2761 return expand_one_builtin (CODE_FOR_ctc3, target, exp, code, 2);
2763 case IQ2000_BUILTIN_MFC0:
2764 code[0] = CONST_INT;
2765 return expand_one_builtin (CODE_FOR_mfc0, target, exp, code, 1);
2767 case IQ2000_BUILTIN_MFC1:
2768 code[0] = CONST_INT;
2769 return expand_one_builtin (CODE_FOR_mfc1, target, exp, code, 1);
2771 case IQ2000_BUILTIN_MFC2:
2772 code[0] = CONST_INT;
2773 return expand_one_builtin (CODE_FOR_mfc2, target, exp, code, 1);
2775 case IQ2000_BUILTIN_MFC3:
2776 code[0] = CONST_INT;
2777 return expand_one_builtin (CODE_FOR_mfc3, target, exp, code, 1);
2779 case IQ2000_BUILTIN_MTC0:
2780 code[1] = CONST_INT;
2781 return expand_one_builtin (CODE_FOR_mtc0, target, exp, code, 2);
2783 case IQ2000_BUILTIN_MTC1:
2784 code[1] = CONST_INT;
2785 return expand_one_builtin (CODE_FOR_mtc1, target, exp, code, 2);
2787 case IQ2000_BUILTIN_MTC2:
2788 code[1] = CONST_INT;
2789 return expand_one_builtin (CODE_FOR_mtc2, target, exp, code, 2);
2791 case IQ2000_BUILTIN_MTC3:
2792 code[1] = CONST_INT;
2793 return expand_one_builtin (CODE_FOR_mtc3, target, exp, code, 2);
2795 case IQ2000_BUILTIN_LUR:
2796 return expand_one_builtin (CODE_FOR_lur, target, exp, code, 2);
2798 case IQ2000_BUILTIN_RB:
2799 return expand_one_builtin (CODE_FOR_rb, target, exp, code, 2);
2801 case IQ2000_BUILTIN_RX:
2802 return expand_one_builtin (CODE_FOR_rx, target, exp, code, 2);
2804 case IQ2000_BUILTIN_SRRD:
2805 return expand_one_builtin (CODE_FOR_srrd, target, exp, code, 1);
2807 case IQ2000_BUILTIN_SRWR:
2808 return expand_one_builtin (CODE_FOR_srwr, target, exp, code, 2);
2810 case IQ2000_BUILTIN_WB:
2811 return expand_one_builtin (CODE_FOR_wb, target, exp, code, 2);
2813 case IQ2000_BUILTIN_WX:
2814 return expand_one_builtin (CODE_FOR_wx, target, exp, code, 2);
2816 case IQ2000_BUILTIN_LUC32L:
2817 return expand_one_builtin (CODE_FOR_luc32l, target, exp, code, 2);
2819 case IQ2000_BUILTIN_LUC64:
2820 return expand_one_builtin (CODE_FOR_luc64, target, exp, code, 2);
2822 case IQ2000_BUILTIN_LUC64L:
2823 return expand_one_builtin (CODE_FOR_luc64l, target, exp, code, 2);
2825 case IQ2000_BUILTIN_LUK:
2826 return expand_one_builtin (CODE_FOR_luk, target, exp, code, 2);
2828 case IQ2000_BUILTIN_LULCK:
2829 return expand_one_builtin (CODE_FOR_lulck, target, exp, code, 1);
2831 case IQ2000_BUILTIN_LUM32:
2832 return expand_one_builtin (CODE_FOR_lum32, target, exp, code, 2);
2834 case IQ2000_BUILTIN_LUM32L:
2835 return expand_one_builtin (CODE_FOR_lum32l, target, exp, code, 2);
2837 case IQ2000_BUILTIN_LUM64:
2838 return expand_one_builtin (CODE_FOR_lum64, target, exp, code, 2);
2840 case IQ2000_BUILTIN_LUM64L:
2841 return expand_one_builtin (CODE_FOR_lum64l, target, exp, code, 2);
2843 case IQ2000_BUILTIN_LURL:
2844 return expand_one_builtin (CODE_FOR_lurl, target, exp, code, 2);
2846 case IQ2000_BUILTIN_MRGB:
2847 code[2] = CONST_INT;
2848 return expand_one_builtin (CODE_FOR_mrgb, target, exp, code, 3);
2850 case IQ2000_BUILTIN_SRRDL:
2851 return expand_one_builtin (CODE_FOR_srrdl, target, exp, code, 1);
2853 case IQ2000_BUILTIN_SRULCK:
2854 return expand_one_builtin (CODE_FOR_srulck, target, exp, code, 1);
2856 case IQ2000_BUILTIN_SRWRU:
2857 return expand_one_builtin (CODE_FOR_srwru, target, exp, code, 2);
2859 case IQ2000_BUILTIN_TRAPQFL:
2860 return expand_one_builtin (CODE_FOR_trapqfl, target, exp, code, 0);
2862 case IQ2000_BUILTIN_TRAPQNE:
2863 return expand_one_builtin (CODE_FOR_trapqne, target, exp, code, 0);
2865 case IQ2000_BUILTIN_TRAPREL:
2866 return expand_one_builtin (CODE_FOR_traprel, target, exp, code, 1);
2868 case IQ2000_BUILTIN_WBU:
2869 return expand_one_builtin (CODE_FOR_wbu, target, exp, code, 3);
2871 case IQ2000_BUILTIN_SYSCALL:
2872 return expand_one_builtin (CODE_FOR_syscall, target, exp, code, 0);
2875 return NULL_RTX;
2878 /* Worker function for TARGET_RETURN_IN_MEMORY. */
2880 static bool
2881 iq2000_return_in_memory (const_tree type, const_tree fntype ATTRIBUTE_UNUSED)
2883 return ((int_size_in_bytes (type) > (2 * UNITS_PER_WORD))
2884 || (int_size_in_bytes (type) == -1));
2887 /* Worker function for TARGET_SETUP_INCOMING_VARARGS. */
2889 static void
2890 iq2000_setup_incoming_varargs (cumulative_args_t cum_v,
2891 machine_mode mode ATTRIBUTE_UNUSED,
2892 tree type ATTRIBUTE_UNUSED, int * pretend_size,
2893 int no_rtl)
2895 CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
2896 unsigned int iq2000_off = ! cum->last_arg_fp;
2897 unsigned int iq2000_fp_off = cum->last_arg_fp;
2899 if ((cum->arg_words < MAX_ARGS_IN_REGISTERS - iq2000_off))
2901 int iq2000_save_gp_regs
2902 = MAX_ARGS_IN_REGISTERS - cum->arg_words - iq2000_off;
2903 int iq2000_save_fp_regs
2904 = (MAX_ARGS_IN_REGISTERS - cum->fp_arg_words - iq2000_fp_off);
2906 if (iq2000_save_gp_regs < 0)
2907 iq2000_save_gp_regs = 0;
2908 if (iq2000_save_fp_regs < 0)
2909 iq2000_save_fp_regs = 0;
2911 *pretend_size = ((iq2000_save_gp_regs * UNITS_PER_WORD)
2912 + (iq2000_save_fp_regs * UNITS_PER_FPREG));
2914 if (! (no_rtl))
2916 if (cum->arg_words < MAX_ARGS_IN_REGISTERS - iq2000_off)
2918 rtx ptr, mem;
2919 ptr = plus_constant (Pmode, virtual_incoming_args_rtx,
2920 - (iq2000_save_gp_regs
2921 * UNITS_PER_WORD));
2922 mem = gen_rtx_MEM (BLKmode, ptr);
2923 move_block_from_reg
2924 (cum->arg_words + GP_ARG_FIRST + iq2000_off,
2925 mem,
2926 iq2000_save_gp_regs);
2932 /* A C compound statement to output to stdio stream STREAM the
2933 assembler syntax for an instruction operand that is a memory
2934 reference whose address is ADDR. ADDR is an RTL expression. */
2936 static void
2937 iq2000_print_operand_address (FILE * file, machine_mode mode, rtx addr)
2939 if (!addr)
2940 error ("PRINT_OPERAND_ADDRESS, null pointer");
2942 else
2943 switch (GET_CODE (addr))
2945 case REG:
2946 if (REGNO (addr) == ARG_POINTER_REGNUM)
2947 abort_with_insn (addr, "Arg pointer not eliminated.");
2949 fprintf (file, "0(%s)", reg_names [REGNO (addr)]);
2950 break;
2952 case LO_SUM:
2954 rtx arg0 = XEXP (addr, 0);
2955 rtx arg1 = XEXP (addr, 1);
2957 if (GET_CODE (arg0) != REG)
2958 abort_with_insn (addr,
2959 "PRINT_OPERAND_ADDRESS, LO_SUM with #1 not REG.");
2961 fprintf (file, "%%lo(");
2962 iq2000_print_operand_address (file, mode, arg1);
2963 fprintf (file, ")(%s)", reg_names [REGNO (arg0)]);
2965 break;
2967 case PLUS:
2969 rtx reg = 0;
2970 rtx offset = 0;
2971 rtx arg0 = XEXP (addr, 0);
2972 rtx arg1 = XEXP (addr, 1);
2974 if (GET_CODE (arg0) == REG)
2976 reg = arg0;
2977 offset = arg1;
2978 if (GET_CODE (offset) == REG)
2979 abort_with_insn (addr, "PRINT_OPERAND_ADDRESS, 2 regs");
2982 else if (GET_CODE (arg1) == REG)
2983 reg = arg1, offset = arg0;
2984 else if (CONSTANT_P (arg0) && CONSTANT_P (arg1))
2986 output_addr_const (file, addr);
2987 break;
2989 else
2990 abort_with_insn (addr, "PRINT_OPERAND_ADDRESS, no regs");
2992 if (! CONSTANT_P (offset))
2993 abort_with_insn (addr, "PRINT_OPERAND_ADDRESS, invalid insn #2");
2995 if (REGNO (reg) == ARG_POINTER_REGNUM)
2996 abort_with_insn (addr, "Arg pointer not eliminated.");
2998 output_addr_const (file, offset);
2999 fprintf (file, "(%s)", reg_names [REGNO (reg)]);
3001 break;
3003 case LABEL_REF:
3004 case SYMBOL_REF:
3005 case CONST_INT:
3006 case CONST:
3007 output_addr_const (file, addr);
3008 if (GET_CODE (addr) == CONST_INT)
3009 fprintf (file, "(%s)", reg_names [0]);
3010 break;
3012 default:
3013 abort_with_insn (addr, "PRINT_OPERAND_ADDRESS, invalid insn #1");
3014 break;
3018 /* A C compound statement to output to stdio stream FILE the
3019 assembler syntax for an instruction operand OP.
3021 LETTER is a value that can be used to specify one of several ways
3022 of printing the operand. It is used when identical operands
3023 must be printed differently depending on the context. LETTER
3024 comes from the `%' specification that was used to request
3025 printing of the operand. If the specification was just `%DIGIT'
3026 then LETTER is 0; if the specification was `%LTR DIGIT' then LETTER
3027 is the ASCII code for LTR.
3029 If OP is a register, this macro should print the register's name.
3030 The names can be found in an array `reg_names' whose type is
3031 `char *[]'. `reg_names' is initialized from `REGISTER_NAMES'.
3033 When the machine description has a specification `%PUNCT' (a `%'
3034 followed by a punctuation character), this macro is called with
3035 a null pointer for X and the punctuation character for LETTER.
3037 The IQ2000 specific codes are:
3039 'X' X is CONST_INT, prints upper 16 bits in hexadecimal format = "0x%04x",
3040 'x' X is CONST_INT, prints lower 16 bits in hexadecimal format = "0x%04x",
3041 'd' output integer constant in decimal,
3042 'z' if the operand is 0, use $0 instead of normal operand.
3043 'D' print second part of double-word register or memory operand.
3044 'L' print low-order register of double-word register operand.
3045 'M' print high-order register of double-word register operand.
3046 'C' print part of opcode for a branch condition.
3047 'F' print part of opcode for a floating-point branch condition.
3048 'N' print part of opcode for a branch condition, inverted.
3049 'W' print part of opcode for a floating-point branch condition, inverted.
3050 'A' Print part of opcode for a bit test condition.
3051 'P' Print label for a bit test.
3052 'p' Print log for a bit test.
3053 'B' print 'z' for EQ, 'n' for NE
3054 'b' print 'n' for EQ, 'z' for NE
3055 'T' print 'f' for EQ, 't' for NE
3056 't' print 't' for EQ, 'f' for NE
3057 'Z' print register and a comma, but print nothing for $fcc0
3058 '?' Print 'l' if we are to use a branch likely instead of normal branch.
3059 '@' Print the name of the assembler temporary register (at or $1).
3060 '.' Print the name of the register with a hard-wired zero (zero or $0).
3061 '$' Print the name of the stack pointer register (sp or $29).
3062 '+' Print the name of the gp register (gp or $28). */
3064 static void
3065 iq2000_print_operand (FILE *file, rtx op, int letter)
3067 enum rtx_code code;
3069 if (iq2000_print_operand_punct_valid_p (letter))
3071 switch (letter)
3073 case '?':
3074 if (iq2000_branch_likely)
3075 putc ('l', file);
3076 break;
3078 case '@':
3079 fputs (reg_names [GP_REG_FIRST + 1], file);
3080 break;
3082 case '.':
3083 fputs (reg_names [GP_REG_FIRST + 0], file);
3084 break;
3086 case '$':
3087 fputs (reg_names[STACK_POINTER_REGNUM], file);
3088 break;
3090 case '+':
3091 fputs (reg_names[GP_REG_FIRST + 28], file);
3092 break;
3094 default:
3095 error ("PRINT_OPERAND: Unknown punctuation '%c'", letter);
3096 break;
3099 return;
3102 if (! op)
3104 error ("PRINT_OPERAND null pointer");
3105 return;
3108 code = GET_CODE (op);
3110 if (code == SIGN_EXTEND)
3111 op = XEXP (op, 0), code = GET_CODE (op);
3113 if (letter == 'C')
3114 switch (code)
3116 case EQ: fputs ("eq", file); break;
3117 case NE: fputs ("ne", file); break;
3118 case GT: fputs ("gt", file); break;
3119 case GE: fputs ("ge", file); break;
3120 case LT: fputs ("lt", file); break;
3121 case LE: fputs ("le", file); break;
3122 case GTU: fputs ("ne", file); break;
3123 case GEU: fputs ("geu", file); break;
3124 case LTU: fputs ("ltu", file); break;
3125 case LEU: fputs ("eq", file); break;
3126 default:
3127 abort_with_insn (op, "PRINT_OPERAND, invalid insn for %%C");
3130 else if (letter == 'N')
3131 switch (code)
3133 case EQ: fputs ("ne", file); break;
3134 case NE: fputs ("eq", file); break;
3135 case GT: fputs ("le", file); break;
3136 case GE: fputs ("lt", file); break;
3137 case LT: fputs ("ge", file); break;
3138 case LE: fputs ("gt", file); break;
3139 case GTU: fputs ("leu", file); break;
3140 case GEU: fputs ("ltu", file); break;
3141 case LTU: fputs ("geu", file); break;
3142 case LEU: fputs ("gtu", file); break;
3143 default:
3144 abort_with_insn (op, "PRINT_OPERAND, invalid insn for %%N");
3147 else if (letter == 'F')
3148 switch (code)
3150 case EQ: fputs ("c1f", file); break;
3151 case NE: fputs ("c1t", file); break;
3152 default:
3153 abort_with_insn (op, "PRINT_OPERAND, invalid insn for %%F");
3156 else if (letter == 'W')
3157 switch (code)
3159 case EQ: fputs ("c1t", file); break;
3160 case NE: fputs ("c1f", file); break;
3161 default:
3162 abort_with_insn (op, "PRINT_OPERAND, invalid insn for %%W");
3165 else if (letter == 'A')
3166 fputs (code == LABEL_REF ? "i" : "in", file);
3168 else if (letter == 'P')
3170 if (code == LABEL_REF)
3171 output_addr_const (file, op);
3172 else if (code != PC)
3173 output_operand_lossage ("invalid %%P operand");
3176 else if (letter == 'p')
3178 int value;
3179 if (code != CONST_INT
3180 || (value = exact_log2 (INTVAL (op))) < 0)
3181 output_operand_lossage ("invalid %%p value");
3182 else
3183 fprintf (file, "%d", value);
3186 else if (letter == 'Z')
3188 gcc_unreachable ();
3191 else if (code == REG || code == SUBREG)
3193 int regnum;
3195 if (code == REG)
3196 regnum = REGNO (op);
3197 else
3198 regnum = true_regnum (op);
3200 if ((letter == 'M' && ! WORDS_BIG_ENDIAN)
3201 || (letter == 'L' && WORDS_BIG_ENDIAN)
3202 || letter == 'D')
3203 regnum++;
3205 fprintf (file, "%s", reg_names[regnum]);
3208 else if (code == MEM)
3210 machine_mode mode = GET_MODE (op);
3212 if (letter == 'D')
3213 output_address (mode, plus_constant (Pmode, XEXP (op, 0), 4));
3214 else
3215 output_address (mode, XEXP (op, 0));
3218 else if (code == CONST_DOUBLE
3219 && GET_MODE_CLASS (GET_MODE (op)) == MODE_FLOAT)
3221 char s[60];
3223 real_to_decimal (s, CONST_DOUBLE_REAL_VALUE (op), sizeof (s), 0, 1);
3224 fputs (s, file);
3227 else if (letter == 'x' && GET_CODE (op) == CONST_INT)
3228 fprintf (file, HOST_WIDE_INT_PRINT_HEX, 0xffff & INTVAL(op));
3230 else if (letter == 'X' && GET_CODE(op) == CONST_INT)
3231 fprintf (file, HOST_WIDE_INT_PRINT_HEX, 0xffff & (INTVAL (op) >> 16));
3233 else if (letter == 'd' && GET_CODE(op) == CONST_INT)
3234 fprintf (file, HOST_WIDE_INT_PRINT_DEC, (INTVAL(op)));
3236 else if (letter == 'z' && GET_CODE (op) == CONST_INT && INTVAL (op) == 0)
3237 fputs (reg_names[GP_REG_FIRST], file);
3239 else if (letter == 'd' || letter == 'x' || letter == 'X')
3240 output_operand_lossage ("invalid use of %%d, %%x, or %%X");
3242 else if (letter == 'B')
3243 fputs (code == EQ ? "z" : "n", file);
3244 else if (letter == 'b')
3245 fputs (code == EQ ? "n" : "z", file);
3246 else if (letter == 'T')
3247 fputs (code == EQ ? "f" : "t", file);
3248 else if (letter == 't')
3249 fputs (code == EQ ? "t" : "f", file);
3251 else if (code == CONST && GET_CODE (XEXP (op, 0)) == REG)
3253 iq2000_print_operand (file, XEXP (op, 0), letter);
3256 else
3257 output_addr_const (file, op);
3260 static bool
3261 iq2000_print_operand_punct_valid_p (unsigned char code)
3263 return iq2000_print_operand_punct[code];
3266 /* For the IQ2000, transform:
3268 memory(X + <large int>)
3269 into:
3270 Y = <large int> & ~0x7fff;
3271 Z = X + Y
3272 memory (Z + (<large int> & 0x7fff));
3276 iq2000_legitimize_address (rtx xinsn, rtx old_x ATTRIBUTE_UNUSED,
3277 machine_mode mode)
3279 if (TARGET_DEBUG_B_MODE)
3281 GO_PRINTF ("\n========== LEGITIMIZE_ADDRESS\n");
3282 GO_DEBUG_RTX (xinsn);
3285 if (iq2000_check_split (xinsn, mode))
3287 return gen_rtx_LO_SUM (Pmode,
3288 copy_to_mode_reg (Pmode,
3289 gen_rtx_HIGH (Pmode, xinsn)),
3290 xinsn);
3293 if (GET_CODE (xinsn) == PLUS)
3295 rtx xplus0 = XEXP (xinsn, 0);
3296 rtx xplus1 = XEXP (xinsn, 1);
3297 enum rtx_code code0 = GET_CODE (xplus0);
3298 enum rtx_code code1 = GET_CODE (xplus1);
3300 if (code0 != REG && code1 == REG)
3302 xplus0 = XEXP (xinsn, 1);
3303 xplus1 = XEXP (xinsn, 0);
3304 code0 = GET_CODE (xplus0);
3305 code1 = GET_CODE (xplus1);
3308 if (code0 == REG && REG_MODE_OK_FOR_BASE_P (xplus0, mode)
3309 && code1 == CONST_INT && !SMALL_INT (xplus1))
3311 rtx int_reg = gen_reg_rtx (Pmode);
3312 rtx ptr_reg = gen_reg_rtx (Pmode);
3314 emit_move_insn (int_reg,
3315 GEN_INT (INTVAL (xplus1) & ~ 0x7fff));
3317 emit_insn (gen_rtx_SET (ptr_reg,
3318 gen_rtx_PLUS (Pmode, xplus0, int_reg)));
3320 return plus_constant (Pmode, ptr_reg, INTVAL (xplus1) & 0x7fff);
3324 if (TARGET_DEBUG_B_MODE)
3325 GO_PRINTF ("LEGITIMIZE_ADDRESS could not fix.\n");
3327 return xinsn;
3331 static bool
3332 iq2000_rtx_costs (rtx x, machine_mode mode, int outer_code ATTRIBUTE_UNUSED,
3333 int opno ATTRIBUTE_UNUSED, int * total,
3334 bool speed ATTRIBUTE_UNUSED)
3336 int code = GET_CODE (x);
3338 switch (code)
3340 case MEM:
3342 int num_words = (GET_MODE_SIZE (mode) > UNITS_PER_WORD) ? 2 : 1;
3344 if (simple_memory_operand (x, mode))
3345 return COSTS_N_INSNS (num_words) != 0;
3347 * total = COSTS_N_INSNS (2 * num_words);
3348 break;
3351 case FFS:
3352 * total = COSTS_N_INSNS (6);
3353 break;
3355 case AND:
3356 case IOR:
3357 case XOR:
3358 case NOT:
3359 * total = COSTS_N_INSNS (mode == DImode ? 2 : 1);
3360 break;
3362 case ASHIFT:
3363 case ASHIFTRT:
3364 case LSHIFTRT:
3365 if (mode == DImode)
3366 * total = COSTS_N_INSNS ((GET_CODE (XEXP (x, 1)) == CONST_INT) ? 4 : 12);
3367 else
3368 * total = COSTS_N_INSNS (1);
3369 break;
3371 case ABS:
3372 if (mode == SFmode || mode == DFmode)
3373 * total = COSTS_N_INSNS (1);
3374 else
3375 * total = COSTS_N_INSNS (4);
3376 break;
3378 case PLUS:
3379 case MINUS:
3380 if (mode == SFmode || mode == DFmode)
3381 * total = COSTS_N_INSNS (6);
3382 else if (mode == DImode)
3383 * total = COSTS_N_INSNS (4);
3384 else
3385 * total = COSTS_N_INSNS (1);
3386 break;
3388 case NEG:
3389 * total = (mode == DImode) ? 4 : 1;
3390 break;
3392 case MULT:
3393 if (mode == SFmode)
3394 * total = COSTS_N_INSNS (7);
3395 else if (mode == DFmode)
3396 * total = COSTS_N_INSNS (8);
3397 else
3398 * total = COSTS_N_INSNS (10);
3399 break;
3401 case DIV:
3402 case MOD:
3403 if (mode == SFmode)
3404 * total = COSTS_N_INSNS (23);
3405 else if (mode == DFmode)
3406 * total = COSTS_N_INSNS (36);
3407 else
3408 * total = COSTS_N_INSNS (69);
3409 break;
3411 case UDIV:
3412 case UMOD:
3413 * total = COSTS_N_INSNS (69);
3414 break;
3416 case SIGN_EXTEND:
3417 * total = COSTS_N_INSNS (2);
3418 break;
3420 case ZERO_EXTEND:
3421 * total = COSTS_N_INSNS (1);
3422 break;
3424 case CONST_INT:
3425 * total = 0;
3426 break;
3428 case LABEL_REF:
3429 * total = COSTS_N_INSNS (2);
3430 break;
3432 case CONST:
3434 rtx offset = const0_rtx;
3435 rtx symref = eliminate_constant_term (XEXP (x, 0), & offset);
3437 if (GET_CODE (symref) == LABEL_REF)
3438 * total = COSTS_N_INSNS (2);
3439 else if (GET_CODE (symref) != SYMBOL_REF)
3440 * total = COSTS_N_INSNS (4);
3441 /* Let's be paranoid.... */
3442 else if (INTVAL (offset) < -32768 || INTVAL (offset) > 32767)
3443 * total = COSTS_N_INSNS (2);
3444 else
3445 * total = COSTS_N_INSNS (SYMBOL_REF_FLAG (symref) ? 1 : 2);
3446 break;
3449 case SYMBOL_REF:
3450 * total = COSTS_N_INSNS (SYMBOL_REF_FLAG (x) ? 1 : 2);
3451 break;
3453 case CONST_DOUBLE:
3455 rtx high, low;
3457 split_double (x, & high, & low);
3459 * total = COSTS_N_INSNS ( (high == CONST0_RTX (GET_MODE (high))
3460 || low == CONST0_RTX (GET_MODE (low)))
3461 ? 2 : 4);
3462 break;
3465 default:
3466 return false;
3468 return true;
3471 /* Worker for TARGET_ASM_TRAMPOLINE_TEMPLATE. */
3473 static void
3474 iq2000_asm_trampoline_template (FILE *f)
3476 fprintf (f, "\t.word\t0x03e00821\t\t# move $1,$31\n");
3477 fprintf (f, "\t.word\t0x04110001\t\t# bgezal $0,.+8\n");
3478 fprintf (f, "\t.word\t0x00000000\t\t# nop\n");
3479 if (Pmode == DImode)
3481 fprintf (f, "\t.word\t0xdfe30014\t\t# ld $3,20($31)\n");
3482 fprintf (f, "\t.word\t0xdfe2001c\t\t# ld $2,28($31)\n");
3484 else
3486 fprintf (f, "\t.word\t0x8fe30014\t\t# lw $3,20($31)\n");
3487 fprintf (f, "\t.word\t0x8fe20018\t\t# lw $2,24($31)\n");
3489 fprintf (f, "\t.word\t0x0060c821\t\t# move $25,$3 (abicalls)\n");
3490 fprintf (f, "\t.word\t0x00600008\t\t# jr $3\n");
3491 fprintf (f, "\t.word\t0x0020f821\t\t# move $31,$1\n");
3492 fprintf (f, "\t.word\t0x00000000\t\t# <function address>\n");
3493 fprintf (f, "\t.word\t0x00000000\t\t# <static chain value>\n");
3496 /* Worker for TARGET_TRAMPOLINE_INIT. */
3498 static void
3499 iq2000_trampoline_init (rtx m_tramp, tree fndecl, rtx chain_value)
3501 rtx fnaddr = XEXP (DECL_RTL (fndecl), 0);
3502 rtx mem;
3504 emit_block_move (m_tramp, assemble_trampoline_template (),
3505 GEN_INT (TRAMPOLINE_CODE_SIZE), BLOCK_OP_NORMAL);
3507 mem = adjust_address (m_tramp, Pmode, TRAMPOLINE_CODE_SIZE);
3508 emit_move_insn (mem, fnaddr);
3509 mem = adjust_address (m_tramp, Pmode,
3510 TRAMPOLINE_CODE_SIZE + GET_MODE_SIZE (Pmode));
3511 emit_move_insn (mem, chain_value);
3514 /* Implement TARGET_HARD_REGNO_MODE_OK. */
3516 static bool
3517 iq2000_hard_regno_mode_ok (unsigned int regno, machine_mode mode)
3519 return (REGNO_REG_CLASS (regno) == GR_REGS
3520 ? (regno & 1) == 0 || GET_MODE_SIZE (mode) <= 4
3521 : (regno & 1) == 0 || GET_MODE_SIZE (mode) == 4);
3524 /* Implement TARGET_MODES_TIEABLE_P. */
3526 static bool
3527 iq2000_modes_tieable_p (machine_mode mode1, machine_mode mode2)
3529 return ((GET_MODE_CLASS (mode1) == MODE_FLOAT
3530 || GET_MODE_CLASS (mode1) == MODE_COMPLEX_FLOAT)
3531 == (GET_MODE_CLASS (mode2) == MODE_FLOAT
3532 || GET_MODE_CLASS (mode2) == MODE_COMPLEX_FLOAT));
3535 #include "gt-iq2000.h"