Import final gcc2 snapshot (990109)
[official-gcc.git] / gcc / config / m68k / mot3300.h
bloba90332efff51436ee0e83dd65dd3d48c44cc41ab
1 /* Definitions of target machine for GNU compiler,
2 SysV68 Motorola 3300 Delta Series.
3 Copyright (C) 1987, 93, 94, 95, 96, 97, 1998 Free Software Foundation, Inc.
4 Contributed by Abramo and Roberto Bagnara (bagnara@dipisa.di.unipi.it)
5 based on Alex Crain's 3B1 definitions.
6 Maintained by Philippe De Muyter (phdm@info.ucl.ac.be).
7 Support for GAS added by merging mot3300g.h into this file by
8 Manfred Hollstein (manfred@lts.sel.alcatel.de).
10 This file is part of GNU CC.
12 GNU CC is free software; you can redistribute it and/or modify
13 it under the terms of the GNU General Public License as published by
14 the Free Software Foundation; either version 2, or (at your option)
15 any later version.
17 GNU CC is distributed in the hope that it will be useful,
18 but WITHOUT ANY WARRANTY; without even the implied warranty of
19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 GNU General Public License for more details.
22 You should have received a copy of the GNU General Public License
23 along with GNU CC; see the file COPYING. If not, write to
24 the Free Software Foundation, 59 Temple Place - Suite 330,
25 Boston, MA 02111-1307, USA. */
27 #ifndef USE_GAS
28 #define MOTOROLA /* Use Motorola syntax rather than "MIT" */
29 #define MOTOROLA_BSR /* Use Span-dependent optimized bsr */
30 #define SGS /* Uses SGS assembler */
31 #define SGS_CMP_ORDER /* Takes cmp operands in reverse order */
32 #define SGS_SWAP_W /* Use swap.w rather than just plain swap */
33 #endif /* USE_GAS */
35 #define NO_DOLLAR_IN_LABEL
36 #define NO_DOT_IN_LABEL
38 #include "m68k/m68k.h"
40 /* See m68k.h. 0407 means 68020-68040. */
42 #ifndef TARGET_DEFAULT
43 #define TARGET_DEFAULT (MASK_68040|MASK_BITFIELD|MASK_68881|MASK_68020)
44 #endif
46 /* -m[c]6800 requires special flag to the assembler. */
48 #undef ASM_SPEC
49 #ifndef USE_GAS
50 #define ASM_SPEC "%{m68000:-p 000}%{mc68000:-p 000}"
51 #else /* USE_GAS */
52 #define ASM_SPEC \
53 "%{v:-v} %{m68000:-mc68000}%{mc68000:-mc68000}%{!mc68000:%{!m68000:-mc68020}}"
54 #endif /* USE_GAS */
56 /* NYI: FP= is equivalent to -msoft-float */
58 /* We use /lib/libp/lib* when profiling. */
60 /* NYI: if FP=M68881U library is -lc881u */
61 /* NYI: if FP= library is -lc. */
62 /* Default for us: FP=M68881 library is -lc881 */
63 #undef LIB_SPEC
64 #define LIB_SPEC "%{!shlib:%{!msoft-float:-lc881}%{msoft-float:-lc}}"
65 #ifdef CROSS_COMPILE
66 #ifndef USE_GLD
67 #define DEFAULT_A_OUT_NAME "m68ka.out"
68 #endif
69 #endif
71 #ifdef USE_GLD
72 #undef LINK_SPEC
73 #define LINK_SPEC "%{v:-v}"
74 #endif /* defined (USE_GLD) */
76 #define CPP_SPEC "%{!msoft-float:-D__HAVE_68881__}\
77 %{!mc68000:%{!m68000: -D__mc68020__}}"
79 /* Shared libraries need to use crt0s.o */
81 #undef STARTFILE_SPEC
82 #ifdef CROSS_COMPILE
83 #define STARTFILE_SPEC \
84 "%{!shlib:%{pg:mcrt0.o%s}%{!pg:%{p:mcrt0.o%s}%{!p:crt0.o%s}}}\
85 %{shlib:crt0s.o%s shlib.ifile%s} %{p:-L"TOOLDIR_BASE_PREFIX DEFAULT_TARGET_MACHINE"/lib/libp} %{pg:-L"TOOLDIR_BASE_PREFIX DEFAULT_TARGET_MACHINE"/lib/libp} "
86 #else /* CROSS_COMPILE */
87 #define STARTFILE_SPEC \
88 "%{!shlib:%{pg:mcrt0.o%s}%{!pg:%{p:mcrt0.o%s}%{!p:crt0.o%s}}}\
89 %{shlib:crt0s.o%s shlib.ifile%s} %{p:-L/usr/lib/libp} %{pg:-L/usr/lib/libp} "
90 #endif /* CROSS_COMPILE */
92 /* Generate calls to memcpy, memcmp and memset. */
94 #define TARGET_MEM_FUNCTIONS
96 /* size_t is unsigned int. */
98 #define SIZE_TYPE "unsigned int"
100 /* Every structure or union's size must be a multiple of 2 bytes. */
102 #define STRUCTURE_SIZE_BOUNDARY 16
104 /* Follow sysV68 cc regarding alignment imposed by char:0; */
106 #define PCC_BITFIELD_TYPE_MATTERS 1
108 /* Allocation boundary (in *bits*) for storing arguments in argument list. */
109 /* Be compatible with native compiler. */
110 #undef PARM_BOUNDARY
111 #define PARM_BOUNDARY 16
113 /* cpp has to support a #sccs directive for the /usr/include files */
115 #define SCCS_DIRECTIVE
117 /* Make output for SDB. */
119 #define SDB_DEBUGGING_INFO
121 #undef REGISTER_PREFIX
122 #define REGISTER_PREFIX "%"
124 #undef LOCAL_LABEL_PREFIX
125 #ifdef USE_GAS
126 #define LOCAL_LABEL_PREFIX ".L"
127 #else
128 #define LOCAL_LABEL_PREFIX "L%"
129 #endif
131 #undef USER_LABEL_PREFIX
133 #undef IMMEDIATE_PREFIX
134 #define IMMEDIATE_PREFIX "&"
136 #undef REGISTER_NAMES
137 #define REGISTER_NAMES \
138 {"%d0", "%d1", "%d2", "%d3", "%d4", "%d5", "%d6", "%d7", \
139 "%a0", "%a1", "%a2", "%a3", "%a4", "%a5", "%fp", "%sp", \
140 "%fp0", "%fp1", "%fp2", "%fp3", "%fp4", "%fp5", "%fp6", "%fp7"}
142 #undef FUNCTION_EXTRA_EPILOGUE
143 #define FUNCTION_EXTRA_EPILOGUE(FILE, SIZE) \
144 { extern int current_function_returns_pointer; \
145 if ((current_function_returns_pointer) && \
146 ! find_equiv_reg (0, get_last_insn (), 0, 0, 0, 8, Pmode)) \
147 asm_fprintf (FILE, "\tmov.l %Ra0,%Rd0\n"); }
149 #undef FUNCTION_PROFILER
150 #define FUNCTION_PROFILER(FILE, LABEL_NO) \
151 asm_fprintf (FILE, "\tmov.l %I%LLP%d,%Ra0\n\tjsr mcount%%\n", (LABEL_NO))
153 /* This is how to output an insn to push a register on the stack.
154 It need not be very fast code. */
156 #undef ASM_OUTPUT_REG_PUSH
157 #define ASM_OUTPUT_REG_PUSH(FILE,REGNO) \
158 fprintf (FILE, "\tmov.l %s,-(%%sp)\n", reg_names[REGNO])
160 /* This is how to output an insn to pop a register from the stack.
161 It need not be very fast code. */
163 #undef ASM_OUTPUT_REG_POP
164 #define ASM_OUTPUT_REG_POP(FILE,REGNO) \
165 fprintf (FILE, "\tmov.l (%%sp)+,%s\n", reg_names[REGNO])
167 #ifndef USE_GAS
169 #undef ASM_APP_ON
170 #define ASM_APP_ON ""
172 #undef ASM_APP_OFF
173 #define ASM_APP_OFF ""
175 #undef TEXT_SECTION_ASM_OP
176 #define TEXT_SECTION_ASM_OP "text"
177 #undef DATA_SECTION_ASM_OP
178 #define DATA_SECTION_ASM_OP "data"
179 #undef ASCII_DATA_ASM_OP
180 #define ASCII_DATA_ASM_OP "byte"
182 #undef SET_ASM_OP
183 #define SET_ASM_OP "set"
185 #endif /* USE_GAS */
187 #ifdef USE_GLD
188 /* Support the ctors and dtors sections for g++. */
190 #define CTORS_SECTION_ASM_OP ".section\t.ctors,\"x\""
191 #define DTORS_SECTION_ASM_OP ".section\t.dtors,\"x\""
193 /* A list of other sections which the compiler might be "in" at any
194 given time. */
196 #undef EXTRA_SECTIONS
197 #define EXTRA_SECTIONS in_ctors, in_dtors
199 /* A list of extra section function definitions. */
201 #undef EXTRA_SECTION_FUNCTIONS
202 #define EXTRA_SECTION_FUNCTIONS \
203 CTORS_SECTION_FUNCTION \
204 DTORS_SECTION_FUNCTION
206 #define CTORS_SECTION_FUNCTION \
207 void \
208 ctors_section () \
210 if (in_section != in_ctors) \
212 fprintf (asm_out_file, "%s\n", CTORS_SECTION_ASM_OP); \
213 in_section = in_ctors; \
217 #define DTORS_SECTION_FUNCTION \
218 void \
219 dtors_section () \
221 if (in_section != in_dtors) \
223 fprintf (asm_out_file, "%s\n", DTORS_SECTION_ASM_OP); \
224 in_section = in_dtors; \
228 /* A C statement (sans semicolon) to output an element in the table of
229 global constructors. */
230 #define ASM_OUTPUT_CONSTRUCTOR(FILE,NAME) \
231 do { \
232 ctors_section (); \
233 fprintf (FILE, "\t%s\t ", ASM_LONG); \
234 assemble_name (FILE, NAME); \
235 fprintf (FILE, "\n"); \
236 } while (0)
238 /* A C statement (sans semicolon) to output an element in the table of
239 global destructors. */
240 #define ASM_OUTPUT_DESTRUCTOR(FILE,NAME) \
241 do { \
242 dtors_section (); \
243 fprintf (FILE, "\t%s\t ", ASM_LONG); \
244 assemble_name (FILE, NAME); \
245 fprintf (FILE, "\n"); \
246 } while (0)
247 #endif /* defined (USE_GLD) */
249 /* The file command should always begin the output. */
251 #undef ASM_FILE_START
252 #ifndef USE_GAS
253 #define ASM_FILE_START(FILE) \
254 output_file_directive ((FILE), main_input_filename)
255 #else /* USE_GAS */
256 #define ASM_FILE_START(FILE) \
258 fprintf (FILE, "%s", ASM_APP_OFF); \
259 output_file_directive ((FILE), main_input_filename); \
261 #endif /* USE_GAS */
263 /* The sysV68 assembler does not accept dots in labels.
264 Let's use percent instead */
266 #define ASM_IDENTIFY_GCC(FILE) fputs("gcc2_compiled%:\n", FILE)
268 /* Names to predefine in the preprocessor for this target machine. */
269 /* ihnp4!lmayk!lgm@eddie.mit.edu says mc68000 and m68k should not be here,
270 on the other hand I don't care what he says. */
272 #undef CPP_PREDEFINES
273 #define CPP_PREDEFINES "-Dm68k -Dunix -DsysV68 -D__motorola__ -Asystem(unix) -Asystem(svr3) -Acpu(m68k) -Amachine(m68k)"
275 #undef TARGET_VERSION
276 #ifndef USE_GAS
277 #define TARGET_VERSION fprintf (stderr, " (68k, SGS/AT&T sysV68 syntax)");
278 #endif /* USE_GAS */
280 /* This will return small structs in d0. */
281 #define RETURN_IN_MEMORY(type) \
282 ((TYPE_MODE (type) == BLKmode) \
283 || (AGGREGATE_TYPE_P (type) \
284 && GET_MODE_SIZE (TYPE_MODE (type)) > UNITS_PER_WORD))
286 /* Don't default to pcc-struct-return, because we have already specified
287 exactly how to return structures in the RETURN_IN_MEMORY macro. */
288 #define DEFAULT_PCC_STRUCT_RETURN 0
290 /* If TARGET_68881, return SF and DF values in fp0 instead of d0. */
291 /* NYI: If FP=M68881U return SF and DF values in d0. */
292 /* NYI: If -mold return pointer in a0 and d0 */
294 #undef FUNCTION_VALUE
295 /* sysV68 (brain damaged) cc convention support. */
296 #define FUNCTION_VALUE(VALTYPE,FUNC) \
297 (TREE_CODE (VALTYPE) == REAL_TYPE && TARGET_68881 \
298 ? gen_rtx_REG (TYPE_MODE (VALTYPE), 16) \
299 : (POINTER_TYPE_P (VALTYPE) \
300 ? gen_rtx_REG (TYPE_MODE (VALTYPE), 8) \
301 : gen_rtx_REG (TYPE_MODE (VALTYPE), 0)))
303 /* If TARGET_68881, SF and DF values are returned in fp0 instead of d0. */
305 /* Is LIBCALL_VALUE never called with a pointer ? */
306 #undef LIBCALL_VALUE
307 #define LIBCALL_VALUE(MODE) \
308 gen_rtx_REG ((MODE), \
309 ((TARGET_68881 \
310 && ((MODE) == SFmode || (MODE) == DFmode \
311 || (MODE) == XFmode)) \
312 ? 16 : 0))
314 /* 1 if N is a possible register number for a function value.
315 d0 may be used, and fp0 as well if -msoft-float is not specified. */
317 #undef FUNCTION_VALUE_REGNO_P
318 /* sysV68 (brain damaged) cc convention support. */
319 #define FUNCTION_VALUE_REGNO_P(N) \
320 ((N) == 0 || (N) == 8 || (TARGET_68881 && (N) == 16))
322 /* Define this to be true when FUNCTION_VALUE_REGNO_P is true for
323 more than one register. */
325 #undef NEEDS_UNTYPED_CALL
326 #define NEEDS_UNTYPED_CALL 1
328 #ifndef USE_GAS
329 /* This is the command to make the user-level label named NAME
330 defined for reference from other files. */
332 #undef GLOBAL_ASM_OP
333 #define GLOBAL_ASM_OP "global"
334 #endif /* USE_GAS */
336 /* Store in OUTPUT a string (made with alloca) containing
337 an assembler-name for a local static variable named NAME.
338 LABELNO is an integer which is different for each call. */
340 #undef ASM_FORMAT_PRIVATE_NAME
341 #define ASM_FORMAT_PRIVATE_NAME(OUTPUT, NAME, LABELNO) \
342 ( (OUTPUT) = (char *) alloca (strlen ((NAME)) + 12), \
343 sprintf ((OUTPUT), "%s_%%%d", (NAME), (LABELNO)))
345 #ifdef USE_GAS
346 #undef ASM_LONG
347 #define ASM_LONG ".long"
348 #undef ASM_SHORT
349 #define ASM_SHORT ".short"
350 #undef ASM_CHAR
351 #define ASM_CHAR ".byte"
352 #undef ASM_BYTE
353 #define ASM_BYTE ".byte"
354 #undef ASM_BYTE_OP
355 #define ASM_BYTE_OP ".byte"
356 #else
357 #undef ASM_LONG
358 #define ASM_LONG "long"
359 #undef ASM_SHORT
360 #define ASM_SHORT "short"
361 #undef ASM_CHAR
362 #define ASM_CHAR "byte"
363 #undef ASM_BYTE
364 #define ASM_BYTE "byte"
365 #undef ASM_BYTE_OP
366 #define ASM_BYTE_OP "byte"
367 #endif /* USE_GAS */
369 /* The sysV68 as doesn't know about double's and float's. */
370 /* This is how to output an assembler line defining a `double' constant. */
372 #undef ASM_OUTPUT_DOUBLE
373 #define ASM_OUTPUT_DOUBLE(FILE,VALUE) \
374 do { long l[2]; \
375 REAL_VALUE_TO_TARGET_DOUBLE (VALUE, l); \
376 fprintf (FILE, "\t%s 0x%x,0x%x\n", ASM_LONG, l[0], l[1]); \
377 } while (0)
379 #undef ASM_OUTPUT_LONG_DOUBLE
380 #define ASM_OUTPUT_LONG_DOUBLE(FILE,VALUE) \
381 do { long l[3]; \
382 REAL_VALUE_TO_TARGET_LONG_DOUBLE (VALUE, l); \
383 fprintf (FILE, "\t%s 0x%x,0x%x,0x%x\n", ASM_LONG, l[0], l[1], l[2]); \
384 } while (0)
386 /* This is how to output an assembler line defining a `float' constant. */
388 #undef ASM_OUTPUT_FLOAT
389 #define ASM_OUTPUT_FLOAT(FILE,VALUE) \
390 do { long l; \
391 REAL_VALUE_TO_TARGET_SINGLE (VALUE, l); \
392 fprintf ((FILE), "\t%s 0x%x\n", ASM_LONG, l); \
393 } while (0)
395 /* This is how to output an assembler line defining an `int' constant. */
397 #undef ASM_OUTPUT_INT
398 #define ASM_OUTPUT_INT(FILE,VALUE) \
399 ( fprintf (FILE, "\t%s ", ASM_LONG), \
400 output_addr_const (FILE, (VALUE)), \
401 fprintf (FILE, "\n"))
403 /* Likewise for `char' and `short' constants. */
405 #undef ASM_OUTPUT_SHORT
406 #define ASM_OUTPUT_SHORT(FILE,VALUE) \
407 ( fprintf (FILE, "\t%s ", ASM_SHORT), \
408 output_addr_const (FILE, (VALUE)), \
409 fprintf (FILE, "\n"))
411 #undef ASM_OUTPUT_CHAR
412 #define ASM_OUTPUT_CHAR(FILE,VALUE) \
413 ( fprintf (FILE, "\t%s ", ASM_CHAR), \
414 output_addr_const (FILE, (VALUE)), \
415 fprintf (FILE, "\n"))
417 /* This is how to output an assembler line for a numeric constant byte. */
419 #undef ASM_OUTPUT_BYTE
420 #define ASM_OUTPUT_BYTE(FILE,VALUE) \
421 fprintf (FILE, "\t%s 0x%x\n", ASM_BYTE, (VALUE))
423 /* This is how to output an assembler line
424 that says to advance the location counter
425 to a multiple of 2**LOG bytes. */
427 #ifndef USE_GAS
428 #define ALIGN_ASM_OP "even"
429 #else /* USE_GAS */
430 #define ALIGN_ASM_OP ".even"
431 #endif /* USE_GAS */
433 #undef ASM_OUTPUT_ALIGN
434 #define ASM_OUTPUT_ALIGN(FILE,LOG) \
435 if ((LOG) >= 1) \
436 fprintf (FILE, "\t%s\n", ALIGN_ASM_OP);
438 #ifndef USE_GAS
439 #define SKIP_ASM_OP "space"
440 #else /* USE_GAS */
441 #define SKIP_ASM_OP ".skip"
442 #endif /* USE_GAS */
444 #undef ASM_OUTPUT_SKIP
445 #define ASM_OUTPUT_SKIP(FILE,SIZE) \
446 fprintf (FILE, "\t%s %u\n", SKIP_ASM_OP, (SIZE))
448 /* Can't use ASM_OUTPUT_SKIP in text section. */
450 #define ASM_NO_SKIP_IN_TEXT 1
452 /* The beginnings of sdb support... */
454 /* Undefining these will allow `output_file_directive' (in toplev.c)
455 to default to the right thing. */
456 #undef ASM_OUTPUT_MAIN_SOURCE_FILENAME
457 #ifndef USE_GAS
458 #define ASM_OUTPUT_SOURCE_FILENAME(FILE, FILENAME) \
459 do { fprintf (FILE, "\tfile\t"); \
460 output_quoted_string (FILE, FILENAME); \
461 fprintf (FILE, "\n"); \
462 } while (0)
464 #undef ASM_OUTPUT_SOURCE_LINE
465 #define ASM_OUTPUT_SOURCE_LINE(FILE, LINENO) \
466 fprintf (FILE, "\tln\t%d\n", \
467 (sdb_begin_function_line \
468 ? last_linenum - sdb_begin_function_line : 1))
470 /* Yet another null terminated string format. */
472 #undef ASM_OUTPUT_ASCII
473 #define ASM_OUTPUT_ASCII(FILE,PTR,LEN) \
474 do { register int sp = 0, lp = 0; \
475 fprintf ((FILE), "\t%s\t", ASM_BYTE_OP); \
476 loop: \
477 if ((PTR)[sp] > ' ' && ! ((PTR)[sp] & 0x80) && (PTR)[sp] != '\\') \
478 { lp += 3; \
479 fprintf ((FILE), "'%c", (PTR)[sp]); } \
480 else \
481 { lp += 5; \
482 fprintf ((FILE), "0x%x", (PTR)[sp]); } \
483 if (++sp < (LEN)) \
484 { if (lp > 60) \
485 { lp = 0; \
486 fprintf ((FILE), "\n\t%s ", ASCII_DATA_ASM_OP); } \
487 else \
488 putc (',', (FILE)); \
489 goto loop; } \
490 putc ('\n', (FILE)); } while (0)
491 #endif /* USE_GAS */
493 #ifndef USE_GAS
494 /* Output a float value (represented as a C double) as an immediate operand.
495 This macro is a 68k-specific macro. */
497 #undef ASM_OUTPUT_FLOAT_OPERAND
498 #define ASM_OUTPUT_FLOAT_OPERAND(CODE,FILE,VALUE) \
499 do { long l; \
500 REAL_VALUE_TO_TARGET_SINGLE (r, l); \
501 /* Use hex representation even if CODE is f. as needs it. */ \
502 fprintf ((FILE), "&0x%lx", l); \
503 } while (0)
505 /* Output a double value (represented as a C double) as an immediate operand.
506 This macro is a 68k-specific macro. */
507 #undef ASM_OUTPUT_DOUBLE_OPERAND
508 #define ASM_OUTPUT_DOUBLE_OPERAND(FILE,VALUE) \
509 do { long l[2]; \
510 REAL_VALUE_TO_TARGET_DOUBLE (VALUE, l); \
511 fprintf ((FILE), "&0x%lx%08lx", l[0], l[1]); \
512 } while (0)
513 #endif /* USE_GAS */
515 /* This is how to store into the string LABEL
516 the symbol_ref name of an internal numbered label where
517 PREFIX is the class of label and NUM is the number within the class.
518 This is suitable for output with `assemble_name'. */
520 #undef ASM_GENERATE_INTERNAL_LABEL
521 #define ASM_GENERATE_INTERNAL_LABEL(LABEL, PREFIX, NUM) \
522 sprintf ((LABEL), "%s%s%d", LOCAL_LABEL_PREFIX, (PREFIX), (NUM))
524 /* This is how to output an internal numbered label where
525 PREFIX is the class of label and NUM is the number within the class. */
527 #undef ASM_OUTPUT_INTERNAL_LABEL
528 #define ASM_OUTPUT_INTERNAL_LABEL(FILE,PREFIX,NUM) \
529 asm_fprintf (FILE, "%L%s%d:\n", PREFIX, NUM)
531 /* The prefix to add to user-visible assembler symbols. */
533 #undef USER_LABEL_PREFIX
534 #define USER_LABEL_PREFIX ""
536 /* This is how to output an element of a case-vector that is absolute.
537 (The 68000 does not use such vectors,
538 but we must define this macro anyway.) */
539 /* The L after the local prefix is the "L" prefix for the normal labels
540 generated by gcc; why are ASM_OUTPUT_ADDR_VEC_ELT and
541 ASM_OUTPUT_ADDR_DIFF_ELT not called with a PREFIX parameter, like
542 ASM_OUTPUT_INTERNAL_LABEL ? */
544 #undef ASM_OUTPUT_ADDR_VEC_ELT
545 #define ASM_OUTPUT_ADDR_VEC_ELT(FILE, VALUE) \
546 asm_fprintf (FILE, "\t%s %LL%d\n", ASM_LONG, (VALUE))
548 /* This is how to output an element of a case-vector that is relative. */
550 #undef ASM_OUTPUT_ADDR_DIFF_ELT
551 #define ASM_OUTPUT_ADDR_DIFF_ELT(FILE, VALUE, REL) \
552 asm_fprintf (FILE, "\t%s %LL%d-%LL%d\n", ASM_SHORT, (VALUE), (REL))
554 #ifndef USE_GAS
556 #define ASM_OUTPUT_CASE_LABEL(FILE,PREFIX,NUM,TABLE) \
557 asm_fprintf (FILE, "\tswbeg &%d\n%L%s%d:\n", \
558 XVECLEN (PATTERN (TABLE), 1), (PREFIX), (NUM))
560 /* sysV68 as cannot handle LD%n(%pc,%reg) */
561 #define SGS_NO_LI
563 /* labelno is not used here */
564 #define ASM_OUTPUT_CASE_FETCH(file, labelno, regname)\
565 asm_fprintf (file, "12(%Rpc,%s.", regname)
567 #define ASM_RETURN_CASE_JUMP \
568 do { \
569 if (TARGET_5200) \
570 return "ext%.l %0\n\tjmp 8(%%pc,%0.l)"; \
571 else \
572 return "jmp 8(%%pc,%0.w)"; \
573 } while (0)
575 #else /* USE_GAS */
577 /* labelno is not used here */
578 #define ASM_OUTPUT_CASE_FETCH(file, labelno, regname)\
579 asm_fprintf (file, "%Rpc@(6,%s:", regname)
581 #define ASM_RETURN_CASE_JUMP return "jmp %%pc@(2,%0:w)"
583 #endif /* USE_GAS */
585 #ifndef USE_GAS
587 /* Translate some opcodes to fit the sysV68 assembler syntax. */
588 /* The opcodes fdmov and fsmov are guesses. */
590 /* cliffm@netcom.com says no need for .w suffix on jumps. */
591 #undef ASM_OUTPUT_OPCODE
592 #define ASM_OUTPUT_OPCODE(FILE, PTR) \
593 { if ((PTR)[0] == 'j' && (PTR)[1] == 'b') \
594 { ++(PTR); \
595 while (*(PTR) != ' ') \
596 { putc (*(PTR), (FILE)); ++(PTR); } \
598 else if ((PTR)[0] == 's') \
600 if (!strncmp ((PTR), "swap", 4)) \
601 { fprintf ((FILE), "swap.w"); (PTR) += 4; } \
603 else if ((PTR)[0] == 'f') \
605 if (!strncmp ((PTR), "fmove", 5)) \
606 { fprintf ((FILE), "fmov"); (PTR) += 5; } \
607 else if (!strncmp ((PTR), "f%$move", 7)) \
608 { if (TARGET_68040_ONLY) \
609 { fprintf ((FILE), "fsmov"); (PTR) += 7; } \
610 else \
611 { fprintf ((FILE), "fmov"); (PTR) += 7; } } \
612 else if (!strncmp ((PTR), "f%&move", 7)) \
613 { if (TARGET_68040_ONLY) \
614 { fprintf ((FILE), "fdmov"); (PTR) += 7; } \
615 else \
616 { fprintf ((FILE), "fmov"); (PTR) += 7; } } \
617 else if (!strncmp ((PTR), "ftst", 4)) \
618 { fprintf ((FILE), "ftest"); (PTR) += 4; } \
619 else if (!strncmp ((PTR), "fbne", 4)) \
620 { fprintf ((FILE), "fbneq"); (PTR) += 4; } \
621 else if (!strncmp ((PTR), "fsne", 4)) \
622 { fprintf ((FILE), "fsneq"); (PTR) += 4; } \
624 /* MOVE, MOVEA, MOVEQ, MOVEC ==> MOV */ \
625 else if ((PTR)[0] == 'm' && (PTR)[1] == 'o' \
626 && (PTR)[2] == 'v' && (PTR)[3] == 'e') \
627 { fprintf ((FILE), "mov"); (PTR) += 4; \
628 if ((PTR)[0] == 'q' || (PTR)[0] == 'a' \
629 || (PTR)[0] == 'c') (PTR)++; } \
630 /* SUB, SUBQ, SUBA, SUBI ==> SUB */ \
631 else if ((PTR)[0] == 's' && (PTR)[1] == 'u' \
632 && (PTR)[2] == 'b') \
633 { fprintf ((FILE), "sub"); (PTR) += 3; \
634 if ((PTR)[0] == 'q' || (PTR)[0] == 'i' \
635 || (PTR)[0] == 'a') (PTR)++; } \
636 /* CMP, CMPA, CMPI, CMPM ==> CMP */ \
637 else if ((PTR)[0] == 'c' && (PTR)[1] == 'm' \
638 && (PTR)[2] == 'p') \
639 { fprintf ((FILE), "cmp"); (PTR) += 3; \
640 if ((PTR)[0] == 'a' || (PTR)[0] == 'i' \
641 || (PTR)[0] == 'm') (PTR)++; } \
643 #endif /* USE_GAS */
645 /* phdm@info.ucl.ac.be says to pass SIZE, not ROUNDED. */
647 /* This says how to output an assembler line
648 to define a global common symbol. */
650 #undef ASM_OUTPUT_COMMON
651 #ifndef USE_GAS
652 #define ASM_OUTPUT_COMMON(FILE, NAME, SIZE, ROUNDED) \
653 ( fputs ("\tcomm ", (FILE)), \
654 assemble_name ((FILE), (NAME)), \
655 fprintf ((FILE), ",%u\n", (SIZE)))
656 #else /* USE_GAS */
657 #define ASM_OUTPUT_COMMON(FILE, NAME, SIZE, ROUNDED) \
658 ( fputs ("\t.comm ", (FILE)), \
659 assemble_name ((FILE), (NAME)), \
660 fprintf ((FILE), ",%u\n", (SIZE)))
661 #endif /* USE_GAS */
663 /* This says how to output an assembler line
664 to define a local common symbol. */
666 #undef ASM_OUTPUT_LOCAL
667 #ifndef USE_GAS
668 #define ASM_OUTPUT_LOCAL(FILE, NAME, SIZE, ROUNDED) \
669 ( fputs ("\tlcomm ", (FILE)), \
670 assemble_name ((FILE), (NAME)), \
671 fprintf ((FILE), ",%u\n", (SIZE)))
672 #else /* USE_GAS */
673 #define ASM_OUTPUT_LOCAL(FILE, NAME, SIZE, ROUNDED) \
674 ( fputs ("\t.lcomm ", (FILE)), \
675 assemble_name ((FILE), (NAME)), \
676 fprintf ((FILE), ",%u\n", (SIZE)))
677 #endif /* USE_GAS */
679 #ifndef USE_GAS
680 /* Override usual definitions of SDB output macros.
681 These definitions differ only in the absence of the period
682 at the beginning of the name of the directive
683 and in the use of `~' as the symbol for the current location. */
685 #define PUT_SDB_SCL(a) fprintf(asm_out_file, "\tscl\t%d;", (a))
686 #define PUT_SDB_INT_VAL(a) fprintf (asm_out_file, "\tval\t%d;", (a))
687 #define PUT_SDB_VAL(a) \
688 ( fputs ("\tval\t", asm_out_file), \
689 output_addr_const (asm_out_file, (a)), \
690 fputc (';', asm_out_file))
692 #define PUT_SDB_DEF(a) \
693 do { fprintf (asm_out_file, "\tdef\t"); \
694 ASM_OUTPUT_LABELREF (asm_out_file, a); \
695 fprintf (asm_out_file, ";"); } while (0)
697 #define PUT_SDB_PLAIN_DEF(a) fprintf(asm_out_file,"\tdef\t~%s;",a)
698 #define PUT_SDB_ENDEF fputs("\tendef\n", asm_out_file)
699 #define PUT_SDB_TYPE(a) fprintf(asm_out_file, "\ttype\t0%o;", a)
700 #define PUT_SDB_SIZE(a) fprintf(asm_out_file, "\tsize\t%d;", a)
701 #define PUT_SDB_START_DIM fprintf(asm_out_file, "\tdim\t")
702 #define PUT_SDB_NEXT_DIM(a) fprintf(asm_out_file, "%d,", a)
703 #define PUT_SDB_LAST_DIM(a) fprintf(asm_out_file, "%d;", a)
705 #define PUT_SDB_TAG(a) \
706 do { fprintf (asm_out_file, "\ttag\t"); \
707 ASM_OUTPUT_LABELREF (asm_out_file, a); \
708 fprintf (asm_out_file, ";"); } while (0)
710 #define PUT_SDB_BLOCK_START(LINE) \
711 fprintf (asm_out_file, \
712 "\tdef\t~bb;\tval\t~;\tscl\t100;\tline\t%d;\tendef\n", \
713 (LINE))
715 #define PUT_SDB_BLOCK_END(LINE) \
716 fprintf (asm_out_file, \
717 "\tdef\t~eb;\tval\t~;\tscl\t100;\tline\t%d;\tendef\n", \
718 (LINE))
720 #define PUT_SDB_FUNCTION_START(LINE) \
721 fprintf (asm_out_file, \
722 "\tdef\t~bf;\tval\t~;\tscl\t101;\tline\t%d;\tendef\n", \
723 (LINE))
725 #define PUT_SDB_FUNCTION_END(LINE) \
726 fprintf (asm_out_file, \
727 "\tdef\t~ef;\tval\t~;\tscl\t101;\tline\t%d;\tendef\n", \
728 (LINE))
730 #define PUT_SDB_EPILOGUE_END(NAME) \
731 fprintf (asm_out_file, \
732 "\tdef\t%s;\tval\t~;\tscl\t-1;\tendef\n", \
733 (NAME))
735 #define SDB_GENERATE_FAKE(BUFFER, NUMBER) \
736 sprintf ((BUFFER), "~%dfake", (NUMBER));
738 #endif /* USE_GAS */
740 /* Define subroutines to call to handle multiply, divide, and remainder.
741 Use the subroutines that the sysV68's library provides.
742 The `*' prevents an underscore from being prepended by the compiler. */
743 /* The '*' is also used by INIT_CUMULATIVE_ARGS */
745 #define DIVSI3_LIBCALL "*ldiv%%"
746 #define UDIVSI3_LIBCALL "*uldiv%%"
747 #define MODSI3_LIBCALL "*lrem%%"
748 #define UMODSI3_LIBCALL "*ulrem%%"
749 #define MULSI3_LIBCALL "*lmul%%"
751 struct sysV68_cumulative_args
753 int offset;
754 int libcall;
757 #undef CUMULATIVE_ARGS
758 #define CUMULATIVE_ARGS struct sysV68_cumulative_args
760 #undef INIT_CUMULATIVE_ARGS
761 #define INIT_CUMULATIVE_ARGS(CUM,FNTYPE,LIBNAME,INDIRECT) \
762 do {(CUM).offset = 0;\
763 (CUM).libcall = (LIBNAME) && (*XSTR((LIBNAME), 0) == '*');} while(0)
765 #undef FUNCTION_ARG_ADVANCE
766 #define FUNCTION_ARG_ADVANCE(CUM, MODE, TYPE, NAMED) \
767 ((CUM).offset += ((MODE) != BLKmode \
768 ? (GET_MODE_SIZE (MODE) + 3) & ~3 \
769 : (int_size_in_bytes (TYPE) + 3) & ~3))
771 #undef FUNCTION_ARG
772 #define FUNCTION_ARG(CUM, MODE, TYPE, NAMED) \
773 (((CUM).libcall && (CUM).offset == 0) ? gen_rtx_REG ((MODE), 0)\
774 : (TARGET_REGPARM && (CUM).offset < 8) ? gen_rtx_REG ((MODE), (CUM).offset / 4) : 0)
776 #undef FUNCTION_ARG_PARTIAL_NREGS
777 #define FUNCTION_ARG_PARTIAL_NREGS(CUM, MODE, TYPE, NAMED) \
778 ((TARGET_REGPARM && (CUM).offset < 8 \
779 && 8 < ((CUM).offset + ((MODE) == BLKmode \
780 ? int_size_in_bytes (TYPE) \
781 : GET_MODE_SIZE (MODE)))) \
782 ? 2 - (CUM).offset / 4 : 0)
784 #undef FUNCTION_ARG_REGNO_P
785 #define FUNCTION_ARG_REGNO_P(N) (TARGET_68020 ? 0 : (N) == 0)
787 /* manfred@lts.sel.alcatel.de: I believe that most delta machines are configured to have
788 a 6888[12] FPU for which we need to link -lm881 instead of -lm; define ALT_LIBM to
789 tell g++.c about that. */
790 #define ALT_LIBM "-lm881"
792 #if (TARGET_DEFAULT & MASK_68881) /* The default configuration has a 6888[12] FPU. */
793 #define MATH_LIBRARY "-lm881"
794 #endif
796 /* Currently we do not have the atexit() function,
797 so take that from libgcc2.c */
799 #define NEED_ATEXIT 1
800 #define HAVE_ATEXIT 1
802 #define EXIT_BODY \
803 do \
805 __stop_monitor (); \
806 _cleanup (); \
807 } while (0)
809 /* FINALIZE_TRAMPOLINE clears the instruction cache. */
811 #undef FINALIZE_TRAMPOLINE
812 #define FINALIZE_TRAMPOLINE(TRAMP) \
813 if (!TARGET_68040) \
815 else \
816 emit_library_call (gen_rtx_SYMBOL_REF (Pmode, "__clear_insn_cache"), \
817 0, VOIDmode, 0)