1 /* Subroutines used for code generation on the DEC Alpha.
2 Copyright (C) 1992, 93, 94, 95, 96, 97, 1998 Free Software Foundation, Inc.
3 Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
5 This file is part of GNU CC.
7 GNU CC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
12 GNU CC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GNU CC; see the file COPYING. If not, write to
19 the Free Software Foundation, 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA. */
28 #include "hard-reg-set.h"
30 #include "insn-config.h"
31 #include "conditions.h"
32 #include "insn-flags.h"
34 #include "insn-attr.h"
45 extern char *version_string;
46 extern int rtx_equal_function_value_matters;
48 /* Specify which cpu to schedule for. */
50 enum processor_type alpha_cpu;
51 static char* const alpha_cpu_name[] =
56 /* Specify how accurate floating-point traps need to be. */
58 enum alpha_trap_precision alpha_tp;
60 /* Specify the floating-point rounding mode. */
62 enum alpha_fp_rounding_mode alpha_fprm;
64 /* Specify which things cause traps. */
66 enum alpha_fp_trap_mode alpha_fptm;
68 /* Strings decoded into the above options. */
70 char *alpha_cpu_string; /* -mcpu= */
71 char *alpha_tp_string; /* -mtrap-precision=[p|s|i] */
72 char *alpha_fprm_string; /* -mfp-rounding-mode=[n|m|c|d] */
73 char *alpha_fptm_string; /* -mfp-trap-mode=[n|u|su|sui] */
74 char *alpha_mlat_string; /* -mmemory-latency= */
76 /* Save information from a "cmpxx" operation until the branch or scc is
79 rtx alpha_compare_op0, alpha_compare_op1;
80 int alpha_compare_fp_p;
82 /* Save the name of the current function as used by the assembler. This
83 is used by the epilogue. */
85 char *alpha_function_name;
87 /* Non-zero if inside of a function, because the Alpha asm can't
88 handle .files inside of functions. */
90 static int inside_function = FALSE;
92 /* Nonzero if the current function needs gp. */
94 int alpha_function_needs_gp;
96 /* If non-null, this rtx holds the return address for the function. */
98 static rtx alpha_return_addr_rtx;
100 /* The number of cycles of latency we should assume on memory reads. */
102 int alpha_memory_latency = 3;
104 /* Declarations of static functions. */
105 static void alpha_set_memflags_1 PROTO((rtx, int, int, int));
106 static rtx alpha_emit_set_const_1 PROTO((rtx, enum machine_mode,
107 HOST_WIDE_INT, int));
108 static void add_long_const PROTO((FILE *, HOST_WIDE_INT, int, int, int));
110 /* Compute the size of the save area in the stack. */
112 static void alpha_sa_mask PROTO((unsigned long *imaskP,
113 unsigned long *fmaskP));
115 /* Get the number of args of a function in one of two ways. */
117 #define NUM_ARGS current_function_args_info.num_args
119 #define NUM_ARGS current_function_args_info
129 /* Parse target option strings. */
134 /* 971208 -- EV6 scheduling parameters are still secret, so don't even
135 pretend and just schedule for an EV5 for now. -- r~ */
137 = TARGET_CPU_DEFAULT & MASK_CPU_EV6 ? PROCESSOR_EV6
138 : (TARGET_CPU_DEFAULT & MASK_CPU_EV5 ? PROCESSOR_EV5 : PROCESSOR_EV4);
140 if (alpha_cpu_string)
142 if (! strcmp (alpha_cpu_string, "ev4")
143 || ! strcmp (alpha_cpu_string, "21064"))
145 alpha_cpu = PROCESSOR_EV4;
146 target_flags &= ~ (MASK_BWX | MASK_CIX | MASK_MAX);
148 else if (! strcmp (alpha_cpu_string, "ev5")
149 || ! strcmp (alpha_cpu_string, "21164"))
151 alpha_cpu = PROCESSOR_EV5;
152 target_flags &= ~ (MASK_BWX | MASK_CIX | MASK_MAX);
154 else if (! strcmp (alpha_cpu_string, "ev56")
155 || ! strcmp (alpha_cpu_string, "21164a"))
157 alpha_cpu = PROCESSOR_EV5;
158 target_flags |= MASK_BWX;
159 target_flags &= ~ (MASK_CIX | MASK_MAX);
161 else if (! strcmp (alpha_cpu_string, "pca56")
162 || ! strcmp (alpha_cpu_string, "21164PC")
163 || ! strcmp (alpha_cpu_string, "21164pc"))
165 alpha_cpu = PROCESSOR_EV5;
166 target_flags |= MASK_BWX | MASK_MAX;
167 target_flags &= ~ MASK_CIX;
169 else if (! strcmp (alpha_cpu_string, "ev6")
170 || ! strcmp (alpha_cpu_string, "21264"))
172 alpha_cpu = PROCESSOR_EV6;
173 target_flags |= MASK_BWX | MASK_CIX | MASK_MAX;
176 error ("bad value `%s' for -mcpu switch", alpha_cpu_string);
179 alpha_tp = ALPHA_TP_PROG;
180 alpha_fprm = ALPHA_FPRM_NORM;
181 alpha_fptm = ALPHA_FPTM_N;
185 alpha_tp = ALPHA_TP_INSN;
186 alpha_fptm = ALPHA_FPTM_SU;
189 if (TARGET_IEEE_WITH_INEXACT)
191 alpha_tp = ALPHA_TP_INSN;
192 alpha_fptm = ALPHA_FPTM_SUI;
197 if (! strcmp (alpha_tp_string, "p"))
198 alpha_tp = ALPHA_TP_PROG;
199 else if (! strcmp (alpha_tp_string, "f"))
200 alpha_tp = ALPHA_TP_FUNC;
201 else if (! strcmp (alpha_tp_string, "i"))
202 alpha_tp = ALPHA_TP_INSN;
204 error ("bad value `%s' for -mtrap-precision switch", alpha_tp_string);
207 if (alpha_fprm_string)
209 if (! strcmp (alpha_fprm_string, "n"))
210 alpha_fprm = ALPHA_FPRM_NORM;
211 else if (! strcmp (alpha_fprm_string, "m"))
212 alpha_fprm = ALPHA_FPRM_MINF;
213 else if (! strcmp (alpha_fprm_string, "c"))
214 alpha_fprm = ALPHA_FPRM_CHOP;
215 else if (! strcmp (alpha_fprm_string,"d"))
216 alpha_fprm = ALPHA_FPRM_DYN;
218 error ("bad value `%s' for -mfp-rounding-mode switch",
222 if (alpha_fptm_string)
224 if (strcmp (alpha_fptm_string, "n") == 0)
225 alpha_fptm = ALPHA_FPTM_N;
226 else if (strcmp (alpha_fptm_string, "u") == 0)
227 alpha_fptm = ALPHA_FPTM_U;
228 else if (strcmp (alpha_fptm_string, "su") == 0)
229 alpha_fptm = ALPHA_FPTM_SU;
230 else if (strcmp (alpha_fptm_string, "sui") == 0)
231 alpha_fptm = ALPHA_FPTM_SUI;
233 error ("bad value `%s' for -mfp-trap-mode switch", alpha_fptm_string);
236 /* Do some sanity checks on the above option. */
238 if ((alpha_fptm == ALPHA_FPTM_SU || alpha_fptm == ALPHA_FPTM_SUI)
239 && alpha_tp != ALPHA_TP_INSN)
241 warning ("fp software completion requires -mtrap-precision=i");
242 alpha_tp = ALPHA_TP_INSN;
245 if (TARGET_FLOAT_VAX)
247 if (alpha_fprm == ALPHA_FPRM_MINF || alpha_fprm == ALPHA_FPRM_DYN)
249 warning ("rounding mode not supported for VAX floats");
250 alpha_fprm = ALPHA_FPRM_NORM;
252 if (alpha_fptm == ALPHA_FPTM_SUI)
254 warning ("trap mode not supported for VAX floats");
255 alpha_fptm = ALPHA_FPTM_SU;
263 if (!alpha_mlat_string)
264 alpha_mlat_string = "L1";
266 if (isdigit (alpha_mlat_string[0])
267 && (lat = strtol (alpha_mlat_string, &end, 10), *end == '\0'))
269 else if ((alpha_mlat_string[0] == 'L' || alpha_mlat_string[0] == 'l')
270 && isdigit (alpha_mlat_string[1])
271 && alpha_mlat_string[2] == '\0')
273 static int const cache_latency[][4] =
275 { 3, 30, -1 }, /* ev4 -- Bcache is a guess */
276 { 2, 12, 38 }, /* ev5 -- Bcache from PC164 LMbench numbers */
277 { 3, 13, -1 }, /* ev6 -- Ho hum, doesn't exist yet */
280 lat = alpha_mlat_string[1] - '0';
281 if (lat < 0 || lat > 3 || cache_latency[alpha_cpu][lat-1] == -1)
283 warning ("L%d cache latency unknown for %s",
284 lat, alpha_cpu_name[alpha_cpu]);
288 lat = cache_latency[alpha_cpu][lat-1];
290 else if (! strcmp (alpha_mlat_string, "main"))
292 /* Most current memories have about 370ns latency. This is
293 a reasonable guess for a fast cpu. */
298 warning ("bad value `%s' for -mmemory-latency", alpha_mlat_string);
302 alpha_memory_latency = lat;
305 /* Default the definition of "small data" to 8 bytes. */
310 /* Returns 1 if VALUE is a mask that contains full bytes of zero or ones. */
318 for (i = 0; i < HOST_BITS_PER_WIDE_INT / HOST_BITS_PER_CHAR;
320 if ((value & 0xff) != 0 && (value & 0xff) != 0xff)
326 /* Returns 1 if OP is either the constant zero or a register. If a
327 register, it must be in the proper mode unless MODE is VOIDmode. */
330 reg_or_0_operand (op, mode)
332 enum machine_mode mode;
334 return op == const0_rtx || register_operand (op, mode);
337 /* Return 1 if OP is a constant in the range of 0-63 (for a shift) or
341 reg_or_6bit_operand (op, mode)
343 enum machine_mode mode;
345 return ((GET_CODE (op) == CONST_INT
346 && (unsigned HOST_WIDE_INT) INTVAL (op) < 64)
347 || register_operand (op, mode));
351 /* Return 1 if OP is an 8-bit constant or any register. */
354 reg_or_8bit_operand (op, mode)
356 enum machine_mode mode;
358 return ((GET_CODE (op) == CONST_INT
359 && (unsigned HOST_WIDE_INT) INTVAL (op) < 0x100)
360 || register_operand (op, mode));
363 /* Return 1 if OP is an 8-bit constant. */
366 cint8_operand (op, mode)
368 enum machine_mode mode;
370 return (GET_CODE (op) == CONST_INT
371 && (unsigned HOST_WIDE_INT) INTVAL (op) < 0x100);
374 /* Return 1 if the operand is a valid second operand to an add insn. */
377 add_operand (op, mode)
379 enum machine_mode mode;
381 if (GET_CODE (op) == CONST_INT)
382 return (CONST_OK_FOR_LETTER_P (INTVAL (op), 'K')
383 || CONST_OK_FOR_LETTER_P (INTVAL (op), 'L')
384 || CONST_OK_FOR_LETTER_P (INTVAL (op), 'O'));
386 return register_operand (op, mode);
389 /* Return 1 if the operand is a valid second operand to a sign-extending
393 sext_add_operand (op, mode)
395 enum machine_mode mode;
397 if (GET_CODE (op) == CONST_INT)
398 return ((unsigned HOST_WIDE_INT) INTVAL (op) < 255
399 || (unsigned HOST_WIDE_INT) (- INTVAL (op)) < 255);
401 return register_operand (op, mode);
404 /* Return 1 if OP is the constant 4 or 8. */
407 const48_operand (op, mode)
409 enum machine_mode mode;
411 return (GET_CODE (op) == CONST_INT
412 && (INTVAL (op) == 4 || INTVAL (op) == 8));
415 /* Return 1 if OP is a valid first operand to an AND insn. */
418 and_operand (op, mode)
420 enum machine_mode mode;
422 if (GET_CODE (op) == CONST_DOUBLE && GET_MODE (op) == VOIDmode)
423 return (zap_mask (CONST_DOUBLE_LOW (op))
424 && zap_mask (CONST_DOUBLE_HIGH (op)));
426 if (GET_CODE (op) == CONST_INT)
427 return ((unsigned HOST_WIDE_INT) INTVAL (op) < 0x100
428 || (unsigned HOST_WIDE_INT) ~ INTVAL (op) < 0x100
429 || zap_mask (INTVAL (op)));
431 return register_operand (op, mode);
434 /* Return 1 if OP is a valid first operand to an IOR or XOR insn. */
437 or_operand (op, mode)
439 enum machine_mode mode;
441 if (GET_CODE (op) == CONST_INT)
442 return ((unsigned HOST_WIDE_INT) INTVAL (op) < 0x100
443 || (unsigned HOST_WIDE_INT) ~ INTVAL (op) < 0x100);
445 return register_operand (op, mode);
448 /* Return 1 if OP is a constant that is the width, in bits, of an integral
449 mode smaller than DImode. */
452 mode_width_operand (op, mode)
454 enum machine_mode mode;
456 return (GET_CODE (op) == CONST_INT
457 && (INTVAL (op) == 8 || INTVAL (op) == 16
458 || INTVAL (op) == 32 || INTVAL (op) == 64));
461 /* Return 1 if OP is a constant that is the width of an integral machine mode
462 smaller than an integer. */
465 mode_mask_operand (op, mode)
467 enum machine_mode mode;
469 #if HOST_BITS_PER_WIDE_INT == 32
470 if (GET_CODE (op) == CONST_DOUBLE)
471 return (CONST_DOUBLE_LOW (op) == -1
472 && (CONST_DOUBLE_HIGH (op) == -1
473 || CONST_DOUBLE_HIGH (op) == 0));
475 if (GET_CODE (op) == CONST_DOUBLE)
476 return (CONST_DOUBLE_LOW (op) == -1 && CONST_DOUBLE_HIGH (op) == 0);
479 return (GET_CODE (op) == CONST_INT
480 && (INTVAL (op) == 0xff
481 || INTVAL (op) == 0xffff
482 || INTVAL (op) == 0xffffffff
483 #if HOST_BITS_PER_WIDE_INT == 64
484 || INTVAL (op) == 0xffffffffffffffff
489 /* Return 1 if OP is a multiple of 8 less than 64. */
492 mul8_operand (op, mode)
494 enum machine_mode mode;
496 return (GET_CODE (op) == CONST_INT
497 && (unsigned HOST_WIDE_INT) INTVAL (op) < 64
498 && (INTVAL (op) & 7) == 0);
501 /* Return 1 if OP is the constant zero in floating-point. */
504 fp0_operand (op, mode)
506 enum machine_mode mode;
508 return (GET_MODE (op) == mode
509 && GET_MODE_CLASS (mode) == MODE_FLOAT && op == CONST0_RTX (mode));
512 /* Return 1 if OP is the floating-point constant zero or a register. */
515 reg_or_fp0_operand (op, mode)
517 enum machine_mode mode;
519 return fp0_operand (op, mode) || register_operand (op, mode);
522 /* Return 1 if OP is a hard floating-point register. */
525 hard_fp_register_operand (op, mode)
527 enum machine_mode mode;
529 return ((GET_CODE (op) == REG && REGNO_REG_CLASS (REGNO (op)) == FLOAT_REGS)
530 || (GET_CODE (op) == SUBREG
531 && hard_fp_register_operand (SUBREG_REG (op), mode)));
534 /* Return 1 if OP is a register or a constant integer. */
538 reg_or_cint_operand (op, mode)
540 enum machine_mode mode;
542 return GET_CODE (op) == CONST_INT || register_operand (op, mode);
545 /* Return 1 if OP is something that can be reloaded into a register;
546 if it is a MEM, it need not be valid. */
549 some_operand (op, mode)
551 enum machine_mode mode;
553 if (mode != VOIDmode && GET_MODE (op) != VOIDmode && mode != GET_MODE (op))
556 switch (GET_CODE (op))
558 case REG: case MEM: case CONST_DOUBLE:
559 case CONST_INT: case LABEL_REF: case SYMBOL_REF: case CONST:
563 return some_operand (SUBREG_REG (op), VOIDmode);
572 /* Return 1 if OP is a valid operand for the source of a move insn. */
575 input_operand (op, mode)
577 enum machine_mode mode;
579 if (mode != VOIDmode && GET_MODE (op) != VOIDmode && mode != GET_MODE (op))
582 if (GET_MODE_CLASS (mode) == MODE_FLOAT && GET_MODE (op) != mode)
585 switch (GET_CODE (op))
590 /* This handles both the Windows/NT and OSF cases. */
591 return mode == ptr_mode || mode == DImode;
597 if (register_operand (op, mode))
599 /* ... fall through ... */
601 return ((TARGET_BWX || (mode != HImode && mode != QImode))
602 && general_operand (op, mode));
605 return GET_MODE_CLASS (mode) == MODE_FLOAT && op == CONST0_RTX (mode);
608 return mode == QImode || mode == HImode || add_operand (op, mode);
617 /* Return 1 if OP is a SYMBOL_REF for a function known to be in this
621 current_file_function_operand (op, mode)
623 enum machine_mode mode;
625 return (GET_CODE (op) == SYMBOL_REF
626 && ! profile_flag && ! profile_block_flag
627 && (SYMBOL_REF_FLAG (op)
628 || op == XEXP (DECL_RTL (current_function_decl), 0)));
631 /* Return 1 if OP is a valid operand for the MEM of a CALL insn. */
634 call_operand (op, mode)
636 enum machine_mode mode;
641 return (GET_CODE (op) == SYMBOL_REF
642 || (GET_CODE (op) == REG
643 && (TARGET_OPEN_VMS || TARGET_WINDOWS_NT || REGNO (op) == 27)));
646 /* Return 1 if OP is a valid Alpha comparison operator. Here we know which
647 comparisons are valid in which insn. */
650 alpha_comparison_operator (op, mode)
652 enum machine_mode mode;
654 enum rtx_code code = GET_CODE (op);
656 if (mode != GET_MODE (op) || GET_RTX_CLASS (code) != '<')
659 return (code == EQ || code == LE || code == LT
660 || (mode == DImode && (code == LEU || code == LTU)));
663 /* Return 1 if OP is a valid Alpha swapped comparison operator. */
666 alpha_swapped_comparison_operator (op, mode)
668 enum machine_mode mode;
670 enum rtx_code code = GET_CODE (op);
672 if (mode != GET_MODE (op) || GET_RTX_CLASS (code) != '<')
675 code = swap_condition (code);
676 return (code == EQ || code == LE || code == LT
677 || (mode == DImode && (code == LEU || code == LTU)));
680 /* Return 1 if OP is a signed comparison operation. */
683 signed_comparison_operator (op, mode)
685 enum machine_mode mode;
687 switch (GET_CODE (op))
689 case EQ: case NE: case LE: case LT: case GE: case GT:
699 /* Return 1 if this is a divide or modulus operator. */
702 divmod_operator (op, mode)
704 enum machine_mode mode;
706 switch (GET_CODE (op))
708 case DIV: case MOD: case UDIV: case UMOD:
718 /* Return 1 if this memory address is a known aligned register plus
719 a constant. It must be a valid address. This means that we can do
720 this as an aligned reference plus some offset.
722 Take into account what reload will do.
724 We could say that out-of-range stack slots are alignable, but that would
725 complicate get_aligned_mem and it isn't worth the trouble since few
726 functions have large stack space. */
729 aligned_memory_operand (op, mode)
731 enum machine_mode mode;
733 if (GET_CODE (op) == SUBREG)
735 if (GET_MODE (op) != mode)
737 op = SUBREG_REG (op);
738 mode = GET_MODE (op);
741 if (reload_in_progress && GET_CODE (op) == REG
742 && REGNO (op) >= FIRST_PSEUDO_REGISTER)
743 op = reg_equiv_mem[REGNO (op)];
745 if (GET_CODE (op) != MEM || GET_MODE (op) != mode
746 || ! memory_address_p (mode, XEXP (op, 0)))
751 if (GET_CODE (op) == PLUS)
754 return (GET_CODE (op) == REG
755 && REGNO_POINTER_ALIGN (REGNO (op)) >= 4);
758 /* Similar, but return 1 if OP is a MEM which is not alignable. */
761 unaligned_memory_operand (op, mode)
763 enum machine_mode mode;
765 if (GET_CODE (op) == SUBREG)
767 if (GET_MODE (op) != mode)
769 op = SUBREG_REG (op);
770 mode = GET_MODE (op);
773 if (reload_in_progress && GET_CODE (op) == REG
774 && REGNO (op) >= FIRST_PSEUDO_REGISTER)
775 op = reg_equiv_mem[REGNO (op)];
777 if (GET_CODE (op) != MEM || GET_MODE (op) != mode)
782 if (! memory_address_p (mode, op))
785 if (GET_CODE (op) == PLUS)
788 return (GET_CODE (op) != REG
789 || REGNO_POINTER_ALIGN (REGNO (op)) < 4);
792 /* Return 1 if OP is either a register or an unaligned memory location. */
795 reg_or_unaligned_mem_operand (op, mode)
797 enum machine_mode mode;
799 return register_operand (op, mode) || unaligned_memory_operand (op, mode);
802 /* Return 1 if OP is any memory location. During reload a pseudo matches. */
805 any_memory_operand (op, mode)
807 enum machine_mode mode;
809 return (GET_CODE (op) == MEM
810 || (GET_CODE (op) == SUBREG && GET_CODE (SUBREG_REG (op)) == REG)
811 || (reload_in_progress && GET_CODE (op) == REG
812 && REGNO (op) >= FIRST_PSEUDO_REGISTER)
813 || (reload_in_progress && GET_CODE (op) == SUBREG
814 && GET_CODE (SUBREG_REG (op)) == REG
815 && REGNO (SUBREG_REG (op)) >= FIRST_PSEUDO_REGISTER));
818 /* REF is an alignable memory location. Place an aligned SImode
819 reference into *PALIGNED_MEM and the number of bits to shift into
823 get_aligned_mem (ref, paligned_mem, pbitnum)
825 rtx *paligned_mem, *pbitnum;
828 HOST_WIDE_INT offset = 0;
830 if (GET_CODE (ref) == SUBREG)
832 offset = SUBREG_WORD (ref) * UNITS_PER_WORD;
833 if (BYTES_BIG_ENDIAN)
834 offset -= (MIN (UNITS_PER_WORD, GET_MODE_SIZE (GET_MODE (ref)))
835 - MIN (UNITS_PER_WORD,
836 GET_MODE_SIZE (GET_MODE (SUBREG_REG (ref)))));
837 ref = SUBREG_REG (ref);
840 if (GET_CODE (ref) == REG)
841 ref = reg_equiv_mem[REGNO (ref)];
843 if (reload_in_progress)
844 base = find_replacement (&XEXP (ref, 0));
846 base = XEXP (ref, 0);
848 if (GET_CODE (base) == PLUS)
849 offset += INTVAL (XEXP (base, 1)), base = XEXP (base, 0);
851 *paligned_mem = gen_rtx_MEM (SImode,
852 plus_constant (base, offset & ~3));
853 MEM_IN_STRUCT_P (*paligned_mem) = MEM_IN_STRUCT_P (ref);
854 MEM_VOLATILE_P (*paligned_mem) = MEM_VOLATILE_P (ref);
855 RTX_UNCHANGING_P (*paligned_mem) = RTX_UNCHANGING_P (ref);
857 *pbitnum = GEN_INT ((offset & 3) * 8);
860 /* Similar, but just get the address. Handle the two reload cases.
861 Add EXTRA_OFFSET to the address we return. */
864 get_unaligned_address (ref, extra_offset)
869 HOST_WIDE_INT offset = 0;
871 if (GET_CODE (ref) == SUBREG)
873 offset = SUBREG_WORD (ref) * UNITS_PER_WORD;
874 if (BYTES_BIG_ENDIAN)
875 offset -= (MIN (UNITS_PER_WORD, GET_MODE_SIZE (GET_MODE (ref)))
876 - MIN (UNITS_PER_WORD,
877 GET_MODE_SIZE (GET_MODE (SUBREG_REG (ref)))));
878 ref = SUBREG_REG (ref);
881 if (GET_CODE (ref) == REG)
882 ref = reg_equiv_mem[REGNO (ref)];
884 if (reload_in_progress)
885 base = find_replacement (&XEXP (ref, 0));
887 base = XEXP (ref, 0);
889 if (GET_CODE (base) == PLUS)
890 offset += INTVAL (XEXP (base, 1)), base = XEXP (base, 0);
892 return plus_constant (base, offset + extra_offset);
895 /* Subfunction of the following function. Update the flags of any MEM
896 found in part of X. */
899 alpha_set_memflags_1 (x, in_struct_p, volatile_p, unchanging_p)
901 int in_struct_p, volatile_p, unchanging_p;
905 switch (GET_CODE (x))
909 for (i = XVECLEN (x, 0) - 1; i >= 0; i--)
910 alpha_set_memflags_1 (XVECEXP (x, 0, i), in_struct_p, volatile_p,
915 alpha_set_memflags_1 (PATTERN (x), in_struct_p, volatile_p,
920 alpha_set_memflags_1 (SET_DEST (x), in_struct_p, volatile_p,
922 alpha_set_memflags_1 (SET_SRC (x), in_struct_p, volatile_p,
927 MEM_IN_STRUCT_P (x) = in_struct_p;
928 MEM_VOLATILE_P (x) = volatile_p;
929 RTX_UNCHANGING_P (x) = unchanging_p;
937 /* Given INSN, which is either an INSN or a SEQUENCE generated to
938 perform a memory operation, look for any MEMs in either a SET_DEST or
939 a SET_SRC and copy the in-struct, unchanging, and volatile flags from
940 REF into each of the MEMs found. If REF is not a MEM, don't do
944 alpha_set_memflags (insn, ref)
948 /* Note that it is always safe to get these flags, though they won't
949 be what we think if REF is not a MEM. */
950 int in_struct_p = MEM_IN_STRUCT_P (ref);
951 int volatile_p = MEM_VOLATILE_P (ref);
952 int unchanging_p = RTX_UNCHANGING_P (ref);
954 if (GET_CODE (ref) != MEM
955 || (! in_struct_p && ! volatile_p && ! unchanging_p))
958 alpha_set_memflags_1 (insn, in_struct_p, volatile_p, unchanging_p);
961 /* Try to output insns to set TARGET equal to the constant C if it can be
962 done in less than N insns. Do all computations in MODE. Returns the place
963 where the output has been placed if it can be done and the insns have been
964 emitted. If it would take more than N insns, zero is returned and no
965 insns and emitted. */
968 alpha_emit_set_const (target, mode, c, n)
970 enum machine_mode mode;
977 /* Try 1 insn, then 2, then up to N. */
978 for (i = 1; i <= n; i++)
979 if ((pat = alpha_emit_set_const_1 (target, mode, c, i)) != 0)
985 /* Internal routine for the above to check for N or below insns. */
988 alpha_emit_set_const_1 (target, mode, c, n)
990 enum machine_mode mode;
994 HOST_WIDE_INT new = c;
996 /* Use a pseudo if highly optimizing and still generating RTL. */
998 = (flag_expensive_optimizations && rtx_equal_function_value_matters
1002 #if HOST_BITS_PER_WIDE_INT == 64
1003 /* We are only called for SImode and DImode. If this is SImode, ensure that
1004 we are sign extended to a full word. This does not make any sense when
1005 cross-compiling on a narrow machine. */
1008 c = (c & 0xffffffff) - 2 * (c & 0x80000000);
1011 /* If this is a sign-extended 32-bit constant, we can do this in at most
1012 three insns, so do it if we have enough insns left. We always have
1013 a sign-extended 32-bit constant when compiling on a narrow machine. */
1015 if (HOST_BITS_PER_WIDE_INT != 64
1016 || c >> 31 == -1 || c >> 31 == 0)
1018 HOST_WIDE_INT low = (c & 0xffff) - 2 * (c & 0x8000);
1019 HOST_WIDE_INT tmp1 = c - low;
1021 = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
1022 HOST_WIDE_INT extra = 0;
1024 /* If HIGH will be interpreted as negative but the constant is
1025 positive, we must adjust it to do two ldha insns. */
1027 if ((high & 0x8000) != 0 && c >= 0)
1031 high = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
1034 if (c == low || (low == 0 && extra == 0))
1036 /* We used to use copy_to_suggested_reg (GEN_INT (c), target, mode)
1037 but that meant that we can't handle INT_MIN on 32-bit machines
1038 (like NT/Alpha), because we recurse indefinitely through
1039 emit_move_insn to gen_movdi. So instead, since we know exactly
1040 what we want, create it explicitly. */
1043 target = gen_reg_rtx (mode);
1044 emit_insn (gen_rtx_SET (VOIDmode, target, GEN_INT (c)));
1047 else if (n >= 2 + (extra != 0))
1049 temp = copy_to_suggested_reg (GEN_INT (low), subtarget, mode);
1052 temp = expand_binop (mode, add_optab, temp, GEN_INT (extra << 16),
1053 subtarget, 0, OPTAB_WIDEN);
1055 return expand_binop (mode, add_optab, temp, GEN_INT (high << 16),
1056 target, 0, OPTAB_WIDEN);
1060 /* If we couldn't do it that way, try some other methods. But if we have
1061 no instructions left, don't bother. Likewise, if this is SImode and
1062 we can't make pseudos, we can't do anything since the expand_binop
1063 and expand_unop calls will widen and try to make pseudos. */
1066 || (mode == SImode && ! rtx_equal_function_value_matters))
1069 #if HOST_BITS_PER_WIDE_INT == 64
1070 /* First, see if can load a value into the target that is the same as the
1071 constant except that all bytes that are 0 are changed to be 0xff. If we
1072 can, then we can do a ZAPNOT to obtain the desired constant. */
1074 for (i = 0; i < 64; i += 8)
1075 if ((new & ((HOST_WIDE_INT) 0xff << i)) == 0)
1076 new |= (HOST_WIDE_INT) 0xff << i;
1078 /* We are only called for SImode and DImode. If this is SImode, ensure that
1079 we are sign extended to a full word. */
1082 new = (new & 0xffffffff) - 2 * (new & 0x80000000);
1085 && (temp = alpha_emit_set_const (subtarget, mode, new, n - 1)) != 0)
1086 return expand_binop (mode, and_optab, temp, GEN_INT (c | ~ new),
1087 target, 0, OPTAB_WIDEN);
1090 /* Next, see if we can load a related constant and then shift and possibly
1091 negate it to get the constant we want. Try this once each increasing
1092 numbers of insns. */
1094 for (i = 1; i < n; i++)
1096 /* First try complementing. */
1097 if ((temp = alpha_emit_set_const (subtarget, mode, ~ c, i)) != 0)
1098 return expand_unop (mode, one_cmpl_optab, temp, target, 0);
1100 /* Next try to form a constant and do a left shift. We can do this
1101 if some low-order bits are zero; the exact_log2 call below tells
1102 us that information. The bits we are shifting out could be any
1103 value, but here we'll just try the 0- and sign-extended forms of
1104 the constant. To try to increase the chance of having the same
1105 constant in more than one insn, start at the highest number of
1106 bits to shift, but try all possibilities in case a ZAPNOT will
1109 if ((bits = exact_log2 (c & - c)) > 0)
1110 for (; bits > 0; bits--)
1111 if ((temp = (alpha_emit_set_const
1113 (unsigned HOST_WIDE_INT) c >> bits, i))) != 0
1114 || ((temp = (alpha_emit_set_const
1116 ((unsigned HOST_WIDE_INT) c) >> bits, i)))
1118 return expand_binop (mode, ashl_optab, temp, GEN_INT (bits),
1119 target, 0, OPTAB_WIDEN);
1121 /* Now try high-order zero bits. Here we try the shifted-in bits as
1122 all zero and all ones. Be careful to avoid shifting outside the
1123 mode and to avoid shifting outside the host wide int size. */
1124 /* On narrow hosts, don't shift a 1 into the high bit, since we'll
1125 confuse the recursive call and set all of the high 32 bits. */
1127 if ((bits = (MIN (HOST_BITS_PER_WIDE_INT, GET_MODE_SIZE (mode) * 8)
1128 - floor_log2 (c) - 1 - (HOST_BITS_PER_WIDE_INT < 64))) > 0)
1129 for (; bits > 0; bits--)
1130 if ((temp = alpha_emit_set_const (subtarget, mode,
1132 || ((temp = (alpha_emit_set_const
1134 ((c << bits) | (((HOST_WIDE_INT) 1 << bits) - 1)),
1137 return expand_binop (mode, lshr_optab, temp, GEN_INT (bits),
1138 target, 1, OPTAB_WIDEN);
1140 /* Now try high-order 1 bits. We get that with a sign-extension.
1141 But one bit isn't enough here. Be careful to avoid shifting outside
1142 the mode and to avoid shifting outside the host wide int size. */
1144 if ((bits = (MIN (HOST_BITS_PER_WIDE_INT, GET_MODE_SIZE (mode) * 8)
1145 - floor_log2 (~ c) - 2)) > 0)
1146 for (; bits > 0; bits--)
1147 if ((temp = alpha_emit_set_const (subtarget, mode,
1149 || ((temp = (alpha_emit_set_const
1151 ((c << bits) | (((HOST_WIDE_INT) 1 << bits) - 1)),
1154 return expand_binop (mode, ashr_optab, temp, GEN_INT (bits),
1155 target, 0, OPTAB_WIDEN);
1161 #if HOST_BITS_PER_WIDE_INT == 64
1162 /* Having failed to find a 3 insn sequence in alpha_emit_set_const,
1163 fall back to a straight forward decomposition. We do this to avoid
1164 exponential run times encountered when looking for longer sequences
1165 with alpha_emit_set_const. */
1168 alpha_emit_set_long_const (target, c)
1172 /* Use a pseudo if highly optimizing and still generating RTL. */
1174 = (flag_expensive_optimizations && rtx_equal_function_value_matters
1176 HOST_WIDE_INT d1, d2, d3, d4;
1179 /* Decompose the entire word */
1180 d1 = ((c & 0xffff) ^ 0x8000) - 0x8000;
1182 d2 = ((c & 0xffffffff) ^ 0x80000000) - 0x80000000;
1184 d3 = ((c & 0xffff) ^ 0x8000) - 0x8000;
1186 d4 = ((c & 0xffffffff) ^ 0x80000000) - 0x80000000;
1191 /* Construct the high word */
1193 r1 = copy_to_suggested_reg (GEN_INT (d4), subtarget, DImode);
1195 r1 = copy_to_suggested_reg (GEN_INT (d3), subtarget, DImode);
1197 r1 = expand_binop (DImode, add_optab, GEN_INT (d3), GEN_INT (d4),
1198 subtarget, 0, OPTAB_WIDEN);
1200 /* Shift it into place */
1201 r2 = expand_binop (DImode, ashl_optab, r1, GEN_INT (32),
1202 subtarget, 0, OPTAB_WIDEN);
1204 if (subtarget == 0 && d1 == d3 && d2 == d4)
1205 r1 = expand_binop (DImode, add_optab, r1, r2, subtarget, 0, OPTAB_WIDEN);
1210 /* Add in the low word */
1212 r1 = expand_binop (DImode, add_optab, r1, GEN_INT (d2),
1213 subtarget, 0, OPTAB_WIDEN);
1215 r1 = expand_binop (DImode, add_optab, r1, GEN_INT (d1),
1216 subtarget, 0, OPTAB_WIDEN);
1220 r1 = copy_to_suggested_reg(r1, target, DImode);
1224 #endif /* HOST_BITS_PER_WIDE_INT == 64 */
1226 /* Generate the comparison for a conditional branch. */
1229 alpha_emit_conditional_branch (code)
1232 enum rtx_code cmp_code, branch_code;
1233 enum machine_mode cmp_mode, branch_mode = VOIDmode;
1234 rtx op0 = alpha_compare_op0, op1 = alpha_compare_op1;
1237 /* The general case: fold the comparison code to the types of compares
1238 that we have, choosing the branch as necessary. */
1241 case EQ: case LE: case LT: case LEU: case LTU:
1242 /* We have these compares: */
1243 cmp_code = code, branch_code = NE;
1247 /* This must be reversed. */
1248 cmp_code = EQ, branch_code = EQ;
1251 case GE: case GT: case GEU: case GTU:
1252 /* For FP, we swap them, for INT, we reverse them. */
1253 if (alpha_compare_fp_p)
1255 cmp_code = swap_condition (code);
1257 tem = op0, op0 = op1, op1 = tem;
1261 cmp_code = reverse_condition (code);
1270 if (alpha_compare_fp_p)
1275 /* When we are not as concerned about non-finite values, and we
1276 are comparing against zero, we can branch directly. */
1277 if (op1 == CONST0_RTX (DFmode))
1278 cmp_code = NIL, branch_code = code;
1279 else if (op0 == CONST0_RTX (DFmode))
1281 /* Undo the swap we probably did just above. */
1282 tem = op0, op0 = op1, op1 = tem;
1283 cmp_code = NIL, branch_code = swap_condition (cmp_code);
1288 /* ??? We mark the the branch mode to be CCmode to prevent the
1289 compare and branch from being combined, since the compare
1290 insn follows IEEE rules that the branch does not. */
1291 branch_mode = CCmode;
1298 /* The following optimizations are only for signed compares. */
1299 if (code != LEU && code != LTU && code != GEU && code != GTU)
1301 /* Whee. Compare and branch against 0 directly. */
1302 if (op1 == const0_rtx)
1303 cmp_code = NIL, branch_code = code;
1305 /* We want to use cmpcc/bcc when we can, since there is a zero delay
1306 bypass between logicals and br/cmov on EV5. But we don't want to
1307 force valid immediate constants into registers needlessly. */
1308 else if (GET_CODE (op1) == CONST_INT)
1310 HOST_WIDE_INT v = INTVAL (op1), n = -v;
1312 if (! CONST_OK_FOR_LETTER_P (v, 'I')
1313 && (CONST_OK_FOR_LETTER_P (n, 'K')
1314 || CONST_OK_FOR_LETTER_P (n, 'L')))
1316 cmp_code = PLUS, branch_code = code;
1323 /* Force op0 into a register. */
1324 if (GET_CODE (op0) != REG)
1325 op0 = force_reg (cmp_mode, op0);
1327 /* Emit an initial compare instruction, if necessary. */
1329 if (cmp_code != NIL)
1331 tem = gen_reg_rtx (cmp_mode);
1332 emit_move_insn (tem, gen_rtx_fmt_ee (cmp_code, cmp_mode, op0, op1));
1335 /* Return the branch comparison. */
1336 return gen_rtx_fmt_ee (branch_code, branch_mode, tem, CONST0_RTX (cmp_mode));
1340 /* Rewrite a comparison against zero CMP of the form
1341 (CODE (cc0) (const_int 0)) so it can be written validly in
1342 a conditional move (if_then_else CMP ...).
1343 If both of the operands that set cc0 are non-zero we must emit
1344 an insn to perform the compare (it can't be done within
1345 the conditional move). */
1347 alpha_emit_conditional_move (cmp, mode)
1349 enum machine_mode mode;
1351 enum rtx_code code = GET_CODE (cmp);
1352 enum rtx_code cmov_code = NE;
1353 rtx op0 = alpha_compare_op0;
1354 rtx op1 = alpha_compare_op1;
1355 enum machine_mode cmp_mode
1356 = (GET_MODE (op0) == VOIDmode ? DImode : GET_MODE (op0));
1357 enum machine_mode cmp_op_mode = alpha_compare_fp_p ? DFmode : DImode;
1358 enum machine_mode cmov_mode = VOIDmode;
1361 if (alpha_compare_fp_p != FLOAT_MODE_P (mode))
1364 /* We may be able to use a conditional move directly.
1365 This avoids emitting spurious compares. */
1366 if (signed_comparison_operator (cmp, cmp_op_mode)
1367 && (!alpha_compare_fp_p || flag_fast_math)
1368 && (op0 == CONST0_RTX (cmp_mode) || op1 == CONST0_RTX (cmp_mode)))
1369 return gen_rtx_fmt_ee (code, VOIDmode, op0, op1);
1371 /* We can't put the comparison insides a conditional move;
1372 emit a compare instruction and put that inside the
1373 conditional move. Make sure we emit only comparisons we have;
1374 swap or reverse as necessary. */
1378 case EQ: case LE: case LT: case LEU: case LTU:
1379 /* We have these compares: */
1383 /* This must be reversed. */
1384 code = reverse_condition (code);
1388 case GE: case GT: case GEU: case GTU:
1389 /* These must be swapped. Make sure the new first operand is in
1391 code = swap_condition (code);
1392 tem = op0, op0 = op1, op1 = tem;
1393 op0 = force_reg (cmp_mode, op0);
1400 /* ??? We mark the the branch mode to be CCmode to prevent the compare
1401 and cmov from being combined, since the compare insn follows IEEE
1402 rules that the cmov does not. */
1403 if (alpha_compare_fp_p && !flag_fast_math)
1406 tem = gen_reg_rtx (cmp_op_mode);
1407 emit_move_insn (tem, gen_rtx_fmt_ee (code, cmp_op_mode, op0, op1));
1408 return gen_rtx_fmt_ee (cmov_code, cmov_mode, tem, CONST0_RTX (cmp_op_mode));
1411 /* Use ext[wlq][lh] as the Architecture Handbook describes for extracting
1415 word: ldq_u r1,X(r11) ldq_u r1,X(r11)
1416 ldq_u r2,X+1(r11) ldq_u r2,X+1(r11)
1417 lda r3,X(r11) lda r3,X+2(r11)
1418 extwl r1,r3,r1 extql r1,r3,r1
1419 extwh r2,r3,r2 extqh r2,r3,r2
1420 or r1.r2.r1 or r1,r2,r1
1423 long: ldq_u r1,X(r11) ldq_u r1,X(r11)
1424 ldq_u r2,X+3(r11) ldq_u r2,X+3(r11)
1425 lda r3,X(r11) lda r3,X(r11)
1426 extll r1,r3,r1 extll r1,r3,r1
1427 extlh r2,r3,r2 extlh r2,r3,r2
1428 or r1.r2.r1 addl r1,r2,r1
1430 quad: ldq_u r1,X(r11)
1439 alpha_expand_unaligned_load (tgt, mem, size, ofs, sign)
1441 HOST_WIDE_INT size, ofs;
1444 rtx meml, memh, addr, extl, exth;
1445 enum machine_mode mode;
1447 meml = gen_reg_rtx (DImode);
1448 memh = gen_reg_rtx (DImode);
1449 addr = gen_reg_rtx (DImode);
1450 extl = gen_reg_rtx (DImode);
1451 exth = gen_reg_rtx (DImode);
1453 emit_move_insn (meml,
1454 change_address (mem, DImode,
1455 gen_rtx_AND (DImode,
1456 plus_constant (XEXP (mem, 0),
1460 emit_move_insn (memh,
1461 change_address (mem, DImode,
1462 gen_rtx_AND (DImode,
1463 plus_constant (XEXP (mem, 0),
1467 if (sign && size == 2)
1469 emit_move_insn (addr, plus_constant (XEXP (mem, 0), ofs+2));
1471 emit_insn (gen_extxl (extl, meml, GEN_INT (64), addr));
1472 emit_insn (gen_extqh (exth, memh, addr));
1474 /* We must use tgt here for the target. Alpha-vms port fails if we use
1475 addr for the target, because addr is marked as a pointer and combine
1476 knows that pointers are always sign-extended 32 bit values. */
1477 addr = expand_binop (DImode, ior_optab, extl, exth, tgt, 1, OPTAB_WIDEN);
1478 addr = expand_binop (DImode, ashr_optab, addr, GEN_INT (48),
1479 addr, 1, OPTAB_WIDEN);
1483 emit_move_insn (addr, plus_constant (XEXP (mem, 0), ofs));
1484 emit_insn (gen_extxl (extl, meml, GEN_INT (size*8), addr));
1488 emit_insn (gen_extwh (exth, memh, addr));
1493 emit_insn (gen_extlh (exth, memh, addr));
1498 emit_insn (gen_extqh (exth, memh, addr));
1503 addr = expand_binop (mode, ior_optab, gen_lowpart (mode, extl),
1504 gen_lowpart (mode, exth), gen_lowpart (mode, tgt),
1509 emit_move_insn (tgt, gen_lowpart(GET_MODE (tgt), addr));
1512 /* Similarly, use ins and msk instructions to perform unaligned stores. */
1515 alpha_expand_unaligned_store (dst, src, size, ofs)
1517 HOST_WIDE_INT size, ofs;
1519 rtx dstl, dsth, addr, insl, insh, meml, memh;
1521 dstl = gen_reg_rtx (DImode);
1522 dsth = gen_reg_rtx (DImode);
1523 insl = gen_reg_rtx (DImode);
1524 insh = gen_reg_rtx (DImode);
1526 meml = change_address (dst, DImode,
1527 gen_rtx_AND (DImode,
1528 plus_constant (XEXP (dst, 0), ofs),
1530 memh = change_address (dst, DImode,
1531 gen_rtx_AND (DImode,
1532 plus_constant (XEXP (dst, 0),
1536 emit_move_insn (dsth, memh);
1537 emit_move_insn (dstl, meml);
1538 addr = copy_addr_to_reg (plus_constant (XEXP (dst, 0), ofs));
1540 if (src != const0_rtx)
1542 emit_insn (gen_insxh (insh, gen_lowpart (DImode, src),
1543 GEN_INT (size*8), addr));
1548 emit_insn (gen_inswl (insl, gen_lowpart (HImode, src), addr));
1551 emit_insn (gen_insll (insl, gen_lowpart (SImode, src), addr));
1554 emit_insn (gen_insql (insl, src, addr));
1559 emit_insn (gen_mskxh (dsth, dsth, GEN_INT (size*8), addr));
1564 emit_insn (gen_mskxl (dstl, dstl, GEN_INT (0xffff), addr));
1567 emit_insn (gen_mskxl (dstl, dstl, GEN_INT (0xffffffff), addr));
1571 #if HOST_BITS_PER_WIDE_INT == 32
1572 rtx msk = immed_double_const (0xffffffff, 0xffffffff, DImode);
1574 rtx msk = immed_double_const (0xffffffffffffffff, 0, DImode);
1576 emit_insn (gen_mskxl (dstl, dstl, msk, addr));
1581 if (src != const0_rtx)
1583 dsth = expand_binop (DImode, ior_optab, insh, dsth, dsth, 0, OPTAB_WIDEN);
1584 dstl = expand_binop (DImode, ior_optab, insl, dstl, dstl, 0, OPTAB_WIDEN);
1587 /* Must store high before low for degenerate case of aligned. */
1588 emit_move_insn (memh, dsth);
1589 emit_move_insn (meml, dstl);
1592 /* The block move code tries to maximize speed by separating loads and
1593 stores at the expense of register pressure: we load all of the data
1594 before we store it back out. There are two secondary effects worth
1595 mentioning, that this speeds copying to/from aligned and unaligned
1596 buffers, and that it makes the code significantly easier to write. */
1598 #define MAX_MOVE_WORDS 8
1600 /* Load an integral number of consecutive unaligned quadwords. */
1603 alpha_expand_unaligned_load_words (out_regs, smem, words, ofs)
1606 HOST_WIDE_INT words, ofs;
1608 rtx const im8 = GEN_INT (-8);
1609 rtx const i64 = GEN_INT (64);
1610 rtx ext_tmps[MAX_MOVE_WORDS], data_regs[MAX_MOVE_WORDS+1];
1614 /* Generate all the tmp registers we need. */
1615 for (i = 0; i < words; ++i)
1617 data_regs[i] = out_regs[i];
1618 ext_tmps[i] = gen_reg_rtx (DImode);
1620 data_regs[words] = gen_reg_rtx (DImode);
1623 smem = change_address (smem, GET_MODE (smem),
1624 plus_constant (XEXP (smem, 0), ofs));
1626 /* Load up all of the source data. */
1627 for (i = 0; i < words; ++i)
1629 emit_move_insn (data_regs[i],
1630 change_address (smem, DImode,
1631 gen_rtx_AND (DImode,
1632 plus_constant (XEXP(smem,0),
1636 emit_move_insn (data_regs[words],
1637 change_address (smem, DImode,
1638 gen_rtx_AND (DImode,
1639 plus_constant (XEXP(smem,0),
1643 /* Extract the half-word fragments. Unfortunately DEC decided to make
1644 extxh with offset zero a noop instead of zeroing the register, so
1645 we must take care of that edge condition ourselves with cmov. */
1647 sreg = copy_addr_to_reg (XEXP (smem, 0));
1648 areg = expand_binop (DImode, and_optab, sreg, GEN_INT (7), NULL,
1650 for (i = 0; i < words; ++i)
1652 emit_insn (gen_extxl (data_regs[i], data_regs[i], i64, sreg));
1654 emit_insn (gen_extqh (ext_tmps[i], data_regs[i+1], sreg));
1655 emit_insn (gen_rtx_SET (VOIDmode, ext_tmps[i],
1656 gen_rtx_IF_THEN_ELSE (DImode,
1657 gen_rtx_EQ (DImode, areg,
1659 const0_rtx, ext_tmps[i])));
1662 /* Merge the half-words into whole words. */
1663 for (i = 0; i < words; ++i)
1665 out_regs[i] = expand_binop (DImode, ior_optab, data_regs[i],
1666 ext_tmps[i], data_regs[i], 1, OPTAB_WIDEN);
1670 /* Store an integral number of consecutive unaligned quadwords. DATA_REGS
1671 may be NULL to store zeros. */
1674 alpha_expand_unaligned_store_words (data_regs, dmem, words, ofs)
1677 HOST_WIDE_INT words, ofs;
1679 rtx const im8 = GEN_INT (-8);
1680 rtx const i64 = GEN_INT (64);
1681 #if HOST_BITS_PER_WIDE_INT == 32
1682 rtx const im1 = immed_double_const (0xffffffff, 0xffffffff, DImode);
1684 rtx const im1 = immed_double_const (0xffffffffffffffff, 0, DImode);
1686 rtx ins_tmps[MAX_MOVE_WORDS];
1687 rtx st_tmp_1, st_tmp_2, dreg;
1688 rtx st_addr_1, st_addr_2;
1691 /* Generate all the tmp registers we need. */
1692 if (data_regs != NULL)
1693 for (i = 0; i < words; ++i)
1694 ins_tmps[i] = gen_reg_rtx(DImode);
1695 st_tmp_1 = gen_reg_rtx(DImode);
1696 st_tmp_2 = gen_reg_rtx(DImode);
1699 dmem = change_address (dmem, GET_MODE (dmem),
1700 plus_constant (XEXP (dmem, 0), ofs));
1703 st_addr_2 = change_address (dmem, DImode,
1704 gen_rtx_AND (DImode,
1705 plus_constant (XEXP(dmem,0),
1708 st_addr_1 = change_address (dmem, DImode,
1709 gen_rtx_AND (DImode,
1713 /* Load up the destination end bits. */
1714 emit_move_insn (st_tmp_2, st_addr_2);
1715 emit_move_insn (st_tmp_1, st_addr_1);
1717 /* Shift the input data into place. */
1718 dreg = copy_addr_to_reg (XEXP (dmem, 0));
1719 if (data_regs != NULL)
1721 for (i = words-1; i >= 0; --i)
1723 emit_insn (gen_insxh (ins_tmps[i], data_regs[i], i64, dreg));
1724 emit_insn (gen_insql (data_regs[i], data_regs[i], dreg));
1726 for (i = words-1; i > 0; --i)
1728 ins_tmps[i-1] = expand_binop (DImode, ior_optab, data_regs[i],
1729 ins_tmps[i-1], ins_tmps[i-1], 1,
1734 /* Split and merge the ends with the destination data. */
1735 emit_insn (gen_mskxh (st_tmp_2, st_tmp_2, i64, dreg));
1736 emit_insn (gen_mskxl (st_tmp_1, st_tmp_1, im1, dreg));
1738 if (data_regs != NULL)
1740 st_tmp_2 = expand_binop (DImode, ior_optab, st_tmp_2, ins_tmps[words-1],
1741 st_tmp_2, 1, OPTAB_WIDEN);
1742 st_tmp_1 = expand_binop (DImode, ior_optab, st_tmp_1, data_regs[0],
1743 st_tmp_1, 1, OPTAB_WIDEN);
1747 emit_move_insn (st_addr_2, st_tmp_2);
1748 for (i = words-1; i > 0; --i)
1750 emit_move_insn (change_address (dmem, DImode,
1751 gen_rtx_AND (DImode,
1752 plus_constant(XEXP (dmem,0),
1755 data_regs ? ins_tmps[i-1] : const0_rtx);
1757 emit_move_insn (st_addr_1, st_tmp_1);
1761 /* Expand string/block move operations.
1763 operands[0] is the pointer to the destination.
1764 operands[1] is the pointer to the source.
1765 operands[2] is the number of bytes to move.
1766 operands[3] is the alignment. */
1769 alpha_expand_block_move (operands)
1772 rtx bytes_rtx = operands[2];
1773 rtx align_rtx = operands[3];
1774 HOST_WIDE_INT bytes = INTVAL (bytes_rtx);
1775 HOST_WIDE_INT src_align = INTVAL (align_rtx);
1776 HOST_WIDE_INT dst_align = src_align;
1777 rtx orig_src = operands[1];
1778 rtx orig_dst = operands[0];
1779 rtx data_regs[2*MAX_MOVE_WORDS+16];
1781 int i, words, ofs, nregs = 0;
1785 if (bytes > MAX_MOVE_WORDS*8)
1788 /* Look for additional alignment information from recorded register info. */
1790 tmp = XEXP (orig_src, 0);
1791 if (GET_CODE (tmp) == REG)
1793 if (REGNO_POINTER_ALIGN (REGNO (tmp)) > src_align)
1794 src_align = REGNO_POINTER_ALIGN (REGNO (tmp));
1796 else if (GET_CODE (tmp) == PLUS
1797 && GET_CODE (XEXP (tmp, 0)) == REG
1798 && GET_CODE (XEXP (tmp, 1)) == CONST_INT)
1800 HOST_WIDE_INT c = INTVAL (XEXP (tmp, 1));
1801 int a = REGNO_POINTER_ALIGN (REGNO (XEXP (tmp, 0)));
1805 if (a >= 8 && c % 8 == 0)
1807 else if (a >= 4 && c % 4 == 0)
1809 else if (a >= 2 && c % 2 == 0)
1814 tmp = XEXP (orig_dst, 0);
1815 if (GET_CODE (tmp) == REG)
1817 if (REGNO_POINTER_ALIGN (REGNO (tmp)) > dst_align)
1818 dst_align = REGNO_POINTER_ALIGN (REGNO (tmp));
1820 else if (GET_CODE (tmp) == PLUS
1821 && GET_CODE (XEXP (tmp, 0)) == REG
1822 && GET_CODE (XEXP (tmp, 1)) == CONST_INT)
1824 HOST_WIDE_INT c = INTVAL (XEXP (tmp, 1));
1825 int a = REGNO_POINTER_ALIGN (REGNO (XEXP (tmp, 0)));
1829 if (a >= 8 && c % 8 == 0)
1831 else if (a >= 4 && c % 4 == 0)
1833 else if (a >= 2 && c % 2 == 0)
1839 * Load the entire block into registers.
1842 if (GET_CODE (XEXP (orig_src, 0)) == ADDRESSOF)
1844 enum machine_mode mode;
1845 tmp = XEXP (XEXP (orig_src, 0), 0);
1847 mode = mode_for_size (bytes, MODE_INT, 1);
1849 && GET_MODE_SIZE (GET_MODE (tmp)) <= bytes)
1851 /* Whee! Optimize the load to use the existing register. */
1852 data_regs[nregs++] = gen_lowpart (mode, tmp);
1856 /* ??? We could potentially be copying 3 bytes or whatnot from
1857 a wider reg. Probably not worth worrying about. */
1858 /* No appropriate mode; fall back on memory. */
1859 orig_src = change_address (orig_src, GET_MODE (orig_src),
1860 copy_addr_to_reg (XEXP (orig_src, 0)));
1864 if (src_align >= 8 && bytes >= 8)
1868 for (i = 0; i < words; ++i)
1869 data_regs[nregs+i] = gen_reg_rtx(DImode);
1871 for (i = 0; i < words; ++i)
1873 emit_move_insn (data_regs[nregs+i],
1874 change_address(orig_src, DImode,
1875 plus_constant (XEXP (orig_src, 0),
1883 if (src_align >= 4 && bytes >= 4)
1887 for (i = 0; i < words; ++i)
1888 data_regs[nregs+i] = gen_reg_rtx(SImode);
1890 for (i = 0; i < words; ++i)
1892 emit_move_insn (data_regs[nregs+i],
1893 change_address(orig_src, SImode,
1894 plus_constant (XEXP (orig_src, 0),
1906 for (i = 0; i < words+1; ++i)
1907 data_regs[nregs+i] = gen_reg_rtx(DImode);
1909 alpha_expand_unaligned_load_words(data_regs+nregs, orig_src, words, ofs);
1915 if (!TARGET_BWX && bytes >= 8)
1917 data_regs[nregs++] = tmp = gen_reg_rtx (DImode);
1918 alpha_expand_unaligned_load (tmp, orig_src, 8, ofs, 0);
1922 if (!TARGET_BWX && bytes >= 4)
1924 data_regs[nregs++] = tmp = gen_reg_rtx (SImode);
1925 alpha_expand_unaligned_load (tmp, orig_src, 4, ofs, 0);
1934 data_regs[nregs++] = tmp = gen_reg_rtx (HImode);
1935 emit_move_insn (tmp,
1936 change_address (orig_src, HImode,
1937 plus_constant (XEXP (orig_src, 0),
1941 } while (bytes >= 2);
1943 else if (!TARGET_BWX)
1945 data_regs[nregs++] = tmp = gen_reg_rtx (HImode);
1946 alpha_expand_unaligned_load (tmp, orig_src, 2, ofs, 0);
1953 data_regs[nregs++] = tmp = gen_reg_rtx (QImode);
1954 emit_move_insn (tmp,
1955 change_address (orig_src, QImode,
1956 plus_constant (XEXP (orig_src, 0),
1963 if (nregs > sizeof(data_regs)/sizeof(*data_regs))
1967 * Now save it back out again.
1972 if (GET_CODE (XEXP (orig_dst, 0)) == ADDRESSOF)
1974 enum machine_mode mode;
1975 tmp = XEXP (XEXP (orig_dst, 0), 0);
1977 mode = mode_for_size (bytes, MODE_INT, 1);
1978 if (GET_MODE (tmp) == mode && nregs == 1)
1980 emit_move_insn (tmp, data_regs[0]);
1985 /* ??? If nregs > 1, consider reconstructing the word in regs. */
1986 /* ??? Optimize mode < dst_mode with strict_low_part. */
1987 /* No appropriate mode; fall back on memory. */
1988 orig_dst = change_address (orig_dst, GET_MODE (orig_dst),
1989 copy_addr_to_reg (XEXP (orig_dst, 0)));
1992 /* Write out the data in whatever chunks reading the source allowed. */
1995 while (i < nregs && GET_MODE (data_regs[i]) == DImode)
1997 emit_move_insn (change_address(orig_dst, DImode,
1998 plus_constant (XEXP (orig_dst, 0),
2007 /* If the source has remaining DImode regs, write them out in
2009 while (i < nregs && GET_MODE (data_regs[i]) == DImode)
2011 tmp = expand_binop (DImode, lshr_optab, data_regs[i], GEN_INT (32),
2012 NULL_RTX, 1, OPTAB_WIDEN);
2014 emit_move_insn (change_address(orig_dst, SImode,
2015 plus_constant (XEXP (orig_dst, 0),
2017 gen_lowpart (SImode, data_regs[i]));
2018 emit_move_insn (change_address(orig_dst, SImode,
2019 plus_constant (XEXP (orig_dst, 0),
2021 gen_lowpart (SImode, tmp));
2026 while (i < nregs && GET_MODE (data_regs[i]) == SImode)
2028 emit_move_insn (change_address(orig_dst, SImode,
2029 plus_constant (XEXP (orig_dst, 0),
2036 if (i < nregs && GET_MODE (data_regs[i]) == DImode)
2038 /* Write out a remaining block of words using unaligned methods. */
2040 for (words = 1; i+words < nregs ; ++words)
2041 if (GET_MODE (data_regs[i+words]) != DImode)
2045 alpha_expand_unaligned_store (orig_dst, data_regs[i], 8, ofs);
2047 alpha_expand_unaligned_store_words (data_regs+i, orig_dst, words, ofs);
2053 /* Due to the above, this won't be aligned. */
2054 /* ??? If we have more than one of these, consider constructing full
2055 words in registers and using alpha_expand_unaligned_store_words. */
2056 while (i < nregs && GET_MODE (data_regs[i]) == SImode)
2058 alpha_expand_unaligned_store (orig_dst, data_regs[i], 4, ofs);
2064 while (i < nregs && GET_MODE (data_regs[i]) == HImode)
2066 emit_move_insn (change_address (orig_dst, HImode,
2067 plus_constant (XEXP (orig_dst, 0),
2074 while (i < nregs && GET_MODE (data_regs[i]) == HImode)
2076 alpha_expand_unaligned_store (orig_dst, data_regs[i], 2, ofs);
2080 while (i < nregs && GET_MODE (data_regs[i]) == QImode)
2082 emit_move_insn (change_address (orig_dst, QImode,
2083 plus_constant (XEXP (orig_dst, 0),
2098 alpha_expand_block_clear (operands)
2101 rtx bytes_rtx = operands[1];
2102 rtx align_rtx = operands[2];
2103 HOST_WIDE_INT bytes = INTVAL (bytes_rtx);
2104 HOST_WIDE_INT align = INTVAL (align_rtx);
2105 rtx orig_dst = operands[0];
2107 HOST_WIDE_INT i, words, ofs = 0;
2111 if (bytes > MAX_MOVE_WORDS*8)
2114 /* Look for stricter alignment. */
2116 tmp = XEXP (orig_dst, 0);
2117 if (GET_CODE (tmp) == REG)
2119 if (REGNO_POINTER_ALIGN (REGNO (tmp)) > align)
2120 align = REGNO_POINTER_ALIGN (REGNO (tmp));
2122 else if (GET_CODE (tmp) == PLUS
2123 && GET_CODE (XEXP (tmp, 0)) == REG
2124 && GET_CODE (XEXP (tmp, 1)) == CONST_INT)
2126 HOST_WIDE_INT c = INTVAL (XEXP (tmp, 1));
2127 int a = REGNO_POINTER_ALIGN (REGNO (XEXP (tmp, 0)));
2131 if (a >= 8 && c % 8 == 0)
2133 else if (a >= 4 && c % 4 == 0)
2135 else if (a >= 2 && c % 2 == 0)
2140 /* Handle a block of contiguous words first. */
2142 if (align >= 8 && bytes >= 8)
2146 for (i = 0; i < words; ++i)
2148 emit_move_insn (change_address(orig_dst, DImode,
2149 plus_constant (XEXP (orig_dst, 0),
2157 if (align >= 4 && bytes >= 4)
2161 for (i = 0; i < words; ++i)
2163 emit_move_insn (change_address(orig_dst, SImode,
2164 plus_constant (XEXP (orig_dst, 0),
2176 alpha_expand_unaligned_store_words (NULL, orig_dst, words, ofs);
2182 /* Next clean up any trailing pieces. We know from the contiguous
2183 block move that there are no aligned SImode or DImode hunks left. */
2185 if (!TARGET_BWX && bytes >= 8)
2187 alpha_expand_unaligned_store (orig_dst, const0_rtx, 8, ofs);
2191 if (!TARGET_BWX && bytes >= 4)
2193 alpha_expand_unaligned_store (orig_dst, const0_rtx, 4, ofs);
2202 emit_move_insn (change_address (orig_dst, HImode,
2203 plus_constant (XEXP (orig_dst, 0),
2208 } while (bytes >= 2);
2210 else if (!TARGET_BWX)
2212 alpha_expand_unaligned_store (orig_dst, const0_rtx, 2, ofs);
2219 emit_move_insn (change_address (orig_dst, QImode,
2220 plus_constant (XEXP (orig_dst, 0),
2231 /* Adjust the cost of a scheduling dependency. Return the new cost of
2232 a dependency LINK or INSN on DEP_INSN. COST is the current cost. */
2235 alpha_adjust_cost (insn, link, dep_insn, cost)
2242 enum attr_type insn_type, dep_insn_type;
2244 /* If the dependence is an anti-dependence, there is no cost. For an
2245 output dependence, there is sometimes a cost, but it doesn't seem
2246 worth handling those few cases. */
2248 if (REG_NOTE_KIND (link) != 0)
2251 /* If we can't recognize the insns, we can't really do anything. */
2252 if (recog_memoized (insn) < 0 || recog_memoized (dep_insn) < 0)
2255 insn_type = get_attr_type (insn);
2256 dep_insn_type = get_attr_type (dep_insn);
2258 /* Bring in the user-defined memory latency. */
2259 if (dep_insn_type == TYPE_ILD
2260 || dep_insn_type == TYPE_FLD
2261 || dep_insn_type == TYPE_LDSYM)
2262 cost += alpha_memory_latency-1;
2267 /* On EV4, if INSN is a store insn and DEP_INSN is setting the data
2268 being stored, we can sometimes lower the cost. */
2270 if ((insn_type == TYPE_IST || insn_type == TYPE_FST)
2271 && (set = single_set (dep_insn)) != 0
2272 && GET_CODE (PATTERN (insn)) == SET
2273 && rtx_equal_p (SET_DEST (set), SET_SRC (PATTERN (insn))))
2275 switch (dep_insn_type)
2279 /* No savings here. */
2283 /* In these cases, we save one cycle. */
2287 /* In all other cases, we save two cycles. */
2288 return MAX (0, cost - 2);
2292 /* Another case that needs adjustment is an arithmetic or logical
2293 operation. It's cost is usually one cycle, but we default it to
2294 two in the MD file. The only case that it is actually two is
2295 for the address in loads, stores, and jumps. */
2297 if (dep_insn_type == TYPE_IADD || dep_insn_type == TYPE_ILOG)
2312 /* The final case is when a compare feeds into an integer branch;
2313 the cost is only one cycle in that case. */
2315 if (dep_insn_type == TYPE_ICMP && insn_type == TYPE_IBR)
2320 /* And the lord DEC saith: "A special bypass provides an effective
2321 latency of 0 cycles for an ICMP or ILOG insn producing the test
2322 operand of an IBR or ICMOV insn." */
2324 if ((dep_insn_type == TYPE_ICMP || dep_insn_type == TYPE_ILOG)
2325 && (set = single_set (dep_insn)) != 0)
2327 /* A branch only has one input. This must be it. */
2328 if (insn_type == TYPE_IBR)
2330 /* A conditional move has three, make sure it is the test. */
2331 if (insn_type == TYPE_ICMOV
2332 && GET_CODE (set_src = PATTERN (insn)) == SET
2333 && GET_CODE (set_src = SET_SRC (set_src)) == IF_THEN_ELSE
2334 && rtx_equal_p (SET_DEST (set), XEXP (set_src, 0)))
2338 /* "The multiplier is unable to receive data from IEU bypass paths.
2339 The instruction issues at the expected time, but its latency is
2340 increased by the time it takes for the input data to become
2341 available to the multiplier" -- which happens in pipeline stage
2342 six, when results are comitted to the register file. */
2344 if (insn_type == TYPE_IMUL)
2346 switch (dep_insn_type)
2348 /* These insns produce their results in pipeline stage five. */
2355 /* Other integer insns produce results in pipeline stage four. */
2363 /* There is additional latency to move the result of (most) FP
2364 operations anywhere but the FP register file. */
2366 if ((insn_type == TYPE_FST || insn_type == TYPE_FTOI)
2367 && (dep_insn_type == TYPE_FADD ||
2368 dep_insn_type == TYPE_FMUL ||
2369 dep_insn_type == TYPE_FCMOV))
2375 /* Otherwise, return the default cost. */
2379 /* Functions to save and restore alpha_return_addr_rtx. */
2381 struct machine_function
2387 alpha_save_machine_status (p)
2390 struct machine_function *machine =
2391 (struct machine_function *) xmalloc (sizeof (struct machine_function));
2393 p->machine = machine;
2394 machine->ra_rtx = alpha_return_addr_rtx;
2398 alpha_restore_machine_status (p)
2401 struct machine_function *machine = p->machine;
2403 alpha_return_addr_rtx = machine->ra_rtx;
2406 p->machine = (struct machine_function *)0;
2409 /* Do anything needed before RTL is emitted for each function. */
2412 alpha_init_expanders ()
2414 alpha_return_addr_rtx = NULL_RTX;
2416 /* Arrange to save and restore machine status around nested functions. */
2417 save_machine_status = alpha_save_machine_status;
2418 restore_machine_status = alpha_restore_machine_status;
2421 /* Start the ball rolling with RETURN_ADDR_RTX. */
2424 alpha_return_addr (count, frame)
2433 if (alpha_return_addr_rtx)
2434 return alpha_return_addr_rtx;
2436 /* No rtx yet. Invent one, and initialize it from $26 in the prologue. */
2437 alpha_return_addr_rtx = gen_reg_rtx (Pmode);
2438 init = gen_rtx_SET (Pmode, alpha_return_addr_rtx,
2439 gen_rtx_REG (Pmode, REG_RA));
2441 /* Emit the insn to the prologue with the other argument copies. */
2442 push_topmost_sequence ();
2443 emit_insn_after (init, get_insns ());
2444 pop_topmost_sequence ();
2446 return alpha_return_addr_rtx;
2450 alpha_ra_ever_killed ()
2452 if (!alpha_return_addr_rtx)
2453 return regs_ever_live[REG_RA];
2455 return reg_set_between_p (gen_rtx_REG (Pmode, REG_RA),
2456 get_insns(), NULL_RTX);
2460 /* Print an operand. Recognize special options, documented below. */
2463 print_operand (file, x, code)
2473 /* Generates fp-rounding mode suffix: nothing for normal, 'c' for
2474 chopped, 'm' for minus-infinity, and 'd' for dynamic rounding
2475 mode. alpha_fprm controls which suffix is generated. */
2478 case ALPHA_FPRM_NORM:
2480 case ALPHA_FPRM_MINF:
2483 case ALPHA_FPRM_CHOP:
2486 case ALPHA_FPRM_DYN:
2493 /* Generates trap-mode suffix for instructions that accept the su
2494 suffix only (cmpt et al). */
2495 if (alpha_tp == ALPHA_TP_INSN)
2500 /* Generates trap-mode suffix for instructions that accept the
2501 v and sv suffix. The only instruction that needs this is cvtql. */
2510 case ALPHA_FPTM_SUI:
2517 /* Generates trap-mode suffix for instructions that accept the
2518 v, sv, and svi suffix. The only instruction that needs this
2530 case ALPHA_FPTM_SUI:
2531 fputs ("svi", file);
2537 /* Generates trap-mode suffix for instructions that accept the u, su,
2538 and sui suffix. This is the bulk of the IEEE floating point
2539 instructions (addt et al). */
2550 case ALPHA_FPTM_SUI:
2551 fputs ("sui", file);
2557 /* Generates trap-mode suffix for instructions that accept the sui
2558 suffix (cvtqt and cvtqs). */
2563 case ALPHA_FPTM_SU: /* cvtqt/cvtqs can't cause underflow */
2565 case ALPHA_FPTM_SUI:
2566 fputs ("sui", file);
2572 /* Generates single precision instruction suffix. */
2573 fprintf (file, "%c", (TARGET_FLOAT_VAX ? 'f' : 's'));
2577 /* Generates double precision instruction suffix. */
2578 fprintf (file, "%c", (TARGET_FLOAT_VAX ? 'g' : 't'));
2582 /* If this operand is the constant zero, write it as "$31". */
2583 if (GET_CODE (x) == REG)
2584 fprintf (file, "%s", reg_names[REGNO (x)]);
2585 else if (x == CONST0_RTX (GET_MODE (x)))
2586 fprintf (file, "$31");
2588 output_operand_lossage ("invalid %%r value");
2593 /* Similar, but for floating-point. */
2594 if (GET_CODE (x) == REG)
2595 fprintf (file, "%s", reg_names[REGNO (x)]);
2596 else if (x == CONST0_RTX (GET_MODE (x)))
2597 fprintf (file, "$f31");
2599 output_operand_lossage ("invalid %%R value");
2604 /* Write the 1's complement of a constant. */
2605 if (GET_CODE (x) != CONST_INT)
2606 output_operand_lossage ("invalid %%N value");
2608 fprintf (file, HOST_WIDE_INT_PRINT_DEC, ~ INTVAL (x));
2612 /* Write 1 << C, for a constant C. */
2613 if (GET_CODE (x) != CONST_INT)
2614 output_operand_lossage ("invalid %%P value");
2616 fprintf (file, HOST_WIDE_INT_PRINT_DEC, (HOST_WIDE_INT) 1 << INTVAL (x));
2620 /* Write the high-order 16 bits of a constant, sign-extended. */
2621 if (GET_CODE (x) != CONST_INT)
2622 output_operand_lossage ("invalid %%h value");
2624 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x) >> 16);
2628 /* Write the low-order 16 bits of a constant, sign-extended. */
2629 if (GET_CODE (x) != CONST_INT)
2630 output_operand_lossage ("invalid %%L value");
2632 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
2633 (INTVAL (x) & 0xffff) - 2 * (INTVAL (x) & 0x8000));
2637 /* Write mask for ZAP insn. */
2638 if (GET_CODE (x) == CONST_DOUBLE)
2640 HOST_WIDE_INT mask = 0;
2641 HOST_WIDE_INT value;
2643 value = CONST_DOUBLE_LOW (x);
2644 for (i = 0; i < HOST_BITS_PER_WIDE_INT / HOST_BITS_PER_CHAR;
2649 value = CONST_DOUBLE_HIGH (x);
2650 for (i = 0; i < HOST_BITS_PER_WIDE_INT / HOST_BITS_PER_CHAR;
2653 mask |= (1 << (i + sizeof (int)));
2655 fprintf (file, HOST_WIDE_INT_PRINT_DEC, mask & 0xff);
2658 else if (GET_CODE (x) == CONST_INT)
2660 HOST_WIDE_INT mask = 0, value = INTVAL (x);
2662 for (i = 0; i < 8; i++, value >>= 8)
2666 fprintf (file, HOST_WIDE_INT_PRINT_DEC, mask);
2669 output_operand_lossage ("invalid %%m value");
2673 /* 'b', 'w', 'l', or 'q' as the value of the constant. */
2674 if (GET_CODE (x) != CONST_INT
2675 || (INTVAL (x) != 8 && INTVAL (x) != 16
2676 && INTVAL (x) != 32 && INTVAL (x) != 64))
2677 output_operand_lossage ("invalid %%M value");
2679 fprintf (file, "%s",
2680 (INTVAL (x) == 8 ? "b"
2681 : INTVAL (x) == 16 ? "w"
2682 : INTVAL (x) == 32 ? "l"
2687 /* Similar, except do it from the mask. */
2688 if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0xff)
2689 fprintf (file, "b");
2690 else if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0xffff)
2691 fprintf (file, "w");
2692 else if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0xffffffff)
2693 fprintf (file, "l");
2694 #if HOST_BITS_PER_WIDE_INT == 32
2695 else if (GET_CODE (x) == CONST_DOUBLE
2696 && CONST_DOUBLE_HIGH (x) == 0
2697 && CONST_DOUBLE_LOW (x) == -1)
2698 fprintf (file, "l");
2699 else if (GET_CODE (x) == CONST_DOUBLE
2700 && CONST_DOUBLE_HIGH (x) == -1
2701 && CONST_DOUBLE_LOW (x) == -1)
2702 fprintf (file, "q");
2704 else if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0xffffffffffffffff)
2705 fprintf (file, "q");
2706 else if (GET_CODE (x) == CONST_DOUBLE
2707 && CONST_DOUBLE_HIGH (x) == 0
2708 && CONST_DOUBLE_LOW (x) == -1)
2709 fprintf (file, "q");
2712 output_operand_lossage ("invalid %%U value");
2716 /* Write the constant value divided by 8. */
2717 if (GET_CODE (x) != CONST_INT
2718 && (unsigned HOST_WIDE_INT) INTVAL (x) >= 64
2719 && (INTVAL (x) & 7) != 8)
2720 output_operand_lossage ("invalid %%s value");
2722 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x) / 8);
2726 /* Same, except compute (64 - c) / 8 */
2728 if (GET_CODE (x) != CONST_INT
2729 && (unsigned HOST_WIDE_INT) INTVAL (x) >= 64
2730 && (INTVAL (x) & 7) != 8)
2731 output_operand_lossage ("invalid %%s value");
2733 fprintf (file, HOST_WIDE_INT_PRINT_DEC, (64 - INTVAL (x)) / 8);
2736 case 'C': case 'D': case 'c': case 'd':
2737 /* Write out comparison name. */
2739 enum rtx_code c = GET_CODE (x);
2741 if (GET_RTX_CLASS (c) != '<')
2742 output_operand_lossage ("invalid %%C value");
2745 c = reverse_condition (c);
2746 else if (code == 'c')
2747 c = swap_condition (c);
2748 else if (code == 'd')
2749 c = swap_condition (reverse_condition (c));
2752 fprintf (file, "ule");
2754 fprintf (file, "ult");
2756 fprintf (file, "%s", GET_RTX_NAME (c));
2761 /* Write the divide or modulus operator. */
2762 switch (GET_CODE (x))
2765 fprintf (file, "div%s", GET_MODE (x) == SImode ? "l" : "q");
2768 fprintf (file, "div%su", GET_MODE (x) == SImode ? "l" : "q");
2771 fprintf (file, "rem%s", GET_MODE (x) == SImode ? "l" : "q");
2774 fprintf (file, "rem%su", GET_MODE (x) == SImode ? "l" : "q");
2777 output_operand_lossage ("invalid %%E value");
2783 /* Write "_u" for unaligned access. */
2784 if (GET_CODE (x) == MEM && GET_CODE (XEXP (x, 0)) == AND)
2785 fprintf (file, "_u");
2789 if (GET_CODE (x) == REG)
2790 fprintf (file, "%s", reg_names[REGNO (x)]);
2791 else if (GET_CODE (x) == MEM)
2792 output_address (XEXP (x, 0));
2794 output_addr_const (file, x);
2798 output_operand_lossage ("invalid %%xn code");
2802 /* Do what is necessary for `va_start'. The argument is ignored;
2803 We look at the current function to determine if stdarg or varargs
2804 is used and fill in an initial va_list. A pointer to this constructor
2808 alpha_builtin_saveregs (arglist)
2811 rtx block, addr, dest, argsize;
2812 tree fntype = TREE_TYPE (current_function_decl);
2813 int stdarg = (TYPE_ARG_TYPES (fntype) != 0
2814 && (TREE_VALUE (tree_last (TYPE_ARG_TYPES (fntype)))
2815 != void_type_node));
2817 /* Compute the current position into the args, taking into account
2818 both registers and memory. Both of these are already included in
2821 argsize = GEN_INT (NUM_ARGS * UNITS_PER_WORD);
2823 /* For Unix, SETUP_INCOMING_VARARGS moves the starting address base up by 48,
2824 storing fp arg registers in the first 48 bytes, and the integer arg
2825 registers in the next 48 bytes. This is only done, however, if any
2826 integer registers need to be stored.
2828 If no integer registers need be stored, then we must subtract 48 in
2829 order to account for the integer arg registers which are counted in
2830 argsize above, but which are not actually stored on the stack. */
2832 if (TARGET_OPEN_VMS)
2833 addr = plus_constant (virtual_incoming_args_rtx,
2834 NUM_ARGS <= 5 + stdarg
2835 ? UNITS_PER_WORD : - 6 * UNITS_PER_WORD);
2837 addr = (NUM_ARGS <= 5 + stdarg
2838 ? plus_constant (virtual_incoming_args_rtx,
2840 : plus_constant (virtual_incoming_args_rtx,
2841 - (6 * UNITS_PER_WORD)));
2843 /* For VMS, we include the argsize, while on Unix, it's handled as
2844 a separate field. */
2845 if (TARGET_OPEN_VMS)
2846 addr = plus_constant (addr, INTVAL (argsize));
2848 addr = force_operand (addr, NULL_RTX);
2850 #ifdef POINTERS_EXTEND_UNSIGNED
2851 addr = convert_memory_address (ptr_mode, addr);
2854 if (TARGET_OPEN_VMS)
2858 /* Allocate the va_list constructor */
2859 block = assign_stack_local (BLKmode, 2 * UNITS_PER_WORD, BITS_PER_WORD);
2860 RTX_UNCHANGING_P (block) = 1;
2861 RTX_UNCHANGING_P (XEXP (block, 0)) = 1;
2863 /* Store the address of the first integer register in the __base
2866 dest = change_address (block, ptr_mode, XEXP (block, 0));
2867 emit_move_insn (dest, addr);
2869 if (flag_check_memory_usage)
2870 emit_library_call (chkr_set_right_libfunc, 1, VOIDmode, 3,
2872 GEN_INT (GET_MODE_SIZE (ptr_mode)),
2873 TYPE_MODE (sizetype),
2874 GEN_INT (MEMORY_USE_RW),
2875 TYPE_MODE (integer_type_node));
2877 /* Store the argsize as the __va_offset member. */
2878 dest = change_address (block, TYPE_MODE (integer_type_node),
2879 plus_constant (XEXP (block, 0),
2880 POINTER_SIZE/BITS_PER_UNIT));
2881 emit_move_insn (dest, argsize);
2883 if (flag_check_memory_usage)
2884 emit_library_call (chkr_set_right_libfunc, 1, VOIDmode, 3,
2886 GEN_INT (GET_MODE_SIZE
2887 (TYPE_MODE (integer_type_node))),
2888 TYPE_MODE (sizetype),
2889 GEN_INT (MEMORY_USE_RW),
2890 TYPE_MODE (integer_type_node));
2892 /* Return the address of the va_list constructor, but don't put it in a
2893 register. Doing so would fail when not optimizing and produce worse
2894 code when optimizing. */
2895 return XEXP (block, 0);
2899 /* This page contains routines that are used to determine what the function
2900 prologue and epilogue code will do and write them out. */
2902 /* Compute the size of the save area in the stack. */
2906 /* These variables are used for communication between the following functions.
2907 They indicate various things about the current function being compiled
2908 that are used to tell what kind of prologue, epilogue and procedure
2909 descriptior to generate. */
2911 /* Nonzero if we need a stack procedure. */
2912 static int is_stack_procedure;
2914 /* Register number (either FP or SP) that is used to unwind the frame. */
2915 static int unwind_regno;
2917 /* Register number used to save FP. We need not have one for RA since
2918 we don't modify it for register procedures. This is only defined
2919 for register frame procedures. */
2920 static int save_fp_regno;
2922 /* Register number used to reference objects off our PV. */
2923 static int base_regno;
2925 /* Compute register masks for saved registers. */
2928 alpha_sa_mask (imaskP, fmaskP)
2929 unsigned long *imaskP;
2930 unsigned long *fmaskP;
2932 unsigned long imask = 0;
2933 unsigned long fmask = 0;
2936 if (is_stack_procedure)
2937 imask |= (1L << HARD_FRAME_POINTER_REGNUM);
2939 /* One for every register we have to save. */
2941 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
2942 if (! fixed_regs[i] && ! call_used_regs[i]
2943 && regs_ever_live[i] && i != REG_RA)
2948 fmask |= (1L << (i - 32));
2961 HOST_WIDE_INT stack_needed;
2964 /* One for every register we have to save. */
2966 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
2967 if (! fixed_regs[i] && ! call_used_regs[i]
2968 && regs_ever_live[i] && i != REG_RA)
2971 /* Start by assuming we can use a register procedure if we don't make any
2972 calls (REG_RA not used) or need to save any registers and a stack
2973 procedure if we do. */
2974 is_stack_procedure = sa_size != 0 || alpha_ra_ever_killed ();
2976 /* Decide whether to refer to objects off our PV via FP or PV.
2977 If we need FP for something else or if we receive a nonlocal
2978 goto (which expects PV to contain the value), we must use PV.
2979 Otherwise, start by assuming we can use FP. */
2980 base_regno = (frame_pointer_needed || current_function_has_nonlocal_label
2981 || is_stack_procedure
2982 || current_function_outgoing_args_size
2983 ? REG_PV : HARD_FRAME_POINTER_REGNUM);
2985 /* If we want to copy PV into FP, we need to find some register in which to
2990 if (base_regno == HARD_FRAME_POINTER_REGNUM)
2991 for (i = 0; i < 32; i++)
2992 if (! fixed_regs[i] && call_used_regs[i] && ! regs_ever_live[i])
2995 if (save_fp_regno == -1)
2996 base_regno = REG_PV, is_stack_procedure = 1;
2998 /* Stack unwinding should be done via FP unless we use it for PV. */
3000 = base_regno == REG_PV ? HARD_FRAME_POINTER_REGNUM : STACK_POINTER_REGNUM;
3002 /* If this is a stack procedure, allow space for saving FP and RA. */
3003 if (is_stack_procedure)
3010 alpha_pv_save_size ()
3013 return is_stack_procedure ? 8 : 0;
3020 return unwind_regno == HARD_FRAME_POINTER_REGNUM;
3023 #else /* ! OPEN_VMS */
3031 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
3032 if (! fixed_regs[i] && ! call_used_regs[i]
3033 && regs_ever_live[i] && i != REG_RA)
3036 /* If some registers were saved but not reg 26, reg 26 must also
3037 be saved, so leave space for it. */
3038 if (size != 0 || alpha_ra_ever_killed ())
3041 /* Our size must be even (multiple of 16 bytes). */
3048 #endif /* ! OPEN_VMS */
3050 /* Return 1 if this function can directly return via $26. */
3055 return (! TARGET_OPEN_VMS && reload_completed && alpha_sa_size () == 0
3056 && get_frame_size () == 0
3057 && current_function_outgoing_args_size == 0
3058 && current_function_pretend_args_size == 0);
3061 /* Write a version stamp. Don't write anything if we are running as a
3062 cross-compiler. Otherwise, use the versions in /usr/include/stamp.h. */
3064 #if !defined(CROSS_COMPILE) && !defined(_WIN32) && !defined(__linux__) && !defined(VMS)
3069 alpha_write_verstamp (file)
3073 fprintf (file, "\t.verstamp %d %d\n", MS_STAMP, LS_STAMP);
3077 /* Write code to add constant C to register number IN_REG (possibly 31)
3078 and put the result into OUT_REG. Use TEMP_REG as a scratch register;
3079 usually this will be OUT_REG, but should not be if OUT_REG is
3080 STACK_POINTER_REGNUM, since it must be updated in a single instruction.
3081 Write the code to FILE. */
3084 add_long_const (file, c, in_reg, out_reg, temp_reg)
3087 int in_reg, out_reg, temp_reg;
3089 HOST_WIDE_INT low = (c & 0xffff) - 2 * (c & 0x8000);
3090 HOST_WIDE_INT tmp1 = c - low;
3091 HOST_WIDE_INT high = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
3092 HOST_WIDE_INT extra = 0;
3094 /* We don't have code to write out constants larger than 32 bits. */
3095 #if HOST_BITS_PER_LONG_INT == 64
3096 if ((unsigned HOST_WIDE_INT) c >> 32 != 0)
3100 /* If HIGH will be interpreted as negative, we must adjust it to do two
3101 ldha insns. Note that we will never be building a negative constant
3108 high = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
3113 int result_reg = (extra == 0 && high == 0) ? out_reg : temp_reg;
3115 if (low >= 0 && low < 255)
3116 fprintf (file, "\taddq $%d,%d,$%d\n", in_reg, low, result_reg);
3118 fprintf (file, "\tlda $%d,%d($%d)\n", result_reg, low, in_reg);
3120 in_reg = result_reg;
3125 int result_reg = (high == 0) ? out_reg : temp_reg;
3127 fprintf (file, "\tldah $%d,%d($%d)\n", result_reg, extra, in_reg);
3128 in_reg = result_reg;
3132 fprintf (file, "\tldah $%d,%d($%d)\n", out_reg, high, in_reg);
3135 /* Write function prologue. */
3139 /* On vms we have two kinds of functions:
3141 - stack frame (PROC_STACK)
3142 these are 'normal' functions with local vars and which are
3143 calling other functions
3144 - register frame (PROC_REGISTER)
3145 keeps all data in registers, needs no stack
3147 We must pass this to the assembler so it can generate the
3148 proper pdsc (procedure descriptor)
3149 This is done with the '.pdesc' command.
3151 size is the stack size needed for local variables. */
3154 output_prolog (file, size)
3158 unsigned long imask = 0;
3159 unsigned long fmask = 0;
3160 /* Stack space needed for pushing registers clobbered by us. */
3161 HOST_WIDE_INT sa_size;
3162 /* Complete stack size needed. */
3163 HOST_WIDE_INT frame_size;
3164 /* Offset from base reg to register save area. */
3166 /* Offset during register save. */
3168 /* Label for the procedure entry. */
3169 char *entry_label = (char *) alloca (strlen (alpha_function_name) + 6);
3172 sa_size = alpha_sa_size ();
3174 = ALPHA_ROUND (sa_size
3175 + (is_stack_procedure ? 8 : 0)
3176 + size + current_function_pretend_args_size);
3178 /* Issue function start and label. */
3179 fprintf (file, "\t.ent ");
3180 assemble_name (file, alpha_function_name);
3181 fprintf (file, "\n");
3182 sprintf (entry_label, "%s..en", alpha_function_name);
3183 ASM_OUTPUT_LABEL (file, entry_label);
3184 inside_function = TRUE;
3186 fprintf (file, "\t.base $%d\n", base_regno);
3188 /* Calculate register masks for clobbered registers. */
3190 if (is_stack_procedure)
3191 alpha_sa_mask (&imask, &fmask);
3193 /* Adjust the stack by the frame size. If the frame size is > 4096
3194 bytes, we need to be sure we probe somewhere in the first and last
3195 4096 bytes (we can probably get away without the latter test) and
3196 every 8192 bytes in between. If the frame size is > 32768, we
3197 do this in a loop. Otherwise, we generate the explicit probe
3200 Note that we are only allowed to adjust sp once in the prologue. */
3202 if (frame_size < 32768)
3204 if (frame_size > 4096)
3208 fprintf (file, "\tstq $31,-%d($30)\n", probed);
3210 while (probed + 8192 < frame_size)
3211 fprintf (file, "\tstq $31,-%d($30)\n", probed += 8192);
3213 /* We only have to do this probe if we aren't saving registers. */
3214 if (sa_size == 0 && probed + 4096 < frame_size)
3215 fprintf (file, "\tstq $31,-%d($30)\n", frame_size);
3218 if (frame_size != 0)
3219 fprintf (file, "\tlda $30,-%d($30)\n", frame_size);
3223 /* Here we generate code to set R4 to SP + 4096 and set R23 to the
3224 number of 8192 byte blocks to probe. We then probe each block
3225 in the loop and then set SP to the proper location. If the
3226 amount remaining is > 4096, we have to do one more probe if we
3227 are not saving any registers. */
3229 HOST_WIDE_INT blocks = (frame_size + 4096) / 8192;
3230 HOST_WIDE_INT leftover = frame_size + 4096 - blocks * 8192;
3232 add_long_const (file, blocks, 31, 23, 23);
3234 fprintf (file, "\tlda $22,4096($30)\n");
3237 assemble_name (file, alpha_function_name);
3238 fprintf (file, "..sc:\n");
3240 fprintf (file, "\tstq $31,-8192($22)\n");
3241 fprintf (file, "\tsubq $23,1,$23\n");
3242 fprintf (file, "\tlda $22,-8192($22)\n");
3244 fprintf (file, "\tbne $23,$");
3245 assemble_name (file, alpha_function_name);
3246 fprintf (file, "..sc\n");
3248 if (leftover > 4096 && sa_size == 0)
3249 fprintf (file, "\tstq $31,-%d($22)\n", leftover);
3251 fprintf (file, "\tlda $30,-%d($22)\n", leftover);
3254 if (is_stack_procedure)
3256 int reg_offset = rsa_offset;
3258 /* Store R26 (RA) first. */
3259 fprintf (file, "\tstq $26,%d($30)\n", reg_offset);
3262 /* Store integer regs. according to mask. */
3263 for (i = 0; i < 32; i++)
3264 if (imask & (1L<<i))
3266 fprintf (file, "\tstq $%d,%d($30)\n", i, reg_offset);
3270 /* Print the register mask and do floating-point saves. */
3273 fprintf (file, "\t.mask 0x%x,0\n", imask);
3275 for (i = 0; i < 32; i++)
3277 if (fmask & (1L << i))
3279 fprintf (file, "\tstt $f%d,%d($30)\n", i, reg_offset);
3284 /* Print the floating-point mask, if we've saved any fp register. */
3286 fprintf (file, "\t.fmask 0x%x,0\n", fmask);
3288 fprintf (file, "\tstq $27,0($30)\n");
3292 fprintf (file, "\t.fp_save $%d\n", save_fp_regno);
3293 fprintf (file, "\tbis $%d,$%d,$%d\n", HARD_FRAME_POINTER_REGNUM,
3294 HARD_FRAME_POINTER_REGNUM, save_fp_regno);
3297 if (base_regno != REG_PV)
3298 fprintf (file, "\tbis $%d,$%d,$%d\n", REG_PV, REG_PV, base_regno);
3300 if (unwind_regno == HARD_FRAME_POINTER_REGNUM)
3301 fprintf (file, "\tbis $%d,$%d,$%d\n", STACK_POINTER_REGNUM,
3302 STACK_POINTER_REGNUM, HARD_FRAME_POINTER_REGNUM);
3304 /* Describe our frame. */
3305 fprintf (file, "\t.frame $%d,", unwind_regno);
3307 /* If the frame size is larger than an integer, print it as zero to
3308 avoid an assembler error. We won't be properly describing such a
3309 frame, but that's the best we can do. */
3310 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
3311 #if HOST_BITS_PER_WIDE_INT == 64
3312 frame_size >= (1l << 31) ? 0:
3316 fprintf (file, ",$26,%d\n", rsa_offset);
3318 /* If we have to allocate space for outgoing args, do it now. */
3319 if (current_function_outgoing_args_size != 0)
3320 fprintf (file, "\tlda $%d,%d($%d)\n", STACK_POINTER_REGNUM,
3321 - ALPHA_ROUND (current_function_outgoing_args_size),
3322 HARD_FRAME_POINTER_REGNUM);
3324 fprintf (file, "\t.prologue\n");
3326 readonly_section ();
3327 fprintf (file, "\t.align 3\n");
3328 assemble_name (file, alpha_function_name); fputs ("..na:\n", file);
3329 fputs ("\t.ascii \"", file);
3330 assemble_name (file, alpha_function_name);
3331 fputs ("\\0\"\n", file);
3334 fprintf (file, "\t.align 3\n");
3335 fputs ("\t.name ", file);
3336 assemble_name (file, alpha_function_name);
3337 fputs ("..na\n", file);
3338 ASM_OUTPUT_LABEL (file, alpha_function_name);
3339 fprintf (file, "\t.pdesc ");
3340 assemble_name (file, alpha_function_name);
3341 fprintf (file, "..en,%s\n", is_stack_procedure ? "stack" : "reg");
3342 alpha_need_linkage (alpha_function_name, 1);
3348 /* Write function epilogue. */
3351 output_epilog (file, size)
3355 unsigned long imask = 0;
3356 unsigned long fmask = 0;
3357 /* Stack space needed for pushing registers clobbered by us. */
3358 HOST_WIDE_INT sa_size = alpha_sa_size ();
3359 /* Complete stack size needed. */
3360 HOST_WIDE_INT frame_size
3361 = ALPHA_ROUND (sa_size
3362 + (is_stack_procedure ? 8 : 0)
3363 + size + current_function_pretend_args_size);
3365 rtx insn = get_last_insn ();
3367 /* If the last insn was a BARRIER, we don't have to write anything except
3368 the .end pseudo-op. */
3370 if (GET_CODE (insn) == NOTE)
3371 insn = prev_nonnote_insn (insn);
3373 if (insn == 0 || GET_CODE (insn) != BARRIER)
3375 /* Restore clobbered registers, load FP last. */
3377 if (is_stack_procedure)
3383 if (unwind_regno == HARD_FRAME_POINTER_REGNUM)
3384 fprintf (file, "\tbis $%d,$%d,$%d\n", HARD_FRAME_POINTER_REGNUM,
3385 HARD_FRAME_POINTER_REGNUM, STACK_POINTER_REGNUM);
3387 alpha_sa_mask (&imask, &fmask);
3389 /* Start reloading registers after RA. */
3390 reg_offset = rsa_offset + 8;
3392 for (i = 0; i < 32; i++)
3393 if (imask & (1L<<i))
3395 if (i == HARD_FRAME_POINTER_REGNUM)
3396 fp_offset = reg_offset;
3398 fprintf (file, "\tldq $%d,%d($30)\n",
3403 for (i = 0; i < 32; i++)
3404 if (fmask & (1L << i))
3406 fprintf (file, "\tldt $f%d,%d($30)\n", i, reg_offset);
3410 /* Restore R26 (RA). */
3411 fprintf (file, "\tldq $26,%d($30)\n", rsa_offset);
3413 /* Restore R29 (FP). */
3414 fprintf (file, "\tldq $29,%d($30)\n", fp_offset);
3417 fprintf (file, "\tbis $%d,$%d,$%d\n", save_fp_regno, save_fp_regno,
3418 HARD_FRAME_POINTER_REGNUM);
3420 if (frame_size != 0)
3422 if (frame_size < 32768)
3423 fprintf (file, "\tlda $30,%d($30)\n", frame_size);
3426 long high = frame_size >> 16;
3427 long low = frame_size & 0xffff;
3431 low = -32768 + (low & 0x7fff);
3433 fprintf (file, "\tldah $2,%ld($31)\n", high);
3434 fprintf (file, "\tlda $2,%ld($2)\n", low);
3435 fprintf (file, "\taddq $30,$2,$30\n");
3439 /* Finally return to the caller. */
3440 fprintf (file, "\tret $31,($26),1\n");
3443 /* End the function. */
3444 fprintf (file, "\t.end ");
3445 assemble_name (file, alpha_function_name);
3446 fprintf (file, "\n");
3447 inside_function = FALSE;
3449 /* Show that we know this function if it is called again. */
3450 SYMBOL_REF_FLAG (XEXP (DECL_RTL (current_function_decl), 0)) = 1;
3454 vms_valid_decl_attribute_p (decl, attributes, identifier, args)
3460 if (is_attribute_p ("overlaid", identifier))
3461 return (args == NULL_TREE);
3465 #else /* !OPEN_VMS */
3468 alpha_does_function_need_gp ()
3472 /* We never need a GP for Windows/NT. */
3473 if (TARGET_WINDOWS_NT)
3476 #ifdef TARGET_PROFILING_NEEDS_GP
3481 /* If we need a GP (we have a LDSYM insn or a CALL_INSN), load it first.
3482 Even if we are a static function, we still need to do this in case
3483 our address is taken and passed to something like qsort. */
3485 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
3486 if (GET_RTX_CLASS (GET_CODE (insn)) == 'i'
3487 && GET_CODE (PATTERN (insn)) != USE
3488 && GET_CODE (PATTERN (insn)) != CLOBBER)
3490 enum attr_type type = get_attr_type (insn);
3491 if (type == TYPE_LDSYM || type == TYPE_JSR)
3499 output_prolog (file, size)
3503 HOST_WIDE_INT out_args_size
3504 = ALPHA_ROUND (current_function_outgoing_args_size);
3505 HOST_WIDE_INT sa_size = alpha_sa_size ();
3506 HOST_WIDE_INT frame_size
3507 = (out_args_size + sa_size
3508 + ALPHA_ROUND (size + current_function_pretend_args_size));
3509 HOST_WIDE_INT reg_offset = out_args_size;
3510 HOST_WIDE_INT start_reg_offset = reg_offset;
3511 HOST_WIDE_INT actual_start_reg_offset = start_reg_offset;
3512 int int_reg_save_area_size = 0;
3513 unsigned reg_mask = 0;
3516 /* Ecoff can handle multiple .file directives, so put out file and lineno.
3517 We have to do that before the .ent directive as we cannot switch
3518 files within procedures with native ecoff because line numbers are
3519 linked to procedure descriptors.
3520 Outputting the lineno helps debugging of one line functions as they
3521 would otherwise get no line number at all. Please note that we would
3522 like to put out last_linenum from final.c, but it is not accessible. */
3524 if (write_symbols == SDB_DEBUG)
3526 ASM_OUTPUT_SOURCE_FILENAME (file,
3527 DECL_SOURCE_FILE (current_function_decl));
3528 if (debug_info_level != DINFO_LEVEL_TERSE)
3529 ASM_OUTPUT_SOURCE_LINE (file,
3530 DECL_SOURCE_LINE (current_function_decl));
3533 /* The assembly language programmer's guide states that the second argument
3534 to the .ent directive, the lex_level, is ignored by the assembler,
3535 so we might as well omit it. */
3537 if (!flag_inhibit_size_directive)
3539 fprintf (file, "\t.ent ");
3540 assemble_name (file, alpha_function_name);
3541 fprintf (file, "\n");
3543 ASM_OUTPUT_LABEL (file, alpha_function_name);
3544 inside_function = TRUE;
3546 if (TARGET_IEEE_CONFORMANT && !flag_inhibit_size_directive)
3547 /* Set flags in procedure descriptor to request IEEE-conformant
3548 math-library routines. The value we set it to is PDSC_EXC_IEEE
3549 (/usr/include/pdsc.h). */
3550 fprintf (file, "\t.eflag 48\n");
3552 /* Set up offsets to alpha virtual arg/local debugging pointer. */
3554 alpha_auto_offset = -frame_size + current_function_pretend_args_size;
3555 alpha_arg_offset = -frame_size + 48;
3557 alpha_function_needs_gp = alpha_does_function_need_gp ();
3559 if (TARGET_WINDOWS_NT == 0)
3561 if (alpha_function_needs_gp)
3562 fprintf (file, "\tldgp $29,0($27)\n");
3564 /* Put a label after the GP load so we can enter the function at it. */
3566 assemble_name (file, alpha_function_name);
3567 fprintf (file, "..ng:\n");
3570 /* Adjust the stack by the frame size. If the frame size is > 4096
3571 bytes, we need to be sure we probe somewhere in the first and last
3572 4096 bytes (we can probably get away without the latter test) and
3573 every 8192 bytes in between. If the frame size is > 32768, we
3574 do this in a loop. Otherwise, we generate the explicit probe
3577 Note that we are only allowed to adjust sp once in the prologue. */
3579 if (frame_size < 32768)
3581 if (frame_size > 4096)
3585 fprintf (file, "\tstq $31,-%d($30)\n", probed);
3587 while (probed + 8192 < frame_size)
3588 fprintf (file, "\tstq $31,-%d($30)\n", probed += 8192);
3590 /* We only have to do this probe if we aren't saving registers. */
3591 if (sa_size == 0 && probed + 4096 < frame_size)
3592 fprintf (file, "\tstq $31,-%d($30)\n", frame_size);
3595 if (frame_size != 0)
3596 fprintf (file, "\tlda $30,-%d($30)\n", frame_size);
3600 /* Here we generate code to set R4 to SP + 4096 and set R5 to the
3601 number of 8192 byte blocks to probe. We then probe each block
3602 in the loop and then set SP to the proper location. If the
3603 amount remaining is > 4096, we have to do one more probe if we
3604 are not saving any registers. */
3606 HOST_WIDE_INT blocks = (frame_size + 4096) / 8192;
3607 HOST_WIDE_INT leftover = frame_size + 4096 - blocks * 8192;
3609 add_long_const (file, blocks, 31, 5, 5);
3611 fprintf (file, "\tlda $4,4096($30)\n");
3614 assemble_name (file, alpha_function_name);
3615 fprintf (file, "..sc:\n");
3617 fprintf (file, "\tstq $31,-8192($4)\n");
3618 fprintf (file, "\tsubq $5,1,$5\n");
3619 fprintf (file, "\tlda $4,-8192($4)\n");
3621 fprintf (file, "\tbne $5,$");
3622 assemble_name (file, alpha_function_name);
3623 fprintf (file, "..sc\n");
3625 if (leftover > 4096 && sa_size == 0)
3626 fprintf (file, "\tstq $31,-%d($4)\n", leftover);
3628 fprintf (file, "\tlda $30,-%d($4)\n", leftover);
3631 /* Describe our frame. */
3632 if (!flag_inhibit_size_directive)
3634 fprintf (file, "\t.frame $%d,",
3635 (frame_pointer_needed
3636 ? HARD_FRAME_POINTER_REGNUM : STACK_POINTER_REGNUM));
3638 /* If the frame size is larger than an integer, print it as zero to
3639 avoid an assembler error. We won't be properly describing such a
3640 frame, but that's the best we can do. */
3641 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
3642 #if HOST_BITS_PER_WIDE_INT == 64
3643 frame_size >= (1l << 31) ? 0 :
3647 fprintf (file, ",$26,%d\n", current_function_pretend_args_size);
3650 /* Cope with very large offsets to the register save area. */
3652 if (reg_offset + sa_size > 0x8000)
3654 int low = ((reg_offset & 0xffff) ^ 0x8000) - 0x8000;
3655 if (low + sa_size <= 0x8000)
3657 add_long_const (file, reg_offset - low, 30, 24, 24);
3662 add_long_const (file, reg_offset, 30, 24, 24);
3668 /* Save register RA if any other register needs to be saved. */
3671 reg_mask |= 1 << REG_RA;
3672 fprintf (file, "\tstq $26,%d($%d)\n", reg_offset, sa_reg);
3674 int_reg_save_area_size += 8;
3677 /* Now save any other used integer registers required to be saved. */
3678 for (i = 0; i < 32; i++)
3679 if (! fixed_regs[i] && ! call_used_regs[i]
3680 && regs_ever_live[i] && i != REG_RA)
3683 fprintf (file, "\tstq $%d,%d($%d)\n", i, reg_offset, sa_reg);
3685 int_reg_save_area_size += 8;
3688 /* Print the register mask and do floating-point saves. */
3689 if (reg_mask && !flag_inhibit_size_directive)
3691 fprintf (file, "\t.mask 0x%x,", reg_mask);
3692 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
3693 #if HOST_BITS_PER_WIDE_INT == 64
3694 frame_size >= (1l << 31) ? 0 :
3696 actual_start_reg_offset - frame_size);
3697 fprintf (file, "\n");
3700 start_reg_offset = reg_offset;
3703 for (i = 0; i < 32; i++)
3704 if (! fixed_regs[i + 32] && ! call_used_regs[i + 32]
3705 && regs_ever_live[i + 32])
3708 fprintf (file, "\tstt $f%d,%d($%d)\n", i, reg_offset, sa_reg);
3712 /* Print the floating-point mask, if we've saved any fp register. */
3713 if (reg_mask && !flag_inhibit_size_directive)
3714 fprintf (file, "\t.fmask 0x%x,%d\n", reg_mask,
3715 actual_start_reg_offset - frame_size + int_reg_save_area_size);
3717 /* If we need a frame pointer, set it from the stack pointer. Note that
3718 this must always be the last instruction in the prologue. */
3719 if (frame_pointer_needed)
3720 fprintf (file, "\tbis $30,$30,$15\n");
3722 /* End the prologue and say if we used gp. */
3723 if (!flag_inhibit_size_directive)
3724 fprintf (file, "\t.prologue %d\n", alpha_function_needs_gp);
3727 /* Write function epilogue. */
3730 output_epilog (file, size)
3734 rtx insn = get_last_insn ();
3735 HOST_WIDE_INT out_args_size
3736 = ALPHA_ROUND (current_function_outgoing_args_size);
3737 HOST_WIDE_INT sa_size = alpha_sa_size ();
3738 HOST_WIDE_INT frame_size
3739 = (out_args_size + sa_size
3740 + ALPHA_ROUND (size + current_function_pretend_args_size));
3741 HOST_WIDE_INT reg_offset = out_args_size;
3743 = frame_pointer_needed && regs_ever_live[HARD_FRAME_POINTER_REGNUM];
3746 /* If the last insn was a BARRIER, we don't have to write anything except
3747 the .end pseudo-op. */
3748 if (GET_CODE (insn) == NOTE)
3749 insn = prev_nonnote_insn (insn);
3750 if (insn == 0 || GET_CODE (insn) != BARRIER)
3755 /* If we have a frame pointer, restore SP from it. */
3756 if (frame_pointer_needed)
3757 fprintf (file, "\tbis $15,$15,$30\n");
3759 /* Cope with large offsets to the register save area. */
3761 if (reg_offset + sa_size > 0x8000)
3763 int low = ((reg_offset & 0xffff) ^ 0x8000) - 0x8000;
3764 if (low + sa_size <= 0x8000)
3766 add_long_const (file, reg_offset - low, 30, 24, 24);
3771 add_long_const (file, reg_offset, 30, 24, 24);
3777 /* Restore all the registers, starting with the return address
3781 fprintf (file, "\tldq $26,%d($%d)\n", reg_offset, sa_reg);
3785 /* Now restore any other used integer registers that we saved,
3786 except for FP if it is being used as FP, since it must be
3789 for (i = 0; i < 32; i++)
3790 if (! fixed_regs[i] && ! call_used_regs[i] && regs_ever_live[i]
3793 if (i == HARD_FRAME_POINTER_REGNUM && frame_pointer_needed)
3794 fp_offset = reg_offset;
3796 fprintf (file, "\tldq $%d,%d($%d)\n", i, reg_offset, sa_reg);
3800 for (i = 0; i < 32; i++)
3801 if (! fixed_regs[i + 32] && ! call_used_regs[i + 32]
3802 && regs_ever_live[i + 32])
3804 fprintf (file, "\tldt $f%d,%d($%d)\n", i, reg_offset, sa_reg);
3808 /* If the stack size is large and we have a frame pointer, compute the
3809 size of the stack into a register because the old FP restore, stack
3810 pointer adjust, and return are required to be consecutive
3812 if (frame_size > 32767 && restore_fp)
3813 add_long_const (file, frame_size, 31, 1, 1);
3815 /* If we needed a frame pointer and we have to restore it, do it
3816 now. This must be done in one instruction immediately
3817 before the SP update. */
3818 if (restore_fp && fp_offset)
3819 fprintf (file, "\tldq $15,%d($%d)\n", fp_offset, sa_reg);
3821 /* Now update the stack pointer, if needed. Only one instruction must
3822 modify the stack pointer. It must be the last instruction in the
3823 sequence and must be an ADDQ or LDA instruction. If the frame
3824 pointer was loaded above, we may only put one instruction here. */
3826 if (frame_size > 32768 && restore_fp)
3827 fprintf (file, "\taddq $1,$30,$30\n");
3829 add_long_const (file, frame_size, 30, 30, 1);
3831 /* Finally return to the caller. */
3832 fprintf (file, "\tret $31,($26),1\n");
3835 /* End the function. */
3836 if (!flag_inhibit_size_directive)
3838 fprintf (file, "\t.end ");
3839 assemble_name (file, alpha_function_name);
3840 fprintf (file, "\n");
3842 inside_function = FALSE;
3844 /* Show that we know this function if it is called again.
3846 Don't do this for global functions in object files destined for a
3847 shared library because the function may be overridden by the application
3849 ??? Is this just ELF? */
3851 if (!flag_pic || !TREE_PUBLIC (current_function_decl))
3852 SYMBOL_REF_FLAG (XEXP (DECL_RTL (current_function_decl), 0)) = 1;
3854 #endif /* !OPEN_VMS */
3856 /* Debugging support. */
3860 /* Count the number of sdb related labels are generated (to find block
3861 start and end boundaries). */
3863 int sdb_label_count = 0;
3865 /* Next label # for each statement. */
3867 static int sym_lineno = 0;
3869 /* Count the number of .file directives, so that .loc is up to date. */
3871 static int num_source_filenames = 0;
3873 /* Name of the file containing the current function. */
3875 static char *current_function_file = "";
3877 /* Offsets to alpha virtual arg/local debugging pointers. */
3879 long alpha_arg_offset;
3880 long alpha_auto_offset;
3882 /* Emit a new filename to a stream. */
3885 alpha_output_filename (stream, name)
3889 static int first_time = TRUE;
3890 char ltext_label_name[100];
3895 ++num_source_filenames;
3896 current_function_file = name;
3897 fprintf (stream, "\t.file\t%d ", num_source_filenames);
3898 output_quoted_string (stream, name);
3899 fprintf (stream, "\n");
3900 if (!TARGET_GAS && write_symbols == DBX_DEBUG)
3901 fprintf (stream, "\t#@stabs\n");
3904 else if (write_symbols == DBX_DEBUG)
3906 ASM_GENERATE_INTERNAL_LABEL (ltext_label_name, "Ltext", 0);
3907 fprintf (stream, "%s ", ASM_STABS_OP);
3908 output_quoted_string (stream, name);
3909 fprintf (stream, ",%d,0,0,%s\n", N_SOL, <ext_label_name[1]);
3912 else if (name != current_function_file
3913 && strcmp (name, current_function_file) != 0)
3915 if (inside_function && ! TARGET_GAS)
3916 fprintf (stream, "\t#.file\t%d ", num_source_filenames);
3919 ++num_source_filenames;
3920 current_function_file = name;
3921 fprintf (stream, "\t.file\t%d ", num_source_filenames);
3924 output_quoted_string (stream, name);
3925 fprintf (stream, "\n");
3929 /* Emit a linenumber to a stream. */
3932 alpha_output_lineno (stream, line)
3936 if (write_symbols == DBX_DEBUG)
3938 /* mips-tfile doesn't understand .stabd directives. */
3940 fprintf (stream, "$LM%d:\n\t%s %d,0,%d,$LM%d\n",
3941 sym_lineno, ASM_STABN_OP, N_SLINE, line, sym_lineno);
3944 fprintf (stream, "\n\t.loc\t%d %d\n", num_source_filenames, line);
3947 /* Structure to show the current status of registers and memory. */
3949 struct shadow_summary
3952 unsigned long i : 31; /* Mask of int regs */
3953 unsigned long fp : 31; /* Mask of fp regs */
3954 unsigned long mem : 1; /* mem == imem | fpmem */
3958 /* Summary the effects of expression X on the machine. Update SUM, a pointer
3959 to the summary structure. SET is nonzero if the insn is setting the
3960 object, otherwise zero. */
3963 summarize_insn (x, sum, set)
3965 struct shadow_summary *sum;
3974 switch (GET_CODE (x))
3976 /* ??? Note that this case would be incorrect if the Alpha had a
3977 ZERO_EXTRACT in SET_DEST. */
3979 summarize_insn (SET_SRC (x), sum, 0);
3980 summarize_insn (SET_DEST (x), sum, 1);
3984 summarize_insn (XEXP (x, 0), sum, 1);
3988 summarize_insn (XEXP (x, 0), sum, 0);
3992 for (i = ASM_OPERANDS_INPUT_LENGTH (x) - 1; i >= 0; i--)
3993 summarize_insn (ASM_OPERANDS_INPUT (x, i), sum, 0);
3997 for (i = XVECLEN (x, 0) - 1; i >= 0; i--)
3998 summarize_insn (XVECEXP (x, 0, i), sum, 0);
4007 int regno = REGNO (x);
4008 unsigned long mask = 1UL << (regno % 32);
4010 if (regno == 31 || regno == 63)
4016 sum->defd.i |= mask;
4018 sum->defd.fp |= mask;
4023 sum->used.i |= mask;
4025 sum->used.fp |= mask;
4036 /* Find the regs used in memory address computation: */
4037 summarize_insn (XEXP (x, 0), sum, 0);
4040 case CONST_INT: case CONST_DOUBLE:
4041 case SYMBOL_REF: case LABEL_REF: case CONST:
4044 /* Handle common unary and binary ops for efficiency. */
4045 case COMPARE: case PLUS: case MINUS: case MULT: case DIV:
4046 case MOD: case UDIV: case UMOD: case AND: case IOR:
4047 case XOR: case ASHIFT: case ROTATE: case ASHIFTRT: case LSHIFTRT:
4048 case ROTATERT: case SMIN: case SMAX: case UMIN: case UMAX:
4049 case NE: case EQ: case GE: case GT: case LE:
4050 case LT: case GEU: case GTU: case LEU: case LTU:
4051 summarize_insn (XEXP (x, 0), sum, 0);
4052 summarize_insn (XEXP (x, 1), sum, 0);
4055 case NEG: case NOT: case SIGN_EXTEND: case ZERO_EXTEND:
4056 case TRUNCATE: case FLOAT_EXTEND: case FLOAT_TRUNCATE: case FLOAT:
4057 case FIX: case UNSIGNED_FLOAT: case UNSIGNED_FIX: case ABS:
4058 case SQRT: case FFS:
4059 summarize_insn (XEXP (x, 0), sum, 0);
4063 format_ptr = GET_RTX_FORMAT (GET_CODE (x));
4064 for (i = GET_RTX_LENGTH (GET_CODE (x)) - 1; i >= 0; i--)
4065 switch (format_ptr[i])
4068 summarize_insn (XEXP (x, i), sum, 0);
4072 for (j = XVECLEN (x, i) - 1; j >= 0; j--)
4073 summarize_insn (XVECEXP (x, i, j), sum, 0);
4082 /* Ensure a sufficient number of `trapb' insns are in the code when the user
4083 requests code with a trap precision of functions or instructions.
4085 In naive mode, when the user requests a trap-precision of "instruction", a
4086 trapb is needed after every instruction that may generate a trap (and after
4087 jsr/bsr instructions, because called functions may import a trap from the
4088 caller). This ensures that the code is resumption safe but it is also slow.
4090 When optimizations are turned on, we delay issuing a trapb as long as
4091 possible. In this context, a trap shadow is the sequence of instructions
4092 that starts with a (potentially) trap generating instruction and extends to
4093 the next trapb or call_pal instruction (but GCC never generates call_pal by
4094 itself). We can delay (and therefore sometimes omit) a trapb subject to the
4095 following conditions:
4097 (a) On entry to the trap shadow, if any Alpha register or memory location
4098 contains a value that is used as an operand value by some instruction in
4099 the trap shadow (live on entry), then no instruction in the trap shadow
4100 may modify the register or memory location.
4102 (b) Within the trap shadow, the computation of the base register for a
4103 memory load or store instruction may not involve using the result
4104 of an instruction that might generate an UNPREDICTABLE result.
4106 (c) Within the trap shadow, no register may be used more than once as a
4107 destination register. (This is to make life easier for the trap-handler.)
4109 (d) The trap shadow may not include any branch instructions. */
4112 alpha_handle_trap_shadows (insns)
4115 struct shadow_summary shadow;
4116 int trap_pending, exception_nesting;
4119 if (alpha_tp == ALPHA_TP_PROG && !flag_exceptions)
4123 exception_nesting = 0;
4126 shadow.used.mem = 0;
4127 shadow.defd = shadow.used;
4129 for (i = insns; i ; i = NEXT_INSN (i))
4131 if (GET_CODE (i) == NOTE)
4133 switch (NOTE_LINE_NUMBER (i))
4135 case NOTE_INSN_EH_REGION_BEG:
4136 exception_nesting++;
4141 case NOTE_INSN_EH_REGION_END:
4142 exception_nesting--;
4147 case NOTE_INSN_EPILOGUE_BEG:
4148 if (trap_pending && alpha_tp >= ALPHA_TP_FUNC)
4153 else if (trap_pending)
4155 if (alpha_tp == ALPHA_TP_FUNC)
4157 if (GET_CODE (i) == JUMP_INSN
4158 && GET_CODE (PATTERN (i)) == RETURN)
4161 else if (alpha_tp == ALPHA_TP_INSN)
4165 struct shadow_summary sum;
4170 sum.defd = sum.used;
4172 switch (GET_CODE (i))
4175 /* Annoyingly, get_attr_trap will abort on these. */
4176 if (GET_CODE (PATTERN (i)) == USE
4177 || GET_CODE (PATTERN (i)) == CLOBBER)
4180 summarize_insn (PATTERN (i), &sum, 0);
4182 if ((sum.defd.i & shadow.defd.i)
4183 || (sum.defd.fp & shadow.defd.fp))
4185 /* (c) would be violated */
4189 /* Combine shadow with summary of current insn: */
4190 shadow.used.i |= sum.used.i;
4191 shadow.used.fp |= sum.used.fp;
4192 shadow.used.mem |= sum.used.mem;
4193 shadow.defd.i |= sum.defd.i;
4194 shadow.defd.fp |= sum.defd.fp;
4195 shadow.defd.mem |= sum.defd.mem;
4197 if ((sum.defd.i & shadow.used.i)
4198 || (sum.defd.fp & shadow.used.fp)
4199 || (sum.defd.mem & shadow.used.mem))
4201 /* (a) would be violated (also takes care of (b)) */
4202 if (get_attr_trap (i) == TRAP_YES
4203 && ((sum.defd.i & sum.used.i)
4204 || (sum.defd.fp & sum.used.fp)))
4223 emit_insn_before (gen_trapb (), i);
4227 shadow.used.mem = 0;
4228 shadow.defd = shadow.used;
4233 if ((exception_nesting > 0 || alpha_tp >= ALPHA_TP_FUNC)
4234 && GET_CODE (i) == INSN
4235 && GET_CODE (PATTERN (i)) != USE
4236 && GET_CODE (PATTERN (i)) != CLOBBER
4237 && get_attr_trap (i) == TRAP_YES)
4239 if (optimize && !trap_pending)
4240 summarize_insn (PATTERN (i), &shadow, 0);
4246 /* Machine dependant reorg pass. */
4252 alpha_handle_trap_shadows (insns);
4256 /* Check a floating-point value for validity for a particular machine mode. */
4258 static char *float_strings[] =
4260 /* These are for FLOAT_VAX. */
4261 "1.70141173319264430e+38", /* 2^127 (2^24 - 1) / 2^24 */
4262 "-1.70141173319264430e+38",
4263 "2.93873587705571877e-39", /* 2^-128 */
4264 "-2.93873587705571877e-39",
4265 /* These are for the default broken IEEE mode, which traps
4266 on infinity or denormal numbers. */
4267 "3.402823466385288598117e+38", /* 2^128 (1 - 2^-24) */
4268 "-3.402823466385288598117e+38",
4269 "1.1754943508222875079687e-38", /* 2^-126 */
4270 "-1.1754943508222875079687e-38",
4273 static REAL_VALUE_TYPE float_values[8];
4274 static int inited_float_values = 0;
4277 check_float_value (mode, d, overflow)
4278 enum machine_mode mode;
4283 if (TARGET_IEEE || TARGET_IEEE_CONFORMANT || TARGET_IEEE_WITH_INEXACT)
4286 if (inited_float_values == 0)
4289 for (i = 0; i < 8; i++)
4290 float_values[i] = REAL_VALUE_ATOF (float_strings[i], DFmode);
4292 inited_float_values = 1;
4298 REAL_VALUE_TYPE *fvptr;
4300 if (TARGET_FLOAT_VAX)
4301 fvptr = &float_values[0];
4303 fvptr = &float_values[4];
4305 bcopy ((char *) d, (char *) &r, sizeof (REAL_VALUE_TYPE));
4306 if (REAL_VALUES_LESS (fvptr[0], r))
4308 bcopy ((char *) &fvptr[0], (char *) d,
4309 sizeof (REAL_VALUE_TYPE));
4312 else if (REAL_VALUES_LESS (r, fvptr[1]))
4314 bcopy ((char *) &fvptr[1], (char *) d,
4315 sizeof (REAL_VALUE_TYPE));
4318 else if (REAL_VALUES_LESS (dconst0, r)
4319 && REAL_VALUES_LESS (r, fvptr[2]))
4321 bcopy ((char *) &dconst0, (char *) d, sizeof (REAL_VALUE_TYPE));
4324 else if (REAL_VALUES_LESS (r, dconst0)
4325 && REAL_VALUES_LESS (fvptr[3], r))
4327 bcopy ((char *) &dconst0, (char *) d, sizeof (REAL_VALUE_TYPE));
4337 /* Return the VMS argument type corresponding to MODE. */
4340 alpha_arg_type (mode)
4341 enum machine_mode mode;
4346 return TARGET_FLOAT_VAX ? FF : FS;
4348 return TARGET_FLOAT_VAX ? FD : FT;
4354 /* Return an rtx for an integer representing the VMS Argument Information
4358 alpha_arg_info_reg_val (cum)
4359 CUMULATIVE_ARGS cum;
4361 unsigned HOST_WIDE_INT regval = cum.num_args;
4364 for (i = 0; i < 6; i++)
4365 regval |= ((int) cum.atypes[i]) << (i * 3 + 8);
4367 return GEN_INT (regval);
4370 /* Structure to collect function names for final output
4373 enum links_kind {KIND_UNUSED, KIND_LOCAL, KIND_EXTERN};
4376 struct alpha_links {
4377 struct alpha_links *next;
4379 enum links_kind kind;
4382 static struct alpha_links *alpha_links_base = 0;
4384 /* Make (or fake) .linkage entry for function call.
4386 IS_LOCAL is 0 if name is used in call, 1 if name is used in definition. */
4389 alpha_need_linkage (name, is_local)
4394 struct alpha_links *lptr, *nptr;
4399 /* Is this name already defined ? */
4401 for (lptr = alpha_links_base; lptr; lptr = lptr->next)
4402 if (strcmp (lptr->name, name) == 0)
4406 /* Defined here but external assumed. */
4407 if (lptr->kind == KIND_EXTERN)
4408 lptr->kind = KIND_LOCAL;
4412 /* Used here but unused assumed. */
4413 if (lptr->kind == KIND_UNUSED)
4414 lptr->kind = KIND_LOCAL;
4419 nptr = (struct alpha_links *) xmalloc (sizeof (struct alpha_links));
4420 nptr->next = alpha_links_base;
4421 nptr->name = xstrdup (name);
4423 /* Assume external if no definition. */
4424 nptr->kind = (is_local ? KIND_UNUSED : KIND_EXTERN);
4426 /* Ensure we have an IDENTIFIER so assemble_name can mark is used. */
4427 get_identifier (name);
4429 alpha_links_base = nptr;
4436 alpha_write_linkage (stream)
4439 struct alpha_links *lptr, *nptr;
4441 readonly_section ();
4443 fprintf (stream, "\t.align 3\n");
4445 for (lptr = alpha_links_base; lptr; lptr = nptr)
4449 if (lptr->kind == KIND_UNUSED
4450 || ! TREE_SYMBOL_REFERENCED (get_identifier (lptr->name)))
4453 fprintf (stream, "$%s..lk:\n", lptr->name);
4454 if (lptr->kind == KIND_LOCAL)
4456 /* Local and used, build linkage pair. */
4457 fprintf (stream, "\t.quad %s..en\n", lptr->name);
4458 fprintf (stream, "\t.quad %s\n", lptr->name);
4461 /* External and used, request linkage pair. */
4462 fprintf (stream, "\t.linkage %s\n", lptr->name);
4469 alpha_need_linkage (name, is_local)
4475 #endif /* OPEN_VMS */