1 /* Subroutines for gcc2 for pdp11.
2 Copyright (C) 1994-2015 Free Software Foundation, Inc.
3 Contributed by Michael K. Gschwind (mike@vlsivie.tuwien.ac.at).
5 This file is part of GCC.
7 GCC 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 3, or (at your option)
12 GCC 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 GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
23 #include "coretypes.h"
30 #include "insn-config.h"
31 #include "conditions.h"
33 #include "insn-attr.h"
36 #include "stor-layout.h"
46 #include "diagnostic-core.h"
53 #include "cfgcleanup.h"
58 /* This file should be included last. */
59 #include "target-def.h"
61 /* this is the current value returned by the macro FIRST_PARM_OFFSET
63 int current_first_parm_offset
;
65 /* Routines to encode/decode pdp11 floats */
66 static void encode_pdp11_f (const struct real_format
*fmt
,
67 long *, const REAL_VALUE_TYPE
*);
68 static void decode_pdp11_f (const struct real_format
*,
69 REAL_VALUE_TYPE
*, const long *);
70 static void encode_pdp11_d (const struct real_format
*fmt
,
71 long *, const REAL_VALUE_TYPE
*);
72 static void decode_pdp11_d (const struct real_format
*,
73 REAL_VALUE_TYPE
*, const long *);
75 /* These two are taken from the corresponding vax descriptors
76 in real.c, changing only the encode/decode routine pointers. */
77 const struct real_format pdp11_f_format
=
99 const struct real_format pdp11_d_format
=
122 encode_pdp11_f (const struct real_format
*fmt ATTRIBUTE_UNUSED
, long *buf
,
123 const REAL_VALUE_TYPE
*r
)
125 (*vax_f_format
.encode
) (fmt
, buf
, r
);
126 buf
[0] = ((buf
[0] >> 16) & 0xffff) | ((buf
[0] & 0xffff) << 16);
130 decode_pdp11_f (const struct real_format
*fmt ATTRIBUTE_UNUSED
,
131 REAL_VALUE_TYPE
*r
, const long *buf
)
134 tbuf
= ((buf
[0] >> 16) & 0xffff) | ((buf
[0] & 0xffff) << 16);
135 (*vax_f_format
.decode
) (fmt
, r
, &tbuf
);
139 encode_pdp11_d (const struct real_format
*fmt ATTRIBUTE_UNUSED
, long *buf
,
140 const REAL_VALUE_TYPE
*r
)
142 (*vax_d_format
.encode
) (fmt
, buf
, r
);
143 buf
[0] = ((buf
[0] >> 16) & 0xffff) | ((buf
[0] & 0xffff) << 16);
144 buf
[1] = ((buf
[1] >> 16) & 0xffff) | ((buf
[1] & 0xffff) << 16);
148 decode_pdp11_d (const struct real_format
*fmt ATTRIBUTE_UNUSED
,
149 REAL_VALUE_TYPE
*r
, const long *buf
)
152 tbuf
[0] = ((buf
[0] >> 16) & 0xffff) | ((buf
[0] & 0xffff) << 16);
153 tbuf
[1] = ((buf
[1] >> 16) & 0xffff) | ((buf
[1] & 0xffff) << 16);
154 (*vax_d_format
.decode
) (fmt
, r
, tbuf
);
157 /* This is where the condition code register lives. */
158 /* rtx cc0_reg_rtx; - no longer needed? */
160 static const char *singlemove_string (rtx
*);
161 static bool pdp11_assemble_integer (rtx
, unsigned int, int);
162 static bool pdp11_rtx_costs (rtx
, machine_mode
, int, int, int *, bool);
163 static bool pdp11_return_in_memory (const_tree
, const_tree
);
164 static rtx
pdp11_function_value (const_tree
, const_tree
, bool);
165 static rtx
pdp11_libcall_value (machine_mode
, const_rtx
);
166 static bool pdp11_function_value_regno_p (const unsigned int);
167 static void pdp11_trampoline_init (rtx
, tree
, rtx
);
168 static rtx
pdp11_function_arg (cumulative_args_t
, machine_mode
,
170 static void pdp11_function_arg_advance (cumulative_args_t
,
171 machine_mode
, const_tree
, bool);
172 static void pdp11_conditional_register_usage (void);
173 static bool pdp11_legitimate_constant_p (machine_mode
, rtx
);
175 static bool pdp11_scalar_mode_supported_p (machine_mode
);
177 /* Initialize the GCC target structure. */
178 #undef TARGET_ASM_BYTE_OP
179 #define TARGET_ASM_BYTE_OP NULL
180 #undef TARGET_ASM_ALIGNED_HI_OP
181 #define TARGET_ASM_ALIGNED_HI_OP NULL
182 #undef TARGET_ASM_ALIGNED_SI_OP
183 #define TARGET_ASM_ALIGNED_SI_OP NULL
184 #undef TARGET_ASM_INTEGER
185 #define TARGET_ASM_INTEGER pdp11_assemble_integer
187 #undef TARGET_ASM_OPEN_PAREN
188 #define TARGET_ASM_OPEN_PAREN "["
189 #undef TARGET_ASM_CLOSE_PAREN
190 #define TARGET_ASM_CLOSE_PAREN "]"
192 #undef TARGET_RTX_COSTS
193 #define TARGET_RTX_COSTS pdp11_rtx_costs
195 #undef TARGET_FUNCTION_ARG
196 #define TARGET_FUNCTION_ARG pdp11_function_arg
197 #undef TARGET_FUNCTION_ARG_ADVANCE
198 #define TARGET_FUNCTION_ARG_ADVANCE pdp11_function_arg_advance
200 #undef TARGET_RETURN_IN_MEMORY
201 #define TARGET_RETURN_IN_MEMORY pdp11_return_in_memory
203 #undef TARGET_FUNCTION_VALUE
204 #define TARGET_FUNCTION_VALUE pdp11_function_value
205 #undef TARGET_LIBCALL_VALUE
206 #define TARGET_LIBCALL_VALUE pdp11_libcall_value
207 #undef TARGET_FUNCTION_VALUE_REGNO_P
208 #define TARGET_FUNCTION_VALUE_REGNO_P pdp11_function_value_regno_p
210 #undef TARGET_TRAMPOLINE_INIT
211 #define TARGET_TRAMPOLINE_INIT pdp11_trampoline_init
213 #undef TARGET_SECONDARY_RELOAD
214 #define TARGET_SECONDARY_RELOAD pdp11_secondary_reload
216 #undef TARGET_REGISTER_MOVE_COST
217 #define TARGET_REGISTER_MOVE_COST pdp11_register_move_cost
219 #undef TARGET_PREFERRED_RELOAD_CLASS
220 #define TARGET_PREFERRED_RELOAD_CLASS pdp11_preferred_reload_class
222 #undef TARGET_PREFERRED_OUTPUT_RELOAD_CLASS
223 #define TARGET_PREFERRED_OUTPUT_RELOAD_CLASS pdp11_preferred_output_reload_class
225 #undef TARGET_LEGITIMATE_ADDRESS_P
226 #define TARGET_LEGITIMATE_ADDRESS_P pdp11_legitimate_address_p
228 #undef TARGET_CONDITIONAL_REGISTER_USAGE
229 #define TARGET_CONDITIONAL_REGISTER_USAGE pdp11_conditional_register_usage
231 #undef TARGET_ASM_FUNCTION_SECTION
232 #define TARGET_ASM_FUNCTION_SECTION pdp11_function_section
234 #undef TARGET_PRINT_OPERAND
235 #define TARGET_PRINT_OPERAND pdp11_asm_print_operand
237 #undef TARGET_PRINT_OPERAND_PUNCT_VALID_P
238 #define TARGET_PRINT_OPERAND_PUNCT_VALID_P pdp11_asm_print_operand_punct_valid_p
240 #undef TARGET_LEGITIMATE_CONSTANT_P
241 #define TARGET_LEGITIMATE_CONSTANT_P pdp11_legitimate_constant_p
243 #undef TARGET_SCALAR_MODE_SUPPORTED_P
244 #define TARGET_SCALAR_MODE_SUPPORTED_P pdp11_scalar_mode_supported_p
246 /* A helper function to determine if REGNO should be saved in the
247 current function's stack frame. */
250 pdp11_saved_regno (unsigned regno
)
252 return !call_used_regs
[regno
] && df_regs_ever_live_p (regno
);
255 /* Expand the function prologue. */
258 pdp11_expand_prologue (void)
260 HOST_WIDE_INT fsize
= get_frame_size ();
262 rtx x
, via_ac
= NULL
;
264 /* If we are outputting code for main, the switch FPU to the
265 right mode if TARGET_FPU. */
266 if (MAIN_NAME_P (DECL_NAME (current_function_decl
)) && TARGET_FPU
)
268 emit_insn (gen_setd ());
269 emit_insn (gen_seti ());
272 if (frame_pointer_needed
)
274 x
= gen_rtx_PRE_DEC (Pmode
, stack_pointer_rtx
);
275 x
= gen_frame_mem (Pmode
, x
);
276 emit_move_insn (x
, hard_frame_pointer_rtx
);
278 emit_move_insn (hard_frame_pointer_rtx
, stack_pointer_rtx
);
284 emit_insn (gen_addhi3 (stack_pointer_rtx
, stack_pointer_rtx
,
287 /* Prevent frame references via the frame pointer from being
288 scheduled before the frame is allocated. */
289 if (frame_pointer_needed
)
290 emit_insn (gen_blockage ());
293 /* Save CPU registers. */
294 for (regno
= R0_REGNUM
; regno
<= PC_REGNUM
; regno
++)
295 if (pdp11_saved_regno (regno
)
296 && (regno
!= HARD_FRAME_POINTER_REGNUM
|| !frame_pointer_needed
))
298 x
= gen_rtx_PRE_DEC (Pmode
, stack_pointer_rtx
);
299 x
= gen_frame_mem (Pmode
, x
);
300 emit_move_insn (x
, gen_rtx_REG (Pmode
, regno
));
303 /* Save FPU registers. */
304 for (regno
= AC0_REGNUM
; regno
<= AC3_REGNUM
; regno
++)
305 if (pdp11_saved_regno (regno
))
307 x
= gen_rtx_PRE_DEC (Pmode
, stack_pointer_rtx
);
308 x
= gen_frame_mem (DFmode
, x
);
309 via_ac
= gen_rtx_REG (DFmode
, regno
);
310 emit_move_insn (x
, via_ac
);
313 /* ??? Maybe make ac4, ac5 call used regs?? */
314 for (regno
= AC4_REGNUM
; regno
<= AC5_REGNUM
; regno
++)
315 if (pdp11_saved_regno (regno
))
317 gcc_assert (via_ac
!= NULL
);
318 emit_move_insn (via_ac
, gen_rtx_REG (DFmode
, regno
));
320 x
= gen_rtx_PRE_DEC (Pmode
, stack_pointer_rtx
);
321 x
= gen_frame_mem (DFmode
, x
);
322 emit_move_insn (x
, via_ac
);
326 /* The function epilogue should not depend on the current stack pointer!
327 It should use the frame pointer only. This is mandatory because
328 of alloca; we also take advantage of it to omit stack adjustments
331 /* Maybe we can make leaf functions faster by switching to the
332 second register file - this way we don't have to save regs!
333 leaf functions are ~ 50% of all functions (dynamically!)
335 set/clear bit 11 (dec. 2048) of status word for switching register files -
336 but how can we do this? the pdp11/45 manual says bit may only
337 be set (p.24), but not cleared!
339 switching to kernel is probably more expensive, so we'll leave it
340 like this and not use the second set of registers...
342 maybe as option if you want to generate code for kernel mode? */
345 pdp11_expand_epilogue (void)
347 HOST_WIDE_INT fsize
= get_frame_size ();
349 rtx x
, reg
, via_ac
= NULL
;
351 if (pdp11_saved_regno (AC4_REGNUM
) || pdp11_saved_regno (AC5_REGNUM
))
353 /* Find a temporary with which to restore AC4/5. */
354 for (regno
= AC0_REGNUM
; regno
<= AC3_REGNUM
; regno
++)
355 if (pdp11_saved_regno (regno
))
357 via_ac
= gen_rtx_REG (DFmode
, regno
);
362 /* If possible, restore registers via pops. */
363 if (!frame_pointer_needed
|| crtl
->sp_is_unchanging
)
365 /* Restore registers via pops. */
367 for (regno
= AC5_REGNUM
; regno
>= AC0_REGNUM
; regno
--)
368 if (pdp11_saved_regno (regno
))
370 x
= gen_rtx_POST_INC (Pmode
, stack_pointer_rtx
);
371 x
= gen_frame_mem (DFmode
, x
);
372 reg
= gen_rtx_REG (DFmode
, regno
);
374 if (LOAD_FPU_REG_P (regno
))
375 emit_move_insn (reg
, x
);
378 emit_move_insn (via_ac
, x
);
379 emit_move_insn (reg
, via_ac
);
383 for (regno
= PC_REGNUM
; regno
>= R0_REGNUM
+ 2; regno
--)
384 if (pdp11_saved_regno (regno
)
385 && (regno
!= HARD_FRAME_POINTER_REGNUM
|| !frame_pointer_needed
))
387 x
= gen_rtx_POST_INC (Pmode
, stack_pointer_rtx
);
388 x
= gen_frame_mem (Pmode
, x
);
389 emit_move_insn (gen_rtx_REG (Pmode
, regno
), x
);
394 /* Restore registers via moves. */
395 /* ??? If more than a few registers need to be restored, it's smaller
396 to generate a pointer through which we can emit pops. Consider
397 that moves cost 2*NREG words and pops cost NREG+3 words. This
398 means that the crossover is NREG=3.
400 Possible registers to use are:
401 (1) The first call-saved general register. This register will
402 be restored with the last pop.
403 (2) R1, if it's not used as a return register.
404 (3) FP itself. This option may result in +4 words, since we
405 may need two add imm,rn instructions instead of just one.
406 This also has the downside that we're not representing
407 the unwind info in any way, so during the epilogue the
408 debugger may get lost. */
410 HOST_WIDE_INT ofs
= -pdp11_sp_frame_offset ();
412 for (regno
= AC5_REGNUM
; regno
>= AC0_REGNUM
; regno
--)
413 if (pdp11_saved_regno (regno
))
415 x
= plus_constant (Pmode
, hard_frame_pointer_rtx
, ofs
);
416 x
= gen_frame_mem (DFmode
, x
);
417 reg
= gen_rtx_REG (DFmode
, regno
);
419 if (LOAD_FPU_REG_P (regno
))
420 emit_move_insn (reg
, x
);
423 emit_move_insn (via_ac
, x
);
424 emit_move_insn (reg
, via_ac
);
429 for (regno
= PC_REGNUM
; regno
>= R0_REGNUM
+ 2; regno
--)
430 if (pdp11_saved_regno (regno
)
431 && (regno
!= HARD_FRAME_POINTER_REGNUM
|| !frame_pointer_needed
))
433 x
= plus_constant (Pmode
, hard_frame_pointer_rtx
, ofs
);
434 x
= gen_frame_mem (Pmode
, x
);
435 emit_move_insn (gen_rtx_REG (Pmode
, regno
), x
);
440 /* Deallocate the stack frame. */
443 /* Prevent frame references via any pointer from being
444 scheduled after the frame is deallocated. */
445 emit_insn (gen_blockage ());
447 if (frame_pointer_needed
)
449 /* We can deallocate the frame with a single move. */
450 emit_move_insn (stack_pointer_rtx
, hard_frame_pointer_rtx
);
453 emit_insn (gen_addhi3 (stack_pointer_rtx
, stack_pointer_rtx
,
457 if (frame_pointer_needed
)
459 x
= gen_rtx_POST_INC (Pmode
, stack_pointer_rtx
);
460 x
= gen_frame_mem (Pmode
, x
);
461 emit_move_insn (hard_frame_pointer_rtx
, x
);
464 emit_jump_insn (gen_return ());
467 /* Return the best assembler insn template
468 for moving operands[1] into operands[0] as a fullword. */
470 singlemove_string (rtx
*operands
)
472 if (operands
[1] != const0_rtx
)
479 /* Expand multi-word operands (SImode or DImode) into the 2 or 4
480 corresponding HImode operands. The number of operands is given
481 as the third argument, and the required order of the parts as
482 the fourth argument. */
484 pdp11_expand_operands (rtx
*operands
, rtx exops
[][2], int opcount
,
485 pdp11_action
*action
, pdp11_partorder order
)
487 int words
, op
, w
, i
, sh
;
488 pdp11_partorder useorder
;
489 bool sameoff
= false;
490 enum { REGOP
, OFFSOP
, MEMOP
, PUSHOP
, POPOP
, CNSTOP
, RNDOP
} optype
;
494 words
= GET_MODE_BITSIZE (GET_MODE (operands
[0])) / 16;
496 /* If either piece order is accepted and one is pre-decrement
497 while the other is post-increment, set order to be high order
498 word first. That will force the pre-decrement to be turned
499 into a pointer adjust, then offset addressing.
500 Otherwise, if either operand uses pre-decrement, that means
501 the order is low order first.
502 Otherwise, if both operands are registers and destination is
503 higher than source and they overlap, do low order word (highest
504 register number) first. */
508 if (!REG_P (operands
[0]) && !REG_P (operands
[1]) &&
509 !(CONSTANT_P (operands
[1]) ||
510 GET_CODE (operands
[1]) == CONST_DOUBLE
) &&
511 ((GET_CODE (XEXP (operands
[0], 0)) == POST_INC
&&
512 GET_CODE (XEXP (operands
[1], 0)) == PRE_DEC
) ||
513 (GET_CODE (XEXP (operands
[0], 0)) == PRE_DEC
&&
514 GET_CODE (XEXP (operands
[1], 0)) == POST_INC
)))
516 else if ((!REG_P (operands
[0]) &&
517 GET_CODE (XEXP (operands
[0], 0)) == PRE_DEC
) ||
518 (!REG_P (operands
[1]) &&
519 !(CONSTANT_P (operands
[1]) ||
520 GET_CODE (operands
[1]) == CONST_DOUBLE
) &&
521 GET_CODE (XEXP (operands
[1], 0)) == PRE_DEC
))
523 else if (REG_P (operands
[0]) && REG_P (operands
[1]) &&
524 REGNO (operands
[0]) > REGNO (operands
[1]) &&
525 REGNO (operands
[0]) < REGNO (operands
[1]) + words
)
528 /* Check for source == offset from register and dest == push of
529 the same register. In that case, we have to use the same
530 offset (the one for the low order word) for all words, because
531 the push increases the offset to each source word.
532 In theory there are other cases like this, for example dest == pop,
533 but those don't occur in real life so ignore those. */
534 if (GET_CODE (operands
[0]) == MEM
535 && GET_CODE (XEXP (operands
[0], 0)) == PRE_DEC
536 && REGNO (XEXP (XEXP (operands
[0], 0), 0)) == STACK_POINTER_REGNUM
537 && reg_overlap_mentioned_p (stack_pointer_rtx
, operands
[1]))
541 /* If the caller didn't specify order, use the one we computed,
542 or high word first if we don't care either. If the caller did
543 specify, verify we don't have a problem with that order.
544 (If it matters to the caller, constraints need to be used to
545 ensure this case doesn't occur). */
547 order
= (useorder
== either
) ? big
: useorder
;
549 gcc_assert (useorder
== either
|| useorder
== order
);
552 for (op
= 0; op
< opcount
; op
++)
554 /* First classify the operand. */
555 if (REG_P (operands
[op
]))
557 else if (CONSTANT_P (operands
[op
])
558 || GET_CODE (operands
[op
]) == CONST_DOUBLE
)
560 else if (GET_CODE (XEXP (operands
[op
], 0)) == POST_INC
)
562 else if (GET_CODE (XEXP (operands
[op
], 0)) == PRE_DEC
)
564 else if (!reload_in_progress
|| offsettable_memref_p (operands
[op
]))
566 else if (GET_CODE (operands
[op
]) == MEM
)
571 /* Check for the cases that the operand constraints are not
572 supposed to allow to happen. Return failure for such cases. */
577 action
[op
] = no_action
;
579 /* If the operand uses pre-decrement addressing but we
580 want to get the parts high order first,
581 decrement the former register explicitly
582 and change the operand into ordinary indexing. */
583 if (optype
== PUSHOP
&& order
== big
)
585 gcc_assert (action
!= NULL
);
586 action
[op
] = dec_before
;
587 operands
[op
] = gen_rtx_MEM (GET_MODE (operands
[op
]),
588 XEXP (XEXP (operands
[op
], 0), 0));
591 /* If the operand uses post-increment mode but we want
592 to get the parts low order first, change the operand
593 into ordinary indexing and remember to increment
594 the register explicitly when we're done. */
595 else if (optype
== POPOP
&& order
== little
)
597 gcc_assert (action
!= NULL
);
598 action
[op
] = inc_after
;
599 operands
[op
] = gen_rtx_MEM (GET_MODE (operands
[op
]),
600 XEXP (XEXP (operands
[op
], 0), 0));
604 if (GET_CODE (operands
[op
]) == CONST_DOUBLE
)
606 REAL_VALUE_FROM_CONST_DOUBLE (r
, operands
[op
]);
607 REAL_VALUE_TO_TARGET_DOUBLE (r
, sval
);
610 for (i
= 0; i
< words
; i
++)
619 /* Set the output operand to be word "w" of the input. */
621 exops
[i
][op
] = gen_rtx_REG (HImode
, REGNO (operands
[op
]) + w
);
622 else if (optype
== OFFSOP
)
623 exops
[i
][op
] = adjust_address (operands
[op
], HImode
, w
* 2);
624 else if (optype
== CNSTOP
)
626 if (GET_CODE (operands
[op
]) == CONST_DOUBLE
)
628 sh
= 16 - (w
& 1) * 16;
629 exops
[i
][op
] = gen_rtx_CONST_INT (HImode
, (sval
[w
/ 2] >> sh
) & 0xffff);
633 sh
= ((words
- 1 - w
) * 16);
634 exops
[i
][op
] = gen_rtx_CONST_INT (HImode
, trunc_int_for_mode (INTVAL(operands
[op
]) >> sh
, HImode
));
638 exops
[i
][op
] = operands
[op
];
644 /* Output assembler code to perform a multiple-word move insn
645 with operands OPERANDS. This moves 2 or 4 words depending
646 on the machine mode of the operands. */
649 output_move_multiple (rtx
*operands
)
652 pdp11_action action
[2];
655 words
= GET_MODE_BITSIZE (GET_MODE (operands
[0])) / 16;
657 pdp11_expand_operands (operands
, exops
, 2, action
, either
);
659 /* Check for explicit decrement before. */
660 if (action
[0] == dec_before
)
662 operands
[0] = XEXP (operands
[0], 0);
663 output_asm_insn ("sub $4,%0", operands
);
665 if (action
[1] == dec_before
)
667 operands
[1] = XEXP (operands
[1], 0);
668 output_asm_insn ("sub $4,%1", operands
);
672 for (i
= 0; i
< words
; i
++)
673 output_asm_insn (singlemove_string (exops
[i
]), exops
[i
]);
675 /* Check for increment after. */
676 if (action
[0] == inc_after
)
678 operands
[0] = XEXP (operands
[0], 0);
679 output_asm_insn ("add $4,%0", operands
);
681 if (action
[1] == inc_after
)
683 operands
[1] = XEXP (operands
[1], 0);
684 output_asm_insn ("add $4,%1", operands
);
690 /* Output an ascii string. */
692 output_ascii (FILE *file
, const char *p
, int size
)
696 /* This used to output .byte "string", which doesn't work with the UNIX
697 assembler and I think not with DEC ones either. */
698 fprintf (file
, "\t.byte ");
700 for (i
= 0; i
< size
; i
++)
702 register int c
= p
[i
];
705 fprintf (file
, "%#o", c
);
714 pdp11_asm_output_var (FILE *file
, const char *name
, int size
,
715 int align
, bool global
)
718 fprintf (file
, "\n\t.even\n");
721 fprintf (file
, ".globl ");
722 assemble_name (file
, name
);
724 fprintf (file
, "\n");
725 assemble_name (file
, name
);
726 fprintf (file
, ": .=.+ %#ho\n", (unsigned short)size
);
730 pdp11_asm_print_operand (FILE *file
, rtx x
, int code
)
737 else if (code
== '@')
744 else if (GET_CODE (x
) == REG
)
745 fprintf (file
, "%s", reg_names
[REGNO (x
)]);
746 else if (GET_CODE (x
) == MEM
)
747 output_address (XEXP (x
, 0));
748 else if (GET_CODE (x
) == CONST_DOUBLE
&& GET_MODE (x
) != SImode
)
750 REAL_VALUE_FROM_CONST_DOUBLE (r
, x
);
751 REAL_VALUE_TO_TARGET_DOUBLE (r
, sval
);
752 fprintf (file
, "$%#lo", sval
[0] >> 16);
757 output_addr_const_pdp11 (file
, x
);
762 pdp11_asm_print_operand_punct_valid_p (unsigned char c
)
764 return (c
== '#' || c
== '@');
768 print_operand_address (FILE *file
, register rtx addr
)
776 switch (GET_CODE (addr
))
783 addr
= XEXP (addr
, 0);
788 fprintf (file
, "(%s)", reg_names
[REGNO (addr
)]);
793 fprintf (file
, "-(%s)", reg_names
[REGNO (XEXP (addr
, 0))]);
798 fprintf (file
, "(%s)+", reg_names
[REGNO (XEXP (addr
, 0))]);
804 if (CONSTANT_ADDRESS_P (XEXP (addr
, 0))
805 || GET_CODE (XEXP (addr
, 0)) == MEM
)
807 offset
= XEXP (addr
, 0);
808 addr
= XEXP (addr
, 1);
810 else if (CONSTANT_ADDRESS_P (XEXP (addr
, 1))
811 || GET_CODE (XEXP (addr
, 1)) == MEM
)
813 offset
= XEXP (addr
, 1);
814 addr
= XEXP (addr
, 0);
816 if (GET_CODE (addr
) != PLUS
)
818 else if (GET_CODE (XEXP (addr
, 0)) == REG
)
820 breg
= XEXP (addr
, 0);
821 addr
= XEXP (addr
, 1);
823 else if (GET_CODE (XEXP (addr
, 1)) == REG
)
825 breg
= XEXP (addr
, 1);
826 addr
= XEXP (addr
, 0);
828 if (GET_CODE (addr
) == REG
)
830 gcc_assert (breg
== 0);
836 gcc_assert (addr
== 0);
840 output_addr_const_pdp11 (file
, addr
);
843 gcc_assert (GET_CODE (breg
) == REG
);
844 fprintf (file
, "(%s)", reg_names
[REGNO (breg
)]);
849 if (!again
&& GET_CODE (addr
) == CONST_INT
)
851 /* Absolute (integer number) address. */
852 if (!TARGET_UNIX_ASM
)
853 fprintf (file
, "@$");
855 output_addr_const_pdp11 (file
, addr
);
859 /* Target hook to assemble integer objects. We need to use the
860 pdp-specific version of output_addr_const. */
863 pdp11_assemble_integer (rtx x
, unsigned int size
, int aligned_p
)
869 fprintf (asm_out_file
, "\t.byte\t");
870 output_addr_const_pdp11 (asm_out_file
, GEN_INT (INTVAL (x
) & 0xff));
872 fprintf (asm_out_file
, " /* char */\n");
876 fprintf (asm_out_file
, TARGET_UNIX_ASM
? "\t" : "\t.word\t");
877 output_addr_const_pdp11 (asm_out_file
, x
);
878 fprintf (asm_out_file
, " /* short */\n");
881 return default_assemble_integer (x
, size
, aligned_p
);
885 /* register move costs, indexed by regs */
887 static const int move_costs
[N_REG_CLASSES
][N_REG_CLASSES
] =
889 /* NO MUL GEN LFPU NLFPU FPU ALL */
891 /* NO */ { 0, 0, 0, 0, 0, 0, 0},
892 /* MUL */ { 0, 2, 2, 22, 22, 22, 22},
893 /* GEN */ { 0, 2, 2, 22, 22, 22, 22},
894 /* LFPU */ { 0, 22, 22, 2, 2, 2, 22},
895 /* NLFPU */ { 0, 22, 22, 2, 10, 10, 22},
896 /* FPU */ { 0, 22, 22, 2, 10, 10, 22},
897 /* ALL */ { 0, 22, 22, 22, 22, 22, 22}
901 /* -- note that some moves are tremendously expensive,
902 because they require lots of tricks! do we have to
903 charge the costs incurred by secondary reload class
904 -- as we do here with 10 -- or not ? */
907 pdp11_register_move_cost (machine_mode mode ATTRIBUTE_UNUSED
,
908 reg_class_t c1
, reg_class_t c2
)
910 return move_costs
[(int)c1
][(int)c2
];
914 pdp11_rtx_costs (rtx x
, machine_mode mode
, int outer_code ATTRIBUTE_UNUSED
,
915 int opno ATTRIBUTE_UNUSED
, int *total
,
916 bool speed ATTRIBUTE_UNUSED
)
918 int code
= GET_CODE (x
);
923 if (INTVAL (x
) == 0 || INTVAL (x
) == -1 || INTVAL (x
) == 1)
933 /* Twice as expensive as REG. */
938 /* Twice (or 4 times) as expensive as 16 bit. */
943 /* ??? There is something wrong in MULT because MULT is not
944 as cheap as total = 2 even if we can shift! */
945 /* If optimizing for size make mult etc cheap, but not 1, so when
946 in doubt the faster insn is chosen. */
948 *total
= COSTS_N_INSNS (2);
950 *total
= COSTS_N_INSNS (11);
955 *total
= COSTS_N_INSNS (2);
957 *total
= COSTS_N_INSNS (25);
962 *total
= COSTS_N_INSNS (2);
964 *total
= COSTS_N_INSNS (26);
968 /* Equivalent to length, so same for optimize_size. */
969 *total
= COSTS_N_INSNS (3);
973 /* Only used for qi->hi. */
974 *total
= COSTS_N_INSNS (1);
979 *total
= COSTS_N_INSNS (1);
980 else if (mode
== SImode
)
981 *total
= COSTS_N_INSNS (6);
983 *total
= COSTS_N_INSNS (2);
990 *total
= COSTS_N_INSNS (1);
991 else if (mode
== QImode
)
993 if (GET_CODE (XEXP (x
, 1)) != CONST_INT
)
994 *total
= COSTS_N_INSNS (8); /* worst case */
996 *total
= COSTS_N_INSNS (INTVAL (XEXP (x
, 1)));
998 else if (mode
== HImode
)
1000 if (GET_CODE (XEXP (x
, 1)) == CONST_INT
)
1002 if (abs (INTVAL (XEXP (x
, 1))) == 1)
1003 *total
= COSTS_N_INSNS (1);
1005 *total
= COSTS_N_INSNS (2.5 + 0.5 * INTVAL (XEXP (x
, 1)));
1008 *total
= COSTS_N_INSNS (10); /* worst case */
1010 else if (mode
== SImode
)
1012 if (GET_CODE (XEXP (x
, 1)) == CONST_INT
)
1013 *total
= COSTS_N_INSNS (2.5 + 0.5 * INTVAL (XEXP (x
, 1)));
1014 else /* worst case */
1015 *total
= COSTS_N_INSNS (18);
1025 output_jump (enum rtx_code code
, int inv
, int length
)
1029 static char buf
[1000];
1030 const char *pos
, *neg
;
1032 if (cc_prev_status
.flags
& CC_NO_OVERFLOW
)
1036 case GTU
: code
= GT
; break;
1037 case LTU
: code
= LT
; break;
1038 case GEU
: code
= GE
; break;
1039 case LEU
: code
= LE
; break;
1045 case EQ
: pos
= "beq", neg
= "bne"; break;
1046 case NE
: pos
= "bne", neg
= "beq"; break;
1047 case GT
: pos
= "bgt", neg
= "ble"; break;
1048 case GTU
: pos
= "bhi", neg
= "blos"; break;
1049 case LT
: pos
= "blt", neg
= "bge"; break;
1050 case LTU
: pos
= "blo", neg
= "bhis"; break;
1051 case GE
: pos
= "bge", neg
= "blt"; break;
1052 case GEU
: pos
= "bhis", neg
= "blo"; break;
1053 case LE
: pos
= "ble", neg
= "bgt"; break;
1054 case LEU
: pos
= "blos", neg
= "bhi"; break;
1055 default: gcc_unreachable ();
1059 /* currently we don't need this, because the tstdf and cmpdf
1060 copy the condition code immediately, and other float operations are not
1061 yet recognized as changing the FCC - if so, then the length-cost of all
1062 jump insns increases by one, because we have to potentially copy the
1064 if (cc_status
.flags
& CC_IN_FPU
)
1065 output_asm_insn("cfcc", NULL
);
1072 sprintf(buf
, "%s %%l1", inv
? neg
: pos
);
1078 sprintf(buf
, "%s JMP_%d\n\tjmp %%l1\nJMP_%d:", inv
? pos
: neg
, x
, x
);
1092 notice_update_cc_on_set(rtx exp
, rtx insn ATTRIBUTE_UNUSED
)
1094 if (GET_CODE (SET_DEST (exp
)) == CC0
)
1096 cc_status
.flags
= 0;
1097 cc_status
.value1
= SET_DEST (exp
);
1098 cc_status
.value2
= SET_SRC (exp
);
1100 else if (GET_CODE (SET_SRC (exp
)) == CALL
)
1104 else if (SET_DEST(exp
) == pc_rtx
)
1108 else if (GET_MODE (SET_DEST(exp
)) == HImode
1109 || GET_MODE (SET_DEST(exp
)) == QImode
)
1111 cc_status
.flags
= GET_CODE (SET_SRC(exp
)) == MINUS
? 0 : CC_NO_OVERFLOW
;
1112 cc_status
.value1
= SET_SRC (exp
);
1113 cc_status
.value2
= SET_DEST (exp
);
1115 if (cc_status
.value1
&& GET_CODE (cc_status
.value1
) == REG
1117 && reg_overlap_mentioned_p (cc_status
.value1
, cc_status
.value2
))
1118 cc_status
.value2
= 0;
1119 if (cc_status
.value1
&& GET_CODE (cc_status
.value1
) == MEM
1121 && GET_CODE (cc_status
.value2
) == MEM
)
1122 cc_status
.value2
= 0;
1132 simple_memory_operand(rtx op
, machine_mode mode ATTRIBUTE_UNUSED
)
1136 /* Eliminate non-memory operations */
1137 if (GET_CODE (op
) != MEM
)
1141 /* dword operations really put out 2 instructions, so eliminate them. */
1142 if (GET_MODE_SIZE (GET_MODE (op
)) > (HAVE_64BIT_P () ? 8 : 4))
1146 /* Decode the address now. */
1150 addr
= XEXP (op
, 0);
1152 switch (GET_CODE (addr
))
1155 /* (R0) - no extra cost */
1160 /* -(R0), (R0)+ - cheap! */
1164 /* cheap - is encoded in addressing mode info!
1166 -- except for @(R0), which has to be @0(R0) !!! */
1168 if (GET_CODE (XEXP (addr
, 0)) == REG
)
1178 /* @#address - extra cost */
1182 /* X(R0) - extra cost */
1194 * output a block move:
1196 * operands[0] ... to
1197 * operands[1] ... from
1198 * operands[2] ... length
1199 * operands[3] ... alignment
1200 * operands[4] ... scratch register
1205 output_block_move(rtx
*operands
)
1207 static int count
= 0;
1212 /* Move of zero bytes is a NOP. */
1213 if (operands
[2] == const0_rtx
)
1216 /* Look for moves by small constant byte counts, those we'll
1217 expand to straight line code. */
1218 if (CONSTANT_P (operands
[2]))
1220 if (INTVAL (operands
[2]) < 16
1221 && (!optimize_size
|| INTVAL (operands
[2]) < 5)
1222 && INTVAL (operands
[3]) == 1)
1226 for (i
= 1; i
<= INTVAL (operands
[2]); i
++)
1227 output_asm_insn("movb (%1)+, (%0)+", operands
);
1231 else if (INTVAL(operands
[2]) < 32
1232 && (!optimize_size
|| INTVAL (operands
[2]) < 9)
1233 && INTVAL (operands
[3]) >= 2)
1237 for (i
= 1; i
<= INTVAL (operands
[2]) / 2; i
++)
1238 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1239 if (INTVAL (operands
[2]) & 1)
1240 output_asm_insn ("movb (%1), (%0)", operands
);
1246 /* Ideally we'd look for moves that are multiples of 4 or 8
1247 bytes and handle those by unrolling the move loop. That
1248 makes for a lot of code if done at run time, but it's ok
1249 for constant counts. Also, for variable counts we have
1250 to worry about odd byte count with even aligned pointers.
1251 On 11/40 and up we handle that case; on older machines
1252 we don't and just use byte-wise moves all the time. */
1254 if (CONSTANT_P (operands
[2]) )
1256 if (INTVAL (operands
[3]) < 2)
1260 lastbyte
= INTVAL (operands
[2]) & 1;
1262 if (optimize_size
|| INTVAL (operands
[2]) & 2)
1264 else if (INTVAL (operands
[2]) & 4)
1270 /* Loop count is byte count scaled by unroll. */
1271 operands
[2] = GEN_INT (INTVAL (operands
[2]) >> unroll
);
1272 output_asm_insn ("mov %2, %4", operands
);
1276 /* Variable byte count; use the input register
1278 operands
[4] = operands
[2];
1280 /* Decide whether to move by words, and check
1281 the byte count for zero. */
1282 if (TARGET_40_PLUS
&& INTVAL (operands
[3]) > 1)
1285 output_asm_insn ("asr %4", operands
);
1290 output_asm_insn ("tst %4", operands
);
1292 sprintf (buf
, "beq movestrhi%d", count
+ 1);
1293 output_asm_insn (buf
, NULL
);
1296 /* Output the loop label. */
1297 sprintf (buf
, "\nmovestrhi%d:", count
);
1298 output_asm_insn (buf
, NULL
);
1300 /* Output the appropriate move instructions. */
1304 output_asm_insn ("movb (%1)+, (%0)+", operands
);
1308 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1312 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1313 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1317 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1318 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1319 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1320 output_asm_insn ("mov (%1)+, (%0)+", operands
);
1324 /* Output the decrement and test. */
1327 sprintf (buf
, "sob %%4, movestrhi%d", count
);
1328 output_asm_insn (buf
, operands
);
1332 output_asm_insn ("dec %4", operands
);
1333 sprintf (buf
, "bgt movestrhi%d", count
);
1334 output_asm_insn (buf
, NULL
);
1338 /* If constant odd byte count, move the last byte. */
1340 output_asm_insn ("movb (%1), (%0)", operands
);
1341 else if (!CONSTANT_P (operands
[2]))
1343 /* Output the destination label for the zero byte count check. */
1344 sprintf (buf
, "\nmovestrhi%d:", count
);
1345 output_asm_insn (buf
, NULL
);
1348 /* If we did word moves, check for trailing last byte. */
1351 sprintf (buf
, "bcc movestrhi%d", count
);
1352 output_asm_insn (buf
, NULL
);
1353 output_asm_insn ("movb (%1), (%0)", operands
);
1354 sprintf (buf
, "\nmovestrhi%d:", count
);
1355 output_asm_insn (buf
, NULL
);
1363 /* This function checks whether a real value can be encoded as
1364 a literal, i.e., addressing mode 27. In that mode, real values
1365 are one word values, so the remaining 48 bits have to be zero. */
1367 legitimate_const_double_p (rtx address
)
1371 REAL_VALUE_FROM_CONST_DOUBLE (r
, address
);
1372 REAL_VALUE_TO_TARGET_DOUBLE (r
, sval
);
1373 if ((sval
[0] & 0xffff) == 0 && sval
[1] == 0)
1378 /* Implement CANNOT_CHANGE_MODE_CLASS. */
1380 pdp11_cannot_change_mode_class (machine_mode from
,
1382 enum reg_class rclass
)
1384 /* Also, FPU registers contain a whole float value and the parts of
1385 it are not separately accessible.
1387 So we disallow all mode changes involving FPRs. */
1388 if (FLOAT_MODE_P (from
) != FLOAT_MODE_P (to
))
1391 return reg_classes_intersect_p (FPU_REGS
, rclass
);
1394 /* TARGET_PREFERRED_RELOAD_CLASS
1396 Given an rtx X being reloaded into a reg required to be
1397 in class CLASS, return the class of reg to actually use.
1398 In general this is just CLASS; but on some machines
1399 in some cases it is preferable to use a more restrictive class.
1401 loading is easier into LOAD_FPU_REGS than FPU_REGS! */
1404 pdp11_preferred_reload_class (rtx x
, reg_class_t rclass
)
1406 if (rclass
== FPU_REGS
)
1407 return LOAD_FPU_REGS
;
1408 if (rclass
== ALL_REGS
)
1410 if (FLOAT_MODE_P (GET_MODE (x
)))
1411 return LOAD_FPU_REGS
;
1413 return GENERAL_REGS
;
1418 /* TARGET_PREFERRED_OUTPUT_RELOAD_CLASS
1420 Given an rtx X being reloaded into a reg required to be
1421 in class CLASS, return the class of reg to actually use.
1422 In general this is just CLASS; but on some machines
1423 in some cases it is preferable to use a more restrictive class.
1425 loading is easier into LOAD_FPU_REGS than FPU_REGS! */
1428 pdp11_preferred_output_reload_class (rtx x
, reg_class_t rclass
)
1430 if (rclass
== FPU_REGS
)
1431 return LOAD_FPU_REGS
;
1432 if (rclass
== ALL_REGS
)
1434 if (FLOAT_MODE_P (GET_MODE (x
)))
1435 return LOAD_FPU_REGS
;
1437 return GENERAL_REGS
;
1443 /* TARGET_SECONDARY_RELOAD.
1445 FPU registers AC4 and AC5 (class NO_LOAD_FPU_REGS) require an
1446 intermediate register (AC0-AC3: LOAD_FPU_REGS). Everything else
1447 can be loade/stored directly. */
1449 pdp11_secondary_reload (bool in_p ATTRIBUTE_UNUSED
,
1451 reg_class_t reload_class
,
1452 machine_mode reload_mode ATTRIBUTE_UNUSED
,
1453 secondary_reload_info
*sri ATTRIBUTE_UNUSED
)
1455 if (reload_class
!= NO_LOAD_FPU_REGS
|| GET_CODE (x
) != REG
||
1456 REGNO_REG_CLASS (REGNO (x
)) == LOAD_FPU_REGS
)
1459 return LOAD_FPU_REGS
;
1462 /* Target routine to check if register to register move requires memory.
1464 The answer is yes if we're going between general register and FPU
1465 registers. The mode doesn't matter in making this check.
1468 pdp11_secondary_memory_needed (reg_class_t c1
, reg_class_t c2
,
1469 machine_mode mode ATTRIBUTE_UNUSED
)
1471 int fromfloat
= (c1
== LOAD_FPU_REGS
|| c1
== NO_LOAD_FPU_REGS
||
1473 int tofloat
= (c2
== LOAD_FPU_REGS
|| c2
== NO_LOAD_FPU_REGS
||
1476 return (fromfloat
!= tofloat
);
1479 /* TARGET_LEGITIMATE_ADDRESS_P recognizes an RTL expression
1480 that is a valid memory address for an instruction.
1481 The MODE argument is the machine mode for the MEM expression
1482 that wants to use this address.
1487 pdp11_legitimate_address_p (machine_mode mode
,
1488 rtx operand
, bool strict
)
1492 /* accept @#address */
1493 if (CONSTANT_ADDRESS_P (operand
))
1496 switch (GET_CODE (operand
))
1500 return !strict
|| REGNO_OK_FOR_BASE_P (REGNO (operand
));
1504 return GET_CODE (XEXP (operand
, 0)) == REG
1505 && (!strict
|| REGNO_OK_FOR_BASE_P (REGNO (XEXP (operand
, 0))))
1506 && CONSTANT_ADDRESS_P (XEXP (operand
, 1));
1510 return GET_CODE (XEXP (operand
, 0)) == REG
1511 && (!strict
|| REGNO_OK_FOR_BASE_P (REGNO (XEXP (operand
, 0))));
1515 return GET_CODE (XEXP (operand
, 0)) == REG
1516 && (!strict
|| REGNO_OK_FOR_BASE_P (REGNO (XEXP (operand
, 0))));
1519 /* accept -(SP) -- which uses PRE_MODIFY for byte mode */
1520 return GET_CODE (XEXP (operand
, 0)) == REG
1521 && REGNO (XEXP (operand
, 0)) == STACK_POINTER_REGNUM
1522 && GET_CODE ((xfoob
= XEXP (operand
, 1))) == PLUS
1523 && GET_CODE (XEXP (xfoob
, 0)) == REG
1524 && REGNO (XEXP (xfoob
, 0)) == STACK_POINTER_REGNUM
1525 && CONSTANT_P (XEXP (xfoob
, 1))
1526 && INTVAL (XEXP (xfoob
,1)) == -2;
1529 /* accept (SP)+ -- which uses POST_MODIFY for byte mode */
1530 return GET_CODE (XEXP (operand
, 0)) == REG
1531 && REGNO (XEXP (operand
, 0)) == STACK_POINTER_REGNUM
1532 && GET_CODE ((xfoob
= XEXP (operand
, 1))) == PLUS
1533 && GET_CODE (XEXP (xfoob
, 0)) == REG
1534 && REGNO (XEXP (xfoob
, 0)) == STACK_POINTER_REGNUM
1535 && CONSTANT_P (XEXP (xfoob
, 1))
1536 && INTVAL (XEXP (xfoob
,1)) == 2;
1539 /* handle another level of indirection ! */
1540 xfoob
= XEXP (operand
, 0);
1542 /* (MEM:xx (MEM:xx ())) is not valid for SI, DI and currently
1543 also forbidden for float, because we have to handle this
1544 in output_move_double and/or output_move_quad() - we could
1545 do it, but currently it's not worth it!!!
1546 now that DFmode cannot go into CPU register file,
1547 maybe I should allow float ...
1548 but then I have to handle memory-to-memory moves in movdf ?? */
1549 if (GET_MODE_BITSIZE(mode
) > 16)
1552 /* accept @address */
1553 if (CONSTANT_ADDRESS_P (xfoob
))
1556 switch (GET_CODE (xfoob
))
1559 /* accept @(R0) - which is @0(R0) */
1560 return !strict
|| REGNO_OK_FOR_BASE_P(REGNO (xfoob
));
1564 return GET_CODE (XEXP (xfoob
, 0)) == REG
1565 && (!strict
|| REGNO_OK_FOR_BASE_P (REGNO (XEXP (xfoob
, 0))))
1566 && CONSTANT_ADDRESS_P (XEXP (xfoob
, 1));
1570 return GET_CODE (XEXP (xfoob
, 0)) == REG
1571 && (!strict
|| REGNO_OK_FOR_BASE_P (REGNO (XEXP (xfoob
, 0))));
1575 return GET_CODE (XEXP (xfoob
, 0)) == REG
1576 && (!strict
|| REGNO_OK_FOR_BASE_P (REGNO (XEXP (xfoob
, 0))));
1579 /* anything else is invalid */
1584 /* anything else is invalid */
1589 /* Return the class number of the smallest class containing
1590 reg number REGNO. */
1592 pdp11_regno_reg_class (int regno
)
1594 if (regno
== FRAME_POINTER_REGNUM
|| regno
== ARG_POINTER_REGNUM
)
1595 return GENERAL_REGS
;
1596 else if (regno
> AC3_REGNUM
)
1597 return NO_LOAD_FPU_REGS
;
1598 else if (regno
>= AC0_REGNUM
)
1599 return LOAD_FPU_REGS
;
1603 return GENERAL_REGS
;
1608 pdp11_sp_frame_offset (void)
1610 int offset
= 0, regno
;
1611 offset
= get_frame_size();
1612 for (regno
= 0; regno
<= PC_REGNUM
; regno
++)
1613 if (pdp11_saved_regno (regno
))
1615 for (regno
= AC0_REGNUM
; regno
<= AC5_REGNUM
; regno
++)
1616 if (pdp11_saved_regno (regno
))
1622 /* Return the offset between two registers, one to be eliminated, and the other
1623 its replacement, at the start of a routine. */
1626 pdp11_initial_elimination_offset (int from
, int to
)
1630 if (from
== ARG_POINTER_REGNUM
&& to
== HARD_FRAME_POINTER_REGNUM
)
1632 else if (from
== FRAME_POINTER_REGNUM
1633 && to
== HARD_FRAME_POINTER_REGNUM
)
1637 gcc_assert (to
== STACK_POINTER_REGNUM
);
1639 /* Get the size of the register save area. */
1640 spoff
= pdp11_sp_frame_offset ();
1641 if (from
== FRAME_POINTER_REGNUM
)
1644 gcc_assert (from
== ARG_POINTER_REGNUM
);
1646 /* If there is a frame pointer, that is saved too. */
1647 if (frame_pointer_needed
)
1650 /* Account for the saved PC in the function call. */
1655 /* A copy of output_addr_const modified for pdp11 expression syntax.
1656 output_addr_const also gets called for %cDIGIT and %nDIGIT, which we don't
1657 use, and for debugging output, which we don't support with this port either.
1658 So this copy should get called whenever needed.
1661 output_addr_const_pdp11 (FILE *file
, rtx x
)
1667 switch (GET_CODE (x
))
1670 gcc_assert (flag_pic
);
1675 assemble_name (file
, XSTR (x
, 0));
1679 ASM_GENERATE_INTERNAL_LABEL (buf
, "L", CODE_LABEL_NUMBER (XEXP (x
, 0)));
1680 assemble_name (file
, buf
);
1684 ASM_GENERATE_INTERNAL_LABEL (buf
, "L", CODE_LABEL_NUMBER (x
));
1685 assemble_name (file
, buf
);
1693 fprintf (file
, "-");
1695 fprintf (file
, "%#o", i
& 0xffff);
1699 /* This used to output parentheses around the expression,
1700 but that does not work on the 386 (either ATT or BSD assembler). */
1701 output_addr_const_pdp11 (file
, XEXP (x
, 0));
1705 if (GET_MODE (x
) == VOIDmode
)
1707 /* We can use %o if the number is one word and positive. */
1708 gcc_assert (!CONST_DOUBLE_HIGH (x
));
1709 fprintf (file
, "%#ho", (unsigned short) CONST_DOUBLE_LOW (x
));
1712 /* We can't handle floating point constants;
1713 PRINT_OPERAND must handle them. */
1714 output_operand_lossage ("floating constant misused");
1718 /* Some assemblers need integer constants to appear last (e.g. masm). */
1719 if (GET_CODE (XEXP (x
, 0)) == CONST_INT
)
1721 output_addr_const_pdp11 (file
, XEXP (x
, 1));
1722 if (INTVAL (XEXP (x
, 0)) >= 0)
1723 fprintf (file
, "+");
1724 output_addr_const_pdp11 (file
, XEXP (x
, 0));
1728 output_addr_const_pdp11 (file
, XEXP (x
, 0));
1729 if (INTVAL (XEXP (x
, 1)) >= 0)
1730 fprintf (file
, "+");
1731 output_addr_const_pdp11 (file
, XEXP (x
, 1));
1736 /* Avoid outputting things like x-x or x+5-x,
1737 since some assemblers can't handle that. */
1738 x
= simplify_subtraction (x
);
1739 if (GET_CODE (x
) != MINUS
)
1742 output_addr_const_pdp11 (file
, XEXP (x
, 0));
1743 if (GET_CODE (XEXP (x
, 1)) != CONST_INT
1744 || INTVAL (XEXP (x
, 1)) >= 0)
1745 fprintf (file
, "-");
1746 output_addr_const_pdp11 (file
, XEXP (x
, 1));
1751 output_addr_const_pdp11 (file
, XEXP (x
, 0));
1755 output_operand_lossage ("invalid expression as operand");
1759 /* Worker function for TARGET_RETURN_IN_MEMORY. */
1762 pdp11_return_in_memory (const_tree type
, const_tree fntype ATTRIBUTE_UNUSED
)
1764 /* Integers 32 bits and under, and scalar floats (if FPU), are returned
1765 in registers. The rest go into memory. */
1766 return (TYPE_MODE (type
) == DImode
1767 || (FLOAT_MODE_P (TYPE_MODE (type
)) && ! TARGET_AC0
)
1768 || TREE_CODE (type
) == VECTOR_TYPE
1769 || COMPLEX_MODE_P (TYPE_MODE (type
)));
1772 /* Worker function for TARGET_FUNCTION_VALUE.
1774 On the pdp11 the value is found in R0 (or ac0??? not without FPU!!!! ) */
1777 pdp11_function_value (const_tree valtype
,
1778 const_tree fntype_or_decl ATTRIBUTE_UNUSED
,
1779 bool outgoing ATTRIBUTE_UNUSED
)
1781 return gen_rtx_REG (TYPE_MODE (valtype
),
1782 BASE_RETURN_VALUE_REG(TYPE_MODE(valtype
)));
1785 /* Worker function for TARGET_LIBCALL_VALUE. */
1788 pdp11_libcall_value (machine_mode mode
,
1789 const_rtx fun ATTRIBUTE_UNUSED
)
1791 return gen_rtx_REG (mode
, BASE_RETURN_VALUE_REG(mode
));
1794 /* Worker function for TARGET_FUNCTION_VALUE_REGNO_P.
1796 On the pdp, the first "output" reg is the only register thus used.
1798 maybe ac0 ? - as option someday! */
1801 pdp11_function_value_regno_p (const unsigned int regno
)
1803 return (regno
== RETVAL_REGNUM
) || (TARGET_AC0
&& (regno
== AC0_REGNUM
));
1806 /* Worker function for TARGET_TRAMPOLINE_INIT.
1808 trampoline - how should i do it in separate i+d ?
1809 have some allocate_trampoline magic???
1811 the following should work for shared I/D:
1813 MOV #STATIC, $4 01270Y 0x0000 <- STATIC; Y = STATIC_CHAIN_REGNUM
1814 JMP @#FUNCTION 000137 0x0000 <- FUNCTION
1818 pdp11_trampoline_init (rtx m_tramp
, tree fndecl
, rtx chain_value
)
1820 rtx fnaddr
= XEXP (DECL_RTL (fndecl
), 0);
1823 gcc_assert (!TARGET_SPLIT
);
1825 mem
= adjust_address (m_tramp
, HImode
, 0);
1826 emit_move_insn (mem
, GEN_INT (012700+STATIC_CHAIN_REGNUM
));
1827 mem
= adjust_address (m_tramp
, HImode
, 2);
1828 emit_move_insn (mem
, chain_value
);
1829 mem
= adjust_address (m_tramp
, HImode
, 4);
1830 emit_move_insn (mem
, GEN_INT (000137));
1831 emit_move_insn (mem
, fnaddr
);
1834 /* Worker function for TARGET_FUNCTION_ARG.
1836 Determine where to put an argument to a function.
1837 Value is zero to push the argument on the stack,
1838 or a hard register in which to store the argument.
1840 MODE is the argument's machine mode.
1841 TYPE is the data type of the argument (as a tree).
1842 This is null for libcalls where that information may
1844 CUM is a variable of type CUMULATIVE_ARGS which gives info about
1845 the preceding args and about the function being called.
1846 NAMED is nonzero if this argument is a named parameter
1847 (otherwise it is an extra parameter matching an ellipsis). */
1850 pdp11_function_arg (cumulative_args_t cum ATTRIBUTE_UNUSED
,
1851 machine_mode mode ATTRIBUTE_UNUSED
,
1852 const_tree type ATTRIBUTE_UNUSED
,
1853 bool named ATTRIBUTE_UNUSED
)
1858 /* Worker function for TARGET_FUNCTION_ARG_ADVANCE.
1860 Update the data in CUM to advance over an argument of mode MODE and
1861 data type TYPE. (TYPE is null for libcalls where that information
1862 may not be available.) */
1865 pdp11_function_arg_advance (cumulative_args_t cum_v
, machine_mode mode
,
1866 const_tree type
, bool named ATTRIBUTE_UNUSED
)
1868 CUMULATIVE_ARGS
*cum
= get_cumulative_args (cum_v
);
1870 *cum
+= (mode
!= BLKmode
1871 ? GET_MODE_SIZE (mode
)
1872 : int_size_in_bytes (type
));
1875 /* Make sure everything's fine if we *don't* have an FPU.
1876 This assumes that putting a register in fixed_regs will keep the
1877 compiler's mitts completely off it. We don't bother to zero it out
1878 of register classes. Also fix incompatible register naming with
1879 the UNIX assembler. */
1882 pdp11_conditional_register_usage (void)
1888 COPY_HARD_REG_SET (x
, reg_class_contents
[(int)FPU_REGS
]);
1889 for (i
= 0; i
< FIRST_PSEUDO_REGISTER
; i
++ )
1890 if (TEST_HARD_REG_BIT (x
, i
))
1891 fixed_regs
[i
] = call_used_regs
[i
] = 1;
1895 call_used_regs
[AC0_REGNUM
] = 1;
1896 if (TARGET_UNIX_ASM
)
1898 /* Change names of FPU registers for the UNIX assembler. */
1899 reg_names
[8] = "fr0";
1900 reg_names
[9] = "fr1";
1901 reg_names
[10] = "fr2";
1902 reg_names
[11] = "fr3";
1903 reg_names
[12] = "fr4";
1904 reg_names
[13] = "fr5";
1909 pdp11_function_section (tree decl ATTRIBUTE_UNUSED
,
1910 enum node_frequency freq ATTRIBUTE_UNUSED
,
1911 bool startup ATTRIBUTE_UNUSED
,
1912 bool exit ATTRIBUTE_UNUSED
)
1917 /* Implement TARGET_LEGITIMATE_CONSTANT_P. */
1920 pdp11_legitimate_constant_p (machine_mode mode ATTRIBUTE_UNUSED
, rtx x
)
1922 return GET_CODE (x
) != CONST_DOUBLE
|| legitimate_const_double_p (x
);
1925 /* Implement TARGET_SCALAR_MODE_SUPPORTED_P. */
1928 pdp11_scalar_mode_supported_p (machine_mode mode
)
1930 /* Support SFmode even with -mfloat64. */
1933 return default_scalar_mode_supported_p (mode
);
1936 struct gcc_target targetm
= TARGET_INITIALIZER
;