X-Git-Url: http://git.sourceforge.jp/view?a=blobdiff_plain;f=gcc%2Fconfig%2Fi386%2Fi386.h;h=ee1fbbc27651be8547e25f562b7a953de1a86939;hb=e174638ff04a9c48151382a725c55994a8a8d558;hp=d1f5dd95f563a350f6b38ea797122530c3a33c86;hpb=43e4a084f6bba2151bbad13a71324ecf18957a10;p=pf3gnuchains%2Fgcc-fork.git diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h index d1f5dd95f56..ee1fbbc2765 100644 --- a/gcc/config/i386/i386.h +++ b/gcc/config/i386/i386.h @@ -1,6 +1,7 @@ /* Definitions of target machine for GCC for IA-32. Copyright (C) 1988, 1992, 1994, 1995, 1996, 1997, 1998, 1999, 2000, - 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc. + 2001, 2002, 2003, 2004, 2005, 2006, 2007 Free Software Foundation, + Inc. This file is part of GCC. @@ -34,6 +35,55 @@ Boston, MA 02110-1301, USA. */ ADDR_BEG, ADDR_END, PRINT_IREG, PRINT_SCALE, PRINT_B_I_S, and many that start with ASM_ or end in ASM_OP. */ +/* Redefines for option macros. */ + +#define TARGET_64BIT OPTION_ISA_64BIT +#define TARGET_MMX OPTION_ISA_MMX +#define TARGET_3DNOW OPTION_ISA_3DNOW +#define TARGET_3DNOW_A OPTION_ISA_3DNOW_A +#define TARGET_SSE OPTION_ISA_SSE +#define TARGET_SSE2 OPTION_ISA_SSE2 +#define TARGET_SSE3 OPTION_ISA_SSE3 +#define TARGET_SSSE3 OPTION_ISA_SSSE3 +#define TARGET_SSE4_1 OPTION_ISA_SSE4_1 +#define TARGET_SSE4_2 OPTION_ISA_SSE4_2 +#define TARGET_SSE4A OPTION_ISA_SSE4A + +#include "config/vxworks-dummy.h" + +/* Algorithm to expand string function with. */ +enum stringop_alg +{ + no_stringop, + libcall, + rep_prefix_1_byte, + rep_prefix_4_byte, + rep_prefix_8_byte, + loop_1_byte, + loop, + unrolled_loop +}; + +#define NAX_STRINGOP_ALGS 4 + +/* Specify what algorithm to use for stringops on known size. + When size is unknown, the UNKNOWN_SIZE alg is used. When size is + known at compile time or estimated via feedback, the SIZE array + is walked in order until MAX is greater then the estimate (or -1 + means infinity). Corresponding ALG is used then. + For example initializer: + {{256, loop}, {-1, rep_prefix_4_byte}} + will use loop for blocks smaller or equal to 256 bytes, rep prefix will + be used otherwise. */ +struct stringop_algs +{ + const enum stringop_alg unknown_size; + const struct stringop_strategy { + const int max; + const enum stringop_alg alg; + } size [NAX_STRINGOP_ALGS]; +}; + /* Define the specific costs for a given cpu */ struct processor_costs { @@ -84,6 +134,9 @@ struct processor_costs { const int fabs; /* cost of FABS instruction. */ const int fchs; /* cost of FCHS instruction. */ const int fsqrt; /* cost of FSQRT instruction. */ + /* Specify what algorithm + to use for stringops on unknown size. */ + struct stringop_algs memcpy[2], memset[2]; }; extern const struct processor_costs *ix86_cost; @@ -93,11 +146,7 @@ extern const struct processor_costs *ix86_cost; /* configure can arrange to make this 2, to force a 486. */ #ifndef TARGET_CPU_DEFAULT -#ifdef TARGET_64BIT_DEFAULT -#define TARGET_CPU_DEFAULT TARGET_CPU_DEFAULT_k8 -#else -#define TARGET_CPU_DEFAULT 0 -#endif +#define TARGET_CPU_DEFAULT TARGET_CPU_DEFAULT_generic #endif #ifndef TARGET_FPMATH_DEFAULT @@ -134,101 +183,202 @@ extern const struct processor_costs *ix86_cost; #define TARGET_486 (ix86_tune == PROCESSOR_I486) #define TARGET_PENTIUM (ix86_tune == PROCESSOR_PENTIUM) #define TARGET_PENTIUMPRO (ix86_tune == PROCESSOR_PENTIUMPRO) +#define TARGET_GEODE (ix86_tune == PROCESSOR_GEODE) #define TARGET_K6 (ix86_tune == PROCESSOR_K6) #define TARGET_ATHLON (ix86_tune == PROCESSOR_ATHLON) #define TARGET_PENTIUM4 (ix86_tune == PROCESSOR_PENTIUM4) #define TARGET_K8 (ix86_tune == PROCESSOR_K8) #define TARGET_ATHLON_K8 (TARGET_K8 || TARGET_ATHLON) #define TARGET_NOCONA (ix86_tune == PROCESSOR_NOCONA) +#define TARGET_CORE2 (ix86_tune == PROCESSOR_CORE2) +#define TARGET_GENERIC32 (ix86_tune == PROCESSOR_GENERIC32) +#define TARGET_GENERIC64 (ix86_tune == PROCESSOR_GENERIC64) +#define TARGET_GENERIC (TARGET_GENERIC32 || TARGET_GENERIC64) +#define TARGET_AMDFAM10 (ix86_tune == PROCESSOR_AMDFAM10) + +/* Feature tests against the various tunings. */ +enum ix86_tune_indices { + X86_TUNE_USE_LEAVE, + X86_TUNE_PUSH_MEMORY, + X86_TUNE_ZERO_EXTEND_WITH_AND, + X86_TUNE_USE_BIT_TEST, + X86_TUNE_UNROLL_STRLEN, + X86_TUNE_DEEP_BRANCH_PREDICTION, + X86_TUNE_BRANCH_PREDICTION_HINTS, + X86_TUNE_DOUBLE_WITH_ADD, + X86_TUNE_USE_SAHF, + X86_TUNE_MOVX, + X86_TUNE_PARTIAL_REG_STALL, + X86_TUNE_PARTIAL_FLAG_REG_STALL, + X86_TUNE_USE_HIMODE_FIOP, + X86_TUNE_USE_SIMODE_FIOP, + X86_TUNE_USE_MOV0, + X86_TUNE_USE_CLTD, + X86_TUNE_USE_XCHGB, + X86_TUNE_SPLIT_LONG_MOVES, + X86_TUNE_READ_MODIFY_WRITE, + X86_TUNE_READ_MODIFY, + X86_TUNE_PROMOTE_QIMODE, + X86_TUNE_FAST_PREFIX, + X86_TUNE_SINGLE_STRINGOP, + X86_TUNE_QIMODE_MATH, + X86_TUNE_HIMODE_MATH, + X86_TUNE_PROMOTE_QI_REGS, + X86_TUNE_PROMOTE_HI_REGS, + X86_TUNE_ADD_ESP_4, + X86_TUNE_ADD_ESP_8, + X86_TUNE_SUB_ESP_4, + X86_TUNE_SUB_ESP_8, + X86_TUNE_INTEGER_DFMODE_MOVES, + X86_TUNE_PARTIAL_REG_DEPENDENCY, + X86_TUNE_SSE_PARTIAL_REG_DEPENDENCY, + X86_TUNE_SSE_UNALIGNED_MOVE_OPTIMAL, + X86_TUNE_SSE_SPLIT_REGS, + X86_TUNE_SSE_TYPELESS_STORES, + X86_TUNE_SSE_LOAD0_BY_PXOR, + X86_TUNE_MEMORY_MISMATCH_STALL, + X86_TUNE_PROLOGUE_USING_MOVE, + X86_TUNE_EPILOGUE_USING_MOVE, + X86_TUNE_SHIFT1, + X86_TUNE_USE_FFREEP, + X86_TUNE_INTER_UNIT_MOVES, + X86_TUNE_FOUR_JUMP_LIMIT, + X86_TUNE_SCHEDULE, + X86_TUNE_USE_BT, + X86_TUNE_USE_INCDEC, + X86_TUNE_PAD_RETURNS, + X86_TUNE_EXT_80387_CONSTANTS, + X86_TUNE_SHORTEN_X87_SSE, + X86_TUNE_AVOID_VECTOR_DECODE, + X86_TUNE_PROMOTE_HIMODE_IMUL, + X86_TUNE_SLOW_IMUL_IMM32_MEM, + X86_TUNE_SLOW_IMUL_IMM8, + X86_TUNE_MOVE_M1_VIA_OR, + X86_TUNE_NOT_UNPAIRABLE, + X86_TUNE_NOT_VECTORMODE, + + X86_TUNE_LAST +}; + +extern unsigned int ix86_tune_features[X86_TUNE_LAST]; + +#define TARGET_USE_LEAVE ix86_tune_features[X86_TUNE_USE_LEAVE] +#define TARGET_PUSH_MEMORY ix86_tune_features[X86_TUNE_PUSH_MEMORY] +#define TARGET_ZERO_EXTEND_WITH_AND \ + ix86_tune_features[X86_TUNE_ZERO_EXTEND_WITH_AND] +#define TARGET_USE_BIT_TEST ix86_tune_features[X86_TUNE_USE_BIT_TEST] +#define TARGET_UNROLL_STRLEN ix86_tune_features[X86_TUNE_UNROLL_STRLEN] +#define TARGET_DEEP_BRANCH_PREDICTION \ + ix86_tune_features[X86_TUNE_DEEP_BRANCH_PREDICTION] +#define TARGET_BRANCH_PREDICTION_HINTS \ + ix86_tune_features[X86_TUNE_BRANCH_PREDICTION_HINTS] +#define TARGET_DOUBLE_WITH_ADD ix86_tune_features[X86_TUNE_DOUBLE_WITH_ADD] +#define TARGET_USE_SAHF ix86_tune_features[X86_TUNE_USE_SAHF] +#define TARGET_MOVX ix86_tune_features[X86_TUNE_MOVX] +#define TARGET_PARTIAL_REG_STALL ix86_tune_features[X86_TUNE_PARTIAL_REG_STALL] +#define TARGET_PARTIAL_FLAG_REG_STALL \ + ix86_tune_features[X86_TUNE_PARTIAL_FLAG_REG_STALL] +#define TARGET_USE_HIMODE_FIOP ix86_tune_features[X86_TUNE_USE_HIMODE_FIOP] +#define TARGET_USE_SIMODE_FIOP ix86_tune_features[X86_TUNE_USE_SIMODE_FIOP] +#define TARGET_USE_MOV0 ix86_tune_features[X86_TUNE_USE_MOV0] +#define TARGET_USE_CLTD ix86_tune_features[X86_TUNE_USE_CLTD] +#define TARGET_USE_XCHGB ix86_tune_features[X86_TUNE_USE_XCHGB] +#define TARGET_SPLIT_LONG_MOVES ix86_tune_features[X86_TUNE_SPLIT_LONG_MOVES] +#define TARGET_READ_MODIFY_WRITE ix86_tune_features[X86_TUNE_READ_MODIFY_WRITE] +#define TARGET_READ_MODIFY ix86_tune_features[X86_TUNE_READ_MODIFY] +#define TARGET_PROMOTE_QImode ix86_tune_features[X86_TUNE_PROMOTE_QIMODE] +#define TARGET_FAST_PREFIX ix86_tune_features[X86_TUNE_FAST_PREFIX] +#define TARGET_SINGLE_STRINGOP ix86_tune_features[X86_TUNE_SINGLE_STRINGOP] +#define TARGET_QIMODE_MATH ix86_tune_features[X86_TUNE_QIMODE_MATH] +#define TARGET_HIMODE_MATH ix86_tune_features[X86_TUNE_HIMODE_MATH] +#define TARGET_PROMOTE_QI_REGS ix86_tune_features[X86_TUNE_PROMOTE_QI_REGS] +#define TARGET_PROMOTE_HI_REGS ix86_tune_features[X86_TUNE_PROMOTE_HI_REGS] +#define TARGET_ADD_ESP_4 ix86_tune_features[X86_TUNE_ADD_ESP_4] +#define TARGET_ADD_ESP_8 ix86_tune_features[X86_TUNE_ADD_ESP_8] +#define TARGET_SUB_ESP_4 ix86_tune_features[X86_TUNE_SUB_ESP_4] +#define TARGET_SUB_ESP_8 ix86_tune_features[X86_TUNE_SUB_ESP_8] +#define TARGET_INTEGER_DFMODE_MOVES \ + ix86_tune_features[X86_TUNE_INTEGER_DFMODE_MOVES] +#define TARGET_PARTIAL_REG_DEPENDENCY \ + ix86_tune_features[X86_TUNE_PARTIAL_REG_DEPENDENCY] +#define TARGET_SSE_PARTIAL_REG_DEPENDENCY \ + ix86_tune_features[X86_TUNE_SSE_PARTIAL_REG_DEPENDENCY] +#define TARGET_SSE_UNALIGNED_MOVE_OPTIMAL \ + ix86_tune_features[X86_TUNE_SSE_UNALIGNED_MOVE_OPTIMAL] +#define TARGET_SSE_SPLIT_REGS ix86_tune_features[X86_TUNE_SSE_SPLIT_REGS] +#define TARGET_SSE_TYPELESS_STORES \ + ix86_tune_features[X86_TUNE_SSE_TYPELESS_STORES] +#define TARGET_SSE_LOAD0_BY_PXOR ix86_tune_features[X86_TUNE_SSE_LOAD0_BY_PXOR] +#define TARGET_MEMORY_MISMATCH_STALL \ + ix86_tune_features[X86_TUNE_MEMORY_MISMATCH_STALL] +#define TARGET_PROLOGUE_USING_MOVE \ + ix86_tune_features[X86_TUNE_PROLOGUE_USING_MOVE] +#define TARGET_EPILOGUE_USING_MOVE \ + ix86_tune_features[X86_TUNE_EPILOGUE_USING_MOVE] +#define TARGET_SHIFT1 ix86_tune_features[X86_TUNE_SHIFT1] +#define TARGET_USE_FFREEP ix86_tune_features[X86_TUNE_USE_FFREEP] +#define TARGET_INTER_UNIT_MOVES ix86_tune_features[X86_TUNE_INTER_UNIT_MOVES] +#define TARGET_FOUR_JUMP_LIMIT ix86_tune_features[X86_TUNE_FOUR_JUMP_LIMIT] +#define TARGET_SCHEDULE ix86_tune_features[X86_TUNE_SCHEDULE] +#define TARGET_USE_BT ix86_tune_features[X86_TUNE_USE_BT] +#define TARGET_USE_INCDEC ix86_tune_features[X86_TUNE_USE_INCDEC] +#define TARGET_PAD_RETURNS ix86_tune_features[X86_TUNE_PAD_RETURNS] +#define TARGET_EXT_80387_CONSTANTS \ + ix86_tune_features[X86_TUNE_EXT_80387_CONSTANTS] +#define TARGET_SHORTEN_X87_SSE ix86_tune_features[X86_TUNE_SHORTEN_X87_SSE] +#define TARGET_AVOID_VECTOR_DECODE \ + ix86_tune_features[X86_TUNE_AVOID_VECTOR_DECODE] +#define TARGET_TUNE_PROMOTE_HIMODE_IMUL \ + ix86_tune_features[X86_TUNE_PROMOTE_HIMODE_IMUL] +#define TARGET_SLOW_IMUL_IMM32_MEM \ + ix86_tune_features[X86_TUNE_SLOW_IMUL_IMM32_MEM] +#define TARGET_SLOW_IMUL_IMM8 ix86_tune_features[X86_TUNE_SLOW_IMUL_IMM8] +#define TARGET_MOVE_M1_VIA_OR ix86_tune_features[X86_TUNE_MOVE_M1_VIA_OR] +#define TARGET_NOT_UNPAIRABLE ix86_tune_features[X86_TUNE_NOT_UNPAIRABLE] +#define TARGET_NOT_VECTORMODE ix86_tune_features[X86_TUNE_NOT_VECTORMODE] + +/* Feature tests against the various architecture variations. */ +enum ix86_arch_indices { + X86_ARCH_CMOVE, /* || TARGET_SSE */ + X86_ARCH_CMPXCHG, + X86_ARCH_CMPXCHG8B, + X86_ARCH_XADD, + X86_ARCH_BSWAP, + + X86_ARCH_LAST +}; + +extern unsigned int ix86_arch_features[X86_ARCH_LAST]; + +#define TARGET_CMOVE ix86_arch_features[X86_ARCH_CMOVE] +#define TARGET_CMPXCHG ix86_arch_features[X86_ARCH_CMPXCHG] +#define TARGET_CMPXCHG8B ix86_arch_features[X86_ARCH_CMPXCHG8B] +#define TARGET_XADD ix86_arch_features[X86_ARCH_XADD] +#define TARGET_BSWAP ix86_arch_features[X86_ARCH_BSWAP] + +#define TARGET_FISTTP (TARGET_SSE3 && TARGET_80387) -#define TUNEMASK (1 << ix86_tune) -extern const int x86_use_leave, x86_push_memory, x86_zero_extend_with_and; -extern const int x86_use_bit_test, x86_cmove, x86_fisttp, x86_deep_branch; -extern const int x86_branch_hints, x86_unroll_strlen; -extern const int x86_double_with_add, x86_partial_reg_stall, x86_movx; -extern const int x86_use_himode_fiop, x86_use_simode_fiop; -extern const int x86_use_mov0, x86_use_cltd, x86_read_modify_write; -extern const int x86_read_modify, x86_split_long_moves; -extern const int x86_promote_QImode, x86_single_stringop, x86_fast_prefix; -extern const int x86_himode_math, x86_qimode_math, x86_promote_qi_regs; -extern const int x86_promote_hi_regs, x86_integer_DFmode_moves; -extern const int x86_add_esp_4, x86_add_esp_8, x86_sub_esp_4, x86_sub_esp_8; -extern const int x86_partial_reg_dependency, x86_memory_mismatch_stall; -extern const int x86_accumulate_outgoing_args, x86_prologue_using_move; -extern const int x86_epilogue_using_move, x86_decompose_lea; -extern const int x86_arch_always_fancy_math_387, x86_shift1; -extern const int x86_sse_partial_reg_dependency, x86_sse_split_regs; -extern const int x86_sse_typeless_stores, x86_sse_load0_by_pxor; -extern const int x86_use_ffreep; -extern const int x86_inter_unit_moves, x86_schedule; -extern const int x86_use_bt; -extern const int x86_cmpxchg, x86_xadd; extern int x86_prefetch_sse; -#define TARGET_USE_LEAVE (x86_use_leave & TUNEMASK) -#define TARGET_PUSH_MEMORY (x86_push_memory & TUNEMASK) -#define TARGET_ZERO_EXTEND_WITH_AND (x86_zero_extend_with_and & TUNEMASK) -#define TARGET_USE_BIT_TEST (x86_use_bit_test & TUNEMASK) -#define TARGET_UNROLL_STRLEN (x86_unroll_strlen & TUNEMASK) -/* For sane SSE instruction set generation we need fcomi instruction. It is - safe to enable all CMOVE instructions. */ -#define TARGET_CMOVE ((x86_cmove & (1 << ix86_arch)) || TARGET_SSE) -#define TARGET_FISTTP (x86_fisttp & (1 << ix86_arch)) -#define TARGET_DEEP_BRANCH_PREDICTION (x86_deep_branch & TUNEMASK) -#define TARGET_BRANCH_PREDICTION_HINTS (x86_branch_hints & TUNEMASK) -#define TARGET_DOUBLE_WITH_ADD (x86_double_with_add & TUNEMASK) -#define TARGET_USE_SAHF ((x86_use_sahf & TUNEMASK) && !TARGET_64BIT) -#define TARGET_MOVX (x86_movx & TUNEMASK) -#define TARGET_PARTIAL_REG_STALL (x86_partial_reg_stall & TUNEMASK) -#define TARGET_USE_HIMODE_FIOP (x86_use_himode_fiop & TUNEMASK) -#define TARGET_USE_SIMODE_FIOP (x86_use_simode_fiop & TUNEMASK) -#define TARGET_USE_MOV0 (x86_use_mov0 & TUNEMASK) -#define TARGET_USE_CLTD (x86_use_cltd & TUNEMASK) -#define TARGET_SPLIT_LONG_MOVES (x86_split_long_moves & TUNEMASK) -#define TARGET_READ_MODIFY_WRITE (x86_read_modify_write & TUNEMASK) -#define TARGET_READ_MODIFY (x86_read_modify & TUNEMASK) -#define TARGET_PROMOTE_QImode (x86_promote_QImode & TUNEMASK) -#define TARGET_FAST_PREFIX (x86_fast_prefix & TUNEMASK) -#define TARGET_SINGLE_STRINGOP (x86_single_stringop & TUNEMASK) -#define TARGET_QIMODE_MATH (x86_qimode_math & TUNEMASK) -#define TARGET_HIMODE_MATH (x86_himode_math & TUNEMASK) -#define TARGET_PROMOTE_QI_REGS (x86_promote_qi_regs & TUNEMASK) -#define TARGET_PROMOTE_HI_REGS (x86_promote_hi_regs & TUNEMASK) -#define TARGET_ADD_ESP_4 (x86_add_esp_4 & TUNEMASK) -#define TARGET_ADD_ESP_8 (x86_add_esp_8 & TUNEMASK) -#define TARGET_SUB_ESP_4 (x86_sub_esp_4 & TUNEMASK) -#define TARGET_SUB_ESP_8 (x86_sub_esp_8 & TUNEMASK) -#define TARGET_INTEGER_DFMODE_MOVES (x86_integer_DFmode_moves & TUNEMASK) -#define TARGET_PARTIAL_REG_DEPENDENCY (x86_partial_reg_dependency & TUNEMASK) -#define TARGET_SSE_PARTIAL_REG_DEPENDENCY \ - (x86_sse_partial_reg_dependency & TUNEMASK) -#define TARGET_SSE_SPLIT_REGS (x86_sse_split_regs & TUNEMASK) -#define TARGET_SSE_TYPELESS_STORES (x86_sse_typeless_stores & TUNEMASK) -#define TARGET_SSE_LOAD0_BY_PXOR (x86_sse_load0_by_pxor & TUNEMASK) -#define TARGET_MEMORY_MISMATCH_STALL (x86_memory_mismatch_stall & TUNEMASK) -#define TARGET_PROLOGUE_USING_MOVE (x86_prologue_using_move & TUNEMASK) -#define TARGET_EPILOGUE_USING_MOVE (x86_epilogue_using_move & TUNEMASK) -#define TARGET_DECOMPOSE_LEA (x86_decompose_lea & TUNEMASK) -#define TARGET_PREFETCH_SSE (x86_prefetch_sse) -#define TARGET_SHIFT1 (x86_shift1 & TUNEMASK) -#define TARGET_USE_FFREEP (x86_use_ffreep & TUNEMASK) -#define TARGET_REP_MOVL_OPTIMAL (x86_rep_movl_optimal & TUNEMASK) -#define TARGET_INTER_UNIT_MOVES (x86_inter_unit_moves & TUNEMASK) -#define TARGET_FOUR_JUMP_LIMIT (x86_four_jump_limit & TUNEMASK) -#define TARGET_SCHEDULE (x86_schedule & TUNEMASK) -#define TARGET_USE_BT (x86_use_bt & TUNEMASK) - -#define ASSEMBLER_DIALECT (ix86_asm_dialect) - -#define TARGET_SSE_MATH ((ix86_fpmath & FPMATH_SSE) != 0) -#define TARGET_MIX_SSE_I387 ((ix86_fpmath & FPMATH_SSE) \ - && (ix86_fpmath & FPMATH_387)) - -#define TARGET_GNU_TLS (ix86_tls_dialect == TLS_DIALECT_GNU) -#define TARGET_SUN_TLS (ix86_tls_dialect == TLS_DIALECT_SUN) - -#define TARGET_CMPXCHG (x86_cmpxchg & (1 << ix86_arch)) -#define TARGET_XADD (x86_xadd & (1 << ix86_arch)) +#define TARGET_ABM x86_abm +#define TARGET_CMPXCHG16B x86_cmpxchg16b +#define TARGET_POPCNT x86_popcnt +#define TARGET_PREFETCH_SSE x86_prefetch_sse +#define TARGET_SAHF x86_sahf +#define TARGET_RECIP x86_recip + +#define ASSEMBLER_DIALECT (ix86_asm_dialect) + +#define TARGET_SSE_MATH ((ix86_fpmath & FPMATH_SSE) != 0) +#define TARGET_MIX_SSE_I387 \ + ((ix86_fpmath & (FPMATH_SSE | FPMATH_387)) == (FPMATH_SSE | FPMATH_387)) + +#define TARGET_GNU_TLS (ix86_tls_dialect == TLS_DIALECT_GNU) +#define TARGET_GNU2_TLS (ix86_tls_dialect == TLS_DIALECT_GNU2) +#define TARGET_ANY_GNU_TLS (TARGET_GNU_TLS || TARGET_GNU2_TLS) +#define TARGET_SUN_TLS (ix86_tls_dialect == TLS_DIALECT_SUN) + +extern int ix86_isa_flags; #ifndef TARGET_64BIT_DEFAULT #define TARGET_64BIT_DEFAULT 0 @@ -237,16 +387,36 @@ extern int x86_prefetch_sse; #define TARGET_TLS_DIRECT_SEG_REFS_DEFAULT 0 #endif +/* Fence to use after loop using storent. */ + +extern tree x86_mfence; +#define FENCE_FOLLOWING_MOVNT x86_mfence + /* Once GDB has been enhanced to deal with functions without frame pointers, we can change this to allow for elimination of the frame pointer in leaf functions. */ #define TARGET_DEFAULT 0 +/* Extra bits to force. */ +#define TARGET_SUBTARGET_DEFAULT 0 +#define TARGET_SUBTARGET_ISA_DEFAULT 0 + +/* Extra bits to force on w/ 32-bit mode. */ +#define TARGET_SUBTARGET32_DEFAULT 0 +#define TARGET_SUBTARGET32_ISA_DEFAULT 0 + +/* Extra bits to force on w/ 64-bit mode. */ +#define TARGET_SUBTARGET64_DEFAULT 0 +#define TARGET_SUBTARGET64_ISA_DEFAULT 0 + /* This is not really a target flag, but is done this way so that it's analogous to similar code for Mach-O on PowerPC. darwin.h redefines this to 1. */ #define TARGET_MACHO 0 +/* Likewise, for the Windows 64-bit ABI. */ +#define TARGET_64BIT_MS_ABI 0 + /* Subtargets may reset this to 1 in order to enable 96-bit long double with the rounding mode forced to 53 bits. */ #define TARGET_96_ROUND_53_LONG_DOUBLE 0 @@ -266,32 +436,45 @@ extern int x86_prefetch_sse; #define OPTIMIZATION_OPTIONS(LEVEL, SIZE) \ optimization_options ((LEVEL), (SIZE)) -/* Support for configure-time defaults of some command line options. */ +/* -march=native handling only makes sense with compiler running on + an x86 or x86_64 chip. If changing this condition, also change + the condition in driver-i386.c. */ +#if defined(__i386__) || defined(__x86_64__) +/* In driver-i386.c. */ +extern const char *host_detect_local_cpu (int argc, const char **argv); +#define EXTRA_SPEC_FUNCTIONS \ + { "local_cpu_detect", host_detect_local_cpu }, +#define HAVE_LOCAL_CPU_DETECT +#endif + +/* Support for configure-time defaults of some command line options. + The order here is important so that -march doesn't squash the + tune or cpu values. */ #define OPTION_DEFAULT_SPECS \ - {"arch", "%{!march=*:-march=%(VALUE)}"}, \ {"tune", "%{!mtune=*:%{!mcpu=*:%{!march=*:-mtune=%(VALUE)}}}" }, \ - {"cpu", "%{!mtune=*:%{!mcpu=*:%{!march=*:-mtune=%(VALUE)}}}" } + {"cpu", "%{!mtune=*:%{!mcpu=*:%{!march=*:-mtune=%(VALUE)}}}" }, \ + {"arch", "%{!march=*:-march=%(VALUE)}"} /* Specs for the compiler proper */ #ifndef CC1_CPU_SPEC -#define CC1_CPU_SPEC "\ -%{!mtune*: \ -%{m386:mtune=i386 \ -%n`-m386' is deprecated. Use `-march=i386' or `-mtune=i386' instead.\n} \ -%{m486:-mtune=i486 \ -%n`-m486' is deprecated. Use `-march=i486' or `-mtune=i486' instead.\n} \ -%{mpentium:-mtune=pentium \ -%n`-mpentium' is deprecated. Use `-march=pentium' or `-mtune=pentium' instead.\n} \ -%{mpentiumpro:-mtune=pentiumpro \ -%n`-mpentiumpro' is deprecated. Use `-march=pentiumpro' or `-mtune=pentiumpro' instead.\n} \ +#define CC1_CPU_SPEC_1 "\ %{mcpu=*:-mtune=%* \ -%n`-mcpu=' is deprecated. Use `-mtune=' or '-march=' instead.\n}} \ +%n`-mcpu=' is deprecated. Use `-mtune=' or '-march=' instead.\n} \ % STACK_BOUNDARY && !TARGET_64BIT) +/* Target OS keeps a vector-aligned (128-bit, 16-byte) stack. This is + mandatory for the 64-bit ABI, and may or may not be true for other + operating systems. */ +#define TARGET_KEEPS_VECTOR_ALIGNED_STACK TARGET_64BIT + /* Minimum allocation boundary for the code of a function. */ #define FUNCTION_BOUNDARY 8 @@ -575,7 +799,7 @@ extern int x86_prefetch_sse; /* Decide whether a variable of mode MODE should be 128 bit aligned. */ #define ALIGN_MODE_128(MODE) \ - ((MODE) == XFmode || (MODE) == TFmode || SSE_REG_MODE_P (MODE)) + ((MODE) == XFmode || SSE_REG_MODE_P (MODE)) /* The published ABIs say that doubles should be aligned on word boundaries, so lower the alignment for structure fields unless @@ -658,7 +882,9 @@ extern int x86_prefetch_sse; #define STACK_REGS #define IS_STACK_MODE(MODE) \ - ((MODE) == DFmode || (MODE) == SFmode || (MODE) == XFmode) \ + (((MODE) == SFmode && (!TARGET_SSE || !TARGET_SSE_MATH)) \ + || ((MODE) == DFmode && (!TARGET_SSE2 || !TARGET_SSE_MATH)) \ + || (MODE) == XFmode) /* Number of actual hardware registers. The hardware registers are assigned numbers for the compiler @@ -696,8 +922,8 @@ extern int x86_prefetch_sse; #define FIXED_REGISTERS \ /*ax,dx,cx,bx,si,di,bp,sp,st,st1,st2,st3,st4,st5,st6,st7*/ \ { 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, \ -/*arg,flags,fpsr,dir,frame*/ \ - 1, 1, 1, 1, 1, \ +/*arg,flags,fpsr,fpcr,frame*/ \ + 1, 1, 1, 1, 1, \ /*xmm0,xmm1,xmm2,xmm3,xmm4,xmm5,xmm6,xmm7*/ \ 0, 0, 0, 0, 0, 0, 0, 0, \ /*mmx0,mmx1,mmx2,mmx3,mmx4,mmx5,mmx6,mmx7*/ \ @@ -724,10 +950,10 @@ extern int x86_prefetch_sse; #define CALL_USED_REGISTERS \ /*ax,dx,cx,bx,si,di,bp,sp,st,st1,st2,st3,st4,st5,st6,st7*/ \ { 1, 1, 1, 0, 3, 3, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, \ -/*arg,flags,fpsr,dir,frame*/ \ - 1, 1, 1, 1, 1, \ +/*arg,flags,fpsr,fpcr,frame*/ \ + 1, 1, 1, 1, 1, \ /*xmm0,xmm1,xmm2,xmm3,xmm4,xmm5,xmm6,xmm7*/ \ - 1, 1, 1, 1, 1, 1, 1, 1, \ + 1, 1, 1, 1, 1, 1, 1, 1, \ /*mmx0,mmx1,mmx2,mmx3,mmx4,mmx5,mmx6,mmx7*/ \ 1, 1, 1, 1, 1, 1, 1, 1, \ /* r8, r9, r10, r11, r12, r13, r14, r15*/ \ @@ -752,7 +978,7 @@ extern int x86_prefetch_sse; /* ORDER_REGS_FOR_LOCAL_ALLOC is a macro which permits reg_alloc_order to be rearranged based on a particular function. When using sse math, - we want to allocate SSE before x87 registers and vice vera. */ + we want to allocate SSE before x87 registers and vice versa. */ #define ORDER_REGS_FOR_LOCAL_ALLOC x86_order_regs_for_local_alloc () @@ -761,6 +987,7 @@ extern int x86_prefetch_sse; #define CONDITIONAL_REGISTER_USAGE \ do { \ int i; \ + unsigned int j; \ for (i = 0; i < FIRST_PSEUDO_REGISTER; i++) \ { \ if (fixed_regs[i] > 1) \ @@ -769,10 +996,11 @@ do { \ call_used_regs[i] = (call_used_regs[i] \ == (TARGET_64BIT ? 3 : 2)); \ } \ - if (PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM) \ + j = PIC_OFFSET_TABLE_REGNUM; \ + if (j != INVALID_REGNUM) \ { \ - fixed_regs[PIC_OFFSET_TABLE_REGNUM] = 1; \ - call_used_regs[PIC_OFFSET_TABLE_REGNUM] = 1; \ + fixed_regs[j] = 1; \ + call_used_regs[j] = 1; \ } \ if (! TARGET_MMX) \ { \ @@ -805,6 +1033,11 @@ do { \ for (i = FIRST_REX_SSE_REG; i <= LAST_REX_SSE_REG; i++) \ reg_names[i] = ""; \ } \ + if (TARGET_64BIT_MS_ABI) \ + { \ + call_used_regs[4 /*RSI*/] = 0; \ + call_used_regs[5 /*RDI*/] = 0; \ + } \ } while (0) /* Return number of consecutive hard regs needed starting at reg REGNO @@ -826,6 +1059,15 @@ do { \ ? (TARGET_64BIT ? 4 : 6) \ : ((GET_MODE_SIZE (MODE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD))) +#define HARD_REGNO_NREGS_HAS_PADDING(REGNO, MODE) \ + ((TARGET_128BIT_LONG_DOUBLE && !TARGET_64BIT) \ + ? (FP_REGNO_P (REGNO) || SSE_REGNO_P (REGNO) || MMX_REGNO_P (REGNO) \ + ? 0 \ + : ((MODE) == XFmode || (MODE) == XCmode)) \ + : 0) + +#define HARD_REGNO_NREGS_WITH_PADDING(REGNO, MODE) ((MODE) == XFmode ? 4 : 8) + #define VALID_SSE2_REG_MODE(MODE) \ ((MODE) == V16QImode || (MODE) == V8HImode || (MODE) == V2DFmode \ || (MODE) == V2DImode || (MODE) == DFmode) @@ -1018,7 +1260,7 @@ do { \ opcode needs reg %ebx. But some systems pass args to the OS in ebx, and the "b" register constraint is useful in asms for syscalls. - The flags and fpsr registers are in no class. */ + The flags, fpsr and fpcr registers are in no class. */ enum reg_class { @@ -1032,6 +1274,7 @@ enum reg_class GENERAL_REGS, /* %eax %ebx %ecx %edx %esi %edi %ebp %esp %r8 - %r15*/ FP_TOP_REG, FP_SECOND_REG, /* %st(0) %st(1) */ FLOAT_REGS, + SSE_FIRST_REG, SSE_REGS, MMX_REGS, FP_TOP_SSE_REGS, @@ -1050,7 +1293,7 @@ enum reg_class #define FLOAT_CLASS_P(CLASS) \ reg_class_subset_p ((CLASS), FLOAT_REGS) #define SSE_CLASS_P(CLASS) \ - ((CLASS) == SSE_REGS) + reg_class_subset_p ((CLASS), SSE_REGS) #define MMX_CLASS_P(CLASS) \ ((CLASS) == MMX_REGS) #define MAYBE_INTEGER_CLASS_P(CLASS) \ @@ -1078,6 +1321,7 @@ enum reg_class "GENERAL_REGS", \ "FP_TOP_REG", "FP_SECOND_REG", \ "FLOAT_REGS", \ + "SSE_FIRST_REG", \ "SSE_REGS", \ "MMX_REGS", \ "FP_TOP_SSE_REGS", \ @@ -1101,15 +1345,16 @@ enum reg_class { 0x0f, 0x0 }, /* Q_REGS */ \ { 0x1100f0, 0x1fe0 }, /* NON_Q_REGS */ \ { 0x7f, 0x1fe0 }, /* INDEX_REGS */ \ - { 0x1100ff, 0x0 }, /* LEGACY_REGS */ \ + { 0x1100ff, 0x0 }, /* LEGACY_REGS */ \ { 0x1100ff, 0x1fe0 }, /* GENERAL_REGS */ \ { 0x100, 0x0 }, { 0x0200, 0x0 },/* FP_TOP_REG, FP_SECOND_REG */\ { 0xff00, 0x0 }, /* FLOAT_REGS */ \ + { 0x200000, 0x0 }, /* SSE_FIRST_REG */ \ { 0x1fe00000,0x1fe000 }, /* SSE_REGS */ \ { 0xe0000000, 0x1f }, /* MMX_REGS */ \ { 0x1fe00100,0x1fe000 }, /* FP_TOP_SSE_REG */ \ { 0x1fe00200,0x1fe000 }, /* FP_SECOND_SSE_REG */ \ -{ 0x1fe0ff00,0x1fe000 }, /* FLOAT_SSE_REGS */ \ +{ 0x1fe0ff00,0x3fe000 }, /* FLOAT_SSE_REGS */ \ { 0x1ffff, 0x1fe0 }, /* FLOAT_INT_REGS */ \ { 0x1fe100ff,0x1fffe0 }, /* INT_SSE_REGS */ \ { 0x1fe1ffff,0x1fffe0 }, /* FLOAT_INT_SSE_REGS */ \ @@ -1129,51 +1374,47 @@ enum reg_class #define SMALL_REGISTER_CLASSES 1 -#define QI_REG_P(X) \ - (REG_P (X) && REGNO (X) < 4) +#define QI_REG_P(X) (REG_P (X) && REGNO (X) < 4) #define GENERAL_REGNO_P(N) \ - ((N) < 8 || REX_INT_REGNO_P (N)) + ((N) <= STACK_POINTER_REGNUM || REX_INT_REGNO_P (N)) #define GENERAL_REG_P(X) \ (REG_P (X) && GENERAL_REGNO_P (REGNO (X))) #define ANY_QI_REG_P(X) (TARGET_64BIT ? GENERAL_REG_P(X) : QI_REG_P (X)) -#define NON_QI_REG_P(X) \ - (REG_P (X) && REGNO (X) >= 4 && REGNO (X) < FIRST_PSEUDO_REGISTER) - -#define REX_INT_REGNO_P(N) ((N) >= FIRST_REX_INT_REG && (N) <= LAST_REX_INT_REG) +#define REX_INT_REGNO_P(N) \ + IN_RANGE ((N), FIRST_REX_INT_REG, LAST_REX_INT_REG) #define REX_INT_REG_P(X) (REG_P (X) && REX_INT_REGNO_P (REGNO (X))) #define FP_REG_P(X) (REG_P (X) && FP_REGNO_P (REGNO (X))) -#define FP_REGNO_P(N) ((N) >= FIRST_STACK_REG && (N) <= LAST_STACK_REG) +#define FP_REGNO_P(N) IN_RANGE ((N), FIRST_STACK_REG, LAST_STACK_REG) #define ANY_FP_REG_P(X) (REG_P (X) && ANY_FP_REGNO_P (REGNO (X))) #define ANY_FP_REGNO_P(N) (FP_REGNO_P (N) || SSE_REGNO_P (N)) -#define SSE_REGNO_P(N) \ - (((N) >= FIRST_SSE_REG && (N) <= LAST_SSE_REG) \ - || ((N) >= FIRST_REX_SSE_REG && (N) <= LAST_REX_SSE_REG)) +#define X87_FLOAT_MODE_P(MODE) \ + (TARGET_80387 && ((MODE) == SFmode || (MODE) == DFmode || (MODE) == XFmode)) + +#define SSE_REG_P(N) (REG_P (N) && SSE_REGNO_P (REGNO (N))) +#define SSE_REGNO_P(N) \ + (IN_RANGE ((N), FIRST_SSE_REG, LAST_SSE_REG) \ + || REX_SSE_REGNO_P (N)) #define REX_SSE_REGNO_P(N) \ - ((N) >= FIRST_REX_SSE_REG && (N) <= LAST_REX_SSE_REG) + IN_RANGE ((N), FIRST_REX_SSE_REG, LAST_REX_SSE_REG) #define SSE_REGNO(N) \ ((N) < 8 ? FIRST_SSE_REG + (N) : FIRST_REX_SSE_REG + (N) - 8) -#define SSE_REG_P(N) (REG_P (N) && SSE_REGNO_P (REGNO (N))) #define SSE_FLOAT_MODE_P(MODE) \ ((TARGET_SSE && (MODE) == SFmode) || (TARGET_SSE2 && (MODE) == DFmode)) -#define MMX_REGNO_P(N) ((N) >= FIRST_MMX_REG && (N) <= LAST_MMX_REG) #define MMX_REG_P(XOP) (REG_P (XOP) && MMX_REGNO_P (REGNO (XOP))) +#define MMX_REGNO_P(N) IN_RANGE ((N), FIRST_MMX_REG, LAST_MMX_REG) -#define STACK_REG_P(XOP) \ - (REG_P (XOP) && \ - REGNO (XOP) >= FIRST_STACK_REG && \ - REGNO (XOP) <= LAST_STACK_REG) - -#define NON_STACK_REG_P(XOP) (REG_P (XOP) && ! STACK_REG_P (XOP)) +#define STACK_REG_P(XOP) (REG_P (XOP) && STACK_REGNO_P (REGNO (XOP))) +#define STACK_REGNO_P(N) IN_RANGE ((N), FIRST_STACK_REG, LAST_STACK_REG) #define STACK_TOP_P(XOP) (REG_P (XOP) && REGNO (XOP) == FIRST_STACK_REG) @@ -1185,92 +1426,6 @@ enum reg_class #define INDEX_REG_CLASS INDEX_REGS #define BASE_REG_CLASS GENERAL_REGS -/* Unused letters: - B TU W - h jk vw z -*/ - -/* Get reg_class from a letter such as appears in the machine description. */ - -#define REG_CLASS_FROM_LETTER(C) \ - ((C) == 'r' ? GENERAL_REGS : \ - (C) == 'R' ? LEGACY_REGS : \ - (C) == 'q' ? TARGET_64BIT ? GENERAL_REGS : Q_REGS : \ - (C) == 'Q' ? Q_REGS : \ - (C) == 'f' ? (TARGET_80387 || TARGET_FLOAT_RETURNS_IN_80387 \ - ? FLOAT_REGS \ - : NO_REGS) : \ - (C) == 't' ? (TARGET_80387 || TARGET_FLOAT_RETURNS_IN_80387 \ - ? FP_TOP_REG \ - : NO_REGS) : \ - (C) == 'u' ? (TARGET_80387 || TARGET_FLOAT_RETURNS_IN_80387 \ - ? FP_SECOND_REG \ - : NO_REGS) : \ - (C) == 'a' ? AREG : \ - (C) == 'b' ? BREG : \ - (C) == 'c' ? CREG : \ - (C) == 'd' ? DREG : \ - (C) == 'x' ? TARGET_SSE ? SSE_REGS : NO_REGS : \ - (C) == 'Y' ? TARGET_SSE2? SSE_REGS : NO_REGS : \ - (C) == 'y' ? TARGET_MMX ? MMX_REGS : NO_REGS : \ - (C) == 'A' ? AD_REGS : \ - (C) == 'D' ? DIREG : \ - (C) == 'S' ? SIREG : \ - (C) == 'l' ? INDEX_REGS : \ - NO_REGS) - -/* The letters I, J, K, L, M, N, and O in a register constraint string - can be used to stand for particular ranges of immediate operands. - This macro defines what the ranges are. - C is the letter, and VALUE is a constant value. - Return 1 if VALUE is in the range specified by C. - - I is for non-DImode shifts. - J is for DImode shifts. - K is for signed imm8 operands. - L is for andsi as zero-extending move. - M is for shifts that can be executed by the "lea" opcode. - N is for immediate operands for out/in instructions (0-255) - O is for TImode shifts. - */ - -#define CONST_OK_FOR_LETTER_P(VALUE, C) \ - ((C) == 'I' ? (VALUE) >= 0 && (VALUE) <= 31 \ - : (C) == 'J' ? (VALUE) >= 0 && (VALUE) <= 63 \ - : (C) == 'K' ? (VALUE) >= -128 && (VALUE) <= 127 \ - : (C) == 'L' ? (VALUE) == 0xff || (VALUE) == 0xffff \ - : (C) == 'M' ? (VALUE) >= 0 && (VALUE) <= 3 \ - : (C) == 'N' ? (VALUE) >= 0 && (VALUE) <= 255 \ - : (C) == 'O' ? (VALUE) >= 0 && (VALUE) <= 127 \ - : 0) - -/* Similar, but for floating constants, and defining letters G and H. - Here VALUE is the CONST_DOUBLE rtx itself. We allow constants even if - TARGET_387 isn't set, because the stack register converter may need to - load 0.0 into the function value register. */ - -#define CONST_DOUBLE_OK_FOR_LETTER_P(VALUE, C) \ - ((C) == 'G' ? standard_80387_constant_p (VALUE) \ - : 0) - -/* A C expression that defines the optional machine-dependent - constraint letters that can be used to segregate specific types of - operands, usually memory references, for the target machine. Any - letter that is not elsewhere defined and not matched by - `REG_CLASS_FROM_LETTER' may be used. Normally this macro will not - be defined. - - If it is required for a particular target machine, it should - return 1 if VALUE corresponds to the operand type represented by - the constraint letter C. If C is not defined as an extra - constraint, the value returned should be 0 regardless of VALUE. */ - -#define EXTRA_CONSTRAINT(VALUE, D) \ - ((D) == 'e' ? x86_64_immediate_operand (VALUE, VOIDmode) \ - : (D) == 'Z' ? x86_64_zext_immediate_operand (VALUE, VOIDmode) \ - : (D) == 'C' ? standard_sse_constant_p (VALUE) \ - : 0) - /* Place additional restrictions on the register class to use when it is necessary to be able to hold a value of mode MODE in a reload register for which class CLASS would ordinarily be used. */ @@ -1297,6 +1452,12 @@ enum reg_class #define PREFERRED_RELOAD_CLASS(X, CLASS) \ ix86_preferred_reload_class ((X), (CLASS)) +/* Discourage putting floating-point values in SSE registers unless + SSE math is being used, and likewise for the 387 registers. */ + +#define PREFERRED_OUTPUT_RELOAD_CLASS(X, CLASS) \ + ix86_preferred_output_reload_class ((X), (CLASS)) + /* If we are copying between general and FP registers, we need a memory location. The same is true for SSE and MMX registers. */ #define SECONDARY_MEMORY_NEEDED(CLASS1, CLASS2, MODE) \ @@ -1359,7 +1520,7 @@ enum reg_class makes the stack pointer a smaller address. */ #define STACK_GROWS_DOWNWARD -/* Define this to non-zero if the nominal address of the stack frame +/* Define this to nonzero if the nominal address of the stack frame is at the high-address end of the local variables; that is, each additional local variable allocated goes at a more negative offset in the frame. */ @@ -1373,9 +1534,10 @@ enum reg_class /* If we generate an insn to push BYTES bytes, this says how many the stack pointer really advances by. - On 386 pushw decrements by exactly 2 no matter what the position was. - On the 386 there is no pushb; we use pushw instead, and this - has the effect of rounding up to 2. + On 386, we have pushw instruction that decrements by exactly 2 no + matter what the position was, there is no pushb. + But as CIE data alignment factor on this arch is -4, we need to make + sure all stack pointer adjustments are in multiple of 4. For 64bit ABI we round up to 8 bytes. */ @@ -1383,7 +1545,7 @@ enum reg_class #define PUSH_ROUNDING(BYTES) \ (TARGET_64BIT \ ? (((BYTES) + 7) & (-8)) \ - : (((BYTES) + 1) & (-2))) + : (((BYTES) + 3) & (-4))) /* If defined, the maximum amount of space required for outgoing arguments will be computed and placed into the variable @@ -1600,26 +1762,15 @@ typedef struct ix86_args { #define REGNO_OK_FOR_INDEX_P(REGNO) \ ((REGNO) < STACK_POINTER_REGNUM \ - || (REGNO >= FIRST_REX_INT_REG \ - && (REGNO) <= LAST_REX_INT_REG) \ - || ((unsigned) reg_renumber[(REGNO)] >= FIRST_REX_INT_REG \ - && (unsigned) reg_renumber[(REGNO)] <= LAST_REX_INT_REG) \ - || (unsigned) reg_renumber[(REGNO)] < STACK_POINTER_REGNUM) + || REX_INT_REGNO_P (REGNO) \ + || (unsigned) reg_renumber[(REGNO)] < STACK_POINTER_REGNUM \ + || REX_INT_REGNO_P ((unsigned) reg_renumber[(REGNO)])) #define REGNO_OK_FOR_BASE_P(REGNO) \ - ((REGNO) <= STACK_POINTER_REGNUM \ + (GENERAL_REGNO_P (REGNO) \ || (REGNO) == ARG_POINTER_REGNUM \ || (REGNO) == FRAME_POINTER_REGNUM \ - || (REGNO >= FIRST_REX_INT_REG \ - && (REGNO) <= LAST_REX_INT_REG) \ - || ((unsigned) reg_renumber[(REGNO)] >= FIRST_REX_INT_REG \ - && (unsigned) reg_renumber[(REGNO)] <= LAST_REX_INT_REG) \ - || (unsigned) reg_renumber[(REGNO)] <= STACK_POINTER_REGNUM) - -#define REGNO_OK_FOR_SIREG_P(REGNO) \ - ((REGNO) == 4 || reg_renumber[(REGNO)] == 4) -#define REGNO_OK_FOR_DIREG_P(REGNO) \ - ((REGNO) == 5 || reg_renumber[(REGNO)] == 5) + || GENERAL_REGNO_P ((unsigned) reg_renumber[(REGNO)])) /* The macros REG_OK_FOR..._P assume that the arg is a REG rtx and check its validity for a certain class. @@ -1638,16 +1789,13 @@ typedef struct ix86_args { /* Non strict versions, pseudos are ok. */ #define REG_OK_FOR_INDEX_NONSTRICT_P(X) \ (REGNO (X) < STACK_POINTER_REGNUM \ - || (REGNO (X) >= FIRST_REX_INT_REG \ - && REGNO (X) <= LAST_REX_INT_REG) \ + || REX_INT_REGNO_P (REGNO (X)) \ || REGNO (X) >= FIRST_PSEUDO_REGISTER) #define REG_OK_FOR_BASE_NONSTRICT_P(X) \ - (REGNO (X) <= STACK_POINTER_REGNUM \ + (GENERAL_REGNO_P (REGNO (X)) \ || REGNO (X) == ARG_POINTER_REGNUM \ || REGNO (X) == FRAME_POINTER_REGNUM \ - || (REGNO (X) >= FIRST_REX_INT_REG \ - && REGNO (X) <= LAST_REX_INT_REG) \ || REGNO (X) >= FIRST_PSEUDO_REGISTER) /* Strict versions, hard registers only */ @@ -1738,8 +1886,6 @@ do { \ goto WIN; \ } while (0) -#define REWRITE_ADDRESS(X) rewrite_address (X) - /* Nonzero if the constant value X is a legitimate general operand when generating PIC code. It is given that flag_pic is on and that X satisfies CONSTANT_P or is a CONST_DOUBLE. */ @@ -1754,13 +1900,9 @@ do { \ /* Go to LABEL if ADDR (a legitimate address expression) has an effect that depends on the machine mode it is used for. On the 80386, only postdecrement and postincrement address depend thus - (the amount of decrement or increment being the length of the operand). */ -#define GO_IF_MODE_DEPENDENT_ADDRESS(ADDR, LABEL) \ -do { \ - if (GET_CODE (ADDR) == POST_INC \ - || GET_CODE (ADDR) == POST_DEC) \ - goto LABEL; \ -} while (0) + (the amount of decrement or increment being the length of the operand). + These are now caught in recog.c. */ +#define GO_IF_MODE_DEPENDENT_ADDRESS(ADDR, LABEL) /* Max number of args passed in registers. If this is more than 3, we will have problems with ebx (register #4), since it is a caller save register and @@ -1776,17 +1918,12 @@ do { \ /* Specify the machine mode that this machine uses for the index in the tablejump instruction. */ -#define CASE_VECTOR_MODE (!TARGET_64BIT || flag_pic ? SImode : DImode) +#define CASE_VECTOR_MODE \ + (!TARGET_64BIT || (flag_pic && ix86_cmodel != CM_LARGE_PIC) ? SImode : DImode) /* Define this as 1 if `char' should by default be signed; else as 0. */ #define DEFAULT_SIGNED_CHAR 1 -/* Number of bytes moved into a data cache for a single prefetch operation. */ -#define PREFETCH_BLOCK ix86_cost->prefetch_block - -/* Number of prefetch operations that can be done in parallel. */ -#define SIMULTANEOUS_PREFETCHES ix86_cost->simultaneous_prefetches - /* Max number of bytes we can move from memory to memory in one reasonably fast instruction. */ #define MOVE_MAX 16 @@ -1943,7 +2080,7 @@ do { \ /* How to refer to registers in assembler output. This sequence is indexed by compiler's hard-register-number (see above). */ -/* In order to refer to the first 8 regs as 32 bit regs, prefix an "e". +/* In order to refer to the first 8 regs as 32-bit regs, prefix an "e". For non floating point regs, the following are the HImode names. For float regs, the stack top is sometimes referred to as "%st(0)" @@ -1952,9 +2089,9 @@ do { \ #define HI_REGISTER_NAMES \ {"ax","dx","cx","bx","si","di","bp","sp", \ "st","st(1)","st(2)","st(3)","st(4)","st(5)","st(6)","st(7)", \ - "argp", "flags", "fpsr", "dirflag", "frame", \ + "argp", "flags", "fpsr", "fpcr", "frame", \ "xmm0","xmm1","xmm2","xmm3","xmm4","xmm5","xmm6","xmm7", \ - "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7" , \ + "mm0", "mm1", "mm2", "mm3", "mm4", "mm5", "mm6", "mm7", \ "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", \ "xmm8", "xmm9", "xmm10", "xmm11", "xmm12", "xmm13", "xmm14", "xmm15"} @@ -2023,9 +2160,7 @@ extern int const svr4_dbx_register_map[FIRST_PSEUDO_REGISTER]; Whether or not a particular assembler allows us to enter such, I guess we'll have to see. */ #define ASM_PREFERRED_EH_DATA_FORMAT(CODE, GLOBAL) \ - (flag_pic \ - ? ((GLOBAL) ? DW_EH_PE_indirect : 0) | DW_EH_PE_pcrel | DW_EH_PE_sdata4\ - : DW_EH_PE_absptr) + asm_preferred_eh_data_format ((CODE), (GLOBAL)) /* This is how to output an insn to push a register on the stack. It need not be very fast code. */ @@ -2061,11 +2196,13 @@ do { \ #define ASM_OUTPUT_ADDR_DIFF_ELT(FILE, BODY, VALUE, REL) \ ix86_output_addr_diff_elt ((FILE), (VALUE), (REL)) -/* Under some conditions we need jump tables in the text section, because - the assembler cannot handle label differences between sections. */ +/* Under some conditions we need jump tables in the text section, + because the assembler cannot handle label differences between + sections. This is the case for x86_64 on Mach-O for example. */ #define JUMP_TABLES_IN_TEXT_SECTION \ - (!TARGET_64BIT && flag_pic && !HAVE_AS_GOTOFF_IN_DATA) + (flag_pic && ((TARGET_MACHO && TARGET_64BIT) \ + || (!TARGET_64BIT && !HAVE_AS_GOTOFF_IN_DATA))) /* Switch to init or fini section via SECTION_OP, emit a call to FUNC, and switch back. For x86 we do this only to save a few bytes that @@ -2094,13 +2231,6 @@ do { \ if (! output_addr_const_extra (FILE, (X))) \ goto FAIL; \ } while (0); - -/* a letter which is not needed by the normal asm syntax, which - we can use for operand syntax in the extended asm */ - -#define ASM_OPERAND_LETTER '#' -#define RET return "" -#define AT_SP(MODE) (gen_rtx_MEM ((MODE), stack_pointer_rtx)) /* 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. */ @@ -2111,11 +2241,16 @@ enum processor_type PROCESSOR_I486, /* 80486DX, 80486SX, 80486DX[24] */ PROCESSOR_PENTIUM, PROCESSOR_PENTIUMPRO, + PROCESSOR_GEODE, PROCESSOR_K6, PROCESSOR_ATHLON, PROCESSOR_PENTIUM4, PROCESSOR_K8, PROCESSOR_NOCONA, + PROCESSOR_CORE2, + PROCESSOR_GENERIC32, + PROCESSOR_GENERIC64, + PROCESSOR_AMDFAM10, PROCESSOR_max }; @@ -2133,6 +2268,7 @@ extern enum fpmath_unit ix86_fpmath; enum tls_dialect { TLS_DIALECT_GNU, + TLS_DIALECT_GNU2, TLS_DIALECT_SUN }; @@ -2145,7 +2281,8 @@ enum cmodel { CM_MEDIUM, /* Assumes code fits in the low 31 bits; data unlimited. */ CM_LARGE, /* No assumptions. */ CM_SMALL_PIC, /* Assumes code+data+got/plt fits in a 31 bit region. */ - CM_MEDIUM_PIC /* Assumes code+got/plt fits in a 31 bit region. */ + CM_MEDIUM_PIC,/* Assumes code+got/plt fits in a 31 bit region. */ + CM_LARGE_PIC /* No assumptions. */ }; extern enum cmodel ix86_cmodel; @@ -2195,7 +2332,7 @@ enum ix86_entity MAX_386_ENTITIES }; -enum ix86_stack_slot +enum ix86_stack_slot { SLOT_TEMP = 0, SLOT_CW_STORED, @@ -2253,17 +2390,16 @@ enum ix86_stack_slot ??? Maybe Pentium chips benefits from renaming, someone can try.... */ #define HARD_REGNO_RENAME_OK(SRC, TARGET) \ - ((SRC) < FIRST_STACK_REG || (SRC) > LAST_STACK_REG) + (! IN_RANGE ((SRC), FIRST_STACK_REG, LAST_STACK_REG)) -#define DLL_IMPORT_EXPORT_PREFIX '#' - #define FASTCALL_PREFIX '@' struct machine_function GTY(()) { struct stack_local_entry *stack_locals; const char *some_ld_name; + rtx force_align_arg_pointer; int save_varrargs_registers; int accesses_prev_frame; int optimize_mode_switching[MAX_386_ENTITIES]; @@ -2273,11 +2409,30 @@ struct machine_function GTY(()) /* Number of saved registers USE_FAST_PROLOGUE_EPILOGUE has been computed for. */ int use_fast_prologue_epilogue_nregs; + /* If true, the current function needs the default PIC register, not + an alternate register (on x86) and must not use the red zone (on + x86_64), even if it's a leaf function. We don't want the + function to be regarded as non-leaf because TLS calls need not + affect register allocation. This flag is set when a TLS call + instruction is expanded within a function, and never reset, even + if all such instructions are optimized away. Use the + ix86_current_function_calls_tls_descriptor macro for a better + approximation. */ + int tls_descriptor_call_expanded_p; }; #define ix86_stack_locals (cfun->machine->stack_locals) #define ix86_save_varrargs_registers (cfun->machine->save_varrargs_registers) #define ix86_optimize_mode_switching (cfun->machine->optimize_mode_switching) +#define ix86_tls_descriptor_calls_expanded_in_cfun \ + (cfun->machine->tls_descriptor_call_expanded_p) +/* Since tls_descriptor_call_expanded is not cleared, even if all TLS + calls are optimized away, we try to detect cases in which it was + optimized away. Since such instructions (use (reg REG_SP)), we can + verify whether there's any such instruction live by testing that + REG_SP is live. */ +#define ix86_current_function_calls_tls_descriptor \ + (ix86_tls_descriptor_calls_expanded_in_cfun && df_regs_ever_live_p (SP_REG)) /* Control behavior of x86_file_start. */ #define X86_FILE_START_VERSION_DIRECTIVE false @@ -2287,6 +2442,17 @@ struct machine_function GTY(()) #define SYMBOL_FLAG_FAR_ADDR (SYMBOL_FLAG_MACH_DEP << 0) #define SYMBOL_REF_FAR_ADDR_P(X) \ ((SYMBOL_REF_FLAGS (X) & SYMBOL_FLAG_FAR_ADDR) != 0) + +/* Flags to mark dllimport/dllexport. Used by PE ports, but handy to + have defined always, to avoid ifdefing. */ +#define SYMBOL_FLAG_DLLIMPORT (SYMBOL_FLAG_MACH_DEP << 1) +#define SYMBOL_REF_DLLIMPORT_P(X) \ + ((SYMBOL_REF_FLAGS (X) & SYMBOL_FLAG_DLLIMPORT) != 0) + +#define SYMBOL_FLAG_DLLEXPORT (SYMBOL_FLAG_MACH_DEP << 2) +#define SYMBOL_REF_DLLEXPORT_P(X) \ + ((SYMBOL_REF_FLAGS (X) & SYMBOL_FLAG_DLLEXPORT) != 0) + /* Local variables: version-control: t