enum sparc_arch_types {v6, v7, v8, leon, sparclet, sparclite, sparc86x, v8plus,
v8plusa, v9, v9a, v9b, v9_64};
-/* Hardware capability sets, used to keep sparc_arch_table easy to
- read. */
-#define HWS_V8 HWCAP_MUL32 | HWCAP_DIV32 | HWCAP_FSMULD
-#define HWS_V9 HWS_V8 | HWCAP_POPC
-#define HWS_VA HWS_V9 | HWCAP_VIS
-#define HWS_VB HWS_VA | HWCAP_VIS2
-#define HWS_VC HWS_VB | HWCAP_ASI_BLK_INIT
-#define HWS_VD HWS_VC | HWCAP_FMAF | HWCAP_VIS3 | HWCAP_HPC
-#define HWS_VE HWS_VD \
- | HWCAP_AES | HWCAP_DES | HWCAP_KASUMI | HWCAP_CAMELLIA \
- | HWCAP_MD5 | HWCAP_SHA1 | HWCAP_SHA256 |HWCAP_SHA512 | HWCAP_MPMUL \
- | HWCAP_MONT | HWCAP_CRC32C | HWCAP_CBCOND | HWCAP_PAUSE
-#define HWS_VV HWS_VE | HWCAP_FJFMAU | HWCAP_IMA
-#define HWS_VM HWS_VV
-
-#define HWS2_VM \
- HWCAP2_VIS3B | HWCAP2_ADP | HWCAP2_SPARC5 | HWCAP2_MWAIT \
- | HWCAP2_XMPMUL | HWCAP2_XMONT
-
static struct sparc_arch {
const char *name;
const char *opcode_arch;
int default_arch_size;
/* Allowable arg to -A? */
int user_option_p;
+ /* Extra hardware capabilities allowed. These are added to the
+ hardware capabilities associated with the opcode
+ architecture. */
int hwcap_allowed;
int hwcap2_allowed;
} sparc_arch_table[] = {
{ "v6", "v6", v6, 0, 1, 0, 0 },
{ "v7", "v7", v7, 0, 1, 0, 0 },
- { "v8", "v8", v8, 32, 1, HWS_V8, 0 },
- { "v8a", "v8", v8, 32, 1, HWS_V8, 0 },
- { "sparc", "v9", v9, 0, 1, HWCAP_V8PLUS|HWS_V9, 0 },
- { "sparcvis", "v9a", v9, 0, 1, HWS_VA, 0 },
- { "sparcvis2", "v9b", v9, 0, 1, HWS_VB, 0 },
- { "sparcfmaf", "v9b", v9, 0, 1, HWS_VB|HWCAP_FMAF, 0 },
- { "sparcima", "v9b", v9, 0, 1, HWS_VB|HWCAP_FMAF|HWCAP_IMA, 0 },
- { "sparcvis3", "v9b", v9, 0, 1, HWS_VB|HWCAP_FMAF|HWCAP_VIS3|HWCAP_HPC, 0 },
- { "sparcvis3r", "v9b", v9, 0, 1, HWS_VB|HWCAP_FMAF|HWCAP_VIS3|HWCAP_HPC|HWCAP_FJFMAU, 0 },
-
- { "sparc4", "v9v", v9, 0, 1, HWS_VV, 0 },
- { "sparc5", "v9m", v9, 0, 1, HWS_VM, HWS2_VM },
-
- { "leon", "leon", leon, 32, 1, HWS_V8, 0 },
- { "sparclet", "sparclet", sparclet, 32, 1, HWS_V8, 0 },
- { "sparclite", "sparclite", sparclite, 32, 1, HWS_V8, 0 },
- { "sparc86x", "sparclite", sparc86x, 32, 1, HWS_V8, 0 },
-
- { "v8plus", "v9", v9, 0, 1, HWCAP_V8PLUS|HWS_V9, 0 },
- { "v8plusa", "v9a", v9, 0, 1, HWCAP_V8PLUS|HWS_VA, 0 },
- { "v8plusb", "v9b", v9, 0, 1, HWCAP_V8PLUS|HWS_VB, 0 },
- { "v8plusc", "v9c", v9, 0, 1, HWCAP_V8PLUS|HWS_VC, 0 },
- { "v8plusd", "v9d", v9, 0, 1, HWCAP_V8PLUS|HWS_VD, 0 },
- { "v8pluse", "v9e", v9, 0, 1, HWCAP_V8PLUS|HWS_VE, 0 },
- { "v8plusv", "v9v", v9, 0, 1, HWCAP_V8PLUS|HWS_VV, 0 },
- { "v8plusm", "v9m", v9, 0, 1, HWCAP_V8PLUS|HWS_VM, 0 },
-
- { "v9", "v9", v9, 0, 1, HWS_V9, 0 },
- { "v9a", "v9a", v9, 0, 1, HWS_VA, 0 },
- { "v9b", "v9b", v9, 0, 1, HWS_VB, 0 },
- { "v9c", "v9c", v9, 0, 1, HWS_VC, 0 },
- { "v9d", "v9d", v9, 0, 1, HWS_VD, 0 },
- { "v9e", "v9e", v9, 0, 1, HWS_VE, 0 },
- { "v9v", "v9v", v9, 0, 1, HWS_VV, 0 },
- { "v9m", "v9m", v9, 0, 1, HWS_VM, HWS2_VM },
+ { "v8", "v8", v8, 32, 1, 0, 0 },
+ { "v8a", "v8", v8, 32, 1, 0, 0 },
+ { "sparc", "v9", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "sparcvis", "v9a", v9, 0, 1, 0, 0 },
+ { "sparcvis2", "v9b", v9, 0, 1, 0, 0 },
+ { "sparcfmaf", "v9b", v9, 0, 1, HWCAP_FMAF, 0 },
+ { "sparcima", "v9b", v9, 0, 1, HWCAP_FMAF|HWCAP_IMA, 0 },
+ { "sparcvis3", "v9b", v9, 0, 1, HWCAP_FMAF|HWCAP_VIS3|HWCAP_HPC, 0 },
+ { "sparcvis3r", "v9b", v9, 0, 1, HWCAP_FMAF|HWCAP_VIS3|HWCAP_HPC|HWCAP_FJFMAU, 0 },
+
+ { "sparc4", "v9v", v9, 0, 1, 0, 0 },
+ { "sparc5", "v9m", v9, 0, 1, 0, 0 },
+
+ { "leon", "leon", leon, 32, 1, 0, 0 },
+ { "sparclet", "sparclet", sparclet, 32, 1, 0, 0 },
+ { "sparclite", "sparclite", sparclite, 32, 1, 0, 0 },
+ { "sparc86x", "sparclite", sparc86x, 32, 1, 0, 0 },
+
+ { "v8plus", "v9", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "v8plusa", "v9a", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "v8plusb", "v9b", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "v8plusc", "v9c", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "v8plusd", "v9d", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "v8pluse", "v9e", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "v8plusv", "v9v", v9, 0, 1, HWCAP_V8PLUS, 0 },
+ { "v8plusm", "v9m", v9, 0, 1, HWCAP_V8PLUS, 0 },
+
+ { "v9", "v9", v9, 0, 1, 0, 0 },
+ { "v9a", "v9a", v9, 0, 1, 0, 0 },
+ { "v9b", "v9b", v9, 0, 1, 0, 0 },
+ { "v9c", "v9c", v9, 0, 1, 0, 0 },
+ { "v9d", "v9d", v9, 0, 1, 0, 0 },
+ { "v9e", "v9e", v9, 0, 1, 0, 0 },
+ { "v9v", "v9v", v9, 0, 1, 0, 0 },
+ { "v9m", "v9m", v9, 0, 1, 0, 0 },
/* This exists to allow configure.tgt to pass one
value to specify both the default machine and default word size. */
- { "v9-64", "v9", v9, 64, 0, HWS_V9, 0 },
+ { "v9-64", "v9", v9, 64, 0, 0, 0 },
{ NULL, NULL, v8, 0, 0, 0, 0 }
};
if (!architecture_requested
|| opcode_arch > max_architecture)
max_architecture = opcode_arch;
- hwcap_allowed
- |= (((bfd_uint64_t) sa->hwcap2_allowed) << 32) | sa->hwcap_allowed;
+
+ /* The allowed hardware capabilities are the implied by the
+ opcodes arch plus any extra capabilities defined in the GAS
+ arch. */
+ hwcap_allowed
+ = (hwcap_allowed
+ | (((bfd_uint64_t) sparc_opcode_archs[opcode_arch].hwcaps2) << 32)
+ | (((bfd_uint64_t) sa->hwcap2_allowed) << 32)
+ | sparc_opcode_archs[opcode_arch].hwcaps
+ | sa->hwcap_allowed);
architecture_requested = 1;
}
break;
warn_after_architecture = needed_architecture;
}
current_architecture = needed_architecture;
- hwcap_allowed |= hwcaps;
+ hwcap_allowed
+ = (hwcap_allowed
+ | hwcaps
+ | (((bfd_uint64_t) sparc_opcode_archs[current_architecture].hwcaps2) << 32)
+ | sparc_opcode_archs[current_architecture].hwcaps);
}
/* Conflict. */
/* ??? This seems to be a bit fragile. What if the next entry in
otherwise. */
#define v9notv9a (MASK_V9)
+/* Hardware capability sets, used to keep sparc_opcode_archs easy to
+ read. */
+#define HWS_V8 HWCAP_MUL32 | HWCAP_DIV32 | HWCAP_FSMULD
+#define HWS_V9 HWS_V8 | HWCAP_POPC
+#define HWS_VA HWS_V9 | HWCAP_VIS
+#define HWS_VB HWS_VA | HWCAP_VIS2
+#define HWS_VC HWS_VB | HWCAP_ASI_BLK_INIT
+#define HWS_VD HWS_VC | HWCAP_FMAF | HWCAP_VIS3 | HWCAP_HPC
+#define HWS_VE HWS_VD \
+ | HWCAP_AES | HWCAP_DES | HWCAP_KASUMI | HWCAP_CAMELLIA \
+ | HWCAP_MD5 | HWCAP_SHA1 | HWCAP_SHA256 |HWCAP_SHA512 | HWCAP_MPMUL \
+ | HWCAP_MONT | HWCAP_CRC32C | HWCAP_CBCOND | HWCAP_PAUSE
+#define HWS_VV HWS_VE | HWCAP_FJFMAU | HWCAP_IMA
+#define HWS_VM HWS_VV
+
+#define HWS2_VM \
+ HWCAP2_VIS3B | HWCAP2_ADP | HWCAP2_SPARC5 | HWCAP2_MWAIT \
+ | HWCAP2_XMPMUL | HWCAP2_XMONT
+
/* Table of opcode architectures.
The order is defined in opcode/sparc.h. */
const struct sparc_opcode_arch sparc_opcode_archs[] =
{
- { "v6", MASK_V6 },
- { "v7", MASK_V6 | MASK_V7 },
- { "v8", MASK_V6 | MASK_V7 | MASK_V8 },
- { "leon", MASK_V6 | MASK_V7 | MASK_V8 | MASK_LEON },
- { "sparclet", MASK_V6 | MASK_V7 | MASK_V8 | MASK_SPARCLET },
- { "sparclite", MASK_V6 | MASK_V7 | MASK_V8 | MASK_SPARCLITE },
+ { "v6", MASK_V6, 0, 0 },
+ { "v7", MASK_V6 | MASK_V7, 0, 0 },
+ { "v8", MASK_V6 | MASK_V7 | MASK_V8, HWS_V8, 0 },
+ { "leon", MASK_V6 | MASK_V7 | MASK_V8 | MASK_LEON, HWS_V8, 0 },
+ { "sparclet", MASK_V6 | MASK_V7 | MASK_V8 | MASK_SPARCLET, HWS_V8, 0 },
+ { "sparclite", MASK_V6 | MASK_V7 | MASK_V8 | MASK_SPARCLITE, HWS_V8, 0 },
/* ??? Don't some v8 priviledged insns conflict with v9? */
- { "v9", MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 },
+ { "v9", MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9, HWS_V9, 0 },
/* v9 with ultrasparc additions */
- { "v9a", MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A },
+ { "v9a", MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A, HWS_VA, 0 },
/* v9 with cheetah additions */
- { "v9b", MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A | MASK_V9B },
+ { "v9b", MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A | MASK_V9B, HWS_VB, 0 },
/* v9 with UA2005 and T1 additions. */
{ "v9c", (MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A | MASK_V9B
- | MASK_V9C) },
+ | MASK_V9C), HWS_VC, 0 },
/* v9 with UA2007 and T3 additions. */
{ "v9d", (MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A | MASK_V9B
- | MASK_V9C | MASK_V9D) },
+ | MASK_V9C | MASK_V9D), HWS_VD, 0 },
/* v9 with OSA2011 and T4 additions modulus integer multiply-add. */
{ "v9e", (MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A | MASK_V9B
- | MASK_V9C | MASK_V9D | MASK_V9E) },
+ | MASK_V9C | MASK_V9D | MASK_V9E), HWS_VE, 0 },
/* V9 with OSA2011 and T4 additions, integer multiply and Fujitsu fp
multiply-add. */
{ "v9v", (MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A | MASK_V9B
- | MASK_V9C | MASK_V9D | MASK_V9E | MASK_V9V) },
+ | MASK_V9C | MASK_V9D | MASK_V9E | MASK_V9V), HWS_VV, 0 },
/* v9 with OSA2015 and M7 additions. */
{ "v9m", (MASK_V6 | MASK_V7 | MASK_V8 | MASK_V9 | MASK_V9A | MASK_V9B
- | MASK_V9C | MASK_V9D | MASK_V9E | MASK_V9V | MASK_V9M) },
- { NULL, 0 }
+ | MASK_V9C | MASK_V9D | MASK_V9E | MASK_V9V | MASK_V9M), HWS_VM, HWS2_VM },
+ { NULL, 0, 0, 0 }
};
/* Given NAME, return it's architecture entry. */