1 /* Subroutines used for code generation on IBM S/390 and zSeries
2 Copyright (C) 1999, 2000, 2001, 2002, 2003, 2004, 2005
3 Free Software Foundation, Inc.
4 Contributed by Hartmut Penner (hpenner@de.ibm.com) and
5 Ulrich Weigand (uweigand@de.ibm.com).
7 This file is part of GCC.
9 GCC is free software; you can redistribute it and/or modify it under
10 the terms of the GNU General Public License as published by the Free
11 Software Foundation; either version 2, or (at your option) any later
14 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
15 WARRANTY; without even the implied warranty of MERCHANTABILITY or
16 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING. If not, write to the Free
21 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
26 #include "coretypes.h"
32 #include "hard-reg-set.h"
34 #include "insn-config.h"
35 #include "conditions.h"
37 #include "insn-attr.h"
45 #include "basic-block.h"
46 #include "integrate.h"
49 #include "target-def.h"
51 #include "langhooks.h"
53 #include "tree-gimple.h"
56 static bool s390_assemble_integer (rtx, unsigned int, int);
57 static bool s390_handle_option (size_t, const char *, int);
58 static void s390_encode_section_info (tree, rtx, int);
59 static bool s390_cannot_force_const_mem (rtx);
60 static rtx s390_delegitimize_address (rtx);
61 static bool s390_return_in_memory (tree, tree);
62 static void s390_init_builtins (void);
63 static rtx s390_expand_builtin (tree, rtx, rtx, enum machine_mode, int);
64 static void s390_output_mi_thunk (FILE *, tree, HOST_WIDE_INT,
66 static enum attr_type s390_safe_attr_type (rtx);
68 static int s390_adjust_priority (rtx, int);
69 static int s390_issue_rate (void);
70 static int s390_first_cycle_multipass_dfa_lookahead (void);
71 static bool s390_cannot_copy_insn_p (rtx);
72 static bool s390_rtx_costs (rtx, int, int, int *);
73 static int s390_address_cost (rtx);
74 static void s390_reorg (void);
75 static bool s390_valid_pointer_mode (enum machine_mode);
76 static tree s390_build_builtin_va_list (void);
77 static tree s390_gimplify_va_arg (tree, tree, tree *, tree *);
78 static bool s390_function_ok_for_sibcall (tree, tree);
79 static bool s390_call_saved_register_used (tree);
80 static bool s390_pass_by_reference (CUMULATIVE_ARGS *, enum machine_mode mode,
82 static bool s390_fixed_condition_code_regs (unsigned int *, unsigned int *);
83 static enum machine_mode s390_cc_modes_compatible (enum machine_mode,
87 /* Define the specific costs for a given cpu. */
89 struct processor_costs
92 const int m; /* cost of an M instruction. */
93 const int mghi; /* cost of an MGHI instruction. */
94 const int mh; /* cost of an MH instruction. */
95 const int mhi; /* cost of an MHI instruction. */
96 const int ml; /* cost of an ML instruction. */
97 const int mr; /* cost of an MR instruction. */
98 const int ms; /* cost of an MS instruction. */
99 const int msg; /* cost of an MSG instruction. */
100 const int msgf; /* cost of an MSGF instruction. */
101 const int msgfr; /* cost of an MSGFR instruction. */
102 const int msgr; /* cost of an MSGR instruction. */
103 const int msr; /* cost of an MSR instruction. */
104 const int mult_df; /* cost of multiplication in DFmode. */
106 const int sqdbr; /* cost of square root in DFmode. */
107 const int sqebr; /* cost of square root in SFmode. */
108 /* multiply and add */
109 const int madbr; /* cost of multiply and add in DFmode. */
110 const int maebr; /* cost of multiply and add in SFmode. */
123 const struct processor_costs *s390_cost;
126 struct processor_costs z900_cost =
128 COSTS_N_INSNS (5), /* M */
129 COSTS_N_INSNS (10), /* MGHI */
130 COSTS_N_INSNS (5), /* MH */
131 COSTS_N_INSNS (4), /* MHI */
132 COSTS_N_INSNS (5), /* ML */
133 COSTS_N_INSNS (5), /* MR */
134 COSTS_N_INSNS (4), /* MS */
135 COSTS_N_INSNS (15), /* MSG */
136 COSTS_N_INSNS (7), /* MSGF */
137 COSTS_N_INSNS (7), /* MSGFR */
138 COSTS_N_INSNS (10), /* MSGR */
139 COSTS_N_INSNS (4), /* MSR */
140 COSTS_N_INSNS (7), /* multiplication in DFmode */
141 COSTS_N_INSNS (44), /* SQDBR */
142 COSTS_N_INSNS (35), /* SQEBR */
143 COSTS_N_INSNS (18), /* MADBR */
144 COSTS_N_INSNS (13), /* MAEBR */
145 COSTS_N_INSNS (30), /* DDBR */
146 COSTS_N_INSNS (30), /* DDR */
147 COSTS_N_INSNS (27), /* DEBR */
148 COSTS_N_INSNS (26), /* DER */
149 COSTS_N_INSNS (220), /* DLGR */
150 COSTS_N_INSNS (34), /* DLR */
151 COSTS_N_INSNS (34), /* DR */
152 COSTS_N_INSNS (32), /* DSGFR */
153 COSTS_N_INSNS (32), /* DSGR */
157 struct processor_costs z990_cost =
159 COSTS_N_INSNS (4), /* M */
160 COSTS_N_INSNS (2), /* MGHI */
161 COSTS_N_INSNS (2), /* MH */
162 COSTS_N_INSNS (2), /* MHI */
163 COSTS_N_INSNS (4), /* ML */
164 COSTS_N_INSNS (4), /* MR */
165 COSTS_N_INSNS (5), /* MS */
166 COSTS_N_INSNS (6), /* MSG */
167 COSTS_N_INSNS (4), /* MSGF */
168 COSTS_N_INSNS (4), /* MSGFR */
169 COSTS_N_INSNS (4), /* MSGR */
170 COSTS_N_INSNS (4), /* MSR */
171 COSTS_N_INSNS (1), /* multiplication in DFmode */
172 COSTS_N_INSNS (66), /* SQDBR */
173 COSTS_N_INSNS (38), /* SQEBR */
174 COSTS_N_INSNS (1), /* MADBR */
175 COSTS_N_INSNS (1), /* MAEBR */
176 COSTS_N_INSNS (40), /* DDBR */
177 COSTS_N_INSNS (44), /* DDR */
178 COSTS_N_INSNS (26), /* DDBR */
179 COSTS_N_INSNS (28), /* DER */
180 COSTS_N_INSNS (176), /* DLGR */
181 COSTS_N_INSNS (31), /* DLR */
182 COSTS_N_INSNS (31), /* DR */
183 COSTS_N_INSNS (31), /* DSGFR */
184 COSTS_N_INSNS (31), /* DSGR */
188 #undef TARGET_ASM_ALIGNED_HI_OP
189 #define TARGET_ASM_ALIGNED_HI_OP "\t.word\t"
190 #undef TARGET_ASM_ALIGNED_DI_OP
191 #define TARGET_ASM_ALIGNED_DI_OP "\t.quad\t"
192 #undef TARGET_ASM_INTEGER
193 #define TARGET_ASM_INTEGER s390_assemble_integer
195 #undef TARGET_ASM_OPEN_PAREN
196 #define TARGET_ASM_OPEN_PAREN ""
198 #undef TARGET_ASM_CLOSE_PAREN
199 #define TARGET_ASM_CLOSE_PAREN ""
201 #undef TARGET_DEFAULT_TARGET_FLAGS
202 #define TARGET_DEFAULT_TARGET_FLAGS (TARGET_DEFAULT | MASK_FUSED_MADD)
203 #undef TARGET_HANDLE_OPTION
204 #define TARGET_HANDLE_OPTION s390_handle_option
206 #undef TARGET_ENCODE_SECTION_INFO
207 #define TARGET_ENCODE_SECTION_INFO s390_encode_section_info
210 #undef TARGET_HAVE_TLS
211 #define TARGET_HAVE_TLS true
213 #undef TARGET_CANNOT_FORCE_CONST_MEM
214 #define TARGET_CANNOT_FORCE_CONST_MEM s390_cannot_force_const_mem
216 #undef TARGET_DELEGITIMIZE_ADDRESS
217 #define TARGET_DELEGITIMIZE_ADDRESS s390_delegitimize_address
219 #undef TARGET_RETURN_IN_MEMORY
220 #define TARGET_RETURN_IN_MEMORY s390_return_in_memory
222 #undef TARGET_INIT_BUILTINS
223 #define TARGET_INIT_BUILTINS s390_init_builtins
224 #undef TARGET_EXPAND_BUILTIN
225 #define TARGET_EXPAND_BUILTIN s390_expand_builtin
227 #undef TARGET_ASM_OUTPUT_MI_THUNK
228 #define TARGET_ASM_OUTPUT_MI_THUNK s390_output_mi_thunk
229 #undef TARGET_ASM_CAN_OUTPUT_MI_THUNK
230 #define TARGET_ASM_CAN_OUTPUT_MI_THUNK hook_bool_tree_hwi_hwi_tree_true
232 #undef TARGET_SCHED_ADJUST_PRIORITY
233 #define TARGET_SCHED_ADJUST_PRIORITY s390_adjust_priority
234 #undef TARGET_SCHED_ISSUE_RATE
235 #define TARGET_SCHED_ISSUE_RATE s390_issue_rate
236 #undef TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD
237 #define TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD s390_first_cycle_multipass_dfa_lookahead
239 #undef TARGET_CANNOT_COPY_INSN_P
240 #define TARGET_CANNOT_COPY_INSN_P s390_cannot_copy_insn_p
241 #undef TARGET_RTX_COSTS
242 #define TARGET_RTX_COSTS s390_rtx_costs
243 #undef TARGET_ADDRESS_COST
244 #define TARGET_ADDRESS_COST s390_address_cost
246 #undef TARGET_MACHINE_DEPENDENT_REORG
247 #define TARGET_MACHINE_DEPENDENT_REORG s390_reorg
249 #undef TARGET_VALID_POINTER_MODE
250 #define TARGET_VALID_POINTER_MODE s390_valid_pointer_mode
252 #undef TARGET_BUILD_BUILTIN_VA_LIST
253 #define TARGET_BUILD_BUILTIN_VA_LIST s390_build_builtin_va_list
254 #undef TARGET_GIMPLIFY_VA_ARG_EXPR
255 #define TARGET_GIMPLIFY_VA_ARG_EXPR s390_gimplify_va_arg
257 #undef TARGET_PROMOTE_FUNCTION_ARGS
258 #define TARGET_PROMOTE_FUNCTION_ARGS hook_bool_tree_true
259 #undef TARGET_PROMOTE_FUNCTION_RETURN
260 #define TARGET_PROMOTE_FUNCTION_RETURN hook_bool_tree_true
261 #undef TARGET_PASS_BY_REFERENCE
262 #define TARGET_PASS_BY_REFERENCE s390_pass_by_reference
264 #undef TARGET_FUNCTION_OK_FOR_SIBCALL
265 #define TARGET_FUNCTION_OK_FOR_SIBCALL s390_function_ok_for_sibcall
267 #undef TARGET_FIXED_CONDITION_CODE_REGS
268 #define TARGET_FIXED_CONDITION_CODE_REGS s390_fixed_condition_code_regs
270 #undef TARGET_CC_MODES_COMPATIBLE
271 #define TARGET_CC_MODES_COMPATIBLE s390_cc_modes_compatible
273 struct gcc_target targetm = TARGET_INITIALIZER;
275 extern int reload_completed;
277 /* The alias set for prologue/epilogue register save/restore. */
278 static int s390_sr_alias_set = 0;
280 /* Save information from a "cmpxx" operation until the branch or scc is
282 rtx s390_compare_op0, s390_compare_op1;
284 /* Structure used to hold the components of a S/390 memory
285 address. A legitimate address on S/390 is of the general
287 base + index + displacement
288 where any of the components is optional.
290 base and index are registers of the class ADDR_REGS,
291 displacement is an unsigned 12-bit immediate constant. */
301 /* Which cpu are we tuning for. */
302 enum processor_type s390_tune = PROCESSOR_max;
303 enum processor_flags s390_tune_flags;
304 /* Which instruction set architecture to use. */
305 enum processor_type s390_arch;
306 enum processor_flags s390_arch_flags;
307 static const char *s390_arch_string;
309 HOST_WIDE_INT s390_warn_framesize = 0;
310 HOST_WIDE_INT s390_stack_size = 0;
311 HOST_WIDE_INT s390_stack_guard = 0;
313 /* The following structure is embedded in the machine
314 specific part of struct function. */
316 struct s390_frame_layout GTY (())
318 /* Offset within stack frame. */
319 HOST_WIDE_INT gprs_offset;
320 HOST_WIDE_INT f0_offset;
321 HOST_WIDE_INT f4_offset;
322 HOST_WIDE_INT f8_offset;
323 HOST_WIDE_INT backchain_offset;
325 /* Number of first and last gpr to be saved, restored. */
327 int first_restore_gpr;
329 int last_restore_gpr;
331 /* Bits standing for floating point registers. Set, if the
332 respective register has to be saved. Starting with reg 16 (f0)
333 at the rightmost bit.
334 Bit 15 - 8 7 6 5 4 3 2 1 0
335 fpr 15 - 8 7 5 3 1 6 4 2 0
336 reg 31 - 24 23 22 21 20 19 18 17 16 */
337 unsigned int fpr_bitmap;
339 /* Number of floating point registers f8-f15 which must be saved. */
342 /* Set if return address needs to be saved. */
343 bool save_return_addr_p;
345 /* Size of stack frame. */
346 HOST_WIDE_INT frame_size;
349 /* Define the structure for the machine field in struct function. */
351 struct machine_function GTY(())
353 struct s390_frame_layout frame_layout;
355 /* Literal pool base register. */
358 /* True if we may need to perform branch splitting. */
359 bool split_branches_pending_p;
361 /* Some local-dynamic TLS symbol name. */
362 const char *some_ld_name;
365 /* Few accessor macros for struct cfun->machine->s390_frame_layout. */
367 #define cfun_frame_layout (cfun->machine->frame_layout)
368 #define cfun_save_high_fprs_p (!!cfun_frame_layout.high_fprs)
369 #define cfun_gprs_save_area_size ((cfun_frame_layout.last_save_gpr - \
370 cfun_frame_layout.first_save_gpr + 1) * UNITS_PER_WORD)
371 #define cfun_set_fpr_bit(BITNUM) (cfun->machine->frame_layout.fpr_bitmap |= \
373 #define cfun_fpr_bit_p(BITNUM) (!!(cfun->machine->frame_layout.fpr_bitmap & \
376 static int s390_match_ccmode_set (rtx, enum machine_mode);
377 static const char *s390_branch_condition_mnemonic (rtx, int);
378 static int s390_short_displacement (rtx);
379 static int s390_decompose_address (rtx, struct s390_address *);
380 static rtx get_thread_pointer (void);
381 static rtx legitimize_tls_address (rtx, rtx);
382 static void print_shift_count_operand (FILE *, rtx);
383 static const char *get_some_local_dynamic_name (void);
384 static int get_some_local_dynamic_name_1 (rtx *, void *);
385 static int reg_used_in_mem_p (int, rtx);
386 static int addr_generation_dependency_p (rtx, rtx);
387 static int s390_split_branches (void);
388 static void annotate_constant_pool_refs (rtx *x);
389 static void find_constant_pool_ref (rtx, rtx *);
390 static void replace_constant_pool_ref (rtx *, rtx, rtx);
391 static rtx find_ltrel_base (rtx);
392 static void replace_ltrel_base (rtx *);
393 static void s390_optimize_prologue (void);
394 static int find_unused_clobbered_reg (void);
395 static void s390_frame_area (int *, int *);
396 static void s390_register_info (int []);
397 static void s390_frame_info (void);
398 static void s390_init_frame_layout (void);
399 static void s390_update_frame_layout (void);
400 static rtx save_fpr (rtx, int, int);
401 static rtx restore_fpr (rtx, int, int);
402 static rtx save_gprs (rtx, int, int, int);
403 static rtx restore_gprs (rtx, int, int, int);
404 static int s390_function_arg_size (enum machine_mode, tree);
405 static bool s390_function_arg_float (enum machine_mode, tree);
406 static struct machine_function * s390_init_machine_status (void);
408 /* Return true if CODE is a valid address without index. */
411 s390_legitimate_address_without_index_p (rtx op)
413 struct s390_address addr;
415 if (!s390_decompose_address (XEXP (op, 0), &addr))
423 /* Return true if SET either doesn't set the CC register, or else
424 the source and destination have matching CC modes and that
425 CC mode is at least as constrained as REQ_MODE. */
428 s390_match_ccmode_set (rtx set, enum machine_mode req_mode)
430 enum machine_mode set_mode;
432 if (GET_CODE (set) != SET)
435 if (GET_CODE (SET_DEST (set)) != REG || !CC_REGNO_P (REGNO (SET_DEST (set))))
438 set_mode = GET_MODE (SET_DEST (set));
452 if (req_mode != set_mode)
457 if (req_mode != CCSmode && req_mode != CCUmode && req_mode != CCTmode
458 && req_mode != CCSRmode && req_mode != CCURmode)
464 if (req_mode != CCAmode)
472 return (GET_MODE (SET_SRC (set)) == set_mode);
475 /* Return true if every SET in INSN that sets the CC register
476 has source and destination with matching CC modes and that
477 CC mode is at least as constrained as REQ_MODE.
478 If REQ_MODE is VOIDmode, always return false. */
481 s390_match_ccmode (rtx insn, enum machine_mode req_mode)
485 /* s390_tm_ccmode returns VOIDmode to indicate failure. */
486 if (req_mode == VOIDmode)
489 if (GET_CODE (PATTERN (insn)) == SET)
490 return s390_match_ccmode_set (PATTERN (insn), req_mode);
492 if (GET_CODE (PATTERN (insn)) == PARALLEL)
493 for (i = 0; i < XVECLEN (PATTERN (insn), 0); i++)
495 rtx set = XVECEXP (PATTERN (insn), 0, i);
496 if (GET_CODE (set) == SET)
497 if (!s390_match_ccmode_set (set, req_mode))
504 /* If a test-under-mask instruction can be used to implement
505 (compare (and ... OP1) OP2), return the CC mode required
506 to do that. Otherwise, return VOIDmode.
507 MIXED is true if the instruction can distinguish between
508 CC1 and CC2 for mixed selected bits (TMxx), it is false
509 if the instruction cannot (TM). */
512 s390_tm_ccmode (rtx op1, rtx op2, int mixed)
516 /* ??? Fixme: should work on CONST_DOUBLE as well. */
517 if (GET_CODE (op1) != CONST_INT || GET_CODE (op2) != CONST_INT)
520 /* Selected bits all zero: CC0.
521 e.g.: int a; if ((a & (16 + 128)) == 0) */
522 if (INTVAL (op2) == 0)
525 /* Selected bits all one: CC3.
526 e.g.: int a; if ((a & (16 + 128)) == 16 + 128) */
527 if (INTVAL (op2) == INTVAL (op1))
530 /* Exactly two bits selected, mixed zeroes and ones: CC1 or CC2. e.g.:
532 if ((a & (16 + 128)) == 16) -> CCT1
533 if ((a & (16 + 128)) == 128) -> CCT2 */
536 bit1 = exact_log2 (INTVAL (op2));
537 bit0 = exact_log2 (INTVAL (op1) ^ INTVAL (op2));
538 if (bit0 != -1 && bit1 != -1)
539 return bit0 > bit1 ? CCT1mode : CCT2mode;
545 /* Given a comparison code OP (EQ, NE, etc.) and the operands
546 OP0 and OP1 of a COMPARE, return the mode to be used for the
550 s390_select_ccmode (enum rtx_code code, rtx op0, rtx op1)
556 if ((GET_CODE (op0) == NEG || GET_CODE (op0) == ABS)
557 && GET_MODE_CLASS (GET_MODE (op0)) == MODE_INT)
559 if (GET_CODE (op0) == PLUS && GET_CODE (XEXP (op0, 1)) == CONST_INT
560 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (XEXP (op0, 1)), 'K', "K"))
562 if ((GET_CODE (op0) == PLUS || GET_CODE (op0) == MINUS
563 || GET_CODE (op1) == NEG)
564 && GET_MODE_CLASS (GET_MODE (op0)) == MODE_INT)
567 if (GET_CODE (op0) == AND)
569 /* Check whether we can potentially do it via TM. */
570 enum machine_mode ccmode;
571 ccmode = s390_tm_ccmode (XEXP (op0, 1), op1, 1);
572 if (ccmode != VOIDmode)
574 /* Relax CCTmode to CCZmode to allow fall-back to AND
575 if that turns out to be beneficial. */
576 return ccmode == CCTmode ? CCZmode : ccmode;
580 if (register_operand (op0, HImode)
581 && GET_CODE (op1) == CONST_INT
582 && (INTVAL (op1) == -1 || INTVAL (op1) == 65535))
584 if (register_operand (op0, QImode)
585 && GET_CODE (op1) == CONST_INT
586 && (INTVAL (op1) == -1 || INTVAL (op1) == 255))
595 /* The only overflow condition of NEG and ABS happens when
596 -INT_MAX is used as parameter, which stays negative. So
597 we have an overflow from a positive value to a negative.
598 Using CCAP mode the resulting cc can be used for comparisons. */
599 if ((GET_CODE (op0) == NEG || GET_CODE (op0) == ABS)
600 && GET_MODE_CLASS (GET_MODE (op0)) == MODE_INT)
603 /* If constants are involved in an add instruction it is possible to use
604 the resulting cc for comparisons with zero. Knowing the sign of the
605 constant the overflow behavior gets predictable. e.g.:
606 int a, b; if ((b = a + c) > 0)
607 with c as a constant value: c < 0 -> CCAN and c >= 0 -> CCAP */
608 if (GET_CODE (op0) == PLUS && GET_CODE (XEXP (op0, 1)) == CONST_INT
609 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (XEXP (op0, 1)), 'K', "K"))
611 if (INTVAL (XEXP((op0), 1)) < 0)
625 if ((GET_CODE (op0) == SIGN_EXTEND || GET_CODE (op0) == ZERO_EXTEND)
626 && GET_CODE (op1) != CONST_INT)
632 if (GET_CODE (op0) == PLUS
633 && GET_MODE_CLASS (GET_MODE (op0)) == MODE_INT)
636 if ((GET_CODE (op0) == SIGN_EXTEND || GET_CODE (op0) == ZERO_EXTEND)
637 && GET_CODE (op1) != CONST_INT)
643 if (GET_CODE (op0) == MINUS
644 && GET_MODE_CLASS (GET_MODE (op0)) == MODE_INT)
647 if ((GET_CODE (op0) == SIGN_EXTEND || GET_CODE (op0) == ZERO_EXTEND)
648 && GET_CODE (op1) != CONST_INT)
657 /* Replace the comparison OP0 CODE OP1 by a semantically equivalent one
658 that we can implement more efficiently. */
661 s390_canonicalize_comparison (enum rtx_code *code, rtx *op0, rtx *op1)
663 /* Convert ZERO_EXTRACT back to AND to enable TM patterns. */
664 if ((*code == EQ || *code == NE)
665 && *op1 == const0_rtx
666 && GET_CODE (*op0) == ZERO_EXTRACT
667 && GET_CODE (XEXP (*op0, 1)) == CONST_INT
668 && GET_CODE (XEXP (*op0, 2)) == CONST_INT
669 && SCALAR_INT_MODE_P (GET_MODE (XEXP (*op0, 0))))
671 rtx inner = XEXP (*op0, 0);
672 HOST_WIDE_INT modesize = GET_MODE_BITSIZE (GET_MODE (inner));
673 HOST_WIDE_INT len = INTVAL (XEXP (*op0, 1));
674 HOST_WIDE_INT pos = INTVAL (XEXP (*op0, 2));
676 if (len > 0 && len < modesize
677 && pos >= 0 && pos + len <= modesize
678 && modesize <= HOST_BITS_PER_WIDE_INT)
680 unsigned HOST_WIDE_INT block;
681 block = ((unsigned HOST_WIDE_INT) 1 << len) - 1;
682 block <<= modesize - pos - len;
684 *op0 = gen_rtx_AND (GET_MODE (inner), inner,
685 gen_int_mode (block, GET_MODE (inner)));
689 /* Narrow AND of memory against immediate to enable TM. */
690 if ((*code == EQ || *code == NE)
691 && *op1 == const0_rtx
692 && GET_CODE (*op0) == AND
693 && GET_CODE (XEXP (*op0, 1)) == CONST_INT
694 && SCALAR_INT_MODE_P (GET_MODE (XEXP (*op0, 0))))
696 rtx inner = XEXP (*op0, 0);
697 rtx mask = XEXP (*op0, 1);
699 /* Ignore paradoxical SUBREGs if all extra bits are masked out. */
700 if (GET_CODE (inner) == SUBREG
701 && SCALAR_INT_MODE_P (GET_MODE (SUBREG_REG (inner)))
702 && (GET_MODE_SIZE (GET_MODE (inner))
703 >= GET_MODE_SIZE (GET_MODE (SUBREG_REG (inner))))
705 & GET_MODE_MASK (GET_MODE (inner))
706 & ~GET_MODE_MASK (GET_MODE (SUBREG_REG (inner))))
708 inner = SUBREG_REG (inner);
710 /* Do not change volatile MEMs. */
711 if (MEM_P (inner) && !MEM_VOLATILE_P (inner))
713 int part = s390_single_part (XEXP (*op0, 1),
714 GET_MODE (inner), QImode, 0);
717 mask = gen_int_mode (s390_extract_part (mask, QImode, 0), QImode);
718 inner = adjust_address_nv (inner, QImode, part);
719 *op0 = gen_rtx_AND (QImode, inner, mask);
724 /* Narrow comparisons against 0xffff to HImode if possible. */
725 if ((*code == EQ || *code == NE)
726 && GET_CODE (*op1) == CONST_INT
727 && INTVAL (*op1) == 0xffff
728 && SCALAR_INT_MODE_P (GET_MODE (*op0))
729 && (nonzero_bits (*op0, GET_MODE (*op0))
730 & ~(unsigned HOST_WIDE_INT) 0xffff) == 0)
732 *op0 = gen_lowpart (HImode, *op0);
737 /* Remove redundant UNSPEC_CMPINT conversions if possible. */
738 if (GET_CODE (*op0) == UNSPEC
739 && XINT (*op0, 1) == UNSPEC_CMPINT
740 && XVECLEN (*op0, 0) == 1
741 && GET_MODE (XVECEXP (*op0, 0, 0)) == CCUmode
742 && GET_CODE (XVECEXP (*op0, 0, 0)) == REG
743 && REGNO (XVECEXP (*op0, 0, 0)) == CC_REGNUM
744 && *op1 == const0_rtx)
746 enum rtx_code new_code = UNKNOWN;
749 case EQ: new_code = EQ; break;
750 case NE: new_code = NE; break;
751 case LT: new_code = GTU; break;
752 case GT: new_code = LTU; break;
753 case LE: new_code = GEU; break;
754 case GE: new_code = LEU; break;
758 if (new_code != UNKNOWN)
760 *op0 = XVECEXP (*op0, 0, 0);
766 /* Emit a compare instruction suitable to implement the comparison
767 OP0 CODE OP1. Return the correct condition RTL to be placed in
768 the IF_THEN_ELSE of the conditional branch testing the result. */
771 s390_emit_compare (enum rtx_code code, rtx op0, rtx op1)
773 enum machine_mode mode = s390_select_ccmode (code, op0, op1);
774 rtx cc = gen_rtx_REG (mode, CC_REGNUM);
776 emit_insn (gen_rtx_SET (VOIDmode, cc, gen_rtx_COMPARE (mode, op0, op1)));
777 return gen_rtx_fmt_ee (code, VOIDmode, cc, const0_rtx);
780 /* Emit a jump instruction to TARGET. If COND is NULL_RTX, emit an
781 unconditional jump, else a conditional jump under condition COND. */
784 s390_emit_jump (rtx target, rtx cond)
788 target = gen_rtx_LABEL_REF (VOIDmode, target);
790 target = gen_rtx_IF_THEN_ELSE (VOIDmode, cond, target, pc_rtx);
792 insn = gen_rtx_SET (VOIDmode, pc_rtx, target);
793 emit_jump_insn (insn);
796 /* Return branch condition mask to implement a branch
797 specified by CODE. Return -1 for invalid comparisons. */
800 s390_branch_condition_mask (rtx code)
802 const int CC0 = 1 << 3;
803 const int CC1 = 1 << 2;
804 const int CC2 = 1 << 1;
805 const int CC3 = 1 << 0;
807 if (GET_CODE (XEXP (code, 0)) != REG
808 || REGNO (XEXP (code, 0)) != CC_REGNUM
809 || XEXP (code, 1) != const0_rtx)
812 switch (GET_MODE (XEXP (code, 0)))
815 switch (GET_CODE (code))
818 case NE: return CC1 | CC2 | CC3;
824 switch (GET_CODE (code))
827 case NE: return CC0 | CC2 | CC3;
833 switch (GET_CODE (code))
836 case NE: return CC0 | CC1 | CC3;
842 switch (GET_CODE (code))
845 case NE: return CC0 | CC1 | CC2;
851 switch (GET_CODE (code))
853 case EQ: return CC0 | CC2;
854 case NE: return CC1 | CC3;
860 switch (GET_CODE (code))
862 case LTU: return CC2 | CC3; /* carry */
863 case GEU: return CC0 | CC1; /* no carry */
869 switch (GET_CODE (code))
871 case GTU: return CC0 | CC1; /* borrow */
872 case LEU: return CC2 | CC3; /* no borrow */
878 switch (GET_CODE (code))
880 case EQ: return CC0 | CC2;
881 case NE: return CC1 | CC3;
882 case LTU: return CC1;
883 case GTU: return CC3;
884 case LEU: return CC1 | CC2;
885 case GEU: return CC2 | CC3;
890 switch (GET_CODE (code))
893 case NE: return CC1 | CC2 | CC3;
894 case LTU: return CC1;
895 case GTU: return CC2;
896 case LEU: return CC0 | CC1;
897 case GEU: return CC0 | CC2;
903 switch (GET_CODE (code))
906 case NE: return CC2 | CC1 | CC3;
907 case LTU: return CC2;
908 case GTU: return CC1;
909 case LEU: return CC0 | CC2;
910 case GEU: return CC0 | CC1;
916 switch (GET_CODE (code))
919 case NE: return CC1 | CC2 | CC3;
920 case LT: return CC1 | CC3;
922 case LE: return CC0 | CC1 | CC3;
923 case GE: return CC0 | CC2;
929 switch (GET_CODE (code))
932 case NE: return CC1 | CC2 | CC3;
934 case GT: return CC2 | CC3;
935 case LE: return CC0 | CC1;
936 case GE: return CC0 | CC2 | CC3;
942 switch (GET_CODE (code))
945 case NE: return CC1 | CC2 | CC3;
948 case LE: return CC0 | CC1;
949 case GE: return CC0 | CC2;
950 case UNORDERED: return CC3;
951 case ORDERED: return CC0 | CC1 | CC2;
952 case UNEQ: return CC0 | CC3;
953 case UNLT: return CC1 | CC3;
954 case UNGT: return CC2 | CC3;
955 case UNLE: return CC0 | CC1 | CC3;
956 case UNGE: return CC0 | CC2 | CC3;
957 case LTGT: return CC1 | CC2;
963 switch (GET_CODE (code))
966 case NE: return CC2 | CC1 | CC3;
969 case LE: return CC0 | CC2;
970 case GE: return CC0 | CC1;
971 case UNORDERED: return CC3;
972 case ORDERED: return CC0 | CC2 | CC1;
973 case UNEQ: return CC0 | CC3;
974 case UNLT: return CC2 | CC3;
975 case UNGT: return CC1 | CC3;
976 case UNLE: return CC0 | CC2 | CC3;
977 case UNGE: return CC0 | CC1 | CC3;
978 case LTGT: return CC2 | CC1;
988 /* If INV is false, return assembler mnemonic string to implement
989 a branch specified by CODE. If INV is true, return mnemonic
990 for the corresponding inverted branch. */
993 s390_branch_condition_mnemonic (rtx code, int inv)
995 static const char *const mnemonic[16] =
997 NULL, "o", "h", "nle",
998 "l", "nhe", "lh", "ne",
999 "e", "nlh", "he", "nl",
1000 "le", "nh", "no", NULL
1003 int mask = s390_branch_condition_mask (code);
1004 gcc_assert (mask >= 0);
1009 if (mask < 1 || mask > 14)
1012 return mnemonic[mask];
1015 /* Return the part of op which has a value different from def.
1016 The size of the part is determined by mode.
1017 Use this function only if you already know that op really
1018 contains such a part. */
1020 unsigned HOST_WIDE_INT
1021 s390_extract_part (rtx op, enum machine_mode mode, int def)
1023 unsigned HOST_WIDE_INT value = 0;
1024 int max_parts = HOST_BITS_PER_WIDE_INT / GET_MODE_BITSIZE (mode);
1025 int part_bits = GET_MODE_BITSIZE (mode);
1026 unsigned HOST_WIDE_INT part_mask = (1 << part_bits) - 1;
1029 for (i = 0; i < max_parts; i++)
1032 value = (unsigned HOST_WIDE_INT) INTVAL (op);
1034 value >>= part_bits;
1036 if ((value & part_mask) != (def & part_mask))
1037 return value & part_mask;
1043 /* If OP is an integer constant of mode MODE with exactly one
1044 part of mode PART_MODE unequal to DEF, return the number of that
1045 part. Otherwise, return -1. */
1048 s390_single_part (rtx op,
1049 enum machine_mode mode,
1050 enum machine_mode part_mode,
1053 unsigned HOST_WIDE_INT value = 0;
1054 int n_parts = GET_MODE_SIZE (mode) / GET_MODE_SIZE (part_mode);
1055 unsigned HOST_WIDE_INT part_mask = (1 << GET_MODE_BITSIZE (part_mode)) - 1;
1058 if (GET_CODE (op) != CONST_INT)
1061 for (i = 0; i < n_parts; i++)
1064 value = (unsigned HOST_WIDE_INT) INTVAL (op);
1066 value >>= GET_MODE_BITSIZE (part_mode);
1068 if ((value & part_mask) != (def & part_mask))
1076 return part == -1 ? -1 : n_parts - 1 - part;
1079 /* Check whether we can (and want to) split a double-word
1080 move in mode MODE from SRC to DST into two single-word
1081 moves, moving the subword FIRST_SUBWORD first. */
1084 s390_split_ok_p (rtx dst, rtx src, enum machine_mode mode, int first_subword)
1086 /* Floating point registers cannot be split. */
1087 if (FP_REG_P (src) || FP_REG_P (dst))
1090 /* We don't need to split if operands are directly accessible. */
1091 if (s_operand (src, mode) || s_operand (dst, mode))
1094 /* Non-offsettable memory references cannot be split. */
1095 if ((GET_CODE (src) == MEM && !offsettable_memref_p (src))
1096 || (GET_CODE (dst) == MEM && !offsettable_memref_p (dst)))
1099 /* Moving the first subword must not clobber a register
1100 needed to move the second subword. */
1101 if (register_operand (dst, mode))
1103 rtx subreg = operand_subword (dst, first_subword, 0, mode);
1104 if (reg_overlap_mentioned_p (subreg, src))
1111 /* Check whether the address of memory reference MEM2 equals exactly
1112 the address of memory reference MEM1 plus DELTA. Return true if
1113 we can prove this to be the case, false otherwise. */
1116 s390_offset_p (rtx mem1, rtx mem2, rtx delta)
1118 rtx addr1, addr2, addr_delta;
1120 if (GET_CODE (mem1) != MEM || GET_CODE (mem2) != MEM)
1123 addr1 = XEXP (mem1, 0);
1124 addr2 = XEXP (mem2, 0);
1126 addr_delta = simplify_binary_operation (MINUS, Pmode, addr2, addr1);
1127 if (!addr_delta || !rtx_equal_p (addr_delta, delta))
1133 /* Expand logical operator CODE in mode MODE with operands OPERANDS. */
1136 s390_expand_logical_operator (enum rtx_code code, enum machine_mode mode,
1139 enum machine_mode wmode = mode;
1140 rtx dst = operands[0];
1141 rtx src1 = operands[1];
1142 rtx src2 = operands[2];
1145 /* If we cannot handle the operation directly, use a temp register. */
1146 if (!s390_logical_operator_ok_p (operands))
1147 dst = gen_reg_rtx (mode);
1149 /* QImode and HImode patterns make sense only if we have a destination
1150 in memory. Otherwise perform the operation in SImode. */
1151 if ((mode == QImode || mode == HImode) && GET_CODE (dst) != MEM)
1154 /* Widen operands if required. */
1157 if (GET_CODE (dst) == SUBREG
1158 && (tem = simplify_subreg (wmode, dst, mode, 0)) != 0)
1160 else if (REG_P (dst))
1161 dst = gen_rtx_SUBREG (wmode, dst, 0);
1163 dst = gen_reg_rtx (wmode);
1165 if (GET_CODE (src1) == SUBREG
1166 && (tem = simplify_subreg (wmode, src1, mode, 0)) != 0)
1168 else if (GET_MODE (src1) != VOIDmode)
1169 src1 = gen_rtx_SUBREG (wmode, force_reg (mode, src1), 0);
1171 if (GET_CODE (src2) == SUBREG
1172 && (tem = simplify_subreg (wmode, src2, mode, 0)) != 0)
1174 else if (GET_MODE (src2) != VOIDmode)
1175 src2 = gen_rtx_SUBREG (wmode, force_reg (mode, src2), 0);
1178 /* Emit the instruction. */
1179 op = gen_rtx_SET (VOIDmode, dst, gen_rtx_fmt_ee (code, wmode, src1, src2));
1180 clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, CC_REGNUM));
1181 emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, op, clob)));
1183 /* Fix up the destination if needed. */
1184 if (dst != operands[0])
1185 emit_move_insn (operands[0], gen_lowpart (mode, dst));
1188 /* Check whether OPERANDS are OK for a logical operation (AND, IOR, XOR). */
1191 s390_logical_operator_ok_p (rtx *operands)
1193 /* If the destination operand is in memory, it needs to coincide
1194 with one of the source operands. After reload, it has to be
1195 the first source operand. */
1196 if (GET_CODE (operands[0]) == MEM)
1197 return rtx_equal_p (operands[0], operands[1])
1198 || (!reload_completed && rtx_equal_p (operands[0], operands[2]));
1203 /* Narrow logical operation CODE of memory operand MEMOP with immediate
1204 operand IMMOP to switch from SS to SI type instructions. */
1207 s390_narrow_logical_operator (enum rtx_code code, rtx *memop, rtx *immop)
1209 int def = code == AND ? -1 : 0;
1213 gcc_assert (GET_CODE (*memop) == MEM);
1214 gcc_assert (!MEM_VOLATILE_P (*memop));
1216 mask = s390_extract_part (*immop, QImode, def);
1217 part = s390_single_part (*immop, GET_MODE (*memop), QImode, def);
1218 gcc_assert (part >= 0);
1220 *memop = adjust_address (*memop, QImode, part);
1221 *immop = gen_int_mode (mask, QImode);
1225 /* Change optimizations to be performed, depending on the
1228 LEVEL is the optimization level specified; 2 if `-O2' is
1229 specified, 1 if `-O' is specified, and 0 if neither is specified.
1231 SIZE is nonzero if `-Os' is specified and zero otherwise. */
1234 optimization_options (int level ATTRIBUTE_UNUSED, int size ATTRIBUTE_UNUSED)
1236 /* ??? There are apparently still problems with -fcaller-saves. */
1237 flag_caller_saves = 0;
1239 /* By default, always emit DWARF-2 unwind info. This allows debugging
1240 without maintaining a stack frame back-chain. */
1241 flag_asynchronous_unwind_tables = 1;
1244 /* Return true if ARG is the name of a processor. Set *TYPE and *FLAGS
1245 to the associated processor_type and processor_flags if so. */
1248 s390_handle_arch_option (const char *arg,
1249 enum processor_type *type,
1250 enum processor_flags *flags)
1254 const char *const name; /* processor name or nickname. */
1255 const enum processor_type processor;
1256 const enum processor_flags flags;
1258 const processor_alias_table[] =
1260 {"g5", PROCESSOR_9672_G5, PF_IEEE_FLOAT},
1261 {"g6", PROCESSOR_9672_G6, PF_IEEE_FLOAT},
1262 {"z900", PROCESSOR_2064_Z900, PF_IEEE_FLOAT | PF_ZARCH},
1263 {"z990", PROCESSOR_2084_Z990, PF_IEEE_FLOAT | PF_ZARCH
1264 | PF_LONG_DISPLACEMENT},
1268 for (i = 0; i < ARRAY_SIZE (processor_alias_table); i++)
1269 if (strcmp (arg, processor_alias_table[i].name) == 0)
1271 *type = processor_alias_table[i].processor;
1272 *flags = processor_alias_table[i].flags;
1278 /* Implement TARGET_HANDLE_OPTION. */
1281 s390_handle_option (size_t code, const char *arg, int value ATTRIBUTE_UNUSED)
1286 s390_arch_string = arg;
1287 return s390_handle_arch_option (arg, &s390_arch, &s390_arch_flags);
1289 case OPT_mstack_guard_:
1290 if (sscanf (arg, HOST_WIDE_INT_PRINT_DEC, &s390_stack_guard) != 1)
1292 if (exact_log2 (s390_stack_guard) == -1)
1293 error ("stack guard value must be an exact power of 2");
1296 case OPT_mstack_size_:
1297 if (sscanf (arg, HOST_WIDE_INT_PRINT_DEC, &s390_stack_size) != 1)
1299 if (exact_log2 (s390_stack_size) == -1)
1300 error ("stack size must be an exact power of 2");
1304 return s390_handle_arch_option (arg, &s390_tune, &s390_tune_flags);
1306 case OPT_mwarn_framesize_:
1307 return sscanf (arg, HOST_WIDE_INT_PRINT_DEC, &s390_warn_framesize) == 1;
1315 override_options (void)
1317 /* Acquire a unique set number for our register saves and restores. */
1318 s390_sr_alias_set = new_alias_set ();
1320 /* Set up function hooks. */
1321 init_machine_status = s390_init_machine_status;
1323 /* Architecture mode defaults according to ABI. */
1324 if (!(target_flags_explicit & MASK_ZARCH))
1327 target_flags |= MASK_ZARCH;
1329 target_flags &= ~MASK_ZARCH;
1332 /* Determine processor architectural level. */
1333 if (!s390_arch_string)
1335 s390_arch_string = TARGET_ZARCH? "z900" : "g5";
1336 s390_handle_arch_option (s390_arch_string, &s390_arch, &s390_arch_flags);
1339 /* Determine processor to tune for. */
1340 if (s390_tune == PROCESSOR_max)
1342 s390_tune = s390_arch;
1343 s390_tune_flags = s390_arch_flags;
1346 /* Sanity checks. */
1347 if (TARGET_ZARCH && !(s390_arch_flags & PF_ZARCH))
1348 error ("z/Architecture mode not supported on %s.", s390_arch_string);
1349 if (TARGET_64BIT && !TARGET_ZARCH)
1350 error ("64-bit ABI not supported in ESA/390 mode.");
1353 /* Set processor cost function. */
1354 if (s390_tune == PROCESSOR_2084_Z990)
1355 s390_cost = &z990_cost;
1357 s390_cost = &z900_cost;
1360 if (TARGET_BACKCHAIN && TARGET_PACKED_STACK && TARGET_HARD_FLOAT)
1361 error ("-mbackchain -mpacked-stack -mhard-float are not supported "
1364 if (s390_stack_size)
1366 if (!s390_stack_guard)
1367 error ("-mstack-size implies use of -mstack-guard");
1368 else if (s390_stack_guard >= s390_stack_size)
1369 error ("stack size must be greater than the stack guard value");
1371 else if (s390_stack_guard)
1372 error ("-mstack-guard implies use of -mstack-size");
1375 /* Map for smallest class containing reg regno. */
1377 const enum reg_class regclass_map[FIRST_PSEUDO_REGISTER] =
1378 { GENERAL_REGS, ADDR_REGS, ADDR_REGS, ADDR_REGS,
1379 ADDR_REGS, ADDR_REGS, ADDR_REGS, ADDR_REGS,
1380 ADDR_REGS, ADDR_REGS, ADDR_REGS, ADDR_REGS,
1381 ADDR_REGS, ADDR_REGS, ADDR_REGS, ADDR_REGS,
1382 FP_REGS, FP_REGS, FP_REGS, FP_REGS,
1383 FP_REGS, FP_REGS, FP_REGS, FP_REGS,
1384 FP_REGS, FP_REGS, FP_REGS, FP_REGS,
1385 FP_REGS, FP_REGS, FP_REGS, FP_REGS,
1386 ADDR_REGS, CC_REGS, ADDR_REGS, ADDR_REGS,
1387 ACCESS_REGS, ACCESS_REGS
1390 /* Return attribute type of insn. */
1392 static enum attr_type
1393 s390_safe_attr_type (rtx insn)
1395 if (recog_memoized (insn) >= 0)
1396 return get_attr_type (insn);
1401 /* Return true if DISP is a valid short displacement. */
1404 s390_short_displacement (rtx disp)
1406 /* No displacement is OK. */
1410 /* Integer displacement in range. */
1411 if (GET_CODE (disp) == CONST_INT)
1412 return INTVAL (disp) >= 0 && INTVAL (disp) < 4096;
1414 /* GOT offset is not OK, the GOT can be large. */
1415 if (GET_CODE (disp) == CONST
1416 && GET_CODE (XEXP (disp, 0)) == UNSPEC
1417 && (XINT (XEXP (disp, 0), 1) == UNSPEC_GOT
1418 || XINT (XEXP (disp, 0), 1) == UNSPEC_GOTNTPOFF))
1421 /* All other symbolic constants are literal pool references,
1422 which are OK as the literal pool must be small. */
1423 if (GET_CODE (disp) == CONST)
1429 /* Return true if OP is a valid operand for a C constraint. */
1432 s390_extra_constraint_str (rtx op, int c, const char * str)
1434 struct s390_address addr;
1439 /* Check for offsettable variants of memory constraints. */
1442 /* Only accept non-volatile MEMs. */
1443 if (!MEM_P (op) || MEM_VOLATILE_P (op))
1446 if ((reload_completed || reload_in_progress)
1447 ? !offsettable_memref_p (op)
1448 : !offsettable_nonstrict_memref_p (op))
1454 /* Check for non-literal-pool variants of memory constraints. */
1457 if (GET_CODE (op) != MEM)
1459 if (!s390_decompose_address (XEXP (op, 0), &addr))
1461 if (addr.base && REG_P (addr.base) && REGNO (addr.base) == BASE_REGNUM)
1463 if (addr.indx && REG_P (addr.indx) && REGNO (addr.indx) == BASE_REGNUM)
1472 if (GET_CODE (op) != MEM)
1474 if (!s390_decompose_address (XEXP (op, 0), &addr))
1479 if (TARGET_LONG_DISPLACEMENT)
1481 if (!s390_short_displacement (addr.disp))
1487 if (GET_CODE (op) != MEM)
1490 if (TARGET_LONG_DISPLACEMENT)
1492 if (!s390_decompose_address (XEXP (op, 0), &addr))
1494 if (!s390_short_displacement (addr.disp))
1500 if (!TARGET_LONG_DISPLACEMENT)
1502 if (GET_CODE (op) != MEM)
1504 if (!s390_decompose_address (XEXP (op, 0), &addr))
1508 if (s390_short_displacement (addr.disp))
1513 if (!TARGET_LONG_DISPLACEMENT)
1515 if (GET_CODE (op) != MEM)
1517 /* Any invalid address here will be fixed up by reload,
1518 so accept it for the most generic constraint. */
1519 if (s390_decompose_address (XEXP (op, 0), &addr)
1520 && s390_short_displacement (addr.disp))
1525 if (TARGET_LONG_DISPLACEMENT)
1527 if (!s390_decompose_address (op, &addr))
1529 if (!s390_short_displacement (addr.disp))
1535 if (!TARGET_LONG_DISPLACEMENT)
1537 /* Any invalid address here will be fixed up by reload,
1538 so accept it for the most generic constraint. */
1539 if (s390_decompose_address (op, &addr)
1540 && s390_short_displacement (addr.disp))
1545 return shift_count_operand (op, VOIDmode);
1554 /* Return true if VALUE matches the constraint STR. */
1557 s390_const_ok_for_constraint_p (HOST_WIDE_INT value,
1561 enum machine_mode mode, part_mode;
1563 int part, part_goal;
1571 return (unsigned int)value < 256;
1574 return (unsigned int)value < 4096;
1577 return value >= -32768 && value < 32768;
1580 return (TARGET_LONG_DISPLACEMENT ?
1581 (value >= -524288 && value <= 524287)
1582 : (value >= 0 && value <= 4095));
1584 return value == 2147483647;
1590 part_goal = str[1] - '0';
1594 case 'H': part_mode = HImode; break;
1595 case 'Q': part_mode = QImode; break;
1601 case 'H': mode = HImode; break;
1602 case 'S': mode = SImode; break;
1603 case 'D': mode = DImode; break;
1609 case '0': def = 0; break;
1610 case 'F': def = -1; break;
1614 if (GET_MODE_SIZE (mode) <= GET_MODE_SIZE (part_mode))
1617 part = s390_single_part (GEN_INT (value), mode, part_mode, def);
1620 if (part_goal != -1 && part_goal != part)
1632 /* Compute a (partial) cost for rtx X. Return true if the complete
1633 cost has been computed, and false if subexpressions should be
1634 scanned. In either case, *TOTAL contains the cost result.
1635 CODE contains GET_CODE (x), OUTER_CODE contains the code
1636 of the superexpression of x. */
1639 s390_rtx_costs (rtx x, int code, int outer_code, int *total)
1662 *total = COSTS_N_INSNS (1);
1667 /* Check for multiply and add. */
1668 if ((GET_MODE (x) == DFmode || GET_MODE (x) == SFmode)
1669 && GET_CODE (XEXP (x, 0)) == MULT
1670 && TARGET_HARD_FLOAT && TARGET_IEEE_FLOAT && TARGET_FUSED_MADD)
1672 /* This is the multiply and add case. */
1673 if (GET_MODE (x) == DFmode)
1674 *total = s390_cost->madbr;
1676 *total = s390_cost->maebr;
1677 *total += rtx_cost (XEXP (XEXP (x, 0), 0), MULT)
1678 + rtx_cost (XEXP (XEXP (x, 0), 1), MULT)
1679 + rtx_cost (XEXP (x, 1), code);
1680 return true; /* Do not do an additional recursive descent. */
1682 *total = COSTS_N_INSNS (1);
1686 switch (GET_MODE (x))
1690 rtx left = XEXP (x, 0);
1691 rtx right = XEXP (x, 1);
1692 if (GET_CODE (right) == CONST_INT
1693 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (right), 'K', "K"))
1694 *total = s390_cost->mhi;
1695 else if (GET_CODE (left) == SIGN_EXTEND)
1696 *total = s390_cost->mh;
1698 *total = s390_cost->ms; /* msr, ms, msy */
1703 rtx left = XEXP (x, 0);
1704 rtx right = XEXP (x, 1);
1707 if (GET_CODE (right) == CONST_INT
1708 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (right), 'K', "K"))
1709 *total = s390_cost->mghi;
1710 else if (GET_CODE (left) == SIGN_EXTEND)
1711 *total = s390_cost->msgf;
1713 *total = s390_cost->msg; /* msgr, msg */
1715 else /* TARGET_31BIT */
1717 if (GET_CODE (left) == SIGN_EXTEND
1718 && GET_CODE (right) == SIGN_EXTEND)
1719 /* mulsidi case: mr, m */
1720 *total = s390_cost->m;
1721 else if (GET_CODE (left) == ZERO_EXTEND
1722 && GET_CODE (right) == ZERO_EXTEND
1723 && TARGET_CPU_ZARCH)
1724 /* umulsidi case: ml, mlr */
1725 *total = s390_cost->ml;
1727 /* Complex calculation is required. */
1728 *total = COSTS_N_INSNS (40);
1734 *total = s390_cost->mult_df;
1743 if (GET_MODE (x) == TImode) /* 128 bit division */
1744 *total = s390_cost->dlgr;
1745 else if (GET_MODE (x) == DImode)
1747 rtx right = XEXP (x, 1);
1748 if (GET_CODE (right) == ZERO_EXTEND) /* 64 by 32 bit division */
1749 *total = s390_cost->dlr;
1750 else /* 64 by 64 bit division */
1751 *total = s390_cost->dlgr;
1753 else if (GET_MODE (x) == SImode) /* 32 bit division */
1754 *total = s390_cost->dlr;
1759 if (GET_MODE (x) == DImode)
1761 rtx right = XEXP (x, 1);
1762 if (GET_CODE (right) == ZERO_EXTEND) /* 64 by 32 bit division */
1764 *total = s390_cost->dsgfr;
1766 *total = s390_cost->dr;
1767 else /* 64 by 64 bit division */
1768 *total = s390_cost->dsgr;
1770 else if (GET_MODE (x) == SImode) /* 32 bit division */
1771 *total = s390_cost->dlr;
1772 else if (GET_MODE (x) == SFmode)
1774 if (TARGET_IEEE_FLOAT)
1775 *total = s390_cost->debr;
1776 else /* TARGET_IBM_FLOAT */
1777 *total = s390_cost->der;
1779 else if (GET_MODE (x) == DFmode)
1781 if (TARGET_IEEE_FLOAT)
1782 *total = s390_cost->ddbr;
1783 else /* TARGET_IBM_FLOAT */
1784 *total = s390_cost->ddr;
1789 if (GET_MODE (x) == SFmode)
1790 *total = s390_cost->sqebr;
1792 *total = s390_cost->sqdbr;
1797 if (outer_code == MULT || outer_code == DIV || outer_code == MOD
1798 || outer_code == PLUS || outer_code == MINUS
1799 || outer_code == COMPARE)
1804 *total = COSTS_N_INSNS (1);
1805 if (GET_CODE (XEXP (x, 0)) == AND
1806 && GET_CODE (XEXP (x, 1)) == CONST_INT
1807 && GET_CODE (XEXP (XEXP (x, 0), 1)) == CONST_INT)
1809 rtx op0 = XEXP (XEXP (x, 0), 0);
1810 rtx op1 = XEXP (XEXP (x, 0), 1);
1811 rtx op2 = XEXP (x, 1);
1813 if (memory_operand (op0, GET_MODE (op0))
1814 && s390_tm_ccmode (op1, op2, 0) != VOIDmode)
1816 if (register_operand (op0, GET_MODE (op0))
1817 && s390_tm_ccmode (op1, op2, 1) != VOIDmode)
1827 /* Return the cost of an address rtx ADDR. */
1830 s390_address_cost (rtx addr)
1832 struct s390_address ad;
1833 if (!s390_decompose_address (addr, &ad))
1836 return ad.indx? COSTS_N_INSNS (1) + 1 : COSTS_N_INSNS (1);
1839 /* If OP is a SYMBOL_REF of a thread-local symbol, return its TLS mode,
1840 otherwise return 0. */
1843 tls_symbolic_operand (register rtx op)
1845 if (GET_CODE (op) != SYMBOL_REF)
1847 return SYMBOL_REF_TLS_MODEL (op);
1850 /* Split DImode access register reference REG (on 64-bit) into its constituent
1851 low and high parts, and store them into LO and HI. Note that gen_lowpart/
1852 gen_highpart cannot be used as they assume all registers are word-sized,
1853 while our access registers have only half that size. */
1856 s390_split_access_reg (rtx reg, rtx *lo, rtx *hi)
1858 gcc_assert (TARGET_64BIT);
1859 gcc_assert (ACCESS_REG_P (reg));
1860 gcc_assert (GET_MODE (reg) == DImode);
1861 gcc_assert (!(REGNO (reg) & 1));
1863 *lo = gen_rtx_REG (SImode, REGNO (reg) + 1);
1864 *hi = gen_rtx_REG (SImode, REGNO (reg));
1867 /* Return true if OP contains a symbol reference */
1870 symbolic_reference_mentioned_p (rtx op)
1872 register const char *fmt;
1875 if (GET_CODE (op) == SYMBOL_REF || GET_CODE (op) == LABEL_REF)
1878 fmt = GET_RTX_FORMAT (GET_CODE (op));
1879 for (i = GET_RTX_LENGTH (GET_CODE (op)) - 1; i >= 0; i--)
1885 for (j = XVECLEN (op, i) - 1; j >= 0; j--)
1886 if (symbolic_reference_mentioned_p (XVECEXP (op, i, j)))
1890 else if (fmt[i] == 'e' && symbolic_reference_mentioned_p (XEXP (op, i)))
1897 /* Return true if OP contains a reference to a thread-local symbol. */
1900 tls_symbolic_reference_mentioned_p (rtx op)
1902 register const char *fmt;
1905 if (GET_CODE (op) == SYMBOL_REF)
1906 return tls_symbolic_operand (op);
1908 fmt = GET_RTX_FORMAT (GET_CODE (op));
1909 for (i = GET_RTX_LENGTH (GET_CODE (op)) - 1; i >= 0; i--)
1915 for (j = XVECLEN (op, i) - 1; j >= 0; j--)
1916 if (tls_symbolic_reference_mentioned_p (XVECEXP (op, i, j)))
1920 else if (fmt[i] == 'e' && tls_symbolic_reference_mentioned_p (XEXP (op, i)))
1928 /* Return true if OP is a legitimate general operand when
1929 generating PIC code. It is given that flag_pic is on
1930 and that OP satisfies CONSTANT_P or is a CONST_DOUBLE. */
1933 legitimate_pic_operand_p (register rtx op)
1935 /* Accept all non-symbolic constants. */
1936 if (!SYMBOLIC_CONST (op))
1939 /* Reject everything else; must be handled
1940 via emit_symbolic_move. */
1944 /* Returns true if the constant value OP is a legitimate general operand.
1945 It is given that OP satisfies CONSTANT_P or is a CONST_DOUBLE. */
1948 legitimate_constant_p (register rtx op)
1950 /* Accept all non-symbolic constants. */
1951 if (!SYMBOLIC_CONST (op))
1954 /* Accept immediate LARL operands. */
1955 if (TARGET_CPU_ZARCH && larl_operand (op, VOIDmode))
1958 /* Thread-local symbols are never legal constants. This is
1959 so that emit_call knows that computing such addresses
1960 might require a function call. */
1961 if (TLS_SYMBOLIC_CONST (op))
1964 /* In the PIC case, symbolic constants must *not* be
1965 forced into the literal pool. We accept them here,
1966 so that they will be handled by emit_symbolic_move. */
1970 /* All remaining non-PIC symbolic constants are
1971 forced into the literal pool. */
1975 /* Determine if it's legal to put X into the constant pool. This
1976 is not possible if X contains the address of a symbol that is
1977 not constant (TLS) or not known at final link time (PIC). */
1980 s390_cannot_force_const_mem (rtx x)
1982 switch (GET_CODE (x))
1986 /* Accept all non-symbolic constants. */
1990 /* Labels are OK iff we are non-PIC. */
1991 return flag_pic != 0;
1994 /* 'Naked' TLS symbol references are never OK,
1995 non-TLS symbols are OK iff we are non-PIC. */
1996 if (tls_symbolic_operand (x))
1999 return flag_pic != 0;
2002 return s390_cannot_force_const_mem (XEXP (x, 0));
2005 return s390_cannot_force_const_mem (XEXP (x, 0))
2006 || s390_cannot_force_const_mem (XEXP (x, 1));
2009 switch (XINT (x, 1))
2011 /* Only lt-relative or GOT-relative UNSPECs are OK. */
2012 case UNSPEC_LTREL_OFFSET:
2020 case UNSPEC_GOTNTPOFF:
2021 case UNSPEC_INDNTPOFF:
2024 /* If the literal pool shares the code section, be put
2025 execute template placeholders into the pool as well. */
2027 return TARGET_CPU_ZARCH;
2039 /* Returns true if the constant value OP is a legitimate general
2040 operand during and after reload. The difference to
2041 legitimate_constant_p is that this function will not accept
2042 a constant that would need to be forced to the literal pool
2043 before it can be used as operand. */
2046 legitimate_reload_constant_p (register rtx op)
2048 /* Accept la(y) operands. */
2049 if (GET_CODE (op) == CONST_INT
2050 && DISP_IN_RANGE (INTVAL (op)))
2053 /* Accept l(g)hi operands. */
2054 if (GET_CODE (op) == CONST_INT
2055 && CONST_OK_FOR_CONSTRAINT_P (INTVAL (op), 'K', "K"))
2058 /* Accept lliXX operands. */
2060 && s390_single_part (op, DImode, HImode, 0) >= 0)
2063 /* Accept larl operands. */
2064 if (TARGET_CPU_ZARCH
2065 && larl_operand (op, VOIDmode))
2068 /* Everything else cannot be handled without reload. */
2072 /* Given an rtx OP being reloaded into a reg required to be in class CLASS,
2073 return the class of reg to actually use. */
2076 s390_preferred_reload_class (rtx op, enum reg_class class)
2078 switch (GET_CODE (op))
2080 /* Constants we cannot reload must be forced into the
2085 if (legitimate_reload_constant_p (op))
2090 /* If a symbolic constant or a PLUS is reloaded,
2091 it is most likely being used as an address, so
2092 prefer ADDR_REGS. If 'class' is not a superset
2093 of ADDR_REGS, e.g. FP_REGS, reject this reload. */
2098 if (reg_class_subset_p (ADDR_REGS, class))
2110 /* Return the register class of a scratch register needed to
2111 load IN into a register of class CLASS in MODE.
2113 We need a temporary when loading a PLUS expression which
2114 is not a legitimate operand of the LOAD ADDRESS instruction. */
2117 s390_secondary_input_reload_class (enum reg_class class,
2118 enum machine_mode mode, rtx in)
2120 if (s390_plus_operand (in, mode))
2123 if (reg_classes_intersect_p (CC_REGS, class))
2124 return GENERAL_REGS;
2129 /* Return the register class of a scratch register needed to
2130 store a register of class CLASS in MODE into OUT:
2132 We need a temporary when storing a double-word to a
2133 non-offsettable memory address. */
2136 s390_secondary_output_reload_class (enum reg_class class,
2137 enum machine_mode mode, rtx out)
2139 if ((TARGET_64BIT ? mode == TImode
2140 : (mode == DImode || mode == DFmode))
2141 && reg_classes_intersect_p (GENERAL_REGS, class)
2142 && GET_CODE (out) == MEM
2143 && GET_CODE (XEXP (out, 0)) == PLUS
2144 && GET_CODE (XEXP (XEXP (out, 0), 0)) == PLUS
2145 && GET_CODE (XEXP (XEXP (out, 0), 1)) == CONST_INT
2146 && !DISP_IN_RANGE (INTVAL (XEXP (XEXP (out, 0), 1))
2147 + GET_MODE_SIZE (mode) - 1))
2150 if (reg_classes_intersect_p (CC_REGS, class))
2151 return GENERAL_REGS;
2156 /* Generate code to load SRC, which is PLUS that is not a
2157 legitimate operand for the LA instruction, into TARGET.
2158 SCRATCH may be used as scratch register. */
2161 s390_expand_plus_operand (register rtx target, register rtx src,
2162 register rtx scratch)
2165 struct s390_address ad;
2167 /* src must be a PLUS; get its two operands. */
2168 if (GET_CODE (src) != PLUS || GET_MODE (src) != Pmode)
2171 /* Check if any of the two operands is already scheduled
2172 for replacement by reload. This can happen e.g. when
2173 float registers occur in an address. */
2174 sum1 = find_replacement (&XEXP (src, 0));
2175 sum2 = find_replacement (&XEXP (src, 1));
2176 src = gen_rtx_PLUS (Pmode, sum1, sum2);
2178 /* If the address is already strictly valid, there's nothing to do. */
2179 if (!s390_decompose_address (src, &ad)
2180 || (ad.base && !REG_OK_FOR_BASE_STRICT_P (ad.base))
2181 || (ad.indx && !REG_OK_FOR_INDEX_STRICT_P (ad.indx)))
2183 /* Otherwise, one of the operands cannot be an address register;
2184 we reload its value into the scratch register. */
2185 if (true_regnum (sum1) < 1 || true_regnum (sum1) > 15)
2187 emit_move_insn (scratch, sum1);
2190 if (true_regnum (sum2) < 1 || true_regnum (sum2) > 15)
2192 emit_move_insn (scratch, sum2);
2196 /* According to the way these invalid addresses are generated
2197 in reload.c, it should never happen (at least on s390) that
2198 *neither* of the PLUS components, after find_replacements
2199 was applied, is an address register. */
2200 if (sum1 == scratch && sum2 == scratch)
2206 src = gen_rtx_PLUS (Pmode, sum1, sum2);
2209 /* Emit the LOAD ADDRESS pattern. Note that reload of PLUS
2210 is only ever performed on addresses, so we can mark the
2211 sum as legitimate for LA in any case. */
2212 s390_load_address (target, src);
2216 /* Decompose a RTL expression ADDR for a memory address into
2217 its components, returned in OUT.
2219 Returns 0 if ADDR is not a valid memory address, nonzero
2220 otherwise. If OUT is NULL, don't return the components,
2221 but check for validity only.
2223 Note: Only addresses in canonical form are recognized.
2224 LEGITIMIZE_ADDRESS should convert non-canonical forms to the
2225 canonical form so that they will be recognized. */
2228 s390_decompose_address (register rtx addr, struct s390_address *out)
2230 HOST_WIDE_INT offset = 0;
2231 rtx base = NULL_RTX;
2232 rtx indx = NULL_RTX;
2233 rtx disp = NULL_RTX;
2235 int pointer = FALSE;
2236 int base_ptr = FALSE;
2237 int indx_ptr = FALSE;
2239 /* Decompose address into base + index + displacement. */
2241 if (GET_CODE (addr) == REG || GET_CODE (addr) == UNSPEC)
2244 else if (GET_CODE (addr) == PLUS)
2246 rtx op0 = XEXP (addr, 0);
2247 rtx op1 = XEXP (addr, 1);
2248 enum rtx_code code0 = GET_CODE (op0);
2249 enum rtx_code code1 = GET_CODE (op1);
2251 if (code0 == REG || code0 == UNSPEC)
2253 if (code1 == REG || code1 == UNSPEC)
2255 indx = op0; /* index + base */
2261 base = op0; /* base + displacement */
2266 else if (code0 == PLUS)
2268 indx = XEXP (op0, 0); /* index + base + disp */
2269 base = XEXP (op0, 1);
2280 disp = addr; /* displacement */
2282 /* Extract integer part of displacement. */
2286 if (GET_CODE (disp) == CONST_INT)
2288 offset = INTVAL (disp);
2291 else if (GET_CODE (disp) == CONST
2292 && GET_CODE (XEXP (disp, 0)) == PLUS
2293 && GET_CODE (XEXP (XEXP (disp, 0), 1)) == CONST_INT)
2295 offset = INTVAL (XEXP (XEXP (disp, 0), 1));
2296 disp = XEXP (XEXP (disp, 0), 0);
2300 /* Strip off CONST here to avoid special case tests later. */
2301 if (disp && GET_CODE (disp) == CONST)
2302 disp = XEXP (disp, 0);
2304 /* We can convert literal pool addresses to
2305 displacements by basing them off the base register. */
2306 if (disp && GET_CODE (disp) == SYMBOL_REF && CONSTANT_POOL_ADDRESS_P (disp))
2308 /* Either base or index must be free to hold the base register. */
2310 base = gen_rtx_REG (Pmode, BASE_REGNUM);
2312 indx = gen_rtx_REG (Pmode, BASE_REGNUM);
2316 /* Mark up the displacement. */
2317 disp = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, disp),
2318 UNSPEC_LTREL_OFFSET);
2321 /* Validate base register. */
2324 if (GET_CODE (base) == UNSPEC)
2325 switch (XINT (base, 1))
2329 disp = gen_rtx_UNSPEC (Pmode,
2330 gen_rtvec (1, XVECEXP (base, 0, 0)),
2331 UNSPEC_LTREL_OFFSET);
2335 base = gen_rtx_REG (Pmode, BASE_REGNUM);
2338 case UNSPEC_LTREL_BASE:
2339 base = gen_rtx_REG (Pmode, BASE_REGNUM);
2346 if (GET_CODE (base) != REG || GET_MODE (base) != Pmode)
2349 if (REGNO (base) == BASE_REGNUM
2350 || REGNO (base) == STACK_POINTER_REGNUM
2351 || REGNO (base) == FRAME_POINTER_REGNUM
2352 || ((reload_completed || reload_in_progress)
2353 && frame_pointer_needed
2354 && REGNO (base) == HARD_FRAME_POINTER_REGNUM)
2355 || REGNO (base) == ARG_POINTER_REGNUM
2357 && REGNO (base) == PIC_OFFSET_TABLE_REGNUM))
2358 pointer = base_ptr = TRUE;
2361 /* Validate index register. */
2364 if (GET_CODE (indx) == UNSPEC)
2365 switch (XINT (indx, 1))
2369 disp = gen_rtx_UNSPEC (Pmode,
2370 gen_rtvec (1, XVECEXP (indx, 0, 0)),
2371 UNSPEC_LTREL_OFFSET);
2375 indx = gen_rtx_REG (Pmode, BASE_REGNUM);
2378 case UNSPEC_LTREL_BASE:
2379 indx = gen_rtx_REG (Pmode, BASE_REGNUM);
2386 if (GET_CODE (indx) != REG || GET_MODE (indx) != Pmode)
2389 if (REGNO (indx) == BASE_REGNUM
2390 || REGNO (indx) == STACK_POINTER_REGNUM
2391 || REGNO (indx) == FRAME_POINTER_REGNUM
2392 || ((reload_completed || reload_in_progress)
2393 && frame_pointer_needed
2394 && REGNO (indx) == HARD_FRAME_POINTER_REGNUM)
2395 || REGNO (indx) == ARG_POINTER_REGNUM
2397 && REGNO (indx) == PIC_OFFSET_TABLE_REGNUM))
2398 pointer = indx_ptr = TRUE;
2401 /* Prefer to use pointer as base, not index. */
2402 if (base && indx && !base_ptr
2403 && (indx_ptr || (!REG_POINTER (base) && REG_POINTER (indx))))
2410 /* Validate displacement. */
2413 /* If the argument pointer or the return address pointer are involved,
2414 the displacement will change later anyway as the virtual registers get
2415 eliminated. This could make a valid displacement invalid, but it is
2416 more likely to make an invalid displacement valid, because we sometimes
2417 access the register save area via negative offsets to one of those
2419 Thus we don't check the displacement for validity here. If after
2420 elimination the displacement turns out to be invalid after all,
2421 this is fixed up by reload in any case. */
2422 if (base != arg_pointer_rtx
2423 && indx != arg_pointer_rtx
2424 && base != return_address_pointer_rtx
2425 && indx != return_address_pointer_rtx)
2426 if (!DISP_IN_RANGE (offset))
2431 /* All the special cases are pointers. */
2434 /* In the small-PIC case, the linker converts @GOT
2435 and @GOTNTPOFF offsets to possible displacements. */
2436 if (GET_CODE (disp) == UNSPEC
2437 && (XINT (disp, 1) == UNSPEC_GOT
2438 || XINT (disp, 1) == UNSPEC_GOTNTPOFF)
2445 /* Accept chunkified literal pool symbol references. */
2446 else if (GET_CODE (disp) == MINUS
2447 && GET_CODE (XEXP (disp, 0)) == LABEL_REF
2448 && GET_CODE (XEXP (disp, 1)) == LABEL_REF)
2453 /* Accept literal pool references. */
2454 else if (GET_CODE (disp) == UNSPEC
2455 && XINT (disp, 1) == UNSPEC_LTREL_OFFSET)
2457 orig_disp = gen_rtx_CONST (Pmode, disp);
2460 /* If we have an offset, make sure it does not
2461 exceed the size of the constant pool entry. */
2462 rtx sym = XVECEXP (disp, 0, 0);
2463 if (offset >= GET_MODE_SIZE (get_pool_mode (sym)))
2466 orig_disp = plus_constant (orig_disp, offset);
2481 out->disp = orig_disp;
2482 out->pointer = pointer;
2488 /* Return nonzero if ADDR is a valid memory address.
2489 STRICT specifies whether strict register checking applies. */
2492 legitimate_address_p (enum machine_mode mode ATTRIBUTE_UNUSED,
2493 register rtx addr, int strict)
2495 struct s390_address ad;
2496 if (!s390_decompose_address (addr, &ad))
2501 if (ad.base && !REG_OK_FOR_BASE_STRICT_P (ad.base))
2503 if (ad.indx && !REG_OK_FOR_INDEX_STRICT_P (ad.indx))
2508 if (ad.base && !REG_OK_FOR_BASE_NONSTRICT_P (ad.base))
2510 if (ad.indx && !REG_OK_FOR_INDEX_NONSTRICT_P (ad.indx))
2517 /* Return 1 if OP is a valid operand for the LA instruction.
2518 In 31-bit, we need to prove that the result is used as an
2519 address, as LA performs only a 31-bit addition. */
2522 legitimate_la_operand_p (register rtx op)
2524 struct s390_address addr;
2525 if (!s390_decompose_address (op, &addr))
2528 if (TARGET_64BIT || addr.pointer)
2534 /* Return 1 if it is valid *and* preferable to use LA to
2535 compute the sum of OP1 and OP2. */
2538 preferred_la_operand_p (rtx op1, rtx op2)
2540 struct s390_address addr;
2542 if (op2 != const0_rtx)
2543 op1 = gen_rtx_PLUS (Pmode, op1, op2);
2545 if (!s390_decompose_address (op1, &addr))
2547 if (addr.base && !REG_OK_FOR_BASE_STRICT_P (addr.base))
2549 if (addr.indx && !REG_OK_FOR_INDEX_STRICT_P (addr.indx))
2552 if (!TARGET_64BIT && !addr.pointer)
2558 if ((addr.base && REG_P (addr.base) && REG_POINTER (addr.base))
2559 || (addr.indx && REG_P (addr.indx) && REG_POINTER (addr.indx)))
2565 /* Emit a forced load-address operation to load SRC into DST.
2566 This will use the LOAD ADDRESS instruction even in situations
2567 where legitimate_la_operand_p (SRC) returns false. */
2570 s390_load_address (rtx dst, rtx src)
2573 emit_move_insn (dst, src);
2575 emit_insn (gen_force_la_31 (dst, src));
2578 /* Return a legitimate reference for ORIG (an address) using the
2579 register REG. If REG is 0, a new pseudo is generated.
2581 There are two types of references that must be handled:
2583 1. Global data references must load the address from the GOT, via
2584 the PIC reg. An insn is emitted to do this load, and the reg is
2587 2. Static data references, constant pool addresses, and code labels
2588 compute the address as an offset from the GOT, whose base is in
2589 the PIC reg. Static data objects have SYMBOL_FLAG_LOCAL set to
2590 differentiate them from global data objects. The returned
2591 address is the PIC reg + an unspec constant.
2593 GO_IF_LEGITIMATE_ADDRESS rejects symbolic references unless the PIC
2594 reg also appears in the address. */
2597 legitimize_pic_address (rtx orig, rtx reg)
2603 if (GET_CODE (addr) == LABEL_REF
2604 || (GET_CODE (addr) == SYMBOL_REF && SYMBOL_REF_LOCAL_P (addr)))
2606 /* This is a local symbol. */
2607 if (TARGET_CPU_ZARCH && larl_operand (addr, VOIDmode))
2609 /* Access local symbols PC-relative via LARL.
2610 This is the same as in the non-PIC case, so it is
2611 handled automatically ... */
2615 /* Access local symbols relative to the GOT. */
2617 rtx temp = reg? reg : gen_reg_rtx (Pmode);
2619 if (reload_in_progress || reload_completed)
2620 regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
2622 addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTOFF);
2623 addr = gen_rtx_CONST (Pmode, addr);
2624 addr = force_const_mem (Pmode, addr);
2625 emit_move_insn (temp, addr);
2627 new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, temp);
2630 s390_load_address (reg, new);
2635 else if (GET_CODE (addr) == SYMBOL_REF)
2638 reg = gen_reg_rtx (Pmode);
2642 /* Assume GOT offset < 4k. This is handled the same way
2643 in both 31- and 64-bit code (@GOT). */
2645 if (reload_in_progress || reload_completed)
2646 regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
2648 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOT);
2649 new = gen_rtx_CONST (Pmode, new);
2650 new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new);
2651 new = gen_const_mem (Pmode, new);
2652 emit_move_insn (reg, new);
2655 else if (TARGET_CPU_ZARCH)
2657 /* If the GOT offset might be >= 4k, we determine the position
2658 of the GOT entry via a PC-relative LARL (@GOTENT). */
2660 rtx temp = gen_reg_rtx (Pmode);
2662 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTENT);
2663 new = gen_rtx_CONST (Pmode, new);
2664 emit_move_insn (temp, new);
2666 new = gen_const_mem (Pmode, temp);
2667 emit_move_insn (reg, new);
2672 /* If the GOT offset might be >= 4k, we have to load it
2673 from the literal pool (@GOT). */
2675 rtx temp = gen_reg_rtx (Pmode);
2677 if (reload_in_progress || reload_completed)
2678 regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
2680 addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOT);
2681 addr = gen_rtx_CONST (Pmode, addr);
2682 addr = force_const_mem (Pmode, addr);
2683 emit_move_insn (temp, addr);
2685 new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, temp);
2686 new = gen_const_mem (Pmode, new);
2687 emit_move_insn (reg, new);
2693 if (GET_CODE (addr) == CONST)
2695 addr = XEXP (addr, 0);
2696 if (GET_CODE (addr) == UNSPEC)
2698 if (XVECLEN (addr, 0) != 1)
2700 switch (XINT (addr, 1))
2702 /* If someone moved a GOT-relative UNSPEC
2703 out of the literal pool, force them back in. */
2706 new = force_const_mem (Pmode, orig);
2709 /* @GOT is OK as is if small. */
2712 new = force_const_mem (Pmode, orig);
2715 /* @GOTENT is OK as is. */
2719 /* @PLT is OK as is on 64-bit, must be converted to
2720 GOT-relative @PLTOFF on 31-bit. */
2722 if (!TARGET_CPU_ZARCH)
2724 rtx temp = reg? reg : gen_reg_rtx (Pmode);
2726 if (reload_in_progress || reload_completed)
2727 regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
2729 addr = XVECEXP (addr, 0, 0);
2730 addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr),
2732 addr = gen_rtx_CONST (Pmode, addr);
2733 addr = force_const_mem (Pmode, addr);
2734 emit_move_insn (temp, addr);
2736 new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, temp);
2739 s390_load_address (reg, new);
2745 /* Everything else cannot happen. */
2750 else if (GET_CODE (addr) != PLUS)
2753 if (GET_CODE (addr) == PLUS)
2755 rtx op0 = XEXP (addr, 0), op1 = XEXP (addr, 1);
2756 /* Check first to see if this is a constant offset
2757 from a local symbol reference. */
2758 if ((GET_CODE (op0) == LABEL_REF
2759 || (GET_CODE (op0) == SYMBOL_REF && SYMBOL_REF_LOCAL_P (op0)))
2760 && GET_CODE (op1) == CONST_INT)
2762 if (TARGET_CPU_ZARCH && larl_operand (op0, VOIDmode))
2764 if (INTVAL (op1) & 1)
2766 /* LARL can't handle odd offsets, so emit a
2767 pair of LARL and LA. */
2768 rtx temp = reg? reg : gen_reg_rtx (Pmode);
2770 if (!DISP_IN_RANGE (INTVAL (op1)))
2772 int even = INTVAL (op1) - 1;
2773 op0 = gen_rtx_PLUS (Pmode, op0, GEN_INT (even));
2774 op0 = gen_rtx_CONST (Pmode, op0);
2778 emit_move_insn (temp, op0);
2779 new = gen_rtx_PLUS (Pmode, temp, op1);
2783 s390_load_address (reg, new);
2789 /* If the offset is even, we can just use LARL.
2790 This will happen automatically. */
2795 /* Access local symbols relative to the GOT. */
2797 rtx temp = reg? reg : gen_reg_rtx (Pmode);
2799 if (reload_in_progress || reload_completed)
2800 regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
2802 addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op0),
2804 addr = gen_rtx_PLUS (Pmode, addr, op1);
2805 addr = gen_rtx_CONST (Pmode, addr);
2806 addr = force_const_mem (Pmode, addr);
2807 emit_move_insn (temp, addr);
2809 new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, temp);
2812 s390_load_address (reg, new);
2818 /* Now, check whether it is a GOT relative symbol plus offset
2819 that was pulled out of the literal pool. Force it back in. */
2821 else if (GET_CODE (op0) == UNSPEC
2822 && GET_CODE (op1) == CONST_INT
2823 && XINT (op0, 1) == UNSPEC_GOTOFF)
2825 if (XVECLEN (op0, 0) != 1)
2828 new = force_const_mem (Pmode, orig);
2831 /* Otherwise, compute the sum. */
2834 base = legitimize_pic_address (XEXP (addr, 0), reg);
2835 new = legitimize_pic_address (XEXP (addr, 1),
2836 base == reg ? NULL_RTX : reg);
2837 if (GET_CODE (new) == CONST_INT)
2838 new = plus_constant (base, INTVAL (new));
2841 if (GET_CODE (new) == PLUS && CONSTANT_P (XEXP (new, 1)))
2843 base = gen_rtx_PLUS (Pmode, base, XEXP (new, 0));
2844 new = XEXP (new, 1);
2846 new = gen_rtx_PLUS (Pmode, base, new);
2849 if (GET_CODE (new) == CONST)
2850 new = XEXP (new, 0);
2851 new = force_operand (new, 0);
2858 /* Load the thread pointer into a register. */
2861 get_thread_pointer (void)
2863 rtx tp = gen_reg_rtx (Pmode);
2865 emit_move_insn (tp, gen_rtx_REG (Pmode, TP_REGNUM));
2866 mark_reg_pointer (tp, BITS_PER_WORD);
2871 /* Emit a tls call insn. The call target is the SYMBOL_REF stored
2872 in s390_tls_symbol which always refers to __tls_get_offset.
2873 The returned offset is written to RESULT_REG and an USE rtx is
2874 generated for TLS_CALL. */
2876 static GTY(()) rtx s390_tls_symbol;
2879 s390_emit_tls_call_insn (rtx result_reg, rtx tls_call)
2886 if (!s390_tls_symbol)
2887 s390_tls_symbol = gen_rtx_SYMBOL_REF (Pmode, "__tls_get_offset");
2889 insn = s390_emit_call (s390_tls_symbol, tls_call, result_reg,
2890 gen_rtx_REG (Pmode, RETURN_REGNUM));
2892 use_reg (&CALL_INSN_FUNCTION_USAGE (insn), result_reg);
2893 CONST_OR_PURE_CALL_P (insn) = 1;
2896 /* ADDR contains a thread-local SYMBOL_REF. Generate code to compute
2897 this (thread-local) address. REG may be used as temporary. */
2900 legitimize_tls_address (rtx addr, rtx reg)
2902 rtx new, tls_call, temp, base, r2, insn;
2904 if (GET_CODE (addr) == SYMBOL_REF)
2905 switch (tls_symbolic_operand (addr))
2907 case TLS_MODEL_GLOBAL_DYNAMIC:
2909 r2 = gen_rtx_REG (Pmode, 2);
2910 tls_call = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_TLSGD);
2911 new = gen_rtx_CONST (Pmode, tls_call);
2912 new = force_const_mem (Pmode, new);
2913 emit_move_insn (r2, new);
2914 s390_emit_tls_call_insn (r2, tls_call);
2915 insn = get_insns ();
2918 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_NTPOFF);
2919 temp = gen_reg_rtx (Pmode);
2920 emit_libcall_block (insn, temp, r2, new);
2922 new = gen_rtx_PLUS (Pmode, get_thread_pointer (), temp);
2925 s390_load_address (reg, new);
2930 case TLS_MODEL_LOCAL_DYNAMIC:
2932 r2 = gen_rtx_REG (Pmode, 2);
2933 tls_call = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, const0_rtx), UNSPEC_TLSLDM);
2934 new = gen_rtx_CONST (Pmode, tls_call);
2935 new = force_const_mem (Pmode, new);
2936 emit_move_insn (r2, new);
2937 s390_emit_tls_call_insn (r2, tls_call);
2938 insn = get_insns ();
2941 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, const0_rtx), UNSPEC_TLSLDM_NTPOFF);
2942 temp = gen_reg_rtx (Pmode);
2943 emit_libcall_block (insn, temp, r2, new);
2945 new = gen_rtx_PLUS (Pmode, get_thread_pointer (), temp);
2946 base = gen_reg_rtx (Pmode);
2947 s390_load_address (base, new);
2949 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_DTPOFF);
2950 new = gen_rtx_CONST (Pmode, new);
2951 new = force_const_mem (Pmode, new);
2952 temp = gen_reg_rtx (Pmode);
2953 emit_move_insn (temp, new);
2955 new = gen_rtx_PLUS (Pmode, base, temp);
2958 s390_load_address (reg, new);
2963 case TLS_MODEL_INITIAL_EXEC:
2966 /* Assume GOT offset < 4k. This is handled the same way
2967 in both 31- and 64-bit code. */
2969 if (reload_in_progress || reload_completed)
2970 regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
2972 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTNTPOFF);
2973 new = gen_rtx_CONST (Pmode, new);
2974 new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new);
2975 new = gen_const_mem (Pmode, new);
2976 temp = gen_reg_rtx (Pmode);
2977 emit_move_insn (temp, new);
2979 else if (TARGET_CPU_ZARCH)
2981 /* If the GOT offset might be >= 4k, we determine the position
2982 of the GOT entry via a PC-relative LARL. */
2984 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_INDNTPOFF);
2985 new = gen_rtx_CONST (Pmode, new);
2986 temp = gen_reg_rtx (Pmode);
2987 emit_move_insn (temp, new);
2989 new = gen_const_mem (Pmode, temp);
2990 temp = gen_reg_rtx (Pmode);
2991 emit_move_insn (temp, new);
2995 /* If the GOT offset might be >= 4k, we have to load it
2996 from the literal pool. */
2998 if (reload_in_progress || reload_completed)
2999 regs_ever_live[PIC_OFFSET_TABLE_REGNUM] = 1;
3001 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTNTPOFF);
3002 new = gen_rtx_CONST (Pmode, new);
3003 new = force_const_mem (Pmode, new);
3004 temp = gen_reg_rtx (Pmode);
3005 emit_move_insn (temp, new);
3007 new = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, temp);
3008 new = gen_const_mem (Pmode, new);
3010 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, new, addr), UNSPEC_TLS_LOAD);
3011 temp = gen_reg_rtx (Pmode);
3012 emit_insn (gen_rtx_SET (Pmode, temp, new));
3016 /* In position-dependent code, load the absolute address of
3017 the GOT entry from the literal pool. */
3019 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_INDNTPOFF);
3020 new = gen_rtx_CONST (Pmode, new);
3021 new = force_const_mem (Pmode, new);
3022 temp = gen_reg_rtx (Pmode);
3023 emit_move_insn (temp, new);
3026 new = gen_const_mem (Pmode, new);
3027 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, new, addr), UNSPEC_TLS_LOAD);
3028 temp = gen_reg_rtx (Pmode);
3029 emit_insn (gen_rtx_SET (Pmode, temp, new));
3032 new = gen_rtx_PLUS (Pmode, get_thread_pointer (), temp);
3035 s390_load_address (reg, new);
3040 case TLS_MODEL_LOCAL_EXEC:
3041 new = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_NTPOFF);
3042 new = gen_rtx_CONST (Pmode, new);
3043 new = force_const_mem (Pmode, new);
3044 temp = gen_reg_rtx (Pmode);
3045 emit_move_insn (temp, new);
3047 new = gen_rtx_PLUS (Pmode, get_thread_pointer (), temp);
3050 s390_load_address (reg, new);
3059 else if (GET_CODE (addr) == CONST && GET_CODE (XEXP (addr, 0)) == UNSPEC)
3061 switch (XINT (XEXP (addr, 0), 1))
3063 case UNSPEC_INDNTPOFF:
3064 if (TARGET_CPU_ZARCH)
3075 else if (GET_CODE (addr) == CONST && GET_CODE (XEXP (addr, 0)) == PLUS
3076 && GET_CODE (XEXP (XEXP (addr, 0), 1)) == CONST_INT)
3078 new = XEXP (XEXP (addr, 0), 0);
3079 if (GET_CODE (new) != SYMBOL_REF)
3080 new = gen_rtx_CONST (Pmode, new);
3082 new = legitimize_tls_address (new, reg);
3083 new = plus_constant (new, INTVAL (XEXP (XEXP (addr, 0), 1)));
3084 new = force_operand (new, 0);
3088 abort (); /* for now ... */
3093 /* Emit insns to move operands[1] into operands[0]. */
3096 emit_symbolic_move (rtx *operands)
3098 rtx temp = no_new_pseudos ? operands[0] : gen_reg_rtx (Pmode);
3100 if (GET_CODE (operands[0]) == MEM)
3101 operands[1] = force_reg (Pmode, operands[1]);
3102 else if (TLS_SYMBOLIC_CONST (operands[1]))
3103 operands[1] = legitimize_tls_address (operands[1], temp);
3105 operands[1] = legitimize_pic_address (operands[1], temp);
3108 /* Try machine-dependent ways of modifying an illegitimate address X
3109 to be legitimate. If we find one, return the new, valid address.
3111 OLDX is the address as it was before break_out_memory_refs was called.
3112 In some cases it is useful to look at this to decide what needs to be done.
3114 MODE is the mode of the operand pointed to by X.
3116 When -fpic is used, special handling is needed for symbolic references.
3117 See comments by legitimize_pic_address for details. */
3120 legitimize_address (register rtx x, register rtx oldx ATTRIBUTE_UNUSED,
3121 enum machine_mode mode ATTRIBUTE_UNUSED)
3123 rtx constant_term = const0_rtx;
3125 if (TLS_SYMBOLIC_CONST (x))
3127 x = legitimize_tls_address (x, 0);
3129 if (legitimate_address_p (mode, x, FALSE))
3134 if (SYMBOLIC_CONST (x)
3135 || (GET_CODE (x) == PLUS
3136 && (SYMBOLIC_CONST (XEXP (x, 0))
3137 || SYMBOLIC_CONST (XEXP (x, 1)))))
3138 x = legitimize_pic_address (x, 0);
3140 if (legitimate_address_p (mode, x, FALSE))
3144 x = eliminate_constant_term (x, &constant_term);
3146 /* Optimize loading of large displacements by splitting them
3147 into the multiple of 4K and the rest; this allows the
3148 former to be CSE'd if possible.
3150 Don't do this if the displacement is added to a register
3151 pointing into the stack frame, as the offsets will
3152 change later anyway. */
3154 if (GET_CODE (constant_term) == CONST_INT
3155 && !TARGET_LONG_DISPLACEMENT
3156 && !DISP_IN_RANGE (INTVAL (constant_term))
3157 && !(REG_P (x) && REGNO_PTR_FRAME_P (REGNO (x))))
3159 HOST_WIDE_INT lower = INTVAL (constant_term) & 0xfff;
3160 HOST_WIDE_INT upper = INTVAL (constant_term) ^ lower;
3162 rtx temp = gen_reg_rtx (Pmode);
3163 rtx val = force_operand (GEN_INT (upper), temp);
3165 emit_move_insn (temp, val);
3167 x = gen_rtx_PLUS (Pmode, x, temp);
3168 constant_term = GEN_INT (lower);
3171 if (GET_CODE (x) == PLUS)
3173 if (GET_CODE (XEXP (x, 0)) == REG)
3175 register rtx temp = gen_reg_rtx (Pmode);
3176 register rtx val = force_operand (XEXP (x, 1), temp);
3178 emit_move_insn (temp, val);
3180 x = gen_rtx_PLUS (Pmode, XEXP (x, 0), temp);
3183 else if (GET_CODE (XEXP (x, 1)) == REG)
3185 register rtx temp = gen_reg_rtx (Pmode);
3186 register rtx val = force_operand (XEXP (x, 0), temp);
3188 emit_move_insn (temp, val);
3190 x = gen_rtx_PLUS (Pmode, temp, XEXP (x, 1));
3194 if (constant_term != const0_rtx)
3195 x = gen_rtx_PLUS (Pmode, x, constant_term);
3200 /* Try a machine-dependent way of reloading an illegitimate address AD
3201 operand. If we find one, push the reload and and return the new address.
3203 MODE is the mode of the enclosing MEM. OPNUM is the operand number
3204 and TYPE is the reload type of the current reload. */
3207 legitimize_reload_address (rtx ad, enum machine_mode mode ATTRIBUTE_UNUSED,
3208 int opnum, int type)
3210 if (!optimize || TARGET_LONG_DISPLACEMENT)
3213 if (GET_CODE (ad) == PLUS)
3215 rtx tem = simplify_binary_operation (PLUS, Pmode,
3216 XEXP (ad, 0), XEXP (ad, 1));
3221 if (GET_CODE (ad) == PLUS
3222 && GET_CODE (XEXP (ad, 0)) == REG
3223 && GET_CODE (XEXP (ad, 1)) == CONST_INT
3224 && !DISP_IN_RANGE (INTVAL (XEXP (ad, 1))))
3226 HOST_WIDE_INT lower = INTVAL (XEXP (ad, 1)) & 0xfff;
3227 HOST_WIDE_INT upper = INTVAL (XEXP (ad, 1)) ^ lower;
3230 cst = GEN_INT (upper);
3231 if (!legitimate_reload_constant_p (cst))
3232 cst = force_const_mem (Pmode, cst);
3234 tem = gen_rtx_PLUS (Pmode, XEXP (ad, 0), cst);
3235 new = gen_rtx_PLUS (Pmode, tem, GEN_INT (lower));
3237 push_reload (XEXP (tem, 1), 0, &XEXP (tem, 1), 0,
3238 BASE_REG_CLASS, Pmode, VOIDmode, 0, 0,
3239 opnum, (enum reload_type) type);
3246 /* Emit code to move LEN bytes from DST to SRC. */
3249 s390_expand_movmem (rtx dst, rtx src, rtx len)
3251 if (GET_CODE (len) == CONST_INT && INTVAL (len) >= 0 && INTVAL (len) <= 256)
3253 if (INTVAL (len) > 0)
3254 emit_insn (gen_movmem_short (dst, src, GEN_INT (INTVAL (len) - 1)));
3257 else if (TARGET_MVCLE)
3259 emit_insn (gen_movmem_long (dst, src, convert_to_mode (Pmode, len, 1)));
3264 rtx dst_addr, src_addr, count, blocks, temp;
3265 rtx loop_start_label = gen_label_rtx ();
3266 rtx loop_end_label = gen_label_rtx ();
3267 rtx end_label = gen_label_rtx ();
3268 enum machine_mode mode;
3270 mode = GET_MODE (len);
3271 if (mode == VOIDmode)
3274 dst_addr = gen_reg_rtx (Pmode);
3275 src_addr = gen_reg_rtx (Pmode);
3276 count = gen_reg_rtx (mode);
3277 blocks = gen_reg_rtx (mode);
3279 convert_move (count, len, 1);
3280 emit_cmp_and_jump_insns (count, const0_rtx,
3281 EQ, NULL_RTX, mode, 1, end_label);
3283 emit_move_insn (dst_addr, force_operand (XEXP (dst, 0), NULL_RTX));
3284 emit_move_insn (src_addr, force_operand (XEXP (src, 0), NULL_RTX));
3285 dst = change_address (dst, VOIDmode, dst_addr);
3286 src = change_address (src, VOIDmode, src_addr);
3288 temp = expand_binop (mode, add_optab, count, constm1_rtx, count, 1, 0);
3290 emit_move_insn (count, temp);
3292 temp = expand_binop (mode, ashr_optab, count, GEN_INT (8), blocks, 1, 0);
3294 emit_move_insn (blocks, temp);
3296 emit_cmp_and_jump_insns (blocks, const0_rtx,
3297 EQ, NULL_RTX, mode, 1, loop_end_label);
3299 emit_label (loop_start_label);
3301 emit_insn (gen_movmem_short (dst, src, GEN_INT (255)));
3302 s390_load_address (dst_addr,
3303 gen_rtx_PLUS (Pmode, dst_addr, GEN_INT (256)));
3304 s390_load_address (src_addr,
3305 gen_rtx_PLUS (Pmode, src_addr, GEN_INT (256)));
3307 temp = expand_binop (mode, add_optab, blocks, constm1_rtx, blocks, 1, 0);
3309 emit_move_insn (blocks, temp);
3311 emit_cmp_and_jump_insns (blocks, const0_rtx,
3312 EQ, NULL_RTX, mode, 1, loop_end_label);
3314 emit_jump (loop_start_label);
3315 emit_label (loop_end_label);
3317 emit_insn (gen_movmem_short (dst, src,
3318 convert_to_mode (Pmode, count, 1)));
3319 emit_label (end_label);
3323 /* Emit code to clear LEN bytes at DST. */
3326 s390_expand_clrmem (rtx dst, rtx len)
3328 if (GET_CODE (len) == CONST_INT && INTVAL (len) >= 0 && INTVAL (len) <= 256)
3330 if (INTVAL (len) > 0)
3331 emit_insn (gen_clrmem_short (dst, GEN_INT (INTVAL (len) - 1)));
3334 else if (TARGET_MVCLE)
3336 emit_insn (gen_clrmem_long (dst, convert_to_mode (Pmode, len, 1)));
3341 rtx dst_addr, src_addr, count, blocks, temp;
3342 rtx loop_start_label = gen_label_rtx ();
3343 rtx loop_end_label = gen_label_rtx ();
3344 rtx end_label = gen_label_rtx ();
3345 enum machine_mode mode;
3347 mode = GET_MODE (len);
3348 if (mode == VOIDmode)
3351 dst_addr = gen_reg_rtx (Pmode);
3352 src_addr = gen_reg_rtx (Pmode);
3353 count = gen_reg_rtx (mode);
3354 blocks = gen_reg_rtx (mode);
3356 convert_move (count, len, 1);
3357 emit_cmp_and_jump_insns (count, const0_rtx,
3358 EQ, NULL_RTX, mode, 1, end_label);
3360 emit_move_insn (dst_addr, force_operand (XEXP (dst, 0), NULL_RTX));
3361 dst = change_address (dst, VOIDmode, dst_addr);
3363 temp = expand_binop (mode, add_optab, count, constm1_rtx, count, 1, 0);
3365 emit_move_insn (count, temp);
3367 temp = expand_binop (mode, ashr_optab, count, GEN_INT (8), blocks, 1, 0);
3369 emit_move_insn (blocks, temp);
3371 emit_cmp_and_jump_insns (blocks, const0_rtx,
3372 EQ, NULL_RTX, mode, 1, loop_end_label);
3374 emit_label (loop_start_label);
3376 emit_insn (gen_clrmem_short (dst, GEN_INT (255)));
3377 s390_load_address (dst_addr,
3378 gen_rtx_PLUS (Pmode, dst_addr, GEN_INT (256)));
3380 temp = expand_binop (mode, add_optab, blocks, constm1_rtx, blocks, 1, 0);
3382 emit_move_insn (blocks, temp);
3384 emit_cmp_and_jump_insns (blocks, const0_rtx,
3385 EQ, NULL_RTX, mode, 1, loop_end_label);
3387 emit_jump (loop_start_label);
3388 emit_label (loop_end_label);
3390 emit_insn (gen_clrmem_short (dst, convert_to_mode (Pmode, count, 1)));
3391 emit_label (end_label);
3395 /* Emit code to compare LEN bytes at OP0 with those at OP1,
3396 and return the result in TARGET. */
3399 s390_expand_cmpmem (rtx target, rtx op0, rtx op1, rtx len)
3401 rtx ccreg = gen_rtx_REG (CCUmode, CC_REGNUM);
3404 /* As the result of CMPINT is inverted compared to what we need,
3405 we have to swap the operands. */
3406 tmp = op0; op0 = op1; op1 = tmp;
3408 if (GET_CODE (len) == CONST_INT && INTVAL (len) >= 0 && INTVAL (len) <= 256)
3410 if (INTVAL (len) > 0)
3412 emit_insn (gen_cmpmem_short (op0, op1, GEN_INT (INTVAL (len) - 1)));
3413 emit_insn (gen_cmpint (target, ccreg));
3416 emit_move_insn (target, const0_rtx);
3418 else if (TARGET_MVCLE)
3420 emit_insn (gen_cmpmem_long (op0, op1, convert_to_mode (Pmode, len, 1)));
3421 emit_insn (gen_cmpint (target, ccreg));
3425 rtx addr0, addr1, count, blocks, temp;
3426 rtx loop_start_label = gen_label_rtx ();
3427 rtx loop_end_label = gen_label_rtx ();
3428 rtx end_label = gen_label_rtx ();
3429 enum machine_mode mode;
3431 mode = GET_MODE (len);
3432 if (mode == VOIDmode)
3435 addr0 = gen_reg_rtx (Pmode);
3436 addr1 = gen_reg_rtx (Pmode);
3437 count = gen_reg_rtx (mode);
3438 blocks = gen_reg_rtx (mode);
3440 convert_move (count, len, 1);
3441 emit_cmp_and_jump_insns (count, const0_rtx,
3442 EQ, NULL_RTX, mode, 1, end_label);
3444 emit_move_insn (addr0, force_operand (XEXP (op0, 0), NULL_RTX));
3445 emit_move_insn (addr1, force_operand (XEXP (op1, 0), NULL_RTX));
3446 op0 = change_address (op0, VOIDmode, addr0);
3447 op1 = change_address (op1, VOIDmode, addr1);
3449 temp = expand_binop (mode, add_optab, count, constm1_rtx, count, 1, 0);
3451 emit_move_insn (count, temp);
3453 temp = expand_binop (mode, ashr_optab, count, GEN_INT (8), blocks, 1, 0);
3455 emit_move_insn (blocks, temp);
3457 emit_cmp_and_jump_insns (blocks, const0_rtx,
3458 EQ, NULL_RTX, mode, 1, loop_end_label);
3460 emit_label (loop_start_label);
3462 emit_insn (gen_cmpmem_short (op0, op1, GEN_INT (255)));
3463 temp = gen_rtx_NE (VOIDmode, ccreg, const0_rtx);
3464 temp = gen_rtx_IF_THEN_ELSE (VOIDmode, temp,
3465 gen_rtx_LABEL_REF (VOIDmode, end_label), pc_rtx);
3466 temp = gen_rtx_SET (VOIDmode, pc_rtx, temp);
3467 emit_jump_insn (temp);
3469 s390_load_address (addr0,
3470 gen_rtx_PLUS (Pmode, addr0, GEN_INT (256)));
3471 s390_load_address (addr1,
3472 gen_rtx_PLUS (Pmode, addr1, GEN_INT (256)));
3474 temp = expand_binop (mode, add_optab, blocks, constm1_rtx, blocks, 1, 0);
3476 emit_move_insn (blocks, temp);
3478 emit_cmp_and_jump_insns (blocks, const0_rtx,
3479 EQ, NULL_RTX, mode, 1, loop_end_label);
3481 emit_jump (loop_start_label);
3482 emit_label (loop_end_label);
3484 emit_insn (gen_cmpmem_short (op0, op1,
3485 convert_to_mode (Pmode, count, 1)));
3486 emit_label (end_label);
3488 emit_insn (gen_cmpint (target, ccreg));
3493 /* Expand conditional increment or decrement using alc/slb instructions.
3494 Should generate code setting DST to either SRC or SRC + INCREMENT,
3495 depending on the result of the comparison CMP_OP0 CMP_CODE CMP_OP1.
3496 Returns true if successful, false otherwise.
3498 That makes it possible to implement some if-constructs without jumps e.g.:
3499 (borrow = CC0 | CC1 and carry = CC2 | CC3)
3500 unsigned int a, b, c;
3501 if (a < b) c++; -> CCU b > a -> CC2; c += carry;
3502 if (a < b) c--; -> CCL3 a - b -> borrow; c -= borrow;
3503 if (a <= b) c++; -> CCL3 b - a -> borrow; c += carry;
3504 if (a <= b) c--; -> CCU a <= b -> borrow; c -= borrow;
3506 Checks for EQ and NE with a nonzero value need an additional xor e.g.:
3507 if (a == b) c++; -> CCL3 a ^= b; 0 - a -> borrow; c += carry;
3508 if (a == b) c--; -> CCU a ^= b; a <= 0 -> CC0 | CC1; c -= borrow;
3509 if (a != b) c++; -> CCU a ^= b; a > 0 -> CC2; c += carry;
3510 if (a != b) c--; -> CCL3 a ^= b; 0 - a -> borrow; c -= borrow; */
3513 s390_expand_addcc (enum rtx_code cmp_code, rtx cmp_op0, rtx cmp_op1,
3514 rtx dst, rtx src, rtx increment)
3516 enum machine_mode cmp_mode;
3517 enum machine_mode cc_mode;
3522 if ((GET_MODE (cmp_op0) == SImode || GET_MODE (cmp_op0) == VOIDmode)
3523 && (GET_MODE (cmp_op1) == SImode || GET_MODE (cmp_op1) == VOIDmode))
3525 else if ((GET_MODE (cmp_op0) == DImode || GET_MODE (cmp_op0) == VOIDmode)
3526 && (GET_MODE (cmp_op1) == DImode || GET_MODE (cmp_op1) == VOIDmode))
3531 /* Try ADD LOGICAL WITH CARRY. */
3532 if (increment == const1_rtx)
3534 /* Determine CC mode to use. */
3535 if (cmp_code == EQ || cmp_code == NE)
3537 if (cmp_op1 != const0_rtx)
3539 cmp_op0 = expand_simple_binop (cmp_mode, XOR, cmp_op0, cmp_op1,
3540 NULL_RTX, 0, OPTAB_WIDEN);
3541 cmp_op1 = const0_rtx;
3544 cmp_code = cmp_code == EQ ? LEU : GTU;
3547 if (cmp_code == LTU || cmp_code == LEU)
3552 cmp_code = swap_condition (cmp_code);
3569 /* Emit comparison instruction pattern. */
3570 if (!register_operand (cmp_op0, cmp_mode))
3571 cmp_op0 = force_reg (cmp_mode, cmp_op0);
3573 insn = gen_rtx_SET (VOIDmode, gen_rtx_REG (cc_mode, CC_REGNUM),
3574 gen_rtx_COMPARE (cc_mode, cmp_op0, cmp_op1));
3575 /* We use insn_invalid_p here to add clobbers if required. */
3576 if (insn_invalid_p (emit_insn (insn)))
3579 /* Emit ALC instruction pattern. */
3580 op_res = gen_rtx_fmt_ee (cmp_code, GET_MODE (dst),
3581 gen_rtx_REG (cc_mode, CC_REGNUM),
3584 if (src != const0_rtx)
3586 if (!register_operand (src, GET_MODE (dst)))
3587 src = force_reg (GET_MODE (dst), src);
3589 src = gen_rtx_PLUS (GET_MODE (dst), src, const0_rtx);
3590 op_res = gen_rtx_PLUS (GET_MODE (dst), src, op_res);
3593 p = rtvec_alloc (2);
3595 gen_rtx_SET (VOIDmode, dst, op_res);
3597 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, CC_REGNUM));
3598 emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
3603 /* Try SUBTRACT LOGICAL WITH BORROW. */
3604 if (increment == constm1_rtx)
3606 /* Determine CC mode to use. */
3607 if (cmp_code == EQ || cmp_code == NE)
3609 if (cmp_op1 != const0_rtx)
3611 cmp_op0 = expand_simple_binop (cmp_mode, XOR, cmp_op0, cmp_op1,
3612 NULL_RTX, 0, OPTAB_WIDEN);
3613 cmp_op1 = const0_rtx;
3616 cmp_code = cmp_code == EQ ? LEU : GTU;
3619 if (cmp_code == GTU || cmp_code == GEU)
3624 cmp_code = swap_condition (cmp_code);
3641 /* Emit comparison instruction pattern. */
3642 if (!register_operand (cmp_op0, cmp_mode))
3643 cmp_op0 = force_reg (cmp_mode, cmp_op0);
3645 insn = gen_rtx_SET (VOIDmode, gen_rtx_REG (cc_mode, CC_REGNUM),
3646 gen_rtx_COMPARE (cc_mode, cmp_op0, cmp_op1));
3647 /* We use insn_invalid_p here to add clobbers if required. */
3648 if (insn_invalid_p (emit_insn (insn)))
3651 /* Emit SLB instruction pattern. */
3652 if (!register_operand (src, GET_MODE (dst)))
3653 src = force_reg (GET_MODE (dst), src);
3655 op_res = gen_rtx_MINUS (GET_MODE (dst),
3656 gen_rtx_MINUS (GET_MODE (dst), src, const0_rtx),
3657 gen_rtx_fmt_ee (cmp_code, GET_MODE (dst),
3658 gen_rtx_REG (cc_mode, CC_REGNUM),
3660 p = rtvec_alloc (2);
3662 gen_rtx_SET (VOIDmode, dst, op_res);
3664 gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, CC_REGNUM));
3665 emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
3674 /* This is called from dwarf2out.c via ASM_OUTPUT_DWARF_DTPREL.
3675 We need to emit DTP-relative relocations. */
3678 s390_output_dwarf_dtprel (FILE *file, int size, rtx x)
3683 fputs ("\t.long\t", file);
3686 fputs ("\t.quad\t", file);
3691 output_addr_const (file, x);
3692 fputs ("@DTPOFF", file);
3695 /* In the name of slightly smaller debug output, and to cater to
3696 general assembler lossage, recognize various UNSPEC sequences
3697 and turn them back into a direct symbol reference. */
3700 s390_delegitimize_address (rtx orig_x)
3704 if (GET_CODE (x) != MEM)
3708 if (GET_CODE (x) == PLUS
3709 && GET_CODE (XEXP (x, 1)) == CONST
3710 && GET_CODE (XEXP (x, 0)) == REG
3711 && REGNO (XEXP (x, 0)) == PIC_OFFSET_TABLE_REGNUM)
3713 y = XEXP (XEXP (x, 1), 0);
3714 if (GET_CODE (y) == UNSPEC
3715 && XINT (y, 1) == UNSPEC_GOT)
3716 return XVECEXP (y, 0, 0);
3720 if (GET_CODE (x) == CONST)
3723 if (GET_CODE (y) == UNSPEC
3724 && XINT (y, 1) == UNSPEC_GOTENT)
3725 return XVECEXP (y, 0, 0);
3732 /* Output shift count operand OP to stdio stream FILE. */
3735 print_shift_count_operand (FILE *file, rtx op)
3737 HOST_WIDE_INT offset = 0;
3739 /* We can have an integer constant, an address register,
3740 or a sum of the two. */
3741 if (GET_CODE (op) == CONST_INT)
3743 offset = INTVAL (op);
3746 if (op && GET_CODE (op) == PLUS && GET_CODE (XEXP (op, 1)) == CONST_INT)
3748 offset = INTVAL (XEXP (op, 1));
3751 while (op && GET_CODE (op) == SUBREG)
3752 op = SUBREG_REG (op);
3755 if (op && (GET_CODE (op) != REG
3756 || REGNO (op) >= FIRST_PSEUDO_REGISTER
3757 || REGNO_REG_CLASS (REGNO (op)) != ADDR_REGS))
3760 /* Shift counts are truncated to the low six bits anyway. */
3761 fprintf (file, HOST_WIDE_INT_PRINT_DEC, offset & 63);
3763 fprintf (file, "(%s)", reg_names[REGNO (op)]);
3766 /* Locate some local-dynamic symbol still in use by this function
3767 so that we can print its name in local-dynamic base patterns. */
3770 get_some_local_dynamic_name (void)
3774 if (cfun->machine->some_ld_name)
3775 return cfun->machine->some_ld_name;
3777 for (insn = get_insns (); insn ; insn = NEXT_INSN (insn))
3779 && for_each_rtx (&PATTERN (insn), get_some_local_dynamic_name_1, 0))
3780 return cfun->machine->some_ld_name;
3786 get_some_local_dynamic_name_1 (rtx *px, void *data ATTRIBUTE_UNUSED)
3790 if (GET_CODE (x) == SYMBOL_REF && CONSTANT_POOL_ADDRESS_P (x))
3792 x = get_pool_constant (x);
3793 return for_each_rtx (&x, get_some_local_dynamic_name_1, 0);
3796 if (GET_CODE (x) == SYMBOL_REF
3797 && tls_symbolic_operand (x) == TLS_MODEL_LOCAL_DYNAMIC)
3799 cfun->machine->some_ld_name = XSTR (x, 0);
3806 /* Output machine-dependent UNSPECs occurring in address constant X
3807 in assembler syntax to stdio stream FILE. Returns true if the
3808 constant X could be recognized, false otherwise. */
3811 s390_output_addr_const_extra (FILE *file, rtx x)
3813 if (GET_CODE (x) == UNSPEC && XVECLEN (x, 0) == 1)
3814 switch (XINT (x, 1))
3817 output_addr_const (file, XVECEXP (x, 0, 0));
3818 fprintf (file, "@GOTENT");
3821 output_addr_const (file, XVECEXP (x, 0, 0));
3822 fprintf (file, "@GOT");
3825 output_addr_const (file, XVECEXP (x, 0, 0));
3826 fprintf (file, "@GOTOFF");
3829 output_addr_const (file, XVECEXP (x, 0, 0));
3830 fprintf (file, "@PLT");
3833 output_addr_const (file, XVECEXP (x, 0, 0));
3834 fprintf (file, "@PLTOFF");
3837 output_addr_const (file, XVECEXP (x, 0, 0));
3838 fprintf (file, "@TLSGD");
3841 assemble_name (file, get_some_local_dynamic_name ());
3842 fprintf (file, "@TLSLDM");
3845 output_addr_const (file, XVECEXP (x, 0, 0));
3846 fprintf (file, "@DTPOFF");
3849 output_addr_const (file, XVECEXP (x, 0, 0));
3850 fprintf (file, "@NTPOFF");
3852 case UNSPEC_GOTNTPOFF:
3853 output_addr_const (file, XVECEXP (x, 0, 0));
3854 fprintf (file, "@GOTNTPOFF");
3856 case UNSPEC_INDNTPOFF:
3857 output_addr_const (file, XVECEXP (x, 0, 0));
3858 fprintf (file, "@INDNTPOFF");
3865 /* Output address operand ADDR in assembler syntax to
3866 stdio stream FILE. */
3869 print_operand_address (FILE *file, rtx addr)
3871 struct s390_address ad;
3873 if (!s390_decompose_address (addr, &ad)
3874 || (ad.base && !REG_OK_FOR_BASE_STRICT_P (ad.base))
3875 || (ad.indx && !REG_OK_FOR_INDEX_STRICT_P (ad.indx)))
3876 output_operand_lossage ("Cannot decompose address.");
3879 output_addr_const (file, ad.disp);
3881 fprintf (file, "0");
3883 if (ad.base && ad.indx)
3884 fprintf (file, "(%s,%s)", reg_names[REGNO (ad.indx)],
3885 reg_names[REGNO (ad.base)]);
3887 fprintf (file, "(%s)", reg_names[REGNO (ad.base)]);
3890 /* Output operand X in assembler syntax to stdio stream FILE.
3891 CODE specified the format flag. The following format flags
3894 'C': print opcode suffix for branch condition.
3895 'D': print opcode suffix for inverse branch condition.
3896 'J': print tls_load/tls_gdcall/tls_ldcall suffix
3897 'O': print only the displacement of a memory reference.
3898 'R': print only the base register of a memory reference.
3899 'S': print S-type memory reference (base+displacement).
3900 'N': print the second word of a DImode operand.
3901 'M': print the second word of a TImode operand.
3902 'Y': print shift count operand.
3904 'b': print integer X as if it's an unsigned byte.
3905 'x': print integer X as if it's an unsigned word.
3906 'h': print integer X as if it's a signed word.
3907 'i': print the first nonzero HImode part of X.
3908 'j': print the first HImode part unequal to 0xffff of X. */
3911 print_operand (FILE *file, rtx x, int code)
3916 fprintf (file, s390_branch_condition_mnemonic (x, FALSE));
3920 fprintf (file, s390_branch_condition_mnemonic (x, TRUE));
3924 if (GET_CODE (x) == SYMBOL_REF)
3926 fprintf (file, "%s", ":tls_load:");
3927 output_addr_const (file, x);
3929 else if (GET_CODE (x) == UNSPEC && XINT (x, 1) == UNSPEC_TLSGD)
3931 fprintf (file, "%s", ":tls_gdcall:");
3932 output_addr_const (file, XVECEXP (x, 0, 0));
3934 else if (GET_CODE (x) == UNSPEC && XINT (x, 1) == UNSPEC_TLSLDM)
3936 fprintf (file, "%s", ":tls_ldcall:");
3937 assemble_name (file, get_some_local_dynamic_name ());
3945 struct s390_address ad;
3947 if (GET_CODE (x) != MEM
3948 || !s390_decompose_address (XEXP (x, 0), &ad)
3949 || (ad.base && !REG_OK_FOR_BASE_STRICT_P (ad.base))
3954 output_addr_const (file, ad.disp);
3956 fprintf (file, "0");
3962 struct s390_address ad;
3964 if (GET_CODE (x) != MEM
3965 || !s390_decompose_address (XEXP (x, 0), &ad)
3966 || (ad.base && !REG_OK_FOR_BASE_STRICT_P (ad.base))
3971 fprintf (file, "%s", reg_names[REGNO (ad.base)]);
3973 fprintf (file, "0");
3979 struct s390_address ad;
3981 if (GET_CODE (x) != MEM
3982 || !s390_decompose_address (XEXP (x, 0), &ad)
3983 || (ad.base && !REG_OK_FOR_BASE_STRICT_P (ad.base))
3988 output_addr_const (file, ad.disp);
3990 fprintf (file, "0");
3993 fprintf (file, "(%s)", reg_names[REGNO (ad.base)]);
3998 if (GET_CODE (x) == REG)
3999 x = gen_rtx_REG (GET_MODE (x), REGNO (x) + 1);
4000 else if (GET_CODE (x) == MEM)
4001 x = change_address (x, VOIDmode, plus_constant (XEXP (x, 0), 4));
4007 if (GET_CODE (x) == REG)
4008 x = gen_rtx_REG (GET_MODE (x), REGNO (x) + 1);
4009 else if (GET_CODE (x) == MEM)
4010 x = change_address (x, VOIDmode, plus_constant (XEXP (x, 0), 8));
4016 print_shift_count_operand (file, x);
4020 switch (GET_CODE (x))
4023 fprintf (file, "%s", reg_names[REGNO (x)]);
4027 output_address (XEXP (x, 0));
4034 output_addr_const (file, x);
4039 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x) & 0xff);
4040 else if (code == 'x')
4041 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x) & 0xffff);
4042 else if (code == 'h')
4043 fprintf (file, HOST_WIDE_INT_PRINT_DEC, ((INTVAL (x) & 0xffff) ^ 0x8000) - 0x8000);
4044 else if (code == 'i')
4045 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
4046 s390_extract_part (x, HImode, 0));
4047 else if (code == 'j')
4048 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
4049 s390_extract_part (x, HImode, -1));
4051 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x));
4055 if (GET_MODE (x) != VOIDmode)
4058 fprintf (file, HOST_WIDE_INT_PRINT_DEC, CONST_DOUBLE_LOW (x) & 0xff);
4059 else if (code == 'x')
4060 fprintf (file, HOST_WIDE_INT_PRINT_DEC, CONST_DOUBLE_LOW (x) & 0xffff);
4061 else if (code == 'h')
4062 fprintf (file, HOST_WIDE_INT_PRINT_DEC, ((CONST_DOUBLE_LOW (x) & 0xffff) ^ 0x8000) - 0x8000);
4068 fatal_insn ("UNKNOWN in print_operand !?", x);
4073 /* Target hook for assembling integer objects. We need to define it
4074 here to work a round a bug in some versions of GAS, which couldn't
4075 handle values smaller than INT_MIN when printed in decimal. */
4078 s390_assemble_integer (rtx x, unsigned int size, int aligned_p)
4080 if (size == 8 && aligned_p
4081 && GET_CODE (x) == CONST_INT && INTVAL (x) < INT_MIN)
4083 fprintf (asm_out_file, "\t.quad\t" HOST_WIDE_INT_PRINT_HEX "\n",
4087 return default_assemble_integer (x, size, aligned_p);
4090 /* Returns true if register REGNO is used for forming
4091 a memory address in expression X. */
4094 reg_used_in_mem_p (int regno, rtx x)
4096 enum rtx_code code = GET_CODE (x);
4102 if (refers_to_regno_p (regno, regno+1,
4106 else if (code == SET
4107 && GET_CODE (SET_DEST (x)) == PC)
4109 if (refers_to_regno_p (regno, regno+1,
4114 fmt = GET_RTX_FORMAT (code);
4115 for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
4118 && reg_used_in_mem_p (regno, XEXP (x, i)))
4121 else if (fmt[i] == 'E')
4122 for (j = 0; j < XVECLEN (x, i); j++)
4123 if (reg_used_in_mem_p (regno, XVECEXP (x, i, j)))
4129 /* Returns true if expression DEP_RTX sets an address register
4130 used by instruction INSN to address memory. */
4133 addr_generation_dependency_p (rtx dep_rtx, rtx insn)
4137 if (GET_CODE (dep_rtx) == INSN)
4138 dep_rtx = PATTERN (dep_rtx);
4140 if (GET_CODE (dep_rtx) == SET)
4142 target = SET_DEST (dep_rtx);
4143 if (GET_CODE (target) == STRICT_LOW_PART)
4144 target = XEXP (target, 0);
4145 while (GET_CODE (target) == SUBREG)
4146 target = SUBREG_REG (target);
4148 if (GET_CODE (target) == REG)
4150 int regno = REGNO (target);
4152 if (s390_safe_attr_type (insn) == TYPE_LA)
4154 pat = PATTERN (insn);
4155 if (GET_CODE (pat) == PARALLEL)
4157 if (XVECLEN (pat, 0) != 2)
4159 pat = XVECEXP (pat, 0, 0);
4161 if (GET_CODE (pat) == SET)
4162 return refers_to_regno_p (regno, regno+1, SET_SRC (pat), 0);
4166 else if (get_attr_atype (insn) == ATYPE_AGEN)
4167 return reg_used_in_mem_p (regno, PATTERN (insn));
4173 /* Return 1, if dep_insn sets register used in insn in the agen unit. */
4176 s390_agen_dep_p (rtx dep_insn, rtx insn)
4178 rtx dep_rtx = PATTERN (dep_insn);
4181 if (GET_CODE (dep_rtx) == SET
4182 && addr_generation_dependency_p (dep_rtx, insn))
4184 else if (GET_CODE (dep_rtx) == PARALLEL)
4186 for (i = 0; i < XVECLEN (dep_rtx, 0); i++)
4188 if (addr_generation_dependency_p (XVECEXP (dep_rtx, 0, i), insn))
4195 /* A C statement (sans semicolon) to update the integer scheduling priority
4196 INSN_PRIORITY (INSN). Increase the priority to execute the INSN earlier,
4197 reduce the priority to execute INSN later. Do not define this macro if
4198 you do not need to adjust the scheduling priorities of insns.
4200 A STD instruction should be scheduled earlier,
4201 in order to use the bypass. */
4204 s390_adjust_priority (rtx insn ATTRIBUTE_UNUSED, int priority)
4206 if (! INSN_P (insn))
4209 if (s390_tune != PROCESSOR_2084_Z990)
4212 switch (s390_safe_attr_type (insn))
4216 priority = priority << 3;
4220 priority = priority << 1;
4228 /* The number of instructions that can be issued per cycle. */
4231 s390_issue_rate (void)
4233 if (s390_tune == PROCESSOR_2084_Z990)
4239 s390_first_cycle_multipass_dfa_lookahead (void)
4245 /* Split all branches that exceed the maximum distance.
4246 Returns true if this created a new literal pool entry. */
4249 s390_split_branches (void)
4251 rtx temp_reg = gen_rtx_REG (Pmode, RETURN_REGNUM);
4252 int new_literal = 0;
4253 rtx insn, pat, tmp, target;
4256 /* We need correct insn addresses. */
4258 shorten_branches (get_insns ());
4260 /* Find all branches that exceed 64KB, and split them. */
4262 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
4264 if (GET_CODE (insn) != JUMP_INSN)
4267 pat = PATTERN (insn);
4268 if (GET_CODE (pat) == PARALLEL && XVECLEN (pat, 0) > 2)
4269 pat = XVECEXP (pat, 0, 0);
4270 if (GET_CODE (pat) != SET || SET_DEST (pat) != pc_rtx)
4273 if (GET_CODE (SET_SRC (pat)) == LABEL_REF)
4275 label = &SET_SRC (pat);
4277 else if (GET_CODE (SET_SRC (pat)) == IF_THEN_ELSE)
4279 if (GET_CODE (XEXP (SET_SRC (pat), 1)) == LABEL_REF)
4280 label = &XEXP (SET_SRC (pat), 1);
4281 else if (GET_CODE (XEXP (SET_SRC (pat), 2)) == LABEL_REF)
4282 label = &XEXP (SET_SRC (pat), 2);
4289 if (get_attr_length (insn) <= 4)
4292 /* We are going to use the return register as scratch register,
4293 make sure it will be saved/restored by the prologue/epilogue. */
4294 cfun_frame_layout.save_return_addr_p = 1;
4299 tmp = force_const_mem (Pmode, *label);
4300 tmp = emit_insn_before (gen_rtx_SET (Pmode, temp_reg, tmp), insn);
4301 INSN_ADDRESSES_NEW (tmp, -1);
4302 annotate_constant_pool_refs (&PATTERN (tmp));
4309 target = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, *label),
4310 UNSPEC_LTREL_OFFSET);
4311 target = gen_rtx_CONST (Pmode, target);
4312 target = force_const_mem (Pmode, target);
4313 tmp = emit_insn_before (gen_rtx_SET (Pmode, temp_reg, target), insn);
4314 INSN_ADDRESSES_NEW (tmp, -1);
4315 annotate_constant_pool_refs (&PATTERN (tmp));
4317 target = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, XEXP (target, 0),
4318 cfun->machine->base_reg),
4320 target = gen_rtx_PLUS (Pmode, temp_reg, target);
4323 if (!validate_change (insn, label, target, 0))
4330 /* Annotate every literal pool reference in X by an UNSPEC_LTREF expression.
4331 Fix up MEMs as required. */
4334 annotate_constant_pool_refs (rtx *x)
4339 if (GET_CODE (*x) == SYMBOL_REF
4340 && CONSTANT_POOL_ADDRESS_P (*x))
4343 /* Literal pool references can only occur inside a MEM ... */
4344 if (GET_CODE (*x) == MEM)
4346 rtx memref = XEXP (*x, 0);
4348 if (GET_CODE (memref) == SYMBOL_REF
4349 && CONSTANT_POOL_ADDRESS_P (memref))
4351 rtx base = cfun->machine->base_reg;
4352 rtx addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, memref, base),
4355 *x = replace_equiv_address (*x, addr);
4359 if (GET_CODE (memref) == CONST
4360 && GET_CODE (XEXP (memref, 0)) == PLUS
4361 && GET_CODE (XEXP (XEXP (memref, 0), 1)) == CONST_INT
4362 && GET_CODE (XEXP (XEXP (memref, 0), 0)) == SYMBOL_REF
4363 && CONSTANT_POOL_ADDRESS_P (XEXP (XEXP (memref, 0), 0)))
4365 HOST_WIDE_INT off = INTVAL (XEXP (XEXP (memref, 0), 1));
4366 rtx sym = XEXP (XEXP (memref, 0), 0);
4367 rtx base = cfun->machine->base_reg;
4368 rtx addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, sym, base),
4371 *x = replace_equiv_address (*x, plus_constant (addr, off));
4376 /* ... or a load-address type pattern. */
4377 if (GET_CODE (*x) == SET)
4379 rtx addrref = SET_SRC (*x);
4381 if (GET_CODE (addrref) == SYMBOL_REF
4382 && CONSTANT_POOL_ADDRESS_P (addrref))
4384 rtx base = cfun->machine->base_reg;
4385 rtx addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, addrref, base),
4388 SET_SRC (*x) = addr;
4392 if (GET_CODE (addrref) == CONST
4393 && GET_CODE (XEXP (addrref, 0)) == PLUS
4394 && GET_CODE (XEXP (XEXP (addrref, 0), 1)) == CONST_INT
4395 && GET_CODE (XEXP (XEXP (addrref, 0), 0)) == SYMBOL_REF
4396 && CONSTANT_POOL_ADDRESS_P (XEXP (XEXP (addrref, 0), 0)))
4398 HOST_WIDE_INT off = INTVAL (XEXP (XEXP (addrref, 0), 1));
4399 rtx sym = XEXP (XEXP (addrref, 0), 0);
4400 rtx base = cfun->machine->base_reg;
4401 rtx addr = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, sym, base),
4404 SET_SRC (*x) = plus_constant (addr, off);
4409 /* Annotate LTREL_BASE as well. */
4410 if (GET_CODE (*x) == UNSPEC
4411 && XINT (*x, 1) == UNSPEC_LTREL_BASE)
4413 rtx base = cfun->machine->base_reg;
4414 *x = gen_rtx_UNSPEC (Pmode, gen_rtvec (2, XVECEXP (*x, 0, 0), base),
4419 fmt = GET_RTX_FORMAT (GET_CODE (*x));
4420 for (i = GET_RTX_LENGTH (GET_CODE (*x)) - 1; i >= 0; i--)
4424 annotate_constant_pool_refs (&XEXP (*x, i));
4426 else if (fmt[i] == 'E')
4428 for (j = 0; j < XVECLEN (*x, i); j++)
4429 annotate_constant_pool_refs (&XVECEXP (*x, i, j));
4435 /* Find an annotated literal pool symbol referenced in RTX X,
4436 and store it at REF. Will abort if X contains references to
4437 more than one such pool symbol; multiple references to the same
4438 symbol are allowed, however.
4440 The rtx pointed to by REF must be initialized to NULL_RTX
4441 by the caller before calling this routine. */
4444 find_constant_pool_ref (rtx x, rtx *ref)
4449 /* Ignore LTREL_BASE references. */
4450 if (GET_CODE (x) == UNSPEC
4451 && XINT (x, 1) == UNSPEC_LTREL_BASE)
4453 /* Likewise POOL_ENTRY insns. */
4454 if (GET_CODE (x) == UNSPEC_VOLATILE
4455 && XINT (x, 1) == UNSPECV_POOL_ENTRY)
4458 if (GET_CODE (x) == SYMBOL_REF
4459 && CONSTANT_POOL_ADDRESS_P (x))
4462 if (GET_CODE (x) == UNSPEC && XINT (x, 1) == UNSPEC_LTREF)
4464 rtx sym = XVECEXP (x, 0, 0);
4465 if (GET_CODE (sym) != SYMBOL_REF
4466 || !CONSTANT_POOL_ADDRESS_P (sym))
4469 if (*ref == NULL_RTX)
4471 else if (*ref != sym)
4477 fmt = GET_RTX_FORMAT (GET_CODE (x));
4478 for (i = GET_RTX_LENGTH (GET_CODE (x)) - 1; i >= 0; i--)
4482 find_constant_pool_ref (XEXP (x, i), ref);
4484 else if (fmt[i] == 'E')
4486 for (j = 0; j < XVECLEN (x, i); j++)
4487 find_constant_pool_ref (XVECEXP (x, i, j), ref);
4492 /* Replace every reference to the annotated literal pool
4493 symbol REF in X by its base plus OFFSET. */
4496 replace_constant_pool_ref (rtx *x, rtx ref, rtx offset)
4504 if (GET_CODE (*x) == UNSPEC
4505 && XINT (*x, 1) == UNSPEC_LTREF
4506 && XVECEXP (*x, 0, 0) == ref)
4508 *x = gen_rtx_PLUS (Pmode, XVECEXP (*x, 0, 1), offset);
4512 if (GET_CODE (*x) == PLUS
4513 && GET_CODE (XEXP (*x, 1)) == CONST_INT
4514 && GET_CODE (XEXP (*x, 0)) == UNSPEC
4515 && XINT (XEXP (*x, 0), 1) == UNSPEC_LTREF
4516 && XVECEXP (XEXP (*x, 0), 0, 0) == ref)
4518 rtx addr = gen_rtx_PLUS (Pmode, XVECEXP (XEXP (*x, 0), 0, 1), offset);
4519 *x = plus_constant (addr, INTVAL (XEXP (*x, 1)));
4523 fmt = GET_RTX_FORMAT (GET_CODE (*x));
4524 for (i = GET_RTX_LENGTH (GET_CODE (*x)) - 1; i >= 0; i--)
4528 replace_constant_pool_ref (&XEXP (*x, i), ref, offset);
4530 else if (fmt[i] == 'E')
4532 for (j = 0; j < XVECLEN (*x, i); j++)
4533 replace_constant_pool_ref (&XVECEXP (*x, i, j), ref, offset);
4538 /* Check whether X contains an UNSPEC_LTREL_BASE.
4539 Return its constant pool symbol if found, NULL_RTX otherwise. */
4542 find_ltrel_base (rtx x)
4547 if (GET_CODE (x) == UNSPEC
4548 && XINT (x, 1) == UNSPEC_LTREL_BASE)
4549 return XVECEXP (x, 0, 0);
4551 fmt = GET_RTX_FORMAT (GET_CODE (x));
4552 for (i = GET_RTX_LENGTH (GET_CODE (x)) - 1; i >= 0; i--)
4556 rtx fnd = find_ltrel_base (XEXP (x, i));
4560 else if (fmt[i] == 'E')
4562 for (j = 0; j < XVECLEN (x, i); j++)
4564 rtx fnd = find_ltrel_base (XVECEXP (x, i, j));
4574 /* Replace any occurrence of UNSPEC_LTREL_BASE in X with its base. */
4577 replace_ltrel_base (rtx *x)
4582 if (GET_CODE (*x) == UNSPEC
4583 && XINT (*x, 1) == UNSPEC_LTREL_BASE)
4585 *x = XVECEXP (*x, 0, 1);
4589 fmt = GET_RTX_FORMAT (GET_CODE (*x));
4590 for (i = GET_RTX_LENGTH (GET_CODE (*x)) - 1; i >= 0; i--)
4594 replace_ltrel_base (&XEXP (*x, i));
4596 else if (fmt[i] == 'E')
4598 for (j = 0; j < XVECLEN (*x, i); j++)
4599 replace_ltrel_base (&XVECEXP (*x, i, j));
4605 /* We keep a list of constants which we have to add to internal
4606 constant tables in the middle of large functions. */
4608 #define NR_C_MODES 7
4609 enum machine_mode constant_modes[NR_C_MODES] =
4620 struct constant *next;
4625 struct constant_pool
4627 struct constant_pool *next;
4632 struct constant *constants[NR_C_MODES];
4633 struct constant *execute;
4638 static struct constant_pool * s390_mainpool_start (void);
4639 static void s390_mainpool_finish (struct constant_pool *);
4640 static void s390_mainpool_cancel (struct constant_pool *);
4642 static struct constant_pool * s390_chunkify_start (void);
4643 static void s390_chunkify_finish (struct constant_pool *);
4644 static void s390_chunkify_cancel (struct constant_pool *);
4646 static struct constant_pool *s390_start_pool (struct constant_pool **, rtx);
4647 static void s390_end_pool (struct constant_pool *, rtx);
4648 static void s390_add_pool_insn (struct constant_pool *, rtx);
4649 static struct constant_pool *s390_find_pool (struct constant_pool *, rtx);
4650 static void s390_add_constant (struct constant_pool *, rtx, enum machine_mode);
4651 static rtx s390_find_constant (struct constant_pool *, rtx, enum machine_mode);
4652 static void s390_add_execute (struct constant_pool *, rtx);
4653 static rtx s390_find_execute (struct constant_pool *, rtx);
4654 static rtx s390_execute_label (rtx);
4655 static rtx s390_execute_target (rtx);
4656 static void s390_dump_pool (struct constant_pool *, bool);
4657 static void s390_dump_execute (struct constant_pool *);
4658 static struct constant_pool *s390_alloc_pool (void);
4659 static void s390_free_pool (struct constant_pool *);
4661 /* Create new constant pool covering instructions starting at INSN
4662 and chain it to the end of POOL_LIST. */
4664 static struct constant_pool *
4665 s390_start_pool (struct constant_pool **pool_list, rtx insn)
4667 struct constant_pool *pool, **prev;
4669 pool = s390_alloc_pool ();
4670 pool->first_insn = insn;
4672 for (prev = pool_list; *prev; prev = &(*prev)->next)
4679 /* End range of instructions covered by POOL at INSN and emit
4680 placeholder insn representing the pool. */
4683 s390_end_pool (struct constant_pool *pool, rtx insn)
4685 rtx pool_size = GEN_INT (pool->size + 8 /* alignment slop */);
4688 insn = get_last_insn ();
4690 pool->pool_insn = emit_insn_after (gen_pool (pool_size), insn);
4691 INSN_ADDRESSES_NEW (pool->pool_insn, -1);
4694 /* Add INSN to the list of insns covered by POOL. */
4697 s390_add_pool_insn (struct constant_pool *pool, rtx insn)
4699 bitmap_set_bit (pool->insns, INSN_UID (insn));
4702 /* Return pool out of POOL_LIST that covers INSN. */
4704 static struct constant_pool *
4705 s390_find_pool (struct constant_pool *pool_list, rtx insn)
4707 struct constant_pool *pool;
4709 for (pool = pool_list; pool; pool = pool->next)
4710 if (bitmap_bit_p (pool->insns, INSN_UID (insn)))
4716 /* Add constant VAL of mode MODE to the constant pool POOL. */
4719 s390_add_constant (struct constant_pool *pool, rtx val, enum machine_mode mode)
4724 for (i = 0; i < NR_C_MODES; i++)
4725 if (constant_modes[i] == mode)
4727 if (i == NR_C_MODES)
4730 for (c = pool->constants[i]; c != NULL; c = c->next)
4731 if (rtx_equal_p (val, c->value))
4736 c = (struct constant *) xmalloc (sizeof *c);
4738 c->label = gen_label_rtx ();
4739 c->next = pool->constants[i];
4740 pool->constants[i] = c;
4741 pool->size += GET_MODE_SIZE (mode);
4745 /* Find constant VAL of mode MODE in the constant pool POOL.
4746 Return an RTX describing the distance from the start of
4747 the pool to the location of the new constant. */
4750 s390_find_constant (struct constant_pool *pool, rtx val,
4751 enum machine_mode mode)
4757 for (i = 0; i < NR_C_MODES; i++)
4758 if (constant_modes[i] == mode)
4760 if (i == NR_C_MODES)
4763 for (c = pool->constants[i]; c != NULL; c = c->next)
4764 if (rtx_equal_p (val, c->value))
4770 offset = gen_rtx_MINUS (Pmode, gen_rtx_LABEL_REF (Pmode, c->label),
4771 gen_rtx_LABEL_REF (Pmode, pool->label));
4772 offset = gen_rtx_CONST (Pmode, offset);
4776 /* Add execute target for INSN to the constant pool POOL. */
4779 s390_add_execute (struct constant_pool *pool, rtx insn)
4783 for (c = pool->execute; c != NULL; c = c->next)
4784 if (INSN_UID (insn) == INSN_UID (c->value))
4789 rtx label = s390_execute_label (insn);
4792 c = (struct constant *) xmalloc (sizeof *c);
4794 c->label = label == const0_rtx ? gen_label_rtx () : XEXP (label, 0);
4795 c->next = pool->execute;
4797 pool->size += label == const0_rtx ? 6 : 0;
4801 /* Find execute target for INSN in the constant pool POOL.
4802 Return an RTX describing the distance from the start of
4803 the pool to the location of the execute target. */
4806 s390_find_execute (struct constant_pool *pool, rtx insn)
4811 for (c = pool->execute; c != NULL; c = c->next)
4812 if (INSN_UID (insn) == INSN_UID (c->value))
4818 offset = gen_rtx_MINUS (Pmode, gen_rtx_LABEL_REF (Pmode, c->label),
4819 gen_rtx_LABEL_REF (Pmode, pool->label));
4820 offset = gen_rtx_CONST (Pmode, offset);
4824 /* Check whether INSN is an execute. Return the label_ref to its
4825 execute target template if so, NULL_RTX otherwise. */
4828 s390_execute_label (rtx insn)
4830 if (GET_CODE (insn) == INSN
4831 && GET_CODE (PATTERN (insn)) == PARALLEL
4832 && GET_CODE (XVECEXP (PATTERN (insn), 0, 0)) == UNSPEC
4833 && XINT (XVECEXP (PATTERN (insn), 0, 0), 1) == UNSPEC_EXECUTE)
4834 return XVECEXP (XVECEXP (PATTERN (insn), 0, 0), 0, 2);
4839 /* For an execute INSN, extract the execute target template. */
4842 s390_execute_target (rtx insn)
4844 rtx pattern = PATTERN (insn);
4845 gcc_assert (s390_execute_label (insn));
4847 if (XVECLEN (pattern, 0) == 2)
4849 pattern = copy_rtx (XVECEXP (pattern, 0, 1));
4853 rtvec vec = rtvec_alloc (XVECLEN (pattern, 0) - 1);
4856 for (i = 0; i < XVECLEN (pattern, 0) - 1; i++)
4857 RTVEC_ELT (vec, i) = copy_rtx (XVECEXP (pattern, 0, i + 1));
4859 pattern = gen_rtx_PARALLEL (VOIDmode, vec);
4865 /* Indicate that INSN cannot be duplicated. This is the case for
4866 execute insns that carry a unique label. */
4869 s390_cannot_copy_insn_p (rtx insn)
4871 rtx label = s390_execute_label (insn);
4872 return label && label != const0_rtx;
4875 /* Dump out the constants in POOL. If REMOTE_LABEL is true,
4876 do not emit the pool base label. */
4879 s390_dump_pool (struct constant_pool *pool, bool remote_label)
4882 rtx insn = pool->pool_insn;
4885 /* Switch to rodata section. */
4886 if (TARGET_CPU_ZARCH)
4888 insn = emit_insn_after (gen_pool_section_start (), insn);
4889 INSN_ADDRESSES_NEW (insn, -1);
4892 /* Ensure minimum pool alignment. */
4893 if (TARGET_CPU_ZARCH)
4894 insn = emit_insn_after (gen_pool_align (GEN_INT (8)), insn);
4896 insn = emit_insn_after (gen_pool_align (GEN_INT (4)), insn);
4897 INSN_ADDRESSES_NEW (insn, -1);
4899 /* Emit pool base label. */
4902 insn = emit_label_after (pool->label, insn);
4903 INSN_ADDRESSES_NEW (insn, -1);
4906 /* Dump constants in descending alignment requirement order,
4907 ensuring proper alignment for every constant. */
4908 for (i = 0; i < NR_C_MODES; i++)
4909 for (c = pool->constants[i]; c; c = c->next)
4911 /* Convert UNSPEC_LTREL_OFFSET unspecs to pool-relative references. */
4912 rtx value = c->value;
4913 if (GET_CODE (value) == CONST
4914 && GET_CODE (XEXP (value, 0)) == UNSPEC
4915 && XINT (XEXP (value, 0), 1) == UNSPEC_LTREL_OFFSET
4916 && XVECLEN (XEXP (value, 0), 0) == 1)
4918 value = gen_rtx_MINUS (Pmode, XVECEXP (XEXP (value, 0), 0, 0),
4919 gen_rtx_LABEL_REF (VOIDmode, pool->label));
4920 value = gen_rtx_CONST (VOIDmode, value);
4923 insn = emit_label_after (c->label, insn);
4924 INSN_ADDRESSES_NEW (insn, -1);
4926 value = gen_rtx_UNSPEC_VOLATILE (constant_modes[i],
4927 gen_rtvec (1, value),
4928 UNSPECV_POOL_ENTRY);
4929 insn = emit_insn_after (value, insn);
4930 INSN_ADDRESSES_NEW (insn, -1);
4933 /* Ensure minimum alignment for instructions. */
4934 insn = emit_insn_after (gen_pool_align (GEN_INT (2)), insn);
4935 INSN_ADDRESSES_NEW (insn, -1);
4937 /* Output in-pool execute template insns. */
4938 for (c = pool->execute; c; c = c->next)
4940 if (s390_execute_label (c->value) != const0_rtx)
4943 insn = emit_label_after (c->label, insn);
4944 INSN_ADDRESSES_NEW (insn, -1);
4946 insn = emit_insn_after (s390_execute_target (c->value), insn);
4947 INSN_ADDRESSES_NEW (insn, -1);
4950 /* Switch back to previous section. */
4951 if (TARGET_CPU_ZARCH)
4953 insn = emit_insn_after (gen_pool_section_end (), insn);
4954 INSN_ADDRESSES_NEW (insn, -1);
4957 insn = emit_barrier_after (insn);
4958 INSN_ADDRESSES_NEW (insn, -1);
4960 /* Remove placeholder insn. */
4961 remove_insn (pool->pool_insn);
4963 /* Output out-of-pool execute template isns. */
4964 s390_dump_execute (pool);
4967 /* Dump out the out-of-pool execute template insns in POOL
4968 at the end of the instruction stream. */
4971 s390_dump_execute (struct constant_pool *pool)
4976 for (c = pool->execute; c; c = c->next)
4978 if (s390_execute_label (c->value) == const0_rtx)
4981 insn = emit_label (c->label);
4982 INSN_ADDRESSES_NEW (insn, -1);
4984 insn = emit_insn (s390_execute_target (c->value));
4985 INSN_ADDRESSES_NEW (insn, -1);
4989 /* Allocate new constant_pool structure. */
4991 static struct constant_pool *
4992 s390_alloc_pool (void)
4994 struct constant_pool *pool;
4997 pool = (struct constant_pool *) xmalloc (sizeof *pool);
4999 for (i = 0; i < NR_C_MODES; i++)
5000 pool->constants[i] = NULL;
5002 pool->execute = NULL;
5003 pool->label = gen_label_rtx ();
5004 pool->first_insn = NULL_RTX;
5005 pool->pool_insn = NULL_RTX;
5006 pool->insns = BITMAP_ALLOC (NULL);
5012 /* Free all memory used by POOL. */
5015 s390_free_pool (struct constant_pool *pool)
5017 struct constant *c, *next;
5020 for (i = 0; i < NR_C_MODES; i++)
5021 for (c = pool->constants[i]; c; c = next)
5027 for (c = pool->execute; c; c = next)
5033 BITMAP_FREE (pool->insns);
5038 /* Collect main literal pool. Return NULL on overflow. */
5040 static struct constant_pool *
5041 s390_mainpool_start (void)
5043 struct constant_pool *pool;
5046 pool = s390_alloc_pool ();
5048 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
5050 if (GET_CODE (insn) == INSN
5051 && GET_CODE (PATTERN (insn)) == SET
5052 && GET_CODE (SET_SRC (PATTERN (insn))) == UNSPEC_VOLATILE
5053 && XINT (SET_SRC (PATTERN (insn)), 1) == UNSPECV_MAIN_POOL)
5055 if (pool->pool_insn)
5057 pool->pool_insn = insn;
5060 if (s390_execute_label (insn))
5062 s390_add_execute (pool, insn);
5064 else if (GET_CODE (insn) == INSN || GET_CODE (insn) == CALL_INSN)
5066 rtx pool_ref = NULL_RTX;
5067 find_constant_pool_ref (PATTERN (insn), &pool_ref);
5070 rtx constant = get_pool_constant (pool_ref);
5071 enum machine_mode mode = get_pool_mode (pool_ref);
5072 s390_add_constant (pool, constant, mode);
5077 if (!pool->pool_insn && pool->size > 0)
5080 if (pool->size >= 4096)
5082 /* We're going to chunkify the pool, so remove the main
5083 pool placeholder insn. */
5084 remove_insn (pool->pool_insn);
5086 s390_free_pool (pool);
5093 /* POOL holds the main literal pool as collected by s390_mainpool_start.
5094 Modify the current function to output the pool constants as well as
5095 the pool register setup instruction. */
5098 s390_mainpool_finish (struct constant_pool *pool)
5100 rtx base_reg = cfun->machine->base_reg;
5103 /* If the pool is empty, we're done. */
5104 if (pool->size == 0)
5106 /* However, we may have out-of-pool execute templates. */
5107 s390_dump_execute (pool);
5109 /* We don't actually need a base register after all. */
5110 cfun->machine->base_reg = NULL_RTX;
5112 if (pool->pool_insn)
5113 remove_insn (pool->pool_insn);
5114 s390_free_pool (pool);
5118 /* We need correct insn addresses. */
5119 shorten_branches (get_insns ());
5121 /* On zSeries, we use a LARL to load the pool register. The pool is
5122 located in the .rodata section, so we emit it after the function. */
5123 if (TARGET_CPU_ZARCH)
5125 insn = gen_main_base_64 (base_reg, pool->label);
5126 insn = emit_insn_after (insn, pool->pool_insn);
5127 INSN_ADDRESSES_NEW (insn, -1);
5128 remove_insn (pool->pool_insn);
5130 insn = get_last_insn ();
5131 pool->pool_insn = emit_insn_after (gen_pool (const0_rtx), insn);
5132 INSN_ADDRESSES_NEW (pool->pool_insn, -1);
5134 s390_dump_pool (pool, 0);
5137 /* On S/390, if the total size of the function's code plus literal pool
5138 does not exceed 4096 bytes, we use BASR to set up a function base
5139 pointer, and emit the literal pool at the end of the function. */
5140 else if (INSN_ADDRESSES (INSN_UID (get_last_insn ()))
5141 + pool->size + 8 /* alignment slop */ < 4096)
5143 insn = gen_main_base_31_small (base_reg, pool->label);
5144 insn = emit_insn_after (insn, pool->pool_insn);
5145 INSN_ADDRESSES_NEW (insn, -1);
5146 remove_insn (pool->pool_insn);
5148 insn = emit_label_after (pool->label, insn);
5149 INSN_ADDRESSES_NEW (insn, -1);
5151 insn = get_last_insn ();
5152 pool->pool_insn = emit_insn_after (gen_pool (const0_rtx), insn);
5153 INSN_ADDRESSES_NEW (pool->pool_insn, -1);
5155 s390_dump_pool (pool, 1);
5158 /* Otherwise, we emit an inline literal pool and use BASR to branch
5159 over it, setting up the pool register at the same time. */
5162 rtx pool_end = gen_label_rtx ();
5164 insn = gen_main_base_31_large (base_reg, pool->label, pool_end);
5165 insn = emit_insn_after (insn, pool->pool_insn);
5166 INSN_ADDRESSES_NEW (insn, -1);
5167 remove_insn (pool->pool_insn);
5169 insn = emit_label_after (pool->label, insn);
5170 INSN_ADDRESSES_NEW (insn, -1);
5172 pool->pool_insn = emit_insn_after (gen_pool (const0_rtx), insn);
5173 INSN_ADDRESSES_NEW (pool->pool_insn, -1);
5175 insn = emit_label_after (pool_end, pool->pool_insn);
5176 INSN_ADDRESSES_NEW (insn, -1);
5178 s390_dump_pool (pool, 1);
5182 /* Replace all literal pool references. */
5184 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
5187 replace_ltrel_base (&PATTERN (insn));
5189 if (GET_CODE (insn) == INSN || GET_CODE (insn) == CALL_INSN)
5191 rtx addr, pool_ref = NULL_RTX;
5192 find_constant_pool_ref (PATTERN (insn), &pool_ref);
5195 if (s390_execute_label (insn))
5196 addr = s390_find_execute (pool, insn);
5198 addr = s390_find_constant (pool, get_pool_constant (pool_ref),
5199 get_pool_mode (pool_ref));
5201 replace_constant_pool_ref (&PATTERN (insn), pool_ref, addr);
5202 INSN_CODE (insn) = -1;
5208 /* Free the pool. */
5209 s390_free_pool (pool);
5212 /* POOL holds the main literal pool as collected by s390_mainpool_start.
5213 We have decided we cannot use this pool, so revert all changes
5214 to the current function that were done by s390_mainpool_start. */
5216 s390_mainpool_cancel (struct constant_pool *pool)
5218 /* We didn't actually change the instruction stream, so simply
5219 free the pool memory. */
5220 s390_free_pool (pool);
5224 /* Chunkify the literal pool. */
5226 #define S390_POOL_CHUNK_MIN 0xc00
5227 #define S390_POOL_CHUNK_MAX 0xe00
5229 static struct constant_pool *
5230 s390_chunkify_start (void)
5232 struct constant_pool *curr_pool = NULL, *pool_list = NULL;
5235 rtx pending_ltrel = NULL_RTX;
5238 rtx (*gen_reload_base) (rtx, rtx) =
5239 TARGET_CPU_ZARCH? gen_reload_base_64 : gen_reload_base_31;
5242 /* We need correct insn addresses. */
5244 shorten_branches (get_insns ());
5246 /* Scan all insns and move literals to pool chunks. */
5248 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
5250 /* Check for pending LTREL_BASE. */
5253 rtx ltrel_base = find_ltrel_base (PATTERN (insn));
5256 if (ltrel_base == pending_ltrel)
5257 pending_ltrel = NULL_RTX;
5263 if (s390_execute_label (insn))
5266 curr_pool = s390_start_pool (&pool_list, insn);
5268 s390_add_execute (curr_pool, insn);
5269 s390_add_pool_insn (curr_pool, insn);
5271 else if (GET_CODE (insn) == INSN || GET_CODE (insn) == CALL_INSN)
5273 rtx pool_ref = NULL_RTX;
5274 find_constant_pool_ref (PATTERN (insn), &pool_ref);
5277 rtx constant = get_pool_constant (pool_ref);
5278 enum machine_mode mode = get_pool_mode (pool_ref);
5281 curr_pool = s390_start_pool (&pool_list, insn);
5283 s390_add_constant (curr_pool, constant, mode);
5284 s390_add_pool_insn (curr_pool, insn);
5286 /* Don't split the pool chunk between a LTREL_OFFSET load
5287 and the corresponding LTREL_BASE. */
5288 if (GET_CODE (constant) == CONST
5289 && GET_CODE (XEXP (constant, 0)) == UNSPEC
5290 && XINT (XEXP (constant, 0), 1) == UNSPEC_LTREL_OFFSET)
5294 pending_ltrel = pool_ref;
5299 if (GET_CODE (insn) == JUMP_INSN || GET_CODE (insn) == CODE_LABEL)
5302 s390_add_pool_insn (curr_pool, insn);
5303 /* An LTREL_BASE must follow within the same basic block. */
5309 || INSN_ADDRESSES_SIZE () <= (size_t) INSN_UID (insn)
5310 || INSN_ADDRESSES (INSN_UID (insn)) == -1)
5313 if (TARGET_CPU_ZARCH)
5315 if (curr_pool->size < S390_POOL_CHUNK_MAX)
5318 s390_end_pool (curr_pool, NULL_RTX);
5323 int chunk_size = INSN_ADDRESSES (INSN_UID (insn))
5324 - INSN_ADDRESSES (INSN_UID (curr_pool->first_insn))
5327 /* We will later have to insert base register reload insns.
5328 Those will have an effect on code size, which we need to
5329 consider here. This calculation makes rather pessimistic
5330 worst-case assumptions. */
5331 if (GET_CODE (insn) == CODE_LABEL)
5334 if (chunk_size < S390_POOL_CHUNK_MIN
5335 && curr_pool->size < S390_POOL_CHUNK_MIN)
5338 /* Pool chunks can only be inserted after BARRIERs ... */
5339 if (GET_CODE (insn) == BARRIER)
5341 s390_end_pool (curr_pool, insn);
5346 /* ... so if we don't find one in time, create one. */
5347 else if ((chunk_size > S390_POOL_CHUNK_MAX
5348 || curr_pool->size > S390_POOL_CHUNK_MAX))
5350 rtx label, jump, barrier;
5352 /* We can insert the barrier only after a 'real' insn. */
5353 if (GET_CODE (insn) != INSN && GET_CODE (insn) != CALL_INSN)
5355 if (get_attr_length (insn) == 0)
5358 /* Don't separate LTREL_BASE from the corresponding
5359 LTREL_OFFSET load. */
5363 label = gen_label_rtx ();
5364 jump = emit_jump_insn_after (gen_jump (label), insn);
5365 barrier = emit_barrier_after (jump);
5366 insn = emit_label_after (label, barrier);
5367 JUMP_LABEL (jump) = label;
5368 LABEL_NUSES (label) = 1;
5370 INSN_ADDRESSES_NEW (jump, -1);
5371 INSN_ADDRESSES_NEW (barrier, -1);
5372 INSN_ADDRESSES_NEW (insn, -1);
5374 s390_end_pool (curr_pool, barrier);
5382 s390_end_pool (curr_pool, NULL_RTX);
5387 /* Find all labels that are branched into
5388 from an insn belonging to a different chunk. */
5390 far_labels = BITMAP_ALLOC (NULL);
5392 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
5394 /* Labels marked with LABEL_PRESERVE_P can be target
5395 of non-local jumps, so we have to mark them.
5396 The same holds for named labels.
5398 Don't do that, however, if it is the label before
5401 if (GET_CODE (insn) == CODE_LABEL
5402 && (LABEL_PRESERVE_P (insn) || LABEL_NAME (insn)))
5404 rtx vec_insn = next_real_insn (insn);
5405 rtx vec_pat = vec_insn && GET_CODE (vec_insn) == JUMP_INSN ?
5406 PATTERN (vec_insn) : NULL_RTX;
5408 || !(GET_CODE (vec_pat) == ADDR_VEC
5409 || GET_CODE (vec_pat) == ADDR_DIFF_VEC))
5410 bitmap_set_bit (far_labels, CODE_LABEL_NUMBER (insn));
5413 /* If we have a direct jump (conditional or unconditional)
5414 or a casesi jump, check all potential targets. */
5415 else if (GET_CODE (insn) == JUMP_INSN)
5417 rtx pat = PATTERN (insn);
5418 if (GET_CODE (pat) == PARALLEL && XVECLEN (pat, 0) > 2)
5419 pat = XVECEXP (pat, 0, 0);
5421 if (GET_CODE (pat) == SET)
5423 rtx label = JUMP_LABEL (insn);
5426 if (s390_find_pool (pool_list, label)
5427 != s390_find_pool (pool_list, insn))
5428 bitmap_set_bit (far_labels, CODE_LABEL_NUMBER (label));
5431 else if (GET_CODE (pat) == PARALLEL
5432 && XVECLEN (pat, 0) == 2
5433 && GET_CODE (XVECEXP (pat, 0, 0)) == SET
5434 && GET_CODE (XVECEXP (pat, 0, 1)) == USE
5435 && GET_CODE (XEXP (XVECEXP (pat, 0, 1), 0)) == LABEL_REF)
5437 /* Find the jump table used by this casesi jump. */
5438 rtx vec_label = XEXP (XEXP (XVECEXP (pat, 0, 1), 0), 0);
5439 rtx vec_insn = next_real_insn (vec_label);
5440 rtx vec_pat = vec_insn && GET_CODE (vec_insn) == JUMP_INSN ?
5441 PATTERN (vec_insn) : NULL_RTX;
5443 && (GET_CODE (vec_pat) == ADDR_VEC
5444 || GET_CODE (vec_pat) == ADDR_DIFF_VEC))
5446 int i, diff_p = GET_CODE (vec_pat) == ADDR_DIFF_VEC;
5448 for (i = 0; i < XVECLEN (vec_pat, diff_p); i++)
5450 rtx label = XEXP (XVECEXP (vec_pat, diff_p, i), 0);
5452 if (s390_find_pool (pool_list, label)
5453 != s390_find_pool (pool_list, insn))
5454 bitmap_set_bit (far_labels, CODE_LABEL_NUMBER (label));
5461 /* Insert base register reload insns before every pool. */
5463 for (curr_pool = pool_list; curr_pool; curr_pool = curr_pool->next)
5465 rtx new_insn = gen_reload_base (cfun->machine->base_reg,
5467 rtx insn = curr_pool->first_insn;
5468 INSN_ADDRESSES_NEW (emit_insn_before (new_insn, insn), -1);
5471 /* Insert base register reload insns at every far label. */
5473 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
5474 if (GET_CODE (insn) == CODE_LABEL
5475 && bitmap_bit_p (far_labels, CODE_LABEL_NUMBER (insn)))
5477 struct constant_pool *pool = s390_find_pool (pool_list, insn);
5480 rtx new_insn = gen_reload_base (cfun->machine->base_reg,
5482 INSN_ADDRESSES_NEW (emit_insn_after (new_insn, insn), -1);
5487 BITMAP_FREE (far_labels);
5490 /* Recompute insn addresses. */
5492 init_insn_lengths ();
5493 shorten_branches (get_insns ());
5498 /* POOL_LIST is a chunk list as prepared by s390_chunkify_start.
5499 After we have decided to use this list, finish implementing
5500 all changes to the current function as required. */
5503 s390_chunkify_finish (struct constant_pool *pool_list)
5505 struct constant_pool *curr_pool = NULL;
5509 /* Replace all literal pool references. */
5511 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
5514 replace_ltrel_base (&PATTERN (insn));
5516 curr_pool = s390_find_pool (pool_list, insn);
5520 if (GET_CODE (insn) == INSN || GET_CODE (insn) == CALL_INSN)
5522 rtx addr, pool_ref = NULL_RTX;
5523 find_constant_pool_ref (PATTERN (insn), &pool_ref);
5526 if (s390_execute_label (insn))
5527 addr = s390_find_execute (curr_pool, insn);
5529 addr = s390_find_constant (curr_pool,
5530 get_pool_constant (pool_ref),
5531 get_pool_mode (pool_ref));
5533 replace_constant_pool_ref (&PATTERN (insn), pool_ref, addr);
5534 INSN_CODE (insn) = -1;
5539 /* Dump out all literal pools. */
5541 for (curr_pool = pool_list; curr_pool; curr_pool = curr_pool->next)
5542 s390_dump_pool (curr_pool, 0);
5544 /* Free pool list. */
5548 struct constant_pool *next = pool_list->next;
5549 s390_free_pool (pool_list);
5554 /* POOL_LIST is a chunk list as prepared by s390_chunkify_start.
5555 We have decided we cannot use this list, so revert all changes
5556 to the current function that were done by s390_chunkify_start. */
5559 s390_chunkify_cancel (struct constant_pool *pool_list)
5561 struct constant_pool *curr_pool = NULL;
5564 /* Remove all pool placeholder insns. */
5566 for (curr_pool = pool_list; curr_pool; curr_pool = curr_pool->next)
5568 /* Did we insert an extra barrier? Remove it. */
5569 rtx barrier = PREV_INSN (curr_pool->pool_insn);
5570 rtx jump = barrier? PREV_INSN (barrier) : NULL_RTX;
5571 rtx label = NEXT_INSN (curr_pool->pool_insn);
5573 if (jump && GET_CODE (jump) == JUMP_INSN
5574 && barrier && GET_CODE (barrier) == BARRIER
5575 && label && GET_CODE (label) == CODE_LABEL
5576 && GET_CODE (PATTERN (jump)) == SET
5577 && SET_DEST (PATTERN (jump)) == pc_rtx
5578 && GET_CODE (SET_SRC (PATTERN (jump))) == LABEL_REF
5579 && XEXP (SET_SRC (PATTERN (jump)), 0) == label)
5582 remove_insn (barrier);
5583 remove_insn (label);
5586 remove_insn (curr_pool->pool_insn);
5589 /* Remove all base register reload insns. */
5591 for (insn = get_insns (); insn; )
5593 rtx next_insn = NEXT_INSN (insn);
5595 if (GET_CODE (insn) == INSN
5596 && GET_CODE (PATTERN (insn)) == SET
5597 && GET_CODE (SET_SRC (PATTERN (insn))) == UNSPEC
5598 && XINT (SET_SRC (PATTERN (insn)), 1) == UNSPEC_RELOAD_BASE)
5604 /* Free pool list. */
5608 struct constant_pool *next = pool_list->next;
5609 s390_free_pool (pool_list);
5615 /* Output the constant pool entry EXP in mode MODE with alignment ALIGN. */
5618 s390_output_pool_entry (rtx exp, enum machine_mode mode, unsigned int align)
5622 switch (GET_MODE_CLASS (mode))
5625 if (GET_CODE (exp) != CONST_DOUBLE)
5628 REAL_VALUE_FROM_CONST_DOUBLE (r, exp);
5629 assemble_real (r, mode, align);
5633 assemble_integer (exp, GET_MODE_SIZE (mode), align, 1);
5642 /* Rework the prologue/epilogue to avoid saving/restoring
5643 registers unnecessarily. */
5646 s390_optimize_prologue (void)
5648 rtx insn, new_insn, next_insn;
5650 /* Do a final recompute of the frame-related data. */
5652 s390_update_frame_layout ();
5654 /* If all special registers are in fact used, there's nothing we
5655 can do, so no point in walking the insn list. */
5657 if (cfun_frame_layout.first_save_gpr <= BASE_REGNUM
5658 && cfun_frame_layout.last_save_gpr >= BASE_REGNUM
5659 && (TARGET_CPU_ZARCH
5660 || (cfun_frame_layout.first_save_gpr <= RETURN_REGNUM
5661 && cfun_frame_layout.last_save_gpr >= RETURN_REGNUM)))
5664 /* Search for prologue/epilogue insns and replace them. */
5666 for (insn = get_insns (); insn; insn = next_insn)
5668 int first, last, off;
5669 rtx set, base, offset;
5671 next_insn = NEXT_INSN (insn);
5673 if (GET_CODE (insn) != INSN)
5676 if (GET_CODE (PATTERN (insn)) == PARALLEL
5677 && store_multiple_operation (PATTERN (insn), VOIDmode))
5679 set = XVECEXP (PATTERN (insn), 0, 0);
5680 first = REGNO (SET_SRC (set));
5681 last = first + XVECLEN (PATTERN (insn), 0) - 1;
5682 offset = const0_rtx;
5683 base = eliminate_constant_term (XEXP (SET_DEST (set), 0), &offset);
5684 off = INTVAL (offset);
5686 if (GET_CODE (base) != REG || off < 0)
5688 if (REGNO (base) != STACK_POINTER_REGNUM
5689 && REGNO (base) != HARD_FRAME_POINTER_REGNUM)
5691 if (first > BASE_REGNUM || last < BASE_REGNUM)
5694 if (cfun_frame_layout.first_save_gpr != -1)
5696 new_insn = save_gprs (base,
5697 off + (cfun_frame_layout.first_save_gpr
5698 - first) * UNITS_PER_WORD,
5699 cfun_frame_layout.first_save_gpr,
5700 cfun_frame_layout.last_save_gpr);
5701 new_insn = emit_insn_before (new_insn, insn);
5702 INSN_ADDRESSES_NEW (new_insn, -1);
5709 if (GET_CODE (PATTERN (insn)) == SET
5710 && GET_CODE (SET_SRC (PATTERN (insn))) == REG
5711 && (REGNO (SET_SRC (PATTERN (insn))) == BASE_REGNUM
5712 || (!TARGET_CPU_ZARCH
5713 && REGNO (SET_SRC (PATTERN (insn))) == RETURN_REGNUM))
5714 && GET_CODE (SET_DEST (PATTERN (insn))) == MEM)
5716 set = PATTERN (insn);
5717 first = REGNO (SET_SRC (set));
5718 offset = const0_rtx;
5719 base = eliminate_constant_term (XEXP (SET_DEST (set), 0), &offset);
5720 off = INTVAL (offset);
5722 if (GET_CODE (base) != REG || off < 0)
5724 if (REGNO (base) != STACK_POINTER_REGNUM
5725 && REGNO (base) != HARD_FRAME_POINTER_REGNUM)
5727 if (cfun_frame_layout.first_save_gpr != -1)
5729 new_insn = save_gprs (base,
5730 off + (cfun_frame_layout.first_save_gpr
5731 - first) * UNITS_PER_WORD,
5732 cfun_frame_layout.first_save_gpr,
5733 cfun_frame_layout.last_save_gpr);
5734 new_insn = emit_insn_before (new_insn, insn);
5735 INSN_ADDRESSES_NEW (new_insn, -1);
5742 if (GET_CODE (PATTERN (insn)) == PARALLEL
5743 && load_multiple_operation (PATTERN (insn), VOIDmode))
5745 set = XVECEXP (PATTERN (insn), 0, 0);
5746 first = REGNO (SET_DEST (set));
5747 last = first + XVECLEN (PATTERN (insn), 0) - 1;
5748 offset = const0_rtx;
5749 base = eliminate_constant_term (XEXP (SET_SRC (set), 0), &offset);
5750 off = INTVAL (offset);
5752 if (GET_CODE (base) != REG || off < 0)
5754 if (REGNO (base) != STACK_POINTER_REGNUM
5755 && REGNO (base) != HARD_FRAME_POINTER_REGNUM)
5757 if (first > BASE_REGNUM || last < BASE_REGNUM)
5760 if (cfun_frame_layout.first_restore_gpr != -1)
5762 new_insn = restore_gprs (base,
5763 off + (cfun_frame_layout.first_restore_gpr
5764 - first) * UNITS_PER_WORD,
5765 cfun_frame_layout.first_restore_gpr,
5766 cfun_frame_layout.last_restore_gpr);
5767 new_insn = emit_insn_before (new_insn, insn);
5768 INSN_ADDRESSES_NEW (new_insn, -1);
5775 if (GET_CODE (PATTERN (insn)) == SET
5776 && GET_CODE (SET_DEST (PATTERN (insn))) == REG
5777 && (REGNO (SET_DEST (PATTERN (insn))) == BASE_REGNUM
5778 || (!TARGET_CPU_ZARCH
5779 && REGNO (SET_DEST (PATTERN (insn))) == RETURN_REGNUM))
5780 && GET_CODE (SET_SRC (PATTERN (insn))) == MEM)
5782 set = PATTERN (insn);
5783 first = REGNO (SET_DEST (set));
5784 offset = const0_rtx;
5785 base = eliminate_constant_term (XEXP (SET_SRC (set), 0), &offset);
5786 off = INTVAL (offset);
5788 if (GET_CODE (base) != REG || off < 0)
5790 if (REGNO (base) != STACK_POINTER_REGNUM
5791 && REGNO (base) != HARD_FRAME_POINTER_REGNUM)
5793 if (cfun_frame_layout.first_restore_gpr != -1)
5795 new_insn = restore_gprs (base,
5796 off + (cfun_frame_layout.first_restore_gpr
5797 - first) * UNITS_PER_WORD,
5798 cfun_frame_layout.first_restore_gpr,
5799 cfun_frame_layout.last_restore_gpr);
5800 new_insn = emit_insn_before (new_insn, insn);
5801 INSN_ADDRESSES_NEW (new_insn, -1);
5810 /* Perform machine-dependent processing. */
5815 bool pool_overflow = false;
5817 /* Make sure all splits have been performed; splits after
5818 machine_dependent_reorg might confuse insn length counts. */
5819 split_all_insns_noflow ();
5822 /* Install the main literal pool and the associated base
5823 register load insns.
5825 In addition, there are two problematic situations we need
5828 - the literal pool might be > 4096 bytes in size, so that
5829 some of its elements cannot be directly accessed
5831 - a branch target might be > 64K away from the branch, so that
5832 it is not possible to use a PC-relative instruction.
5834 To fix those, we split the single literal pool into multiple
5835 pool chunks, reloading the pool base register at various
5836 points throughout the function to ensure it always points to
5837 the pool chunk the following code expects, and / or replace
5838 PC-relative branches by absolute branches.
5840 However, the two problems are interdependent: splitting the
5841 literal pool can move a branch further away from its target,
5842 causing the 64K limit to overflow, and on the other hand,
5843 replacing a PC-relative branch by an absolute branch means
5844 we need to put the branch target address into the literal
5845 pool, possibly causing it to overflow.
5847 So, we loop trying to fix up both problems until we manage
5848 to satisfy both conditions at the same time. Note that the
5849 loop is guaranteed to terminate as every pass of the loop
5850 strictly decreases the total number of PC-relative branches
5851 in the function. (This is not completely true as there
5852 might be branch-over-pool insns introduced by chunkify_start.
5853 Those never need to be split however.) */
5857 struct constant_pool *pool = NULL;
5859 /* Collect the literal pool. */
5862 pool = s390_mainpool_start ();
5864 pool_overflow = true;
5867 /* If literal pool overflowed, start to chunkify it. */
5869 pool = s390_chunkify_start ();
5871 /* Split out-of-range branches. If this has created new
5872 literal pool entries, cancel current chunk list and
5873 recompute it. zSeries machines have large branch
5874 instructions, so we never need to split a branch. */
5875 if (!TARGET_CPU_ZARCH && s390_split_branches ())
5878 s390_chunkify_cancel (pool);
5880 s390_mainpool_cancel (pool);
5885 /* If we made it up to here, both conditions are satisfied.
5886 Finish up literal pool related changes. */
5888 s390_chunkify_finish (pool);
5890 s390_mainpool_finish (pool);
5892 /* We're done splitting branches. */
5893 cfun->machine->split_branches_pending_p = false;
5897 s390_optimize_prologue ();
5901 /* Return an RTL expression representing the value of the return address
5902 for the frame COUNT steps up from the current frame. FRAME is the
5903 frame pointer of that frame. */
5906 s390_return_addr_rtx (int count, rtx frame ATTRIBUTE_UNUSED)
5911 /* Without backchain, we fail for all but the current frame. */
5913 if (!TARGET_BACKCHAIN && count > 0)
5916 /* For the current frame, we need to make sure the initial
5917 value of RETURN_REGNUM is actually saved. */
5921 cfun_frame_layout.save_return_addr_p = true;
5922 return gen_rtx_MEM (Pmode, return_address_pointer_rtx);
5925 if (TARGET_PACKED_STACK)
5926 offset = -2 * UNITS_PER_WORD;
5928 offset = RETURN_REGNUM * UNITS_PER_WORD;
5930 addr = plus_constant (frame, offset);
5931 addr = memory_address (Pmode, addr);
5932 return gen_rtx_MEM (Pmode, addr);
5935 /* Return an RTL expression representing the back chain stored in
5936 the current stack frame. */
5939 s390_back_chain_rtx (void)
5943 gcc_assert (TARGET_BACKCHAIN);
5945 if (TARGET_PACKED_STACK)
5946 chain = plus_constant (stack_pointer_rtx,
5947 STACK_POINTER_OFFSET - UNITS_PER_WORD);
5949 chain = stack_pointer_rtx;
5951 chain = gen_rtx_MEM (Pmode, chain);
5955 /* Find first call clobbered register unused in a function.
5956 This could be used as base register in a leaf function
5957 or for holding the return address before epilogue. */
5960 find_unused_clobbered_reg (void)
5963 for (i = 0; i < 6; i++)
5964 if (!regs_ever_live[i])
5969 /* Determine the frame area which actually has to be accessed
5970 in the function epilogue. The values are stored at the
5971 given pointers AREA_BOTTOM (address of the lowest used stack
5972 address) and AREA_TOP (address of the first item which does
5973 not belong to the stack frame). */
5976 s390_frame_area (int *area_bottom, int *area_top)
5984 if (cfun_frame_layout.first_restore_gpr != -1)
5986 b = (cfun_frame_layout.gprs_offset
5987 + cfun_frame_layout.first_restore_gpr * UNITS_PER_WORD);
5988 t = b + (cfun_frame_layout.last_restore_gpr
5989 - cfun_frame_layout.first_restore_gpr + 1) * UNITS_PER_WORD;
5992 if (TARGET_64BIT && cfun_save_high_fprs_p)
5994 b = MIN (b, cfun_frame_layout.f8_offset);
5995 t = MAX (t, (cfun_frame_layout.f8_offset
5996 + cfun_frame_layout.high_fprs * 8));
6000 for (i = 2; i < 4; i++)
6001 if (cfun_fpr_bit_p (i))
6003 b = MIN (b, cfun_frame_layout.f4_offset + (i - 2) * 8);
6004 t = MAX (t, cfun_frame_layout.f4_offset + (i - 1) * 8);
6011 /* Fill cfun->machine with info about register usage of current function.
6012 Return in LIVE_REGS which GPRs are currently considered live. */
6015 s390_register_info (int live_regs[])
6019 /* fprs 8 - 15 are call saved for 64 Bit ABI. */
6020 cfun_frame_layout.fpr_bitmap = 0;
6021 cfun_frame_layout.high_fprs = 0;
6023 for (i = 24; i < 32; i++)
6024 if (regs_ever_live[i] && !global_regs[i])
6026 cfun_set_fpr_bit (i - 16);
6027 cfun_frame_layout.high_fprs++;
6030 /* Find first and last gpr to be saved. We trust regs_ever_live
6031 data, except that we don't save and restore global registers.
6033 Also, all registers with special meaning to the compiler need
6034 to be handled extra. */
6036 for (i = 0; i < 16; i++)
6037 live_regs[i] = regs_ever_live[i] && !global_regs[i];
6040 live_regs[PIC_OFFSET_TABLE_REGNUM]
6041 = regs_ever_live[PIC_OFFSET_TABLE_REGNUM];
6043 live_regs[BASE_REGNUM]
6044 = cfun->machine->base_reg
6045 && REGNO (cfun->machine->base_reg) == BASE_REGNUM;
6047 live_regs[RETURN_REGNUM]
6048 = cfun->machine->split_branches_pending_p
6049 || cfun_frame_layout.save_return_addr_p;
6051 live_regs[STACK_POINTER_REGNUM]
6052 = !current_function_is_leaf
6053 || TARGET_TPF_PROFILING
6054 || cfun_save_high_fprs_p
6055 || get_frame_size () > 0
6056 || current_function_calls_alloca
6057 || current_function_stdarg;
6059 for (i = 6; i < 16; i++)
6062 for (j = 15; j > i; j--)
6068 /* Nothing to save/restore. */
6069 cfun_frame_layout.first_save_gpr = -1;
6070 cfun_frame_layout.first_restore_gpr = -1;
6071 cfun_frame_layout.last_save_gpr = -1;
6072 cfun_frame_layout.last_restore_gpr = -1;
6076 /* Save / Restore from gpr i to j. */
6077 cfun_frame_layout.first_save_gpr = i;
6078 cfun_frame_layout.first_restore_gpr = i;
6079 cfun_frame_layout.last_save_gpr = j;
6080 cfun_frame_layout.last_restore_gpr = j;
6083 if (current_function_stdarg)
6085 /* Varargs functions need to save gprs 2 to 6. */
6086 if (cfun_frame_layout.first_save_gpr == -1
6087 || cfun_frame_layout.first_save_gpr > 2)
6088 cfun_frame_layout.first_save_gpr = 2;
6090 if (cfun_frame_layout.last_save_gpr == -1
6091 || cfun_frame_layout.last_save_gpr < 6)
6092 cfun_frame_layout.last_save_gpr = 6;
6094 /* Mark f0, f2 for 31 bit and f0-f4 for 64 bit to be saved. */
6095 if (TARGET_HARD_FLOAT)
6096 for (i = 0; i < (TARGET_64BIT ? 4 : 2); i++)
6097 cfun_set_fpr_bit (i);
6101 for (i = 2; i < 4; i++)
6102 if (regs_ever_live[i + 16] && !global_regs[i + 16])
6103 cfun_set_fpr_bit (i);
6106 /* Fill cfun->machine with info about frame of current function. */
6109 s390_frame_info (void)
6113 cfun_frame_layout.frame_size = get_frame_size ();
6114 if (!TARGET_64BIT && cfun_frame_layout.frame_size > 0x7fff0000)
6115 fatal_error ("Total size of local variables exceeds architecture limit.");
6117 if (!TARGET_PACKED_STACK)
6119 cfun_frame_layout.backchain_offset = 0;
6120 cfun_frame_layout.f0_offset = 16 * UNITS_PER_WORD;
6121 cfun_frame_layout.f4_offset = cfun_frame_layout.f0_offset + 2 * 8;
6122 cfun_frame_layout.f8_offset = -cfun_frame_layout.high_fprs * 8;
6123 cfun_frame_layout.gprs_offset = (cfun_frame_layout.first_save_gpr
6126 else if (TARGET_BACKCHAIN) /* kernel stack layout */
6128 cfun_frame_layout.backchain_offset = (STACK_POINTER_OFFSET
6130 cfun_frame_layout.gprs_offset
6131 = (cfun_frame_layout.backchain_offset
6132 - (STACK_POINTER_REGNUM - cfun_frame_layout.first_save_gpr + 1)
6137 cfun_frame_layout.f4_offset
6138 = (cfun_frame_layout.gprs_offset
6139 - 8 * (cfun_fpr_bit_p (2) + cfun_fpr_bit_p (3)));
6141 cfun_frame_layout.f0_offset
6142 = (cfun_frame_layout.f4_offset
6143 - 8 * (cfun_fpr_bit_p (0) + cfun_fpr_bit_p (1)));
6147 /* On 31 bit we have to care about alignment of the
6148 floating point regs to provide fastest access. */
6149 cfun_frame_layout.f0_offset
6150 = ((cfun_frame_layout.gprs_offset
6151 & ~(STACK_BOUNDARY / BITS_PER_UNIT - 1))
6152 - 8 * (cfun_fpr_bit_p (0) + cfun_fpr_bit_p (1)));
6154 cfun_frame_layout.f4_offset
6155 = (cfun_frame_layout.f0_offset
6156 - 8 * (cfun_fpr_bit_p (2) + cfun_fpr_bit_p (3)));
6159 else /* no backchain */
6161 cfun_frame_layout.f4_offset
6162 = (STACK_POINTER_OFFSET
6163 - 8 * (cfun_fpr_bit_p (2) + cfun_fpr_bit_p (3)));
6165 cfun_frame_layout.f0_offset
6166 = (cfun_frame_layout.f4_offset
6167 - 8 * (cfun_fpr_bit_p (0) + cfun_fpr_bit_p (1)));
6169 cfun_frame_layout.gprs_offset
6170 = cfun_frame_layout.f0_offset - cfun_gprs_save_area_size;
6173 if (current_function_is_leaf
6174 && !TARGET_TPF_PROFILING
6175 && cfun_frame_layout.frame_size == 0
6176 && !cfun_save_high_fprs_p
6177 && !current_function_calls_alloca
6178 && !current_function_stdarg)
6181 if (!TARGET_PACKED_STACK)
6182 cfun_frame_layout.frame_size += (STARTING_FRAME_OFFSET
6183 + cfun_frame_layout.high_fprs * 8);
6186 if (TARGET_BACKCHAIN)
6187 cfun_frame_layout.frame_size += UNITS_PER_WORD;
6189 /* No alignment trouble here because f8-f15 are only saved under
6191 cfun_frame_layout.f8_offset = (MIN (MIN (cfun_frame_layout.f0_offset,
6192 cfun_frame_layout.f4_offset),
6193 cfun_frame_layout.gprs_offset)
6194 - cfun_frame_layout.high_fprs * 8);
6196 cfun_frame_layout.frame_size += cfun_frame_layout.high_fprs * 8;
6198 for (i = 0; i < 8; i++)
6199 if (cfun_fpr_bit_p (i))
6200 cfun_frame_layout.frame_size += 8;
6202 cfun_frame_layout.frame_size += cfun_gprs_save_area_size;
6204 /* If under 31 bit an odd number of gprs has to be saved we have to adjust
6205 the frame size to sustain 8 byte alignment of stack frames. */
6206 cfun_frame_layout.frame_size = ((cfun_frame_layout.frame_size +
6207 STACK_BOUNDARY / BITS_PER_UNIT - 1)
6208 & ~(STACK_BOUNDARY / BITS_PER_UNIT - 1));
6210 cfun_frame_layout.frame_size += current_function_outgoing_args_size;
6214 /* Generate frame layout. Fills in register and frame data for the current
6215 function in cfun->machine. This routine can be called multiple times;
6216 it will re-do the complete frame layout every time. */
6219 s390_init_frame_layout (void)
6221 HOST_WIDE_INT frame_size;
6225 /* If return address register is explicitly used, we need to save it. */
6226 if (regs_ever_live[RETURN_REGNUM]
6227 || !current_function_is_leaf
6228 || TARGET_TPF_PROFILING
6229 || current_function_stdarg
6230 || current_function_calls_eh_return)
6231 cfun_frame_layout.save_return_addr_p = true;
6233 /* On S/390 machines, we may need to perform branch splitting, which
6234 will require both base and return address register. We have no
6235 choice but to assume we're going to need them until right at the
6236 end of the machine dependent reorg phase. */
6237 if (!TARGET_CPU_ZARCH)
6238 cfun->machine->split_branches_pending_p = true;
6242 frame_size = cfun_frame_layout.frame_size;
6244 /* Try to predict whether we'll need the base register. */
6245 base_used = cfun->machine->split_branches_pending_p
6246 || current_function_uses_const_pool
6247 || (!DISP_IN_RANGE (-frame_size)
6248 && !CONST_OK_FOR_CONSTRAINT_P (-frame_size, 'K', "K"));
6250 /* Decide which register to use as literal pool base. In small
6251 leaf functions, try to use an unused call-clobbered register
6252 as base register to avoid save/restore overhead. */
6254 cfun->machine->base_reg = NULL_RTX;
6255 else if (current_function_is_leaf && !regs_ever_live[5])
6256 cfun->machine->base_reg = gen_rtx_REG (Pmode, 5);
6258 cfun->machine->base_reg = gen_rtx_REG (Pmode, BASE_REGNUM);
6260 s390_register_info (live_regs);
6263 while (frame_size != cfun_frame_layout.frame_size);
6266 /* Update frame layout. Recompute actual register save data based on
6267 current info and update regs_ever_live for the special registers.
6268 May be called multiple times, but may never cause *more* registers
6269 to be saved than s390_init_frame_layout allocated room for. */
6272 s390_update_frame_layout (void)
6276 s390_register_info (live_regs);
6278 regs_ever_live[BASE_REGNUM] = live_regs[BASE_REGNUM];
6279 regs_ever_live[RETURN_REGNUM] = live_regs[RETURN_REGNUM];
6280 regs_ever_live[STACK_POINTER_REGNUM] = live_regs[STACK_POINTER_REGNUM];
6282 if (cfun->machine->base_reg)
6283 regs_ever_live[REGNO (cfun->machine->base_reg)] = 1;
6286 /* Return true if register FROM can be eliminated via register TO. */
6289 s390_can_eliminate (int from, int to)
6291 gcc_assert (to == STACK_POINTER_REGNUM
6292 || to == HARD_FRAME_POINTER_REGNUM);
6294 gcc_assert (from == FRAME_POINTER_REGNUM
6295 || from == ARG_POINTER_REGNUM
6296 || from == RETURN_ADDRESS_POINTER_REGNUM);
6298 /* Make sure we actually saved the return address. */
6299 if (from == RETURN_ADDRESS_POINTER_REGNUM)
6300 if (!current_function_calls_eh_return
6301 && !current_function_stdarg
6302 && !cfun_frame_layout.save_return_addr_p)
6308 /* Return offset between register FROM and TO initially after prolog. */
6311 s390_initial_elimination_offset (int from, int to)
6313 HOST_WIDE_INT offset;
6316 /* ??? Why are we called for non-eliminable pairs? */
6317 if (!s390_can_eliminate (from, to))
6322 case FRAME_POINTER_REGNUM:
6326 case ARG_POINTER_REGNUM:
6327 s390_init_frame_layout ();
6328 offset = cfun_frame_layout.frame_size + STACK_POINTER_OFFSET;
6331 case RETURN_ADDRESS_POINTER_REGNUM:
6332 s390_init_frame_layout ();
6333 index = RETURN_REGNUM - cfun_frame_layout.first_save_gpr;
6334 gcc_assert (index >= 0);
6335 offset = cfun_frame_layout.frame_size + cfun_frame_layout.gprs_offset;
6336 offset += index * UNITS_PER_WORD;
6346 /* Emit insn to save fpr REGNUM at offset OFFSET relative
6347 to register BASE. Return generated insn. */
6350 save_fpr (rtx base, int offset, int regnum)
6353 addr = gen_rtx_MEM (DFmode, plus_constant (base, offset));
6354 set_mem_alias_set (addr, s390_sr_alias_set);
6356 return emit_move_insn (addr, gen_rtx_REG (DFmode, regnum));
6359 /* Emit insn to restore fpr REGNUM from offset OFFSET relative
6360 to register BASE. Return generated insn. */
6363 restore_fpr (rtx base, int offset, int regnum)
6366 addr = gen_rtx_MEM (DFmode, plus_constant (base, offset));
6367 set_mem_alias_set (addr, s390_sr_alias_set);
6369 return emit_move_insn (gen_rtx_REG (DFmode, regnum), addr);
6372 /* Generate insn to save registers FIRST to LAST into
6373 the register save area located at offset OFFSET
6374 relative to register BASE. */
6377 save_gprs (rtx base, int offset, int first, int last)
6379 rtx addr, insn, note;
6382 addr = plus_constant (base, offset);
6383 addr = gen_rtx_MEM (Pmode, addr);
6384 set_mem_alias_set (addr, s390_sr_alias_set);
6386 /* Special-case single register. */
6390 insn = gen_movdi (addr, gen_rtx_REG (Pmode, first));
6392 insn = gen_movsi (addr, gen_rtx_REG (Pmode, first));
6394 RTX_FRAME_RELATED_P (insn) = 1;
6399 insn = gen_store_multiple (addr,
6400 gen_rtx_REG (Pmode, first),
6401 GEN_INT (last - first + 1));
6404 /* We need to set the FRAME_RELATED flag on all SETs
6405 inside the store-multiple pattern.
6407 However, we must not emit DWARF records for registers 2..5
6408 if they are stored for use by variable arguments ...
6410 ??? Unfortunately, it is not enough to simply not the the
6411 FRAME_RELATED flags for those SETs, because the first SET
6412 of the PARALLEL is always treated as if it had the flag
6413 set, even if it does not. Therefore we emit a new pattern
6414 without those registers as REG_FRAME_RELATED_EXPR note. */
6418 rtx pat = PATTERN (insn);
6420 for (i = 0; i < XVECLEN (pat, 0); i++)
6421 if (GET_CODE (XVECEXP (pat, 0, i)) == SET)
6422 RTX_FRAME_RELATED_P (XVECEXP (pat, 0, i)) = 1;
6424 RTX_FRAME_RELATED_P (insn) = 1;
6428 addr = plus_constant (base, offset + (6 - first) * UNITS_PER_WORD);
6429 note = gen_store_multiple (gen_rtx_MEM (Pmode, addr),
6430 gen_rtx_REG (Pmode, 6),
6431 GEN_INT (last - 6 + 1));
6432 note = PATTERN (note);
6435 gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
6436 note, REG_NOTES (insn));
6438 for (i = 0; i < XVECLEN (note, 0); i++)
6439 if (GET_CODE (XVECEXP (note, 0, i)) == SET)
6440 RTX_FRAME_RELATED_P (XVECEXP (note, 0, i)) = 1;
6442 RTX_FRAME_RELATED_P (insn) = 1;
6448 /* Generate insn to restore registers FIRST to LAST from
6449 the register save area located at offset OFFSET
6450 relative to register BASE. */
6453 restore_gprs (rtx base, int offset, int first, int last)
6457 addr = plus_constant (base, offset);
6458 addr = gen_rtx_MEM (Pmode, addr);
6459 set_mem_alias_set (addr, s390_sr_alias_set);
6461 /* Special-case single register. */
6465 insn = gen_movdi (gen_rtx_REG (Pmode, first), addr);
6467 insn = gen_movsi (gen_rtx_REG (Pmode, first), addr);
6472 insn = gen_load_multiple (gen_rtx_REG (Pmode, first),
6474 GEN_INT (last - first + 1));
6478 /* Return insn sequence to load the GOT register. */
6480 static GTY(()) rtx got_symbol;
6482 s390_load_got (void)
6488 got_symbol = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
6489 SYMBOL_REF_FLAGS (got_symbol) = SYMBOL_FLAG_LOCAL;
6494 if (TARGET_CPU_ZARCH)
6496 emit_move_insn (pic_offset_table_rtx, got_symbol);
6502 offset = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, got_symbol),
6503 UNSPEC_LTREL_OFFSET);
6504 offset = gen_rtx_CONST (Pmode, offset);
6505 offset = force_const_mem (Pmode, offset);
6507 emit_move_insn (pic_offset_table_rtx, offset);
6509 offset = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, XEXP (offset, 0)),
6511 offset = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, offset);
6513 emit_move_insn (pic_offset_table_rtx, offset);
6516 insns = get_insns ();
6521 /* Expand the prologue into a bunch of separate insns. */
6524 s390_emit_prologue (void)
6532 /* Complete frame layout. */
6534 s390_update_frame_layout ();
6536 /* Annotate all constant pool references to let the scheduler know
6537 they implicitly use the base register. */
6539 push_topmost_sequence ();
6541 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
6543 annotate_constant_pool_refs (&PATTERN (insn));
6545 pop_topmost_sequence ();
6547 /* Choose best register to use for temp use within prologue.
6548 See below for why TPF must use the register 1. */
6550 if (!current_function_is_leaf && !TARGET_TPF_PROFILING)
6551 temp_reg = gen_rtx_REG (Pmode, RETURN_REGNUM);
6553 temp_reg = gen_rtx_REG (Pmode, 1);
6555 /* Save call saved gprs. */
6556 if (cfun_frame_layout.first_save_gpr != -1)
6558 insn = save_gprs (stack_pointer_rtx,
6559 cfun_frame_layout.gprs_offset,
6560 cfun_frame_layout.first_save_gpr,
6561 cfun_frame_layout.last_save_gpr);
6565 /* Dummy insn to mark literal pool slot. */
6567 if (cfun->machine->base_reg)
6568 emit_insn (gen_main_pool (cfun->machine->base_reg));
6570 offset = cfun_frame_layout.f0_offset;
6572 /* Save f0 and f2. */
6573 for (i = 0; i < 2; i++)
6575 if (cfun_fpr_bit_p (i))
6577 save_fpr (stack_pointer_rtx, offset, i + 16);
6580 else if (!TARGET_PACKED_STACK)
6584 /* Save f4 and f6. */
6585 offset = cfun_frame_layout.f4_offset;
6586 for (i = 2; i < 4; i++)
6588 if (cfun_fpr_bit_p (i))
6590 insn = save_fpr (stack_pointer_rtx, offset, i + 16);
6593 /* If f4 and f6 are call clobbered they are saved due to stdargs and
6594 therefore are not frame related. */
6595 if (!call_really_used_regs[i + 16])
6596 RTX_FRAME_RELATED_P (insn) = 1;
6598 else if (!TARGET_PACKED_STACK)
6602 if (TARGET_PACKED_STACK
6603 && cfun_save_high_fprs_p
6604 && cfun_frame_layout.f8_offset + cfun_frame_layout.high_fprs * 8 > 0)
6606 offset = (cfun_frame_layout.f8_offset
6607 + (cfun_frame_layout.high_fprs - 1) * 8);
6609 for (i = 15; i > 7 && offset >= 0; i--)
6610 if (cfun_fpr_bit_p (i))
6612 insn = save_fpr (stack_pointer_rtx, offset, i + 16);
6614 RTX_FRAME_RELATED_P (insn) = 1;
6617 if (offset >= cfun_frame_layout.f8_offset)
6621 if (!TARGET_PACKED_STACK)
6622 next_fpr = cfun_save_high_fprs_p ? 31 : 0;
6624 /* Decrement stack pointer. */
6626 if (cfun_frame_layout.frame_size > 0)
6628 rtx frame_off = GEN_INT (-cfun_frame_layout.frame_size);
6630 if (s390_stack_size)
6632 HOST_WIDE_INT stack_check_mask = ((s390_stack_size - 1)
6633 & ~(s390_stack_guard - 1));
6634 rtx t = gen_rtx_AND (Pmode, stack_pointer_rtx,
6635 GEN_INT (stack_check_mask));
6638 gen_cmpdi (t, const0_rtx);
6640 gen_cmpsi (t, const0_rtx);
6642 emit_insn (gen_conditional_trap (gen_rtx_EQ (CCmode,
6643 gen_rtx_REG (CCmode,
6649 if (s390_warn_framesize > 0
6650 && cfun_frame_layout.frame_size >= s390_warn_framesize)
6651 warning ("frame size of %qs is " HOST_WIDE_INT_PRINT_DEC " bytes",
6652 current_function_name (), cfun_frame_layout.frame_size);
6654 if (s390_warn_dynamicstack_p && cfun->calls_alloca)
6655 warning ("%qs uses dynamic stack allocation", current_function_name ());
6657 /* Save incoming stack pointer into temp reg. */
6658 if (TARGET_BACKCHAIN || next_fpr)
6659 insn = emit_insn (gen_move_insn (temp_reg, stack_pointer_rtx));
6661 /* Subtract frame size from stack pointer. */
6663 if (DISP_IN_RANGE (INTVAL (frame_off)))
6665 insn = gen_rtx_SET (VOIDmode, stack_pointer_rtx,
6666 gen_rtx_PLUS (Pmode, stack_pointer_rtx,
6668 insn = emit_insn (insn);
6672 if (!CONST_OK_FOR_CONSTRAINT_P (INTVAL (frame_off), 'K', "K"))
6673 frame_off = force_const_mem (Pmode, frame_off);
6675 insn = emit_insn (gen_add2_insn (stack_pointer_rtx, frame_off));
6676 annotate_constant_pool_refs (&PATTERN (insn));
6679 RTX_FRAME_RELATED_P (insn) = 1;
6681 gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
6682 gen_rtx_SET (VOIDmode, stack_pointer_rtx,
6683 gen_rtx_PLUS (Pmode, stack_pointer_rtx,
6684 GEN_INT (-cfun_frame_layout.frame_size))),
6687 /* Set backchain. */
6689 if (TARGET_BACKCHAIN)
6691 if (cfun_frame_layout.backchain_offset)
6692 addr = gen_rtx_MEM (Pmode,
6693 plus_constant (stack_pointer_rtx,
6694 cfun_frame_layout.backchain_offset));
6696 addr = gen_rtx_MEM (Pmode, stack_pointer_rtx);
6697 set_mem_alias_set (addr, s390_sr_alias_set);
6698 insn = emit_insn (gen_move_insn (addr, temp_reg));
6701 /* If we support asynchronous exceptions (e.g. for Java),
6702 we need to make sure the backchain pointer is set up
6703 before any possibly trapping memory access. */
6705 if (TARGET_BACKCHAIN && flag_non_call_exceptions)
6707 addr = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (VOIDmode));
6708 emit_insn (gen_rtx_CLOBBER (VOIDmode, addr));
6712 /* Save fprs 8 - 15 (64 bit ABI). */
6714 if (cfun_save_high_fprs_p && next_fpr)
6716 insn = emit_insn (gen_add2_insn (temp_reg,
6717 GEN_INT (cfun_frame_layout.f8_offset)));
6721 for (i = 24; i <= next_fpr; i++)
6722 if (cfun_fpr_bit_p (i - 16))
6724 rtx addr = plus_constant (stack_pointer_rtx,
6725 cfun_frame_layout.frame_size
6726 + cfun_frame_layout.f8_offset
6729 insn = save_fpr (temp_reg, offset, i);
6731 RTX_FRAME_RELATED_P (insn) = 1;
6733 gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
6734 gen_rtx_SET (VOIDmode,
6735 gen_rtx_MEM (DFmode, addr),
6736 gen_rtx_REG (DFmode, i)),
6741 /* Set frame pointer, if needed. */
6743 if (frame_pointer_needed)
6745 insn = emit_move_insn (hard_frame_pointer_rtx, stack_pointer_rtx);
6746 RTX_FRAME_RELATED_P (insn) = 1;
6749 /* Set up got pointer, if needed. */
6751 if (flag_pic && regs_ever_live[PIC_OFFSET_TABLE_REGNUM])
6753 rtx insns = s390_load_got ();
6755 for (insn = insns; insn; insn = NEXT_INSN (insn))
6757 annotate_constant_pool_refs (&PATTERN (insn));
6759 REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_MAYBE_DEAD, NULL_RTX,
6766 if (TARGET_TPF_PROFILING)
6768 /* Generate a BAS instruction to serve as a function
6769 entry intercept to facilitate the use of tracing
6770 algorithms located at the branch target. */
6771 emit_insn (gen_prologue_tpf ());
6773 /* Emit a blockage here so that all code
6774 lies between the profiling mechanisms. */
6775 emit_insn (gen_blockage ());
6779 /* Expand the epilogue into a bunch of separate insns. */
6782 s390_emit_epilogue (bool sibcall)
6784 rtx frame_pointer, return_reg;
6785 int area_bottom, area_top, offset = 0;
6790 if (TARGET_TPF_PROFILING)
6793 /* Generate a BAS instruction to serve as a function
6794 entry intercept to facilitate the use of tracing
6795 algorithms located at the branch target. */
6797 /* Emit a blockage here so that all code
6798 lies between the profiling mechanisms. */
6799 emit_insn (gen_blockage ());
6801 emit_insn (gen_epilogue_tpf ());
6804 /* Check whether to use frame or stack pointer for restore. */
6806 frame_pointer = (frame_pointer_needed
6807 ? hard_frame_pointer_rtx : stack_pointer_rtx);
6809 s390_frame_area (&area_bottom, &area_top);
6811 /* Check whether we can access the register save area.
6812 If not, increment the frame pointer as required. */
6814 if (area_top <= area_bottom)
6816 /* Nothing to restore. */
6818 else if (DISP_IN_RANGE (cfun_frame_layout.frame_size + area_bottom)
6819 && DISP_IN_RANGE (cfun_frame_layout.frame_size + area_top - 1))
6821 /* Area is in range. */
6822 offset = cfun_frame_layout.frame_size;
6826 rtx insn, frame_off;
6828 offset = area_bottom < 0 ? -area_bottom : 0;
6829 frame_off = GEN_INT (cfun_frame_layout.frame_size - offset);
6831 if (DISP_IN_RANGE (INTVAL (frame_off)))
6833 insn = gen_rtx_SET (VOIDmode, frame_pointer,
6834 gen_rtx_PLUS (Pmode, frame_pointer, frame_off));
6835 insn = emit_insn (insn);
6839 if (!CONST_OK_FOR_CONSTRAINT_P (INTVAL (frame_off), 'K', "K"))
6840 frame_off = force_const_mem (Pmode, frame_off);
6842 insn = emit_insn (gen_add2_insn (frame_pointer, frame_off));
6843 annotate_constant_pool_refs (&PATTERN (insn));
6847 /* Restore call saved fprs. */
6851 if (cfun_save_high_fprs_p)
6853 next_offset = cfun_frame_layout.f8_offset;
6854 for (i = 24; i < 32; i++)
6856 if (cfun_fpr_bit_p (i - 16))
6858 restore_fpr (frame_pointer,
6859 offset + next_offset, i);
6868 next_offset = cfun_frame_layout.f4_offset;
6869 for (i = 18; i < 20; i++)
6871 if (cfun_fpr_bit_p (i - 16))
6873 restore_fpr (frame_pointer,
6874 offset + next_offset, i);
6877 else if (!TARGET_PACKED_STACK)
6883 /* Return register. */
6885 return_reg = gen_rtx_REG (Pmode, RETURN_REGNUM);
6887 /* Restore call saved gprs. */
6889 if (cfun_frame_layout.first_restore_gpr != -1)
6894 /* Check for global register and save them
6895 to stack location from where they get restored. */
6897 for (i = cfun_frame_layout.first_restore_gpr;
6898 i <= cfun_frame_layout.last_restore_gpr;
6901 /* These registers are special and need to be
6902 restored in any case. */
6903 if (i == STACK_POINTER_REGNUM
6904 || i == RETURN_REGNUM
6906 || (flag_pic && i == (int)PIC_OFFSET_TABLE_REGNUM))
6911 addr = plus_constant (frame_pointer,
6912 offset + cfun_frame_layout.gprs_offset
6913 + (i - cfun_frame_layout.first_save_gpr)
6915 addr = gen_rtx_MEM (Pmode, addr);
6916 set_mem_alias_set (addr, s390_sr_alias_set);
6917 emit_move_insn (addr, gen_rtx_REG (Pmode, i));
6923 /* Fetch return address from stack before load multiple,
6924 this will do good for scheduling. */
6926 if (cfun_frame_layout.save_return_addr_p
6927 || (cfun_frame_layout.first_restore_gpr < BASE_REGNUM
6928 && cfun_frame_layout.last_restore_gpr > RETURN_REGNUM))
6930 int return_regnum = find_unused_clobbered_reg();
6933 return_reg = gen_rtx_REG (Pmode, return_regnum);
6935 addr = plus_constant (frame_pointer,
6936 offset + cfun_frame_layout.gprs_offset
6938 - cfun_frame_layout.first_save_gpr)
6940 addr = gen_rtx_MEM (Pmode, addr);
6941 set_mem_alias_set (addr, s390_sr_alias_set);
6942 emit_move_insn (return_reg, addr);
6946 insn = restore_gprs (frame_pointer,
6947 offset + cfun_frame_layout.gprs_offset
6948 + (cfun_frame_layout.first_restore_gpr
6949 - cfun_frame_layout.first_save_gpr)
6951 cfun_frame_layout.first_restore_gpr,
6952 cfun_frame_layout.last_restore_gpr);
6959 /* Return to caller. */
6961 p = rtvec_alloc (2);
6963 RTVEC_ELT (p, 0) = gen_rtx_RETURN (VOIDmode);
6964 RTVEC_ELT (p, 1) = gen_rtx_USE (VOIDmode, return_reg);
6965 emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, p));
6970 /* Return the size in bytes of a function argument of
6971 type TYPE and/or mode MODE. At least one of TYPE or
6972 MODE must be specified. */
6975 s390_function_arg_size (enum machine_mode mode, tree type)
6978 return int_size_in_bytes (type);
6980 /* No type info available for some library calls ... */
6981 if (mode != BLKmode)
6982 return GET_MODE_SIZE (mode);
6984 /* If we have neither type nor mode, abort */
6988 /* Return true if a function argument of type TYPE and mode MODE
6989 is to be passed in a floating-point register, if available. */
6992 s390_function_arg_float (enum machine_mode mode, tree type)
6994 int size = s390_function_arg_size (mode, type);
6998 /* Soft-float changes the ABI: no floating-point registers are used. */
6999 if (TARGET_SOFT_FLOAT)
7002 /* No type info available for some library calls ... */
7004 return mode == SFmode || mode == DFmode;
7006 /* The ABI says that record types with a single member are treated
7007 just like that member would be. */
7008 while (TREE_CODE (type) == RECORD_TYPE)
7010 tree field, single = NULL_TREE;
7012 for (field = TYPE_FIELDS (type); field; field = TREE_CHAIN (field))
7014 if (TREE_CODE (field) != FIELD_DECL)
7017 if (single == NULL_TREE)
7018 single = TREE_TYPE (field);
7023 if (single == NULL_TREE)
7029 return TREE_CODE (type) == REAL_TYPE;
7032 /* Return true if a function argument of type TYPE and mode MODE
7033 is to be passed in an integer register, or a pair of integer
7034 registers, if available. */
7037 s390_function_arg_integer (enum machine_mode mode, tree type)
7039 int size = s390_function_arg_size (mode, type);
7043 /* No type info available for some library calls ... */
7045 return GET_MODE_CLASS (mode) == MODE_INT
7046 || (TARGET_SOFT_FLOAT && GET_MODE_CLASS (mode) == MODE_FLOAT);
7048 /* We accept small integral (and similar) types. */
7049 if (INTEGRAL_TYPE_P (type)
7050 || POINTER_TYPE_P (type)
7051 || TREE_CODE (type) == OFFSET_TYPE
7052 || (TARGET_SOFT_FLOAT && TREE_CODE (type) == REAL_TYPE))
7055 /* We also accept structs of size 1, 2, 4, 8 that are not
7056 passed in floating-point registers. */
7057 if (AGGREGATE_TYPE_P (type)
7058 && exact_log2 (size) >= 0
7059 && !s390_function_arg_float (mode, type))
7065 /* Return 1 if a function argument of type TYPE and mode MODE
7066 is to be passed by reference. The ABI specifies that only
7067 structures of size 1, 2, 4, or 8 bytes are passed by value,
7068 all other structures (and complex numbers) are passed by
7072 s390_pass_by_reference (CUMULATIVE_ARGS *ca ATTRIBUTE_UNUSED,
7073 enum machine_mode mode, tree type,
7074 bool named ATTRIBUTE_UNUSED)
7076 int size = s390_function_arg_size (mode, type);
7082 if (AGGREGATE_TYPE_P (type) && exact_log2 (size) < 0)
7085 if (TREE_CODE (type) == COMPLEX_TYPE
7086 || TREE_CODE (type) == VECTOR_TYPE)
7093 /* Update the data in CUM to advance over an argument of mode MODE and
7094 data type TYPE. (TYPE is null for libcalls where that information
7095 may not be available.). The boolean NAMED specifies whether the
7096 argument is a named argument (as opposed to an unnamed argument
7097 matching an ellipsis). */
7100 s390_function_arg_advance (CUMULATIVE_ARGS *cum, enum machine_mode mode,
7101 tree type, int named ATTRIBUTE_UNUSED)
7103 if (s390_function_arg_float (mode, type))
7107 else if (s390_function_arg_integer (mode, type))
7109 int size = s390_function_arg_size (mode, type);
7110 cum->gprs += ((size + UNITS_PER_WORD-1) / UNITS_PER_WORD);
7116 /* Define where to put the arguments to a function.
7117 Value is zero to push the argument on the stack,
7118 or a hard register in which to store the argument.
7120 MODE is the argument's machine mode.
7121 TYPE is the data type of the argument (as a tree).
7122 This is null for libcalls where that information may
7124 CUM is a variable of type CUMULATIVE_ARGS which gives info about
7125 the preceding args and about the function being called.
7126 NAMED is nonzero if this argument is a named parameter
7127 (otherwise it is an extra parameter matching an ellipsis).
7129 On S/390, we use general purpose registers 2 through 6 to
7130 pass integer, pointer, and certain structure arguments, and
7131 floating point registers 0 and 2 (0, 2, 4, and 6 on 64-bit)
7132 to pass floating point arguments. All remaining arguments
7133 are pushed to the stack. */
7136 s390_function_arg (CUMULATIVE_ARGS *cum, enum machine_mode mode, tree type,
7137 int named ATTRIBUTE_UNUSED)
7139 if (s390_function_arg_float (mode, type))
7141 if (cum->fprs + 1 > (TARGET_64BIT? 4 : 2))
7144 return gen_rtx_REG (mode, cum->fprs + 16);
7146 else if (s390_function_arg_integer (mode, type))
7148 int size = s390_function_arg_size (mode, type);
7149 int n_gprs = (size + UNITS_PER_WORD-1) / UNITS_PER_WORD;
7151 if (cum->gprs + n_gprs > 5)
7154 return gen_rtx_REG (mode, cum->gprs + 2);
7157 /* After the real arguments, expand_call calls us once again
7158 with a void_type_node type. Whatever we return here is
7159 passed as operand 2 to the call expanders.
7161 We don't need this feature ... */
7162 else if (type == void_type_node)
7168 /* Return true if return values of type TYPE should be returned
7169 in a memory buffer whose address is passed by the caller as
7170 hidden first argument. */
7173 s390_return_in_memory (tree type, tree fundecl ATTRIBUTE_UNUSED)
7175 /* We accept small integral (and similar) types. */
7176 if (INTEGRAL_TYPE_P (type)
7177 || POINTER_TYPE_P (type)
7178 || TREE_CODE (type) == OFFSET_TYPE
7179 || TREE_CODE (type) == REAL_TYPE)
7180 return int_size_in_bytes (type) > 8;
7182 /* Aggregates and similar constructs are always returned
7184 if (AGGREGATE_TYPE_P (type)
7185 || TREE_CODE (type) == COMPLEX_TYPE
7186 || TREE_CODE (type) == VECTOR_TYPE)
7189 /* ??? We get called on all sorts of random stuff from
7190 aggregate_value_p. We can't abort, but it's not clear
7191 what's safe to return. Pretend it's a struct I guess. */
7195 /* Define where to return a (scalar) value of type TYPE.
7196 If TYPE is null, define where to return a (scalar)
7197 value of mode MODE from a libcall. */
7200 s390_function_value (tree type, enum machine_mode mode)
7204 int unsignedp = TYPE_UNSIGNED (type);
7205 mode = promote_mode (type, TYPE_MODE (type), &unsignedp, 1);
7208 if (GET_MODE_CLASS (mode) != MODE_INT
7209 && GET_MODE_CLASS (mode) != MODE_FLOAT)
7211 if (GET_MODE_SIZE (mode) > 8)
7214 if (TARGET_HARD_FLOAT && GET_MODE_CLASS (mode) == MODE_FLOAT)
7215 return gen_rtx_REG (mode, 16);
7217 return gen_rtx_REG (mode, 2);
7221 /* Create and return the va_list datatype.
7223 On S/390, va_list is an array type equivalent to
7225 typedef struct __va_list_tag
7229 void *__overflow_arg_area;
7230 void *__reg_save_area;
7233 where __gpr and __fpr hold the number of general purpose
7234 or floating point arguments used up to now, respectively,
7235 __overflow_arg_area points to the stack location of the
7236 next argument passed on the stack, and __reg_save_area
7237 always points to the start of the register area in the
7238 call frame of the current function. The function prologue
7239 saves all registers used for argument passing into this
7240 area if the function uses variable arguments. */
7243 s390_build_builtin_va_list (void)
7245 tree f_gpr, f_fpr, f_ovf, f_sav, record, type_decl;
7247 record = lang_hooks.types.make_type (RECORD_TYPE);
7250 build_decl (TYPE_DECL, get_identifier ("__va_list_tag"), record);
7252 f_gpr = build_decl (FIELD_DECL, get_identifier ("__gpr"),
7253 long_integer_type_node);
7254 f_fpr = build_decl (FIELD_DECL, get_identifier ("__fpr"),
7255 long_integer_type_node);
7256 f_ovf = build_decl (FIELD_DECL, get_identifier ("__overflow_arg_area"),
7258 f_sav = build_decl (FIELD_DECL, get_identifier ("__reg_save_area"),
7261 DECL_FIELD_CONTEXT (f_gpr) = record;
7262 DECL_FIELD_CONTEXT (f_fpr) = record;
7263 DECL_FIELD_CONTEXT (f_ovf) = record;
7264 DECL_FIELD_CONTEXT (f_sav) = record;
7266 TREE_CHAIN (record) = type_decl;
7267 TYPE_NAME (record) = type_decl;
7268 TYPE_FIELDS (record) = f_gpr;
7269 TREE_CHAIN (f_gpr) = f_fpr;
7270 TREE_CHAIN (f_fpr) = f_ovf;
7271 TREE_CHAIN (f_ovf) = f_sav;
7273 layout_type (record);
7275 /* The correct type is an array type of one element. */
7276 return build_array_type (record, build_index_type (size_zero_node));
7279 /* Implement va_start by filling the va_list structure VALIST.
7280 STDARG_P is always true, and ignored.
7281 NEXTARG points to the first anonymous stack argument.
7283 The following global variables are used to initialize
7284 the va_list structure:
7286 current_function_args_info:
7287 holds number of gprs and fprs used for named arguments.
7288 current_function_arg_offset_rtx:
7289 holds the offset of the first anonymous stack argument
7290 (relative to the virtual arg pointer). */
7293 s390_va_start (tree valist, rtx nextarg ATTRIBUTE_UNUSED)
7295 HOST_WIDE_INT n_gpr, n_fpr;
7297 tree f_gpr, f_fpr, f_ovf, f_sav;
7298 tree gpr, fpr, ovf, sav, t;
7300 f_gpr = TYPE_FIELDS (TREE_TYPE (va_list_type_node));
7301 f_fpr = TREE_CHAIN (f_gpr);
7302 f_ovf = TREE_CHAIN (f_fpr);
7303 f_sav = TREE_CHAIN (f_ovf);
7305 valist = build_va_arg_indirect_ref (valist);
7306 gpr = build (COMPONENT_REF, TREE_TYPE (f_gpr), valist, f_gpr, NULL_TREE);
7307 fpr = build (COMPONENT_REF, TREE_TYPE (f_fpr), valist, f_fpr, NULL_TREE);
7308 ovf = build (COMPONENT_REF, TREE_TYPE (f_ovf), valist, f_ovf, NULL_TREE);
7309 sav = build (COMPONENT_REF, TREE_TYPE (f_sav), valist, f_sav, NULL_TREE);
7311 /* Count number of gp and fp argument registers used. */
7313 n_gpr = current_function_args_info.gprs;
7314 n_fpr = current_function_args_info.fprs;
7316 t = build (MODIFY_EXPR, TREE_TYPE (gpr), gpr,
7317 build_int_cst (NULL_TREE, n_gpr));
7318 TREE_SIDE_EFFECTS (t) = 1;
7319 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
7321 t = build (MODIFY_EXPR, TREE_TYPE (fpr), fpr,
7322 build_int_cst (NULL_TREE, n_fpr));
7323 TREE_SIDE_EFFECTS (t) = 1;
7324 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
7326 /* Find the overflow area. */
7327 t = make_tree (TREE_TYPE (ovf), virtual_incoming_args_rtx);
7329 off = INTVAL (current_function_arg_offset_rtx);
7330 off = off < 0 ? 0 : off;
7331 if (TARGET_DEBUG_ARG)
7332 fprintf (stderr, "va_start: n_gpr = %d, n_fpr = %d off %d\n",
7333 (int)n_gpr, (int)n_fpr, off);
7335 t = build (PLUS_EXPR, TREE_TYPE (ovf), t, build_int_cst (NULL_TREE, off));
7337 t = build (MODIFY_EXPR, TREE_TYPE (ovf), ovf, t);
7338 TREE_SIDE_EFFECTS (t) = 1;
7339 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
7341 /* Find the register save area. */
7342 t = make_tree (TREE_TYPE (sav), return_address_pointer_rtx);
7343 t = build (PLUS_EXPR, TREE_TYPE (sav), t,
7344 build_int_cst (NULL_TREE, -RETURN_REGNUM * UNITS_PER_WORD));
7346 t = build (MODIFY_EXPR, TREE_TYPE (sav), sav, t);
7347 TREE_SIDE_EFFECTS (t) = 1;
7348 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
7351 /* Implement va_arg by updating the va_list structure
7352 VALIST as required to retrieve an argument of type
7353 TYPE, and returning that argument.
7355 Generates code equivalent to:
7357 if (integral value) {
7358 if (size <= 4 && args.gpr < 5 ||
7359 size > 4 && args.gpr < 4 )
7360 ret = args.reg_save_area[args.gpr+8]
7362 ret = *args.overflow_arg_area++;
7363 } else if (float value) {
7365 ret = args.reg_save_area[args.fpr+64]
7367 ret = *args.overflow_arg_area++;
7368 } else if (aggregate value) {
7370 ret = *args.reg_save_area[args.gpr]
7372 ret = **args.overflow_arg_area++;
7376 s390_gimplify_va_arg (tree valist, tree type, tree *pre_p,
7377 tree *post_p ATTRIBUTE_UNUSED)
7379 tree f_gpr, f_fpr, f_ovf, f_sav;
7380 tree gpr, fpr, ovf, sav, reg, t, u;
7381 int indirect_p, size, n_reg, sav_ofs, sav_scale, max_reg;
7382 tree lab_false, lab_over, addr;
7384 f_gpr = TYPE_FIELDS (TREE_TYPE (va_list_type_node));
7385 f_fpr = TREE_CHAIN (f_gpr);
7386 f_ovf = TREE_CHAIN (f_fpr);
7387 f_sav = TREE_CHAIN (f_ovf);
7389 valist = build_va_arg_indirect_ref (valist);
7390 gpr = build (COMPONENT_REF, TREE_TYPE (f_gpr), valist, f_gpr, NULL_TREE);
7391 fpr = build (COMPONENT_REF, TREE_TYPE (f_fpr), valist, f_fpr, NULL_TREE);
7392 ovf = build (COMPONENT_REF, TREE_TYPE (f_ovf), valist, f_ovf, NULL_TREE);
7393 sav = build (COMPONENT_REF, TREE_TYPE (f_sav), valist, f_sav, NULL_TREE);
7395 size = int_size_in_bytes (type);
7397 if (pass_by_reference (NULL, TYPE_MODE (type), type, false))
7399 if (TARGET_DEBUG_ARG)
7401 fprintf (stderr, "va_arg: aggregate type");
7405 /* Aggregates are passed by reference. */
7410 /* kernel stack layout on 31 bit: It is assumed here that no padding
7411 will be added by s390_frame_info because for va_args always an even
7412 number of gprs has to be saved r15-r2 = 14 regs. */
7413 sav_ofs = 2 * UNITS_PER_WORD;
7414 sav_scale = UNITS_PER_WORD;
7415 size = UNITS_PER_WORD;
7418 else if (s390_function_arg_float (TYPE_MODE (type), type))
7420 if (TARGET_DEBUG_ARG)
7422 fprintf (stderr, "va_arg: float type");
7426 /* FP args go in FP registers, if present. */
7430 sav_ofs = 16 * UNITS_PER_WORD;
7432 /* TARGET_64BIT has up to 4 parameter in fprs */
7433 max_reg = TARGET_64BIT ? 3 : 1;
7437 if (TARGET_DEBUG_ARG)
7439 fprintf (stderr, "va_arg: other type");
7443 /* Otherwise into GP registers. */
7446 n_reg = (size + UNITS_PER_WORD - 1) / UNITS_PER_WORD;
7448 /* kernel stack layout on 31 bit: It is assumed here that no padding
7449 will be added by s390_frame_info because for va_args always an even
7450 number of gprs has to be saved r15-r2 = 14 regs. */
7451 sav_ofs = 2 * UNITS_PER_WORD;
7453 if (size < UNITS_PER_WORD)
7454 sav_ofs += UNITS_PER_WORD - size;
7456 sav_scale = UNITS_PER_WORD;
7463 /* Pull the value out of the saved registers ... */
7465 lab_false = create_artificial_label ();
7466 lab_over = create_artificial_label ();
7467 addr = create_tmp_var (ptr_type_node, "addr");
7468 DECL_POINTER_ALIAS_SET (addr) = s390_sr_alias_set;
7470 t = fold_convert (TREE_TYPE (reg), size_int (max_reg));
7471 t = build2 (GT_EXPR, boolean_type_node, reg, t);
7472 u = build1 (GOTO_EXPR, void_type_node, lab_false);
7473 t = build3 (COND_EXPR, void_type_node, t, u, NULL_TREE);
7474 gimplify_and_add (t, pre_p);
7476 t = build2 (PLUS_EXPR, ptr_type_node, sav,
7477 fold_convert (ptr_type_node, size_int (sav_ofs)));
7478 u = build2 (MULT_EXPR, TREE_TYPE (reg), reg,
7479 fold_convert (TREE_TYPE (reg), size_int (sav_scale)));
7480 t = build2 (PLUS_EXPR, ptr_type_node, t, fold_convert (ptr_type_node, u));
7482 t = build2 (MODIFY_EXPR, void_type_node, addr, t);
7483 gimplify_and_add (t, pre_p);
7485 t = build1 (GOTO_EXPR, void_type_node, lab_over);
7486 gimplify_and_add (t, pre_p);
7488 t = build1 (LABEL_EXPR, void_type_node, lab_false);
7489 append_to_statement_list (t, pre_p);
7492 /* ... Otherwise out of the overflow area. */
7495 if (size < UNITS_PER_WORD)
7496 t = build2 (PLUS_EXPR, ptr_type_node, t,
7497 fold_convert (ptr_type_node, size_int (UNITS_PER_WORD - size)));
7499 gimplify_expr (&t, pre_p, NULL, is_gimple_val, fb_rvalue);
7501 u = build2 (MODIFY_EXPR, void_type_node, addr, t);
7502 gimplify_and_add (u, pre_p);
7504 t = build2 (PLUS_EXPR, ptr_type_node, t,
7505 fold_convert (ptr_type_node, size_int (size)));
7506 t = build2 (MODIFY_EXPR, ptr_type_node, ovf, t);
7507 gimplify_and_add (t, pre_p);
7509 t = build1 (LABEL_EXPR, void_type_node, lab_over);
7510 append_to_statement_list (t, pre_p);
7513 /* Increment register save count. */
7515 u = build2 (PREINCREMENT_EXPR, TREE_TYPE (reg), reg,
7516 fold_convert (TREE_TYPE (reg), size_int (n_reg)));
7517 gimplify_and_add (u, pre_p);
7521 t = build_pointer_type (build_pointer_type (type));
7522 addr = fold_convert (t, addr);
7523 addr = build_va_arg_indirect_ref (addr);
7527 t = build_pointer_type (type);
7528 addr = fold_convert (t, addr);
7531 return build_va_arg_indirect_ref (addr);
7539 S390_BUILTIN_THREAD_POINTER,
7540 S390_BUILTIN_SET_THREAD_POINTER,
7545 static unsigned int const code_for_builtin_64[S390_BUILTIN_max] = {
7550 static unsigned int const code_for_builtin_31[S390_BUILTIN_max] = {
7556 s390_init_builtins (void)
7560 ftype = build_function_type (ptr_type_node, void_list_node);
7561 lang_hooks.builtin_function ("__builtin_thread_pointer", ftype,
7562 S390_BUILTIN_THREAD_POINTER, BUILT_IN_MD,
7565 ftype = build_function_type_list (void_type_node, ptr_type_node, NULL_TREE);
7566 lang_hooks.builtin_function ("__builtin_set_thread_pointer", ftype,
7567 S390_BUILTIN_SET_THREAD_POINTER, BUILT_IN_MD,
7571 /* Expand an expression EXP that calls a built-in function,
7572 with result going to TARGET if that's convenient
7573 (and in mode MODE if that's convenient).
7574 SUBTARGET may be used as the target for computing one of EXP's operands.
7575 IGNORE is nonzero if the value is to be ignored. */
7578 s390_expand_builtin (tree exp, rtx target, rtx subtarget ATTRIBUTE_UNUSED,
7579 enum machine_mode mode ATTRIBUTE_UNUSED,
7580 int ignore ATTRIBUTE_UNUSED)
7584 unsigned int const *code_for_builtin =
7585 TARGET_64BIT ? code_for_builtin_64 : code_for_builtin_31;
7587 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7588 unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
7589 tree arglist = TREE_OPERAND (exp, 1);
7590 enum insn_code icode;
7591 rtx op[MAX_ARGS], pat;
7595 if (fcode >= S390_BUILTIN_max)
7596 internal_error ("bad builtin fcode");
7597 icode = code_for_builtin[fcode];
7599 internal_error ("bad builtin fcode");
7601 nonvoid = TREE_TYPE (TREE_TYPE (fndecl)) != void_type_node;
7603 for (arglist = TREE_OPERAND (exp, 1), arity = 0;
7605 arglist = TREE_CHAIN (arglist), arity++)
7607 const struct insn_operand_data *insn_op;
7609 tree arg = TREE_VALUE (arglist);
7610 if (arg == error_mark_node)
7612 if (arity > MAX_ARGS)
7615 insn_op = &insn_data[icode].operand[arity + nonvoid];
7617 op[arity] = expand_expr (arg, NULL_RTX, insn_op->mode, 0);
7619 if (!(*insn_op->predicate) (op[arity], insn_op->mode))
7620 op[arity] = copy_to_mode_reg (insn_op->mode, op[arity]);
7625 enum machine_mode tmode = insn_data[icode].operand[0].mode;
7627 || GET_MODE (target) != tmode
7628 || !(*insn_data[icode].operand[0].predicate) (target, tmode))
7629 target = gen_reg_rtx (tmode);
7635 pat = GEN_FCN (icode) (target);
7639 pat = GEN_FCN (icode) (target, op[0]);
7641 pat = GEN_FCN (icode) (op[0]);
7644 pat = GEN_FCN (icode) (target, op[0], op[1]);
7660 /* Output assembly code for the trampoline template to
7663 On S/390, we use gpr 1 internally in the trampoline code;
7664 gpr 0 is used to hold the static chain. */
7667 s390_trampoline_template (FILE *file)
7670 op[0] = gen_rtx_REG (Pmode, 0);
7671 op[1] = gen_rtx_REG (Pmode, 1);
7675 output_asm_insn ("basr\t%1,0", op);
7676 output_asm_insn ("lmg\t%0,%1,14(%1)", op);
7677 output_asm_insn ("br\t%1", op);
7678 ASM_OUTPUT_SKIP (file, (HOST_WIDE_INT)(TRAMPOLINE_SIZE - 10));
7682 output_asm_insn ("basr\t%1,0", op);
7683 output_asm_insn ("lm\t%0,%1,6(%1)", op);
7684 output_asm_insn ("br\t%1", op);
7685 ASM_OUTPUT_SKIP (file, (HOST_WIDE_INT)(TRAMPOLINE_SIZE - 8));
7689 /* Emit RTL insns to initialize the variable parts of a trampoline.
7690 FNADDR is an RTX for the address of the function's pure code.
7691 CXT is an RTX for the static chain value for the function. */
7694 s390_initialize_trampoline (rtx addr, rtx fnaddr, rtx cxt)
7696 emit_move_insn (gen_rtx_MEM (Pmode,
7697 memory_address (Pmode,
7698 plus_constant (addr, (TARGET_64BIT ? 16 : 8)))), cxt);
7699 emit_move_insn (gen_rtx_MEM (Pmode,
7700 memory_address (Pmode,
7701 plus_constant (addr, (TARGET_64BIT ? 24 : 12)))), fnaddr);
7704 /* Return rtx for 64-bit constant formed from the 32-bit subwords
7705 LOW and HIGH, independent of the host word size. */
7708 s390_gen_rtx_const_DI (int high, int low)
7710 #if HOST_BITS_PER_WIDE_INT >= 64
7712 val = (HOST_WIDE_INT)high;
7714 val |= (HOST_WIDE_INT)low;
7716 return GEN_INT (val);
7718 #if HOST_BITS_PER_WIDE_INT >= 32
7719 return immed_double_const ((HOST_WIDE_INT)low, (HOST_WIDE_INT)high, DImode);
7726 /* Output assembler code to FILE to increment profiler label # LABELNO
7727 for profiling a function entry. */
7730 s390_function_profiler (FILE *file, int labelno)
7735 ASM_GENERATE_INTERNAL_LABEL (label, "LP", labelno);
7737 fprintf (file, "# function profiler \n");
7739 op[0] = gen_rtx_REG (Pmode, RETURN_REGNUM);
7740 op[1] = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
7741 op[1] = gen_rtx_MEM (Pmode, plus_constant (op[1], UNITS_PER_WORD));
7743 op[2] = gen_rtx_REG (Pmode, 1);
7744 op[3] = gen_rtx_SYMBOL_REF (Pmode, label);
7745 SYMBOL_REF_FLAGS (op[3]) = SYMBOL_FLAG_LOCAL;
7747 op[4] = gen_rtx_SYMBOL_REF (Pmode, "_mcount");
7750 op[4] = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op[4]), UNSPEC_PLT);
7751 op[4] = gen_rtx_CONST (Pmode, op[4]);
7756 output_asm_insn ("stg\t%0,%1", op);
7757 output_asm_insn ("larl\t%2,%3", op);
7758 output_asm_insn ("brasl\t%0,%4", op);
7759 output_asm_insn ("lg\t%0,%1", op);
7763 op[6] = gen_label_rtx ();
7765 output_asm_insn ("st\t%0,%1", op);
7766 output_asm_insn ("bras\t%2,%l6", op);
7767 output_asm_insn (".long\t%4", op);
7768 output_asm_insn (".long\t%3", op);
7769 targetm.asm_out.internal_label (file, "L", CODE_LABEL_NUMBER (op[6]));
7770 output_asm_insn ("l\t%0,0(%2)", op);
7771 output_asm_insn ("l\t%2,4(%2)", op);
7772 output_asm_insn ("basr\t%0,%0", op);
7773 output_asm_insn ("l\t%0,%1", op);
7777 op[5] = gen_label_rtx ();
7778 op[6] = gen_label_rtx ();
7780 output_asm_insn ("st\t%0,%1", op);
7781 output_asm_insn ("bras\t%2,%l6", op);
7782 targetm.asm_out.internal_label (file, "L", CODE_LABEL_NUMBER (op[5]));
7783 output_asm_insn (".long\t%4-%l5", op);
7784 output_asm_insn (".long\t%3-%l5", op);
7785 targetm.asm_out.internal_label (file, "L", CODE_LABEL_NUMBER (op[6]));
7786 output_asm_insn ("lr\t%0,%2", op);
7787 output_asm_insn ("a\t%0,0(%2)", op);
7788 output_asm_insn ("a\t%2,4(%2)", op);
7789 output_asm_insn ("basr\t%0,%0", op);
7790 output_asm_insn ("l\t%0,%1", op);
7794 /* Encode symbol attributes (local vs. global, tls model) of a SYMBOL_REF
7795 into its SYMBOL_REF_FLAGS. */
7798 s390_encode_section_info (tree decl, rtx rtl, int first)
7800 default_encode_section_info (decl, rtl, first);
7802 /* If a variable has a forced alignment to < 2 bytes, mark it with
7803 SYMBOL_FLAG_ALIGN1 to prevent it from being used as LARL operand. */
7804 if (TREE_CODE (decl) == VAR_DECL
7805 && DECL_USER_ALIGN (decl) && DECL_ALIGN (decl) < 16)
7806 SYMBOL_REF_FLAGS (XEXP (rtl, 0)) |= SYMBOL_FLAG_ALIGN1;
7809 /* Output thunk to FILE that implements a C++ virtual function call (with
7810 multiple inheritance) to FUNCTION. The thunk adjusts the this pointer
7811 by DELTA, and unless VCALL_OFFSET is zero, applies an additional adjustment
7812 stored at VCALL_OFFSET in the vtable whose address is located at offset 0
7813 relative to the resulting this pointer. */
7816 s390_output_mi_thunk (FILE *file, tree thunk ATTRIBUTE_UNUSED,
7817 HOST_WIDE_INT delta, HOST_WIDE_INT vcall_offset,
7823 /* Operand 0 is the target function. */
7824 op[0] = XEXP (DECL_RTL (function), 0);
7825 if (flag_pic && !SYMBOL_REF_LOCAL_P (op[0]))
7828 op[0] = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op[0]),
7829 TARGET_64BIT ? UNSPEC_PLT : UNSPEC_GOT);
7830 op[0] = gen_rtx_CONST (Pmode, op[0]);
7833 /* Operand 1 is the 'this' pointer. */
7834 if (aggregate_value_p (TREE_TYPE (TREE_TYPE (function)), function))
7835 op[1] = gen_rtx_REG (Pmode, 3);
7837 op[1] = gen_rtx_REG (Pmode, 2);
7839 /* Operand 2 is the delta. */
7840 op[2] = GEN_INT (delta);
7842 /* Operand 3 is the vcall_offset. */
7843 op[3] = GEN_INT (vcall_offset);
7845 /* Operand 4 is the temporary register. */
7846 op[4] = gen_rtx_REG (Pmode, 1);
7848 /* Operands 5 to 8 can be used as labels. */
7854 /* Operand 9 can be used for temporary register. */
7857 /* Generate code. */
7860 /* Setup literal pool pointer if required. */
7861 if ((!DISP_IN_RANGE (delta)
7862 && !CONST_OK_FOR_CONSTRAINT_P (delta, 'K', "K"))
7863 || (!DISP_IN_RANGE (vcall_offset)
7864 && !CONST_OK_FOR_CONSTRAINT_P (vcall_offset, 'K', "K")))
7866 op[5] = gen_label_rtx ();
7867 output_asm_insn ("larl\t%4,%5", op);
7870 /* Add DELTA to this pointer. */
7873 if (CONST_OK_FOR_CONSTRAINT_P (delta, 'J', "J"))
7874 output_asm_insn ("la\t%1,%2(%1)", op);
7875 else if (DISP_IN_RANGE (delta))
7876 output_asm_insn ("lay\t%1,%2(%1)", op);
7877 else if (CONST_OK_FOR_CONSTRAINT_P (delta, 'K', "K"))
7878 output_asm_insn ("aghi\t%1,%2", op);
7881 op[6] = gen_label_rtx ();
7882 output_asm_insn ("agf\t%1,%6-%5(%4)", op);
7886 /* Perform vcall adjustment. */
7889 if (DISP_IN_RANGE (vcall_offset))
7891 output_asm_insn ("lg\t%4,0(%1)", op);
7892 output_asm_insn ("ag\t%1,%3(%4)", op);
7894 else if (CONST_OK_FOR_CONSTRAINT_P (vcall_offset, 'K', "K"))
7896 output_asm_insn ("lghi\t%4,%3", op);
7897 output_asm_insn ("ag\t%4,0(%1)", op);
7898 output_asm_insn ("ag\t%1,0(%4)", op);
7902 op[7] = gen_label_rtx ();
7903 output_asm_insn ("llgf\t%4,%7-%5(%4)", op);
7904 output_asm_insn ("ag\t%4,0(%1)", op);
7905 output_asm_insn ("ag\t%1,0(%4)", op);
7909 /* Jump to target. */
7910 output_asm_insn ("jg\t%0", op);
7912 /* Output literal pool if required. */
7915 output_asm_insn (".align\t4", op);
7916 targetm.asm_out.internal_label (file, "L",
7917 CODE_LABEL_NUMBER (op[5]));
7921 targetm.asm_out.internal_label (file, "L",
7922 CODE_LABEL_NUMBER (op[6]));
7923 output_asm_insn (".long\t%2", op);
7927 targetm.asm_out.internal_label (file, "L",
7928 CODE_LABEL_NUMBER (op[7]));
7929 output_asm_insn (".long\t%3", op);
7934 /* Setup base pointer if required. */
7936 || (!DISP_IN_RANGE (delta)
7937 && !CONST_OK_FOR_CONSTRAINT_P (delta, 'K', "K"))
7938 || (!DISP_IN_RANGE (delta)
7939 && !CONST_OK_FOR_CONSTRAINT_P (vcall_offset, 'K', "K")))
7941 op[5] = gen_label_rtx ();
7942 output_asm_insn ("basr\t%4,0", op);
7943 targetm.asm_out.internal_label (file, "L",
7944 CODE_LABEL_NUMBER (op[5]));
7947 /* Add DELTA to this pointer. */
7950 if (CONST_OK_FOR_CONSTRAINT_P (delta, 'J', "J"))
7951 output_asm_insn ("la\t%1,%2(%1)", op);
7952 else if (DISP_IN_RANGE (delta))
7953 output_asm_insn ("lay\t%1,%2(%1)", op);
7954 else if (CONST_OK_FOR_CONSTRAINT_P (delta, 'K', "K"))
7955 output_asm_insn ("ahi\t%1,%2", op);
7958 op[6] = gen_label_rtx ();
7959 output_asm_insn ("a\t%1,%6-%5(%4)", op);
7963 /* Perform vcall adjustment. */
7966 if (CONST_OK_FOR_CONSTRAINT_P (vcall_offset, 'J', "J"))
7968 output_asm_insn ("lg\t%4,0(%1)", op);
7969 output_asm_insn ("a\t%1,%3(%4)", op);
7971 else if (DISP_IN_RANGE (vcall_offset))
7973 output_asm_insn ("lg\t%4,0(%1)", op);
7974 output_asm_insn ("ay\t%1,%3(%4)", op);
7976 else if (CONST_OK_FOR_CONSTRAINT_P (vcall_offset, 'K', "K"))
7978 output_asm_insn ("lhi\t%4,%3", op);
7979 output_asm_insn ("a\t%4,0(%1)", op);
7980 output_asm_insn ("a\t%1,0(%4)", op);
7984 op[7] = gen_label_rtx ();
7985 output_asm_insn ("l\t%4,%7-%5(%4)", op);
7986 output_asm_insn ("a\t%4,0(%1)", op);
7987 output_asm_insn ("a\t%1,0(%4)", op);
7990 /* We had to clobber the base pointer register.
7991 Re-setup the base pointer (with a different base). */
7992 op[5] = gen_label_rtx ();
7993 output_asm_insn ("basr\t%4,0", op);
7994 targetm.asm_out.internal_label (file, "L",
7995 CODE_LABEL_NUMBER (op[5]));
7998 /* Jump to target. */
7999 op[8] = gen_label_rtx ();
8002 output_asm_insn ("l\t%4,%8-%5(%4)", op);
8004 output_asm_insn ("a\t%4,%8-%5(%4)", op);
8005 /* We cannot call through .plt, since .plt requires %r12 loaded. */
8006 else if (flag_pic == 1)
8008 output_asm_insn ("a\t%4,%8-%5(%4)", op);
8009 output_asm_insn ("l\t%4,%0(%4)", op);
8011 else if (flag_pic == 2)
8013 op[9] = gen_rtx_REG (Pmode, 0);
8014 output_asm_insn ("l\t%9,%8-4-%5(%4)", op);
8015 output_asm_insn ("a\t%4,%8-%5(%4)", op);
8016 output_asm_insn ("ar\t%4,%9", op);
8017 output_asm_insn ("l\t%4,0(%4)", op);
8020 output_asm_insn ("br\t%4", op);
8022 /* Output literal pool. */
8023 output_asm_insn (".align\t4", op);
8025 if (nonlocal && flag_pic == 2)
8026 output_asm_insn (".long\t%0", op);
8029 op[0] = gen_rtx_SYMBOL_REF (Pmode, "_GLOBAL_OFFSET_TABLE_");
8030 SYMBOL_REF_FLAGS (op[0]) = SYMBOL_FLAG_LOCAL;
8033 targetm.asm_out.internal_label (file, "L", CODE_LABEL_NUMBER (op[8]));
8035 output_asm_insn (".long\t%0", op);
8037 output_asm_insn (".long\t%0-%5", op);
8041 targetm.asm_out.internal_label (file, "L",
8042 CODE_LABEL_NUMBER (op[6]));
8043 output_asm_insn (".long\t%2", op);
8047 targetm.asm_out.internal_label (file, "L",
8048 CODE_LABEL_NUMBER (op[7]));
8049 output_asm_insn (".long\t%3", op);
8055 s390_valid_pointer_mode (enum machine_mode mode)
8057 return (mode == SImode || (TARGET_64BIT && mode == DImode));
8060 /* How to allocate a 'struct machine_function'. */
8062 static struct machine_function *
8063 s390_init_machine_status (void)
8065 return ggc_alloc_cleared (sizeof (struct machine_function));
8068 /* Checks whether the given ARGUMENT_LIST would use a caller
8069 saved register. This is used to decide whether sibling call
8070 optimization could be performed on the respective function
8074 s390_call_saved_register_used (tree argument_list)
8076 CUMULATIVE_ARGS cum;
8078 enum machine_mode mode;
8083 INIT_CUMULATIVE_ARGS (cum, NULL, NULL, 0, 0);
8085 while (argument_list)
8087 parameter = TREE_VALUE (argument_list);
8088 argument_list = TREE_CHAIN (argument_list);
8093 /* For an undeclared variable passed as parameter we will get
8094 an ERROR_MARK node here. */
8095 if (TREE_CODE (parameter) == ERROR_MARK)
8098 if (! (type = TREE_TYPE (parameter)))
8101 if (! (mode = TYPE_MODE (TREE_TYPE (parameter))))
8104 if (pass_by_reference (&cum, mode, type, true))
8107 type = build_pointer_type (type);
8110 parm_rtx = s390_function_arg (&cum, mode, type, 0);
8112 s390_function_arg_advance (&cum, mode, type, 0);
8114 if (parm_rtx && REG_P (parm_rtx))
8117 reg < HARD_REGNO_NREGS (REGNO (parm_rtx), GET_MODE (parm_rtx));
8119 if (! call_used_regs[reg + REGNO (parm_rtx)])
8126 /* Return true if the given call expression can be
8127 turned into a sibling call.
8128 DECL holds the declaration of the function to be called whereas
8129 EXP is the call expression itself. */
8132 s390_function_ok_for_sibcall (tree decl, tree exp)
8134 /* The TPF epilogue uses register 1. */
8135 if (TARGET_TPF_PROFILING)
8138 /* The 31 bit PLT code uses register 12 (GOT pointer - caller saved)
8139 which would have to be restored before the sibcall. */
8140 if (!TARGET_64BIT && flag_pic && decl && TREE_PUBLIC (decl))
8143 /* Register 6 on s390 is available as an argument register but unfortunately
8144 "caller saved". This makes functions needing this register for arguments
8145 not suitable for sibcalls. */
8146 if (TREE_OPERAND (exp, 1)
8147 && s390_call_saved_register_used (TREE_OPERAND (exp, 1)))
8153 /* Return the fixed registers used for condition codes. */
8156 s390_fixed_condition_code_regs (unsigned int *p1, unsigned int *p2)
8159 *p2 = INVALID_REGNUM;
8164 /* If two condition code modes are compatible, return a condition code
8165 mode which is compatible with both. Otherwise, return
8168 static enum machine_mode
8169 s390_cc_modes_compatible (enum machine_mode m1, enum machine_mode m2)
8177 if (m2 == CCUmode || m2 == CCTmode
8178 || m2 == CCSmode || m2 == CCSRmode || m2 == CCURmode)
8198 /* This function is used by the call expanders of the machine description.
8199 It emits the call insn itself together with the necessary operations
8200 to adjust the target address and returns the emitted insn.
8201 ADDR_LOCATION is the target address rtx
8202 TLS_CALL the location of the thread-local symbol
8203 RESULT_REG the register where the result of the call should be stored
8204 RETADDR_REG the register where the return address should be stored
8205 If this parameter is NULL_RTX the call is considered
8206 to be a sibling call. */
8209 s390_emit_call (rtx addr_location, rtx tls_call, rtx result_reg,
8212 bool plt_call = false;
8218 /* Direct function calls need special treatment. */
8219 if (GET_CODE (addr_location) == SYMBOL_REF)
8221 /* When calling a global routine in PIC mode, we must
8222 replace the symbol itself with the PLT stub. */
8223 if (flag_pic && !SYMBOL_REF_LOCAL_P (addr_location))
8225 addr_location = gen_rtx_UNSPEC (Pmode,
8226 gen_rtvec (1, addr_location),
8228 addr_location = gen_rtx_CONST (Pmode, addr_location);
8232 /* Unless we can use the bras(l) insn, force the
8233 routine address into a register. */
8234 if (!TARGET_SMALL_EXEC && !TARGET_CPU_ZARCH)
8237 addr_location = legitimize_pic_address (addr_location, 0);
8239 addr_location = force_reg (Pmode, addr_location);
8243 /* If it is already an indirect call or the code above moved the
8244 SYMBOL_REF to somewhere else make sure the address can be found in
8246 if (retaddr_reg == NULL_RTX
8247 && GET_CODE (addr_location) != SYMBOL_REF
8250 emit_move_insn (gen_rtx_REG (Pmode, SIBCALL_REGNUM), addr_location);
8251 addr_location = gen_rtx_REG (Pmode, SIBCALL_REGNUM);
8254 addr_location = gen_rtx_MEM (QImode, addr_location);
8255 call = gen_rtx_CALL (VOIDmode, addr_location, const0_rtx);
8257 if (result_reg != NULL_RTX)
8258 call = gen_rtx_SET (VOIDmode, result_reg, call);
8260 if (retaddr_reg != NULL_RTX)
8262 clobber = gen_rtx_CLOBBER (VOIDmode, retaddr_reg);
8264 if (tls_call != NULL_RTX)
8265 vec = gen_rtvec (3, call, clobber,
8266 gen_rtx_USE (VOIDmode, tls_call));
8268 vec = gen_rtvec (2, call, clobber);
8270 call = gen_rtx_PARALLEL (VOIDmode, vec);
8273 insn = emit_call_insn (call);
8275 /* 31-bit PLT stubs and tls calls use the GOT register implicitly. */
8276 if ((!TARGET_64BIT && plt_call) || tls_call != NULL_RTX)
8278 /* s390_function_ok_for_sibcall should
8279 have denied sibcalls in this case. */
8280 if (retaddr_reg == NULL_RTX)
8283 use_reg (&CALL_INSN_FUNCTION_USAGE (insn), pic_offset_table_rtx);
8288 /* Implement CONDITIONAL_REGISTER_USAGE. */
8291 s390_conditional_register_usage (void)
8297 fixed_regs[PIC_OFFSET_TABLE_REGNUM] = 1;
8298 call_used_regs[PIC_OFFSET_TABLE_REGNUM] = 1;
8300 if (TARGET_CPU_ZARCH)
8302 fixed_regs[RETURN_REGNUM] = 0;
8303 call_used_regs[RETURN_REGNUM] = 0;
8307 for (i = 24; i < 32; i++)
8308 call_used_regs[i] = call_really_used_regs[i] = 0;
8312 for (i = 18; i < 20; i++)
8313 call_used_regs[i] = call_really_used_regs[i] = 0;
8316 if (TARGET_SOFT_FLOAT)
8318 for (i = 16; i < 32; i++)
8319 call_used_regs[i] = fixed_regs[i] = 1;
8323 /* Corresponding function to eh_return expander. */
8325 static GTY(()) rtx s390_tpf_eh_return_symbol;
8327 s390_emit_tpf_eh_return (rtx target)
8331 if (!s390_tpf_eh_return_symbol)
8332 s390_tpf_eh_return_symbol = gen_rtx_SYMBOL_REF (Pmode, "__tpf_eh_return");
8334 reg = gen_rtx_REG (Pmode, 2);
8336 emit_move_insn (reg, target);
8337 insn = s390_emit_call (s390_tpf_eh_return_symbol, NULL_RTX, reg,
8338 gen_rtx_REG (Pmode, RETURN_REGNUM));
8339 use_reg (&CALL_INSN_FUNCTION_USAGE (insn), reg);
8341 emit_move_insn (EH_RETURN_HANDLER_RTX, reg);
8344 #include "gt-s390.h"