From patchwork Thu Aug 8 05:12:23 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Xinliang David Li X-Patchwork-Id: 265646 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1 with cipher DHE-RSA-AES256-SHA (256/256 bits)) (Client CN "localhost", Issuer "www.qmailtoaster.com" (not verified)) by ozlabs.org (Postfix) with ESMTPS id 96EA02C00A6 for ; Thu, 8 Aug 2013 15:12:45 +1000 (EST) DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :mime-version:date:message-id:subject:from:to:cc:content-type; q=dns; s=default; b=OMy4UAQTZO6WTMrQFJ11D1CNBgiFuAO99UOByQj4BOr 6MGgxyq9YUKC2nf0gpDcEedZz1Ia59Ht3PLK1Bpg4m6SrcJIJIXBIS1yj9mh58xk ykmT9LZ1rKMGPwwL9Jk80EmL9jndDYV9CIzTv2CVfYMKsO/2GOxpIlXF/KeRborQ = DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :mime-version:date:message-id:subject:from:to:cc:content-type; s=default; bh=PZpEP8awloynoMWca259cP3Ae5g=; b=lxQaAZRGlba55ZoQT lKYKwgTP3Gaf47CNw1XmvgRAglHW3GXsu8DMFb1505UJyo3CwalG4HWUIKSygTyU kxgsrDT88KP4ZQ262Jm3R3aKwGOxyCOUquP1d4KW5JLiNK3fAZD/sjxQ0cI7/PhH R5OBfPEviJ874pYgvMFE5CfUm4= Received: (qmail 4526 invoked by alias); 8 Aug 2013 05:12:36 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Received: (qmail 4494 invoked by uid 89); 8 Aug 2013 05:12:35 -0000 X-Spam-SWARE-Status: No, score=-2.9 required=5.0 tests=AWL, BAYES_00, RCVD_IN_DNSWL_LOW, RCVD_IN_HOSTKARMA_YE, RDNS_NONE, SPF_PASS autolearn=no version=3.3.1 Received: from Unknown (HELO mail-wi0-f180.google.com) (209.85.212.180) by sourceware.org (qpsmtpd/0.84/v0.84-167-ge50287c) with ESMTP; Thu, 08 Aug 2013 05:12:32 +0000 Received: by mail-wi0-f180.google.com with SMTP id f14so172906wiw.1 for ; Wed, 07 Aug 2013 22:12:24 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-gm-message-state:mime-version:date:message-id:subject:from:to:cc :content-type; bh=n2NjLaFiUHJrZYXesprJTHkyQeV/zmsKm1lhrlW8Tno=; b=GX7ZZ8nPR2uDqFrYSSR6fjZb7kpad6cyXS7++bOEddZBXpV0HwndMkDjJpaLQBf8VH 0yNKy0K+pDSfiFiD61garDcSOjMuTxs9jqSvz+lNVFt4cXHZ7btXSFMDNf7fSsW8LhCI SYQ5FFrK0il6lJ1B+yivdqKDyaEoVdFz6c1HC8DXaNXedcEy7IM2tgXnwHI0UTKKJ4sT ZCtECLWUgeBMAr12vNUKv5uxdmaK8fZQo8wxVg/IFeMXW+lTlFO0sZUo1oK0/j2CUo2H tyLKJn5RJX0mOlm6SSRa+k8yr6ZoSpeFW6Ieg08MZKgsFwzC8IwEMZyp9nbl6DywpXDl dN7w== X-Gm-Message-State: ALoCoQm4D5hEF8BGHlq1W3wv3nikEGWcPNJ8vDQvpd3raJsQiIGKvMCm11Ioi3uXqa8tsncUuyVONtvsJ6vWDQKNQKr7aVzZJv7yJ/xwa3Y4HPnUMGE0lr8GSYzf3VDnf3z6QfapBr4+k1wQ1zv4XXQv6zdpapQU8uXw2PXzSgi5EVMBkKND+l9Z4oAIYUQK884zuexd+fJSlCQ1468cVKOhkrqUfEM6XA== MIME-Version: 1.0 X-Received: by 10.180.75.239 with SMTP id f15mr4027220wiw.43.1375938743320; Wed, 07 Aug 2013 22:12:23 -0700 (PDT) Received: by 10.180.212.81 with HTTP; Wed, 7 Aug 2013 22:12:23 -0700 (PDT) Date: Wed, 7 Aug 2013 22:12:23 -0700 Message-ID: Subject: -mtune-ctrl=.... support, round-2 From: Xinliang David Li To: "Joseph S. Myers" Cc: Andi Kleen , Richard Biener , GCC Patches , Jan Hubicka , Teresa Johnson X-Virus-Found: No Hi, the attached is a follow up patch. The patch includes the following changes: 1. new option -mno-default -- suggested by H.J. It can be combined with -mtune-ctrl= to clear the default settings. 2. new option -mdump-tune-features -- this option can be used to dump all feature names and their default settings. 3. Added documentation to the 3 new options 4. Move the contents of inital_x86_tune_features into x86-tune.def to make sure they are always in sync 5. Some refactoring and handle the the tune features properly during target option restore. 2013-08-07 Xinliang David Li * config/i386/i386.h: Adjust macro definition. * config/i386/i386.opt: Define two new options. * config/i386/x86-tune.def: Add arch selector field in macros. * config/i386/i386.h: include x86-tune.def. * config/i386/i386.c (ix86_option_override_internal): Refactor the code. (parse_mtune_ctrl_str): New function. (set_ix86_tune_features): New function. (ix86_function_specific_restore): Call the new helper function. Ok for trunk after testing? thanks, David On Wed, Aug 7, 2013 at 5:22 PM, Xinliang David Li wrote: > On Wed, Aug 7, 2013 at 4:54 PM, Joseph S. Myers wrote: >> On Sun, 4 Aug 2013, Andi Kleen wrote: >> >>> Richard Biener writes: >>> > >>> > The patch fails to add documentation. >>> >>> That seems like a feature, it's likely not useful for the general >>> public. More for specialized tools that automatically search >>> for the best tuning. >> >> If such a tool is not part of GCC itself, then it is a user of GCC and >> documentation should be provided for those writing such a tool. >> >> Options should be undocumented in very limited cases such as multiple >> variant spellings where only one should be used but others are accepted >> because they were historically, or whether the user interface to an option >> is separate from the internal option passed to cc1 (the documentation is >> of options as passed to the driver, but the .opt file may describe options >> passed to cc1 as a result of other options being passed to the driver), or >> the option really is only for use within the build of GCC itself. >> Otherwise, the strong presumption is that all options should be >> documented, with appropriate caveats as applicable about the cases where >> an option is useful. >> > > Fair enough. I will add the documentation in a followup patch which > also implements H.J's proposal -mno-default and cleans up the initial > tuning array to be always in sync with new enums. > > >>> > And I am nervous about testing >>> > coverage - is this considered a development option only or are random >>> > combinations expected to work in all situations? I expect not, thus >>> > this looks like a dangerous option? >>> >>> When it's undocumented it doesn't need to work in every situation? >> >> No input files and command-line arguments whatsoever to the driver should >> result in ICEs, including undocumented options. > > True -- if ICEs are found, we should fix them. > > thanks, > > David > >> >> -- >> Joseph S. Myers >> joseph@codesourcery.com Index: doc/invoke.texi =================================================================== --- doc/invoke.texi (revision 201581) +++ doc/invoke.texi (working copy) @@ -637,6 +637,7 @@ Objective-C and Objective-C++ Dialects}. @emph{i386 and x86-64 Options} @gccoptlist{-mtune=@var{cpu-type} -march=@var{cpu-type} @gol +-mtune-ctrl=@var{feature-list} -mdump-tune-features -mno-default @gol -mfpmath=@var{unit} @gol -masm=@var{dialect} -mno-fancy-math-387 @gol -mno-fp-ret-in-387 -msoft-float @gol @@ -14428,6 +14429,24 @@ supported architecture, using the approp the file containing the CPU detection code should be compiled without these options. +@item -mdump-tune-features +@opindex mdump-tune-features +This option instructs GCC to dump the names of the x86 performance +tuning features and default settings. The names can be used in +@option{-mtune-ctrl=@var{feature-list}}. + +@item -mtune-ctrl=@var{feature-list} +@opindex mtune-ctrl=@var{feature-list} +This option is used to do fine grain control of x86 code generation features. +@var{feature-list} is a comma separated list of @var{feature} names. See also +@option{-mdump-tune-features}. When specified, the @var{feature} will be turned +on if it is not preceded with @code{^}, otherwise, it will be turned off. + +@item -mno-default +@opindex mno-default +This option instructs GCC to turn off all tunable features. See also +@option{-mtune-ctrl=@var{feature-list}} and @option{-mdump-tune-features}. + @item -mcld @opindex mcld This option instructs GCC to emit a @code{cld} instruction in the prologue Index: config/i386/i386.opt =================================================================== --- config/i386/i386.opt (revision 201582) +++ config/i386/i386.opt (working copy) @@ -374,6 +374,13 @@ mtune-ctrl= Target RejectNegative Joined Var(ix86_tune_ctrl_string) Fine grain control of tune features +mno-default +Target RejectNegative Var(ix86_tune_no_default) Init(0) +Clear all tune features + +mdump-tune-features +Target RejectNegative Var(ix86_dump_tunes) Init(0) + mabi= Target RejectNegative Joined Var(ix86_abi) Enum(calling_abi) Init(SYSV_ABI) Generate code that conforms to the given ABI Index: config/i386/i386.c =================================================================== --- config/i386/i386.c (revision 201582) +++ config/i386/i386.c (working copy) @@ -1837,7 +1837,7 @@ const struct processor_costs *ix86_cost const char* ix86_tune_feature_names[X86_TUNE_LAST] = { #undef DEF_TUNE -#define DEF_TUNE(tune, name) name, +#define DEF_TUNE(tune, name, selector) name, #include "x86-tune.def" #undef DEF_TUNE }; @@ -1848,281 +1848,10 @@ unsigned char ix86_tune_features[X86_TUN /* Feature tests against the various tunings used to create ix86_tune_features based on the processor mask. */ static unsigned int initial_ix86_tune_features[X86_TUNE_LAST] = { - /* X86_TUNE_USE_LEAVE: Leave does not affect Nocona SPEC2000 results - negatively, so enabling for Generic64 seems like good code size - tradeoff. We can't enable it for 32bit generic because it does not - work well with PPro base chips. */ - m_386 | m_CORE_ALL | m_K6_GEODE | m_AMD_MULTIPLE | m_GENERIC64, - - /* X86_TUNE_PUSH_MEMORY */ - m_386 | m_P4_NOCONA | m_CORE_ALL | m_K6_GEODE | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_ZERO_EXTEND_WITH_AND */ - m_486 | m_PENT, - - /* X86_TUNE_UNROLL_STRLEN */ - m_486 | m_PENT | m_PPRO | m_ATOM | m_SLM | m_CORE_ALL | m_K6 | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_BRANCH_PREDICTION_HINTS: Branch hints were put in P4 based - on simulation result. But after P4 was made, no performance benefit - was observed with branch hints. It also increases the code size. - As a result, icc never generates branch hints. */ - 0, - - /* X86_TUNE_DOUBLE_WITH_ADD */ - ~m_386, - - /* X86_TUNE_USE_SAHF */ - m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_K6_GEODE | m_K8 | m_AMDFAM10 | m_BDVER | m_BTVER | m_GENERIC, - - /* X86_TUNE_MOVX: Enable to zero extend integer registers to avoid - partial dependencies. */ - m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_GEODE | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_PARTIAL_REG_STALL: We probably ought to watch for partial - register stalls on Generic32 compilation setting as well. However - in current implementation the partial register stalls are not eliminated - very well - they can be introduced via subregs synthesized by combine - and can happen in caller/callee saving sequences. Because this option - pays back little on PPro based chips and is in conflict with partial reg - dependencies used by Athlon/P4 based chips, it is better to leave it off - for generic32 for now. */ - m_PPRO, - - /* X86_TUNE_PARTIAL_FLAG_REG_STALL */ - m_CORE_ALL | m_GENERIC, - - /* X86_TUNE_LCP_STALL: Avoid an expensive length-changing prefix stall - * on 16-bit immediate moves into memory on Core2 and Corei7. */ - m_CORE_ALL | m_GENERIC, - - /* X86_TUNE_USE_HIMODE_FIOP */ - m_386 | m_486 | m_K6_GEODE, - - /* X86_TUNE_USE_SIMODE_FIOP */ - ~(m_PENT | m_PPRO | m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE | m_GENERIC), - - /* X86_TUNE_USE_MOV0 */ - m_K6, - - /* X86_TUNE_USE_CLTD */ - ~(m_PENT | m_ATOM | m_SLM | m_K6), - - /* X86_TUNE_USE_XCHGB: Use xchgb %rh,%rl instead of rolw/rorw $8,rx. */ - m_PENT4, - - /* X86_TUNE_SPLIT_LONG_MOVES */ - m_PPRO, - - /* X86_TUNE_READ_MODIFY_WRITE */ - ~m_PENT, - - /* X86_TUNE_READ_MODIFY */ - ~(m_PENT | m_PPRO), - - /* X86_TUNE_PROMOTE_QIMODE */ - m_386 | m_486 | m_PENT | m_CORE_ALL | m_ATOM | m_SLM | m_K6_GEODE | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_FAST_PREFIX */ - ~(m_386 | m_486 | m_PENT), - - /* X86_TUNE_SINGLE_STRINGOP */ - m_386 | m_P4_NOCONA, - - /* X86_TUNE_QIMODE_MATH */ - ~0, - - /* X86_TUNE_HIMODE_MATH: On PPro this flag is meant to avoid partial - register stalls. Just like X86_TUNE_PARTIAL_REG_STALL this option - might be considered for Generic32 if our scheme for avoiding partial - stalls was more effective. */ - ~m_PPRO, - - /* X86_TUNE_PROMOTE_QI_REGS */ - 0, - - /* X86_TUNE_PROMOTE_HI_REGS */ - m_PPRO, - - /* X86_TUNE_SINGLE_POP: Enable if single pop insn is preferred - over esp addition. */ - m_386 | m_486 | m_PENT | m_PPRO, - - /* X86_TUNE_DOUBLE_POP: Enable if double pop insn is preferred - over esp addition. */ - m_PENT, - - /* X86_TUNE_SINGLE_PUSH: Enable if single push insn is preferred - over esp subtraction. */ - m_386 | m_486 | m_PENT | m_K6_GEODE, - - /* X86_TUNE_DOUBLE_PUSH. Enable if double push insn is preferred - over esp subtraction. */ - m_PENT | m_K6_GEODE, - - /* X86_TUNE_INTEGER_DFMODE_MOVES: Enable if integer moves are preferred - for DFmode copies */ - ~(m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_GEODE | m_AMD_MULTIPLE | m_GENERIC), - - /* X86_TUNE_PARTIAL_REG_DEPENDENCY */ - m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_SSE_PARTIAL_REG_DEPENDENCY: In the Generic model we have a - conflict here in between PPro/Pentium4 based chips that thread 128bit - SSE registers as single units versus K8 based chips that divide SSE - registers to two 64bit halves. This knob promotes all store destinations - to be 128bit to allow register renaming on 128bit SSE units, but usually - results in one extra microop on 64bit SSE units. Experimental results - shows that disabling this option on P4 brings over 20% SPECfp regression, - while enabling it on K8 brings roughly 2.4% regression that can be partly - masked by careful scheduling of moves. */ - m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_AMDFAM10 | m_BDVER | m_GENERIC, - - /* X86_TUNE_SSE_UNALIGNED_LOAD_OPTIMAL */ - m_COREI7 | m_AMDFAM10 | m_BDVER | m_BTVER | m_SLM, - - /* X86_TUNE_SSE_UNALIGNED_STORE_OPTIMAL */ - m_COREI7 | m_BDVER | m_SLM, - - /* X86_TUNE_SSE_PACKED_SINGLE_INSN_OPTIMAL */ - m_BDVER , - - /* X86_TUNE_SSE_SPLIT_REGS: Set for machines where the type and dependencies - are resolved on SSE register parts instead of whole registers, so we may - maintain just lower part of scalar values in proper format leaving the - upper part undefined. */ - m_ATHLON_K8, - - /* X86_TUNE_SSE_TYPELESS_STORES */ - m_AMD_MULTIPLE, - - /* X86_TUNE_SSE_LOAD0_BY_PXOR */ - m_PPRO | m_P4_NOCONA, - - /* X86_TUNE_MEMORY_MISMATCH_STALL */ - m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_PROLOGUE_USING_MOVE */ - m_PPRO | m_ATHLON_K8, - - /* X86_TUNE_EPILOGUE_USING_MOVE */ - m_PPRO | m_ATHLON_K8, - - /* X86_TUNE_SHIFT1 */ - ~m_486, - - /* X86_TUNE_USE_FFREEP */ - m_AMD_MULTIPLE, - - /* X86_TUNE_INTER_UNIT_MOVES_TO_VEC */ - ~(m_AMD_MULTIPLE | m_GENERIC), - - /* X86_TUNE_INTER_UNIT_MOVES_FROM_VEC */ - ~m_ATHLON_K8, - - /* X86_TUNE_INTER_UNIT_CONVERSIONS */ - ~(m_AMDFAM10 | m_BDVER ), - - /* X86_TUNE_FOUR_JUMP_LIMIT: Some CPU cores are not able to predict more - than 4 branch instructions in the 16 byte window. */ - m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_SCHEDULE */ - m_PENT | m_PPRO | m_CORE_ALL | m_ATOM | m_SLM | m_K6_GEODE | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_USE_BT */ - m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_USE_INCDEC */ - ~(m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_GENERIC), - - /* X86_TUNE_PAD_RETURNS */ - m_CORE_ALL | m_AMD_MULTIPLE | m_GENERIC, - - /* X86_TUNE_PAD_SHORT_FUNCTION: Pad short function. */ - m_ATOM, - - /* X86_TUNE_EXT_80387_CONSTANTS */ - m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_K6_GEODE | m_ATHLON_K8 | m_GENERIC, - - /* X86_TUNE_AVOID_VECTOR_DECODE */ - m_CORE_ALL | m_K8 | m_GENERIC64, - - /* X86_TUNE_PROMOTE_HIMODE_IMUL: Modern CPUs have same latency for HImode - and SImode multiply, but 386 and 486 do HImode multiply faster. */ - ~(m_386 | m_486), - - /* X86_TUNE_SLOW_IMUL_IMM32_MEM: Imul of 32-bit constant and memory is - vector path on AMD machines. */ - m_CORE_ALL | m_K8 | m_AMDFAM10 | m_BDVER | m_BTVER | m_GENERIC64, - - /* X86_TUNE_SLOW_IMUL_IMM8: Imul of 8-bit constant is vector path on AMD - machines. */ - m_CORE_ALL | m_K8 | m_AMDFAM10 | m_BDVER | m_BTVER | m_GENERIC64, - - /* X86_TUNE_MOVE_M1_VIA_OR: On pentiums, it is faster to load -1 via OR - than a MOV. */ - m_PENT, - - /* X86_TUNE_NOT_UNPAIRABLE: NOT is not pairable on Pentium, while XOR is, - but one byte longer. */ - m_PENT, - - /* X86_TUNE_NOT_VECTORMODE: On AMD K6, NOT is vector decoded with memory - operand that cannot be represented using a modRM byte. The XOR - replacement is long decoded, so this split helps here as well. */ - m_K6, - - /* X86_TUNE_USE_VECTOR_FP_CONVERTS: Prefer vector packed SSE conversion - from FP to FP. */ - m_CORE_ALL | m_AMDFAM10 | m_GENERIC, - - /* X86_TUNE_USE_VECTOR_CONVERTS: Prefer vector packed SSE conversion - from integer to FP. */ - m_AMDFAM10, - - /* X86_TUNE_FUSE_CMP_AND_BRANCH: Fuse a compare or test instruction - with a subsequent conditional jump instruction into a single - compare-and-branch uop. */ - m_BDVER, - - /* X86_TUNE_OPT_AGU: Optimize for Address Generation Unit. This flag - will impact LEA instruction selection. */ - m_ATOM | m_SLM, - - /* X86_TUNE_VECTORIZE_DOUBLE: Enable double precision vector - instructions. */ - ~m_ATOM, - - /* X86_TUNE_SOFTWARE_PREFETCHING_BENEFICIAL: Enable software prefetching - at -O3. For the moment, the prefetching seems badly tuned for Intel - chips. */ - m_K6_GEODE | m_AMD_MULTIPLE, - - /* X86_TUNE_AVX128_OPTIMAL: Enable 128-bit AVX instruction generation for - the auto-vectorizer. */ - m_BDVER | m_BTVER2, - - /* X86_TUNE_REASSOC_INT_TO_PARALLEL: Try to produce parallel computations - during reassociation of integer computation. */ - m_ATOM, - - /* X86_TUNE_REASSOC_FP_TO_PARALLEL: Try to produce parallel computations - during reassociation of fp computation. */ - m_ATOM | m_SLM | m_HASWELL | m_BDVER1 | m_BDVER2, - - /* X86_TUNE_GENERAL_REGS_SSE_SPILL: Try to spill general regs to SSE - regs instead of memory. */ - m_CORE_ALL, - - /* X86_TUNE_AVOID_MEM_OPND_FOR_CMOVE: Try to avoid memory operands for - a conditional move. */ - m_ATOM, - - /* X86_TUNE_SPLIT_MEM_OPND_FOR_FP_CONVERTS: Try to split memory operand for - fp converts to destination register. */ - m_SLM - +#undef DEF_TUNE +#define DEF_TUNE(tune, name, selector) selector, +#include "x86-tune.def" +#undef DEF_TUNE }; /* Feature tests against the various architecture variations. */ @@ -2927,6 +2656,80 @@ ix86_debug_options (void) return; } +/* parse -mtune-ctrl= option. When DUMP is true, + print the features that are explicitly set. */ + +static void +parse_mtune_ctrl_str (bool dump) +{ + if (!ix86_tune_ctrl_string) + return; + + char *next_feature_string = NULL; + char *curr_feature_string = xstrdup (ix86_tune_ctrl_string); + char *orig = curr_feature_string; + int i; + do + { + bool clear = false; + + next_feature_string = strchr (curr_feature_string, ','); + if (next_feature_string) + *next_feature_string++ = '\0'; + if (*curr_feature_string == '^') + { + curr_feature_string++; + clear = true; + } + for (i = 0; i < X86_TUNE_LAST; i++) + { + if (!strcmp (curr_feature_string, ix86_tune_feature_names[i])) + { + ix86_tune_features[i] = !clear; + if (dump) + fprintf (stderr, "Explicitly %s feature %s\n", + clear ? "clear" : "set", ix86_tune_feature_names[i]); + break; + } + } + if (i == X86_TUNE_LAST) + error ("Unknown parameter to option -mtune-ctrl: %s", + clear ? curr_feature_string - 1 : curr_feature_string); + curr_feature_string = next_feature_string; + } + while (curr_feature_string); + free (orig); +} + +/* Helper function to set ix86_tune_features. IX86_TUNE is the + processor type. */ + +static void +set_ix86_tune_features (enum processor_type ix86_tune, bool dump) +{ + unsigned int ix86_tune_mask = 1u << ix86_tune; + int i; + + for (i = 0; i < X86_TUNE_LAST; ++i) + { + if (ix86_tune_no_default) + ix86_tune_features[i] = 0; + else + ix86_tune_features[i] = !!(initial_ix86_tune_features[i] & ix86_tune_mask); + } + + if (dump) + { + fprintf (stderr, "List of x86 specific tuning parameter names:\n"); + for (i = 0; i < X86_TUNE_LAST; i++) + fprintf (stderr, "%s : %s\n", ix86_tune_feature_names[i], + ix86_tune_features[i] ? "on" : "off"); + } + + parse_mtune_ctrl_str (dump); +} + + /* Override various settings based on options. If MAIN_ARGS_P, the options are from the command line, otherwise they are from attributes. */ @@ -3572,43 +3375,7 @@ ix86_option_override_internal (bool main error ("bad value (%s) for %stune=%s %s", ix86_tune_string, prefix, suffix, sw); - ix86_tune_mask = 1u << ix86_tune; - for (i = 0; i < X86_TUNE_LAST; ++i) - ix86_tune_features[i] = !!(initial_ix86_tune_features[i] & ix86_tune_mask); - - if (ix86_tune_ctrl_string) - { - /* parse the tune ctrl string in the following form: - [^]tune_name1,[^]tune_name2,..a */ - char *next_feature_string = NULL; - char *curr_feature_string = xstrdup (ix86_tune_ctrl_string); - char *orig = curr_feature_string; - do { - bool clear = false; - - next_feature_string = strchr (curr_feature_string, ','); - if (next_feature_string) - *next_feature_string++ = '\0'; - if (*curr_feature_string == '^') - { - curr_feature_string++; - clear = true; - } - for (i = 0; i < X86_TUNE_LAST; i++) - { - if (!strcmp (curr_feature_string, ix86_tune_feature_names[i])) - { - ix86_tune_features[i] = !clear; - break; - } - } - if (i == X86_TUNE_LAST) - warning (0, "Unknown parameter to option -mtune-ctrl: %s", - clear ? curr_feature_string - 1 : curr_feature_string); - curr_feature_string = next_feature_string; - } while (curr_feature_string); - free (orig); - } + set_ix86_tune_features (ix86_tune, ix86_dump_tunes); #ifndef USE_IX86_FRAME_POINTER #define USE_IX86_FRAME_POINTER 0 @@ -3844,6 +3611,7 @@ ix86_option_override_internal (bool main gcc_unreachable (); } + ix86_tune_mask = 1u << ix86_tune; if ((!USE_IX86_FRAME_POINTER || (x86_accumulate_outgoing_args & ix86_tune_mask)) && !(target_flags_explicit & MASK_ACCUMULATE_OUTGOING_ARGS) @@ -4194,7 +3962,7 @@ ix86_function_specific_restore (struct c { enum processor_type old_tune = ix86_tune; enum processor_type old_arch = ix86_arch; - unsigned int ix86_arch_mask, ix86_tune_mask; + unsigned int ix86_arch_mask; int i; ix86_arch = (enum processor_type) ptr->arch; @@ -4218,12 +3986,7 @@ ix86_function_specific_restore (struct c /* Recreate the tune optimization tests */ if (old_tune != ix86_tune) - { - ix86_tune_mask = 1u << ix86_tune; - for (i = 0; i < X86_TUNE_LAST; ++i) - ix86_tune_features[i] - = !!(initial_ix86_tune_features[i] & ix86_tune_mask); - } + set_ix86_tune_features (ix86_tune, false); } /* Print the current options */ Index: config/i386/i386.h =================================================================== --- config/i386/i386.h (revision 201582) +++ config/i386/i386.h (working copy) @@ -262,7 +262,7 @@ extern const struct processor_costs ix86 /* Feature tests against the various tunings. */ enum ix86_tune_indices { #undef DEF_TUNE -#define DEF_TUNE(tune, name) tune, +#define DEF_TUNE(tune, name, selector) tune, #include "x86-tune.def" #undef DEF_TUNE X86_TUNE_LAST Index: config/i386/x86-tune.def =================================================================== --- config/i386/x86-tune.def (revision 201582) +++ config/i386/x86-tune.def (working copy) @@ -13,85 +13,220 @@ but WITHOUT ANY WARRANTY; without even t MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. -Under Section 7 of GPL version 3, you are granted additional -permissions described in the GCC Runtime Library Exception, version -3.1, as published by the Free Software Foundation. - You should have received a copy of the GNU General Public License and a copy of the GCC Runtime Library Exception along with this program; see the files COPYING3 and COPYING.RUNTIME respectively. If not, see . */ -DEF_TUNE (X86_TUNE_USE_LEAVE, "use_leave") -DEF_TUNE (X86_TUNE_PUSH_MEMORY, "push_memory") -DEF_TUNE (X86_TUNE_ZERO_EXTEND_WITH_AND, "zero_extend_with_and") -DEF_TUNE (X86_TUNE_UNROLL_STRLEN, "unroll_strlen") -DEF_TUNE (X86_TUNE_BRANCH_PREDICTION_HINTS, "branch_prediction_hints") -DEF_TUNE (X86_TUNE_DOUBLE_WITH_ADD, "double_with_add") -DEF_TUNE (X86_TUNE_USE_SAHF, "use_sahf") -DEF_TUNE (X86_TUNE_MOVX, "movx") -DEF_TUNE (X86_TUNE_PARTIAL_REG_STALL, "partial_reg_stall") -DEF_TUNE (X86_TUNE_PARTIAL_FLAG_REG_STALL, "partial_flag_reg_stall") -DEF_TUNE (X86_TUNE_LCP_STALL, "lcp_stall") -DEF_TUNE (X86_TUNE_USE_HIMODE_FIOP, "use_himode_fiop") -DEF_TUNE (X86_TUNE_USE_SIMODE_FIOP, "use_simode_fiop") -DEF_TUNE (X86_TUNE_USE_MOV0, "use_mov0") -DEF_TUNE (X86_TUNE_USE_CLTD, "use_cltd") -DEF_TUNE (X86_TUNE_USE_XCHGB, "use_xchgb") -DEF_TUNE (X86_TUNE_SPLIT_LONG_MOVES, "split_long_moves") -DEF_TUNE (X86_TUNE_READ_MODIFY_WRITE, "read_modify_write") -DEF_TUNE (X86_TUNE_READ_MODIFY, "read_modify") -DEF_TUNE (X86_TUNE_PROMOTE_QIMODE, "promote_qimode") -DEF_TUNE (X86_TUNE_FAST_PREFIX, "fast_prefix") -DEF_TUNE (X86_TUNE_SINGLE_STRINGOP, "single_stringop") -DEF_TUNE (X86_TUNE_QIMODE_MATH, "qimode_math") -DEF_TUNE (X86_TUNE_HIMODE_MATH, "himode_math") -DEF_TUNE (X86_TUNE_PROMOTE_QI_REGS, "promote_qi_regs") -DEF_TUNE (X86_TUNE_PROMOTE_HI_REGS, "promote_hi_regs") -DEF_TUNE (X86_TUNE_SINGLE_POP, "single_pop") -DEF_TUNE (X86_TUNE_DOUBLE_POP, "double_pop") -DEF_TUNE (X86_TUNE_SINGLE_PUSH, "single_push") -DEF_TUNE (X86_TUNE_DOUBLE_PUSH, "double_push") -DEF_TUNE (X86_TUNE_INTEGER_DFMODE_MOVES, "integer_dfmode_moves") -DEF_TUNE (X86_TUNE_PARTIAL_REG_DEPENDENCY, "partial_reg_dependency") -DEF_TUNE (X86_TUNE_SSE_PARTIAL_REG_DEPENDENCY, "sse_partial_reg_dependency") -DEF_TUNE (X86_TUNE_SSE_UNALIGNED_LOAD_OPTIMAL, "sse_unaligned_load_optimal") -DEF_TUNE (X86_TUNE_SSE_UNALIGNED_STORE_OPTIMAL, "sse_unaligned_store_optimal") -DEF_TUNE (X86_TUNE_SSE_PACKED_SINGLE_INSN_OPTIMAL, "sse_packed_single_insn_optimal") -DEF_TUNE (X86_TUNE_SSE_SPLIT_REGS, "sse_split_regs") -DEF_TUNE (X86_TUNE_SSE_TYPELESS_STORES, "sse_typeless_stores") -DEF_TUNE (X86_TUNE_SSE_LOAD0_BY_PXOR, "sse_load0_by_pxor") -DEF_TUNE (X86_TUNE_MEMORY_MISMATCH_STALL, "memory_mismatch_stall") -DEF_TUNE (X86_TUNE_PROLOGUE_USING_MOVE, "prologue_using_move") -DEF_TUNE (X86_TUNE_EPILOGUE_USING_MOVE, "epilogue_using_move") -DEF_TUNE (X86_TUNE_SHIFT1, "shift1") -DEF_TUNE (X86_TUNE_USE_FFREEP, "use_ffreep") -DEF_TUNE (X86_TUNE_INTER_UNIT_MOVES_TO_VEC, "inter_unit_moves_to_vec") -DEF_TUNE (X86_TUNE_INTER_UNIT_MOVES_FROM_VEC, "inter_unit_moves_from_vec") -DEF_TUNE (X86_TUNE_INTER_UNIT_CONVERSIONS, "inter_unit_conversions") -DEF_TUNE (X86_TUNE_FOUR_JUMP_LIMIT, "four_jump_limit") -DEF_TUNE (X86_TUNE_SCHEDULE, "schedule") -DEF_TUNE (X86_TUNE_USE_BT, "use_bt") -DEF_TUNE (X86_TUNE_USE_INCDEC, "use_incdec") -DEF_TUNE (X86_TUNE_PAD_RETURNS, "pad_returns") -DEF_TUNE (X86_TUNE_PAD_SHORT_FUNCTION, "pad_short_function") -DEF_TUNE (X86_TUNE_EXT_80387_CONSTANTS, "ext_80387_constants") -DEF_TUNE (X86_TUNE_AVOID_VECTOR_DECODE, "avoid_vector_decode") -DEF_TUNE (X86_TUNE_PROMOTE_HIMODE_IMUL, "promote_himode_imul") -DEF_TUNE (X86_TUNE_SLOW_IMUL_IMM32_MEM, "slow_imul_imm32_mem") -DEF_TUNE (X86_TUNE_SLOW_IMUL_IMM8, "slow_imul_imm8") -DEF_TUNE (X86_TUNE_MOVE_M1_VIA_OR, "move_m1_via_or") -DEF_TUNE (X86_TUNE_NOT_UNPAIRABLE, "not_unpairable") -DEF_TUNE (X86_TUNE_NOT_VECTORMODE, "not_vectormode") -DEF_TUNE (X86_TUNE_USE_VECTOR_FP_CONVERTS, "use_vector_fp_converts") -DEF_TUNE (X86_TUNE_USE_VECTOR_CONVERTS, "use_vector_converts") -DEF_TUNE (X86_TUNE_FUSE_CMP_AND_BRANCH, "fuse_cmp_and_branch") -DEF_TUNE (X86_TUNE_OPT_AGU, "opt_agu") -DEF_TUNE (X86_TUNE_VECTORIZE_DOUBLE, "vectorize_double") -DEF_TUNE (X86_TUNE_SOFTWARE_PREFETCHING_BENEFICIAL, "software_prefetching_beneficial") -DEF_TUNE (X86_TUNE_AVX128_OPTIMAL, "avx128_optimal") -DEF_TUNE (X86_TUNE_REASSOC_INT_TO_PARALLEL, "reassoc_int_to_parallel") -DEF_TUNE (X86_TUNE_REASSOC_FP_TO_PARALLEL, "reassoc_fp_to_parallel") -DEF_TUNE (X86_TUNE_GENERAL_REGS_SSE_SPILL, "general_regs_sse_spill") -DEF_TUNE (X86_TUNE_AVOID_MEM_OPND_FOR_CMOVE, "avoid_mem_opnd_for_cmove") -DEF_TUNE (X86_TUNE_SPLIT_MEM_OPND_FOR_FP_CONVERTS, "split_mem_opnd_for_fp_converts") +/* X86_TUNE_USE_LEAVE: Leave does not affect Nocona SPEC2000 results + negatively, so enabling for Generic64 seems like good code size + tradeoff. We can't enable it for 32bit generic because it does not + work well with PPro base chips. */ +DEF_TUNE (X86_TUNE_USE_LEAVE, "use_leave", + m_386 | m_CORE_ALL | m_K6_GEODE | m_AMD_MULTIPLE | m_GENERIC64) +DEF_TUNE (X86_TUNE_PUSH_MEMORY, "push_memory", + m_386 | m_P4_NOCONA | m_CORE_ALL | m_K6_GEODE | m_AMD_MULTIPLE + | m_GENERIC) +DEF_TUNE (X86_TUNE_ZERO_EXTEND_WITH_AND, "zero_extend_with_and", m_486 | m_PENT) +DEF_TUNE (X86_TUNE_UNROLL_STRLEN, "unroll_strlen", + m_486 | m_PENT | m_PPRO | m_ATOM | m_SLM | m_CORE_ALL | m_K6 + | m_AMD_MULTIPLE | m_GENERIC) +/* X86_TUNE_BRANCH_PREDICTION_HINTS: Branch hints were put in P4 based + on simulation result. But after P4 was made, no performance benefit + was observed with branch hints. It also increases the code size. + As a result, icc never generates branch hints. */ +DEF_TUNE (X86_TUNE_BRANCH_PREDICTION_HINTS, "branch_prediction_hints", 0) +DEF_TUNE (X86_TUNE_DOUBLE_WITH_ADD, "double_with_add", ~m_386) +DEF_TUNE (X86_TUNE_USE_SAHF, "use_sahf", + m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_K6_GEODE + | m_K8 | m_AMDFAM10 | m_BDVER | m_BTVER | m_GENERIC) +/* X86_TUNE_MOVX: Enable to zero extend integer registers to avoid + partial dependencies. */ +DEF_TUNE (X86_TUNE_MOVX, "movx", + m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_GEODE + | m_AMD_MULTIPLE | m_GENERIC) +/* X86_TUNE_PARTIAL_REG_STALL: We probably ought to watch for partial + register stalls on Generic32 compilation setting as well. However + in current implementation the partial register stalls are not eliminated + very well - they can be introduced via subregs synthesized by combine + and can happen in caller/callee saving sequences. Because this option + pays back little on PPro based chips and is in conflict with partial reg + dependencies used by Athlon/P4 based chips, it is better to leave it off + for generic32 for now. */ +DEF_TUNE (X86_TUNE_PARTIAL_REG_STALL, "partial_reg_stall", m_PPRO) +DEF_TUNE (X86_TUNE_PARTIAL_FLAG_REG_STALL, "partial_flag_reg_stall", + m_CORE_ALL | m_GENERIC) +/* X86_TUNE_LCP_STALL: Avoid an expensive length-changing prefix stall + * on 16-bit immediate moves into memory on Core2 and Corei7. */ +DEF_TUNE (X86_TUNE_LCP_STALL, "lcp_stall", m_CORE_ALL | m_GENERIC) +DEF_TUNE (X86_TUNE_USE_HIMODE_FIOP, "use_himode_fiop", + m_386 | m_486 | m_K6_GEODE) +DEF_TUNE (X86_TUNE_USE_SIMODE_FIOP, "use_simode_fiop", + ~(m_PENT | m_PPRO | m_CORE_ALL | m_ATOM + | m_SLM | m_AMD_MULTIPLE | m_GENERIC)) +DEF_TUNE (X86_TUNE_USE_MOV0, "use_mov0", m_K6) +DEF_TUNE (X86_TUNE_USE_CLTD, "use_cltd", m_386 | m_486 | m_K6_GEODE) +/* X86_TUNE_USE_XCHGB: Use xchgb %rh,%rl instead of rolw/rorw $8,rx. */ +DEF_TUNE (X86_TUNE_USE_XCHGB, "use_xchgb", m_PENT4) +DEF_TUNE (X86_TUNE_SPLIT_LONG_MOVES, "split_long_moves", m_PPRO) +DEF_TUNE (X86_TUNE_READ_MODIFY_WRITE, "read_modify_write", ~m_PENT) +DEF_TUNE (X86_TUNE_READ_MODIFY, "read_modify", ~(m_PENT | m_PPRO)) +DEF_TUNE (X86_TUNE_PROMOTE_QIMODE, "promote_qimode", + m_386 | m_486 | m_PENT | m_CORE_ALL | m_ATOM | m_SLM + | m_K6_GEODE | m_AMD_MULTIPLE | m_GENERIC) +DEF_TUNE (X86_TUNE_FAST_PREFIX, "fast_prefix", ~(m_386 | m_486 | m_PENT)) +DEF_TUNE (X86_TUNE_SINGLE_STRINGOP, "single_stringop", m_386 | m_P4_NOCONA) +DEF_TUNE (X86_TUNE_QIMODE_MATH, "qimode_math", ~0) +/* X86_TUNE_HIMODE_MATH: On PPro this flag is meant to avoid partial + register stalls. Just like X86_TUNE_PARTIAL_REG_STALL this option + might be considered for Generic32 if our scheme for avoiding partial + stalls was more effective. */ +DEF_TUNE (X86_TUNE_HIMODE_MATH, "himode_math", ~m_PPRO) +DEF_TUNE (X86_TUNE_PROMOTE_QI_REGS, "promote_qi_regs", 0) +DEF_TUNE (X86_TUNE_PROMOTE_HI_REGS, "promote_hi_regs", m_PPRO) +/* X86_TUNE_SINGLE_POP: Enable if single pop insn is preferred + over esp addition. */ +DEF_TUNE (X86_TUNE_SINGLE_POP, "single_pop", m_386 | m_486 | m_PENT | m_PPRO) +/* X86_TUNE_DOUBLE_POP: Enable if double pop insn is preferred + over esp addition. */ +DEF_TUNE (X86_TUNE_DOUBLE_POP, "double_pop", m_PENT) +/* X86_TUNE_SINGLE_PUSH: Enable if single push insn is preferred + over esp subtraction. */ +DEF_TUNE (X86_TUNE_SINGLE_PUSH, "single_push", m_386 | m_486 | m_PENT + | m_K6_GEODE) +/* X86_TUNE_DOUBLE_PUSH. Enable if double push insn is preferred + over esp subtraction. */ +DEF_TUNE (X86_TUNE_DOUBLE_PUSH, "double_push", m_PENT | m_K6_GEODE) +/* X86_TUNE_INTEGER_DFMODE_MOVES: Enable if integer moves are preferred + for DFmode copies */ +DEF_TUNE (X86_TUNE_INTEGER_DFMODE_MOVES, "integer_dfmode_moves", + ~(m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM + | m_GEODE | m_AMD_MULTIPLE | m_GENERIC)) +DEF_TUNE (X86_TUNE_PARTIAL_REG_DEPENDENCY, "partial_reg_dependency", + m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE + | m_GENERIC) +/* X86_TUNE_SSE_PARTIAL_REG_DEPENDENCY: In the Generic model we have a + conflict here in between PPro/Pentium4 based chips that thread 128bit + SSE registers as single units versus K8 based chips that divide SSE + registers to two 64bit halves. This knob promotes all store destinations + to be 128bit to allow register renaming on 128bit SSE units, but usually + results in one extra microop on 64bit SSE units. Experimental results + shows that disabling this option on P4 brings over 20% SPECfp regression, + while enabling it on K8 brings roughly 2.4% regression that can be partly + masked by careful scheduling of moves. */ +DEF_TUNE (X86_TUNE_SSE_PARTIAL_REG_DEPENDENCY, "sse_partial_reg_dependency", + m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_AMDFAM10 + | m_BDVER | m_GENERIC) +DEF_TUNE (X86_TUNE_SSE_UNALIGNED_LOAD_OPTIMAL, "sse_unaligned_load_optimal", + m_COREI7 | m_AMDFAM10 | m_BDVER | m_BTVER | m_SLM) +DEF_TUNE (X86_TUNE_SSE_UNALIGNED_STORE_OPTIMAL, "sse_unaligned_store_optimal", + m_COREI7 | m_BDVER | m_SLM) +DEF_TUNE (X86_TUNE_SSE_PACKED_SINGLE_INSN_OPTIMAL, "sse_packed_single_insn_optimal", + m_BDVER) +/* X86_TUNE_SSE_SPLIT_REGS: Set for machines where the type and dependencies + are resolved on SSE register parts instead of whole registers, so we may + maintain just lower part of scalar values in proper format leaving the + upper part undefined. */ +DEF_TUNE (X86_TUNE_SSE_SPLIT_REGS, "sse_split_regs", m_ATHLON_K8) +DEF_TUNE (X86_TUNE_SSE_TYPELESS_STORES, "sse_typeless_stores", m_AMD_MULTIPLE) +DEF_TUNE (X86_TUNE_SSE_LOAD0_BY_PXOR, "sse_load0_by_pxor", m_PPRO | m_P4_NOCONA) +DEF_TUNE (X86_TUNE_MEMORY_MISMATCH_STALL, "memory_mismatch_stall", + m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE | m_GENERIC) +DEF_TUNE (X86_TUNE_PROLOGUE_USING_MOVE, "prologue_using_move", + m_PPRO | m_ATHLON_K8) +DEF_TUNE (X86_TUNE_EPILOGUE_USING_MOVE, "epilogue_using_move", + m_PPRO | m_ATHLON_K8) +DEF_TUNE (X86_TUNE_SHIFT1, "shift1", ~m_486) +DEF_TUNE (X86_TUNE_USE_FFREEP, "use_ffreep", m_AMD_MULTIPLE) +DEF_TUNE (X86_TUNE_INTER_UNIT_MOVES_TO_VEC, "inter_unit_moves_to_vec", + ~(m_AMD_MULTIPLE | m_GENERIC)) +DEF_TUNE (X86_TUNE_INTER_UNIT_MOVES_FROM_VEC, "inter_unit_moves_from_vec", + ~m_ATHLON_K8) +DEF_TUNE (X86_TUNE_INTER_UNIT_CONVERSIONS, "inter_unit_conversions", + ~(m_AMDFAM10 | m_BDVER )) +/* X86_TUNE_FOUR_JUMP_LIMIT: Some CPU cores are not able to predict more + than 4 branch instructions in the 16 byte window. */ +DEF_TUNE (X86_TUNE_FOUR_JUMP_LIMIT, "four_jump_limit", + m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM| m_AMD_MULTIPLE + | m_GENERIC) +DEF_TUNE (X86_TUNE_SCHEDULE, "schedule", + m_PENT | m_PPRO | m_CORE_ALL | m_ATOM | m_SLM | m_K6_GEODE + | m_AMD_MULTIPLE | m_GENERIC) +DEF_TUNE (X86_TUNE_USE_BT, "use_bt", + m_CORE_ALL | m_ATOM | m_SLM | m_AMD_MULTIPLE | m_GENERIC) +DEF_TUNE (X86_TUNE_USE_INCDEC, "use_incdec", + ~(m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_GENERIC)) +DEF_TUNE (X86_TUNE_PAD_RETURNS, "pad_returns", + m_CORE_ALL | m_AMD_MULTIPLE | m_GENERIC) +DEF_TUNE (X86_TUNE_PAD_SHORT_FUNCTION, "pad_short_function", m_ATOM) +DEF_TUNE (X86_TUNE_EXT_80387_CONSTANTS, "ext_80387_constants", + m_PPRO | m_P4_NOCONA | m_CORE_ALL | m_ATOM | m_SLM | m_K6_GEODE + | m_ATHLON_K8 | m_GENERIC) +DEF_TUNE (X86_TUNE_AVOID_VECTOR_DECODE, "avoid_vector_decode", + m_CORE_ALL | m_K8 | m_GENERIC64) +/* X86_TUNE_PROMOTE_HIMODE_IMUL: Modern CPUs have same latency for HImode + and SImode multiply, but 386 and 486 do HImode multiply faster. */ +DEF_TUNE (X86_TUNE_PROMOTE_HIMODE_IMUL, "promote_himode_imul", + ~(m_386 | m_486)) +/* X86_TUNE_SLOW_IMUL_IMM32_MEM: Imul of 32-bit constant and memory is + vector path on AMD machines. */ +DEF_TUNE (X86_TUNE_SLOW_IMUL_IMM32_MEM, "slow_imul_imm32_mem", + m_CORE_ALL | m_K8 | m_AMDFAM10 | m_BDVER | m_BTVER | m_GENERIC64) +/* X86_TUNE_SLOW_IMUL_IMM8: Imul of 8-bit constant is vector path on AMD + machines. */ +DEF_TUNE (X86_TUNE_SLOW_IMUL_IMM8, "slow_imul_imm8", + m_CORE_ALL | m_K8 | m_AMDFAM10 | m_BDVER | m_BTVER | m_GENERIC64) +/* X86_TUNE_MOVE_M1_VIA_OR: On pentiums, it is faster to load -1 via OR + than a MOV. */ +DEF_TUNE (X86_TUNE_MOVE_M1_VIA_OR, "move_m1_via_or", m_PENT) +/* X86_TUNE_NOT_UNPAIRABLE: NOT is not pairable on Pentium, while XOR is, + but one byte longer. */ +DEF_TUNE (X86_TUNE_NOT_UNPAIRABLE, "not_unpairable", m_PENT) +/* X86_TUNE_NOT_VECTORMODE: On AMD K6, NOT is vector decoded with memory + operand that cannot be represented using a modRM byte. The XOR + replacement is long decoded, so this split helps here as well. */ +DEF_TUNE (X86_TUNE_NOT_VECTORMODE, "not_vectormode", m_K6) +/* X86_TUNE_USE_VECTOR_FP_CONVERTS: Prefer vector packed SSE conversion + from FP to FP. */ +DEF_TUNE (X86_TUNE_USE_VECTOR_FP_CONVERTS, "use_vector_fp_converts", + m_CORE_ALL | m_AMDFAM10 | m_GENERIC) +/* X86_TUNE_USE_VECTOR_CONVERTS: Prefer vector packed SSE conversion + from integer to FP. */ +DEF_TUNE (X86_TUNE_USE_VECTOR_CONVERTS, "use_vector_converts", m_AMDFAM10) +/* X86_TUNE_FUSE_CMP_AND_BRANCH: Fuse a compare or test instruction + with a subsequent conditional jump instruction into a single + compare-and-branch uop. */ +DEF_TUNE (X86_TUNE_FUSE_CMP_AND_BRANCH, "fuse_cmp_and_branch", m_BDVER) +/* X86_TUNE_OPT_AGU: Optimize for Address Generation Unit. This flag + will impact LEA instruction selection. */ +DEF_TUNE (X86_TUNE_OPT_AGU, "opt_agu", m_ATOM | m_SLM) +/* X86_TUNE_VECTORIZE_DOUBLE: Enable double precision vector + instructions. */ +DEF_TUNE (X86_TUNE_VECTORIZE_DOUBLE, "vectorize_double", ~m_ATOM) +/* X86_TUNE_SOFTWARE_PREFETCHING_BENEFICIAL: Enable software prefetching + at -O3. For the moment, the prefetching seems badly tuned for Intel + chips. */ +DEF_TUNE (X86_TUNE_SOFTWARE_PREFETCHING_BENEFICIAL, "software_prefetching_beneficial", + m_K6_GEODE | m_AMD_MULTIPLE) +/* X86_TUNE_AVX128_OPTIMAL: Enable 128-bit AVX instruction generation for + the auto-vectorizer. */ +DEF_TUNE (X86_TUNE_AVX128_OPTIMAL, "avx128_optimal", m_BDVER | m_BTVER2) +/* X86_TUNE_REASSOC_INT_TO_PARALLEL: Try to produce parallel computations + during reassociation of integer computation. */ +DEF_TUNE (X86_TUNE_REASSOC_INT_TO_PARALLEL, "reassoc_int_to_parallel", + m_ATOM) +/* X86_TUNE_REASSOC_FP_TO_PARALLEL: Try to produce parallel computations + during reassociation of fp computation. */ +DEF_TUNE (X86_TUNE_REASSOC_FP_TO_PARALLEL, "reassoc_fp_to_parallel", + m_ATOM | m_SLM | m_HASWELL | m_BDVER1 | m_BDVER2) +/* X86_TUNE_GENERAL_REGS_SSE_SPILL: Try to spill general regs to SSE + regs instead of memory. */ +DEF_TUNE (X86_TUNE_GENERAL_REGS_SSE_SPILL, "general_regs_sse_spill", + m_CORE_ALL) +/* X86_TUNE_AVOID_MEM_OPND_FOR_CMOVE: Try to avoid memory operands for + a conditional move. */ +DEF_TUNE (X86_TUNE_AVOID_MEM_OPND_FOR_CMOVE, "avoid_mem_opnd_for_cmove", m_ATOM) +/* X86_TUNE_SPLIT_MEM_OPND_FOR_FP_CONVERTS: Try to split memory operand for + fp converts to destination register. */ +DEF_TUNE (X86_TUNE_SPLIT_MEM_OPND_FOR_FP_CONVERTS, "split_mem_opnd_for_fp_converts", + m_SLM)