📄 i386.h
字号:
/* Definitions of target machine for GNU compiler for Intel X86 (386, 486, Pentium). Copyright (C) 1988, 92, 94, 95, 96, 97, 1998 Free Software Foundation, Inc.This file is part of GNU CC.GNU CC is free software; you can redistribute it and/or modifyit under the terms of the GNU General Public License as published bythe Free Software Foundation; either version 2, or (at your option)any later version.GNU CC is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty ofMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See theGNU General Public License for more details.You should have received a copy of the GNU General Public Licensealong with GNU CC; see the file COPYING. If not, write tothe Free Software Foundation, 59 Temple Place - Suite 330,Boston, MA 02111-1307, USA. *//* The purpose of this file is to define the characteristics of the i386, independent of assembler syntax or operating system. Three other files build on this one to describe a specific assembler syntax: bsd386.h, att386.h, and sun386.h. The actual tm.h file for a particular system should include this file, and then the file for the appropriate assembler syntax. Many macros that specify assembler syntax are omitted entirely from this file because they really belong in the files for particular assemblers. These include AS1, AS2, AS3, RP, IP, LPREFIX, L_SIZE, PUT_OP_SIZE, USE_STAR, ADDR_BEG, ADDR_END, PRINT_IREG, PRINT_SCALE, PRINT_B_I_S, and many that start with ASM_ or end in ASM_OP. *//* Names to predefine in the preprocessor for this target machine. */#define I386 1/* Stubs for half-pic support if not OSF/1 reference platform. */#ifndef HALF_PIC_P#define HALF_PIC_P() 0#define HALF_PIC_NUMBER_PTRS 0#define HALF_PIC_NUMBER_REFS 0#define HALF_PIC_ENCODE(DECL)#define HALF_PIC_DECLARE(NAME)#define HALF_PIC_INIT() error ("half-pic init called on systems that don't support it.")#define HALF_PIC_ADDRESS_P(X) 0#define HALF_PIC_PTR(X) X#define HALF_PIC_FINISH(STREAM)#endif/* Define the specific costs for a given cpu */struct processor_costs { int add; /* cost of an add instruction */ int lea; /* cost of a lea instruction */ int shift_var; /* variable shift costs */ int shift_const; /* constant shift costs */ int mult_init; /* cost of starting a multiply */ int mult_bit; /* cost of multiply per each bit set */ int divide; /* cost of a divide/mod */};extern struct processor_costs *ix86_cost;/* Run-time compilation parameters selecting different hardware subsets. */extern int target_flags;/* Macros used in the machine description to test the flags. *//* configure can arrange to make this 2, to force a 486. */#ifndef TARGET_CPU_DEFAULT#define TARGET_CPU_DEFAULT 0#endif/* Masks for the -m switches */#define MASK_80387 000000000001 /* Hardware floating point */#define MASK_NOTUSED1 000000000002 /* bit not currently used */#define MASK_NOTUSED2 000000000004 /* bit not currently used */#define MASK_RTD 000000000010 /* Use ret that pops args */#define MASK_ALIGN_DOUBLE 000000000020 /* align doubles to 2 word boundary */#define MASK_SVR3_SHLIB 000000000040 /* Uninit locals into bss */#define MASK_IEEE_FP 000000000100 /* IEEE fp comparisons */#define MASK_FLOAT_RETURNS 000000000200 /* Return float in st(0) */#define MASK_NO_FANCY_MATH_387 000000000400 /* Disable sin, cos, sqrt */#define MASK_OMIT_LEAF_FRAME_POINTER 0x00000800 /* omit leaf frame pointers */ /* Temporary codegen switches */#define MASK_DEBUG_ADDR 000001000000 /* Debug GO_IF_LEGITIMATE_ADDRESS */#define MASK_NO_WIDE_MULTIPLY 000002000000 /* Disable 32x32->64 multiplies */#define MASK_NO_MOVE 000004000000 /* Don't generate mem->mem */#define MASK_NO_PSEUDO 000010000000 /* Move op's args -> pseudos */#define MASK_DEBUG_ARG 000020000000 /* Debug function_arg */ #define MASK_SCHEDULE_PROLOGUE 000040000000 /* Emit prologue as rtl */#define MASK_STACK_PROBE 000100000000 /* Enable stack probing *//* Use the floating point instructions */#define TARGET_80387 (target_flags & MASK_80387)/* Compile using ret insn that pops args. This will not work unless you use prototypes at least for all functions that can take varying numbers of args. */ #define TARGET_RTD (target_flags & MASK_RTD)/* Align doubles to a two word boundary. This breaks compatibility with the published ABI's for structures containing doubles, but produces faster code on the pentium. */#define TARGET_ALIGN_DOUBLE (target_flags & MASK_ALIGN_DOUBLE)/* Put uninitialized locals into bss, not data. Meaningful only on svr3. */#define TARGET_SVR3_SHLIB (target_flags & MASK_SVR3_SHLIB)/* Use IEEE floating point comparisons. These handle correctly the cases where the result of a comparison is unordered. Normally SIGFPE is generated in such cases, in which case this isn't needed. */#define TARGET_IEEE_FP (target_flags & MASK_IEEE_FP)/* Functions that return a floating point value may return that value in the 387 FPU or in 386 integer registers. If set, this flag causes the 387 to be used, which is compatible with most calling conventions. */#define TARGET_FLOAT_RETURNS_IN_80387 (target_flags & MASK_FLOAT_RETURNS)/* Disable generation of FP sin, cos and sqrt operations for 387. This is because FreeBSD lacks these in the math-emulator-code */#define TARGET_NO_FANCY_MATH_387 (target_flags & MASK_NO_FANCY_MATH_387)/* Don't create frame pointers for leaf functions */#define TARGET_OMIT_LEAF_FRAME_POINTER (target_flags & MASK_OMIT_LEAF_FRAME_POINTER)/* Temporary switches for tuning code generation *//* Disable 32x32->64 bit multiplies that are used for long long multiplies and division by constants, but sometimes cause reload problems. */#define TARGET_NO_WIDE_MULTIPLY (target_flags & MASK_NO_WIDE_MULTIPLY)#define TARGET_WIDE_MULTIPLY (!TARGET_NO_WIDE_MULTIPLY)/* Emit/Don't emit prologue as rtl */#define TARGET_SCHEDULE_PROLOGUE (target_flags & MASK_SCHEDULE_PROLOGUE)/* Debug GO_IF_LEGITIMATE_ADDRESS */#define TARGET_DEBUG_ADDR (target_flags & MASK_DEBUG_ADDR)/* Debug FUNCTION_ARG macros */#define TARGET_DEBUG_ARG (target_flags & MASK_DEBUG_ARG)/* Hack macros for tuning code generation */#define TARGET_MOVE ((target_flags & MASK_NO_MOVE) == 0) /* Don't generate memory->memory */#define TARGET_PSEUDO ((target_flags & MASK_NO_PSEUDO) == 0) /* Move op's args into pseudos */#define TARGET_386 (ix86_cpu == PROCESSOR_I386)#define TARGET_486 (ix86_cpu == PROCESSOR_I486)#define TARGET_PENTIUM (ix86_cpu == PROCESSOR_PENTIUM)#define TARGET_PENTIUMPRO (ix86_cpu == PROCESSOR_PENTIUMPRO)#define TARGET_K6 (ix86_cpu == PROCESSOR_K6)#define CPUMASK (1 << ix86_cpu)extern const int x86_use_leave, x86_push_memory, x86_zero_extend_with_and;extern const int x86_use_bit_test, x86_cmove, x86_deep_branch;extern const int x86_unroll_strlen, x86_use_q_reg, x86_use_any_reg;extern const int x86_double_with_add;#define TARGET_USE_LEAVE (x86_use_leave & CPUMASK)#define TARGET_PUSH_MEMORY (x86_push_memory & CPUMASK)#define TARGET_ZERO_EXTEND_WITH_AND (x86_zero_extend_with_and & CPUMASK)#define TARGET_USE_BIT_TEST (x86_use_bit_test & CPUMASK)#define TARGET_UNROLL_STRLEN (x86_unroll_strlen & CPUMASK)#define TARGET_USE_Q_REG (x86_use_q_reg & CPUMASK)#define TARGET_USE_ANY_REG (x86_use_any_reg & CPUMASK)#define TARGET_CMOVE (x86_cmove & (1 << ix86_arch))#define TARGET_DEEP_BRANCH_PREDICTION (x86_deep_branch & CPUMASK)#define TARGET_DOUBLE_WITH_ADD (x86_double_with_add & CPUMASK)#define TARGET_STACK_PROBE (target_flags & MASK_STACK_PROBE)#define TARGET_SWITCHES \{ { "80387", MASK_80387, "Use hardware fp" }, \ { "no-80387", -MASK_80387, "Do not use hardware fp" },\ { "hard-float", MASK_80387, "Use hardware fp" }, \ { "soft-float", -MASK_80387, "Do not use hardware fp" },\ { "no-soft-float", MASK_80387, "Use hardware fp" }, \ { "386", 0, "Same as -mcpu=i386" }, \ { "486", 0, "Same as -mcpu=i486" }, \ { "pentium", 0, "Same as -mcpu=pentium" }, \ { "pentiumpro", 0, "Same as -mcpu=pentiumpro" }, \ { "rtd", MASK_RTD, "Alternate calling convention" },\ { "no-rtd", -MASK_RTD, "Use normal calling convention" },\ { "align-double", MASK_ALIGN_DOUBLE, "Align some doubles on dword boundary" },\ { "no-align-double", -MASK_ALIGN_DOUBLE, "Align doubles on word boundary" }, \ { "svr3-shlib", MASK_SVR3_SHLIB, "Uninitialized locals in .bss" }, \ { "no-svr3-shlib", -MASK_SVR3_SHLIB, "Uninitialized locals in .data" }, \ { "ieee-fp", MASK_IEEE_FP, "Use IEEE math for fp comparisons" }, \ { "no-ieee-fp", -MASK_IEEE_FP, "Do not use IEEE math for fp comparisons" }, \ { "fp-ret-in-387", MASK_FLOAT_RETURNS, "Return values of functions in FPU registers" }, \ { "no-fp-ret-in-387", -MASK_FLOAT_RETURNS , "Do not return values of functions in FPU registers"}, \ { "no-fancy-math-387", MASK_NO_FANCY_MATH_387, "Do not generate sin, cos, sqrt for 387" }, \ { "fancy-math-387", -MASK_NO_FANCY_MATH_387, "Generate sin, cos, sqrt for FPU"}, \ { "omit-leaf-frame-pointer", MASK_OMIT_LEAF_FRAME_POINTER, "Omit the frame pointer in leaf functions" }, \ { "no-omit-leaf-frame-pointer",-MASK_OMIT_LEAF_FRAME_POINTER, "" }, \ { "no-wide-multiply", MASK_NO_WIDE_MULTIPLY, "multiplies of 32 bits constrained to 32 bits" }, \ { "wide-multiply", -MASK_NO_WIDE_MULTIPLY, "multiplies of 32 bits are 64 bits" }, \ { "schedule-prologue", MASK_SCHEDULE_PROLOGUE, "Schedule function prologues" }, \ { "no-schedule-prologue", -MASK_SCHEDULE_PROLOGUE, "" }, \ { "debug-addr", MASK_DEBUG_ADDR, 0 /* intentionally undoc */ }, \ { "no-debug-addr", -MASK_DEBUG_ADDR, 0 /* intentionally undoc */ }, \ { "move", -MASK_NO_MOVE, "Generate mem-mem moves" }, \ { "no-move", MASK_NO_MOVE, "Don't generate mem-mem moves" }, \ { "debug-arg", MASK_DEBUG_ARG, 0 /* intentionally undoc */ }, \ { "no-debug-arg", -MASK_DEBUG_ARG, 0 /* intentionally undoc */ }, \ { "stack-arg-probe", MASK_STACK_PROBE, "Enable stack probing" }, \ { "no-stack-arg-probe", -MASK_STACK_PROBE, "" }, \ { "windows", 0, 0 /* intentionally undoc */ }, \ { "dll", 0, 0 /* intentionally undoc */ }, \ SUBTARGET_SWITCHES \ { "", MASK_SCHEDULE_PROLOGUE | TARGET_DEFAULT, 0 }}/* Which processor to schedule for. The cpu attribute defines a list that mirrors this list, so changes to i386.md must be made at the same time. */enum processor_type {PROCESSOR_I386, /* 80386 */ PROCESSOR_I486, /* 80486DX, 80486SX, 80486DX[24] */ PROCESSOR_PENTIUM, PROCESSOR_PENTIUMPRO, PROCESSOR_K6};#define PROCESSOR_I386_STRING "i386"#define PROCESSOR_I486_STRING "i486"#define PROCESSOR_I586_STRING "i586"#define PROCESSOR_PENTIUM_STRING "pentium"#define PROCESSOR_I686_STRING "i686"#define PROCESSOR_PENTIUMPRO_STRING "pentiumpro"#define PROCESSOR_K6_STRING "k6"extern enum processor_type ix86_cpu;extern int ix86_arch;/* Define the default processor. This is overridden by other tm.h files. */#define PROCESSOR_DEFAULT (enum processor_type) TARGET_CPU_DEFAULT#define PROCESSOR_DEFAULT_STRING \ (PROCESSOR_DEFAULT == PROCESSOR_I486 ? PROCESSOR_I486_STRING \ : PROCESSOR_DEFAULT == PROCESSOR_PENTIUM ? PROCESSOR_PENTIUM_STRING \ : PROCESSOR_DEFAULT == PROCESSOR_PENTIUMPRO ? PROCESSOR_PENTIUMPRO_STRING \ : PROCESSOR_DEFAULT == PROCESSOR_K6 ? PROCESSOR_K6_STRING \ : PROCESSOR_I386_STRING)/* This macro is similar to `TARGET_SWITCHES' but defines names of command options that have values. Its definition is an initializer with a subgrouping for each command option. Each subgrouping contains a string constant, that defines the fixed part of the option name, and the address of a variable. The variable, type `char *', is set to the variable part of the given option if the fixed part matches. The actual option name is made by appending `-m' to the specified name. */#define TARGET_OPTIONS \{ { "cpu=", &ix86_cpu_string, "Schedule code for given CPU"}, \ { "arch=", &ix86_arch_string, "Generate code for given CPU"}, \ { "reg-alloc=", &i386_reg_alloc_order, "Control allocation order of integer registers" }, \ { "regparm=", &i386_regparm_string, "Number of registers used to pass integer arguments" }, \ { "align-loops=", &i386_align_loops_string, "Loop code aligned to this power of 2" }, \ { "align-jumps=", &i386_align_jumps_string, "Jump targets are aligned to this power of 2" }, \ { "align-functions=", &i386_align_funcs_string, "Function starts are aligned to this power of 2" }, \ { "preferred-stack-boundary=", &i386_preferred_stack_boundary_string, "Attempt to keep stack aligned to this power of 2" }, \ { "branch-cost=", &i386_branch_cost_string, "Branches are this expensive (1-5, arbitrary units)" }, \ SUBTARGET_OPTIONS \}/* Sometimes certain combinations of command options do not make sense on a particular target machine. You can define a macro `OVERRIDE_OPTIONS' to take account of this. This macro, if defined, is executed once just after all the command options have been parsed. Don't use this macro to turn on various extra optimizations for `-O'. That is what `OPTIMIZATION_OPTIONS' is for. */#define OVERRIDE_OPTIONS override_options ()/* These are meant to be redefined in the host dependent files */#define SUBTARGET_SWITCHES#define SUBTARGET_OPTIONS/* Define this to change the optimizations performed by default. */#define OPTIMIZATION_OPTIONS(LEVEL,SIZE) optimization_options(LEVEL,SIZE)/* Specs for the compiler proper */#ifndef CC1_CPU_SPEC#define CC1_CPU_SPEC "\%{!mcpu*: \%{m386:-mcpu=i386 -march=i386} \%{m486:-mcpu=i486 -march=i486} \%{mpentium:-mcpu=pentium} \%{mpentiumpro:-mcpu=pentiumpro}}"#endif#define CPP_486_SPEC "%{!ansi:-Di486} -D__i486 -D__i486__"#define CPP_586_SPEC "%{!ansi:-Di586 -Dpentium} \ -D__i586 -D__i586__ -D__pentium -D__pentium__"#define CPP_K6_SPEC "%{!ansi:-Di586 -Dk6} \ -D__i586 -D__i586__ -D__k6 -D__k6__" #define CPP_686_SPEC "%{!ansi:-Di686 -Dpentiumpro} \ -D__i686 -D__i686__ -D__pentiumpro -D__pentiumpro__"#ifndef CPP_CPU_DEFAULT_SPEC#if TARGET_CPU_DEFAULT == 1#define CPP_CPU_DEFAULT_SPEC "%(cpp_486)"#endif#if TARGET_CPU_DEFAULT == 2#define CPP_CPU_DEFAULT_SPEC "%(cpp_586)"#endif#if TARGET_CPU_DEFAULT == 3#define CPP_CPU_DEFAULT_SPEC "%(cpp_686)"#endif#if TARGET_CPU_DEFAULT == 4#define CPP_CPU_DEFAULT_SPEC "%(cpp_k6)"#endif#ifndef CPP_CPU_DEFAULT_SPEC#define CPP_CPU_DEFAULT_SPEC ""#endif#endif /* CPP_CPU_DEFAULT_SPEC */#ifndef CPP_CPU_SPEC#define CPP_CPU_SPEC "\-Acpu(i386) -Amachine(i386) \%{!ansi:-Di386} -D__i386 -D__i386__ \%{mcpu=i486:%(cpp_486)} %{m486:%(cpp_486)} \%{mpentium:%(cpp_586)} %{mcpu=pentium:%(cpp_586)} \%{mpentiumpro:%(cpp_686)} %{mcpu=pentiumpro:%(cpp_686)} \%{mcpu=k6:%(cpp_k6)} \%{!mcpu*:%{!m486:%{!mpentium*:%(cpp_cpu_default)}}}"
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -