import of gcc-2.8
[official-gcc.git] / gcc / config / alpha / alpha.c
blobf98cb192a857198c18aae634694874fdf264c9d3
1 /* Subroutines used for code generation on the DEC Alpha.
2 Copyright (C) 1992, 93, 94, 95, 96, 1997 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)
10 any later version.
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. */
23 #include "config.h"
24 #include <stdio.h>
25 #include "rtl.h"
26 #include "regs.h"
27 #include "hard-reg-set.h"
28 #include "real.h"
29 #include "insn-config.h"
30 #include "conditions.h"
31 #include "insn-flags.h"
32 #include "output.h"
33 #include "insn-attr.h"
34 #include "flags.h"
35 #include "recog.h"
36 #include "reload.h"
37 #include "expr.h"
38 #include "obstack.h"
39 #include "tree.h"
41 /* Specify which cpu to schedule for. */
42 enum processor_type alpha_cpu;
44 /* Specify how accurate floating-point traps need to be. */
46 enum alpha_trap_precision alpha_tp;
48 /* Specify the floating-point rounding mode. */
50 enum alpha_fp_rounding_mode alpha_fprm;
52 /* Specify which things cause traps. */
54 enum alpha_fp_trap_mode alpha_fptm;
56 /* Strings decoded into the above options. */
57 char *alpha_cpu_string; /* -mcpu=ev[4|5] */
58 char *alpha_tp_string; /* -mtrap-precision=[p|s|i] */
59 char *alpha_fprm_string; /* -mfp-rounding-mode=[n|m|c|d] */
60 char *alpha_fptm_string; /* -mfp-trap-mode=[n|u|su|sui] */
62 /* Save information from a "cmpxx" operation until the branch or scc is
63 emitted. */
65 rtx alpha_compare_op0, alpha_compare_op1;
66 int alpha_compare_fp_p;
68 /* Save the name of the current function as used by the assembler. This
69 is used by the epilogue. */
71 char *alpha_function_name;
73 /* Non-zero if inside of a function, because the Alpha asm can't
74 handle .files inside of functions. */
76 static int inside_function = FALSE;
78 /* Non-zero if an instruction that may cause a trap is pending. */
80 static int trap_pending = 0;
82 /* Nonzero if the current function needs gp. */
84 int alpha_function_needs_gp;
86 extern char *version_string;
87 extern int rtx_equal_function_value_matters;
89 /* Declarations of static functions. */
90 static void alpha_set_memflags_1 PROTO((rtx, int, int, int));
91 static rtx alpha_emit_set_const_1 PROTO((rtx, enum machine_mode,
92 HOST_WIDE_INT, int));
93 static void add_long_const PROTO((FILE *, HOST_WIDE_INT, int, int, int));
95 /* Compute the size of the save area in the stack. */
96 static void alpha_sa_mask PROTO((unsigned long *imaskP,
97 unsigned long *fmaskP));
99 /* Get the number of args of a function in one of two ways. */
100 #ifdef OPEN_VMS
101 #define NUM_ARGS current_function_args_info.num_args
102 #else
103 #define NUM_ARGS current_function_args_info
104 #endif
106 /* Parse target option strings. */
108 void
109 override_options ()
111 alpha_cpu
112 = TARGET_CPU_DEFAULT & MASK_CPU_EV6 ? PROCESSOR_EV6
113 : (TARGET_CPU_DEFAULT & MASK_CPU_EV5 ? PROCESSOR_EV5 : PROCESSOR_EV4);
115 if (alpha_cpu_string)
117 if (! strcmp (alpha_cpu_string, "ev4")
118 || ! strcmp (alpha_cpu_string, "21064"))
120 alpha_cpu = PROCESSOR_EV4;
121 target_flags &= ~ (MASK_BWX | MASK_CIX | MASK_MAX);
123 else if (! strcmp (alpha_cpu_string, "ev5")
124 || ! strcmp (alpha_cpu_string, "21164"))
126 alpha_cpu = PROCESSOR_EV5;
127 target_flags &= ~ (MASK_BWX | MASK_CIX | MASK_MAX);
129 else if (! strcmp (alpha_cpu_string, "ev56")
130 || ! strcmp (alpha_cpu_string, "21164a"))
132 alpha_cpu = PROCESSOR_EV5;
133 target_flags |= MASK_BWX;
134 target_flags &= ~ (MASK_CIX | MASK_MAX);
136 else if (! strcmp (alpha_cpu_string, "pca56")
137 || ! strcmp (alpha_cpu_string, "21164PC"))
139 alpha_cpu = PROCESSOR_EV5;
140 target_flags |= MASK_BWX | MASK_MAX;
141 target_flags &= ~ MASK_CIX;
143 else if (! strcmp (alpha_cpu_string, "ev6")
144 || ! strcmp (alpha_cpu_string, "21264"))
146 alpha_cpu = PROCESSOR_EV6;
147 target_flags |= MASK_BWX | MASK_CIX | MASK_MAX;
149 else
150 error ("bad value `%s' for -mcpu switch", alpha_cpu_string);
153 alpha_tp = ALPHA_TP_PROG;
154 alpha_fprm = ALPHA_FPRM_NORM;
155 alpha_fptm = ALPHA_FPTM_N;
157 if (TARGET_IEEE)
159 alpha_tp = ALPHA_TP_INSN;
160 alpha_fptm = ALPHA_FPTM_SU;
163 if (TARGET_IEEE_WITH_INEXACT)
165 alpha_tp = ALPHA_TP_INSN;
166 alpha_fptm = ALPHA_FPTM_SUI;
169 if (alpha_tp_string)
171 if (! strcmp (alpha_tp_string, "p"))
172 alpha_tp = ALPHA_TP_PROG;
173 else if (! strcmp (alpha_tp_string, "f"))
174 alpha_tp = ALPHA_TP_FUNC;
175 else if (! strcmp (alpha_tp_string, "i"))
176 alpha_tp = ALPHA_TP_INSN;
177 else
178 error ("bad value `%s' for -mtrap-precision switch", alpha_tp_string);
181 if (alpha_fprm_string)
183 if (! strcmp (alpha_fprm_string, "n"))
184 alpha_fprm = ALPHA_FPRM_NORM;
185 else if (! strcmp (alpha_fprm_string, "m"))
186 alpha_fprm = ALPHA_FPRM_MINF;
187 else if (! strcmp (alpha_fprm_string, "c"))
188 alpha_fprm = ALPHA_FPRM_CHOP;
189 else if (! strcmp (alpha_fprm_string,"d"))
190 alpha_fprm = ALPHA_FPRM_DYN;
191 else
192 error ("bad value `%s' for -mfp-rounding-mode switch",
193 alpha_fprm_string);
196 if (alpha_fptm_string)
198 if (strcmp (alpha_fptm_string, "n") == 0)
199 alpha_fptm = ALPHA_FPTM_N;
200 else if (strcmp (alpha_fptm_string, "u") == 0)
201 alpha_fptm = ALPHA_FPTM_U;
202 else if (strcmp (alpha_fptm_string, "su") == 0)
203 alpha_fptm = ALPHA_FPTM_SU;
204 else if (strcmp (alpha_fptm_string, "sui") == 0)
205 alpha_fptm = ALPHA_FPTM_SUI;
206 else
207 error ("bad value `%s' for -mfp-trap-mode switch", alpha_fptm_string);
210 /* Do some sanity checks on the above option. */
212 if ((alpha_fptm == ALPHA_FPTM_SU || alpha_fptm == ALPHA_FPTM_SUI)
213 && alpha_tp != ALPHA_TP_INSN)
215 warning ("fp software completion requires -mtrap-precision=i");
216 alpha_tp = ALPHA_TP_INSN;
219 if (TARGET_FLOAT_VAX)
221 if (alpha_fprm == ALPHA_FPRM_MINF || alpha_fprm == ALPHA_FPRM_DYN)
223 warning ("rounding mode not supported for VAX floats");
224 alpha_fprm = ALPHA_FPRM_NORM;
226 if (alpha_fptm == ALPHA_FPTM_SUI)
228 warning ("trap mode not supported for VAX floats");
229 alpha_fptm = ALPHA_FPTM_SU;
234 /* Returns 1 if VALUE is a mask that contains full bytes of zero or ones. */
237 zap_mask (value)
238 HOST_WIDE_INT value;
240 int i;
242 for (i = 0; i < HOST_BITS_PER_WIDE_INT / HOST_BITS_PER_CHAR;
243 i++, value >>= 8)
244 if ((value & 0xff) != 0 && (value & 0xff) != 0xff)
245 return 0;
247 return 1;
250 /* Returns 1 if OP is either the constant zero or a register. If a
251 register, it must be in the proper mode unless MODE is VOIDmode. */
254 reg_or_0_operand (op, mode)
255 register rtx op;
256 enum machine_mode mode;
258 return op == const0_rtx || register_operand (op, mode);
261 /* Return 1 if OP is a constant in the range of 0-63 (for a shift) or
262 any register. */
265 reg_or_6bit_operand (op, mode)
266 register rtx op;
267 enum machine_mode mode;
269 return ((GET_CODE (op) == CONST_INT
270 && (unsigned HOST_WIDE_INT) INTVAL (op) < 64)
271 || register_operand (op, mode));
275 /* Return 1 if OP is an 8-bit constant or any register. */
278 reg_or_8bit_operand (op, mode)
279 register rtx op;
280 enum machine_mode mode;
282 return ((GET_CODE (op) == CONST_INT
283 && (unsigned HOST_WIDE_INT) INTVAL (op) < 0x100)
284 || register_operand (op, mode));
287 /* Return 1 if OP is an 8-bit constant. */
290 cint8_operand (op, mode)
291 register rtx op;
292 enum machine_mode mode;
294 return (GET_CODE (op) == CONST_INT
295 && (unsigned HOST_WIDE_INT) INTVAL (op) < 0x100);
298 /* Return 1 if the operand is a valid second operand to an add insn. */
301 add_operand (op, mode)
302 register rtx op;
303 enum machine_mode mode;
305 if (GET_CODE (op) == CONST_INT)
306 return (CONST_OK_FOR_LETTER_P (INTVAL (op), 'K')
307 || CONST_OK_FOR_LETTER_P (INTVAL (op), 'L')
308 || CONST_OK_FOR_LETTER_P (INTVAL (op), 'O'));
310 return register_operand (op, mode);
313 /* Return 1 if the operand is a valid second operand to a sign-extending
314 add insn. */
317 sext_add_operand (op, mode)
318 register rtx op;
319 enum machine_mode mode;
321 if (GET_CODE (op) == CONST_INT)
322 return ((unsigned HOST_WIDE_INT) INTVAL (op) < 255
323 || (unsigned HOST_WIDE_INT) (- INTVAL (op)) < 255);
325 return register_operand (op, mode);
328 /* Return 1 if OP is the constant 4 or 8. */
331 const48_operand (op, mode)
332 register rtx op;
333 enum machine_mode mode;
335 return (GET_CODE (op) == CONST_INT
336 && (INTVAL (op) == 4 || INTVAL (op) == 8));
339 /* Return 1 if OP is a valid first operand to an AND insn. */
342 and_operand (op, mode)
343 register rtx op;
344 enum machine_mode mode;
346 if (GET_CODE (op) == CONST_DOUBLE && GET_MODE (op) == VOIDmode)
347 return (zap_mask (CONST_DOUBLE_LOW (op))
348 && zap_mask (CONST_DOUBLE_HIGH (op)));
350 if (GET_CODE (op) == CONST_INT)
351 return ((unsigned HOST_WIDE_INT) INTVAL (op) < 0x100
352 || (unsigned HOST_WIDE_INT) ~ INTVAL (op) < 0x100
353 || zap_mask (INTVAL (op)));
355 return register_operand (op, mode);
358 /* Return 1 if OP is a valid first operand to an IOR or XOR insn. */
361 or_operand (op, mode)
362 register rtx op;
363 enum machine_mode mode;
365 if (GET_CODE (op) == CONST_INT)
366 return ((unsigned HOST_WIDE_INT) INTVAL (op) < 0x100
367 || (unsigned HOST_WIDE_INT) ~ INTVAL (op) < 0x100);
369 return register_operand (op, mode);
372 /* Return 1 if OP is a constant that is the width, in bits, of an integral
373 mode smaller than DImode. */
376 mode_width_operand (op, mode)
377 register rtx op;
378 enum machine_mode mode;
380 return (GET_CODE (op) == CONST_INT
381 && (INTVAL (op) == 8 || INTVAL (op) == 16 || INTVAL (op) == 32));
384 /* Return 1 if OP is a constant that is the width of an integral machine mode
385 smaller than an integer. */
388 mode_mask_operand (op, mode)
389 register rtx op;
390 enum machine_mode mode;
392 #if HOST_BITS_PER_WIDE_INT == 32
393 if (GET_CODE (op) == CONST_DOUBLE)
394 return CONST_DOUBLE_HIGH (op) == 0 && CONST_DOUBLE_LOW (op) == -1;
395 #endif
397 return (GET_CODE (op) == CONST_INT
398 && (INTVAL (op) == 0xff
399 || INTVAL (op) == 0xffff
400 #if HOST_BITS_PER_WIDE_INT == 64
401 || INTVAL (op) == 0xffffffff
402 #endif
406 /* Return 1 if OP is a multiple of 8 less than 64. */
409 mul8_operand (op, mode)
410 register rtx op;
411 enum machine_mode mode;
413 return (GET_CODE (op) == CONST_INT
414 && (unsigned HOST_WIDE_INT) INTVAL (op) < 64
415 && (INTVAL (op) & 7) == 0);
418 /* Return 1 if OP is the constant zero in floating-point. */
421 fp0_operand (op, mode)
422 register rtx op;
423 enum machine_mode mode;
425 return (GET_MODE (op) == mode
426 && GET_MODE_CLASS (mode) == MODE_FLOAT && op == CONST0_RTX (mode));
429 /* Return 1 if OP is the floating-point constant zero or a register. */
432 reg_or_fp0_operand (op, mode)
433 register rtx op;
434 enum machine_mode mode;
436 return fp0_operand (op, mode) || register_operand (op, mode);
439 /* Return 1 if OP is a register or a constant integer. */
443 reg_or_cint_operand (op, mode)
444 register rtx op;
445 enum machine_mode mode;
447 return GET_CODE (op) == CONST_INT || register_operand (op, mode);
450 /* Return 1 if OP is something that can be reloaded into a register;
451 if it is a MEM, it need not be valid. */
454 some_operand (op, mode)
455 register rtx op;
456 enum machine_mode mode;
458 if (mode != VOIDmode && GET_MODE (op) != VOIDmode && mode != GET_MODE (op))
459 return 0;
461 switch (GET_CODE (op))
463 case REG: case MEM: case CONST_DOUBLE:
464 case CONST_INT: case LABEL_REF: case SYMBOL_REF: case CONST:
465 return 1;
467 case SUBREG:
468 return some_operand (SUBREG_REG (op), VOIDmode);
471 return 0;
474 /* Return 1 if OP is a valid operand for the source of a move insn. */
477 input_operand (op, mode)
478 register rtx op;
479 enum machine_mode mode;
481 if (mode != VOIDmode && GET_MODE (op) != VOIDmode && mode != GET_MODE (op))
482 return 0;
484 if (GET_MODE_CLASS (mode) == MODE_FLOAT && GET_MODE (op) != mode)
485 return 0;
487 switch (GET_CODE (op))
489 case LABEL_REF:
490 case SYMBOL_REF:
491 case CONST:
492 /* This handles both the Windows/NT and OSF cases. */
493 return mode == ptr_mode || mode == DImode;
495 case REG:
496 return 1;
498 case SUBREG:
499 if (register_operand (op, mode))
500 return 1;
501 /* ... fall through ... */
502 case MEM:
503 return ((TARGET_BWX || (mode != HImode && mode != QImode))
504 && general_operand (op, mode));
506 case CONST_DOUBLE:
507 return GET_MODE_CLASS (mode) == MODE_FLOAT && op == CONST0_RTX (mode);
509 case CONST_INT:
510 return mode == QImode || mode == HImode || add_operand (op, mode);
513 return 0;
516 /* Return 1 if OP is a SYMBOL_REF for a function known to be in this
517 file. */
520 current_file_function_operand (op, mode)
521 rtx op;
522 enum machine_mode mode;
524 return (GET_CODE (op) == SYMBOL_REF
525 && ! profile_flag && ! profile_block_flag
526 && (SYMBOL_REF_FLAG (op)
527 || op == XEXP (DECL_RTL (current_function_decl), 0)));
530 /* Return 1 if OP is a valid operand for the MEM of a CALL insn. */
533 call_operand (op, mode)
534 rtx op;
535 enum machine_mode mode;
537 if (mode != Pmode)
538 return 0;
540 return (GET_CODE (op) == SYMBOL_REF
541 || (GET_CODE (op) == REG && (TARGET_OPEN_VMS || REGNO (op) == 27)));
544 /* Return 1 if OP is a valid Alpha comparison operator. Here we know which
545 comparisons are valid in which insn. */
548 alpha_comparison_operator (op, mode)
549 register rtx op;
550 enum machine_mode mode;
552 enum rtx_code code = GET_CODE (op);
554 if (mode != GET_MODE (op) || GET_RTX_CLASS (code) != '<')
555 return 0;
557 return (code == EQ || code == LE || code == LT
558 || (mode == DImode && (code == LEU || code == LTU)));
561 /* Return 1 if OP is a valid Alpha swapped comparison operator. */
564 alpha_swapped_comparison_operator (op, mode)
565 register rtx op;
566 enum machine_mode mode;
568 enum rtx_code code = GET_CODE (op);
570 if (mode != GET_MODE (op) || GET_RTX_CLASS (code) != '<')
571 return 0;
573 code = swap_condition (code);
574 return (code == EQ || code == LE || code == LT
575 || (mode == DImode && (code == LEU || code == LTU)));
578 /* Return 1 if OP is a signed comparison operation. */
581 signed_comparison_operator (op, mode)
582 register rtx op;
583 enum machine_mode mode;
585 switch (GET_CODE (op))
587 case EQ: case NE: case LE: case LT: case GE: case GT:
588 return 1;
591 return 0;
594 /* Return 1 if this is a divide or modulus operator. */
597 divmod_operator (op, mode)
598 register rtx op;
599 enum machine_mode mode;
601 switch (GET_CODE (op))
603 case DIV: case MOD: case UDIV: case UMOD:
604 return 1;
607 return 0;
610 /* Return 1 if this memory address is a known aligned register plus
611 a constant. It must be a valid address. This means that we can do
612 this as an aligned reference plus some offset.
614 Take into account what reload will do.
616 We could say that out-of-range stack slots are alignable, but that would
617 complicate get_aligned_mem and it isn't worth the trouble since few
618 functions have large stack space. */
621 aligned_memory_operand (op, mode)
622 register rtx op;
623 enum machine_mode mode;
625 if (GET_CODE (op) == SUBREG)
627 if (GET_MODE (op) != mode)
628 return 0;
629 op = SUBREG_REG (op);
630 mode = GET_MODE (op);
633 if (reload_in_progress && GET_CODE (op) == REG
634 && REGNO (op) >= FIRST_PSEUDO_REGISTER)
635 op = reg_equiv_mem[REGNO (op)];
637 if (GET_CODE (op) != MEM || GET_MODE (op) != mode
638 || ! memory_address_p (mode, XEXP (op, 0)))
639 return 0;
641 op = XEXP (op, 0);
643 if (GET_CODE (op) == PLUS)
644 op = XEXP (op, 0);
646 return (GET_CODE (op) == REG
647 && REGNO_POINTER_ALIGN (REGNO (op)) >= 4);
650 /* Similar, but return 1 if OP is a MEM which is not alignable. */
653 unaligned_memory_operand (op, mode)
654 register rtx op;
655 enum machine_mode mode;
657 if (GET_CODE (op) == SUBREG)
659 if (GET_MODE (op) != mode)
660 return 0;
661 op = SUBREG_REG (op);
662 mode = GET_MODE (op);
665 if (reload_in_progress && GET_CODE (op) == REG
666 && REGNO (op) >= FIRST_PSEUDO_REGISTER)
667 op = reg_equiv_mem[REGNO (op)];
669 if (GET_CODE (op) != MEM || GET_MODE (op) != mode)
670 return 0;
672 op = XEXP (op, 0);
674 if (! memory_address_p (mode, op))
675 return 1;
677 if (GET_CODE (op) == PLUS)
678 op = XEXP (op, 0);
680 return (GET_CODE (op) != REG
681 || REGNO_POINTER_ALIGN (REGNO (op)) < 4);
684 /* Return 1 if OP is either a register or an unaligned memory location. */
687 reg_or_unaligned_mem_operand (op, mode)
688 rtx op;
689 enum machine_mode mode;
691 return register_operand (op, mode) || unaligned_memory_operand (op, mode);
694 /* Return 1 if OP is any memory location. During reload a pseudo matches. */
697 any_memory_operand (op, mode)
698 register rtx op;
699 enum machine_mode mode;
701 return (GET_CODE (op) == MEM
702 || (GET_CODE (op) == SUBREG && GET_CODE (SUBREG_REG (op)) == REG)
703 || (reload_in_progress && GET_CODE (op) == REG
704 && REGNO (op) >= FIRST_PSEUDO_REGISTER)
705 || (reload_in_progress && GET_CODE (op) == SUBREG
706 && GET_CODE (SUBREG_REG (op)) == REG
707 && REGNO (SUBREG_REG (op)) >= FIRST_PSEUDO_REGISTER));
710 /* REF is an alignable memory location. Place an aligned SImode
711 reference into *PALIGNED_MEM and the number of bits to shift into
712 *PBITNUM. */
714 void
715 get_aligned_mem (ref, paligned_mem, pbitnum)
716 rtx ref;
717 rtx *paligned_mem, *pbitnum;
719 rtx base;
720 HOST_WIDE_INT offset = 0;
722 if (GET_CODE (ref) == SUBREG)
724 offset = SUBREG_WORD (ref) * UNITS_PER_WORD;
725 if (BYTES_BIG_ENDIAN)
726 offset -= (MIN (UNITS_PER_WORD, GET_MODE_SIZE (GET_MODE (ref)))
727 - MIN (UNITS_PER_WORD,
728 GET_MODE_SIZE (GET_MODE (SUBREG_REG (ref)))));
729 ref = SUBREG_REG (ref);
732 if (GET_CODE (ref) == REG)
733 ref = reg_equiv_mem[REGNO (ref)];
735 if (reload_in_progress)
736 base = find_replacement (&XEXP (ref, 0));
737 else
738 base = XEXP (ref, 0);
740 if (GET_CODE (base) == PLUS)
741 offset += INTVAL (XEXP (base, 1)), base = XEXP (base, 0);
743 *paligned_mem = gen_rtx (MEM, SImode,
744 plus_constant (base, offset & ~3));
745 MEM_IN_STRUCT_P (*paligned_mem) = MEM_IN_STRUCT_P (ref);
746 MEM_VOLATILE_P (*paligned_mem) = MEM_VOLATILE_P (ref);
747 RTX_UNCHANGING_P (*paligned_mem) = RTX_UNCHANGING_P (ref);
749 *pbitnum = GEN_INT ((offset & 3) * 8);
752 /* Similar, but just get the address. Handle the two reload cases.
753 Add EXTRA_OFFSET to the address we return. */
756 get_unaligned_address (ref, extra_offset)
757 rtx ref;
758 int extra_offset;
760 rtx base;
761 HOST_WIDE_INT offset = 0;
763 if (GET_CODE (ref) == SUBREG)
765 offset = SUBREG_WORD (ref) * UNITS_PER_WORD;
766 if (BYTES_BIG_ENDIAN)
767 offset -= (MIN (UNITS_PER_WORD, GET_MODE_SIZE (GET_MODE (ref)))
768 - MIN (UNITS_PER_WORD,
769 GET_MODE_SIZE (GET_MODE (SUBREG_REG (ref)))));
770 ref = SUBREG_REG (ref);
773 if (GET_CODE (ref) == REG)
774 ref = reg_equiv_mem[REGNO (ref)];
776 if (reload_in_progress)
777 base = find_replacement (&XEXP (ref, 0));
778 else
779 base = XEXP (ref, 0);
781 if (GET_CODE (base) == PLUS)
782 offset += INTVAL (XEXP (base, 1)), base = XEXP (base, 0);
784 return plus_constant (base, offset + extra_offset);
787 /* Subfunction of the following function. Update the flags of any MEM
788 found in part of X. */
790 static void
791 alpha_set_memflags_1 (x, in_struct_p, volatile_p, unchanging_p)
792 rtx x;
793 int in_struct_p, volatile_p, unchanging_p;
795 int i;
797 switch (GET_CODE (x))
799 case SEQUENCE:
800 case PARALLEL:
801 for (i = XVECLEN (x, 0) - 1; i >= 0; i--)
802 alpha_set_memflags_1 (XVECEXP (x, 0, i), in_struct_p, volatile_p,
803 unchanging_p);
804 break;
806 case INSN:
807 alpha_set_memflags_1 (PATTERN (x), in_struct_p, volatile_p,
808 unchanging_p);
809 break;
811 case SET:
812 alpha_set_memflags_1 (SET_DEST (x), in_struct_p, volatile_p,
813 unchanging_p);
814 alpha_set_memflags_1 (SET_SRC (x), in_struct_p, volatile_p,
815 unchanging_p);
816 break;
818 case MEM:
819 MEM_IN_STRUCT_P (x) = in_struct_p;
820 MEM_VOLATILE_P (x) = volatile_p;
821 RTX_UNCHANGING_P (x) = unchanging_p;
822 break;
826 /* Given INSN, which is either an INSN or a SEQUENCE generated to
827 perform a memory operation, look for any MEMs in either a SET_DEST or
828 a SET_SRC and copy the in-struct, unchanging, and volatile flags from
829 REF into each of the MEMs found. If REF is not a MEM, don't do
830 anything. */
832 void
833 alpha_set_memflags (insn, ref)
834 rtx insn;
835 rtx ref;
837 /* Note that it is always safe to get these flags, though they won't
838 be what we think if REF is not a MEM. */
839 int in_struct_p = MEM_IN_STRUCT_P (ref);
840 int volatile_p = MEM_VOLATILE_P (ref);
841 int unchanging_p = RTX_UNCHANGING_P (ref);
843 if (GET_CODE (ref) != MEM
844 || (! in_struct_p && ! volatile_p && ! unchanging_p))
845 return;
847 alpha_set_memflags_1 (insn, in_struct_p, volatile_p, unchanging_p);
850 /* Try to output insns to set TARGET equal to the constant C if it can be
851 done in less than N insns. Do all computations in MODE. Returns the place
852 where the output has been placed if it can be done and the insns have been
853 emitted. If it would take more than N insns, zero is returned and no
854 insns and emitted. */
857 alpha_emit_set_const (target, mode, c, n)
858 rtx target;
859 enum machine_mode mode;
860 HOST_WIDE_INT c;
861 int n;
863 rtx pat;
864 int i;
866 /* Try 1 insn, then 2, then up to N. */
867 for (i = 1; i <= n; i++)
868 if ((pat = alpha_emit_set_const_1 (target, mode, c, i)) != 0)
869 return pat;
871 return 0;
874 /* Internal routine for the above to check for N or below insns. */
876 static rtx
877 alpha_emit_set_const_1 (target, mode, c, n)
878 rtx target;
879 enum machine_mode mode;
880 HOST_WIDE_INT c;
881 int n;
883 HOST_WIDE_INT new = c;
884 int i, bits;
885 /* Use a pseudo if highly optimizing and still generating RTL. */
886 rtx subtarget
887 = (flag_expensive_optimizations && rtx_equal_function_value_matters
888 ? 0 : target);
889 rtx temp;
891 #if HOST_BITS_PER_WIDE_INT == 64
892 /* We are only called for SImode and DImode. If this is SImode, ensure that
893 we are sign extended to a full word. This does not make any sense when
894 cross-compiling on a narrow machine. */
896 if (mode == SImode)
897 c = (c & 0xffffffff) - 2 * (c & 0x80000000);
898 #endif
900 /* If this is a sign-extended 32-bit constant, we can do this in at most
901 three insns, so do it if we have enough insns left. We always have
902 a sign-extended 32-bit constant when compiling on a narrow machine.
903 Note that we cannot handle the constant 0x80000000. */
905 if ((HOST_BITS_PER_WIDE_INT != 64
906 || c >> 31 == -1 || c >> 31 == 0)
907 && c != 0x80000000U)
909 HOST_WIDE_INT low = (c & 0xffff) - 2 * (c & 0x8000);
910 HOST_WIDE_INT tmp1 = c - low;
911 HOST_WIDE_INT high
912 = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
913 HOST_WIDE_INT extra = 0;
915 /* If HIGH will be interpreted as negative but the constant is
916 positive, we must adjust it to do two ldha insns. */
918 if ((high & 0x8000) != 0 && c >= 0)
920 extra = 0x4000;
921 tmp1 -= 0x40000000;
922 high = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
925 if (c == low || (low == 0 && extra == 0))
926 return copy_to_suggested_reg (GEN_INT (c), target, mode);
927 else if (n >= 2 + (extra != 0))
929 temp = copy_to_suggested_reg (GEN_INT (low), subtarget, mode);
931 if (extra != 0)
932 temp = expand_binop (mode, add_optab, temp, GEN_INT (extra << 16),
933 subtarget, 0, OPTAB_WIDEN);
935 return expand_binop (mode, add_optab, temp, GEN_INT (high << 16),
936 target, 0, OPTAB_WIDEN);
940 /* If we couldn't do it that way, try some other methods. But if we have
941 no instructions left, don't bother. Likewise, if this is SImode and
942 we can't make pseudos, we can't do anything since the expand_binop
943 and expand_unop calls will widen and try to make pseudos. */
945 if (n == 1
946 || (mode == SImode && ! rtx_equal_function_value_matters))
947 return 0;
949 #if HOST_BITS_PER_WIDE_INT == 64
950 /* First, see if can load a value into the target that is the same as the
951 constant except that all bytes that are 0 are changed to be 0xff. If we
952 can, then we can do a ZAPNOT to obtain the desired constant. */
954 for (i = 0; i < 64; i += 8)
955 if ((new & ((HOST_WIDE_INT) 0xff << i)) == 0)
956 new |= (HOST_WIDE_INT) 0xff << i;
958 /* We are only called for SImode and DImode. If this is SImode, ensure that
959 we are sign extended to a full word. */
961 if (mode == SImode)
962 new = (new & 0xffffffff) - 2 * (new & 0x80000000);
964 if (new != c
965 && (temp = alpha_emit_set_const (subtarget, mode, new, n - 1)) != 0)
966 return expand_binop (mode, and_optab, temp, GEN_INT (c | ~ new),
967 target, 0, OPTAB_WIDEN);
968 #endif
970 /* Next, see if we can load a related constant and then shift and possibly
971 negate it to get the constant we want. Try this once each increasing
972 numbers of insns. */
974 for (i = 1; i < n; i++)
976 /* First try complementing. */
977 if ((temp = alpha_emit_set_const (subtarget, mode, ~ c, i)) != 0)
978 return expand_unop (mode, one_cmpl_optab, temp, target, 0);
980 /* Next try to form a constant and do a left shift. We can do this
981 if some low-order bits are zero; the exact_log2 call below tells
982 us that information. The bits we are shifting out could be any
983 value, but here we'll just try the 0- and sign-extended forms of
984 the constant. To try to increase the chance of having the same
985 constant in more than one insn, start at the highest number of
986 bits to shift, but try all possibilities in case a ZAPNOT will
987 be useful. */
989 if ((bits = exact_log2 (c & - c)) > 0)
990 for (; bits > 0; bits--)
991 if ((temp = (alpha_emit_set_const
992 (subtarget, mode,
993 (unsigned HOST_WIDE_INT) c >> bits, i))) != 0
994 || ((temp = (alpha_emit_set_const
995 (subtarget, mode,
996 ((unsigned HOST_WIDE_INT) c) >> bits, i)))
997 != 0))
998 return expand_binop (mode, ashl_optab, temp, GEN_INT (bits),
999 target, 0, OPTAB_WIDEN);
1001 /* Now try high-order zero bits. Here we try the shifted-in bits as
1002 all zero and all ones. Be careful to avoid shifting outside the
1003 mode and to avoid shifting outside the host wide int size. */
1005 if ((bits = (MIN (HOST_BITS_PER_WIDE_INT, GET_MODE_SIZE (mode) * 8)
1006 - floor_log2 (c) - 1)) > 0)
1007 for (; bits > 0; bits--)
1008 if ((temp = alpha_emit_set_const (subtarget, mode,
1009 c << bits, i)) != 0
1010 || ((temp = (alpha_emit_set_const
1011 (subtarget, mode,
1012 ((c << bits) | (((HOST_WIDE_INT) 1 << bits) - 1)),
1013 i)))
1014 != 0))
1015 return expand_binop (mode, lshr_optab, temp, GEN_INT (bits),
1016 target, 1, OPTAB_WIDEN);
1018 /* Now try high-order 1 bits. We get that with a sign-extension.
1019 But one bit isn't enough here. Be careful to avoid shifting outside
1020 the mode and to avoid shifting outside the host wide int size. */
1022 if ((bits = (MIN (HOST_BITS_PER_WIDE_INT, GET_MODE_SIZE (mode) * 8)
1023 - floor_log2 (~ c) - 2)) > 0)
1024 for (; bits > 0; bits--)
1025 if ((temp = alpha_emit_set_const (subtarget, mode,
1026 c << bits, i)) != 0
1027 || ((temp = (alpha_emit_set_const
1028 (subtarget, mode,
1029 ((c << bits) | (((HOST_WIDE_INT) 1 << bits) - 1)),
1030 i)))
1031 != 0))
1032 return expand_binop (mode, ashr_optab, temp, GEN_INT (bits),
1033 target, 0, OPTAB_WIDEN);
1036 return 0;
1039 #if HOST_BITS_PER_WIDE_INT == 64
1040 /* Having failed to find a 3 insn sequence in alpha_emit_set_const,
1041 fall back to a straight forward decomposition. We do this to avoid
1042 exponential run times encountered when looking for longer sequences
1043 with alpha_emit_set_const. */
1046 alpha_emit_set_long_const (target, c)
1047 rtx target;
1048 HOST_WIDE_INT c;
1050 /* Use a pseudo if highly optimizing and still generating RTL. */
1051 rtx subtarget
1052 = (flag_expensive_optimizations && rtx_equal_function_value_matters
1053 ? 0 : target);
1054 HOST_WIDE_INT d1, d2, d3, d4;
1055 rtx r1, r2;
1057 /* Decompose the entire word */
1058 d1 = ((c & 0xffff) ^ 0x8000) - 0x8000;
1059 c -= d1;
1060 d2 = ((c & 0xffffffff) ^ 0x80000000) - 0x80000000;
1061 c = (c - d2) >> 32;
1062 d3 = ((c & 0xffff) ^ 0x8000) - 0x8000;
1063 c -= d3;
1064 d4 = ((c & 0xffffffff) ^ 0x80000000) - 0x80000000;
1066 if (c - d4 != 0)
1067 abort();
1069 /* Construct the high word */
1070 if (d3 == 0)
1071 r1 = copy_to_suggested_reg (GEN_INT (d4), subtarget, DImode);
1072 else if (d4 == 0)
1073 r1 = copy_to_suggested_reg (GEN_INT (d3), subtarget, DImode);
1074 else
1075 r1 = expand_binop (DImode, add_optab, GEN_INT (d3), GEN_INT (d4),
1076 subtarget, 0, OPTAB_WIDEN);
1078 /* Shift it into place */
1079 r2 = expand_binop (DImode, ashl_optab, r1, GEN_INT (32),
1080 subtarget, 0, OPTAB_WIDEN);
1082 if (subtarget == 0 && d1 == d3 && d2 == d4)
1083 r1 = expand_binop (DImode, add_optab, r1, r2, subtarget, 0, OPTAB_WIDEN);
1084 else
1086 r1 = r2;
1088 /* Add in the low word */
1089 if (d2 != 0)
1090 r1 = expand_binop (DImode, add_optab, r1, GEN_INT (d2),
1091 subtarget, 0, OPTAB_WIDEN);
1092 if (d1 != 0)
1093 r1 = expand_binop (DImode, add_optab, r1, GEN_INT (d1),
1094 subtarget, 0, OPTAB_WIDEN);
1097 if (subtarget == 0)
1098 r1 = copy_to_suggested_reg(r1, target, DImode);
1100 return r1;
1102 #endif /* HOST_BITS_PER_WIDE_INT == 64 */
1104 /* Rewrite a comparison against zero CMP of the form
1105 (CODE (cc0) (const_int 0)) so it can be written validly in
1106 a conditional move (if_then_else CMP ...).
1107 If both of the operands that set cc0 are non-zero we must emit
1108 an insn to perform the compare (it can't be done within
1109 the conditional move). */
1111 alpha_emit_conditional_move (cmp, mode)
1112 rtx cmp;
1113 enum machine_mode mode;
1115 enum rtx_code code = GET_CODE (cmp);
1116 enum rtx_code cmov_code = NE;
1117 rtx op0 = alpha_compare_op0;
1118 rtx op1 = alpha_compare_op1;
1119 enum machine_mode cmp_mode
1120 = (GET_MODE (op0) == VOIDmode ? DImode : GET_MODE (op0));
1121 enum machine_mode cmp_op_mode = alpha_compare_fp_p ? DFmode : DImode;
1122 rtx tem;
1124 if (alpha_compare_fp_p != FLOAT_MODE_P (mode))
1125 return 0;
1127 /* We may be able to use a conditional move directly.
1128 This avoids emitting spurious compares. */
1129 if (signed_comparison_operator (cmp, cmp_op_mode)
1130 && (op0 == CONST0_RTX (cmp_mode) || op1 == CONST0_RTX (cmp_mode)))
1131 return gen_rtx (code, VOIDmode, op0, op1);
1133 /* We can't put the comparison insides a conditional move;
1134 emit a compare instruction and put that inside the
1135 conditional move. Make sure we emit only comparisons we have;
1136 swap or reverse as necessary. */
1138 switch (code)
1140 case EQ: case LE: case LT: case LEU: case LTU:
1141 /* We have these compares: */
1142 break;
1144 case NE:
1145 /* This must be reversed. */
1146 code = reverse_condition (code);
1147 cmov_code = EQ;
1148 break;
1150 case GE: case GT: case GEU: case GTU:
1151 /* These must be swapped. Make sure the new first operand is in
1152 a register. */
1153 code = swap_condition (code);
1154 tem = op0, op0 = op1, op1 = tem;
1155 op0 = force_reg (cmp_mode, op0);
1156 break;
1158 default:
1159 abort ();
1162 tem = gen_reg_rtx (cmp_op_mode);
1163 emit_move_insn (tem, gen_rtx (code, cmp_op_mode, op0, op1));
1164 return gen_rtx (cmov_code, VOIDmode, tem, CONST0_RTX (cmp_op_mode));
1167 /* Adjust the cost of a scheduling dependency. Return the new cost of
1168 a dependency LINK or INSN on DEP_INSN. COST is the current cost. */
1171 alpha_adjust_cost (insn, link, dep_insn, cost)
1172 rtx insn;
1173 rtx link;
1174 rtx dep_insn;
1175 int cost;
1177 rtx set;
1179 /* If the dependence is an anti-dependence, there is no cost. For an
1180 output dependence, there is sometimes a cost, but it doesn't seem
1181 worth handling those few cases. */
1183 if (REG_NOTE_KIND (link) != 0)
1184 return 0;
1186 /* EV5 costs are as given in alpha.md; exceptions are given here. */
1187 if (alpha_cpu == PROCESSOR_EV5)
1189 /* And the lord DEC saith: "A special bypass provides an effective
1190 latency of 0 cycles for an ICMP or ILOG insn producing the test
1191 operand of an IBR or CMOV insn." */
1192 if (recog_memoized (dep_insn) >= 0
1193 && (get_attr_type (dep_insn) == TYPE_ICMP
1194 || get_attr_type (dep_insn) == TYPE_ILOG)
1195 && recog_memoized (insn) >= 0
1196 && (get_attr_type (insn) == TYPE_IBR
1197 || (get_attr_type (insn) == TYPE_CMOV
1198 && !((set = single_set (dep_insn)) != 0
1199 && GET_CODE (PATTERN (insn)) == SET
1200 && GET_CODE (SET_SRC (PATTERN (insn))) == IF_THEN_ELSE
1201 && (rtx_equal_p (SET_DEST (set),
1202 XEXP (SET_SRC (PATTERN (insn)), 1))
1203 || rtx_equal_p (SET_DEST (set),
1204 XEXP (SET_SRC (PATTERN (insn)), 2)))))))
1205 return 1;
1206 return cost;
1209 /* If INSN is a store insn and DEP_INSN is setting the data being stored,
1210 we can sometimes lower the cost. */
1212 if (recog_memoized (insn) >= 0 && get_attr_type (insn) == TYPE_ST
1213 && (set = single_set (dep_insn)) != 0
1214 && GET_CODE (PATTERN (insn)) == SET
1215 && rtx_equal_p (SET_DEST (set), SET_SRC (PATTERN (insn))))
1216 switch (get_attr_type (dep_insn))
1218 case TYPE_LD:
1219 /* No savings here. */
1220 return cost;
1222 case TYPE_IMULL:
1223 case TYPE_IMULQ:
1224 /* In these cases, we save one cycle. */
1225 return cost - 2;
1227 default:
1228 /* In all other cases, we save two cycles. */
1229 return MAX (0, cost - 4);
1232 /* Another case that needs adjustment is an arithmetic or logical
1233 operation. It's cost is usually one cycle, but we default it to
1234 two in the MD file. The only case that it is actually two is
1235 for the address in loads and stores. */
1237 if (recog_memoized (dep_insn) >= 0
1238 && (get_attr_type (dep_insn) == TYPE_IADD
1239 || get_attr_type (dep_insn) == TYPE_ILOG))
1240 switch (get_attr_type (insn))
1242 case TYPE_LD:
1243 case TYPE_ST:
1244 return cost;
1246 default:
1247 return 2;
1250 /* The final case is when a compare feeds into an integer branch. The cost
1251 is only one cycle in that case. */
1253 if (recog_memoized (dep_insn) >= 0
1254 && get_attr_type (dep_insn) == TYPE_ICMP
1255 && recog_memoized (insn) >= 0
1256 && get_attr_type (insn) == TYPE_IBR)
1257 return 2;
1259 /* Otherwise, return the default cost. */
1261 return cost;
1264 /* Print an operand. Recognize special options, documented below. */
1266 void
1267 print_operand (file, x, code)
1268 FILE *file;
1269 rtx x;
1270 char code;
1272 int i;
1274 switch (code)
1276 case '&':
1277 /* Generates fp-rounding mode suffix: nothing for normal, 'c' for
1278 chopped, 'm' for minus-infinity, and 'd' for dynamic rounding
1279 mode. alpha_fprm controls which suffix is generated. */
1280 switch (alpha_fprm)
1282 case ALPHA_FPRM_NORM:
1283 break;
1284 case ALPHA_FPRM_MINF:
1285 fputc ('m', file);
1286 break;
1287 case ALPHA_FPRM_CHOP:
1288 fputc ('c', file);
1289 break;
1290 case ALPHA_FPRM_DYN:
1291 fputc ('d', file);
1292 break;
1294 break;
1296 case '\'':
1297 /* Generates trap-mode suffix for instructions that accept the su
1298 suffix only (cmpt et al). */
1299 if (alpha_tp == ALPHA_TP_INSN)
1300 fputs ("su", file);
1301 break;
1303 case ')':
1304 /* Generates trap-mode suffix for instructions that accept the u, su,
1305 and sui suffix. This is the bulk of the IEEE floating point
1306 instructions (addt et al). */
1307 switch (alpha_fptm)
1309 case ALPHA_FPTM_N:
1310 break;
1311 case ALPHA_FPTM_U:
1312 fputc ('u', file);
1313 break;
1314 case ALPHA_FPTM_SU:
1315 fputs ("su", file);
1316 break;
1317 case ALPHA_FPTM_SUI:
1318 fputs ("sui", file);
1319 break;
1321 break;
1323 case '+':
1324 /* Generates trap-mode suffix for instructions that accept the sui
1325 suffix (cvtqt and cvtqs). */
1326 switch (alpha_fptm)
1328 case ALPHA_FPTM_N: case ALPHA_FPTM_U:
1329 case ALPHA_FPTM_SU: /* cvtqt/cvtqs can't cause underflow */
1330 break;
1331 case ALPHA_FPTM_SUI:
1332 fputs ("sui", file);
1333 break;
1335 break;
1337 case ',':
1338 /* Generates single precision instruction suffix. */
1339 fprintf (file, "%c", (TARGET_FLOAT_VAX ? 'f' : 's'));
1340 break;
1342 case '-':
1343 /* Generates double precision instruction suffix. */
1344 fprintf (file, "%c", (TARGET_FLOAT_VAX ? 'g' : 't'));
1345 break;
1347 case 'r':
1348 /* If this operand is the constant zero, write it as "$31". */
1349 if (GET_CODE (x) == REG)
1350 fprintf (file, "%s", reg_names[REGNO (x)]);
1351 else if (x == CONST0_RTX (GET_MODE (x)))
1352 fprintf (file, "$31");
1353 else
1354 output_operand_lossage ("invalid %%r value");
1356 break;
1358 case 'R':
1359 /* Similar, but for floating-point. */
1360 if (GET_CODE (x) == REG)
1361 fprintf (file, "%s", reg_names[REGNO (x)]);
1362 else if (x == CONST0_RTX (GET_MODE (x)))
1363 fprintf (file, "$f31");
1364 else
1365 output_operand_lossage ("invalid %%R value");
1367 break;
1369 case 'N':
1370 /* Write the 1's complement of a constant. */
1371 if (GET_CODE (x) != CONST_INT)
1372 output_operand_lossage ("invalid %%N value");
1374 fprintf (file, HOST_WIDE_INT_PRINT_DEC, ~ INTVAL (x));
1375 break;
1377 case 'P':
1378 /* Write 1 << C, for a constant C. */
1379 if (GET_CODE (x) != CONST_INT)
1380 output_operand_lossage ("invalid %%P value");
1382 fprintf (file, HOST_WIDE_INT_PRINT_DEC, (HOST_WIDE_INT) 1 << INTVAL (x));
1383 break;
1385 case 'h':
1386 /* Write the high-order 16 bits of a constant, sign-extended. */
1387 if (GET_CODE (x) != CONST_INT)
1388 output_operand_lossage ("invalid %%h value");
1390 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x) >> 16);
1391 break;
1393 case 'L':
1394 /* Write the low-order 16 bits of a constant, sign-extended. */
1395 if (GET_CODE (x) != CONST_INT)
1396 output_operand_lossage ("invalid %%L value");
1398 fprintf (file, HOST_WIDE_INT_PRINT_DEC,
1399 (INTVAL (x) & 0xffff) - 2 * (INTVAL (x) & 0x8000));
1400 break;
1402 case 'm':
1403 /* Write mask for ZAP insn. */
1404 if (GET_CODE (x) == CONST_DOUBLE)
1406 HOST_WIDE_INT mask = 0;
1407 HOST_WIDE_INT value;
1409 value = CONST_DOUBLE_LOW (x);
1410 for (i = 0; i < HOST_BITS_PER_WIDE_INT / HOST_BITS_PER_CHAR;
1411 i++, value >>= 8)
1412 if (value & 0xff)
1413 mask |= (1 << i);
1415 value = CONST_DOUBLE_HIGH (x);
1416 for (i = 0; i < HOST_BITS_PER_WIDE_INT / HOST_BITS_PER_CHAR;
1417 i++, value >>= 8)
1418 if (value & 0xff)
1419 mask |= (1 << (i + sizeof (int)));
1421 fprintf (file, HOST_WIDE_INT_PRINT_DEC, mask & 0xff);
1424 else if (GET_CODE (x) == CONST_INT)
1426 HOST_WIDE_INT mask = 0, value = INTVAL (x);
1428 for (i = 0; i < 8; i++, value >>= 8)
1429 if (value & 0xff)
1430 mask |= (1 << i);
1432 fprintf (file, HOST_WIDE_INT_PRINT_DEC, mask);
1434 else
1435 output_operand_lossage ("invalid %%m value");
1436 break;
1438 case 'M':
1439 /* 'b', 'w', or 'l' as the value of the constant. */
1440 if (GET_CODE (x) != CONST_INT
1441 || (INTVAL (x) != 8 && INTVAL (x) != 16 && INTVAL (x) != 32))
1442 output_operand_lossage ("invalid %%M value");
1444 fprintf (file, "%s",
1445 INTVAL (x) == 8 ? "b" : INTVAL (x) == 16 ? "w" : "l");
1446 break;
1448 case 'U':
1449 /* Similar, except do it from the mask. */
1450 if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0xff)
1451 fprintf (file, "b");
1452 else if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0xffff)
1453 fprintf (file, "w");
1454 #if HOST_BITS_PER_WIDE_INT == 32
1455 else if (GET_CODE (x) == CONST_DOUBLE
1456 && CONST_DOUBLE_HIGH (x) == 0
1457 && CONST_DOUBLE_LOW (x) == -1)
1458 fprintf (file, "l");
1459 #else
1460 else if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0xffffffff)
1461 fprintf (file, "l");
1462 #endif
1463 else
1464 output_operand_lossage ("invalid %%U value");
1465 break;
1467 case 's':
1468 /* Write the constant value divided by 8. */
1469 if (GET_CODE (x) != CONST_INT
1470 && (unsigned HOST_WIDE_INT) INTVAL (x) >= 64
1471 && (INTVAL (x) & 7) != 8)
1472 output_operand_lossage ("invalid %%s value");
1474 fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x) / 8);
1475 break;
1477 case 'S':
1478 /* Same, except compute (64 - c) / 8 */
1480 if (GET_CODE (x) != CONST_INT
1481 && (unsigned HOST_WIDE_INT) INTVAL (x) >= 64
1482 && (INTVAL (x) & 7) != 8)
1483 output_operand_lossage ("invalid %%s value");
1485 fprintf (file, HOST_WIDE_INT_PRINT_DEC, (64 - INTVAL (x)) / 8);
1486 break;
1488 case 'C': case 'D': case 'c': case 'd':
1489 /* Write out comparison name. */
1491 enum rtx_code c = GET_CODE (x);
1493 if (GET_RTX_CLASS (c) != '<')
1494 output_operand_lossage ("invalid %%C value");
1496 if (code == 'D')
1497 c = reverse_condition (c);
1498 else if (code == 'c')
1499 c = swap_condition (c);
1500 else if (code == 'd')
1501 c = swap_condition (reverse_condition (c));
1503 if (c == LEU)
1504 fprintf (file, "ule");
1505 else if (c == LTU)
1506 fprintf (file, "ult");
1507 else
1508 fprintf (file, "%s", GET_RTX_NAME (c));
1510 break;
1512 case 'E':
1513 /* Write the divide or modulus operator. */
1514 switch (GET_CODE (x))
1516 case DIV:
1517 fprintf (file, "div%s", GET_MODE (x) == SImode ? "l" : "q");
1518 break;
1519 case UDIV:
1520 fprintf (file, "div%su", GET_MODE (x) == SImode ? "l" : "q");
1521 break;
1522 case MOD:
1523 fprintf (file, "rem%s", GET_MODE (x) == SImode ? "l" : "q");
1524 break;
1525 case UMOD:
1526 fprintf (file, "rem%su", GET_MODE (x) == SImode ? "l" : "q");
1527 break;
1528 default:
1529 output_operand_lossage ("invalid %%E value");
1530 break;
1532 break;
1534 case 'A':
1535 /* Write "_u" for unaligned access. */
1536 if (GET_CODE (x) == MEM && GET_CODE (XEXP (x, 0)) == AND)
1537 fprintf (file, "_u");
1538 break;
1540 case 0:
1541 if (GET_CODE (x) == REG)
1542 fprintf (file, "%s", reg_names[REGNO (x)]);
1543 else if (GET_CODE (x) == MEM)
1544 output_address (XEXP (x, 0));
1545 else
1546 output_addr_const (file, x);
1547 break;
1549 default:
1550 output_operand_lossage ("invalid %%xn code");
1554 /* Do what is necessary for `va_start'. The argument is ignored;
1555 We look at the current function to determine if stdarg or varargs
1556 is used and fill in an initial va_list. A pointer to this constructor
1557 is returned. */
1559 struct rtx_def *
1560 alpha_builtin_saveregs (arglist)
1561 tree arglist;
1563 rtx block, addr, dest, argsize;
1564 tree fntype = TREE_TYPE (current_function_decl);
1565 int stdarg = (TYPE_ARG_TYPES (fntype) != 0
1566 && (TREE_VALUE (tree_last (TYPE_ARG_TYPES (fntype)))
1567 != void_type_node));
1569 /* Compute the current position into the args, taking into account
1570 both registers and memory. Both of these are already included in
1571 NUM_ARGS. */
1573 argsize = GEN_INT (NUM_ARGS * UNITS_PER_WORD);
1575 /* For Unix, SETUP_INCOMING_VARARGS moves the starting address base up by 48,
1576 storing fp arg registers in the first 48 bytes, and the integer arg
1577 registers in the next 48 bytes. This is only done, however, if any
1578 integer registers need to be stored.
1580 If no integer registers need be stored, then we must subtract 48 in
1581 order to account for the integer arg registers which are counted in
1582 argsize above, but which are not actually stored on the stack. */
1584 if (TARGET_OPEN_VMS)
1585 addr = plus_constant (virtual_incoming_args_rtx,
1586 NUM_ARGS <= 5 + stdarg
1587 ? UNITS_PER_WORD : - 6 * UNITS_PER_WORD);
1588 else
1589 addr = (NUM_ARGS <= 5 + stdarg
1590 ? plus_constant (virtual_incoming_args_rtx,
1591 6 * UNITS_PER_WORD)
1592 : plus_constant (virtual_incoming_args_rtx,
1593 - (6 * UNITS_PER_WORD)));
1595 /* For VMS, we include the argsize, while on Unix, it's handled as
1596 a separate field. */
1597 if (TARGET_OPEN_VMS)
1598 addr = plus_constant (addr, INTVAL (argsize));
1600 addr = force_operand (addr, NULL_RTX);
1602 #ifdef POINTERS_EXTEND_UNSIGNED
1603 addr = convert_memory_address (ptr_mode, addr);
1604 #endif
1606 if (TARGET_OPEN_VMS)
1607 return addr;
1608 else
1610 /* Allocate the va_list constructor */
1611 block = assign_stack_local (BLKmode, 2 * UNITS_PER_WORD, BITS_PER_WORD);
1612 RTX_UNCHANGING_P (block) = 1;
1613 RTX_UNCHANGING_P (XEXP (block, 0)) = 1;
1615 /* Store the address of the first integer register in the __base
1616 member. */
1618 dest = change_address (block, ptr_mode, XEXP (block, 0));
1619 emit_move_insn (dest, addr);
1621 if (flag_check_memory_usage)
1622 emit_library_call (chkr_set_right_libfunc, 1, VOIDmode, 3,
1623 dest, ptr_mode,
1624 GEN_INT (GET_MODE_SIZE (ptr_mode)),
1625 TYPE_MODE (sizetype),
1626 GEN_INT (MEMORY_USE_RW),
1627 TYPE_MODE (integer_type_node));
1629 /* Store the argsize as the __va_offset member. */
1630 dest = change_address (block, TYPE_MODE (integer_type_node),
1631 plus_constant (XEXP (block, 0),
1632 POINTER_SIZE/BITS_PER_UNIT));
1633 emit_move_insn (dest, argsize);
1635 if (flag_check_memory_usage)
1636 emit_library_call (chkr_set_right_libfunc, 1, VOIDmode, 3,
1637 dest, ptr_mode,
1638 GEN_INT (GET_MODE_SIZE
1639 (TYPE_MODE (integer_type_node))),
1640 TYPE_MODE (sizetype),
1641 GEN_INT (MEMORY_USE_RW),
1642 TYPE_MODE (integer_type_node));
1644 /* Return the address of the va_list constructor, but don't put it in a
1645 register. Doing so would fail when not optimizing and produce worse
1646 code when optimizing. */
1647 return XEXP (block, 0);
1651 #if OPEN_VMS
1652 #define REG_PV 27
1653 #define REG_RA 26
1654 #else
1655 #define REG_RA 26
1656 #endif
1658 /* Find the current function's return address.
1660 ??? It would be better to arrange things such that if we would ordinarily
1661 have been a leaf function and we didn't spill the hard reg that we
1662 wouldn't have to save the register in the prolog. But it's not clear
1663 how to get the right information at the right time. */
1665 static rtx alpha_return_addr_rtx;
1668 alpha_return_addr ()
1670 rtx ret;
1672 if ((ret = alpha_return_addr_rtx) == NULL)
1674 alpha_return_addr_rtx = ret = gen_reg_rtx (Pmode);
1676 emit_insn_after (gen_rtx (SET, VOIDmode, ret,
1677 gen_rtx (REG, Pmode, REG_RA)),
1678 get_insns ());
1681 return ret;
1684 /* This page contains routines that are used to determine what the function
1685 prologue and epilogue code will do and write them out. */
1687 /* Compute the size of the save area in the stack. */
1689 #if OPEN_VMS
1691 /* These variables are used for communication between the following functions.
1692 They indicate various things about the current function being compiled
1693 that are used to tell what kind of prologue, epilogue and procedure
1694 descriptior to generate. */
1696 /* Nonzero if we need a stack procedure. */
1697 static int is_stack_procedure;
1699 /* Register number (either FP or SP) that is used to unwind the frame. */
1700 static int unwind_regno;
1702 /* Register number used to save FP. We need not have one for RA since
1703 we don't modify it for register procedures. This is only defined
1704 for register frame procedures. */
1705 static int save_fp_regno;
1707 /* Register number used to reference objects off our PV. */
1708 static int base_regno;
1710 /* Compute register masks for saved registers. */
1712 static void
1713 alpha_sa_mask (imaskP, fmaskP)
1714 unsigned long *imaskP;
1715 unsigned long *fmaskP;
1717 unsigned long imask = 0;
1718 unsigned long fmask = 0;
1719 int i;
1721 if (is_stack_procedure)
1722 imask |= (1L << HARD_FRAME_POINTER_REGNUM);
1724 /* One for every register we have to save. */
1726 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1727 if (! fixed_regs[i] && ! call_used_regs[i] && regs_ever_live[i])
1729 if (i < 32)
1730 imask |= (1L << i);
1731 else
1732 fmask |= (1L << (i - 32));
1735 *imaskP = imask;
1736 *fmaskP = fmask;
1738 return;
1742 alpha_sa_size ()
1744 int sa_size = 0;
1745 HOST_WIDE_INT stack_needed;
1746 int i;
1748 /* One for every register we have to save. */
1750 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1751 if (! fixed_regs[i] && ! call_used_regs[i] && regs_ever_live[i])
1752 sa_size++;
1754 /* Start by assuming we can use a register procedure if we don't make any
1755 calls (REG_RA not used) or need to save any registers and a stack
1756 procedure if we do. */
1757 is_stack_procedure = regs_ever_live[REG_RA] || sa_size != 0;
1759 /* Decide whether to refer to objects off our PV via FP or PV.
1760 If we need need FP for something else or if we receive a nonlocal
1761 goto (which expects PV to contain the value), we must use PV.
1762 Otherwise, start by assuming we can use FP. */
1763 base_regno = (frame_pointer_needed || current_function_has_nonlocal_label
1764 || is_stack_procedure
1765 || current_function_outgoing_args_size
1766 ? REG_PV : HARD_FRAME_POINTER_REGNUM);
1768 /* If we want to copy PV into FP, we need to find some register in which to
1769 save FP. */
1771 save_fp_regno = -1;
1773 if (base_regno == HARD_FRAME_POINTER_REGNUM)
1774 for (i = 0; i < 32; i++)
1775 if (! fixed_regs[i] && call_used_regs[i] && ! regs_ever_live[i])
1776 save_fp_regno = i;
1778 if (save_fp_regno == -1)
1779 base_regno = REG_PV, is_stack_procedure = 1;
1781 /* Stack unwinding should be done via FP unless we use it for PV. */
1782 unwind_regno
1783 = base_regno == REG_PV ? HARD_FRAME_POINTER_REGNUM : STACK_POINTER_REGNUM;
1785 /* If this is a stack procedure, allow space for saving FP and RA. */
1786 if (is_stack_procedure)
1787 sa_size += 2;
1789 return sa_size * 8;
1793 alpha_pv_save_size ()
1795 alpha_sa_size ();
1796 return is_stack_procedure ? 8 : 0;
1800 alpha_using_fp ()
1802 alpha_sa_size ();
1803 return unwind_regno == HARD_FRAME_POINTER_REGNUM;
1806 #else /* ! OPEN_VMS */
1809 alpha_sa_size ()
1811 int size = 0;
1812 int i;
1814 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1815 if (! fixed_regs[i] && ! call_used_regs[i] && regs_ever_live[i])
1816 size++;
1818 /* If some registers were saved but not reg 26, reg 26 must also
1819 be saved, so leave space for it. */
1820 if (size != 0 && ! regs_ever_live[26])
1821 size++;
1823 /* Our size must be even (multiple of 16 bytes). */
1824 if (size & 1)
1825 size ++;
1827 return size * 8;
1830 #endif /* ! OPEN_VMS */
1832 /* Return 1 if this function can directly return via $26. */
1835 direct_return ()
1837 return (! TARGET_OPEN_VMS && reload_completed && alpha_sa_size () == 0
1838 && get_frame_size () == 0
1839 && current_function_outgoing_args_size == 0
1840 && current_function_pretend_args_size == 0);
1843 /* Write a version stamp. Don't write anything if we are running as a
1844 cross-compiler. Otherwise, use the versions in /usr/include/stamp.h. */
1846 #if !defined(CROSS_COMPILE) && !defined(_WIN32) && !defined(__linux__) && !defined(VMS)
1847 #include <stamp.h>
1848 #endif
1850 void
1851 alpha_write_verstamp (file)
1852 FILE *file;
1854 #ifdef MS_STAMP
1855 fprintf (file, "\t.verstamp %d %d\n", MS_STAMP, LS_STAMP);
1856 #endif
1859 /* Write code to add constant C to register number IN_REG (possibly 31)
1860 and put the result into OUT_REG. Use TEMP_REG as a scratch register;
1861 usually this will be OUT_REG, but should not be if OUT_REG is
1862 STACK_POINTER_REGNUM, since it must be updated in a single instruction.
1863 Write the code to FILE. */
1865 static void
1866 add_long_const (file, c, in_reg, out_reg, temp_reg)
1867 FILE *file;
1868 HOST_WIDE_INT c;
1869 int in_reg, out_reg, temp_reg;
1871 HOST_WIDE_INT low = (c & 0xffff) - 2 * (c & 0x8000);
1872 HOST_WIDE_INT tmp1 = c - low;
1873 HOST_WIDE_INT high = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
1874 HOST_WIDE_INT extra = 0;
1876 /* We don't have code to write out constants larger than 32 bits. */
1877 #if HOST_BITS_PER_LONG_INT == 64
1878 if ((unsigned HOST_WIDE_INT) c >> 32 != 0)
1879 abort ();
1880 #endif
1882 /* If HIGH will be interpreted as negative, we must adjust it to do two
1883 ldha insns. Note that we will never be building a negative constant
1884 here. */
1886 if (high & 0x8000)
1888 extra = 0x4000;
1889 tmp1 -= 0x40000000;
1890 high = ((tmp1 >> 16) & 0xffff) - 2 * ((tmp1 >> 16) & 0x8000);
1893 if (low != 0)
1895 int result_reg = (extra == 0 && high == 0) ? out_reg : temp_reg;
1897 if (low >= 0 && low < 255)
1898 fprintf (file, "\taddq $%d,%d,$%d\n", in_reg, low, result_reg);
1899 else
1900 fprintf (file, "\tlda $%d,%d($%d)\n", result_reg, low, in_reg);
1902 in_reg = result_reg;
1905 if (extra)
1907 int result_reg = (high == 0) ? out_reg : temp_reg;
1909 fprintf (file, "\tldah $%d,%d($%d)\n", result_reg, extra, in_reg);
1910 in_reg = result_reg;
1913 if (high)
1914 fprintf (file, "\tldah $%d,%d($%d)\n", out_reg, high, in_reg);
1917 /* Write function prologue. */
1919 #if OPEN_VMS
1921 /* On vms we have two kinds of functions:
1923 - stack frame (PROC_STACK)
1924 these are 'normal' functions with local vars and which are
1925 calling other functions
1926 - register frame (PROC_REGISTER)
1927 keeps all data in registers, needs no stack
1929 We must pass this to the assembler so it can generate the
1930 proper pdsc (procedure descriptor)
1931 This is done with the '.pdesc' command.
1933 size is the stack size needed for local variables. */
1935 void
1936 output_prolog (file, size)
1937 FILE *file;
1938 HOST_WIDE_INT size;
1940 unsigned long imask = 0;
1941 unsigned long fmask = 0;
1942 /* Stack space needed for pushing registers clobbered by us. */
1943 HOST_WIDE_INT sa_size;
1944 /* Complete stack size needed. */
1945 HOST_WIDE_INT frame_size;
1946 /* Offset from base reg to register save area. */
1947 int rsa_offset = 8;
1948 /* Offset during register save. */
1949 int reg_offset;
1950 /* Label for the procedure entry. */
1951 char *entry_label = (char *) alloca (strlen (alpha_function_name) + 5);
1952 int i;
1954 sa_size = alpha_sa_size ();
1955 frame_size
1956 = ALPHA_ROUND (sa_size
1957 + (is_stack_procedure ? 8 : 0)
1958 + size + current_function_pretend_args_size);
1960 /* Issue function start and label. */
1961 fprintf (file, "\t.ent ");
1962 assemble_name (file, alpha_function_name);
1963 fprintf (file, "\n");
1964 sprintf (entry_label, "%s..en", alpha_function_name);
1965 ASM_OUTPUT_LABEL (file, entry_label);
1966 inside_function = TRUE;
1968 fprintf (file, "\t.base $%d\n", base_regno);
1970 /* Calculate register masks for clobbered registers. */
1972 if (is_stack_procedure)
1973 alpha_sa_mask (&imask, &fmask);
1975 /* Adjust the stack by the frame size. If the frame size is > 4096
1976 bytes, we need to be sure we probe somewhere in the first and last
1977 4096 bytes (we can probably get away without the latter test) and
1978 every 8192 bytes in between. If the frame size is > 32768, we
1979 do this in a loop. Otherwise, we generate the explicit probe
1980 instructions.
1982 Note that we are only allowed to adjust sp once in the prologue. */
1984 if (frame_size < 32768)
1986 if (frame_size > 4096)
1988 int probed = 4096;
1990 fprintf (file, "\tstq $31,-%d($30)\n", probed);
1992 while (probed + 8192 < frame_size)
1993 fprintf (file, "\tstq $31,-%d($30)\n", probed += 8192);
1995 /* We only have to do this probe if we aren't saving registers. */
1996 if (sa_size == 0 && probed + 4096 < frame_size)
1997 fprintf (file, "\tstq $31,-%d($30)\n", frame_size);
2000 if (frame_size != 0)
2001 fprintf (file, "\tlda $30,-%d($30)\n", frame_size);
2003 else
2005 /* Here we generate code to set R4 to SP + 4096 and set R23 to the
2006 number of 8192 byte blocks to probe. We then probe each block
2007 in the loop and then set SP to the proper location. If the
2008 amount remaining is > 4096, we have to do one more probe if we
2009 are not saving any registers. */
2011 HOST_WIDE_INT blocks = (frame_size + 4096) / 8192;
2012 HOST_WIDE_INT leftover = frame_size + 4096 - blocks * 8192;
2014 add_long_const (file, blocks, 31, 23, 23);
2016 fprintf (file, "\tlda $22,4096($30)\n");
2018 assemble_name (file, alpha_function_name);
2019 fprintf (file, "..sc:\n");
2021 fprintf (file, "\tstq $31,-8192($22)\n");
2022 fprintf (file, "\tsubq $23,1,$23\n");
2023 fprintf (file, "\tlda $22,-8192($22)\n");
2025 fprintf (file, "\tbne $23,");
2026 assemble_name (file, alpha_function_name);
2027 fprintf (file, "..sc\n");
2029 if (leftover > 4096 && sa_size == 0)
2030 fprintf (file, "\tstq $31,-%d($22)\n", leftover);
2032 fprintf (file, "\tlda $30,-%d($22)\n", leftover);
2035 if (is_stack_procedure)
2037 int reg_offset = rsa_offset;
2039 /* Store R26 (RA) first. */
2040 fprintf (file, "\tstq $26,%d($30)\n", reg_offset);
2041 reg_offset += 8;
2043 /* Store integer regs. according to mask. */
2044 for (i = 0; i < 32; i++)
2045 if (imask & (1L<<i))
2047 fprintf (file, "\tstq $%d,%d($30)\n", i, reg_offset);
2048 reg_offset += 8;
2051 /* Print the register mask and do floating-point saves. */
2053 if (imask)
2054 fprintf (file, "\t.mask 0x%x,0\n", imask);
2056 for (i = 0; i < 32; i++)
2058 if (fmask & (1L << i))
2060 fprintf (file, "\tstt $f%d,%d($30)\n", i, reg_offset);
2061 reg_offset += 8;
2065 /* Print the floating-point mask, if we've saved any fp register. */
2066 if (fmask)
2067 fprintf (file, "\t.fmask 0x%x,0\n", fmask);
2069 fprintf (file, "\tstq $27,0($30)\n");
2071 else
2073 fprintf (file, "\t.fp_save $%d\n", save_fp_regno);
2074 fprintf (file, "\tbis $%d,$%d,$%d\n", HARD_FRAME_POINTER_REGNUM,
2075 HARD_FRAME_POINTER_REGNUM, save_fp_regno);
2078 if (base_regno != REG_PV)
2079 fprintf (file, "\tbis $%d,$%d,$%d\n", REG_PV, REG_PV, base_regno);
2081 if (unwind_regno == HARD_FRAME_POINTER_REGNUM)
2082 fprintf (file, "\tbis $%d,$%d,$%d\n", STACK_POINTER_REGNUM,
2083 STACK_POINTER_REGNUM, HARD_FRAME_POINTER_REGNUM);
2085 /* Describe our frame. */
2086 fprintf (file, "\t.frame $%d,%d,$26,%d\n",
2087 unwind_regno, frame_size, rsa_offset);
2089 /* If we have to allocate space for outgoing args, do it now. */
2090 if (current_function_outgoing_args_size != 0)
2091 fprintf (file, "\tlda $%d,%d($%d)\n", STACK_POINTER_REGNUM,
2092 - ALPHA_ROUND (current_function_outgoing_args_size),
2093 HARD_FRAME_POINTER_REGNUM);
2095 fprintf (file, "\t.prologue\n");
2097 link_section ();
2098 fprintf (file, "\t.align 3\n");
2099 ASM_OUTPUT_LABEL (file, alpha_function_name);
2100 fprintf (file, "\t.pdesc ");
2101 assemble_name (file, alpha_function_name);
2102 fprintf (file, "..en,%s\n", is_stack_procedure ? "stack" : "reg");
2103 alpha_need_linkage (alpha_function_name, 1);
2104 text_section ();
2106 return;
2109 /* Write function epilogue. */
2111 void
2112 output_epilog (file, size)
2113 FILE *file;
2114 int size;
2116 unsigned long imask = 0;
2117 unsigned long fmask = 0;
2118 /* Stack space needed for pushing registers clobbered by us. */
2119 HOST_WIDE_INT sa_size = alpha_sa_size ();
2120 /* Complete stack size needed. */
2121 HOST_WIDE_INT frame_size
2122 = ALPHA_ROUND (sa_size
2123 + (is_stack_procedure ? 8 : 0)
2124 + size + current_function_pretend_args_size);
2125 int i;
2126 rtx insn = get_last_insn ();
2128 /* If the last insn was a BARRIER, we don't have to write anything except
2129 the .end pseudo-op. */
2131 if (GET_CODE (insn) == NOTE)
2132 insn = prev_nonnote_insn (insn);
2134 if (insn == 0 || GET_CODE (insn) != BARRIER)
2136 /* Restore clobbered registers, load FP last. */
2138 if (is_stack_procedure)
2140 int rsa_offset = 8;
2141 int reg_offset;
2142 int fp_offset;
2144 if (unwind_regno == HARD_FRAME_POINTER_REGNUM)
2145 fprintf (file, "\tbis $%d,$%d,$%d\n", HARD_FRAME_POINTER_REGNUM,
2146 HARD_FRAME_POINTER_REGNUM, STACK_POINTER_REGNUM);
2148 alpha_sa_mask (&imask, &fmask);
2150 /* Start reloading registers after RA. */
2151 reg_offset = rsa_offset + 8;
2153 for (i = 0; i < 32; i++)
2154 if (imask & (1L<<i))
2156 if (i == HARD_FRAME_POINTER_REGNUM)
2157 fp_offset = reg_offset;
2158 else
2159 fprintf (file, "\tldq $%d,%d($30)\n",
2160 i, reg_offset);
2161 reg_offset += 8;
2164 for (i = 0; i < 32; i++)
2165 if (fmask & (1L << i))
2167 fprintf (file, "\tldt $f%d,%d($30)\n", i, reg_offset);
2168 reg_offset += 8;
2171 /* Restore R26 (RA). */
2172 fprintf (file, "\tldq $26,%d($30)\n", rsa_offset);
2174 /* Restore R29 (FP). */
2175 fprintf (file, "\tldq $29,%d($30)\n", fp_offset);
2177 else
2178 fprintf (file, "\tbis $%d,$%d,$%d\n", save_fp_regno, save_fp_regno,
2179 HARD_FRAME_POINTER_REGNUM);
2181 if (frame_size != 0)
2183 if (frame_size < 32768)
2184 fprintf (file, "\tlda $30,%d($30)\n", frame_size);
2185 else
2187 long high = frame_size >> 16;
2188 long low = frame_size & 0xffff;
2189 if (low & 0x8000)
2191 high++;
2192 low = -32768 + (low & 0x7fff);
2194 fprintf (file, "\tldah $2,%ld($31)\n", high);
2195 fprintf (file, "\tlda $2,%ld($2)\n", low);
2196 fprintf (file, "\taddq $30,$2,$30\n");
2200 /* Finally return to the caller. */
2201 fprintf (file, "\tret $31,($26),1\n");
2204 /* End the function. */
2205 fprintf (file, "\t.end ");
2206 assemble_name (file, alpha_function_name);
2207 fprintf (file, "\n");
2208 inside_function = FALSE;
2210 /* Show that we know this function if it is called again. */
2211 SYMBOL_REF_FLAG (XEXP (DECL_RTL (current_function_decl), 0)) = 1;
2213 alpha_return_addr_rtx = 0;
2217 vms_valid_decl_attribute_p (decl, attributes, identifier, args)
2218 tree decl;
2219 tree attributes;
2220 tree identifier;
2221 tree args;
2223 if (is_attribute_p ("overlaid", identifier))
2224 return (args == NULL_TREE);
2227 #else /* !OPEN_VMS */
2229 void
2230 output_prolog (file, size)
2231 FILE *file;
2232 int size;
2234 HOST_WIDE_INT out_args_size
2235 = ALPHA_ROUND (current_function_outgoing_args_size);
2236 HOST_WIDE_INT sa_size = alpha_sa_size ();
2237 HOST_WIDE_INT frame_size
2238 = (out_args_size + sa_size
2239 + ALPHA_ROUND (size + current_function_pretend_args_size));
2240 HOST_WIDE_INT reg_offset = out_args_size;
2241 HOST_WIDE_INT start_reg_offset = reg_offset;
2242 HOST_WIDE_INT actual_start_reg_offset = start_reg_offset;
2243 int int_reg_save_area_size = 0;
2244 rtx insn;
2245 unsigned reg_mask = 0;
2246 int i;
2248 /* Ecoff can handle multiple .file directives, so put out file and lineno.
2249 We have to do that before the .ent directive as we cannot switch
2250 files within procedures with native ecoff because line numbers are
2251 linked to procedure descriptors.
2252 Outputting the lineno helps debugging of one line functions as they
2253 would otherwise get no line number at all. Please note that we would
2254 like to put out last_linenum from final.c, but it is not accessible. */
2256 if (write_symbols == SDB_DEBUG)
2258 ASM_OUTPUT_SOURCE_FILENAME (file,
2259 DECL_SOURCE_FILE (current_function_decl));
2260 if (debug_info_level != DINFO_LEVEL_TERSE)
2261 ASM_OUTPUT_SOURCE_LINE (file,
2262 DECL_SOURCE_LINE (current_function_decl));
2265 /* The assembly language programmer's guide states that the second argument
2266 to the .ent directive, the lex_level, is ignored by the assembler,
2267 so we might as well omit it. */
2269 if (!flag_inhibit_size_directive)
2271 fprintf (file, "\t.ent ");
2272 assemble_name (file, alpha_function_name);
2273 fprintf (file, "\n");
2275 ASM_OUTPUT_LABEL (file, alpha_function_name);
2276 inside_function = TRUE;
2278 if (TARGET_IEEE_CONFORMANT && !flag_inhibit_size_directive)
2279 /* Set flags in procedure descriptor to request IEEE-conformant
2280 math-library routines. The value we set it to is PDSC_EXC_IEEE
2281 (/usr/include/pdsc.h). */
2282 fprintf (file, "\t.eflag 48\n");
2284 /* Set up offsets to alpha virtual arg/local debugging pointer. */
2286 alpha_auto_offset = -frame_size + current_function_pretend_args_size;
2287 alpha_arg_offset = -frame_size + 48;
2289 /* If we need a GP (we have a LDSYM insn or a CALL_INSN), load it first.
2290 Even if we are a static function, we still need to do this in case
2291 our address is taken and passed to something like qsort.
2293 We never need a GP for Windows/NT. */
2295 alpha_function_needs_gp = 0;
2297 #ifdef TARGET_PROFILING_NEEDS_GP
2298 if (profile_flag)
2299 alpha_function_needs_gp = 1;
2300 #endif
2302 for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
2303 if ((GET_CODE (insn) == CALL_INSN)
2304 || (GET_RTX_CLASS (GET_CODE (insn)) == 'i'
2305 && GET_CODE (PATTERN (insn)) != USE
2306 && GET_CODE (PATTERN (insn)) != CLOBBER
2307 && (get_attr_type (insn) == TYPE_LDSYM
2308 || get_attr_type (insn) == TYPE_ISUBR)))
2310 alpha_function_needs_gp = 1;
2311 break;
2314 if (TARGET_WINDOWS_NT == 0)
2316 if (alpha_function_needs_gp)
2317 fprintf (file, "\tldgp $29,0($27)\n");
2319 /* Put a label after the GP load so we can enter the function at it. */
2320 assemble_name (file, alpha_function_name);
2321 fprintf (file, "..ng:\n");
2324 /* Adjust the stack by the frame size. If the frame size is > 4096
2325 bytes, we need to be sure we probe somewhere in the first and last
2326 4096 bytes (we can probably get away without the latter test) and
2327 every 8192 bytes in between. If the frame size is > 32768, we
2328 do this in a loop. Otherwise, we generate the explicit probe
2329 instructions.
2331 Note that we are only allowed to adjust sp once in the prologue. */
2333 if (frame_size < 32768)
2335 if (frame_size > 4096)
2337 int probed = 4096;
2339 fprintf (file, "\tstq $31,-%d($30)\n", probed);
2341 while (probed + 8192 < frame_size)
2342 fprintf (file, "\tstq $31,-%d($30)\n", probed += 8192);
2344 /* We only have to do this probe if we aren't saving registers. */
2345 if (sa_size == 0 && probed + 4096 < frame_size)
2346 fprintf (file, "\tstq $31,-%d($30)\n", frame_size);
2349 if (frame_size != 0)
2350 fprintf (file, "\tlda $30,-%d($30)\n", frame_size);
2352 else
2354 /* Here we generate code to set R4 to SP + 4096 and set R5 to the
2355 number of 8192 byte blocks to probe. We then probe each block
2356 in the loop and then set SP to the proper location. If the
2357 amount remaining is > 4096, we have to do one more probe if we
2358 are not saving any registers. */
2360 HOST_WIDE_INT blocks = (frame_size + 4096) / 8192;
2361 HOST_WIDE_INT leftover = frame_size + 4096 - blocks * 8192;
2363 add_long_const (file, blocks, 31, 5, 5);
2365 fprintf (file, "\tlda $4,4096($30)\n");
2367 assemble_name (file, alpha_function_name);
2368 fprintf (file, "..sc:\n");
2370 fprintf (file, "\tstq $31,-8192($4)\n");
2371 fprintf (file, "\tsubq $5,1,$5\n");
2372 fprintf (file, "\tlda $4,-8192($4)\n");
2374 fprintf (file, "\tbne $5,");
2375 assemble_name (file, alpha_function_name);
2376 fprintf (file, "..sc\n");
2378 if (leftover > 4096 && sa_size == 0)
2379 fprintf (file, "\tstq $31,-%d($4)\n", leftover);
2381 fprintf (file, "\tlda $30,-%d($4)\n", leftover);
2384 /* Describe our frame. */
2385 if (!flag_inhibit_size_directive)
2387 fprintf (file, "\t.frame $%d,%d,$26,%d\n",
2388 (frame_pointer_needed
2389 ? HARD_FRAME_POINTER_REGNUM : STACK_POINTER_REGNUM),
2390 frame_size, current_function_pretend_args_size);
2393 /* Save register 26 if any other register needs to be saved. */
2394 if (sa_size != 0)
2396 reg_mask |= 1 << 26;
2397 fprintf (file, "\tstq $26,%d($30)\n", reg_offset);
2398 reg_offset += 8;
2399 int_reg_save_area_size += 8;
2402 /* Now save any other used integer registers required to be saved. */
2403 for (i = 0; i < 32; i++)
2404 if (! fixed_regs[i] && ! call_used_regs[i] && regs_ever_live[i] && i != 26)
2406 reg_mask |= 1 << i;
2407 fprintf (file, "\tstq $%d,%d($30)\n", i, reg_offset);
2408 reg_offset += 8;
2409 int_reg_save_area_size += 8;
2412 /* Print the register mask and do floating-point saves. */
2413 if (reg_mask && !flag_inhibit_size_directive)
2414 fprintf (file, "\t.mask 0x%x,%d\n", reg_mask,
2415 actual_start_reg_offset - frame_size);
2417 start_reg_offset = reg_offset;
2418 reg_mask = 0;
2420 for (i = 0; i < 32; i++)
2421 if (! fixed_regs[i + 32] && ! call_used_regs[i + 32]
2422 && regs_ever_live[i + 32])
2424 reg_mask |= 1 << i;
2425 fprintf (file, "\tstt $f%d,%d($30)\n", i, reg_offset);
2426 reg_offset += 8;
2429 /* Print the floating-point mask, if we've saved any fp register. */
2430 if (reg_mask && !flag_inhibit_size_directive)
2431 fprintf (file, "\t.fmask 0x%x,%d\n", reg_mask,
2432 actual_start_reg_offset - frame_size + int_reg_save_area_size);
2434 /* If we need a frame pointer, set it from the stack pointer. Note that
2435 this must always be the last instruction in the prologue. */
2436 if (frame_pointer_needed)
2437 fprintf (file, "\tbis $30,$30,$15\n");
2439 /* End the prologue and say if we used gp. */
2440 if (!flag_inhibit_size_directive)
2441 fprintf (file, "\t.prologue %d\n", alpha_function_needs_gp);
2444 /* Write function epilogue. */
2446 void
2447 output_epilog (file, size)
2448 FILE *file;
2449 int size;
2451 rtx insn = get_last_insn ();
2452 HOST_WIDE_INT out_args_size
2453 = ALPHA_ROUND (current_function_outgoing_args_size);
2454 HOST_WIDE_INT sa_size = alpha_sa_size ();
2455 HOST_WIDE_INT frame_size
2456 = (out_args_size + sa_size
2457 + ALPHA_ROUND (size + current_function_pretend_args_size));
2458 HOST_WIDE_INT reg_offset = out_args_size;
2459 HOST_WIDE_INT frame_size_from_reg_save = frame_size - reg_offset;
2460 int restore_fp
2461 = frame_pointer_needed && regs_ever_live[HARD_FRAME_POINTER_REGNUM];
2462 int i;
2464 /* If the last insn was a BARRIER, we don't have to write anything except
2465 the .end pseudo-op. */
2466 if (GET_CODE (insn) == NOTE)
2467 insn = prev_nonnote_insn (insn);
2468 if (insn == 0 || GET_CODE (insn) != BARRIER)
2470 int fp_offset = 0;
2472 final_prescan_insn (NULL_RTX, NULL_PTR, 0);
2474 /* If we have a frame pointer, restore SP from it. */
2475 if (frame_pointer_needed)
2476 fprintf (file, "\tbis $15,$15,$30\n");
2478 /* Restore all the registers, starting with the return address
2479 register. */
2480 if (sa_size != 0)
2482 fprintf (file, "\tldq $26,%d($30)\n", reg_offset);
2483 reg_offset += 8;
2486 /* Now restore any other used integer registers that that we saved,
2487 except for FP if it is being used as FP, since it must be
2488 restored last. */
2490 for (i = 0; i < 32; i++)
2491 if (! fixed_regs[i] && ! call_used_regs[i] && regs_ever_live[i]
2492 && i != 26)
2494 if (i == HARD_FRAME_POINTER_REGNUM && frame_pointer_needed)
2495 fp_offset = reg_offset;
2496 else
2497 fprintf (file, "\tldq $%d,%d($30)\n", i, reg_offset);
2498 reg_offset += 8;
2501 for (i = 0; i < 32; i++)
2502 if (! fixed_regs[i + 32] && ! call_used_regs[i + 32]
2503 && regs_ever_live[i + 32])
2505 fprintf (file, "\tldt $f%d,%d($30)\n", i, reg_offset);
2506 reg_offset += 8;
2509 /* If the stack size is large and we have a frame pointer, compute the
2510 size of the stack into a register because the old FP restore, stack
2511 pointer adjust, and return are required to be consecutive
2512 instructions. */
2513 if (frame_size > 32767 && restore_fp)
2514 add_long_const (file, frame_size, 31, 1, 1);
2516 /* If we needed a frame pointer and we have to restore it, do it
2517 now. This must be done in one instruction immediately
2518 before the SP update. */
2519 if (restore_fp && fp_offset)
2520 fprintf (file, "\tldq $15,%d($30)\n", fp_offset);
2522 /* Now update the stack pointer, if needed. Only one instruction must
2523 modify the stack pointer. It must be the last instruction in the
2524 sequence and must be an ADDQ or LDA instruction. If the frame
2525 pointer was loaded above, we may only put one instruction here. */
2527 if (frame_size > 32768 && restore_fp)
2528 fprintf (file, "\taddq $1,$30,$30\n");
2529 else
2530 add_long_const (file, frame_size, 30, 30, 1);
2532 /* Finally return to the caller. */
2533 fprintf (file, "\tret $31,($26),1\n");
2536 /* End the function. */
2537 if (!flag_inhibit_size_directive)
2539 fprintf (file, "\t.end ");
2540 assemble_name (file, alpha_function_name);
2541 fprintf (file, "\n");
2543 inside_function = FALSE;
2545 /* Show that we know this function if it is called again. */
2546 SYMBOL_REF_FLAG (XEXP (DECL_RTL (current_function_decl), 0)) = 1;
2548 alpha_return_addr_rtx = 0;
2550 #endif /* !OPEN_VMS */
2552 /* Debugging support. */
2554 #include "gstab.h"
2556 /* Count the number of sdb related labels are generated (to find block
2557 start and end boundaries). */
2559 int sdb_label_count = 0;
2561 /* Next label # for each statement. */
2563 static int sym_lineno = 0;
2565 /* Count the number of .file directives, so that .loc is up to date. */
2567 static int num_source_filenames = 0;
2569 /* Name of the file containing the current function. */
2571 static char *current_function_file = "";
2573 /* Offsets to alpha virtual arg/local debugging pointers. */
2575 long alpha_arg_offset;
2576 long alpha_auto_offset;
2578 /* Emit a new filename to a stream. */
2580 void
2581 alpha_output_filename (stream, name)
2582 FILE *stream;
2583 char *name;
2585 static int first_time = TRUE;
2586 char ltext_label_name[100];
2588 if (first_time)
2590 first_time = FALSE;
2591 ++num_source_filenames;
2592 current_function_file = name;
2593 fprintf (stream, "\t.file\t%d ", num_source_filenames);
2594 output_quoted_string (stream, name);
2595 fprintf (stream, "\n");
2596 if (!TARGET_GAS && write_symbols == DBX_DEBUG)
2597 fprintf (stream, "\t#@stabs\n");
2600 else if (write_symbols == DBX_DEBUG)
2602 ASM_GENERATE_INTERNAL_LABEL (ltext_label_name, "Ltext", 0);
2603 fprintf (stream, "%s ", ASM_STABS_OP);
2604 output_quoted_string (stream, name);
2605 fprintf (stream, ",%d,0,0,%s\n", N_SOL, &ltext_label_name[1]);
2608 else if (name != current_function_file
2609 && strcmp (name, current_function_file) != 0)
2611 if (inside_function && ! TARGET_GAS)
2612 fprintf (stream, "\t#.file\t%d ", num_source_filenames);
2613 else
2615 ++num_source_filenames;
2616 current_function_file = name;
2617 fprintf (stream, "\t.file\t%d ", num_source_filenames);
2620 output_quoted_string (stream, name);
2621 fprintf (stream, "\n");
2625 /* Emit a linenumber to a stream. */
2627 void
2628 alpha_output_lineno (stream, line)
2629 FILE *stream;
2630 int line;
2632 if (write_symbols == DBX_DEBUG)
2634 /* mips-tfile doesn't understand .stabd directives. */
2635 ++sym_lineno;
2636 fprintf (stream, "$LM%d:\n\t%s %d,0,%d,$LM%d\n",
2637 sym_lineno, ASM_STABN_OP, N_SLINE, line, sym_lineno);
2639 else
2640 fprintf (stream, "\n\t.loc\t%d %d\n", num_source_filenames, line);
2643 /* Structure to show the current status of registers and memory. */
2645 struct shadow_summary
2647 struct {
2648 unsigned long i : 32; /* Mask of int regs */
2649 unsigned long fp : 32; /* Mask of fp regs */
2650 unsigned long mem : 1; /* mem == imem | fpmem */
2651 } used, defd;
2654 /* Summary the effects of expression X on the machine. Update SUM, a pointer
2655 to the summary structure. SET is nonzero if the insn is setting the
2656 object, otherwise zero. */
2658 static void
2659 summarize_insn (x, sum, set)
2660 rtx x;
2661 struct shadow_summary *sum;
2662 int set;
2664 char *format_ptr;
2665 int i, j;
2667 if (x == 0)
2668 return;
2670 switch (GET_CODE (x))
2672 /* ??? Note that this case would be incorrect if the Alpha had a
2673 ZERO_EXTRACT in SET_DEST. */
2674 case SET:
2675 summarize_insn (SET_SRC (x), sum, 0);
2676 summarize_insn (SET_DEST (x), sum, 1);
2677 break;
2679 case CLOBBER:
2680 summarize_insn (XEXP (x, 0), sum, 1);
2681 break;
2683 case USE:
2684 summarize_insn (XEXP (x, 0), sum, 0);
2685 break;
2687 case PARALLEL:
2688 for (i = XVECLEN (x, 0) - 1; i >= 0; i--)
2689 summarize_insn (XVECEXP (x, 0, i), sum, 0);
2690 break;
2692 case REG:
2694 int regno = REGNO (x);
2695 unsigned long mask = 1UL << (regno % 32);
2697 if (regno == 31 || regno == 63)
2698 break;
2700 if (set)
2702 if (regno < 32)
2703 sum->defd.i |= mask;
2704 else
2705 sum->defd.fp |= mask;
2707 else
2709 if (regno < 32)
2710 sum->used.i |= mask;
2711 else
2712 sum->used.fp |= mask;
2715 break;
2717 case MEM:
2718 if (set)
2719 sum->defd.mem = 1;
2720 else
2721 sum->used.mem = 1;
2723 /* Find the regs used in memory address computation: */
2724 summarize_insn (XEXP (x, 0), sum, 0);
2725 break;
2727 case SUBREG:
2728 summarize_insn (SUBREG_REG (x), sum, 0);
2729 break;
2731 case CONST_INT: case CONST_DOUBLE:
2732 case SYMBOL_REF: case LABEL_REF: case CONST:
2733 break;
2735 /* Handle common unary and binary ops for efficiency. */
2736 case COMPARE: case PLUS: case MINUS: case MULT: case DIV:
2737 case MOD: case UDIV: case UMOD: case AND: case IOR:
2738 case XOR: case ASHIFT: case ROTATE: case ASHIFTRT: case LSHIFTRT:
2739 case ROTATERT: case SMIN: case SMAX: case UMIN: case UMAX:
2740 case NE: case EQ: case GE: case GT: case LE:
2741 case LT: case GEU: case GTU: case LEU: case LTU:
2742 summarize_insn (XEXP (x, 0), sum, 0);
2743 summarize_insn (XEXP (x, 1), sum, 0);
2744 break;
2746 case NEG: case NOT: case SIGN_EXTEND: case ZERO_EXTEND:
2747 case TRUNCATE: case FLOAT_EXTEND: case FLOAT_TRUNCATE: case FLOAT:
2748 case FIX: case UNSIGNED_FLOAT: case UNSIGNED_FIX: case ABS:
2749 case SQRT: case FFS:
2750 summarize_insn (XEXP (x, 0), sum, 0);
2751 break;
2753 default:
2754 format_ptr = GET_RTX_FORMAT (GET_CODE (x));
2755 for (i = GET_RTX_LENGTH (GET_CODE (x)) - 1; i >= 0; i--)
2756 switch (format_ptr[i])
2758 case 'e':
2759 summarize_insn (XEXP (x, i), sum, 0);
2760 break;
2762 case 'E':
2763 for (j = XVECLEN (x, i) - 1; j >= 0; j--)
2764 summarize_insn (XVECEXP (x, i, j), sum, 0);
2765 break;
2767 default:
2768 abort ();
2773 /* This function is executed just prior to the output of assembler code for
2774 INSN to modify the extracted operands so they will be output differently.
2776 OPVEC is the vector containing the operands extracted from INSN, and
2777 NOPERANDS is the number of elements of the vector which contain meaningful
2778 data for this insn. The contents of this vector are what will be used to
2779 convert the insn template into assembler code, so you can change the
2780 assembler output by changing the contents of the vector.
2782 We use this function to ensure a sufficient number of `trapb' instructions
2783 are in the code when the user requests code with a trap precision of
2784 functions or instructions.
2786 In naive mode, when the user requests a trap-precision of "instruction", a
2787 trapb is needed after every instruction that may generate a trap (and after
2788 jsr/bsr instructions, because called functions may import a trap from the
2789 caller). This ensures that the code is resumption safe but it is also slow.
2791 When optimizations are turned on, we delay issuing a trapb as long as
2792 possible. In this context, a trap shadow is the sequence of instructions
2793 that starts with a (potentially) trap generating instruction and extends to
2794 the next trapb or call_pal instruction (but GCC never generates call_pal by
2795 itself). We can delay (and therefore sometimes omit) a trapb subject to the
2796 following conditions:
2798 (a) On entry to the trap shadow, if any Alpha register or memory location
2799 contains a value that is used as an operand value by some instruction in
2800 the trap shadow (live on entry), then no instruction in the trap shadow
2801 may modify the register or memory location.
2803 (b) Within the trap shadow, the computation of the base register for a
2804 memory load or store instruction may not involve using the result
2805 of an instruction that might generate an UNPREDICTABLE result.
2807 (c) Within the trap shadow, no register may be used more than once as a
2808 destination register. (This is to make life easier for the trap-handler.)
2810 (d) The trap shadow may not include any branch instructions.
2814 void
2815 final_prescan_insn (insn, opvec, noperands)
2816 rtx insn;
2817 rtx *opvec;
2818 int noperands;
2820 static struct shadow_summary shadow = {0, 0, 0, 0, 0};
2822 #define CLOSE_SHADOW \
2823 do \
2825 fputs ("\ttrapb\n", asm_out_file); \
2826 trap_pending = 0; \
2827 bzero ((char *) &shadow, sizeof shadow); \
2829 while (0)
2831 if (alpha_tp == ALPHA_TP_PROG)
2832 return;
2834 if (trap_pending)
2835 switch (alpha_tp)
2837 case ALPHA_TP_FUNC:
2838 /* Generate one trapb before epilogue (indicated by INSN==0) */
2839 if (insn == 0)
2840 CLOSE_SHADOW;
2841 break;
2843 case ALPHA_TP_INSN:
2844 if (optimize && insn != 0)
2846 struct shadow_summary sum = {0, 0, 0};
2848 switch (GET_CODE(insn))
2850 case INSN:
2851 summarize_insn (PATTERN (insn), &sum, 0);
2853 if ((sum.defd.i & shadow.defd.i)
2854 || (sum.defd.fp & shadow.defd.fp))
2856 /* (c) would be violated */
2857 CLOSE_SHADOW;
2858 break;
2861 /* Combine shadow with summary of current insn: */
2862 shadow.used.i |= sum.used.i;
2863 shadow.used.fp |= sum.used.fp;
2864 shadow.used.mem |= sum.used.mem;
2865 shadow.defd.i |= sum.defd.i;
2866 shadow.defd.fp |= sum.defd.fp;
2867 shadow.defd.mem |= sum.defd.mem;
2869 if ((sum.defd.i & shadow.used.i)
2870 || (sum.defd.fp & shadow.used.fp)
2871 || (sum.defd.mem & shadow.used.mem))
2873 /* (a) would be violated (also takes care of (b)). */
2874 if (get_attr_trap (insn) == TRAP_YES
2875 && ((sum.defd.i & sum.used.i)
2876 || (sum.defd.fp & sum.used.fp)))
2877 abort ();
2879 CLOSE_SHADOW;
2880 break;
2882 break;
2884 case JUMP_INSN:
2885 case CALL_INSN:
2886 case CODE_LABEL:
2887 CLOSE_SHADOW;
2888 break;
2890 default:
2891 abort ();
2894 else
2895 CLOSE_SHADOW;
2896 break;
2899 if (insn != 0 && get_attr_trap (insn) == TRAP_YES)
2901 if (optimize && !trap_pending && GET_CODE (insn) == INSN)
2902 summarize_insn (PATTERN (insn), &shadow, 0);
2903 trap_pending = 1;
2907 /* Check a floating-point value for validity for a particular machine mode. */
2909 static char *float_strings[] =
2911 /* These are for FLOAT_VAX. */
2912 "1.70141173319264430e+38", /* 2^127 (2^24 - 1) / 2^24 */
2913 "-1.70141173319264430e+38",
2914 "2.93873587705571877e-39", /* 2^-128 */
2915 "-2.93873587705571877e-39",
2916 /* These are for the default broken IEEE mode, which traps
2917 on infinity or denormal numbers. */
2918 "3.402823466385288598117e+38", /* 2^128 (1 - 2^-24) */
2919 "-3.402823466385288598117e+38",
2920 "1.1754943508222875079687e-38", /* 2^-126 */
2921 "-1.1754943508222875079687e-38",
2924 static REAL_VALUE_TYPE float_values[8];
2925 static int inited_float_values = 0;
2928 check_float_value (mode, d, overflow)
2929 enum machine_mode mode;
2930 REAL_VALUE_TYPE *d;
2931 int overflow;
2934 if (TARGET_IEEE || TARGET_IEEE_CONFORMANT || TARGET_IEEE_WITH_INEXACT)
2935 return 0;
2937 if (inited_float_values == 0)
2939 int i;
2940 for (i = 0; i < 8; i++)
2941 float_values[i] = REAL_VALUE_ATOF (float_strings[i], DFmode);
2943 inited_float_values = 1;
2946 if (mode == SFmode)
2948 REAL_VALUE_TYPE r;
2949 REAL_VALUE_TYPE *fvptr;
2951 if (TARGET_FLOAT_VAX)
2952 fvptr = &float_values[0];
2953 else
2954 fvptr = &float_values[4];
2956 bcopy ((char *) d, (char *) &r, sizeof (REAL_VALUE_TYPE));
2957 if (REAL_VALUES_LESS (fvptr[0], r))
2959 bcopy ((char *) &fvptr[0], (char *) d,
2960 sizeof (REAL_VALUE_TYPE));
2961 return 1;
2963 else if (REAL_VALUES_LESS (r, fvptr[1]))
2965 bcopy ((char *) &fvptr[1], (char *) d,
2966 sizeof (REAL_VALUE_TYPE));
2967 return 1;
2969 else if (REAL_VALUES_LESS (dconst0, r)
2970 && REAL_VALUES_LESS (r, fvptr[2]))
2972 bcopy ((char *) &dconst0, (char *) d, sizeof (REAL_VALUE_TYPE));
2973 return 1;
2975 else if (REAL_VALUES_LESS (r, dconst0)
2976 && REAL_VALUES_LESS (fvptr[3], r))
2978 bcopy ((char *) &dconst0, (char *) d, sizeof (REAL_VALUE_TYPE));
2979 return 1;
2983 return 0;
2986 #if OPEN_VMS
2988 /* Return the VMS argument type corresponding to MODE. */
2990 enum avms_arg_type
2991 alpha_arg_type (mode)
2992 enum machine_mode mode;
2994 switch (mode)
2996 case SFmode:
2997 return TARGET_FLOAT_VAX ? FF : FS;
2998 case DFmode:
2999 return TARGET_FLOAT_VAX ? FD : FT;
3000 default:
3001 return I64;
3005 /* Return an rtx for an integer representing the VMS Argument Information
3006 register value. */
3008 struct rtx_def *
3009 alpha_arg_info_reg_val (cum)
3010 CUMULATIVE_ARGS cum;
3012 unsigned HOST_WIDE_INT regval = cum.num_args;
3013 int i;
3015 for (i = 0; i < 6; i++)
3016 regval |= ((int) cum.atypes[i]) << (i * 3 + 8);
3018 return GEN_INT (regval);
3021 /* Structure to collect function names for final output
3022 in link section. */
3024 enum links_kind {KIND_UNUSED, KIND_LOCAL, KIND_EXTERN};
3027 struct alpha_links {
3028 struct alpha_links *next;
3029 char *name;
3030 enum links_kind kind;
3033 static struct alpha_links *alpha_links_base = 0;
3035 /* Make (or fake) .linkage entry for function call.
3037 IS_LOCAL is 0 if name is used in call, 1 if name is used in definition. */
3039 void
3040 alpha_need_linkage (name, is_local)
3041 char *name;
3042 int is_local;
3044 rtx x;
3045 struct alpha_links *lptr, *nptr;
3047 if (name[0] == '*')
3048 name++;
3050 /* Is this name already defined ? */
3052 for (lptr = alpha_links_base; lptr; lptr = lptr->next)
3053 if (strcmp (lptr->name, name) == 0)
3055 if (is_local)
3057 /* Defined here but external assumed. */
3058 if (lptr->kind == KIND_EXTERN)
3059 lptr->kind = KIND_LOCAL;
3061 else
3063 /* Used here but unused assumed. */
3064 if (lptr->kind == KIND_UNUSED)
3065 lptr->kind = KIND_LOCAL;
3067 return;
3070 nptr = (struct alpha_links *) xmalloc (sizeof (struct alpha_links));
3071 nptr->next = alpha_links_base;
3072 nptr->name = xstrdup (name);
3074 /* Assume external if no definition. */
3075 nptr->kind = (is_local ? KIND_UNUSED : KIND_EXTERN);
3077 /* Ensure we have an IDENTIFIER so assemble_name can mark is used. */
3078 get_identifier (name);
3080 alpha_links_base = nptr;
3082 return;
3086 void
3087 alpha_write_linkage (stream)
3088 FILE *stream;
3090 struct alpha_links *lptr, *nptr;
3092 readonly_section ();
3094 fprintf (stream, "\t.align 3\n");
3096 for (lptr = alpha_links_base; lptr; lptr = nptr)
3098 nptr = lptr->next;
3100 if (lptr->kind == KIND_UNUSED
3101 || ! TREE_SYMBOL_REFERENCED (get_identifier (lptr->name)))
3102 continue;
3104 fprintf (stream, "%s..lk:\n", lptr->name);
3105 if (lptr->kind == KIND_LOCAL)
3107 /* Local and used, build linkage pair. */
3108 fprintf (stream, "\t.quad %s..en\n", lptr->name);
3109 fprintf (stream, "\t.quad %s\n", lptr->name);
3111 else
3112 /* External and used, request linkage pair. */
3113 fprintf (stream, "\t.linkage %s\n", lptr->name);
3117 #else
3119 void
3120 alpha_need_linkage (name, is_local)
3121 char *name;
3122 int is_local;
3126 #endif /* OPEN_VMS */