1671c41b6516fcd204c7c9fc0a4596922d6bd01d
[gcc.git] / gcc / config / picochip / picochip.c
1 /* Subroutines used for code generation on picoChip processors.
2 Copyright (C) 2001, 2008, 2009, 2010 Free Software Foundation, Inc.
3 Contributed by picoChip Designs Ltd. (http://www.picochip.com)
4 Maintained by Daniel Towner (daniel.towner@picochip.com) and
5 Hariharan Sandanagobalane (hariharan@picochip.com)
6
7 This file is part of GCC.
8
9 GCC is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3, or (at your option)
12 any later version.
13
14 GCC is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with GCC; see the file COPYING3. If not, see
21 <http://www.gnu.org/licenses/>. */
22
23 #include "config.h"
24 #include "system.h"
25 #include "coretypes.h"
26 #include "tm.h"
27 #include "rtl.h"
28 #include "regs.h"
29 #include "hard-reg-set.h"
30 #include "insn-config.h"
31 #include "conditions.h"
32 #include "insn-attr.h"
33 #include "flags.h"
34 #include "recog.h"
35 #include "obstack.h"
36 #include "tree.h"
37 #include "expr.h"
38 #include "optabs.h"
39 #include "except.h"
40 #include "function.h"
41 #include "output.h"
42 #include "basic-block.h"
43 #include "integrate.h"
44 #include "diagnostic-core.h"
45 #include "toplev.h"
46 #include "ggc.h"
47 #include "hashtab.h"
48 #include "tm_p.h"
49 #include "target.h"
50 #include "target-def.h"
51 #include "langhooks.h"
52 #include "reload.h"
53 #include "params.h"
54
55 #include "picochip-protos.h"
56
57 #include "insn-attr.h" /* For DFA state_t. */
58 #include "insn-config.h" /* Required by recog.h */
59 #include "insn-codes.h" /* For CODE_FOR_? */
60 #include "optabs.h" /* For GEN_FCN */
61 #include "basic-block.h" /* UPDATE_LIFE_GLOBAL* for picochip_reorg. */
62 #include "timevar.h" /* For TV_SCHED2, in picochip_reorg. */
63 #include "libfuncs.h" /* For memcpy_libfuncs, etc. */
64 #include "df.h" /* For df_regs_ever_live_df_regs_ever_live_pp, etc. */
65 \f
66
67 /* Target AE ISA information. */
68 enum picochip_dfa_type picochip_schedule_type;
69
70 bool picochip_has_mul_unit = false;
71 bool picochip_has_mac_unit = false;
72
73 /* targetm hook function prototypes. */
74
75 void picochip_asm_file_start (void);
76 void picochip_asm_file_end (void);
77
78 void picochip_init_libfuncs (void);
79 void picochip_reorg (void);
80
81 int picochip_arg_partial_bytes (CUMULATIVE_ARGS * p_cum,
82 enum machine_mode mode,
83 tree type, bool named);
84
85 int picochip_sched_lookahead (void);
86 int picochip_sched_issue_rate (void);
87 int picochip_sched_adjust_cost (rtx insn, rtx link,
88 rtx dep_insn, int cost);
89 int picochip_sched_reorder (FILE * file, int verbose, rtx * ready,
90 int *n_readyp, int clock);
91
92 void picochip_init_builtins (void);
93 rtx picochip_expand_builtin (tree, rtx, rtx, enum machine_mode, int);
94
95 bool picochip_rtx_costs (rtx x, int code, int outer_code, int* total, bool speed);
96 bool picochip_return_in_memory(const_tree type,
97 const_tree fntype ATTRIBUTE_UNUSED);
98 bool picochip_legitimate_address_p (enum machine_mode, rtx, bool);
99 rtx picochip_legitimize_address (rtx x, rtx oldx ATTRIBUTE_UNUSED,
100 enum machine_mode mode);
101 int picochip_legitimize_reload_address (rtx *x, enum machine_mode mode,
102 int opnum, int type, int ind_levels);
103
104 rtx picochip_struct_value_rtx(tree fntype ATTRIBUTE_UNUSED, int incoming ATTRIBUTE_UNUSED);
105 rtx picochip_function_value (const_tree valtype, const_tree func ATTRIBUTE_UNUSED,
106 bool outgoing ATTRIBUTE_UNUSED);
107 reg_class_t
108 picochip_secondary_reload (bool in_p,
109 rtx x ATTRIBUTE_UNUSED,
110 reg_class_t cla ATTRIBUTE_UNUSED,
111 enum machine_mode mode,
112 secondary_reload_info *sri);
113 void
114 picochip_asm_named_section (const char *name,
115 unsigned int flags ATTRIBUTE_UNUSED,
116 tree decl ATTRIBUTE_UNUSED);
117
118 static rtx picochip_static_chain (const_tree, bool);
119
120 static void picochip_option_override (void);
121
122 /* Lookup table mapping a register number to the earliest containing
123 class. Used by REGNO_REG_CLASS. */
124 const enum reg_class picochip_regno_reg_class[FIRST_PSEUDO_REGISTER] =
125 {
126 TWIN_REGS, TWIN_REGS, TWIN_REGS, TWIN_REGS,
127 TWIN_REGS, TWIN_REGS, TWIN_REGS, TWIN_REGS,
128 TWIN_REGS, TWIN_REGS, TWIN_REGS, TWIN_REGS,
129 GR_REGS, FRAME_REGS, PTR_REGS, CONST_REGS,
130 ACC_REGS, CC_REGS, GR_REGS, GR_REGS
131 };
132
133 /* picoChip register names. */
134 const char *picochip_regnames[] = REGISTER_NAMES;
135
136 /* Define the maximum number of registers which may be used to pass
137 * parameters to functions. */
138 #define MAX_CALL_PARAMETER_REGS 6
139 \f
140
141 /* Target scheduling information. */
142
143 /* Determine whether we run our final scheduling pass or not. We always
144 avoid the normal second scheduling pass. */
145 int picochip_flag_schedule_insns2;
146
147 /* Check if variable tracking needs to be run. */
148 int picochip_flag_var_tracking;
149
150 /* This flag indicates whether the next instruction to be output is a
151 VLIW continuation instruction. It is used to communicate between
152 final_prescan_insn and asm_output_opcode. */
153 static int picochip_vliw_continuation = 0;
154
155 /* This variable is used to communicate the current instruction
156 between final_prescan_insn and functions such as asm_output_opcode,
157 and picochip_get_vliw_alu_id (which are otherwise unable to determine the
158 current instruction. */
159 static rtx picochip_current_prescan_insn;
160
161 static bool picochip_is_delay_slot_pending = 0;
162
163 /* When final_prescan_insn is called, it computes information about
164 the current VLIW packet, and stores it in this structure. When
165 instructions are output, this state is used to make sure that the
166 instructions are output in the correct way (e.g., which ALU to use,
167 whether a macro branch was ever previously a real branch, etc.). */
168 struct vliw_state
169 {
170 int contains_pico_alu_insn;
171 int contains_non_cc_alu_insn;
172 int num_alu_insns_so_far;
173
174 /* Record how many instructions are contained in the packet. */
175 int num_insns_in_packet;
176
177 /* There was a case for this to be more than 1 */
178 int num_cfi_labels_deferred;
179 char cfi_label_name[2][256]; /* Used to record the name of a CFI label
180 emitted inside a VLIW packet. */
181 char lm_label_name[256]; /* Used to record the name of an LM label. */
182 };
183
184 struct vliw_state picochip_current_vliw_state;
185
186 /* Save/restore recog_data. */
187 static int picochip_saved_which_alternative;
188 static struct recog_data picochip_saved_recog_data;
189
190 /* Determine which ALU to use for the instruction in
191 picochip_current_prescan_insn. */
192 static char picochip_get_vliw_alu_id (void);
193 \f
194 /* Initialize the GCC target structure. */
195
196 #undef TARGET_ASM_FUNCTION_PROLOGUE
197 #define TARGET_ASM_FUNCTION_PROLOGUE picochip_function_prologue
198
199 #undef TARGET_ASM_FUNCTION_EPILOGUE
200 #define TARGET_ASM_FUNCTION_EPILOGUE picochip_function_epilogue
201
202 #undef TARGET_ASM_INTERNAL_LABEL
203 #define TARGET_ASM_INTERNAL_LABEL picochip_output_internal_label
204
205 #undef TARGET_ASM_GLOBALIZE_LABEL
206 #define TARGET_ASM_GLOBALIZE_LABEL picochip_output_global
207
208 #undef TARGET_ASM_BYTE_OP
209 #define TARGET_ASM_BYTE_OP ".initByte "
210 #undef TARGET_ASM_ALIGNED_HI_OP
211 #define TARGET_ASM_ALIGNED_HI_OP ".initWord "
212 #undef TARGET_ASM_UNALIGNED_HI_OP
213 #define TARGET_ASM_UNALIGNED_HI_OP ".unalignedInitWord "
214 #undef TARGET_ASM_ALIGNED_SI_OP
215 #define TARGET_ASM_ALIGNED_SI_OP ".initLong "
216 #undef TARGET_ASM_UNALIGNED_SI_OP
217 #define TARGET_ASM_UNALIGNED_SI_OP ".unalignedInitLong "
218
219 #undef TARGET_INIT_BUILTINS
220 #define TARGET_INIT_BUILTINS picochip_init_builtins
221
222 #undef TARGET_EXPAND_BUILTIN
223 #define TARGET_EXPAND_BUILTIN picochip_expand_builtin
224
225 #undef TARGET_RTX_COSTS
226 #define TARGET_RTX_COSTS picochip_rtx_costs
227
228 #undef TARGET_SCHED_ISSUE_RATE
229 #define TARGET_SCHED_ISSUE_RATE picochip_sched_issue_rate
230
231 #undef TARGET_SCHED_REORDER
232 #define TARGET_SCHED_REORDER picochip_sched_reorder
233
234 #undef TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD
235 #define TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD \
236 picochip_sched_lookahead
237
238 #undef TARGET_SCHED_ADJUST_COST
239 #define TARGET_SCHED_ADJUST_COST picochip_sched_adjust_cost
240
241 #undef TARGET_ASM_NAMED_SECTION
242 #define TARGET_ASM_NAMED_SECTION picochip_asm_named_section
243
244 #undef TARGET_HAVE_NAMED_SECTIONS
245 #define TARGET_HAVE_NAMED_SECTIONS 1
246
247 #undef TARGET_HAVE_SWITCHABLE_BSS_SECTIONS
248 #define TARGET_HAVE_SWITCHABLE_BSS_SECTIONS 1
249
250 #undef TARGET_INIT_LIBFUNCS
251 #define TARGET_INIT_LIBFUNCS picochip_init_libfuncs
252
253 #undef TARGET_ASM_FILE_START
254 #define TARGET_ASM_FILE_START picochip_asm_file_start
255
256 #undef TARGET_ASM_FILE_END
257 #define TARGET_ASM_FILE_END picochip_asm_file_end
258
259 #undef TARGET_MACHINE_DEPENDENT_REORG
260 #define TARGET_MACHINE_DEPENDENT_REORG picochip_reorg
261
262 #undef TARGET_ARG_PARTIAL_BYTES
263 #define TARGET_ARG_PARTIAL_BYTES picochip_arg_partial_bytes
264
265 #undef TARGET_PROMOTE_FUNCTION_MODE
266 #define TARGET_PROMOTE_FUNCTION_MODE default_promote_function_mode_always_promote
267 #undef TARGET_PROMOTE_PROTOTYPES
268 #define TARGET_PROMOTE_PROTOTYPES hook_bool_const_tree_true
269
270 /* Target support for Anchored Addresses optimization */
271 #undef TARGET_MIN_ANCHOR_OFFSET
272 #define TARGET_MIN_ANCHOR_OFFSET 0
273 #undef TARGET_MAX_ANCHOR_OFFSET
274 #define TARGET_MAX_ANCHOR_OFFSET 7
275 #undef TARGET_ASM_OUTPUT_ANCHOR
276 #define TARGET_ASM_OUTPUT_ANCHOR picochip_asm_output_anchor
277
278 #undef TARGET_FUNCTION_VALUE
279 #define TARGET_FUNCTION_VALUE picochip_function_value
280 /*
281 #undef TARGET_LIBGCC_CMP_RETURN_MODE
282 #define TARGET_LIBGCC_CMP_RETURN_MODE picochip_libgcc_cmp_return_mode
283 */
284
285 #undef TARGET_LEGITIMATE_ADDRESS_P
286 #define TARGET_LEGITIMATE_ADDRESS_P picochip_legitimate_address_p
287
288 #undef TARGET_LEGITIMIZE_ADDRESS
289 #define TARGET_LEGITIMIZE_ADDRESS picochip_legitimize_address
290
291 /* Loading and storing QImode values to and from memory
292 usually requires a scratch register. */
293 #undef TARGET_SECONDARY_RELOAD
294 #define TARGET_SECONDARY_RELOAD picochip_secondary_reload
295 #undef DONT_USE_BUILTIN_SETJMP
296 #define DONT_USE_BUILTIN_SETJMP 1
297
298 /* How Large Values are Returned */
299
300 #undef TARGET_RETURN_IN_MEMORY
301 #define TARGET_RETURN_IN_MEMORY picochip_return_in_memory
302
303 #undef TARGET_STATIC_CHAIN
304 #define TARGET_STATIC_CHAIN picochip_static_chain
305
306 #undef TARGET_OPTION_OVERRIDE
307 #define TARGET_OPTION_OVERRIDE picochip_option_override
308
309 #undef TARGET_OVERRIDE_OPTIONS_AFTER_CHANGE
310 #define TARGET_OVERRIDE_OPTIONS_AFTER_CHANGE picochip_option_override
311
312 struct gcc_target targetm = TARGET_INITIALIZER;
313 \f
314
315 /* Only return a value in memory if it is greater than 4 bytes.
316 int_size_in_bytes returns -1 for variable size objects, which go in
317 memory always. The cast to unsigned makes -1 > 8. */
318
319 bool
320 picochip_return_in_memory(const_tree type, const_tree fntype ATTRIBUTE_UNUSED)
321 {
322 return ((unsigned HOST_WIDE_INT) int_size_in_bytes (type) > 4);
323 }
324
325 /* Allow some options to be overriden. In particular, the 2nd
326 scheduling pass option is switched off, and a machine dependent
327 reorganisation ensures that it is run later on, after the second
328 jump optimisation. */
329
330 static void
331 picochip_option_override (void)
332 {
333 /* If we are optimizing for stack, dont let inliner to inline functions
334 that could potentially increase stack size.*/
335 if (flag_conserve_stack)
336 {
337 PARAM_VALUE (PARAM_LARGE_STACK_FRAME) = 0;
338 PARAM_VALUE (PARAM_STACK_FRAME_GROWTH) = 0;
339 }
340
341 /* Turn off the elimination of unused types. The elaborator
342 generates various interesting types to represent constants,
343 generics, and so on, and it is useful to retain this information
344 in the debug output. The increased size of the debug information
345 is not really an issue for us. */
346 flag_eliminate_unused_debug_types = 0;
347
348 /* Even if the user specifies a -fno-omit-frame-pointer on the
349 command line, we still want to go ahead and omit frame pointer
350 usages, since we dont really have a frame pointer register.
351 So, all accesses to FP need to be converted to accesses off
352 stack pointer.*/
353 flag_omit_frame_pointer = 1;
354
355 /* Turning on anchored addresses by default. This is an optimization
356 that could decrease the code size by placing anchors in data and
357 accessing offsets from the anchor for file local data variables.*/
358 if (optimize >= 1)
359 flag_section_anchors = 1;
360
361 /* Turn off the second scheduling pass, and move it to
362 picochip_reorg, to avoid having the second jump optimisation
363 trash the instruction modes (e.g., instructions are changed to
364 TImode to mark the beginning of cycles). Two types of DFA
365 scheduling are possible: space and speed. In both cases,
366 instructions are reordered to avoid stalls (e.g., memory loads
367 stall for one cycle). Speed scheduling will also enable VLIW
368 instruction packing. VLIW instructions use more code space, so
369 VLIW scheduling is disabled when scheduling for size. */
370 picochip_flag_schedule_insns2 = flag_schedule_insns_after_reload;
371 flag_schedule_insns_after_reload = 0;
372 if (picochip_flag_schedule_insns2)
373 {
374 if (optimize_size)
375 picochip_schedule_type = DFA_TYPE_SPACE;
376 else
377 {
378 picochip_schedule_type = DFA_TYPE_SPEED;
379 flag_delayed_branch = 0;
380 }
381 }
382 else
383 picochip_schedule_type = DFA_TYPE_NONE;
384
385 /* Ensure that the debug level is always at least -g2. The flow
386 analyser works at its best if it always has debug
387 information. DWARF is non-intrusive, so it makes no difference to
388 code quality if debug is always enabled. */
389 if (debug_info_level < DINFO_LEVEL_NORMAL)
390 {
391 debug_info_level = DINFO_LEVEL_NORMAL;
392 write_symbols = DWARF2_DEBUG;
393 }
394
395 /* Options of the form -mae=mac, and so on will be substituted by
396 the compiler driver for the appropriate byte access and multiply
397 unit ISA options. Any unrecognised AE types will end up being
398 passed to the compiler, which should reject them as invalid. */
399 if (picochip_ae_type_string != NULL)
400 error ("invalid AE type specified (%s)\n", picochip_ae_type_string);
401
402 /* Override any specific capabilities of the instruction set. These
403 take precedence over any capabilities inferred from the AE type,
404 regardless of where the options appear on the command line. */
405 if (picochip_mul_type_string == NULL)
406 {
407 /* Default to MEM-type multiply, for historical compatibility. */
408 picochip_has_mac_unit = false;
409 picochip_has_mul_unit = true;
410 }
411 else
412 {
413 picochip_has_mac_unit = false;
414 picochip_has_mul_unit = false;
415
416 if (strcmp (picochip_mul_type_string, "mul") == 0)
417 picochip_has_mul_unit = true;
418 else if (strcmp (picochip_mul_type_string, "mac") == 0)
419 picochip_has_mac_unit = true;
420 else if (strcmp (picochip_mul_type_string, "none") == 0)
421 { /* Do nothing. Unit types already set to false. */ }
422 else
423 error ("Invalid mul type specified (%s) - expected mac, mul or none",
424 picochip_mul_type_string);
425 }
426
427 }
428 \f
429
430 /* Initialise the library functions to handle arithmetic on some of
431 the larger modes. */
432 void
433 picochip_init_libfuncs (void)
434 {
435 /* 64-bit shifts */
436 set_optab_libfunc (ashr_optab, DImode, "__ashrdi3");
437 set_optab_libfunc (ashl_optab, DImode, "__ashldi3");
438 set_optab_libfunc (lshr_optab, DImode, "__lshrdi3");
439
440 /* 64-bit signed multiplication. */
441 set_optab_libfunc (smul_optab, DImode, "__muldi3");
442
443 /* Signed division */
444 set_optab_libfunc (sdiv_optab, HImode, "__divhi3");
445 set_optab_libfunc (sdiv_optab, DImode, "__divdi3");
446
447 /* Signed modulus */
448 set_optab_libfunc (smod_optab, HImode, "__modhi3");
449 set_optab_libfunc (smod_optab, DImode, "__moddi3");
450
451 /* 32-bit count leading Zeros*/
452 set_optab_libfunc (clz_optab, SImode, "_clzsi2");
453
454 /* 64-bit comparison */
455 set_optab_libfunc (ucmp_optab, DImode, "__ucmpdi2");
456 set_optab_libfunc (cmp_optab, DImode, "__cmpdi2");
457
458 /* 64-bit addition and subtraction*/
459 set_optab_libfunc (add_optab, DImode, "_adddi3");
460 set_optab_libfunc (sub_optab, DImode, "_subdi3");
461 }
462
463 /* Memcpy function */
464 int
465 picochip_expand_movmemhi (rtx *operands)
466 {
467 rtx src_addr_reg, dst_addr_reg, count_reg, src_mem, dst_mem, tmp_reg;
468 rtx start_label;
469 int align, size;
470 src_addr_reg = gen_reg_rtx(HImode);
471 dst_addr_reg = gen_reg_rtx(HImode);
472 count_reg = gen_reg_rtx(HImode);
473 emit_insn (gen_movhi (count_reg, operands[2]));
474 emit_insn (gen_movqi (src_addr_reg, XEXP(operands[1], 0)));
475 emit_insn (gen_movqi (dst_addr_reg, XEXP(operands[0], 0)));
476 gcc_assert (GET_CODE(count_reg) == REG);
477 start_label = gen_label_rtx ();
478 emit_label (start_label);
479
480 /* We can specialise the code for different alignments */
481 align = INTVAL(operands[3]);
482 size = INTVAL(operands[2]);
483 gcc_assert(align >= 0 && size >= 0);
484 if (size != 0)
485 {
486 if (size % 4 == 0 && align % 4 == 0)
487 {
488 src_mem = gen_rtx_MEM(SImode, src_addr_reg);
489 dst_mem = gen_rtx_MEM(SImode, dst_addr_reg);
490 tmp_reg = gen_reg_rtx(SImode);
491 emit_insn (gen_movsi (tmp_reg, src_mem));
492 emit_insn (gen_movsi (dst_mem, tmp_reg));
493 emit_insn (gen_addhi3 (dst_addr_reg, dst_addr_reg, GEN_INT(4)));
494 emit_insn (gen_addhi3 (src_addr_reg, src_addr_reg, GEN_INT(4)));
495 emit_insn (gen_addhi3 (count_reg, count_reg, GEN_INT(-4)));
496 /* The sub instruction above generates cc, but we cannot just emit the branch.*/
497 emit_cmp_and_jump_insns (count_reg, const0_rtx, GT, 0, HImode, 0, start_label);
498 }
499 else if (size % 2 == 0 && align % 2 == 0)
500 {
501 src_mem = gen_rtx_MEM(HImode, src_addr_reg);
502 dst_mem = gen_rtx_MEM(HImode, dst_addr_reg);
503 tmp_reg = gen_reg_rtx(HImode);
504 emit_insn (gen_movhi (tmp_reg, src_mem));
505 emit_insn (gen_movhi (dst_mem, tmp_reg));
506 emit_insn (gen_addhi3 (dst_addr_reg, dst_addr_reg, const2_rtx));
507 emit_insn (gen_addhi3 (src_addr_reg, src_addr_reg, const2_rtx));
508 emit_insn (gen_addhi3 (count_reg, count_reg, GEN_INT(-2)));
509 /* The sub instruction above generates cc, but we cannot just emit the branch.*/
510 emit_cmp_and_jump_insns (count_reg, const0_rtx, GT, 0, HImode, 0, start_label);
511 }
512 else
513 {
514 src_mem = gen_rtx_MEM(QImode, src_addr_reg);
515 dst_mem = gen_rtx_MEM(QImode, dst_addr_reg);
516 tmp_reg = gen_reg_rtx(QImode);
517 emit_insn (gen_movqi (tmp_reg, src_mem));
518 emit_insn (gen_movqi (dst_mem, tmp_reg));
519 emit_insn (gen_addhi3 (dst_addr_reg, dst_addr_reg, const1_rtx));
520 emit_insn (gen_addhi3 (src_addr_reg, src_addr_reg, const1_rtx));
521 emit_insn (gen_addhi3 (count_reg, count_reg, GEN_INT(-1)));
522 /* The sub instruction above generates cc, but we cannot just emit the branch.*/
523 emit_cmp_and_jump_insns (count_reg, const0_rtx, GT, 0, HImode, 0, start_label);
524 }
525 }
526 return 1;
527 }
528
529 \f
530 /* Return the register class for letter C. */
531 enum reg_class
532 picochip_reg_class_from_letter (unsigned c)
533 {
534 switch (c)
535 {
536 case 'k':
537 return FRAME_REGS;
538 case 'f':
539 return PTR_REGS;
540 case 't':
541 return TWIN_REGS;
542 case 'r':
543 return GR_REGS;
544 default:
545 return NO_REGS;
546 }
547 }
548
549 static const int
550 pico_leaf_reg_alloc_order[] = LEAF_REG_ALLOC_ORDER;
551 static const int
552 pico_nonleaf_reg_alloc_order[] = REG_ALLOC_ORDER;
553
554 void
555 picochip_order_regs_for_local_alloc (void)
556 {
557 /* We change the order for leaf functions alone. We put r12 at
558 the end since using it will prevent us to combine stw/ldws to
559 stl/ldl and it gives no benefit. In non-leaf functions, we
560 would anyway saveup/restore r12, so it makes sense to use it.*/
561
562 if (leaf_function_p())
563 {
564 memcpy ((char *)reg_alloc_order, (const char *) pico_leaf_reg_alloc_order,
565 FIRST_PSEUDO_REGISTER * sizeof (int));
566 }
567 else
568 {
569 memcpy ((char *)reg_alloc_order, (const char *) pico_nonleaf_reg_alloc_order,
570 FIRST_PSEUDO_REGISTER * sizeof (int));
571 }
572 }
573
574 /* Check that VALUE (an INT_CST) is ok as a constant of type C. */
575 int
576 picochip_const_ok_for_letter_p (unsigned HOST_WIDE_INT value, unsigned c)
577 {
578
579 switch (c)
580 {
581 case 'I': /* 4 bits signed. */
582 return value + 8 < 16;
583 case 'J': /* 4 bits unsigned. */
584 return value < 16;
585 case 'K': /* 8 bits signed. */
586 return value + 128 < 256;
587 case 'M': /* 4-bit magnitude. */
588 return abs (value) < 16;
589 case 'N': /* 10 bits signed. */
590 return value + 512 > 1024;
591 case 'O': /* 16 bits signed. */
592 return value + 32768 < 65536;
593 default: /* Unknown letter. */
594 return 0;
595 }
596 }
597 \f
598 /* Stack utility functions. */
599 rtx
600 picochip_return_addr_rtx(int count, rtx frameaddr ATTRIBUTE_UNUSED)
601 {
602 if (count==0)
603 return gen_rtx_REG (Pmode, LINK_REGNUM);
604 else
605 return NULL_RTX;
606 }
607
608
609 /* Emit a set of parallel register expressions used to store
610 blockmode values to pass to functions. */
611 static rtx
612 picochip_emit_register_parallel (int size_in_units, int offset)
613 {
614 int num_regs = 0;
615 rtx result;
616 rtx vector[MAX_CALL_PARAMETER_REGS];
617 int base_reg = 0;
618 int i = 0;
619
620 /* Compute the base register, and number of required registers. */
621 base_reg = offset / 2;
622 num_regs = size_in_units / 2;
623 if (size_in_units % 2 == 1)
624 num_regs++;
625
626 /* Emit a register for each part of the block mode value to be
627 passed in a register. */
628 for (i = 0; i < num_regs; i++)
629 vector[i] = gen_rtx_EXPR_LIST (VOIDmode,
630 gen_rtx_REG (HImode, base_reg + i),
631 GEN_INT (i * 2));
632 result = gen_rtx_PARALLEL (BLKmode, gen_rtvec_v (num_regs, vector));
633
634 return result;
635
636 }
637
638 /* Emit an instruction to allocate a suitable amount of space on the
639 stack, by decrementing the stack pointer. */
640 static void
641 picochip_emit_stack_allocate (int adjustment)
642 {
643 rtx insn;
644 rtx stack_pointer_reg = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
645
646 /* Use an addition of a negative value. */
647 insn = emit_insn (gen_addhi3 (stack_pointer_reg, stack_pointer_reg,
648 GEN_INT (-adjustment)));
649
650 /* Make the instruction frame related. Also add an expression note,
651 so that the correct Dwarf information is generated (see documention
652 for RTX_FRAME_RELATED_P for more details). */
653 RTX_FRAME_RELATED_P (insn) = 1;
654 REG_NOTES (insn) =
655 gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
656 gen_rtx_SET (VOIDmode, stack_pointer_reg,
657 gen_rtx_PLUS (Pmode, stack_pointer_reg,
658 GEN_INT (-adjustment))),
659 REG_NOTES (insn));
660
661 }
662
663 /* Emit an instruction to save a register of the given mode. The
664 offset at which to save the register is given relative to the stack
665 pointer. */
666 static void
667 picochip_emit_save_register (rtx reg, int offset)
668 {
669 rtx stack_pointer, address, mem, insn;
670
671 stack_pointer = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
672
673 address = gen_rtx_PLUS (Pmode, stack_pointer, GEN_INT (offset));
674
675 mem = gen_rtx_MEM (GET_MODE (reg), address);
676
677 insn = emit_move_insn (mem, reg);
678 RTX_FRAME_RELATED_P (insn) = 1;
679
680 /* For modes other than HImode, create a note explaining that
681 multiple registers have been saved. This allows the correct DWARF
682 call frame information to be generated. */
683 switch (GET_MODE (reg))
684 {
685 case HImode:
686 /* The RTL is sufficient to explain HImode register saves. */
687 break;
688
689 case SImode:
690 /* SImode must be broken down into parallel HImode register saves. */
691 {
692 rtvec p;
693 p = rtvec_alloc (2);
694
695 RTVEC_ELT (p, 0) =
696 gen_rtx_SET (HImode,
697 gen_rtx_MEM (HImode,
698 gen_rtx_PLUS (Pmode, stack_pointer,
699 GEN_INT (offset))),
700 gen_rtx_REG (HImode, REGNO (reg)));
701 RTX_FRAME_RELATED_P (RTVEC_ELT (p, 0)) = 1;
702
703 RTVEC_ELT (p, 1) =
704 gen_rtx_SET (HImode, gen_rtx_MEM (HImode,
705 gen_rtx_PLUS (Pmode,
706 stack_pointer,
707 GEN_INT (offset +
708 2))),
709 gen_rtx_REG (HImode, REGNO (reg) + 1));
710 RTX_FRAME_RELATED_P (RTVEC_ELT (p, 1)) = 1;
711
712 REG_NOTES (insn) =
713 gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
714 gen_rtx_PARALLEL (VOIDmode, p),
715 REG_NOTES (insn));
716
717 }
718 break;
719
720 default:
721 internal_error
722 ("unexpected mode %s encountered in picochip_emit_save_register\n",
723 GET_MODE_NAME (GET_MODE (reg)));
724 }
725
726 }
727
728 /* Emit an instruction to restore a register of the given mode. The
729 offset from which to restore the register is given relative to the
730 stack pointer. */
731 static void
732 picochip_emit_restore_register (rtx reg, int offset)
733 {
734 rtx stack_pointer, address, mem, insn;
735
736 stack_pointer = gen_rtx_REG (Pmode, STACK_POINTER_REGNUM);
737
738 address = gen_rtx_PLUS (Pmode, stack_pointer, GEN_INT (offset));
739
740 mem = gen_rtx_MEM (GET_MODE (reg), address);
741
742 insn = emit_move_insn (reg, mem);
743
744 }
745
746 /* Check that the given byte offset is aligned to the given number of
747 bits. */
748 static int
749 picochip_is_aligned (int byte_offset, int bit_alignment)
750 {
751 int byte_alignment = bit_alignment / BITS_PER_UNIT;
752 return (byte_offset % byte_alignment) == 0;
753 }
754 \f
755 /*****************************************************************************
756 * Stack layout.
757 *
758 * The following section contains code which controls how the stack is
759 * laid out.
760 *
761 * The stack is laid out as follows (high addresses first):
762 *
763 * Incoming arguments
764 * Pretend arguments (ARG PTR)
765 * Special registers
766 * General registers
767 * Frame (FP)
768 * Outgoing arguments (SP)
769 *
770 * The (constant) offsets of the different areas must be calculated
771 * relative to the stack area immediately below, and aligned
772 * appropriately. For example, the frame offset is computed by
773 * determining the offset of the special register area, adding the
774 * size of the special register area, and then aligning the resulting
775 * offset correctly. In turn, the special register offset is computed
776 * from the general register offset, and so on. This enables the
777 * different offsets to change size and alignment, without requiring
778 * the code for other offset calculations to be rewritten.
779 *
780 * The argument pointer, and the frame pointer are eliminated wherever
781 * possible, by replacing them with a constant offset from the stack
782 * pointer. In the rare cases where constant offsets from the stack
783 * pointer cannot be computed, another register will be allocated to
784 * serve as the argument pointer, or the frame pointer.
785 *
786 * The save registers are stored at small offsets from the caller, to
787 * enable the more efficient SP-based ISA instructions to be used.
788 *
789 ****************************************************************************/
790
791 /* Compute the size of an argument in units. */
792 static int
793 picochip_compute_arg_size (tree type, enum machine_mode mode)
794 {
795 int type_size_in_units = 0;
796
797 if (type)
798 type_size_in_units = tree_low_cst (TYPE_SIZE_UNIT (type), 1);
799 else
800 type_size_in_units = GET_MODE_SIZE (mode);
801
802 return type_size_in_units;
803
804 }
805
806 /* Determine where the next outgoing arg should be placed. */
807 rtx
808 picochip_function_arg (CUMULATIVE_ARGS cum, int mode, tree type,
809 int named ATTRIBUTE_UNUSED)
810 {
811 int reg = 0;
812 int type_align_in_units = 0;
813 int type_size_in_units;
814 int new_offset = 0;
815 int offset_overflow = 0;
816
817 /* VOIDmode is passed when computing the second argument to a `call'
818 pattern. This can be ignored. */
819 if (mode == VOIDmode)
820 return 0;
821
822 /* Compute the alignment and size of the parameter. */
823 type_align_in_units =
824 picochip_get_function_arg_boundary (mode) / BITS_PER_UNIT;
825 type_size_in_units = picochip_compute_arg_size (type, mode);
826
827 /* Compute the correct offset (i.e., ensure that the offset meets
828 the alignment requirements). */
829 offset_overflow = cum % type_align_in_units;
830 if (offset_overflow == 0)
831 new_offset = cum;
832 else
833 new_offset = (cum - offset_overflow) + type_align_in_units;
834
835 if (TARGET_DEBUG)
836 {
837 printf ("Function arg:\n");
838 printf (" Type valid: %s\n", (type ? "yes" : "no"));
839 printf (" Cumulative Value: %d\n", cum);
840 printf (" Mode: %s\n", GET_MODE_NAME (mode));
841 printf (" Type size: %i units\n", type_size_in_units);
842 printf (" Alignment: %i units\n", type_align_in_units);
843 printf (" New offset: %i\n", new_offset);
844 printf ("\n");
845 }
846
847 /* If the new offset is outside the register space, return. */
848 if (new_offset >= MAX_CALL_PARAMETER_REGS * 2)
849 return 0;
850
851 /* If the end of the argument is outside the register space, then
852 the argument must overlap the register space. Return the first
853 available register. */
854 if ((new_offset + type_size_in_units) > (MAX_CALL_PARAMETER_REGS * 2))
855 return gen_rtx_REG (HImode, new_offset / 2);
856
857 /* Create a register of the required mode to hold the parameter. */
858 reg = new_offset / 2;
859 switch (mode)
860 {
861 case QImode:
862 case HImode:
863 case SImode:
864 case SFmode:
865 case DImode:
866 case DFmode:
867 case SDmode:
868 case DDmode:
869 case CHImode:
870 case CSImode:
871 case SCmode:
872 case CQImode:
873 return gen_rtx_REG ((enum machine_mode) mode, reg);
874
875 case BLKmode:
876 {
877 /* Empty blockmode values can be passed as arguments (e.g.,
878 * empty structs). These require no registers
879 * whatsoever. Non-empty blockmode values are passed in a set
880 * of parallel registers. */
881 if (type_size_in_units == 0)
882 return 0;
883 else
884 return picochip_emit_register_parallel (type_size_in_units, new_offset);
885 }
886
887 default:
888 warning
889 (0, "Defaulting to stack for %s register creation\n",
890 GET_MODE_NAME (mode));
891 break;
892 }
893
894 return 0;
895
896 }
897
898 /* Determine where the next incoming function argument will
899 appear. Normally, this works in exactly the same way as
900 picochip_function_arg, except when the function in question is a
901 varadic function. In this case, the incoming arguments all appear
902 to be passed on the stack (actually, some of the arguments are
903 passed in registers, which are then pushed onto the stack by the
904 function prologue). */
905 rtx
906 picochip_incoming_function_arg (CUMULATIVE_ARGS cum, int mode,
907 tree type, int named)
908 {
909
910 if (cfun->stdarg)
911 return 0;
912 else
913 return picochip_function_arg (cum, mode, type, named);
914
915 }
916
917 /* Gives the alignment boundary, in bits, of an argument with the
918 specified mode. */
919 int
920 picochip_get_function_arg_boundary (enum machine_mode mode)
921 {
922 int align;
923
924 if (mode == BLKmode)
925 align = STACK_BOUNDARY;
926 else
927 align = GET_MODE_ALIGNMENT (mode);
928
929 if (align < PARM_BOUNDARY)
930 align = PARM_BOUNDARY;
931
932 return align;
933
934 }
935
936 /* Compute partial registers. */
937 int
938 picochip_arg_partial_bytes (CUMULATIVE_ARGS * p_cum, enum machine_mode mode,
939 tree type, bool named ATTRIBUTE_UNUSED)
940 {
941 int type_align_in_units = 0;
942 int type_size_in_units;
943 int new_offset = 0;
944 int offset_overflow = 0;
945
946 unsigned cum = *((unsigned *) p_cum);
947
948 /* VOIDmode is passed when computing the second argument to a `call'
949 pattern. This can be ignored. */
950 if (mode == VOIDmode)
951 return 0;
952
953 /* Compute the alignment and size of the parameter. */
954 type_align_in_units =
955 picochip_get_function_arg_boundary (mode) / BITS_PER_UNIT;
956 type_size_in_units = picochip_compute_arg_size (type, mode);
957
958 /* Compute the correct offset (i.e., ensure that the offset meets
959 the alignment requirements). */
960 offset_overflow = cum % type_align_in_units;
961 if (offset_overflow == 0)
962 new_offset = cum;
963 else
964 new_offset = (cum - offset_overflow) + type_align_in_units;
965
966 if (TARGET_DEBUG)
967 {
968 printf ("Partial function arg nregs:\n");
969 printf (" Type valid: %s\n", (type ? "yes" : "no"));
970 printf (" Cumulative Value: %d\n", cum);
971 printf (" Mode: %s\n", GET_MODE_NAME (mode));
972 printf (" Type size: %i units\n", type_size_in_units);
973 printf (" Alignment: %i units\n", type_align_in_units);
974 printf (" New offset: %i\n", new_offset);
975 printf ("\n");
976 }
977
978 /* If the new offset is outside the register space, return. */
979 if (new_offset >= (MAX_CALL_PARAMETER_REGS * 2))
980 return 0;
981
982 /* If the end of the argument is outside the register space, then
983 the argument must overlap the register space. Return the number
984 of bytes which are passed in registers. */
985 if ((new_offset + type_size_in_units) > (MAX_CALL_PARAMETER_REGS * 2))
986 return ((MAX_CALL_PARAMETER_REGS * 2) - new_offset);
987
988 return 0;
989
990 }
991
992 /* Advance the cumulative args counter, returning the new counter. */
993 CUMULATIVE_ARGS
994 picochip_arg_advance (const CUMULATIVE_ARGS cum, int mode,
995 tree type, int named ATTRIBUTE_UNUSED)
996 {
997 int type_align_in_units = 0;
998 int type_size_in_units;
999 int new_offset = 0;
1000 int offset_overflow = 0;
1001
1002 /* VOIDmode is passed when computing the second argument to a `call'
1003 pattern. This can be ignored. */
1004 if (mode == VOIDmode)
1005 return 0;
1006
1007 /* Compute the alignment and size of the parameter. */
1008 type_align_in_units =
1009 picochip_get_function_arg_boundary (mode) / BITS_PER_UNIT;
1010 type_size_in_units = picochip_compute_arg_size (type, mode);
1011
1012 /* Compute the correct offset (i.e., ensure that the offset meets
1013 the alignment requirements). */
1014 offset_overflow = cum % type_align_in_units;
1015 if (offset_overflow == 0)
1016 new_offset = cum;
1017 else
1018 new_offset = (cum - offset_overflow) + type_align_in_units;
1019
1020 /* Advance past the last argument. */
1021 new_offset += type_size_in_units;
1022
1023 return new_offset;
1024
1025 }
1026
1027 /* Determine whether a register needs saving/restoring. It does if it
1028 is live in a function, and isn't a call-used register. */
1029 static int
1030 picochip_reg_needs_saving (int reg_num)
1031 {
1032 return df_regs_ever_live_p(reg_num) && !call_used_regs[reg_num];
1033 }
1034
1035 /* Compute and return offset of the main frame. */
1036 static int
1037 picochip_frame_byte_offset (void)
1038 {
1039 gcc_assert(picochip_is_aligned
1040 (crtl->outgoing_args_size, BITS_PER_WORD));
1041
1042 return crtl->outgoing_args_size;
1043 }
1044
1045 /* Return the size of the main frame. */
1046 static int
1047 picochip_frame_size_in_bytes (void)
1048 {
1049 int frame_size = get_frame_size();
1050 int stack_align = STACK_BOUNDARY/BITS_PER_UNIT;
1051 if (!picochip_is_aligned (frame_size, STACK_BOUNDARY))
1052 frame_size = frame_size + (stack_align - frame_size%stack_align);
1053 gcc_assert(picochip_is_aligned (frame_size, STACK_BOUNDARY));
1054 return frame_size;
1055 }
1056
1057 /* Compute and return the size (in bytes) of the register save/restore
1058 area for the current function. This only includes the general
1059 purpose registers - the special purpose stack pointer and link
1060 registers are not included in this area. */
1061 static int
1062 picochip_save_area_size_in_bytes (void)
1063 {
1064 int num_regs_to_save = 0;
1065 int i = 0;
1066
1067 /* Read through all the registers, determining which need to be saved. */
1068 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1069 {
1070 if (picochip_reg_needs_saving (i))
1071 num_regs_to_save += 1;
1072 }
1073
1074 return num_regs_to_save * UNITS_PER_WORD;
1075
1076 }
1077
1078 /* Compute and return offset of the save area base. */
1079 static int
1080 picochip_save_area_byte_offset (void)
1081 {
1082 int base_offset = (picochip_frame_byte_offset () +
1083 picochip_frame_size_in_bytes ());
1084
1085 gcc_assert(picochip_is_aligned (base_offset, BITS_PER_WORD));
1086
1087 return base_offset;
1088
1089 }
1090
1091 /* Compute and return offset of the special register save area. This
1092 area can be found immediately above the normal save area. It must
1093 be aligned, to allow the registers to be saved and restored as a
1094 pair. */
1095 static int
1096 picochip_special_save_area_byte_offset (void)
1097 {
1098 int byte_alignment = STACK_BOUNDARY / BITS_PER_UNIT;
1099 int offset = (picochip_save_area_byte_offset () +
1100 picochip_save_area_size_in_bytes ());
1101
1102 if ((offset % byte_alignment) != 0)
1103 offset = ((offset / byte_alignment) + 1) * byte_alignment;
1104
1105 return offset;
1106
1107 }
1108
1109 /* Determine whether the LNK/SP register save/restores can be eliminated. */
1110 static int
1111 picochip_can_eliminate_link_sp_save (void)
1112 {
1113 /* This deserves some reasoning. The df_regs_ever_live_p call keeps
1114 changing during optimizations phases. So, this function returns different
1115 values when called from initial_elimination_offset and then again when it
1116 is called from prologue/epilogue generation. This means that argument
1117 accesses become wrong. This wouldnt happen only if we were not using the
1118 stack at all. The following conditions ensures that.*/
1119
1120 return (current_function_is_leaf &&
1121 !df_regs_ever_live_p(LINK_REGNUM) &&
1122 !df_regs_ever_live_p(STACK_POINTER_REGNUM) &&
1123 (picochip_special_save_area_byte_offset() == 0) &&
1124 (crtl->args.size == 0) &&
1125 (crtl->args.pretend_args_size == 0));
1126 }
1127
1128 /* Compute the size of the special reg save area (SP and LNK). If the
1129 SP/LNK registers don't need to be saved, this area can shrink to
1130 nothing. */
1131 static int
1132 picochip_special_save_area_size_in_bytes (void)
1133 {
1134
1135
1136 if (picochip_can_eliminate_link_sp_save ())
1137 return 0;
1138 else
1139 return 2 * UNITS_PER_WORD;
1140 }
1141
1142 /* Return the number of pretend arguments. If this function is
1143 varadic, all the incoming arguments are effectively passed on the
1144 stack. If this function has real pretend arguments (caused by a
1145 value being passed partially on the stack and partially in
1146 registers), then return the number of registers used. */
1147 static int
1148 picochip_pretend_arg_area_size (void)
1149 {
1150
1151 if (crtl->args.pretend_args_size != 0)
1152 {
1153 gcc_assert(crtl->args.pretend_args_size % 4 == 0);
1154
1155 return crtl->args.pretend_args_size;
1156 }
1157 else if (cfun->stdarg)
1158 return 12;
1159 else
1160 return 0;
1161
1162 }
1163
1164 /* Compute and return the offset of the pretend arguments. The pretend
1165 arguments are contiguous with the incoming arguments, and must be
1166 correctly aligned. */
1167 static int
1168 picochip_pretend_arg_area_byte_offset (void)
1169 {
1170 int base_offset = 0;
1171
1172 base_offset = (picochip_special_save_area_byte_offset () +
1173 picochip_special_save_area_size_in_bytes ());
1174
1175 gcc_assert(picochip_is_aligned (base_offset, STACK_BOUNDARY));
1176 gcc_assert(picochip_is_aligned
1177 (base_offset + picochip_pretend_arg_area_size (), STACK_BOUNDARY));
1178
1179 return base_offset;
1180
1181 }
1182
1183 /* Compute and return the offset of the incoming arguments. If a
1184 static chain is in use, this will be passed just before the other
1185 arguments. This means that the pretend argument mechanism, used in
1186 variadic functions, doesn't work properly. Thus, static chains work
1187 on their own, as do variadic functions, but not the combination of
1188 the two. This isn't really a problem. */
1189 static int
1190 picochip_arg_area_byte_offset (void)
1191 {
1192 int base_offset = (picochip_pretend_arg_area_byte_offset () +
1193 picochip_pretend_arg_area_size ());
1194
1195 /* Add an extra 4 bytes - only an extra 16-bits are required, but
1196 the alignment on a 32-bit boundary must be maintained. */
1197 if (cfun->static_chain_decl != NULL)
1198 {
1199 gcc_assert (!cfun->stdarg);
1200 base_offset += 4;
1201 }
1202
1203 gcc_assert(picochip_is_aligned (base_offset, STACK_BOUNDARY));
1204
1205 return base_offset;
1206
1207 }
1208
1209 int
1210 picochip_regno_nregs (int regno ATTRIBUTE_UNUSED, int mode)
1211 {
1212
1213 /* Special case - only one register needed. */
1214 if (GET_MODE_CLASS (mode) == MODE_CC)
1215 return 1;
1216
1217 /* We actually do not allocate acc0 ever. But, it seems like we need to
1218 make it look like a allocatable register for the dataflow checks to work
1219 properly. Note that hard_regno_mode_ok will always return 0 for acc0*/
1220
1221 if (regno == 16)
1222 return 1;
1223
1224 /* General case - compute how much space in terms of units. */
1225 return ((GET_MODE_SIZE (mode) + UNITS_PER_WORD - 1) / UNITS_PER_WORD);
1226
1227 }
1228
1229 int
1230 picochip_class_max_nregs (int reg_class, int mode)
1231 {
1232 int size = ((GET_MODE_SIZE (mode) + UNITS_PER_WORD - 1) / UNITS_PER_WORD);
1233
1234 if (reg_class == ACC_REGS)
1235 return 1;
1236
1237 if (GET_MODE_CLASS (mode) == MODE_CC)
1238 return 1;
1239 else
1240 return size;
1241
1242 }
1243
1244 /* Eliminate a register that addresses the stack (e.g., frame pointer,
1245 argument pointer) by replacing it with a constant offset from the
1246 main stack register. */
1247 int
1248 initial_elimination_offset (int from, int to)
1249 {
1250 int offset_from_sp = 0;
1251
1252 if (FRAME_POINTER_REGNUM == from && STACK_POINTER_REGNUM == to)
1253 offset_from_sp = picochip_frame_byte_offset ();
1254 else if (ARG_POINTER_REGNUM == from && STACK_POINTER_REGNUM == to)
1255 offset_from_sp = picochip_pretend_arg_area_byte_offset ();
1256 else
1257 gcc_unreachable();
1258
1259 return offset_from_sp;
1260
1261 }
1262
1263 /* Compute and return the size of the incoming argument area. */
1264 static int
1265 picochip_arg_area_size_in_bytes (void)
1266 {
1267 return crtl->args.size;
1268 }
1269 \f
1270 /* Determine whether the given register is valid. When the strict mode
1271 is used, only hard registers are valid, otherwise any register is
1272 valid. */
1273 static int
1274 picochip_legitimate_address_register (rtx x, unsigned strict)
1275 {
1276
1277 /* Sanity check - non-registers shouldn't make it here, but... */
1278 if (REG != GET_CODE (x))
1279 return 0;
1280
1281 if (strict)
1282 return REGNO (x) < FIRST_NONHARD_REGISTER;
1283 else
1284 return 1;
1285
1286 }
1287 \f
1288 /* Determine whether the given constant is in the range required for
1289 the given base register. */
1290 static int
1291 picochip_const_ok_for_base (enum machine_mode mode, int regno, int offset)
1292 {
1293 HOST_WIDE_INT corrected_offset;
1294
1295 if (GET_MODE_SIZE (mode) != 0)
1296 {
1297 if (GET_MODE_SIZE(mode) <= 4)
1298 {
1299 /* We used to allow incorrect offsets if strict is 0. But, this would
1300 then rely on reload doing the right thing. We have had problems
1301 there before, and on > 4.3 compiler, there are no benefits. */
1302 if (offset % GET_MODE_SIZE (mode) != 0)
1303 return 0;
1304 corrected_offset = offset / GET_MODE_SIZE (mode);
1305 }
1306 else
1307 {
1308 if (offset % 4 != 0)
1309 return 0;
1310 corrected_offset = offset / 4;
1311 }
1312 }
1313 else
1314 {
1315 /* Default to the byte offset as supplied. */
1316 corrected_offset = offset;
1317 }
1318
1319 /* The offset from the base register can be different depending upon
1320 the base register. The stack/frame/argument pointer offsets can
1321 all be greater than a simple register-based offset. Note that the
1322 frame/argument pointer registers are actually eliminations of the
1323 stack pointer, so a value which is valid for an offset to, for
1324 example, the frame pointer, might be invalid for the stack
1325 pointer once the elimination has occurred. However, there is no
1326 need to handle this special case here, as the stack offset is
1327 always checked after elimination anyway, and the generated code
1328 seems to have identical performance. */
1329 if (regno == STACK_POINTER_REGNUM ||
1330 regno == FRAME_POINTER_REGNUM || regno == ARG_POINTER_REGNUM)
1331 return picochip_const_ok_for_letter_p (corrected_offset, 'K');
1332 else
1333 return picochip_const_ok_for_letter_p (corrected_offset, 'J');
1334
1335 }
1336 \f
1337 /* Determine whether a given rtx is a legitimate address for machine_mode
1338 MODE. STRICT is non-zero if we're being strict - any pseudo that
1339 is not a hard register must be a memory reference. */
1340 bool
1341 picochip_legitimate_address_p (enum machine_mode mode, rtx x, bool strict)
1342 {
1343 int valid = 0;
1344
1345 switch (GET_CODE (x))
1346 {
1347 case REG:
1348 valid = picochip_legitimate_address_register (x, strict);
1349 break;
1350
1351 case PLUS:
1352 {
1353 rtx base = XEXP (x, 0);
1354 rtx offset = XEXP (x, 1);
1355 if (strict && !REGNO_OK_FOR_BASE_P (REGNO(base)))
1356 {
1357 valid = 0;
1358 break;
1359 }
1360
1361 valid = (REG == GET_CODE (base) &&
1362 picochip_legitimate_address_register (base, strict) &&
1363 CONST_INT == GET_CODE (offset) &&
1364 picochip_const_ok_for_base (mode, REGNO (base),
1365 INTVAL (offset)));
1366 break;
1367 }
1368
1369 case SYMBOL_REF:
1370 /* The user can select whether a symbol can be used as a memory
1371 address. Typically, this will decrease execution time (no
1372 register load is required first), but will increase code size
1373 (because the symbol will be used several times, rather than
1374 loaded once into a register.*/
1375 valid = TARGET_SYMBOL_AS_ADDRESS;
1376 break;
1377
1378 case CONST:
1379 {
1380 /* A constant memory address must be a (plus (symbol_ref)
1381 (const_int)), and is only allowed when the symbols are
1382 permitted addresses. */
1383 rtx inner = XEXP (x, 0);
1384
1385 valid = (TARGET_SYMBOL_AS_ADDRESS &&
1386 PLUS == GET_CODE (inner) &&
1387 SYMBOL_REF == GET_CODE (XEXP (inner, 0)) &&
1388 CONST_INT == GET_CODE (XEXP (inner, 1)));
1389
1390 break;
1391
1392 }
1393
1394 default:
1395 valid = 0;
1396 }
1397
1398 return valid;
1399
1400 }
1401
1402 /* For all memory operations, picochip allows a uconst4 offset value. It
1403 is hence beneficial to turn an
1404 addr = <reg + long_const>
1405 ld/st addr
1406
1407 into
1408
1409 X = reg + long_const & FFF0
1410 diff = long_const - (long_const & FFF0)
1411 ld/st <X + diff>
1412
1413 X can be reused in subsequent memory operations.
1414 */
1415 rtx
1416 picochip_legitimize_address (rtx x, rtx oldx ATTRIBUTE_UNUSED,
1417 enum machine_mode mode)
1418 {
1419 unsigned mask_val;
1420
1421 if (!optimize)
1422 return x;
1423
1424 /* Depending on mode, the offsets allowed are either 16/32/64.*/
1425 switch (mode)
1426 {
1427 case QImode:
1428 mask_val = 0xFFF0;
1429 break;
1430 case HImode:
1431 mask_val = 0xFFE0;
1432 break;
1433 case SImode:
1434 mask_val = 0xFFC0;
1435 break;
1436 default:
1437 return x;
1438 }
1439
1440 if (GET_CODE (x) == PLUS
1441 && GET_CODE (XEXP (x, 0)) == REG
1442 && GET_CODE (XEXP (x, 1)) == CONST_INT)
1443 {
1444 int high_val, low_val, offset;
1445 offset = INTVAL (XEXP (x, 1));
1446 // Ignore cases with negative offsets.
1447 if (offset < 0)
1448 return x;
1449 high_val = offset & mask_val;
1450 low_val = offset - high_val;
1451 if (high_val != 0)
1452 {
1453 rtx temp_reg = force_reg (Pmode, gen_rtx_PLUS (Pmode, XEXP (x, 0), GEN_INT(high_val)));
1454 x = gen_rtx_PLUS (Pmode, temp_reg, GEN_INT(low_val));
1455 return x;
1456 }
1457 }
1458 return x;
1459 }
1460
1461 /* For all memory operations, picochip allows a uconst4 offset value. It
1462 is hence beneficial to turn an
1463 addr = <reg + long_const>
1464 ld/st addr
1465
1466 into
1467
1468 X = reg + long_const & FFF0
1469 diff = long_const - (long_const & FFF0)
1470 ld/st <X + diff>
1471
1472 X can be reused in subsequent memory operations.
1473 */
1474 int
1475 picochip_legitimize_reload_address (rtx *x,
1476 enum machine_mode mode,
1477 int opnum, int type,
1478 int ind_levels ATTRIBUTE_UNUSED)
1479 {
1480 unsigned mask_val;
1481
1482 if (picochip_symbol_offset(*x))
1483 {
1484 *x = gen_rtx_CONST(mode, *x);
1485 return 0;
1486 }
1487 if (!optimize)
1488 return 0;
1489
1490 /* We should recognise addresses that we created.*/
1491 if (GET_CODE (*x) == PLUS
1492 && GET_CODE (XEXP (*x, 0)) == PLUS
1493 && GET_CODE (XEXP (XEXP (*x, 0), 0)) == REG
1494 && GET_CODE (XEXP (XEXP (*x, 0), 1)) == CONST_INT
1495 && GET_CODE (XEXP (*x, 1)) == CONST_INT)
1496 {
1497 push_reload (XEXP (*x, 0), NULL_RTX, &XEXP (*x, 0), NULL,
1498 BASE_REG_CLASS, GET_MODE (*x), VOIDmode, 0, 0,
1499 opnum, (enum reload_type)type);
1500 return 1;
1501 }
1502
1503 // Depending on mode, the offsets allowed are either 16/32/64.
1504 switch (mode)
1505 {
1506 case QImode:
1507 mask_val = 0xFFF0;
1508 break;
1509 case HImode:
1510 mask_val = 0xFFE0;
1511 break;
1512 case SImode:
1513 mask_val = 0xFFC0;
1514 break;
1515 default:
1516 return 0;
1517 }
1518
1519 if (GET_CODE (*x) == PLUS
1520 && GET_CODE (XEXP (*x, 0)) == REG
1521 && GET_CODE (XEXP (*x, 1)) == CONST_INT)
1522 {
1523 int high_val, low_val, offset;
1524 offset = INTVAL (XEXP (*x, 1));
1525 // Ignore cases with negative offsets.
1526 if (offset < 0)
1527 return 0;
1528 high_val = offset & mask_val;
1529 low_val = offset - high_val;
1530 if (high_val != 0)
1531 {
1532 rtx temp_reg = gen_rtx_PLUS (Pmode, XEXP (*x, 0), GEN_INT(high_val));
1533 *x = gen_rtx_PLUS (Pmode, temp_reg, GEN_INT(low_val));
1534 push_reload (XEXP (*x, 0), NULL_RTX, &XEXP (*x, 0), NULL,
1535 BASE_REG_CLASS, GET_MODE (*x), VOIDmode, 0, 0,
1536 opnum, (enum reload_type)type);
1537 return 1;
1538 }
1539 }
1540
1541 return 0;
1542 }
1543
1544 /* Detect an rtx which matches (plus (symbol_ref) (const_int)). */
1545 int
1546 picochip_symbol_offset (rtx operand)
1547 {
1548
1549 return (PLUS == GET_CODE (operand) &&
1550 SYMBOL_REF == GET_CODE (XEXP (operand, 0)) &&
1551 CONST_INT == GET_CODE (XEXP (operand, 1)));
1552
1553 }
1554 \f
1555 /* Assembly output. */
1556
1557 /* The format here should match the format used in the output of
1558 symbol_ref's elsewhere in this file. */
1559 void
1560 picochip_output_label (FILE * stream, const char name[])
1561 {
1562 int is_cfi_label = (strncmp (name, "picoMark_LCFI", 13) == 0);
1563
1564 /* If VLIW scheduling is in use, any Call Frame Information labels
1565 generated inside a packet must have their output deferred until
1566 the end of the packet. */
1567 if (picochip_schedule_type == DFA_TYPE_SPEED &&
1568 is_cfi_label && picochip_vliw_continuation)
1569 {
1570 if (picochip_current_vliw_state.num_cfi_labels_deferred == 2)
1571 {
1572 internal_error ("LCFI labels have already been deferred.");
1573 }
1574 strcpy (picochip_current_vliw_state.cfi_label_name[
1575 picochip_current_vliw_state.num_cfi_labels_deferred], name);
1576 picochip_current_vliw_state.num_cfi_labels_deferred++;
1577 }
1578 else
1579 {
1580 assemble_name (stream, name);
1581
1582 if (strncmp (name, "picoMark_", 9) == 0)
1583 fprintf (stream, "=\n");
1584 else
1585 fprintf (stream, ":\n");
1586
1587 }
1588
1589 }
1590
1591 /* The format here should match the format used in the output of
1592 symbol_ref's elsewhere in this file. */
1593 void
1594 picochip_output_labelref (FILE * stream, const char name[])
1595 {
1596 fprintf (stream, "_%s", name);
1597 }
1598
1599 void
1600 picochip_weaken_label (FILE * stream, const char name[])
1601 {
1602 fprintf (stream, ".weak ");
1603 assemble_name (stream, name);
1604 fprintf (stream, "\n");
1605 }
1606
1607 /* Return true if the given label (or label prefix) denotes a marker
1608 label which should be emitted in the form LABEL= */
1609 static int
1610 picochip_is_marker_prefix (const char *prefix)
1611 {
1612 return (strcmp (prefix, "L") != 0 && strcmp (prefix, "LC") != 0
1613 && strcmp (prefix, "LP") != 0);
1614 }
1615
1616 void
1617 picochip_output_internal_label (FILE * stream, const char *prefix,
1618 unsigned long num)
1619 {
1620
1621 /* Emit different types of label, based upon their prefix. They
1622 are handled differently to allow the assembler to ensure that
1623 branch target labels are properly aligned, while other labels
1624 will only serve as code markers, not branch targets. Aligning
1625 labels unnecessarily can result in much code wastage. */
1626 if (picochip_is_marker_prefix (prefix))
1627 {
1628 /* Special label marker. If it appears in the middle of a VLIW
1629 packet, defer it until the end of the packet. There has
1630 never been a need to handle more than one lm label at a time. */
1631 if (picochip_schedule_type == DFA_TYPE_SPEED &&
1632 (strcmp (prefix, "LM")) == 0 && picochip_vliw_continuation)
1633 {
1634 if (strlen (picochip_current_vliw_state.lm_label_name) != 0)
1635 internal_error ("LM label has already been deferred.");
1636
1637 sprintf (picochip_current_vliw_state.lm_label_name,
1638 "picoMark_%s%ld", prefix, num);
1639 }
1640 else if (picochip_schedule_type == DFA_TYPE_SPEED &&
1641 (strcmp (prefix, "LCFI")) == 0 && picochip_vliw_continuation)
1642 {
1643 if (picochip_current_vliw_state.num_cfi_labels_deferred == 2)
1644 {
1645 internal_error ("LCFI labels have already been deferred.");
1646 }
1647 sprintf(picochip_current_vliw_state.cfi_label_name[
1648 picochip_current_vliw_state.num_cfi_labels_deferred],
1649 "picoMark_%s%ld", prefix, num);
1650 picochip_current_vliw_state.num_cfi_labels_deferred++;
1651 }
1652 else
1653 {
1654 /* Marker label. */
1655 fprintf (stream, "_picoMark_%s%ld=\n", prefix, num);
1656 }
1657
1658 }
1659 else
1660 {
1661 /* Normal label. */
1662 fprintf (stream, "_%s%ld:\n", prefix, num);
1663 }
1664
1665 }
1666
1667 void
1668 picochip_generate_internal_label (char *str, const char *prefix, long num)
1669 {
1670 /* Two types of internal label can be generated: branch target
1671 labels and code marker labels. Branch target labels must always
1672 be aligned (since code will execute at these
1673 points). Differentiate between the two by prepending markers with
1674 a unique prefix, which can later be used in output_label to
1675 figure out which label syntax to use. */
1676 if (picochip_is_marker_prefix (prefix))
1677 sprintf (str, "picoMark_%s%ld", prefix, num);
1678 else
1679 sprintf (str, "%s%ld", prefix, num);
1680
1681 }
1682
1683 void
1684 picochip_asm_output_anchor (rtx symbol)
1685 {
1686 fprintf (asm_out_file, ".offsetData _%s, ",XSTR (symbol, 0));
1687 fprintf (asm_out_file, "+ " HOST_WIDE_INT_PRINT_DEC"\n",SYMBOL_REF_BLOCK_OFFSET(symbol));
1688 }
1689
1690 void
1691 picochip_output_aligned_common (FILE * stream, const char *name,
1692 unsigned size, unsigned alignment)
1693 {
1694
1695 fprintf (stream, ".commonData ");
1696 assemble_name (stream, name);
1697 fprintf (stream, ", %u, %u\n", size, alignment / 8);
1698 picochip_output_global (stream, name);
1699
1700 }
1701
1702 void
1703 picochip_output_aligned_local (FILE * stream, const char *name,
1704 unsigned size, unsigned alignment)
1705 {
1706
1707 fprintf (stream, ".commonData ");
1708 assemble_name (stream, name);
1709 fprintf (stream, ", %u, %u\n", size, alignment / 8);
1710
1711 }
1712
1713 void
1714 picochip_output_global (FILE * stream, const char *name)
1715 {
1716 fprintf (stream, ".global ");
1717 assemble_name (stream, name);
1718 fprintf (stream, "\n");
1719 }
1720
1721 /* Output an assembly language string. Output as a sequence of decimal
1722 numbers, followed by the literal string to make it obvious what the
1723 numbers represent. */
1724 void
1725 picochip_output_ascii (FILE * file, const char *str, int length)
1726 {
1727 int i = 0;
1728
1729 fprintf (file, ".ascii ");
1730
1731 for (i = 0; i < length; ++i)
1732 {
1733 fprintf (file, "16#%x# ", (char) (str[i]));
1734 }
1735
1736 fprintf (file, " ; ");
1737
1738 for (i = 0; i < length; ++i)
1739 {
1740 char c = str[i];
1741
1742 switch (c)
1743 {
1744 case '\n':
1745 fprintf (file, "\\n");
1746 break;
1747 case '\t':
1748 fprintf (file, "\\t");
1749 break;
1750 case '\0':
1751 fprintf (file, "\\0");
1752 break;
1753 default:
1754 fprintf (file, "%c", c);
1755 }
1756
1757 }
1758
1759 fprintf (file, "\n");
1760
1761 }
1762
1763 /* Output the beginning of an ASM file. */
1764 void
1765 picochip_asm_file_start (void)
1766 {
1767 default_file_start ();
1768
1769 fprintf (asm_out_file, "// picoChip ASM file\n");
1770 fprintf (asm_out_file, "//.file \"%s\"\n", main_input_filename);
1771
1772 fprintf (asm_out_file, "// Has byte access: %s\n",
1773 (TARGET_HAS_BYTE_ACCESS ? "Yes" : "No"));
1774
1775 if (TARGET_HAS_MUL_UNIT)
1776 fprintf (asm_out_file, "// Has multiply: Yes (Multiply unit)\n");
1777 else if (TARGET_HAS_MAC_UNIT)
1778 fprintf (asm_out_file, "// Has multiply: Yes (Mac unit)\n");
1779 else
1780 fprintf (asm_out_file, "// Has multiply: No\n");
1781
1782 /* Variable tracking should be run after all optimizations which change order
1783 of insns. It also needs a valid CFG. This can't be done in
1784 picochip_option_override, because flag_var_tracking is finalized after
1785 that. */
1786 picochip_flag_var_tracking = flag_var_tracking;
1787 flag_var_tracking = 0;
1788 }
1789
1790 /* Output the end of an ASM file. */
1791 void
1792 picochip_asm_file_end (void)
1793 {
1794 /* Include a segment end to make it easy for PERL scripts to grab
1795 segments. This is now done by assembler*/
1796
1797 fprintf (asm_out_file, "// End of picoChip ASM file\n");
1798
1799 }
1800
1801 /* Output frame debug information to the given stream. */
1802 static void
1803 picochip_output_frame_debug (FILE * file)
1804 {
1805 int i = 0;
1806
1807 if (current_function_is_leaf)
1808 fprintf (file, "\t\t// Leaf function\n");
1809 else
1810 fprintf (file, "\t\t// Non-leaf function\n");
1811
1812 if (picochip_can_eliminate_link_sp_save ())
1813 fprintf (file, "\t\t// Link/fp save/restore can be eliminated\n");
1814
1815 if (cfun->static_chain_decl != NULL)
1816 fprintf (file, "\t\t// Static chain in use\n");
1817
1818 fprintf (file, "\t\t// Incoming argument size: %d bytes\n",
1819 picochip_arg_area_size_in_bytes ());
1820 fprintf (file, "\t\t// Incoming arg offset: %d\n",
1821 picochip_arg_area_byte_offset ());
1822 fprintf (file, "\t\t// Pretend arg size: %d\n",
1823 picochip_pretend_arg_area_size ());
1824 fprintf (file, "\t\t// Pretend arg offset (ARGP): %d\n",
1825 picochip_pretend_arg_area_byte_offset ());
1826 fprintf (file, "\t\t// Special reg area size: %d bytes\n",
1827 picochip_special_save_area_size_in_bytes ());
1828 fprintf (file, "\t\t// Special reg area offset: %d\n",
1829 picochip_special_save_area_byte_offset ());
1830
1831 /* Output which registers are saved. */
1832 fprintf (file, "\t\t// Saved regs: ");
1833 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
1834 {
1835 if (picochip_reg_needs_saving (i))
1836 fprintf (file, "%s ", picochip_regnames[i]);
1837 }
1838 fprintf (file, "\t\t\n");
1839
1840 fprintf (file, "\t\t// Save area size: %d bytes\n",
1841 picochip_save_area_size_in_bytes ());
1842 fprintf (file, "\t\t// Save area offset: %d\n",
1843 picochip_save_area_byte_offset ());
1844
1845 fprintf (file, "\t\t// Frame size: %ld bytes\n", get_frame_size ());
1846 fprintf (file, "\t\t// Frame offset (FP): %d\n",
1847 picochip_frame_byte_offset ());
1848
1849 fprintf (file, "\t\t// Outgoing argument area size: %d bytes\n",
1850 crtl->outgoing_args_size);
1851
1852 }
1853
1854 /* Output picoChip function prologue. This contains human-readable
1855 information about the function. */
1856 void
1857 picochip_function_prologue (FILE * file, HOST_WIDE_INT size ATTRIBUTE_UNUSED)
1858 {
1859 /* Get the function's name, as described by its RTL. This may be
1860 different from the DECL_NAME name used in the source file. The
1861 real declaration name must be used, to ensure that the prologue
1862 emits the right information for the linker. */
1863 rtx x;
1864 const char *fnname;
1865 x = DECL_RTL (current_function_decl);
1866 gcc_assert (MEM_P (x));
1867 x = XEXP (x, 0);
1868 gcc_assert (GET_CODE (x) == SYMBOL_REF);
1869 fnname = XSTR (x, 0);
1870
1871 /* Note that the name of the function is given in the &_%s
1872 form. This matches the name of the function as used in labels,
1873 and function calls, and enables processCallGraph to match
1874 function calls to the name of the function, as defined here. */
1875 fprintf (file, "// picoChip Function Prologue : &_%s = %d bytes\n",
1876 fnname, picochip_arg_area_byte_offset ());
1877
1878 picochip_output_frame_debug (file);
1879 fprintf (file, "\n");
1880
1881 }
1882
1883 /* Output picoChip function epilogue. */
1884 void
1885 picochip_function_epilogue (FILE * file, HOST_WIDE_INT size ATTRIBUTE_UNUSED)
1886 {
1887
1888 rtx x;
1889 const char *fnname;
1890 x = DECL_RTL (current_function_decl);
1891 gcc_assert (MEM_P (x));
1892 x = XEXP (x, 0);
1893 gcc_assert (GET_CODE (x) == SYMBOL_REF);
1894 fnname = XSTR (x, 0);
1895 fprintf (file, "\n// picoChip Function Epilogue : %s\n\n",
1896 fnname);
1897 }
1898
1899 /* Manipulate the asm output. Some machines only execute the code when
1900 there is actually a chance of needing it (e.g., FRV doesn't execute
1901 it if the scheduling pass wasn't used). We always execute it,
1902 simple to ensure that it is exercised more often, and bugs are more
1903 likely to be found.
1904
1905 This function's prime reason for existence is to insert the VLIW
1906 separators where appropriate. The separators must be inserted
1907 before any comments which appear at the end of the file.
1908
1909 */
1910 const char *
1911 picochip_asm_output_opcode (FILE * f, const char *ptr)
1912 {
1913 int c;
1914
1915 /* Flag to specify when a VLIW continuation has been inserted onto
1916 the line. Continuations are either inserted before any comments,
1917 or before the end of the line is reached. The flag ensures that
1918 we don't insert continuations twice (i.e., at the comment and the
1919 end of line). */
1920 int continuation_inserted = 0;
1921
1922 /* If the instruction uses multiple lines (i.e., a new line
1923 character appears in the opcode), then ensure that no attempt is
1924 made to pack it into a VLIW. */
1925 if (strchr (ptr, '\n') != NULL && picochip_vliw_continuation)
1926 internal_error
1927 ("picochip_asm_output_opcode - Found multiple lines in VLIW packet %s\n",
1928 ptr);
1929
1930
1931 /* If a delay slot is pending, output the directive to the assembler
1932 before the instruction. */
1933 if (picochip_is_delay_slot_pending)
1934 {
1935 picochip_is_delay_slot_pending = 0;
1936 fputs ("=->\t", f);
1937 }
1938
1939 /* Keep going for entire opcode. All substitution performed ourselves. */
1940 while (*ptr)
1941 {
1942 c = *ptr++;
1943
1944 /* Determine whether a VLIW continuation must be inserted before
1945 any comments, or the end of the opcode. A flag is set to show
1946 that we have inserted a continuation on this line, so that we
1947 don't try to insert another continuation when the end of the
1948 opcode is reached. The only other case for a continuation
1949 might have been a newline, but these aren't allowed in
1950 conjunction with VLIW continuations (see above code). */
1951 if (picochip_vliw_continuation &&
1952 !continuation_inserted &&
1953 ((c == '/' && (*ptr == '/')) || *ptr == '\0'))
1954 {
1955 fprintf (f, "\\ ");
1956 continuation_inserted = 1;
1957 }
1958
1959 /* Detect an explicit VLIW separator. */
1960 if (c == '%' && (*ptr == '|'))
1961 {
1962 fprintf (f, "\\");
1963 ptr++;
1964 }
1965 /* Detect the need for an ALU id operand. */
1966 else if (c == '%' && (*ptr == '#'))
1967 {
1968 fputc (picochip_get_vliw_alu_id (), f);
1969
1970 if (TARGET_DEBUG)
1971 printf ("Generated ALU char at %s for insn %d\n", ptr,
1972 INSN_UID (picochip_current_prescan_insn));
1973
1974 /* Skip past unwanted # */
1975 ptr++;
1976 }
1977 /* Detect the need for branch delay slot. */
1978 else if (c == '%' && (*ptr == '>'))
1979 {
1980 /* Only emit delay slots (NOP's, or otherwise) when delay
1981 * slot scheduling has actually been enabled, otherwise VLIW
1982 * scheduling and delay slot scheduling output combine to
1983 * produce nasty effects. */
1984 if (flag_delayed_branch)
1985 {
1986 if (dbr_sequence_length () == 0)
1987 fputs ("\n=->\tNOP", f);
1988 else
1989 picochip_is_delay_slot_pending = 1;
1990 }
1991
1992 /* Skip past unwanted > */
1993 ptr++;
1994 }
1995 /* Detect any %digit specifiers. */
1996 else if (c == '%' && (*ptr >= '0' && *ptr <= '9'))
1997 {
1998 c = atoi (ptr);
1999 picochip_print_operand (f, recog_data.operand[c], 0);
2000 while ((c = *ptr) >= '0' && c <= '9')
2001 ptr++;
2002 }
2003 /* Detect any %letterdigit specifiers. */
2004 else if (c == '%' && ((*ptr >= 'a' && *ptr <= 'z')
2005 || (*ptr >= 'A' && *ptr <= 'Z')))
2006 {
2007 int letter = *ptr++;
2008
2009 c = atoi (ptr);
2010
2011 switch (letter)
2012 {
2013 case 'l':
2014 output_asm_label (recog_data.operand[c]);
2015 break;
2016
2017 case 'a':
2018 output_address (recog_data.operand[c]);
2019 break;
2020
2021 default:
2022 picochip_print_operand (f, recog_data.operand[c], letter);
2023 }
2024
2025 while ((c = *ptr) >= '0' && c <= '9')
2026 ptr++;
2027 }
2028 else if (c == '%')
2029 internal_error
2030 ("picochip_asm_output_opcode - can't output unknown operator %c\n",
2031 *ptr);
2032 else
2033 fputc (c, f);
2034 }
2035
2036 /* Reached the end of the packet. If any labels were deferred
2037 during output, emit them now. */
2038 if (!picochip_vliw_continuation)
2039 {
2040 if (picochip_current_vliw_state.num_cfi_labels_deferred != 0)
2041 {
2042 fprintf (f, "\n");
2043 assemble_name (f, picochip_current_vliw_state.cfi_label_name[0]);
2044 fprintf (f, "=");
2045 if (picochip_current_vliw_state.num_cfi_labels_deferred == 2)
2046 {
2047 fprintf (f, "\n");
2048 assemble_name (f, picochip_current_vliw_state.cfi_label_name[1]);
2049 fprintf (f, "=");
2050 }
2051 }
2052
2053 if (strlen (picochip_current_vliw_state.lm_label_name) != 0)
2054 {
2055 fprintf (f, "\n");
2056 assemble_name (f, picochip_current_vliw_state.lm_label_name);
2057 fprintf (f, "=");
2058 }
2059 }
2060
2061 /* Output an end-of-packet marker if requested. */
2062 if (!picochip_vliw_continuation &&
2063 TARGET_DEBUG && picochip_schedule_type == DFA_TYPE_SPEED)
2064 fprintf (f, "\n\t//-------------- End of VLIW packet -----------------");
2065
2066 return ptr;
2067 }
2068 \f
2069 /* Function RTL expansion. */
2070
2071 /* Expand the prologue into RTL. */
2072 void
2073 picochip_expand_prologue (void)
2074 {
2075 int stack_adjustment = 0;
2076 int special_save_offset = 0;
2077 int general_save_offset = 0;
2078 int reg_save_offset = 0;
2079 int i = 0;
2080
2081 stack_adjustment = picochip_arg_area_byte_offset ();
2082 general_save_offset =
2083 -(stack_adjustment - picochip_save_area_byte_offset ());
2084 special_save_offset =
2085 -(stack_adjustment - picochip_special_save_area_byte_offset ());
2086
2087 /* Save the link registers. We could try to save just one register
2088 here. This would reduce the amount of stack space required.
2089 There hasnt been a good reason to do that so far. */
2090 if (!picochip_can_eliminate_link_sp_save ())
2091 picochip_emit_save_register (gen_rtx_REG (SImode, LINK_REGNUM),
2092 special_save_offset);
2093
2094 /* Save callee-save registers. */
2095 reg_save_offset = 0;
2096 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
2097 {
2098 if (picochip_reg_needs_saving (i))
2099 {
2100
2101 /* If this register is an even numbered register, and the
2102 next register also needs to be saved, use a SImode save,
2103 which does both in one instruction. Note that a special
2104 check is performed to ensure that the double word aligned
2105 store is valid (e.g., it is possible that r6, r8, r9 need
2106 to be saved, in which case once r6 has been saved, the
2107 stored offset is no longer aligned, and an STL/LDL
2108 instruction becomes invalid). Alternately, we could store all
2109 aligned registers first and then save the single one(s). */
2110 if ((i % 2 == 0) &&
2111 picochip_reg_needs_saving (i + 1) &&
2112 picochip_is_aligned (reg_save_offset, LONG_TYPE_SIZE))
2113 {
2114 picochip_emit_save_register (gen_rtx_REG (SImode, i),
2115 general_save_offset +
2116 reg_save_offset);
2117 reg_save_offset += 2 * UNITS_PER_WORD;
2118 i++;
2119 }
2120 else
2121 {
2122 picochip_emit_save_register (gen_rtx_REG (HImode, i),
2123 general_save_offset +
2124 reg_save_offset);
2125 reg_save_offset += UNITS_PER_WORD;
2126 }
2127 }
2128
2129 }
2130
2131 /* Emit a stack adjustment where required. */
2132 if (stack_adjustment != 0)
2133 picochip_emit_stack_allocate (stack_adjustment);
2134
2135 /* If this function uses varadic arguments, write any unnamed
2136 registers to the stack. */
2137 if (cfun->stdarg)
2138 {
2139 int stdarg_offset = picochip_pretend_arg_area_byte_offset ();
2140
2141 /* Sanity check. The pretend argument offset should be 32-bit aligned. */
2142 gcc_assert(picochip_pretend_arg_area_byte_offset () % 4 == 0);
2143
2144 picochip_emit_save_register (gen_rtx_REG (SImode, 0), stdarg_offset);
2145 picochip_emit_save_register (gen_rtx_REG (SImode, 2),
2146 stdarg_offset + 4);
2147 picochip_emit_save_register (gen_rtx_REG (SImode, 4),
2148 stdarg_offset + 8);
2149
2150 }
2151
2152 }
2153
2154 /* Expand the epilogue into RTL. */
2155 void
2156 picochip_expand_epilogue (int is_sibling_call ATTRIBUTE_UNUSED)
2157 {
2158 int stack_adjustment = 0;
2159 int special_save_offset = 0;
2160 int general_save_offset = 0;
2161 int reg_save_offset = 0;
2162 int i = 0;
2163 int use_link_fp_restore_stack_adjust = 0; /* Default to using an explicit
2164 stack restore. */
2165
2166 stack_adjustment = picochip_arg_area_byte_offset ();
2167 general_save_offset =
2168 -(stack_adjustment - picochip_save_area_byte_offset ());
2169 special_save_offset =
2170 -(stack_adjustment - picochip_special_save_area_byte_offset ());
2171
2172 /* Emit a stack adjustment where required. */
2173 if (stack_adjustment != 0)
2174 {
2175 /* If the link/fp is already being restored, and the offset to
2176 their save location is small enough, don't bother adjusting
2177 the stack explicitly. */
2178 if (picochip_special_save_area_byte_offset () < 512 &&
2179 !picochip_can_eliminate_link_sp_save ())
2180 use_link_fp_restore_stack_adjust = 1;
2181 else
2182 /* Explicitly restore the stack. */
2183 picochip_emit_stack_allocate (-stack_adjustment);
2184 }
2185
2186 /* Restore the Link/FP registers. Only save the link register? */
2187 if (!picochip_can_eliminate_link_sp_save ())
2188 {
2189 if (use_link_fp_restore_stack_adjust)
2190 picochip_emit_restore_register (gen_rtx_REG (SImode, LINK_REGNUM),
2191 picochip_special_save_area_byte_offset
2192 ());
2193 else
2194 picochip_emit_restore_register (gen_rtx_REG (SImode, LINK_REGNUM),
2195 special_save_offset);
2196 }
2197
2198 /* Restore callee-save registers. */
2199 reg_save_offset = 0;
2200 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
2201 {
2202 if (picochip_reg_needs_saving (i))
2203 {
2204
2205 /* If this register is an even numbered register, and the
2206 next register also needs to be saved, use a SImode save,
2207 which does both in one instruction. Note that a special
2208 check is performed to ensure that the double word aligned
2209 store is valid (e.g., it is possible that r6, r8, r9 need
2210 to be saved, in which case once r6 has been saved, the
2211 stored offset is no longer aligned, and an STL/LDL
2212 instruction becomes invalid). We could store all aligned
2213 registers first, and then save the single one(s). */
2214 if ((i % 2 == 0) &&
2215 picochip_reg_needs_saving (i + 1) &&
2216 picochip_is_aligned (reg_save_offset, LONG_TYPE_SIZE))
2217 {
2218 picochip_emit_restore_register (gen_rtx_REG (SImode, i),
2219 general_save_offset +
2220 reg_save_offset);
2221 reg_save_offset += 2 * UNITS_PER_WORD;
2222 i++;
2223 }
2224 else
2225 {
2226 picochip_emit_restore_register (gen_rtx_REG (HImode, i),
2227 general_save_offset +
2228 reg_save_offset);
2229 reg_save_offset += UNITS_PER_WORD;
2230 }
2231 }
2232
2233 }
2234
2235 /* Emit a return instruction, which matches a (parallel
2236 [(return) (use r12)]) */
2237 {
2238 rtvec p;
2239 p = rtvec_alloc (2);
2240
2241 RTVEC_ELT (p, 0) = gen_rtx_RETURN (VOIDmode);
2242 RTVEC_ELT (p, 1) = gen_rtx_USE (VOIDmode,
2243 gen_rtx_REG (Pmode, LINK_REGNUM));
2244 emit_jump_insn (gen_rtx_PARALLEL (VOIDmode, p));
2245 }
2246
2247 }
2248 \f
2249 /* Assembly instruction output. */
2250
2251 /* Test whether the given branch instruction is short, or long. Short
2252 * branches are equivalent to real branches, and may be DFA
2253 * scheduled. Long branches expand to a macro which is handled by the
2254 * elaborator, and cannot be scheduled. Occasionally, the branch
2255 * shortening pass, which is run after DFA scheduling, will change the
2256 * code layout and cause the short branch to be reverted into a long
2257 * branch. Instead of having to fix this up by emitting new assembly,
2258 * the short branch is emitted anyway. There is plenty of slack in the
2259 * calculation of long and short branches (10-bit offset, but only
2260 * 9-bits used in computation), so there is enough slack for this to
2261 * be safe. */
2262 static int
2263 picochip_is_short_branch (rtx insn)
2264 {
2265 int isRealShortBranch = (get_attr_length(insn) == SHORT_BRANCH_LENGTH);
2266
2267 return (isRealShortBranch ||
2268 (!isRealShortBranch &&
2269 picochip_current_vliw_state.num_insns_in_packet > 1));
2270 }
2271
2272 /* Output a compare-and-branch instruction (matching the cbranch
2273 pattern). */
2274 const char *
2275 picochip_output_cbranch (rtx operands[])
2276 {
2277
2278 if (HImode != GET_MODE (operands[1]) ||
2279 (HImode != GET_MODE (operands[2]) &&
2280 GET_CODE (operands[2]) != CONST_INT))
2281 {
2282 internal_error ("%s: At least one operand can't be handled",
2283 __FUNCTION__);
2284 }
2285
2286 /* Use the type of comparison to output the appropriate condition
2287 test. */
2288 switch (GET_CODE (operands[0]))
2289 {
2290 case NE:
2291 return ("// if (%1 != %2) goto %l3\n\tSUB.%# %1,%2,r15\n\tJMPNE %l3");
2292
2293 case EQ:
2294 return ("// if (%1 == %2) goto %l3\n\tSUB.%# %1,%2,r15\n\tJMPEQ %l3");
2295
2296 case LE:
2297 /* Reverse the operand order to be GE */
2298 return ("// if (%1 <= %2) goto %l3\n\tSUB.%# %2,%1,r15\n\tJMPGE %l3");
2299
2300 case LEU:
2301 /* Reverse operand order of GEU. */
2302 return ("// if (%1 <= %2) goto %l3\n\tSUB.%# %2,%1,r15\n\tJMPHS %l3");
2303
2304 case GE:
2305 return ("// if (%1 >= %2) goto %l3\n\tSUB.%# %1,%2,r15\n\tJMPGE %l3");
2306
2307 case GEU:
2308 return ("// if (%1 >= %2) goto %l3\n\tSUB.%# %1,%2,r15\n\tJMPHS %l3");
2309
2310 case LT:
2311 return ("// if (%1 < %2) goto %l3\n\tSUB.%# %1,%2,r15\n\tJMPLT %l3");
2312
2313 case LTU:
2314 return ("// if (%1 <{U} %2) goto %l3\n\tSUB.%# %1,%2,r15\n\tJMPLO %l3");
2315
2316 case GT:
2317 /* Reversed operand version of LT. */
2318 return ("// if (%1 > %2) goto %l3\n\tSUB.%# %2,%1,r15\n\tJMPLT %l3");
2319
2320 case GTU:
2321 /* Reverse an LTU. */
2322 return ("// if (%1 >{U} %2) goto %l3\n\tSUB.%# %2,%1,r15\n\tJMPLO %l3");
2323
2324 default:
2325 gcc_unreachable();
2326 }
2327 }
2328
2329 /* Output a compare-and-branch instruction (matching the cbranch
2330 pattern). This function is current unused since the cbranch
2331 split is disabled. The function is kept around so we can use
2332 it when we understand how to do cbranch split safely. */
2333 const char *
2334 picochip_output_compare (rtx operands[])
2335 {
2336 int code;
2337
2338 if (HImode != GET_MODE (operands[1]) ||
2339 (HImode != GET_MODE (operands[2]) &&
2340 GET_CODE (operands[2]) != CONST_INT))
2341 {
2342 internal_error ("%s: At least one operand can't be handled",
2343 __FUNCTION__);
2344 }
2345
2346 code = GET_CODE (operands[0]);
2347 /* Use the type of comparison to output the appropriate condition
2348 test. */
2349 switch (code)
2350 {
2351 case NE:
2352 return ("SUB.%# %1,%2,r15\t// CC := (%0)");
2353
2354 case EQ:
2355 return ("SUB.%# %1,%2,r15\t// CC := (%0)");
2356
2357 case LE:
2358 /* Reverse the operand order to be GE */
2359 return ("SUB.%# %2,%1,r15\t// CC := (%0)");
2360
2361 case LEU:
2362 /* Reverse operand order of GEU. */
2363 return ("SUB.%# %2,%1,r15\t// CC := (%0)");
2364
2365 case GE:
2366 return ("SUB.%# %1,%2,r15\t// CC := (%0)");
2367
2368 case GEU:
2369 return ("SUB.%# %1,%2,r15\t// CC := (%0)");
2370
2371 case LT:
2372 return ("SUB.%# %1,%2,r15\t// CC := (%0)");
2373
2374 case LTU:
2375 return ("SUB.%# %1,%2,r15\t// CC := (%0)");
2376
2377 case GT:
2378 /* Reversed operand version of LT. */
2379 return ("SUB.%# %2,%1,r15\t// CC := (%0)");
2380
2381 case GTU:
2382 /* Reverse an LTU. */
2383 return ("SUB.%# %2,%1,r15\t// CC := (%0)");
2384
2385 default:
2386 gcc_unreachable();
2387 }
2388 }
2389
2390 /* Output the branch insn part of a compare-and-branch split. */
2391 const char *
2392 picochip_output_branch (rtx operands[], rtx insn)
2393 {
2394
2395 int code = GET_CODE(operands[2]);
2396 if (picochip_is_short_branch (insn))
2397 {
2398 /* Short branches can be output directly using the
2399 appropriate instruction. */
2400 switch (code)
2401 {
2402 case NE:
2403 return ("BNE %l0 %>");
2404 case EQ:
2405 return ("BEQ %l0 %>");
2406 case LE:
2407 return ("BGE %l0 %>");
2408 case LEU:
2409 return ("BHS %l0 %>");
2410 case GE:
2411 return ("BGE %l0 %>");
2412 case GEU:
2413 return ("BHS %l0 %>");
2414 case LT:
2415 return ("BLT %l0 %>");
2416 case LTU:
2417 return ("BLO %l0 %>");
2418 case GT:
2419 return ("BLT %l0 %>");
2420 case GTU:
2421 return ("BLO %l0 %>");
2422 default:
2423 internal_error ("Unknown short branch in %s (type %d)\n",
2424 __FUNCTION__, (int) INTVAL (operands[1]));
2425 return "UNKNOWN_BRANCH";
2426 }
2427 }
2428 else
2429 {
2430 /* Long branches result in the emission of a special
2431 instruction, which the assembler expands into a suitable long
2432 branch. */
2433
2434 /* Use the type of comparison to output the appropriate condition
2435 test. */
2436 switch (code)
2437 {
2438 case NE:
2439 return ("JMPNE %l0 %>");
2440 case EQ:
2441 return ("JMPEQ %l0 %>");
2442 case LE:
2443 return ("JMPGE %l0 %>");
2444 case LEU:
2445 return ("JMPHS %l0 %>");
2446 case GE:
2447 return ("JMPGE %l0 %>");
2448 case GEU:
2449 return ("JMPHS %l0 %>");
2450 case LT:
2451 return ("JMPLT %l0 %>");
2452 case LTU:
2453 return ("JMPLO %l0 %>");
2454 case GT:
2455 return ("JMPLT %l0 %>");
2456 case GTU:
2457 return ("JMPLO %l0 %>");
2458
2459 default:
2460 internal_error ("Unknown long branch in %s (type %d)\n",
2461 __FUNCTION__, (int) INTVAL (operands[1]));
2462 return "UNKNOWN_BRANCH";
2463 }
2464
2465 }
2466 }
2467
2468 /* Output a jump instruction. */
2469 const char *
2470 picochip_output_jump (rtx insn)
2471 {
2472 if (picochip_is_short_branch (insn))
2473 return "BRA %l0%>";
2474 else
2475 return "JMPRA %l0%>";
2476 }
2477 \f
2478 const char *
2479 picochip_output_put_array (int alternative, rtx operands[])
2480 {
2481 /* Local output buffer. */
2482 char buf[256];
2483
2484 int portArraySize = INTVAL(operands[1]);
2485 int portBaseIndex = INTVAL(operands[2]);
2486
2487 if (alternative == 0)
2488 {
2489 sprintf (buf, "// Array put\n\tadd.0 [lsl %%0,2],&__commTable_put_%d_%d,lr\n\tjl (lr)",
2490 portArraySize, portBaseIndex);
2491 output_asm_insn (buf, operands);
2492 }
2493 else if (alternative == 1)
2494 {
2495 /* Constant port id. Emit a real instruction. */
2496 int portIndex = INTVAL(operands[0]) + portBaseIndex;
2497 if (portIndex < portBaseIndex ||
2498 portIndex >= (portBaseIndex + portArraySize))
2499 {
2500 error ("PUT uses port array index %d, which is out of range [%d..%d)",
2501 portIndex, portBaseIndex, portBaseIndex + portArraySize);
2502 }
2503 sprintf(buf, "PUT R[0:1],%d", portIndex);
2504 output_asm_insn (buf, operands);
2505 }
2506 else
2507 gcc_unreachable();
2508
2509 /* Both alternatives output the insn directly. */
2510 return "";
2511 }
2512
2513 const char *picochip_output_get_array (int alternative, rtx operands[])
2514 {
2515 /* Local output buffer. */
2516 char buf[256];
2517
2518 int portArraySize = INTVAL(operands[1]);
2519 int portBaseIndex = INTVAL(operands[2]);
2520
2521 if (alternative == 0)
2522 {
2523 sprintf (buf, "// Array get\n\tadd.0 [lsl %%0,2],&__commTable_get_%d_%d,lr\n\tjl (lr)",
2524 portArraySize, portBaseIndex);
2525 output_asm_insn (buf, operands);
2526 }
2527 else if (alternative == 1)
2528 {
2529 /* Constant port id. Emit a real instruction. */
2530 int portIndex = INTVAL(operands[0]) + portBaseIndex;
2531 if (portIndex < portBaseIndex ||
2532 portIndex >= (portBaseIndex + portArraySize))
2533 {
2534 error ("GET uses port array index %d, which is out of range [%d..%d)",
2535 portIndex, portBaseIndex, portBaseIndex + portArraySize);
2536 }
2537 sprintf(buf, "GET %d,R[0:1]", portIndex);
2538 output_asm_insn (buf, operands);
2539 }
2540 else
2541 gcc_unreachable();
2542
2543 /* Both alternatives output the insn directly. */
2544 return "";
2545 }
2546
2547 const char *picochip_output_testport_array (int alternative, rtx operands[])
2548 {
2549 /* Local output buffer. */
2550 char buf[256];
2551
2552 int portArraySize = INTVAL(operands[2]);
2553 int portBaseIndex = INTVAL(operands[3]);
2554
2555 if (alternative == 0)
2556 {
2557 sprintf (buf, "// Array tstport\n\tadd.0 [lsl %%1,2],&__commTable_tstport_%d_%d,lr\n\tjl (lr)\n=->\tcopy.0 0,%%0\n\tcopyeq 1,%%0",
2558 portArraySize, portBaseIndex);
2559 output_asm_insn (buf, operands);
2560 }
2561 else if (alternative == 1)
2562 {
2563 /* Constant port id. Emit a real instruction. */
2564 int portIndex = INTVAL(operands[1]) + portBaseIndex;
2565 if (portIndex < portBaseIndex ||
2566 portIndex >= (portBaseIndex + portArraySize))
2567 {
2568 error ("PUT uses port array index %d, which is out of range [%d..%d)",
2569 portIndex, portBaseIndex, portBaseIndex + portArraySize);
2570 }
2571 sprintf(buf, "copy.1 0,%%0 %%| TSTPORT %d\n\tcopyeq 1,%%0", portIndex);
2572 output_asm_insn (buf, operands);
2573 }
2574 else
2575 gcc_unreachable();
2576
2577 /* Both alternatives output the insn directly. */
2578 return "";
2579 }
2580 \f
2581 /* Output a comparison operand as a symbol (e.g., >). */
2582 static void
2583 picochip_print_comparison (FILE * file, rtx operand, int letter)
2584 {
2585
2586 if (letter == 'i')
2587 {
2588 /* Output just the comparison symbol. */
2589 switch (GET_CODE (operand))
2590 {
2591 case NE:
2592 fprintf (file, "!=");
2593 break;
2594 case EQ:
2595 fprintf (file, "==");
2596 break;
2597 case GE:
2598 fprintf (file, ">=");
2599 break;
2600 case GEU:
2601 fprintf (file, ">={U}");
2602 break;
2603 case LT:
2604 fprintf (file, "<");
2605 break;
2606 case LTU:
2607 fprintf (file, "<{U}");
2608 break;
2609 case LE:
2610 fprintf (file, "<=");
2611 break;
2612 case LEU:
2613 fprintf (file, "<={U}");
2614 break;
2615 case GT:
2616 fprintf (file, ">");
2617 break;
2618 case GTU:
2619 fprintf (file, ">{U}");
2620 break;
2621 default:
2622 gcc_unreachable();
2623 }
2624 }
2625 else
2626 {
2627 /* Output the comparison formatted as operand,symbol,operand */
2628 rtx op0 = XEXP (operand, 0);
2629 rtx op1 = XEXP (operand, 1);
2630
2631 picochip_print_operand (file, op0, 0);
2632 picochip_print_comparison (file, operand, 'i');
2633 picochip_print_operand (file, op1, 0);
2634 }
2635 }
2636
2637 /* This function generates a memory address operand in the given
2638 mode. That is, if the address contains a constant offset, then the
2639 offset is divided by the required mode size to compute the
2640 mode specific offset. By default, picochip_print_operand_address calls
2641 this function using the natural mode of the operand, but special
2642 operand codes can be used to invoke the computation using an
2643 unnatural mode (e.g., compute the HI aligned address of an SI mode
2644 address). */
2645 static void
2646 picochip_print_memory_address (FILE * file, rtx operand,
2647 enum machine_mode mode)
2648 {
2649 rtx address = XEXP (operand, 0);
2650
2651 /* Sanity check. */
2652 if (MEM != GET_CODE (operand))
2653 fatal_insn ("picochip_print_memory_address - Operand isn't memory based",
2654 operand);
2655
2656 if (TARGET_DEBUG)
2657 {
2658 printf ("picochip_print_memory_address: ");
2659 print_rtl (stdout, operand);
2660 printf ("\n");
2661 }
2662
2663 switch (GET_CODE (address))
2664 {
2665 case PLUS:
2666 {
2667 /* Grab the address components. */
2668 rtx base = XEXP (address, 0);
2669 rtx offset = XEXP (address, 1);
2670
2671 /* Only handle reg+const addresses */
2672 if (REG == GET_CODE (base) && CONST_INT == GET_CODE (offset))
2673 {
2674 /* Sanity check. If an FP+offset address is given, ensure
2675 that the offset lies within the given frame, or a lower
2676 frame. */
2677 if (REGNO (base) == STACK_POINTER_REGNUM )
2678 gcc_assert (INTVAL (offset) <= (picochip_arg_area_byte_offset () +
2679 crtl->args.size));
2680
2681 /* Print the base register - identical for all modes. */
2682 fprintf (file, "(");
2683 picochip_print_operand (file, base, 'r');
2684 fprintf (file, ")");
2685
2686 /* Print the constant offset with compensation for the mode. */
2687 switch (mode)
2688 {
2689 case QImode:
2690 picochip_print_operand (file, offset, 'Q');
2691 break;
2692
2693 case HImode:
2694 picochip_print_operand (file, offset, 'H');
2695 break;
2696
2697 case SImode:
2698 case SFmode:
2699 picochip_print_operand (file, offset, 'S');
2700 break;
2701
2702 case DImode:
2703 picochip_print_operand (file, offset, 'D');
2704 break;
2705
2706 default:
2707 gcc_unreachable();
2708 }
2709
2710 }
2711
2712 }
2713
2714 break;
2715
2716 case SYMBOL_REF:
2717 picochip_print_operand (file, address, 's');
2718 break;
2719
2720 case CONST:
2721 {
2722 rtx inner;
2723 rtx base;
2724 rtx offset;
2725
2726 inner = XEXP (address, 0);
2727
2728 /* Sanity check - the CONST memory address must be a base+offset. */
2729 gcc_assert (PLUS == GET_CODE (inner));
2730
2731 base = XEXP (inner, 0);
2732 offset = XEXP (inner, 1);
2733
2734 fprintf (file, "&_%s%+d", XSTR (base, 0), XINT (offset, 0));
2735
2736 break;
2737 }
2738
2739 case REG:
2740 /* Register operand. Provide a zero offset. */
2741 fprintf (file, "(");
2742 picochip_print_operand (file, address, 'r');
2743 fprintf (file, ")0");
2744 break;
2745
2746 default:
2747 gcc_unreachable();
2748 }
2749
2750 }
2751
2752 /* Output an operand. Formatting letters allow particular parts of
2753 the operand to be output. */
2754 void
2755 picochip_print_operand (FILE * file, rtx operand, int letter)
2756 {
2757
2758 /* Handle special cases. */
2759 switch (letter)
2760 {
2761 /* VLIW continuation, for explicit VLIW sequences. */
2762 case '|':
2763 fprintf (file, "\\");
2764 return;
2765
2766 /* ALU selector. */
2767 case '#':
2768 fputc (picochip_get_vliw_alu_id (), file);
2769 return;
2770
2771 /* Delay slot specifier. */
2772 case '>':
2773 /* This should be handled in asm_output_opcode. */
2774 gcc_unreachable();
2775
2776 /* Instruction mnemonics (e.g., lshift becomes LSL). */
2777 case 'I':
2778 switch (GET_CODE (operand))
2779 {
2780 case AND:
2781 fprintf (file, "AND");
2782 break;
2783 case IOR:
2784 fprintf (file, "OR");
2785 break;
2786 case XOR:
2787 fprintf (file, "XOR");
2788 break;
2789 case PLUS:
2790 fprintf (file, "ADD");
2791 break;
2792 case MINUS:
2793 fprintf (file, "SUB");
2794 break;
2795 default:
2796 gcc_unreachable();
2797 }
2798 return;
2799
2800 /* Symbolic instructions (e.g., lshift becomes <<). */
2801 case 'i':
2802 switch (GET_CODE (operand))
2803 {
2804 case AND:
2805 fprintf (file, "&");
2806 break;
2807 case IOR:
2808 fprintf (file, "|");
2809 break;
2810 case XOR:
2811 fprintf (file, "^");
2812 break;
2813 case PLUS:
2814 fprintf (file, "+");
2815 break;
2816 case MINUS:
2817 fprintf (file, "-");
2818 break;
2819 default:
2820 fprintf (file, "UNKNOWN_INSN");
2821 break;
2822 }
2823 return;
2824
2825 default: /* Not a punctuation character - process as normal. */
2826 break;
2827 }
2828
2829 switch (GET_CODE (operand))
2830 {
2831 case REG:
2832 switch (letter)
2833 {
2834 case 'R':
2835 /* Write a range of registers. */
2836 fprintf (file, "R[%d:%d]", REGNO (operand) + 1, REGNO (operand));
2837 break;
2838
2839 case 'U':
2840 /* The upper register of a pair is requested. */
2841 fprintf (file, "%s", picochip_regnames[REGNO (operand) + 1]);
2842 break;
2843
2844 case 'L':
2845 /* The lower register of a pair is requested. Equivalent to the
2846 default, but included for completeness. */
2847 fprintf (file, "%s", picochip_regnames[REGNO (operand)]);
2848 break;
2849
2850 case 'X':
2851 /* The 3rd register of a DI mode register. */
2852 fprintf (file, "%s", picochip_regnames[REGNO (operand) + 2]);
2853 break;
2854
2855 case 'Y':
2856 /* The 4th register of a DI mode register. */
2857 fprintf (file, "%s", picochip_regnames[REGNO (operand) + 3]);
2858 break;
2859
2860 default:
2861 fprintf (file, "%s", picochip_regnames[REGNO (operand)]);
2862 }
2863 break;
2864
2865 case CONST_INT:
2866 /* A range of letters can be used to format integers. The
2867 letters Q/H/S are used to divide the constant by the width of
2868 QI/HI/SI mode integers in bytes. The U/L modifiers are used
2869 to obtain the upper and lower 16-bits of a 32-bit
2870 constant. Where possible, signed numbers are used, since
2871 signed representations of numbers may be more compact (e.g.,
2872 65535 can be represented as -1, which fits into a small
2873 constant, whereas 65535 requires a large constant). */
2874 switch (letter)
2875 {
2876 case 'Q':
2877 fprintf (file, "%ld", INTVAL (operand));
2878 break;
2879
2880 case 'H':
2881 fprintf (file, "%ld", INTVAL (operand) / 2);
2882 break;
2883
2884 case 'S':
2885 fprintf (file, "%ld", INTVAL (operand) / 4);
2886 break;
2887
2888 case 'P':
2889 fprintf (file, "%d", exact_log2 (INTVAL(operand)));
2890 break;
2891
2892 case 'U':
2893 fprintf (file, "%hi", (short) ((INTVAL (operand) >> 16) & 0xFFFF));
2894 break;
2895
2896 case 'L':
2897 fprintf (file, "%hi", (short) (INTVAL (operand) & 0xFFFF));
2898 break;
2899
2900 default:
2901 fprintf (file, "%ld", INTVAL (operand));
2902 break;
2903 }
2904 break;
2905
2906 case CONST_DOUBLE:
2907 {
2908 long val;
2909 REAL_VALUE_TYPE rv;
2910
2911 if (GET_MODE (operand) != SFmode)
2912 fatal_insn ("Unknown mode in print_operand (CONST_DOUBLE) :",
2913 operand);
2914 REAL_VALUE_FROM_CONST_DOUBLE (rv, operand);
2915 REAL_VALUE_TO_TARGET_SINGLE (rv, val);
2916
2917 switch (letter)
2918 {
2919 case 'U':
2920 fprintf (file, "%hi", (short) ((val >> 16) & 0xFFFF));
2921 break;
2922
2923 case 'L':
2924 fprintf (file, "%hi", (short) (val & 0xFFFF));
2925 break;
2926 }
2927
2928 break;
2929
2930 }
2931
2932 /* Output a symbol. The output format must match that of
2933 picochip_output_label. */
2934 case SYMBOL_REF:
2935 /* Ensure that the symbol is marked as referenced. Gcc can
2936 occasionally omit the function bodies when it believes them
2937 to be unreferenced. */
2938 if (SYMBOL_REF_DECL (operand))
2939 mark_decl_referenced (SYMBOL_REF_DECL (operand));
2940 fprintf (file, "&");
2941 assemble_name (file, XSTR (operand, 0));
2942 break;
2943
2944 case LABEL_REF:
2945 /* This format must match that of picochip_output_label. */
2946 fprintf (file, "&");
2947 output_asm_label (operand);
2948 break;
2949
2950 case MEM:
2951 {
2952 rtx addr = XEXP (operand, 0);
2953
2954 switch (letter)
2955 {
2956 case 'o':
2957 if (PLUS != GET_CODE (addr))
2958 fatal_insn ("Bad address, not (reg+disp):", addr);
2959 else
2960 picochip_print_operand (file, XEXP (addr, 1), 0);
2961 break;
2962
2963 case 'M':
2964 /* Output a memory address in byte mode notation (i.e., the
2965 constant address (if any) is the actual byte address. */
2966 picochip_print_memory_address (file, operand, QImode);
2967 break;
2968
2969 /* Output a constant offset of the given mode (i.e., divide
2970 the constant by the number of units in the mode to get the
2971 constant). */
2972 case 'Q':
2973 picochip_print_memory_address (file, operand, QImode);
2974 break;
2975
2976 case 'H':
2977 picochip_print_memory_address (file, operand, HImode);
2978 break;
2979
2980 case 'S':
2981 picochip_print_memory_address (file, operand, SImode);
2982 break;
2983
2984 case 'F':
2985 picochip_print_memory_address (file, operand, SFmode);
2986 break;
2987
2988 case 'b':
2989 if (PLUS != GET_CODE (addr))
2990 fatal_insn ("Bad address, not (reg+disp):", addr);
2991 else
2992 picochip_print_operand (file, XEXP (addr, 0), 0);
2993 break;
2994
2995 /* When the mem operand is (reg + big offset) which cannot
2996 be represented in an instruction as operand, the compiler
2997 automatically generates the instruction to put in (reg +
2998 big offset) into another register. In such cases, it
2999 returns '0' as the character. This needs to be handled
3000 as well. */
3001 case 0:
3002 case 'r':
3003 if (REG != GET_CODE (addr))
3004 fatal_insn ("Bad address, not register:", addr);
3005 else
3006 picochip_print_operand (file, addr, 0);
3007 break;
3008
3009 default:
3010 fprintf (file, "Unknown mem operand - letter %c ",
3011 (char) (letter));
3012 print_rtl (file, operand);
3013 }
3014
3015 break;
3016 }
3017
3018 case CONST:
3019 {
3020 rtx const_exp = XEXP (operand, 0);
3021
3022 /* Handle constant offsets to symbol references. */
3023 if (PLUS == GET_CODE (const_exp) &&
3024 SYMBOL_REF == GET_CODE (XEXP (const_exp, 0)) &&
3025 CONST_INT == GET_CODE (XEXP (const_exp, 1)))
3026 {
3027
3028 picochip_print_operand (file, XEXP (const_exp, 0), 0);
3029 if (INTVAL (XEXP (const_exp, 1)) >= 0)
3030 fprintf (file, "+");
3031 /* else use the - from the operand (i.e., AP-2)) */
3032
3033 picochip_print_operand (file, XEXP (const_exp, 1), letter);
3034
3035 }
3036 }
3037 break;
3038
3039
3040 case PLUS:
3041 {
3042 /* PLUS expressions are of the form (base + offset). Different
3043 options (analagous to those of memory PLUS expressions) are used
3044 to extract the base and offset components. */
3045
3046 switch (letter)
3047 {
3048 case 'b':
3049 picochip_print_operand (file, XEXP (operand, 0), 0);
3050 break;
3051
3052 case 'o':
3053 picochip_print_operand (file, XEXP (operand, 1), 0);
3054 break;
3055
3056 default:
3057
3058 /* If the expression is composed entirely of constants,
3059 evaluate the result. This should only occur with the
3060 picoChip specific comms instructions, which are emitted as
3061 base+offset expressions. */
3062 if (CONST_INT == GET_CODE (XEXP (operand, 0)) &&
3063 CONST_INT == GET_CODE (XEXP (operand, 1)))
3064 {
3065 HOST_WIDE_INT result = (XINT (XEXP (operand, 0), 0) +
3066 XINT (XEXP (operand, 1), 0));
3067 fprintf (file, "%ld", result);
3068 }
3069 else
3070 {
3071 fprintf (file, "(");
3072 picochip_print_operand (file, XEXP (operand, 0), 0);
3073 fprintf (file, "+");
3074 picochip_print_operand (file, XEXP (operand, 1), 0);
3075 fprintf (file, ")");
3076 }
3077 }
3078
3079 break;
3080 }
3081
3082 /* Comparison operations. */
3083 case NE:
3084 case EQ:
3085 case GE:
3086 case GEU:
3087 case LT:
3088 case LTU:
3089 case LE:
3090 case LEU:
3091 case GT:
3092 case GTU:
3093 picochip_print_comparison (file, operand, letter);
3094 return;
3095
3096 default:
3097 fprintf (stderr, "Unknown operand encountered in %s\n", __FUNCTION__);
3098 print_rtl (file, operand);
3099 break;
3100
3101 }
3102
3103 }
3104
3105 /* Output an operand address */
3106 void
3107 picochip_print_operand_address (FILE * file, rtx operand)
3108 {
3109
3110 switch (GET_CODE (operand))
3111 {
3112
3113 case SYMBOL_REF:
3114 /* This format must match that of picochip_output_label. */
3115 assemble_name (file, XSTR (operand, 0));
3116 break;
3117
3118 case CODE_LABEL:
3119 /* Note this format must match that of picochip_output_label. */
3120 fprintf (file, "_L%d", XINT (operand, 5));
3121 break;
3122
3123 case MEM:
3124 /* Pass on to a specialised memory address generator. */
3125 picochip_print_memory_address (file, operand, GET_MODE (operand));
3126 break;
3127
3128 default:
3129 gcc_unreachable();
3130
3131 }
3132
3133 }
3134 \f
3135
3136 /* Scheduling functions. */
3137
3138 /* Save some of the contents of recog_data. */
3139 static void
3140 picochip_save_recog_data (void)
3141 {
3142 picochip_saved_which_alternative = which_alternative;
3143 memcpy (&picochip_saved_recog_data, &recog_data,
3144 sizeof (struct recog_data));
3145 }
3146
3147 /* Restore some of the contents of global variable recog_data. */
3148 static void
3149 picochip_restore_recog_data (void)
3150 {
3151 which_alternative = picochip_saved_which_alternative;
3152 memcpy (&recog_data, &picochip_saved_recog_data,
3153 sizeof (struct recog_data));
3154 }
3155
3156 /* Ensure that no var tracking notes are emitted in the middle of a
3157 three-instruction bundle. */
3158 static void
3159 reorder_var_tracking_notes (void)
3160 {
3161 basic_block bb;
3162
3163 FOR_EACH_BB (bb)
3164 {
3165 rtx insn, next, last_insn = NULL_RTX;
3166 rtx vliw_start = NULL_RTX;
3167 rtx queue = NULL_RTX;
3168
3169 /* Iterate through the bb and find the last non-debug insn */
3170 for (insn = BB_HEAD (bb); insn != NEXT_INSN(BB_END (bb)); insn = NEXT_INSN(insn))
3171 {
3172 if (NONDEBUG_INSN_P(insn))
3173 last_insn = insn;
3174 }
3175
3176 /* In all normal cases, queue up notes and emit them just before a TImode
3177 instruction. For the last instruction, emit the queued notes just after
3178 the last instruction. */
3179 for (insn = BB_HEAD (bb); insn != NEXT_INSN(BB_END (bb)); insn = next)
3180 {
3181 next = NEXT_INSN (insn);
3182
3183 if (insn == last_insn)
3184 {
3185 while (queue)
3186 {
3187 rtx next_queue = PREV_INSN (queue);
3188 PREV_INSN (NEXT_INSN(insn)) = queue;
3189 NEXT_INSN(queue) = NEXT_INSN(insn);
3190 PREV_INSN(queue) = insn;
3191 NEXT_INSN(insn) = queue;
3192 queue = next_queue;
3193 }
3194 /* There is no more to do for this bb. break*/
3195 break;
3196 }
3197 else if (NONDEBUG_INSN_P (insn))
3198 {
3199 /* Emit queued up notes before the first instruction of a bundle. */
3200 if (GET_MODE (insn) == TImode)
3201 {
3202 while (queue)
3203 {
3204 rtx next_queue = PREV_INSN (queue);
3205 NEXT_INSN (PREV_INSN(insn)) = queue;
3206 PREV_INSN (queue) = PREV_INSN(insn);
3207 PREV_INSN (insn) = queue;
3208 NEXT_INSN (queue) = insn;
3209 queue = next_queue;
3210 }
3211 }
3212 }
3213 else if (NOTE_P (insn) && NOTE_KIND (insn) == NOTE_INSN_VAR_LOCATION)
3214 {
3215 rtx prev = PREV_INSN (insn);
3216 PREV_INSN (next) = prev;
3217 NEXT_INSN (prev) = next;
3218 PREV_INSN (insn) = queue;
3219 queue = insn;
3220 }
3221 }
3222 /* Make sure we are not dropping debug instructions.*/
3223 gcc_assert (queue == NULL_RTX);
3224 }
3225 }
3226
3227 /* Perform machine dependent operations on the rtl chain INSNS. */
3228 void
3229 picochip_reorg (void)
3230 {
3231 rtx insn, insn1, vliw_start = NULL_RTX;
3232 int vliw_insn_location = 0;
3233
3234 /* We are freeing block_for_insn in the toplev to keep compatibility
3235 with old MDEP_REORGS that are not CFG based. Recompute it now. */
3236 compute_bb_for_insn ();
3237
3238 if (optimize == 0)
3239 split_all_insns ();
3240
3241 if (picochip_schedule_type != DFA_TYPE_NONE)
3242 {
3243 timevar_push (TV_SCHED2);
3244
3245 /* Process the instruction list, computing the sizes of each
3246 instruction, and consequently branch distances. This can
3247 result in some branches becoming short enough to be treated
3248 as a real branch instruction, rather than an assembly branch
3249 macro which may expand into multiple instructions. The
3250 benefit of shortening branches is that real branch
3251 instructions can be properly DFA scheduled, whereas macro
3252 branches cannot. */
3253 shorten_branches (get_insns ());
3254
3255 /* Do control and data sched analysis again,
3256 and write some more of the results to dump file. */
3257
3258 split_all_insns ();
3259
3260 schedule_ebbs ();
3261
3262 timevar_pop (TV_SCHED2);
3263
3264 ggc_collect ();
3265
3266 if (picochip_schedule_type == DFA_TYPE_SPEED)
3267 {
3268 /* Whenever a VLIW packet is generated, all instructions in
3269 that packet must appear to come from the same source
3270 location. The following code finds all the VLIW packets,
3271 and tags their instructions with the location of the first
3272 instruction from the packet. Clearly this will result in
3273 strange behaviour when debugging the code, but since
3274 debugging and optimisation are being used in conjunction,
3275 strange behaviour is certain to occur anyway. */
3276 /* Slight bit of change. If the vliw set contains a branch
3277 or call instruction, we pick its location.*/
3278 for (insn = get_insns (); insn; insn = next_real_insn (insn))
3279 {
3280
3281 /* If this is the first instruction in the VLIW packet,
3282 extract its location. */
3283 if (GET_MODE (insn) == TImode)
3284 {
3285 vliw_start = insn;
3286 vliw_insn_location = INSN_LOCATOR (insn);
3287 }
3288 if (JUMP_P (insn) || CALL_P(insn))
3289 {
3290 vliw_insn_location = INSN_LOCATOR (insn);
3291 for (insn1 = vliw_start; insn1 != insn ; insn1 = next_real_insn (insn1))
3292 INSN_LOCATOR (insn1) = vliw_insn_location;
3293 }
3294 /* Tag subsequent instructions with the same location. */
3295 INSN_LOCATOR (insn) = vliw_insn_location;
3296 }
3297 }
3298
3299 }
3300
3301 /* Locate the note marking the end of the function's prologue. If
3302 the note appears in the middle of a VLIW packet, move the note to
3303 the end. This avoids unpleasant consequences such as trying to
3304 emit prologue markers (e.g., .loc/.file directives) in the middle
3305 of VLIW packets. */
3306 if (picochip_schedule_type == DFA_TYPE_SPEED)
3307 {
3308 rtx prologue_end_note = NULL;
3309 rtx last_insn_in_packet = NULL;
3310
3311 for (insn = get_insns (); insn; insn = next_insn (insn))
3312 {
3313 /* The prologue end must be moved to the end of the VLIW packet. */
3314 if (NOTE_P (insn) && NOTE_KIND (insn) == NOTE_INSN_PROLOGUE_END)
3315 {
3316 prologue_end_note = insn;
3317 break;
3318 }
3319 }
3320
3321 /* Find the last instruction in this packet. */
3322 for (insn = prologue_end_note; insn; insn = next_real_insn (insn))
3323 {
3324 if (GET_MODE (insn) == TImode)
3325 break;
3326 else
3327 last_insn_in_packet = insn;
3328 }
3329
3330 if (last_insn_in_packet != NULL)
3331 {
3332 rtx tmp_note = emit_note_after (NOTE_KIND(prologue_end_note), last_insn_in_packet);
3333 memcpy(&NOTE_DATA (tmp_note), &NOTE_DATA(prologue_end_note), sizeof(NOTE_DATA(prologue_end_note)));
3334 delete_insn (prologue_end_note);
3335 }
3336 }
3337 if (picochip_flag_var_tracking)
3338 {
3339 timevar_push (TV_VAR_TRACKING);
3340 variable_tracking_main ();
3341 /* We also have to deal with variable tracking notes in the middle
3342 of VLIW packets. */
3343 reorder_var_tracking_notes();
3344 timevar_pop (TV_VAR_TRACKING);
3345 }
3346 }
3347
3348 /* Return the ALU character identifier for the current
3349 instruction. This will be 0 or 1. */
3350 static char
3351 picochip_get_vliw_alu_id (void)
3352 {
3353 int attr_type = 0;
3354
3355 /* Always use ALU 0 if VLIW scheduling is disabled. */
3356 if (picochip_schedule_type != DFA_TYPE_SPEED)
3357 return '0';
3358
3359 /* Get the attribute type of the instruction. Note that this can
3360 ruin the contents of recog_data, so save/restore around the
3361 call. */
3362 picochip_save_recog_data ();
3363 attr_type = get_attr_type (picochip_current_prescan_insn);
3364 picochip_restore_recog_data ();
3365
3366 if (picochip_current_vliw_state.contains_pico_alu_insn)
3367 {
3368
3369 /* If this a picoAlu insn? If it is, then stuff it into ALU 0,
3370 else it must be the other ALU (either basic or nonCc)
3371 instruction which goes into 1. */
3372 if (attr_type == TYPE_PICOALU)
3373 return '0';
3374 else
3375 return '1';
3376
3377 }
3378 else if (picochip_current_vliw_state.contains_non_cc_alu_insn)
3379 {
3380 /* Is this the non CC instruction? If it is, then stuff it into
3381 ALU 1, else it must be a picoAlu or basicAlu, in which case
3382 it goes into ALU 0. */
3383 if (attr_type == TYPE_NONCCALU)
3384 return '1';
3385 else
3386 return '0';
3387 }
3388 else
3389 {
3390 /* No picoAlu/nonCc instructions in use, so purely dependent upon
3391 whether an ALU instruction has already been scheduled in this
3392 cycle. */
3393 switch (picochip_current_vliw_state.num_alu_insns_so_far)
3394 {
3395 case 0:
3396 picochip_current_vliw_state.num_alu_insns_so_far++;
3397 return '0';
3398
3399 case 1:
3400 picochip_current_vliw_state.num_alu_insns_so_far++;
3401 return '1';
3402
3403 default:
3404 internal_error ("Too many ALU instructions emitted (%d)\n",
3405 picochip_current_vliw_state.num_alu_insns_so_far);
3406 return 'X';
3407 }
3408 }
3409
3410 }
3411
3412 /* Reset any information about the current VLIW packing status. */
3413 static void
3414 picochip_reset_vliw (rtx insn)
3415 {
3416 rtx local_insn = insn;
3417
3418 /* Nothing to do if VLIW scheduling isn't being used. */
3419 if (picochip_schedule_type != DFA_TYPE_SPEED)
3420 return;
3421
3422 if (TARGET_DEBUG)
3423 printf ("%s on insn %d\n", __FUNCTION__, INSN_UID (insn));
3424
3425 /* Reset. */
3426 picochip_current_vliw_state.contains_pico_alu_insn = 0;
3427 picochip_current_vliw_state.contains_non_cc_alu_insn = 0;
3428 picochip_current_vliw_state.num_alu_insns_so_far = 0;
3429 picochip_current_vliw_state.num_cfi_labels_deferred = 0;
3430 picochip_current_vliw_state.lm_label_name[0] = 0;
3431 picochip_current_vliw_state.num_insns_in_packet = 0;
3432
3433 /* Read through the VLIW packet, classifying the instructions where
3434 appropriate. */
3435 local_insn = insn;
3436 do
3437 {
3438 if (NOTE_P (local_insn) || DEBUG_INSN_P(local_insn))
3439 {
3440 local_insn = NEXT_INSN (local_insn);
3441 continue;
3442 }
3443 else if (!INSN_P (local_insn))
3444 break;
3445 else
3446 {
3447 /* It is an instruction, but is it ours? */
3448 if (INSN_CODE (local_insn) != -1)
3449 {
3450 int attr_type = 0;
3451
3452 picochip_current_vliw_state.num_insns_in_packet += 1;
3453
3454 /* Is it a picoAlu or nonCcAlu instruction? Note that the
3455 get_attr_type function can overwrite the values in
3456 the recog_data global, hence this is saved and
3457 restored around the call. Not doing so results in
3458 asm_output_opcode being called with a different
3459 instruction to final_prescan_insn, which is fatal. */
3460 picochip_save_recog_data ();
3461 attr_type = get_attr_type (local_insn);
3462 picochip_restore_recog_data ();
3463
3464 if (attr_type == TYPE_PICOALU)
3465 picochip_current_vliw_state.contains_pico_alu_insn = 1;
3466 if (attr_type == TYPE_NONCCALU)
3467 picochip_current_vliw_state.contains_non_cc_alu_insn = 1;
3468
3469 }
3470 }
3471
3472 /* Get the next instruction. */
3473 local_insn = NEXT_INSN (local_insn);
3474
3475 /* Keep going while the next instruction is part of the same
3476 VLIW packet (i.e., its a valid instruction and doesn't mark
3477 the start of a new VLIW packet. */
3478 }
3479 while (local_insn &&
3480 (GET_MODE (local_insn) != TImode) && (INSN_CODE (local_insn) != -1));
3481
3482 }
3483
3484 int
3485 picochip_sched_reorder (FILE * file, int verbose,
3486 rtx * ready ATTRIBUTE_UNUSED,
3487 int *n_readyp ATTRIBUTE_UNUSED, int clock)
3488 {
3489
3490 if (verbose > 0)
3491 fprintf (file, ";;\tClock %d\n", clock);
3492
3493 return picochip_sched_issue_rate ();
3494
3495 }
3496
3497 int
3498 picochip_sched_lookahead (void)
3499 {
3500 /* It should always be enough to lookahead by 2 insns. Only slot0/1 could
3501 have a conflict. */
3502 return 2;
3503 }
3504
3505 int
3506 picochip_sched_issue_rate (void)
3507 {
3508 return 3;
3509 }
3510
3511 /* Adjust the scheduling cost between the two given instructions,
3512 which have the given dependency. */
3513 int
3514 picochip_sched_adjust_cost (rtx insn, rtx link, rtx dep_insn, int cost)
3515 {
3516
3517 if (TARGET_DEBUG)
3518 {
3519 printf ("Sched Adjust Cost: %d->%d is %d\n",
3520 INSN_UID (insn), INSN_UID (dep_insn), cost);
3521
3522 printf (" Dependency type:");
3523 switch (REG_NOTE_KIND (link))
3524 {
3525 case 0:
3526 printf ("Data\n");
3527 break;
3528 case REG_DEP_ANTI:
3529 printf ("ANTI\n");
3530 break;
3531 case REG_DEP_OUTPUT:
3532 printf ("OUTPUT\n");
3533 break;
3534 default:
3535 printf ("Unknown (%d)\n", REG_NOTE_KIND (link));
3536 }
3537 }
3538
3539 /* Anti-dependencies are used to enforce the ordering between a
3540 * branch, and any subsequent instructions. For example:
3541 *
3542 * BNE someLabel
3543 * ADD.0 r0,r1,r2
3544 *
3545 * The ADD instruction must execute after the branch, and this is
3546 * enforced using an anti-dependency. Unfortunately, VLIW machines
3547 * are happy to execute anti-dependent instructions in the same
3548 * cycle, which then results in a schedule like the following being
3549 * created:
3550 *
3551 * BNE someLabel \ ADD.0 r0,r1,r2
3552 *
3553 * The instruction which would normally be conditionally executed
3554 * depending upon the outcome of the branch, is now unconditionally
3555 * executed every time. To prevent this happening, any
3556 * anti-dependencies between a branch and another instruction are
3557 * promoted to become real dependencies.
3558 */
3559 if ((JUMP_P (dep_insn) || CALL_P(dep_insn)) && REG_NOTE_KIND (link) == REG_DEP_ANTI)
3560 {
3561
3562 if (TARGET_DEBUG)
3563 printf ("Promoting anti-dependency %d->%d to a true-dependency\n",
3564 INSN_UID (insn), INSN_UID (dep_insn));
3565
3566 return 1;
3567 }
3568
3569 return cost;
3570
3571 }
3572
3573 /* Return the minimum of the two values */
3574 static int
3575 minimum (int a, int b)
3576 {
3577 if (a < b)
3578 return a;
3579 if (b < a)
3580 return b;
3581 /* I dont expect to get to this function with a==b.*/
3582 gcc_unreachable();
3583 }
3584
3585
3586 /* This function checks if the memory of the two stores are just off by 2 bytes.
3587 It returns the lower memory operand's index.*/
3588
3589 static int
3590 memory_just_off (rtx opnd1, rtx opnd2)
3591 {
3592 int offset1 = 0, offset2 = 0;
3593 int reg1, reg2;
3594
3595 if (GET_CODE(XEXP(opnd1, 0)) == PLUS && GET_CODE(XEXP(XEXP(opnd1, 0),1)) == CONST_INT)
3596 {
3597 offset1 = INTVAL(XEXP(XEXP(opnd1, 0), 1));
3598 reg1 = REGNO(XEXP(XEXP(opnd1, 0), 0));
3599 }
3600 else
3601 {
3602 reg1 = REGNO(XEXP(opnd1, 0));
3603 }
3604 if (GET_CODE(XEXP(opnd2, 0)) == PLUS && GET_CODE(XEXP(XEXP(opnd2, 0), 1)) == CONST_INT)
3605 {
3606 offset2 = INTVAL(XEXP(XEXP(opnd2, 0), 1));
3607 reg2 = REGNO(XEXP(XEXP(opnd2, 0), 0));
3608 }
3609 else
3610 {
3611 reg2 = REGNO(XEXP(opnd2, 0));
3612 }
3613
3614 /* Peepholing 2 STW/LDWs has the restriction that the resulting STL/LDL's address
3615 should be 4 byte aligned. We can currently guarentee that only if the base
3616 address is FP(R13) and the offset is aligned. */
3617
3618 if (reg1 == reg2 && reg1 == 13 && abs(offset1-offset2) == 2 && minimum(offset1, offset2) % 4 == 0)
3619 return (minimum(offset1, offset2) == offset1) ? 1:2;
3620
3621 return 0;
3622 }
3623
3624 static int
3625 registers_just_off (rtx opnd1, rtx opnd2)
3626 {
3627 int reg1, reg2;
3628 reg1 = REGNO(opnd1);
3629 reg2 = REGNO(opnd2);
3630 if (abs(reg1-reg2) == 1 && minimum(reg1, reg2) % 2 == 0)
3631 return (minimum(reg1, reg2) == reg1)?1:2;
3632 return 0;
3633 }
3634
3635 /* Check to see if the two LDWs can be peepholed together into a LDL
3636 They can be if the registers getting loaded into are contiguous
3637 and the memory addresses are contiguous as well.
3638 for eg.
3639 LDW r2,[r11]x
3640 LDW r3,[r11]x+1
3641 can be merged together into
3642 LDL r[3:2],[r11]
3643
3644 NOTE:
3645 1. The LDWs themselves only guarentee that r11 will be a 2-byte
3646 aligned address. Only FP can be assumed to be 4 byte aligned.
3647 2. The progression of addresses and the register numbers should
3648 be similar. For eg., if you swap r2 and r3 in the above instructions,
3649 the resultant pair cannot be merged.
3650
3651 */
3652 bool
3653 ok_to_peephole_ldw(rtx opnd0, rtx opnd1, rtx opnd2, rtx opnd3)
3654 {
3655 int memtest=0,regtest=0;
3656 regtest = registers_just_off(opnd1,opnd3);
3657 if (regtest == 0)
3658 return false;
3659
3660 memtest = memory_just_off(opnd0,opnd2);
3661 if (memtest == 0)
3662 return false;
3663
3664 if (regtest == memtest)
3665 {
3666 return true;
3667 }
3668 return false;
3669 }
3670
3671 /* Similar to LDW peephole */
3672 bool
3673 ok_to_peephole_stw(rtx opnd0, rtx opnd1, rtx opnd2, rtx opnd3)
3674 {
3675 int memtest=0,regtest=0;
3676 regtest = registers_just_off(opnd1,opnd3);
3677 if (regtest == 0)
3678 return false;
3679
3680 memtest = memory_just_off(opnd0,opnd2);
3681 if (memtest == 0)
3682 return false;
3683
3684 if (regtest == memtest)
3685 {
3686 return true;
3687 }
3688 return false;
3689 }
3690
3691
3692 /* Generate a SImode register with the register number that is the smaller of the two */
3693 rtx
3694 gen_min_reg(rtx opnd1,rtx opnd2)
3695 {
3696 return gen_rtx_REG (SImode, minimum(REGNO(opnd1),REGNO(opnd2)));
3697 }
3698
3699 /* Generate a SImode memory with the address that is the smaller of the two */
3700 rtx
3701 gen_SImode_mem(rtx opnd1,rtx opnd2)
3702 {
3703 int offset1=0,offset2=0;
3704 rtx reg;
3705 rtx address;
3706 if (GET_CODE(XEXP(opnd1,0)) == PLUS && GET_CODE(XEXP(XEXP(opnd1,0),1)) == CONST_INT)
3707 {
3708 offset1 = INTVAL(XEXP(XEXP(opnd1,0),1));
3709 reg = XEXP(XEXP(opnd1,0),0);
3710 }
3711 else
3712 {
3713 reg = XEXP(opnd1,0);
3714 }
3715 if (GET_CODE(XEXP(opnd2,0)) == PLUS && GET_CODE(XEXP(XEXP(opnd2,0),1)) == CONST_INT)
3716 {
3717 offset2 = INTVAL(XEXP(XEXP(opnd2,0),1));
3718 }
3719 address = gen_rtx_PLUS (HImode, reg, GEN_INT(minimum(offset1,offset2)));
3720 return gen_rtx_MEM(SImode,address);
3721 }
3722
3723 bool
3724 picochip_rtx_costs (rtx x, int code, int outer_code ATTRIBUTE_UNUSED, int* total, bool speed)
3725 {
3726
3727 int localTotal = 0;
3728
3729 if (!speed)
3730 {
3731 /* Need to penalize immediates that need to be encoded as long constants.*/
3732 if (code == CONST_INT && !(INTVAL (x) >= 0 && INTVAL (x) < 16))
3733 {
3734 *total = COSTS_N_INSNS(1);
3735 return true;
3736 }
3737 }
3738 switch (code)
3739 {
3740 case SYMBOL_REF:
3741 case LABEL_REF:
3742 *total = COSTS_N_INSNS (outer_code != MEM);
3743 return true;
3744 break;
3745
3746 case IF_THEN_ELSE:
3747 /* if_then_else come out of cbranch instructions. It will get split into
3748 a condition code generating subtraction and a branch */
3749 *total = COSTS_N_INSNS (2);
3750 return true;
3751 break;
3752
3753 case AND:
3754 case IOR:
3755 case XOR:
3756 if (GET_MODE(x) == SImode)
3757 *total = COSTS_N_INSNS (2);
3758 if (GET_MODE(x) == DImode)
3759 *total = COSTS_N_INSNS (4);
3760 return false;
3761
3762 case MEM:
3763 /* Byte Memory access on a NO_BYTE_ACCESS machine would be expensive */
3764 if (GET_MODE(x) == QImode && !TARGET_HAS_BYTE_ACCESS)
3765 *total = COSTS_N_INSNS (10);
3766
3767 /* 64-bit accesses have to be done through 2 32-bit access */
3768 if (GET_MODE(x) == DImode)
3769 *total = COSTS_N_INSNS (2);
3770 return false;
3771 break;
3772
3773 case ASHIFTRT:
3774
3775 /* SImode shifts are expensive */
3776 if (GET_MODE(x) == SImode)
3777 *total = COSTS_N_INSNS (10);
3778
3779 /* Register shift by constant is cheap. */
3780 if ((GET_MODE(x) == QImode || GET_MODE(x) == HImode)
3781 && GET_CODE(XEXP(x, 0)) == REG
3782 && GET_CODE(XEXP(x, 1)) == CONST_INT)
3783 *total = COSTS_N_INSNS (1);
3784 else
3785 *total = COSTS_N_INSNS (4);
3786 return false;
3787 break;
3788
3789 case DIV:
3790 case MOD:
3791
3792 /* Divisions are more expensive than the default 7*/
3793 if (GET_MODE(x) == SImode)
3794 *total = COSTS_N_INSNS (20);
3795 else
3796 *total = COSTS_N_INSNS (12);
3797 return false;
3798 break;
3799
3800 case MULT:
3801 /* Look for the simple cases of multiplying register*register or
3802 register*constant. */
3803 if ((GET_MODE(x) == QImode || GET_MODE(x) == HImode)
3804 && ((GET_CODE(XEXP(x, 0)) == REG
3805 && (GET_CODE(XEXP(x, 1)) == REG || GET_CODE(XEXP(x,1)) == CONST_INT))
3806 || (GET_CODE(XEXP(x, 0)) == ZERO_EXTEND
3807 && GET_CODE(XEXP(XEXP(x, 0),0)) == REG
3808 && GET_CODE(XEXP(x, 1)) == ZERO_EXTEND
3809 && GET_CODE(XEXP(XEXP(x, 1),0)) == REG)))
3810 {
3811
3812 /* When optimising for size, multiplication by constant
3813 should be discouraged slightly over multiplication by a
3814 register. */
3815 if (picochip_has_mac_unit)
3816 {
3817 /* Single cycle multiplication, but the result must be
3818 loaded back into a general register afterwards. */
3819 *total = COSTS_N_INSNS(2);
3820 return true;
3821 }
3822 else if (picochip_has_mul_unit)
3823 {
3824 /* Single cycle multiplication. */
3825 *total = COSTS_N_INSNS(1);
3826 return true;
3827 }
3828 /* Else no multiply available. Use default cost. */
3829
3830 }
3831 break;
3832
3833 default:
3834 /* Do nothing. */
3835 break;
3836 }
3837
3838 if (localTotal != 0)
3839 {
3840 *total = localTotal;
3841 return true;
3842 }
3843 else
3844 {
3845 return false;
3846 }
3847
3848 }
3849
3850 void
3851 picochip_final_prescan_insn (rtx insn, rtx * opvec ATTRIBUTE_UNUSED,
3852 int num_operands ATTRIBUTE_UNUSED)
3853 {
3854 rtx local_insn;
3855
3856 picochip_current_prescan_insn = insn;
3857
3858 if (TARGET_DEBUG)
3859 printf ("Final prescan on INSN %d with mode %s\n",
3860 INSN_UID (insn), GET_MODE_NAME (GET_MODE (insn)));
3861
3862 /* If this is the start of a new instruction cycle, or no scheduling
3863 is used, then reset the VLIW status. */
3864 if (GET_MODE (insn) == TImode || !picochip_schedule_type == DFA_TYPE_SPEED)
3865 picochip_reset_vliw (insn);
3866
3867 /* No VLIW scheduling occured, so don't go any further. */
3868 if (picochip_schedule_type != DFA_TYPE_SPEED)
3869 return;
3870
3871 /* Look for the next printable instruction. This loop terminates on
3872 any recognisable instruction, and on any unrecognisable
3873 instruction with TImode. */
3874 local_insn = insn;
3875 for (local_insn = NEXT_INSN (local_insn); local_insn;
3876 local_insn = NEXT_INSN (local_insn))
3877 {
3878 if (NOTE_P (local_insn) || DEBUG_INSN_P(local_insn))
3879 continue;
3880 else if (!INSN_P (local_insn))
3881 break;
3882 else if (GET_MODE (local_insn) == TImode
3883 || INSN_CODE (local_insn) != -1)
3884 break;
3885 }
3886
3887 /* Set the continuation flag if the next instruction can be packed
3888 with the current instruction (i.e., the next instruction is
3889 valid, and isn't the start of a new cycle). */
3890 picochip_vliw_continuation = (local_insn && NONDEBUG_INSN_P (local_insn) &&
3891 (GET_MODE (local_insn) != TImode));
3892
3893 }
3894 \f
3895 /* Builtin functions. */
3896 /* Given a builtin function taking 2 operands (i.e., target + source),
3897 emit the RTL for the underlying instruction. */
3898 static rtx
3899 picochip_expand_builtin_2op (enum insn_code icode, tree call, rtx target)
3900 {
3901 tree arg0;
3902 rtx op0, pat;
3903 enum machine_mode tmode, mode0;
3904
3905 /* Grab the incoming argument and emit its RTL. */
3906 arg0 = CALL_EXPR_ARG (call, 0);
3907 op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
3908
3909 /* Determine the modes of the instruction operands. */
3910 tmode = insn_data[icode].operand[0].mode;
3911 mode0 = insn_data[icode].operand[1].mode;
3912
3913 /* Ensure that the incoming argument RTL is in a register of the
3914 correct mode. */
3915 if (!(*insn_data[icode].operand[1].predicate) (op0, mode0))
3916 op0 = copy_to_mode_reg (mode0, op0);
3917
3918 /* If there isn't a suitable target, emit a target register. */
3919 if (target == 0
3920 || GET_MODE (target) != tmode
3921 || !(*insn_data[icode].operand[0].predicate) (target, tmode))
3922 target = gen_reg_rtx (tmode);
3923
3924 /* Emit and return the new instruction. */
3925 pat = GEN_FCN (icode) (target, op0);
3926 if (!pat)
3927 return 0;
3928 emit_insn (pat);
3929
3930 return target;
3931
3932 }
3933
3934 /* Given a builtin function taking 3 operands (i.e., target + two
3935 source), emit the RTL for the underlying instruction. */
3936 static rtx
3937 picochip_expand_builtin_3op (enum insn_code icode, tree call, rtx target)
3938 {
3939 tree arg0, arg1;
3940 rtx op0, op1, pat;
3941 enum machine_mode tmode, mode0, mode1;
3942
3943 /* Grab the function's arguments. */
3944 arg0 = CALL_EXPR_ARG (call, 0);
3945 arg1 = CALL_EXPR_ARG (call, 1);
3946
3947 /* Emit rtl sequences for the function arguments. */
3948 op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
3949 op1 = expand_expr (arg1, NULL_RTX, VOIDmode, 0);
3950
3951 /* Get the mode's of each of the instruction operands. */
3952 tmode = insn_data[icode].operand[0].mode;
3953 mode0 = insn_data[icode].operand[1].mode;
3954 mode1 = insn_data[icode].operand[2].mode;
3955
3956 /* Ensure that each of the function argument rtl sequences are in a
3957 register of the correct mode. */
3958 if (!(*insn_data[icode].operand[1].predicate) (op0, mode0))
3959 op0 = copy_to_mode_reg (mode0, op0);
3960 if (!(*insn_data[icode].operand[2].predicate) (op1, mode1))
3961 op1 = copy_to_mode_reg (mode1, op1);
3962
3963 /* If no target has been given, create a register to use as the target. */
3964 if (target == 0
3965 || GET_MODE (target) != tmode
3966 || !(*insn_data[icode].operand[0].predicate) (target, tmode))
3967 target = gen_reg_rtx (tmode);
3968
3969 /* Emit and return the new instruction. */
3970 pat = GEN_FCN (icode) (target, op0, op1);
3971 if (!pat)
3972 return 0;
3973 emit_insn (pat);
3974
3975 return target;
3976
3977 }
3978
3979 /* Expand a builtin function which takes two arguments, and returns a void. */
3980 static rtx
3981 picochip_expand_builtin_2opvoid (enum insn_code icode, tree call)
3982 {
3983 tree arg0, arg1;
3984 rtx op0, op1, pat;
3985 enum machine_mode mode0, mode1;
3986
3987 /* Grab the function's arguments. */
3988 arg0 = CALL_EXPR_ARG (call, 0);
3989 arg1 = CALL_EXPR_ARG (call, 1);
3990
3991 /* Emit rtl sequences for the function arguments. */
3992 op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
3993 op1 = expand_expr (arg1, NULL_RTX, VOIDmode, 0);
3994
3995 /* Get the mode's of each of the instruction operands. */
3996 mode0 = insn_data[icode].operand[0].mode;
3997 mode1 = insn_data[icode].operand[1].mode;
3998
3999 /* Ensure that each of the function argument rtl sequences are in a
4000 register of the correct mode. */
4001 if (!(*insn_data[icode].operand[0].predicate) (op0, mode0))
4002 op0 = copy_to_mode_reg (mode0, op0);
4003 if (!(*insn_data[icode].operand[1].predicate) (op1, mode1))
4004 op1 = copy_to_mode_reg (mode1, op1);
4005
4006 /* Emit and return the new instruction. */
4007 pat = GEN_FCN (icode) (op0, op1);
4008 if (!pat)
4009 return 0;
4010 emit_insn (pat);
4011
4012 return NULL_RTX;
4013
4014 }
4015
4016 /* Expand an array get into the corresponding RTL. */
4017 static rtx
4018 picochip_expand_array_get (tree call, rtx target)
4019 {
4020 tree arg0, arg1, arg2;
4021 rtx op0, op1, op2, pat;
4022
4023 /* Grab the function's arguments. */
4024 arg0 = CALL_EXPR_ARG (call, 0);
4025 arg1 = CALL_EXPR_ARG (call, 1);
4026 arg2 = CALL_EXPR_ARG (call, 2) ;
4027
4028 /* Emit rtl sequences for the function arguments. */
4029 op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
4030 op1 = expand_expr (arg1, NULL_RTX, VOIDmode, 0);
4031 op2 = expand_expr (arg2, NULL_RTX, VOIDmode, 0);
4032
4033 /* The second and third operands must be constant. Nothing else will
4034 do. */
4035 if (CONST_INT != GET_CODE (op1))
4036 internal_error ("%s: Second source operand is not a constant",
4037 __FUNCTION__);
4038 if (CONST_INT != GET_CODE (op2))
4039 internal_error ("%s: Third source operand is not a constant",
4040 __FUNCTION__);
4041
4042 /* If no target has been given, create a register to use as the target. */
4043 if (target == 0 || GET_MODE (target) != SImode)
4044 target = gen_reg_rtx (SImode);
4045
4046 /* The first operand must be a HImode register or a constant. If it
4047 isn't, force it into a HImode register. */
4048 if (GET_MODE (op0) != HImode || REG != GET_CODE (op0))
4049 op0 = copy_to_mode_reg (HImode, op0);
4050
4051
4052 /* Emit and return the new instruction. */
4053 pat = gen_commsArrayGet (target, op0, op1, op2);
4054 emit_insn (pat);
4055
4056 return target;
4057
4058 }
4059
4060 /* Expand an array put into the corresponding RTL. */
4061 static rtx
4062 picochip_expand_array_put (tree call, rtx target)
4063 {
4064 tree arg0, arg1, arg2, arg3;
4065 rtx op0, op1, op2, op3, pat;
4066
4067 /* Grab the function's arguments. */
4068 arg0 = CALL_EXPR_ARG (call, 0);
4069 arg1 = CALL_EXPR_ARG (call, 1);
4070 arg2 = CALL_EXPR_ARG (call, 2);
4071 arg3 = CALL_EXPR_ARG (call, 3);
4072
4073 /* Emit rtl sequences for the function arguments. */
4074 op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
4075 op1 = expand_expr (arg1, NULL_RTX, VOIDmode, 0);
4076 op2 = expand_expr (arg2, NULL_RTX, VOIDmode, 0);
4077 op3 = expand_expr (arg3, NULL_RTX, VOIDmode, 0);
4078
4079 /* The first operand must be an SImode register. */
4080 if (GET_MODE (op0) != SImode || REG != GET_CODE (op0))
4081 op0 = copy_to_mode_reg (SImode, op0);
4082
4083 /* The second (index) operand must be a HImode register, or a
4084 constant. If it isn't, force it into a HImode register. */
4085 if (GET_MODE (op1) != HImode || REG != GET_CODE (op1))
4086 op1 = copy_to_mode_reg (HImode, op1);
4087
4088 /* The remaining operands must be constant. Nothing else will do. */
4089 if (CONST_INT != GET_CODE (op2))
4090 internal_error ("%s: Third source operand is not a constant",
4091 __FUNCTION__);
4092 if (CONST_INT != GET_CODE (op3))
4093 internal_error ("%s: Fourth source operand is not a constant",
4094 __FUNCTION__);
4095
4096 /* Emit and return the new instruction. */
4097 pat = gen_commsArrayPut (op0, op1, op2, op3);
4098 emit_insn (pat);
4099
4100 return target;
4101
4102 }
4103
4104 /* Expand an array testport into the corresponding RTL. */
4105 static rtx
4106 picochip_expand_array_testport (tree call, rtx target)
4107 {
4108 tree arg0, arg1, arg2;
4109 rtx op0, op1, op2, pat;
4110
4111 /* Grab the function's arguments. */
4112 arg0 = CALL_EXPR_ARG (call, 0);
4113 arg1 = CALL_EXPR_ARG (call, 1);
4114 arg2 = CALL_EXPR_ARG (call, 2);
4115
4116 /* Emit rtl sequences for the function arguments. */
4117 op0 = expand_expr (arg0, NULL_RTX, VOIDmode, 0);
4118 op1 = expand_expr (arg1, NULL_RTX, VOIDmode, 0);
4119 op2 = expand_expr (arg2, NULL_RTX, VOIDmode, 0);
4120
4121 /* The first operand must be a HImode register, or a constant. If it
4122 isn't, force it into a HImode register. */
4123 if (GET_MODE (op0) != HImode || REG != GET_CODE (op0))
4124 op0 = copy_to_mode_reg (HImode, op0);
4125
4126 /* The second and third operands must be constant. Nothing else will
4127 do. */
4128 if (CONST_INT != GET_CODE (op1))
4129 internal_error ("%s: Second source operand is not a constant",
4130 __FUNCTION__);
4131 if (CONST_INT != GET_CODE (op2))
4132 internal_error ("%s: Third source operand is not a constant",
4133 __FUNCTION__);
4134
4135 /* If no target has been given, create a HImode register to use as
4136 the target. */
4137 if (target == 0 || GET_MODE (target) != HImode)
4138 target = gen_reg_rtx (HImode);
4139
4140 /* Emit and return the new instruction. */
4141 pat = gen_commsArrayTestPort (target, op0, op1, op2);
4142 emit_insn (pat);
4143
4144 return target;
4145
4146 }
4147
4148 /* Generate a unique HALT instruction by giving the instruction a
4149 unique integer. This integer makes no difference to the assembly
4150 output (other than a comment indicating the supplied id), but the
4151 presence of the unique integer prevents the compiler from combining
4152 several different halt instructions into one instruction. This
4153 means that each use of the halt instruction is unique, which in
4154 turn means that assertions work as expected. */
4155 static rtx
4156 picochip_generate_halt (void)
4157 {
4158 static int currentId = 0;
4159 rtx insns;
4160 rtx id = GEN_INT (currentId);
4161 currentId += 1;
4162
4163 start_sequence();
4164 emit_insn (gen_halt (id));
4165
4166 /* A barrier is inserted to prevent the compiler from thinking that
4167 it has to continue execution after the HALT.*/
4168 emit_barrier ();
4169
4170 insns = get_insns();
4171 end_sequence();
4172 emit_insn (insns);
4173
4174 return const0_rtx;
4175 }
4176
4177 /* Initialise the builtin functions. Start by initialising
4178 descriptions of different types of functions (e.g., void fn(int),
4179 int fn(void)), and then use these to define the builtins. */
4180 void
4181 picochip_init_builtins (void)
4182 {
4183 tree noreturn;
4184 tree endlink = void_list_node;
4185 tree int_endlink = tree_cons (NULL_TREE, integer_type_node, endlink);
4186 tree unsigned_endlink = tree_cons (NULL_TREE, unsigned_type_node, endlink);
4187 tree long_endlink = tree_cons (NULL_TREE, long_integer_type_node, endlink);
4188 tree int_int_endlink =
4189 tree_cons (NULL_TREE, integer_type_node, int_endlink);
4190 tree int_int_int_endlink =
4191 tree_cons (NULL_TREE, integer_type_node, int_int_endlink);
4192 tree int_long_endlink =
4193 tree_cons (NULL_TREE, integer_type_node, long_endlink);
4194 tree pchar_type_node = build_pointer_type (char_type_node);
4195 tree long_int_int_int_endlink =
4196 tree_cons (NULL_TREE, long_integer_type_node, int_int_int_endlink);
4197
4198 tree int_ftype_void, int_ftype_int, int_ftype_int_int, void_ftype_pchar;
4199 tree long_ftype_int, long_ftype_int_int, long_ftype_int_int_int;
4200 tree void_ftype_int_long, int_ftype_int_int_int,
4201 void_ftype_long_int_int_int;
4202 tree void_ftype_void, void_ftype_int, unsigned_ftype_unsigned;
4203
4204 /* void func (void) */
4205 void_ftype_void = build_function_type (void_type_node, endlink);
4206
4207 /* void func (void *) */
4208 void_ftype_pchar
4209 = build_function_type (void_type_node,
4210 tree_cons (NULL_TREE, pchar_type_node, endlink));
4211
4212 /* int func (void) */
4213 int_ftype_void = build_function_type (integer_type_node, endlink);
4214
4215 /* void func (int) */
4216 void_ftype_int = build_function_type (void_type_node, int_endlink);
4217
4218 /* int func (int) */
4219 int_ftype_int = build_function_type (integer_type_node, int_endlink);
4220
4221 /* unsigned int func (unsigned int) */
4222 unsigned_ftype_unsigned = build_function_type (unsigned_type_node, unsigned_endlink);
4223
4224 /* int func(int, int) */
4225 int_ftype_int_int
4226 = build_function_type (integer_type_node, int_int_endlink);
4227
4228 /* long func(int) */
4229 long_ftype_int = build_function_type (long_integer_type_node, int_endlink);
4230
4231 /* long func(int, int) */
4232 long_ftype_int_int
4233 = build_function_type (long_integer_type_node, int_int_endlink);
4234
4235 /* long func(int, int, int) */
4236 long_ftype_int_int_int
4237 = build_function_type (long_integer_type_node, int_int_int_endlink);
4238
4239 /* int func(int, int, int) */
4240 int_ftype_int_int_int
4241 = build_function_type (integer_type_node, int_int_int_endlink);
4242
4243 /* void func(int, long) */
4244 void_ftype_int_long
4245 = build_function_type (void_type_node, int_long_endlink);
4246
4247 /* void func(long, int, int, int) */
4248 void_ftype_long_int_int_int
4249 = build_function_type (void_type_node, long_int_int_int_endlink);
4250
4251 /* Initialise the sign-bit-count function. */
4252 add_builtin_function ("__builtin_sbc", int_ftype_int,
4253 PICOCHIP_BUILTIN_SBC, BUILT_IN_MD, NULL,
4254 NULL_TREE);
4255 add_builtin_function ("picoSbc", int_ftype_int, PICOCHIP_BUILTIN_SBC,
4256 BUILT_IN_MD, NULL, NULL_TREE);
4257
4258 /* Initialise the bit reverse function. */
4259 add_builtin_function ("__builtin_brev", unsigned_ftype_unsigned,
4260 PICOCHIP_BUILTIN_BREV, BUILT_IN_MD, NULL,
4261 NULL_TREE);
4262 add_builtin_function ("picoBrev", unsigned_ftype_unsigned,
4263 PICOCHIP_BUILTIN_BREV, BUILT_IN_MD, NULL,
4264 NULL_TREE);
4265
4266 /* Initialise the byte swap function. */
4267 add_builtin_function ("__builtin_byteswap", unsigned_ftype_unsigned,
4268 PICOCHIP_BUILTIN_BYTESWAP, BUILT_IN_MD, NULL,
4269 NULL_TREE);
4270 add_builtin_function ("picoByteSwap", unsigned_ftype_unsigned,
4271 PICOCHIP_BUILTIN_BYTESWAP, BUILT_IN_MD, NULL,
4272 NULL_TREE);
4273
4274 /* Initialise the ASRI function (note that while this can be coded
4275 using a signed shift in C, extra scratch registers are required,
4276 which we avoid by having a direct builtin to map to the
4277 instruction). */
4278 add_builtin_function ("__builtin_asri", int_ftype_int_int,
4279 PICOCHIP_BUILTIN_ASRI, BUILT_IN_MD, NULL,
4280 NULL_TREE);
4281
4282 /* Initialise saturating addition. */
4283 add_builtin_function ("__builtin_adds", int_ftype_int_int,
4284 PICOCHIP_BUILTIN_ADDS, BUILT_IN_MD, NULL,
4285 NULL_TREE);
4286 add_builtin_function ("picoAdds", int_ftype_int_int,
4287 PICOCHIP_BUILTIN_ADDS, BUILT_IN_MD, NULL,
4288 NULL_TREE);
4289
4290 /* Initialise saturating subtraction. */
4291 add_builtin_function ("__builtin_subs", int_ftype_int_int,
4292 PICOCHIP_BUILTIN_SUBS, BUILT_IN_MD, NULL,
4293 NULL_TREE);
4294 add_builtin_function ("picoSubs", int_ftype_int_int,
4295 PICOCHIP_BUILTIN_SUBS, BUILT_IN_MD, NULL,
4296 NULL_TREE);
4297
4298 /* Scalar comms builtins. */
4299 add_builtin_function ("__builtin_get", long_ftype_int,
4300 PICOCHIP_BUILTIN_GET, BUILT_IN_MD, NULL,
4301 NULL_TREE);
4302 add_builtin_function ("__builtin_put", void_ftype_int_long,
4303 PICOCHIP_BUILTIN_PUT, BUILT_IN_MD, NULL,
4304 NULL_TREE);
4305 add_builtin_function ("__builtin_testport", int_ftype_int,
4306 PICOCHIP_BUILTIN_TESTPORT, BUILT_IN_MD, NULL,
4307 NULL_TREE);
4308
4309 /* Array comms builtins. */
4310 add_builtin_function ("__builtin_put_array",
4311 void_ftype_long_int_int_int,
4312 PICOCHIP_BUILTIN_PUT_ARRAY, BUILT_IN_MD, NULL,
4313 NULL_TREE);
4314 add_builtin_function ("__builtin_get_array", long_ftype_int_int_int,
4315 PICOCHIP_BUILTIN_GET_ARRAY, BUILT_IN_MD, NULL,
4316 NULL_TREE);
4317 add_builtin_function ("__builtin_testport_array",
4318 int_ftype_int_int_int,
4319 PICOCHIP_BUILTIN_TESTPORT_ARRAY, BUILT_IN_MD,
4320 NULL, NULL_TREE);
4321
4322 /* Halt instruction. Note that the builtin function is marked as
4323 having the attribute `noreturn' so that the compiler realises
4324 that the halt stops the program dead. */
4325 noreturn = tree_cons (get_identifier ("noreturn"), NULL, NULL);
4326 add_builtin_function ("__builtin_halt", void_ftype_void,
4327 PICOCHIP_BUILTIN_HALT, BUILT_IN_MD, NULL,
4328 noreturn);
4329 add_builtin_function ("picoHalt", void_ftype_void,
4330 PICOCHIP_BUILTIN_HALT, BUILT_IN_MD, NULL,
4331 noreturn);
4332
4333 }
4334
4335 /* Expand a call to a builtin function. */
4336 rtx
4337 picochip_expand_builtin (tree exp, rtx target, rtx subtarget ATTRIBUTE_UNUSED,
4338 enum machine_mode mode ATTRIBUTE_UNUSED,
4339 int ignore ATTRIBUTE_UNUSED)
4340 {
4341 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
4342 int fcode = DECL_FUNCTION_CODE (fndecl);
4343
4344 switch (fcode)
4345 {
4346 case PICOCHIP_BUILTIN_ASRI:
4347 return picochip_expand_builtin_3op (CODE_FOR_builtin_asri, exp,
4348 target);
4349
4350 case PICOCHIP_BUILTIN_ADDS:
4351 return picochip_expand_builtin_3op (CODE_FOR_sataddhi3, exp,
4352 target);
4353
4354 case PICOCHIP_BUILTIN_SUBS:
4355 return picochip_expand_builtin_3op (CODE_FOR_satsubhi3, exp,
4356 target);
4357
4358 case PICOCHIP_BUILTIN_SBC:
4359 return picochip_expand_builtin_2op (CODE_FOR_sbc, exp, target);
4360
4361 case PICOCHIP_BUILTIN_BREV:
4362 return picochip_expand_builtin_2op (CODE_FOR_brev, exp, target);
4363
4364 case PICOCHIP_BUILTIN_BYTESWAP:
4365 return picochip_expand_builtin_2op (CODE_FOR_bswaphi2, exp, target);
4366
4367 case PICOCHIP_BUILTIN_GET:
4368 return picochip_expand_builtin_2op (CODE_FOR_commsGet, exp, target);
4369
4370 case PICOCHIP_BUILTIN_PUT:
4371 return picochip_expand_builtin_2opvoid (CODE_FOR_commsPut, exp);
4372
4373 case PICOCHIP_BUILTIN_TESTPORT:
4374 return picochip_expand_builtin_2op (CODE_FOR_commsTestPort, exp,
4375 target);
4376
4377 case PICOCHIP_BUILTIN_PUT_ARRAY:
4378 return picochip_expand_array_put (exp, target);
4379
4380 case PICOCHIP_BUILTIN_GET_ARRAY:
4381 return picochip_expand_array_get (exp, target);
4382
4383 case PICOCHIP_BUILTIN_TESTPORT_ARRAY:
4384 return picochip_expand_array_testport (exp, target);
4385
4386 case PICOCHIP_BUILTIN_HALT:
4387 return picochip_generate_halt ();
4388
4389 default:
4390 gcc_unreachable();
4391
4392 }
4393
4394 /* Should really do something sensible here. */
4395 return NULL_RTX;
4396 }
4397 \f
4398 /* Emit warnings. */
4399 static void
4400 picochip_warn_inefficient (const char *msg)
4401 {
4402 if (TARGET_INEFFICIENT_WARNINGS)
4403 warning (OPT_minefficient_warnings,
4404 "%s (disable warning using -mno-inefficient-warnings)", msg);
4405 }
4406
4407 void
4408 warn_of_byte_access (void)
4409 {
4410 static int warned = 0;
4411
4412 if (!warned)
4413 {
4414 picochip_warn_inefficient
4415 ("byte access is synthesised - consider using MUL AE");
4416 warned = 1;
4417 }
4418
4419 }
4420 \f
4421 rtx
4422 picochip_function_value (const_tree valtype, const_tree func,
4423 bool outgoing ATTRIBUTE_UNUSED)
4424 {
4425 enum machine_mode mode = TYPE_MODE (valtype);
4426 int unsignedp = TYPE_UNSIGNED (valtype);
4427
4428 /* Since we define PROMOTE_FUNCTION_RETURN, we must promote the mode
4429 just as PROMOTE_MODE does. */
4430 mode = promote_function_mode (valtype, mode, &unsignedp, func, 1);
4431
4432 return gen_rtx_REG (mode, 0);
4433
4434 }
4435 \f
4436 /* Check that the value of the given mode will fit in the register of
4437 the given mode. */
4438 int
4439 picochip_hard_regno_mode_ok (int regno, enum machine_mode mode)
4440 {
4441
4442 if (GET_MODE_CLASS (mode) == MODE_CC)
4443 return regno == CC_REGNUM;
4444
4445 /* If the CC register is being used, then only CC mode values are
4446 allowed (which have already been tested). */
4447 if (regno == CC_REGNUM || regno == ACC_REGNUM)
4448 return 0;
4449
4450 /* Must be a valid register. */
4451 if (regno > 16)
4452 return 0;
4453
4454 /* Modes QI and HI may be placed in any register except the CC. */
4455 if (mode == QImode || mode == HImode)
4456 return 1;
4457
4458 /* DI must be in a quad register. */
4459 if (mode == DImode)
4460 return (regno % 4 == 0);
4461
4462 /* All other modes must be placed in a even numbered register. */
4463 return !(regno & 1);
4464
4465 }
4466 \f
4467 /* Extract the lower and upper components of a constant value. */
4468
4469 rtx
4470 picochip_get_low_const (rtx value)
4471 {
4472 return gen_int_mode (INTVAL (value) & 0xFFFF, HImode);
4473 }
4474
4475 rtx
4476 picochip_get_high_const (rtx value)
4477 {
4478 /*return GEN_INT ((((INTVAL (value) >> 16) & 0xFFFF) ^ 0x8000) - 0x8000); */
4479 return gen_int_mode ((INTVAL (value) >> 16) & 0xFFFF, HImode);
4480 }
4481
4482 \f
4483 /* Loading and storing QImode values to and from memory in a machine
4484 without byte access requires might require a scratch
4485 register. However, the scratch register might correspond to the
4486 register in which the value is being loaded. To ensure that a
4487 scratch register is supplied which is definitely different to the
4488 output register, request a register pair. This effectively gives a
4489 choice of two registers to choose from, so that we a guaranteed to
4490 get at least one register which is different to the output
4491 register. This trick is taken from the alpha implementation. */
4492 reg_class_t
4493 picochip_secondary_reload (bool in_p,
4494 rtx x ATTRIBUTE_UNUSED,
4495 reg_class_t cla ATTRIBUTE_UNUSED,
4496 enum machine_mode mode,
4497 secondary_reload_info *sri)
4498 {
4499 if (mode == QImode && !TARGET_HAS_BYTE_ACCESS)
4500 {
4501 if (in_p == 0)
4502 sri->icode = CODE_FOR_reload_outqi;
4503 else
4504 sri->icode = CODE_FOR_reload_inqi;
4505 }
4506
4507 /* We dont need to return a register class type when we need only a
4508 scratch register. It realizes the scratch register type by looking
4509 at the instruction definition for sri->icode. We only need to
4510 return the register type when we need intermediaries for copies.*/
4511 return NO_REGS;
4512 }
4513 \f
4514 /* Return true if the given memory operand can be aligned to a
4515 word+offset memory reference (e.g., FP+3 can be converted into the
4516 memory operand FP+2, with the offset 1). */
4517 int
4518 picochip_alignable_memory_operand (rtx mem_operand,
4519 enum machine_mode mode ATTRIBUTE_UNUSED)
4520 {
4521 rtx address;
4522
4523 /* Not a mem operand. Refuse immediately. */
4524 if (MEM != GET_CODE (mem_operand))
4525 return 0;
4526
4527 address = XEXP (mem_operand, 0);
4528
4529 /* Return true if a PLUS of the SP and a (valid) constant, or SP itself. */
4530 return ((PLUS == GET_CODE (address) &&
4531 REGNO (XEXP (address, 0)) == STACK_POINTER_REGNUM &&
4532 CONST_INT == GET_CODE (XEXP (address, 1)) &&
4533 picochip_const_ok_for_letter_p (INTVAL (XEXP (address, 1)), 'K'))
4534 || (REG == GET_CODE (address)
4535 && REGNO (address) == STACK_POINTER_REGNUM));
4536
4537 }
4538 \f
4539 /* Return true if the given memory reference is to a word aligned
4540 address. Currently this means it must be either SP, or
4541 SP+offset. We could replace this function with alignable
4542 memory references in the above function?. */
4543 int
4544 picochip_word_aligned_memory_reference (rtx operand)
4545 {
4546
4547
4548 /* The address must be the SP register, or a constant, aligned
4549 offset from SP which doesn't exceed the FP+offset
4550 restrictions. */
4551 return ((PLUS == GET_CODE (operand)
4552 && REGNO (XEXP (operand, 0)) == STACK_POINTER_REGNUM
4553 && picochip_is_aligned (INTVAL (XEXP (operand, 1)), 16)
4554 && picochip_const_ok_for_letter_p (INTVAL (XEXP (operand, 1)),
4555 'K'))
4556 || (REG == GET_CODE (operand)
4557 && REGNO (operand) == STACK_POINTER_REGNUM));
4558
4559 }
4560 \f
4561 /* Given an alignable memory location, convert the memory location
4562 into a HI mode access, storing the new memory reference in
4563 paligned_mem, and the number of bits by which to shift in pbitnum
4564 (i.e., given a reference to FP+3, this creates an aligned reference
4565 of FP+2, with an 8-bit shift). This code is a modification of that
4566 found in the Alpha port. */
4567 void
4568 picochip_get_hi_aligned_mem (rtx ref, rtx * paligned_mem, rtx * pbitnum)
4569 {
4570 rtx base;
4571 HOST_WIDE_INT offset = 0;
4572
4573 gcc_assert (GET_CODE (ref) == MEM);
4574
4575 if (reload_in_progress && !memory_address_p (GET_MODE (ref), XEXP (ref, 0)))
4576 {
4577 base = find_replacement (&XEXP (ref, 0));
4578
4579 gcc_assert(memory_address_p (GET_MODE (ref), base));
4580 }
4581 else
4582 {
4583 base = XEXP (ref, 0);
4584 }
4585
4586 if (GET_CODE (base) == PLUS)
4587 {
4588 offset += INTVAL (XEXP (base, 1));
4589 base = XEXP (base, 0);
4590 }
4591
4592 *paligned_mem = widen_memory_access (ref, HImode, (offset & ~1) - offset);
4593
4594 if (offset > 0)
4595 {
4596 if (TARGET_DEBUG)
4597 {
4598 printf
4599 ("Found non-zero offset in get_hi_aligned_mem - check that the correct value is being used (as this functionality hasn't been exploited yet).\n");
4600 }
4601 }
4602
4603 *pbitnum = GEN_INT ((offset & 1) * 8);
4604
4605 }
4606 \f
4607 /* Return true if the given operand is an absolute address in memory
4608 (i.e., a symbolic offset). */
4609 int
4610 picochip_absolute_memory_operand (rtx op,
4611 enum machine_mode mode ATTRIBUTE_UNUSED)
4612 {
4613
4614 if (MEM == GET_CODE (op))
4615 {
4616 rtx address = XEXP (op, 0);
4617
4618 /* Symbols are valid absolute addresses. */
4619 if (SYMBOL_REF == GET_CODE (address))
4620 return 1;
4621
4622 /* Constant offsets to symbols are valid absolute addresses. */
4623 if (CONST == GET_CODE (address) &&
4624 PLUS == GET_CODE (XEXP (address, 0)) &&
4625 SYMBOL_REF == GET_CODE (XEXP (XEXP (address, 0), 0)) &&
4626 CONST_INT == GET_CODE (XEXP (XEXP (address, 0), 1)))
4627 return 1;
4628
4629 }
4630 else
4631 return 0;
4632
4633 /* Symbols are valid absolute addresses. */
4634 if (SYMBOL_REF == GET_CODE (XEXP (op, 0)))
4635 return 1;
4636
4637
4638 return 0;
4639
4640 }
4641 \f
4642 void
4643 picochip_asm_named_section (const char *name,
4644 unsigned int flags ATTRIBUTE_UNUSED,
4645 tree decl ATTRIBUTE_UNUSED)
4646 {
4647 fprintf (asm_out_file, ".section %s\n", name);
4648 }
4649 \f
4650
4651 /* Check if we can make a conditional copy instruction. This is emitted as an
4652 instruction to set the condition register, followed by an instruction which
4653 uses the condition registers to perform the conditional move. */
4654 int
4655 picochip_check_conditional_copy (rtx * operands)
4656 {
4657
4658 rtx branch_op_0 = XEXP (operands[1], 0);
4659 rtx branch_op_1 = XEXP (operands[1], 1);
4660
4661 /* Only HI mode conditional moves are currently allowed. Can we add
4662 SI mode moves? */
4663 if (GET_CODE (operands[1]) != EQ && GET_CODE (operands[1]) != NE)
4664 return 0;
4665
4666 /* Is the comparison valid? Only allow operands which are registers
4667 if they are HImode. SI mode comparisons against 0 could be
4668 handled using logical operations (e.g., SIreg != 0 when low ||
4669 high). Need to find test cases to provoke this though (fixunssfdi
4670 in libgcc does, but is complicated). */
4671 if (register_operand(branch_op_0, GET_MODE(branch_op_0)) &&
4672 GET_MODE(branch_op_0) != HImode)
4673 return 0;
4674 if (register_operand(branch_op_1, GET_MODE(branch_op_1)) &&
4675 GET_MODE(branch_op_1) != HImode)
4676 return 0;
4677
4678 return 1;
4679
4680 }
4681
4682 \f
4683 static rtx
4684 picochip_static_chain (const_tree ARG_UNUSED (fndecl), bool incoming_p)
4685 {
4686 rtx addr;
4687 if (incoming_p)
4688 addr = arg_pointer_rtx;
4689 else
4690 addr = plus_constant (stack_pointer_rtx, -2 * UNITS_PER_WORD);
4691 return gen_frame_mem (Pmode, addr);
4692 }