/* tc-i386.h -- Header file for tc-i386.c
Copyright 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
- 2001, 2002, 2003, 2004, 2005, 2006, 2007
+ 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
Free Software Foundation, Inc.
This file is part of GAS, the GNU Assembler.
#define TARGET_BYTES_BIG_ENDIAN 0
-#define TARGET_ARCH bfd_arch_i386
+#define TARGET_ARCH (i386_arch ())
#define TARGET_MACH (i386_mach ())
+extern enum bfd_architecture i386_arch (void);
extern unsigned long i386_mach (void);
#ifdef TE_FreeBSD
#define ELF_TARGET_FORMAT "elf32-i386-vxworks"
#endif
+#ifdef TE_SOLARIS
+#define ELF_TARGET_FORMAT "elf32-i386-sol2"
+#define ELF_TARGET_FORMAT64 "elf64-x86-64-sol2"
+#endif
+
#ifndef ELF_TARGET_FORMAT
#define ELF_TARGET_FORMAT "elf32-i386"
#endif
#define ELF_TARGET_FORMAT64 "elf64-x86-64"
#endif
+#ifndef ELF_TARGET_FORMAT32
+#define ELF_TARGET_FORMAT32 "elf32-x86-64"
+#endif
+
+#ifndef ELF_TARGET_L1OM_FORMAT
+#define ELF_TARGET_L1OM_FORMAT "elf64-l1om"
+#endif
+
+#ifndef ELF_TARGET_K1OM_FORMAT
+#define ELF_TARGET_K1OM_FORMAT "elf64-k1om"
+#endif
+
#if ((defined (OBJ_MAYBE_COFF) && defined (OBJ_MAYBE_AOUT)) \
- || defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF))
+ || defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF) \
+ || defined (TE_PE) || defined (TE_PEP) || defined (OBJ_MACH_O))
extern const char *i386_target_format (void);
#define TARGET_FORMAT i386_target_format ()
#else
-#ifdef OBJ_ELF
-#define TARGET_FORMAT ELF_TARGET_FORMAT
+#ifdef TE_GO32
+#define TARGET_FORMAT "coff-go32"
#endif
#ifdef OBJ_AOUT
#define TARGET_FORMAT AOUT_TARGET_FORMAT
#define SUB_SEGMENT_ALIGN(SEG, FRCHAIN) 0
+/* '$' may be used as immediate prefix. */
+#undef LOCAL_LABELS_DOLLAR
+#define LOCAL_LABELS_DOLLAR 0
+#undef LOCAL_LABELS_FB
#define LOCAL_LABELS_FB 1
extern const char extra_symbol_chars[];
extern const char *i386_comment_chars;
#define tc_comment_chars i386_comment_chars
-/* Prefixes will be emitted in the order defined below.
- WAIT_PREFIX must be the first prefix since FWAIT is really is an
- instruction, and so must come before any prefixes.
- The preferred prefix order is SEG_PREFIX, ADDR_PREFIX, DATA_PREFIX,
- LOCKREP_PREFIX. */
-#define WAIT_PREFIX 0
-#define SEG_PREFIX 1
-#define ADDR_PREFIX 2
-#define DATA_PREFIX 3
-#define LOCKREP_PREFIX 4
-#define REX_PREFIX 5 /* must come last. */
-#define MAX_PREFIXES 6 /* max prefixes per opcode */
-
-/* we define the syntax here (modulo base,index,scale syntax) */
-#define REGISTER_PREFIX '%'
-#define IMMEDIATE_PREFIX '$'
-#define ABSOLUTE_PREFIX '*'
-
-/* these are the instruction mnemonic suffixes. */
-#define WORD_MNEM_SUFFIX 'w'
-#define BYTE_MNEM_SUFFIX 'b'
-#define SHORT_MNEM_SUFFIX 's'
-#define LONG_MNEM_SUFFIX 'l'
-#define QWORD_MNEM_SUFFIX 'q'
-/* Intel Syntax. Use a non-ascii letter since since it never appears
- in instructions. */
-#define LONG_DOUBLE_MNEM_SUFFIX '\1'
-
-#define END_OF_INSN '\0'
-
-/*
- 'templates' is for grouping together 'template' structures for opcodes
- of the same name. This is only used for storing the insns in the grand
- ole hash table of insns.
- The templates themselves start at START and range up to (but not including)
- END.
- */
-typedef struct
-{
- const template *start;
- const template *end;
-}
-templates;
-
-/* 386 operand encoding bytes: see 386 book for details of this. */
-typedef struct
-{
- unsigned int regmem; /* codes register or memory operand */
- unsigned int reg; /* codes register operand (or extended opcode) */
- unsigned int mode; /* how to interpret regmem & reg */
-}
-modrm_byte;
-
-/* x86-64 extension prefix. */
-typedef int rex_byte;
-
-/* The SSE5 instructions have a two bit instruction modifier (OC) that
- is stored in two separate bytes in the instruction. Pick apart OC
- into the 2 separate bits for instruction. */
-#define DREX_OC0(x) (((x) & 1) != 0)
-#define DREX_OC1(x) (((x) & 2) != 0)
-
-#define DREX_OC0_MASK (1 << 3) /* set OC0 in byte 4 */
-#define DREX_OC1_MASK (1 << 2) /* set OC1 in byte 3 */
-
-/* OC mappings */
-#define DREX_XMEM_X1_X2_X2 0 /* 4 op insn, dest = src3, src1 = reg/mem */
-#define DREX_X1_XMEM_X2_X2 1 /* 4 op insn, dest = src3, src2 = reg/mem */
-#define DREX_X1_XMEM_X2_X1 2 /* 4 op insn, dest = src1, src2 = reg/mem */
-#define DREX_X1_X2_XMEM_X1 3 /* 4 op insn, dest = src1, src3 = reg/mem */
-
-#define DREX_XMEM_X1_X2 0 /* 3 op insn, src1 = reg/mem */
-#define DREX_X1_XMEM_X2 1 /* 3 op insn, src1 = reg/mem */
-
-/* Information needed to create the DREX byte in SSE5 instructions. */
-typedef struct
-{
- unsigned int reg; /* register */
- unsigned int rex; /* REX flags */
- unsigned int modrm_reg; /* which arg goes in the modrm.reg field */
- unsigned int modrm_regmem; /* which arg goes in the modrm.regmem field */
-} drex_byte;
-
-/* 386 opcode byte to code indirect addressing. */
-typedef struct
-{
- unsigned base;
- unsigned index;
- unsigned scale;
-}
-sib_byte;
-
-enum processor_type
-{
- PROCESSOR_UNKNOWN,
- PROCESSOR_I386,
- PROCESSOR_I486,
- PROCESSOR_PENTIUM,
- PROCESSOR_PENTIUMPRO,
- PROCESSOR_PENTIUM4,
- PROCESSOR_NOCONA,
- PROCESSOR_CORE,
- PROCESSOR_CORE2,
- PROCESSOR_K6,
- PROCESSOR_ATHLON,
- PROCESSOR_K8,
- PROCESSOR_GENERIC32,
- PROCESSOR_GENERIC64,
- PROCESSOR_AMDFAM10
-};
-
-/* x86 arch names, types and features */
-typedef struct
-{
- const char *name; /* arch name */
- enum processor_type type; /* arch type */
- i386_cpu_flags flags; /* cpu feature flags */
-}
-arch_entry;
-
/* The name of the global offset table generated by the compiler. Allow
this to be overridden if need be. */
#ifndef GLOBAL_OFFSET_TABLE_NAME
#if (defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF)) && !defined (LEX_AT)
#define TC_PARSE_CONS_EXPRESSION(EXP, NBYTES) x86_cons (EXP, NBYTES)
-extern void x86_cons (expressionS *, int);
#endif
+extern void x86_cons (expressionS *, int);
#define TC_CONS_FIX_NEW(FRAG,OFF,LEN,EXP) x86_cons_fix_new(FRAG, OFF, LEN, EXP)
extern void x86_cons_fix_new
/* This expression evaluates to true if the relocation is for a local
object for which we still want to do the relocation at runtime.
False if we are willing to perform this relocation while building
- the .o file. GOTOFF does not need to be checked here because it is
- not pcrel. I am not sure if some of the others are ever used with
- pcrel, but it is easier to be safe than sorry. */
+ the .o file. GOTOFF and GOT32 do not need to be checked here because
+ they are not pcrel. .*/
#define TC_FORCE_RELOCATION_LOCAL(FIX) \
(!(FIX)->fx_pcrel \
|| (FIX)->fx_r_type == BFD_RELOC_386_PLT32 \
- || (FIX)->fx_r_type == BFD_RELOC_386_GOT32 \
|| (FIX)->fx_r_type == BFD_RELOC_386_GOTPC \
+ || (FIX)->fx_r_type == BFD_RELOC_X86_64_GOTPCREL \
|| TC_FORCE_RELOCATION (FIX))
extern int i386_parse_name (char *, expressionS *, char *);
#define md_parse_name(s, e, m, c) i386_parse_name (s, e, c)
+extern operatorT i386_operator (const char *name, unsigned int operands, char *);
+#define md_operator i386_operator
+
+extern int i386_need_index_operator (void);
+#define md_need_index_operator i386_need_index_operator
+
#define md_register_arithmetic 0
extern const struct relax_type md_relax_table[];
#define md_number_to_chars number_to_chars_littleendian
+enum processor_type
+{
+ PROCESSOR_UNKNOWN,
+ PROCESSOR_I386,
+ PROCESSOR_I486,
+ PROCESSOR_PENTIUM,
+ PROCESSOR_PENTIUMPRO,
+ PROCESSOR_PENTIUM4,
+ PROCESSOR_NOCONA,
+ PROCESSOR_CORE,
+ PROCESSOR_CORE2,
+ PROCESSOR_COREI7,
+ PROCESSOR_L1OM,
+ PROCESSOR_K1OM,
+ PROCESSOR_K6,
+ PROCESSOR_ATHLON,
+ PROCESSOR_K8,
+ PROCESSOR_GENERIC32,
+ PROCESSOR_GENERIC64,
+ PROCESSOR_AMDFAM10,
+ PROCESSOR_BD
+};
+
+extern enum processor_type cpu_arch_tune;
+extern enum processor_type cpu_arch_isa;
+extern i386_cpu_flags cpu_arch_isa_flags;
+
+struct i386_tc_frag_data
+{
+ enum processor_type isa;
+ i386_cpu_flags isa_flags;
+ enum processor_type tune;
+};
+
+/* We need to emit the right NOP pattern in .align frags. This is
+ done after the text-to-bits assembly pass, so we need to mark it with
+ the isa/tune settings at the time the .align was assembled. */
+#define TC_FRAG_TYPE struct i386_tc_frag_data
+
+#define TC_FRAG_INIT(FRAGP) \
+ do \
+ { \
+ (FRAGP)->tc_frag_data.isa = cpu_arch_isa; \
+ (FRAGP)->tc_frag_data.isa_flags = cpu_arch_isa_flags; \
+ (FRAGP)->tc_frag_data.tune = cpu_arch_tune; \
+ } \
+ while (0)
+
#ifdef SCO_ELF
#define tc_init_after_args() sco_id ()
extern void sco_id (void);
extern int x86_cie_data_alignment;
#define DWARF2_CIE_DATA_ALIGNMENT x86_cie_data_alignment
-#define tc_regname_to_dw2regnum tc_x86_regname_to_dw2regnum
-extern int tc_x86_regname_to_dw2regnum (char *);
+#define tc_parse_to_dw2regnum tc_x86_parse_to_dw2regnum
+extern void tc_x86_parse_to_dw2regnum (expressionS *);
#define tc_cfi_frame_initial_instructions tc_x86_frame_initial_instructions
extern void tc_x86_frame_initial_instructions (void);
#define md_elf_section_type(str,len) i386_elf_section_type (str, len)
extern int i386_elf_section_type (const char *, size_t);
+#ifdef TE_SOLARIS
+#define md_fix_up_eh_frame(sec) i386_solaris_fix_up_eh_frame (sec)
+extern void i386_solaris_fix_up_eh_frame (segT);
+#endif
+
/* Support for SHF_X86_64_LARGE */
-extern int x86_64_section_word (char *, size_t);
-extern int x86_64_section_letter (int, char **);
+extern bfd_vma x86_64_section_word (char *, size_t);
+extern bfd_vma x86_64_section_letter (int, char **);
#define md_elf_section_letter(LETTER, PTR_MSG) x86_64_section_letter (LETTER, PTR_MSG)
#define md_elf_section_word(STR, LEN) x86_64_section_word (STR, LEN)
#endif /* TE_PE */
+/* X_add_symbol:X_op_symbol (Intel mode only) */
+#define O_full_ptr O_md2
+
#endif /* TC_I386 */