Add hppa*-*-hpux* to targets which do not support split DWARF
[official-gcc.git] / gcc / config / msp430 / msp430.cc
blob21be7f1e6e131544432de95abcb8cd04fced5d9c
1 /* Subroutines used for code generation on TI MSP430 processors.
2 Copyright (C) 2012-2024 Free Software Foundation, Inc.
3 Contributed by Red Hat.
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3, or (at your option)
10 any later version.
12 GCC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING3. If not see
19 <http://www.gnu.org/licenses/>. */
21 #define IN_TARGET_CODE 1
23 #include "config.h"
24 #include "system.h"
25 #include "coretypes.h"
26 #include "backend.h"
27 #include "target.h"
28 #include "rtl.h"
29 #include "tree.h"
30 #include "stringpool.h"
31 #include "attribs.h"
32 #include "gimple-expr.h"
33 #include "df.h"
34 #include "memmodel.h"
35 #include "tm_p.h"
36 #include "regs.h"
37 #include "emit-rtl.h"
38 #include "varasm.h"
39 #include "diagnostic-core.h"
40 #include "fold-const.h"
41 #include "stor-layout.h"
42 #include "calls.h"
43 #include "output.h"
44 #include "explow.h"
45 #include "expr.h"
46 #include "langhooks.h"
47 #include "builtins.h"
48 #include "intl.h"
49 #include "msp430-devices.h"
50 #include "incpath.h"
51 #include "prefix.h"
52 #include "insn-config.h"
53 #include "insn-attr.h"
54 #include "recog.h"
56 /* This file should be included last. */
57 #include "target-def.h"
60 static void msp430_compute_frame_info (void);
61 static bool msp430_use_16bit_hwmult (void);
62 static bool msp430_use_32bit_hwmult (void);
63 static bool use_helper_for_const_shift (machine_mode mode, HOST_WIDE_INT amt);
67 /* Run-time Target Specification. */
69 bool msp430x = true;
71 struct GTY(()) machine_function
73 /* If set, the rest of the fields have been computed. */
74 int computed;
75 /* Which registers need to be saved in the pro/epilogue. */
76 int need_to_save[FIRST_PSEUDO_REGISTER];
78 /* These fields describe the frame layout... */
79 /* arg pointer */
80 /* 2/4 bytes for saved PC */
81 int framesize_regs;
82 /* frame pointer */
83 int framesize_locals;
84 int framesize_outgoing;
85 /* stack pointer */
86 int framesize;
88 /* How much we adjust the stack when returning from an exception
89 handler. */
90 rtx eh_stack_adjust;
93 /* This is our init_machine_status, as set in
94 msp430_option_override. */
95 static struct machine_function *
96 msp430_init_machine_status (void)
98 struct machine_function *m;
100 m = ggc_cleared_alloc<machine_function> ();
102 return m;
105 #undef TARGET_OPTION_OVERRIDE
106 #define TARGET_OPTION_OVERRIDE msp430_option_override
108 /* Generate a C preprocessor symbol based upon the MCU selected by the user.
109 If a specific MCU has not been selected then return a generic symbol
110 instead. */
112 const char *
113 msp430_mcu_name (void)
115 if (target_mcu)
117 msp430_extract_mcu_data (target_mcu);
118 unsigned int i;
119 unsigned int start_upper;
120 unsigned int end_upper;
121 static char mcu_name[64];
123 /* The 'i' in the device name symbol for msp430i* devices must be lower
124 case, to match the expected symbol in msp430.h. */
125 if (startswith (target_mcu, "msp430i"))
127 snprintf (mcu_name, sizeof (mcu_name) - 1, "__MSP430i%s__",
128 target_mcu + 7);
129 start_upper = 9;
131 else
133 snprintf (mcu_name, sizeof (mcu_name) - 1, "__%s__", target_mcu);
134 start_upper = 2;
136 end_upper = strlen (mcu_name) - 2;
137 for (i = start_upper; i < end_upper; i++)
138 mcu_name[i] = TOUPPER (mcu_name[i]);
139 return mcu_name;
142 return msp430x ? "__MSP430XGENERIC__" : "__MSP430GENERIC__";
145 static const char *
146 hwmult_name (unsigned int val)
148 switch (val)
150 case 0: return "none";
151 case 1: return "16-bit";
152 case 2: return "16-bit";
153 case 4: return "32-bit";
154 case 8: return "32-bit (5xx)";
155 default: gcc_unreachable ();
159 static void
160 msp430_option_override (void)
162 /* The MSP430 architecture can safely dereference a NULL pointer. In fact,
163 there are memory mapped registers there. */
164 flag_delete_null_pointer_checks = 0;
166 init_machine_status = msp430_init_machine_status;
168 msp430x = target_cpu >= MSP430_CPU_MSP430X_DEFAULT;
170 if (target_mcu)
172 msp430_extract_mcu_data (target_mcu);
174 if (extracted_mcu_data.name != NULL)
176 bool xisa = extracted_mcu_data.revision >= 1;
178 if (msp430_warn_mcu)
180 if (target_cpu != MSP430_CPU_MSP430X_DEFAULT && msp430x != xisa)
181 warning (0, "MCU %qs supports %s ISA but %<-mcpu%> option "
182 "is set to %s",
183 target_mcu, xisa ? "430X" : "430",
184 msp430x ? "430X" : "430");
186 if (extracted_mcu_data.hwmpy == 0
187 && msp430_hwmult_type != MSP430_HWMULT_AUTO
188 && msp430_hwmult_type != MSP430_HWMULT_NONE)
189 warning (0, "MCU %qs does not have hardware multiply "
190 "support, but %<-mhwmult%> is set to %s",
191 target_mcu,
192 msp430_hwmult_type == MSP430_HWMULT_SMALL ? "16-bit"
193 : msp430_hwmult_type == MSP430_HWMULT_LARGE
194 ? "32-bit" : "f5series");
195 else if (msp430_hwmult_type == MSP430_HWMULT_SMALL
196 && extracted_mcu_data.hwmpy != 1
197 && extracted_mcu_data.hwmpy != 2)
198 warning (0, "MCU %qs supports %s hardware multiply, "
199 "but %<-mhwmult%> is set to 16-bit",
200 target_mcu, hwmult_name (extracted_mcu_data.hwmpy));
201 else if (msp430_hwmult_type == MSP430_HWMULT_LARGE
202 && extracted_mcu_data.hwmpy != 4)
203 warning (0, "MCU %qs supports %s hardware multiply, "
204 "but %<-mhwmult%> is set to 32-bit",
205 target_mcu, hwmult_name (extracted_mcu_data.hwmpy));
206 else if (msp430_hwmult_type == MSP430_HWMULT_F5SERIES
207 && extracted_mcu_data.hwmpy != 8)
208 warning (0, "MCU %qs supports %s hardware multiply, "
209 "but %<-mhwmult%> is set to f5series",
210 target_mcu, hwmult_name (extracted_mcu_data.hwmpy));
212 /* Only override the default setting with the extracted ISA value if
213 the user has not passed -mcpu=. */
214 if (target_cpu == MSP430_CPU_MSP430X_DEFAULT)
215 msp430x = xisa;
217 else
219 if (msp430_hwmult_type == MSP430_HWMULT_AUTO)
221 if (msp430_warn_mcu)
223 if (target_cpu == MSP430_CPU_MSP430X_DEFAULT)
224 warning (0,
225 "unrecognized MCU name %qs, assuming that it is "
226 "just a MSP430X with no hardware multiply; "
227 "use the %<-mcpu%> and %<-mhwmult%> options to "
228 "set these explicitly",
229 target_mcu);
230 else
231 warning (0,
232 "unrecognized MCU name %qs, assuming that it "
233 "has no hardware multiply; use the %<-mhwmult%> "
234 "option to set this explicitly",
235 target_mcu);
238 msp430_hwmult_type = MSP430_HWMULT_NONE;
240 else if (target_cpu == MSP430_CPU_MSP430X_DEFAULT)
242 if (msp430_warn_mcu)
243 warning (0,
244 "unrecognized MCU name %qs, assuming that it just "
245 "supports the MSP430X ISA; use the %<-mcpu%> option "
246 "to set the ISA explicitly",
247 target_mcu);
249 else if (msp430_warn_mcu)
250 warning (0, "Unrecognized MCU name %qs.", target_mcu);
254 if (TARGET_LARGE && !msp430x)
255 error ("%<-mlarge%> requires a 430X-compatible %<-mmcu=%>");
257 if (!TARGET_LARGE && msp430_code_region == MSP430_REGION_EITHER)
258 error ("%<-mcode-region=either%> requires the large memory model "
259 "(%<-mlarge%>)");
260 else if (!TARGET_LARGE && msp430_code_region == MSP430_REGION_UPPER)
261 error ("%<-mcode-region=upper%> requires the large memory model "
262 "(%<-mlarge%>)");
264 if (!TARGET_LARGE && msp430_data_region == MSP430_REGION_EITHER)
265 error ("%<-mdata-region=either%> requires the large memory model "
266 "(%<-mlarge%>)");
267 else if (!TARGET_LARGE && msp430_data_region == MSP430_REGION_UPPER)
268 error ("%<-mdata-region=upper%> requires the large memory model "
269 "(%<-mlarge%>)");
271 if (flag_exceptions || flag_non_call_exceptions
272 || flag_unwind_tables || flag_asynchronous_unwind_tables)
273 flag_omit_frame_pointer = false;
274 else
275 flag_omit_frame_pointer = true;
277 /* This is a hack to work around a problem with the newlib build
278 mechanism. Newlib always appends CFLAGS to the end of the GCC
279 command line and always sets -O2 in CFLAGS. Thus it is not
280 possible to build newlib with -Os enabled. Until now... */
281 if (TARGET_OPT_SPACE && optimize < 3)
282 optimize_size = 1;
284 #if !DEFAULT_USE_CXA_ATEXIT
285 /* For some configurations, we use atexit () instead of __cxa_atexit () by
286 default to save on code size and remove the declaration of __dso_handle
287 from the CRT library.
288 Configuring GCC with --enable-__cxa-atexit re-enables it by defining
289 DEFAULT_USE_CXA_ATEXIT to 1. */
290 if (flag_use_cxa_atexit)
291 error ("%<-fuse-cxa-atexit%> is not supported for msp430-elf");
292 #endif
294 #ifndef HAVE_NEWLIB_NANO_FORMATTED_IO
295 if (TARGET_TINY_PRINTF)
296 error ("GCC must be configured with %<--enable-newlib-nano-formatted-io%> "
297 "to use %<-mtiny-printf%>");
298 #endif
301 #undef TARGET_SCALAR_MODE_SUPPORTED_P
302 #define TARGET_SCALAR_MODE_SUPPORTED_P msp430_scalar_mode_supported_p
304 static bool
305 msp430_scalar_mode_supported_p (scalar_mode m)
307 if (m == PSImode && msp430x)
308 return true;
309 #if 0
310 if (m == TImode)
311 return true;
312 #endif
313 return default_scalar_mode_supported_p (m);
318 /* Storage Layout */
320 #undef TARGET_MS_BITFIELD_LAYOUT_P
321 #define TARGET_MS_BITFIELD_LAYOUT_P msp430_ms_bitfield_layout_p
323 bool
324 msp430_ms_bitfield_layout_p (const_tree record_type ATTRIBUTE_UNUSED)
326 return false;
331 /* Register Usage */
333 #undef TARGET_HARD_REGNO_NREGS
334 #define TARGET_HARD_REGNO_NREGS msp430_hard_regno_nregs
336 static unsigned int
337 msp430_hard_regno_nregs (unsigned int, machine_mode mode)
339 if (mode == PSImode && msp430x)
340 return 1;
341 if (mode == CPSImode && msp430x)
342 return 2;
343 return ((GET_MODE_SIZE (mode) + UNITS_PER_WORD - 1)
344 / UNITS_PER_WORD);
347 /* subreg_get_info correctly handles PSImode registers, so defining
348 HARD_REGNO_NREGS_HAS_PADDING and HARD_REGNO_NREGS_WITH_PADDING
349 has no effect. */
351 #undef TARGET_HARD_REGNO_MODE_OK
352 #define TARGET_HARD_REGNO_MODE_OK msp430_hard_regno_mode_ok
354 static bool
355 msp430_hard_regno_mode_ok (unsigned int regno, machine_mode mode)
357 return regno <= (ARG_POINTER_REGNUM
358 - (unsigned int) msp430_hard_regno_nregs (regno, mode));
361 #undef TARGET_MODES_TIEABLE_P
362 #define TARGET_MODES_TIEABLE_P msp430_modes_tieable_p
364 static bool
365 msp430_modes_tieable_p (machine_mode mode1, machine_mode mode2)
367 if ((mode1 == PSImode || mode2 == SImode)
368 || (mode1 == SImode || mode2 == PSImode))
369 return false;
371 return ((GET_MODE_CLASS (mode1) == MODE_FLOAT
372 || GET_MODE_CLASS (mode1) == MODE_COMPLEX_FLOAT)
373 == (GET_MODE_CLASS (mode2) == MODE_FLOAT
374 || GET_MODE_CLASS (mode2) == MODE_COMPLEX_FLOAT));
377 #undef TARGET_FRAME_POINTER_REQUIRED
378 #define TARGET_FRAME_POINTER_REQUIRED msp430_frame_pointer_required
380 static bool
381 msp430_frame_pointer_required (void)
383 return false;
386 #undef TARGET_CAN_ELIMINATE
387 #define TARGET_CAN_ELIMINATE msp430_can_eliminate
389 static bool
390 msp430_can_eliminate (const int from_reg ATTRIBUTE_UNUSED,
391 const int to_reg ATTRIBUTE_UNUSED)
393 return true;
396 /* Implements INITIAL_ELIMINATION_OFFSET. */
398 msp430_initial_elimination_offset (int from, int to)
400 int rv = 0; /* As if arg to arg. */
402 msp430_compute_frame_info ();
404 switch (to)
406 case STACK_POINTER_REGNUM:
407 rv += cfun->machine->framesize_outgoing;
408 rv += cfun->machine->framesize_locals;
409 /* Fall through. */
410 case FRAME_POINTER_REGNUM:
411 rv += cfun->machine->framesize_regs;
412 /* Allow for the saved return address. */
413 rv += (TARGET_LARGE ? 4 : 2);
414 /* NB/ No need to allow for crtl->args.pretend_args_size.
415 GCC does that for us. */
416 break;
417 default:
418 gcc_unreachable ();
421 switch (from)
423 case FRAME_POINTER_REGNUM:
424 /* Allow for the fall through above. */
425 rv -= (TARGET_LARGE ? 4 : 2);
426 rv -= cfun->machine->framesize_regs;
427 case ARG_POINTER_REGNUM:
428 break;
429 default:
430 gcc_unreachable ();
433 return rv;
436 /* Named Address Space support */
439 /* Return the appropriate mode for a named address pointer. */
440 #undef TARGET_ADDR_SPACE_POINTER_MODE
441 #define TARGET_ADDR_SPACE_POINTER_MODE msp430_addr_space_pointer_mode
442 #undef TARGET_ADDR_SPACE_ADDRESS_MODE
443 #define TARGET_ADDR_SPACE_ADDRESS_MODE msp430_addr_space_pointer_mode
445 static scalar_int_mode
446 msp430_addr_space_pointer_mode (addr_space_t addrspace)
448 switch (addrspace)
450 default:
451 case ADDR_SPACE_GENERIC:
452 return Pmode;
453 case ADDR_SPACE_NEAR:
454 return HImode;
455 case ADDR_SPACE_FAR:
456 return PSImode;
460 /* Function pointers are stored in unwind_word sized
461 variables, so make sure that unwind_word is big enough. */
462 #undef TARGET_UNWIND_WORD_MODE
463 #define TARGET_UNWIND_WORD_MODE msp430_unwind_word_mode
465 static scalar_int_mode
466 msp430_unwind_word_mode (void)
468 /* This needs to match msp430_init_dwarf_reg_sizes_extra (below). */
469 return msp430x ? PSImode : HImode;
472 /* Determine if one named address space is a subset of another. */
473 #undef TARGET_ADDR_SPACE_SUBSET_P
474 #define TARGET_ADDR_SPACE_SUBSET_P msp430_addr_space_subset_p
475 static bool
476 msp430_addr_space_subset_p (addr_space_t subset, addr_space_t superset)
478 if (subset == superset)
479 return true;
480 else
481 return (subset != ADDR_SPACE_FAR && superset == ADDR_SPACE_FAR);
484 #undef TARGET_ADDR_SPACE_CONVERT
485 #define TARGET_ADDR_SPACE_CONVERT msp430_addr_space_convert
486 /* Convert from one address space to another. */
487 static rtx
488 msp430_addr_space_convert (rtx op, tree from_type, tree to_type)
490 addr_space_t from_as = TYPE_ADDR_SPACE (TREE_TYPE (from_type));
491 addr_space_t to_as = TYPE_ADDR_SPACE (TREE_TYPE (to_type));
492 rtx result;
494 if (to_as != ADDR_SPACE_FAR && from_as == ADDR_SPACE_FAR)
496 /* This is unpredictable, as we're truncating off usable address
497 bits. */
499 if (CONSTANT_P (op))
500 return gen_rtx_CONST (HImode, op);
502 result = gen_reg_rtx (HImode);
503 emit_insn (gen_truncpsihi2 (result, op));
504 return result;
506 else if (to_as == ADDR_SPACE_FAR && from_as != ADDR_SPACE_FAR)
508 /* This always works. */
510 if (CONSTANT_P (op))
511 return gen_rtx_CONST (PSImode, op);
513 result = gen_reg_rtx (PSImode);
514 emit_insn (gen_zero_extendhipsi2 (result, op));
515 return result;
517 else
518 gcc_unreachable ();
521 /* Stack Layout and Calling Conventions. */
523 /* For each function, we list the gcc version and the TI version on
524 each line, where we're converting the function names. */
525 static char const * const special_convention_function_names[] =
527 "__muldi3", "__mspabi_mpyll",
528 "__udivdi3", "__mspabi_divull",
529 "__umoddi3", "__mspabi_remull",
530 "__divdi3", "__mspabi_divlli",
531 "__moddi3", "__mspabi_remlli",
532 "__mspabi_srall",
533 "__mspabi_srlll",
534 "__mspabi_sllll",
535 "__adddf3", "__mspabi_addd",
536 "__subdf3", "__mspabi_subd",
537 "__muldf3", "__mspabi_mpyd",
538 "__divdf3", "__mspabi_divd",
539 "__mspabi_cmpd",
540 NULL
543 /* TRUE if the function passed is a "speical" function. Special
544 functions pass two DImode parameters in registers. */
545 static bool
546 msp430_special_register_convention_p (const char *name)
548 int i;
550 for (i = 0; special_convention_function_names[i]; i++)
551 if (!strcmp (name, special_convention_function_names[i]))
552 return true;
554 return false;
557 #undef TARGET_FUNCTION_VALUE_REGNO_P
558 #define TARGET_FUNCTION_VALUE_REGNO_P msp430_function_value_regno_p
560 bool
561 msp430_function_value_regno_p (unsigned int regno)
563 return regno == 12;
567 #undef TARGET_FUNCTION_VALUE
568 #define TARGET_FUNCTION_VALUE msp430_function_value
571 msp430_function_value (const_tree ret_type,
572 const_tree fn_decl_or_type ATTRIBUTE_UNUSED,
573 bool outgoing ATTRIBUTE_UNUSED)
575 return gen_rtx_REG (TYPE_MODE (ret_type), 12);
578 #undef TARGET_LIBCALL_VALUE
579 #define TARGET_LIBCALL_VALUE msp430_libcall_value
582 msp430_libcall_value (machine_mode mode, const_rtx fun ATTRIBUTE_UNUSED)
584 return gen_rtx_REG (mode, 12);
587 /* Implements INIT_CUMULATIVE_ARGS. */
588 void
589 msp430_init_cumulative_args (CUMULATIVE_ARGS *ca,
590 tree fntype ATTRIBUTE_UNUSED,
591 rtx libname ATTRIBUTE_UNUSED,
592 tree fndecl ATTRIBUTE_UNUSED,
593 int n_named_args ATTRIBUTE_UNUSED)
595 const char *fname;
596 memset (ca, 0, sizeof(*ca));
598 ca->can_split = 1;
600 if (fndecl)
601 fname = IDENTIFIER_POINTER (DECL_NAME (fndecl));
602 else if (libname)
603 fname = XSTR (libname, 0);
604 else
605 fname = NULL;
607 if (fname && msp430_special_register_convention_p (fname))
608 ca->special_p = 1;
611 /* Helper function for argument passing; this function is the common
612 code that determines where an argument will be passed. */
613 static void
614 msp430_evaluate_arg (cumulative_args_t cap,
615 machine_mode mode,
616 const_tree type ATTRIBUTE_UNUSED,
617 bool named)
619 CUMULATIVE_ARGS *ca = get_cumulative_args (cap);
620 int nregs = GET_MODE_SIZE (mode);
621 int i;
623 ca->reg_count = 0;
624 ca->mem_count = 0;
626 if (!named)
627 return;
629 if (mode == PSImode)
630 nregs = 1;
631 else
632 nregs = (nregs + 1) / 2;
634 if (ca->special_p)
636 /* Function is passed two DImode operands, in R8:R11 and
637 R12:15. */
638 ca->start_reg = 8;
639 ca->reg_count = 4;
640 return;
643 switch (nregs)
645 case 1:
646 for (i = 0; i < 4; i++)
647 if (!ca->reg_used[i])
649 ca->reg_count = 1;
650 ca->start_reg = CA_FIRST_REG + i;
651 return;
653 break;
654 case 2:
655 for (i = 0; i < 3; i++)
656 if (!ca->reg_used[i] && !ca->reg_used[i + 1])
658 ca->reg_count = 2;
659 ca->start_reg = CA_FIRST_REG + i;
660 return;
662 if (!ca->reg_used[3] && ca->can_split)
664 ca->reg_count = 1;
665 ca->mem_count = 2;
666 ca->start_reg = CA_FIRST_REG + 3;
667 return;
669 break;
670 case 3:
671 case 4:
672 ca->can_split = 0;
673 if (!ca->reg_used[0]
674 && !ca->reg_used[1]
675 && !ca->reg_used[2]
676 && !ca->reg_used[3])
678 ca->reg_count = 4;
679 ca->start_reg = CA_FIRST_REG;
680 return;
682 break;
686 #undef TARGET_PROMOTE_PROTOTYPES
687 #define TARGET_PROMOTE_PROTOTYPES msp430_promote_prototypes
689 bool
690 msp430_promote_prototypes (const_tree fntype ATTRIBUTE_UNUSED)
692 return false;
695 #undef TARGET_FUNCTION_ARG
696 #define TARGET_FUNCTION_ARG msp430_function_arg
699 msp430_function_arg (cumulative_args_t cap,
700 const function_arg_info &arg)
702 CUMULATIVE_ARGS *ca = get_cumulative_args (cap);
704 msp430_evaluate_arg (cap, arg.mode, arg.type, arg.named);
706 if (ca->reg_count)
707 return gen_rtx_REG (arg.mode, ca->start_reg);
709 return 0;
712 #undef TARGET_ARG_PARTIAL_BYTES
713 #define TARGET_ARG_PARTIAL_BYTES msp430_arg_partial_bytes
716 msp430_arg_partial_bytes (cumulative_args_t cap, const function_arg_info &arg)
718 CUMULATIVE_ARGS *ca = get_cumulative_args (cap);
720 msp430_evaluate_arg (cap, arg.mode, arg.type, arg.named);
722 if (ca->reg_count && ca->mem_count)
723 return ca->reg_count * UNITS_PER_WORD;
725 return 0;
728 #undef TARGET_PASS_BY_REFERENCE
729 #define TARGET_PASS_BY_REFERENCE msp430_pass_by_reference
731 static bool
732 msp430_pass_by_reference (cumulative_args_t, const function_arg_info &arg)
734 return (arg.mode == BLKmode
735 || (arg.type && TREE_CODE (arg.type) == RECORD_TYPE)
736 || (arg.type && TREE_CODE (arg.type) == UNION_TYPE));
739 #undef TARGET_CALLEE_COPIES
740 #define TARGET_CALLEE_COPIES hook_bool_CUMULATIVE_ARGS_arg_info_true
742 #undef TARGET_FUNCTION_ARG_ADVANCE
743 #define TARGET_FUNCTION_ARG_ADVANCE msp430_function_arg_advance
745 void
746 msp430_function_arg_advance (cumulative_args_t cap,
747 const function_arg_info &arg)
749 CUMULATIVE_ARGS *ca = get_cumulative_args (cap);
750 int i;
752 msp430_evaluate_arg (cap, arg.mode, arg.type, arg.named);
754 if (ca->start_reg >= CA_FIRST_REG)
755 for (i = 0; i < ca->reg_count; i ++)
756 ca->reg_used[i + ca->start_reg - CA_FIRST_REG] = 1;
758 ca->special_p = 0;
761 #undef TARGET_FUNCTION_ARG_BOUNDARY
762 #define TARGET_FUNCTION_ARG_BOUNDARY msp430_function_arg_boundary
764 static unsigned int
765 msp430_function_arg_boundary (machine_mode mode, const_tree type)
767 if (mode == BLKmode
768 && int_size_in_bytes (type) > 1)
769 return 16;
770 if (GET_MODE_BITSIZE (mode) > 8)
771 return 16;
772 return 8;
775 #undef TARGET_RETURN_IN_MEMORY
776 #define TARGET_RETURN_IN_MEMORY msp430_return_in_memory
778 static bool
779 msp430_return_in_memory (const_tree ret_type,
780 const_tree fntype ATTRIBUTE_UNUSED)
782 machine_mode mode = TYPE_MODE (ret_type);
784 if (mode == BLKmode
785 || (fntype && TREE_CODE (TREE_TYPE (fntype)) == RECORD_TYPE)
786 || (fntype && TREE_CODE (TREE_TYPE (fntype)) == UNION_TYPE))
787 return true;
789 if (GET_MODE_SIZE (mode) > 8)
790 return true;
792 return false;
795 #undef TARGET_GET_RAW_ARG_MODE
796 #define TARGET_GET_RAW_ARG_MODE msp430_get_raw_arg_mode
798 static fixed_size_mode
799 msp430_get_raw_arg_mode (int regno)
801 return as_a <fixed_size_mode> (regno == ARG_POINTER_REGNUM
802 ? VOIDmode : Pmode);
805 #undef TARGET_GET_RAW_RESULT_MODE
806 #define TARGET_GET_RAW_RESULT_MODE msp430_get_raw_result_mode
808 static fixed_size_mode
809 msp430_get_raw_result_mode (int regno ATTRIBUTE_UNUSED)
811 return Pmode;
814 #undef TARGET_GIMPLIFY_VA_ARG_EXPR
815 #define TARGET_GIMPLIFY_VA_ARG_EXPR msp430_gimplify_va_arg_expr
817 #include "gimplify.h"
819 static tree
820 msp430_gimplify_va_arg_expr (tree valist, tree type, gimple_seq *pre_p,
821 gimple_seq *post_p)
823 tree addr, t, type_size, rounded_size, valist_tmp;
824 unsigned HOST_WIDE_INT align, boundary;
825 bool indirect;
827 indirect = pass_va_arg_by_reference (type);
828 if (indirect)
829 type = build_pointer_type (type);
831 align = PARM_BOUNDARY / BITS_PER_UNIT;
832 boundary = targetm.calls.function_arg_boundary (TYPE_MODE (type), type);
834 /* When we align parameter on stack for caller, if the parameter
835 alignment is beyond MAX_SUPPORTED_STACK_ALIGNMENT, it will be
836 aligned at MAX_SUPPORTED_STACK_ALIGNMENT. We will match callee
837 here with caller. */
838 if (boundary > MAX_SUPPORTED_STACK_ALIGNMENT)
839 boundary = MAX_SUPPORTED_STACK_ALIGNMENT;
841 boundary /= BITS_PER_UNIT;
843 /* Hoist the valist value into a temporary for the moment. */
844 valist_tmp = get_initialized_tmp_var (valist, pre_p, NULL);
846 /* va_list pointer is aligned to PARM_BOUNDARY. If argument actually
847 requires greater alignment, we must perform dynamic alignment. */
848 if (boundary > align
849 && !integer_zerop (TYPE_SIZE (type)))
851 /* FIXME: This is where this function diverts from targhooks.cc:
852 std_gimplify_va_arg_expr(). It works, but I do not know why... */
853 if (! POINTER_TYPE_P (type))
855 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
856 fold_build_pointer_plus_hwi (valist_tmp, boundary - 1));
857 gimplify_and_add (t, pre_p);
859 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
860 fold_build2 (BIT_AND_EXPR, TREE_TYPE (valist),
861 valist_tmp,
862 build_int_cst (TREE_TYPE (valist),
863 -boundary)));
864 gimplify_and_add (t, pre_p);
867 else
868 boundary = align;
870 /* If the actual alignment is less than the alignment of the type,
871 adjust the type accordingly so that we don't assume strict alignment
872 when dereferencing the pointer. */
873 boundary *= BITS_PER_UNIT;
874 if (boundary < TYPE_ALIGN (type))
876 type = build_variant_type_copy (type);
877 SET_TYPE_ALIGN (type, boundary);
880 /* Compute the rounded size of the type. */
881 type_size = size_in_bytes (type);
882 rounded_size = round_up (type_size, align);
884 /* Reduce rounded_size so it's sharable with the postqueue. */
885 gimplify_expr (&rounded_size, pre_p, post_p, is_gimple_val, fb_rvalue);
887 /* Get AP. */
888 addr = valist_tmp;
890 /* Compute new value for AP. */
891 t = fold_build_pointer_plus (valist_tmp, rounded_size);
892 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist, t);
893 gimplify_and_add (t, pre_p);
895 addr = fold_convert (build_pointer_type (type), addr);
897 if (indirect)
898 addr = build_va_arg_indirect_ref (addr);
900 addr = build_va_arg_indirect_ref (addr);
902 return addr;
905 #undef TARGET_LRA_P
906 #define TARGET_LRA_P hook_bool_void_false
908 /* Addressing Modes */
910 #undef TARGET_LEGITIMATE_ADDRESS_P
911 #define TARGET_LEGITIMATE_ADDRESS_P msp430_legitimate_address_p
913 static bool
914 reg_ok_for_addr (rtx r, bool strict)
916 int rn = REGNO (r);
918 if (strict && rn >= FIRST_PSEUDO_REGISTER)
919 rn = reg_renumber[rn];
920 if (strict && 0 <= rn && rn < FIRST_PSEUDO_REGISTER)
921 return true;
922 if (!strict)
923 return true;
924 return false;
927 bool
928 msp430_legitimate_address_p (machine_mode mode ATTRIBUTE_UNUSED,
929 rtx x ATTRIBUTE_UNUSED,
930 bool strict ATTRIBUTE_UNUSED,
931 code_helper = ERROR_MARK)
933 switch (GET_CODE (x))
935 case MEM:
936 return false;
938 case PLUS:
939 case POST_INC:
940 if (REG_P (XEXP (x, 0)))
942 if (GET_MODE (x) != GET_MODE (XEXP (x, 0)))
943 return false;
944 if (!reg_ok_for_addr (XEXP (x, 0), strict))
945 return false;
946 if (GET_CODE (x) == POST_INC)
947 /* At this point, if the original rtx was a post_inc, we don't have
948 anything further to check. */
949 return true;
950 switch (GET_CODE (XEXP (x, 1)))
952 case CONST:
953 case SYMBOL_REF:
954 case CONST_INT:
955 return true;
956 default:
957 return false;
960 return false;
962 case REG:
963 if (!reg_ok_for_addr (x, strict))
964 return false;
965 /* FALLTHRU */
966 case CONST:
967 case SYMBOL_REF:
968 case CONST_INT:
969 return true;
971 default:
972 return false;
976 #undef TARGET_ADDR_SPACE_LEGITIMATE_ADDRESS_P
977 #define TARGET_ADDR_SPACE_LEGITIMATE_ADDRESS_P \
978 msp430_addr_space_legitimate_address_p
980 bool
981 msp430_addr_space_legitimate_address_p (machine_mode mode,
982 rtx x,
983 bool strict,
984 addr_space_t as ATTRIBUTE_UNUSED,
985 code_helper ch = ERROR_MARK)
987 return msp430_legitimate_address_p (mode, x, strict, ch);
990 #undef TARGET_ASM_INTEGER
991 #define TARGET_ASM_INTEGER msp430_asm_integer
992 static bool
993 msp430_asm_integer (rtx x, unsigned int size, int aligned_p)
995 int c = GET_CODE (x);
997 if (size == 3 && GET_MODE (x) == PSImode)
998 size = 4;
1000 switch (size)
1002 case 4:
1003 if (c == SYMBOL_REF || c == CONST || c == LABEL_REF || c == CONST_INT
1004 || c == PLUS || c == MINUS)
1006 fprintf (asm_out_file, "\t.long\t");
1007 output_addr_const (asm_out_file, x);
1008 fputc ('\n', asm_out_file);
1009 return true;
1011 break;
1013 return default_assemble_integer (x, size, aligned_p);
1016 #undef TARGET_ASM_OUTPUT_ADDR_CONST_EXTRA
1017 #define TARGET_ASM_OUTPUT_ADDR_CONST_EXTRA msp430_asm_output_addr_const_extra
1018 static bool
1019 msp430_asm_output_addr_const_extra (FILE *file ATTRIBUTE_UNUSED, rtx x)
1021 debug_rtx (x);
1022 return false;
1025 #undef TARGET_LEGITIMATE_CONSTANT_P
1026 #define TARGET_LEGITIMATE_CONSTANT_P msp430_legitimate_constant
1028 static bool
1029 msp430_legitimate_constant (machine_mode mode, rtx x)
1031 return ! CONST_INT_P (x)
1032 || mode != PSImode
1033 /* GCC does not know the width of the PSImode, so make
1034 sure that it does not try to use a constant value that
1035 is out of range. */
1036 || (INTVAL (x) < (1 << 20)
1037 && INTVAL (x) >= (HOST_WIDE_INT)(HOST_WIDE_INT_M1U << 20));
1041 /* Describing Relative Costs of Operations
1042 To model the cost of an instruction, use the number of cycles when
1043 optimizing for speed, and the number of words when optimizing for size.
1044 The cheapest instruction will execute in one cycle and cost one word.
1045 The cycle and size costs correspond to 430 ISA instructions, not 430X
1046 instructions or 430X "address" instructions. The relative costs of 430X
1047 instructions is accurately modeled with the 430 costs. The relative costs
1048 of some "address" instructions can differ, but these are not yet handled.
1049 Adding support for this could improve performance/code size. */
1051 struct single_op_cost
1053 const int reg;
1054 /* Indirect register (@Rn) or indirect autoincrement (@Rn+). */
1055 const int ind;
1056 const int mem;
1059 static const struct single_op_cost cycle_cost_single_op =
1061 1, 3, 4
1064 static const struct single_op_cost size_cost_single_op =
1066 1, 1, 2
1069 /* When the destination of an insn is memory, the cost is always the same
1070 regardless of whether that memory is accessed using indirect register,
1071 indexed or absolute addressing.
1072 When the source operand is memory, indirect register and post-increment have
1073 the same cost, which is lower than indexed and absolute, which also have
1074 the same cost. */
1075 struct double_op_cost
1077 /* Source operand is a register. */
1078 const int r2r;
1079 const int r2pc;
1080 const int r2m;
1082 /* Source operand is memory, using indirect register (@Rn) or indirect
1083 autoincrement (@Rn+) addressing modes. */
1084 const int ind2r;
1085 const int ind2pc;
1086 const int ind2m;
1088 /* Source operand is an immediate. */
1089 const int imm2r;
1090 const int imm2pc;
1091 const int imm2m;
1093 /* Source operand is memory, using indexed (x(Rn)) or absolute (&ADDR)
1094 addressing modes. */
1095 const int mem2r;
1096 const int mem2pc;
1097 const int mem2m;
1100 /* These structures describe the cost of MOV, BIT and CMP instructions, in terms
1101 of clock cycles or words. */
1102 static const struct double_op_cost cycle_cost_double_op_mov =
1104 1, 3, 3,
1105 2, 4, 4,
1106 2, 3, 4,
1107 3, 5, 5
1110 /* Cycle count when memory is the destination operand is one larger than above
1111 for instructions that aren't MOV, BIT or CMP. */
1112 static const struct double_op_cost cycle_cost_double_op =
1114 1, 3, 4,
1115 2, 4, 5,
1116 2, 3, 5,
1117 3, 5, 6
1120 static const struct double_op_cost size_cost_double_op =
1122 1, 1, 2,
1123 1, 1, 2,
1124 2, 2, 3,
1125 2, 2, 3
1128 struct msp430_multlib_costs
1130 const int mulhi;
1131 const int mulsi;
1132 const int muldi;
1135 /* There is no precise size cost when using libcalls, instead it is disparaged
1136 relative to other instructions.
1137 The cycle costs are from the CALL to the RET, inclusive.
1138 FIXME muldi cost is not accurate. */
1139 static const struct msp430_multlib_costs cycle_cost_multlib_32bit =
1141 27, 33, 66
1144 /* 32bit multiply takes a few more instructions on 16bit hwmult. */
1145 static const struct msp430_multlib_costs cycle_cost_multlib_16bit =
1147 27, 42, 66
1150 /* TARGET_REGISTER_MOVE_COST
1151 There is only one class of general-purpose, non-fixed registers, and the
1152 relative cost of moving data between them is always the same.
1153 Therefore, the default of 2 is optimal. */
1155 #undef TARGET_MEMORY_MOVE_COST
1156 #define TARGET_MEMORY_MOVE_COST msp430_memory_move_cost
1158 /* Return the cost of moving data between registers and memory.
1159 The returned cost must be relative to the default TARGET_REGISTER_MOVE_COST
1160 of 2.
1161 IN is false if the value is to be written to memory. */
1162 static int
1163 msp430_memory_move_cost (machine_mode mode ATTRIBUTE_UNUSED,
1164 reg_class_t rclass ATTRIBUTE_UNUSED,
1165 bool in)
1167 int cost;
1168 const struct double_op_cost *cost_p;
1169 /* Optimize with a code size focus by default, unless -O2 or above is
1170 specified. */
1171 bool speed = (!optimize_size && optimize >= 2);
1173 cost_p = (speed ? &cycle_cost_double_op_mov : &size_cost_double_op);
1175 if (in)
1176 /* Reading from memory using indirect addressing is assumed to be the more
1177 common case. */
1178 cost = cost_p->ind2r;
1179 else
1180 cost = cost_p->r2m;
1182 /* All register to register moves cost 1 cycle or 1 word, so multiply by 2
1183 to get the costs relative to TARGET_REGISTER_MOVE_COST of 2. */
1184 return 2 * cost;
1187 /* For X, which must be a MEM RTX, return TRUE if it is an indirect memory
1188 reference, @Rn or @Rn+. */
1189 static bool
1190 msp430_is_mem_indirect (rtx x)
1192 gcc_assert (GET_CODE (x) == MEM);
1193 rtx op0 = XEXP (x, 0);
1194 return (GET_CODE (op0) == REG || GET_CODE (op0) == POST_INC);
1197 /* Costs of MSP430 instructions are generally based on the addressing mode
1198 combination of the source and destination operands.
1199 Given source operand SRC (which may be NULL to indicate a single-operand
1200 instruction) and destination operand DST return the cost of this
1201 expression. */
1202 static int
1203 msp430_costs (rtx src, rtx dst, bool speed, rtx outer_rtx)
1205 enum rtx_code src_code = GET_CODE (src);
1206 enum rtx_code dst_code = GET_CODE (dst);
1207 enum rtx_code outer_code = GET_CODE (outer_rtx);
1208 machine_mode outer_mode = GET_MODE (outer_rtx);
1209 const struct double_op_cost *cost_p;
1210 cost_p = (speed ? &cycle_cost_double_op : &size_cost_double_op);
1212 if (outer_code == TRUNCATE
1213 && (outer_mode == QImode
1214 || outer_mode == HImode
1215 || outer_mode == PSImode))
1216 /* Truncation to these modes is normally free as a side effect of the
1217 instructions themselves. */
1218 return 0;
1220 if (dst_code == SYMBOL_REF
1221 || dst_code == LABEL_REF
1222 || dst_code == CONST_INT)
1223 /* Catch RTX like (minus (const_int 0) (reg)) but don't add any cost. */
1224 return 0;
1226 switch (src_code)
1228 case REG:
1229 return (dst_code == REG ? cost_p->r2r
1230 : (dst_code == PC ? cost_p->r2pc : cost_p->r2m));
1232 case CONST_INT:
1233 case SYMBOL_REF:
1234 case LABEL_REF:
1235 case CONST:
1236 return (dst_code == REG ? cost_p->imm2r
1237 : (dst_code == PC ? cost_p->imm2pc : cost_p->imm2m));
1240 case MEM:
1241 if (msp430_is_mem_indirect (src))
1242 return (dst_code == REG ? cost_p->ind2r : (dst_code == PC
1243 ? cost_p->ind2pc
1244 : cost_p->ind2m));
1245 else
1246 return (dst_code == REG ? cost_p->mem2r : (dst_code == PC
1247 ? cost_p->mem2pc
1248 : cost_p->mem2m));
1249 default:
1250 return cost_p->mem2m;
1254 /* Given source operand SRC and destination operand DST from the shift or
1255 rotate RTX OUTER_RTX, return the cost of performing that shift, assuming
1256 optimization for speed when SPEED is true. */
1257 static int
1258 msp430_shift_costs (rtx src, rtx dst, bool speed, rtx outer_rtx)
1260 int amt;
1261 enum rtx_code src_code = GET_CODE (src);
1262 enum rtx_code dst_code = GET_CODE (dst);
1263 const struct single_op_cost *cost_p;
1265 cost_p = (speed ? &cycle_cost_single_op : &size_cost_single_op);
1267 if (src_code != CONST_INT)
1268 /* The size or speed cost when the shift amount is unknown cannot be
1269 accurately calculated, so just disparage it slightly. */
1270 return 2 * msp430_costs (src, dst, speed, outer_rtx);
1272 if (use_helper_for_const_shift (GET_MODE (outer_rtx), amt = INTVAL (src)))
1274 /* GCC sometimes tries to perform shifts in some very inventive ways,
1275 resulting in much larger code size usage than necessary, if
1276 they are disparaged too much here. So in general, if
1277 use_helper_for_const_shift thinks a helper should be used, obey
1278 that and don't disparage the shift any more than a regular
1279 instruction, even though the shift may actually cost more.
1280 This ensures that the RTL generated at the initial expand pass has the
1281 expected shift instructions, which can be mapped to the helper
1282 functions. */
1283 return msp430_costs (src, dst, speed, outer_rtx);
1286 if (!msp430x)
1288 /* Each shift by one place will be emitted individually. */
1289 switch (dst_code)
1291 case REG:
1292 case CONST_INT:
1293 return amt * cost_p->reg;
1294 case MEM:
1295 if (msp430_is_mem_indirect (dst))
1296 return amt * cost_p->ind;
1297 else
1298 return amt * cost_p->mem;
1299 default:
1300 return amt * cost_p->mem;
1304 /* RRAM, RRCM, RRUM, RLAM are used for shift counts <= 4, otherwise, the 'X'
1305 versions are used.
1306 Instructions which shift a MEM operand will never actually be output. It
1307 will always be copied into a register to allow for efficient shifting. So
1308 the cost just takes into account the cost of an additional copy in that
1309 case. */
1310 return (amt <= 4 ? (speed ? amt : 1) : (speed ? amt + 1 : 2)
1311 + (dst_code == REG ? 0
1312 : msp430_costs (dst, gen_rtx_REG (HImode, 10), speed, outer_rtx)));
1315 /* Given source operand SRC and destination operand DST from the MULT/DIV/MOD
1316 RTX OUTER_RTX, return the cost of performing that operation, assuming
1317 optimization for speed when SPEED is true. */
1318 static int
1319 msp430_muldiv_costs (rtx src, rtx dst, bool speed, rtx outer_rtx,
1320 machine_mode outer_mode)
1322 enum rtx_code outer_code = GET_CODE (outer_rtx);
1323 const struct msp430_multlib_costs *cost_p;
1324 cost_p = (msp430_use_16bit_hwmult ()
1325 ? &cycle_cost_multlib_32bit
1326 : &cycle_cost_multlib_16bit);
1328 int factor = 1;
1329 /* Only used in some calculations. */
1330 int mode_factor = 1;
1331 if (outer_mode == SImode)
1332 mode_factor = 2;
1333 else if (outer_mode == PSImode)
1334 /* PSImode multiplication is performed using SImode operands, so has extra
1335 cost to factor in the conversions necessary before/after the
1336 operation. */
1337 mode_factor = 3;
1338 else if (outer_mode == DImode)
1339 mode_factor = 4;
1341 if (!speed)
1343 /* The codesize cost of using a helper function to perform the
1344 multiplication or division cannot be accurately calculated, since the
1345 cost depends on how many times the operation is performed in the
1346 entire program. */
1347 if (outer_code != MULT)
1348 /* Division is always expensive. */
1349 factor = 7;
1350 else if (((msp430_use_16bit_hwmult () && outer_mode != DImode)
1351 || msp430_use_32bit_hwmult ()
1352 || msp430_use_f5_series_hwmult ()))
1353 /* When the hardware multiplier is available, only disparage
1354 slightly. */
1355 factor = 2;
1356 else
1357 factor = 5;
1358 return factor * mode_factor * msp430_costs (src, dst, speed, outer_rtx);
1361 /* When there is hardware multiply support, there is a relatively low, fixed
1362 cycle cost to performing any multiplication, but when there is no hardware
1363 multiply support it is very costly. That precise cycle cost has not been
1364 calculated here.
1365 Division is extra slow since it always uses a software library.
1366 The 16-bit hardware multiply library cannot be used to produce 64-bit
1367 results. */
1368 if (outer_code != MULT || !msp430_has_hwmult ()
1369 || (outer_mode == DImode && msp430_use_16bit_hwmult ()))
1371 factor = (outer_code == MULT ? 50 : 70);
1372 return factor * mode_factor * msp430_costs (src, dst, speed, outer_rtx);
1375 switch (outer_mode)
1377 case E_QImode:
1378 case E_HImode:
1379 /* Include the cost of copying the operands into and out of the hardware
1380 multiply routine. */
1381 return cost_p->mulhi + (3 * msp430_costs (src, dst, speed, outer_rtx));
1383 case E_PSImode:
1384 /* Extra factor for the conversions necessary to do PSI->SI before the
1385 operation. */
1386 factor = 2;
1387 /* fallthru. */
1388 case E_SImode:
1389 return factor * (cost_p->mulsi
1390 + (6 * msp430_costs (src, dst, speed, outer_rtx)));
1392 case E_DImode:
1393 default:
1394 return cost_p->muldi + (12 * msp430_costs (src, dst, speed, outer_rtx));
1398 /* Recurse within X to find the actual destination operand of the expression.
1399 For example:
1400 (plus (ashift (minus (ashift (reg)
1401 (const_int) ......
1402 should return the reg RTX. */
1403 static rtx
1404 msp430_get_inner_dest_code (rtx x)
1406 enum rtx_code code = GET_CODE (x);
1407 rtx op0 = XEXP (x, 0);
1408 switch (code)
1410 case REG:
1411 case SYMBOL_REF:
1412 case CONST_INT:
1413 case CONST:
1414 case LABEL_REF:
1415 return x;
1417 case MEM:
1418 /* Return the MEM expr not the inner REG for these cases. */
1419 switch (GET_CODE (op0))
1421 case REG:
1422 case SYMBOL_REF:
1423 case LABEL_REF:
1424 case CONST:
1425 case POST_INC:
1426 return x;
1428 case PLUS:
1429 /* return MEM (PLUS (REG) (CONST)) */
1430 if (GET_CODE (XEXP (op0, 0)) == REG)
1432 if (GET_CODE (XEXP (op0, 1)) == CONST_INT
1433 || GET_CODE (XEXP (op0, 1)) == CONST
1434 || GET_CODE (XEXP (op0, 1)) == LABEL_REF
1435 || GET_CODE (XEXP (op0, 1)) == SYMBOL_REF)
1436 return x;
1437 else
1438 return msp430_get_inner_dest_code (op0);
1440 return msp430_get_inner_dest_code (op0);
1442 default:
1443 if (GET_RTX_FORMAT (code)[0] != 'e')
1444 return x;
1445 return msp430_get_inner_dest_code (op0);
1447 break;
1449 default:
1450 if (op0 == NULL_RTX)
1451 gcc_unreachable ();
1452 else
1454 if (GET_RTX_FORMAT (code)[0] != 'e'
1455 && code != ENTRY_VALUE)
1456 return x;
1457 return msp430_get_inner_dest_code (op0);
1462 /* Calculate the cost of an MSP430 single-operand instruction, for operand DST
1463 within the RTX OUTER_RTX, optimizing for speed if SPEED is true. */
1464 static int
1465 msp430_single_op_cost (rtx dst, bool speed, rtx /* outer_rtx */)
1467 enum rtx_code dst_code = GET_CODE (dst);
1468 const struct single_op_cost *cost_p;
1469 const struct double_op_cost *double_op_cost_p;
1471 cost_p = (speed ? &cycle_cost_single_op : &size_cost_single_op);
1472 double_op_cost_p = (speed ? &cycle_cost_double_op : &size_cost_double_op);
1474 switch (dst_code)
1476 case REG:
1477 return cost_p->reg;
1478 case MEM:
1479 if (msp430_is_mem_indirect (dst))
1480 return cost_p->ind;
1481 else
1482 return cost_p->mem;
1484 case CONST_INT:
1485 case CONST_FIXED:
1486 case CONST_DOUBLE:
1487 case SYMBOL_REF:
1488 case CONST:
1489 /* A constant value would need to be copied into a register first. */
1490 return double_op_cost_p->imm2r + cost_p->reg;
1492 default:
1493 return cost_p->mem;
1497 #undef TARGET_RTX_COSTS
1498 #define TARGET_RTX_COSTS msp430_rtx_costs
1500 /* This target hook describes the relative costs of RTL expressions.
1501 The function recurses to just before the lowest level of the expression,
1502 when both of the operands of the expression can be examined at the same time.
1503 This is because the cost of the expression depends on the specific
1504 addressing mode combination of the operands.
1505 The hook returns true when all subexpressions of X have been processed, and
1506 false when rtx_cost should recurse. */
1507 static bool
1508 msp430_rtx_costs (rtx x,
1509 machine_mode mode,
1510 int outer_code ATTRIBUTE_UNUSED,
1511 int opno ATTRIBUTE_UNUSED,
1512 int * total,
1513 bool speed)
1515 enum rtx_code code = GET_CODE (x);
1516 rtx dst, src;
1517 rtx dst_inner, src_inner;
1519 *total = 0;
1520 dst = XEXP (x, 0);
1521 if (GET_RTX_LENGTH (code) == 1)
1522 /* Some RTX that are single-op in GCC are double-op when translated to
1523 MSP430 instructions e.g NOT, NEG, ZERO_EXTEND. */
1524 src = dst;
1525 else
1526 src = XEXP (x, 1);
1529 switch (code)
1531 case SET:
1532 /* Ignoring SET improves codesize. */
1533 if (!speed)
1534 return true;
1535 /* fallthru. */
1536 case PLUS:
1537 if (outer_code == MEM)
1538 /* Do not add any cost for the plus itself, but recurse in case there
1539 are more complicated RTX inside. */
1540 return false;
1541 /* fallthru. */
1542 case MINUS:
1543 case AND:
1544 case IOR:
1545 case XOR:
1546 case NOT:
1547 case ZERO_EXTEND:
1548 case TRUNCATE:
1549 case NEG:
1550 case ZERO_EXTRACT:
1551 case SIGN_EXTRACT:
1552 case IF_THEN_ELSE:
1553 dst_inner = msp430_get_inner_dest_code (dst);
1554 src_inner = msp430_get_inner_dest_code (src);
1555 *total = COSTS_N_INSNS (msp430_costs (src_inner, dst_inner, speed, x));
1556 if (mode == SImode)
1557 *total *= 2;
1558 if (mode == DImode)
1559 *total *= 4;
1560 return false;
1562 case ROTATE:
1563 case ASHIFT:
1564 case ASHIFTRT:
1565 case LSHIFTRT:
1566 dst_inner = msp430_get_inner_dest_code (dst);
1567 src_inner = msp430_get_inner_dest_code (src);
1568 *total = COSTS_N_INSNS (msp430_shift_costs (src_inner, dst_inner,
1569 speed, x));
1570 if (mode == SImode)
1571 *total *= 2;
1572 if (mode == DImode)
1573 *total *= 4;
1574 return false;
1576 case MULT:
1577 case DIV:
1578 case MOD:
1579 case UDIV:
1580 case UMOD:
1581 dst_inner = msp430_get_inner_dest_code (dst);
1582 src_inner = msp430_get_inner_dest_code (src);
1583 *total = COSTS_N_INSNS (msp430_muldiv_costs (src_inner, dst_inner, speed,
1584 x, mode));
1585 return false;
1587 case CALL:
1588 case SIGN_EXTEND:
1589 dst_inner = msp430_get_inner_dest_code (dst);
1590 *total = COSTS_N_INSNS (msp430_single_op_cost (dst_inner, speed, x));
1591 if (mode == SImode)
1592 *total *= 2;
1593 if (mode == DImode)
1594 *total *= 4;
1595 return false;
1597 case CONST_INT:
1598 case CONST_FIXED:
1599 case CONST_DOUBLE:
1600 case SYMBOL_REF:
1601 case CONST:
1602 case LABEL_REF:
1603 case REG:
1604 case PC:
1605 case POST_INC:
1606 if (mode == SImode)
1607 *total = COSTS_N_INSNS (2);
1608 else if (mode == DImode)
1609 *total = COSTS_N_INSNS (4);
1610 return true;
1612 case MEM:
1613 /* PSImode operands are expensive when in memory. */
1614 if (mode == PSImode)
1615 *total = COSTS_N_INSNS (1);
1616 else if (mode == SImode)
1617 *total = COSTS_N_INSNS (2);
1618 else if (mode == DImode)
1619 *total = COSTS_N_INSNS (4);
1620 /* Recurse into the MEM. */
1621 return false;
1623 case EQ:
1624 case NE:
1625 case GT:
1626 case GTU:
1627 case GE:
1628 case GEU:
1629 case LT:
1630 case LTU:
1631 case LE:
1632 case LEU:
1633 /* Conditions are mostly equivalent, changing their relative
1634 costs has no effect. */
1635 return false;
1637 case ASM_OPERANDS:
1638 case ASM_INPUT:
1639 case CLOBBER:
1640 case COMPARE:
1641 case CONCAT:
1642 case ENTRY_VALUE:
1643 /* Other unhandled expressions. */
1644 return false;
1646 default:
1647 return false;
1651 #undef TARGET_INSN_COST
1652 #define TARGET_INSN_COST msp430_insn_cost
1654 static int
1655 msp430_insn_cost (rtx_insn *insn, bool speed ATTRIBUTE_UNUSED)
1657 if (recog_memoized (insn) < 0)
1658 return 0;
1660 /* The returned cost must be relative to COSTS_N_INSNS (1). An insn with a
1661 length of 2 bytes is the smallest possible size and so must be equivalent
1662 to COSTS_N_INSNS (1). */
1663 return COSTS_N_INSNS (get_attr_length (insn) / 2);
1665 /* FIXME Add more detailed costs when optimizing for speed.
1666 For now the length of the instruction is a good approximiation and roughly
1667 correlates with cycle cost. */
1671 /* Function Entry and Exit */
1673 /* The MSP430 call frame looks like this:
1675 <higher addresses>
1676 +--------------------+
1678 | Stack Arguments |
1680 +--------------------+ <-- "arg pointer"
1682 | PC from call | (2 bytes for 430, 4 for TARGET_LARGE)
1684 +--------------------+
1685 | SR if this func has|
1686 | been called via an |
1687 | interrupt. |
1688 +--------------------+ <-- SP before prologue, also AP
1690 | Saved Regs | (2 bytes per reg for 430, 4 per for TARGET_LARGE)
1692 +--------------------+ <-- "frame pointer"
1694 | Locals |
1696 +--------------------+
1698 | Outgoing Args |
1700 +--------------------+ <-- SP during function
1701 <lower addresses>
1705 /* We use this to wrap all emitted insns in the prologue, so they get
1706 the "frame-related" (/f) flag set. */
1707 static rtx
1708 F (rtx x)
1710 RTX_FRAME_RELATED_P (x) = 1;
1711 return x;
1714 /* This is the one spot that decides if a register is to be saved and
1715 restored in the prologue/epilogue. */
1716 static bool
1717 msp430_preserve_reg_p (int regno)
1719 /* PC, SP, SR, and the constant generator. */
1720 if (regno <= 3)
1721 return false;
1723 /* FIXME: add interrupt, EH, etc. */
1724 if (crtl->calls_eh_return)
1725 return true;
1727 /* Shouldn't be more than the above, but just in case... */
1728 if (fixed_regs[regno])
1729 return false;
1731 /* For interrupt functions we must save and restore the used regs that
1732 would normally be caller-saved (R11->R15). */
1733 if (msp430_is_interrupt_func () && regno >= 11 && regno <= 15)
1735 if (crtl->is_leaf && df_regs_ever_live_p (regno))
1736 /* If the interrupt func is a leaf then we only need to restore the
1737 caller-saved regs that are used. */
1738 return true;
1739 else if (!crtl->is_leaf)
1740 /* If the interrupt function is not a leaf we must save all
1741 caller-saved regs in case the callee modifies them. */
1742 return true;
1745 if (!call_used_or_fixed_reg_p (regno)
1746 && df_regs_ever_live_p (regno))
1747 return true;
1749 return false;
1752 /* Compute all the frame-related fields in our machine_function
1753 structure. */
1754 static void
1755 msp430_compute_frame_info (void)
1757 int i;
1759 cfun->machine->computed = 1;
1760 cfun->machine->framesize_regs = 0;
1761 cfun->machine->framesize_locals = get_frame_size ();
1762 cfun->machine->framesize_outgoing = crtl->outgoing_args_size;
1764 for (i = 0; i < ARG_POINTER_REGNUM; i ++)
1765 if (msp430_preserve_reg_p (i))
1767 cfun->machine->need_to_save[i] = 1;
1768 cfun->machine->framesize_regs += (TARGET_LARGE ? 4 : 2);
1770 else
1771 cfun->machine->need_to_save[i] = 0;
1773 if ((cfun->machine->framesize_locals + cfun->machine->framesize_outgoing) & 1)
1774 cfun->machine->framesize_locals ++;
1776 cfun->machine->framesize = (cfun->machine->framesize_regs
1777 + cfun->machine->framesize_locals
1778 + cfun->machine->framesize_outgoing);
1781 /* Attribute Handling. */
1783 const char * const ATTR_INTR = "interrupt";
1784 const char * const ATTR_WAKEUP = "wakeup";
1785 const char * const ATTR_NAKED = "naked";
1786 const char * const ATTR_REENT = "reentrant";
1787 const char * const ATTR_CRIT = "critical";
1788 const char * const ATTR_LOWER = "lower";
1789 const char * const ATTR_UPPER = "upper";
1790 const char * const ATTR_EITHER = "either";
1791 const char * const ATTR_NOINIT = "noinit";
1792 const char * const ATTR_PERSIST = "persistent";
1794 static inline bool
1795 has_attr (const char * attr, tree decl)
1797 if (decl == NULL_TREE)
1798 return false;
1799 return lookup_attribute (attr, DECL_ATTRIBUTES (decl)) != NULL_TREE;
1802 static bool
1803 is_interrupt_func (tree decl = current_function_decl)
1805 return has_attr (ATTR_INTR, decl);
1808 /* Returns true if the current function has the "interrupt" attribute. */
1810 bool
1811 msp430_is_interrupt_func (void)
1813 return is_interrupt_func (current_function_decl);
1816 static bool
1817 is_wakeup_func (tree decl = current_function_decl)
1819 return is_interrupt_func (decl) && has_attr (ATTR_WAKEUP, decl);
1822 static inline bool
1823 is_naked_func (tree decl = current_function_decl)
1825 return has_attr (ATTR_NAKED, decl);
1828 static inline bool
1829 is_reentrant_func (tree decl = current_function_decl)
1831 return has_attr (ATTR_REENT, decl);
1834 static inline bool
1835 is_critical_func (tree decl = current_function_decl)
1837 return has_attr (ATTR_CRIT, decl);
1840 static bool
1841 has_section_name (const char * name, tree decl = current_function_decl)
1843 if (decl == NULL_TREE)
1844 return false;
1845 return (DECL_SECTION_NAME (decl)
1846 && (strcmp (name, DECL_SECTION_NAME (decl)) == 0));
1849 #undef TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS
1850 #define TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS \
1851 msp430_allocate_stack_slots_for_args
1853 static bool
1854 msp430_allocate_stack_slots_for_args (void)
1856 /* Naked functions should not allocate stack slots for arguments. */
1857 return ! is_naked_func ();
1860 #undef TARGET_WARN_FUNC_RETURN
1861 #define TARGET_WARN_FUNC_RETURN msp430_warn_func_return
1863 static bool
1864 msp430_warn_func_return (tree decl)
1866 /* Naked functions are implemented entirely in assembly, including the
1867 return sequence, so suppress warnings about this. */
1868 return !is_naked_func (decl);
1871 /* Verify MSP430 specific attributes. */
1872 #define TREE_NAME_EQ(NAME, STR) (strcmp (IDENTIFIER_POINTER (NAME), (STR)) == 0)
1874 static tree
1875 msp430_attr (tree * node,
1876 tree name,
1877 tree args,
1878 int flags ATTRIBUTE_UNUSED,
1879 bool * no_add_attrs)
1881 gcc_assert (DECL_P (* node));
1883 /* Only the interrupt attribute takes an argument. */
1884 if (args != NULL)
1886 tree value = TREE_VALUE (args);
1888 switch (TREE_CODE (value))
1890 case STRING_CST:
1891 if ( strcmp (TREE_STRING_POINTER (value), "reset")
1892 && strcmp (TREE_STRING_POINTER (value), "nmi")
1893 && strcmp (TREE_STRING_POINTER (value), "watchdog"))
1894 /* Allow the attribute to be added - the linker script
1895 being used may still recognise this name. */
1896 warning (OPT_Wattributes,
1897 "unrecognized interrupt vector argument of %qE attribute",
1898 name);
1899 break;
1901 case INTEGER_CST:
1902 if (wi::gtu_p (wi::to_wide (value), 63))
1903 /* Allow the attribute to be added - the linker script
1904 being used may still recognise this value. */
1905 warning (OPT_Wattributes,
1906 "numeric argument of %qE attribute must be in range [0-63]",
1907 name);
1908 break;
1910 default:
1911 warning (OPT_Wattributes,
1912 "argument of %qE attribute is not a string constant "
1913 "or number", name);
1914 *no_add_attrs = true;
1915 break;
1919 const char * message = NULL;
1921 if (TREE_CODE (* node) != FUNCTION_DECL)
1923 message = "%qE attribute only applies to functions";
1925 else if (TREE_NAME_EQ (name, ATTR_INTR))
1927 if (TREE_CODE (TREE_TYPE (* node)) == FUNCTION_TYPE
1928 && ! VOID_TYPE_P (TREE_TYPE (TREE_TYPE (* node))))
1929 message = "interrupt handlers must be void";
1930 else
1932 /* Ensure interrupt handlers never get optimised out. */
1933 TREE_USED (* node) = 1;
1934 DECL_PRESERVE_P (* node) = 1;
1936 if (is_critical_func (* node))
1938 /* We always ignore the critical attribute when interrupt and
1939 critical are used together. */
1940 warning (OPT_Wattributes,
1941 "critical attribute has no effect on interrupt functions");
1942 DECL_ATTRIBUTES (*node) = remove_attribute (ATTR_CRIT,
1943 DECL_ATTRIBUTES (* node));
1946 else if (TREE_NAME_EQ (name, ATTR_CRIT))
1948 if (is_interrupt_func ( *node))
1949 message = "critical attribute has no effect on interrupt functions";
1952 if (message)
1954 warning (OPT_Wattributes, message, name);
1955 * no_add_attrs = true;
1958 return NULL_TREE;
1961 static tree
1962 msp430_section_attr (tree * node,
1963 tree name,
1964 tree args,
1965 int flags ATTRIBUTE_UNUSED,
1966 bool * no_add_attrs ATTRIBUTE_UNUSED)
1968 gcc_assert (DECL_P (* node));
1969 gcc_assert (args == NULL);
1971 const char * message = NULL;
1973 /* The "noinit", "persistent", and "section" attributes are handled
1974 generically, so we cannot set up additional target-specific attribute
1975 exclusions using the existing mechanism. */
1976 if (has_attr (ATTR_NOINIT, *node) && !TREE_NAME_EQ (name, "lower"))
1977 message = G_("ignoring attribute %qE because it conflicts with "
1978 "attribute %<noinit%>");
1979 else if (has_attr ("section", *node) && !TREE_NAME_EQ (name, "lower"))
1980 message = G_("ignoring attribute %qE because it conflicts with "
1981 "attribute %<section%>");
1982 else if (has_attr (ATTR_PERSIST, *node) && !TREE_NAME_EQ (name, "lower"))
1983 message = G_("ignoring attribute %qE because it conflicts with "
1984 "attribute %<persistent%>");
1985 /* It does not make sense to use upper/lower/either attributes without
1986 -mlarge.
1987 Without -mlarge, "lower" is the default and only region, so is redundant.
1988 Without -mlarge, "upper" will (and "either" might) place code/data in the
1989 upper region, which for data could result in relocation overflows, and for
1990 code could result in stack mismanagement and incorrect call/return
1991 instructions. */
1992 else if (!TARGET_LARGE)
1993 message = G_("%qE attribute ignored. Large memory model (%<-mlarge%>) "
1994 "is required.");
1996 if (message)
1998 warning (OPT_Wattributes, message, name);
1999 * no_add_attrs = true;
2002 return NULL_TREE;
2005 /* Helper to define attribute exclusions. */
2006 #define ATTR_EXCL(name, function, type, variable) \
2007 { name, function, type, variable }
2009 /* "reentrant", "critical" and "naked" functions must conflict because
2010 they all modify the prologue or epilogue of functions in mutually exclusive
2011 ways. */
2012 static const struct attribute_spec::exclusions attr_reent_exclusions[] =
2014 ATTR_EXCL (ATTR_NAKED, true, true, true),
2015 ATTR_EXCL (ATTR_CRIT, true, true, true),
2016 ATTR_EXCL (NULL, false, false, false)
2019 static const struct attribute_spec::exclusions attr_naked_exclusions[] =
2021 ATTR_EXCL (ATTR_REENT, true, true, true),
2022 ATTR_EXCL (ATTR_CRIT, true, true, true),
2023 ATTR_EXCL (NULL, false, false, false)
2026 static const struct attribute_spec::exclusions attr_crit_exclusions[] =
2028 ATTR_EXCL (ATTR_REENT, true, true, true),
2029 ATTR_EXCL (ATTR_NAKED, true, true, true),
2030 ATTR_EXCL (NULL, false, false, false)
2033 /* Attributes which put the given object in a specific section must conflict
2034 with one another. */
2035 static const struct attribute_spec::exclusions attr_lower_exclusions[] =
2037 ATTR_EXCL (ATTR_UPPER, true, true, true),
2038 ATTR_EXCL (ATTR_EITHER, true, true, true),
2039 ATTR_EXCL (NULL, false, false, false)
2042 static const struct attribute_spec::exclusions attr_upper_exclusions[] =
2044 ATTR_EXCL (ATTR_LOWER, true, true, true),
2045 ATTR_EXCL (ATTR_EITHER, true, true, true),
2046 ATTR_EXCL (NULL, false, false, false)
2049 static const struct attribute_spec::exclusions attr_either_exclusions[] =
2051 ATTR_EXCL (ATTR_LOWER, true, true, true),
2052 ATTR_EXCL (ATTR_UPPER, true, true, true),
2053 ATTR_EXCL (NULL, false, false, false)
2056 #undef TARGET_ATTRIBUTE_TABLE
2057 #define TARGET_ATTRIBUTE_TABLE msp430_attribute_table
2059 /* Table of MSP430-specific attributes. */
2060 TARGET_GNU_ATTRIBUTES (msp430_attribute_table,
2062 /* { name, min_num_args, max_num_args, decl_req, type_req, fn_type_req,
2063 affects_type_identity, handler, exclude } */
2064 { ATTR_INTR, 0, 1, true, false, false, false, msp430_attr, NULL },
2065 { ATTR_NAKED, 0, 0, true, false, false, false, msp430_attr,
2066 attr_naked_exclusions },
2067 { ATTR_REENT, 0, 0, true, false, false, false, msp430_attr,
2068 attr_reent_exclusions },
2069 { ATTR_CRIT, 0, 0, true, false, false, false, msp430_attr,
2070 attr_crit_exclusions },
2071 { ATTR_WAKEUP, 0, 0, true, false, false, false, msp430_attr, NULL },
2073 { ATTR_LOWER, 0, 0, true, false, false, false, msp430_section_attr,
2074 attr_lower_exclusions },
2075 { ATTR_UPPER, 0, 0, true, false, false, false, msp430_section_attr,
2076 attr_upper_exclusions },
2077 { ATTR_EITHER, 0, 0, true, false, false, false, msp430_section_attr,
2078 attr_either_exclusions }
2081 #undef TARGET_HANDLE_GENERIC_ATTRIBUTE
2082 #define TARGET_HANDLE_GENERIC_ATTRIBUTE msp430_handle_generic_attribute
2084 tree
2085 msp430_handle_generic_attribute (tree *node,
2086 tree name,
2087 tree args ATTRIBUTE_UNUSED,
2088 int flags ATTRIBUTE_UNUSED,
2089 bool *no_add_attrs)
2092 const char *message = NULL;
2094 /* Permit the "lower" attribute to be set on variables with the "section",
2095 "noinit" and "persistent" attributes. This is used to indicate that the
2096 corresponding output section will be in lower memory, so a 430X
2097 instruction is not required to handle it. */
2098 if (has_attr (ATTR_LOWER, *node)
2099 && !(TREE_NAME_EQ (name, "section") || TREE_NAME_EQ (name, ATTR_PERSIST)
2100 || TREE_NAME_EQ (name, ATTR_NOINIT)))
2101 message = G_("ignoring attribute %qE because it conflicts with "
2102 "attribute %<lower%>");
2103 else if (has_attr (ATTR_UPPER, *node))
2104 message = G_("ignoring attribute %qE because it conflicts with "
2105 "attribute %<upper%>");
2106 else if (has_attr (ATTR_EITHER, *node))
2107 message = G_("ignoring attribute %qE because it conflicts with "
2108 "attribute %<either%>");
2110 if (message)
2112 warning (OPT_Wattributes, message, name);
2113 *no_add_attrs = true;
2116 return NULL_TREE;
2119 /* Given a non-automatic VAR_DECL which can possibly have a section, return
2120 true if the variable will definitely be placed in the lower memory
2121 region (below address 0x10000). */
2122 static bool
2123 msp430_var_in_low_mem (tree decl)
2125 gcc_assert (VAR_P (decl));
2127 /* "noinit" variables are always placed in the lower memory region. */
2128 if (has_attr (ATTR_UPPER, decl)
2129 || has_attr (ATTR_EITHER, decl)
2130 || has_attr (ATTR_PERSIST, decl)
2131 /* Unless the variable is marked with the lower or noinit attribute, we
2132 cannot assume that it is in the lower region if it is marked with the
2133 section attribute or -mdata-region={upper,either,none} have been
2134 passed.
2135 The noinit and section attributes conflict. */
2136 || (!has_attr (ATTR_LOWER, decl) && !has_attr (ATTR_NOINIT, decl)
2137 && (has_attr ("section", decl)
2138 || msp430_data_region == MSP430_REGION_UPPER
2139 || msp430_data_region == MSP430_REGION_EITHER
2140 || msp430_data_region == MSP430_REGION_ANY)))
2141 return false;
2142 return true;
2145 #undef TARGET_ENCODE_SECTION_INFO
2146 #define TARGET_ENCODE_SECTION_INFO msp430_encode_section_info
2148 /* Encode whether a SYMBOL_REF is definitely in the lower memory region. */
2149 static void
2150 msp430_encode_section_info (tree decl, rtx rtl, int first)
2152 rtx symbol;
2153 default_encode_section_info (decl, rtl, first);
2155 /* Careful not to prod global register variables. */
2156 if (!MEM_P (rtl))
2157 return;
2158 symbol = XEXP (rtl, 0);
2159 if (GET_CODE (symbol) != SYMBOL_REF)
2160 return;
2162 if (VAR_P (decl)
2163 && (TREE_STATIC (decl) || DECL_EXTERNAL (decl))
2164 && msp430_var_in_low_mem (decl))
2165 SYMBOL_REF_FLAGS (symbol) = SYMBOL_FLAG_LOW_MEM;
2168 #undef TARGET_ASM_FUNCTION_PROLOGUE
2169 #define TARGET_ASM_FUNCTION_PROLOGUE msp430_start_function
2171 static void
2172 msp430_start_function (FILE *outfile)
2174 int r, n;
2176 fprintf (outfile, "; start of function\n");
2178 if (DECL_ATTRIBUTES (current_function_decl) != NULL_TREE)
2180 fprintf (outfile, "; attributes: ");
2181 if (is_naked_func ())
2182 fprintf (outfile, "naked ");
2183 if (msp430_is_interrupt_func ())
2184 fprintf (outfile, "interrupt ");
2185 if (is_reentrant_func ())
2186 fprintf (outfile, "reentrant ");
2187 if (is_critical_func ())
2188 fprintf (outfile, "critical ");
2189 if (is_wakeup_func ())
2190 fprintf (outfile, "wakeup ");
2191 fprintf (outfile, "\n");
2194 fprintf (outfile, "; framesize_regs: %d\n",
2195 cfun->machine->framesize_regs);
2196 fprintf (outfile, "; framesize_locals: %d\n",
2197 cfun->machine->framesize_locals);
2198 fprintf (outfile, "; framesize_outgoing: %d\n",
2199 cfun->machine->framesize_outgoing);
2200 fprintf (outfile, "; framesize: %d\n", cfun->machine->framesize);
2201 fprintf (outfile, "; elim ap -> fp %d\n",
2202 msp430_initial_elimination_offset (ARG_POINTER_REGNUM,
2203 FRAME_POINTER_REGNUM));
2204 fprintf (outfile, "; elim fp -> sp %d\n",
2205 msp430_initial_elimination_offset (FRAME_POINTER_REGNUM,
2206 STACK_POINTER_REGNUM));
2208 n = 0;
2209 fprintf (outfile, "; saved regs:");
2210 for (r = 0; r < ARG_POINTER_REGNUM; r++)
2211 if (cfun->machine->need_to_save[r])
2213 fprintf (outfile, " %s", reg_names[r]);
2214 n = 1;
2216 if (n == 0)
2217 fprintf (outfile, "(none)");
2218 fprintf (outfile, "\n");
2221 /* Common code to change the stack pointer. */
2222 static void
2223 increment_stack (HOST_WIDE_INT amount)
2225 rtx inc;
2226 rtx sp = stack_pointer_rtx;
2228 if (amount == 0)
2229 return;
2231 if (amount < 0)
2233 inc = GEN_INT (- amount);
2234 if (TARGET_LARGE)
2235 F (emit_insn (gen_subpsi3 (sp, sp, inc)));
2236 else
2237 F (emit_insn (gen_subhi3 (sp, sp, inc)));
2239 else
2241 inc = GEN_INT (amount);
2242 if (TARGET_LARGE)
2243 F (emit_insn (gen_addpsi3 (sp, sp, inc)));
2244 else
2245 F (emit_insn (gen_addhi3 (sp, sp, inc)));
2249 void
2250 msp430_start_function (FILE *file, const char *name, tree decl)
2252 tree int_attr;
2254 int_attr = lookup_attribute ("interrupt", DECL_ATTRIBUTES (decl));
2255 if (int_attr != NULL_TREE)
2257 tree intr_vector = TREE_VALUE (int_attr);
2259 if (intr_vector != NULL_TREE)
2261 char buf[101];
2263 /* Interrupt vector sections should be unique, but use of weak
2264 functions implies multiple definitions. */
2265 if (DECL_WEAK (decl))
2267 error ("argument to interrupt attribute is unsupported for weak "
2268 "functions");
2271 intr_vector = TREE_VALUE (intr_vector);
2273 /* The interrupt attribute has a vector value. Turn this into a
2274 section name, switch to that section and put the address of
2275 the current function into that vector slot. Note msp430_attr()
2276 has already verified the vector name for us. */
2277 if (TREE_CODE (intr_vector) == STRING_CST)
2278 sprintf (buf, "__interrupt_vector_%.80s",
2279 TREE_STRING_POINTER (intr_vector));
2280 else /* TREE_CODE (intr_vector) == INTEGER_CST */
2281 sprintf (buf, "__interrupt_vector_%u",
2282 (unsigned int) TREE_INT_CST_LOW (intr_vector));
2284 switch_to_section (get_section (buf, SECTION_CODE, decl));
2285 fputs ("\t.word\t", file);
2286 assemble_name (file, name);
2287 fputc ('\n', file);
2288 fputc ('\t', file);
2292 switch_to_section (function_section (decl));
2293 ASM_OUTPUT_TYPE_DIRECTIVE (file, name, "function");
2294 ASM_OUTPUT_FUNCTION_LABEL (file, name, decl);
2297 static const char * const lower_prefix = ".lower";
2298 static const char * const upper_prefix = ".upper";
2299 static const char * const either_prefix = ".either";
2301 /* Generate a prefix for a section name, based upon
2302 the region into which the object should be placed. */
2304 static const char *
2305 gen_prefix (tree decl)
2307 if (DECL_ONE_ONLY (decl))
2308 return NULL;
2310 /* If the user has specified a particular section then do not use any
2311 prefix. */
2312 if (has_attr ("section", decl))
2313 return NULL;
2315 /* If the function has been put in the .lowtext section (because it is an
2316 interrupt handler, and the large memory model is used), then do not add
2317 any prefixes. */
2318 if (has_section_name (".lowtext", decl))
2319 return NULL;
2321 /* Memory regions require the large memory model. */
2322 if (!TARGET_LARGE)
2323 return NULL;
2325 /* Note that we always apply the lower prefix when the attribute has been
2326 used. But we only apply the lower prefix when the lower region has been
2327 specified by a command line option if -muse-lower-region-prefix has also
2328 been passed. */
2329 if (has_attr (ATTR_LOWER, decl))
2330 return lower_prefix;
2332 if (has_attr (ATTR_UPPER, decl))
2333 return upper_prefix;
2335 if (has_attr (ATTR_EITHER, decl))
2336 return either_prefix;
2338 if (TREE_CODE (decl) == FUNCTION_DECL)
2340 if ((msp430_code_region == MSP430_REGION_LOWER)
2341 && TARGET_USE_LOWER_REGION_PREFIX)
2342 return lower_prefix;
2344 if (msp430_code_region == MSP430_REGION_UPPER)
2345 return upper_prefix;
2347 if (msp430_code_region == MSP430_REGION_EITHER)
2348 return either_prefix;
2350 else
2352 if ((msp430_data_region == MSP430_REGION_LOWER)
2353 && TARGET_USE_LOWER_REGION_PREFIX)
2354 return lower_prefix;
2356 if (msp430_data_region == MSP430_REGION_UPPER)
2357 return upper_prefix;
2359 if (msp430_data_region == MSP430_REGION_EITHER)
2360 return either_prefix;
2363 return NULL;
2366 #undef TARGET_ASM_SELECT_SECTION
2367 #define TARGET_ASM_SELECT_SECTION msp430_select_section
2369 static section *
2370 msp430_select_section (tree decl, int reloc, unsigned HOST_WIDE_INT align)
2372 const char *prefix;
2373 const char *sec_name;
2374 const char *base_sec_name;
2376 gcc_assert (decl != NULL_TREE);
2378 if (TREE_CODE (decl) == STRING_CST
2379 || TREE_CODE (decl) == CONSTRUCTOR
2380 || TREE_CODE (decl) == INTEGER_CST
2381 || TREE_CODE (decl) == VECTOR_CST
2382 || TREE_CODE (decl) == COMPLEX_CST)
2383 return default_select_section (decl, reloc, align);
2385 /* In large mode we must make sure that interrupt handlers are put into
2386 low memory as the vector table only accepts 16-bit addresses. */
2387 if (TARGET_LARGE && TREE_CODE (decl) == FUNCTION_DECL
2388 && is_interrupt_func (decl))
2389 return get_section (".lowtext", SECTION_CODE | SECTION_WRITE , decl);
2391 /* The "noinit" and "persistent" attributes are handled generically. */
2392 if (has_attr (ATTR_NOINIT, decl) || has_attr (ATTR_PERSIST, decl))
2393 return default_elf_select_section (decl, reloc, align);
2395 prefix = gen_prefix (decl);
2397 switch (categorize_decl_for_section (decl, reloc))
2399 case SECCAT_TEXT:
2400 if (!prefix)
2401 return text_section;
2402 base_sec_name = ".text";
2403 break;
2404 case SECCAT_DATA:
2405 if (!prefix)
2406 return data_section;
2407 base_sec_name = ".data";
2408 break;
2409 case SECCAT_BSS:
2410 if (!prefix)
2411 return bss_section;
2412 base_sec_name = ".bss";
2413 break;
2414 case SECCAT_RODATA:
2415 if (!prefix)
2416 return readonly_data_section;
2417 base_sec_name = ".rodata";
2418 break;
2420 /* Enable merging of constant data by the GNU linker using
2421 default_elf_select_section and therefore enabling creation of
2422 sections with the SHF_MERGE flag. */
2423 case SECCAT_RODATA_MERGE_STR:
2424 case SECCAT_RODATA_MERGE_STR_INIT:
2425 case SECCAT_RODATA_MERGE_CONST:
2426 return default_elf_select_section (decl, reloc, align);
2428 /* The sections listed below are not supported for MSP430.
2429 They should not be generated, but in case they are, we use
2430 default_select_section so they get placed in sections
2431 the msp430 assembler and linker understand. */
2432 /* "small data" sections are not supported. */
2433 case SECCAT_SRODATA:
2434 case SECCAT_SDATA:
2435 case SECCAT_SBSS:
2436 /* Thread-local storage (TLS) is not supported. */
2437 case SECCAT_TDATA:
2438 case SECCAT_TBSS:
2439 /* Sections used by a dynamic linker are not supported. */
2440 case SECCAT_DATA_REL:
2441 case SECCAT_DATA_REL_LOCAL:
2442 case SECCAT_DATA_REL_RO:
2443 case SECCAT_DATA_REL_RO_LOCAL:
2444 return default_select_section (decl, reloc, align);
2446 default:
2447 gcc_unreachable ();
2450 sec_name = ACONCAT ((prefix, base_sec_name, DECL_SECTION_NAME (decl), NULL));
2452 return get_named_section (decl, sec_name, 0);
2455 #undef TARGET_ASM_FUNCTION_SECTION
2456 #define TARGET_ASM_FUNCTION_SECTION msp430_function_section
2458 static section *
2459 msp430_function_section (tree decl, enum node_frequency freq, bool startup,
2460 bool exit)
2462 const char * name;
2464 gcc_assert (DECL_SECTION_NAME (decl) != NULL);
2465 name = DECL_SECTION_NAME (decl);
2467 const char * prefix = gen_prefix (decl);
2468 if (prefix == NULL
2469 || startswith (name, prefix))
2470 return default_function_section (decl, freq, startup, exit);
2472 name = ACONCAT ((prefix, name, NULL));
2473 return get_named_section (decl, name, 0);
2476 #undef TARGET_SECTION_TYPE_FLAGS
2477 #define TARGET_SECTION_TYPE_FLAGS msp430_section_type_flags
2479 unsigned int
2480 msp430_section_type_flags (tree decl, const char * name, int reloc)
2482 if (startswith (name, lower_prefix))
2483 name += strlen (lower_prefix);
2484 else if (startswith (name, upper_prefix))
2485 name += strlen (upper_prefix);
2486 else if (startswith (name, either_prefix))
2487 name += strlen (either_prefix);
2489 return default_section_type_flags (decl, name, reloc);
2492 #undef TARGET_ASM_UNIQUE_SECTION
2493 #define TARGET_ASM_UNIQUE_SECTION msp430_unique_section
2495 static void
2496 msp430_unique_section (tree decl, int reloc)
2498 gcc_assert (decl != NULL_TREE);
2500 /* In large mode we must make sure that interrupt handlers are put into
2501 low memory as the vector table only accepts 16-bit addresses. */
2502 if (TARGET_LARGE && TREE_CODE (decl) == FUNCTION_DECL
2503 && is_interrupt_func (decl))
2505 set_decl_section_name (decl, ".lowtext");
2506 return;
2509 default_unique_section (decl, reloc);
2511 const char * prefix;
2513 if ( TREE_CODE (decl) == STRING_CST
2514 || TREE_CODE (decl) == CONSTRUCTOR
2515 || TREE_CODE (decl) == INTEGER_CST
2516 || TREE_CODE (decl) == VECTOR_CST
2517 || TREE_CODE (decl) == COMPLEX_CST
2518 || (prefix = gen_prefix (decl)) == NULL)
2519 return;
2521 const char * dec_name = DECL_SECTION_NAME (decl);
2522 char * name = ACONCAT ((prefix, dec_name, NULL));
2524 set_decl_section_name (decl, name);
2527 /* Emit a declaration of a common symbol.
2528 If a data region is in use then put the symbol into the
2529 equivalent .bss section instead.
2530 If LOCAL is 1, then DECL is for a local common variable. */
2531 void
2532 msp430_output_aligned_decl_common (FILE * stream,
2533 const tree decl,
2534 const char * name,
2535 unsigned HOST_WIDE_INT size,
2536 unsigned int align,
2537 int local)
2539 /* Only emit a common symbol if the variable does not have a specific section
2540 assigned. */
2541 if ((msp430_data_region == MSP430_REGION_ANY
2542 || ((msp430_data_region == MSP430_REGION_LOWER)
2543 && !TARGET_USE_LOWER_REGION_PREFIX))
2544 && !(decl != NULL_TREE && DECL_SECTION_NAME (decl))
2545 && !has_attr (ATTR_EITHER, decl)
2546 && !has_attr (ATTR_LOWER, decl)
2547 && !has_attr (ATTR_UPPER, decl)
2548 && !has_attr (ATTR_PERSIST, decl)
2549 && !has_attr (ATTR_NOINIT, decl))
2551 if (local)
2553 fprintf (stream, LOCAL_ASM_OP);
2554 assemble_name (stream, name);
2555 fprintf (stream, "\n");
2557 fprintf (stream, COMMON_ASM_OP);
2558 assemble_name (stream, name);
2559 fprintf (stream, "," HOST_WIDE_INT_PRINT_UNSIGNED",%u\n",
2560 size, align / BITS_PER_UNIT);
2562 else
2564 section * sec;
2566 if (decl)
2567 sec = msp430_select_section (decl, 0, align);
2568 else
2569 switch (msp430_data_region)
2571 case MSP430_REGION_UPPER:
2572 sec = get_named_section (NULL, ".upper.bss", 0);
2573 break;
2574 case MSP430_REGION_LOWER:
2575 sec = get_named_section (NULL, ".lower.bss", 0);
2576 break;
2577 case MSP430_REGION_EITHER:
2578 sec = get_named_section (NULL, ".either.bss", 0);
2579 break;
2580 default:
2581 gcc_unreachable ();
2583 gcc_assert (sec != NULL);
2585 switch_to_section (sec);
2586 ASM_OUTPUT_ALIGN (stream, floor_log2 (align / BITS_PER_UNIT));
2587 if (!local)
2589 targetm.asm_out.globalize_label (stream, name);
2590 ASM_WEAKEN_LABEL (stream, name);
2592 ASM_OUTPUT_LABEL (stream, name);
2593 ASM_OUTPUT_SKIP (stream, size ? size : 1);
2597 #undef TARGET_ASM_FILE_END
2598 #define TARGET_ASM_FILE_END msp430_file_end
2600 /* Emit MSPABI and GNU object attributes.
2601 Tags and values for MSPABI attributes are:
2602 OFBA_MSPABI_Tag_ISA 4
2603 MSP430 1
2604 MSP430X 2
2605 OFBA_MSPABI_Tag_Code_Model 6
2606 Small 1
2607 Large 2
2608 OFBA_MSPABI_Tag_Data_Model 8
2609 Small 1
2610 Large 2
2611 Restricted 3 (Unused by GNU)
2612 OFBA_MSPABI_Tag_enum_size 10 (Unused by GNU)
2613 Note that Code_Model and Data_Model are always equal for GNU.
2614 We define a new .gnu_attribute to keep track of the data region used.
2615 Tag_GNU_MSP430_Data_Region 4
2616 LOWER 1
2617 ANY 2
2618 See binutils-gdb/include/elf/msp430.h for the full details. */
2619 static void
2620 msp430_file_end (void)
2622 #ifdef HAVE_AS_MSPABI_ATTRIBUTE
2623 /* Enum for tag names. */
2624 enum
2626 OFBA_MSPABI_Tag_ISA = 4,
2627 OFBA_MSPABI_Tag_Code_Model = 6,
2628 OFBA_MSPABI_Tag_Data_Model = 8,
2629 Tag_GNU_MSP430_Data_Region = 4
2631 /* Enum for tag values. */
2632 enum
2634 OFBA_MSPABI_Val_ISA_MSP430 = 1,
2635 OFBA_MSPABI_Val_ISA_MSP430X = 2,
2636 OFBA_MSPABI_Val_Model_Small = 1,
2637 OFBA_MSPABI_Val_Model_Large = 2,
2638 Tag_GNU_MSP430_Data_Region_Lower = 1,
2639 Tag_GNU_MSP430_Data_Region_Any = 2
2641 /* .mspabi_attribute is a GNU assembler directive only. The assembler will
2642 construct a .MSP430.attributes section based on the options it is invoked
2643 with. The values it reads from these directives are used for validating
2644 those options. */
2645 const char *msp430_attr = ".mspabi_attribute";
2646 const char *gnu_attr = ".gnu_attribute";
2648 /* Emit .mspabi_attribute directive for OFBA_MSPABI_Tag_ISA. */
2649 fprintf (asm_out_file, "\t%s %d, %d\n", msp430_attr, OFBA_MSPABI_Tag_ISA,
2650 msp430x ? OFBA_MSPABI_Val_ISA_MSP430X : OFBA_MSPABI_Val_ISA_MSP430);
2651 /* Emit .mspabi_attribute directive for OFBA_MSPABI_Tag_Code_Model. */
2652 fprintf (asm_out_file, "\t%s %d, %d\n", msp430_attr,
2653 OFBA_MSPABI_Tag_Code_Model,
2654 TARGET_LARGE ? OFBA_MSPABI_Val_Model_Large
2655 : OFBA_MSPABI_Val_Model_Small);
2656 /* Emit .mspabi_attribute directive for OFBA_MSPABI_Tag_Data_Model. */
2657 fprintf (asm_out_file, "\t%s %d, %d\n", msp430_attr,
2658 OFBA_MSPABI_Tag_Data_Model,
2659 TARGET_LARGE ? OFBA_MSPABI_Val_Model_Large
2660 : OFBA_MSPABI_Val_Model_Small);
2661 #ifdef HAVE_AS_GNU_ATTRIBUTE
2662 /* Emit .gnu_attribute directive for Tag_GNU_MSP430_Data_Region. */
2663 fprintf (asm_out_file, "\t%s %d, %d\n", gnu_attr, Tag_GNU_MSP430_Data_Region,
2664 msp430_data_region == MSP430_REGION_LOWER
2665 ? Tag_GNU_MSP430_Data_Region_Lower
2666 : Tag_GNU_MSP430_Data_Region_Any);
2667 #endif
2668 #endif
2671 enum msp430_builtin
2673 MSP430_BUILTIN_BIC_SR,
2674 MSP430_BUILTIN_BIS_SR,
2675 MSP430_BUILTIN_DELAY_CYCLES,
2676 MSP430_BUILTIN_max
2679 static GTY(()) tree msp430_builtins[(int) MSP430_BUILTIN_max];
2681 static void
2682 msp430_init_builtins (void)
2684 tree void_ftype_int = build_function_type_list (void_type_node,
2685 integer_type_node, NULL);
2686 tree void_ftype_longlong
2687 = build_function_type_list (void_type_node, long_long_integer_type_node,
2688 NULL);
2690 msp430_builtins[MSP430_BUILTIN_BIC_SR] =
2691 add_builtin_function ( "__bic_SR_register_on_exit", void_ftype_int,
2692 MSP430_BUILTIN_BIC_SR, BUILT_IN_MD, NULL, NULL_TREE);
2694 msp430_builtins[MSP430_BUILTIN_BIS_SR] =
2695 add_builtin_function ( "__bis_SR_register_on_exit", void_ftype_int,
2696 MSP430_BUILTIN_BIS_SR, BUILT_IN_MD, NULL, NULL_TREE);
2698 msp430_builtins[MSP430_BUILTIN_DELAY_CYCLES] =
2699 add_builtin_function ( "__delay_cycles", void_ftype_longlong,
2700 MSP430_BUILTIN_DELAY_CYCLES, BUILT_IN_MD, NULL,
2701 NULL_TREE);
2704 static tree
2705 msp430_builtin_decl (unsigned code, bool initialize ATTRIBUTE_UNUSED)
2707 switch (code)
2709 case MSP430_BUILTIN_BIC_SR:
2710 case MSP430_BUILTIN_BIS_SR:
2711 case MSP430_BUILTIN_DELAY_CYCLES:
2712 return msp430_builtins[code];
2713 default:
2714 return error_mark_node;
2718 /* These constants are really register reads, which are faster than
2719 regular constants. */
2720 static int
2721 cg_magic_constant (HOST_WIDE_INT c)
2723 switch (c)
2725 case 0xffff:
2726 case -1:
2727 case 0:
2728 case 1:
2729 case 2:
2730 case 4:
2731 case 8:
2732 return 1;
2733 default:
2734 return 0;
2738 static rtx
2739 msp430_expand_delay_cycles (rtx arg)
2741 HOST_WIDE_INT i, c, n;
2742 /* extra cycles for MSP430X instructions */
2743 #define CYCX(M,X) (msp430x ? (X) : (M))
2745 if (GET_CODE (arg) != CONST_INT)
2747 error ("%<__delay_cycles%> only takes constant arguments");
2748 return NULL_RTX;
2751 c = INTVAL (arg);
2753 if (HOST_BITS_PER_WIDE_INT > 32)
2755 if (c < 0)
2757 error ("%<__delay_cycles%> only takes non-negative cycle counts");
2758 return NULL_RTX;
2762 emit_insn (gen_delay_cycles_start (arg));
2764 /* For 32-bit loops, there's 13(16) + 5(min(x,0x10000) + 6x cycles. */
2765 if (c > 3 * 0xffff + CYCX (7, 10))
2767 n = c;
2768 /* There's 4 cycles in the short (i>0xffff) loop and 7 in the long
2769 (x<=0xffff) loop. */
2770 if (c >= 0x10000 * 7 + CYCX (14, 16))
2772 i = 0x10000;
2773 c -= CYCX (14, 16) + 7 * 0x10000;
2774 i += c / 4;
2775 c %= 4;
2776 if ((unsigned long long) i > 0xffffffffULL)
2778 error ("%<__delay_cycles%> is limited to 32-bit loop counts");
2779 return NULL_RTX;
2782 else
2784 i = (c - CYCX (14, 16)) / 7;
2785 c -= CYCX (14, 16) + i * 7;
2788 if (cg_magic_constant (i & 0xffff))
2789 c ++;
2790 if (cg_magic_constant ((i >> 16) & 0xffff))
2791 c ++;
2793 if (msp430x)
2794 emit_insn (gen_delay_cycles_32x (GEN_INT (i), GEN_INT (n - c)));
2795 else
2796 emit_insn (gen_delay_cycles_32 (GEN_INT (i), GEN_INT (n - c)));
2799 /* For 16-bit loops, there's 7(10) + 3x cycles - so the max cycles is
2800 0x30004(7). */
2801 if (c > 12)
2803 n = c;
2804 i = (c - CYCX (7, 10)) / 3;
2805 c -= CYCX (7, 10) + i * 3;
2807 if (cg_magic_constant (i))
2808 c ++;
2810 if (msp430x)
2811 emit_insn (gen_delay_cycles_16x (GEN_INT (i), GEN_INT (n - c)));
2812 else
2813 emit_insn (gen_delay_cycles_16 (GEN_INT (i), GEN_INT (n - c)));
2816 while (c > 1)
2818 emit_insn (gen_delay_cycles_2 ());
2819 c -= 2;
2822 if (c)
2824 emit_insn (gen_delay_cycles_1 ());
2825 c -= 1;
2828 emit_insn (gen_delay_cycles_end (arg));
2830 return NULL_RTX;
2833 static rtx
2834 msp430_expand_builtin (tree exp,
2835 rtx target ATTRIBUTE_UNUSED,
2836 rtx subtarget ATTRIBUTE_UNUSED,
2837 machine_mode mode ATTRIBUTE_UNUSED,
2838 int ignore ATTRIBUTE_UNUSED)
2840 tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
2841 unsigned int fcode = DECL_MD_FUNCTION_CODE (fndecl);
2842 rtx arg1 = expand_normal (CALL_EXPR_ARG (exp, 0));
2844 if (fcode == MSP430_BUILTIN_DELAY_CYCLES)
2845 return msp430_expand_delay_cycles (arg1);
2847 if (! msp430_is_interrupt_func ())
2849 error ("MSP430 built-in functions only work inside interrupt handlers");
2850 return NULL_RTX;
2853 if (! REG_P (arg1) && ! CONSTANT_P (arg1))
2854 arg1 = force_reg (mode, arg1);
2856 switch (fcode)
2858 case MSP430_BUILTIN_BIC_SR: emit_insn (gen_bic_SR (arg1)); break;
2859 case MSP430_BUILTIN_BIS_SR: emit_insn (gen_bis_SR (arg1)); break;
2860 default:
2861 internal_error ("bad builtin code");
2862 break;
2864 return NULL_RTX;
2867 #undef TARGET_INIT_BUILTINS
2868 #define TARGET_INIT_BUILTINS msp430_init_builtins
2870 #undef TARGET_EXPAND_BUILTIN
2871 #define TARGET_EXPAND_BUILTIN msp430_expand_builtin
2873 #undef TARGET_BUILTIN_DECL
2874 #define TARGET_BUILTIN_DECL msp430_builtin_decl
2876 void
2877 msp430_expand_prologue (void)
2879 int i, j;
2880 int fs;
2881 /* Always use stack_pointer_rtx instead of calling
2882 rtx_gen_REG ourselves. Code elsewhere in GCC assumes
2883 that there is a single rtx representing the stack pointer,
2884 namely stack_pointer_rtx, and uses == to recognize it. */
2885 rtx sp = stack_pointer_rtx;
2886 rtx p;
2888 if (is_naked_func ())
2890 /* We must generate some RTX as thread_prologue_and_epilogue_insns()
2891 examines the output of the gen_prologue() function. */
2892 emit_insn (gen_rtx_CLOBBER (VOIDmode, GEN_INT (0)));
2893 return;
2896 emit_insn (gen_prologue_start_marker ());
2898 if (is_critical_func ())
2900 emit_insn (gen_push_intr_state ());
2901 emit_insn (gen_disable_interrupts ());
2903 else if (is_reentrant_func ())
2904 emit_insn (gen_disable_interrupts ());
2906 if (!cfun->machine->computed)
2907 msp430_compute_frame_info ();
2909 if (flag_stack_usage_info)
2910 current_function_static_stack_size = cfun->machine->framesize;
2912 if (crtl->args.pretend_args_size)
2914 rtx note;
2916 gcc_assert (crtl->args.pretend_args_size == 2);
2918 p = emit_insn (gen_grow_and_swap ());
2920 /* Document the stack decrement... */
2921 note = F (gen_rtx_SET (stack_pointer_rtx,
2922 gen_rtx_MINUS (Pmode,
2923 stack_pointer_rtx, GEN_INT (2))));
2924 add_reg_note (p, REG_FRAME_RELATED_EXPR, note);
2926 /* ...and the establishment of a new location for the return address. */
2927 note = F (gen_rtx_SET (gen_rtx_MEM (Pmode,
2928 gen_rtx_PLUS (Pmode,
2929 stack_pointer_rtx,
2930 GEN_INT (-2))),
2931 pc_rtx));
2932 add_reg_note (p, REG_CFA_OFFSET, note);
2933 F (p);
2936 for (i = 15; i >= 4; i--)
2937 if (cfun->machine->need_to_save[i])
2939 /* We need to save COUNT sequential registers starting from regnum
2940 I. */
2941 int seq, count;
2942 rtx note;
2944 for (seq = i - 1; seq >= 4 && cfun->machine->need_to_save[seq]; seq --)
2946 count = i - seq;
2948 if (msp430x)
2950 /* Note: with TARGET_LARGE we still use PUSHM as PUSHX.A is two
2951 bytes bigger. */
2952 p = F (emit_insn (gen_pushm (gen_rtx_REG (Pmode, i),
2953 GEN_INT (count))));
2955 /* Document the stack decrement as a result of PUSHM. */
2956 note = gen_rtx_SEQUENCE (VOIDmode, rtvec_alloc (count + 1));
2958 XVECEXP (note, 0, 0)
2959 = F (gen_rtx_SET (stack_pointer_rtx,
2960 gen_rtx_PLUS (Pmode,
2961 stack_pointer_rtx,
2962 GEN_INT (count * (TARGET_LARGE
2963 ? -4 : -2)))));
2965 /* *sp-- = R[i-j] */
2966 /* sp+N R10
2968 sp R4 */
2969 for (j = 0; j < count; j ++)
2971 rtx addr;
2972 int ofs = (count - j - 1) * (TARGET_LARGE ? 4 : 2);
2974 if (ofs)
2975 addr = gen_rtx_PLUS (Pmode, sp, GEN_INT (ofs));
2976 else
2977 addr = stack_pointer_rtx;
2979 XVECEXP (note, 0, j + 1) =
2980 F (gen_rtx_SET (gen_rtx_MEM (Pmode, addr),
2981 gen_rtx_REG (Pmode, i - j)));
2984 add_reg_note (p, REG_FRAME_RELATED_EXPR, note);
2985 i -= count - 1;
2987 else
2988 F (emit_insn (gen_push (gen_rtx_REG (Pmode, i))));
2991 if (frame_pointer_needed)
2992 F (emit_move_insn (gen_rtx_REG (Pmode, FRAME_POINTER_REGNUM), sp));
2994 fs = cfun->machine->framesize_locals + cfun->machine->framesize_outgoing;
2996 increment_stack (- fs);
2998 emit_insn (gen_prologue_end_marker ());
3001 void
3002 msp430_expand_epilogue (int is_eh)
3004 int i, j;
3005 int fs;
3006 rtx sp = stack_pointer_rtx;
3007 rtx p;
3008 int helper_n = 0;
3010 if (is_naked_func ())
3012 /* We must generate some RTX as thread_prologue_and_epilogue_insns()
3013 examines the output of the gen_epilogue() function. */
3014 emit_insn (gen_rtx_CLOBBER (VOIDmode, GEN_INT (0)));
3015 return;
3018 if (cfun->machine->need_to_save[10])
3020 /* Check for a helper function. */
3021 helper_n = 7; /* For when the loop below never sees a match. */
3022 for (i = 9; i >= 4; i--)
3023 if (!cfun->machine->need_to_save[i])
3025 helper_n = 10 - i;
3026 for (; i >= 4; i--)
3027 if (cfun->machine->need_to_save[i])
3029 helper_n = 0;
3030 break;
3032 break;
3036 emit_insn (gen_epilogue_start_marker ());
3038 if (cfun->decl && strcmp (IDENTIFIER_POINTER (DECL_NAME (cfun->decl)),
3039 "main") == 0)
3040 emit_insn (gen_msp430_refsym_need_exit ());
3042 if (is_wakeup_func ())
3043 /* Clear the SCG1, SCG0, OSCOFF and CPUOFF bits in the saved copy of the
3044 status register current residing on the stack. When this function
3045 executes its RETI instruction the SR will be updated with this saved
3046 value, thus ensuring that the processor is woken up from any low power
3047 state in which it may be residing. */
3048 emit_insn (gen_bic_SR (GEN_INT (0xf0)));
3050 fs = cfun->machine->framesize_locals + cfun->machine->framesize_outgoing;
3052 increment_stack (fs);
3054 if (is_eh)
3056 /* We need to add the right "SP" register save just after the
3057 regular ones, so that when we pop it off we're in the EH
3058 return frame, not this one. This overwrites our own return
3059 address, but we're not going to be returning anyway. */
3060 rtx r12 = gen_rtx_REG (Pmode, 12);
3061 rtx (*addPmode)(rtx, rtx, rtx) = TARGET_LARGE ? gen_addpsi3 : gen_addhi3;
3063 /* R12 will hold the new SP. */
3064 i = cfun->machine->framesize_regs;
3065 emit_move_insn (r12, stack_pointer_rtx);
3066 emit_insn (addPmode (r12, r12, EH_RETURN_STACKADJ_RTX));
3067 emit_insn (addPmode (r12, r12, GEN_INT (i)));
3068 emit_move_insn (gen_rtx_MEM (Pmode, plus_constant (Pmode,
3069 stack_pointer_rtx,
3070 i)), r12);
3073 for (i = 4; i <= 15; i++)
3074 if (cfun->machine->need_to_save[i])
3076 /* We need to restore COUNT sequential registers starting from regnum
3077 I. */
3078 int seq;
3079 int count = 1;
3080 int helper_used = 0;
3081 rtx note, addr;
3083 if (msp430x)
3085 for (seq = i + 1; seq <= 15 && cfun->machine->need_to_save[seq];
3086 seq++)
3088 count = seq - i;
3091 if (msp430x)
3093 /* Note: With TARGET_LARGE we still use
3094 POPM as POPX.A is two bytes bigger. */
3095 p = F (emit_insn (gen_popm (stack_pointer_rtx, GEN_INT (seq - 1),
3096 GEN_INT (count))));
3098 else if (i == 11 - helper_n
3099 && ! msp430_is_interrupt_func ()
3100 && ! is_reentrant_func ()
3101 && ! is_critical_func ()
3102 && crtl->args.pretend_args_size == 0
3103 /* Calling the helper takes as many bytes as the POP;RET
3104 sequence. */
3105 && helper_n > 1
3106 && !is_eh)
3108 p = F (emit_jump_insn (gen_epilogue_helper (GEN_INT (helper_n))));
3109 count = helper_n;
3110 helper_used = 1;
3112 else
3113 p = F (emit_insn (gen_pop (gen_rtx_REG (Pmode, i))));
3115 /* Document the stack increment as a result of POPM. */
3116 note = gen_rtx_SEQUENCE (VOIDmode, rtvec_alloc (count + 1));
3118 addr = gen_rtx_PLUS (Pmode, stack_pointer_rtx,
3119 GEN_INT (count * (TARGET_LARGE ? 4 : 2)));
3121 XVECEXP (note, 0, 0) = F (gen_rtx_SET (stack_pointer_rtx, addr));
3124 /* *sp++ = R[i+j] */
3125 /* sp R4
3127 sp+N R10. */
3128 for (j = 0; j < count; j++)
3130 int ofs = j * (TARGET_LARGE ? 4 : 2);
3132 if (ofs)
3133 addr = gen_rtx_PLUS (Pmode, sp, GEN_INT (ofs));
3134 else
3135 addr = stack_pointer_rtx;
3137 XVECEXP (note, 0, j + 1)
3138 = F (gen_rtx_SET (gen_rtx_MEM (Pmode, addr),
3139 gen_rtx_REG (Pmode, i + j)));
3141 add_reg_note (p, REG_FRAME_RELATED_EXPR, note);
3142 i += count - 1;
3144 if (helper_used)
3145 return;
3148 if (is_eh)
3150 /* Also pop SP, which puts us into the EH return frame. Except
3151 that you can't "pop" sp, you have to just load it off the
3152 stack. */
3153 emit_move_insn (stack_pointer_rtx, gen_rtx_MEM (Pmode,
3154 stack_pointer_rtx));
3157 if (crtl->args.pretend_args_size)
3158 emit_insn (gen_swap_and_shrink ());
3160 if (is_critical_func ())
3161 emit_insn (gen_pop_intr_state ());
3162 else if (is_reentrant_func ())
3163 emit_insn (gen_enable_interrupts ());
3165 emit_jump_insn (gen_msp430_return ());
3168 /* Implements EH_RETURN_STACKADJ_RTX. Saved and used later in
3169 m32c_emit_eh_epilogue. */
3171 msp430_eh_return_stackadj_rtx (void)
3173 if (!cfun->machine->eh_stack_adjust)
3175 rtx sa;
3177 sa = gen_rtx_REG (Pmode, 15);
3178 cfun->machine->eh_stack_adjust = sa;
3180 return cfun->machine->eh_stack_adjust;
3183 /* This function is called before reload, to "fix" the stack in
3184 preparation for an EH return. */
3185 void
3186 msp430_expand_eh_return (rtx eh_handler)
3188 /* These are all Pmode */
3189 rtx ap, sa, ra, tmp;
3191 ap = arg_pointer_rtx;
3192 sa = msp430_eh_return_stackadj_rtx ();
3193 ra = eh_handler;
3195 tmp = ap;
3196 tmp = gen_rtx_PLUS (Pmode, ap, sa);
3197 tmp = plus_constant (Pmode, tmp, TARGET_LARGE ? -4 : -2);
3198 tmp = gen_rtx_MEM (Pmode, tmp);
3199 emit_move_insn (tmp, ra);
3202 #undef TARGET_INIT_DWARF_REG_SIZES_EXTRA
3203 #define TARGET_INIT_DWARF_REG_SIZES_EXTRA msp430_init_dwarf_reg_sizes_extra
3204 void
3205 msp430_init_dwarf_reg_sizes_extra (tree address)
3207 int i;
3208 rtx addr = expand_normal (address);
3209 rtx mem = gen_rtx_MEM (BLKmode, addr);
3211 /* This needs to match msp430_unwind_word_mode (above). */
3212 if (!msp430x)
3213 return;
3215 for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
3217 unsigned int dnum = DWARF_FRAME_REGNUM (i);
3218 unsigned int rnum = DWARF2_FRAME_REG_OUT (dnum, 1);
3220 if (rnum < DWARF_FRAME_REGISTERS)
3222 HOST_WIDE_INT offset = rnum * GET_MODE_SIZE (QImode);
3224 emit_move_insn (adjust_address (mem, QImode, offset),
3225 gen_int_mode (4, QImode));
3230 /* The MSP430 ABI defines a number of helper functions that should be
3231 used for, for example, 32-bit shifts. This function is called to
3232 emit such a function, using the table above to optimize some
3233 cases. */
3234 void
3235 msp430_expand_helper (rtx *operands, const char *helper_name,
3236 bool const_variants)
3238 rtx c, fusage, fsym;
3239 char *helper_const = NULL;
3240 int arg1 = 12;
3241 int arg2 = 13;
3242 int arg1sz = 1;
3243 machine_mode arg0mode = GET_MODE (operands[0]);
3244 machine_mode arg1mode = GET_MODE (operands[1]);
3245 machine_mode arg2mode = GET_MODE (operands[2]);
3246 int expand_mpy = startswith (helper_name, "__mspabi_mpy");
3247 /* This function has been used incorrectly if CONST_VARIANTS is TRUE for a
3248 hwmpy function. */
3249 gcc_assert (!(expand_mpy && const_variants));
3251 if (arg1mode != VOIDmode && arg2mode != VOIDmode)
3252 /* Modes of arguments must be equal if not constants. */
3253 gcc_assert (arg1mode == arg2mode);
3255 if (arg1mode == VOIDmode)
3256 arg1mode = arg0mode;
3257 if (arg2mode == VOIDmode)
3258 arg2mode = arg0mode;
3260 if (arg1mode == SImode)
3262 arg2 = 14;
3263 arg1sz = 2;
3265 else if (arg1mode == DImode)
3267 arg1 = 8;
3268 arg1sz = 4;
3269 arg2 = 12;
3272 /* Use the "const_variant" of a shift library function if requested.
3273 These are faster, but have larger code size. */
3274 if (const_variants
3275 && CONST_INT_P (operands[2])
3276 && INTVAL (operands[2]) >= 1
3277 && INTVAL (operands[2]) <= 15)
3279 /* Note that the INTVAL is limited in value and length by the conditional
3280 above. */
3281 int len = strlen (helper_name) + 4;
3282 helper_const = (char *) xmalloc (len);
3283 snprintf (helper_const, len, "%s_%d", helper_name,
3284 (int) INTVAL (operands[2]));
3287 /* Setup the arguments to the helper function. */
3288 emit_move_insn (gen_rtx_REG (arg1mode, arg1),
3289 operands[1]);
3290 if (!helper_const)
3291 emit_move_insn (gen_rtx_REG (arg2mode, arg2),
3292 operands[2]);
3294 if (expand_mpy)
3296 if (msp430_use_f5_series_hwmult ())
3297 fsym = gen_rtx_SYMBOL_REF (VOIDmode, concat (helper_name,
3298 "_f5hw", NULL));
3299 else if (msp430_use_32bit_hwmult ())
3301 /* When the arguments are 16-bits, the 16-bit hardware multiplier is
3302 used. */
3303 if (arg1mode == HImode)
3304 fsym = gen_rtx_SYMBOL_REF (VOIDmode, concat (helper_name,
3305 "_hw", NULL));
3306 else
3307 fsym = gen_rtx_SYMBOL_REF (VOIDmode, concat (helper_name,
3308 "_hw32", NULL));
3310 else if (msp430_use_16bit_hwmult ())
3311 fsym = gen_rtx_SYMBOL_REF (VOIDmode, concat (helper_name,
3312 "_hw", NULL));
3313 else
3314 fsym = gen_rtx_SYMBOL_REF (VOIDmode, helper_name);
3316 else
3317 fsym = gen_rtx_SYMBOL_REF (VOIDmode,
3318 helper_const ? helper_const : helper_name);
3320 c = gen_call_value_internal (gen_rtx_REG (arg0mode, 12), fsym, GEN_INT (0));
3322 c = emit_call_insn (c);
3323 RTL_CONST_CALL_P (c) = 1;
3325 /* Add register usage information for the arguments to the call. */
3326 fusage = NULL;
3327 use_regs (&fusage, arg1, arg1sz);
3328 if (!helper_const)
3330 /* If we are expanding a shift, we only need to use the low register
3331 for the shift amount. */
3332 if (!expand_mpy)
3333 use_regs (&fusage, arg2, 1);
3334 else
3335 use_regs (&fusage, arg2, arg1sz);
3337 add_function_usage_to (c, fusage);
3339 emit_move_insn (operands[0],
3340 /* Return value will always start in R12. */
3341 gen_rtx_REG (arg0mode, 12));
3344 /* Return TRUE if the helper function should be used and FALSE if the shifts
3345 insns should be emitted inline. */
3346 static bool
3347 use_helper_for_const_shift (machine_mode mode, HOST_WIDE_INT amt)
3349 const int default_inline_shift = 4;
3350 /* We initialize the option to 65 so we know if the user set it or not. */
3351 int user_set_max_inline = (msp430_max_inline_shift == 65 ? 0 : 1);
3352 int max_inline = (user_set_max_inline ? msp430_max_inline_shift
3353 : default_inline_shift);
3354 /* 32-bit shifts are roughly twice as costly as 16-bit shifts so we adjust
3355 the heuristic accordingly. */
3356 int max_inline_32 = max_inline / 2;
3358 if (mode == E_DImode)
3359 return true;
3361 /* Don't use helpers for these modes on 430X, when optimizing for speed, or
3362 when emitting a small number of insns. */
3363 if ((mode == E_QImode || mode == E_HImode || mode == E_PSImode)
3364 && (msp430x
3365 /* If the user set max_inline then we always obey that number.
3366 Otherwise we always emit the shifts inline at -O2 and above. */
3367 || amt <= max_inline
3368 || (!user_set_max_inline
3369 && (optimize >= 2 && !optimize_size))))
3370 return false;
3372 /* 430 and 430X codegen for SImode shifts is the same.
3373 Set a hard limit of 15 for the number of shifts that will be emitted
3374 inline by default, even at -O2 and above, to prevent code size
3375 explosion. */
3376 if (mode == E_SImode
3377 && (amt <= max_inline_32
3378 || (!user_set_max_inline
3379 && (optimize >= 2 && !optimize_size)
3380 && amt <= 15)))
3381 return false;
3383 return true;
3386 /* For shift operations which will use an mspabi helper function, setup the
3387 call to msp430_expand helper. Return 1 to indicate we have finished with
3388 this insn and invoke "DONE".
3389 Otherwise return 0 to indicate the insn should fallthrough.
3390 Never FAIL. */
3392 msp430_expand_shift (enum rtx_code code, machine_mode mode, rtx *operands)
3394 /* Always use the helper function when the shift amount is not a
3395 constant. */
3396 if (!CONST_INT_P (operands[2])
3397 || mode == E_DImode
3398 || use_helper_for_const_shift (mode, INTVAL (operands[2])))
3400 const char *helper_name = NULL;
3401 /* The const variants of mspabi shifts have significantly larger code
3402 size than the generic version, so use the generic version if
3403 optimizing for size. */
3404 bool const_variant = !optimize_size;
3405 switch (mode)
3407 case E_HImode:
3408 helper_name = (code == ASHIFT ? "__mspabi_slli" :
3409 (code == ASHIFTRT ? "__mspabi_srai" :
3410 (code == LSHIFTRT ? "__mspabi_srli" :
3411 NULL)));
3412 break;
3413 case E_PSImode:
3414 helper_name = (code == ASHIFT ? "__gnu_mspabi_sllp" :
3415 (code == ASHIFTRT ? "__gnu_mspabi_srap" :
3416 (code == LSHIFTRT ? "__gnu_mspabi_srlp" :
3417 NULL)));
3418 /* No const variant for PSImode shifts FIXME. */
3419 const_variant = false;
3420 break;
3421 case E_SImode:
3422 helper_name = (code == ASHIFT ? "__mspabi_slll" :
3423 (code == ASHIFTRT ? "__mspabi_sral" :
3424 (code == LSHIFTRT ? "__mspabi_srll" :
3425 NULL)));
3426 break;
3427 case E_DImode:
3428 helper_name = (code == ASHIFT ? "__mspabi_sllll" :
3429 (code == ASHIFTRT ? "__mspabi_srall" :
3430 (code == LSHIFTRT ? "__mspabi_srlll" :
3431 NULL)));
3432 /* No const variant for DImode shifts. */
3433 const_variant = false;
3434 break;
3435 default:
3436 gcc_unreachable ();
3437 break;
3439 gcc_assert (helper_name);
3440 msp430_expand_helper (operands, helper_name, const_variant);
3441 return 1;
3443 /* When returning 0, there must be an insn to match the RTL pattern
3444 otherwise there will be an unrecognizeable insn. */
3445 return 0;
3448 /* Helper function to emit a sequence of shift instructions. The amount of
3449 shift instructions to emit is in OPERANDS[2].
3450 For 430 we output copies of identical inline shifts for all modes.
3451 For 430X it is inneficient to do so for any modes except SI and DI, since we
3452 can make use of R*M insns or RPT with 430X insns, so this function is only
3453 used for SImode in that case. */
3455 msp430_output_asm_shift_insns (enum rtx_code code, machine_mode mode,
3456 rtx *operands, bool return_length)
3458 int i;
3459 int amt;
3460 int max_shift = GET_MODE_BITSIZE (mode) - 1;
3461 int length = 0;
3463 gcc_assert (CONST_INT_P (operands[2]));
3464 amt = INTVAL (operands[2]);
3466 if (amt == 0 || amt > max_shift)
3468 if (return_length)
3469 return 0;
3470 switch (code)
3472 case ASHIFT:
3473 output_asm_insn ("# ignored undefined behaviour left shift "
3474 "of %1 by %2", operands);
3475 break;
3476 case ASHIFTRT:
3477 output_asm_insn ("# ignored undefined behaviour arithmetic right "
3478 "shift of %1 by %2", operands);
3479 break;
3480 case LSHIFTRT:
3481 output_asm_insn ("# ignored undefined behaviour logical right shift "
3482 "of %1 by %2", operands);
3483 break;
3484 default:
3485 gcc_unreachable ();
3487 return 0;
3490 if (code == ASHIFT)
3492 if (!msp430x && mode == HImode)
3494 if (return_length)
3495 length = 2 + (MEM_P (operands[0]) ? 2 : 0);
3496 else
3497 for (i = 0; i < amt; i++)
3498 output_asm_insn ("RLA.W\t%0", operands);
3500 else if (mode == SImode)
3502 if (return_length)
3503 length = 4 + (MEM_P (operands[0]) ? 4 : 0)
3504 + (4 * msp430x_insn_required (operands[0]));
3505 else
3506 for (i = 0; i < amt; i++)
3507 output_asm_insn ("RLA%X0.W\t%L0 { RLC%X0.W\t%H0", operands);
3509 else
3510 /* Catch unhandled cases. */
3511 gcc_unreachable ();
3513 else if (code == ASHIFTRT)
3515 if (!msp430x && mode == HImode)
3517 if (return_length)
3518 length = 2 + (MEM_P (operands[0]) ? 2 : 0);
3519 else
3520 for (i = 0; i < amt; i++)
3521 output_asm_insn ("RRA.W\t%0", operands);
3523 else if (mode == SImode)
3525 if (return_length)
3526 length = 4 + (MEM_P (operands[0]) ? 4 : 0)
3527 + (4 * msp430x_insn_required (operands[0]));
3528 else
3529 for (i = 0; i < amt; i++)
3530 output_asm_insn ("RRA%X0.W\t%H0 { RRC%X0.W\t%L0", operands);
3532 else
3533 gcc_unreachable ();
3535 else if (code == LSHIFTRT)
3537 if (!msp430x && mode == HImode)
3539 if (return_length)
3540 length = 4 + (MEM_P (operands[0]) ? 2 : 0);
3541 else
3542 for (i = 0; i < amt; i++)
3543 output_asm_insn ("CLRC { RRC.W\t%0", operands);
3545 else if (mode == SImode)
3547 if (return_length)
3548 length = 6 + (MEM_P (operands[0]) ? 4 : 0)
3549 + (4 * msp430x_insn_required (operands[0]));
3550 else
3551 for (i = 0; i < amt; i++)
3552 output_asm_insn ("CLRC { RRC%X0.W\t%H0 { RRC%X0.W\t%L0",
3553 operands);
3555 /* FIXME: Why doesn't "RRUX.W\t%H0 { RRC%X0.W\t%L0" work for msp430x?
3556 It causes execution timeouts e.g. pr41963.c. */
3557 #if 0
3558 else if (msp430x && mode == SImode)
3560 if (return_length)
3561 length = 2;
3562 else
3563 for (i = 0; i < amt; i++)
3564 output_asm_insn ("RRUX.W\t%H0 { RRC%X0.W\t%L0", operands);
3566 #endif
3567 else
3568 gcc_unreachable ();
3570 return length * amt;
3573 /* Called by cbranch<mode>4 to coerce operands into usable forms. */
3574 void
3575 msp430_fixup_compare_operands (machine_mode my_mode, rtx * operands)
3577 /* constants we're looking for, not constants which are allowed. */
3578 int const_op_idx = 1;
3580 if (msp430_reversible_cmp_operator (operands[0], VOIDmode))
3581 const_op_idx = 2;
3583 if (GET_CODE (operands[const_op_idx]) != REG
3584 && GET_CODE (operands[const_op_idx]) != MEM)
3585 operands[const_op_idx] = copy_to_mode_reg (my_mode, operands[const_op_idx]);
3588 /* Simplify_gen_subreg() doesn't handle memory references the way we
3589 need it to below, so we use this function for when we must get a
3590 valid subreg in a "natural" state. */
3592 msp430_subreg (machine_mode mode, rtx r, machine_mode omode, int byte)
3594 rtx rv;
3595 gcc_assert (mode == HImode);
3597 if (GET_CODE (r) == SUBREG
3598 && SUBREG_BYTE (r) == 0)
3600 rtx ireg = SUBREG_REG (r);
3601 machine_mode imode = GET_MODE (ireg);
3603 /* special case for (HI (SI (PSI ...), 0)) */
3604 if (imode == PSImode
3605 && mode == HImode
3606 && byte == 0)
3607 rv = gen_rtx_SUBREG (mode, ireg, byte);
3608 else
3609 rv = simplify_gen_subreg (mode, ireg, imode, byte);
3611 else if (GET_CODE (r) == MEM)
3613 /* When byte == 2, we can be certain that we were already called with an
3614 identical rtx with byte == 0. So we don't need to do anything to
3615 get a 2 byte offset of a (mem (post_inc)) rtx, since the address has
3616 already been offset by the post_inc itself. */
3617 if (GET_CODE (XEXP (r, 0)) == POST_INC && byte == 2)
3618 byte = 0;
3619 rv = adjust_address (r, mode, byte);
3621 else if (GET_CODE (r) == SYMBOL_REF
3622 && (byte == 0 || byte == 2)
3623 && mode == HImode)
3625 rv = gen_rtx_ZERO_EXTRACT (HImode, r, GEN_INT (16), GEN_INT (8*byte));
3626 rv = gen_rtx_CONST (HImode, r);
3628 else
3629 rv = simplify_gen_subreg (mode, r, omode, byte);
3631 if (!rv)
3632 gcc_unreachable ();
3634 return rv;
3638 msp430_split_addsi (rtx *operands)
3640 operands[3] = msp430_subreg (HImode, operands[0], SImode, 0);
3641 operands[4] = msp430_subreg (HImode, operands[1], SImode, 0);
3642 operands[5] = msp430_subreg (HImode, operands[2], SImode, 0);
3643 operands[6] = msp430_subreg (HImode, operands[0], SImode, 2);
3644 operands[7] = msp430_subreg (HImode, operands[1], SImode, 2);
3645 operands[8] = msp430_subreg (HImode, operands[2], SImode, 2);
3647 /* BZ 64160: Do not use this splitter when the dest partially overlaps the
3648 source. */
3649 if (reg_overlap_mentioned_p (operands[3], operands[7])
3650 || reg_overlap_mentioned_p (operands[3], operands[8]))
3651 return 1;
3653 if (GET_CODE (operands[5]) == CONST_INT)
3654 operands[9] = GEN_INT (INTVAL (operands[5]) & 0xffff);
3655 /* Handle post_inc, for example:
3656 (set (reg:SI)
3657 (plus:SI (reg:SI)
3658 (mem:SI (post_inc:PSI (reg:PSI))))). */
3659 else if (MEM_P (operands[5]) && GET_CODE (XEXP (operands[5], 0)) == POST_INC)
3661 /* Strip out the post_inc from (mem (post_inc (reg))). */
3662 operands[9] = XEXP (XEXP (operands[5], 0), 0);
3663 operands[9] = gen_rtx_MEM (HImode, operands[9]);
3664 /* Then zero extend as normal. */
3665 operands[9] = gen_rtx_ZERO_EXTEND (SImode, operands[9]);
3667 else
3668 operands[9] = gen_rtx_ZERO_EXTEND (SImode, operands[5]);
3669 return 0;
3672 /* Called by movsi_x to generate the HImode operands. */
3673 void
3674 msp430_split_movsi (rtx *operands)
3676 rtx op00, op02, op10, op12;
3678 op00 = msp430_subreg (HImode, operands[0], SImode, 0);
3679 op02 = msp430_subreg (HImode, operands[0], SImode, 2);
3681 if (GET_CODE (operands[1]) == CONST
3682 || GET_CODE (operands[1]) == SYMBOL_REF)
3684 op10 = gen_rtx_ZERO_EXTRACT (HImode, operands[1], GEN_INT (16),
3685 GEN_INT (0));
3686 op10 = gen_rtx_CONST (HImode, op10);
3687 op12 = gen_rtx_ZERO_EXTRACT (HImode, operands[1], GEN_INT (16),
3688 GEN_INT (16));
3689 op12 = gen_rtx_CONST (HImode, op12);
3691 else
3693 op10 = msp430_subreg (HImode, operands[1], SImode, 0);
3694 op12 = msp430_subreg (HImode, operands[1], SImode, 2);
3697 if (rtx_equal_p (operands[0], operands[1]))
3699 operands[2] = op02;
3700 operands[4] = op12;
3701 operands[3] = op00;
3702 operands[5] = op10;
3704 else if (rtx_equal_p (op00, op12)
3705 /* Catch the case where we are loading (rN, rN+1) from mem (rN). */
3706 || (REG_P (op00) && reg_mentioned_p (op00, op10))
3707 /* Or storing (rN) into mem (rN). */
3708 || (REG_P (op10) && reg_mentioned_p (op10, op00)))
3710 operands[2] = op02;
3711 operands[4] = op12;
3712 operands[3] = op00;
3713 operands[5] = op10;
3715 else
3717 operands[2] = op00;
3718 operands[4] = op10;
3719 operands[3] = op02;
3720 operands[5] = op12;
3725 /* The MSPABI specifies the names of various helper functions, many of
3726 which are compatible with GCC's helpers. This table maps the GCC
3727 name to the MSPABI name. */
3728 static const struct
3730 char const * const gcc_name;
3731 char const * const ti_name;
3733 helper_function_name_mappings[] =
3735 /* Floating point to/from integer conversions. */
3736 { "__truncdfsf2", "__mspabi_cvtdf" },
3737 { "__extendsfdf2", "__mspabi_cvtfd" },
3738 { "__fixdfhi", "__mspabi_fixdi" },
3739 { "__fixdfsi", "__mspabi_fixdli" },
3740 { "__fixdfdi", "__mspabi_fixdlli" },
3741 { "__fixunsdfhi", "__mspabi_fixdu" },
3742 { "__fixunsdfsi", "__mspabi_fixdul" },
3743 { "__fixunsdfdi", "__mspabi_fixdull" },
3744 { "__fixsfhi", "__mspabi_fixfi" },
3745 { "__fixsfsi", "__mspabi_fixfli" },
3746 { "__fixsfdi", "__mspabi_fixflli" },
3747 { "__fixunsfhi", "__mspabi_fixfu" },
3748 { "__fixunsfsi", "__mspabi_fixful" },
3749 { "__fixunsfdi", "__mspabi_fixfull" },
3750 { "__floathisf", "__mspabi_fltif" },
3751 { "__floatsisf", "__mspabi_fltlif" },
3752 { "__floatdisf", "__mspabi_fltllif" },
3753 { "__floathidf", "__mspabi_fltid" },
3754 { "__floatsidf", "__mspabi_fltlid" },
3755 { "__floatdidf", "__mspabi_fltllid" },
3756 { "__floatunhisf", "__mspabi_fltuf" },
3757 { "__floatunsisf", "__mspabi_fltulf" },
3758 { "__floatundisf", "__mspabi_fltullf" },
3759 { "__floatunhidf", "__mspabi_fltud" },
3760 { "__floatunsidf", "__mspabi_fltuld" },
3761 { "__floatundidf", "__mspabi_fltulld" },
3763 /* Floating point comparisons. */
3764 /* GCC uses individual functions for each comparison, TI uses one
3765 compare <=> function. */
3767 /* Floating point arithmetic. */
3768 { "__adddf3", "__mspabi_addd" },
3769 { "__addsf3", "__mspabi_addf" },
3770 { "__divdf3", "__mspabi_divd" },
3771 { "__divsf3", "__mspabi_divf" },
3772 { "__muldf3", "__mspabi_mpyd" },
3773 { "__mulsf3", "__mspabi_mpyf" },
3774 { "__subdf3", "__mspabi_subd" },
3775 { "__subsf3", "__mspabi_subf" },
3776 /* GCC does not use helper functions for negation. */
3778 /* Integer multiply, divide, remainder. */
3779 { "__mulhi3", "__mspabi_mpyi" },
3780 { "__mulsi3", "__mspabi_mpyl" },
3781 { "__muldi3", "__mspabi_mpyll" },
3782 #if 0
3783 /* Clarify signed vs unsigned first. */
3784 { "__mulhisi3", "__mspabi_mpysl" }, /* gcc doesn't use widening multiply
3785 (yet?) */
3786 { "__mulsidi3", "__mspabi_mpysll" }, /* gcc doesn't use widening multiply
3787 (yet?) */
3788 #endif
3790 { "__divhi3", "__mspabi_divi" },
3791 { "__divsi3", "__mspabi_divli" },
3792 { "__divdi3", "__mspabi_divlli" },
3793 { "__udivhi3", "__mspabi_divu" },
3794 { "__udivsi3", "__mspabi_divul" },
3795 { "__udivdi3", "__mspabi_divull" },
3796 { "__modhi3", "__mspabi_remi" },
3797 { "__modsi3", "__mspabi_remli" },
3798 { "__moddi3", "__mspabi_remlli" },
3799 { "__umodhi3", "__mspabi_remu" },
3800 { "__umodsi3", "__mspabi_remul" },
3801 { "__umoddi3", "__mspabi_remull" },
3803 /* Bitwise operations. */
3804 /* Rotation - no rotation support yet. */
3805 /* Logical left shift - gcc already does these itself. */
3806 /* Arithmetic left shift - gcc already does these itself. */
3807 /* Arithmetic right shift - gcc already does these itself. */
3809 { NULL, NULL }
3812 /* Returns true if the current MCU supports an F5xxx series
3813 hardware multiper. */
3815 bool
3816 msp430_use_f5_series_hwmult (void)
3818 static const char * cached_match = NULL;
3819 static bool cached_result;
3821 if (msp430_hwmult_type == MSP430_HWMULT_F5SERIES)
3822 return true;
3824 if (target_mcu == NULL || msp430_hwmult_type != MSP430_HWMULT_AUTO)
3825 return false;
3827 if (target_mcu == cached_match)
3828 return cached_result;
3830 cached_match = target_mcu;
3832 if (strncasecmp (target_mcu, "msp430f5", 8) == 0)
3833 return cached_result = true;
3834 if (strncasecmp (target_mcu, "msp430fr5", 9) == 0)
3835 return cached_result = true;
3836 if (strncasecmp (target_mcu, "msp430f6", 8) == 0)
3837 return cached_result = true;
3839 msp430_extract_mcu_data (target_mcu);
3841 if (extracted_mcu_data.name != NULL)
3842 return cached_result = extracted_mcu_data.hwmpy == 8;
3844 return cached_result = false;
3847 /* Returns true if the current MCU has a second generation
3848 32-bit hardware multiplier. */
3850 static bool
3851 msp430_use_32bit_hwmult (void)
3853 static const char * cached_match = NULL;
3854 static bool cached_result;
3856 if (msp430_hwmult_type == MSP430_HWMULT_LARGE)
3857 return true;
3859 if (target_mcu == NULL || msp430_hwmult_type != MSP430_HWMULT_AUTO)
3860 return false;
3862 if (target_mcu == cached_match)
3863 return cached_result;
3865 cached_match = target_mcu;
3867 msp430_extract_mcu_data (target_mcu);
3868 if (extracted_mcu_data.name != NULL)
3869 return cached_result = extracted_mcu_data.hwmpy == 4;
3871 return cached_result = false;
3874 /* Returns true if the current MCU has a first generation
3875 16-bit hardware multiplier. */
3877 static bool
3878 msp430_use_16bit_hwmult (void)
3880 static const char * cached_match = NULL;
3881 static bool cached_result;
3883 if (msp430_hwmult_type == MSP430_HWMULT_SMALL)
3884 return true;
3886 if (target_mcu == NULL || msp430_hwmult_type != MSP430_HWMULT_AUTO)
3887 return false;
3889 if (target_mcu == cached_match)
3890 return cached_result;
3892 cached_match = target_mcu;
3894 msp430_extract_mcu_data (target_mcu);
3895 if (extracted_mcu_data.name != NULL)
3896 return cached_result = (extracted_mcu_data.hwmpy == 1
3897 || extracted_mcu_data.hwmpy == 2);
3899 return cached_result = false;
3902 /* Returns true if the current MCU does not have a
3903 hardware multiplier of any kind. */
3905 bool
3906 msp430_has_hwmult (void)
3908 static const char * cached_match = NULL;
3909 static bool cached_result;
3911 if (msp430_hwmult_type == MSP430_HWMULT_NONE)
3912 return false;
3914 /* TRUE for any other explicit hwmult specified. */
3915 if (msp430_hwmult_type != MSP430_HWMULT_AUTO)
3916 return true;
3918 /* Now handle -mhwmult=auto. */
3919 if (target_mcu == NULL)
3920 return false;
3922 if (target_mcu == cached_match)
3923 return cached_result;
3925 cached_match = target_mcu;
3927 msp430_extract_mcu_data (target_mcu);
3928 if (extracted_mcu_data.name != NULL)
3929 return cached_result = extracted_mcu_data.hwmpy != 0;
3931 /* If we do not recognise the MCU name, we assume that it does not support
3932 any kind of hardware multiply - this is the safest assumption to make. */
3933 return cached_result = false;
3936 /* This function does the same as the default, but it will replace GCC
3937 function names with the MSPABI-specified ones. */
3939 void
3940 msp430_output_labelref (FILE *file, const char *name)
3942 int i;
3944 for (i = 0; helper_function_name_mappings[i].gcc_name; i++)
3945 if (strcmp (helper_function_name_mappings[i].gcc_name, name) == 0)
3947 name = helper_function_name_mappings[i].ti_name;
3948 break;
3951 if (user_label_prefix[0] != 0)
3952 fputs (user_label_prefix, file);
3954 fputs (name, file);
3957 /* Common code for msp430_print_operand... */
3959 static void
3960 msp430_print_operand_raw (FILE * file, rtx op)
3962 HOST_WIDE_INT i;
3964 switch (GET_CODE (op))
3966 case REG:
3967 fprintf (file, "%s", reg_names[REGNO (op)]);
3968 break;
3970 case CONST_INT:
3971 i = INTVAL (op);
3972 if (TARGET_ASM_HEX)
3973 fprintf (file, "%#" HOST_WIDE_INT_PRINT "x", i);
3974 else
3975 fprintf (file, "%" HOST_WIDE_INT_PRINT "d", i);
3976 break;
3978 case CONST:
3979 case PLUS:
3980 case MINUS:
3981 case SYMBOL_REF:
3982 case LABEL_REF:
3983 output_addr_const (file, op);
3984 break;
3986 default:
3987 print_rtl (file, op);
3988 break;
3992 #undef TARGET_ASM_ALIGNED_PSI_OP
3993 #define TARGET_ASM_ALIGNED_PSI_OP "\t.long\t"
3994 #undef TARGET_ASM_UNALIGNED_PSI_OP
3995 #define TARGET_ASM_UNALIGNED_PSI_OP TARGET_ASM_ALIGNED_PSI_OP
3997 #undef TARGET_PRINT_OPERAND_ADDRESS
3998 #define TARGET_PRINT_OPERAND_ADDRESS msp430_print_operand_addr
4000 /* Output to stdio stream FILE the assembler syntax for an
4001 instruction operand that is a memory reference whose address
4002 is ADDR. */
4004 static void
4005 msp430_print_operand_addr (FILE * file, machine_mode /*mode*/, rtx addr)
4007 switch (GET_CODE (addr))
4009 case PLUS:
4010 msp430_print_operand_raw (file, XEXP (addr, 1));
4011 gcc_assert (REG_P (XEXP (addr, 0)));
4012 fprintf (file, "(%s)", reg_names[REGNO (XEXP (addr, 0))]);
4013 return;
4015 case REG:
4016 fprintf (file, "@");
4017 break;
4019 case POST_INC:
4020 fprintf (file, "@%s+", reg_names[REGNO (XEXP (addr, 0))]);
4021 return;
4023 case CONST:
4024 case CONST_INT:
4025 case SYMBOL_REF:
4026 case LABEL_REF:
4027 fprintf (file, "&");
4028 break;
4030 default:
4031 break;
4034 msp430_print_operand_raw (file, addr);
4037 /* We can only allow signed 15-bit indexes i.e. +/-32K. */
4038 static bool
4039 msp430_check_index_not_high_mem (rtx op)
4041 if (CONST_INT_P (op)
4042 && IN_RANGE (INTVAL (op), HOST_WIDE_INT_M1U << 15, (1 << 15) - 1))
4043 return true;
4044 return false;
4047 /* If this returns true, we don't need a 430X insn. */
4048 static bool
4049 msp430_check_plus_not_high_mem (rtx op)
4051 if (GET_CODE (op) != PLUS)
4052 return false;
4053 rtx op0 = XEXP (op, 0);
4054 rtx op1 = XEXP (op, 1);
4055 if (SYMBOL_REF_P (op0)
4056 && (SYMBOL_REF_FLAGS (op0) & SYMBOL_FLAG_LOW_MEM)
4057 && msp430_check_index_not_high_mem (op1))
4058 return true;
4059 return false;
4062 /* Determine whether an RTX is definitely not a MEM referencing an address in
4063 the upper memory region. Returns true if we've decided the address will be
4064 in the lower memory region, or the RTX is not a MEM. Returns false
4065 otherwise.
4066 The Ys constraint will catch (mem (plus (const/reg)) but we catch cases
4067 involving a symbol_ref here. */
4068 bool
4069 msp430_op_not_in_high_mem (rtx op)
4071 rtx op0;
4073 if (!TARGET_LARGE || !MEM_P (op))
4074 return true;
4076 op0 = XEXP (op, 0);
4078 if (SYMBOL_REF_P (op0) && (SYMBOL_REF_FLAGS (op0) & SYMBOL_FLAG_LOW_MEM))
4079 /* msp430_encode_section_info decided this mem will be in lower
4080 memory. */
4081 return true;
4083 /* Check possibilites for (mem (plus)).
4084 e.g. (mem (const (plus ((symbol_ref) (const_int))))) : &addr+2. */
4085 if (msp430_check_plus_not_high_mem (op0)
4086 || ((GET_CODE (op0) == CONST)
4087 && msp430_check_plus_not_high_mem (XEXP (op0, 0))))
4088 return true;
4090 /* An absolute 16-bit address is allowed. */
4091 if ((CONST_INT_P (op0) && (IN_RANGE (INTVAL (op0), 0, (1 << 16) - 1))))
4092 return true;
4094 /* Return false when undecided. */
4095 return false;
4098 /* Based on the operand OP, is a 430X insn required to handle it?
4099 There are only 3 conditions for which a 430X insn is required:
4100 - PSImode operand
4101 - memory reference to a symbol which could be in upper memory
4102 (so its address is > 0xFFFF)
4103 - absolute address which has VOIDmode, i.e. (mem:HI (const_int))
4104 Use a 430 insn if none of these conditions are true. */
4105 bool
4106 msp430x_insn_required (rtx op)
4108 return (GET_MODE (op) == PSImode
4109 || !msp430_op_not_in_high_mem (op));
4112 #undef TARGET_PRINT_OPERAND
4113 #define TARGET_PRINT_OPERAND msp430_print_operand
4115 /* A Select low 16-bits of the constant/register/memory operand.
4116 B Select high 16-bits of the constant/register/memory
4117 operand.
4118 C Select bits 32-47 of the constant/register/memory operand.
4119 D Select bits 48-63 of the constant/register/memory operand.
4120 H Equivalent to @code{B} (for backwards compatibility).
4121 I Print the inverse (logical @code{NOT}) of the constant
4122 value.
4123 J Print an integer without a @code{#} prefix.
4124 L Equivalent to @code{A} (for backwards compatibility).
4125 O Offset of the current frame from the top of the stack.
4126 Q Use the @code{A} instruction postfix.
4127 R Inverse of condition code, for unsigned comparisons.
4128 W Subtract 16 from the constant value.
4129 X Use the @code{X} instruction postfix.
4130 Y Subtract 4 from the constant value.
4131 Z Subtract 1 from the constant value.
4132 b Append @code{.B}, @code{.W} or @code{.A} to the
4133 instruction, depending on the mode.
4134 d Offset 1 byte of a memory reference or constant value.
4135 e Offset 3 bytes of a memory reference or constant value.
4136 f Offset 5 bytes of a memory reference or constant value.
4137 g Offset 7 bytes of a memory reference or constant value.
4138 p Print the value of 2, raised to the power of the given
4139 constant. Used to select the specified bit position.
4140 r Inverse of condition code, for signed comparisons.
4141 x Equivialent to @code{X}, but only for pointers. */
4143 static void
4144 msp430_print_operand (FILE * file, rtx op, int letter)
4146 rtx addr;
4147 /* These are used by the 'A', 'B', 'C', 'D', 'd', 'e', 'f' and 'g' modifiers
4148 to describe how to process the operand to get the requested value. */
4149 int mem_off = 0;
4150 int reg_off = 0;
4151 int const_shift = 0;
4153 /* We can't use c, n, a, or l. */
4154 switch (letter)
4156 case 'Z':
4157 gcc_assert (CONST_INT_P (op));
4158 /* Print the constant value, less one. */
4159 fprintf (file, "#%ld", (long) (INTVAL (op) - 1));
4160 return;
4161 case 'Y':
4162 gcc_assert (CONST_INT_P (op));
4163 /* Print the constant value, less four. */
4164 fprintf (file, "#%ld", (long) (INTVAL (op) - 4));
4165 return;
4166 case 'W':
4167 gcc_assert (CONST_INT_P (op));
4168 /* Print the constant value, less 16. */
4169 fprintf (file, "#%ld", (long) (INTVAL (op) - 16));
4170 return;
4171 case 'I':
4172 if (GET_CODE (op) == CONST_INT)
4174 /* Inverse of constants */
4175 int i = INTVAL (op);
4176 fprintf (file, "%d", ~i);
4177 return;
4179 op = XEXP (op, 0);
4180 break;
4181 case 'r': /* Conditional jump where the condition is reversed. */
4182 switch (GET_CODE (op))
4184 case EQ: fprintf (file, "NE"); break;
4185 case NE: fprintf (file, "EQ"); break;
4186 case GEU: fprintf (file, "LO"); break;
4187 case LTU: fprintf (file, "HS"); break;
4188 case GE: fprintf (file, "L"); break;
4189 case LT: fprintf (file, "GE"); break;
4190 /* Assume these have reversed operands. */
4191 case GTU: fprintf (file, "HS"); break;
4192 case LEU: fprintf (file, "LO"); break;
4193 case GT: fprintf (file, "GE"); break;
4194 case LE: fprintf (file, "L"); break;
4195 default:
4196 msp430_print_operand_raw (file, op);
4197 break;
4199 return;
4200 case 'R': /* Conditional jump where the operands are reversed. */
4201 switch (GET_CODE (op))
4203 case GTU: fprintf (file, "LO"); break;
4204 case LEU: fprintf (file, "HS"); break;
4205 case GT: fprintf (file, "L"); break;
4206 case LE: fprintf (file, "GE"); break;
4207 default:
4208 msp430_print_operand_raw (file, op);
4209 break;
4211 return;
4212 case 'p': /* Bit position. 0 == 0x01, 3 = 0x08 etc. */
4213 gcc_assert (CONST_INT_P (op));
4214 fprintf (file, "#%d", 1 << INTVAL (op));
4215 return;
4216 case 'b':
4217 switch (GET_MODE (op))
4219 case E_QImode: fprintf (file, ".B"); return;
4220 case E_HImode: fprintf (file, ".W"); return;
4221 case E_PSImode: fprintf (file, ".A"); return;
4222 case E_SImode: fprintf (file, ".A"); return;
4223 default:
4224 return;
4226 case 'd': case 'e': case 'f': case 'g':
4227 if (REG_P (op))
4229 output_operand_lossage ("%%d, %%e, %%f, %%g operand modifiers are "
4230 "for memory references or constant values "
4231 "only");
4232 return;
4234 /* fallthru */
4235 case 'B': case 'H': /* high half */
4236 case 'C':
4237 case 'D':
4238 switch (letter)
4240 case 'd':
4241 mem_off = 1;
4242 const_shift = 8;
4243 break;
4244 case 'B':
4245 case 'H':
4246 mem_off = 2;
4247 reg_off = 1;
4248 const_shift = 16;
4249 break;
4250 case 'e':
4251 mem_off = 3;
4252 const_shift = 24;
4253 break;
4254 case 'C':
4255 mem_off = 4;
4256 reg_off = 2;
4257 const_shift = 32;
4258 break;
4259 case 'f':
4260 mem_off = 5;
4261 const_shift = 40;
4262 break;
4263 case 'D':
4264 mem_off = 6;
4265 reg_off = 3;
4266 const_shift = 48;
4267 break;
4268 case 'g':
4269 mem_off = 7;
4270 const_shift = 56;
4271 break;
4272 default:
4273 gcc_unreachable ();
4274 break;
4276 /* fallthru */
4277 case 'A': case 'L': /* Low half. */
4278 switch (GET_CODE (op))
4280 case MEM:
4281 /* We don't need to adjust the address for post_inc. */
4282 op = adjust_address (op, Pmode,
4283 (GET_CODE (XEXP (op, 0)) == POST_INC)
4284 ? 0 : mem_off);
4285 break;
4286 case REG:
4287 op = gen_rtx_REG (Pmode, REGNO (op) + reg_off);
4288 break;
4289 case CONST_INT:
4290 op = GEN_INT (((long long) INTVAL (op) >> const_shift) & 0xffff);
4291 letter = 0;
4292 break;
4293 default:
4294 /* If you get here, figure out a test case :-) */
4295 gcc_unreachable ();
4297 break;
4299 case 'X':
4300 /* This is used to turn, for example, an ADD opcode into an ADDX
4301 opcode when we're using 20-bit addresses.
4302 This can be used for insns which have only one operand which might be
4303 a mem.
4304 If an insn has two different operands which could be memory operands,
4305 then the "Yx" constraint must be used to determine if the X suffix is
4306 required by checking both operands. */
4307 if (GET_MODE (op) == PSImode
4308 || !msp430_op_not_in_high_mem (op))
4309 fprintf (file, "X");
4310 return;
4312 case 'x':
4313 /* Similarly, but only for PSImodes. BIC, and other insn patterns using
4314 the QHI mode iterator (which includes, QI, HI, and PSImode) use
4315 this. */
4316 if (GET_MODE (op) == PSImode)
4317 fprintf (file, "X");
4318 return;
4320 case 'Q':
4321 /* Likewise, for BR -> BRA. */
4322 if (TARGET_LARGE)
4323 fprintf (file, "A");
4324 return;
4326 case 'O':
4327 /* Computes the offset to the top of the stack for the current frame.
4328 This has to be done here rather than in, say, msp430_expand_builtin()
4329 because builtins are expanded before the frame layout is
4330 determined. */
4331 fprintf (file, "%d",
4332 msp430_initial_elimination_offset (ARG_POINTER_REGNUM,
4333 STACK_POINTER_REGNUM)
4334 - (TARGET_LARGE ? 4 : 2));
4335 return;
4337 case 'J':
4338 gcc_assert (GET_CODE (op) == CONST_INT);
4339 case 0:
4340 break;
4341 default:
4342 output_operand_lossage ("invalid operand prefix");
4343 return;
4346 switch (GET_CODE (op))
4348 case REG:
4349 msp430_print_operand_raw (file, op);
4350 break;
4352 case MEM:
4353 addr = XEXP (op, 0);
4354 msp430_print_operand_addr (file, GET_MODE (op), addr);
4355 break;
4357 case CONST:
4358 if (GET_CODE (XEXP (op, 0)) == ZERO_EXTRACT)
4360 op = XEXP (op, 0);
4361 switch (INTVAL (XEXP (op, 2)))
4363 case 0:
4364 fprintf (file, "#lo (");
4365 msp430_print_operand_raw (file, XEXP (op, 0));
4366 fprintf (file, ")");
4367 break;
4369 case 16:
4370 fprintf (file, "#hi (");
4371 msp430_print_operand_raw (file, XEXP (op, 0));
4372 fprintf (file, ")");
4373 break;
4375 default:
4376 output_operand_lossage ("invalid zero extract");
4377 break;
4379 break;
4381 /* Fall through. */
4382 case CONST_INT:
4383 case SYMBOL_REF:
4384 case LABEL_REF:
4385 if (letter == 0)
4386 fprintf (file, "#");
4387 msp430_print_operand_raw (file, op);
4388 break;
4390 case EQ: fprintf (file, "EQ"); break;
4391 case NE: fprintf (file, "NE"); break;
4392 case GEU: fprintf (file, "HS"); break;
4393 case LTU: fprintf (file, "LO"); break;
4394 case GE: fprintf (file, "GE"); break;
4395 case LT: fprintf (file, "L"); break;
4397 default:
4398 print_rtl (file, op);
4399 break;
4404 /* Frame stuff. */
4407 msp430_return_addr_rtx (int count)
4409 int ra_size;
4410 if (count)
4411 return NULL_RTX;
4413 ra_size = TARGET_LARGE ? 4 : 2;
4414 if (crtl->args.pretend_args_size)
4415 ra_size += 2;
4417 return gen_rtx_MEM (Pmode, gen_rtx_PLUS (Pmode, arg_pointer_rtx,
4418 GEN_INT (- ra_size)));
4422 msp430_incoming_return_addr_rtx (void)
4424 return gen_rtx_MEM (Pmode, stack_pointer_rtx);
4427 /* If the path to the MSP430-GCC support files has been found by examining
4428 an environment variable (see msp430_check_env_var_for_devices in
4429 msp430-devices.cc), or -mdevices-csv-loc=, register this path as an include
4430 directory so the user can #include msp430.h without needing to specify the
4431 path to the support files with -I. */
4432 void
4433 msp430_register_pre_includes (const char *sysroot ATTRIBUTE_UNUSED,
4434 const char *iprefix ATTRIBUTE_UNUSED,
4435 int stdinc ATTRIBUTE_UNUSED)
4437 char *include_dir;
4438 if (msp430_devices_csv_loc)
4439 include_dir = xstrdup (msp430_devices_csv_loc);
4440 else if (msp430_check_env_var_for_devices (&include_dir))
4441 return;
4442 include_dir = msp430_dirname (include_dir);
4444 include_dir = update_path (include_dir, "");
4445 add_path (include_dir, INC_SYSTEM, false, false);
4448 /* Instruction generation stuff. */
4450 /* Generate a sequence of instructions to sign-extend an HI
4451 value into an SI value. Handles the tricky case where
4452 we are overwriting the destination.
4453 Return the number of bytes used by the emitted instructions.
4454 If RETURN_LENGTH is true then do not emit the assembly instruction
4455 sequence. */
4457 msp430x_extendhisi (rtx * operands, bool return_length)
4459 if (REGNO (operands[0]) == REGNO (operands[1]))
4461 /* Low word of dest == source word. */
4462 if (!return_length)
4463 output_asm_insn ("BIT.W\t#0x8000, %L0 { SUBC.W\t%H0, %H0 { INV.W\t%H0, %H0",
4464 operands);
4465 return 8;
4467 else if (! msp430x)
4469 /* Note: This sequence is approximately the same length as invoking a
4470 helper function to perform the sign-extension, as in:
4472 MOV.W %1, %L0
4473 MOV.W %1, r12
4474 CALL __mspabi_srai_15
4475 MOV.W r12, %H0
4477 but this version does not involve any function calls or using argument
4478 registers, so it reduces register pressure. */
4479 if (!return_length)
4480 output_asm_insn ("MOV.W\t%1, %L0 { BIT.W\t#0x8000, %L0 { SUBC.W\t%H0, %H0 { INV.W\t%H0, %H0",
4481 operands);
4482 return 10;
4484 else if (REGNO (operands[0]) + 1 == REGNO (operands[1]))
4486 /* High word of dest == source word. */
4487 if (!return_length)
4488 output_asm_insn ("MOV.W\t%1, %L0 { RPT\t#15 { RRAX.W\t%H0",
4489 operands);
4490 return 6;
4493 /* No overlap between dest and source. */
4494 if (!return_length)
4495 output_asm_insn ("MOV.W\t%1, %L0 { MOV.W\t%1, %H0 { RPT\t#15 { RRAX.W\t%H0",
4496 operands);
4497 return 8;
4500 /* Stop GCC from thinking that it can eliminate (SUBREG:PSI (SI)). */
4502 #undef TARGET_CAN_CHANGE_MODE_CLASS
4503 #define TARGET_CAN_CHANGE_MODE_CLASS msp430_can_change_mode_class
4505 static bool
4506 msp430_can_change_mode_class (machine_mode from, machine_mode to, reg_class_t)
4508 if ((to == PSImode && from == SImode)
4509 || (to == SImode && from == PSImode)
4510 || (to == DImode && from == PSImode)
4511 || (to == PSImode && from == DImode))
4512 return false;
4513 return true;
4516 #undef TARGET_HAVE_SPECULATION_SAFE_VALUE
4517 #define TARGET_HAVE_SPECULATION_SAFE_VALUE speculation_safe_value_not_needed
4519 struct gcc_target targetm = TARGET_INITIALIZER;
4521 #include "gt-msp430.h"