This is the mail archive of the
binutils@sources.redhat.com
mailing list for the binutils project.
Re: [Revised patch] Rework MIPS command-line handling
cgd@broadcom.com writes:
> > If that idea really doesn't fly, I'd rather have _MIPS_ARCH
> > be a string and define _MIPS_ARCH_FOO when compiling for FOO.
>
> You know, now that you mention it, i think that might actually be the
> best solution. (kind of a "back to the future" thing, but with the
> addition of a string for _MIPS_ARCH. 8-)
New version below. Also includes the suggested gas config changes
(infer processor name from mipsisa32foo, base MIPS_DEFAULT_64BIT
on full target triple).
As Gerald pointed out, the changes ought to be mentioned on the
3.3 pages, so I've attached a patch for that too.
GAS patch tested on a fairly random selection of targets:
mips-ecoff, mips-elf, mips-sgi-irix6.5m mips64-elf, mips64orion-elf,
mips64vr4100el-elf, mipsel-ecoff, mipsel-linux-gnu, mipsisa32-elf,
mipsisa32-linux-gnu, mipsisa64-elf and mipstx39-elf.
GCC patch tested by bootstrapping on mips-sgi-irix6.5. Also
tested mips-elf and mips64-elf (in the latter case, both with
and without the GAS changes).
OK to install?
[include/]
* opcode/mips.h (CPU_R2000): Remove.
[gas/]
* doc/c-mips.texi: Remove -mcpu. Document -mabi.
* configure.in (MIPS_CPU_STRING_DEFAULT): New configuration macro.
(USE_E_MIPS_ABI_O32, MIPS_DEFAULT_64BIT): New configuration macros.
* configure, config.in: Regenerate.
* config/tc-mips.c (file_mips_abi): Rename to mips_abi.
(mips_set_options): Remove "abi" field.
(mips_opts): Update accordingly. Replace all uses of mips_opts.abi
with mips_abi.
(mips_cpu): Remove.
(mips_arch_string, mips_arch_info): New vars.
(mips_tune_string, mips_tune_info): New vars.
(ABI_NEEDS_32BIT_REGS, ABI_NEEDS_64BIT_REGS): New macros.
(HAVE_32BIT_GPRS, HAVE_32BIT_FPRS): Don't check the ABI.
(mips_isa_to_str, mips_cpu_to_str): Remove.
(mips_ip): If the selected architecture is a generic ISA rather
than a processor, only mention the ISA level in error messages.
(OPTION_MCPU): Remove.
(OPTION_FP64): New.
(md_longopts): Add -mfp64, remove -mcpu.
(mips_set_option_string): New fn.
(md_parse_option): Make -mipsN update file_mips_isa rather than
mips_opts.isa. Use mips_set_option_string to set -march or -mtune.
Don't let -mgp32 and -mfp32 change the ABI.
(show): Move to end of file. Constify string argument.
(md_show_usage): Move to the end of the file. Read available
architectures from mips_cpu_info_table.
(mips_set_architecture): New fn.
(mips_after_parse_args): Rework. Remove -mcpu handling. -mipsN
is an alias for -march=mipsN. Don't change the ABI based on other
flags. Infer the register size from the ABI as well as the
architecture. Complain about more conflicting arguments.
[Logic unified with gcc 3.2.]
(s_mipsset): Don't change the ABI.
(mips_elf_final_processing): Check USE_E_MIPS_ABI_O32.
(mips_cpu_info_table): Remove Generic-MIPS* entries, keeping just
"mipsN"-type entries. Remove entries that vary only in the
manufacturer's prefix, or that have "000" replaced by "k".
Remove TARGET_CPU entries. Make r2000 entry use CPU_R3000.
(mips_strict_matching_cpu_name_p, mips_matching_cpu_name_p): New fns.
(mips_parse_cpu): New fn.
(mips_cpu_info_from_name, mips_cpu_info_from_cpu): Remove.
(mips_cpu_info_from_isa): Minor formatting tweak.
[gas/testsuite]
* gas/mips/mips-gp32-fp64.d,
* gas/mips/mips-gp32-fp64-pic.d: Add -mfp64.
[gcc/]
* doc/invoke.texi: Document -mabi=meabi, and expand on the EABI
description. Document -mips32, -mips64, and the associated -march
values. Describe the "mipsN" arguments to -march. Say that the
-mipsN options are equivalent to -march. Reword the description
of default type sizes.
* toplev.h (target_flags_explicit): Declare.
* toplev.c (target_flags_explicit): New var.
(set_target_switch): Update target_flags_explicit.
* config/mips/abi64.h (SUBTARGET_TARGET_OPTIONS): Undefine.
* config/mips/elf64.h (MIPS_ISA_DEFAULT): Undefine.
* config/mips/iris6.h (SUBTARGET_ASM_SPEC): -mabi=64 implies -mips3.
* config/mips/isa3264.h (MIPS_ENABLE_EMBEDDED_O32): Undefine.
* config/mips/mips.h (mips_cpu_info): New struct.
(mips_cpu_string, mips_explicit_type_size_string): Remove.
(mips_cpu_info_table, mips_arch_info, mips_tune_info): Declare.
(MIPS_CPP_SET_PROCESSOR): New macro.
(TARGET_CPP_BUILTINS): Declare a macro for each supported processor.
Define _MIPS_ARCH and _MIPS_TUNE.
(MIPS_ISA_DEFAULT): Don't provide a default value. Instead...
(MIPS_CPU_STRING_DEFAULT): Set to "from-abi" if neither it nor
MIPS_ISA_DEFAULT were already defined.
(MULTILIB_DEFAULTS): Add MULTILIB_ABI_DEFAULT.
(TARGET_OPTIONS): Remove -mcpu and -mexplicit-type-size.
(ABI_NEEDS_32BIT_REGS, ABI_NEEDS_64BIT_REGS): New.
(GAS_ASM_SPEC): Remove -march, -mcpu, -mgp* and -mabi rules.
(ABI_GAS_ASM_SPEC): Remove.
(MULTILIB_ABI_DEFAULT, ASM_ABI_DEFAULT_SPEC): New macros.
(ASM_SPEC): Add -mgp32, -mgp64, -march, -mabi=eabi and -mabi=o64.
Invoke %(asm_abi_default_spec) if no ABI was specified.
(CC1_SPEC): Remove ISA -> register-size rules.
(EXTRA_SPECS): Remove abi_gas_asm_spec. Add asm_abi_default_spec.
* config/mips/mips.c (mips_arch_info, mips_tune_info): New vars.
(mips_cpu_string, mips_explicit_type_size_string): Remove.
(mips_cpu_info_table): New array.
(mips_set_architecture, mips_set_tune): New fns.
(override_options): Rework to make -mipsN equivalent to -march.
Detect more erroneous cases, including those removed from CC1_SPEC.
Don't change the ABI based on architecture, or vice versa.
Unify logic with GAS 2.14.
(mips_asm_file_start): Get architecture name from mips_arch_info.
(mips_strict_matching_cpu_name_p, mips_matching_cpu_name_p): New fns.
(mips_parse_cpu): Take the name of the option as argument. Handle
'from-abi'. Raise an error if the option is wrong.
(mips_cpu_info_from_isa): New fn.
[gcc/testsuite]
* gcc.dg/mips-args-[123].c: New tests.
Index: include/opcode/mips.h
===================================================================
RCS file: /cvs/src/src/include/opcode/mips.h,v
retrieving revision 1.27
diff -c -d -p -r1.27 mips.h
*** include/opcode/mips.h 9 Jul 2002 14:21:40 -0000 1.27
--- include/opcode/mips.h 19 Jul 2002 18:37:29 -0000
*************** struct mips_opcode
*** 377,383 ****
/* CPU defines, use instead of hardcoding processor number. Keep this
in sync with bfd/archures.c in order for machine selection to work. */
#define CPU_UNKNOWN 0 /* Gas internal use. */
- #define CPU_R2000 2000
#define CPU_R3000 3000
#define CPU_R3900 3900
#define CPU_R4000 4000
--- 377,382 ----
Index: gas/doc/c-mips.texi
===================================================================
RCS file: /cvs/src/src/gas/doc/c-mips.texi,v
retrieving revision 1.22
diff -c -d -p -r1.22 c-mips.texi
*** gas/doc/c-mips.texi 31 May 2002 01:17:15 -0000 1.22
--- gas/doc/c-mips.texi 19 Jul 2002 18:37:30 -0000
*************** sb1
*** 175,186 ****
Schedule and tune for a particular MIPS cpu. Valid @var{cpu} values are
identical to @samp{-march=@var{cpu}}.
! @item -mcpu=@var{cpu}
! Generate code and schedule for a particular MIPS cpu. This is exactly
! equivalent to @samp{-march=@var{cpu}} and @samp{-mtune=@var{cpu}}. Valid
! @var{cpu} values are identical to @samp{-march=@var{cpu}}.
! Use of this option is discouraged.
!
@cindex @code{-nocpp} ignored (MIPS)
@item -nocpp
--- 175,183 ----
Schedule and tune for a particular MIPS cpu. Valid @var{cpu} values are
identical to @samp{-march=@var{cpu}}.
! @item -mabi=@var{abi}
! Record which ABI the source code uses. The recognized arguments
! are: @samp{32}, @samp{n32}, @samp{o64}, @samp{64} and @samp{eabi}.
@cindex @code{-nocpp} ignored (MIPS)
@item -nocpp
Index: gas/configure.in
===================================================================
RCS file: /cvs/src/src/gas/configure.in,v
retrieving revision 1.110
diff -c -d -p -r1.110 configure.in
*** gas/configure.in 9 Jul 2002 02:41:16 -0000 1.110
--- gas/configure.in 19 Jul 2002 18:37:30 -0000
*************** changequote([,])dnl
*** 555,560 ****
--- 555,615 ----
# Other random stuff.
+ case ${cpu_type} in
+ mips)
+ # Set mips_cpu to the name of the default CPU.
+ case ${target_cpu} in
+ mips | mipsbe | mipseb | mipsle | mipsel | mips64 | mips64el)
+ mips_cpu=from-abi
+ ;;
+ mipsisa32 | mipsisa32el)
+ mips_cpu=mips32
+ ;;
+ mipsisa64 | mipsisa64el)
+ mips_cpu=mips64
+ ;;
+ mipstx39 | mipstx39el)
+ mips_cpu=r3900
+ ;;
+ mips64* | mipsisa64* | mipsisa32*)
+ changequote(,)dnl
+ mips_cpu=`echo $target_cpu | sed -e 's/[a-z]*..//' -e 's/el$//'`
+ changequote([,])dnl
+ ;;
+ *)
+ AC_ERROR($target_cpu isn't a supported MIPS CPU name)
+ ;;
+ esac
+ # See whether it's appropriate to set E_MIPS_ABI_O32 for o32
+ # binaries. It's a GNU extension that some OSes don't understand.
+ # The value only matters on ELF targets.
+ case ${target} in
+ *-*-irix*)
+ use_e_mips_abi_o32=0
+ ;;
+ *)
+ use_e_mips_abi_o32=1
+ ;;
+ esac
+ # Decide whether to generate 32-bit or 64-bit code by default.
+ # Used to resolve -march=from-abi when an embedded ABI is selected.
+ case ${target} in
+ mips64*-*-* | mipsisa64*-*-*)
+ mips_default_64bit=1
+ ;;
+ *)
+ mips_default_64bit=0
+ ;;
+ esac
+ AC_DEFINE_UNQUOTED(MIPS_CPU_STRING_DEFAULT, "$mips_cpu",
+ [Default CPU for MIPS targets. ])
+ AC_DEFINE_UNQUOTED(USE_E_MIPS_ABI_O32, $use_e_mips_abi_o32,
+ [Allow use of E_MIPS_ABI_O32 on MIPS targets. ])
+ AC_DEFINE_UNQUOTED(MIPS_DEFAULT_64BIT, $mips_default_64bit,
+ [Generate 64-bit code by default on MIPS targets. ])
+ ;;
+ esac
+
# Do we need the opcodes library?
case ${cpu_type} in
vax | i386 | tic30)
Index: gas/config/tc-mips.c
===================================================================
RCS file: /cvs/src/src/gas/config/tc-mips.c,v
retrieving revision 1.147
diff -c -d -p -r1.147 tc-mips.c
*** gas/config/tc-mips.c 9 Jul 2002 14:21:40 -0000 1.147
--- gas/config/tc-mips.c 19 Jul 2002 18:37:30 -0000
*************** enum mips_abi_level
*** 129,135 ****
};
/* MIPS ABI we are using for this output file. */
! static enum mips_abi_level file_mips_abi = NO_ABI;
/* This is the set of options which may be modified by the .set
pseudo-op. We use a struct so that .set push and .set pop are more
--- 129,135 ----
};
/* MIPS ABI we are using for this output file. */
! static enum mips_abi_level mips_abi = NO_ABI;
/* This is the set of options which may be modified by the .set
pseudo-op. We use a struct so that .set push and .set pop are more
*************** struct mips_set_options
*** 177,185 ****
is passed but can changed if the assembler code uses .set mipsN. */
int gp32;
int fp32;
- /* The ABI currently in use. This is changed by .set mipsN to loosen
- restrictions and doesn't affect the whole file. */
- enum mips_abi_level abi;
};
/* True if -mgp32 was passed. */
--- 177,182 ----
*************** static int file_mips_fp32 = -1;
*** 194,200 ****
static struct mips_set_options mips_opts =
{
! ISA_UNKNOWN, -1, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0, NO_ABI
};
/* These variables are filled in with the masks of registers used.
--- 191,197 ----
static struct mips_set_options mips_opts =
{
! ISA_UNKNOWN, -1, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0
};
/* These variables are filled in with the masks of registers used.
*************** static int file_ase_mips3d;
*** 218,235 ****
command line (e.g., by -march). */
static int file_ase_mdmx;
- /* The argument of the -mcpu= flag. Historical for code generation. */
- static int mips_cpu = CPU_UNKNOWN;
-
/* The argument of the -march= flag. The architecture we are assembling. */
static int mips_arch = CPU_UNKNOWN;
/* The argument of the -mtune= flag. The architecture for which we
are optimizing. */
static int mips_tune = CPU_UNKNOWN;
! /* If they asked for mips1 or mips2 and a cpu that is
! mips3 or greater, then mark the object file 32BITMODE. */
static int mips_32bitmode = 0;
/* Some ISA's have delay slots for instructions which read or write
--- 215,232 ----
command line (e.g., by -march). */
static int file_ase_mdmx;
/* The argument of the -march= flag. The architecture we are assembling. */
static int mips_arch = CPU_UNKNOWN;
+ static const char *mips_arch_string;
+ static const struct mips_cpu_info *mips_arch_info;
/* The argument of the -mtune= flag. The architecture for which we
are optimizing. */
static int mips_tune = CPU_UNKNOWN;
+ static const char *mips_tune_string;
+ static const struct mips_cpu_info *mips_tune_info;
! /* True when generating 32-bit code for a 64-bit processor. */
static int mips_32bitmode = 0;
/* Some ISA's have delay slots for instructions which read or write
*************** static int mips_32bitmode = 0;
*** 246,251 ****
--- 243,257 ----
|| (ISA) == ISA_MIPS3 \
)
+ /* True if the given ABI requires 32-bit registers. */
+ #define ABI_NEEDS_32BIT_REGS(ABI) ((ABI) == O32_ABI)
+
+ /* Likewise 64-bit registers. */
+ #define ABI_NEEDS_64BIT_REGS(ABI) \
+ ((ABI) == N32_ABI \
+ || (ABI) == N64_ABI \
+ || (ABI) == O64_ABI)
+
/* Return true if ISA supports 64 bit gp register instructions. */
#define ISA_HAS_64BIT_REGS(ISA) ( \
(ISA) == ISA_MIPS3 \
*************** static int mips_32bitmode = 0;
*** 255,275 ****
)
#define HAVE_32BIT_GPRS \
! (mips_opts.gp32 \
! || mips_opts.abi == O32_ABI \
! || ! ISA_HAS_64BIT_REGS (mips_opts.isa))
#define HAVE_32BIT_FPRS \
! (mips_opts.fp32 \
! || mips_opts.abi == O32_ABI \
! || ! ISA_HAS_64BIT_REGS (mips_opts.isa))
#define HAVE_64BIT_GPRS (! HAVE_32BIT_GPRS)
#define HAVE_64BIT_FPRS (! HAVE_32BIT_FPRS)
! #define HAVE_NEWABI (mips_opts.abi == N32_ABI || mips_opts.abi == N64_ABI)
! #define HAVE_64BIT_OBJECTS (mips_opts.abi == N64_ABI)
/* We can only have 64bit addresses if the object file format
supports it. */
--- 261,277 ----
)
#define HAVE_32BIT_GPRS \
! (mips_opts.gp32 || ! ISA_HAS_64BIT_REGS (mips_opts.isa))
#define HAVE_32BIT_FPRS \
! (mips_opts.fp32 || ! ISA_HAS_64BIT_REGS (mips_opts.isa))
#define HAVE_64BIT_GPRS (! HAVE_32BIT_GPRS)
#define HAVE_64BIT_FPRS (! HAVE_32BIT_FPRS)
! #define HAVE_NEWABI (mips_abi == N32_ABI || mips_abi == N64_ABI)
! #define HAVE_64BIT_OBJECTS (mips_abi == N64_ABI)
/* We can only have 64bit addresses if the object file format
supports it. */
*************** static void my_getExpression PARAMS ((ex
*** 741,746 ****
--- 743,749 ----
#ifdef OBJ_ELF
static int support_64bit_objects PARAMS((void));
#endif
+ static void mips_set_option_string PARAMS ((const char **, const char *));
static symbolS *get_symbol PARAMS ((void));
static void mips_align PARAMS ((int to, int fill, symbolS *label));
static void s_align PARAMS ((int));
*************** static void s_mips_weakext PARAMS ((int)
*** 772,781 ****
static void s_mips_file PARAMS ((int));
static void s_mips_loc PARAMS ((int));
static int mips16_extended_frag PARAMS ((fragS *, asection *, long));
- static const char *mips_isa_to_str PARAMS ((int));
- static const char *mips_cpu_to_str PARAMS ((int));
static int validate_mips_insn PARAMS ((const struct mips_opcode *));
! static void show PARAMS ((FILE *, char *, int *, int *));
#ifdef OBJ_ELF
static int mips_need_elf_addend_fixup PARAMS ((fixS *));
#endif
--- 775,782 ----
static void s_mips_file PARAMS ((int));
static void s_mips_loc PARAMS ((int));
static int mips16_extended_frag PARAMS ((fragS *, asection *, long));
static int validate_mips_insn PARAMS ((const struct mips_opcode *));
! static void show PARAMS ((FILE *, const char *, int *, int *));
#ifdef OBJ_ELF
static int mips_need_elf_addend_fixup PARAMS ((fixS *));
#endif
*************** struct mips_cpu_info
*** 817,825 ****
int cpu; /* CPU number (default CPU if ISA). */
};
! static const struct mips_cpu_info *mips_cpu_info_from_name PARAMS ((const char *));
static const struct mips_cpu_info *mips_cpu_info_from_isa PARAMS ((int));
- static const struct mips_cpu_info *mips_cpu_info_from_cpu PARAMS ((int));
/* Pseudo-op table.
--- 818,831 ----
int cpu; /* CPU number (default CPU if ISA). */
};
! static void mips_set_architecture PARAMS ((const struct mips_cpu_info *));
! static void mips_set_tune PARAMS ((const struct mips_cpu_info *));
! static boolean mips_strict_matching_cpu_name_p PARAMS ((const char *,
! const char *));
! static boolean mips_matching_cpu_name_p PARAMS ((const char *, const char *));
! static const struct mips_cpu_info *mips_parse_cpu PARAMS ((const char *,
! const char *));
static const struct mips_cpu_info *mips_cpu_info_from_isa PARAMS ((int));
/* Pseudo-op table.
*************** static boolean mips16_small, mips16_ext;
*** 972,1007 ****
static segT pdr_seg;
- static const char *
- mips_isa_to_str (isa)
- int isa;
- {
- const struct mips_cpu_info *ci;
- static char s[20];
-
- ci = mips_cpu_info_from_isa (isa);
- if (ci != NULL)
- return (ci->name);
-
- sprintf (s, "ISA#%d", isa);
- return s;
- }
-
- static const char *
- mips_cpu_to_str (cpu)
- int cpu;
- {
- const struct mips_cpu_info *ci;
- static char s[16];
-
- ci = mips_cpu_info_from_cpu (cpu);
- if (ci != NULL)
- return (ci->name);
-
- sprintf (s, "CPU#%d", cpu);
- return s;
- }
-
/* The default target format to use. */
const char *
--- 978,983 ----
*************** md_begin ()
*** 1177,1183 ****
if (strcmp (TARGET_OS, "elf") != 0)
flags |= SEC_ALLOC | SEC_LOAD;
! if (file_mips_abi != N64_ABI)
{
sec = subseg_new (".reginfo", (subsegT) 0);
--- 1153,1159 ----
if (strcmp (TARGET_OS, "elf") != 0)
flags |= SEC_ALLOC | SEC_LOAD;
! if (mips_abi != N64_ABI)
{
sec = subseg_new (".reginfo", (subsegT) 0);
*************** mips_ip (str, ip)
*** 7763,7773 ****
if (!insn_error)
{
static char buf[100];
! sprintf (buf,
! _("opcode not supported on this processor: %s (%s)"),
! mips_cpu_to_str (mips_arch),
! mips_isa_to_str (mips_opts.isa));
!
insn_error = buf;
}
if (save_c)
--- 7739,7753 ----
if (!insn_error)
{
static char buf[100];
! if (mips_arch_info->is_isa)
! sprintf (buf,
! _("opcode not supported at this ISA level (%s)"),
! mips_cpu_info_from_isa (mips_opts.isa)->name);
! else
! sprintf (buf,
! _("opcode not supported on this processor: %s (%s)"),
! mips_arch_info->name,
! mips_cpu_info_from_isa (mips_opts.isa)->name);
insn_error = buf;
}
if (save_c)
*************** struct option md_longopts[] =
*** 9892,9899 ****
{"march", required_argument, NULL, OPTION_MARCH},
#define OPTION_MTUNE (OPTION_MD_BASE + 22)
{"mtune", required_argument, NULL, OPTION_MTUNE},
! #define OPTION_MCPU (OPTION_MD_BASE + 23)
! {"mcpu", required_argument, NULL, OPTION_MCPU},
#define OPTION_M4650 (OPTION_MD_BASE + 24)
{"m4650", no_argument, NULL, OPTION_M4650},
#define OPTION_NO_M4650 (OPTION_MD_BASE + 25)
--- 9872,9879 ----
{"march", required_argument, NULL, OPTION_MARCH},
#define OPTION_MTUNE (OPTION_MD_BASE + 22)
{"mtune", required_argument, NULL, OPTION_MTUNE},
! #define OPTION_FP64 (OPTION_MD_BASE + 23)
! {"mfp64", no_argument, NULL, OPTION_FP64},
#define OPTION_M4650 (OPTION_MD_BASE + 24)
{"m4650", no_argument, NULL, OPTION_M4650},
#define OPTION_NO_M4650 (OPTION_MD_BASE + 25)
*************** struct option md_longopts[] =
*** 9946,9951 ****
--- 9926,9949 ----
};
size_t md_longopts_size = sizeof (md_longopts);
+ /* Set STRING_PTR (either &mips_arch_string or &mips_tune_string) to
+ NEW_VALUE. Warn if another value was already specified. Note:
+ we have to defer parsing the -march and -mtune arguments in order
+ to handle 'from-abi' correctly, since the ABI might be specified
+ in a later argument. */
+
+ static void
+ mips_set_option_string (string_ptr, new_value)
+ const char **string_ptr, *new_value;
+ {
+ if (*string_ptr != 0 && strcasecmp (*string_ptr, new_value) != 0)
+ as_warn (_("A different %s was already specified, is now %s"),
+ string_ptr == &mips_arch_string ? "-march" : "-mtune",
+ new_value);
+
+ *string_ptr = new_value;
+ }
+
int
md_parse_option (c, arg)
int c;
*************** md_parse_option (c, arg)
*** 10001,10130 ****
break;
case OPTION_MIPS1:
! mips_opts.isa = ISA_MIPS1;
break;
case OPTION_MIPS2:
! mips_opts.isa = ISA_MIPS2;
break;
case OPTION_MIPS3:
! mips_opts.isa = ISA_MIPS3;
break;
case OPTION_MIPS4:
! mips_opts.isa = ISA_MIPS4;
break;
case OPTION_MIPS5:
! mips_opts.isa = ISA_MIPS5;
break;
case OPTION_MIPS32:
! mips_opts.isa = ISA_MIPS32;
break;
case OPTION_MIPS64:
! mips_opts.isa = ISA_MIPS64;
break;
case OPTION_MTUNE:
! case OPTION_MARCH:
! case OPTION_MCPU:
! {
! int cpu = CPU_UNKNOWN;
!
! /* Identify the processor type. */
! if (strcasecmp (arg, "default") != 0)
! {
! const struct mips_cpu_info *ci;
!
! ci = mips_cpu_info_from_name (arg);
! if (ci == NULL || ci->is_isa)
! {
! switch (c)
! {
! case OPTION_MTUNE:
! as_fatal (_("invalid architecture -mtune=%s"), arg);
! break;
! case OPTION_MARCH:
! as_fatal (_("invalid architecture -march=%s"), arg);
! break;
! case OPTION_MCPU:
! as_fatal (_("invalid architecture -mcpu=%s"), arg);
! break;
! }
! }
! else
! cpu = ci->cpu;
! }
! switch (c)
! {
! case OPTION_MTUNE:
! if (mips_tune != CPU_UNKNOWN && mips_tune != cpu)
! as_warn (_("A different -mtune= was already specified, is now "
! "-mtune=%s"), arg);
! mips_tune = cpu;
! break;
! case OPTION_MARCH:
! if (mips_arch != CPU_UNKNOWN && mips_arch != cpu)
! as_warn (_("A different -march= was already specified, is now "
! "-march=%s"), arg);
! mips_arch = cpu;
! break;
! case OPTION_MCPU:
! if (mips_cpu != CPU_UNKNOWN && mips_cpu != cpu)
! as_warn (_("A different -mcpu= was already specified, is now "
! "-mcpu=%s"), arg);
! mips_cpu = cpu;
! }
! }
break;
case OPTION_M4650:
! if ((mips_arch != CPU_UNKNOWN && mips_arch != CPU_R4650)
! || (mips_tune != CPU_UNKNOWN && mips_tune != CPU_R4650))
! as_warn (_("A different -march= or -mtune= was already specified, "
! "is now -m4650"));
! mips_arch = CPU_R4650;
! mips_tune = CPU_R4650;
break;
case OPTION_NO_M4650:
break;
case OPTION_M4010:
! if ((mips_arch != CPU_UNKNOWN && mips_arch != CPU_R4010)
! || (mips_tune != CPU_UNKNOWN && mips_tune != CPU_R4010))
! as_warn (_("A different -march= or -mtune= was already specified, "
! "is now -m4010"));
! mips_arch = CPU_R4010;
! mips_tune = CPU_R4010;
break;
case OPTION_NO_M4010:
break;
case OPTION_M4100:
! if ((mips_arch != CPU_UNKNOWN && mips_arch != CPU_VR4100)
! || (mips_tune != CPU_UNKNOWN && mips_tune != CPU_VR4100))
! as_warn (_("A different -march= or -mtune= was already specified, "
! "is now -m4100"));
! mips_arch = CPU_VR4100;
! mips_tune = CPU_VR4100;
break;
case OPTION_NO_M4100:
break;
case OPTION_M3900:
! if ((mips_arch != CPU_UNKNOWN && mips_arch != CPU_R3900)
! || (mips_tune != CPU_UNKNOWN && mips_tune != CPU_R3900))
! as_warn (_("A different -march= or -mtune= was already specified, "
! "is now -m3900"));
! mips_arch = CPU_R3900;
! mips_tune = CPU_R3900;
break;
case OPTION_NO_M3900:
--- 9999,10066 ----
break;
case OPTION_MIPS1:
! file_mips_isa = ISA_MIPS1;
break;
case OPTION_MIPS2:
! file_mips_isa = ISA_MIPS2;
break;
case OPTION_MIPS3:
! file_mips_isa = ISA_MIPS3;
break;
case OPTION_MIPS4:
! file_mips_isa = ISA_MIPS4;
break;
case OPTION_MIPS5:
! file_mips_isa = ISA_MIPS5;
break;
case OPTION_MIPS32:
! file_mips_isa = ISA_MIPS32;
break;
case OPTION_MIPS64:
! file_mips_isa = ISA_MIPS64;
break;
case OPTION_MTUNE:
! mips_set_option_string (&mips_tune_string, arg);
! break;
! case OPTION_MARCH:
! mips_set_option_string (&mips_arch_string, arg);
break;
case OPTION_M4650:
! mips_set_option_string (&mips_arch_string, "4650");
! mips_set_option_string (&mips_tune_string, "4650");
break;
case OPTION_NO_M4650:
break;
case OPTION_M4010:
! mips_set_option_string (&mips_arch_string, "4010");
! mips_set_option_string (&mips_tune_string, "4010");
break;
case OPTION_NO_M4010:
break;
case OPTION_M4100:
! mips_set_option_string (&mips_arch_string, "4100");
! mips_set_option_string (&mips_tune_string, "4100");
break;
case OPTION_NO_M4100:
break;
case OPTION_M3900:
! mips_set_option_string (&mips_arch_string, "3900");
! mips_set_option_string (&mips_tune_string, "3900");
break;
case OPTION_NO_M3900:
*************** md_parse_option (c, arg)
*** 10227,10233 ****
as_bad (_("-32 is supported for ELF format only"));
return 0;
}
! mips_opts.abi = O32_ABI;
break;
case OPTION_N32:
--- 10163,10169 ----
as_bad (_("-32 is supported for ELF format only"));
return 0;
}
! mips_abi = O32_ABI;
break;
case OPTION_N32:
*************** md_parse_option (c, arg)
*** 10236,10242 ****
as_bad (_("-n32 is supported for ELF format only"));
return 0;
}
! mips_opts.abi = N32_ABI;
break;
case OPTION_64:
--- 10172,10178 ----
as_bad (_("-n32 is supported for ELF format only"));
return 0;
}
! mips_abi = N32_ABI;
break;
case OPTION_64:
*************** md_parse_option (c, arg)
*** 10245,10251 ****
as_bad (_("-64 is supported for ELF format only"));
return 0;
}
! mips_opts.abi = N64_ABI;
if (! support_64bit_objects())
as_fatal (_("No compiled in support for 64 bit object file format"));
break;
--- 10181,10187 ----
as_bad (_("-64 is supported for ELF format only"));
return 0;
}
! mips_abi = N64_ABI;
if (! support_64bit_objects())
as_fatal (_("No compiled in support for 64 bit object file format"));
break;
*************** md_parse_option (c, arg)
*** 10253,10272 ****
case OPTION_GP32:
file_mips_gp32 = 1;
- if (mips_opts.abi != O32_ABI)
- mips_opts.abi = NO_ABI;
break;
case OPTION_GP64:
file_mips_gp32 = 0;
- if (mips_opts.abi == O32_ABI)
- mips_opts.abi = NO_ABI;
break;
case OPTION_FP32:
file_mips_fp32 = 1;
! if (mips_opts.abi != O32_ABI)
! mips_opts.abi = NO_ABI;
break;
#ifdef OBJ_ELF
--- 10189,10206 ----
case OPTION_GP32:
file_mips_gp32 = 1;
break;
case OPTION_GP64:
file_mips_gp32 = 0;
break;
case OPTION_FP32:
file_mips_fp32 = 1;
! break;
!
! case OPTION_FP64:
! file_mips_fp32 = 0;
break;
#ifdef OBJ_ELF
*************** md_parse_option (c, arg)
*** 10277,10296 ****
return 0;
}
if (strcmp (arg, "32") == 0)
! mips_opts.abi = O32_ABI;
else if (strcmp (arg, "o64") == 0)
! mips_opts.abi = O64_ABI;
else if (strcmp (arg, "n32") == 0)
! mips_opts.abi = N32_ABI;
else if (strcmp (arg, "64") == 0)
{
! mips_opts.abi = N64_ABI;
if (! support_64bit_objects())
as_fatal (_("No compiled in support for 64 bit object file "
"format"));
}
else if (strcmp (arg, "eabi") == 0)
! mips_opts.abi = EABI_ABI;
else
{
as_fatal (_("invalid abi -mabi=%s"), arg);
--- 10211,10230 ----
return 0;
}
if (strcmp (arg, "32") == 0)
! mips_abi = O32_ABI;
else if (strcmp (arg, "o64") == 0)
! mips_abi = O64_ABI;
else if (strcmp (arg, "n32") == 0)
! mips_abi = N32_ABI;
else if (strcmp (arg, "64") == 0)
{
! mips_abi = N64_ABI;
if (! support_64bit_objects())
as_fatal (_("No compiled in support for 64 bit object file "
"format"));
}
else if (strcmp (arg, "eabi") == 0)
! mips_abi = EABI_ABI;
else
{
as_fatal (_("invalid abi -mabi=%s"), arg);
*************** md_parse_option (c, arg)
*** 10323,10466 ****
return 1;
}
static void
! show (stream, string, col_p, first_p)
! FILE *stream;
! char *string;
! int *col_p;
! int *first_p;
{
! if (*first_p)
! {
! fprintf (stream, "%24s", "");
! *col_p = 24;
! }
! else
! {
! fprintf (stream, ", ");
! *col_p += 2;
! }
!
! if (*col_p + strlen (string) > 72)
{
! fprintf (stream, "\n%24s", "");
! *col_p = 24;
}
-
- fprintf (stream, "%s", string);
- *col_p += strlen (string);
-
- *first_p = 0;
}
- void
- md_show_usage (stream)
- FILE *stream;
- {
- int column, first;
-
- fprintf (stream, _("\
- MIPS options:\n\
- -membedded-pic generate embedded position independent code\n\
- -EB generate big endian output\n\
- -EL generate little endian output\n\
- -g, -g2 do not remove unneeded NOPs or swap branches\n\
- -G NUM allow referencing objects up to NUM bytes\n\
- implicitly with the gp register [default 8]\n"));
- fprintf (stream, _("\
- -mips1 generate MIPS ISA I instructions\n\
- -mips2 generate MIPS ISA II instructions\n\
- -mips3 generate MIPS ISA III instructions\n\
- -mips4 generate MIPS ISA IV instructions\n\
- -mips5 generate MIPS ISA V instructions\n\
- -mips32 generate MIPS32 ISA instructions\n\
- -mips64 generate MIPS64 ISA instructions\n\
- -march=CPU/-mtune=CPU generate code/schedule for CPU, where CPU is one of:\n"));
-
- first = 1;
-
- show (stream, "2000", &column, &first);
- show (stream, "3000", &column, &first);
- show (stream, "3900", &column, &first);
- show (stream, "4000", &column, &first);
- show (stream, "4010", &column, &first);
- show (stream, "4100", &column, &first);
- show (stream, "4111", &column, &first);
- show (stream, "4300", &column, &first);
- show (stream, "4400", &column, &first);
- show (stream, "4600", &column, &first);
- show (stream, "4650", &column, &first);
- show (stream, "5000", &column, &first);
- show (stream, "5200", &column, &first);
- show (stream, "5230", &column, &first);
- show (stream, "5231", &column, &first);
- show (stream, "5261", &column, &first);
- show (stream, "5721", &column, &first);
- show (stream, "6000", &column, &first);
- show (stream, "8000", &column, &first);
- show (stream, "10000", &column, &first);
- show (stream, "12000", &column, &first);
- show (stream, "sb1", &column, &first);
- fputc ('\n', stream);
-
- fprintf (stream, _("\
- -mCPU equivalent to -march=CPU -mtune=CPU. Deprecated.\n\
- -no-mCPU don't generate code specific to CPU.\n\
- For -mCPU and -no-mCPU, CPU must be one of:\n"));
-
- first = 1;
-
- show (stream, "3900", &column, &first);
- show (stream, "4010", &column, &first);
- show (stream, "4100", &column, &first);
- show (stream, "4650", &column, &first);
- fputc ('\n', stream);
-
- fprintf (stream, _("\
- -mips16 generate mips16 instructions\n\
- -no-mips16 do not generate mips16 instructions\n"));
- fprintf (stream, _("\
- -mgp32 use 32-bit GPRs, regardless of the chosen ISA\n\
- -mfp32 use 32-bit FPRs, regardless of the chosen ISA\n\
- -O0 remove unneeded NOPs, do not swap branches\n\
- -O remove unneeded NOPs and swap branches\n\
- -n warn about NOPs generated from macros\n\
- --[no-]construct-floats [dis]allow floating point values to be constructed\n\
- --trap, --no-break trap exception on div by 0 and mult overflow\n\
- --break, --no-trap break exception on div by 0 and mult overflow\n"));
- #ifdef OBJ_ELF
- fprintf (stream, _("\
- -KPIC, -call_shared generate SVR4 position independent code\n\
- -non_shared do not generate position independent code\n\
- -xgot assume a 32 bit GOT\n\
- -mabi=ABI create ABI conformant object file for:\n"));
! first = 1;
! show (stream, "32", &column, &first);
! show (stream, "o64", &column, &first);
! show (stream, "n32", &column, &first);
! show (stream, "64", &column, &first);
! show (stream, "eabi", &column, &first);
- fputc ('\n', stream);
- fprintf (stream, _("\
- -32 create o32 ABI object file (default)\n\
- -n32 create n32 ABI object file\n\
- -64 create 64 ABI object file\n"));
- #endif
- }
-
void
mips_after_parse_args ()
{
- const char *cpu;
- char *a = NULL;
- int mips_isa_from_cpu;
- const struct mips_cpu_info *ci;
-
/* GP relative stuff not working for PE */
if (strncmp (TARGET_OS, "pe", 2) == 0
&& g_switch_value != 0)
--- 10257,10296 ----
return 1;
}
+
+ /* Set up globals to generate code for the ISA or processor
+ described by INFO. */
static void
! mips_set_architecture (info)
! const struct mips_cpu_info *info;
{
! if (info != 0)
{
! mips_arch_info = info;
! mips_arch = info->cpu;
! mips_opts.isa = info->isa;
}
}
! /* Likewise for tuning. */
! static void
! mips_set_tune (info)
! const struct mips_cpu_info *info;
! {
! if (info != 0)
! {
! mips_tune_info = info;
! mips_tune = info->cpu;
! }
! }
void
mips_after_parse_args ()
{
/* GP relative stuff not working for PE */
if (strncmp (TARGET_OS, "pe", 2) == 0
&& g_switch_value != 0)
*************** mips_after_parse_args ()
*** 10470,10653 ****
g_switch_value = 0;
}
! cpu = TARGET_CPU;
! if (strcmp (cpu + (sizeof TARGET_CPU) - 3, "el") == 0)
! {
! a = xmalloc (sizeof TARGET_CPU);
! strcpy (a, TARGET_CPU);
! a[(sizeof TARGET_CPU) - 3] = '\0';
! cpu = a;
! }
! /* Backward compatibility for historic -mcpu= option. Check for
! incompatible options, warn if -mcpu is used. */
! if (mips_cpu != CPU_UNKNOWN
! && mips_arch != CPU_UNKNOWN
! && mips_cpu != mips_arch)
! {
! as_fatal (_("The -mcpu option can't be used together with -march. "
! "Use -mtune instead of -mcpu."));
! }
! if (mips_cpu != CPU_UNKNOWN
! && mips_tune != CPU_UNKNOWN
! && mips_cpu != mips_tune)
! {
! as_fatal (_("The -mcpu option can't be used together with -mtune. "
! "Use -march instead of -mcpu."));
! }
! #if 1
! /* For backward compatibility, let -mipsN set various defaults. */
! /* This code should go away, to be replaced with something rather more
! draconian. Until GCC 3.1 has been released for some reasonable
! amount of time, however, we need to support this. */
! if (mips_opts.isa != ISA_UNKNOWN)
{
! /* Translate -mipsN to the appropriate settings of file_mips_gp32
! and file_mips_fp32. Tag binaries as using the mipsN ISA. */
! if (file_mips_gp32 < 0)
! {
! if (ISA_HAS_64BIT_REGS (mips_opts.isa))
! file_mips_gp32 = 0;
! else
! file_mips_gp32 = 1;
! }
! if (file_mips_fp32 < 0)
! {
! if (ISA_HAS_64BIT_REGS (mips_opts.isa))
! file_mips_fp32 = 0;
! else
! file_mips_fp32 = 1;
! }
!
! ci = mips_cpu_info_from_isa (mips_opts.isa);
! assert (ci != NULL);
! /* -mipsN has higher priority than -mcpu but lower than -march. */
! if (mips_arch == CPU_UNKNOWN)
! mips_arch = ci->cpu;
!
! /* Default mips_abi. */
! if (mips_opts.abi == NO_ABI)
{
! if (mips_opts.isa == ISA_MIPS1 || mips_opts.isa == ISA_MIPS2)
! mips_opts.abi = O32_ABI;
! else if (mips_opts.isa == ISA_MIPS3 || mips_opts.isa == ISA_MIPS4)
! mips_opts.abi = O64_ABI;
}
}
! if (mips_arch == CPU_UNKNOWN && mips_cpu != CPU_UNKNOWN)
! {
! ci = mips_cpu_info_from_cpu (mips_cpu);
! assert (ci != NULL);
! mips_arch = ci->cpu;
! as_warn (_("The -mcpu option is deprecated. Please use -march and "
! "-mtune instead."));
! }
!
! /* Set tune from -mcpu, not from -mipsN. */
! if (mips_tune == CPU_UNKNOWN && mips_cpu != CPU_UNKNOWN)
! {
! ci = mips_cpu_info_from_cpu (mips_cpu);
! assert (ci != NULL);
! mips_tune = ci->cpu;
! }
!
! /* At this point, mips_arch will either be CPU_UNKNOWN if no ARCH was
! specified on the command line, or some other value if one was.
! Similarly, mips_opts.isa will be ISA_UNKNOWN if not specified on
! the command line, or will be set otherwise if one was. */
! if (mips_arch != CPU_UNKNOWN && mips_opts.isa != ISA_UNKNOWN)
! /* Handled above. */;
! #else
! if (mips_arch == CPU_UNKNOWN && mips_cpu != CPU_UNKNOWN)
! {
! ci = mips_cpu_info_from_cpu (mips_cpu);
! assert (ci != NULL);
! mips_arch = ci->cpu;
! as_warn (_("The -mcpu option is deprecated. Please use -march and "
! "-mtune instead."));
! }
! /* At this point, mips_arch will either be CPU_UNKNOWN if no ARCH was
! specified on the command line, or some other value if one was.
! Similarly, mips_opts.isa will be ISA_UNKNOWN if not specified on
! the command line, or will be set otherwise if one was. */
! if (mips_arch != CPU_UNKNOWN && mips_opts.isa != ISA_UNKNOWN)
! {
! /* We have to check if the isa is the default isa of arch. Otherwise
! we'll get invalid object file headers. */
! ci = mips_cpu_info_from_cpu (mips_arch);
! assert (ci != NULL);
! if (mips_opts.isa != ci->isa)
! {
! /* This really should be an error instead of a warning, but old
! compilers only have -mcpu which sets both arch and tune. For
! now, we discard arch and preserve tune. */
! as_warn (_("The -march option is incompatible to -mipsN and "
! "therefore ignored."));
! if (mips_tune == CPU_UNKNOWN)
! mips_tune = mips_arch;
! ci = mips_cpu_info_from_isa (mips_opts.isa);
! assert (ci != NULL);
! mips_arch = ci->cpu;
! }
! }
! #endif
! else if (mips_arch != CPU_UNKNOWN && mips_opts.isa == ISA_UNKNOWN)
! {
! /* We have ARCH, we need ISA. */
! ci = mips_cpu_info_from_cpu (mips_arch);
! assert (ci != NULL);
! mips_opts.isa = ci->isa;
! }
! else if (mips_arch == CPU_UNKNOWN && mips_opts.isa != ISA_UNKNOWN)
{
! /* We have ISA, we need default ARCH. */
! ci = mips_cpu_info_from_isa (mips_opts.isa);
! assert (ci != NULL);
! mips_arch = ci->cpu;
}
else
{
! /* We need to set both ISA and ARCH from target cpu. */
! ci = mips_cpu_info_from_name (cpu);
! if (ci == NULL)
! ci = mips_cpu_info_from_cpu (CPU_R3000);
! assert (ci != NULL);
! mips_opts.isa = ci->isa;
! mips_arch = ci->cpu;
}
! if (mips_tune == CPU_UNKNOWN)
! mips_tune = mips_arch;
! ci = mips_cpu_info_from_cpu (mips_arch);
! assert (ci != NULL);
! mips_isa_from_cpu = ci->isa;
! /* End of TARGET_CPU processing, get rid of malloced memory
! if necessary. */
! cpu = NULL;
! if (a != NULL)
! {
! free (a);
! a = NULL;
! }
if (mips_opts.isa == ISA_MIPS1 && mips_trap)
as_bad (_("trap exception not supported at ISA 1"));
- /* If they asked for mips1 or mips2 and a cpu that is
- mips3 or greater, then mark the object file 32BITMODE. */
- if (mips_isa_from_cpu != ISA_UNKNOWN
- && ! ISA_HAS_64BIT_REGS (mips_opts.isa)
- && ISA_HAS_64BIT_REGS (mips_isa_from_cpu))
- mips_32bitmode = 1;
-
/* If the selected architecture includes support for ASEs, enable
generation of code for them. */
if (mips_opts.mips16 == -1)
--- 10300,10387 ----
g_switch_value = 0;
}
! /* The following code determines the architecture and register size.
! Similar code was added to GCC 3.2 (see override_options() in
! config/mips/mips.c). The GAS and GCC code should be kept in
! sync as much as possible. */
! if (mips_arch_string != 0)
! mips_set_architecture (mips_parse_cpu ("-march", mips_arch_string));
! if (mips_tune_string != 0)
! mips_set_tune (mips_parse_cpu ("-mtune", mips_tune_string));
! if (file_mips_isa != ISA_UNKNOWN)
{
! /* Handle -mipsN. At this point, file_mips_isa contains the
! ISA level specified by -mipsN, while mips_opts.isa contains
! the -march selection (if any). */
! if (mips_arch_info != 0)
{
! /* -march takes precedence over -mipsN, since it is more descriptive.
! There's no harm in specifying both as long as the ISA levels
! are the same. */
! if (file_mips_isa != mips_opts.isa)
! as_bad (_("-%s conflicts with the other architecture options, which imply -%s"),
! mips_cpu_info_from_isa (file_mips_isa)->name,
! mips_cpu_info_from_isa (mips_opts.isa)->name);
}
+ else
+ mips_set_architecture (mips_cpu_info_from_isa (file_mips_isa));
}
! if (mips_arch_info == 0)
! mips_set_architecture (mips_parse_cpu ("default CPU",
! MIPS_CPU_STRING_DEFAULT));
! if (ABI_NEEDS_64BIT_REGS (mips_abi) && !ISA_HAS_64BIT_REGS (mips_opts.isa))
! as_bad ("-march=%s is not compatible with the selected ABI",
! mips_arch_info->name);
! /* Optimize for mips_arch, unless -mtune selects a different processor. */
! if (mips_tune_info == 0)
! mips_set_tune (mips_arch_info);
! if (file_mips_gp32 >= 0)
{
! /* The user specified the size of the integer registers. Make sure
! it agrees with the ABI and ISA. */
! if (file_mips_gp32 == 0 && !ISA_HAS_64BIT_REGS (mips_opts.isa))
! as_bad (_("-mgp64 used with a 32-bit processor"));
! else if (file_mips_gp32 == 1 && ABI_NEEDS_64BIT_REGS (mips_abi))
! as_bad (_("-mgp32 used with a 64-bit ABI"));
! else if (file_mips_gp32 == 0 && ABI_NEEDS_32BIT_REGS (mips_abi))
! as_bad (_("-mgp64 used with a 32-bit ABI"));
}
else
{
! /* Infer the integer register size from the ABI and processor.
! Restrict ourselves to 32-bit registers if that's all the
! processor has, or if the ABI cannot handle 64-bit registers. */
! file_mips_gp32 = (ABI_NEEDS_32BIT_REGS (mips_abi)
! || !ISA_HAS_64BIT_REGS (mips_opts.isa));
}
! /* ??? GAS treats single-float processors as though they had 64-bit
! float registers (although it complains when double-precision
! instructions are used). As things stand, saying they have 32-bit
! registers would lead to spurious "register must be even" messages.
! So here we assume float registers are always the same size as
! integer ones, unless the user says otherwise. */
! if (file_mips_fp32 < 0)
! file_mips_fp32 = file_mips_gp32;
! /* End of GCC-shared inference code. */
! /* ??? When do we want this flag to be set? Who uses it? */
! if (file_mips_gp32 == 1
! && mips_abi == NO_ABI
! && ISA_HAS_64BIT_REGS (mips_opts.isa))
! mips_32bitmode = 1;
if (mips_opts.isa == ISA_MIPS1 && mips_trap)
as_bad (_("trap exception not supported at ISA 1"));
/* If the selected architecture includes support for ASEs, enable
generation of code for them. */
if (mips_opts.mips16 == -1)
*************** mips_after_parse_args ()
*** 10657,10669 ****
if (mips_opts.ase_mdmx == -1)
mips_opts.ase_mdmx = (CPU_HAS_MDMX (mips_arch)) ? 1 : 0;
- if (file_mips_gp32 < 0)
- file_mips_gp32 = 0;
- if (file_mips_fp32 < 0)
- file_mips_fp32 = 0;
-
file_mips_isa = mips_opts.isa;
- file_mips_abi = mips_opts.abi;
file_ase_mips16 = mips_opts.mips16;
file_ase_mips3d = mips_opts.ase_mips3d;
file_ase_mdmx = mips_opts.ase_mdmx;
--- 10391,10397 ----
*************** s_mipsset (x)
*** 11738,11744 ****
case 0:
mips_opts.gp32 = file_mips_gp32;
mips_opts.fp32 = file_mips_fp32;
- mips_opts.abi = file_mips_abi;
break;
case 1:
case 2:
--- 11466,11471 ----
*************** s_mipsset (x)
*** 11750,11758 ****
case 4:
case 5:
case 64:
- /* Loosen ABI register width restriction. */
- if (mips_opts.abi == O32_ABI)
- mips_opts.abi = NO_ABI;
mips_opts.gp32 = 0;
mips_opts.fp32 = 0;
break;
--- 11477,11482 ----
*************** void
*** 13201,13207 ****
mips_elf_final_processing ()
{
/* Write out the register information. */
! if (file_mips_abi != N64_ABI)
{
Elf32_RegInfo s;
--- 12925,12931 ----
mips_elf_final_processing ()
{
/* Write out the register information. */
! if (mips_abi != N64_ABI)
{
Elf32_RegInfo s;
*************** mips_elf_final_processing ()
*** 13251,13272 ****
elf_elfheader (stdoutput)->e_flags |= EF_MIPS_ARCH_ASE_MDMX;
/* Set the MIPS ELF ABI flags. */
! if (file_mips_abi == NO_ABI)
! ;
! else if (file_mips_abi == O32_ABI)
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_O32;
! else if (file_mips_abi == O64_ABI)
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_O64;
! else if (file_mips_abi == EABI_ABI)
{
! /* Set the EABI kind based on the ISA. This isn't really
! the best, but then neither is basing the abi on the isa. */
! if (ISA_HAS_64BIT_REGS (file_mips_isa))
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_EABI64;
else
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_EABI32;
}
! else if (file_mips_abi == N32_ABI)
elf_elfheader (stdoutput)->e_flags |= EF_MIPS_ABI2;
/* Nothing to do for N64_ABI. */
--- 12975,12992 ----
elf_elfheader (stdoutput)->e_flags |= EF_MIPS_ARCH_ASE_MDMX;
/* Set the MIPS ELF ABI flags. */
! if (mips_abi == O32_ABI && USE_E_MIPS_ABI_O32)
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_O32;
! else if (mips_abi == O64_ABI)
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_O64;
! else if (mips_abi == EABI_ABI)
{
! if (!file_mips_gp32)
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_EABI64;
else
elf_elfheader (stdoutput)->e_flags |= E_MIPS_ABI_EABI32;
}
! else if (mips_abi == N32_ABI)
elf_elfheader (stdoutput)->e_flags |= EF_MIPS_ABI2;
/* Nothing to do for N64_ABI. */
*************** s_loc (x)
*** 13707,13882 ****
}
#endif
! /* CPU name/ISA/number mapping table.
!
! Entries are grouped by type. The first matching CPU or ISA entry
! gets chosen by CPU or ISA, so it should be the 'canonical' name
! for that type. Entries after that within the type are sorted
! alphabetically.
! Case is ignored in comparison, so put the canonical entry in the
! appropriate case but everything else in lower case to ease eye pain. */
static const struct mips_cpu_info mips_cpu_info_table[] =
{
! /* MIPS1 ISA */
! { "MIPS1", 1, ISA_MIPS1, CPU_R3000, },
! { "mips", 1, ISA_MIPS1, CPU_R3000, },
! /* MIPS2 ISA */
! { "MIPS2", 1, ISA_MIPS2, CPU_R6000, },
! /* MIPS3 ISA */
! { "MIPS3", 1, ISA_MIPS3, CPU_R4000, },
! /* MIPS4 ISA */
! { "MIPS4", 1, ISA_MIPS4, CPU_R8000, },
! /* MIPS5 ISA */
! { "MIPS5", 1, ISA_MIPS5, CPU_MIPS5, },
! { "Generic-MIPS5", 0, ISA_MIPS5, CPU_MIPS5, },
! /* MIPS32 ISA */
! { "MIPS32", 1, ISA_MIPS32, CPU_MIPS32, },
! { "mipsisa32", 0, ISA_MIPS32, CPU_MIPS32, },
! { "Generic-MIPS32", 0, ISA_MIPS32, CPU_MIPS32, },
{ "4kc", 0, ISA_MIPS32, CPU_MIPS32, },
! { "4km", 0, ISA_MIPS32, CPU_MIPS32, },
! { "4kp", 0, ISA_MIPS32, CPU_MIPS32, },
!
! /* For historical reasons. */
! { "MIPS64", 1, ISA_MIPS3, CPU_R4000, },
! /* MIPS64 ISA */
! { "mipsisa64", 1, ISA_MIPS64, CPU_MIPS64, },
! { "Generic-MIPS64", 0, ISA_MIPS64, CPU_MIPS64, },
! { "5kc", 0, ISA_MIPS64, CPU_MIPS64, },
! { "20kc", 0, ISA_MIPS64, CPU_MIPS64, },
! /* R2000 CPU */
! { "R2000", 0, ISA_MIPS1, CPU_R2000, },
! { "2000", 0, ISA_MIPS1, CPU_R2000, },
! { "2k", 0, ISA_MIPS1, CPU_R2000, },
! { "r2k", 0, ISA_MIPS1, CPU_R2000, },
! /* R3000 CPU */
! { "R3000", 0, ISA_MIPS1, CPU_R3000, },
! { "3000", 0, ISA_MIPS1, CPU_R3000, },
! { "3k", 0, ISA_MIPS1, CPU_R3000, },
! { "r3k", 0, ISA_MIPS1, CPU_R3000, },
- /* TX3900 CPU */
- { "R3900", 0, ISA_MIPS1, CPU_R3900, },
- { "3900", 0, ISA_MIPS1, CPU_R3900, },
- { "mipstx39", 0, ISA_MIPS1, CPU_R3900, },
! /* R4000 CPU */
! { "R4000", 0, ISA_MIPS3, CPU_R4000, },
! { "4000", 0, ISA_MIPS3, CPU_R4000, },
! { "4k", 0, ISA_MIPS3, CPU_R4000, }, /* beware */
! { "r4k", 0, ISA_MIPS3, CPU_R4000, },
! /* R4010 CPU */
! { "R4010", 0, ISA_MIPS2, CPU_R4010, },
! { "4010", 0, ISA_MIPS2, CPU_R4010, },
! /* R4400 CPU */
! { "R4400", 0, ISA_MIPS3, CPU_R4400, },
! { "4400", 0, ISA_MIPS3, CPU_R4400, },
! /* R4600 CPU */
! { "R4600", 0, ISA_MIPS3, CPU_R4600, },
! { "4600", 0, ISA_MIPS3, CPU_R4600, },
! { "mips64orion", 0, ISA_MIPS3, CPU_R4600, },
! { "orion", 0, ISA_MIPS3, CPU_R4600, },
- /* R4650 CPU */
- { "R4650", 0, ISA_MIPS3, CPU_R4650, },
- { "4650", 0, ISA_MIPS3, CPU_R4650, },
! /* R6000 CPU */
! { "R6000", 0, ISA_MIPS2, CPU_R6000, },
! { "6000", 0, ISA_MIPS2, CPU_R6000, },
! { "6k", 0, ISA_MIPS2, CPU_R6000, },
! { "r6k", 0, ISA_MIPS2, CPU_R6000, },
! /* R8000 CPU */
! { "R8000", 0, ISA_MIPS4, CPU_R8000, },
! { "8000", 0, ISA_MIPS4, CPU_R8000, },
! { "8k", 0, ISA_MIPS4, CPU_R8000, },
! { "r8k", 0, ISA_MIPS4, CPU_R8000, },
! /* R10000 CPU */
! { "R10000", 0, ISA_MIPS4, CPU_R10000, },
! { "10000", 0, ISA_MIPS4, CPU_R10000, },
! { "10k", 0, ISA_MIPS4, CPU_R10000, },
! { "r10k", 0, ISA_MIPS4, CPU_R10000, },
! /* R12000 CPU */
! { "R12000", 0, ISA_MIPS4, CPU_R12000, },
! { "12000", 0, ISA_MIPS4, CPU_R12000, },
! { "12k", 0, ISA_MIPS4, CPU_R12000, },
! { "r12k", 0, ISA_MIPS4, CPU_R12000, },
! /* VR4100 CPU */
! { "VR4100", 0, ISA_MIPS3, CPU_VR4100, },
! { "4100", 0, ISA_MIPS3, CPU_VR4100, },
! { "mips64vr4100", 0, ISA_MIPS3, CPU_VR4100, },
! { "r4100", 0, ISA_MIPS3, CPU_VR4100, },
! /* VR4111 CPU */
! { "VR4111", 0, ISA_MIPS3, CPU_R4111, },
! { "4111", 0, ISA_MIPS3, CPU_R4111, },
! { "mips64vr4111", 0, ISA_MIPS3, CPU_R4111, },
! { "r4111", 0, ISA_MIPS3, CPU_R4111, },
- /* VR4300 CPU */
- { "VR4300", 0, ISA_MIPS3, CPU_R4300, },
- { "4300", 0, ISA_MIPS3, CPU_R4300, },
- { "mips64vr4300", 0, ISA_MIPS3, CPU_R4300, },
- { "r4300", 0, ISA_MIPS3, CPU_R4300, },
! /* VR5000 CPU */
! { "VR5000", 0, ISA_MIPS4, CPU_R5000, },
! { "5000", 0, ISA_MIPS4, CPU_R5000, },
! { "5k", 0, ISA_MIPS4, CPU_R5000, },
! { "mips64vr5000", 0, ISA_MIPS4, CPU_R5000, },
! { "r5000", 0, ISA_MIPS4, CPU_R5000, },
! { "r5200", 0, ISA_MIPS4, CPU_R5000, },
! { "rm5200", 0, ISA_MIPS4, CPU_R5000, },
! { "r5230", 0, ISA_MIPS4, CPU_R5000, },
! { "rm5230", 0, ISA_MIPS4, CPU_R5000, },
! { "r5231", 0, ISA_MIPS4, CPU_R5000, },
! { "rm5231", 0, ISA_MIPS4, CPU_R5000, },
! { "r5261", 0, ISA_MIPS4, CPU_R5000, },
! { "rm5261", 0, ISA_MIPS4, CPU_R5000, },
! { "r5721", 0, ISA_MIPS4, CPU_R5000, },
! { "rm5721", 0, ISA_MIPS4, CPU_R5000, },
! { "r5k", 0, ISA_MIPS4, CPU_R5000, },
! { "r7000", 0, ISA_MIPS4, CPU_R5000, },
!
! /* Broadcom SB-1 CPU */
! { "SB-1", 0, ISA_MIPS64, CPU_SB1, },
! { "sb-1250", 0, ISA_MIPS64, CPU_SB1, },
! { "sb1", 0, ISA_MIPS64, CPU_SB1, },
! { "sb1250", 0, ISA_MIPS64, CPU_SB1, },
! /* End marker. */
! { NULL, 0, 0, 0, },
! };
static const struct mips_cpu_info *
! mips_cpu_info_from_name (name)
! const char *name;
{
! int i;
! for (i = 0; mips_cpu_info_table[i].name != NULL; i++)
! if (strcasecmp (name, mips_cpu_info_table[i].name) == 0)
! return (&mips_cpu_info_table[i]);
! return NULL;
}
static const struct mips_cpu_info *
mips_cpu_info_from_isa (isa)
int isa;
--- 13427,13604 ----
}
#endif
! /* A table describing all the processors gas knows about. Names are
! matched in the order listed.
! To ease comparison, please keep this table in the same order as
! gcc's mips_cpu_info_table[]. */
static const struct mips_cpu_info mips_cpu_info_table[] =
{
! /* Entries for generic ISAs */
! { "mips1", 1, ISA_MIPS1, CPU_R3000 },
! { "mips2", 1, ISA_MIPS2, CPU_R6000 },
! { "mips3", 1, ISA_MIPS3, CPU_R4000 },
! { "mips4", 1, ISA_MIPS4, CPU_R8000 },
! { "mips5", 1, ISA_MIPS5, CPU_MIPS5 },
! { "mips32", 1, ISA_MIPS32, CPU_MIPS32 },
! { "mips64", 1, ISA_MIPS64, CPU_MIPS64 },
! /* MIPS I */
! { "r3000", 0, ISA_MIPS1, CPU_R3000 },
! { "r2000", 0, ISA_MIPS1, CPU_R3000 },
! { "r3900", 0, ISA_MIPS1, CPU_R3900 },
! /* MIPS II */
! { "r6000", 0, ISA_MIPS2, CPU_R6000 },
! /* MIPS III */
! { "r4000", 0, ISA_MIPS3, CPU_R4000 },
! { "r4010", 0, ISA_MIPS2, CPU_R4010 },
! { "vr4100", 0, ISA_MIPS3, CPU_VR4100 },
! { "vr4111", 0, ISA_MIPS3, CPU_R4111 },
! { "vr4300", 0, ISA_MIPS3, CPU_R4300 },
! { "r4400", 0, ISA_MIPS3, CPU_R4400 },
! { "r4600", 0, ISA_MIPS3, CPU_R4600 },
! { "orion", 0, ISA_MIPS3, CPU_R4600 },
! { "r4650", 0, ISA_MIPS3, CPU_R4650 },
! /* MIPS IV */
! { "r8000", 0, ISA_MIPS4, CPU_R8000 },
! { "r10000", 0, ISA_MIPS4, CPU_R10000 },
! { "r12000", 0, ISA_MIPS4, CPU_R12000 },
! { "vr5000", 0, ISA_MIPS4, CPU_R5000 },
! { "rm5200", 0, ISA_MIPS4, CPU_R5000 },
! { "rm5230", 0, ISA_MIPS4, CPU_R5000 },
! { "rm5231", 0, ISA_MIPS4, CPU_R5000 },
! { "rm5261", 0, ISA_MIPS4, CPU_R5000 },
! { "rm5721", 0, ISA_MIPS4, CPU_R5000 },
! { "r7000", 0, ISA_MIPS4, CPU_R5000 },
! /* MIPS 32 */
{ "4kc", 0, ISA_MIPS32, CPU_MIPS32, },
! { "4km", 0, ISA_MIPS32, CPU_MIPS32 },
! { "4kp", 0, ISA_MIPS32, CPU_MIPS32 },
! /* MIPS 64 */
! { "5kc", 0, ISA_MIPS64, CPU_MIPS64 },
! { "20kc", 0, ISA_MIPS64, CPU_MIPS64 },
! /* Broadcom SB-1 CPU */
! { "SB-1", 0, ISA_MIPS64, CPU_SB1 },
! { "sb-1250", 0, ISA_MIPS64, CPU_SB1 },
! { "sb1", 0, ISA_MIPS64, CPU_SB1 },
! { "sb1250", 0, ISA_MIPS64, CPU_SB1 },
! /* End marker */
! { NULL, 0, 0, 0 }
! };
! /* Return true if GIVEN is the same as CANONICAL, or if it is CANONICAL
! with a final "000" replaced by "k". Ignore case.
! Note: this function is shared between GCC and GAS. */
! static boolean
! mips_strict_matching_cpu_name_p (canonical, given)
! const char *canonical, *given;
! {
! while (*given != 0 && TOLOWER (*given) == TOLOWER (*canonical))
! given++, canonical++;
! return ((*given == 0 && *canonical == 0)
! || (strcmp (canonical, "000") == 0 && strcasecmp (given, "k") == 0));
! }
! /* Return true if GIVEN matches CANONICAL, where GIVEN is a user-supplied
! CPU name. We've traditionally allowed a lot of variation here.
! Note: this function is shared between GCC and GAS. */
! static boolean
! mips_matching_cpu_name_p (canonical, given)
! const char *canonical, *given;
! {
! /* First see if the name matches exactly, or with a final "000"
! turned into "k". */
! if (mips_strict_matching_cpu_name_p (canonical, given))
! return true;
! /* If not, try comparing based on numerical designation alone.
! See if GIVEN is an unadorned number, or 'r' followed by a number. */
! if (TOLOWER (*given) == 'r')
! given++;
! if (!ISDIGIT (*given))
! return false;
! /* Skip over some well-known prefixes in the canonical name,
! hoping to find a number there too. */
! if (TOLOWER (canonical[0]) == 'v' && TOLOWER (canonical[1]) == 'r')
! canonical += 2;
! else if (TOLOWER (canonical[0]) == 'r' && TOLOWER (canonical[1]) == 'm')
! canonical += 2;
! else if (TOLOWER (canonical[0]) == 'r')
! canonical += 1;
! return mips_strict_matching_cpu_name_p (canonical, given);
! }
! /* Parse an option that takes the name of a processor as its argument.
! OPTION is the name of the option and CPU_STRING is the argument.
! Return the corresponding processor enumeration if the CPU_STRING is
! recognized, otherwise report an error and return null.
! A similar function exists in GCC. */
static const struct mips_cpu_info *
! mips_parse_cpu (option, cpu_string)
! const char *option, *cpu_string;
{
! const struct mips_cpu_info *p;
! /* 'from-abi' selects the most compatible architecture for the given
! ABI: MIPS I for 32-bit ABIs and MIPS III for 64-bit ABIs. For the
! EABIs, we have to decide whether we're using the 32-bit or 64-bit
! version. Look first at the -mgp options, if given, otherwise base
! the choice on MIPS_DEFAULT_64BIT.
! Treat NO_ABI like the EABIs. One reason to do this is that the
! plain 'mips' and 'mips64' configs have 'from-abi' as their default
! architecture. This code picks MIPS I for 'mips' and MIPS III for
! 'mips64', just as we did in the days before 'from-abi'. */
! if (strcasecmp (cpu_string, "from-abi") == 0)
! {
! if (ABI_NEEDS_32BIT_REGS (mips_abi))
! return mips_cpu_info_from_isa (ISA_MIPS1);
!
! if (ABI_NEEDS_64BIT_REGS (mips_abi))
! return mips_cpu_info_from_isa (ISA_MIPS3);
!
! if (file_mips_gp32 >= 0)
! return mips_cpu_info_from_isa (file_mips_gp32 ? ISA_MIPS1 : ISA_MIPS3);
!
! return mips_cpu_info_from_isa (MIPS_DEFAULT_64BIT
! ? ISA_MIPS3
! : ISA_MIPS1);
! }
!
! /* 'default' has traditionally been a no-op. Probably not very useful. */
! if (strcasecmp (cpu_string, "default") == 0)
! return 0;
!
! for (p = mips_cpu_info_table; p->name != 0; p++)
! if (mips_matching_cpu_name_p (p->name, cpu_string))
! return p;
!
! as_bad ("Bad value (%s) for %s", cpu_string, option);
! return 0;
}
+ /* Return the canonical processor information for ISA (a member of the
+ ISA_MIPS* enumeration). */
+
static const struct mips_cpu_info *
mips_cpu_info_from_isa (isa)
int isa;
*************** mips_cpu_info_from_isa (isa)
*** 13885,13906 ****
for (i = 0; mips_cpu_info_table[i].name != NULL; i++)
if (mips_cpu_info_table[i].is_isa
! && isa == mips_cpu_info_table[i].isa)
return (&mips_cpu_info_table[i]);
return NULL;
}
! static const struct mips_cpu_info *
! mips_cpu_info_from_cpu (cpu)
! int cpu;
{
! int i;
for (i = 0; mips_cpu_info_table[i].name != NULL; i++)
! if (!mips_cpu_info_table[i].is_isa
! && cpu == mips_cpu_info_table[i].cpu)
! return (&mips_cpu_info_table[i]);
! return NULL;
}
--- 13607,13725 ----
for (i = 0; mips_cpu_info_table[i].name != NULL; i++)
if (mips_cpu_info_table[i].is_isa
! && isa == mips_cpu_info_table[i].isa)
return (&mips_cpu_info_table[i]);
return NULL;
}
+
+ static void
+ show (stream, string, col_p, first_p)
+ FILE *stream;
+ const char *string;
+ int *col_p;
+ int *first_p;
+ {
+ if (*first_p)
+ {
+ fprintf (stream, "%24s", "");
+ *col_p = 24;
+ }
+ else
+ {
+ fprintf (stream, ", ");
+ *col_p += 2;
+ }
+
+ if (*col_p + strlen (string) > 72)
+ {
+ fprintf (stream, "\n%24s", "");
+ *col_p = 24;
+ }
+
+ fprintf (stream, "%s", string);
+ *col_p += strlen (string);
+
+ *first_p = 0;
+ }
! void
! md_show_usage (stream)
! FILE *stream;
{
! int column, first;
! size_t i;
!
! fprintf (stream, _("\
! MIPS options:\n\
! -membedded-pic generate embedded position independent code\n\
! -EB generate big endian output\n\
! -EL generate little endian output\n\
! -g, -g2 do not remove unneeded NOPs or swap branches\n\
! -G NUM allow referencing objects up to NUM bytes\n\
! implicitly with the gp register [default 8]\n"));
! fprintf (stream, _("\
! -mips1 generate MIPS ISA I instructions\n\
! -mips2 generate MIPS ISA II instructions\n\
! -mips3 generate MIPS ISA III instructions\n\
! -mips4 generate MIPS ISA IV instructions\n\
! -mips5 generate MIPS ISA V instructions\n\
! -mips32 generate MIPS32 ISA instructions\n\
! -mips64 generate MIPS64 ISA instructions\n\
! -march=CPU/-mtune=CPU generate code/schedule for CPU, where CPU is one of:\n"));
!
! first = 1;
for (i = 0; mips_cpu_info_table[i].name != NULL; i++)
! show (stream, mips_cpu_info_table[i].name, &column, &first);
! show (stream, "from-abi", &column, &first);
! fputc ('\n', stream);
! fprintf (stream, _("\
! -mCPU equivalent to -march=CPU -mtune=CPU. Deprecated.\n\
! -no-mCPU don't generate code specific to CPU.\n\
! For -mCPU and -no-mCPU, CPU must be one of:\n"));
!
! first = 1;
!
! show (stream, "3900", &column, &first);
! show (stream, "4010", &column, &first);
! show (stream, "4100", &column, &first);
! show (stream, "4650", &column, &first);
! fputc ('\n', stream);
!
! fprintf (stream, _("\
! -mips16 generate mips16 instructions\n\
! -no-mips16 do not generate mips16 instructions\n"));
! fprintf (stream, _("\
! -mgp32 use 32-bit GPRs, regardless of the chosen ISA\n\
! -mfp32 use 32-bit FPRs, regardless of the chosen ISA\n\
! -O0 remove unneeded NOPs, do not swap branches\n\
! -O remove unneeded NOPs and swap branches\n\
! -n warn about NOPs generated from macros\n\
! --[no-]construct-floats [dis]allow floating point values to be constructed\n\
! --trap, --no-break trap exception on div by 0 and mult overflow\n\
! --break, --no-trap break exception on div by 0 and mult overflow\n"));
! #ifdef OBJ_ELF
! fprintf (stream, _("\
! -KPIC, -call_shared generate SVR4 position independent code\n\
! -non_shared do not generate position independent code\n\
! -xgot assume a 32 bit GOT\n\
! -mabi=ABI create ABI conformant object file for:\n"));
!
! first = 1;
!
! show (stream, "32", &column, &first);
! show (stream, "o64", &column, &first);
! show (stream, "n32", &column, &first);
! show (stream, "64", &column, &first);
! show (stream, "eabi", &column, &first);
!
! fputc ('\n', stream);
!
! fprintf (stream, _("\
! -32 create o32 ABI object file (default)\n\
! -n32 create n32 ABI object file\n\
! -64 create 64 ABI object file\n"));
! #endif
}
Index: gas/testsuite/gas/mips/mips-gp32-fp64.d
===================================================================
RCS file: /cvs/src/src/gas/testsuite/gas/mips/mips-gp32-fp64.d,v
retrieving revision 1.3
diff -c -d -p -r1.3 mips-gp32-fp64.d
*** gas/testsuite/gas/mips/mips-gp32-fp64.d 10 Aug 2001 16:28:04 -0000 1.3
--- gas/testsuite/gas/mips/mips-gp32-fp64.d 19 Jul 2002 18:37:30 -0000
***************
*** 1,5 ****
#objdump: -d -mmips:8000
! #as: -march=8000 -EB -mgp32
#name: MIPS -mgp32 -mfp64
.*: +file format.*
--- 1,5 ----
#objdump: -d -mmips:8000
! #as: -march=8000 -EB -mgp32 -mfp64
#name: MIPS -mgp32 -mfp64
.*: +file format.*
Index: gas/testsuite/gas/mips/mips-gp32-fp64-pic.d
===================================================================
RCS file: /cvs/src/src/gas/testsuite/gas/mips/mips-gp32-fp64-pic.d,v
retrieving revision 1.3
diff -c -d -p -r1.3 mips-gp32-fp64-pic.d
*** gas/testsuite/gas/mips/mips-gp32-fp64-pic.d 10 Aug 2001 16:28:04 -0000 1.3
--- gas/testsuite/gas/mips/mips-gp32-fp64-pic.d 19 Jul 2002 18:37:30 -0000
***************
*** 1,5 ****
#objdump: -d -mmips:8000
! #as: -march=8000 -EB -mgp32 -KPIC
#name: MIPS -mgp32 -mfp64 (SVR4 PIC)
.*: +file format.*
--- 1,5 ----
#objdump: -d -mmips:8000
! #as: -march=8000 -EB -mgp32 -mfp64 -KPIC
#name: MIPS -mgp32 -mfp64 (SVR4 PIC)
.*: +file format.*
Index: doc/invoke.texi
===================================================================
RCS file: /cvs/gcc/gcc/gcc/doc/invoke.texi,v
retrieving revision 1.158
diff -c -d -p -r1.158 invoke.texi
*** doc/invoke.texi 16 Jul 2002 17:46:33 -0000 1.158
--- doc/invoke.texi 19 Jul 2002 18:37:49 -0000
*************** These @samp{-m} options are defined for
*** 6959,7023 ****
@table @gcctabopt
! @item -march=@var{cpu-type}
@opindex march
! Assume the defaults for the machine type @var{cpu-type} when generating
! instructions. The choices for @var{cpu-type} are @samp{r2000}, @samp{r3000},
! @samp{r3900}, @samp{r4000}, @samp{r4100}, @samp{r4300}, @samp{r4400},
! @samp{r4600}, @samp{r4650}, @samp{r5000}, @samp{r6000}, @samp{r8000},
! and @samp{orion}. Additionally, the @samp{r2000}, @samp{r3000},
! @samp{r4000}, @samp{r5000}, and @samp{r6000} can be abbreviated as
! @samp{r2k} (or @samp{r2K}), @samp{r3k}, etc.
! @item -mtune=@var{cpu-type}
@opindex mtune
! Assume the defaults for the machine type @var{cpu-type} when scheduling
! instructions. The choices for @var{cpu-type} are @samp{r2000}, @samp{r3000},
! @samp{r3900}, @samp{r4000}, @samp{r4100}, @samp{r4300}, @samp{r4400},
! @samp{r4600}, @samp{r4650}, @samp{r5000}, @samp{r6000}, @samp{r8000},
! and @samp{orion}. Additionally, the @samp{r2000}, @samp{r3000},
! @samp{r4000}, @samp{r5000}, and @samp{r6000} can be abbreviated as
! @samp{r2k} (or @samp{r2K}), @samp{r3k}, etc. While picking a specific
! @var{cpu-type} will schedule things appropriately for that particular
! chip, the compiler will not generate any code that does not meet level 1
! of the MIPS ISA (instruction set architecture) without a @option{-mipsX}
! or @option{-mabi} switch being used.
! @item -mcpu=@var{cpu-type}
! @opindex mcpu
! This is identical to specifying both @option{-march} and @option{-mtune}.
@item -mips1
@opindex mips1
! Issue instructions from level 1 of the MIPS ISA@. This is the default.
! @samp{r3000} is the default @var{cpu-type} at this ISA level.
@item -mips2
@opindex mips2
! Issue instructions from level 2 of the MIPS ISA (branch likely, square
! root instructions). @samp{r6000} is the default @var{cpu-type} at this
! ISA level.
@item -mips3
@opindex mips3
! Issue instructions from level 3 of the MIPS ISA (64-bit instructions).
! @samp{r4000} is the default @var{cpu-type} at this ISA level.
@item -mips4
@opindex mips4
! Issue instructions from level 4 of the MIPS ISA (conditional move,
! prefetch, enhanced FPU instructions). @samp{r8000} is the default
! @var{cpu-type} at this ISA level.
! @item -mfp32
! @opindex mfp32
! Assume that 32 32-bit floating point registers are available. This is
! the default.
! @item -mfp64
! @opindex mfp64
! Assume that 32 64-bit floating point registers are available. This is
! the default when the @option{-mips3} option is used.
@item -mfused-madd
@itemx -mno-fused-madd
--- 6959,7035 ----
@table @gcctabopt
! @item -march=@var{arch}
@opindex march
! Generate code that will run on @var{arch}, which can be the name of a
! generic MIPS ISA, or the name of a particular processor. The ISA names
! are: @samp{mips1}, @samp{mips2}, @samp{mips3}, @samp{mips4}, @samp{mips32}
! and @samp{mips64}. The processor names are: @samp{r2000},
! @samp{r3000}, @samp{r3900}, @samp{r4000}, @samp{vr4100}, @samp{vr4300},
! @samp{r4400}, @samp{r4600}, @samp{r4650}, @samp{vr5000}, @samp{r6000},
! @samp{r8000}, @samp{4kc}, @samp{4kp}, @samp{5kc}, @samp{20kc}
! and @samp{orion}. The special value @samp{from-abi} selects the
! most compatible architecture for the selected ABI (that is,
! @samp{mips1} for 32-bit ABIs and @samp{mips3} for 64-bit ABIs)@.
! In processor names, a final @samp{000} can be abbreviated as @samp{k}
! (for example, @samp{-march=r2k}). Prefixes are optional, and
! @samp{vr} may be written @samp{r}.
!
! GCC defines two macros based on the value of this option. The first
! is @samp{_MIPS_ARCH}, which gives the name of target architecture, as
! a string. The second has the form @samp{_MIPS_ARCH_@var{foo}},
! where @var{foo} is the capitialized value of @samp{_MIPS_ARCH}@.
! For example, @samp{-march=r2000} will set @samp{_MIPS_ARCH}
! to @samp{"r2000"} and define the macro @samp{_MIPS_ARCH_R2000}.
!
! Note that the @samp{_MIPS_ARCH} uses processor names given above. In
! other words, it will have the full prefix, and will not abbreviate
! @samp{000} as @samp{k}. In the case of @samp{from-abi}, the macro
! names the resolved architecture (either @samp{"mips1"} or
! @samp{"mips3"}). It names the default architecture when no
! @option{-march} option is given.
!
! @item -mtune=@var{arch}
@opindex mtune
! Optimize for @var{arch}. Among other things, this option controls
! the way instructions are scheduled, and the perceived cost of arithmetic
! operations. The list of @var{arch} values is the same as for
! @option{-march}.
! When this option is not used, GCC will optimize for the processor
! specified by @option{-march}, or (failing that) for the default
! processor. By using @option{-march} and @option{-mtune} together, it is
! possible to generate code that will run on a family of processors, but
! optimize the code for one particular member of that family.
!
! @samp{-mtune} defines the macros @samp{_MIPS_TUNE} and
! @samp{_MIPS_TUNE_@var{foo}}, which work in the same way as the
! @samp{-march} ones described above.
@item -mips1
@opindex mips1
! Equivalent to @samp{-march=mips1}.
@item -mips2
@opindex mips2
! Equivalent to @samp{-march=mips2}.
@item -mips3
@opindex mips3
! Equivalent to @samp{-march=mips3}.
@item -mips4
@opindex mips4
! Equivalent to @samp{-march=mips4}.
! @item -mips32
! @opindex mips32
! Equivalent to @samp{-march=mips32}.
! @item -mips64
! @opindex mips64
! Equivalent to @samp{-march=mips64}.
@item -mfused-madd
@itemx -mno-fused-madd
*************** in the mode where denormals are rounded
*** 7031,7045 ****
generated by multiply and accumulate instructions cause exceptions
anyway.
@item -mgp32
@opindex mgp32
! Assume that 32 32-bit general purpose registers are available. This is
! the default.
@item -mgp64
@opindex mgp64
! Assume that 32 64-bit general purpose registers are available. This is
! the default when the @option{-mips3} option is used.
@item -mint64
@opindex mint64
--- 7043,7063 ----
generated by multiply and accumulate instructions cause exceptions
anyway.
+ @item -mfp32
+ @opindex mfp32
+ Assume that floating point registers are 32 bits wide.
+
+ @item -mfp64
+ @opindex mfp64
+ Assume that floating point registers are 64 bits wide.
+
@item -mgp32
@opindex mgp32
! Assume that general purpose registers are 32 bits wide.
@item -mgp64
@opindex mgp64
! Assume that general purpose registers are 64 bits wide.
@item -mint64
@opindex mint64
*************** explanation of the default, and the widt
*** 7055,7085 ****
@opindex mlong32
Force long, int, and pointer types to be 32 bits wide.
! If none of @option{-mlong32}, @option{-mlong64}, or @option{-mint64} are set,
! the size of ints, longs, and pointers depends on the ABI and ISA chosen.
! For @option{-mabi=32}, and @option{-mabi=n32}, ints and longs are 32 bits
! wide. For @option{-mabi=64}, ints are 32 bits, and longs are 64 bits wide.
! For @option{-mabi=eabi} and either @option{-mips1} or @option{-mips2}, ints
! and longs are 32 bits wide. For @option{-mabi=eabi} and higher ISAs, ints
! are 32 bits, and longs are 64 bits wide. The width of pointer types is
! the smaller of the width of longs or the width of general purpose
! registers (which in turn depends on the ISA)@.
@item -mabi=32
@itemx -mabi=o64
@itemx -mabi=n32
@itemx -mabi=64
@itemx -mabi=eabi
@opindex mabi=32
@opindex mabi=o64
@opindex mabi=n32
@opindex mabi=64
@opindex mabi=eabi
! Generate code for the indicated ABI@. The default instruction level is
! @option{-mips1} for @samp{32}, @option{-mips3} for @samp{n32}, and
! @option{-mips4} otherwise. Conversely, with @option{-mips1} or
! @option{-mips2}, the default ABI is @samp{32}; otherwise, the default ABI
! is @samp{64}.
@item -mmips-as
@opindex mmips-as
--- 7073,7104 ----
@opindex mlong32
Force long, int, and pointer types to be 32 bits wide.
! The default size of ints, longs and pointers depends on the ABI@.
! All the supported ABIs use 32-bit ints. n64 uses 64-bit longs, as does
! the 64-bit Cygnus EABI; the others use 32-bit longs. Pointers are
! the same size as longs, or the same size as integer registers,
! whichever is smaller.
@item -mabi=32
@itemx -mabi=o64
@itemx -mabi=n32
@itemx -mabi=64
@itemx -mabi=eabi
+ @itemx -mabi=meabi
@opindex mabi=32
@opindex mabi=o64
@opindex mabi=n32
@opindex mabi=64
@opindex mabi=eabi
! @opindex mabi=meabi
! Generate code for the given ABI@.
!
! Note that there are two embedded ABIs: @option{-mabi=eabi}
! selects the one defined by Cygnus while @option{-meabi=meabi}
! selects the one defined by MIPS@. Both these ABIs have
! 32-bit and 64-bit variants. Normally, GCC will generate
! 64-bit code when you select a 64-bit architecture, but you
! can use @option{-mgp32} to get 32-bit code instead.
@item -mmips-as
@opindex mmips-as
Index: toplev.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/toplev.h,v
retrieving revision 1.87
diff -c -d -p -r1.87 toplev.h
*** toplev.h 5 Jun 2002 19:35:32 -0000 1.87
--- toplev.h 19 Jul 2002 18:37:49 -0000
*************** extern void check_global_declarations
*** 108,113 ****
--- 108,114 ----
extern const char *progname;
extern const char *dump_base_name;
+ extern int target_flags_explicit;
/* The hashtable, so that the C front ends can pass it to cpplib. */
extern struct ht *ident_hash;
Index: toplev.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/toplev.c,v
retrieving revision 1.658
diff -c -d -p -r1.658 toplev.c
*** toplev.c 17 Jul 2002 03:03:40 -0000 1.658
--- toplev.c 19 Jul 2002 18:37:50 -0000
*************** const char *dump_base_name;
*** 180,185 ****
--- 180,190 ----
extern int target_flags;
+ /* A mask of target_flags that includes bit X if X was set or cleared
+ on the command line. */
+
+ int target_flags_explicit;
+
/* Debug hooks - dependent upon command line options. */
const struct gcc_debug_hooks *debug_hooks = &do_nothing_debug_hooks;
*************** set_target_switch (name)
*** 4409,4414 ****
--- 4414,4426 ----
target_flags &= ~-target_switches[j].value;
else
target_flags |= target_switches[j].value;
+ if (name[0] != 0)
+ {
+ if (target_switches[j].value < 0)
+ target_flags_explicit |= -target_switches[j].value;
+ else
+ target_flags_explicit |= target_switches[j].value;
+ }
valid_target_option = 1;
}
Index: config/mips/abi64.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mips/abi64.h,v
retrieving revision 1.26
diff -c -d -p -r1.26 abi64.h
*** config/mips/abi64.h 16 Apr 2002 03:01:17 -0000 1.26
--- config/mips/abi64.h 19 Jul 2002 18:37:50 -0000
*************** Boston, MA 02111-1307, USA. */
*** 21,31 ****
/* Macros to implement the 64 bit ABI. This file is meant to be included
after mips.h. */
- #undef SUBTARGET_TARGET_OPTIONS
- #define SUBTARGET_TARGET_OPTIONS \
- { "abi=", &mips_abi_string, \
- "Specify ABI to use"},
-
#undef STACK_BOUNDARY
#define STACK_BOUNDARY \
((mips_abi == ABI_32 || mips_abi == ABI_O64 || mips_abi == ABI_EABI) \
--- 21,26 ----
Index: config/mips/elf64.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mips/elf64.h,v
retrieving revision 1.43
diff -c -d -p -r1.43 elf64.h
*** config/mips/elf64.h 11 Jun 2002 07:26:37 -0000 1.43
--- config/mips/elf64.h 19 Jul 2002 18:37:50 -0000
*************** Boston, MA 02111-1307, USA. */
*** 22,34 ****
#define OBJECT_FORMAT_ELF
! /* Default to -mips3. */
#ifndef TARGET_DEFAULT
#define TARGET_DEFAULT MASK_FLOAT64|MASK_64BIT
- #endif
-
- #ifndef MIPS_ISA_DEFAULT
- #define MIPS_ISA_DEFAULT 3
#endif
/* This should change to n32 when it is supported in gas. */
--- 22,31 ----
#define OBJECT_FORMAT_ELF
! /* If an embedded ABI is selected, prefer to generate 64-bit code.
! Implies -mips3 in such cases. */
#ifndef TARGET_DEFAULT
#define TARGET_DEFAULT MASK_FLOAT64|MASK_64BIT
#endif
/* This should change to n32 when it is supported in gas. */
Index: config/mips/iris6.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mips/iris6.h,v
retrieving revision 1.50
diff -c -d -p -r1.50 iris6.h
*** config/mips/iris6.h 11 Jul 2002 18:56:56 -0000 1.50
--- config/mips/iris6.h 19 Jul 2002 18:37:50 -0000
*************** Boston, MA 02111-1307, USA. */
*** 238,244 ****
on the mipsX option. */
/* If no mips[3,4] option given, give the appropriate default for mabi=X */
#undef SUBTARGET_ASM_SPEC
! #define SUBTARGET_ASM_SPEC "%{!mabi*:-n32} %{!mips*: %{!mabi*:-mips3} %{mabi=n32:-mips3} %{mabi=64:-mips4}}"
/* Must pass -g0 to the assembler, otherwise it may overwrite our
debug info with its own debug info. */
--- 238,244 ----
on the mipsX option. */
/* If no mips[3,4] option given, give the appropriate default for mabi=X */
#undef SUBTARGET_ASM_SPEC
! #define SUBTARGET_ASM_SPEC "%{!mabi*:-n32} %{!mips*: %{!mabi*:-mips3} %{mabi=n32|mabi=64:-mips3}}"
/* Must pass -g0 to the assembler, otherwise it may overwrite our
debug info with its own debug info. */
Index: config/mips/isa3264.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mips/isa3264.h,v
retrieving revision 1.5
diff -c -d -p -r1.5 isa3264.h
*** config/mips/isa3264.h 17 Jan 2002 07:53:55 -0000 1.5
--- config/mips/isa3264.h 19 Jul 2002 18:37:50 -0000
*************** Boston, MA 02111-1307, USA. */
*** 27,36 ****
#define MIPS_ABI_DEFAULT ABI_MEABI
#endif
- #ifndef MIPS_ENABLE_EMBEDDED_O32
- #define MIPS_ENABLE_EMBEDDED_O32 1
- #endif
-
#ifndef PREFERRED_DEBUGGING_TYPE
#define PREFERRED_DEBUGGING_TYPE DBX_DEBUG
#endif
--- 27,32 ----
Index: config/mips/mips.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mips/mips.h,v
retrieving revision 1.200
diff -c -d -p -r1.200 mips.h
*** config/mips/mips.h 17 Jul 2002 21:31:39 -0000 1.200
--- config/mips/mips.h 19 Jul 2002 18:37:50 -0000
*************** enum block_move_type {
*** 118,123 ****
--- 118,140 ----
BLOCK_MOVE_LAST /* generate just the last store */
};
+ /* Information about one recognised processor. Defined here for the
+ benefit of TARGET_CPU_CPP_BUILTINS. */
+ struct mips_cpu_info {
+ /* The 'canonical' name of the processor as far as GCC is concerned.
+ It's typically a manufacturer's prefix followed by a numerical
+ designation. It should be lower case. */
+ const char *name;
+
+ /* The internal processor number that most closely matches this
+ entry. Several processors can have the same value, if there's no
+ difference between them from GCC's point of view. */
+ enum processor_type cpu;
+
+ /* The ISA level that the processor implements. */
+ int isa;
+ };
+
extern char mips_reg_names[][8]; /* register names (a0 vs. $4). */
extern char mips_print_operand_punct[256]; /* print_operand punctuation chars */
extern const char *current_function_file; /* filename current function is in */
*************** extern int mips_isa; /* architectural
*** 146,159 ****
extern int mips16; /* whether generating mips16 code */
extern int mips16_hard_float; /* mips16 without -msoft-float */
extern int mips_entry; /* generate entry/exit for mips16 */
- extern const char *mips_cpu_string; /* for -mcpu=<xxx> */
extern const char *mips_arch_string; /* for -march=<xxx> */
extern const char *mips_tune_string; /* for -mtune=<xxx> */
extern const char *mips_isa_string; /* for -mips{1,2,3,4} */
extern const char *mips_abi_string; /* for -mabi={32,n32,64} */
extern const char *mips_entry_string; /* for -mentry */
extern const char *mips_no_mips16_string;/* for -mno-mips16 */
- extern const char *mips_explicit_type_size_string;/* for -mexplicit-type-size */
extern const char *mips_cache_flush_func;/* for -mflush-func= and -mno-flush-func */
extern int mips_split_addresses; /* perform high/lo_sum support */
extern int dslots_load_total; /* total # load related delay slots */
--- 163,174 ----
*************** extern GTY(()) rtx mips_load_reg2; /* 2n
*** 167,172 ****
--- 182,190 ----
extern GTY(()) rtx mips_load_reg3; /* 3rd reg to check for load delay */
extern GTY(()) rtx mips_load_reg4; /* 4th reg to check for load delay */
extern int mips_string_length; /* length of strings for mips16 */
+ extern const struct mips_cpu_info mips_cpu_info_table[];
+ extern const struct mips_cpu_info *mips_arch_info;
+ extern const struct mips_cpu_info *mips_tune_info;
/* Functions to change what output section we are using. */
extern void sdata_section PARAMS ((void));
*************** extern void sbss_section PARAMS ((void)
*** 342,347 ****
--- 360,384 ----
#define TUNE_MIPS5000 (mips_tune == PROCESSOR_R5000)
#define TUNE_MIPS6000 (mips_tune == PROCESSOR_R6000)
+ /* Define preprocessor macros for the -march and -mtune options.
+ PREFIX is either _MIPS_ARCH or _MIPS_TUNE, INFO is the selected
+ processor. If INFO's canonical name is "foo", define PREFIX to
+ be "foo", and define an additional macro PREFIX_FOO. */
+ #define MIPS_CPP_SET_PROCESSOR(PREFIX, INFO) \
+ do \
+ { \
+ char *macro, *p; \
+ \
+ macro = concat ((PREFIX), "_", (INFO)->name, NULL); \
+ for (p = macro; *p != 0; p++) \
+ *p = TOUPPER (*p); \
+ \
+ builtin_define (macro); \
+ builtin_define_with_value ((PREFIX), (INFO)->name, 1); \
+ free (macro); \
+ } \
+ while (0)
+
/* Target CPU builtins. */
#define TARGET_CPU_CPP_BUILTINS() \
do \
*************** extern void sbss_section PARAMS ((void)
*** 355,370 ****
if (!flag_iso) \
builtin_define ("mips"); \
\
if (TARGET_64BIT) \
{ \
builtin_define ("__mips64"); \
- /* Silly, but will do until processor defines. */ \
builtin_define_std ("R4000"); \
builtin_define ("_R4000"); \
} \
else \
{ \
- /* Ditto. */ \
builtin_define_std ("R3000"); \
builtin_define ("_R3000"); \
} \
--- 392,407 ----
if (!flag_iso) \
builtin_define ("mips"); \
\
+ /* Treat _R3000 and _R4000 like register-size defines, \
+ which is how they've historically been used. */ \
if (TARGET_64BIT) \
{ \
builtin_define ("__mips64"); \
builtin_define_std ("R4000"); \
builtin_define ("_R4000"); \
} \
else \
{ \
builtin_define_std ("R3000"); \
builtin_define ("_R3000"); \
} \
*************** extern void sbss_section PARAMS ((void)
*** 376,381 ****
--- 413,422 ----
if (TARGET_MIPS16) \
builtin_define ("__mips16"); \
\
+ \
+ MIPS_CPP_SET_PROCESSOR ("_MIPS_ARCH", mips_arch_info); \
+ MIPS_CPP_SET_PROCESSOR ("_MIPS_TUNE", mips_tune_info); \
+ \
if (ISA_MIPS1) \
{ \
builtin_define ("__mips=1"); \
*************** extern void sbss_section PARAMS ((void)
*** 605,612 ****
#define TARGET_ENDIAN_DEFAULT MASK_BIG_ENDIAN
#endif
#ifndef MIPS_ISA_DEFAULT
! #define MIPS_ISA_DEFAULT 1
#endif
#ifdef IN_LIBGCC2
--- 646,656 ----
#define TARGET_ENDIAN_DEFAULT MASK_BIG_ENDIAN
#endif
+ /* 'from-abi' makes a good default: you get whatever the ABI requires. */
#ifndef MIPS_ISA_DEFAULT
! #ifndef MIPS_CPU_STRING_DEFAULT
! #define MIPS_CPU_STRING_DEFAULT "from-abi"
! #endif
#endif
#ifdef IN_LIBGCC2
*************** extern void sbss_section PARAMS ((void)
*** 656,662 ****
#endif
#ifndef MULTILIB_DEFAULTS
! #define MULTILIB_DEFAULTS { MULTILIB_ENDIAN_DEFAULT, MULTILIB_ISA_DEFAULT }
#endif
/* We must pass -EL to the linker by default for little endian embedded
--- 700,707 ----
#endif
#ifndef MULTILIB_DEFAULTS
! #define MULTILIB_DEFAULTS \
! { MULTILIB_ENDIAN_DEFAULT, MULTILIB_ISA_DEFAULT, MULTILIB_ABI_DEFAULT }
#endif
/* We must pass -EL to the linker by default for little endian embedded
*************** extern void sbss_section PARAMS ((void)
*** 675,694 ****
#define TARGET_OPTIONS \
{ \
SUBTARGET_TARGET_OPTIONS \
- { "cpu=", &mips_cpu_string, \
- N_("Specify CPU for scheduling purposes")}, \
{ "tune=", &mips_tune_string, \
N_("Specify CPU for scheduling purposes")}, \
{ "arch=", &mips_arch_string, \
N_("Specify CPU for code generation purposes")}, \
{ "ips", &mips_isa_string, \
N_("Specify a Standard MIPS ISA")}, \
{ "entry", &mips_entry_string, \
N_("Use mips16 entry/exit psuedo ops")}, \
{ "no-mips16", &mips_no_mips16_string, \
N_("Don't use MIPS16 instructions")}, \
- { "explicit-type-size", &mips_explicit_type_size_string, \
- NULL}, \
{ "no-flush-func", &mips_cache_flush_func, \
N_("Don't call any cache flush functions")}, \
{ "flush-func=", &mips_cache_flush_func, \
--- 720,737 ----
#define TARGET_OPTIONS \
{ \
SUBTARGET_TARGET_OPTIONS \
{ "tune=", &mips_tune_string, \
N_("Specify CPU for scheduling purposes")}, \
{ "arch=", &mips_arch_string, \
N_("Specify CPU for code generation purposes")}, \
+ { "abi=", &mips_abi_string, \
+ N_("Specify an ABI")}, \
{ "ips", &mips_isa_string, \
N_("Specify a Standard MIPS ISA")}, \
{ "entry", &mips_entry_string, \
N_("Use mips16 entry/exit psuedo ops")}, \
{ "no-mips16", &mips_no_mips16_string, \
N_("Don't use MIPS16 instructions")}, \
{ "no-flush-func", &mips_cache_flush_func, \
N_("Don't call any cache flush functions")}, \
{ "flush-func=", &mips_cache_flush_func, \
*************** extern void sbss_section PARAMS ((void)
*** 716,721 ****
--- 759,774 ----
#define BRANCH_LIKELY_P() GENERATE_BRANCHLIKELY
#define HAVE_SQRT_P() (!ISA_MIPS1)
+ /* True if the ABI can only work with 64-bit integer registers. We
+ generally allow ad-hoc variations for TARGET_SINGLE_FLOAT, but
+ otherwise floating-point registers must also be 64-bit. */
+ #define ABI_NEEDS_64BIT_REGS (mips_abi == ABI_64 \
+ || mips_abi == ABI_O64 \
+ || mips_abi == ABI_N32)
+
+ /* Likewise for 32-bit regs. */
+ #define ABI_NEEDS_32BIT_REGS (mips_abi == ABI_32)
+
/* ISA has instructions for managing 64 bit fp and gp regs (eg. mips3). */
#define ISA_HAS_64BIT_REGS (ISA_MIPS3 \
|| ISA_MIPS4 \
*************** while (0)
*** 911,917 ****
/* GAS_ASM_SPEC is passed when using gas, rather than the MIPS
assembler. */
! #define GAS_ASM_SPEC "%{march=*} %{mtune=*} %{mcpu=*} %{m4650} %{mmad:-m4650} %{m3900} %{v} %{mgp32} %{mgp64} %(abi_gas_asm_spec) %{mabi=32:%{!mips*:-mips1}}"
extern int mips_abi;
--- 964,970 ----
/* GAS_ASM_SPEC is passed when using gas, rather than the MIPS
assembler. */
! #define GAS_ASM_SPEC "%{mtune=*} %{v}"
extern int mips_abi;
*************** extern int mips_abi;
*** 920,927 ****
#define MIPS_ABI_DEFAULT ABI_32
#endif
! #ifndef ABI_GAS_ASM_SPEC
! #define ABI_GAS_ASM_SPEC ""
#endif
/* TARGET_ASM_SPEC is used to select either MIPS_AS_ASM_SPEC or
--- 973,1015 ----
#define MIPS_ABI_DEFAULT ABI_32
#endif
! /* Use the most portable ABI flag for the ASM specs. */
!
! #if MIPS_ABI_DEFAULT == ABI_32
! #define MULTILIB_ABI_DEFAULT "-mabi=32"
! #define ASM_ABI_DEFAULT_SPEC "-32"
! #endif
!
! #if MIPS_ABI_DEFAULT == ABI_O64
! #define MULTILIB_ABI_DEFAULT "-mabi=o64"
! #define ASM_ABI_DEFAULT_SPEC "-mabi=o64"
! #endif
!
! #if MIPS_ABI_DEFAULT == ABI_N32
! #define MULTILIB_ABI_DEFAULT "-mabi=n32"
! #define ASM_ABI_DEFAULT_SPEC "-n32"
! #endif
!
! #if MIPS_ABI_DEFAULT == ABI_64
! #define MULTILIB_ABI_DEFAULT "-mabi=64"
! #define ASM_ABI_DEFAULT_SPEC "-64"
! #endif
!
! #if MIPS_ABI_DEFAULT == ABI_EABI
! #define MULTILIB_ABI_DEFAULT "-mabi=eabi"
! #define ASM_ABI_DEFAULT_SPEC "-mabi=eabi"
! #endif
!
! #if MIPS_ABI_DEFAULT == ABI_MEABI
! /* Most GAS don't know about MEABI. */
! #define MULTILIB_ABI_DEFAULT "-mabi=meabi"
! #define ASM_ABI_DEFAULT_SPEC ""
! #endif
!
! /* Only ELF targets can switch the ABI. */
! #ifndef OBJECT_FORMAT_ELF
! #undef ASM_ABI_DEFAULT_SPEC
! #define ASM_ABI_DEFAULT_SPEC ""
#endif
/* TARGET_ASM_SPEC is used to select either MIPS_AS_ASM_SPEC or
*************** extern int mips_abi;
*** 969,975 ****
#define SUBTARGET_ASM_SPEC ""
#endif
! /* ASM_SPEC is the set of arguments to pass to the assembler. */
#undef ASM_SPEC
#define ASM_SPEC "\
--- 1057,1067 ----
#define SUBTARGET_ASM_SPEC ""
#endif
! /* ASM_SPEC is the set of arguments to pass to the assembler. Note: we
! pass -mgp32, -mgp64, -march, -mabi=eabi and -meabi=o64 regardless of
! whether we're using GAS. These options can only be used properly
! with GAS, and it is better to get an error from a non-GAS assembler
! than to silently generate bad code. */
#undef ASM_SPEC
#define ASM_SPEC "\
*************** extern int mips_abi;
*** 978,984 ****
%(subtarget_asm_optimizing_spec) \
%(subtarget_asm_debugging_spec) \
%{membedded-pic} \
! %{mabi=32:-32}%{mabi=o32:-32}%{mabi=n32:-n32}%{mabi=64:-64}%{mabi=n64:-64} \
%(target_asm_spec) \
%(subtarget_asm_spec)"
--- 1070,1078 ----
%(subtarget_asm_optimizing_spec) \
%(subtarget_asm_debugging_spec) \
%{membedded-pic} \
! %{mabi=32:-32}%{mabi=n32:-n32}%{mabi=64:-64}%{mabi=n64:-64} \
! %{mabi=eabi} %{mabi=o64} %{!mabi*: %(asm_abi_default_spec)} \
! %{mgp32} %{mgp64} %{march=*} \
%(target_asm_spec) \
%(subtarget_asm_spec)"
*************** extern int mips_abi;
*** 1049,1063 ****
#ifndef CC1_SPEC
#define CC1_SPEC "\
%{gline:%{!g:%{!g0:%{!g1:%{!g2: -g1}}}}} \
- %{mips1:-mfp32 -mgp32} %{mips2:-mfp32 -mgp32}\
- %{mips3:%{!msingle-float:%{!m4650:-mfp64}} -mgp64} \
- %{mips4:%{!msingle-float:%{!m4650:-mfp64}} -mgp64} \
- %{mips32:-mfp32 -mgp32} \
- %{mips64:%{!msingle-float:-mfp64} -mgp64} \
- %{mfp64:%{msingle-float:%emay not use both -mfp64 and -msingle-float}} \
- %{mfp64:%{m4650:%emay not use both -mfp64 and -m4650}} \
- %{mint64|mlong64|mlong32:-mexplicit-type-size }\
- %{mgp32: %{mfp64:%emay not use both -mgp32 and -mfp64} %{!mfp32: -mfp32}} \
%{G*} %{EB:-meb} %{EL:-mel} %{EB:%{EL:%emay not use both -EB and -EL}} \
%{save-temps: } \
%(subtarget_cc1_spec)"
--- 1143,1148 ----
*************** extern int mips_abi;
*** 1088,1099 ****
{ "subtarget_cpp_spec", SUBTARGET_CPP_SPEC }, \
{ "mips_as_asm_spec", MIPS_AS_ASM_SPEC }, \
{ "gas_asm_spec", GAS_ASM_SPEC }, \
- { "abi_gas_asm_spec", ABI_GAS_ASM_SPEC }, \
{ "target_asm_spec", TARGET_ASM_SPEC }, \
{ "subtarget_mips_as_asm_spec", SUBTARGET_MIPS_AS_ASM_SPEC }, \
{ "subtarget_asm_optimizing_spec", SUBTARGET_ASM_OPTIMIZING_SPEC }, \
{ "subtarget_asm_debugging_spec", SUBTARGET_ASM_DEBUGGING_SPEC }, \
{ "subtarget_asm_spec", SUBTARGET_ASM_SPEC }, \
{ "endian_spec", ENDIAN_SPEC }, \
SUBTARGET_EXTRA_SPECS
--- 1173,1184 ----
{ "subtarget_cpp_spec", SUBTARGET_CPP_SPEC }, \
{ "mips_as_asm_spec", MIPS_AS_ASM_SPEC }, \
{ "gas_asm_spec", GAS_ASM_SPEC }, \
{ "target_asm_spec", TARGET_ASM_SPEC }, \
{ "subtarget_mips_as_asm_spec", SUBTARGET_MIPS_AS_ASM_SPEC }, \
{ "subtarget_asm_optimizing_spec", SUBTARGET_ASM_OPTIMIZING_SPEC }, \
{ "subtarget_asm_debugging_spec", SUBTARGET_ASM_DEBUGGING_SPEC }, \
{ "subtarget_asm_spec", SUBTARGET_ASM_SPEC }, \
+ { "asm_abi_default_spec", ASM_ABI_DEFAULT_SPEC }, \
{ "endian_spec", ENDIAN_SPEC }, \
SUBTARGET_EXTRA_SPECS
Index: config/mips/mips.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/config/mips/mips.c,v
retrieving revision 1.217
diff -c -d -p -r1.217 mips.c
*** config/mips/mips.c 17 Jul 2002 09:24:08 -0000 1.217
--- config/mips/mips.c 19 Jul 2002 18:37:50 -0000
*************** static int symbolic_expression_p
*** 119,125 ****
static bool mips_assemble_integer PARAMS ((rtx, unsigned int, int));
static void mips_output_function_epilogue PARAMS ((FILE *, HOST_WIDE_INT));
static void mips_output_function_prologue PARAMS ((FILE *, HOST_WIDE_INT));
! static enum processor_type mips_parse_cpu PARAMS ((const char *));
static void copy_file_data PARAMS ((FILE *, FILE *));
#ifdef TARGET_IRIX6
static void iris6_asm_named_section_1 PARAMS ((const char *,
--- 119,133 ----
static bool mips_assemble_integer PARAMS ((rtx, unsigned int, int));
static void mips_output_function_epilogue PARAMS ((FILE *, HOST_WIDE_INT));
static void mips_output_function_prologue PARAMS ((FILE *, HOST_WIDE_INT));
! static void mips_set_architecture PARAMS ((const struct mips_cpu_info *));
! static void mips_set_tune PARAMS ((const struct mips_cpu_info *));
! static bool mips_strict_matching_cpu_name_p PARAMS ((const char *,
! const char *));
! static bool mips_matching_cpu_name_p PARAMS ((const char *,
! const char *));
! static const struct mips_cpu_info *mips_parse_cpu PARAMS ((const char *,
! const char *));
! static const struct mips_cpu_info *mips_cpu_info_from_isa PARAMS ((int));
static void copy_file_data PARAMS ((FILE *, FILE *));
#ifdef TARGET_IRIX6
static void iris6_asm_named_section_1 PARAMS ((const char *,
*************** enum cmp_type branch_type;
*** 294,302 ****
--- 302,312 ----
/* The target cpu for code generation. */
enum processor_type mips_arch;
+ const struct mips_cpu_info *mips_arch_info;
/* The target cpu for optimization and scheduling. */
enum processor_type mips_tune;
+ const struct mips_cpu_info *mips_tune_info;
/* which instruction set architecture to use. */
int mips_isa;
*************** int mips_isa;
*** 305,311 ****
int mips_abi;
/* Strings to hold which cpu and instruction set architecture to use. */
- const char *mips_cpu_string; /* for -mcpu=<xxx> */
const char *mips_arch_string; /* for -march=<xxx> */
const char *mips_tune_string; /* for -mtune=<xxx> */
const char *mips_isa_string; /* for -mips{1,2,3,4} */
--- 315,320 ----
*************** int mips16;
*** 320,330 ****
just a way to avoid using up another bit in target_flags. */
const char *mips_no_mips16_string;
- /* This is only used to determine if an type size setting option was
- explicitly specified (-mlong64, -mint64, -mlong32). The specs
- set this option if such an option is used. */
- const char *mips_explicit_type_size_string;
-
/* Whether we are generating mips16 hard float code. In mips16 mode
we always set TARGET_SOFT_FLOAT; this variable is nonzero if
-msoft-float was not specified by the user, which means that we
--- 329,334 ----
*************** enum reg_class mips_char_to_class[256] =
*** 562,567 ****
--- 566,619 ----
NO_REGS, NO_REGS, NO_REGS, NO_REGS,
};
+ /* A table describing all the processors gcc knows about. Names are
+ matched in the order listed. The first mention of an ISA level is
+ taken as the canonical name for that ISA.
+
+ To ease comparison, please keep this table in the same order as
+ gas's mips_cpu_info_table[]. */
+ const struct mips_cpu_info mips_cpu_info_table[] = {
+ /* Entries for generic ISAs */
+ { "mips1", PROCESSOR_R3000, 1 },
+ { "mips2", PROCESSOR_R6000, 2 },
+ { "mips3", PROCESSOR_R4000, 3 },
+ { "mips4", PROCESSOR_R8000, 4 },
+ { "mips32", PROCESSOR_R4KC, 32 },
+ { "mips64", PROCESSOR_R5KC, 64 },
+
+ /* MIPS I */
+ { "r3000", PROCESSOR_R3000, 1 },
+ { "r2000", PROCESSOR_R3000, 1 }, /* = r3000 */
+ { "r3900", PROCESSOR_R3900, 1 },
+
+ /* MIPS II */
+ { "r6000", PROCESSOR_R6000, 2 },
+
+ /* MIPS III */
+ { "r4000", PROCESSOR_R4000, 3 },
+ { "vr4100", PROCESSOR_R4100, 3 },
+ { "vr4300", PROCESSOR_R4300, 3 },
+ { "r4400", PROCESSOR_R4000, 3 }, /* = r4000 */
+ { "r4600", PROCESSOR_R4600, 3 },
+ { "orion", PROCESSOR_R4600, 3 }, /* = r4600 */
+ { "r4650", PROCESSOR_R4650, 3 },
+
+ /* MIPS IV */
+ { "r8000", PROCESSOR_R8000, 4 },
+ { "vr5000", PROCESSOR_R5000, 4 },
+
+ /* MIPS 32 */
+ { "4kc", PROCESSOR_R4KC, 32 },
+ { "4kp", PROCESSOR_R4KC, 32 }, /* = 4kc */
+
+ /* MIPS 64 */
+ { "5kc", PROCESSOR_R5KC, 64 },
+ { "20kc", PROCESSOR_R20KC, 64 },
+
+ /* End marker */
+ { 0, 0, 0 }
+ };
+
/* Initialize the GCC target structure. */
#undef TARGET_ASM_ALIGNED_HI_OP
#define TARGET_ASM_ALIGNED_HI_OP "\t.half\t"
*************** abort_with_insn (insn, reason)
*** 4931,4946 ****
abort ();
}
/* Set up the threshold for data to go into the small data area, instead
of the normal data area, and detect any conflicts in the switches. */
void
override_options ()
{
! register int i, start;
! register int regno;
! register enum machine_mode mode;
! register enum processor_type mips_cpu;
mips_section_threshold = g_switch_set ? g_switch_value : MIPS_DEFAULT_GVALUE;
--- 4983,5026 ----
abort ();
}
+ /* Set up globals to generate code for the ISA or processor
+ described by INFO. */
+
+ static void
+ mips_set_architecture (info)
+ const struct mips_cpu_info *info;
+ {
+ if (info != 0)
+ {
+ mips_arch_info = info;
+ mips_arch = info->cpu;
+ mips_isa = info->isa;
+ }
+ }
+
+
+ /* Likewise for tuning. */
+
+ static void
+ mips_set_tune (info)
+ const struct mips_cpu_info *info;
+ {
+ if (info != 0)
+ {
+ mips_tune_info = info;
+ mips_tune = info->cpu;
+ }
+ }
+
+
/* Set up the threshold for data to go into the small data area, instead
of the normal data area, and detect any conflicts in the switches. */
void
override_options ()
{
! int i, start, regno;
! enum machine_mode mode;
mips_section_threshold = g_switch_set ? g_switch_value : MIPS_DEFAULT_GVALUE;
*************** override_options ()
*** 4958,5207 ****
target_flags &= ~((TARGET_DEFAULT) & (MASK_SOFT_FLOAT | MASK_SINGLE_FLOAT));
#endif
! /* Get the architectural level. */
! if (mips_isa_string == 0)
! mips_isa = MIPS_ISA_DEFAULT;
! else if (mips_isa_string != 0
! && mips_arch_string != 0)
! warning ("The -march option is incompatible to -mipsN and therefore ignored.");
! else if (ISDIGIT (*mips_isa_string))
{
! mips_isa = atoi (mips_isa_string);
! if (mips_isa == 16)
{
! /* -mno-mips16 overrides -mips16. */
if (mips_no_mips16_string == NULL)
! {
! target_flags |= MASK_MIPS16;
! if (TARGET_64BIT)
! mips_isa = 3;
! else
! mips_isa = MIPS_ISA_DEFAULT;
! }
! else
! {
! mips_isa = MIPS_ISA_DEFAULT;
! }
}
! else if (mips_isa < 1
! || (mips_isa > 4
! && mips_isa != 32
! && mips_isa != 64))
{
! error ("-mips%d not supported", mips_isa);
! mips_isa = 1;
}
- }
-
- else
- {
- error ("bad value (%s) for -mips switch", mips_isa_string);
- mips_isa = 1;
- }
-
- #ifdef MIPS_ABI_DEFAULT
- /* Get the ABI to use. */
- if (mips_abi_string == (char *) 0)
- mips_abi = MIPS_ABI_DEFAULT;
- else if (! strcmp (mips_abi_string, "32"))
- mips_abi = ABI_32;
- else if (! strcmp (mips_abi_string, "o64"))
- mips_abi = ABI_O64;
- else if (! strcmp (mips_abi_string, "n32"))
- mips_abi = ABI_N32;
- else if (! strcmp (mips_abi_string, "64"))
- mips_abi = ABI_64;
- else if (! strcmp (mips_abi_string, "eabi"))
- mips_abi = ABI_EABI;
- else if (! strcmp (mips_abi_string, "meabi"))
- mips_abi = ABI_MEABI;
- else
- error ("bad value (%s) for -mabi= switch", mips_abi_string);
-
- /* A specified ISA defaults the ABI if it was not specified. */
- if (mips_abi_string == 0 && mips_isa_string
- && mips_abi != ABI_EABI
- && mips_abi != ABI_O64
- && mips_abi != ABI_MEABI)
- {
- if (mips_isa == 64)
- mips_abi = ABI_O64;
else
{
! if (! ISA_HAS_64BIT_REGS)
! mips_abi = ABI_32;
! else if (mips_abi != ABI_N32)
! mips_abi = ABI_64;
}
}
! #ifdef MIPS_CPU_STRING_DEFAULT
! /* A specified ABI defaults the ISA if it was not specified. */
! else if (mips_isa_string == 0 && mips_abi_string
! && mips_abi != ABI_EABI && mips_abi != ABI_O64)
! {
! if (mips_abi == ABI_32)
! mips_isa = 1;
! else if (mips_abi == ABI_N32)
! mips_isa = 3;
! else
! mips_isa = 4;
! }
! #endif
!
! /* If both ABI and ISA were specified, check for conflicts. */
! else if (mips_isa_string && mips_abi_string)
{
! if (! ISA_HAS_64BIT_REGS && (mips_abi == ABI_N32 || mips_abi == ABI_64
! || mips_abi == ABI_O64))
! error ("-mabi=%s does not support -mips%d", mips_abi_string, mips_isa);
! }
!
! /* Override TARGET_DEFAULT if necessary. */
! if (mips_abi == ABI_32)
! target_flags &= ~ (MASK_FLOAT64|MASK_64BIT);
!
! /* If no type size setting options (-mlong64,-mint64,-mlong32) were used
! then set the type sizes. In the EABI in 64 bit mode, longs and
! pointers are 64 bits. Likewise for the SGI Irix6 N64 ABI. */
! if (mips_explicit_type_size_string == NULL
! && ((mips_abi == ABI_EABI && TARGET_64BIT)
! || mips_abi == ABI_64))
! target_flags |= MASK_LONG64;
!
! #else
! if (mips_abi_string)
! error ("this target does not support the -mabi switch");
! #endif
!
#ifdef MIPS_CPU_STRING_DEFAULT
! /* ??? There is a minor inconsistency here. If the user specifies an ISA
! greater than that supported by the default processor, then the user gets
! an error. Normally, the compiler will just default to the base level cpu
! for the indicated isa. */
! if (mips_arch_string == 0)
! mips_arch_string = MIPS_CPU_STRING_DEFAULT;
! if (mips_tune_string == 0)
! mips_tune_string = MIPS_CPU_STRING_DEFAULT;
#endif
! /* Identify the processor type. */
! if (mips_cpu_string != 0)
! {
! mips_cpu = mips_parse_cpu (mips_cpu_string);
! if (mips_cpu == PROCESSOR_DEFAULT)
! {
! error ("bad value (%s) for -mcpu= switch", mips_cpu_string);
! mips_cpu_string = "default";
! }
! mips_arch = mips_cpu;
! mips_tune = mips_cpu;
! }
! if (mips_arch_string == 0
! || ! strcmp (mips_arch_string, "default")
! || ! strcmp (mips_arch_string, "DEFAULT"))
{
! switch (mips_isa)
! {
! default:
! mips_arch_string = "3000";
! mips_arch = PROCESSOR_R3000;
! break;
! case 2:
! mips_arch_string = "6000";
! mips_arch = PROCESSOR_R6000;
! break;
! case 3:
! mips_arch_string = "4000";
! mips_arch = PROCESSOR_R4000;
! break;
! case 4:
! mips_arch_string = "8000";
! mips_arch = PROCESSOR_R8000;
! break;
! case 32:
! mips_arch_string = "4kc";
! mips_arch = PROCESSOR_R4KC;
! break;
! case 64:
! mips_arch_string = "5kc";
! mips_arch = PROCESSOR_R5KC;
! break;
! }
}
else
{
! mips_arch = mips_parse_cpu (mips_arch_string);
! if (mips_arch == PROCESSOR_DEFAULT)
! {
! error ("bad value (%s) for -march= switch", mips_arch_string);
! mips_arch_string = "default";
! }
! }
! if (mips_tune_string == 0
! || ! strcmp (mips_tune_string, "default")
! || ! strcmp (mips_tune_string, "DEFAULT"))
! {
! if (mips_arch != PROCESSOR_DEFAULT)
! mips_tune = mips_arch;
else
! switch (mips_isa)
! {
! default:
! mips_tune_string = "3000";
! mips_tune = PROCESSOR_R3000;
! break;
! case 2:
! mips_tune_string = "6000";
! mips_tune = PROCESSOR_R6000;
! break;
! case 3:
! mips_tune_string = "4000";
! mips_tune = PROCESSOR_R4000;
! break;
! case 4:
! mips_tune_string = "8000";
! mips_tune = PROCESSOR_R8000;
! break;
! case 32:
! mips_tune_string = "4kc";
! mips_tune = PROCESSOR_R4KC;
! break;
! case 64:
! mips_tune_string = "5kc";
! mips_tune = PROCESSOR_R5KC;
! break;
! }
}
else
{
! mips_tune = mips_parse_cpu (mips_tune_string);
! if (mips_tune == PROCESSOR_DEFAULT)
! {
! error ("bad value (%s) for -mtune= switch", mips_tune_string);
! mips_tune_string = "default";
! }
}
! /* make sure sizes of ints/longs/etc. are ok */
! if (! ISA_HAS_64BIT_REGS)
! {
! if (TARGET_FLOAT64)
! {
! error ("-mips%d does not support 64 bit fp registers", mips_isa);
! target_flags &= ~ MASK_FLOAT64;
! }
! else if (TARGET_64BIT)
! {
! error ("-mips%d does not support 64 bit gp registers", mips_isa);
! target_flags &= ~MASK_64BIT;
! }
}
if (mips_abi != ABI_32 && mips_abi != ABI_O64)
--- 5038,5175 ----
target_flags &= ~((TARGET_DEFAULT) & (MASK_SOFT_FLOAT | MASK_SINGLE_FLOAT));
#endif
! /* Interpret -mabi. */
! mips_abi = MIPS_ABI_DEFAULT;
! if (mips_abi_string != 0)
! {
! if (strcmp (mips_abi_string, "32") == 0)
! mips_abi = ABI_32;
! else if (strcmp (mips_abi_string, "o64") == 0)
! mips_abi = ABI_O64;
! else if (strcmp (mips_abi_string, "n32") == 0)
! mips_abi = ABI_N32;
! else if (strcmp (mips_abi_string, "64") == 0)
! mips_abi = ABI_64;
! else if (strcmp (mips_abi_string, "eabi") == 0)
! mips_abi = ABI_EABI;
! else if (strcmp (mips_abi_string, "meabi") == 0)
! mips_abi = ABI_MEABI;
! else
! fatal_error ("bad value (%s) for -mabi= switch", mips_abi_string);
! }
! /* The following code determines the architecture and register size.
! Similar code was added to GAS 2.14 (see tc-mips.c:md_after_parse_args()).
! The GAS and GCC code should be kept in sync as much as possible. */
! if (mips_arch_string != 0)
! mips_set_architecture (mips_parse_cpu ("-march", mips_arch_string));
!
! if (mips_tune_string != 0)
! mips_set_tune (mips_parse_cpu ("-mtune", mips_tune_string));
!
! if (mips_isa_string != 0)
{
! /* Handle -mipsN. */
! int level = atoi (mips_isa_string);
! if (level == 16)
{
! /* -mips16 specifies an ASE rather than a processor, so don't
! change mips_arch here. -mno-mips16 overrides -mips16. */
if (mips_no_mips16_string == NULL)
! target_flags |= MASK_MIPS16;
}
! else if (mips_arch_info != 0)
{
! /* -march takes precedence over -mipsN, since it is more descriptive.
! There's no harm in specifying both as long as the ISA levels
! are the same. */
! if (mips_isa != level)
! error ("-mips%d conflicts with the other architecture options, which specify a MIPS%d processor",
! level, mips_isa);
}
else
{
! mips_set_architecture (mips_cpu_info_from_isa (level));
! if (mips_arch_info == 0)
! error ("bad value (%s) for -mips switch", mips_isa_string);
}
}
! if (mips_arch_info == 0)
{
! /* Provisionally select the default processor or ISA level. */
#ifdef MIPS_CPU_STRING_DEFAULT
! mips_set_architecture (mips_parse_cpu ("default CPU",
! MIPS_CPU_STRING_DEFAULT));
! #else
! mips_set_architecture (mips_cpu_info_from_isa (MIPS_ISA_DEFAULT));
#endif
+ }
! if (ABI_NEEDS_64BIT_REGS && !ISA_HAS_64BIT_REGS)
! error ("-march=%s is not compatible with the selected ABI",
! mips_arch_info->name);
! /* Optimize for mips_arch, unless -mtune selects a different processor. */
! if (mips_tune_info == 0)
! mips_set_tune (mips_arch_info);
! if ((target_flags_explicit & MASK_64BIT) != 0)
{
! /* The user specified the size of the integer registers. Make sure
! it agrees with the ABI and ISA. */
! if (TARGET_64BIT && !ISA_HAS_64BIT_REGS)
! error ("-mgp64 used with a 32-bit processor");
! else if (!TARGET_64BIT && ABI_NEEDS_64BIT_REGS)
! error ("-mgp32 used with a 64-bit ABI");
! else if (TARGET_64BIT && ABI_NEEDS_32BIT_REGS)
! error ("-mgp64 used with a 32-bit ABI");
}
else
{
! /* Infer the integer register size from the ABI and processor.
! Restrict ourselves to 32-bit registers if that's all the
! processor has, or if the ABI cannot handle 64-bit registers. */
! if (ABI_NEEDS_32BIT_REGS || !ISA_HAS_64BIT_REGS)
! target_flags &= ~MASK_64BIT;
else
! target_flags |= MASK_64BIT;
! }
+ if ((target_flags_explicit & MASK_FLOAT64) != 0)
+ {
+ /* Really, -mfp32 and -mfp64 are ornamental options. There's
+ only one right answer here. */
+ if (TARGET_64BIT && TARGET_DOUBLE_FLOAT && !TARGET_FLOAT64)
+ error ("unsupported combination: %s", "-mgp64 -mfp32 -mdouble-float");
+ else if (!TARGET_64BIT && TARGET_FLOAT64)
+ error ("unsupported combination: %s", "-mgp32 -mfp64");
+ else if (TARGET_SINGLE_FLOAT && TARGET_FLOAT64)
+ error ("unsupported combination: %s", "-mfp64 -msingle-float");
}
else
{
! /* -msingle-float selects 32-bit float registers. Otherwise the
! float registers should be the same size as the integer ones. */
! if (TARGET_64BIT && TARGET_DOUBLE_FLOAT)
! target_flags |= MASK_FLOAT64;
! else
! target_flags &= ~MASK_FLOAT64;
}
! /* End of code shared with GAS. */
! if ((target_flags_explicit & MASK_LONG64) == 0)
! {
! /* If no type size setting options (-mlong64,-mint64,-mlong32)
! were used, then set the type sizes. In the EABI in 64 bit mode,
! longs and pointers are 64 bits. Likewise for the SGI Irix6 N64
! ABI. */
! if ((mips_abi == ABI_EABI && TARGET_64BIT) || mips_abi == ABI_64)
! target_flags |= MASK_LONG64;
! else
! target_flags &= ~MASK_LONG64;
}
if (mips_abi != ABI_32 && mips_abi != ABI_O64)
*************** mips_asm_file_start (stream)
*** 6361,6367 ****
if (flag_verbose_asm)
fprintf (stream, "\n%s -G value = %d, Arch = %s, ISA = %d\n",
ASM_COMMENT_START,
! mips_section_threshold, mips_arch_string, mips_isa);
}
/* If we are optimizing the global pointer, emit the text section now and any
--- 6329,6335 ----
if (flag_verbose_asm)
fprintf (stream, "\n%s -G value = %d, Arch = %s, ISA = %d\n",
ASM_COMMENT_START,
! mips_section_threshold, mips_arch_info->name, mips_isa);
}
/* If we are optimizing the global pointer, emit the text section now and any
*************** mips_output_conditional_branch (insn,
*** 10166,10280 ****
/* NOTREACHED */
return 0;
}
! static enum processor_type
! mips_parse_cpu (cpu_string)
! const char *cpu_string;
{
! const char *p = cpu_string;
! int seen_v = 0;
! enum processor_type cpu;
! int warn_upper_case = 0;
! /* We need to cope with the various "vr" prefixes for the NEC 4300
! and 4100 processors. */
! if (*p == 'v' || *p == 'V')
! {
! if (*p == 'V')
! warn_upper_case = 1;
! seen_v = 1, p++;
! }
- if (*p == 'r' || *p == 'R')
- {
- if (*p == 'R')
- warn_upper_case = 1;
- p++;
- }
! if (warn_upper_case)
! warning ("the cpu name must be lower case");
! /* Since there is no difference between a R2000 and R3000 in
! terms of the scheduler, we collapse them into just an R3000. */
! cpu = PROCESSOR_DEFAULT;
! switch (*p)
! {
! case '2':
! if (!strcmp (p, "2000") || !strcmp (p, "2k") || !strcmp (p, "2K"))
! cpu = PROCESSOR_R3000;
! else if (!strcmp (p, "20kc") || !strcmp (p, "20Kc") )
! cpu = PROCESSOR_R20KC;
! break;
! case '3':
! if (!strcmp (p, "3000") || !strcmp (p, "3k") || !strcmp (p, "3K"))
! cpu = PROCESSOR_R3000;
! else if (!strcmp (p, "3900"))
! cpu = PROCESSOR_R3900;
! break;
! case '4':
! if (!strcmp (p, "4000") || !strcmp (p, "4k") || !strcmp (p, "4K"))
! cpu = PROCESSOR_R4000;
! /* The vr4100 is a non-FP ISA III processor with some extra
! instructions. */
! else if (!strcmp (p, "4100"))
! cpu = PROCESSOR_R4100;
! /* The vr4300 is a standard ISA III processor, but with a different
! pipeline. */
! else if (!strcmp (p, "4300"))
! cpu = PROCESSOR_R4300;
! /* The r4400 is exactly the same as the r4000 from the compiler's
! viewpoint. */
! else if (!strcmp (p, "4400"))
! cpu = PROCESSOR_R4000;
! else if (!strcmp (p, "4600"))
! cpu = PROCESSOR_R4600;
! else if (!strcmp (p, "4650"))
! cpu = PROCESSOR_R4650;
! /* The 4kc and 4kp processor cores are the same for
! scheduling purposes; they both implement the MIPS32
! ISA and only differ in their memory management
! methods. */
! else if (!strcmp (p, "4kc") || !strcmp (p, "4Kc")
! || !strcmp (p, "4kp") || !strcmp (p, "4Kp") )
! cpu = PROCESSOR_R4KC;
! break;
! case '5':
! if (!strcmp (p, "5000") || !strcmp (p, "5k") || !strcmp (p, "5K"))
! cpu = PROCESSOR_R5000;
! else if (!strcmp (p, "5kc") || !strcmp (p, "5Kc") )
! cpu = PROCESSOR_R5KC;
! break;
- case '6':
- if (!strcmp (p, "6000") || !strcmp (p, "6k") || !strcmp (p, "6K"))
- cpu = PROCESSOR_R6000;
- break;
! case '8':
! if (!strcmp (p, "8000"))
! cpu = PROCESSOR_R8000;
! break;
! case 'o':
! if (!strcmp (p, "orion"))
! cpu = PROCESSOR_R4600;
! break;
! }
! if (seen_v
! && cpu != PROCESSOR_R4300
! && cpu != PROCESSOR_R4100
! && cpu != PROCESSOR_R5000)
! cpu = PROCESSOR_DEFAULT;
! return cpu;
}
/* Adjust the cost of INSN based on the relationship between INSN that
is dependent on DEP_INSN through the dependence LINK. The default
is to make no adjustment to COST.
--- 10134,10253 ----
/* NOTREACHED */
return 0;
}
+
+ /* Return true if GIVEN is the same as CANONICAL, or if it is CANONICAL
+ with a final "000" replaced by "k". Ignore case.
! Note: this function is shared between GCC and GAS. */
!
! static bool
! mips_strict_matching_cpu_name_p (canonical, given)
! const char *canonical, *given;
{
! while (*given != 0 && TOLOWER (*given) == TOLOWER (*canonical))
! given++, canonical++;
! return ((*given == 0 && *canonical == 0)
! || (strcmp (canonical, "000") == 0 && strcasecmp (given, "k") == 0));
! }
! /* Return true if GIVEN matches CANONICAL, where GIVEN is a user-supplied
! CPU name. We've traditionally allowed a lot of variation here.
! Note: this function is shared between GCC and GAS. */
! static bool
! mips_matching_cpu_name_p (canonical, given)
! const char *canonical, *given;
! {
! /* First see if the name matches exactly, or with a final "000"
! turned into "k". */
! if (mips_strict_matching_cpu_name_p (canonical, given))
! return true;
! /* If not, try comparing based on numerical designation alone.
! See if GIVEN is an unadorned number, or 'r' followed by a number. */
! if (TOLOWER (*given) == 'r')
! given++;
! if (!ISDIGIT (*given))
! return false;
! /* Skip over some well-known prefixes in the canonical name,
! hoping to find a number there too. */
! if (TOLOWER (canonical[0]) == 'v' && TOLOWER (canonical[1]) == 'r')
! canonical += 2;
! else if (TOLOWER (canonical[0]) == 'r' && TOLOWER (canonical[1]) == 'm')
! canonical += 2;
! else if (TOLOWER (canonical[0]) == 'r')
! canonical += 1;
! return mips_strict_matching_cpu_name_p (canonical, given);
! }
! /* Parse an option that takes the name of a processor as its argument.
! OPTION is the name of the option and CPU_STRING is the argument.
! Return the corresponding processor enumeration if the CPU_STRING is
! recognized, otherwise report an error and return null.
! A similar function exists in GAS. */
! static const struct mips_cpu_info *
! mips_parse_cpu (option, cpu_string)
! const char *option, *cpu_string;
! {
! const struct mips_cpu_info *p;
! const char *s;
! /* In the past, we allowed upper-case CPU names, but it doesn't
! work well with the multilib machinery. */
! for (s = cpu_string; *s != 0; s++)
! if (ISUPPER (*s))
! {
! warning ("the cpu name must be lower case");
! break;
! }
!
! /* 'from-abi' selects the most compatible architecture for the given
! ABI: MIPS I for 32-bit ABIs and MIPS III for 64-bit ABIs. For the
! EABIs, we have to decide whether we're using the 32-bit or 64-bit
! version. Look first at the -mgp options, if given, otherwise base
! the choice on MASK_64BIT in TARGET_DEFAULT. */
! if (strcasecmp (cpu_string, "from-abi") == 0)
! return mips_cpu_info_from_isa (ABI_NEEDS_32BIT_REGS ? 1
! : ABI_NEEDS_64BIT_REGS ? 3
! : (TARGET_64BIT ? 3 : 1));
!
! /* 'default' has traditionally been a no-op. Probably not very useful. */
! if (strcasecmp (cpu_string, "default") == 0)
! return 0;
!
! for (p = mips_cpu_info_table; p->name != 0; p++)
! if (mips_matching_cpu_name_p (p->name, cpu_string))
! return p;
!
! error ("bad value (%s) for %s", cpu_string, option);
! return 0;
}
+
+ /* Return the processor associated with the given ISA level, or null
+ if the ISA isn't valid. */
+
+ static const struct mips_cpu_info *
+ mips_cpu_info_from_isa (isa)
+ int isa;
+ {
+ const struct mips_cpu_info *p;
+
+ for (p = mips_cpu_info_table; p->name != 0; p++)
+ if (p->isa == isa)
+ return p;
+
+ return 0;
+ }
+
/* Adjust the cost of INSN based on the relationship between INSN that
is dependent on DEP_INSN through the dependence LINK. The default
is to make no adjustment to COST.
*** /dev/null Tue Nov 14 21:44:43 2000
--- testsuite/gcc.dg/mips-args-1.c Fri Jul 19 18:24:45 2002
***************
*** 0 ****
--- 1,35 ----
+ /* Check that certain preprocessor macros are defined, and do some
+ consistency checks. */
+ /* { dg-do compile { target mips*-*-* } } */
+
+ const char *compiled_for = _MIPS_ARCH;
+ const char *optimized_for = _MIPS_TUNE;
+
+ #if __mips_fpr != 32 && __mips_fpr != 64
+ #error Bad __mips_fpr
+ #endif
+
+ /* Test complementary macro pairs: exactly one of each pair
+ must be defined. */
+
+ #if defined (_R3000) == defined (_R4000)
+ #error _R3000 / _R4000 mismatch
+ #endif
+
+ #if defined (__mips_hard_float) == defined (__mips_soft_float)
+ #error __mips_hard_float / __mips_soft_float mismatch
+ #endif
+
+ #if defined (_MIPSEL) == defined (_MIPSEB)
+ #error _MIPSEL / _MIPSEB mismatch
+ #endif
+
+ /* Check for __mips64 consistency. */
+
+ #if defined (__mips64) != defined (_R4000)
+ #error __mips64 / _R4000 mismatch
+ #endif
+
+ #if defined (__mips64) && __mips != 3 && __mips != 4 && __mips != 64
+ #error __mips64 / __mips mismatch
+ #endif
*** /dev/null Tue Nov 14 21:44:43 2000
--- testsuite/gcc.dg/mips-args-2.c Thu Jul 18 14:24:43 2002
***************
*** 0 ****
--- 1,15 ----
+ /* Check the _MIPSEB and _MIPSEL macros are accurate. */
+ /* { dg-do run { target mips*-*-* } } */
+ short foo = 1;
+ int main ()
+ {
+ char *p = (char *) &foo;
+
+ #ifdef _MIPSEB
+ if (p[0] != 0 || p[1] != 1)
+ #else
+ if (p[0] != 1 || p[1] != 0)
+ #endif
+ abort ();
+ exit (0);
+ }
*** /dev/null Tue Nov 14 21:44:43 2000
--- testsuite/gcc.dg/mips-args-3.c Thu Jul 18 14:31:42 2002
***************
*** 0 ****
--- 1,35 ----
+ /* __mips, and related defines, guarantee that certain assembly
+ instructions can be used. Check a few examples. */
+ /* { dg-do run { target mips*-*-* } } */
+ typedef int int32 __attribute__ ((mode (SI)));
+ typedef int int64 __attribute__ ((mode (DI)));
+ int foo (float inf, int64 in64, int32 in32)
+ {
+ int64 res64;
+ int32 res32;
+
+ #if __mips != 1 && defined (__mips_hard_float)
+ __asm__ ("trunc.w.s %0, %1" : "=f" (res32) : "f" (inf));
+ if (res32 != 11)
+ abort ();
+ #endif
+
+ #if defined (__mips64)
+ __asm__ ("daddu %0, %1, %1" : "=r" (res64) : "r" (in64));
+ if (res64 != 50)
+ abort ();
+ #endif
+
+ #if (__mips == 4 || __mips == 32 || __mips == 64) && !defined (__mips16)
+ __asm__ ("move %0,%.\n\tmovn %0,%1,%2"
+ : "=&r" (res32) : "r" (in32), "r" (in64 != 0));
+ if (res32 != 60)
+ abort ();
+ #endif
+ }
+
+ int main ()
+ {
+ foo (11.4f, 25, 60);
+ exit (0);
+ }
Index: htdocs/gcc-3.3/changes.html
===================================================================
RCS file: /cvs/gcc/wwwdocs/htdocs/gcc-3.3/changes.html,v
retrieving revision 1.1
diff -c -d -p -r1.1 changes.html
*** htdocs/gcc-3.3/changes.html 17 Jul 2002 15:37:12 -0000 1.1
--- htdocs/gcc-3.3/changes.html 22 Jul 2002 09:54:56 -0000
***************
*** 148,153 ****
--- 148,174 ----
<li>SH5, SHmedia, little-endian, 64-bit default,
<code>sh64le-*-netbsd*</code></li>
</ul></li>
+ <li>The following changes have been made to the MIPS port:
+ <ul>
+ <li>All configurations now accept the <code>-mabi</code>
+ switch. Note that you will need appropriate multilibs
+ for this option to work properly.</li>
+ <li>ELF configurations will always pass an ABI flag to
+ the assembler.</li>
+ <li><code>-mabi=64</code> no longer selects MIPS IV code.</li>
+ <li>The <code>-mcpu</code> option, which was deprecated
+ in 3.1 and 3.2, has been removed from this release.</li>
+ <li><code>-march</code> now changes the core ISA level.
+ In previous releases, it would change the use of
+ processor-specific extensions, but would leave the core
+ ISA unchanged. For example, <code>mips64-elf
+ -march=r8000</code> will now generate MIPS IV code.</li>
+ <li>Under most configurations, <code>-mipsN</code> now acts as a
+ synonym for <code>-march</code>.</li>
+ <li>There are some new preprocessor macros to describe the
+ <code>-march</code> and <code>-mtune</code> settings.
+ See the documentation of those options for details.</li>
+ </ul></li>
</ul>