/* Subroutines used for code generation on IA-32.
   Copyright (C) 1988-2019 Free Software Foundation, Inc.

This file is part of GCC.

GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.

GCC is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3.  If not see
<http://www.gnu.org/licenses/>.  */

#define IN_TARGET_CODE 1

#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "backend.h"
#include "rtl.h"
#include "tree.h"
#include "memmodel.h"
#include "gimple.h"
#include "cfghooks.h"
#include "cfgloop.h"
#include "df.h"
#include "tm_p.h"
#include "stringpool.h"
#include "expmed.h"
#include "optabs.h"
#include "regs.h"
#include "emit-rtl.h"
#include "recog.h"
#include "cgraph.h"
#include "diagnostic.h"
#include "cfgbuild.h"
#include "alias.h"
#include "fold-const.h"
#include "attribs.h"
#include "calls.h"
#include "stor-layout.h"
#include "varasm.h"
#include "output.h"
#include "insn-attr.h"
#include "flags.h"
#include "except.h"
#include "explow.h"
#include "expr.h"
#include "cfgrtl.h"
#include "common/common-target.h"
#include "langhooks.h"
#include "reload.h"
#include "gimplify.h"
#include "dwarf2.h"
#include "tm-constrs.h"
#include "params.h"
#include "cselib.h"
#include "sched-int.h"
#include "opts.h"
#include "tree-pass.h"
#include "context.h"
#include "pass_manager.h"
#include "target-globals.h"
#include "gimple-iterator.h"
#include "tree-vectorizer.h"
#include "shrink-wrap.h"
#include "builtins.h"
#include "rtl-iter.h"
#include "tree-iterator.h"
#include "dbgcnt.h"
#include "case-cfn-macros.h"
#include "dojump.h"
#include "fold-const-call.h"
#include "tree-vrp.h"
#include "tree-ssanames.h"
#include "selftest.h"
#include "selftest-rtl.h"
#include "print-rtl.h"
#include "intl.h"
#include "ifcvt.h"
#include "symbol-summary.h"
#include "ipa-prop.h"
#include "ipa-fnsummary.h"
#include "wide-int-bitmask.h"
#include "tree-vector-builder.h"
#include "debug.h"
#include "dwarf2out.h"

/* This file should be included last.  */
#include "target-def.h"

#include "x86-tune-costs.h"

static rtx legitimize_dllimport_symbol (rtx, bool);
static rtx legitimize_pe_coff_extern_decl (rtx, bool);
static rtx legitimize_pe_coff_symbol (rtx, bool);
static void ix86_print_operand_address_as (FILE *, rtx, addr_space_t, bool);
static bool ix86_save_reg (unsigned int, bool, bool);
static bool ix86_function_naked (const_tree);
static bool ix86_notrack_prefixed_insn_p (rtx);
static void ix86_emit_restore_reg_using_pop (rtx);


#ifndef CHECK_STACK_LIMIT
#define CHECK_STACK_LIMIT (-1)
#endif

/* Return index of given mode in mult and division cost tables.  */
#define MODE_INDEX(mode)					\
  ((mode) == QImode ? 0						\
   : (mode) == HImode ? 1					\
   : (mode) == SImode ? 2					\
   : (mode) == DImode ? 3					\
   : 4)


/* Set by -mtune.  */
const struct processor_costs *ix86_tune_cost = NULL;

/* Set by -mtune or -Os.  */
const struct processor_costs *ix86_cost = NULL;

/* Processor feature/optimization bitmasks.  */
#define m_386 (HOST_WIDE_INT_1U<<PROCESSOR_I386)
#define m_486 (HOST_WIDE_INT_1U<<PROCESSOR_I486)
#define m_PENT (HOST_WIDE_INT_1U<<PROCESSOR_PENTIUM)
#define m_LAKEMONT (HOST_WIDE_INT_1U<<PROCESSOR_LAKEMONT)
#define m_PPRO (HOST_WIDE_INT_1U<<PROCESSOR_PENTIUMPRO)
#define m_PENT4 (HOST_WIDE_INT_1U<<PROCESSOR_PENTIUM4)
#define m_NOCONA (HOST_WIDE_INT_1U<<PROCESSOR_NOCONA)
#define m_P4_NOCONA (m_PENT4 | m_NOCONA)
#define m_CORE2 (HOST_WIDE_INT_1U<<PROCESSOR_CORE2)
#define m_NEHALEM (HOST_WIDE_INT_1U<<PROCESSOR_NEHALEM)
#define m_SANDYBRIDGE (HOST_WIDE_INT_1U<<PROCESSOR_SANDYBRIDGE)
#define m_HASWELL (HOST_WIDE_INT_1U<<PROCESSOR_HASWELL)
#define m_BONNELL (HOST_WIDE_INT_1U<<PROCESSOR_BONNELL)
#define m_SILVERMONT (HOST_WIDE_INT_1U<<PROCESSOR_SILVERMONT)
#define m_KNL (HOST_WIDE_INT_1U<<PROCESSOR_KNL)
#define m_KNM (HOST_WIDE_INT_1U<<PROCESSOR_KNM)
#define m_SKYLAKE (HOST_WIDE_INT_1U<<PROCESSOR_SKYLAKE)
#define m_SKYLAKE_AVX512 (HOST_WIDE_INT_1U<<PROCESSOR_SKYLAKE_AVX512)
#define m_CANNONLAKE (HOST_WIDE_INT_1U<<PROCESSOR_CANNONLAKE)
#define m_ICELAKE_CLIENT (HOST_WIDE_INT_1U<<PROCESSOR_ICELAKE_CLIENT)
#define m_ICELAKE_SERVER (HOST_WIDE_INT_1U<<PROCESSOR_ICELAKE_SERVER)
#define m_CASCADELAKE (HOST_WIDE_INT_1U<<PROCESSOR_CASCADELAKE)
#define m_CORE_AVX512 (m_SKYLAKE_AVX512 | m_CANNONLAKE \
		       | m_ICELAKE_CLIENT | m_ICELAKE_SERVER | m_CASCADELAKE)
#define m_CORE_AVX2 (m_HASWELL | m_SKYLAKE | m_CORE_AVX512)
#define m_CORE_ALL (m_CORE2 | m_NEHALEM  | m_SANDYBRIDGE | m_CORE_AVX2)
#define m_GOLDMONT (HOST_WIDE_INT_1U<<PROCESSOR_GOLDMONT)
#define m_GOLDMONT_PLUS (HOST_WIDE_INT_1U<<PROCESSOR_GOLDMONT_PLUS)
#define m_TREMONT (HOST_WIDE_INT_1U<<PROCESSOR_TREMONT)
#define m_INTEL (HOST_WIDE_INT_1U<<PROCESSOR_INTEL)

#define m_GEODE (HOST_WIDE_INT_1U<<PROCESSOR_GEODE)
#define m_K6 (HOST_WIDE_INT_1U<<PROCESSOR_K6)
#define m_K6_GEODE (m_K6 | m_GEODE)
#define m_K8 (HOST_WIDE_INT_1U<<PROCESSOR_K8)
#define m_ATHLON (HOST_WIDE_INT_1U<<PROCESSOR_ATHLON)
#define m_ATHLON_K8 (m_K8 | m_ATHLON)
#define m_AMDFAM10 (HOST_WIDE_INT_1U<<PROCESSOR_AMDFAM10)
#define m_BDVER1 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER1)
#define m_BDVER2 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER2)
#define m_BDVER3 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER3)
#define m_BDVER4 (HOST_WIDE_INT_1U<<PROCESSOR_BDVER4)
#define m_ZNVER1 (HOST_WIDE_INT_1U<<PROCESSOR_ZNVER1)
#define m_ZNVER2 (HOST_WIDE_INT_1U<<PROCESSOR_ZNVER2)
#define m_BTVER1 (HOST_WIDE_INT_1U<<PROCESSOR_BTVER1)
#define m_BTVER2 (HOST_WIDE_INT_1U<<PROCESSOR_BTVER2)
#define m_BDVER	(m_BDVER1 | m_BDVER2 | m_BDVER3 | m_BDVER4)
#define m_BTVER (m_BTVER1 | m_BTVER2)
#define m_ZNVER	(m_ZNVER1 | m_ZNVER2)
#define m_AMD_MULTIPLE (m_ATHLON_K8 | m_AMDFAM10 | m_BDVER | m_BTVER \
			| m_ZNVER)

#define m_GENERIC (HOST_WIDE_INT_1U<<PROCESSOR_GENERIC)

const char* ix86_tune_feature_names[X86_TUNE_LAST] = {
#undef DEF_TUNE
#define DEF_TUNE(tune, name, selector) name,
#include "x86-tune.def"
#undef DEF_TUNE
};

/* Feature tests against the various tunings.  */
unsigned char ix86_tune_features[X86_TUNE_LAST];

/* Feature tests against the various tunings used to create ix86_tune_features
   based on the processor mask.  */
static unsigned HOST_WIDE_INT initial_ix86_tune_features[X86_TUNE_LAST] = {
#undef DEF_TUNE
#define DEF_TUNE(tune, name, selector) selector,
#include "x86-tune.def"
#undef DEF_TUNE
};

/* Feature tests against the various architecture variations.  */
unsigned char ix86_arch_features[X86_ARCH_LAST];

/* Feature tests against the various architecture variations, used to create
   ix86_arch_features based on the processor mask.  */
static unsigned HOST_WIDE_INT initial_ix86_arch_features[X86_ARCH_LAST] = {
  /* X86_ARCH_CMOV: Conditional move was added for pentiumpro.  */
  ~(m_386 | m_486 | m_PENT | m_LAKEMONT | m_K6),

  /* X86_ARCH_CMPXCHG: Compare and exchange was added for 80486.  */
  ~m_386,

  /* X86_ARCH_CMPXCHG8B: Compare and exchange 8 bytes was added for pentium. */
  ~(m_386 | m_486),

  /* X86_ARCH_XADD: Exchange and add was added for 80486.  */
  ~m_386,

  /* X86_ARCH_BSWAP: Byteswap was added for 80486.  */
  ~m_386,
};

/* In case the average insn count for single function invocation is
   lower than this constant, emit fast (but longer) prologue and
   epilogue code.  */
#define FAST_PROLOGUE_INSN_COUNT 20

/* Names for 8 (low), 8 (high), and 16-bit registers, respectively.  */
static const char *const qi_reg_name[] = QI_REGISTER_NAMES;
static const char *const qi_high_reg_name[] = QI_HIGH_REGISTER_NAMES;
static const char *const hi_reg_name[] = HI_REGISTER_NAMES;

/* Array of the smallest class containing reg number REGNO, indexed by
   REGNO.  Used by REGNO_REG_CLASS in i386.h.  */

enum reg_class const regclass_map[FIRST_PSEUDO_REGISTER] =
{
  /* ax, dx, cx, bx */
  AREG, DREG, CREG, BREG,
  /* si, di, bp, sp */
  SIREG, DIREG, NON_Q_REGS, NON_Q_REGS,
  /* FP registers */
  FP_TOP_REG, FP_SECOND_REG, FLOAT_REGS, FLOAT_REGS,
  FLOAT_REGS, FLOAT_REGS, FLOAT_REGS, FLOAT_REGS,
  /* arg pointer, flags, fpsr, frame */
  NON_Q_REGS, NO_REGS, NO_REGS, NON_Q_REGS,
  /* SSE registers */
  SSE_FIRST_REG, SSE_REGS, SSE_REGS, SSE_REGS,
  SSE_REGS, SSE_REGS, SSE_REGS, SSE_REGS,
  /* MMX registers */
  MMX_REGS, MMX_REGS, MMX_REGS, MMX_REGS,
  MMX_REGS, MMX_REGS, MMX_REGS, MMX_REGS,
  /* REX registers */
  GENERAL_REGS, GENERAL_REGS, GENERAL_REGS, GENERAL_REGS,
  GENERAL_REGS, GENERAL_REGS, GENERAL_REGS, GENERAL_REGS,
  /* SSE REX registers */
  SSE_REGS, SSE_REGS, SSE_REGS, SSE_REGS,
  SSE_REGS, SSE_REGS, SSE_REGS, SSE_REGS,
  /* AVX-512 SSE registers */
  ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS,
  ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS,
  ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS,
  ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS, ALL_SSE_REGS,
  /* Mask registers.  */
  ALL_MASK_REGS, MASK_REGS, MASK_REGS, MASK_REGS,
  MASK_REGS, MASK_REGS, MASK_REGS, MASK_REGS
};

/* The "default" register map used in 32bit mode.  */

int const dbx_register_map[FIRST_PSEUDO_REGISTER] =
{
  /* general regs */
  0, 2, 1, 3, 6, 7, 4, 5,
  /* fp regs */
  12, 13, 14, 15, 16, 17, 18, 19,
  /* arg, flags, fpsr, frame */
  IGNORED_DWARF_REGNUM, IGNORED_DWARF_REGNUM,
  IGNORED_DWARF_REGNUM, IGNORED_DWARF_REGNUM,
  /* SSE */
  21, 22, 23, 24, 25, 26, 27, 28,
  /* MMX */
  29, 30, 31, 32, 33, 34, 35, 36,
  /* extended integer registers */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* extended sse registers */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* AVX-512 registers 16-23 */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* AVX-512 registers 24-31 */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* Mask registers */
  93, 94, 95, 96, 97, 98, 99, 100
};

/* The "default" register map used in 64bit mode.  */

int const dbx64_register_map[FIRST_PSEUDO_REGISTER] =
{
  /* general regs */
  0, 1, 2, 3, 4, 5, 6, 7,
  /* fp regs */
  33, 34, 35, 36, 37, 38, 39, 40,
  /* arg, flags, fpsr, frame */
  IGNORED_DWARF_REGNUM, IGNORED_DWARF_REGNUM,
  IGNORED_DWARF_REGNUM, IGNORED_DWARF_REGNUM,
  /* SSE */
  17, 18, 19, 20, 21, 22, 23, 24,
  /* MMX */
  41, 42, 43, 44, 45, 46, 47, 48,
  /* extended integer registers */
  8, 9, 10, 11, 12, 13, 14, 15,
  /* extended SSE registers */
  25, 26, 27, 28, 29, 30, 31, 32,
  /* AVX-512 registers 16-23 */
  67, 68, 69, 70, 71, 72, 73, 74,
  /* AVX-512 registers 24-31 */
  75, 76, 77, 78, 79, 80, 81, 82,
  /* Mask registers */
  118, 119, 120, 121, 122, 123, 124, 125
};

/* Define the register numbers to be used in Dwarf debugging information.
   The SVR4 reference port C compiler uses the following register numbers
   in its Dwarf output code:
	0 for %eax (gcc regno = 0)
	1 for %ecx (gcc regno = 2)
	2 for %edx (gcc regno = 1)
	3 for %ebx (gcc regno = 3)
	4 for %esp (gcc regno = 7)
	5 for %ebp (gcc regno = 6)
	6 for %esi (gcc regno = 4)
	7 for %edi (gcc regno = 5)
   The following three DWARF register numbers are never generated by
   the SVR4 C compiler or by the GNU compilers, but SDB on x86/svr4
   believed these numbers have these meanings.
	8  for %eip    (no gcc equivalent)
	9  for %eflags (gcc regno = 17)
	10 for %trapno (no gcc equivalent)
   It is not at all clear how we should number the FP stack registers
   for the x86 architecture.  If the version of SDB on x86/svr4 were
   a bit less brain dead with respect to floating-point then we would
   have a precedent to follow with respect to DWARF register numbers
   for x86 FP registers, but the SDB on x86/svr4 was so completely
   broken with respect to FP registers that it is hardly worth thinking
   of it as something to strive for compatibility with.
   The version of x86/svr4 SDB I had does (partially)
   seem to believe that DWARF register number 11 is associated with
   the x86 register %st(0), but that's about all.  Higher DWARF
   register numbers don't seem to be associated with anything in
   particular, and even for DWARF regno 11, SDB only seemed to under-
   stand that it should say that a variable lives in %st(0) (when
   asked via an `=' command) if we said it was in DWARF regno 11,
   but SDB still printed garbage when asked for the value of the
   variable in question (via a `/' command).
   (Also note that the labels SDB printed for various FP stack regs
   when doing an `x' command were all wrong.)
   Note that these problems generally don't affect the native SVR4
   C compiler because it doesn't allow the use of -O with -g and
   because when it is *not* optimizing, it allocates a memory
   location for each floating-point variable, and the memory
   location is what gets described in the DWARF AT_location
   attribute for the variable in question.
   Regardless of the severe mental illness of the x86/svr4 SDB, we
   do something sensible here and we use the following DWARF
   register numbers.  Note that these are all stack-top-relative
   numbers.
	11 for %st(0) (gcc regno = 8)
	12 for %st(1) (gcc regno = 9)
	13 for %st(2) (gcc regno = 10)
	14 for %st(3) (gcc regno = 11)
	15 for %st(4) (gcc regno = 12)
	16 for %st(5) (gcc regno = 13)
	17 for %st(6) (gcc regno = 14)
	18 for %st(7) (gcc regno = 15)
*/
int const svr4_dbx_register_map[FIRST_PSEUDO_REGISTER] =
{
  /* general regs */
  0, 2, 1, 3, 6, 7, 5, 4,
  /* fp regs */
  11, 12, 13, 14, 15, 16, 17, 18,
  /* arg, flags, fpsr, frame */
  IGNORED_DWARF_REGNUM, 9,
  IGNORED_DWARF_REGNUM, IGNORED_DWARF_REGNUM,
  /* SSE registers */
  21, 22, 23, 24, 25, 26, 27, 28,
  /* MMX registers */
  29, 30, 31, 32, 33, 34, 35, 36,
  /* extended integer registers */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* extended sse registers */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* AVX-512 registers 16-23 */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* AVX-512 registers 24-31 */
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM, INVALID_REGNUM,
  /* Mask registers */
  93, 94, 95, 96, 97, 98, 99, 100
};

/* Define parameter passing and return registers.  */

static int const x86_64_int_parameter_registers[6] =
{
  DI_REG, SI_REG, DX_REG, CX_REG, R8_REG, R9_REG
};

static int const x86_64_ms_abi_int_parameter_registers[4] =
{
  CX_REG, DX_REG, R8_REG, R9_REG
};

static int const x86_64_int_return_registers[4] =
{
  AX_REG, DX_REG, DI_REG, SI_REG
};

/* Additional registers that are clobbered by SYSV calls.  */

#define NUM_X86_64_MS_CLOBBERED_REGS 12
static int const x86_64_ms_sysv_extra_clobbered_registers
		 [NUM_X86_64_MS_CLOBBERED_REGS] =
{
  SI_REG, DI_REG,
  XMM6_REG, XMM7_REG,
  XMM8_REG, XMM9_REG, XMM10_REG, XMM11_REG,
  XMM12_REG, XMM13_REG, XMM14_REG, XMM15_REG
};

enum xlogue_stub {
  XLOGUE_STUB_SAVE,
  XLOGUE_STUB_RESTORE,
  XLOGUE_STUB_RESTORE_TAIL,
  XLOGUE_STUB_SAVE_HFP,
  XLOGUE_STUB_RESTORE_HFP,
  XLOGUE_STUB_RESTORE_HFP_TAIL,

  XLOGUE_STUB_COUNT
};

enum xlogue_stub_sets {
  XLOGUE_SET_ALIGNED,
  XLOGUE_SET_ALIGNED_PLUS_8,
  XLOGUE_SET_HFP_ALIGNED_OR_REALIGN,
  XLOGUE_SET_HFP_ALIGNED_PLUS_8,

  XLOGUE_SET_COUNT
};

/* Register save/restore layout used by out-of-line stubs.  */
class xlogue_layout {
public:
  struct reginfo
  {
    unsigned regno;
    HOST_WIDE_INT offset;	/* Offset used by stub base pointer (rax or
				   rsi) to where each register is stored.  */
  };

  unsigned get_nregs () const			{return m_nregs;}
  HOST_WIDE_INT get_stack_align_off_in () const	{return m_stack_align_off_in;}

  const reginfo &get_reginfo (unsigned reg) const
  {
    gcc_assert (reg < m_nregs);
    return m_regs[reg];
  }

  static const char *get_stub_name (enum xlogue_stub stub,
				    unsigned n_extra_args);

  /* Returns an rtx for the stub's symbol based upon
       1.) the specified stub (save, restore or restore_ret) and
       2.) the value of cfun->machine->call_ms2sysv_extra_regs and
       3.) rather or not stack alignment is being performed.  */
  static rtx get_stub_rtx (enum xlogue_stub stub);

  /* Returns the amount of stack space (including padding) that the stub
     needs to store registers based upon data in the machine_function.  */
  HOST_WIDE_INT get_stack_space_used () const
  {
    const struct machine_function *m = cfun->machine;
    unsigned last_reg = m->call_ms2sysv_extra_regs + MIN_REGS - 1;

    gcc_assert (m->call_ms2sysv_extra_regs <= MAX_EXTRA_REGS);
    return m_regs[last_reg].offset + STUB_INDEX_OFFSET;
  }

  /* Returns the offset for the base pointer used by the stub.  */
  HOST_WIDE_INT get_stub_ptr_offset () const
  {
    return STUB_INDEX_OFFSET + m_stack_align_off_in;
  }

  static const struct xlogue_layout &get_instance ();
  static unsigned count_stub_managed_regs ();
  static bool is_stub_managed_reg (unsigned regno, unsigned count);

  static const HOST_WIDE_INT STUB_INDEX_OFFSET = 0x70;
  static const unsigned MIN_REGS = NUM_X86_64_MS_CLOBBERED_REGS;
  static const unsigned MAX_REGS = 18;
  static const unsigned MAX_EXTRA_REGS = MAX_REGS - MIN_REGS;
  static const unsigned VARIANT_COUNT = MAX_EXTRA_REGS + 1;
  static const unsigned STUB_NAME_MAX_LEN = 20;
  static const char * const STUB_BASE_NAMES[XLOGUE_STUB_COUNT];
  static const unsigned REG_ORDER[MAX_REGS];
  static const unsigned REG_ORDER_REALIGN[MAX_REGS];

private:
  xlogue_layout ();
  xlogue_layout (HOST_WIDE_INT stack_align_off_in, bool hfp);
  xlogue_layout (const xlogue_layout &);

  /* True if hard frame pointer is used.  */
  bool m_hfp;

  /* Max number of register this layout manages.  */
  unsigned m_nregs;

  /* Incoming offset from 16-byte alignment.  */
  HOST_WIDE_INT m_stack_align_off_in;

  /* Register order and offsets.  */
  struct reginfo m_regs[MAX_REGS];

  /* Lazy-inited cache of symbol names for stubs.  */
  static char s_stub_names[2][XLOGUE_STUB_COUNT][VARIANT_COUNT]
			  [STUB_NAME_MAX_LEN];

  static const xlogue_layout s_instances[XLOGUE_SET_COUNT];
};

const char * const xlogue_layout::STUB_BASE_NAMES[XLOGUE_STUB_COUNT] = {
  "savms64",
  "resms64",
  "resms64x",
  "savms64f",
  "resms64f",
  "resms64fx"
};

const unsigned xlogue_layout::REG_ORDER[xlogue_layout::MAX_REGS] = {
/* The below offset values are where each register is stored for the layout
   relative to incoming stack pointer.  The value of each m_regs[].offset will
   be relative to the incoming base pointer (rax or rsi) used by the stub.

    s_instances:   0		1		2		3
    Offset:					realigned or	aligned + 8
    Register	   aligned	aligned + 8	aligned w/HFP	w/HFP	*/
    XMM15_REG,	/* 0x10		0x18		0x10		0x18	*/
    XMM14_REG,	/* 0x20		0x28		0x20		0x28	*/
    XMM13_REG,	/* 0x30		0x38		0x30		0x38	*/
    XMM12_REG,	/* 0x40		0x48		0x40		0x48	*/
    XMM11_REG,	/* 0x50		0x58		0x50		0x58	*/
    XMM10_REG,	/* 0x60		0x68		0x60		0x68	*/
    XMM9_REG,	/* 0x70		0x78		0x70		0x78	*/
    XMM8_REG,	/* 0x80		0x88		0x80		0x88	*/
    XMM7_REG,	/* 0x90		0x98		0x90		0x98	*/
    XMM6_REG,	/* 0xa0		0xa8		0xa0		0xa8	*/
    SI_REG,	/* 0xa8		0xb0		0xa8		0xb0	*/
    DI_REG,	/* 0xb0		0xb8		0xb0		0xb8	*/
    BX_REG,	/* 0xb8		0xc0		0xb8		0xc0	*/
    BP_REG,	/* 0xc0		0xc8		N/A		N/A	*/
    R12_REG,	/* 0xc8		0xd0		0xc0		0xc8	*/
    R13_REG,	/* 0xd0		0xd8		0xc8		0xd0	*/
    R14_REG,	/* 0xd8		0xe0		0xd0		0xd8	*/
    R15_REG,	/* 0xe0		0xe8		0xd8		0xe0	*/
};

/* Instantiate static const values.  */
const HOST_WIDE_INT xlogue_layout::STUB_INDEX_OFFSET;
const unsigned xlogue_layout::MIN_REGS;
const unsigned xlogue_layout::MAX_REGS;
const unsigned xlogue_layout::MAX_EXTRA_REGS;
const unsigned xlogue_layout::VARIANT_COUNT;
const unsigned xlogue_layout::STUB_NAME_MAX_LEN;

/* Initialize xlogue_layout::s_stub_names to zero.  */
char xlogue_layout::s_stub_names[2][XLOGUE_STUB_COUNT][VARIANT_COUNT]
				[STUB_NAME_MAX_LEN];

/* Instantiates all xlogue_layout instances.  */
const xlogue_layout xlogue_layout::s_instances[XLOGUE_SET_COUNT] = {
  xlogue_layout (0, false),
  xlogue_layout (8, false),
  xlogue_layout (0, true),
  xlogue_layout (8, true)
};

/* Return an appropriate const instance of xlogue_layout based upon values
   in cfun->machine and crtl.  */
const struct xlogue_layout &
xlogue_layout::get_instance ()
{
  enum xlogue_stub_sets stub_set;
  bool aligned_plus_8 = cfun->machine->call_ms2sysv_pad_in;

  if (stack_realign_fp)
    stub_set = XLOGUE_SET_HFP_ALIGNED_OR_REALIGN;
  else if (frame_pointer_needed)
    stub_set = aligned_plus_8
	      ? XLOGUE_SET_HFP_ALIGNED_PLUS_8
	      : XLOGUE_SET_HFP_ALIGNED_OR_REALIGN;
  else
    stub_set = aligned_plus_8 ? XLOGUE_SET_ALIGNED_PLUS_8 : XLOGUE_SET_ALIGNED;

  return s_instances[stub_set];
}

/* Determine how many clobbered registers can be saved by the stub.
   Returns the count of registers the stub will save and restore.  */
unsigned
xlogue_layout::count_stub_managed_regs ()
{
  bool hfp = frame_pointer_needed || stack_realign_fp;
  unsigned i, count;
  unsigned regno;

  for (count = i = MIN_REGS; i < MAX_REGS; ++i)
    {
      regno = REG_ORDER[i];
      if (regno == BP_REG && hfp)
	continue;
      if (!ix86_save_reg (regno, false, false))
	break;
      ++count;
    }
  return count;
}

/* Determine if register REGNO is a stub managed register given the
   total COUNT of stub managed registers.  */
bool
xlogue_layout::is_stub_managed_reg (unsigned regno, unsigned count)
{
  bool hfp = frame_pointer_needed || stack_realign_fp;
  unsigned i;

  for (i = 0; i < count; ++i)
    {
      gcc_assert (i < MAX_REGS);
      if (REG_ORDER[i] == BP_REG && hfp)
	++count;
      else if (REG_ORDER[i] == regno)
	return true;
    }
  return false;
}

/* Constructor for xlogue_layout.  */
xlogue_layout::xlogue_layout (HOST_WIDE_INT stack_align_off_in, bool hfp)
  : m_hfp (hfp) , m_nregs (hfp ? 17 : 18),
    m_stack_align_off_in (stack_align_off_in)
{
  HOST_WIDE_INT offset = stack_align_off_in;
  unsigned i, j;

  for (i = j = 0; i < MAX_REGS; ++i)
    {
      unsigned regno = REG_ORDER[i];

      if (regno == BP_REG && hfp)
	continue;
      if (SSE_REGNO_P (regno))
	{
	  offset += 16;
	  /* Verify that SSE regs are always aligned.  */
	  gcc_assert (!((stack_align_off_in + offset) & 15));
	}
      else
	offset += 8;

      m_regs[j].regno    = regno;
      m_regs[j++].offset = offset - STUB_INDEX_OFFSET;
    }
  gcc_assert (j == m_nregs);
}

const char *
xlogue_layout::get_stub_name (enum xlogue_stub stub,
			      unsigned n_extra_regs)
{
  const int have_avx = TARGET_AVX;
  char *name = s_stub_names[!!have_avx][stub][n_extra_regs];

  /* Lazy init */
  if (!*name)
    {
      int res = snprintf (name, STUB_NAME_MAX_LEN, "__%s_%s_%u",
			  (have_avx ? "avx" : "sse"),
			  STUB_BASE_NAMES[stub],
			  MIN_REGS + n_extra_regs);
      gcc_checking_assert (res < (int)STUB_NAME_MAX_LEN);
    }

  return name;
}

/* Return rtx of a symbol ref for the entry point (based upon
   cfun->machine->call_ms2sysv_extra_regs) of the specified stub.  */
rtx
xlogue_layout::get_stub_rtx (enum xlogue_stub stub)
{
  const unsigned n_extra_regs = cfun->machine->call_ms2sysv_extra_regs;
  gcc_checking_assert (n_extra_regs <= MAX_EXTRA_REGS);
  gcc_assert (stub < XLOGUE_STUB_COUNT);
  gcc_assert (crtl->stack_realign_finalized);

  return gen_rtx_SYMBOL_REF (Pmode, get_stub_name (stub, n_extra_regs));
}

/* Define the structure for the machine field in struct function.  */

struct GTY(()) stack_local_entry {
  unsigned short mode;
  unsigned short n;
  rtx rtl;
  struct stack_local_entry *next;
};

/* Which cpu are we scheduling for.  */
enum attr_cpu ix86_schedule;

/* Which cpu are we optimizing for.  */
enum processor_type ix86_tune;

/* Which instruction set architecture to use.  */
enum processor_type ix86_arch;

/* True if processor has SSE prefetch instruction.  */
unsigned char x86_prefetch_sse;

/* -mstackrealign option */
static const char ix86_force_align_arg_pointer_string[]
  = "force_align_arg_pointer";

static rtx (*ix86_gen_leave) (void);
static rtx (*ix86_gen_add3) (rtx, rtx, rtx);
static rtx (*ix86_gen_sub3) (rtx, rtx, rtx);
static rtx (*ix86_gen_sub3_carry) (rtx, rtx, rtx, rtx, rtx);
static rtx (*ix86_gen_one_cmpl2) (rtx, rtx);
static rtx (*ix86_gen_monitor) (rtx, rtx, rtx);
static rtx (*ix86_gen_monitorx) (rtx, rtx, rtx);
static rtx (*ix86_gen_clzero) (rtx);
static rtx (*ix86_gen_andsp) (rtx, rtx, rtx);
static rtx (*ix86_gen_allocate_stack_worker) (rtx, rtx);
static rtx (*ix86_gen_adjust_stack_and_probe) (rtx, rtx, rtx);
static rtx (*ix86_gen_probe_stack_range) (rtx, rtx, rtx);
static rtx (*ix86_gen_tls_global_dynamic_64) (rtx, rtx, rtx);
static rtx (*ix86_gen_tls_local_dynamic_base_64) (rtx, rtx);

/* Preferred alignment for stack boundary in bits.  */
unsigned int ix86_preferred_stack_boundary;

/* Alignment for incoming stack boundary in bits specified at
   command line.  */
static unsigned int ix86_user_incoming_stack_boundary;

/* Default alignment for incoming stack boundary in bits.  */
static unsigned int ix86_default_incoming_stack_boundary;

/* Alignment for incoming stack boundary in bits.  */
unsigned int ix86_incoming_stack_boundary;

/* Calling abi specific va_list type nodes.  */
static GTY(()) tree sysv_va_list_type_node;
static GTY(()) tree ms_va_list_type_node;

/* Prefix built by ASM_GENERATE_INTERNAL_LABEL.  */
char internal_label_prefix[16];
int internal_label_prefix_len;

/* Fence to use after loop using movnt.  */
tree x86_mfence;

/* Register class used for passing given 64bit part of the argument.
   These represent classes as documented by the PS ABI, with the exception
   of SSESF, SSEDF classes, that are basically SSE class, just gcc will
   use SF or DFmode move instead of DImode to avoid reformatting penalties.

   Similarly we play games with INTEGERSI_CLASS to use cheaper SImode moves
   whenever possible (upper half does contain padding).  */
enum x86_64_reg_class
  {
    X86_64_NO_CLASS,
    X86_64_INTEGER_CLASS,
    X86_64_INTEGERSI_CLASS,
    X86_64_SSE_CLASS,
    X86_64_SSESF_CLASS,
    X86_64_SSEDF_CLASS,
    X86_64_SSEUP_CLASS,
    X86_64_X87_CLASS,
    X86_64_X87UP_CLASS,
    X86_64_COMPLEX_X87_CLASS,
    X86_64_MEMORY_CLASS
  };

#define MAX_CLASSES 8

/* Table of constants used by fldpi, fldln2, etc....  */
static REAL_VALUE_TYPE ext_80387_constants_table [5];
static bool ext_80387_constants_init;


static struct machine_function * ix86_init_machine_status (void);
static rtx ix86_function_value (const_tree, const_tree, bool);
static bool ix86_function_value_regno_p (const unsigned int);
static unsigned int ix86_function_arg_boundary (machine_mode,
						const_tree);
static rtx ix86_static_chain (const_tree, bool);
static int ix86_function_regparm (const_tree, const_tree);
static void ix86_compute_frame_layout (void);
static bool ix86_expand_vector_init_one_nonzero (bool, machine_mode,
						 rtx, rtx, int);
static void ix86_add_new_builtins (HOST_WIDE_INT, HOST_WIDE_INT);
static tree ix86_canonical_va_list_type (tree);
static void predict_jump (int);
static unsigned int split_stack_prologue_scratch_regno (void);
static bool i386_asm_output_addr_const_extra (FILE *, rtx);

enum ix86_function_specific_strings
{
  IX86_FUNCTION_SPECIFIC_ARCH,
  IX86_FUNCTION_SPECIFIC_TUNE,
  IX86_FUNCTION_SPECIFIC_MAX
};

static char *ix86_target_string (HOST_WIDE_INT, HOST_WIDE_INT, int, int,
				 const char *, const char *, enum fpmath_unit,
				 bool);
static void ix86_function_specific_save (struct cl_target_option *,
					 struct gcc_options *opts);
static void ix86_function_specific_restore (struct gcc_options *opts,
					    struct cl_target_option *);
static void ix86_function_specific_post_stream_in (struct cl_target_option *);
static void ix86_function_specific_print (FILE *, int,
					  struct cl_target_option *);
static bool ix86_valid_target_attribute_p (tree, tree, tree, int);
static bool ix86_valid_target_attribute_inner_p (tree, char *[],
						 struct gcc_options *,
						 struct gcc_options *,
						 struct gcc_options *);
static bool ix86_can_inline_p (tree, tree);
static void ix86_set_current_function (tree);
static unsigned int ix86_minimum_incoming_stack_boundary (bool);

static enum calling_abi ix86_function_abi (const_tree);


#ifndef SUBTARGET32_DEFAULT_CPU
#define SUBTARGET32_DEFAULT_CPU "i386"
#endif

/* Whether -mtune= or -march= were specified */
static int ix86_tune_defaulted;
static int ix86_arch_specified;

/* Vectorization library interface and handlers.  */
static tree (*ix86_veclib_handler) (combined_fn, tree, tree);

static tree ix86_veclibabi_svml (combined_fn, tree, tree);
static tree ix86_veclibabi_acml (combined_fn, tree, tree);

/* This table must be in sync with enum processor_type in i386.h.  */ 
static const struct processor_costs *processor_cost_table[] =
{
  &generic_cost,
  &i386_cost,
  &i486_cost,
  &pentium_cost,
  &lakemont_cost,
  &pentiumpro_cost,
  &pentium4_cost,
  &nocona_cost,
  &core_cost,
  &core_cost,
  &core_cost,
  &core_cost,
  &atom_cost,
  &slm_cost,
  &slm_cost,
  &slm_cost,
  &slm_cost,
  &slm_cost,
  &slm_cost,
  &skylake_cost,
  &skylake_cost,
  &skylake_cost,
  &skylake_cost,
  &skylake_cost,
  &skylake_cost,
  &intel_cost,
  &geode_cost,
  &k6_cost,
  &athlon_cost,
  &k8_cost,
  &amdfam10_cost,
  &bdver_cost,
  &bdver_cost,
  &bdver_cost,
  &bdver_cost,
  &btver1_cost,
  &btver2_cost,
  &znver1_cost,
  &znver2_cost
};

/* Guarantee that the array is aligned with enum processor_type.  */
STATIC_ASSERT (ARRAY_SIZE (processor_cost_table) == PROCESSOR_max);

static unsigned int
rest_of_handle_insert_vzeroupper (void)
{
  int i;

  /* vzeroupper instructions are inserted immediately after reload to
     account for possible spills from 256bit or 512bit registers.  The pass
     reuses mode switching infrastructure by re-running mode insertion
     pass, so disable entities that have already been processed.  */
  for (i = 0; i < MAX_386_ENTITIES; i++)
    ix86_optimize_mode_switching[i] = 0;

  ix86_optimize_mode_switching[AVX_U128] = 1;

  /* Call optimize_mode_switching.  */
  g->get_passes ()->execute_pass_mode_switching ();
  return 0;
}

/* Return 1 if INSN uses or defines a hard register.
   Hard register uses in a memory address are ignored.
   Clobbers and flags definitions are ignored.  */

static bool
has_non_address_hard_reg (rtx_insn *insn)
{
  df_ref ref;
  FOR_EACH_INSN_DEF (ref, insn)
    if (HARD_REGISTER_P (DF_REF_REAL_REG (ref))
	&& !DF_REF_FLAGS_IS_SET (ref, DF_REF_MUST_CLOBBER)
	&& DF_REF_REGNO (ref) != FLAGS_REG)
      return true;

  FOR_EACH_INSN_USE (ref, insn)
    if (!DF_REF_REG_MEM_P (ref) && HARD_REGISTER_P (DF_REF_REAL_REG (ref)))
      return true;

  return false;
}

/* Check if comparison INSN may be transformed
   into vector comparison.  Currently we transform
   zero checks only which look like:

   (set (reg:CCZ 17 flags)
        (compare:CCZ (ior:SI (subreg:SI (reg:DI x) 4)
                             (subreg:SI (reg:DI x) 0))
		     (const_int 0 [0])))  */

static bool
convertible_comparison_p (rtx_insn *insn)
{
  if (!TARGET_SSE4_1)
    return false;

  rtx def_set = single_set (insn);

  gcc_assert (def_set);

  rtx src = SET_SRC (def_set);
  rtx dst = SET_DEST (def_set);

  gcc_assert (GET_CODE (src) == COMPARE);

  if (GET_CODE (dst) != REG
      || REGNO (dst) != FLAGS_REG
      || GET_MODE (dst) != CCZmode)
    return false;

  rtx op1 = XEXP (src, 0);
  rtx op2 = XEXP (src, 1);

  if (op2 != CONST0_RTX (GET_MODE (op2)))
    return false;

  if (GET_CODE (op1) != IOR)
    return false;

  op2 = XEXP (op1, 1);
  op1 = XEXP (op1, 0);

  if (!SUBREG_P (op1)
      || !SUBREG_P (op2)
      || GET_MODE (op1) != SImode
      || GET_MODE (op2) != SImode
      || ((SUBREG_BYTE (op1) != 0
	   || SUBREG_BYTE (op2) != GET_MODE_SIZE (SImode))
	  && (SUBREG_BYTE (op2) != 0
	      || SUBREG_BYTE (op1) != GET_MODE_SIZE (SImode))))
    return false;

  op1 = SUBREG_REG (op1);
  op2 = SUBREG_REG (op2);

  if (op1 != op2
      || !REG_P (op1)
      || GET_MODE (op1) != DImode)
    return false;

  return true;
}

/* The DImode version of scalar_to_vector_candidate_p.  */

static bool
dimode_scalar_to_vector_candidate_p (rtx_insn *insn)
{
  rtx def_set = single_set (insn);

  if (!def_set)
    return false;

  if (has_non_address_hard_reg (insn))
    return false;

  rtx src = SET_SRC (def_set);
  rtx dst = SET_DEST (def_set);

  if (GET_CODE (src) == COMPARE)
    return convertible_comparison_p (insn);

  /* We are interested in DImode promotion only.  */
  if ((GET_MODE (src) != DImode
       && !CONST_INT_P (src))
      || GET_MODE (dst) != DImode)
    return false;

  if (!REG_P (dst) && !MEM_P (dst))
    return false;

  switch (GET_CODE (src))
    {
    case ASHIFTRT:
      if (!TARGET_AVX512VL)
	return false;
      /* FALLTHRU */

    case ASHIFT:
    case LSHIFTRT:
      if (!REG_P (XEXP (src, 1))
	  && (!SUBREG_P (XEXP (src, 1))
	      || SUBREG_BYTE (XEXP (src, 1)) != 0
	      || !REG_P (SUBREG_REG (XEXP (src, 1))))
	  && (!CONST_INT_P (XEXP (src, 1))
	      || !IN_RANGE (INTVAL (XEXP (src, 1)), 0, 63)))
	return false;

      if (GET_MODE (XEXP (src, 1)) != QImode
	  && !CONST_INT_P (XEXP (src, 1)))
	return false;
      break;

    case PLUS:
    case MINUS:
    case IOR:
    case XOR:
    case AND:
      if (!REG_P (XEXP (src, 1))
	  && !MEM_P (XEXP (src, 1))
	  && !CONST_INT_P (XEXP (src, 1)))
	return false;

      if (GET_MODE (XEXP (src, 1)) != DImode
	  && !CONST_INT_P (XEXP (src, 1)))
	return false;
      break;

    case NEG:
    case NOT:
      break;

    case REG:
      return true;

    case MEM:
    case CONST_INT:
      return REG_P (dst);

    default:
      return false;
    }

  if (!REG_P (XEXP (src, 0))
      && !MEM_P (XEXP (src, 0))
      && !CONST_INT_P (XEXP (src, 0))
      /* Check for andnot case.  */
      && (GET_CODE (src) != AND
	  || GET_CODE (XEXP (src, 0)) != NOT
	  || !REG_P (XEXP (XEXP (src, 0), 0))))
      return false;

  if (GET_MODE (XEXP (src, 0)) != DImode
      && !CONST_INT_P (XEXP (src, 0)))
    return false;

  return true;
}

/* The TImode version of scalar_to_vector_candidate_p.  */

static bool
timode_scalar_to_vector_candidate_p (rtx_insn *insn)
{
  rtx def_set = single_set (insn);

  if (!def_set)
    return false;

  if (has_non_address_hard_reg (insn))
    return false;

  rtx src = SET_SRC (def_set);
  rtx dst = SET_DEST (def_set);

  /* Only TImode load and store are allowed.  */
  if (GET_MODE (dst) != TImode)
    return false;

  if (MEM_P (dst))
    {
      /* Check for store.  Memory must be aligned or unaligned store
	 is optimal.  Only support store from register, standard SSE
	 constant or CONST_WIDE_INT generated from piecewise store.

	 ??? Verify performance impact before enabling CONST_INT for
	 __int128 store.  */
      if (misaligned_operand (dst, TImode)
	  && !TARGET_SSE_UNALIGNED_STORE_OPTIMAL)
	return false;

      switch (GET_CODE (src))
	{
	default:
	  return false;

	case REG:
	case CONST_WIDE_INT:
	  return true;

	case CONST_INT:
	  return standard_sse_constant_p (src, TImode);
	}
    }
  else if (MEM_P (src))
    {
      /* Check for load.  Memory must be aligned or unaligned load is
	 optimal.  */
      return (REG_P (dst)
	      && (!misaligned_operand (src, TImode)
		  || TARGET_SSE_UNALIGNED_LOAD_OPTIMAL));
    }

  return false;
}

/* Return 1 if INSN may be converted into vector
   instruction.  */

static bool
scalar_to_vector_candidate_p (rtx_insn *insn)
{
  if (TARGET_64BIT)
    return timode_scalar_to_vector_candidate_p (insn);
  else
    return dimode_scalar_to_vector_candidate_p (insn);
}

/* The DImode version of remove_non_convertible_regs.  */

static void
dimode_remove_non_convertible_regs (bitmap candidates)
{
  bitmap_iterator bi;
  unsigned id;
  bitmap regs = BITMAP_ALLOC (NULL);

  EXECUTE_IF_SET_IN_BITMAP (candidates, 0, id, bi)
    {
      rtx def_set = single_set (DF_INSN_UID_GET (id)->insn);
      rtx reg = SET_DEST (def_set);

      if (!REG_P (reg)
	  || bitmap_bit_p (regs, REGNO (reg))
	  || HARD_REGISTER_P (reg))
	continue;

      for (df_ref def = DF_REG_DEF_CHAIN (REGNO (reg));
	   def;
	   def = DF_REF_NEXT_REG (def))
	{
	  if (!bitmap_bit_p (candidates, DF_REF_INSN_UID (def)))
	    {
	      if (dump_file)
		fprintf (dump_file,
			 "r%d has non convertible definition in insn %d\n",
			 REGNO (reg), DF_REF_INSN_UID (def));

	      bitmap_set_bit (regs, REGNO (reg));
	      break;
	    }
	}
    }

  EXECUTE_IF_SET_IN_BITMAP (regs, 0, id, bi)
    {
      for (df_ref def = DF_REG_DEF_CHAIN (id);
	   def;
	   def = DF_REF_NEXT_REG (def))
	if (bitmap_bit_p (candidates, DF_REF_INSN_UID (def)))
	  {
	    if (dump_file)
	      fprintf (dump_file, "Removing insn %d from candidates list\n",
		       DF_REF_INSN_UID (def));

	    bitmap_clear_bit (candidates, DF_REF_INSN_UID (def));
	  }
    }

  BITMAP_FREE (regs);
}

/* For a register REGNO, scan instructions for its defs and uses.
   Put REGNO in REGS if a def or use isn't in CANDIDATES.  */

static void
timode_check_non_convertible_regs (bitmap candidates, bitmap regs,
				   unsigned int regno)
{
  for (df_ref def = DF_REG_DEF_CHAIN (regno);
       def;
       def = DF_REF_NEXT_REG (def))
    {
      if (!bitmap_bit_p (candidates, DF_REF_INSN_UID (def)))
	{
	  if (dump_file)
	    fprintf (dump_file,
		     "r%d has non convertible def in insn %d\n",
		     regno, DF_REF_INSN_UID (def));

	  bitmap_set_bit (regs, regno);
	  break;
	}
    }

  for (df_ref ref = DF_REG_USE_CHAIN (regno);
       ref;
       ref = DF_REF_NEXT_REG (ref))
    {
      /* Debug instructions are skipped.  */
      if (NONDEBUG_INSN_P (DF_REF_INSN (ref))
	  && !bitmap_bit_p (candidates, DF_REF_INSN_UID (ref)))
	{
	  if (dump_file)
	    fprintf (dump_file,
		     "r%d has non convertible use in insn %d\n",
		     regno, DF_REF_INSN_UID (ref));

	  bitmap_set_bit (regs, regno);
	  break;
	}
    }
}

/* The TImode version of remove_non_convertible_regs.  */

static void
timode_remove_non_convertible_regs (bitmap candidates)
{
  bitmap_iterator bi;
  unsigned id;
  bitmap regs = BITMAP_ALLOC (NULL);

  EXECUTE_IF_SET_IN_BITMAP (candidates, 0, id, bi)
    {
      rtx def_set = single_set (DF_INSN_UID_GET (id)->insn);
      rtx dest = SET_DEST (def_set);
      rtx src = SET_SRC (def_set);

      if ((!REG_P (dest)
	   || bitmap_bit_p (regs, REGNO (dest))
	   || HARD_REGISTER_P (dest))
	  && (!REG_P (src)
	      || bitmap_bit_p (regs, REGNO (src))
	      || HARD_REGISTER_P (src)))
	continue;

      if (REG_P (dest))
	timode_check_non_convertible_regs (candidates, regs,
					   REGNO (dest));

      if (REG_P (src))
	timode_check_non_convertible_regs (candidates, regs,
					   REGNO (src));
    }

  EXECUTE_IF_SET_IN_BITMAP (regs, 0, id, bi)
    {
      for (df_ref def = DF_REG_DEF_CHAIN (id);
	   def;
	   def = DF_REF_NEXT_REG (def))
	if (bitmap_bit_p (candidates, DF_REF_INSN_UID (def)))
	  {
	    if (dump_file)
	      fprintf (dump_file, "Removing insn %d from candidates list\n",
		       DF_REF_INSN_UID (def));

	    bitmap_clear_bit (candidates, DF_REF_INSN_UID (def));
	  }

      for (df_ref ref = DF_REG_USE_CHAIN (id);
	   ref;
	   ref = DF_REF_NEXT_REG (ref))
	if (bitmap_bit_p (candidates, DF_REF_INSN_UID (ref)))
	  {
	    if (dump_file)
	      fprintf (dump_file, "Removing insn %d from candidates list\n",
		       DF_REF_INSN_UID (ref));

	    bitmap_clear_bit (candidates, DF_REF_INSN_UID (ref));
	  }
    }

  BITMAP_FREE (regs);
}

/* For a given bitmap of insn UIDs scans all instruction and
   remove insn from CANDIDATES in case it has both convertible
   and not convertible definitions.

   All insns in a bitmap are conversion candidates according to
   scalar_to_vector_candidate_p.  Currently it implies all insns
   are single_set.  */

static void
remove_non_convertible_regs (bitmap candidates)
{
  if (TARGET_64BIT)
    timode_remove_non_convertible_regs (candidates);
  else
    dimode_remove_non_convertible_regs (candidates);
}

class scalar_chain
{
 public:
  scalar_chain ();
  virtual ~scalar_chain ();

  static unsigned max_id;

  /* ID of a chain.  */
  unsigned int chain_id;
  /* A queue of instructions to be included into a chain.  */
  bitmap queue;
  /* Instructions included into a chain.  */
  bitmap insns;
  /* All registers defined by a chain.  */
  bitmap defs;
  /* Registers used in both vector and sclar modes.  */
  bitmap defs_conv;

  void build (bitmap candidates, unsigned insn_uid);
  virtual int compute_convert_gain () = 0;
  int convert ();

 protected:
  void add_to_queue (unsigned insn_uid);
  void emit_conversion_insns (rtx insns, rtx_insn *pos);

 private:
  void add_insn (bitmap candidates, unsigned insn_uid);
  void analyze_register_chain (bitmap candidates, df_ref ref);
  virtual void mark_dual_mode_def (df_ref def) = 0;
  virtual void convert_insn (rtx_insn *insn) = 0;
  virtual void convert_registers () = 0;
};

class dimode_scalar_chain : public scalar_chain
{
 public:
  int compute_convert_gain ();
 private:
  void mark_dual_mode_def (df_ref def);
  rtx replace_with_subreg (rtx x, rtx reg, rtx subreg);
  void replace_with_subreg_in_insn (rtx_insn *insn, rtx reg, rtx subreg);
  void convert_insn (rtx_insn *insn);
  void convert_op (rtx *op, rtx_insn *insn);
  void convert_reg (unsigned regno);
  void make_vector_copies (unsigned regno);
  void convert_registers ();
  int vector_const_cost (rtx exp);
};

class timode_scalar_chain : public scalar_chain
{
 public:
  /* Convert from TImode to V1TImode is always faster.  */
  int compute_convert_gain () { return 1; }

 private:
  void mark_dual_mode_def (df_ref def);
  void fix_debug_reg_uses (rtx reg);
  void convert_insn (rtx_insn *insn);
  /* We don't convert registers to difference size.  */
  void convert_registers () {}
};

unsigned scalar_chain::max_id = 0;

/* Initialize new chain.  */

scalar_chain::scalar_chain ()
{
  chain_id = ++max_id;

   if (dump_file)
    fprintf (dump_file, "Created a new instruction chain #%d\n", chain_id);

  bitmap_obstack_initialize (NULL);
  insns = BITMAP_ALLOC (NULL);
  defs = BITMAP_ALLOC (NULL);
  defs_conv = BITMAP_ALLOC (NULL);
  queue = NULL;
}

/* Free chain's data.  */

scalar_chain::~scalar_chain ()
{
  BITMAP_FREE (insns);
  BITMAP_FREE (defs);
  BITMAP_FREE (defs_conv);
  bitmap_obstack_release (NULL);
}

/* Add instruction into chains' queue.  */

void
scalar_chain::add_to_queue (unsigned insn_uid)
{
  if (bitmap_bit_p (insns, insn_uid)
      || bitmap_bit_p (queue, insn_uid))
    return;

  if (dump_file)
    fprintf (dump_file, "  Adding insn %d into chain's #%d queue\n",
	     insn_uid, chain_id);
  bitmap_set_bit (queue, insn_uid);
}

/* For DImode conversion, mark register defined by DEF as requiring
   conversion.  */

void
dimode_scalar_chain::mark_dual_mode_def (df_ref def)
{
  gcc_assert (DF_REF_REG_DEF_P (def));

  if (bitmap_bit_p (defs_conv, DF_REF_REGNO (def)))
    return;

  if (dump_file)
    fprintf (dump_file,
	     "  Mark r%d def in insn %d as requiring both modes in chain #%d\n",
	     DF_REF_REGNO (def), DF_REF_INSN_UID (def), chain_id);

  bitmap_set_bit (defs_conv, DF_REF_REGNO (def));
}

/* For TImode conversion, it is unused.  */

void
timode_scalar_chain::mark_dual_mode_def (df_ref)
{
  gcc_unreachable ();
}

/* Check REF's chain to add new insns into a queue
   and find registers requiring conversion.  */

void
scalar_chain::analyze_register_chain (bitmap candidates, df_ref ref)
{
  df_link *chain;

  gcc_assert (bitmap_bit_p (insns, DF_REF_INSN_UID (ref))
	      || bitmap_bit_p (candidates, DF_REF_INSN_UID (ref)));
  add_to_queue (DF_REF_INSN_UID (ref));

  for (chain = DF_REF_CHAIN (ref); chain; chain = chain->next)
    {
      unsigned uid = DF_REF_INSN_UID (chain->ref);

      if (!NONDEBUG_INSN_P (DF_REF_INSN (chain->ref)))
	continue;

      if (!DF_REF_REG_MEM_P (chain->ref))
	{
	  if (bitmap_bit_p (insns, uid))
	    continue;

	  if (bitmap_bit_p (candidates, uid))
	    {
	      add_to_queue (uid);
	      continue;
	    }
	}

      if (DF_REF_REG_DEF_P (chain->ref))
	{
	  if (dump_file)
	    fprintf (dump_file, "  r%d def in insn %d isn't convertible\n",
		     DF_REF_REGNO (chain->ref), uid);
	  mark_dual_mode_def (chain->ref);
	}
      else
	{
	  if (dump_file)
	    fprintf (dump_file, "  r%d use in insn %d isn't convertible\n",
		     DF_REF_REGNO (chain->ref), uid);
	  mark_dual_mode_def (ref);
	}
    }
}

/* Add instruction into a chain.  */

void
scalar_chain::add_insn (bitmap candidates, unsigned int insn_uid)
{
  if (bitmap_bit_p (insns, insn_uid))
    return;

  if (dump_file)
    fprintf (dump_file, "  Adding insn %d to chain #%d\n", insn_uid, chain_id);

  bitmap_set_bit (insns, insn_uid);

  rtx_insn *insn = DF_INSN_UID_GET (insn_uid)->insn;
  rtx def_set = single_set (insn);
  if (def_set && REG_P (SET_DEST (def_set))
      && !HARD_REGISTER_P (SET_DEST (def_set)))
    bitmap_set_bit (defs, REGNO (SET_DEST (def_set)));

  df_ref ref;
  df_ref def;
  for (ref = DF_INSN_UID_DEFS (insn_uid); ref; ref = DF_REF_NEXT_LOC (ref))
    if (!HARD_REGISTER_P (DF_REF_REG (ref)))
      for (def = DF_REG_DEF_CHAIN (DF_REF_REGNO (ref));
	   def;
	   def = DF_REF_NEXT_REG (def))
	analyze_register_chain (candidates, def);
  for (ref = DF_INSN_UID_USES (insn_uid); ref; ref = DF_REF_NEXT_LOC (ref))
    if (!DF_REF_REG_MEM_P (ref))
      analyze_register_chain (candidates, ref);
}

/* Build new chain starting from insn INSN_UID recursively
   adding all dependent uses and definitions.  */

void
scalar_chain::build (bitmap candidates, unsigned insn_uid)
{
  queue = BITMAP_ALLOC (NULL);
  bitmap_set_bit (queue, insn_uid);

  if (dump_file)
    fprintf (dump_file, "Building chain #%d...\n", chain_id);

  while (!bitmap_empty_p (queue))
    {
      insn_uid = bitmap_first_set_bit (queue);
      bitmap_clear_bit (queue, insn_uid);
      bitmap_clear_bit (candidates, insn_uid);
      add_insn (candidates, insn_uid);
    }

  if (dump_file)
    {
      fprintf (dump_file, "Collected chain #%d...\n", chain_id);
      fprintf (dump_file, "  insns: ");
      dump_bitmap (dump_file, insns);
      if (!bitmap_empty_p (defs_conv))
	{
	  bitmap_iterator bi;
	  unsigned id;
	  const char *comma = "";
	  fprintf (dump_file, "  defs to convert: ");
	  EXECUTE_IF_SET_IN_BITMAP (defs_conv, 0, id, bi)
	    {
	      fprintf (dump_file, "%sr%d", comma, id);
	      comma = ", ";
	    }
	  fprintf (dump_file, "\n");
	}
    }

  BITMAP_FREE (queue);
}

/* Return a cost of building a vector costant
   instead of using a scalar one.  */

int
dimode_scalar_chain::vector_const_cost (rtx exp)
{
  gcc_assert (CONST_INT_P (exp));

  if (standard_sse_constant_p (exp, V2DImode))
    return COSTS_N_INSNS (1);
  return ix86_cost->sse_load[1];
}

/* Compute a gain for chain conversion.  */

int
dimode_scalar_chain::compute_convert_gain ()
{
  bitmap_iterator bi;
  unsigned insn_uid;
  int gain = 0;
  int cost = 0;

  if (dump_file)
    fprintf (dump_file, "Computing gain for chain #%d...\n", chain_id);

  EXECUTE_IF_SET_IN_BITMAP (insns, 0, insn_uid, bi)
    {
      rtx_insn *insn = DF_INSN_UID_GET (insn_uid)->insn;
      rtx def_set = single_set (insn);
      rtx src = SET_SRC (def_set);
      rtx dst = SET_DEST (def_set);

      if (REG_P (src) && REG_P (dst))
	gain += COSTS_N_INSNS (2) - ix86_cost->xmm_move;
      else if (REG_P (src) && MEM_P (dst))
	gain += 2 * ix86_cost->int_store[2] - ix86_cost->sse_store[1];
      else if (MEM_P (src) && REG_P (dst))
	gain += 2 * ix86_cost->int_load[2] - ix86_cost->sse_load[1];
      else if (GET_CODE (src) == ASHIFT
	       || GET_CODE (src) == ASHIFTRT
	       || GET_CODE (src) == LSHIFTRT)
	{
    	  if (CONST_INT_P (XEXP (src, 0)))
	    gain -= vector_const_cost (XEXP (src, 0));
	  if (CONST_INT_P (XEXP (src, 1)))
	    {
	      gain += ix86_cost->shift_const;
	      if (INTVAL (XEXP (src, 1)) >= 32)
		gain -= COSTS_N_INSNS (1);
	    }
	  else
	    /* Additional gain for omitting two CMOVs.  */
	    gain += ix86_cost->shift_var + COSTS_N_INSNS (2);
	}
      else if (GET_CODE (src) == PLUS
	       || GET_CODE (src) == MINUS
	       || GET_CODE (src) == IOR
	       || GET_CODE (src) == XOR
	       || GET_CODE (src) == AND)
	{
	  gain += ix86_cost->add;
	  /* Additional gain for andnot for targets without BMI.  */
	  if (GET_CODE (XEXP (src, 0)) == NOT
	      && !TARGET_BMI)
	    gain += 2 * ix86_cost->add;

	  if (CONST_INT_P (XEXP (src, 0)))
	    gain -= vector_const_cost (XEXP (src, 0));
	  if (CONST_INT_P (XEXP (src, 1)))
	    gain -= vector_const_cost (XEXP (src, 1));
	}
      else if (GET_CODE (src) == NEG
	       || GET_CODE (src) == NOT)
	gain += ix86_cost->add - COSTS_N_INSNS (1);
      else if (GET_CODE (src) == COMPARE)
	{
	  /* Assume comparison cost is the same.  */
	}
      else if (CONST_INT_P (src))
	{
	  if (REG_P (dst))
	    gain += COSTS_N_INSNS (2);
	  else if (MEM_P (dst))
	    gain += 2 * ix86_cost->int_store[2] - ix86_cost->sse_store[1];
	  gain -= vector_const_cost (src);
	}
      else
	gcc_unreachable ();
    }

  if (dump_file)
    fprintf (dump_file, "  Instruction conversion gain: %d\n", gain);

  EXECUTE_IF_SET_IN_BITMAP (defs_conv, 0, insn_uid, bi)
    cost += DF_REG_DEF_COUNT (insn_uid) * ix86_cost->mmxsse_to_integer;

  if (dump_file)
    fprintf (dump_file, "  Registers conversion cost: %d\n", cost);

  gain -= cost;

  if (dump_file)
    fprintf (dump_file, "  Total gain: %d\n", gain);

  return gain;
}

/* Replace REG in X with a V2DI subreg of NEW_REG.  */

rtx
dimode_scalar_chain::replace_with_subreg (rtx x, rtx reg, rtx new_reg)
{
  if (x == reg)
    return gen_rtx_SUBREG (V2DImode, new_reg, 0);

  const char *fmt = GET_RTX_FORMAT (GET_CODE (x));
  int i, j;
  for (i = GET_RTX_LENGTH (GET_CODE (x)) - 1; i >= 0; i--)
    {
      if (fmt[i] == 'e')
	XEXP (x, i) = replace_with_subreg (XEXP (x, i), reg, new_reg);
      else if (fmt[i] == 'E')
	for (j = XVECLEN (x, i) - 1; j >= 0; j--)
	  XVECEXP (x, i, j) = replace_with_subreg (XVECEXP (x, i, j),
						   reg, new_reg);
    }

  return x;
}

/* Replace REG in INSN with a V2DI subreg of NEW_REG.  */

void
dimode_scalar_chain::replace_with_subreg_in_insn (rtx_insn *insn,
						  rtx reg, rtx new_reg)
{
  replace_with_subreg (single_set (insn), reg, new_reg);
}

/* Insert generated conversion instruction sequence INSNS
   after instruction AFTER.  New BB may be required in case
   instruction has EH region attached.  */

void
scalar_chain::emit_conversion_insns (rtx insns, rtx_insn *after)
{
  if (!control_flow_insn_p (after))
    {
      emit_insn_after (insns, after);
      return;
    }

  basic_block bb = BLOCK_FOR_INSN (after);
  edge e = find_fallthru_edge (bb->succs);
  gcc_assert (e);

  basic_block new_bb = split_edge (e);
  emit_insn_after (insns, BB_HEAD (new_bb));
}

/* Make vector copies for all register REGNO definitions
   and replace its uses in a chain.  */

void
dimode_scalar_chain::make_vector_copies (unsigned regno)
{
  rtx reg = regno_reg_rtx[regno];
  rtx vreg = gen_reg_rtx (DImode);
  bool count_reg = false;
  df_ref ref;

  for (ref = DF_REG_DEF_CHAIN (regno); ref; ref = DF_REF_NEXT_REG (ref))
    if (!bitmap_bit_p (insns, DF_REF_INSN_UID (ref)))
      {
	df_ref use;

	/* Detect the count register of a shift instruction.  */
	for (use = DF_REG_USE_CHAIN (regno); use; use = DF_REF_NEXT_REG (use))
	  if (bitmap_bit_p (insns, DF_REF_INSN_UID (use)))
	    {
	      rtx_insn *insn = DF_REF_INSN (use);
	      rtx def_set = single_set (insn);

	      gcc_assert (def_set);

	      rtx src = SET_SRC (def_set);

	      if ((GET_CODE (src) == ASHIFT
		   || GET_CODE (src) == ASHIFTRT
		   || GET_CODE (src) == LSHIFTRT)
		  && !CONST_INT_P (XEXP (src, 1))
		  && reg_or_subregno (XEXP (src, 1)) == regno)
		count_reg = true;
	    }

	start_sequence ();
	if (count_reg)
	  {
	    rtx qreg = gen_lowpart (QImode, reg);
	    rtx tmp = gen_reg_rtx (SImode);

	    if (TARGET_ZERO_EXTEND_WITH_AND
		&& optimize_function_for_speed_p (cfun))
	      {
		emit_move_insn (tmp, const0_rtx);
		emit_insn (gen_movstrictqi
			   (gen_lowpart (QImode, tmp), qreg));
	      }
	    else
	      emit_insn (gen_rtx_SET
			 (tmp, gen_rtx_ZERO_EXTEND (SImode, qreg)));

	    if (!TARGET_INTER_UNIT_MOVES_TO_VEC)
	      {
		rtx slot = assign_386_stack_local (SImode, SLOT_STV_TEMP);
		emit_move_insn (slot, tmp);
		tmp = copy_rtx (slot);
	      }

	    emit_insn (gen_zero_extendsidi2 (vreg, tmp));
	  }
	else if (!TARGET_INTER_UNIT_MOVES_TO_VEC)
	  {
	    rtx tmp = assign_386_stack_local (DImode, SLOT_STV_TEMP);
	    emit_move_insn (adjust_address (tmp, SImode, 0),
			    gen_rtx_SUBREG (SImode, reg, 0));
	    emit_move_insn (adjust_address (tmp, SImode, 4),
			    gen_rtx_SUBREG (SImode, reg, 4));
	    emit_move_insn (vreg, tmp);
	  }
	else if (TARGET_SSE4_1)
	  {
	    emit_insn (gen_sse2_loadld (gen_rtx_SUBREG (V4SImode, vreg, 0),
					CONST0_RTX (V4SImode),
					gen_rtx_SUBREG (SImode, reg, 0)));
	    emit_insn (gen_sse4_1_pinsrd (gen_rtx_SUBREG (V4SImode, vreg, 0),
					  gen_rtx_SUBREG (V4SImode, vreg, 0),
					  gen_rtx_SUBREG (SImode, reg, 4),
					  GEN_INT (2)));
	  }
	else
	  {
	    rtx tmp = gen_reg_rtx (DImode);
	    emit_insn (gen_sse2_loadld (gen_rtx_SUBREG (V4SImode, vreg, 0),
					CONST0_RTX (V4SImode),
					gen_rtx_SUBREG (SImode, reg, 0)));
	    emit_insn (gen_sse2_loadld (gen_rtx_SUBREG (V4SImode, tmp, 0),
					CONST0_RTX (V4SImode),
					gen_rtx_SUBREG (SImode, reg, 4)));
	    emit_insn (gen_vec_interleave_lowv4si
		       (gen_rtx_SUBREG (V4SImode, vreg, 0),
			gen_rtx_SUBREG (V4SImode, vreg, 0),
			gen_rtx_SUBREG (V4SImode, tmp, 0)));
	  }
	rtx_insn *seq = get_insns ();
	end_sequence ();
	rtx_insn *insn = DF_REF_INSN (ref);
	emit_conversion_insns (seq, insn);

	if (dump_file)
	  fprintf (dump_file,
		   "  Copied r%d to a vector register r%d for insn %d\n",
		   regno, REGNO (vreg), INSN_UID (insn));
      }

  for (ref = DF_REG_USE_CHAIN (regno); ref; ref = DF_REF_NEXT_REG (ref))
    if (bitmap_bit_p (insns, DF_REF_INSN_UID (ref)))
      {
	rtx_insn *insn = DF_REF_INSN (ref);
	if (count_reg)
	  {
	    rtx def_set = single_set (insn);
	    gcc_assert (def_set);

	    rtx src = SET_SRC (def_set);

	    if ((GET_CODE (src) == ASHIFT
		 || GET_CODE (src) == ASHIFTRT
		 || GET_CODE (src) == LSHIFTRT)
		&& !CONST_INT_P (XEXP (src, 1))
		&& reg_or_subregno (XEXP (src, 1)) == regno)
	      XEXP (src, 1) = vreg;
	  }
	else
	  replace_with_subreg_in_insn (insn, reg, vreg);

	if (dump_file)
	  fprintf (dump_file, "  Replaced r%d with r%d in insn %d\n",
		   regno, REGNO (vreg), INSN_UID (insn));
      }
}

/* Convert all definitions of register REGNO
   and fix its uses.  Scalar copies may be created
   in case register is used in not convertible insn.  */

void
dimode_scalar_chain::convert_reg (unsigned regno)
{
  bool scalar_copy = bitmap_bit_p (defs_conv, regno);
  rtx reg = regno_reg_rtx[regno];
  rtx scopy = NULL_RTX;
  df_ref ref;
  bitmap conv;

  conv = BITMAP_ALLOC (NULL);
  bitmap_copy (conv, insns);

  if (scalar_copy)
    scopy = gen_reg_rtx (DImode);

  for (ref = DF_REG_DEF_CHAIN (regno); ref; ref = DF_REF_NEXT_REG (ref))
    {
      rtx_insn *insn = DF_REF_INSN (ref);
      rtx def_set = single_set (insn);
      rtx src = SET_SRC (def_set);
      rtx reg = DF_REF_REG (ref);

      if (!MEM_P (src))
	{
	  replace_with_subreg_in_insn (insn, reg, reg);
	  bitmap_clear_bit (conv, INSN_UID (insn));
	}

      if (scalar_copy)
	{
	  start_sequence ();
	  if (!TARGET_INTER_UNIT_MOVES_FROM_VEC)
	    {
	      rtx tmp = assign_386_stack_local (DImode, SLOT_STV_TEMP);
	      emit_move_insn (tmp, reg);
	      emit_move_insn (gen_rtx_SUBREG (SImode, scopy, 0),
			      adjust_address (tmp, SImode, 0));
	      emit_move_insn (gen_rtx_SUBREG (SImode, scopy, 4),
			      adjust_address (tmp, SImode, 4));
	    }
	  else if (TARGET_SSE4_1)
	    {
	      rtx tmp = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (1, const0_rtx));
	      emit_insn
		(gen_rtx_SET
		 (gen_rtx_SUBREG (SImode, scopy, 0),
		  gen_rtx_VEC_SELECT (SImode,
				      gen_rtx_SUBREG (V4SImode, reg, 0), tmp)));

	      tmp = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (1, const1_rtx));
	      emit_insn
		(gen_rtx_SET
		 (gen_rtx_SUBREG (SImode, scopy, 4),
		  gen_rtx_VEC_SELECT (SImode,
				      gen_rtx_SUBREG (V4SImode, reg, 0), tmp)));
	    }
	  else
	    {
	      rtx vcopy = gen_reg_rtx (V2DImode);
	      emit_move_insn (vcopy, gen_rtx_SUBREG (V2DImode, reg, 0));
	      emit_move_insn (gen_rtx_SUBREG (SImode, scopy, 0),
			      gen_rtx_SUBREG (SImode, vcopy, 0));
	      emit_move_insn (vcopy,
			      gen_rtx_LSHIFTRT (V2DImode, vcopy, GEN_INT (32)));
	      emit_move_insn (gen_rtx_SUBREG (SImode, scopy, 4),
			      gen_rtx_SUBREG (SImode, vcopy, 0));
	    }
	  rtx_insn *seq = get_insns ();
	  end_sequence ();
	  emit_conversion_insns (seq, insn);

	  if (dump_file)
	    fprintf (dump_file,
		     "  Copied r%d to a scalar register r%d for insn %d\n",
		     regno, REGNO (scopy), INSN_UID (insn));
	}
    }

  for (ref = DF_REG_USE_CHAIN (regno); ref; ref = DF_REF_NEXT_REG (ref))
    if (bitmap_bit_p (insns, DF_REF_INSN_UID (ref)))
      {
	if (bitmap_bit_p (conv, DF_REF_INSN_UID (ref)))
	  {
	    rtx_insn *insn = DF_REF_INSN (ref);

	    rtx def_set = single_set (insn);
	    gcc_assert (def_set);

	    rtx src = SET_SRC (def_set);
	    rtx dst = SET_DEST (def_set);

	    if ((GET_CODE (src) == ASHIFT
		 || GET_CODE (src) == ASHIFTRT
		 || GET_CODE (src) == LSHIFTRT)
		&& !CONST_INT_P (XEXP (src, 1))
		&& reg_or_subregno (XEXP (src, 1)) == regno)
	      {
		rtx tmp2 = gen_reg_rtx (V2DImode);

		start_sequence ();

		if (TARGET_SSE4_1)
		  emit_insn (gen_sse4_1_zero_extendv2qiv2di2
			     (tmp2, gen_rtx_SUBREG (V16QImode, reg, 0)));
		else
		  {
		    rtx vec_cst
		      = gen_rtx_CONST_VECTOR (V2DImode,
					      gen_rtvec (2, GEN_INT (0xff),
							 const0_rtx));
		    vec_cst
		      = validize_mem (force_const_mem (V2DImode, vec_cst));

		    emit_insn (gen_rtx_SET
			       (tmp2,
				gen_rtx_AND (V2DImode,
					     gen_rtx_SUBREG (V2DImode, reg, 0),
					     vec_cst)));
		  }
		rtx_insn *seq = get_insns ();
		end_sequence ();

		emit_insn_before (seq, insn);

		XEXP (src, 1) = gen_rtx_SUBREG (DImode, tmp2, 0);
	      }
	    else if (!MEM_P (dst) || !REG_P (src))
	      replace_with_subreg_in_insn (insn, reg, reg);

	    bitmap_clear_bit (conv, INSN_UID (insn));
	  }
      }
    /* Skip debug insns and uninitialized uses.  */
    else if (DF_REF_CHAIN (ref)
	     && NONDEBUG_INSN_P (DF_REF_INSN (ref)))
      {
	gcc_assert (scopy);
	replace_rtx (DF_REF_INSN (ref), reg, scopy);
	df_insn_rescan (DF_REF_INSN (ref));
      }

  BITMAP_FREE (conv);
}

/* Convert operand OP in INSN.  We should handle
   memory operands and uninitialized registers.
   All other register uses are converted during
   registers conversion.  */

void
dimode_scalar_chain::convert_op (rtx *op, rtx_insn *insn)
{
  *op = copy_rtx_if_shared (*op);

  if (GET_CODE (*op) == NOT)
    {
      convert_op (&XEXP (*op, 0), insn);
      PUT_MODE (*op, V2DImode);
    }
  else if (MEM_P (*op))
    {
      rtx tmp = gen_reg_rtx (DImode);

      emit_insn_before (gen_move_insn (tmp, *op), insn);
      *op = gen_rtx_SUBREG (V2DImode, tmp, 0);

      if (dump_file)
	fprintf (dump_file, "  Preloading operand for insn %d into r%d\n",
		 INSN_UID (insn), REGNO (tmp));
    }
  else if (REG_P (*op))
    {
      /* We may have not converted register usage in case
	 this register has no definition.  Otherwise it
	 should be converted in convert_reg.  */
      df_ref ref;
      FOR_EACH_INSN_USE (ref, insn)
	if (DF_REF_REGNO (ref) == REGNO (*op))
	  {
	    gcc_assert (!DF_REF_CHAIN (ref));
	    break;
	  }
      *op = gen_rtx_SUBREG (V2DImode, *op, 0);
    }
  else if (CONST_INT_P (*op))
    {
      rtx vec_cst;
      rtx tmp = gen_rtx_SUBREG (V2DImode, gen_reg_rtx (DImode), 0);

      /* Prefer all ones vector in case of -1.  */
      if (constm1_operand (*op, GET_MODE (*op)))
	vec_cst = CONSTM1_RTX (V2DImode);
      else
	vec_cst = gen_rtx_CONST_VECTOR (V2DImode,
					gen_rtvec (2, *op, const0_rtx));

      if (!standard_sse_constant_p (vec_cst, V2DImode))
	{
	  start_sequence ();
	  vec_cst = validize_mem (force_const_mem (V2DImode, vec_cst));
	  rtx_insn *seq = get_insns ();
	  end_sequence ();
	  emit_insn_before (seq, insn);
	}

      emit_insn_before (gen_move_insn (copy_rtx (tmp), vec_cst), insn);
      *op = tmp;
    }
  else
    {
      gcc_assert (SUBREG_P (*op));
      gcc_assert (GET_MODE (*op) == V2DImode);
    }
}

/* Convert INSN to vector mode.  */

void
dimode_scalar_chain::convert_insn (rtx_insn *insn)
{
  rtx def_set = single_set (insn);
  rtx src = SET_SRC (def_set);
  rtx dst = SET_DEST (def_set);
  rtx subreg;

  if (MEM_P (dst) && !REG_P (src))
    {
      /* There are no scalar integer instructions and therefore
	 temporary register usage is required.  */
      rtx tmp = gen_reg_rtx (DImode);
      emit_conversion_insns (gen_move_insn (dst, tmp), insn);
      dst = gen_rtx_SUBREG (V2DImode, tmp, 0);
    }

  switch (GET_CODE (src))
    {
    case ASHIFT:
    case ASHIFTRT:
    case LSHIFTRT:
      convert_op (&XEXP (src, 0), insn);
      PUT_MODE (src, V2DImode);
      break;

    case PLUS:
    case MINUS:
    case IOR:
    case XOR:
    case AND:
      convert_op (&XEXP (src, 0), insn);
      convert_op (&XEXP (src, 1), insn);
      PUT_MODE (src, V2DImode);
      break;

    case NEG:
      src = XEXP (src, 0);
      convert_op (&src, insn);
      subreg = gen_reg_rtx (V2DImode);
      emit_insn_before (gen_move_insn (subreg, CONST0_RTX (V2DImode)), insn);
      src = gen_rtx_MINUS (V2DImode, subreg, src);
      break;

    case NOT:
      src = XEXP (src, 0);
      convert_op (&src, insn);
      subreg = gen_reg_rtx (V2DImode);
      emit_insn_before (gen_move_insn (subreg, CONSTM1_RTX (V2DImode)), insn);
      src = gen_rtx_XOR (V2DImode, src, subreg);
      break;

    case MEM:
      if (!REG_P (dst))
	convert_op (&src, insn);
      break;

    case REG:
      if (!MEM_P (dst))
	convert_op (&src, insn);
      break;

    case SUBREG:
      gcc_assert (GET_MODE (src) == V2DImode);
      break;

    case COMPARE:
      src = SUBREG_REG (XEXP (XEXP (src, 0), 0));

      gcc_assert ((REG_P (src) && GET_MODE (src) == DImode)
		  || (SUBREG_P (src) && GET_MODE (src) == V2DImode));

      if (REG_P (src))
	subreg = gen_rtx_SUBREG (V2DImode, src, 0);
      else
	subreg = copy_rtx_if_shared (src);
      emit_insn_before (gen_vec_interleave_lowv2di (copy_rtx_if_shared (subreg),
						    copy_rtx_if_shared (subreg),
						    copy_rtx_if_shared (subreg)),
			insn);
      dst = gen_rtx_REG (CCmode, FLAGS_REG);
      src = gen_rtx_UNSPEC (CCmode, gen_rtvec (2, copy_rtx_if_shared (src),
					       copy_rtx_if_shared (src)),
			    UNSPEC_PTEST);
      break;

    case CONST_INT:
      convert_op (&src, insn);
      break;

    default:
      gcc_unreachable ();
    }

  SET_SRC (def_set) = src;
  SET_DEST (def_set) = dst;

  /* Drop possible dead definitions.  */
  PATTERN (insn) = def_set;

  INSN_CODE (insn) = -1;
  recog_memoized (insn);
  df_insn_rescan (insn);
}

/* Fix uses of converted REG in debug insns.  */

void
timode_scalar_chain::fix_debug_reg_uses (rtx reg)
{
  if (!flag_var_tracking)
    return;

  df_ref ref, next;
  for (ref = DF_REG_USE_CHAIN (REGNO (reg)); ref; ref = next)
    {
      rtx_insn *insn = DF_REF_INSN (ref);
      /* Make sure the next ref is for a different instruction,
         so that we're not affected by the rescan.  */
      next = DF_REF_NEXT_REG (ref);
      while (next && DF_REF_INSN (next) == insn)
	next = DF_REF_NEXT_REG (next);

      if (DEBUG_INSN_P (insn))
	{
	  /* It may be a debug insn with a TImode variable in
	     register.  */
	  bool changed = false;
	  for (; ref != next; ref = DF_REF_NEXT_REG (ref))
	    {
	      rtx *loc = DF_REF_LOC (ref);
	      if (REG_P (*loc) && GET_MODE (*loc) == V1TImode)
		{
		  *loc = gen_rtx_SUBREG (TImode, *loc, 0);
		  changed = true;
		}
	    }
	  if (changed)
	    df_insn_rescan (insn);
	}
    }
}

/* Convert INSN from TImode to V1T1mode.  */

void
timode_scalar_chain::convert_insn (rtx_insn *insn)
{
  rtx def_set = single_set (insn);
  rtx src = SET_SRC (def_set);
  rtx dst = SET_DEST (def_set);

  switch (GET_CODE (dst))
    {
    case REG:
      {
	rtx tmp = find_reg_equal_equiv_note (insn);
	if (tmp)
	  PUT_MODE (XEXP (tmp, 0), V1TImode);
	PUT_MODE (dst, V1TImode);
	fix_debug_reg_uses (dst);
      }
      break;
    case MEM:
      PUT_MODE (dst, V1TImode);
      break;

    default:
      gcc_unreachable ();
    }

  switch (GET_CODE (src))
    {
    case REG:
      PUT_MODE (src, V1TImode);
      /* Call fix_debug_reg_uses only if SRC is never defined.  */
      if (!DF_REG_DEF_CHAIN (REGNO (src)))
	fix_debug_reg_uses (src);
      break;

    case MEM:
      PUT_MODE (src, V1TImode);
      break;

    case CONST_WIDE_INT:
      if (NONDEBUG_INSN_P (insn))
	{
	  /* Since there are no instructions to store 128-bit constant,
	     temporary register usage is required.  */
	  rtx tmp = gen_reg_rtx (V1TImode);
	  start_sequence ();
	  src = gen_rtx_CONST_VECTOR (V1TImode, gen_rtvec (1, src));
	  src = validize_mem (force_const_mem (V1TImode, src));
	  rtx_insn *seq = get_insns ();
	  end_sequence ();
	  if (seq)
	    emit_insn_before (seq, insn);
	  emit_conversion_insns (gen_rtx_SET (dst, tmp), insn);
	  dst = tmp;
	}
      break;

    case CONST_INT:
      switch (standard_sse_constant_p (src, TImode))
	{
	case 1:
	  src = CONST0_RTX (GET_MODE (dst));
	  break;
	case 2:
	  src = CONSTM1_RTX (GET_MODE (dst));
	  break;
	default:
	  gcc_unreachable ();
	}
      if (NONDEBUG_INSN_P (insn))
	{
	  rtx tmp = gen_reg_rtx (V1TImode);
	  /* Since there are no instructions to store standard SSE
	     constant, temporary register usage is required.  */
	  emit_conversion_insns (gen_rtx_SET (dst, tmp), insn);
	  dst = tmp;
	}
      break;

    default:
      gcc_unreachable ();
    }

  SET_SRC (def_set) = src;
  SET_DEST (def_set) = dst;

  /* Drop possible dead definitions.  */
  PATTERN (insn) = def_set;

  INSN_CODE (insn) = -1;
  recog_memoized (insn);
  df_insn_rescan (insn);
}

void
dimode_scalar_chain::convert_registers ()
{
  bitmap_iterator bi;
  unsigned id;

  EXECUTE_IF_SET_IN_BITMAP (defs, 0, id, bi)
    convert_reg (id);

  EXECUTE_IF_AND_COMPL_IN_BITMAP (defs_conv, defs, 0, id, bi)
    make_vector_copies (id);
}

/* Convert whole chain creating required register
   conversions and copies.  */

int
scalar_chain::convert ()
{
  bitmap_iterator bi;
  unsigned id;
  int converted_insns = 0;

  if (!dbg_cnt (stv_conversion))
    return 0;

  if (dump_file)
    fprintf (dump_file, "Converting chain #%d...\n", chain_id);

  convert_registers ();

  EXECUTE_IF_SET_IN_BITMAP (insns, 0, id, bi)
    {
      convert_insn (DF_INSN_UID_GET (id)->insn);
      converted_insns++;
    }

  return converted_insns;
}

/* Main STV pass function.  Find and convert scalar
   instructions into vector mode when profitable.  */

static unsigned int
convert_scalars_to_vector ()
{
  basic_block bb;
  bitmap candidates;
  int converted_insns = 0;

  bitmap_obstack_initialize (NULL);
  candidates = BITMAP_ALLOC (NULL);

  calculate_dominance_info (CDI_DOMINATORS);
  df_set_flags (DF_DEFER_INSN_RESCAN);
  df_chain_add_problem (DF_DU_CHAIN | DF_UD_CHAIN);
  df_md_add_problem ();
  df_analyze ();

  /* Find all instructions we want to convert into vector mode.  */
  if (dump_file)
    fprintf (dump_file, "Searching for mode conversion candidates...\n");

  FOR_EACH_BB_FN (bb, cfun)
    {
      rtx_insn *insn;
      FOR_BB_INSNS (bb, insn)
	if (scalar_to_vector_candidate_p (insn))
	  {
	    if (dump_file)
	      fprintf (dump_file, "  insn %d is marked as a candidate\n",
		       INSN_UID (insn));

	    bitmap_set_bit (candidates, INSN_UID (insn));
	  }
    }

  remove_non_convertible_regs (candidates);

  if (bitmap_empty_p (candidates))
    if (dump_file)
      fprintf (dump_file, "There are no candidates for optimization.\n");

  while (!bitmap_empty_p (candidates))
    {
      unsigned uid = bitmap_first_set_bit (candidates);
      scalar_chain *chain;

      if (TARGET_64BIT)
	chain = new timode_scalar_chain;
      else
	chain = new dimode_scalar_chain;

      /* Find instructions chain we want to convert to vector mode.
	 Check all uses and definitions to estimate all required
	 conversions.  */
      chain->build (candidates, uid);

      if (chain->compute_convert_gain () > 0)
	converted_insns += chain->convert ();
      else
	if (dump_file)
	  fprintf (dump_file, "Chain #%d conversion is not profitable\n",
		   chain->chain_id);

      delete chain;
    }

  if (dump_file)
    fprintf (dump_file, "Total insns converted: %d\n", converted_insns);

  BITMAP_FREE (candidates);
  bitmap_obstack_release (NULL);
  df_process_deferred_rescans ();

  /* Conversion means we may have 128bit register spills/fills
     which require aligned stack.  */
  if (converted_insns)
    {
      if (crtl->stack_alignment_needed < 128)
	crtl->stack_alignment_needed = 128;
      if (crtl->stack_alignment_estimated < 128)
	crtl->stack_alignment_estimated = 128;
      /* Fix up DECL_RTL/DECL_INCOMING_RTL of arguments.  */
      if (TARGET_64BIT)
	for (tree parm = DECL_ARGUMENTS (current_function_decl);
	     parm; parm = DECL_CHAIN (parm))
	  {
	    if (TYPE_MODE (TREE_TYPE (parm)) != TImode)
	      continue;
	    if (DECL_RTL_SET_P (parm)
		&& GET_MODE (DECL_RTL (parm)) == V1TImode)
	      {
		rtx r = DECL_RTL (parm);
		if (REG_P (r))
		  SET_DECL_RTL (parm, gen_rtx_SUBREG (TImode, r, 0));
	      }
	    if (DECL_INCOMING_RTL (parm)
		&& GET_MODE (DECL_INCOMING_RTL (parm)) == V1TImode)
	      {
		rtx r = DECL_INCOMING_RTL (parm);
		if (REG_P (r))
		  DECL_INCOMING_RTL (parm) = gen_rtx_SUBREG (TImode, r, 0);
	      }
	  }
    }

  return 0;
}

namespace {

const pass_data pass_data_insert_vzeroupper =
{
  RTL_PASS, /* type */
  "vzeroupper", /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_MACH_DEP, /* tv_id */
  0, /* properties_required */
  0, /* properties_provided */
  0, /* properties_destroyed */
  0, /* todo_flags_start */
  TODO_df_finish, /* todo_flags_finish */
};

class pass_insert_vzeroupper : public rtl_opt_pass
{
public:
  pass_insert_vzeroupper(gcc::context *ctxt)
    : rtl_opt_pass(pass_data_insert_vzeroupper, ctxt)
  {}

  /* opt_pass methods: */
  virtual bool gate (function *)
    {
      return TARGET_AVX
	     && TARGET_VZEROUPPER && flag_expensive_optimizations
	     && !optimize_size;
    }

  virtual unsigned int execute (function *)
    {
      return rest_of_handle_insert_vzeroupper ();
    }

}; // class pass_insert_vzeroupper

const pass_data pass_data_stv =
{
  RTL_PASS, /* type */
  "stv", /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_MACH_DEP, /* tv_id */
  0, /* properties_required */
  0, /* properties_provided */
  0, /* properties_destroyed */
  0, /* todo_flags_start */
  TODO_df_finish, /* todo_flags_finish */
};

class pass_stv : public rtl_opt_pass
{
public:
  pass_stv (gcc::context *ctxt)
    : rtl_opt_pass (pass_data_stv, ctxt),
      timode_p (false)
  {}

  /* opt_pass methods: */
  virtual bool gate (function *)
    {
      return (timode_p == !!TARGET_64BIT
	      && TARGET_STV && TARGET_SSE2 && optimize > 1);
    }

  virtual unsigned int execute (function *)
    {
      return convert_scalars_to_vector ();
    }

  opt_pass *clone ()
    {
      return new pass_stv (m_ctxt);
    }

  void set_pass_param (unsigned int n, bool param)
    {
      gcc_assert (n == 0);
      timode_p = param;
    }

private:
  bool timode_p;
}; // class pass_stv

} // anon namespace

rtl_opt_pass *
make_pass_insert_vzeroupper (gcc::context *ctxt)
{
  return new pass_insert_vzeroupper (ctxt);
}

rtl_opt_pass *
make_pass_stv (gcc::context *ctxt)
{
  return new pass_stv (ctxt);
}

/* Inserting ENDBRANCH instructions.  */

static unsigned int
rest_of_insert_endbranch (void)
{
  timevar_push (TV_MACH_DEP);

  rtx cet_eb;
  rtx_insn *insn;
  basic_block bb;

  /* Currently emit EB if it's a tracking function, i.e. 'nocf_check' is
     absent among function attributes.  Later an optimization will be
     introduced to make analysis if an address of a static function is
     taken.  A static function whose address is not taken will get a
     nocf_check attribute.  This will allow to reduce the number of EB.  */

  if (!lookup_attribute ("nocf_check",
			 TYPE_ATTRIBUTES (TREE_TYPE (cfun->decl)))
      && (!flag_manual_endbr
	  || lookup_attribute ("cf_check",
			       DECL_ATTRIBUTES (cfun->decl)))
      && !cgraph_node::get (cfun->decl)->only_called_directly_p ())
    {
      /* Queue ENDBR insertion to x86_function_profiler.  */
      if (crtl->profile && flag_fentry)
	cfun->machine->endbr_queued_at_entrance = true;
      else
	{
	  cet_eb = gen_nop_endbr ();

	  bb = ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb;
	  insn = BB_HEAD (bb);
	  emit_insn_before (cet_eb, insn);
	}
    }

  bb = 0;
  FOR_EACH_BB_FN (bb, cfun)
    {
      for (insn = BB_HEAD (bb); insn != NEXT_INSN (BB_END (bb));
	   insn = NEXT_INSN (insn))
	{
	  if (CALL_P (insn))
	    {
	      bool need_endbr;
	      need_endbr = find_reg_note (insn, REG_SETJMP, NULL) != NULL;
	      if (!need_endbr && !SIBLING_CALL_P (insn))
		{
		  rtx call = get_call_rtx_from (insn);
		  rtx fnaddr = XEXP (call, 0);
		  tree fndecl = NULL_TREE;

		  /* Also generate ENDBRANCH for non-tail call which
		     may return via indirect branch.  */
		  if (GET_CODE (XEXP (fnaddr, 0)) == SYMBOL_REF)
		    fndecl = SYMBOL_REF_DECL (XEXP (fnaddr, 0));
		  if (fndecl == NULL_TREE)
		    fndecl = MEM_EXPR (fnaddr);
		  if (fndecl
		      && TREE_CODE (TREE_TYPE (fndecl)) != FUNCTION_TYPE
		      && TREE_CODE (TREE_TYPE (fndecl)) != METHOD_TYPE)
		    fndecl = NULL_TREE;
		  if (fndecl && TYPE_ARG_TYPES (TREE_TYPE (fndecl)))
		    {
		      tree fntype = TREE_TYPE (fndecl);
		      if (lookup_attribute ("indirect_return",
					    TYPE_ATTRIBUTES (fntype)))
			need_endbr = true;
		    }
		}
	      if (!need_endbr)
		continue;
	      /* Generate ENDBRANCH after CALL, which can return more than
		 twice, setjmp-like functions.  */

	      cet_eb = gen_nop_endbr ();
	      emit_insn_after_setloc (cet_eb, insn, INSN_LOCATION (insn));
	      continue;
	    }

	  if (JUMP_P (insn) && flag_cet_switch)
	    {
	      rtx target = JUMP_LABEL (insn);
	      if (target == NULL_RTX || ANY_RETURN_P (target))
		continue;

	      /* Check the jump is a switch table.  */
	      rtx_insn *label = as_a<rtx_insn *> (target);
	      rtx_insn *table = next_insn (label);
	      if (table == NULL_RTX || !JUMP_TABLE_DATA_P (table))
		continue;

	      /* For the indirect jump find out all places it jumps and insert
		 ENDBRANCH there.  It should be done under a special flag to
		 control ENDBRANCH generation for switch stmts.  */
	      edge_iterator ei;
	      edge e;
	      basic_block dest_blk;

	      FOR_EACH_EDGE (e, ei, bb->succs)
		{
		  rtx_insn *insn;

		  dest_blk = e->dest;
		  insn = BB_HEAD (dest_blk);
		  gcc_assert (LABEL_P (insn));
		  cet_eb = gen_nop_endbr ();
		  emit_insn_after (cet_eb, insn);
		}
	      continue;
	    }

	  if ((LABEL_P (insn) && LABEL_PRESERVE_P (insn))
	      || (NOTE_P (insn)
		  && NOTE_KIND (insn) == NOTE_INSN_DELETED_LABEL))
	    /* TODO.  Check /s bit also.  */
	    {
	      cet_eb = gen_nop_endbr ();
	      emit_insn_after (cet_eb, insn);
	      continue;
	    }
	}
    }

  timevar_pop (TV_MACH_DEP);
  return 0;
}

namespace {

const pass_data pass_data_insert_endbranch =
{
  RTL_PASS, /* type.  */
  "cet", /* name.  */
  OPTGROUP_NONE, /* optinfo_flags.  */
  TV_MACH_DEP, /* tv_id.  */
  0, /* properties_required.  */
  0, /* properties_provided.  */
  0, /* properties_destroyed.  */
  0, /* todo_flags_start.  */
  0, /* todo_flags_finish.  */
};

class pass_insert_endbranch : public rtl_opt_pass
{
public:
  pass_insert_endbranch (gcc::context *ctxt)
    : rtl_opt_pass (pass_data_insert_endbranch, ctxt)
  {}

  /* opt_pass methods: */
  virtual bool gate (function *)
    {
      return ((flag_cf_protection & CF_BRANCH));
    }

  virtual unsigned int execute (function *)
    {
      return rest_of_insert_endbranch ();
    }

}; // class pass_insert_endbranch

} // anon namespace

rtl_opt_pass *
make_pass_insert_endbranch (gcc::context *ctxt)
{
  return new pass_insert_endbranch (ctxt);
}

/* Return true if a red-zone is in use.  We can't use red-zone when
   there are local indirect jumps, like "indirect_jump" or "tablejump",
   which jumps to another place in the function, since "call" in the
   indirect thunk pushes the return address onto stack, destroying
   red-zone.

   TODO: If we can reserve the first 2 WORDs, for PUSH and, another
   for CALL, in red-zone, we can allow local indirect jumps with
   indirect thunk.  */

bool
ix86_using_red_zone (void)
{
  return (TARGET_RED_ZONE
	  && !TARGET_64BIT_MS_ABI
	  && (!cfun->machine->has_local_indirect_jump
	      || cfun->machine->indirect_branch_type == indirect_branch_keep));
}

/* Return a string that documents the current -m options.  The caller is
   responsible for freeing the string.  */

static char *
ix86_target_string (HOST_WIDE_INT isa, HOST_WIDE_INT isa2,
		    int flags, int flags2,
		    const char *arch, const char *tune,
		    enum fpmath_unit fpmath, bool add_nl_p)
{
  struct ix86_target_opts
  {
    const char *option;		/* option string */
    HOST_WIDE_INT mask;		/* isa mask options */
  };

  /* This table is ordered so that options like -msse4.2 that imply other
     ISAs come first.  Target string will be displayed in the same order.  */
  static struct ix86_target_opts isa2_opts[] =
  {
    { "-mcx16",		OPTION_MASK_ISA_CX16 },
    { "-mvaes",		OPTION_MASK_ISA_VAES },
    { "-mrdpid",	OPTION_MASK_ISA_RDPID },
    { "-mpconfig",	OPTION_MASK_ISA_PCONFIG },
    { "-mwbnoinvd",     OPTION_MASK_ISA_WBNOINVD },
    { "-msgx",		OPTION_MASK_ISA_SGX },
    { "-mavx5124vnniw", OPTION_MASK_ISA_AVX5124VNNIW },
    { "-mavx5124fmaps", OPTION_MASK_ISA_AVX5124FMAPS },
    { "-mhle",		OPTION_MASK_ISA_HLE },
    { "-mmovbe",	OPTION_MASK_ISA_MOVBE },
    { "-mclzero",	OPTION_MASK_ISA_CLZERO },
    { "-mmwaitx",	OPTION_MASK_ISA_MWAITX },
    { "-mmovdir64b",	OPTION_MASK_ISA_MOVDIR64B },
    { "-mwaitpkg",	OPTION_MASK_ISA_WAITPKG },
    { "-mcldemote",	OPTION_MASK_ISA_CLDEMOTE },
    { "-mptwrite",	OPTION_MASK_ISA_PTWRITE }
  };
  static struct ix86_target_opts isa_opts[] =
  {
    { "-mavx512vpopcntdq", OPTION_MASK_ISA_AVX512VPOPCNTDQ },
    { "-mavx512bitalg", OPTION_MASK_ISA_AVX512BITALG },
    { "-mvpclmulqdq",	OPTION_MASK_ISA_VPCLMULQDQ },
    { "-mgfni",		OPTION_MASK_ISA_GFNI },
    { "-mavx512vnni",	OPTION_MASK_ISA_AVX512VNNI },
    { "-mavx512vbmi2",	OPTION_MASK_ISA_AVX512VBMI2 },
    { "-mavx512vbmi",	OPTION_MASK_ISA_AVX512VBMI },
    { "-mavx512ifma",	OPTION_MASK_ISA_AVX512IFMA },
    { "-mavx512vl",	OPTION_MASK_ISA_AVX512VL },
    { "-mavx512bw",	OPTION_MASK_ISA_AVX512BW },
    { "-mavx512dq",	OPTION_MASK_ISA_AVX512DQ },
    { "-mavx512er",	OPTION_MASK_ISA_AVX512ER },
    { "-mavx512pf",	OPTION_MASK_ISA_AVX512PF },
    { "-mavx512cd",	OPTION_MASK_ISA_AVX512CD },
    { "-mavx512f",	OPTION_MASK_ISA_AVX512F },
    { "-mavx2",		OPTION_MASK_ISA_AVX2 },
    { "-mfma",		OPTION_MASK_ISA_FMA },
    { "-mxop",		OPTION_MASK_ISA_XOP },
    { "-mfma4",		OPTION_MASK_ISA_FMA4 },
    { "-mf16c",		OPTION_MASK_ISA_F16C },
    { "-mavx",		OPTION_MASK_ISA_AVX },
/*  { "-msse4"		OPTION_MASK_ISA_SSE4 }, */
    { "-msse4.2",	OPTION_MASK_ISA_SSE4_2 },
    { "-msse4.1",	OPTION_MASK_ISA_SSE4_1 },
    { "-msse4a",	OPTION_MASK_ISA_SSE4A },
    { "-mssse3",	OPTION_MASK_ISA_SSSE3 },
    { "-msse3",		OPTION_MASK_ISA_SSE3 },
    { "-maes",		OPTION_MASK_ISA_AES },
    { "-msha",		OPTION_MASK_ISA_SHA },
    { "-mpclmul",	OPTION_MASK_ISA_PCLMUL },
    { "-msse2",		OPTION_MASK_ISA_SSE2 },
    { "-msse",		OPTION_MASK_ISA_SSE },
    { "-m3dnowa",	OPTION_MASK_ISA_3DNOW_A },
    { "-m3dnow",	OPTION_MASK_ISA_3DNOW },
    { "-mmmx",		OPTION_MASK_ISA_MMX },
    { "-mrtm",		OPTION_MASK_ISA_RTM },
    { "-mprfchw",	OPTION_MASK_ISA_PRFCHW },
    { "-mrdseed",	OPTION_MASK_ISA_RDSEED },
    { "-madx",		OPTION_MASK_ISA_ADX },
    { "-mprefetchwt1",	OPTION_MASK_ISA_PREFETCHWT1 },
    { "-mclflushopt",	OPTION_MASK_ISA_CLFLUSHOPT },
    { "-mxsaves",	OPTION_MASK_ISA_XSAVES },
    { "-mxsavec",	OPTION_MASK_ISA_XSAVEC },
    { "-mxsaveopt",	OPTION_MASK_ISA_XSAVEOPT },
    { "-mxsave",	OPTION_MASK_ISA_XSAVE },
    { "-mabm",		OPTION_MASK_ISA_ABM },
    { "-mbmi",		OPTION_MASK_ISA_BMI },
    { "-mbmi2",		OPTION_MASK_ISA_BMI2 },
    { "-mlzcnt",	OPTION_MASK_ISA_LZCNT },
    { "-mtbm",		OPTION_MASK_ISA_TBM },
    { "-mpopcnt",	OPTION_MASK_ISA_POPCNT },
    { "-msahf",		OPTION_MASK_ISA_SAHF },
    { "-mcrc32",	OPTION_MASK_ISA_CRC32 },
    { "-mfsgsbase",	OPTION_MASK_ISA_FSGSBASE },
    { "-mrdrnd",	OPTION_MASK_ISA_RDRND },
    { "-mpku",		OPTION_MASK_ISA_PKU },
    { "-mlwp",		OPTION_MASK_ISA_LWP },
    { "-mfxsr",		OPTION_MASK_ISA_FXSR },
    { "-mclwb",		OPTION_MASK_ISA_CLWB },
    { "-mshstk",	OPTION_MASK_ISA_SHSTK },
    { "-mmovdiri",	OPTION_MASK_ISA_MOVDIRI }
  };

  /* Flag options.  */
  static struct ix86_target_opts flag_opts[] =
  {
    { "-m128bit-long-double",		MASK_128BIT_LONG_DOUBLE },
    { "-mlong-double-128",		MASK_LONG_DOUBLE_128 },
    { "-mlong-double-64",		MASK_LONG_DOUBLE_64 },
    { "-m80387",			MASK_80387 },
    { "-maccumulate-outgoing-args",	MASK_ACCUMULATE_OUTGOING_ARGS },
    { "-malign-double",			MASK_ALIGN_DOUBLE },
    { "-mcld",				MASK_CLD },
    { "-mfp-ret-in-387",		MASK_FLOAT_RETURNS },
    { "-mieee-fp",			MASK_IEEE_FP },
    { "-minline-all-stringops",		MASK_INLINE_ALL_STRINGOPS },
    { "-minline-stringops-dynamically",	MASK_INLINE_STRINGOPS_DYNAMICALLY },
    { "-mms-bitfields",			MASK_MS_BITFIELD_LAYOUT },
    { "-mno-align-stringops",		MASK_NO_ALIGN_STRINGOPS },
    { "-mno-fancy-math-387",		MASK_NO_FANCY_MATH_387 },
    { "-mno-push-args",			MASK_NO_PUSH_ARGS },
    { "-mno-red-zone",			MASK_NO_RED_ZONE },
    { "-momit-leaf-frame-pointer",	MASK_OMIT_LEAF_FRAME_POINTER },
    { "-mrecip",			MASK_RECIP },
    { "-mrtd",				MASK_RTD },
    { "-msseregparm",			MASK_SSEREGPARM },
    { "-mstack-arg-probe",		MASK_STACK_PROBE },
    { "-mtls-direct-seg-refs",		MASK_TLS_DIRECT_SEG_REFS },
    { "-mvect8-ret-in-mem",		MASK_VECT8_RETURNS },
    { "-m8bit-idiv",			MASK_USE_8BIT_IDIV },
    { "-mvzeroupper",			MASK_VZEROUPPER },
    { "-mstv",				MASK_STV },
    { "-mavx256-split-unaligned-load",	MASK_AVX256_SPLIT_UNALIGNED_LOAD },
    { "-mavx256-split-unaligned-store",	MASK_AVX256_SPLIT_UNALIGNED_STORE },
    { "-mcall-ms2sysv-xlogues",		MASK_CALL_MS2SYSV_XLOGUES }
  };

  /* Additional flag options.  */
  static struct ix86_target_opts flag2_opts[] =
  {
    { "-mgeneral-regs-only",		OPTION_MASK_GENERAL_REGS_ONLY }
  };

  const char *opts[ARRAY_SIZE (isa_opts) + ARRAY_SIZE (isa2_opts)
		   + ARRAY_SIZE (flag_opts) + ARRAY_SIZE (flag2_opts) + 6][2];

  char isa_other[40];
  char isa2_other[40];
  char flags_other[40];
  char flags2_other[40];
  unsigned num = 0;
  unsigned i, j;
  char *ret;
  char *ptr;
  size_t len;
  size_t line_len;
  size_t sep_len;
  const char *abi;

  memset (opts, '\0', sizeof (opts));

  /* Add -march= option.  */
  if (arch)
    {
      opts[num][0] = "-march=";
      opts[num++][1] = arch;
    }

  /* Add -mtune= option.  */
  if (tune)
    {
      opts[num][0] = "-mtune=";
      opts[num++][1] = tune;
    }

  /* Add -m32/-m64/-mx32.  */
  if ((isa & OPTION_MASK_ISA_64BIT) != 0)
    {
      if ((isa & OPTION_MASK_ABI_64) != 0)
	abi = "-m64";
      else
	abi = "-mx32";
      isa &= ~ (OPTION_MASK_ISA_64BIT
		| OPTION_MASK_ABI_64
		| OPTION_MASK_ABI_X32);
    }
  else
    abi = "-m32";
  opts[num++][0] = abi;

  /* Pick out the options in isa2 options.  */
  for (i = 0; i < ARRAY_SIZE (isa2_opts); i++)
    {
      if ((isa2 & isa2_opts[i].mask) != 0)
	{
	  opts[num++][0] = isa2_opts[i].option;
	  isa2 &= ~ isa2_opts[i].mask;
	}
    }

  if (isa2 && add_nl_p)
    {
      opts[num++][0] = isa2_other;
      sprintf (isa2_other, "(other isa2: %#" HOST_WIDE_INT_PRINT "x)", isa2);
    }

  /* Pick out the options in isa options.  */
  for (i = 0; i < ARRAY_SIZE (isa_opts); i++)
    {
      if ((isa & isa_opts[i].mask) != 0)
	{
	  opts[num++][0] = isa_opts[i].option;
	  isa &= ~ isa_opts[i].mask;
	}
    }

  if (isa && add_nl_p)
    {
      opts[num++][0] = isa_other;
      sprintf (isa_other, "(other isa: %#" HOST_WIDE_INT_PRINT "x)", isa);
    }

  /* Add flag options.  */
  for (i = 0; i < ARRAY_SIZE (flag_opts); i++)
    {
      if ((flags & flag_opts[i].mask) != 0)
	{
	  opts[num++][0] = flag_opts[i].option;
	  flags &= ~ flag_opts[i].mask;
	}
    }

  if (flags && add_nl_p)
    {
      opts[num++][0] = flags_other;
      sprintf (flags_other, "(other flags: %#x)", flags);
    }

    /* Add additional flag options.  */
  for (i = 0; i < ARRAY_SIZE (flag2_opts); i++)
    {
      if ((flags2 & flag2_opts[i].mask) != 0)
	{
	  opts[num++][0] = flag2_opts[i].option;
	  flags2 &= ~ flag2_opts[i].mask;
	}
    }

  if (flags2 && add_nl_p)
    {
      opts[num++][0] = flags2_other;
      sprintf (flags2_other, "(other flags2: %#x)", flags2);
    }

  /* Add -fpmath= option.  */
  if (fpmath)
    {
      opts[num][0] = "-mfpmath=";
      switch ((int) fpmath)
	{
	case FPMATH_387:
	  opts[num++][1] = "387";
	  break;

	case FPMATH_SSE:
	  opts[num++][1] = "sse";
	  break;

	case FPMATH_387 | FPMATH_SSE:
	  opts[num++][1] = "sse+387";
	  break;

	default:
	  gcc_unreachable ();
	}
    }

  /* Any options?  */
  if (num == 0)
    return NULL;

  gcc_assert (num < ARRAY_SIZE (opts));

  /* Size the string.  */
  len = 0;
  sep_len = (add_nl_p) ? 3 : 1;
  for (i = 0; i < num; i++)
    {
      len += sep_len;
      for (j = 0; j < 2; j++)
	if (opts[i][j])
	  len += strlen (opts[i][j]);
    }

  /* Build the string.  */
  ret = ptr = (char *) xmalloc (len);
  line_len = 0;

  for (i = 0; i < num; i++)
    {
      size_t len2[2];

      for (j = 0; j < 2; j++)
	len2[j] = (opts[i][j]) ? strlen (opts[i][j]) : 0;

      if (i != 0)
	{
	  *ptr++ = ' ';
	  line_len++;

	  if (add_nl_p && line_len + len2[0] + len2[1] > 70)
	    {
	      *ptr++ = '\\';
	      *ptr++ = '\n';
	      line_len = 0;
	    }
	}

      for (j = 0; j < 2; j++)
	if (opts[i][j])
	  {
	    memcpy (ptr, opts[i][j], len2[j]);
	    ptr += len2[j];
	    line_len += len2[j];
	  }
    }

  *ptr = '\0';
  gcc_assert (ret + len >= ptr);

  return ret;
}

/* Return true, if profiling code should be emitted before
   prologue. Otherwise it returns false.
   Note: For x86 with "hotfix" it is sorried.  */
static bool
ix86_profile_before_prologue (void)
{
  return flag_fentry != 0;
}

/* Function that is callable from the debugger to print the current
   options.  */
void ATTRIBUTE_UNUSED
ix86_debug_options (void)
{
  char *opts = ix86_target_string (ix86_isa_flags, ix86_isa_flags2,
				   target_flags, ix86_target_flags,
				   ix86_arch_string,ix86_tune_string,
				   ix86_fpmath, true);

  if (opts)
    {
      fprintf (stderr, "%s\n\n", opts);
      free (opts);
    }
  else
    fputs ("<no options>\n\n", stderr);

  return;
}

static const char *stringop_alg_names[] = {
#define DEF_ENUM
#define DEF_ALG(alg, name) #name,
#include "stringop.def"
#undef DEF_ENUM
#undef DEF_ALG
};

/* Parse parameter string passed to -mmemcpy-strategy= or -mmemset-strategy=.
   The string is of the following form (or comma separated list of it):

     strategy_alg:max_size:[align|noalign]

   where the full size range for the strategy is either [0, max_size] or
   [min_size, max_size], in which min_size is the max_size + 1 of the
   preceding range.  The last size range must have max_size == -1.

   Examples:

    1.
       -mmemcpy-strategy=libcall:-1:noalign

      this is equivalent to (for known size memcpy) -mstringop-strategy=libcall


   2.
      -mmemset-strategy=rep_8byte:16:noalign,vector_loop:2048:align,libcall:-1:noalign

      This is to tell the compiler to use the following strategy for memset
      1) when the expected size is between [1, 16], use rep_8byte strategy;
      2) when the size is between [17, 2048], use vector_loop;
      3) when the size is > 2048, use libcall.  */

struct stringop_size_range
{
  int max;
  stringop_alg alg;
  bool noalign;
};

static void
ix86_parse_stringop_strategy_string (char *strategy_str, bool is_memset)
{
  const struct stringop_algs *default_algs;
  stringop_size_range input_ranges[MAX_STRINGOP_ALGS];
  char *curr_range_str, *next_range_str;
  const char *opt = is_memset ? "-mmemset_strategy=" : "-mmemcpy_strategy=";
  int i = 0, n = 0;

  if (is_memset)
    default_algs = &ix86_cost->memset[TARGET_64BIT != 0];
  else
    default_algs = &ix86_cost->memcpy[TARGET_64BIT != 0];

  curr_range_str = strategy_str;

  do
    {
      int maxs;
      char alg_name[128];
      char align[16];
      next_range_str = strchr (curr_range_str, ',');
      if (next_range_str)
        *next_range_str++ = '\0';

      if (sscanf (curr_range_str, "%20[^:]:%d:%10s", alg_name, &maxs,
		  align) != 3)
        {
	  error ("wrong argument %qs to option %qs", curr_range_str, opt);
          return;
        }

      if (n > 0 && (maxs < (input_ranges[n - 1].max + 1) && maxs != -1))
        {
	  error ("size ranges of option %qs should be increasing", opt);
          return;
        }

      for (i = 0; i < last_alg; i++)
	if (!strcmp (alg_name, stringop_alg_names[i]))
	  break;

      if (i == last_alg)
        {
	  error ("wrong strategy name %qs specified for option %qs",
		 alg_name, opt);

	  auto_vec <const char *> candidates;
	  for (i = 0; i < last_alg; i++)
	    if ((stringop_alg) i != rep_prefix_8_byte || TARGET_64BIT)
	      candidates.safe_push (stringop_alg_names[i]);

	  char *s;
	  const char *hint
	    = candidates_list_and_hint (alg_name, s, candidates);
	  if (hint)
	    inform (input_location,
		    "valid arguments to %qs are: %s; did you mean %qs?",
		    opt, s, hint);
	  else
	    inform (input_location, "valid arguments to %qs are: %s",
		    opt, s);
	  XDELETEVEC (s);
          return;
        }

      if ((stringop_alg) i == rep_prefix_8_byte
	  && !TARGET_64BIT)
	{
	  /* rep; movq isn't available in 32-bit code.  */
	  error ("strategy name %qs specified for option %qs "
		 "not supported for 32-bit code", alg_name, opt);
	  return;
	}

      input_ranges[n].max = maxs;
      input_ranges[n].alg = (stringop_alg) i;
      if (!strcmp (align, "align"))
        input_ranges[n].noalign = false;
      else if (!strcmp (align, "noalign"))
        input_ranges[n].noalign = true;
      else
        {
	  error ("unknown alignment %qs specified for option %qs", align, opt);
          return;
        }
      n++;
      curr_range_str = next_range_str;
    }
  while (curr_range_str);

  if (input_ranges[n - 1].max != -1)
    {
      error ("the max value for the last size range should be -1"
             " for option %qs", opt);
      return;
    }

  if (n > MAX_STRINGOP_ALGS)
    {
      error ("too many size ranges specified in option %qs", opt);
      return;
    }

  /* Now override the default algs array.  */
  for (i = 0; i < n; i++)
    {
      *const_cast<int *>(&default_algs->size[i].max) = input_ranges[i].max;
      *const_cast<stringop_alg *>(&default_algs->size[i].alg)
          = input_ranges[i].alg;
      *const_cast<int *>(&default_algs->size[i].noalign)
          = input_ranges[i].noalign;
    }
}


/* 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 HOST_WIDE_INT ix86_tune_mask = HOST_WIDE_INT_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);
}


/* Default align_* from the processor table.  */

static void
ix86_default_align (struct gcc_options *opts)
{
  /* -falign-foo without argument: supply one.  */
  if (opts->x_flag_align_loops && !opts->x_str_align_loops)
    opts->x_str_align_loops = processor_cost_table[ix86_tune]->align_loop;
  if (opts->x_flag_align_jumps && !opts->x_str_align_jumps)
    opts->x_str_align_jumps = processor_cost_table[ix86_tune]->align_jump;
  if (opts->x_flag_align_labels && !opts->x_str_align_labels)
    opts->x_str_align_labels = processor_cost_table[ix86_tune]->align_label;
  if (opts->x_flag_align_functions && !opts->x_str_align_functions)
    opts->x_str_align_functions = processor_cost_table[ix86_tune]->align_func;
}

/* Implement TARGET_OVERRIDE_OPTIONS_AFTER_CHANGE hook.  */

static void
ix86_override_options_after_change (void)
{
  ix86_default_align (&global_options);
}



/* Override various settings based on options.  If MAIN_ARGS_P, the
   options are from the command line, otherwise they are from
   attributes.  Return true if there's an error related to march
   option.  */

static bool
ix86_option_override_internal (bool main_args_p,
			       struct gcc_options *opts,
			       struct gcc_options *opts_set)
{
  int i;
  unsigned HOST_WIDE_INT ix86_arch_mask;
  const bool ix86_tune_specified = (opts->x_ix86_tune_string != NULL);

  /* -mrecip options.  */
  static struct
    {
      const char *string;           /* option name */
      unsigned int mask;            /* mask bits to set */
    }
  const recip_options[] =
    {
      { "all",       RECIP_MASK_ALL },
      { "none",      RECIP_MASK_NONE },
      { "div",       RECIP_MASK_DIV },
      { "sqrt",      RECIP_MASK_SQRT },
      { "vec-div",   RECIP_MASK_VEC_DIV },
      { "vec-sqrt",  RECIP_MASK_VEC_SQRT },
    };


  /* Turn off both OPTION_MASK_ABI_64 and OPTION_MASK_ABI_X32 if
     TARGET_64BIT_DEFAULT is true and TARGET_64BIT is false.  */
  if (TARGET_64BIT_DEFAULT && !TARGET_64BIT_P (opts->x_ix86_isa_flags))
    opts->x_ix86_isa_flags &= ~(OPTION_MASK_ABI_64 | OPTION_MASK_ABI_X32);
#ifdef TARGET_BI_ARCH
  else
    {
#if TARGET_BI_ARCH == 1
      /* When TARGET_BI_ARCH == 1, by default, OPTION_MASK_ABI_64
	 is on and OPTION_MASK_ABI_X32 is off.  We turn off
	 OPTION_MASK_ABI_64 if OPTION_MASK_ABI_X32 is turned on by
	 -mx32.  */
      if (TARGET_X32_P (opts->x_ix86_isa_flags))
	opts->x_ix86_isa_flags &= ~OPTION_MASK_ABI_64;
#else
      /* When TARGET_BI_ARCH == 2, by default, OPTION_MASK_ABI_X32 is
	 on and OPTION_MASK_ABI_64 is off.  We turn off
	 OPTION_MASK_ABI_X32 if OPTION_MASK_ABI_64 is turned on by
	 -m64 or OPTION_MASK_CODE16 is turned on by -m16.  */
      if (TARGET_LP64_P (opts->x_ix86_isa_flags)
	  || TARGET_16BIT_P (opts->x_ix86_isa_flags))
	opts->x_ix86_isa_flags &= ~OPTION_MASK_ABI_X32;
#endif
      if (TARGET_64BIT_P (opts->x_ix86_isa_flags)
	  && TARGET_IAMCU_P (opts->x_target_flags))
	sorry ("Intel MCU psABI isn%'t supported in %s mode",
	       TARGET_X32_P (opts->x_ix86_isa_flags) ? "x32" : "64-bit");
    }
#endif

  if (TARGET_X32_P (opts->x_ix86_isa_flags))
    {
      /* Always turn on OPTION_MASK_ISA_64BIT and turn off
	 OPTION_MASK_ABI_64 for TARGET_X32.  */
      opts->x_ix86_isa_flags |= OPTION_MASK_ISA_64BIT;
      opts->x_ix86_isa_flags &= ~OPTION_MASK_ABI_64;
    }
  else if (TARGET_16BIT_P (opts->x_ix86_isa_flags))
    opts->x_ix86_isa_flags &= ~(OPTION_MASK_ISA_64BIT
				| OPTION_MASK_ABI_X32
				| OPTION_MASK_ABI_64);
  else if (TARGET_LP64_P (opts->x_ix86_isa_flags))
    {
      /* Always turn on OPTION_MASK_ISA_64BIT and turn off
	 OPTION_MASK_ABI_X32 for TARGET_LP64.  */
      opts->x_ix86_isa_flags |= OPTION_MASK_ISA_64BIT;
      opts->x_ix86_isa_flags &= ~OPTION_MASK_ABI_X32;
    }

#ifdef SUBTARGET_OVERRIDE_OPTIONS
  SUBTARGET_OVERRIDE_OPTIONS;
#endif

#ifdef SUBSUBTARGET_OVERRIDE_OPTIONS
  SUBSUBTARGET_OVERRIDE_OPTIONS;
#endif

  /* -fPIC is the default for x86_64.  */
  if (TARGET_MACHO && TARGET_64BIT_P (opts->x_ix86_isa_flags))
    opts->x_flag_pic = 2;

  /* Need to check -mtune=generic first.  */
  if (opts->x_ix86_tune_string)
    {
      /* As special support for cross compilers we read -mtune=native
	     as -mtune=generic.  With native compilers we won't see the
	     -mtune=native, as it was changed by the driver.  */
      if (!strcmp (opts->x_ix86_tune_string, "native"))
	{
	  opts->x_ix86_tune_string = "generic";
	}
      else if (!strcmp (opts->x_ix86_tune_string, "x86-64"))
        warning (OPT_Wdeprecated,
		 main_args_p
		 ? G_("%<-mtune=x86-64%> is deprecated; use %<-mtune=k8%> "
		      "or %<-mtune=generic%> instead as appropriate")
		 : G_("%<target(\"tune=x86-64\")%> is deprecated; use "
		      "%<target(\"tune=k8\")%> or %<target(\"tune=generic\")%>"
		      " instead as appropriate"));
    }
  else
    {
      if (opts->x_ix86_arch_string)
	opts->x_ix86_tune_string = opts->x_ix86_arch_string;
      if (!opts->x_ix86_tune_string)
	{
	  opts->x_ix86_tune_string = processor_names[TARGET_CPU_DEFAULT];
	  ix86_tune_defaulted = 1;
	}

      /* opts->x_ix86_tune_string is set to opts->x_ix86_arch_string
	 or defaulted.  We need to use a sensible tune option.  */
      if (!strcmp (opts->x_ix86_tune_string, "x86-64"))
	{
	  opts->x_ix86_tune_string = "generic";
	}
    }

  if (opts->x_ix86_stringop_alg == rep_prefix_8_byte
      && !TARGET_64BIT_P (opts->x_ix86_isa_flags))
    {
      /* rep; movq isn't available in 32-bit code.  */
      error ("-mstringop-strategy=rep_8byte not supported for 32-bit code");
      opts->x_ix86_stringop_alg = no_stringop;
    }

  if (!opts->x_ix86_arch_string)
    opts->x_ix86_arch_string
      = TARGET_64BIT_P (opts->x_ix86_isa_flags)
	? "x86-64" : SUBTARGET32_DEFAULT_CPU;
  else
    ix86_arch_specified = 1;

  if (opts_set->x_ix86_pmode)
    {
      if ((TARGET_LP64_P (opts->x_ix86_isa_flags)
	   && opts->x_ix86_pmode == PMODE_SI)
	  || (!TARGET_64BIT_P (opts->x_ix86_isa_flags)
	       && opts->x_ix86_pmode == PMODE_DI))
	error ("address mode %qs not supported in the %s bit mode",
	       TARGET_64BIT_P (opts->x_ix86_isa_flags) ? "short" : "long",
	       TARGET_64BIT_P (opts->x_ix86_isa_flags) ? "64" : "32");
    }
  else
    opts->x_ix86_pmode = TARGET_LP64_P (opts->x_ix86_isa_flags)
			 ? PMODE_DI : PMODE_SI;

  if (!opts_set->x_ix86_abi)
    opts->x_ix86_abi = DEFAULT_ABI;

  if (opts->x_ix86_abi == MS_ABI && TARGET_X32_P (opts->x_ix86_isa_flags))
    error ("-mabi=ms not supported with X32 ABI");
  gcc_assert (opts->x_ix86_abi == SYSV_ABI || opts->x_ix86_abi == MS_ABI);

  if ((opts->x_flag_sanitize & SANITIZE_USER_ADDRESS) && opts->x_ix86_abi == MS_ABI)
    error ("%<-mabi=ms%> not supported with %<-fsanitize=address%>");
  if ((opts->x_flag_sanitize & SANITIZE_KERNEL_ADDRESS) && opts->x_ix86_abi == MS_ABI)
    error ("%<-mabi=ms%> not supported with %<-fsanitize=kernel-address%>");
  if ((opts->x_flag_sanitize & SANITIZE_THREAD) && opts->x_ix86_abi == MS_ABI)
    error ("%<-mabi=ms%> not supported with %<-fsanitize=thread%>");

  /* For targets using ms ABI enable ms-extensions, if not
     explicit turned off.  For non-ms ABI we turn off this
     option.  */
  if (!opts_set->x_flag_ms_extensions)
    opts->x_flag_ms_extensions = (MS_ABI == DEFAULT_ABI);

  if (opts_set->x_ix86_cmodel)
    {
      switch (opts->x_ix86_cmodel)
	{
	case CM_SMALL:
	case CM_SMALL_PIC:
	  if (opts->x_flag_pic)
	    opts->x_ix86_cmodel = CM_SMALL_PIC;
	  if (!TARGET_64BIT_P (opts->x_ix86_isa_flags))
	    error ("code model %qs not supported in the %s bit mode",
		   "small", "32");
	  break;

	case CM_MEDIUM:
	case CM_MEDIUM_PIC:
	  if (opts->x_flag_pic)
	    opts->x_ix86_cmodel = CM_MEDIUM_PIC;
	  if (!TARGET_64BIT_P (opts->x_ix86_isa_flags))
	    error ("code model %qs not supported in the %s bit mode",
		   "medium", "32");
	  else if (TARGET_X32_P (opts->x_ix86_isa_flags))
	    error ("code model %qs not supported in x32 mode",
		   "medium");
	  break;

	case CM_LARGE:
	case CM_LARGE_PIC:
	  if (opts->x_flag_pic)
	    opts->x_ix86_cmodel = CM_LARGE_PIC;
	  if (!TARGET_64BIT_P (opts->x_ix86_isa_flags))
	    error ("code model %qs not supported in the %s bit mode",
		   "large", "32");
	  else if (TARGET_X32_P (opts->x_ix86_isa_flags))
	    error ("code model %qs not supported in x32 mode",
		   "large");
	  break;

	case CM_32:
	  if (opts->x_flag_pic)
	    error ("code model %s does not support PIC mode", "32");
	  if (TARGET_64BIT_P (opts->x_ix86_isa_flags))
	    error ("code model %qs not supported in the %s bit mode",
		   "32", "64");
	  break;

	case CM_KERNEL:
	  if (opts->x_flag_pic)
	    {
	      error ("code model %s does not support PIC mode", "kernel");
	      opts->x_ix86_cmodel = CM_32;
	    }
	  if (!TARGET_64BIT_P (opts->x_ix86_isa_flags))
	    error ("code model %qs not supported in the %s bit mode",
		   "kernel", "32");
	  break;

	default:
	  gcc_unreachable ();
	}
    }
  else
    {
      /* For TARGET_64BIT and MS_ABI, force pic on, in order to enable the
	 use of rip-relative addressing.  This eliminates fixups that
	 would otherwise be needed if this object is to be placed in a
	 DLL, and is essentially just as efficient as direct addressing.  */
      if (TARGET_64BIT_P (opts->x_ix86_isa_flags)
	  && (TARGET_RDOS || TARGET_PECOFF))
	opts->x_ix86_cmodel = CM_MEDIUM_PIC, opts->x_flag_pic = 1;
      else if (TARGET_64BIT_P (opts->x_ix86_isa_flags))
	opts->x_ix86_cmodel = opts->x_flag_pic ? CM_SMALL_PIC : CM_SMALL;
      else
	opts->x_ix86_cmodel = CM_32;
    }
  if (TARGET_MACHO && opts->x_ix86_asm_dialect == ASM_INTEL)
    {
      error ("-masm=intel not supported in this configuration");
      opts->x_ix86_asm_dialect = ASM_ATT;
    }
  if ((TARGET_64BIT_P (opts->x_ix86_isa_flags) != 0)
      != ((opts->x_ix86_isa_flags & OPTION_MASK_ISA_64BIT) != 0))
    sorry ("%i-bit mode not compiled in",
	   (opts->x_ix86_isa_flags & OPTION_MASK_ISA_64BIT) ? 64 : 32);

  for (i = 0; i < pta_size; i++)
    if (! strcmp (opts->x_ix86_arch_string, processor_alias_table[i].name))
      {
	if (!strcmp (opts->x_ix86_arch_string, "generic"))
	  {
	    error (main_args_p
		   ? G_("%<generic%> CPU can be used only for %<-mtune=%> "
			"switch")
		   : G_("%<generic%> CPU can be used only for "
			"%<target(\"tune=\")%> attribute"));
	    return false;
	  }
	else if (!strcmp (opts->x_ix86_arch_string, "intel"))
	  {
	    error (main_args_p
		   ? G_("%<intel%> CPU can be used only for %<-mtune=%> "
			"switch")
		   : G_("%<intel%> CPU can be used only for "
			"%<target(\"tune=\")%> attribute"));
	    return false;
	  }

	if (TARGET_64BIT_P (opts->x_ix86_isa_flags)
	    && !((processor_alias_table[i].flags & PTA_64BIT) != 0))
	  {
	    error ("CPU you selected does not support x86-64 "
		   "instruction set");
	    return false;
	  }

	ix86_schedule = processor_alias_table[i].schedule;
	ix86_arch = processor_alias_table[i].processor;
	/* Default cpu tuning to the architecture.  */
	ix86_tune = ix86_arch;

	if (((processor_alias_table[i].flags & PTA_MMX) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_MMX))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_MMX;
	if (((processor_alias_table[i].flags & PTA_3DNOW) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_3DNOW))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_3DNOW;
	if (((processor_alias_table[i].flags & PTA_3DNOW_A) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_3DNOW_A))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_3DNOW_A;
	if (((processor_alias_table[i].flags & PTA_SSE) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SSE))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SSE;
	if (((processor_alias_table[i].flags & PTA_SSE2) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SSE2))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SSE2;
	if (((processor_alias_table[i].flags & PTA_SSE3) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SSE3))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SSE3;
	if (((processor_alias_table[i].flags & PTA_SSSE3) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SSSE3))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SSSE3;
	if (((processor_alias_table[i].flags & PTA_SSE4_1) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SSE4_1))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SSE4_1;
	if (((processor_alias_table[i].flags & PTA_SSE4_2) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SSE4_2))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SSE4_2;
	if (((processor_alias_table[i].flags & PTA_AVX) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX;
	if (((processor_alias_table[i].flags & PTA_AVX2) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX2))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX2;
	if (((processor_alias_table[i].flags & PTA_FMA) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_FMA))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_FMA;
	if (((processor_alias_table[i].flags & PTA_SSE4A) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SSE4A))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SSE4A;
	if (((processor_alias_table[i].flags & PTA_FMA4) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_FMA4))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_FMA4;
	if (((processor_alias_table[i].flags & PTA_XOP) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_XOP))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_XOP;
	if (((processor_alias_table[i].flags & PTA_LWP) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_LWP))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_LWP;
	if (((processor_alias_table[i].flags & PTA_ABM) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_ABM))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_ABM;
	if (((processor_alias_table[i].flags & PTA_BMI) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_BMI))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_BMI;
	if (((processor_alias_table[i].flags & (PTA_LZCNT | PTA_ABM)) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_LZCNT))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_LZCNT;
	if (((processor_alias_table[i].flags & PTA_TBM) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_TBM))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_TBM;
	if (((processor_alias_table[i].flags & PTA_BMI2) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_BMI2))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_BMI2;
	if (((processor_alias_table[i].flags & PTA_CX16) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_CX16))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_CX16;
	if (((processor_alias_table[i].flags & (PTA_POPCNT | PTA_ABM)) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_POPCNT))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_POPCNT;
	if (!(TARGET_64BIT_P (opts->x_ix86_isa_flags)
	    && ((processor_alias_table[i].flags & PTA_NO_SAHF) != 0))
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_SAHF))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_SAHF;
	if (((processor_alias_table[i].flags & PTA_MOVBE) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_MOVBE))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_MOVBE;
	if (((processor_alias_table[i].flags & PTA_AES) != 0)
	    && !(ix86_isa_flags_explicit & OPTION_MASK_ISA_AES))
	  ix86_isa_flags |= OPTION_MASK_ISA_AES;
	if (((processor_alias_table[i].flags & PTA_SHA) != 0)
	    && !(ix86_isa_flags_explicit & OPTION_MASK_ISA_SHA))
	  ix86_isa_flags |= OPTION_MASK_ISA_SHA;
	if (((processor_alias_table[i].flags & PTA_PCLMUL) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_PCLMUL))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_PCLMUL;
	if (((processor_alias_table[i].flags & PTA_FSGSBASE) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_FSGSBASE))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_FSGSBASE;
	if (((processor_alias_table[i].flags & PTA_RDRND) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_RDRND))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_RDRND;
	if (((processor_alias_table[i].flags & PTA_F16C) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_F16C))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_F16C;
	if (((processor_alias_table[i].flags & PTA_RTM) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_RTM))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_RTM;
	if (((processor_alias_table[i].flags & PTA_HLE) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_HLE))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_HLE;
	if (((processor_alias_table[i].flags & PTA_PRFCHW) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_PRFCHW))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_PRFCHW;
	if (((processor_alias_table[i].flags & PTA_RDSEED) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_RDSEED))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_RDSEED;
	if (((processor_alias_table[i].flags & PTA_ADX) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_ADX))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_ADX;
	if (((processor_alias_table[i].flags & PTA_FXSR) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_FXSR))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_FXSR;
	if (((processor_alias_table[i].flags & PTA_XSAVE) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_XSAVE))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_XSAVE;
	if (((processor_alias_table[i].flags & PTA_XSAVEOPT) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_XSAVEOPT))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_XSAVEOPT;
	if (((processor_alias_table[i].flags & PTA_AVX512F) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512F))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512F;
	if (((processor_alias_table[i].flags & PTA_AVX512ER) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512ER))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512ER;
	if (((processor_alias_table[i].flags & PTA_AVX512PF) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512PF))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512PF;
	if (((processor_alias_table[i].flags & PTA_AVX512CD) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512CD))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512CD;
	if (((processor_alias_table[i].flags & PTA_PREFETCHWT1) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_PREFETCHWT1))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_PREFETCHWT1;
	if (((processor_alias_table[i].flags & PTA_CLWB) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_CLWB))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_CLWB;
	if (((processor_alias_table[i].flags & PTA_CLFLUSHOPT) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_CLFLUSHOPT))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_CLFLUSHOPT;
	if (((processor_alias_table[i].flags & PTA_CLZERO) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_CLZERO))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_CLZERO;
	if (((processor_alias_table[i].flags & PTA_XSAVEC) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_XSAVEC))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_XSAVEC;
	if (((processor_alias_table[i].flags & PTA_XSAVES) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_XSAVES))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_XSAVES;
	if (((processor_alias_table[i].flags & PTA_AVX512DQ) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512DQ))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512DQ;
	if (((processor_alias_table[i].flags & PTA_AVX512BW) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512BW))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512BW;
	if (((processor_alias_table[i].flags & PTA_AVX512VL) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512VL))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512VL;
	if (((processor_alias_table[i].flags & PTA_AVX512VBMI) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512VBMI))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512VBMI;
	if (((processor_alias_table[i].flags & PTA_AVX512IFMA) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512IFMA))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512IFMA;
	if (((processor_alias_table[i].flags & PTA_AVX512VNNI) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_AVX512VNNI))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512VNNI;
	if (((processor_alias_table[i].flags & PTA_GFNI) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_GFNI))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_GFNI;
	if (((processor_alias_table[i].flags & PTA_AVX512VBMI2) != 0)
	    && !(opts->x_ix86_isa_flags_explicit
	    & OPTION_MASK_ISA_AVX512VBMI2))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512VBMI2;
	if (((processor_alias_table[i].flags & PTA_VPCLMULQDQ) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_VPCLMULQDQ))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_VPCLMULQDQ;
	if (((processor_alias_table[i].flags & PTA_AVX512BITALG) != 0)
	    && !(opts->x_ix86_isa_flags_explicit
	    & OPTION_MASK_ISA_AVX512BITALG))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512BITALG;

	if (((processor_alias_table[i].flags & PTA_AVX5124VNNIW) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit
		 & OPTION_MASK_ISA_AVX5124VNNIW))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_AVX5124VNNIW;
	if (((processor_alias_table[i].flags & PTA_AVX5124FMAPS) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit
		 & OPTION_MASK_ISA_AVX5124FMAPS))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_AVX5124FMAPS;
	if (((processor_alias_table[i].flags & PTA_AVX512VPOPCNTDQ) != 0)
	    && !(opts->x_ix86_isa_flags_explicit
		 & OPTION_MASK_ISA_AVX512VPOPCNTDQ))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_AVX512VPOPCNTDQ;
	if (((processor_alias_table[i].flags & PTA_SGX) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_SGX))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_SGX;
	if (((processor_alias_table[i].flags & PTA_VAES) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_VAES))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_VAES;
	if (((processor_alias_table[i].flags & PTA_RDPID) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_RDPID))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_RDPID;
	if (((processor_alias_table[i].flags & PTA_PCONFIG) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_PCONFIG))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_PCONFIG;
	if (((processor_alias_table[i].flags & PTA_WBNOINVD) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_WBNOINVD))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_WBNOINVD;
	if (((processor_alias_table[i].flags & PTA_PTWRITE) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_PTWRITE))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_PTWRITE;

	if ((processor_alias_table[i].flags
	   & (PTA_PREFETCH_SSE | PTA_SSE)) != 0)
	  x86_prefetch_sse = true;
	if (((processor_alias_table[i].flags & PTA_MWAITX) != 0)
	    && !(opts->x_ix86_isa_flags2_explicit & OPTION_MASK_ISA_MWAITX))
	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA_MWAITX;
	if (((processor_alias_table[i].flags & PTA_PKU) != 0)
	    && !(opts->x_ix86_isa_flags_explicit & OPTION_MASK_ISA_PKU))
	  opts->x_ix86_isa_flags |= OPTION_MASK_ISA_PKU;

	/* Don't enable x87 instructions if only
	   general registers are allowed.  */
	if (!(opts_set->x_ix86_target_flags & OPTION_MASK_GENERAL_REGS_ONLY)
	    && !(opts_set->x_target_flags & MASK_80387))
	  {
	    if (((processor_alias_table[i].flags & PTA_NO_80387) != 0))
	      opts->x_target_flags &= ~MASK_80387;
	    else
	      opts->x_target_flags |= MASK_80387;
	  }
	break;
      }

  if (i == pta_size)
    {
      error (main_args_p
	     ? G_("bad value (%qs) for %<-march=%> switch")
	     : G_("bad value (%qs) for %<target(\"arch=\")%> attribute"),
	     opts->x_ix86_arch_string);

      auto_vec <const char *> candidates;
      for (i = 0; i < pta_size; i++)
	if (strcmp (processor_alias_table[i].name, "generic")
	    && strcmp (processor_alias_table[i].name, "intel")
	    && (!TARGET_64BIT_P (opts->x_ix86_isa_flags)
		|| ((processor_alias_table[i].flags & PTA_64BIT) != 0)))
	  candidates.safe_push (processor_alias_table[i].name);

#ifdef HAVE_LOCAL_CPU_DETECT
      /* Add also "native" as possible value.  */
      candidates.safe_push ("native");
#endif

      char *s;
      const char *hint
	= candidates_list_and_hint (opts->x_ix86_arch_string, s, candidates);
      if (hint)
	inform (input_location,
		main_args_p
		? G_("valid arguments to %<-march=%> switch are: "
		     "%s; did you mean %qs?")
		: G_("valid arguments to %<target(\"arch=\")%> attribute are: "
		     "%s; did you mean %qs?"), s, hint);
      else
	inform (input_location,
		main_args_p
		? G_("valid arguments to %<-march=%> switch are: %s")
		: G_("valid arguments to %<target(\"arch=\")%> attribute "
		     "are: %s"), s);
      XDELETEVEC (s);
    }

  ix86_arch_mask = HOST_WIDE_INT_1U << ix86_arch;
  for (i = 0; i < X86_ARCH_LAST; ++i)
    ix86_arch_features[i] = !!(initial_ix86_arch_features[i] & ix86_arch_mask);

  for (i = 0; i < pta_size; i++)
    if (! strcmp (opts->x_ix86_tune_string, processor_alias_table[i].name))
      {
	ix86_schedule = processor_alias_table[i].schedule;
	ix86_tune = processor_alias_table[i].processor;
	if (TARGET_64BIT_P (opts->x_ix86_isa_flags))
	  {
	    if (!((processor_alias_table[i].flags & PTA_64BIT) != 0))
	      {
		if (ix86_tune_defaulted)
		  {
		    opts->x_ix86_tune_string = "x86-64";
		    for (i = 0; i < pta_size; i++)
		      if (! strcmp (opts->x_ix86_tune_string,
				    processor_alias_table[i].name))
			break;
		    ix86_schedule = processor_alias_table[i].schedule;
		    ix86_tune = processor_alias_table[i].processor;
		  }
		else
		  error ("CPU you selected does not support x86-64 "
			 "instruction set");
	      }
	  }
	/* Intel CPUs have always interpreted SSE prefetch instructions as
	   NOPs; so, we can enable SSE prefetch instructions even when
	   -mtune (rather than -march) points us to a processor that has them.
	   However, the VIA C3 gives a SIGILL, so we only do that for i686 and
	   higher processors.  */
	if (TARGET_CMOV
	    && ((processor_alias_table[i].flags
	      & (PTA_PREFETCH_SSE | PTA_SSE)) != 0))
	  x86_prefetch_sse = true;
	break;
      }

  if (ix86_tune_specified && i == pta_size)
    {
      error (main_args_p
	     ? G_("bad value (%qs) for %<-mtune=%> switch")
	     : G_("bad value (%qs) for %<target(\"tune=\")%> attribute"),
	     opts->x_ix86_tune_string);

      auto_vec <const char *> candidates;
      for (i = 0; i < pta_size; i++)
	if (!TARGET_64BIT_P (opts->x_ix86_isa_flags)
	    || ((processor_alias_table[i].flags & PTA_64BIT) != 0))
	  candidates.safe_push (processor_alias_table[i].name);

#ifdef HAVE_LOCAL_CPU_DETECT
      /* Add also "native" as possible value.  */
      candidates.safe_push ("native");
#endif

      char *s;
      const char *hint
	= candidates_list_and_hint (opts->x_ix86_tune_string, s, candidates);
      if (hint)
	inform (input_location,
		main_args_p
		? G_("valid arguments to %<-mtune=%> switch are: "
		     "%s; did you mean %qs?")
		: G_("valid arguments to %<target(\"tune=\")%> attribute are: "
		     "%s; did you mean %qs?"), s, hint);
      else
	inform (input_location,
		main_args_p
		? G_("valid arguments to %<-mtune=%> switch are: %s")
		: G_("valid arguments to %<target(\"tune=\")%> attribute "
		     "are: %s"), s);
      XDELETEVEC (s);
    }

  set_ix86_tune_features (ix86_tune, opts->x_ix86_dump_tunes);

#ifndef USE_IX86_FRAME_POINTER
#define USE_IX86_FRAME_POINTER 0
#endif

#ifndef USE_X86_64_FRAME_POINTER
#define USE_X86_64_FRAME_POINTER 0
#endif

  /* Set the default values for switches whose default depends on TARGET_64BIT
     in case they weren't overwritten by command line options.  */
  if (TARGET_64BIT_P (opts->x_ix86_isa_flags))
    {
      if (opts->x_optimize >= 1 && !opts_set->x_flag_omit_frame_pointer)
	opts->x_flag_omit_frame_pointer = !USE_X86_64_FRAME_POINTER;
      if (opts->x_flag_asynchronous_unwind_tables
	  && !opts_set->x_flag_unwind_tables
	  && TARGET_64BIT_MS_ABI)
	opts->x_flag_unwind_tables = 1;
      if (opts->x_flag_asynchronous_unwind_tables == 2)
	opts->x_flag_unwind_tables
	  = opts->x_flag_asynchronous_unwind_tables = 1;
      if (opts->x_flag_pcc_struct_return == 2)
	opts->x_flag_pcc_struct_return = 0;
    }
  else
    {
      if (opts->x_optimize >= 1 && !opts_set->x_flag_omit_frame_pointer)
	opts->x_flag_omit_frame_pointer
	  = !(USE_IX86_FRAME_POINTER || opts->x_optimize_size);
      if (opts->x_flag_asynchronous_unwind_tables == 2)
	opts->x_flag_asynchronous_unwind_tables = !USE_IX86_FRAME_POINTER;
      if (opts->x_flag_pcc_struct_return == 2)
	{
	  /* Intel MCU psABI specifies that -freg-struct-return should
	     be on.  Instead of setting DEFAULT_PCC_STRUCT_RETURN to 1,
	     we check -miamcu so that -freg-struct-return is always
	     turned on if -miamcu is used.  */
	  if (TARGET_IAMCU_P (opts->x_target_flags))
	    opts->x_flag_pcc_struct_return = 0;
	  else
	    opts->x_flag_pcc_struct_return = DEFAULT_PCC_STRUCT_RETURN;
	}
    }

  ix86_tune_cost = processor_cost_table[ix86_tune];
  /* TODO: ix86_cost should be chosen at instruction or function granuality
     so for cold code we use size_cost even in !optimize_size compilation.  */
  if (opts->x_optimize_size)
    ix86_cost = &ix86_size_cost;
  else
    ix86_cost = ix86_tune_cost;

  /* Arrange to set up i386_stack_locals for all functions.  */
  init_machine_status = ix86_init_machine_status;

  /* Validate -mregparm= value.  */
  if (opts_set->x_ix86_regparm)
    {
      if (TARGET_64BIT_P (opts->x_ix86_isa_flags))
	warning (0, "-mregparm is ignored in 64-bit mode");
      else if (TARGET_IAMCU_P (opts->x_target_flags))
	warning (0, "-mregparm is ignored for Intel MCU psABI");
      if (opts->x_ix86_regparm > REGPARM_MAX)
	{
	  error ("-mregparm=%d is not between 0 and %d",
		 opts->x_ix86_regparm, REGPARM_MAX);
	  opts->x_ix86_regparm = 0;
	}
    }
  if (TARGET_IAMCU_P (opts->x_target_flags)
      || TARGET_64BIT_P (opts->x_ix86_isa_flags))
    opts->x_ix86_regparm = REGPARM_MAX;

  /* Default align_* from the processor table.  */
  ix86_default_align (opts);

  /* Provide default for -mbranch-cost= value.  */
  if (!opts_set->x_ix86_branch_cost)
    opts->x_ix86_branch_cost = ix86_tune_cost->branch_cost;

  if (TARGET_64BIT_P (opts->x_ix86_isa_flags))
    {
      opts->x_target_flags
	|= TARGET_SUBTARGET64_DEFAULT & ~opts_set->x_target_flags;

      if (!ix86_arch_specified)
	opts->x_ix86_isa_flags
	  |= TARGET_SUBTARGET64_ISA_DEFAULT & ~opts->x_ix86_isa_flags_explicit;

      if (TARGET_RTD_P (opts->x_target_flags))
	warning (0,
		 main_args_p
		 ? G_("%<-mrtd%> is ignored in 64bit mode")
		 : G_("%<target(\"rtd\")%> is ignored in 64bit mode"));
    }
  else
    {
      opts->x_target_flags
	|= TARGET_SUBTARGET32_DEFAULT & ~opts_set->x_target_flags;

      if (!ix86_arch_specified)
        opts->x_ix86_isa_flags
	  |= TARGET_SUBTARGET32_ISA_DEFAULT & ~opts->x_ix86_isa_flags_explicit;

      /* i386 ABI does not specify red zone.  It still makes sense to use it
         when programmer takes care to stack from being destroyed.  */
      if (!(opts_set->x_target_flags & MASK_NO_RED_ZONE))
        opts->x_target_flags |= MASK_NO_RED_ZONE;
    }

  /* Keep nonleaf frame pointers.  */
  if (opts->x_flag_omit_frame_pointer)
    opts->x_target_flags &= ~MASK_OMIT_LEAF_FRAME_POINTER;
  else if (TARGET_OMIT_LEAF_FRAME_POINTER_P (opts->x_target_flags))
    opts->x_flag_omit_frame_pointer = 1;

  /* If we're doing fast math, we don't care about comparison order
     wrt NaNs.  This lets us use a shorter comparison sequence.  */
  if (opts->x_flag_finite_math_only)
    opts->x_target_flags &= ~MASK_IEEE_FP;

  /* If the architecture always has an FPU, turn off NO_FANCY_MATH_387,
     since the insns won't need emulation.  */
  if (ix86_tune_features [X86_TUNE_ALWAYS_FANCY_MATH_387])
    opts->x_target_flags &= ~MASK_NO_FANCY_MATH_387;

  /* Likewise, if the target doesn't have a 387, or we've specified
     software floating point, don't use 387 inline intrinsics.  */
  if (!TARGET_80387_P (opts->x_target_flags))
    opts->x_target_flags |= MASK_NO_FANCY_MATH_387;

  /* Turn on MMX builtins for -msse.  */
  if (TARGET_SSE_P (opts->x_ix86_isa_flags))
    opts->x_ix86_isa_flags
      |= OPTION_MASK_ISA_MMX & ~opts->x_ix86_isa_flags_explicit;

  /* Enable SSE prefetch.  */
  if (TARGET_SSE_P (opts->x_ix86_isa_flags)
      || (TARGET_PRFCHW_P (opts->x_ix86_isa_flags)
	  && !TARGET_3DNOW_P (opts->x_ix86_isa_flags))
      || TARGET_PREFETCHWT1_P (opts->x_ix86_isa_flags))
    x86_prefetch_sse = true;

  /* Enable popcnt instruction for -msse4.2 or -mabm.  */
  if (TARGET_SSE4_2_P (opts->x_ix86_isa_flags)
      || TARGET_ABM_P (opts->x_ix86_isa_flags))
    opts->x_ix86_isa_flags
      |= OPTION_MASK_ISA_POPCNT & ~opts->x_ix86_isa_flags_explicit;

  /* Enable lzcnt instruction for -mabm.  */
  if (TARGET_ABM_P(opts->x_ix86_isa_flags))
    opts->x_ix86_isa_flags
      |= OPTION_MASK_ISA_LZCNT & ~opts->x_ix86_isa_flags_explicit;

  /* Disable BMI, BMI2 and TBM instructions for -m16.  */
  if (TARGET_16BIT_P(opts->x_ix86_isa_flags))
    opts->x_ix86_isa_flags
      &= ~((OPTION_MASK_ISA_BMI | OPTION_MASK_ISA_BMI2 | OPTION_MASK_ISA_TBM)
	   & ~opts->x_ix86_isa_flags_explicit);

  /* Validate -mpreferred-stack-boundary= value or default it to
     PREFERRED_STACK_BOUNDARY_DEFAULT.  */
  ix86_preferred_stack_boundary = PREFERRED_STACK_BOUNDARY_DEFAULT;
  if (opts_set->x_ix86_preferred_stack_boundary_arg)
    {
      int min = TARGET_64BIT_P (opts->x_ix86_isa_flags)? 3 : 2;
      int max = TARGET_SEH ? 4 : 12;

      if (opts->x_ix86_preferred_stack_boundary_arg < min
	  || opts->x_ix86_preferred_stack_boundary_arg > max)
	{
	  if (min == max)
	    error ("-mpreferred-stack-boundary is not supported "
		   "for this target");
	  else
	    error ("-mpreferred-stack-boundary=%d is not between %d and %d",
		   opts->x_ix86_preferred_stack_boundary_arg, min, max);
	}
      else
	ix86_preferred_stack_boundary
	  = (1 << opts->x_ix86_preferred_stack_boundary_arg) * BITS_PER_UNIT;
    }

  /* Set the default value for -mstackrealign.  */
  if (!opts_set->x_ix86_force_align_arg_pointer)
    opts->x_ix86_force_align_arg_pointer = STACK_REALIGN_DEFAULT;

  ix86_default_incoming_stack_boundary = PREFERRED_STACK_BOUNDARY;

  /* Validate -mincoming-stack-boundary= value or default it to
     MIN_STACK_BOUNDARY/PREFERRED_STACK_BOUNDARY.  */
  ix86_incoming_stack_boundary = ix86_default_incoming_stack_boundary;
  if (opts_set->x_ix86_incoming_stack_boundary_arg)
    {
      int min = TARGET_64BIT_P (opts->x_ix86_isa_flags) ? 3 : 2;

      if (opts->x_ix86_incoming_stack_boundary_arg < min
	  || opts->x_ix86_incoming_stack_boundary_arg > 12)
	error ("-mincoming-stack-boundary=%d is not between %d and 12",
	       opts->x_ix86_incoming_stack_boundary_arg, min);
      else
	{
	  ix86_user_incoming_stack_boundary
	    = (1 << opts->x_ix86_incoming_stack_boundary_arg) * BITS_PER_UNIT;
	  ix86_incoming_stack_boundary
	    = ix86_user_incoming_stack_boundary;
	}
    }

#ifndef NO_PROFILE_COUNTERS
  if (flag_nop_mcount)
    error ("-mnop-mcount is not compatible with this target");
#endif
  if (flag_nop_mcount && flag_pic)
    error ("-mnop-mcount is not implemented for -fPIC");

  /* Accept -msseregparm only if at least SSE support is enabled.  */
  if (TARGET_SSEREGPARM_P (opts->x_target_flags)
      && ! TARGET_SSE_P (opts->x_ix86_isa_flags))
    error (main_args_p
	   ? G_("%<-msseregparm%> used without SSE enabled")
	   : G_("%<target(\"sseregparm\")%> used without SSE enabled"));

  if (opts_set->x_ix86_fpmath)
    {
      if (opts->x_ix86_fpmath & FPMATH_SSE)
	{
	  if (!TARGET_SSE_P (opts->x_ix86_isa_flags))
	    {
	      if (TARGET_80387_P (opts->x_target_flags))
		{
		  warning (0, "SSE instruction set disabled, using 387 arithmetics");
		  opts->x_ix86_fpmath = FPMATH_387;
		}
	    }
	  else if ((opts->x_ix86_fpmath & FPMATH_387)
		   && !TARGET_80387_P (opts->x_target_flags))
	    {
	      warning (0, "387 instruction set disabled, using SSE arithmetics");
	      opts->x_ix86_fpmath = FPMATH_SSE;
	    }
	}
    }
  /* For all chips supporting SSE2, -mfpmath=sse performs better than
     fpmath=387.  The second is however default at many targets since the
     extra 80bit precision of temporaries is considered to be part of ABI.
     Overwrite the default at least for -ffast-math. 
     TODO: -mfpmath=both seems to produce same performing code with bit
     smaller binaries.  It is however not clear if register allocation is
     ready for this setting.
     Also -mfpmath=387 is overall a lot more compact (bout 4-5%) than SSE
     codegen.  We may switch to 387 with -ffast-math for size optimized
     functions. */
  else if (fast_math_flags_set_p (&global_options)
	   && TARGET_SSE2_P (opts->x_ix86_isa_flags))
    opts->x_ix86_fpmath = FPMATH_SSE;
  else
    opts->x_ix86_fpmath = TARGET_FPMATH_DEFAULT_P (opts->x_ix86_isa_flags);

  /* Use external vectorized library in vectorizing intrinsics.  */
  if (opts_set->x_ix86_veclibabi_type)
    switch (opts->x_ix86_veclibabi_type)
      {
      case ix86_veclibabi_type_svml:
	ix86_veclib_handler = ix86_veclibabi_svml;
	break;

      case ix86_veclibabi_type_acml:
	ix86_veclib_handler = ix86_veclibabi_acml;
	break;

      default:
	gcc_unreachable ();
      }

  if (ix86_tune_features [X86_TUNE_ACCUMULATE_OUTGOING_ARGS]
      && !(opts_set->x_target_flags & MASK_ACCUMULATE_OUTGOING_ARGS))
    opts->x_target_flags |= MASK_ACCUMULATE_OUTGOING_ARGS;

  /* If stack probes are required, the space used for large function
     arguments on the stack must also be probed, so enable
     -maccumulate-outgoing-args so this happens in the prologue.  */
  if (TARGET_STACK_PROBE_P (opts->x_target_flags)
      && !(opts->x_target_flags & MASK_ACCUMULATE_OUTGOING_ARGS))
    {
      if (opts_set->x_target_flags & MASK_ACCUMULATE_OUTGOING_ARGS)
	warning (0,
		 main_args_p
		 ? G_("stack probing requires %<-maccumulate-outgoing-args%> "
		      "for correctness")
		 : G_("stack probing requires "
		      "%<target(\"accumulate-outgoing-args\")%> for "
		      "correctness"));
      opts->x_target_flags |= MASK_ACCUMULATE_OUTGOING_ARGS;
    }

  /* Stack realignment without -maccumulate-outgoing-args requires %ebp,
     so enable -maccumulate-outgoing-args when %ebp is fixed.  */
  if (fixed_regs[BP_REG]
      && !(opts->x_target_flags & MASK_ACCUMULATE_OUTGOING_ARGS))
    {
      if (opts_set->x_target_flags & MASK_ACCUMULATE_OUTGOING_ARGS)
	warning (0,
		 main_args_p
		 ? G_("fixed ebp register requires "
		      "%<-maccumulate-outgoing-args%>")
		 : G_("fixed ebp register requires "
		      "%<target(\"accumulate-outgoing-args\")%>"));
      opts->x_target_flags |= MASK_ACCUMULATE_OUTGOING_ARGS;
    }

  /* Figure out what ASM_GENERATE_INTERNAL_LABEL builds as a prefix.  */
  {
    char *p;
    ASM_GENERATE_INTERNAL_LABEL (internal_label_prefix, "LX", 0);
    p = strchr (internal_label_prefix, 'X');
    internal_label_prefix_len = p - internal_label_prefix;
    *p = '\0';
  }

  /* When scheduling description is not available, disable scheduler pass
     so it won't slow down the compilation and make x87 code slower.  */
  if (!TARGET_SCHEDULE)
    opts->x_flag_schedule_insns_after_reload = opts->x_flag_schedule_insns = 0;

  maybe_set_param_value (PARAM_SIMULTANEOUS_PREFETCHES,
			 ix86_tune_cost->simultaneous_prefetches,
			 opts->x_param_values,
			 opts_set->x_param_values);
  maybe_set_param_value (PARAM_L1_CACHE_LINE_SIZE,
			 ix86_tune_cost->prefetch_block,
			 opts->x_param_values,
			 opts_set->x_param_values);
  maybe_set_param_value (PARAM_L1_CACHE_SIZE,
			 ix86_tune_cost->l1_cache_size,
			 opts->x_param_values,
			 opts_set->x_param_values);
  maybe_set_param_value (PARAM_L2_CACHE_SIZE,
			 ix86_tune_cost->l2_cache_size,
			 opts->x_param_values,
			 opts_set->x_param_values);

  /* Enable sw prefetching at -O3 for CPUS that prefetching is helpful.  */
  if (opts->x_flag_prefetch_loop_arrays < 0
      && HAVE_prefetch
      && (opts->x_optimize >= 3 || opts->x_flag_profile_use)
      && !opts->x_optimize_size
      && TARGET_SOFTWARE_PREFETCHING_BENEFICIAL)
    opts->x_flag_prefetch_loop_arrays = 1;

  /* If using typedef char *va_list, signal that __builtin_va_start (&ap, 0)
     can be opts->x_optimized to ap = __builtin_next_arg (0).  */
  if (!TARGET_64BIT_P (opts->x_ix86_isa_flags) && !opts->x_flag_split_stack)
    targetm.expand_builtin_va_start = NULL;

  if (TARGET_64BIT_P (opts->x_ix86_isa_flags))
    {
      ix86_gen_leave = gen_leave_rex64;
      if (Pmode == DImode)
	{
	  ix86_gen_tls_global_dynamic_64 = gen_tls_global_dynamic_64_di;
	  ix86_gen_tls_local_dynamic_base_64
	    = gen_tls_local_dynamic_base_64_di;
	}
      else
	{
	  ix86_gen_tls_global_dynamic_64 = gen_tls_global_dynamic_64_si;
	  ix86_gen_tls_local_dynamic_base_64
	    = gen_tls_local_dynamic_base_64_si;
	}
    }
  else
    ix86_gen_leave = gen_leave;

  if (Pmode == DImode)
    {
      ix86_gen_add3 = gen_adddi3;
      ix86_gen_sub3 = gen_subdi3;
      ix86_gen_sub3_carry = gen_subdi3_carry;
      ix86_gen_one_cmpl2 = gen_one_cmpldi2;
      ix86_gen_andsp = gen_anddi3;
      ix86_gen_allocate_stack_worker = gen_allocate_stack_worker_probe_di;
      ix86_gen_adjust_stack_and_probe = gen_adjust_stack_and_probedi;
      ix86_gen_probe_stack_range = gen_probe_stack_rangedi;
      ix86_gen_monitor = gen_sse3_monitor_di;
      ix86_gen_monitorx = gen_monitorx_di;
      ix86_gen_clzero = gen_clzero_di;
    }
  else
    {
      ix86_gen_add3 = gen_addsi3;
      ix86_gen_sub3 = gen_subsi3;
      ix86_gen_sub3_carry = gen_subsi3_carry;
      ix86_gen_one_cmpl2 = gen_one_cmplsi2;
      ix86_gen_andsp = gen_andsi3;
      ix86_gen_allocate_stack_worker = gen_allocate_stack_worker_probe_si;
      ix86_gen_adjust_stack_and_probe = gen_adjust_stack_and_probesi;
      ix86_gen_probe_stack_range = gen_probe_stack_rangesi;
      ix86_gen_monitor = gen_sse3_monitor_si;
      ix86_gen_monitorx = gen_monitorx_si;
      ix86_gen_clzero = gen_clzero_si;
    }

#ifdef USE_IX86_CLD
  /* Use -mcld by default for 32-bit code if configured with --enable-cld.  */
  if (!TARGET_64BIT_P (opts->x_ix86_isa_flags))
    opts->x_target_flags |= MASK_CLD & ~opts_set->x_target_flags;
#endif

  /* Set the default value for -mfentry.  */
  if (!opts_set->x_flag_fentry)
    opts->x_flag_fentry = TARGET_SEH;
  else
    {
      if (!TARGET_64BIT_P (opts->x_ix86_isa_flags) && opts->x_flag_pic
	  && opts->x_flag_fentry)
	sorry ("-mfentry isn%'t supported for 32-bit in combination "
	       "with -fpic");
      else if (TARGET_SEH && !opts->x_flag_fentry)
	sorry ("-mno-fentry isn%'t compatible with SEH");
    }

  if (TARGET_SEH && TARGET_CALL_MS2SYSV_XLOGUES)
    sorry ("-mcall-ms2sysv-xlogues isn%'t currently supported with SEH");

  if (!(opts_set->x_target_flags & MASK_VZEROUPPER)
      && TARGET_EMIT_VZEROUPPER)
    opts->x_target_flags |= MASK_VZEROUPPER;
  if (!(opts_set->x_target_flags & MASK_STV))
    opts->x_target_flags |= MASK_STV;
  /* Disable STV if -mpreferred-stack-boundary={2,3} or
     -mincoming-stack-boundary={2,3} or -mstackrealign - the needed
     stack realignment will be extra cost the pass doesn't take into
     account and the pass can't realign the stack.  */
  if (ix86_preferred_stack_boundary < 128
      || ix86_incoming_stack_boundary < 128
      || opts->x_ix86_force_align_arg_pointer)
    opts->x_target_flags &= ~MASK_STV;
  if (!ix86_tune_features[X86_TUNE_AVX256_UNALIGNED_LOAD_OPTIMAL]
      && !(opts_set->x_target_flags & MASK_AVX256_SPLIT_UNALIGNED_LOAD))
    opts->x_target_flags |= MASK_AVX256_SPLIT_UNALIGNED_LOAD;
  if (!ix86_tune_features[X86_TUNE_AVX256_UNALIGNED_STORE_OPTIMAL]
      && !(opts_set->x_target_flags & MASK_AVX256_SPLIT_UNALIGNED_STORE))
    opts->x_target_flags |= MASK_AVX256_SPLIT_UNALIGNED_STORE;

  /* Enable 128-bit AVX instruction generation
     for the auto-vectorizer.  */
  if (TARGET_AVX128_OPTIMAL
      && (opts_set->x_prefer_vector_width_type == PVW_NONE))
    opts->x_prefer_vector_width_type = PVW_AVX128;

  /* Use 256-bit AVX instruction generation
     in the auto-vectorizer.  */
  if (ix86_tune_features[X86_TUNE_AVX256_OPTIMAL]
      && (opts_set->x_prefer_vector_width_type == PVW_NONE))
    opts->x_prefer_vector_width_type = PVW_AVX256;

  if (opts->x_ix86_recip_name)
    {
      char *p = ASTRDUP (opts->x_ix86_recip_name);
      char *q;
      unsigned int mask, i;
      bool invert;

      while ((q = strtok (p, ",")) != NULL)
	{
	  p = NULL;
	  if (*q == '!')
	    {
	      invert = true;
	      q++;
	    }
	  else
	    invert = false;

	  if (!strcmp (q, "default"))
	    mask = RECIP_MASK_ALL;
	  else
	    {
	      for (i = 0; i < ARRAY_SIZE (recip_options); i++)
		if (!strcmp (q, recip_options[i].string))
		  {
		    mask = recip_options[i].mask;
		    break;
		  }

	      if (i == ARRAY_SIZE (recip_options))
		{
		  error ("unknown option for -mrecip=%s", q);
		  invert = false;
		  mask = RECIP_MASK_NONE;
		}
	    }

	  opts->x_recip_mask_explicit |= mask;
	  if (invert)
	    opts->x_recip_mask &= ~mask;
	  else
	    opts->x_recip_mask |= mask;
	}
    }

  if (TARGET_RECIP_P (opts->x_target_flags))
    opts->x_recip_mask |= RECIP_MASK_ALL & ~opts->x_recip_mask_explicit;
  else if (opts_set->x_target_flags & MASK_RECIP)
    opts->x_recip_mask &= ~(RECIP_MASK_ALL & ~opts->x_recip_mask_explicit);

  /* Default long double to 64-bit for 32-bit Bionic and to __float128
     for 64-bit Bionic.  Also default long double to 64-bit for Intel
     MCU psABI.  */
  if ((TARGET_HAS_BIONIC || TARGET_IAMCU)
      && !(opts_set->x_target_flags
	   & (MASK_LONG_DOUBLE_64 | MASK_LONG_DOUBLE_128)))
    opts->x_target_flags |= (TARGET_64BIT
			     ? MASK_LONG_DOUBLE_128
			     : MASK_LONG_DOUBLE_64);

  /* Only one of them can be active.  */
  gcc_assert ((opts->x_target_flags & MASK_LONG_DOUBLE_64) == 0
	      || (opts->x_target_flags & MASK_LONG_DOUBLE_128) == 0);

  /* Handle stack protector */
  if (!opts_set->x_ix86_stack_protector_guard)
    {
#ifdef TARGET_THREAD_SSP_OFFSET
      if (!TARGET_HAS_BIONIC)
	opts->x_ix86_stack_protector_guard = SSP_TLS;
      else
#endif
	opts->x_ix86_stack_protector_guard = SSP_GLOBAL;
    }

  if (opts_set->x_ix86_stack_protector_guard_offset_str)
    {
      char *endp;
      const char *str = opts->x_ix86_stack_protector_guard_offset_str;

      errno = 0;
      int64_t offset;

#if defined(INT64_T_IS_LONG)
      offset = strtol (str, &endp, 0);
#else
      offset = strtoll (str, &endp, 0);
#endif

      if (!*str || *endp || errno)
	error ("%qs is not a valid number "
	       "in -mstack-protector-guard-offset=", str);

      if (!IN_RANGE (offset, HOST_WIDE_INT_C (-0x80000000),
		     HOST_WIDE_INT_C (0x7fffffff)))
	error ("%qs is not a valid offset "
	       "in -mstack-protector-guard-offset=", str);

      opts->x_ix86_stack_protector_guard_offset = offset;
    }
#ifdef TARGET_THREAD_SSP_OFFSET
  else
    opts->x_ix86_stack_protector_guard_offset = TARGET_THREAD_SSP_OFFSET;
#endif

  if (opts_set->x_ix86_stack_protector_guard_reg_str)
    {
      const char *str = opts->x_ix86_stack_protector_guard_reg_str;
      addr_space_t seg = ADDR_SPACE_GENERIC;

      /* Discard optional register prefix.  */
      if (str[0] == '%')
	str++;

      if (strlen (str) == 2 && str[1] == 's')
	{
	  if (str[0] == 'f')
	    seg = ADDR_SPACE_SEG_FS;
	  else if (str[0] == 'g')
	    seg = ADDR_SPACE_SEG_GS;
	}

      if (seg == ADDR_SPACE_GENERIC)
	error ("%qs is not a valid base register "
	       "in -mstack-protector-guard-reg=",
	       opts->x_ix86_stack_protector_guard_reg_str);

      opts->x_ix86_stack_protector_guard_reg = seg;
    }
  else
    {
      opts->x_ix86_stack_protector_guard_reg = DEFAULT_TLS_SEG_REG;

      /* The kernel uses a different segment register for performance
	 reasons; a system call would not have to trash the userspace
	 segment register, which would be expensive.  */
      if (opts->x_ix86_cmodel == CM_KERNEL)
	opts->x_ix86_stack_protector_guard_reg = ADDR_SPACE_SEG_GS;
    }

  /* Handle -mmemcpy-strategy= and -mmemset-strategy=  */
  if (opts->x_ix86_tune_memcpy_strategy)
    {
      char *str = xstrdup (opts->x_ix86_tune_memcpy_strategy);
      ix86_parse_stringop_strategy_string (str, false);
      free (str);
    }

  if (opts->x_ix86_tune_memset_strategy)
    {
      char *str = xstrdup (opts->x_ix86_tune_memset_strategy);
      ix86_parse_stringop_strategy_string (str, true);
      free (str);
    }

  /* Save the initial options in case the user does function specific
     options.  */
  if (main_args_p)
    target_option_default_node = target_option_current_node
      = build_target_option_node (opts);

  if (opts->x_flag_cf_protection != CF_NONE)
    opts->x_flag_cf_protection
      = (cf_protection_level) (opts->x_flag_cf_protection | CF_SET);

  if (ix86_tune_features [X86_TUNE_AVOID_128FMA_CHAINS])
    maybe_set_param_value (PARAM_AVOID_FMA_MAX_BITS, 128,
			   opts->x_param_values,
			   opts_set->x_param_values);

  return true;
}

/* Implement the TARGET_OPTION_OVERRIDE hook.  */

static void
ix86_option_override (void)
{
  ix86_option_override_internal (true, &global_options, &global_options_set);
}

/* Implement the TARGET_OFFLOAD_OPTIONS hook.  */
static char *
ix86_offload_options (void)
{
  if (TARGET_LP64)
    return xstrdup ("-foffload-abi=lp64");
  return xstrdup ("-foffload-abi=ilp32");
}

/* Update register usage after having seen the compiler flags.  */

static void
ix86_conditional_register_usage (void)
{
  int i, c_mask;

  /* If there are no caller-saved registers, preserve all registers.
     except fixed_regs and registers used for function return value
     since aggregate_value_p checks call_used_regs[regno] on return
     value.  */
  if (cfun && cfun->machine->no_caller_saved_registers)
    for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
      if (!fixed_regs[i] && !ix86_function_value_regno_p (i))
	call_used_regs[i] = 0;

  /* For 32-bit targets, squash the REX registers.  */
  if (! TARGET_64BIT)
    {
      for (i = FIRST_REX_INT_REG; i <= LAST_REX_INT_REG; i++)
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";
      for (i = FIRST_REX_SSE_REG; i <= LAST_REX_SSE_REG; i++)
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";
      for (i = FIRST_EXT_REX_SSE_REG; i <= LAST_EXT_REX_SSE_REG; i++)
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";
    }

  /*  See the definition of CALL_USED_REGISTERS in i386.h.  */
  c_mask = CALL_USED_REGISTERS_MASK (TARGET_64BIT_MS_ABI);
  
  CLEAR_HARD_REG_SET (reg_class_contents[(int)CLOBBERED_REGS]);

  for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
    {
      /* Set/reset conditionally defined registers from
	 CALL_USED_REGISTERS initializer.  */
      if (call_used_regs[i] > 1)
	call_used_regs[i] = !!(call_used_regs[i] & c_mask);

      /* Calculate registers of CLOBBERED_REGS register set
	 as call used registers from GENERAL_REGS register set.  */
      if (TEST_HARD_REG_BIT (reg_class_contents[(int)GENERAL_REGS], i)
	  && call_used_regs[i])
	SET_HARD_REG_BIT (reg_class_contents[(int)CLOBBERED_REGS], i);
    }

  /* If MMX is disabled, squash the registers.  */
  if (! TARGET_MMX)
    for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
      if (TEST_HARD_REG_BIT (reg_class_contents[(int)MMX_REGS], i))
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";

  /* If SSE is disabled, squash the registers.  */
  if (! TARGET_SSE)
    for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
      if (TEST_HARD_REG_BIT (reg_class_contents[(int)SSE_REGS], i))
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";

  /* If the FPU is disabled, squash the registers.  */
  if (! (TARGET_80387 || TARGET_FLOAT_RETURNS_IN_80387))
    for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
      if (TEST_HARD_REG_BIT (reg_class_contents[(int)FLOAT_REGS], i))
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";

  /* If AVX512F is disabled, squash the registers.  */
  if (! TARGET_AVX512F)
    {
      for (i = FIRST_EXT_REX_SSE_REG; i <= LAST_EXT_REX_SSE_REG; i++)
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";

      for (i = FIRST_MASK_REG; i <= LAST_MASK_REG; i++)
	fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";
    }
}

/* Canonicalize a comparison from one we don't have to one we do have.  */

static void
ix86_canonicalize_comparison (int *code, rtx *op0, rtx *op1,
			      bool op0_preserve_value)
{
  /* The order of operands in x87 ficom compare is forced by combine in
     simplify_comparison () function. Float operator is treated as RTX_OBJ
     with a precedence over other operators and is always put in the first
     place. Swap condition and operands to match ficom instruction.  */
  if (!op0_preserve_value
      && GET_CODE (*op0) == FLOAT && MEM_P (XEXP (*op0, 0)) && REG_P (*op1))
    {
      enum rtx_code scode = swap_condition ((enum rtx_code) *code);

      /* We are called only for compares that are split to SAHF instruction.
	 Ensure that we have setcc/jcc insn for the swapped condition.  */
      if (ix86_fp_compare_code_to_integer (scode) != UNKNOWN)
	{
	  std::swap (*op0, *op1);
	  *code = (int) scode;
	}
    }
}

/* Save the current options */

static void
ix86_function_specific_save (struct cl_target_option *ptr,
			     struct gcc_options *opts)
{
  ptr->arch = ix86_arch;
  ptr->schedule = ix86_schedule;
  ptr->prefetch_sse = x86_prefetch_sse;
  ptr->tune = ix86_tune;
  ptr->branch_cost = ix86_branch_cost;
  ptr->tune_defaulted = ix86_tune_defaulted;
  ptr->arch_specified = ix86_arch_specified;
  ptr->x_ix86_isa_flags_explicit = opts->x_ix86_isa_flags_explicit;
  ptr->x_ix86_isa_flags2_explicit = opts->x_ix86_isa_flags2_explicit;
  ptr->x_recip_mask_explicit = opts->x_recip_mask_explicit;
  ptr->x_ix86_arch_string = opts->x_ix86_arch_string;
  ptr->x_ix86_tune_string = opts->x_ix86_tune_string;
  ptr->x_ix86_cmodel = opts->x_ix86_cmodel;
  ptr->x_ix86_abi = opts->x_ix86_abi;
  ptr->x_ix86_asm_dialect = opts->x_ix86_asm_dialect;
  ptr->x_ix86_branch_cost = opts->x_ix86_branch_cost;
  ptr->x_ix86_dump_tunes = opts->x_ix86_dump_tunes;
  ptr->x_ix86_force_align_arg_pointer = opts->x_ix86_force_align_arg_pointer;
  ptr->x_ix86_force_drap = opts->x_ix86_force_drap;
  ptr->x_ix86_incoming_stack_boundary_arg = opts->x_ix86_incoming_stack_boundary_arg;
  ptr->x_ix86_pmode = opts->x_ix86_pmode;
  ptr->x_ix86_preferred_stack_boundary_arg = opts->x_ix86_preferred_stack_boundary_arg;
  ptr->x_ix86_recip_name = opts->x_ix86_recip_name;
  ptr->x_ix86_regparm = opts->x_ix86_regparm;
  ptr->x_ix86_section_threshold = opts->x_ix86_section_threshold;
  ptr->x_ix86_sse2avx = opts->x_ix86_sse2avx;
  ptr->x_ix86_stack_protector_guard = opts->x_ix86_stack_protector_guard;
  ptr->x_ix86_stringop_alg = opts->x_ix86_stringop_alg;
  ptr->x_ix86_tls_dialect = opts->x_ix86_tls_dialect;
  ptr->x_ix86_tune_ctrl_string = opts->x_ix86_tune_ctrl_string;
  ptr->x_ix86_tune_memcpy_strategy = opts->x_ix86_tune_memcpy_strategy;
  ptr->x_ix86_tune_memset_strategy = opts->x_ix86_tune_memset_strategy;
  ptr->x_ix86_tune_no_default = opts->x_ix86_tune_no_default;
  ptr->x_ix86_veclibabi_type = opts->x_ix86_veclibabi_type;

  /* The fields are char but the variables are not; make sure the
     values fit in the fields.  */
  gcc_assert (ptr->arch == ix86_arch);
  gcc_assert (ptr->schedule == ix86_schedule);
  gcc_assert (ptr->tune == ix86_tune);
  gcc_assert (ptr->branch_cost == ix86_branch_cost);
}

/* Restore the current options */

static void
ix86_function_specific_restore (struct gcc_options *opts,
				struct cl_target_option *ptr)
{
  enum processor_type old_tune = ix86_tune;
  enum processor_type old_arch = ix86_arch;
  unsigned HOST_WIDE_INT ix86_arch_mask;
  int i;

  /* We don't change -fPIC.  */
  opts->x_flag_pic = flag_pic;

  ix86_arch = (enum processor_type) ptr->arch;
  ix86_schedule = (enum attr_cpu) ptr->schedule;
  ix86_tune = (enum processor_type) ptr->tune;
  x86_prefetch_sse = ptr->prefetch_sse;
  opts->x_ix86_branch_cost = ptr->branch_cost;
  ix86_tune_defaulted = ptr->tune_defaulted;
  ix86_arch_specified = ptr->arch_specified;
  opts->x_ix86_isa_flags_explicit = ptr->x_ix86_isa_flags_explicit;
  opts->x_ix86_isa_flags2_explicit = ptr->x_ix86_isa_flags2_explicit;
  opts->x_recip_mask_explicit = ptr->x_recip_mask_explicit;
  opts->x_ix86_arch_string = ptr->x_ix86_arch_string;
  opts->x_ix86_tune_string = ptr->x_ix86_tune_string;
  opts->x_ix86_cmodel = ptr->x_ix86_cmodel;
  opts->x_ix86_abi = ptr->x_ix86_abi;
  opts->x_ix86_asm_dialect = ptr->x_ix86_asm_dialect;
  opts->x_ix86_branch_cost = ptr->x_ix86_branch_cost;
  opts->x_ix86_dump_tunes = ptr->x_ix86_dump_tunes;
  opts->x_ix86_force_align_arg_pointer = ptr->x_ix86_force_align_arg_pointer;
  opts->x_ix86_force_drap = ptr->x_ix86_force_drap;
  opts->x_ix86_incoming_stack_boundary_arg = ptr->x_ix86_incoming_stack_boundary_arg;
  opts->x_ix86_pmode = ptr->x_ix86_pmode;
  opts->x_ix86_preferred_stack_boundary_arg = ptr->x_ix86_preferred_stack_boundary_arg;
  opts->x_ix86_recip_name = ptr->x_ix86_recip_name;
  opts->x_ix86_regparm = ptr->x_ix86_regparm;
  opts->x_ix86_section_threshold = ptr->x_ix86_section_threshold;
  opts->x_ix86_sse2avx = ptr->x_ix86_sse2avx;
  opts->x_ix86_stack_protector_guard = ptr->x_ix86_stack_protector_guard;
  opts->x_ix86_stringop_alg = ptr->x_ix86_stringop_alg;
  opts->x_ix86_tls_dialect = ptr->x_ix86_tls_dialect;
  opts->x_ix86_tune_ctrl_string = ptr->x_ix86_tune_ctrl_string;
  opts->x_ix86_tune_memcpy_strategy = ptr->x_ix86_tune_memcpy_strategy;
  opts->x_ix86_tune_memset_strategy = ptr->x_ix86_tune_memset_strategy;
  opts->x_ix86_tune_no_default = ptr->x_ix86_tune_no_default;
  opts->x_ix86_veclibabi_type = ptr->x_ix86_veclibabi_type;
  ix86_tune_cost = processor_cost_table[ix86_tune];
  /* TODO: ix86_cost should be chosen at instruction or function granuality
     so for cold code we use size_cost even in !optimize_size compilation.  */
  if (opts->x_optimize_size)
    ix86_cost = &ix86_size_cost;
  else
    ix86_cost = ix86_tune_cost;

  /* Recreate the arch feature tests if the arch changed */
  if (old_arch != ix86_arch)
    {
      ix86_arch_mask = HOST_WIDE_INT_1U << ix86_arch;
      for (i = 0; i < X86_ARCH_LAST; ++i)
	ix86_arch_features[i]
	  = !!(initial_ix86_arch_features[i] & ix86_arch_mask);
    }

  /* Recreate the tune optimization tests */
  if (old_tune != ix86_tune)
    set_ix86_tune_features (ix86_tune, false);
}

/* Adjust target options after streaming them in.  This is mainly about
   reconciling them with global options.  */

static void
ix86_function_specific_post_stream_in (struct cl_target_option *ptr)
{
  /* flag_pic is a global option, but ix86_cmodel is target saved option
     partly computed from flag_pic.  If flag_pic is on, adjust x_ix86_cmodel
     for PIC, or error out.  */
  if (flag_pic)
    switch (ptr->x_ix86_cmodel)
      {
      case CM_SMALL:
	ptr->x_ix86_cmodel = CM_SMALL_PIC;
	break;

      case CM_MEDIUM:
	ptr->x_ix86_cmodel = CM_MEDIUM_PIC;
	break;

      case CM_LARGE:
	ptr->x_ix86_cmodel = CM_LARGE_PIC;
	break;

      case CM_KERNEL:
	error ("code model %s does not support PIC mode", "kernel");
	break;

      default:
	break;
      }
  else
    switch (ptr->x_ix86_cmodel)
      {
      case CM_SMALL_PIC:
	ptr->x_ix86_cmodel = CM_SMALL;
	break;

      case CM_MEDIUM_PIC:
	ptr->x_ix86_cmodel = CM_MEDIUM;
	break;

      case CM_LARGE_PIC:
	ptr->x_ix86_cmodel = CM_LARGE;
	break;

      default:
	break;
      }
}

/* Print the current options */

static void
ix86_function_specific_print (FILE *file, int indent,
			      struct cl_target_option *ptr)
{
  char *target_string
    = ix86_target_string (ptr->x_ix86_isa_flags, ptr->x_ix86_isa_flags2,
			  ptr->x_target_flags, ptr->x_ix86_target_flags,
			  NULL, NULL, ptr->x_ix86_fpmath, false);

  gcc_assert (ptr->arch < PROCESSOR_max);
  fprintf (file, "%*sarch = %d (%s)\n",
	   indent, "",
	   ptr->arch, processor_names[ptr->arch]);

  gcc_assert (ptr->tune < PROCESSOR_max);
  fprintf (file, "%*stune = %d (%s)\n",
	   indent, "",
	   ptr->tune, processor_names[ptr->tune]);

  fprintf (file, "%*sbranch_cost = %d\n", indent, "", ptr->branch_cost);

  if (target_string)
    {
      fprintf (file, "%*s%s\n", indent, "", target_string);
      free (target_string);
    }
}


/* Inner function to process the attribute((target(...))), take an argument and
   set the current options from the argument. If we have a list, recursively go
   over the list.  */

static bool
ix86_valid_target_attribute_inner_p (tree args, char *p_strings[],
				     struct gcc_options *opts,
				     struct gcc_options *opts_set,
				     struct gcc_options *enum_opts_set)
{
  char *next_optstr;
  bool ret = true;

#define IX86_ATTR_ISA(S,O)   { S, sizeof (S)-1, ix86_opt_isa, O, 0 }
#define IX86_ATTR_STR(S,O)   { S, sizeof (S)-1, ix86_opt_str, O, 0 }
#define IX86_ATTR_ENUM(S,O)  { S, sizeof (S)-1, ix86_opt_enum, O, 0 }
#define IX86_ATTR_YES(S,O,M) { S, sizeof (S)-1, ix86_opt_yes, O, M }
#define IX86_ATTR_NO(S,O,M)  { S, sizeof (S)-1, ix86_opt_no,  O, M }

  enum ix86_opt_type
  {
    ix86_opt_unknown,
    ix86_opt_yes,
    ix86_opt_no,
    ix86_opt_str,
    ix86_opt_enum,
    ix86_opt_isa
  };

  static const struct
  {
    const char *string;
    size_t len;
    enum ix86_opt_type type;
    int opt;
    int mask;
  } attrs[] = {
    /* isa options */
    IX86_ATTR_ISA ("pconfig",	OPT_mpconfig),
    IX86_ATTR_ISA ("wbnoinvd",	OPT_mwbnoinvd),
    IX86_ATTR_ISA ("sgx",	OPT_msgx),
    IX86_ATTR_ISA ("avx5124fmaps", OPT_mavx5124fmaps),
    IX86_ATTR_ISA ("avx5124vnniw", OPT_mavx5124vnniw),
    IX86_ATTR_ISA ("avx512vpopcntdq", OPT_mavx512vpopcntdq),
    IX86_ATTR_ISA ("avx512vbmi2", OPT_mavx512vbmi2),
    IX86_ATTR_ISA ("avx512vnni", OPT_mavx512vnni),
    IX86_ATTR_ISA ("avx512bitalg", OPT_mavx512bitalg),

    IX86_ATTR_ISA ("avx512vbmi", OPT_mavx512vbmi),
    IX86_ATTR_ISA ("avx512ifma", OPT_mavx512ifma),
    IX86_ATTR_ISA ("avx512vl",	OPT_mavx512vl),
    IX86_ATTR_ISA ("avx512bw",	OPT_mavx512bw),
    IX86_ATTR_ISA ("avx512dq",	OPT_mavx512dq),
    IX86_ATTR_ISA ("avx512er",	OPT_mavx512er),
    IX86_ATTR_ISA ("avx512pf",	OPT_mavx512pf),
    IX86_ATTR_ISA ("avx512cd",	OPT_mavx512cd),
    IX86_ATTR_ISA ("avx512f",	OPT_mavx512f),
    IX86_ATTR_ISA ("avx2",	OPT_mavx2),
    IX86_ATTR_ISA ("fma",	OPT_mfma),
    IX86_ATTR_ISA ("xop",	OPT_mxop),
    IX86_ATTR_ISA ("fma4",	OPT_mfma4),
    IX86_ATTR_ISA ("f16c",	OPT_mf16c),
    IX86_ATTR_ISA ("avx",	OPT_mavx),
    IX86_ATTR_ISA ("sse4",	OPT_msse4),
    IX86_ATTR_ISA ("sse4.2",	OPT_msse4_2),
    IX86_ATTR_ISA ("sse4.1",	OPT_msse4_1),
    IX86_ATTR_ISA ("sse4a",	OPT_msse4a),
    IX86_ATTR_ISA ("ssse3",	OPT_mssse3),
    IX86_ATTR_ISA ("sse3",	OPT_msse3),
    IX86_ATTR_ISA ("aes",	OPT_maes),
    IX86_ATTR_ISA ("sha",	OPT_msha),
    IX86_ATTR_ISA ("pclmul",	OPT_mpclmul),
    IX86_ATTR_ISA ("sse2",	OPT_msse2),
    IX86_ATTR_ISA ("sse",	OPT_msse),
    IX86_ATTR_ISA ("3dnowa",	OPT_m3dnowa),
    IX86_ATTR_ISA ("3dnow",	OPT_m3dnow),
    IX86_ATTR_ISA ("mmx",	OPT_mmmx),
    IX86_ATTR_ISA ("rtm",	OPT_mrtm),
    IX86_ATTR_ISA ("prfchw",	OPT_mprfchw),
    IX86_ATTR_ISA ("rdseed",	OPT_mrdseed),
    IX86_ATTR_ISA ("adx",	OPT_madx),
    IX86_ATTR_ISA ("prefetchwt1", OPT_mprefetchwt1),
    IX86_ATTR_ISA ("clflushopt", OPT_mclflushopt),
    IX86_ATTR_ISA ("xsaves",	OPT_mxsaves),
    IX86_ATTR_ISA ("xsavec",	OPT_mxsavec),
    IX86_ATTR_ISA ("xsaveopt",	OPT_mxsaveopt),
    IX86_ATTR_ISA ("xsave",	OPT_mxsave),
    IX86_ATTR_ISA ("abm",	OPT_mabm),
    IX86_ATTR_ISA ("bmi",	OPT_mbmi),
    IX86_ATTR_ISA ("bmi2",	OPT_mbmi2),
    IX86_ATTR_ISA ("lzcnt",	OPT_mlzcnt),
    IX86_ATTR_ISA ("tbm",	OPT_mtbm),
    IX86_ATTR_ISA ("popcnt",	OPT_mpopcnt),
    IX86_ATTR_ISA ("cx16",	OPT_mcx16),
    IX86_ATTR_ISA ("sahf",	OPT_msahf),
    IX86_ATTR_ISA ("movbe",	OPT_mmovbe),
    IX86_ATTR_ISA ("crc32",	OPT_mcrc32),
    IX86_ATTR_ISA ("fsgsbase",	OPT_mfsgsbase),
    IX86_ATTR_ISA ("rdrnd",	OPT_mrdrnd),
    IX86_ATTR_ISA ("mwaitx",	OPT_mmwaitx),
    IX86_ATTR_ISA ("clzero",	OPT_mclzero),
    IX86_ATTR_ISA ("pku",	OPT_mpku),
    IX86_ATTR_ISA ("lwp",	OPT_mlwp),
    IX86_ATTR_ISA ("hle",	OPT_mhle),
    IX86_ATTR_ISA ("fxsr",	OPT_mfxsr),
    IX86_ATTR_ISA ("clwb",	OPT_mclwb),
    IX86_ATTR_ISA ("rdpid",	OPT_mrdpid),
    IX86_ATTR_ISA ("gfni",	OPT_mgfni),
    IX86_ATTR_ISA ("shstk",	OPT_mshstk),
    IX86_ATTR_ISA ("vaes",	OPT_mvaes),
    IX86_ATTR_ISA ("vpclmulqdq", OPT_mvpclmulqdq),
    IX86_ATTR_ISA ("movdiri", OPT_mmovdiri),
    IX86_ATTR_ISA ("movdir64b", OPT_mmovdir64b),
    IX86_ATTR_ISA ("waitpkg", OPT_mwaitpkg),
    IX86_ATTR_ISA ("cldemote", OPT_mcldemote),
    IX86_ATTR_ISA ("ptwrite",   OPT_mptwrite),

    /* enum options */
    IX86_ATTR_ENUM ("fpmath=",	OPT_mfpmath_),

    /* string options */
    IX86_ATTR_STR ("arch=",	IX86_FUNCTION_SPECIFIC_ARCH),
    IX86_ATTR_STR ("tune=",	IX86_FUNCTION_SPECIFIC_TUNE),

    /* flag options */
    IX86_ATTR_YES ("cld",
		   OPT_mcld,
		   MASK_CLD),

    IX86_ATTR_NO ("fancy-math-387",
		  OPT_mfancy_math_387,
		  MASK_NO_FANCY_MATH_387),

    IX86_ATTR_YES ("ieee-fp",
		   OPT_mieee_fp,
		   MASK_IEEE_FP),

    IX86_ATTR_YES ("inline-all-stringops",
		   OPT_minline_all_stringops,
		   MASK_INLINE_ALL_STRINGOPS),

    IX86_ATTR_YES ("inline-stringops-dynamically",
		   OPT_minline_stringops_dynamically,
		   MASK_INLINE_STRINGOPS_DYNAMICALLY),

    IX86_ATTR_NO ("align-stringops",
		  OPT_mno_align_stringops,
		  MASK_NO_ALIGN_STRINGOPS),

    IX86_ATTR_YES ("recip",
		   OPT_mrecip,
		   MASK_RECIP),

  };

  /* If this is a list, recurse to get the options.  */
  if (TREE_CODE (args) == TREE_LIST)
    {
      bool ret = true;

      for (; args; args = TREE_CHAIN (args))
	if (TREE_VALUE (args)
	    && !ix86_valid_target_attribute_inner_p (TREE_VALUE (args),
						     p_strings, opts, opts_set,
						     enum_opts_set))
	  ret = false;

      return ret;
    }

  else if (TREE_CODE (args) != STRING_CST)
    {
      error ("attribute %<target%> argument not a string");
      return false;
    }

  /* Handle multiple arguments separated by commas.  */
  next_optstr = ASTRDUP (TREE_STRING_POINTER (args));

  while (next_optstr && *next_optstr != '\0')
    {
      char *p = next_optstr;
      char *orig_p = p;
      char *comma = strchr (next_optstr, ',');
      const char *opt_string;
      size_t len, opt_len;
      int opt;
      bool opt_set_p;
      char ch;
      unsigned i;
      enum ix86_opt_type type = ix86_opt_unknown;
      int mask = 0;

      if (comma)
	{
	  *comma = '\0';
	  len = comma - next_optstr;
	  next_optstr = comma + 1;
	}
      else
	{
	  len = strlen (p);
	  next_optstr = NULL;
	}

      /* Recognize no-xxx.  */
      if (len > 3 && p[0] == 'n' && p[1] == 'o' && p[2] == '-')
	{
	  opt_set_p = false;
	  p += 3;
	  len -= 3;
	}
      else
	opt_set_p = true;

      /* Find the option.  */
      ch = *p;
      opt = N_OPTS;
      for (i = 0; i < ARRAY_SIZE (attrs); i++)
	{
	  type = attrs[i].type;
	  opt_len = attrs[i].len;
	  if (ch == attrs[i].string[0]
	      && ((type != ix86_opt_str && type != ix86_opt_enum)
		  ? len == opt_len
		  : len > opt_len)
	      && memcmp (p, attrs[i].string, opt_len) == 0)
	    {
	      opt = attrs[i].opt;
	      mask = attrs[i].mask;
	      opt_string = attrs[i].string;
	      break;
	    }
	}

      /* Process the option.  */
      if (opt == N_OPTS)
	{
	  error ("attribute(target(\"%s\")) is unknown", orig_p);
	  ret = false;
	}

      else if (type == ix86_opt_isa)
	{
	  struct cl_decoded_option decoded;

	  generate_option (opt, NULL, opt_set_p, CL_TARGET, &decoded);
	  ix86_handle_option (opts, opts_set,
			      &decoded, input_location);
	}

      else if (type == ix86_opt_yes || type == ix86_opt_no)
	{
	  if (type == ix86_opt_no)
	    opt_set_p = !opt_set_p;

	  if (opt_set_p)
	    opts->x_target_flags |= mask;
	  else
	    opts->x_target_flags &= ~mask;
	}

      else if (type == ix86_opt_str)
	{
	  if (p_strings[opt])
	    {
	      error ("option(\"%s\") was already specified", opt_string);
	      ret = false;
	    }
	  else
	    p_strings[opt] = xstrdup (p + opt_len);
	}

      else if (type == ix86_opt_enum)
	{
	  bool arg_ok;
	  int value;

	  arg_ok = opt_enum_arg_to_value (opt, p + opt_len, &value, CL_TARGET);
	  if (arg_ok)
	    set_option (opts, enum_opts_set, opt, value,
			p + opt_len, DK_UNSPECIFIED, input_location,
			global_dc);
	  else
	    {
	      error ("attribute(target(\"%s\")) is unknown", orig_p);
	      ret = false;
	    }
	}

      else
	gcc_unreachable ();
    }

  return ret;
}

/* Release allocated strings.  */
static void
release_options_strings (char **option_strings)
{
  /* Free up memory allocated to hold the strings */
  for (unsigned i = 0; i < IX86_FUNCTION_SPECIFIC_MAX; i++)
    free (option_strings[i]);
}

/* Return a TARGET_OPTION_NODE tree of the target options listed or NULL.  */

tree
ix86_valid_target_attribute_tree (tree args,
				  struct gcc_options *opts,
				  struct gcc_options *opts_set)
{
  const char *orig_arch_string = opts->x_ix86_arch_string;
  const char *orig_tune_string = opts->x_ix86_tune_string;
  enum fpmath_unit orig_fpmath_set = opts_set->x_ix86_fpmath;
  int orig_tune_defaulted = ix86_tune_defaulted;
  int orig_arch_specified = ix86_arch_specified;
  char *option_strings[IX86_FUNCTION_SPECIFIC_MAX] = { NULL, NULL };
  tree t = NULL_TREE;
  struct cl_target_option *def
    = TREE_TARGET_OPTION (target_option_default_node);
  struct gcc_options enum_opts_set;

  memset (&enum_opts_set, 0, sizeof (enum_opts_set));

  /* Process each of the options on the chain.  */
  if (! ix86_valid_target_attribute_inner_p (args, option_strings, opts,
					     opts_set, &enum_opts_set))
    return error_mark_node;

  /* If the changed options are different from the default, rerun
     ix86_option_override_internal, and then save the options away.
     The string options are attribute options, and will be undone
     when we copy the save structure.  */
  if (opts->x_ix86_isa_flags != def->x_ix86_isa_flags
      || opts->x_ix86_isa_flags2 != def->x_ix86_isa_flags2
      || opts->x_target_flags != def->x_target_flags
      || option_strings[IX86_FUNCTION_SPECIFIC_ARCH]
      || option_strings[IX86_FUNCTION_SPECIFIC_TUNE]
      || enum_opts_set.x_ix86_fpmath)
    {
      /* If we are using the default tune= or arch=, undo the string assigned,
	 and use the default.  */
      if (option_strings[IX86_FUNCTION_SPECIFIC_ARCH])
	{
	  opts->x_ix86_arch_string
	    = ggc_strdup (option_strings[IX86_FUNCTION_SPECIFIC_ARCH]);

	  /* If arch= is set,  clear all bits in x_ix86_isa_flags,
	     except for ISA_64BIT, ABI_64, ABI_X32, and CODE16.  */
	  opts->x_ix86_isa_flags &= (OPTION_MASK_ISA_64BIT
				     | OPTION_MASK_ABI_64
				     | OPTION_MASK_ABI_X32
				     | OPTION_MASK_CODE16);
	  opts->x_ix86_isa_flags2 = 0;
	}
      else if (!orig_arch_specified)
	opts->x_ix86_arch_string = NULL;

      if (option_strings[IX86_FUNCTION_SPECIFIC_TUNE])
	opts->x_ix86_tune_string
	  = ggc_strdup (option_strings[IX86_FUNCTION_SPECIFIC_TUNE]);
      else if (orig_tune_defaulted)
	opts->x_ix86_tune_string = NULL;

      /* If fpmath= is not set, and we now have sse2 on 32-bit, use it.  */
      if (enum_opts_set.x_ix86_fpmath)
	opts_set->x_ix86_fpmath = (enum fpmath_unit) 1;

      /* Do any overrides, such as arch=xxx, or tune=xxx support.  */
      bool r = ix86_option_override_internal (false, opts, opts_set);
      if (!r)
	{
	  release_options_strings (option_strings);
	  return error_mark_node;
	}

      /* Add any builtin functions with the new isa if any.  */
      ix86_add_new_builtins (opts->x_ix86_isa_flags, opts->x_ix86_isa_flags2);

      /* Save the current options unless we are validating options for
	 #pragma.  */
      t = build_target_option_node (opts);

      opts->x_ix86_arch_string = orig_arch_string;
      opts->x_ix86_tune_string = orig_tune_string;
      opts_set->x_ix86_fpmath = orig_fpmath_set;

      release_options_strings (option_strings);
    }

  return t;
}

/* Hook to validate attribute((target("string"))).  */

static bool
ix86_valid_target_attribute_p (tree fndecl,
			       tree ARG_UNUSED (name),
			       tree args,
			       int ARG_UNUSED (flags))
{
  struct gcc_options func_options;
  tree new_target, new_optimize;
  bool ret = true;

  /* attribute((target("default"))) does nothing, beyond
     affecting multi-versioning.  */
  if (TREE_VALUE (args)
      && TREE_CODE (TREE_VALUE (args)) == STRING_CST
      && TREE_CHAIN (args) == NULL_TREE
      && strcmp (TREE_STRING_POINTER (TREE_VALUE (args)), "default") == 0)
    return true;

  tree old_optimize = build_optimization_node (&global_options);

  /* Get the optimization options of the current function.  */  
  tree func_optimize = DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl);
 
  if (!func_optimize)
    func_optimize = old_optimize;

  /* Init func_options.  */
  memset (&func_options, 0, sizeof (func_options));
  init_options_struct (&func_options, NULL);
  lang_hooks.init_options_struct (&func_options);
 
  cl_optimization_restore (&func_options,
			   TREE_OPTIMIZATION (func_optimize));

  /* Initialize func_options to the default before its target options can
     be set.  */
  cl_target_option_restore (&func_options,
			    TREE_TARGET_OPTION (target_option_default_node));

  new_target = ix86_valid_target_attribute_tree (args, &func_options,
						 &global_options_set);

  new_optimize = build_optimization_node (&func_options);

  if (new_target == error_mark_node)
    ret = false;

  else if (fndecl && new_target)
    {
      DECL_FUNCTION_SPECIFIC_TARGET (fndecl) = new_target;

      if (old_optimize != new_optimize)
	DECL_FUNCTION_SPECIFIC_OPTIMIZATION (fndecl) = new_optimize;
    }

  finalize_options_struct (&func_options);

  return ret;
}


/* Hook to determine if one function can safely inline another.  */

static bool
ix86_can_inline_p (tree caller, tree callee)
{
  tree caller_tree = DECL_FUNCTION_SPECIFIC_TARGET (caller);
  tree callee_tree = DECL_FUNCTION_SPECIFIC_TARGET (callee);

  /* Changes of those flags can be tolerated for always inlines. Lets hope
     user knows what he is doing.  */
  const unsigned HOST_WIDE_INT always_inline_safe_mask
	 = (MASK_USE_8BIT_IDIV | MASK_ACCUMULATE_OUTGOING_ARGS
	    | MASK_NO_ALIGN_STRINGOPS | MASK_AVX256_SPLIT_UNALIGNED_LOAD
	    | MASK_AVX256_SPLIT_UNALIGNED_STORE | MASK_CLD
	    | MASK_NO_FANCY_MATH_387 | MASK_IEEE_FP | MASK_INLINE_ALL_STRINGOPS
	    | MASK_INLINE_STRINGOPS_DYNAMICALLY | MASK_RECIP | MASK_STACK_PROBE
	    | MASK_STV | MASK_TLS_DIRECT_SEG_REFS | MASK_VZEROUPPER
	    | MASK_NO_PUSH_ARGS | MASK_OMIT_LEAF_FRAME_POINTER);


  if (!callee_tree)
    callee_tree = target_option_default_node;
  if (!caller_tree)
    caller_tree = target_option_default_node;
  if (callee_tree == caller_tree)
    return true;

  struct cl_target_option *caller_opts = TREE_TARGET_OPTION (caller_tree);
  struct cl_target_option *callee_opts = TREE_TARGET_OPTION (callee_tree);
  bool ret = false;
  bool always_inline
    = (DECL_DISREGARD_INLINE_LIMITS (callee)
       && lookup_attribute ("always_inline",
			    DECL_ATTRIBUTES (callee)));

  cgraph_node *callee_node = cgraph_node::get (callee);
  /* Callee's isa options should be a subset of the caller's, i.e. a SSE4
     function can inline a SSE2 function but a SSE2 function can't inline
     a SSE4 function.  */
  if (((caller_opts->x_ix86_isa_flags & callee_opts->x_ix86_isa_flags)
       != callee_opts->x_ix86_isa_flags)
      || ((caller_opts->x_ix86_isa_flags2 & callee_opts->x_ix86_isa_flags2)
	  != callee_opts->x_ix86_isa_flags2))
    ret = false;

  /* See if we have the same non-isa options.  */
  else if ((!always_inline
	    && caller_opts->x_target_flags != callee_opts->x_target_flags)
	   || (caller_opts->x_target_flags & ~always_inline_safe_mask)
	       != (callee_opts->x_target_flags & ~always_inline_safe_mask))
    ret = false;

  /* See if arch, tune, etc. are the same.  */
  else if (caller_opts->arch != callee_opts->arch)
    ret = false;

  else if (!always_inline && caller_opts->tune != callee_opts->tune)
    ret = false;

  else if (caller_opts->x_ix86_fpmath != callee_opts->x_ix86_fpmath
	   /* If the calle doesn't use FP expressions differences in
	      ix86_fpmath can be ignored.  We are called from FEs
	      for multi-versioning call optimization, so beware of
	      ipa_fn_summaries not available.  */
	   && (! ipa_fn_summaries
	       || ipa_fn_summaries->get (callee_node) == NULL
	       || ipa_fn_summaries->get (callee_node)->fp_expressions))
    ret = false;

  else if (!always_inline
	   && caller_opts->branch_cost != callee_opts->branch_cost)
    ret = false;

  else
    ret = true;

  return ret;
}


/* Remember the last target of ix86_set_current_function.  */
static GTY(()) tree ix86_previous_fndecl;

/* Set targets globals to the default (or current #pragma GCC target
   if active).  Invalidate ix86_previous_fndecl cache.  */

void
ix86_reset_previous_fndecl (void)
{
  tree new_tree = target_option_current_node;
  cl_target_option_restore (&global_options, TREE_TARGET_OPTION (new_tree));
  if (TREE_TARGET_GLOBALS (new_tree))
    restore_target_globals (TREE_TARGET_GLOBALS (new_tree));
  else if (new_tree == target_option_default_node)
    restore_target_globals (&default_target_globals);
  else
    TREE_TARGET_GLOBALS (new_tree) = save_target_globals_default_opts ();
  ix86_previous_fndecl = NULL_TREE;
}

/* Set the func_type field from the function FNDECL.  */

static void
ix86_set_func_type (tree fndecl)
{
  if (cfun->machine->func_type == TYPE_UNKNOWN)
    {
      if (lookup_attribute ("interrupt",
			    TYPE_ATTRIBUTES (TREE_TYPE (fndecl))))
	{
	  if (ix86_function_naked (fndecl))
	    error_at (DECL_SOURCE_LOCATION (fndecl),
		      "interrupt and naked attributes are not compatible");

	  int nargs = 0;
	  for (tree arg = DECL_ARGUMENTS (fndecl);
	       arg;
	       arg = TREE_CHAIN (arg))
	    nargs++;
	  cfun->machine->no_caller_saved_registers = true;
	  cfun->machine->func_type
	    = nargs == 2 ? TYPE_EXCEPTION : TYPE_INTERRUPT;

	  ix86_optimize_mode_switching[X86_DIRFLAG] = 1;

	  /* Only dwarf2out.c can handle -WORD(AP) as a pointer argument.  */
	  if (write_symbols != NO_DEBUG && write_symbols != DWARF2_DEBUG)
	    sorry ("Only DWARF debug format is supported for interrupt "
		   "service routine.");
	}
      else
	{
	  cfun->machine->func_type = TYPE_NORMAL;
	  if (lookup_attribute ("no_caller_saved_registers",
				TYPE_ATTRIBUTES (TREE_TYPE (fndecl))))
	    cfun->machine->no_caller_saved_registers = true;
	}
    }
}

/* Set the indirect_branch_type field from the function FNDECL.  */

static void
ix86_set_indirect_branch_type (tree fndecl)
{
  if (cfun->machine->indirect_branch_type == indirect_branch_unset)
    {
      tree attr = lookup_attribute ("indirect_branch",
				    DECL_ATTRIBUTES (fndecl));
      if (attr != NULL)
	{
	  tree args = TREE_VALUE (attr);
	  if (args == NULL)
	    gcc_unreachable ();
	  tree cst = TREE_VALUE (args);
	  if (strcmp (TREE_STRING_POINTER (cst), "keep") == 0)
	    cfun->machine->indirect_branch_type = indirect_branch_keep;
	  else if (strcmp (TREE_STRING_POINTER (cst), "thunk") == 0)
	    cfun->machine->indirect_branch_type = indirect_branch_thunk;
	  else if (strcmp (TREE_STRING_POINTER (cst), "thunk-inline") == 0)
	    cfun->machine->indirect_branch_type = indirect_branch_thunk_inline;
	  else if (strcmp (TREE_STRING_POINTER (cst), "thunk-extern") == 0)
	    cfun->machine->indirect_branch_type = indirect_branch_thunk_extern;
	  else
	    gcc_unreachable ();
	}
      else
	cfun->machine->indirect_branch_type = ix86_indirect_branch;

      /* -mcmodel=large is not compatible with -mindirect-branch=thunk
	 nor -mindirect-branch=thunk-extern.  */
      if ((ix86_cmodel == CM_LARGE || ix86_cmodel == CM_LARGE_PIC)
	  && ((cfun->machine->indirect_branch_type
	       == indirect_branch_thunk_extern)
	      || (cfun->machine->indirect_branch_type
		  == indirect_branch_thunk)))
	error ("%<-mindirect-branch=%s%> and %<-mcmodel=large%> are not "
	       "compatible",
	       ((cfun->machine->indirect_branch_type
		 == indirect_branch_thunk_extern)
		? "thunk-extern" : "thunk"));
    }

  if (cfun->machine->function_return_type == indirect_branch_unset)
    {
      tree attr = lookup_attribute ("function_return",
				    DECL_ATTRIBUTES (fndecl));
      if (attr != NULL)
	{
	  tree args = TREE_VALUE (attr);
	  if (args == NULL)
	    gcc_unreachable ();
	  tree cst = TREE_VALUE (args);
	  if (strcmp (TREE_STRING_POINTER (cst), "keep") == 0)
	    cfun->machine->function_return_type = indirect_branch_keep;
	  else if (strcmp (TREE_STRING_POINTER (cst), "thunk") == 0)
	    cfun->machine->function_return_type = indirect_branch_thunk;
	  else if (strcmp (TREE_STRING_POINTER (cst), "thunk-inline") == 0)
	    cfun->machine->function_return_type = indirect_branch_thunk_inline;
	  else if (strcmp (TREE_STRING_POINTER (cst), "thunk-extern") == 0)
	    cfun->machine->function_return_type = indirect_branch_thunk_extern;
	  else
	    gcc_unreachable ();
	}
      else
	cfun->machine->function_return_type = ix86_function_return;

      /* -mcmodel=large is not compatible with -mfunction-return=thunk
	 nor -mfunction-return=thunk-extern.  */
      if ((ix86_cmodel == CM_LARGE || ix86_cmodel == CM_LARGE_PIC)
	  && ((cfun->machine->function_return_type
	       == indirect_branch_thunk_extern)
	      || (cfun->machine->function_return_type
		  == indirect_branch_thunk)))
	error ("%<-mfunction-return=%s%> and %<-mcmodel=large%> are not "
	       "compatible",
	       ((cfun->machine->function_return_type
		 == indirect_branch_thunk_extern)
		? "thunk-extern" : "thunk"));
    }
}

/* Establish appropriate back-end context for processing the function
   FNDECL.  The argument might be NULL to indicate processing at top
   level, outside of any function scope.  */
static void
ix86_set_current_function (tree fndecl)
{
  /* Only change the context if the function changes.  This hook is called
     several times in the course of compiling a function, and we don't want to
     slow things down too much or call target_reinit when it isn't safe.  */
  if (fndecl == ix86_previous_fndecl)
    {
      /* There may be 2 function bodies for the same function FNDECL,
	 one is extern inline and one isn't.  Call ix86_set_func_type
	 to set the func_type field.  */
      if (fndecl != NULL_TREE)
	{
	  ix86_set_func_type (fndecl);
	  ix86_set_indirect_branch_type (fndecl);
	}
      return;
    }

  tree old_tree;
  if (ix86_previous_fndecl == NULL_TREE)
    old_tree = target_option_current_node;
  else if (DECL_FUNCTION_SPECIFIC_TARGET (ix86_previous_fndecl))
    old_tree = DECL_FUNCTION_SPECIFIC_TARGET (ix86_previous_fndecl);
  else
    old_tree = target_option_default_node;

  if (fndecl == NULL_TREE)
    {
      if (old_tree != target_option_current_node)
	ix86_reset_previous_fndecl ();
      return;
    }

  ix86_set_func_type (fndecl);
  ix86_set_indirect_branch_type (fndecl);

  tree new_tree = DECL_FUNCTION_SPECIFIC_TARGET (fndecl);
  if (new_tree == NULL_TREE)
    new_tree = target_option_default_node;

  if (old_tree != new_tree)
    {
      cl_target_option_restore (&global_options, TREE_TARGET_OPTION (new_tree));
      if (TREE_TARGET_GLOBALS (new_tree))
	restore_target_globals (TREE_TARGET_GLOBALS (new_tree));
      else if (new_tree == target_option_default_node)
	restore_target_globals (&default_target_globals);
      else
	TREE_TARGET_GLOBALS (new_tree) = save_target_globals_default_opts ();
    }
  ix86_previous_fndecl = fndecl;

  static bool prev_no_caller_saved_registers;

  /* 64-bit MS and SYSV ABI have different set of call used registers.
     Avoid expensive re-initialization of init_regs each time we switch
     function context.  */
  if (TARGET_64BIT
      && (call_used_regs[SI_REG]
	  == (cfun->machine->call_abi == MS_ABI)))
    reinit_regs ();
  /* Need to re-initialize init_regs if caller-saved registers are
     changed.  */
  else if (prev_no_caller_saved_registers
	   != cfun->machine->no_caller_saved_registers)
    reinit_regs ();

  if (cfun->machine->func_type != TYPE_NORMAL
      || cfun->machine->no_caller_saved_registers)
    {
      /* Don't allow SSE, MMX nor x87 instructions since they
	 may change processor state.  */
      const char *isa;
      if (TARGET_SSE)
	isa = "SSE";
      else if (TARGET_MMX)
	isa = "MMX/3Dnow";
      else if (TARGET_80387)
	isa = "80387";
      else
	isa = NULL;
      if (isa != NULL)
	{
	  if (cfun->machine->func_type != TYPE_NORMAL)
	    sorry ("%s instructions aren't allowed in %s service routine",
		   isa, (cfun->machine->func_type == TYPE_EXCEPTION
			 ? "exception" : "interrupt"));
	  else
	    sorry ("%s instructions aren't allowed in function with "
		   "no_caller_saved_registers attribute", isa);
	  /* Don't issue the same error twice.  */
	  cfun->machine->func_type = TYPE_NORMAL;
	  cfun->machine->no_caller_saved_registers = false;
	}
    }

  prev_no_caller_saved_registers
    = cfun->machine->no_caller_saved_registers;
}


/* Return true if this goes in large data/bss.  */

static bool
ix86_in_large_data_p (tree exp)
{
  if (ix86_cmodel != CM_MEDIUM && ix86_cmodel != CM_MEDIUM_PIC)
    return false;

  if (exp == NULL_TREE)
    return false;

  /* Functions are never large data.  */
  if (TREE_CODE (exp) == FUNCTION_DECL)
    return false;

  /* Automatic variables are never large data.  */
  if (VAR_P (exp) && !is_global_var (exp))
    return false;

  if (VAR_P (exp) && DECL_SECTION_NAME (exp))
    {
      const char *section = DECL_SECTION_NAME (exp);
      if (strcmp (section, ".ldata") == 0
	  || strcmp (section, ".lbss") == 0)
	return true;
      return false;
    }
  else
    {
      HOST_WIDE_INT size = int_size_in_bytes (TREE_TYPE (exp));

      /* If this is an incomplete type with size 0, then we can't put it
	 in data because it might be too big when completed.  Also,
	 int_size_in_bytes returns -1 if size can vary or is larger than
	 an integer in which case also it is safer to assume that it goes in
	 large data.  */
      if (size <= 0 || size > ix86_section_threshold)
	return true;
    }

  return false;
}

/* i386-specific section flag to mark large sections.  */
#define SECTION_LARGE SECTION_MACH_DEP

/* Switch to the appropriate section for output of DECL.
   DECL is either a `VAR_DECL' node or a constant of some sort.
   RELOC indicates whether forming the initial value of DECL requires
   link-time relocations.  */

ATTRIBUTE_UNUSED static section *
x86_64_elf_select_section (tree decl, int reloc,
			   unsigned HOST_WIDE_INT align)
{
  if (ix86_in_large_data_p (decl))
    {
      const char *sname = NULL;
      unsigned int flags = SECTION_WRITE | SECTION_LARGE;
      switch (categorize_decl_for_section (decl, reloc))
	{
	case SECCAT_DATA:
	  sname = ".ldata";
	  break;
	case SECCAT_DATA_REL:
	  sname = ".ldata.rel";
	  break;
	case SECCAT_DATA_REL_LOCAL:
	  sname = ".ldata.rel.local";
	  break;
	case SECCAT_DATA_REL_RO:
	  sname = ".ldata.rel.ro";
	  break;
	case SECCAT_DATA_REL_RO_LOCAL:
	  sname = ".ldata.rel.ro.local";
	  break;
	case SECCAT_BSS:
	  sname = ".lbss";
	  flags |= SECTION_BSS;
	  break;
	case SECCAT_RODATA:
	case SECCAT_RODATA_MERGE_STR:
	case SECCAT_RODATA_MERGE_STR_INIT:
	case SECCAT_RODATA_MERGE_CONST:
	  sname = ".lrodata";
	  flags &= ~SECTION_WRITE;
	  break;
	case SECCAT_SRODATA:
	case SECCAT_SDATA:
	case SECCAT_SBSS:
	  gcc_unreachable ();
	case SECCAT_TEXT:
	case SECCAT_TDATA:
	case SECCAT_TBSS:
	  /* We don't split these for medium model.  Place them into
	     default sections and hope for best.  */
	  break;
	}
      if (sname)
	{
	  /* We might get called with string constants, but get_named_section
	     doesn't like them as they are not DECLs.  Also, we need to set
	     flags in that case.  */
	  if (!DECL_P (decl))
	    return get_section (sname, flags, NULL);
	  return get_named_section (decl, sname, reloc);
	}
    }
  return default_elf_select_section (decl, reloc, align);
}

/* Select a set of attributes for section NAME based on the properties
   of DECL and whether or not RELOC indicates that DECL's initializer
   might contain runtime relocations.  */

static unsigned int ATTRIBUTE_UNUSED
x86_64_elf_section_type_flags (tree decl, const char *name, int reloc)
{
  unsigned int flags = default_section_type_flags (decl, name, reloc);

  if (ix86_in_large_data_p (decl))
    flags |= SECTION_LARGE;

  if (decl == NULL_TREE
      && (strcmp (name, ".ldata.rel.ro") == 0
	  || strcmp (name, ".ldata.rel.ro.local") == 0))
    flags |= SECTION_RELRO;

  if (strcmp (name, ".lbss") == 0
      || strncmp (name, ".lbss.", 5) == 0
      || strncmp (name, ".gnu.linkonce.lb.", 16) == 0)
    flags |= SECTION_BSS;

  return flags;
}

/* Build up a unique section name, expressed as a
   STRING_CST node, and assign it to DECL_SECTION_NAME (decl).
   RELOC indicates whether the initial value of EXP requires
   link-time relocations.  */

static void ATTRIBUTE_UNUSED
x86_64_elf_unique_section (tree decl, int reloc)
{
  if (ix86_in_large_data_p (decl))
    {
      const char *prefix = NULL;
      /* We only need to use .gnu.linkonce if we don't have COMDAT groups.  */
      bool one_only = DECL_COMDAT_GROUP (decl) && !HAVE_COMDAT_GROUP;

      switch (categorize_decl_for_section (decl, reloc))
	{
	case SECCAT_DATA:
	case SECCAT_DATA_REL:
	case SECCAT_DATA_REL_LOCAL:
	case SECCAT_DATA_REL_RO:
	case SECCAT_DATA_REL_RO_LOCAL:
          prefix = one_only ? ".ld" : ".ldata";
	  break;
	case SECCAT_BSS:
          prefix = one_only ? ".lb" : ".lbss";
	  break;
	case SECCAT_RODATA:
	case SECCAT_RODATA_MERGE_STR:
	case SECCAT_RODATA_MERGE_STR_INIT:
	case SECCAT_RODATA_MERGE_CONST:
          prefix = one_only ? ".lr" : ".lrodata";
	  break;
	case SECCAT_SRODATA:
	case SECCAT_SDATA:
	case SECCAT_SBSS:
	  gcc_unreachable ();
	case SECCAT_TEXT:
	case SECCAT_TDATA:
	case SECCAT_TBSS:
	  /* We don't split these for medium model.  Place them into
	     default sections and hope for best.  */
	  break;
	}
      if (prefix)
	{
	  const char *name, *linkonce;
	  char *string;

	  name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
	  name = targetm.strip_name_encoding (name);

	  /* If we're using one_only, then there needs to be a .gnu.linkonce
     	     prefix to the section name.  */
	  linkonce = one_only ? ".gnu.linkonce" : "";

	  string = ACONCAT ((linkonce, prefix, ".", name, NULL));

	  set_decl_section_name (decl, string);
	  return;
	}
    }
  default_unique_section (decl, reloc);
}

#ifdef COMMON_ASM_OP

#ifndef LARGECOMM_SECTION_ASM_OP
#define LARGECOMM_SECTION_ASM_OP "\t.largecomm\t"
#endif

/* This says how to output assembler code to declare an
   uninitialized external linkage data object.

   For medium model x86-64 we need to use LARGECOMM_SECTION_ASM_OP opcode for
   large objects.  */
void
x86_elf_aligned_decl_common (FILE *file, tree decl,
			const char *name, unsigned HOST_WIDE_INT size,
			int align)
{
  if ((ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_MEDIUM_PIC)
      && size > (unsigned int)ix86_section_threshold)
    {
      switch_to_section (get_named_section (decl, ".lbss", 0));
      fputs (LARGECOMM_SECTION_ASM_OP, file);
    }
  else
    fputs (COMMON_ASM_OP, file);
  assemble_name (file, name);
  fprintf (file, "," HOST_WIDE_INT_PRINT_UNSIGNED ",%u\n",
	   size, align / BITS_PER_UNIT);
}
#endif

/* Utility function for targets to use in implementing
   ASM_OUTPUT_ALIGNED_BSS.  */

void
x86_output_aligned_bss (FILE *file, tree decl, const char *name,
		       	unsigned HOST_WIDE_INT size, int align)
{
  if ((ix86_cmodel == CM_MEDIUM || ix86_cmodel == CM_MEDIUM_PIC)
      && size > (unsigned int)ix86_section_threshold)
    switch_to_section (get_named_section (decl, ".lbss", 0));
  else
    switch_to_section (bss_section);
  ASM_OUTPUT_ALIGN (file, floor_log2 (align / BITS_PER_UNIT));
#ifdef ASM_DECLARE_OBJECT_NAME
  last_assemble_variable_decl = decl;
  ASM_DECLARE_OBJECT_NAME (file, name, decl);
#else
  /* Standard thing is just output label for the object.  */
  ASM_OUTPUT_LABEL (file, name);
#endif /* ASM_DECLARE_OBJECT_NAME */
  ASM_OUTPUT_SKIP (file, size ? size : 1);
}

/* Decide whether we must probe the stack before any space allocation
   on this target.  It's essentially TARGET_STACK_PROBE except when
   -fstack-check causes the stack to be already probed differently.  */

bool
ix86_target_stack_probe (void)
{
  /* Do not probe the stack twice if static stack checking is enabled.  */
  if (flag_stack_check == STATIC_BUILTIN_STACK_CHECK)
    return false;

  return TARGET_STACK_PROBE;
}

/* Decide whether we can make a sibling call to a function.  DECL is the
   declaration of the function being targeted by the call and EXP is the
   CALL_EXPR representing the call.  */

static bool
ix86_function_ok_for_sibcall (tree decl, tree exp)
{
  tree type, decl_or_type;
  rtx a, b;
  bool bind_global = decl && !targetm.binds_local_p (decl);

  if (ix86_function_naked (current_function_decl))
    return false;

  /* Sibling call isn't OK if there are no caller-saved registers
     since all registers must be preserved before return.  */
  if (cfun->machine->no_caller_saved_registers)
    return false;

  /* If we are generating position-independent code, we cannot sibcall
     optimize direct calls to global functions, as the PLT requires
     %ebx be live. (Darwin does not have a PLT.)  */
  if (!TARGET_MACHO
      && !TARGET_64BIT
      && flag_pic
      && flag_plt
      && bind_global)
    return false;

  /* If we need to align the outgoing stack, then sibcalling would
     unalign the stack, which may break the called function.  */
  if (ix86_minimum_incoming_stack_boundary (true)
      < PREFERRED_STACK_BOUNDARY)
    return false;

  if (decl)
    {
      decl_or_type = decl;
      type = TREE_TYPE (decl);
    }
  else
    {
      /* We're looking at the CALL_EXPR, we need the type of the function.  */
      type = CALL_EXPR_FN (exp);		/* pointer expression */
      type = TREE_TYPE (type);			/* pointer type */
      type = TREE_TYPE (type);			/* function type */
      decl_or_type = type;
    }

  /* Check that the return value locations are the same.  Like
     if we are returning floats on the 80387 register stack, we cannot
     make a sibcall from a function that doesn't return a float to a
     function that does or, conversely, from a function that does return
     a float to a function that doesn't; the necessary stack adjustment
     would not be executed.  This is also the place we notice
     differences in the return value ABI.  Note that it is ok for one
     of the functions to have void return type as long as the return
     value of the other is passed in a register.  */
  a = ix86_function_value (TREE_TYPE (exp), decl_or_type, false);
  b = ix86_function_value (TREE_TYPE (DECL_RESULT (cfun->decl)),
			   cfun->decl, false);
  if (STACK_REG_P (a) || STACK_REG_P (b))
    {
      if (!rtx_equal_p (a, b))
	return false;
    }
  else if (VOID_TYPE_P (TREE_TYPE (DECL_RESULT (cfun->decl))))
    ;
  else if (!rtx_equal_p (a, b))
    return false;

  if (TARGET_64BIT)
    {
      /* The SYSV ABI has more call-clobbered registers;
	 disallow sibcalls from MS to SYSV.  */
      if (cfun->machine->call_abi == MS_ABI
	  && ix86_function_type_abi (type) == SYSV_ABI)
	return false;
    }
  else
    {
      /* If this call is indirect, we'll need to be able to use a
	 call-clobbered register for the address of the target function.
	 Make sure that all such registers are not used for passing
	 parameters.  Note that DLLIMPORT functions and call to global
	 function via GOT slot are indirect.  */
      if (!decl
	  || (bind_global && flag_pic && !flag_plt)
	  || (TARGET_DLLIMPORT_DECL_ATTRIBUTES && DECL_DLLIMPORT_P (decl))
	  || flag_force_indirect_call)
	{
	  /* Check if regparm >= 3 since arg_reg_available is set to
	     false if regparm == 0.  If regparm is 1 or 2, there is
	     always a call-clobbered register available.

	     ??? The symbol indirect call doesn't need a call-clobbered
	     register.  But we don't know if this is a symbol indirect
	     call or not here.  */
	  if (ix86_function_regparm (type, decl) >= 3
	      && !cfun->machine->arg_reg_available)
	    return false;
	}
    }

  /* Otherwise okay.  That also includes certain types of indirect calls.  */
  return true;
}

/* Handle "cdecl", "stdcall", "fastcall", "regparm", "thiscall",
   and "sseregparm" calling convention attributes;
   arguments as in struct attribute_spec.handler.  */

static tree
ix86_handle_cconv_attribute (tree *node, tree name, tree args, int,
			     bool *no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_TYPE
      && TREE_CODE (*node) != METHOD_TYPE
      && TREE_CODE (*node) != FIELD_DECL
      && TREE_CODE (*node) != TYPE_DECL)
    {
      warning (OPT_Wattributes, "%qE attribute only applies to functions",
	       name);
      *no_add_attrs = true;
      return NULL_TREE;
    }

  /* Can combine regparm with all attributes but fastcall, and thiscall.  */
  if (is_attribute_p ("regparm", name))
    {
      tree cst;

      if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node)))
        {
	  error ("fastcall and regparm attributes are not compatible");
	}

      if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node)))
	{
	  error ("regparam and thiscall attributes are not compatible");
	}

      cst = TREE_VALUE (args);
      if (TREE_CODE (cst) != INTEGER_CST)
	{
	  warning (OPT_Wattributes,
		   "%qE attribute requires an integer constant argument",
		   name);
	  *no_add_attrs = true;
	}
      else if (compare_tree_int (cst, REGPARM_MAX) > 0)
	{
	  warning (OPT_Wattributes, "argument to %qE attribute larger than %d",
		   name, REGPARM_MAX);
	  *no_add_attrs = true;
	}

      return NULL_TREE;
    }

  if (TARGET_64BIT)
    {
      /* Do not warn when emulating the MS ABI.  */
      if ((TREE_CODE (*node) != FUNCTION_TYPE
	   && TREE_CODE (*node) != METHOD_TYPE)
	  || ix86_function_type_abi (*node) != MS_ABI)
	warning (OPT_Wattributes, "%qE attribute ignored",
	         name);
      *no_add_attrs = true;
      return NULL_TREE;
    }

  /* Can combine fastcall with stdcall (redundant) and sseregparm.  */
  if (is_attribute_p ("fastcall", name))
    {
      if (lookup_attribute ("cdecl", TYPE_ATTRIBUTES (*node)))
        {
	  error ("fastcall and cdecl attributes are not compatible");
	}
      if (lookup_attribute ("stdcall", TYPE_ATTRIBUTES (*node)))
        {
	  error ("fastcall and stdcall attributes are not compatible");
	}
      if (lookup_attribute ("regparm", TYPE_ATTRIBUTES (*node)))
        {
	  error ("fastcall and regparm attributes are not compatible");
	}
      if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node)))
	{
	  error ("fastcall and thiscall attributes are not compatible");
	}
    }

  /* Can combine stdcall with fastcall (redundant), regparm and
     sseregparm.  */
  else if (is_attribute_p ("stdcall", name))
    {
      if (lookup_attribute ("cdecl", TYPE_ATTRIBUTES (*node)))
        {
	  error ("stdcall and cdecl attributes are not compatible");
	}
      if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node)))
        {
	  error ("stdcall and fastcall attributes are not compatible");
	}
      if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node)))
	{
	  error ("stdcall and thiscall attributes are not compatible");
	}
    }

  /* Can combine cdecl with regparm and sseregparm.  */
  else if (is_attribute_p ("cdecl", name))
    {
      if (lookup_attribute ("stdcall", TYPE_ATTRIBUTES (*node)))
        {
	  error ("stdcall and cdecl attributes are not compatible");
	}
      if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node)))
        {
	  error ("fastcall and cdecl attributes are not compatible");
	}
      if (lookup_attribute ("thiscall", TYPE_ATTRIBUTES (*node)))
	{
	  error ("cdecl and thiscall attributes are not compatible");
	}
    }
  else if (is_attribute_p ("thiscall", name))
    {
      if (TREE_CODE (*node) != METHOD_TYPE && pedantic)
	warning (OPT_Wattributes, "%qE attribute is used for non-class method",
	         name);
      if (lookup_attribute ("stdcall", TYPE_ATTRIBUTES (*node)))
	{
	  error ("stdcall and thiscall attributes are not compatible");
	}
      if (lookup_attribute ("fastcall", TYPE_ATTRIBUTES (*node)))
	{
	  error ("fastcall and thiscall attributes are not compatible");
	}
      if (lookup_attribute ("cdecl", TYPE_ATTRIBUTES (*node)))
	{
	  error ("cdecl and thiscall attributes are not compatible");
	}
    }

  /* Can combine sseregparm with all attributes.  */

  return NULL_TREE;
}

/* The transactional memory builtins are implicitly regparm or fastcall
   depending on the ABI.  Override the generic do-nothing attribute that
   these builtins were declared with, and replace it with one of the two
   attributes that we expect elsewhere.  */

static tree
ix86_handle_tm_regparm_attribute (tree *node, tree, tree,
				  int flags, bool *no_add_attrs)
{
  tree alt;

  /* In no case do we want to add the placeholder attribute.  */
  *no_add_attrs = true;

  /* The 64-bit ABI is unchanged for transactional memory.  */
  if (TARGET_64BIT)
    return NULL_TREE;

  /* ??? Is there a better way to validate 32-bit windows?  We have
     cfun->machine->call_abi, but that seems to be set only for 64-bit.  */
  if (CHECK_STACK_LIMIT > 0)
    alt = tree_cons (get_identifier ("fastcall"), NULL, NULL);
  else
    {
      alt = tree_cons (NULL, build_int_cst (NULL, 2), NULL);
      alt = tree_cons (get_identifier ("regparm"), alt, NULL);
    }
  decl_attributes (node, alt, flags);

  return NULL_TREE;
}

/* This function determines from TYPE the calling-convention.  */

unsigned int
ix86_get_callcvt (const_tree type)
{
  unsigned int ret = 0;
  bool is_stdarg;
  tree attrs;

  if (TARGET_64BIT)
    return IX86_CALLCVT_CDECL;

  attrs = TYPE_ATTRIBUTES (type);
  if (attrs != NULL_TREE)
    {
      if (lookup_attribute ("cdecl", attrs))
	ret |= IX86_CALLCVT_CDECL;
      else if (lookup_attribute ("stdcall", attrs))
	ret |= IX86_CALLCVT_STDCALL;
      else if (lookup_attribute ("fastcall", attrs))
	ret |= IX86_CALLCVT_FASTCALL;
      else if (lookup_attribute ("thiscall", attrs))
	ret |= IX86_CALLCVT_THISCALL;

      /* Regparam isn't allowed for thiscall and fastcall.  */
      if ((ret & (IX86_CALLCVT_THISCALL | IX86_CALLCVT_FASTCALL)) == 0)
	{
	  if (lookup_attribute ("regparm", attrs))
	    ret |= IX86_CALLCVT_REGPARM;
	  if (lookup_attribute ("sseregparm", attrs))
	    ret |= IX86_CALLCVT_SSEREGPARM;
	}

      if (IX86_BASE_CALLCVT(ret) != 0)
	return ret;
    }

  is_stdarg = stdarg_p (type);
  if (TARGET_RTD && !is_stdarg)
    return IX86_CALLCVT_STDCALL | ret;

  if (ret != 0
      || is_stdarg
      || TREE_CODE (type) != METHOD_TYPE
      || ix86_function_type_abi (type) != MS_ABI)
    return IX86_CALLCVT_CDECL | ret;

  return IX86_CALLCVT_THISCALL;
}

/* Return 0 if the attributes for two types are incompatible, 1 if they
   are compatible, and 2 if they are nearly compatible (which causes a
   warning to be generated).  */

static int
ix86_comp_type_attributes (const_tree type1, const_tree type2)
{
  unsigned int ccvt1, ccvt2;

  if (TREE_CODE (type1) != FUNCTION_TYPE
      && TREE_CODE (type1) != METHOD_TYPE)
    return 1;

  ccvt1 = ix86_get_callcvt (type1);
  ccvt2 = ix86_get_callcvt (type2);
  if (ccvt1 != ccvt2)
    return 0;
  if (ix86_function_regparm (type1, NULL)
      != ix86_function_regparm (type2, NULL))
    return 0;

  return 1;
}

/* Return the regparm value for a function with the indicated TYPE and DECL.
   DECL may be NULL when calling function indirectly
   or considering a libcall.  */

static int
ix86_function_regparm (const_tree type, const_tree decl)
{
  tree attr;
  int regparm;
  unsigned int ccvt;

  if (TARGET_64BIT)
    return (ix86_function_type_abi (type) == SYSV_ABI
	    ? X86_64_REGPARM_MAX : X86_64_MS_REGPARM_MAX);
  ccvt = ix86_get_callcvt (type);
  regparm = ix86_regparm;

  if ((ccvt & IX86_CALLCVT_REGPARM) != 0)
    {
      attr = lookup_attribute ("regparm", TYPE_ATTRIBUTES (type));
      if (attr)
	{
	  regparm = TREE_INT_CST_LOW (TREE_VALUE (TREE_VALUE (attr)));
	  return regparm;
	}
    }
  else if ((ccvt & IX86_CALLCVT_FASTCALL) != 0)
    return 2;
  else if ((ccvt & IX86_CALLCVT_THISCALL) != 0)
    return 1;

  /* Use register calling convention for local functions when possible.  */
  if (decl
      && TREE_CODE (decl) == FUNCTION_DECL)
    {
      cgraph_node *target = cgraph_node::get (decl);
      if (target)
	target = target->function_symbol ();

      /* Caller and callee must agree on the calling convention, so
	 checking here just optimize means that with
	 __attribute__((optimize (...))) caller could use regparm convention
	 and callee not, or vice versa.  Instead look at whether the callee
	 is optimized or not.  */
      if (target && opt_for_fn (target->decl, optimize)
	  && !(profile_flag && !flag_fentry))
	{
	  cgraph_local_info *i = &target->local;
	  if (i && i->local && i->can_change_signature)
	    {
	      int local_regparm, globals = 0, regno;

	      /* Make sure no regparm register is taken by a
		 fixed register variable.  */
	      for (local_regparm = 0; local_regparm < REGPARM_MAX;
		   local_regparm++)
		if (fixed_regs[local_regparm])
		  break;

	      /* We don't want to use regparm(3) for nested functions as
		 these use a static chain pointer in the third argument.  */
	      if (local_regparm == 3 && DECL_STATIC_CHAIN (target->decl))
		local_regparm = 2;

	      /* Save a register for the split stack.  */
	      if (flag_split_stack)
		{
		  if (local_regparm == 3)
		    local_regparm = 2;
		  else if (local_regparm == 2
			   && DECL_STATIC_CHAIN (target->decl))
		    local_regparm = 1;
		}

	      /* Each fixed register usage increases register pressure,
		 so less registers should be used for argument passing.
		 This functionality can be overriden by an explicit
		 regparm value.  */
	      for (regno = AX_REG; regno <= DI_REG; regno++)
		if (fixed_regs[regno])
		  globals++;

	      local_regparm
		= globals < local_regparm ? local_regparm - globals : 0;

	      if (local_regparm > regparm)
		regparm = local_regparm;
	    }
	}
    }

  return regparm;
}

/* Return 1 or 2, if we can pass up to SSE_REGPARM_MAX SFmode (1) and
   DFmode (2) arguments in SSE registers for a function with the
   indicated TYPE and DECL.  DECL may be NULL when calling function
   indirectly or considering a libcall.  Return -1 if any FP parameter
   should be rejected by error.  This is used in siutation we imply SSE
   calling convetion but the function is called from another function with
   SSE disabled. Otherwise return 0.  */

static int
ix86_function_sseregparm (const_tree type, const_tree decl, bool warn)
{
  gcc_assert (!TARGET_64BIT);

  /* Use SSE registers to pass SFmode and DFmode arguments if requested
     by the sseregparm attribute.  */
  if (TARGET_SSEREGPARM
      || (type && lookup_attribute ("sseregparm", TYPE_ATTRIBUTES (type))))
    {
      if (!TARGET_SSE)
	{
	  if (warn)
	    {
	      if (decl)
		error ("calling %qD with attribute sseregparm without "
		       "SSE/SSE2 enabled", decl);
	      else
		error ("calling %qT with attribute sseregparm without "
		       "SSE/SSE2 enabled", type);
	    }
	  return 0;
	}

      return 2;
    }

  if (!decl)
    return 0;

  cgraph_node *target = cgraph_node::get (decl);
  if (target)
    target = target->function_symbol ();

  /* For local functions, pass up to SSE_REGPARM_MAX SFmode
     (and DFmode for SSE2) arguments in SSE registers.  */
  if (target
      /* TARGET_SSE_MATH */
      && (target_opts_for_fn (target->decl)->x_ix86_fpmath & FPMATH_SSE)
      && opt_for_fn (target->decl, optimize)
      && !(profile_flag && !flag_fentry))
    {
      cgraph_local_info *i = &target->local;
      if (i && i->local && i->can_change_signature)
	{
	  /* Refuse to produce wrong code when local function with SSE enabled
	     is called from SSE disabled function.
	     FIXME: We need a way to detect these cases cross-ltrans partition
	     and avoid using SSE calling conventions on local functions called
	     from function with SSE disabled.  For now at least delay the
	     warning until we know we are going to produce wrong code.
	     See PR66047  */
	  if (!TARGET_SSE && warn)
	    return -1;
	  return TARGET_SSE2_P (target_opts_for_fn (target->decl)
				->x_ix86_isa_flags) ? 2 : 1;
	}
    }

  return 0;
}

/* Return true if EAX is live at the start of the function.  Used by
   ix86_expand_prologue to determine if we need special help before
   calling allocate_stack_worker.  */

static bool
ix86_eax_live_at_start_p (void)
{
  /* Cheat.  Don't bother working forward from ix86_function_regparm
     to the function type to whether an actual argument is located in
     eax.  Instead just look at cfg info, which is still close enough
     to correct at this point.  This gives false positives for broken
     functions that might use uninitialized data that happens to be
     allocated in eax, but who cares?  */
  return REGNO_REG_SET_P (df_get_live_out (ENTRY_BLOCK_PTR_FOR_FN (cfun)), 0);
}

static bool
ix86_keep_aggregate_return_pointer (tree fntype)
{
  tree attr;

  if (!TARGET_64BIT)
    {
      attr = lookup_attribute ("callee_pop_aggregate_return",
			       TYPE_ATTRIBUTES (fntype));
      if (attr)
	return (TREE_INT_CST_LOW (TREE_VALUE (TREE_VALUE (attr))) == 0);

      /* For 32-bit MS-ABI the default is to keep aggregate
         return pointer.  */
      if (ix86_function_type_abi (fntype) == MS_ABI)
	return true;
    }
  return KEEP_AGGREGATE_RETURN_POINTER != 0;
}

/* Value is the number of bytes of arguments automatically
   popped when returning from a subroutine call.
   FUNDECL is the declaration node of the function (as a tree),
   FUNTYPE is the data type of the function (as a tree),
   or for a library call it is an identifier node for the subroutine name.
   SIZE is the number of bytes of arguments passed on the stack.

   On the 80386, the RTD insn may be used to pop them if the number
     of args is fixed, but if the number is variable then the caller
     must pop them all.  RTD can't be used for library calls now
     because the library is compiled with the Unix compiler.
   Use of RTD is a selectable option, since it is incompatible with
   standard Unix calling sequences.  If the option is not selected,
   the caller must always pop the args.

   The attribute stdcall is equivalent to RTD on a per module basis.  */

static poly_int64
ix86_return_pops_args (tree fundecl, tree funtype, poly_int64 size)
{
  unsigned int ccvt;

  /* None of the 64-bit ABIs pop arguments.  */
  if (TARGET_64BIT)
    return 0;

  ccvt = ix86_get_callcvt (funtype);

  if ((ccvt & (IX86_CALLCVT_STDCALL | IX86_CALLCVT_FASTCALL
	       | IX86_CALLCVT_THISCALL)) != 0
      && ! stdarg_p (funtype))
    return size;

  /* Lose any fake structure return argument if it is passed on the stack.  */
  if (aggregate_value_p (TREE_TYPE (funtype), fundecl)
      && !ix86_keep_aggregate_return_pointer (funtype))
    {
      int nregs = ix86_function_regparm (funtype, fundecl);
      if (nregs == 0)
	return GET_MODE_SIZE (Pmode);
    }

  return 0;
}

/* Implement the TARGET_LEGITIMATE_COMBINED_INSN hook.  */

static bool
ix86_legitimate_combined_insn (rtx_insn *insn)
{
  int i;

  /* Check operand constraints in case hard registers were propagated
     into insn pattern.  This check prevents combine pass from
     generating insn patterns with invalid hard register operands.
     These invalid insns can eventually confuse reload to error out
     with a spill failure.  See also PRs 46829 and 46843.  */

  gcc_assert (INSN_CODE (insn) >= 0);

  extract_insn (insn);
  preprocess_constraints (insn);

  int n_operands = recog_data.n_operands;
  int n_alternatives = recog_data.n_alternatives;
  for (i = 0; i < n_operands; i++)
    {
      rtx op = recog_data.operand[i];
      machine_mode mode = GET_MODE (op);
      const operand_alternative *op_alt;
      int offset = 0;
      bool win;
      int j;

      /* A unary operator may be accepted by the predicate, but it
	 is irrelevant for matching constraints.  */
      if (UNARY_P (op))
	op = XEXP (op, 0);

      if (SUBREG_P (op))
	{
	  if (REG_P (SUBREG_REG (op))
	      && REGNO (SUBREG_REG (op)) < FIRST_PSEUDO_REGISTER)
	    offset = subreg_regno_offset (REGNO (SUBREG_REG (op)),
					  GET_MODE (SUBREG_REG (op)),
					  SUBREG_BYTE (op),
					  GET_MODE (op));
	  op = SUBREG_REG (op);
	}

      if (!(REG_P (op) && HARD_REGISTER_P (op)))
	continue;

      op_alt = recog_op_alt;

      /* Operand has no constraints, anything is OK.  */
      win = !n_alternatives;

      alternative_mask preferred = get_preferred_alternatives (insn);
      for (j = 0; j < n_alternatives; j++, op_alt += n_operands)
	{
	  if (!TEST_BIT (preferred, j))
	    continue;
	  if (op_alt[i].anything_ok
	      || (op_alt[i].matches != -1
		  && operands_match_p
		  (recog_data.operand[i],
		   recog_data.operand[op_alt[i].matches]))
	      || reg_fits_class_p (op, op_alt[i].cl, offset, mode))
	    {
	      win = true;
	      break;
	    }
	}

      if (!win)
	return false;
    }

  return true;
}

/* Implement the TARGET_ASAN_SHADOW_OFFSET hook.  */

static unsigned HOST_WIDE_INT
ix86_asan_shadow_offset (void)
{
  return TARGET_LP64 ? (TARGET_MACHO ? (HOST_WIDE_INT_1 << 44)
				     : HOST_WIDE_INT_C (0x7fff8000))
		     : (HOST_WIDE_INT_1 << 29);
}

/* Argument support functions.  */

/* Return true when register may be used to pass function parameters.  */
bool
ix86_function_arg_regno_p (int regno)
{
  int i;
  enum calling_abi call_abi;
  const int *parm_regs;

  if (!TARGET_64BIT)
    {
      if (TARGET_MACHO)
        return (regno < REGPARM_MAX
                || (TARGET_SSE && SSE_REGNO_P (regno) && !fixed_regs[regno]));
      else
        return (regno < REGPARM_MAX
	        || (TARGET_MMX && MMX_REGNO_P (regno)
	  	    && (regno < FIRST_MMX_REG + MMX_REGPARM_MAX))
	        || (TARGET_SSE && SSE_REGNO_P (regno)
		    && (regno < FIRST_SSE_REG + SSE_REGPARM_MAX)));
    }

  if (TARGET_SSE && SSE_REGNO_P (regno)
      && (regno < FIRST_SSE_REG + SSE_REGPARM_MAX))
    return true;

  /* TODO: The function should depend on current function ABI but
     builtins.c would need updating then. Therefore we use the
     default ABI.  */
  call_abi = ix86_cfun_abi ();

  /* RAX is used as hidden argument to va_arg functions.  */
  if (call_abi == SYSV_ABI && regno == AX_REG)
    return true;

  if (call_abi == MS_ABI)
    parm_regs = x86_64_ms_abi_int_parameter_registers;
  else
    parm_regs = x86_64_int_parameter_registers;

  for (i = 0; i < (call_abi == MS_ABI
		   ? X86_64_MS_REGPARM_MAX : X86_64_REGPARM_MAX); i++)
    if (regno == parm_regs[i])
      return true;
  return false;
}

/* Return if we do not know how to pass TYPE solely in registers.  */

static bool
ix86_must_pass_in_stack (machine_mode mode, const_tree type)
{
  if (must_pass_in_stack_var_size_or_pad (mode, type))
    return true;

  /* For 32-bit, we want TImode aggregates to go on the stack.  But watch out!
     The layout_type routine is crafty and tries to trick us into passing
     currently unsupported vector types on the stack by using TImode.  */
  return (!TARGET_64BIT && mode == TImode
	  && type && TREE_CODE (type) != VECTOR_TYPE);
}

/* It returns the size, in bytes, of the area reserved for arguments passed
   in registers for the function represented by fndecl dependent to the used
   abi format.  */
int
ix86_reg_parm_stack_space (const_tree fndecl)
{
  enum calling_abi call_abi = SYSV_ABI;
  if (fndecl != NULL_TREE && TREE_CODE (fndecl) == FUNCTION_DECL)
    call_abi = ix86_function_abi (fndecl);
  else
    call_abi = ix86_function_type_abi (fndecl);
  if (TARGET_64BIT && call_abi == MS_ABI)
    return 32;
  return 0;
}

/* We add this as a workaround in order to use libc_has_function
   hook in i386.md.  */
bool
ix86_libc_has_function (enum function_class fn_class)
{
  return targetm.libc_has_function (fn_class);
}

/* Returns value SYSV_ABI, MS_ABI dependent on fntype,
   specifying the call abi used.  */
enum calling_abi
ix86_function_type_abi (const_tree fntype)
{
  enum calling_abi abi = ix86_abi;

  if (fntype == NULL_TREE || TYPE_ATTRIBUTES (fntype) == NULL_TREE)
    return abi;

  if (abi == SYSV_ABI
      && lookup_attribute ("ms_abi", TYPE_ATTRIBUTES (fntype)))
    {
      static int warned;
      if (TARGET_X32 && !warned)
	{
	  error ("X32 does not support ms_abi attribute");
	  warned = 1;
	}

      abi = MS_ABI;
    }
  else if (abi == MS_ABI
	   && lookup_attribute ("sysv_abi", TYPE_ATTRIBUTES (fntype)))
    abi = SYSV_ABI;

  return abi;
}

static enum calling_abi
ix86_function_abi (const_tree fndecl)
{
  return fndecl ? ix86_function_type_abi (TREE_TYPE (fndecl)) : ix86_abi;
}

/* Returns value SYSV_ABI, MS_ABI dependent on cfun,
   specifying the call abi used.  */
enum calling_abi
ix86_cfun_abi (void)
{
  return cfun ? cfun->machine->call_abi : ix86_abi;
}

static bool
ix86_function_ms_hook_prologue (const_tree fn)
{
  if (fn && lookup_attribute ("ms_hook_prologue", DECL_ATTRIBUTES (fn)))
    {
      if (decl_function_context (fn) != NULL_TREE)
	error_at (DECL_SOURCE_LOCATION (fn),
		  "ms_hook_prologue is not compatible with nested function");
      else
        return true;
    }
  return false;
}

static bool
ix86_function_naked (const_tree fn)
{
  if (fn && lookup_attribute ("naked", DECL_ATTRIBUTES (fn)))
    return true;

  return false;
}

/* Write the extra assembler code needed to declare a function properly.  */

void
ix86_asm_output_function_label (FILE *asm_out_file, const char *fname,
				tree decl)
{
  bool is_ms_hook = ix86_function_ms_hook_prologue (decl);

  if (is_ms_hook)
    {
      int i, filler_count = (TARGET_64BIT ? 32 : 16);
      unsigned int filler_cc = 0xcccccccc;

      for (i = 0; i < filler_count; i += 4)
        fprintf (asm_out_file, ASM_LONG " %#x\n", filler_cc);
    }

#ifdef SUBTARGET_ASM_UNWIND_INIT
  SUBTARGET_ASM_UNWIND_INIT (asm_out_file);
#endif

  ASM_OUTPUT_LABEL (asm_out_file, fname);

  /* Output magic byte marker, if hot-patch attribute is set.  */
  if (is_ms_hook)
    {
      if (TARGET_64BIT)
	{
	  /* leaq [%rsp + 0], %rsp  */
	  fputs (ASM_BYTE "0x48, 0x8d, 0xa4, 0x24, 0x00, 0x00, 0x00, 0x00\n",
		 asm_out_file);
	}
      else
	{
          /* movl.s %edi, %edi
	     push   %ebp
	     movl.s %esp, %ebp */
	  fputs (ASM_BYTE "0x8b, 0xff, 0x55, 0x8b, 0xec\n", asm_out_file);
	}
    }
}

/* Implementation of call abi switching target hook. Specific to FNDECL
   the specific call register sets are set.  See also
   ix86_conditional_register_usage for more details.  */
void
ix86_call_abi_override (const_tree fndecl)
{
  cfun->machine->call_abi = ix86_function_abi (fndecl);
}

/* Return 1 if pseudo register should be created and used to hold
   GOT address for PIC code.  */
bool
ix86_use_pseudo_pic_reg (void)
{
  if ((TARGET_64BIT
       && (ix86_cmodel == CM_SMALL_PIC
	   || TARGET_PECOFF))
      || !flag_pic)
    return false;
  return true;
}

/* Initialize large model PIC register.  */

static void
ix86_init_large_pic_reg (unsigned int tmp_regno)
{
  rtx_code_label *label;
  rtx tmp_reg;

  gcc_assert (Pmode == DImode);
  label = gen_label_rtx ();
  emit_label (label);
  LABEL_PRESERVE_P (label) = 1;
  tmp_reg = gen_rtx_REG (Pmode, tmp_regno);
  gcc_assert (REGNO (pic_offset_table_rtx) != tmp_regno);
  emit_insn (gen_set_rip_rex64 (pic_offset_table_rtx,
				label));
  emit_insn (gen_set_got_offset_rex64 (tmp_reg, label));
  emit_insn (ix86_gen_add3 (pic_offset_table_rtx,
			    pic_offset_table_rtx, tmp_reg));
  const char *name = LABEL_NAME (label);
  PUT_CODE (label, NOTE);
  NOTE_KIND (label) = NOTE_INSN_DELETED_LABEL;
  NOTE_DELETED_LABEL_NAME (label) = name;
}

/* Create and initialize PIC register if required.  */
static void
ix86_init_pic_reg (void)
{
  edge entry_edge;
  rtx_insn *seq;

  if (!ix86_use_pseudo_pic_reg ())
    return;

  start_sequence ();

  if (TARGET_64BIT)
    {
      if (ix86_cmodel == CM_LARGE_PIC)
	ix86_init_large_pic_reg (R11_REG);
      else
	emit_insn (gen_set_got_rex64 (pic_offset_table_rtx));
    }
  else
    {
      /*  If there is future mcount call in the function it is more profitable
	  to emit SET_GOT into ABI defined REAL_PIC_OFFSET_TABLE_REGNUM.  */
      rtx reg = crtl->profile
		? gen_rtx_REG (Pmode, REAL_PIC_OFFSET_TABLE_REGNUM)
		: pic_offset_table_rtx;
      rtx_insn *insn = emit_insn (gen_set_got (reg));
      RTX_FRAME_RELATED_P (insn) = 1;
      if (crtl->profile)
        emit_move_insn (pic_offset_table_rtx, reg);
      add_reg_note (insn, REG_CFA_FLUSH_QUEUE, NULL_RTX);
    }

  seq = get_insns ();
  end_sequence ();

  entry_edge = single_succ_edge (ENTRY_BLOCK_PTR_FOR_FN (cfun));
  insert_insn_on_edge (seq, entry_edge);
  commit_one_edge_insertion (entry_edge);
}

/* Initialize a variable CUM of type CUMULATIVE_ARGS
   for a call to a function whose data type is FNTYPE.
   For a library call, FNTYPE is 0.  */

void
init_cumulative_args (CUMULATIVE_ARGS *cum,  /* Argument info to initialize */
		      tree fntype,	/* tree ptr for function decl */
		      rtx libname,	/* SYMBOL_REF of library name or 0 */
		      tree fndecl,
		      int caller)
{
  struct cgraph_local_info *i = NULL;
  struct cgraph_node *target = NULL;

  memset (cum, 0, sizeof (*cum));

  if (fndecl)
    {
      target = cgraph_node::get (fndecl);
      if (target)
	{
	  target = target->function_symbol ();
	  i = cgraph_node::local_info (target->decl);
	  cum->call_abi = ix86_function_abi (target->decl);
	}
      else
	cum->call_abi = ix86_function_abi (fndecl);
    }
  else
    cum->call_abi = ix86_function_type_abi (fntype);

  cum->caller = caller;

  /* Set up the number of registers to use for passing arguments.  */
  cum->nregs = ix86_regparm;
  if (TARGET_64BIT)
    {
      cum->nregs = (cum->call_abi == SYSV_ABI
                   ? X86_64_REGPARM_MAX
                   : X86_64_MS_REGPARM_MAX);
    }
  if (TARGET_SSE)
    {
      cum->sse_nregs = SSE_REGPARM_MAX;
      if (TARGET_64BIT)
        {
          cum->sse_nregs = (cum->call_abi == SYSV_ABI
                           ? X86_64_SSE_REGPARM_MAX
                           : X86_64_MS_SSE_REGPARM_MAX);
        }
    }
  if (TARGET_MMX)
    cum->mmx_nregs = MMX_REGPARM_MAX;
  cum->warn_avx512f = true;
  cum->warn_avx = true;
  cum->warn_sse = true;
  cum->warn_mmx = true;

  /* Because type might mismatch in between caller and callee, we need to
     use actual type of function for local calls.
     FIXME: cgraph_analyze can be told to actually record if function uses
     va_start so for local functions maybe_vaarg can be made aggressive
     helping K&R code.
     FIXME: once typesytem is fixed, we won't need this code anymore.  */
  if (i && i->local && i->can_change_signature)
    fntype = TREE_TYPE (target->decl);
  cum->stdarg = stdarg_p (fntype);
  cum->maybe_vaarg = (fntype
		      ? (!prototype_p (fntype) || stdarg_p (fntype))
		      : !libname);

  cum->decl = fndecl;

  cum->warn_empty = !warn_abi || cum->stdarg;
  if (!cum->warn_empty && fntype)
    {
      function_args_iterator iter;
      tree argtype;
      bool seen_empty_type = false;
      FOREACH_FUNCTION_ARGS (fntype, argtype, iter)
	{
	  if (argtype == error_mark_node || VOID_TYPE_P (argtype))
	    break;
	  if (TYPE_EMPTY_P (argtype))
	    seen_empty_type = true;
	  else if (seen_empty_type)
	    {
	      cum->warn_empty = true;
	      break;
	    }
	}
    }

  if (!TARGET_64BIT)
    {
      /* If there are variable arguments, then we won't pass anything
         in registers in 32-bit mode. */
      if (stdarg_p (fntype))
	{
	  cum->nregs = 0;
	  /* Since in 32-bit, variable arguments are always passed on
	     stack, there is scratch register available for indirect
	     sibcall.  */
	  cfun->machine->arg_reg_available = true;
	  cum->sse_nregs = 0;
	  cum->mmx_nregs = 0;
	  cum->warn_avx512f = false;
	  cum->warn_avx = false;
	  cum->warn_sse = false;
	  cum->warn_mmx = false;
	  return;
	}

      /* Use ecx and edx registers if function has fastcall attribute,
	 else look for regparm information.  */
      if (fntype)
	{
	  unsigned int ccvt = ix86_get_callcvt (fntype);
	  if ((ccvt & IX86_CALLCVT_THISCALL) != 0)
	    {
	      cum->nregs = 1;
	      cum->fastcall = 1; /* Same first register as in fastcall.  */
	    }
	  else if ((ccvt & IX86_CALLCVT_FASTCALL) != 0)
	    {
	      cum->nregs = 2;
	      cum->fastcall = 1;
	    }
	  else
	    cum->nregs = ix86_function_regparm (fntype, fndecl);
	}

      /* Set up the number of SSE registers used for passing SFmode
	 and DFmode arguments.  Warn for mismatching ABI.  */
      cum->float_in_sse = ix86_function_sseregparm (fntype, fndecl, true);
    }

  cfun->machine->arg_reg_available = (cum->nregs > 0);
}

/* Return the "natural" mode for TYPE.  In most cases, this is just TYPE_MODE.
   But in the case of vector types, it is some vector mode.

   When we have only some of our vector isa extensions enabled, then there
   are some modes for which vector_mode_supported_p is false.  For these
   modes, the generic vector support in gcc will choose some non-vector mode
   in order to implement the type.  By computing the natural mode, we'll
   select the proper ABI location for the operand and not depend on whatever
   the middle-end decides to do with these vector types.

   The midde-end can't deal with the vector types > 16 bytes.  In this
   case, we return the original mode and warn ABI change if CUM isn't
   NULL. 

   If INT_RETURN is true, warn ABI change if the vector mode isn't
   available for function return value.  */

static machine_mode
type_natural_mode (const_tree type, const CUMULATIVE_ARGS *cum,
		   bool in_return)
{
  machine_mode mode = TYPE_MODE (type);

  if (TREE_CODE (type) == VECTOR_TYPE && !VECTOR_MODE_P (mode))
    {
      HOST_WIDE_INT size = int_size_in_bytes (type);
      if ((size == 8 || size == 16 || size == 32 || size == 64)
	  /* ??? Generic code allows us to create width 1 vectors.  Ignore.  */
	  && TYPE_VECTOR_SUBPARTS (type) > 1)
	{
	  machine_mode innermode = TYPE_MODE (TREE_TYPE (type));

	  /* There are no XFmode vector modes.  */
	  if (innermode == XFmode)
	    return mode;

	  if (TREE_CODE (TREE_TYPE (type)) == REAL_TYPE)
	    mode = MIN_MODE_VECTOR_FLOAT;
	  else
	    mode = MIN_MODE_VECTOR_INT;

	  /* Get the mode which has this inner mode and number of units.  */
	  FOR_EACH_MODE_FROM (mode, mode)
	    if (GET_MODE_NUNITS (mode) == TYPE_VECTOR_SUBPARTS (type)
		&& GET_MODE_INNER (mode) == innermode)
	      {
		if (size == 64 && !TARGET_AVX512F && !TARGET_IAMCU)
		  {
		    static bool warnedavx512f;
		    static bool warnedavx512f_ret;

		    if (cum && cum->warn_avx512f && !warnedavx512f)
		      {
			if (warning (OPT_Wpsabi, "AVX512F vector argument "
				     "without AVX512F enabled changes the ABI"))
			  warnedavx512f = true;
		      }
		    else if (in_return && !warnedavx512f_ret)
		      {
			if (warning (OPT_Wpsabi, "AVX512F vector return "
				     "without AVX512F enabled changes the ABI"))
			  warnedavx512f_ret = true;
		      }

		    return TYPE_MODE (type);
		  }
		else if (size == 32 && !TARGET_AVX && !TARGET_IAMCU)
		  {
		    static bool warnedavx;
		    static bool warnedavx_ret;

		    if (cum && cum->warn_avx && !warnedavx)
		      {
			if (warning (OPT_Wpsabi, "AVX vector argument "
				     "without AVX enabled changes the ABI"))
			  warnedavx = true;
		      }
		    else if (in_return && !warnedavx_ret)
		      {
			if (warning (OPT_Wpsabi, "AVX vector return "
				     "without AVX enabled changes the ABI"))
			  warnedavx_ret = true;
		      }

		    return TYPE_MODE (type);
		  }
		else if (((size == 8 && TARGET_64BIT) || size == 16)
			 && !TARGET_SSE
			 && !TARGET_IAMCU)
		  {
		    static bool warnedsse;
		    static bool warnedsse_ret;

		    if (cum && cum->warn_sse && !warnedsse)
		      {
			if (warning (OPT_Wpsabi, "SSE vector argument "
				     "without SSE enabled changes the ABI"))
			  warnedsse = true;
		      }
		    else if (!TARGET_64BIT && in_return && !warnedsse_ret)
		      {
			if (warning (OPT_Wpsabi, "SSE vector return "
				     "without SSE enabled changes the ABI"))
			  warnedsse_ret = true;
		      }
		  }
		else if ((size == 8 && !TARGET_64BIT)
			 && (!cfun
			     || cfun->machine->func_type == TYPE_NORMAL)
			 && !TARGET_MMX
			 && !TARGET_IAMCU)
		  {
		    static bool warnedmmx;
		    static bool warnedmmx_ret;

		    if (cum && cum->warn_mmx && !warnedmmx)
		      {
			if (warning (OPT_Wpsabi, "MMX vector argument "
				     "without MMX enabled changes the ABI"))
			  warnedmmx = true;
		      }
		    else if (in_return && !warnedmmx_ret)
		      {
			if (warning (OPT_Wpsabi, "MMX vector return "
				     "without MMX enabled changes the ABI"))
			  warnedmmx_ret = true;
		      }
		  }
		return mode;
	      }

	  gcc_unreachable ();
	}
    }

  return mode;
}

/* We want to pass a value in REGNO whose "natural" mode is MODE.  However,
   this may not agree with the mode that the type system has chosen for the
   register, which is ORIG_MODE.  If ORIG_MODE is not BLKmode, then we can
   go ahead and use it.  Otherwise we have to build a PARALLEL instead.  */

static rtx
gen_reg_or_parallel (machine_mode mode, machine_mode orig_mode,
		     unsigned int regno)
{
  rtx tmp;

  if (orig_mode != BLKmode)
    tmp = gen_rtx_REG (orig_mode, regno);
  else
    {
      tmp = gen_rtx_REG (mode, regno);
      tmp = gen_rtx_EXPR_LIST (VOIDmode, tmp, const0_rtx);
      tmp = gen_rtx_PARALLEL (orig_mode, gen_rtvec (1, tmp));
    }

  return tmp;
}

/* x86-64 register passing implementation.  See x86-64 ABI for details.  Goal
   of this code is to classify each 8bytes of incoming argument by the register
   class and assign registers accordingly.  */

/* Return the union class of CLASS1 and CLASS2.
   See the x86-64 PS ABI for details.  */

static enum x86_64_reg_class
merge_classes (enum x86_64_reg_class class1, enum x86_64_reg_class class2)
{
  /* Rule #1: If both classes are equal, this is the resulting class.  */
  if (class1 == class2)
    return class1;

  /* Rule #2: If one of the classes is NO_CLASS, the resulting class is
     the other class.  */
  if (class1 == X86_64_NO_CLASS)
    return class2;
  if (class2 == X86_64_NO_CLASS)
    return class1;

  /* Rule #3: If one of the classes is MEMORY, the result is MEMORY.  */
  if (class1 == X86_64_MEMORY_CLASS || class2 == X86_64_MEMORY_CLASS)
    return X86_64_MEMORY_CLASS;

  /* Rule #4: If one of the classes is INTEGER, the result is INTEGER.  */
  if ((class1 == X86_64_INTEGERSI_CLASS && class2 == X86_64_SSESF_CLASS)
      || (class2 == X86_64_INTEGERSI_CLASS && class1 == X86_64_SSESF_CLASS))
    return X86_64_INTEGERSI_CLASS;
  if (class1 == X86_64_INTEGER_CLASS || class1 == X86_64_INTEGERSI_CLASS
      || class2 == X86_64_INTEGER_CLASS || class2 == X86_64_INTEGERSI_CLASS)
    return X86_64_INTEGER_CLASS;

  /* Rule #5: If one of the classes is X87, X87UP, or COMPLEX_X87 class,
     MEMORY is used.  */
  if (class1 == X86_64_X87_CLASS
      || class1 == X86_64_X87UP_CLASS
      || class1 == X86_64_COMPLEX_X87_CLASS
      || class2 == X86_64_X87_CLASS
      || class2 == X86_64_X87UP_CLASS
      || class2 == X86_64_COMPLEX_X87_CLASS)
    return X86_64_MEMORY_CLASS;

  /* Rule #6: Otherwise class SSE is used.  */
  return X86_64_SSE_CLASS;
}

/* Classify the argument of type TYPE and mode MODE.
   CLASSES will be filled by the register class used to pass each word
   of the operand.  The number of words is returned.  In case the parameter
   should be passed in memory, 0 is returned. As a special case for zero
   sized containers, classes[0] will be NO_CLASS and 1 is returned.

   BIT_OFFSET is used internally for handling records and specifies offset
   of the offset in bits modulo 512 to avoid overflow cases.

   See the x86-64 PS ABI for details.
*/

static int
classify_argument (machine_mode mode, const_tree type,
		   enum x86_64_reg_class classes[MAX_CLASSES], int bit_offset)
{
  HOST_WIDE_INT bytes
    = mode == BLKmode ? int_size_in_bytes (type) : (int) GET_MODE_SIZE (mode);
  int words = CEIL (bytes + (bit_offset % 64) / 8, UNITS_PER_WORD);

  /* Variable sized entities are always passed/returned in memory.  */
  if (bytes < 0)
    return 0;

  if (mode != VOIDmode
      && targetm.calls.must_pass_in_stack (mode, type))
    return 0;

  if (type && AGGREGATE_TYPE_P (type))
    {
      int i;
      tree field;
      enum x86_64_reg_class subclasses[MAX_CLASSES];

      /* On x86-64 we pass structures larger than 64 bytes on the stack.  */
      if (bytes > 64)
	return 0;

      for (i = 0; i < words; i++)
	classes[i] = X86_64_NO_CLASS;

      /* Zero sized arrays or structures are NO_CLASS.  We return 0 to
	 signalize memory class, so handle it as special case.  */
      if (!words)
	{
	  classes[0] = X86_64_NO_CLASS;
	  return 1;
	}

      /* Classify each field of record and merge classes.  */
      switch (TREE_CODE (type))
	{
	case RECORD_TYPE:
	  /* And now merge the fields of structure.  */
	  for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
	    {
	      if (TREE_CODE (field) == FIELD_DECL)
		{
		  int num;

		  if (TREE_TYPE (field) == error_mark_node)
		    continue;

		  /* Bitfields are always classified as integer.  Handle them
		     early, since later code would consider them to be
		     misaligned integers.  */
		  if (DECL_BIT_FIELD (field))
		    {
		      for (i = (int_bit_position (field)
				+ (bit_offset % 64)) / 8 / 8;
			   i < ((int_bit_position (field) + (bit_offset % 64))
			        + tree_to_shwi (DECL_SIZE (field))
				+ 63) / 8 / 8; i++)
			classes[i]
			  = merge_classes (X86_64_INTEGER_CLASS, classes[i]);
		    }
		  else
		    {
		      int pos;

		      type = TREE_TYPE (field);

		      /* Flexible array member is ignored.  */
		      if (TYPE_MODE (type) == BLKmode
			  && TREE_CODE (type) == ARRAY_TYPE
			  && TYPE_SIZE (type) == NULL_TREE
			  && TYPE_DOMAIN (type) != NULL_TREE
			  && (TYPE_MAX_VALUE (TYPE_DOMAIN (type))
			      == NULL_TREE))
			{
			  static bool warned;

			  if (!warned && warn_psabi)
			    {
			      warned = true;
			      inform (input_location,
				      "the ABI of passing struct with"
				      " a flexible array member has"
				      " changed in GCC 4.4");
			    }
			  continue;
			}
		      num = classify_argument (TYPE_MODE (type), type,
					       subclasses,
					       (int_bit_position (field)
						+ bit_offset) % 512);
		      if (!num)
			return 0;
		      pos = (int_bit_position (field)
			     + (bit_offset % 64)) / 8 / 8;
		      for (i = 0; i < num && (i + pos) < words; i++)
			classes[i + pos]
			  = merge_classes (subclasses[i], classes[i + pos]);
		    }
		}
	    }
	  break;

	case ARRAY_TYPE:
	  /* Arrays are handled as small records.  */
	  {
	    int num;
	    num = classify_argument (TYPE_MODE (TREE_TYPE (type)),
				     TREE_TYPE (type), subclasses, bit_offset);
	    if (!num)
	      return 0;

	    /* The partial classes are now full classes.  */
	    if (subclasses[0] == X86_64_SSESF_CLASS && bytes != 4)
	      subclasses[0] = X86_64_SSE_CLASS;
	    if (subclasses[0] == X86_64_INTEGERSI_CLASS
		&& !((bit_offset % 64) == 0 && bytes == 4))
	      subclasses[0] = X86_64_INTEGER_CLASS;

	    for (i = 0; i < words; i++)
	      classes[i] = subclasses[i % num];

	    break;
	  }
	case UNION_TYPE:
	case QUAL_UNION_TYPE:
	  /* Unions are similar to RECORD_TYPE but offset is always 0.
	     */
	  for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
	    {
	      if (TREE_CODE (field) == FIELD_DECL)
		{
		  int num;

		  if (TREE_TYPE (field) == error_mark_node)
		    continue;

		  num = classify_argument (TYPE_MODE (TREE_TYPE (field)),
					   TREE_TYPE (field), subclasses,
					   bit_offset);
		  if (!num)
		    return 0;
		  for (i = 0; i < num && i < words; i++)
		    classes[i] = merge_classes (subclasses[i], classes[i]);
		}
	    }
	  break;

	default:
	  gcc_unreachable ();
	}

      if (words > 2)
	{
	  /* When size > 16 bytes, if the first one isn't
	     X86_64_SSE_CLASS or any other ones aren't
	     X86_64_SSEUP_CLASS, everything should be passed in
	     memory.  */
	  if (classes[0] != X86_64_SSE_CLASS)
	      return 0;

	  for (i = 1; i < words; i++)
	    if (classes[i] != X86_64_SSEUP_CLASS)
	      return 0;
	}

      /* Final merger cleanup.  */
      for (i = 0; i < words; i++)
	{
	  /* If one class is MEMORY, everything should be passed in
	     memory.  */
	  if (classes[i] == X86_64_MEMORY_CLASS)
	    return 0;

	  /* The X86_64_SSEUP_CLASS should be always preceded by
	     X86_64_SSE_CLASS or X86_64_SSEUP_CLASS.  */
	  if (classes[i] == X86_64_SSEUP_CLASS
	      && classes[i - 1] != X86_64_SSE_CLASS
	      && classes[i - 1] != X86_64_SSEUP_CLASS)
	    {
	      /* The first one should never be X86_64_SSEUP_CLASS.  */
	      gcc_assert (i != 0);
	      classes[i] = X86_64_SSE_CLASS;
	    }

	  /*  If X86_64_X87UP_CLASS isn't preceded by X86_64_X87_CLASS,
	       everything should be passed in memory.  */
	  if (classes[i] == X86_64_X87UP_CLASS
	      && (classes[i - 1] != X86_64_X87_CLASS))
	    {
	      static bool warned;

	      /* The first one should never be X86_64_X87UP_CLASS.  */
	      gcc_assert (i != 0);
	      if (!warned && warn_psabi)
		{
		  warned = true;
		  inform (input_location,
			  "the ABI of passing union with long double"
			  " has changed in GCC 4.4");
		}
	      return 0;
	    }
	}
      return words;
    }

  /* Compute alignment needed.  We align all types to natural boundaries with
     exception of XFmode that is aligned to 64bits.  */
  if (mode != VOIDmode && mode != BLKmode)
    {
      int mode_alignment = GET_MODE_BITSIZE (mode);

      if (mode == XFmode)
	mode_alignment = 128;
      else if (mode == XCmode)
	mode_alignment = 256;
      if (COMPLEX_MODE_P (mode))
	mode_alignment /= 2;
      /* Misaligned fields are always returned in memory.  */
      if (bit_offset % mode_alignment)
	return 0;
    }

  /* for V1xx modes, just use the base mode */
  if (VECTOR_MODE_P (mode) && mode != V1DImode && mode != V1TImode
      && GET_MODE_UNIT_SIZE (mode) == bytes)
    mode = GET_MODE_INNER (mode);

  /* Classification of atomic types.  */
  switch (mode)
    {
    case E_SDmode:
    case E_DDmode:
      classes[0] = X86_64_SSE_CLASS;
      return 1;
    case E_TDmode:
      classes[0] = X86_64_SSE_CLASS;
      classes[1] = X86_64_SSEUP_CLASS;
      return 2;
    case E_DImode:
    case E_SImode:
    case E_HImode:
    case E_QImode:
    case E_CSImode:
    case E_CHImode:
    case E_CQImode:
      {
	int size = bit_offset + (int) GET_MODE_BITSIZE (mode);

	/* Analyze last 128 bits only.  */
	size = (size - 1) & 0x7f;

	if (size < 32)
	  {
	    classes[0] = X86_64_INTEGERSI_CLASS;
	    return 1;
	  }
	else if (size < 64)
	  {
	    classes[0] = X86_64_INTEGER_CLASS;
	    return 1;
	  }
	else if (size < 64+32)
	  {
	    classes[0] = X86_64_INTEGER_CLASS;
	    classes[1] = X86_64_INTEGERSI_CLASS;
	    return 2;
	  }
	else if (size < 64+64)
	  {
	    classes[0] = classes[1] = X86_64_INTEGER_CLASS;
	    return 2;
	  }
	else
	  gcc_unreachable ();
      }
    case E_CDImode:
    case E_TImode:
      classes[0] = classes[1] = X86_64_INTEGER_CLASS;
      return 2;
    case E_COImode:
    case E_OImode:
      /* OImode shouldn't be used directly.  */
      gcc_unreachable ();
    case E_CTImode:
      return 0;
    case E_SFmode:
      if (!(bit_offset % 64))
	classes[0] = X86_64_SSESF_CLASS;
      else
	classes[0] = X86_64_SSE_CLASS;
      return 1;
    case E_DFmode:
      classes[0] = X86_64_SSEDF_CLASS;
      return 1;
    case E_XFmode:
      classes[0] = X86_64_X87_CLASS;
      classes[1] = X86_64_X87UP_CLASS;
      return 2;
    case E_TFmode:
      classes[0] = X86_64_SSE_CLASS;
      classes[1] = X86_64_SSEUP_CLASS;
      return 2;
    case E_SCmode:
      classes[0] = X86_64_SSE_CLASS;
      if (!(bit_offset % 64))
	return 1;
      else
	{
	  static bool warned;

	  if (!warned && warn_psabi)
	    {
	      warned = true;
	      inform (input_location,
		      "the ABI of passing structure with complex float"
		      " member has changed in GCC 4.4");
	    }
	  classes[1] = X86_64_SSESF_CLASS;
	  return 2;
	}
    case E_DCmode:
      classes[0] = X86_64_SSEDF_CLASS;
      classes[1] = X86_64_SSEDF_CLASS;
      return 2;
    case E_XCmode:
      classes[0] = X86_64_COMPLEX_X87_CLASS;
      return 1;
    case E_TCmode:
      /* This modes is larger than 16 bytes.  */
      return 0;
    case E_V8SFmode:
    case E_V8SImode:
    case E_V32QImode:
    case E_V16HImode:
    case E_V4DFmode:
    case E_V4DImode:
      classes[0] = X86_64_SSE_CLASS;
      classes[1] = X86_64_SSEUP_CLASS;
      classes[2] = X86_64_SSEUP_CLASS;
      classes[3] = X86_64_SSEUP_CLASS;
      return 4;
    case E_V8DFmode:
    case E_V16SFmode:
    case E_V8DImode:
    case E_V16SImode:
    case E_V32HImode:
    case E_V64QImode:
      classes[0] = X86_64_SSE_CLASS;
      classes[1] = X86_64_SSEUP_CLASS;
      classes[2] = X86_64_SSEUP_CLASS;
      classes[3] = X86_64_SSEUP_CLASS;
      classes[4] = X86_64_SSEUP_CLASS;
      classes[5] = X86_64_SSEUP_CLASS;
      classes[6] = X86_64_SSEUP_CLASS;
      classes[7] = X86_64_SSEUP_CLASS;
      return 8;
    case E_V4SFmode:
    case E_V4SImode:
    case E_V16QImode:
    case E_V8HImode:
    case E_V2DFmode:
    case E_V2DImode:
      classes[0] = X86_64_SSE_CLASS;
      classes[1] = X86_64_SSEUP_CLASS;
      return 2;
    case E_V1TImode:
    case E_V1DImode:
    case E_V2SFmode:
    case E_V2SImode:
    case E_V4HImode:
    case E_V8QImode:
      classes[0] = X86_64_SSE_CLASS;
      return 1;
    case E_BLKmode:
    case E_VOIDmode:
      return 0;
    default:
      gcc_assert (VECTOR_MODE_P (mode));

      if (bytes > 16)
	return 0;

      gcc_assert (GET_MODE_CLASS (GET_MODE_INNER (mode)) == MODE_INT);

      if (bit_offset + GET_MODE_BITSIZE (mode) <= 32)
	classes[0] = X86_64_INTEGERSI_CLASS;
      else
	classes[0] = X86_64_INTEGER_CLASS;
      classes[1] = X86_64_INTEGER_CLASS;
      return 1 + (bytes > 8);
    }
}

/* Examine the argument and return set number of register required in each
   class.  Return true iff parameter should be passed in memory.  */

static bool
examine_argument (machine_mode mode, const_tree type, int in_return,
		  int *int_nregs, int *sse_nregs)
{
  enum x86_64_reg_class regclass[MAX_CLASSES];
  int n = classify_argument (mode, type, regclass, 0);

  *int_nregs = 0;
  *sse_nregs = 0;

  if (!n)
    return true;
  for (n--; n >= 0; n--)
    switch (regclass[n])
      {
      case X86_64_INTEGER_CLASS:
      case X86_64_INTEGERSI_CLASS:
	(*int_nregs)++;
	break;
      case X86_64_SSE_CLASS:
      case X86_64_SSESF_CLASS:
      case X86_64_SSEDF_CLASS:
	(*sse_nregs)++;
	break;
      case X86_64_NO_CLASS:
      case X86_64_SSEUP_CLASS:
	break;
      case X86_64_X87_CLASS:
      case X86_64_X87UP_CLASS:
      case X86_64_COMPLEX_X87_CLASS:
	if (!in_return)
	  return true;
	break;
      case X86_64_MEMORY_CLASS:
	gcc_unreachable ();
      }

  return false;
}

/* Construct container for the argument used by GCC interface.  See
   FUNCTION_ARG for the detailed description.  */

static rtx
construct_container (machine_mode mode, machine_mode orig_mode,
		     const_tree type, int in_return, int nintregs, int nsseregs,
		     const int *intreg, int sse_regno)
{
  /* The following variables hold the static issued_error state.  */
  static bool issued_sse_arg_error;
  static bool issued_sse_ret_error;
  static bool issued_x87_ret_error;

  machine_mode tmpmode;
  int bytes
    = mode == BLKmode ? int_size_in_bytes (type) : (int) GET_MODE_SIZE (mode);
  enum x86_64_reg_class regclass[MAX_CLASSES];
  int n;
  int i;
  int nexps = 0;
  int needed_sseregs, needed_intregs;
  rtx exp[MAX_CLASSES];
  rtx ret;

  n = classify_argument (mode, type, regclass, 0);
  if (!n)
    return NULL;
  if (examine_argument (mode, type, in_return, &needed_intregs,
			&needed_sseregs))
    return NULL;
  if (needed_intregs > nintregs || needed_sseregs > nsseregs)
    return NULL;

  /* We allowed the user to turn off SSE for kernel mode.  Don't crash if
     some less clueful developer tries to use floating-point anyway.  */
  if (needed_sseregs && !TARGET_SSE)
    {
      if (in_return)
	{
	  if (!issued_sse_ret_error)
	    {
	      error ("SSE register return with SSE disabled");
	      issued_sse_ret_error = true;
	    }
	}
      else if (!issued_sse_arg_error)
	{
	  error ("SSE register argument with SSE disabled");
	  issued_sse_arg_error = true;
	}
      return NULL;
    }

  /* Likewise, error if the ABI requires us to return values in the
     x87 registers and the user specified -mno-80387.  */
  if (!TARGET_FLOAT_RETURNS_IN_80387 && in_return)
    for (i = 0; i < n; i++)
      if (regclass[i] == X86_64_X87_CLASS
	  || regclass[i] == X86_64_X87UP_CLASS
	  || regclass[i] == X86_64_COMPLEX_X87_CLASS)
	{
	  if (!issued_x87_ret_error)
	    {
	      error ("x87 register return with x87 disabled");
	      issued_x87_ret_error = true;
	    }
	  return NULL;
	}

  /* First construct simple cases.  Avoid SCmode, since we want to use
     single register to pass this type.  */
  if (n == 1 && mode != SCmode)
    switch (regclass[0])
      {
      case X86_64_INTEGER_CLASS:
      case X86_64_INTEGERSI_CLASS:
	return gen_rtx_REG (mode, intreg[0]);
      case X86_64_SSE_CLASS:
      case X86_64_SSESF_CLASS:
      case X86_64_SSEDF_CLASS:
	if (mode != BLKmode)
	  return gen_reg_or_parallel (mode, orig_mode,
				      GET_SSE_REGNO (sse_regno));
	break;
      case X86_64_X87_CLASS:
      case X86_64_COMPLEX_X87_CLASS:
	return gen_rtx_REG (mode, FIRST_STACK_REG);
      case X86_64_NO_CLASS:
	/* Zero sized array, struct or class.  */
	return NULL;
      default:
	gcc_unreachable ();
      }
  if (n == 2
      && regclass[0] == X86_64_SSE_CLASS
      && regclass[1] == X86_64_SSEUP_CLASS
      && mode != BLKmode)
    return gen_reg_or_parallel (mode, orig_mode,
				GET_SSE_REGNO (sse_regno));
  if (n == 4
      && regclass[0] == X86_64_SSE_CLASS
      && regclass[1] == X86_64_SSEUP_CLASS
      && regclass[2] == X86_64_SSEUP_CLASS
      && regclass[3] == X86_64_SSEUP_CLASS
      && mode != BLKmode)
    return gen_reg_or_parallel (mode, orig_mode,
				GET_SSE_REGNO (sse_regno));
  if (n == 8
      && regclass[0] == X86_64_SSE_CLASS
      && regclass[1] == X86_64_SSEUP_CLASS
      && regclass[2] == X86_64_SSEUP_CLASS
      && regclass[3] == X86_64_SSEUP_CLASS
      && regclass[4] == X86_64_SSEUP_CLASS
      && regclass[5] == X86_64_SSEUP_CLASS
      && regclass[6] == X86_64_SSEUP_CLASS
      && regclass[7] == X86_64_SSEUP_CLASS
      && mode != BLKmode)
    return gen_reg_or_parallel (mode, orig_mode,
				GET_SSE_REGNO (sse_regno));
  if (n == 2
      && regclass[0] == X86_64_X87_CLASS
      && regclass[1] == X86_64_X87UP_CLASS)
    return gen_rtx_REG (XFmode, FIRST_STACK_REG);

  if (n == 2
      && regclass[0] == X86_64_INTEGER_CLASS
      && regclass[1] == X86_64_INTEGER_CLASS
      && (mode == CDImode || mode == TImode || mode == BLKmode)
      && intreg[0] + 1 == intreg[1])
    {
      if (mode == BLKmode)
	{
	  /* Use TImode for BLKmode values in 2 integer registers.  */
	  exp[0] = gen_rtx_EXPR_LIST (VOIDmode,
				      gen_rtx_REG (TImode, intreg[0]),
				      GEN_INT (0));
	  ret = gen_rtx_PARALLEL (mode, rtvec_alloc (1));
	  XVECEXP (ret, 0, 0) = exp[0];
	  return ret;
	}
      else
	return gen_rtx_REG (mode, intreg[0]);
    }

  /* Otherwise figure out the entries of the PARALLEL.  */
  for (i = 0; i < n; i++)
    {
      int pos;

      switch (regclass[i])
        {
	  case X86_64_NO_CLASS:
	    break;
	  case X86_64_INTEGER_CLASS:
	  case X86_64_INTEGERSI_CLASS:
	    /* Merge TImodes on aligned occasions here too.  */
	    if (i * 8 + 8 > bytes)
	      {
		unsigned int tmpbits = (bytes - i * 8) * BITS_PER_UNIT;
		if (!int_mode_for_size (tmpbits, 0).exists (&tmpmode))
		  /* We've requested 24 bytes we
		     don't have mode for.  Use DImode.  */
		  tmpmode = DImode;
	      }
	    else if (regclass[i] == X86_64_INTEGERSI_CLASS)
	      tmpmode = SImode;
	    else
	      tmpmode = DImode;
	    exp [nexps++]
	      = gen_rtx_EXPR_LIST (VOIDmode,
				   gen_rtx_REG (tmpmode, *intreg),
				   GEN_INT (i*8));
	    intreg++;
	    break;
	  case X86_64_SSESF_CLASS:
	    exp [nexps++]
	      = gen_rtx_EXPR_LIST (VOIDmode,
				   gen_rtx_REG (SFmode,
						GET_SSE_REGNO (sse_regno)),
				   GEN_INT (i*8));
	    sse_regno++;
	    break;
	  case X86_64_SSEDF_CLASS:
	    exp [nexps++]
	      = gen_rtx_EXPR_LIST (VOIDmode,
				   gen_rtx_REG (DFmode,
						GET_SSE_REGNO (sse_regno)),
				   GEN_INT (i*8));
	    sse_regno++;
	    break;
	  case X86_64_SSE_CLASS:
	    pos = i;
	    switch (n)
	      {
	      case 1:
		tmpmode = DImode;
		break;
	      case 2:
		if (i == 0 && regclass[1] == X86_64_SSEUP_CLASS)
		  {
		    tmpmode = TImode;
		    i++;
		  }
		else
		  tmpmode = DImode;
		break;
	      case 4:
		gcc_assert (i == 0
			    && regclass[1] == X86_64_SSEUP_CLASS
			    && regclass[2] == X86_64_SSEUP_CLASS
			    && regclass[3] == X86_64_SSEUP_CLASS);
		tmpmode = OImode;
		i += 3;
		break;
	      case 8:
		gcc_assert (i == 0
			    && regclass[1] == X86_64_SSEUP_CLASS
			    && regclass[2] == X86_64_SSEUP_CLASS
			    && regclass[3] == X86_64_SSEUP_CLASS
			    && regclass[4] == X86_64_SSEUP_CLASS
			    && regclass[5] == X86_64_SSEUP_CLASS
			    && regclass[6] == X86_64_SSEUP_CLASS
			    && regclass[7] == X86_64_SSEUP_CLASS);
		tmpmode = XImode;
		i += 7;
		break;
	      default:
		gcc_unreachable ();
	      }
	    exp [nexps++]
	      = gen_rtx_EXPR_LIST (VOIDmode,
				   gen_rtx_REG (tmpmode,
						GET_SSE_REGNO (sse_regno)),
				   GEN_INT (pos*8));
	    sse_regno++;
	    break;
	  default:
	    gcc_unreachable ();
	}
    }

  /* Empty aligned struct, union or class.  */
  if (nexps == 0)
    return NULL;

  ret =  gen_rtx_PARALLEL (mode, rtvec_alloc (nexps));
  for (i = 0; i < nexps; i++)
    XVECEXP (ret, 0, i) = exp [i];
  return ret;
}

/* Update the data in CUM to advance over an argument of mode MODE
   and data type TYPE.  (TYPE is null for libcalls where that information
   may not be available.)

   Return a number of integer regsiters advanced over.  */

static int
function_arg_advance_32 (CUMULATIVE_ARGS *cum, machine_mode mode,
			 const_tree type, HOST_WIDE_INT bytes,
			 HOST_WIDE_INT words)
{
  int res = 0;
  bool error_p = false;

  if (TARGET_IAMCU)
    {
      /* Intel MCU psABI passes scalars and aggregates no larger than 8
	 bytes in registers.  */
      if (!VECTOR_MODE_P (mode) && bytes <= 8)
	goto pass_in_reg;
      return res;
    }

  switch (mode)
    {
    default:
      break;

    case E_BLKmode:
      if (bytes < 0)
	break;
      /* FALLTHRU */

    case E_DImode:
    case E_SImode:
    case E_HImode:
    case E_QImode:
pass_in_reg:
      cum->words += words;
      cum->nregs -= words;
      cum->regno += words;
      if (cum->nregs >= 0)
	res = words;
      if (cum->nregs <= 0)
	{
	  cum->nregs = 0;
	  cfun->machine->arg_reg_available = false;
	  cum->regno = 0;
	}
      break;

    case E_OImode:
      /* OImode shouldn't be used directly.  */
      gcc_unreachable ();

    case E_DFmode:
      if (cum->float_in_sse == -1)
	error_p = true;
      if (cum->float_in_sse < 2)
	break;
      /* FALLTHRU */
    case E_SFmode:
      if (cum->float_in_sse == -1)
	error_p = true;
      if (cum->float_in_sse < 1)
	break;
      /* FALLTHRU */

    case E_V8SFmode:
    case E_V8SImode:
    case E_V64QImode:
    case E_V32HImode:
    case E_V16SImode:
    case E_V8DImode:
    case E_V16SFmode:
    case E_V8DFmode:
    case E_V32QImode:
    case E_V16HImode:
    case E_V4DFmode:
    case E_V4DImode:
    case E_TImode:
    case E_V16QImode:
    case E_V8HImode:
    case E_V4SImode:
    case E_V2DImode:
    case E_V4SFmode:
    case E_V2DFmode:
      if (!type || !AGGREGATE_TYPE_P (type))
	{
	  cum->sse_words += words;
	  cum->sse_nregs -= 1;
	  cum->sse_regno += 1;
	  if (cum->sse_nregs <= 0)
	    {
	      cum->sse_nregs = 0;
	      cum->sse_regno = 0;
	    }
	}
      break;

    case E_V8QImode:
    case E_V4HImode:
    case E_V2SImode:
    case E_V2SFmode:
    case E_V1TImode:
    case E_V1DImode:
      if (!type || !AGGREGATE_TYPE_P (type))
	{
	  cum->mmx_words += words;
	  cum->mmx_nregs -= 1;
	  cum->mmx_regno += 1;
	  if (cum->mmx_nregs <= 0)
	    {
	      cum->mmx_nregs = 0;
	      cum->mmx_regno = 0;
	    }
	}
      break;
    }
  if (error_p)
    {
      cum->float_in_sse = 0;
      error ("calling %qD with SSE calling convention without "
	     "SSE/SSE2 enabled", cum->decl);
      sorry ("this is a GCC bug that can be worked around by adding "
	     "attribute used to function called");
    }

  return res;
}

static int
function_arg_advance_64 (CUMULATIVE_ARGS *cum, machine_mode mode,
			 const_tree type, HOST_WIDE_INT words, bool named)
{
  int int_nregs, sse_nregs;

  /* Unnamed 512 and 256bit vector mode parameters are passed on stack.  */
  if (!named && (VALID_AVX512F_REG_MODE (mode)
		 || VALID_AVX256_REG_MODE (mode)))
    return 0;

  if (!examine_argument (mode, type, 0, &int_nregs, &sse_nregs)
      && sse_nregs <= cum->sse_nregs && int_nregs <= cum->nregs)
    {
      cum->nregs -= int_nregs;
      cum->sse_nregs -= sse_nregs;
      cum->regno += int_nregs;
      cum->sse_regno += sse_nregs;
      return int_nregs;
    }
  else
    {
      int align = ix86_function_arg_boundary (mode, type) / BITS_PER_WORD;
      cum->words = ROUND_UP (cum->words, align);
      cum->words += words;
      return 0;
    }
}

static int
function_arg_advance_ms_64 (CUMULATIVE_ARGS *cum, HOST_WIDE_INT bytes,
			    HOST_WIDE_INT words)
{
  /* Otherwise, this should be passed indirect.  */
  gcc_assert (bytes == 1 || bytes == 2 || bytes == 4 || bytes == 8);

  cum->words += words;
  if (cum->nregs > 0)
    {
      cum->nregs -= 1;
      cum->regno += 1;
      return 1;
    }
  return 0;
}

/* Update the data in CUM to advance over an argument of mode MODE and
   data type TYPE.  (TYPE is null for libcalls where that information
   may not be available.)  */

static void
ix86_function_arg_advance (cumulative_args_t cum_v, machine_mode mode,
			   const_tree type, bool named)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
  HOST_WIDE_INT bytes, words;
  int nregs;

  /* The argument of interrupt handler is a special case and is
     handled in ix86_function_arg.  */
  if (!cum->caller && cfun->machine->func_type != TYPE_NORMAL)
    return;

  if (mode == BLKmode)
    bytes = int_size_in_bytes (type);
  else
    bytes = GET_MODE_SIZE (mode);
  words = CEIL (bytes, UNITS_PER_WORD);

  if (type)
    mode = type_natural_mode (type, NULL, false);

  if (TARGET_64BIT)
    {
      enum calling_abi call_abi = cum ? cum->call_abi : ix86_abi;

      if (call_abi == MS_ABI)
	nregs = function_arg_advance_ms_64 (cum, bytes, words);
      else
	nregs = function_arg_advance_64 (cum, mode, type, words, named);
    }
  else
    nregs = function_arg_advance_32 (cum, mode, type, bytes, words);

  if (!nregs)
    {
      /* Track if there are outgoing arguments on stack.  */
      if (cum->caller)
	cfun->machine->outgoing_args_on_stack = true;
    }
}

/* Define where to put the arguments to a function.
   Value is zero to push the argument on the stack,
   or a hard register in which to store the argument.

   MODE is the argument's machine mode.
   TYPE is the data type of the argument (as a tree).
    This is null for libcalls where that information may
    not be available.
   CUM is a variable of type CUMULATIVE_ARGS which gives info about
    the preceding args and about the function being called.
   NAMED is nonzero if this argument is a named parameter
    (otherwise it is an extra parameter matching an ellipsis).  */

static rtx
function_arg_32 (CUMULATIVE_ARGS *cum, machine_mode mode,
		 machine_mode orig_mode, const_tree type,
		 HOST_WIDE_INT bytes, HOST_WIDE_INT words)
{
  bool error_p = false;

  /* Avoid the AL settings for the Unix64 ABI.  */
  if (mode == VOIDmode)
    return constm1_rtx;

  if (TARGET_IAMCU)
    {
      /* Intel MCU psABI passes scalars and aggregates no larger than 8
	 bytes in registers.  */
      if (!VECTOR_MODE_P (mode) && bytes <= 8)
	goto pass_in_reg;
      return NULL_RTX;
    }

  switch (mode)
    {
    default:
      break;

    case E_BLKmode:
      if (bytes < 0)
	break;
      /* FALLTHRU */
    case E_DImode:
    case E_SImode:
    case E_HImode:
    case E_QImode:
pass_in_reg:
      if (words <= cum->nregs)
	{
	  int regno = cum->regno;

	  /* Fastcall allocates the first two DWORD (SImode) or
            smaller arguments to ECX and EDX if it isn't an
            aggregate type .  */
	  if (cum->fastcall)
	    {
	      if (mode == BLKmode
		  || mode == DImode
		  || (type && AGGREGATE_TYPE_P (type)))
	        break;

	      /* ECX not EAX is the first allocated register.  */
	      if (regno == AX_REG)
		regno = CX_REG;
	    }
	  return gen_rtx_REG (mode, regno);
	}
      break;

    case E_DFmode:
      if (cum->float_in_sse == -1)
	error_p = true;
      if (cum->float_in_sse < 2)
	break;
      /* FALLTHRU */
    case E_SFmode:
      if (cum->float_in_sse == -1)
	error_p = true;
      if (cum->float_in_sse < 1)
	break;
      /* FALLTHRU */
    case E_TImode:
      /* In 32bit, we pass TImode in xmm registers.  */
    case E_V16QImode:
    case E_V8HImode:
    case E_V4SImode:
    case E_V2DImode:
    case E_V4SFmode:
    case E_V2DFmode:
      if (!type || !AGGREGATE_TYPE_P (type))
	{
	  if (cum->sse_nregs)
	    return gen_reg_or_parallel (mode, orig_mode,
				        cum->sse_regno + FIRST_SSE_REG);
	}
      break;

    case E_OImode:
    case E_XImode:
      /* OImode and XImode shouldn't be used directly.  */
      gcc_unreachable ();

    case E_V64QImode:
    case E_V32HImode:
    case E_V16SImode:
    case E_V8DImode:
    case E_V16SFmode:
    case E_V8DFmode:
    case E_V8SFmode:
    case E_V8SImode:
    case E_V32QImode:
    case E_V16HImode:
    case E_V4DFmode:
    case E_V4DImode:
      if (!type || !AGGREGATE_TYPE_P (type))
	{
	  if (cum->sse_nregs)
	    return gen_reg_or_parallel (mode, orig_mode,
				        cum->sse_regno + FIRST_SSE_REG);
	}
      break;

    case E_V8QImode:
    case E_V4HImode:
    case E_V2SImode:
    case E_V2SFmode:
    case E_V1TImode:
    case E_V1DImode:
      if (!type || !AGGREGATE_TYPE_P (type))
	{
	  if (cum->mmx_nregs)
	    return gen_reg_or_parallel (mode, orig_mode,
				        cum->mmx_regno + FIRST_MMX_REG);
	}
      break;
    }
  if (error_p)
    {
      cum->float_in_sse = 0;
      error ("calling %qD with SSE calling convention without "
	     "SSE/SSE2 enabled", cum->decl);
      sorry ("this is a GCC bug that can be worked around by adding "
	     "attribute used to function called");
    }

  return NULL_RTX;
}

static rtx
function_arg_64 (const CUMULATIVE_ARGS *cum, machine_mode mode,
		 machine_mode orig_mode, const_tree type, bool named)
{
  /* Handle a hidden AL argument containing number of registers
     for varargs x86-64 functions.  */
  if (mode == VOIDmode)
    return GEN_INT (cum->maybe_vaarg
		    ? (cum->sse_nregs < 0
		       ? X86_64_SSE_REGPARM_MAX
		       : cum->sse_regno)
		    : -1);

  switch (mode)
    {
    default:
      break;

    case E_V8SFmode:
    case E_V8SImode:
    case E_V32QImode:
    case E_V16HImode:
    case E_V4DFmode:
    case E_V4DImode:
    case E_V16SFmode:
    case E_V16SImode:
    case E_V64QImode:
    case E_V32HImode:
    case E_V8DFmode:
    case E_V8DImode:
      /* Unnamed 256 and 512bit vector mode parameters are passed on stack.  */
      if (!named)
	return NULL;
      break;
    }

  return construct_container (mode, orig_mode, type, 0, cum->nregs,
			      cum->sse_nregs,
			      &x86_64_int_parameter_registers [cum->regno],
			      cum->sse_regno);
}

static rtx
function_arg_ms_64 (const CUMULATIVE_ARGS *cum, machine_mode mode,
		    machine_mode orig_mode, bool named,
		    HOST_WIDE_INT bytes)
{
  unsigned int regno;

  /* We need to add clobber for MS_ABI->SYSV ABI calls in expand_call.
     We use value of -2 to specify that current function call is MSABI.  */
  if (mode == VOIDmode)
    return GEN_INT (-2);

  /* If we've run out of registers, it goes on the stack.  */
  if (cum->nregs == 0)
    return NULL_RTX;

  regno = x86_64_ms_abi_int_parameter_registers[cum->regno];

  /* Only floating point modes are passed in anything but integer regs.  */
  if (TARGET_SSE && (mode == SFmode || mode == DFmode))
    {
      if (named)
	regno = cum->regno + FIRST_SSE_REG;
      else
	{
	  rtx t1, t2;

	  /* Unnamed floating parameters are passed in both the
	     SSE and integer registers.  */
	  t1 = gen_rtx_REG (mode, cum->regno + FIRST_SSE_REG);
	  t2 = gen_rtx_REG (mode, regno);
	  t1 = gen_rtx_EXPR_LIST (VOIDmode, t1, const0_rtx);
	  t2 = gen_rtx_EXPR_LIST (VOIDmode, t2, const0_rtx);
	  return gen_rtx_PARALLEL (mode, gen_rtvec (2, t1, t2));
	}
    }
  /* Handle aggregated types passed in register.  */
  if (orig_mode == BLKmode)
    {
      if (bytes > 0 && bytes <= 8)
        mode = (bytes > 4 ? DImode : SImode);
      if (mode == BLKmode)
        mode = DImode;
    }

  return gen_reg_or_parallel (mode, orig_mode, regno);
}

/* Return where to put the arguments to a function.
   Return zero to push the argument on the stack, or a hard register in which to store the argument.

   MODE is the argument's machine mode.  TYPE is the data type of the
   argument.  It is null for libcalls where that information may not be
   available.  CUM gives information about the preceding args and about
   the function being called.  NAMED is nonzero if this argument is a
   named parameter (otherwise it is an extra parameter matching an
   ellipsis).  */

static rtx
ix86_function_arg (cumulative_args_t cum_v, machine_mode omode,
		   const_tree type, bool named)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
  machine_mode mode = omode;
  HOST_WIDE_INT bytes, words;
  rtx arg;

  if (!cum->caller && cfun->machine->func_type != TYPE_NORMAL)
    {
      gcc_assert (type != NULL_TREE);
      if (POINTER_TYPE_P (type))
	{
	  /* This is the pointer argument.  */
	  gcc_assert (TYPE_MODE (type) == Pmode);
	  /* It is at -WORD(AP) in the current frame in interrupt and
	     exception handlers.  */
	  arg = plus_constant (Pmode, arg_pointer_rtx, -UNITS_PER_WORD);
	}
      else
	{
	  gcc_assert (cfun->machine->func_type == TYPE_EXCEPTION
		      && TREE_CODE (type) == INTEGER_TYPE
		      && TYPE_MODE (type) == word_mode);
	  /* The error code is the word-mode integer argument at
	     -2 * WORD(AP) in the current frame of the exception
	     handler.  */
	  arg = gen_rtx_MEM (word_mode,
			     plus_constant (Pmode,
					    arg_pointer_rtx,
					    -2 * UNITS_PER_WORD));
	}
      return arg;
    }

  if (mode == BLKmode)
    bytes = int_size_in_bytes (type);
  else
    bytes = GET_MODE_SIZE (mode);
  words = CEIL (bytes, UNITS_PER_WORD);

  /* To simplify the code below, represent vector types with a vector mode
     even if MMX/SSE are not active.  */
  if (type && TREE_CODE (type) == VECTOR_TYPE)
    mode = type_natural_mode (type, cum, false);

  if (TARGET_64BIT)
    {
      enum calling_abi call_abi = cum ? cum->call_abi : ix86_abi;

      if (call_abi == MS_ABI)
	arg = function_arg_ms_64 (cum, mode, omode, named, bytes);
      else
	arg = function_arg_64 (cum, mode, omode, type, named);
    }
  else
    arg = function_arg_32 (cum, mode, omode, type, bytes, words);

  /* Track if there are outgoing arguments on stack.  */
  if (arg == NULL_RTX && cum->caller)
    cfun->machine->outgoing_args_on_stack = true;

  return arg;
}

/* A C expression that indicates when an argument must be passed by
   reference.  If nonzero for an argument, a copy of that argument is
   made in memory and a pointer to the argument is passed instead of
   the argument itself.  The pointer is passed in whatever way is
   appropriate for passing a pointer to that type.  */

static bool
ix86_pass_by_reference (cumulative_args_t cum_v, machine_mode mode,
			const_tree type, bool)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);

  if (TARGET_64BIT)
    {
      enum calling_abi call_abi = cum ? cum->call_abi : ix86_abi;

      /* See Windows x64 Software Convention.  */
      if (call_abi == MS_ABI)
	{
	  HOST_WIDE_INT msize = GET_MODE_SIZE (mode);

	  if (type)
	    {
	      /* Arrays are passed by reference.  */
	      if (TREE_CODE (type) == ARRAY_TYPE)
		return true;

	      if (RECORD_OR_UNION_TYPE_P (type))
		{
		  /* Structs/unions of sizes other than 8, 16, 32, or 64 bits
		     are passed by reference.  */
		  msize = int_size_in_bytes (type);
		}
	    }

	  /* __m128 is passed by reference.  */
	  return msize != 1 && msize != 2 && msize != 4 && msize != 8;
	}
      else if (type && int_size_in_bytes (type) == -1)
	return true;
    }

  return false;
}

/* Return true when TYPE should be 128bit aligned for 32bit argument
   passing ABI.  XXX: This function is obsolete and is only used for
   checking psABI compatibility with previous versions of GCC.  */

static bool
ix86_compat_aligned_value_p (const_tree type)
{
  machine_mode mode = TYPE_MODE (type);
  if (((TARGET_SSE && SSE_REG_MODE_P (mode))
       || mode == TDmode
       || mode == TFmode
       || mode == TCmode)
      && (!TYPE_USER_ALIGN (type) || TYPE_ALIGN (type) > 128))
    return true;
  if (TYPE_ALIGN (type) < 128)
    return false;

  if (AGGREGATE_TYPE_P (type))
    {
      /* Walk the aggregates recursively.  */
      switch (TREE_CODE (type))
	{
	case RECORD_TYPE:
	case UNION_TYPE:
	case QUAL_UNION_TYPE:
	  {
	    tree field;

	    /* Walk all the structure fields.  */
	    for (field = TYPE_FIELDS (type); field; field = DECL_CHAIN (field))
	      {
		if (TREE_CODE (field) == FIELD_DECL
		    && ix86_compat_aligned_value_p (TREE_TYPE (field)))
		  return true;
	      }
	    break;
	  }

	case ARRAY_TYPE:
	  /* Just for use if some languages passes arrays by value.  */
	  if (ix86_compat_aligned_value_p (TREE_TYPE (type)))
	    return true;
	  break;

	default:
	  gcc_unreachable ();
	}
    }
  return false;
}

/* Return the alignment boundary for MODE and TYPE with alignment ALIGN.
   XXX: This function is obsolete and is only used for checking psABI
   compatibility with previous versions of GCC.  */

static unsigned int
ix86_compat_function_arg_boundary (machine_mode mode,
				   const_tree type, unsigned int align)
{
  /* In 32bit, only _Decimal128 and __float128 are aligned to their
     natural boundaries.  */
  if (!TARGET_64BIT && mode != TDmode && mode != TFmode)
    {
      /* i386 ABI defines all arguments to be 4 byte aligned.  We have to
	 make an exception for SSE modes since these require 128bit
	 alignment.

	 The handling here differs from field_alignment.  ICC aligns MMX
	 arguments to 4 byte boundaries, while structure fields are aligned
	 to 8 byte boundaries.  */
      if (!type)
	{
	  if (!(TARGET_SSE && SSE_REG_MODE_P (mode)))
	    align = PARM_BOUNDARY;
	}
      else
	{
	  if (!ix86_compat_aligned_value_p (type))
	    align = PARM_BOUNDARY;
	}
    }
  if (align > BIGGEST_ALIGNMENT)
    align = BIGGEST_ALIGNMENT;
  return align;
}

/* Return true when TYPE should be 128bit aligned for 32bit argument
   passing ABI.  */

static bool
ix86_contains_aligned_value_p (const_tree type)
{
  machine_mode mode = TYPE_MODE (type);

  if (mode == XFmode || mode == XCmode)
    return false;

  if (TYPE_ALIGN (type) < 128)
    return false;

  if (AGGREGATE_TYPE_P (type))
    {
      /* Walk the aggregates recursively.  */
      switch (TREE_CODE (type))
	{
	case RECORD_TYPE:
	case UNION_TYPE:
	case QUAL_UNION_TYPE:
	  {
	    tree field;

	    /* Walk all the structure fields.  */
	    for (field = TYPE_FIELDS (type);
		 field;
		 field = DECL_CHAIN (field))
	      {
		if (TREE_CODE (field) == FIELD_DECL
		    && ix86_contains_aligned_value_p (TREE_TYPE (field)))
		  return true;
	      }
	    break;
	  }

	case ARRAY_TYPE:
	  /* Just for use if some languages passes arrays by value.  */
	  if (ix86_contains_aligned_value_p (TREE_TYPE (type)))
	    return true;
	  break;

	default:
	  gcc_unreachable ();
	}
    }
  else
    return TYPE_ALIGN (type) >= 128;

  return false;
}

/* Gives the alignment boundary, in bits, of an argument with the
   specified mode and type.  */

static unsigned int
ix86_function_arg_boundary (machine_mode mode, const_tree type)
{
  unsigned int align;
  if (type)
    {
      /* Since the main variant type is used for call, we convert it to
	 the main variant type.  */
      type = TYPE_MAIN_VARIANT (type);
      align = TYPE_ALIGN (type);
      if (TYPE_EMPTY_P (type))
	return PARM_BOUNDARY;
    }
  else
    align = GET_MODE_ALIGNMENT (mode);
  if (align < PARM_BOUNDARY)
    align = PARM_BOUNDARY;
  else
    {
      static bool warned;
      unsigned int saved_align = align;

      if (!TARGET_64BIT)
	{
	  /* i386 ABI defines XFmode arguments to be 4 byte aligned.  */
	  if (!type)
	    {
	      if (mode == XFmode || mode == XCmode)
		align = PARM_BOUNDARY;
	    }
	  else if (!ix86_contains_aligned_value_p (type))
	    align = PARM_BOUNDARY;

	  if (align < 128)
	    align = PARM_BOUNDARY;
	}

      if (warn_psabi
	  && !warned
	  && align != ix86_compat_function_arg_boundary (mode, type,
							 saved_align))
	{
	  warned = true;
	  inform (input_location,
		  "The ABI for passing parameters with %d-byte"
		  " alignment has changed in GCC 4.6",
		  align / BITS_PER_UNIT);
	}
    }

  return align;
}

/* Return true if N is a possible register number of function value.  */

static bool
ix86_function_value_regno_p (const unsigned int regno)
{
  switch (regno)
    {
    case AX_REG:
      return true;
    case DX_REG:
      return (!TARGET_64BIT || ix86_cfun_abi () != MS_ABI);
    case DI_REG:
    case SI_REG:
      return TARGET_64BIT && ix86_cfun_abi () != MS_ABI;

      /* Complex values are returned in %st(0)/%st(1) pair.  */
    case ST0_REG:
    case ST1_REG:
      /* TODO: The function should depend on current function ABI but
       builtins.c would need updating then. Therefore we use the
       default ABI.  */
      if (TARGET_64BIT && ix86_cfun_abi () == MS_ABI)
	return false;
      return TARGET_FLOAT_RETURNS_IN_80387;

      /* Complex values are returned in %xmm0/%xmm1 pair.  */
    case XMM0_REG:
    case XMM1_REG:
      return TARGET_SSE;

    case MM0_REG:
      if (TARGET_MACHO || TARGET_64BIT)
	return false;
      return TARGET_MMX;
    }

  return false;
}

/* Define how to find the value returned by a function.
   VALTYPE is the data type of the value (as a tree).
   If the precise function being called is known, FUNC is its FUNCTION_DECL;
   otherwise, FUNC is 0.  */

static rtx
function_value_32 (machine_mode orig_mode, machine_mode mode,
		   const_tree fntype, const_tree fn)
{
  unsigned int regno;

  /* 8-byte vector modes in %mm0. See ix86_return_in_memory for where
     we normally prevent this case when mmx is not available.  However
     some ABIs may require the result to be returned like DImode.  */
  if (VECTOR_MODE_P (mode) && GET_MODE_SIZE (mode) == 8)
    regno = FIRST_MMX_REG;

  /* 16-byte vector modes in %xmm0.  See ix86_return_in_memory for where
     we prevent this case when sse is not available.  However some ABIs
     may require the result to be returned like integer TImode.  */
  else if (mode == TImode
	   || (VECTOR_MODE_P (mode) && GET_MODE_SIZE (mode) == 16))
    regno = FIRST_SSE_REG;

  /* 32-byte vector modes in %ymm0.   */
  else if (VECTOR_MODE_P (mode) && GET_MODE_SIZE (mode) == 32)
    regno = FIRST_SSE_REG;

  /* 64-byte vector modes in %zmm0.   */
  else if (VECTOR_MODE_P (mode) && GET_MODE_SIZE (mode) == 64)
    regno = FIRST_SSE_REG;

  /* Floating point return values in %st(0) (unless -mno-fp-ret-in-387).  */
  else if (X87_FLOAT_MODE_P (mode) && TARGET_FLOAT_RETURNS_IN_80387)
    regno = FIRST_FLOAT_REG;
  else
    /* Most things go in %eax.  */
    regno = AX_REG;

  /* Override FP return register with %xmm0 for local functions when
     SSE math is enabled or for functions with sseregparm attribute.  */
  if ((fn || fntype) && (mode == SFmode || mode == DFmode))
    {
      int sse_level = ix86_function_sseregparm (fntype, fn, false);
      if (sse_level == -1)
	{
	  error ("calling %qD with SSE calling convention without "
		 "SSE/SSE2 enabled", fn);
	  sorry ("this is a GCC bug that can be worked around by adding "
		 "attribute used to function called");
	}
      else if ((sse_level >= 1 && mode == SFmode)
	       || (sse_level == 2 && mode == DFmode))
	regno = FIRST_SSE_REG;
    }

  /* OImode shouldn't be used directly.  */
  gcc_assert (mode != OImode);

  return gen_rtx_REG (orig_mode, regno);
}

static rtx
function_value_64 (machine_mode orig_mode, machine_mode mode,
		   const_tree valtype)
{
  rtx ret;

  /* Handle libcalls, which don't provide a type node.  */
  if (valtype == NULL)
    {
      unsigned int regno;

      switch (mode)
	{
	case E_SFmode:
	case E_SCmode:
	case E_DFmode:
	case E_DCmode:
	case E_TFmode:
	case E_SDmode:
	case E_DDmode:
	case E_TDmode:
	  regno = FIRST_SSE_REG;
	  break;
	case E_XFmode:
	case E_XCmode:
	  regno = FIRST_FLOAT_REG;
	  break;
	case E_TCmode:
	  return NULL;
	default:
	  regno = AX_REG;
	}

      return gen_rtx_REG (mode, regno);
    }
  else if (POINTER_TYPE_P (valtype))
    {
      /* Pointers are always returned in word_mode.  */
      mode = word_mode;
    }

  ret = construct_container (mode, orig_mode, valtype, 1,
			     X86_64_REGPARM_MAX, X86_64_SSE_REGPARM_MAX,
			     x86_64_int_return_registers, 0);

  /* For zero sized structures, construct_container returns NULL, but we
     need to keep rest of compiler happy by returning meaningful value.  */
  if (!ret)
    ret = gen_rtx_REG (orig_mode, AX_REG);

  return ret;
}

static rtx
function_value_ms_64 (machine_mode orig_mode, machine_mode mode,
		      const_tree valtype)
{
  unsigned int regno = AX_REG;

  if (TARGET_SSE)
    {
      switch (GET_MODE_SIZE (mode))
	{
	case 16:
	  if (valtype != NULL_TREE
	      && !VECTOR_INTEGER_TYPE_P (valtype)
	      && !VECTOR_INTEGER_TYPE_P (valtype)
	      && !INTEGRAL_TYPE_P (valtype)
	      && !VECTOR_FLOAT_TYPE_P (valtype))
	    break;
	  if ((SCALAR_INT_MODE_P (mode) || VECTOR_MODE_P (mode))
	      && !COMPLEX_MODE_P (mode))
	    regno = FIRST_SSE_REG;
	  break;
	case 8:
	case 4:
	  if (valtype != NULL_TREE && AGGREGATE_TYPE_P (valtype))
	    break;
	  if (mode == SFmode || mode == DFmode)
	    regno = FIRST_SSE_REG;
	  break;
	default:
	  break;
        }
    }
  return gen_rtx_REG (orig_mode, regno);
}

static rtx
ix86_function_value_1 (const_tree valtype, const_tree fntype_or_decl,
		       machine_mode orig_mode, machine_mode mode)
{
  const_tree fn, fntype;

  fn = NULL_TREE;
  if (fntype_or_decl && DECL_P (fntype_or_decl))
    fn = fntype_or_decl;
  fntype = fn ? TREE_TYPE (fn) : fntype_or_decl;

  if (TARGET_64BIT && ix86_function_type_abi (fntype) == MS_ABI)
    return function_value_ms_64 (orig_mode, mode, valtype);
  else if (TARGET_64BIT)
    return function_value_64 (orig_mode, mode, valtype);
  else
    return function_value_32 (orig_mode, mode, fntype, fn);
}

static rtx
ix86_function_value (const_tree valtype, const_tree fntype_or_decl, bool)
{
  machine_mode mode, orig_mode;

  orig_mode = TYPE_MODE (valtype);
  mode = type_natural_mode (valtype, NULL, true);
  return ix86_function_value_1 (valtype, fntype_or_decl, orig_mode, mode);
}

/* Pointer function arguments and return values are promoted to
   word_mode for normal functions.  */

static machine_mode
ix86_promote_function_mode (const_tree type, machine_mode mode,
			    int *punsignedp, const_tree fntype,
			    int for_return)
{
  if (cfun->machine->func_type == TYPE_NORMAL
      && type != NULL_TREE
      && POINTER_TYPE_P (type))
    {
      *punsignedp = POINTERS_EXTEND_UNSIGNED;
      return word_mode;
    }
  return default_promote_function_mode (type, mode, punsignedp, fntype,
					for_return);
}

/* Return true if a structure, union or array with MODE containing FIELD
   should be accessed using BLKmode.  */

static bool
ix86_member_type_forces_blk (const_tree field, machine_mode mode)
{
  /* Union with XFmode must be in BLKmode.  */
  return (mode == XFmode
	  && (TREE_CODE (DECL_FIELD_CONTEXT (field)) == UNION_TYPE
	      || TREE_CODE (DECL_FIELD_CONTEXT (field)) == QUAL_UNION_TYPE));
}

rtx
ix86_libcall_value (machine_mode mode)
{
  return ix86_function_value_1 (NULL, NULL, mode, mode);
}

/* Return true iff type is returned in memory.  */

static bool
ix86_return_in_memory (const_tree type, const_tree fntype ATTRIBUTE_UNUSED)
{
#ifdef SUBTARGET_RETURN_IN_MEMORY
  return SUBTARGET_RETURN_IN_MEMORY (type, fntype);
#else
  const machine_mode mode = type_natural_mode (type, NULL, true);
  HOST_WIDE_INT size;

  if (TARGET_64BIT)
    {
      if (ix86_function_type_abi (fntype) == MS_ABI)
	{
	  size = int_size_in_bytes (type);

	  /* __m128 is returned in xmm0.  */
	  if ((!type || VECTOR_INTEGER_TYPE_P (type)
	       || INTEGRAL_TYPE_P (type)
	       || VECTOR_FLOAT_TYPE_P (type))
	      && (SCALAR_INT_MODE_P (mode) || VECTOR_MODE_P (mode))
	      && !COMPLEX_MODE_P (mode)
	      && (GET_MODE_SIZE (mode) == 16 || size == 16))
	    return false;

	  /* Otherwise, the size must be exactly in [1248]. */
	  return size != 1 && size != 2 && size != 4 && size != 8;
	}
      else
	{
	  int needed_intregs, needed_sseregs;

	  return examine_argument (mode, type, 1,
				   &needed_intregs, &needed_sseregs);
	}
    }
  else
    {
      size = int_size_in_bytes (type);

      /* Intel MCU psABI returns scalars and aggregates no larger than 8
	 bytes in registers.  */
      if (TARGET_IAMCU)
	return VECTOR_MODE_P (mode) || size < 0 || size > 8;

      if (mode == BLKmode)
	return true;

      if (MS_AGGREGATE_RETURN && AGGREGATE_TYPE_P (type) && size <= 8)
	return false;

      if (VECTOR_MODE_P (mode) || mode == TImode)
	{
	  /* User-created vectors small enough to fit in EAX.  */
	  if (size < 8)
	    return false;

	  /* Unless ABI prescibes otherwise,
	     MMX/3dNow values are returned in MM0 if available.  */
	     
	  if (size == 8)
	    return TARGET_VECT8_RETURNS || !TARGET_MMX;

	  /* SSE values are returned in XMM0 if available.  */
	  if (size == 16)
	    return !TARGET_SSE;

	  /* AVX values are returned in YMM0 if available.  */
	  if (size == 32)
	    return !TARGET_AVX;

	  /* AVX512F values are returned in ZMM0 if available.  */
	  if (size == 64)
	    return !TARGET_AVX512F;
	}

      if (mode == XFmode)
	return false;

      if (size > 12)
	return true;

      /* OImode shouldn't be used directly.  */
      gcc_assert (mode != OImode);

      return false;
    }
#endif
}


/* Create the va_list data type.  */

static tree
ix86_build_builtin_va_list_64 (void)
{
  tree f_gpr, f_fpr, f_ovf, f_sav, record, type_decl;

  record = lang_hooks.types.make_type (RECORD_TYPE);
  type_decl = build_decl (BUILTINS_LOCATION,
			  TYPE_DECL, get_identifier ("__va_list_tag"), record);

  f_gpr = build_decl (BUILTINS_LOCATION,
		      FIELD_DECL, get_identifier ("gp_offset"),
		      unsigned_type_node);
  f_fpr = build_decl (BUILTINS_LOCATION,
		      FIELD_DECL, get_identifier ("fp_offset"),
		      unsigned_type_node);
  f_ovf = build_decl (BUILTINS_LOCATION,
		      FIELD_DECL, get_identifier ("overflow_arg_area"),
		      ptr_type_node);
  f_sav = build_decl (BUILTINS_LOCATION,
		      FIELD_DECL, get_identifier ("reg_save_area"),
		      ptr_type_node);

  va_list_gpr_counter_field = f_gpr;
  va_list_fpr_counter_field = f_fpr;

  DECL_FIELD_CONTEXT (f_gpr) = record;
  DECL_FIELD_CONTEXT (f_fpr) = record;
  DECL_FIELD_CONTEXT (f_ovf) = record;
  DECL_FIELD_CONTEXT (f_sav) = record;

  TYPE_STUB_DECL (record) = type_decl;
  TYPE_NAME (record) = type_decl;
  TYPE_FIELDS (record) = f_gpr;
  DECL_CHAIN (f_gpr) = f_fpr;
  DECL_CHAIN (f_fpr) = f_ovf;
  DECL_CHAIN (f_ovf) = f_sav;

  layout_type (record);

  TYPE_ATTRIBUTES (record) = tree_cons (get_identifier ("sysv_abi va_list"),
					NULL_TREE, TYPE_ATTRIBUTES (record));

  /* The correct type is an array type of one element.  */
  return build_array_type (record, build_index_type (size_zero_node));
}

/* Setup the builtin va_list data type and for 64-bit the additional
   calling convention specific va_list data types.  */

static tree
ix86_build_builtin_va_list (void)
{
  if (TARGET_64BIT)
    {
      /* Initialize ABI specific va_list builtin types.

	 In lto1, we can encounter two va_list types:
	 - one as a result of the type-merge across TUs, and
	 - the one constructed here.
	 These two types will not have the same TYPE_MAIN_VARIANT, and therefore
	 a type identity check in canonical_va_list_type based on
	 TYPE_MAIN_VARIANT (which we used to have) will not work.
	 Instead, we tag each va_list_type_node with its unique attribute, and
	 look for the attribute in the type identity check in
	 canonical_va_list_type.

	 Tagging sysv_va_list_type_node directly with the attribute is
	 problematic since it's a array of one record, which will degrade into a
	 pointer to record when used as parameter (see build_va_arg comments for
	 an example), dropping the attribute in the process.  So we tag the
	 record instead.  */

      /* For SYSV_ABI we use an array of one record.  */
      sysv_va_list_type_node = ix86_build_builtin_va_list_64 ();
	
      /* For MS_ABI we use plain pointer to argument area.  */
      tree char_ptr_type = build_pointer_type (char_type_node);
      tree attr = tree_cons (get_identifier ("ms_abi va_list"), NULL_TREE,
			     TYPE_ATTRIBUTES (char_ptr_type));
      ms_va_list_type_node = build_type_attribute_variant (char_ptr_type, attr);

      return ((ix86_abi == MS_ABI)
	      ? ms_va_list_type_node
	      : sysv_va_list_type_node);
    }
  else
    {
      /* For i386 we use plain pointer to argument area.  */
      return build_pointer_type (char_type_node);
    }
}

/* Worker function for TARGET_SETUP_INCOMING_VARARGS.  */

static void
setup_incoming_varargs_64 (CUMULATIVE_ARGS *cum)
{
  rtx save_area, mem;
  alias_set_type set;
  int i, max;

  /* GPR size of varargs save area.  */
  if (cfun->va_list_gpr_size)
    ix86_varargs_gpr_size = X86_64_REGPARM_MAX * UNITS_PER_WORD;
  else
    ix86_varargs_gpr_size = 0;

  /* FPR size of varargs save area.  We don't need it if we don't pass
     anything in SSE registers.  */
  if (TARGET_SSE && cfun->va_list_fpr_size)
    ix86_varargs_fpr_size = X86_64_SSE_REGPARM_MAX * 16;
  else
    ix86_varargs_fpr_size = 0;

  if (! ix86_varargs_gpr_size && ! ix86_varargs_fpr_size)
    return;

  save_area = frame_pointer_rtx;
  set = get_varargs_alias_set ();

  max = cum->regno + cfun->va_list_gpr_size / UNITS_PER_WORD;
  if (max > X86_64_REGPARM_MAX)
    max = X86_64_REGPARM_MAX;

  for (i = cum->regno; i < max; i++)
    {
      mem = gen_rtx_MEM (word_mode,
			 plus_constant (Pmode, save_area, i * UNITS_PER_WORD));
      MEM_NOTRAP_P (mem) = 1;
      set_mem_alias_set (mem, set);
      emit_move_insn (mem,
		      gen_rtx_REG (word_mode,
				   x86_64_int_parameter_registers[i]));
    }

  if (ix86_varargs_fpr_size)
    {
      machine_mode smode;
      rtx_code_label *label;
      rtx test;

      /* Now emit code to save SSE registers.  The AX parameter contains number
	 of SSE parameter registers used to call this function, though all we
	 actually check here is the zero/non-zero status.  */

      label = gen_label_rtx ();
      test = gen_rtx_EQ (VOIDmode, gen_rtx_REG (QImode, AX_REG), const0_rtx);
      emit_jump_insn (gen_cbranchqi4 (test, XEXP (test, 0), XEXP (test, 1),
				      label));

      /* ??? If !TARGET_SSE_TYPELESS_STORES, would we perform better if
	 we used movdqa (i.e. TImode) instead?  Perhaps even better would
	 be if we could determine the real mode of the data, via a hook
	 into pass_stdarg.  Ignore all that for now.  */
      smode = V4SFmode;
      if (crtl->stack_alignment_needed < GET_MODE_ALIGNMENT (smode))
	crtl->stack_alignment_needed = GET_MODE_ALIGNMENT (smode);

      max = cum->sse_regno + cfun->va_list_fpr_size / 16;
      if (max > X86_64_SSE_REGPARM_MAX)
	max = X86_64_SSE_REGPARM_MAX;

      for (i = cum->sse_regno; i < max; ++i)
	{
	  mem = plus_constant (Pmode, save_area,
			       i * 16 + ix86_varargs_gpr_size);
	  mem = gen_rtx_MEM (smode, mem);
	  MEM_NOTRAP_P (mem) = 1;
	  set_mem_alias_set (mem, set);
	  set_mem_align (mem, GET_MODE_ALIGNMENT (smode));

	  emit_move_insn (mem, gen_rtx_REG (smode, GET_SSE_REGNO (i)));
	}

      emit_label (label);
    }
}

static void
setup_incoming_varargs_ms_64 (CUMULATIVE_ARGS *cum)
{
  alias_set_type set = get_varargs_alias_set ();
  int i;

  /* Reset to zero, as there might be a sysv vaarg used
     before.  */
  ix86_varargs_gpr_size = 0;
  ix86_varargs_fpr_size = 0;

  for (i = cum->regno; i < X86_64_MS_REGPARM_MAX; i++)
    {
      rtx reg, mem;

      mem = gen_rtx_MEM (Pmode,
			 plus_constant (Pmode, virtual_incoming_args_rtx,
					i * UNITS_PER_WORD));
      MEM_NOTRAP_P (mem) = 1;
      set_mem_alias_set (mem, set);

      reg = gen_rtx_REG (Pmode, x86_64_ms_abi_int_parameter_registers[i]);
      emit_move_insn (mem, reg);
    }
}

static void
ix86_setup_incoming_varargs (cumulative_args_t cum_v, machine_mode mode,
			     tree type, int *, int no_rtl)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
  CUMULATIVE_ARGS next_cum;
  tree fntype;

  /* This argument doesn't appear to be used anymore.  Which is good,
     because the old code here didn't suppress rtl generation.  */
  gcc_assert (!no_rtl);

  if (!TARGET_64BIT)
    return;

  fntype = TREE_TYPE (current_function_decl);

  /* For varargs, we do not want to skip the dummy va_dcl argument.
     For stdargs, we do want to skip the last named argument.  */
  next_cum = *cum;
  if (stdarg_p (fntype))
    ix86_function_arg_advance (pack_cumulative_args (&next_cum), mode, type,
			       true);

  if (cum->call_abi == MS_ABI)
    setup_incoming_varargs_ms_64 (&next_cum);
  else
    setup_incoming_varargs_64 (&next_cum);
}

static void
ix86_setup_incoming_vararg_bounds (cumulative_args_t cum_v,
				   machine_mode mode,
				   tree type,
				   int *pretend_size ATTRIBUTE_UNUSED,
				   int no_rtl)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);
  CUMULATIVE_ARGS next_cum;
  tree fntype;
  int max;

  gcc_assert (!no_rtl);

  /* Do nothing if we use plain pointer to argument area.  */
  if (!TARGET_64BIT || cum->call_abi == MS_ABI)
    return;

  fntype = TREE_TYPE (current_function_decl);

  /* For varargs, we do not want to skip the dummy va_dcl argument.
     For stdargs, we do want to skip the last named argument.  */
  next_cum = *cum;
  if (stdarg_p (fntype))
    ix86_function_arg_advance (pack_cumulative_args (&next_cum), mode, type,
			       true);

  max = cum->regno + cfun->va_list_gpr_size / UNITS_PER_WORD;
  if (max > X86_64_REGPARM_MAX)
    max = X86_64_REGPARM_MAX;
}


/* Checks if TYPE is of kind va_list char *.  */

static bool
is_va_list_char_pointer (tree type)
{
  tree canonic;

  /* For 32-bit it is always true.  */
  if (!TARGET_64BIT)
    return true;
  canonic = ix86_canonical_va_list_type (type);
  return (canonic == ms_va_list_type_node
          || (ix86_abi == MS_ABI && canonic == va_list_type_node));
}

/* Implement va_start.  */

static void
ix86_va_start (tree valist, rtx nextarg)
{
  HOST_WIDE_INT words, n_gpr, n_fpr;
  tree f_gpr, f_fpr, f_ovf, f_sav;
  tree gpr, fpr, ovf, sav, t;
  tree type;
  rtx ovf_rtx;

  if (flag_split_stack
      && cfun->machine->split_stack_varargs_pointer == NULL_RTX)
    {
      unsigned int scratch_regno;

      /* When we are splitting the stack, we can't refer to the stack
	 arguments using internal_arg_pointer, because they may be on
	 the old stack.  The split stack prologue will arrange to
	 leave a pointer to the old stack arguments in a scratch
	 register, which we here copy to a pseudo-register.  The split
	 stack prologue can't set the pseudo-register directly because
	 it (the prologue) runs before any registers have been saved.  */

      scratch_regno = split_stack_prologue_scratch_regno ();
      if (scratch_regno != INVALID_REGNUM)
	{
	  rtx reg;
	  rtx_insn *seq;

	  reg = gen_reg_rtx (Pmode);
	  cfun->machine->split_stack_varargs_pointer = reg;

	  start_sequence ();
	  emit_move_insn (reg, gen_rtx_REG (Pmode, scratch_regno));
	  seq = get_insns ();
	  end_sequence ();

	  push_topmost_sequence ();
	  emit_insn_after (seq, entry_of_function ());
	  pop_topmost_sequence ();
	}
    }

  /* Only 64bit target needs something special.  */
  if (is_va_list_char_pointer (TREE_TYPE (valist)))
    {
      if (cfun->machine->split_stack_varargs_pointer == NULL_RTX)
	std_expand_builtin_va_start (valist, nextarg);
      else
	{
	  rtx va_r, next;

	  va_r = expand_expr (valist, NULL_RTX, VOIDmode, EXPAND_WRITE);
	  next = expand_binop (ptr_mode, add_optab,
			       cfun->machine->split_stack_varargs_pointer,
			       crtl->args.arg_offset_rtx,
			       NULL_RTX, 0, OPTAB_LIB_WIDEN);
	  convert_move (va_r, next, 0);
	}
      return;
    }

  f_gpr = TYPE_FIELDS (TREE_TYPE (sysv_va_list_type_node));
  f_fpr = DECL_CHAIN (f_gpr);
  f_ovf = DECL_CHAIN (f_fpr);
  f_sav = DECL_CHAIN (f_ovf);

  valist = build_simple_mem_ref (valist);
  TREE_TYPE (valist) = TREE_TYPE (sysv_va_list_type_node);
  /* The following should be folded into the MEM_REF offset.  */
  gpr = build3 (COMPONENT_REF, TREE_TYPE (f_gpr), unshare_expr (valist),
		f_gpr, NULL_TREE);
  fpr = build3 (COMPONENT_REF, TREE_TYPE (f_fpr), unshare_expr (valist),
		f_fpr, NULL_TREE);
  ovf = build3 (COMPONENT_REF, TREE_TYPE (f_ovf), unshare_expr (valist),
		f_ovf, NULL_TREE);
  sav = build3 (COMPONENT_REF, TREE_TYPE (f_sav), unshare_expr (valist),
		f_sav, NULL_TREE);

  /* Count number of gp and fp argument registers used.  */
  words = crtl->args.info.words;
  n_gpr = crtl->args.info.regno;
  n_fpr = crtl->args.info.sse_regno;

  if (cfun->va_list_gpr_size)
    {
      type = TREE_TYPE (gpr);
      t = build2 (MODIFY_EXPR, type,
		  gpr, build_int_cst (type, n_gpr * 8));
      TREE_SIDE_EFFECTS (t) = 1;
      expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
    }

  if (TARGET_SSE && cfun->va_list_fpr_size)
    {
      type = TREE_TYPE (fpr);
      t = build2 (MODIFY_EXPR, type, fpr,
		  build_int_cst (type, n_fpr * 16 + 8*X86_64_REGPARM_MAX));
      TREE_SIDE_EFFECTS (t) = 1;
      expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
    }

  /* Find the overflow area.  */
  type = TREE_TYPE (ovf);
  if (cfun->machine->split_stack_varargs_pointer == NULL_RTX)
    ovf_rtx = crtl->args.internal_arg_pointer;
  else
    ovf_rtx = cfun->machine->split_stack_varargs_pointer;
  t = make_tree (type, ovf_rtx);
  if (words != 0)
    t = fold_build_pointer_plus_hwi (t, words * UNITS_PER_WORD);

  t = build2 (MODIFY_EXPR, type, ovf, t);
  TREE_SIDE_EFFECTS (t) = 1;
  expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);

  if (ix86_varargs_gpr_size || ix86_varargs_fpr_size)
    {
      /* Find the register save area.
	 Prologue of the function save it right above stack frame.  */
      type = TREE_TYPE (sav);
      t = make_tree (type, frame_pointer_rtx);
      if (!ix86_varargs_gpr_size)
	t = fold_build_pointer_plus_hwi (t, -8 * X86_64_REGPARM_MAX);

      t = build2 (MODIFY_EXPR, type, sav, t);
      TREE_SIDE_EFFECTS (t) = 1;
      expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
    }
}

/* Implement va_arg.  */

static tree
ix86_gimplify_va_arg (tree valist, tree type, gimple_seq *pre_p,
		      gimple_seq *post_p)
{
  static const int intreg[6] = { 0, 1, 2, 3, 4, 5 };
  tree f_gpr, f_fpr, f_ovf, f_sav;
  tree gpr, fpr, ovf, sav, t;
  int size, rsize;
  tree lab_false, lab_over = NULL_TREE;
  tree addr, t2;
  rtx container;
  int indirect_p = 0;
  tree ptrtype;
  machine_mode nat_mode;
  unsigned int arg_boundary;

  /* Only 64bit target needs something special.  */
  if (is_va_list_char_pointer (TREE_TYPE (valist)))
    return std_gimplify_va_arg_expr (valist, type, pre_p, post_p);

  f_gpr = TYPE_FIELDS (TREE_TYPE (sysv_va_list_type_node));
  f_fpr = DECL_CHAIN (f_gpr);
  f_ovf = DECL_CHAIN (f_fpr);
  f_sav = DECL_CHAIN (f_ovf);

  gpr = build3 (COMPONENT_REF, TREE_TYPE (f_gpr),
		valist, f_gpr, NULL_TREE);

  fpr = build3 (COMPONENT_REF, TREE_TYPE (f_fpr), valist, f_fpr, NULL_TREE);
  ovf = build3 (COMPONENT_REF, TREE_TYPE (f_ovf), valist, f_ovf, NULL_TREE);
  sav = build3 (COMPONENT_REF, TREE_TYPE (f_sav), valist, f_sav, NULL_TREE);

  indirect_p = pass_by_reference (NULL, TYPE_MODE (type), type, false);
  if (indirect_p)
    type = build_pointer_type (type);
  size = arg_int_size_in_bytes (type);
  rsize = CEIL (size, UNITS_PER_WORD);

  nat_mode = type_natural_mode (type, NULL, false);
  switch (nat_mode)
    {
    case E_V8SFmode:
    case E_V8SImode:
    case E_V32QImode:
    case E_V16HImode:
    case E_V4DFmode:
    case E_V4DImode:
    case E_V16SFmode:
    case E_V16SImode:
    case E_V64QImode:
    case E_V32HImode:
    case E_V8DFmode:
    case E_V8DImode:
      /* Unnamed 256 and 512bit vector mode parameters are passed on stack.  */
      if (!TARGET_64BIT_MS_ABI)
	{
	  container = NULL;
	  break;
	}
      /* FALLTHRU */

    default:
      container = construct_container (nat_mode, TYPE_MODE (type),
				       type, 0, X86_64_REGPARM_MAX,
				       X86_64_SSE_REGPARM_MAX, intreg,
				       0);
      break;
    }

  /* Pull the value out of the saved registers.  */

  addr = create_tmp_var (ptr_type_node, "addr");

  if (container)
    {
      int needed_intregs, needed_sseregs;
      bool need_temp;
      tree int_addr, sse_addr;

      lab_false = create_artificial_label (UNKNOWN_LOCATION);
      lab_over = create_artificial_label (UNKNOWN_LOCATION);

      examine_argument (nat_mode, type, 0, &needed_intregs, &needed_sseregs);

      need_temp = (!REG_P (container)
		   && ((needed_intregs && TYPE_ALIGN (type) > 64)
		       || TYPE_ALIGN (type) > 128));

      /* In case we are passing structure, verify that it is consecutive block
         on the register save area.  If not we need to do moves.  */
      if (!need_temp && !REG_P (container))
	{
	  /* Verify that all registers are strictly consecutive  */
	  if (SSE_REGNO_P (REGNO (XEXP (XVECEXP (container, 0, 0), 0))))
	    {
	      int i;

	      for (i = 0; i < XVECLEN (container, 0) && !need_temp; i++)
		{
		  rtx slot = XVECEXP (container, 0, i);
		  if (REGNO (XEXP (slot, 0)) != FIRST_SSE_REG + (unsigned int) i
		      || INTVAL (XEXP (slot, 1)) != i * 16)
		    need_temp = true;
		}
	    }
	  else
	    {
	      int i;

	      for (i = 0; i < XVECLEN (container, 0) && !need_temp; i++)
		{
		  rtx slot = XVECEXP (container, 0, i);
		  if (REGNO (XEXP (slot, 0)) != (unsigned int) i
		      || INTVAL (XEXP (slot, 1)) != i * 8)
		    need_temp = true;
		}
	    }
	}
      if (!need_temp)
	{
	  int_addr = addr;
	  sse_addr = addr;
	}
      else
	{
	  int_addr = create_tmp_var (ptr_type_node, "int_addr");
	  sse_addr = create_tmp_var (ptr_type_node, "sse_addr");
	}

      /* First ensure that we fit completely in registers.  */
      if (needed_intregs)
	{
	  t = build_int_cst (TREE_TYPE (gpr),
			     (X86_64_REGPARM_MAX - needed_intregs + 1) * 8);
	  t = build2 (GE_EXPR, boolean_type_node, gpr, t);
	  t2 = build1 (GOTO_EXPR, void_type_node, lab_false);
	  t = build3 (COND_EXPR, void_type_node, t, t2, NULL_TREE);
	  gimplify_and_add (t, pre_p);
	}
      if (needed_sseregs)
	{
	  t = build_int_cst (TREE_TYPE (fpr),
			     (X86_64_SSE_REGPARM_MAX - needed_sseregs + 1) * 16
			     + X86_64_REGPARM_MAX * 8);
	  t = build2 (GE_EXPR, boolean_type_node, fpr, t);
	  t2 = build1 (GOTO_EXPR, void_type_node, lab_false);
	  t = build3 (COND_EXPR, void_type_node, t, t2, NULL_TREE);
	  gimplify_and_add (t, pre_p);
	}

      /* Compute index to start of area used for integer regs.  */
      if (needed_intregs)
	{
	  /* int_addr = gpr + sav; */
	  t = fold_build_pointer_plus (sav, gpr);
	  gimplify_assign (int_addr, t, pre_p);
	}
      if (needed_sseregs)
	{
	  /* sse_addr = fpr + sav; */
	  t = fold_build_pointer_plus (sav, fpr);
	  gimplify_assign (sse_addr, t, pre_p);
	}
      if (need_temp)
	{
	  int i, prev_size = 0;
	  tree temp = create_tmp_var (type, "va_arg_tmp");

	  /* addr = &temp; */
	  t = build1 (ADDR_EXPR, build_pointer_type (type), temp);
	  gimplify_assign (addr, t, pre_p);

	  for (i = 0; i < XVECLEN (container, 0); i++)
	    {
	      rtx slot = XVECEXP (container, 0, i);
	      rtx reg = XEXP (slot, 0);
	      machine_mode mode = GET_MODE (reg);
	      tree piece_type;
	      tree addr_type;
	      tree daddr_type;
	      tree src_addr, src;
	      int src_offset;
	      tree dest_addr, dest;
	      int cur_size = GET_MODE_SIZE (mode);

	      gcc_assert (prev_size <= INTVAL (XEXP (slot, 1)));
	      prev_size = INTVAL (XEXP (slot, 1));
	      if (prev_size + cur_size > size)
		{
		  cur_size = size - prev_size;
		  unsigned int nbits = cur_size * BITS_PER_UNIT;
		  if (!int_mode_for_size (nbits, 1).exists (&mode))
		    mode = QImode;
		}
	      piece_type = lang_hooks.types.type_for_mode (mode, 1);
	      if (mode == GET_MODE (reg))
		addr_type = build_pointer_type (piece_type);
	      else
		addr_type = build_pointer_type_for_mode (piece_type, ptr_mode,
							 true);
	      daddr_type = build_pointer_type_for_mode (piece_type, ptr_mode,
							true);

	      if (SSE_REGNO_P (REGNO (reg)))
		{
		  src_addr = sse_addr;
		  src_offset = (REGNO (reg) - FIRST_SSE_REG) * 16;
		}
	      else
		{
		  src_addr = int_addr;
		  src_offset = REGNO (reg) * 8;
		}
	      src_addr = fold_convert (addr_type, src_addr);
	      src_addr = fold_build_pointer_plus_hwi (src_addr, src_offset);

	      dest_addr = fold_convert (daddr_type, addr);
	      dest_addr = fold_build_pointer_plus_hwi (dest_addr, prev_size);
	      if (cur_size == GET_MODE_SIZE (mode))
		{
		  src = build_va_arg_indirect_ref (src_addr);
		  dest = build_va_arg_indirect_ref (dest_addr);

		  gimplify_assign (dest, src, pre_p);
		}
	      else
		{
		  tree copy
		    = build_call_expr (builtin_decl_implicit (BUILT_IN_MEMCPY),
				       3, dest_addr, src_addr,
				       size_int (cur_size));
		  gimplify_and_add (copy, pre_p);
		}
	      prev_size += cur_size;
	    }
	}

      if (needed_intregs)
	{
	  t = build2 (PLUS_EXPR, TREE_TYPE (gpr), gpr,
		      build_int_cst (TREE_TYPE (gpr), needed_intregs * 8));
	  gimplify_assign (gpr, t, pre_p);
	}

      if (needed_sseregs)
	{
	  t = build2 (PLUS_EXPR, TREE_TYPE (fpr), fpr,
		      build_int_cst (TREE_TYPE (fpr), needed_sseregs * 16));
	  gimplify_assign (unshare_expr (fpr), t, pre_p);
	}

      gimple_seq_add_stmt (pre_p, gimple_build_goto (lab_over));

      gimple_seq_add_stmt (pre_p, gimple_build_label (lab_false));
    }

  /* ... otherwise out of the overflow area.  */

  /* When we align parameter on stack for caller, if the parameter
     alignment is beyond MAX_SUPPORTED_STACK_ALIGNMENT, it will be
     aligned at MAX_SUPPORTED_STACK_ALIGNMENT.  We will match callee
     here with caller.  */
  arg_boundary = ix86_function_arg_boundary (VOIDmode, type);
  if ((unsigned int) arg_boundary > MAX_SUPPORTED_STACK_ALIGNMENT)
    arg_boundary = MAX_SUPPORTED_STACK_ALIGNMENT;

  /* Care for on-stack alignment if needed.  */
  if (arg_boundary <= 64 || size == 0)
    t = ovf;
 else
    {
      HOST_WIDE_INT align = arg_boundary / 8;
      t = fold_build_pointer_plus_hwi (ovf, align - 1);
      t = build2 (BIT_AND_EXPR, TREE_TYPE (t), t,
		  build_int_cst (TREE_TYPE (t), -align));
    }

  gimplify_expr (&t, pre_p, NULL, is_gimple_val, fb_rvalue);
  gimplify_assign (addr, t, pre_p);

  t = fold_build_pointer_plus_hwi (t, rsize * UNITS_PER_WORD);
  gimplify_assign (unshare_expr (ovf), t, pre_p);

  if (container)
    gimple_seq_add_stmt (pre_p, gimple_build_label (lab_over));

  ptrtype = build_pointer_type_for_mode (type, ptr_mode, true);
  addr = fold_convert (ptrtype, addr);

  if (indirect_p)
    addr = build_va_arg_indirect_ref (addr);
  return build_va_arg_indirect_ref (addr);
}

/* Return true if OPNUM's MEM should be matched
   in movabs* patterns.  */

bool
ix86_check_movabs (rtx insn, int opnum)
{
  rtx set, mem;

  set = PATTERN (insn);
  if (GET_CODE (set) == PARALLEL)
    set = XVECEXP (set, 0, 0);
  gcc_assert (GET_CODE (set) == SET);
  mem = XEXP (set, opnum);
  while (SUBREG_P (mem))
    mem = SUBREG_REG (mem);
  gcc_assert (MEM_P (mem));
  return volatile_ok || !MEM_VOLATILE_P (mem);
}

/* Return false if INSN contains a MEM with a non-default address space.  */
bool
ix86_check_no_addr_space (rtx insn)
{
  subrtx_var_iterator::array_type array;
  FOR_EACH_SUBRTX_VAR (iter, array, PATTERN (insn), ALL)
    {
      rtx x = *iter;
      if (MEM_P (x) && !ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (x)))
	return false;
    }
  return true;
}

/* Initialize the table of extra 80387 mathematical constants.  */

static void
init_ext_80387_constants (void)
{
  static const char * cst[5] =
  {
    "0.3010299956639811952256464283594894482",  /* 0: fldlg2  */
    "0.6931471805599453094286904741849753009",  /* 1: fldln2  */
    "1.4426950408889634073876517827983434472",  /* 2: fldl2e  */
    "3.3219280948873623478083405569094566090",  /* 3: fldl2t  */
    "3.1415926535897932385128089594061862044",  /* 4: fldpi   */
  };
  int i;

  for (i = 0; i < 5; i++)
    {
      real_from_string (&ext_80387_constants_table[i], cst[i]);
      /* Ensure each constant is rounded to XFmode precision.  */
      real_convert (&ext_80387_constants_table[i],
		    XFmode, &ext_80387_constants_table[i]);
    }

  ext_80387_constants_init = 1;
}

/* Return non-zero if the constant is something that
   can be loaded with a special instruction.  */

int
standard_80387_constant_p (rtx x)
{
  machine_mode mode = GET_MODE (x);

  const REAL_VALUE_TYPE *r;

  if (!(CONST_DOUBLE_P (x) && X87_FLOAT_MODE_P (mode)))
    return -1;

  if (x == CONST0_RTX (mode))
    return 1;
  if (x == CONST1_RTX (mode))
    return 2;

  r = CONST_DOUBLE_REAL_VALUE (x);

  /* For XFmode constants, try to find a special 80387 instruction when
     optimizing for size or on those CPUs that benefit from them.  */
  if (mode == XFmode
      && (optimize_function_for_size_p (cfun) || TARGET_EXT_80387_CONSTANTS))
    {
      int i;

      if (! ext_80387_constants_init)
	init_ext_80387_constants ();

      for (i = 0; i < 5; i++)
        if (real_identical (r, &ext_80387_constants_table[i]))
	  return i + 3;
    }

  /* Load of the constant -0.0 or -1.0 will be split as
     fldz;fchs or fld1;fchs sequence.  */
  if (real_isnegzero (r))
    return 8;
  if (real_identical (r, &dconstm1))
    return 9;

  return 0;
}

/* Return the opcode of the special instruction to be used to load
   the constant X.  */

const char *
standard_80387_constant_opcode (rtx x)
{
  switch (standard_80387_constant_p (x))
    {
    case 1:
      return "fldz";
    case 2:
      return "fld1";
    case 3:
      return "fldlg2";
    case 4:
      return "fldln2";
    case 5:
      return "fldl2e";
    case 6:
      return "fldl2t";
    case 7:
      return "fldpi";
    case 8:
    case 9:
      return "#";
    default:
      gcc_unreachable ();
    }
}

/* Return the CONST_DOUBLE representing the 80387 constant that is
   loaded by the specified special instruction.  The argument IDX
   matches the return value from standard_80387_constant_p.  */

rtx
standard_80387_constant_rtx (int idx)
{
  int i;

  if (! ext_80387_constants_init)
    init_ext_80387_constants ();

  switch (idx)
    {
    case 3:
    case 4:
    case 5:
    case 6:
    case 7:
      i = idx - 3;
      break;

    default:
      gcc_unreachable ();
    }

  return const_double_from_real_value (ext_80387_constants_table[i],
				       XFmode);
}

/* Return 1 if X is all bits 0 and 2 if X is all bits 1
   in supported SSE/AVX vector mode.  */

int
standard_sse_constant_p (rtx x, machine_mode pred_mode)
{
  machine_mode mode;

  if (!TARGET_SSE)
    return 0;

  mode = GET_MODE (x);

  if (x == const0_rtx || const0_operand (x, mode))
    return 1;

  if (x == constm1_rtx || vector_all_ones_operand (x, mode))
    {
      /* VOIDmode integer constant, get mode from the predicate.  */
      if (mode == VOIDmode)
	mode = pred_mode;

      switch (GET_MODE_SIZE (mode))
	{
	case 64:
	  if (TARGET_AVX512F)
	    return 2;
	  break;
	case 32:
	  if (TARGET_AVX2)
	    return 2;
	  break;
	case 16:
	  if (TARGET_SSE2)
	    return 2;
	  break;
	case 0:
	  /* VOIDmode */
	  gcc_unreachable ();
	default:
	  break;
	}
    }

  return 0;
}

/* Return the opcode of the special instruction to be used to load
   the constant operands[1] into operands[0].  */

const char *
standard_sse_constant_opcode (rtx_insn *insn, rtx *operands)
{
  machine_mode mode;
  rtx x = operands[1];

  gcc_assert (TARGET_SSE);

  mode = GET_MODE (x);

  if (x == const0_rtx || const0_operand (x, mode))
    {
      switch (get_attr_mode (insn))
	{
	case MODE_TI:
	  if (!EXT_REX_SSE_REG_P (operands[0]))
	    return "%vpxor\t%0, %d0";
	  /* FALLTHRU */
	case MODE_XI:
	case MODE_OI:
	  if (EXT_REX_SSE_REG_P (operands[0]))
	    return (TARGET_AVX512VL
		    ? "vpxord\t%x0, %x0, %x0"
		    : "vpxord\t%g0, %g0, %g0");
	  return "vpxor\t%x0, %x0, %x0";

	case MODE_V2DF:
	  if (!EXT_REX_SSE_REG_P (operands[0]))
	    return "%vxorpd\t%0, %d0";
	  /* FALLTHRU */
	case MODE_V8DF:
	case MODE_V4DF:
	  if (!EXT_REX_SSE_REG_P (operands[0]))
	    return "vxorpd\t%x0, %x0, %x0";
	  else if (TARGET_AVX512DQ)
	    return (TARGET_AVX512VL
		    ? "vxorpd\t%x0, %x0, %x0"
		    : "vxorpd\t%g0, %g0, %g0");
	  else
	    return (TARGET_AVX512VL
		    ? "vpxorq\t%x0, %x0, %x0"
		    : "vpxorq\t%g0, %g0, %g0");

	case MODE_V4SF:
	  if (!EXT_REX_SSE_REG_P (operands[0]))
	    return "%vxorps\t%0, %d0";
	  /* FALLTHRU */
	case MODE_V16SF:
	case MODE_V8SF:
	  if (!EXT_REX_SSE_REG_P (operands[0]))
	    return "vxorps\t%x0, %x0, %x0";
	  else if (TARGET_AVX512DQ)
	    return (TARGET_AVX512VL
		    ? "vxorps\t%x0, %x0, %x0"
		    : "vxorps\t%g0, %g0, %g0");
	  else
	    return (TARGET_AVX512VL
		    ? "vpxord\t%x0, %x0, %x0"
		    : "vpxord\t%g0, %g0, %g0");

	default:
	  gcc_unreachable ();
	}
    }
  else if (x == constm1_rtx || vector_all_ones_operand (x, mode))
    {
      enum attr_mode insn_mode = get_attr_mode (insn);
      
      switch (insn_mode)
	{
	case MODE_XI:
	case MODE_V8DF:
	case MODE_V16SF:
	  gcc_assert (TARGET_AVX512F);
	  return "vpternlogd\t{$0xFF, %g0, %g0, %g0|%g0, %g0, %g0, 0xFF}";

	case MODE_OI:
	case MODE_V4DF:
	case MODE_V8SF:
	  gcc_assert (TARGET_AVX2);
	  /* FALLTHRU */
	case MODE_TI:
	case MODE_V2DF:
	case MODE_V4SF:
	  gcc_assert (TARGET_SSE2);
	  if (!EXT_REX_SSE_REG_P (operands[0]))
	    return (TARGET_AVX
		    ? "vpcmpeqd\t%0, %0, %0"
		    : "pcmpeqd\t%0, %0");
	  else if (TARGET_AVX512VL)
	    return "vpternlogd\t{$0xFF, %0, %0, %0|%0, %0, %0, 0xFF}";
	  else
	    return "vpternlogd\t{$0xFF, %g0, %g0, %g0|%g0, %g0, %g0, 0xFF}";

	default:
	  gcc_unreachable ();
	}
   }

  gcc_unreachable ();
}

/* Returns true if INSN can be transformed from a memory load
   to a supported FP constant load.  */

bool
ix86_standard_x87sse_constant_load_p (const rtx_insn *insn, rtx dst)
{
  rtx src = find_constant_src (insn);

  gcc_assert (REG_P (dst));

  if (src == NULL
      || (SSE_REGNO_P (REGNO (dst))
	  && standard_sse_constant_p (src, GET_MODE (dst)) != 1)
      || (STACK_REGNO_P (REGNO (dst))
	   && standard_80387_constant_p (src) < 1))
    return false;

  return true;
}

/* Returns true if OP contains a symbol reference */

bool
symbolic_reference_mentioned_p (rtx op)
{
  const char *fmt;
  int i;

  if (GET_CODE (op) == SYMBOL_REF || GET_CODE (op) == LABEL_REF)
    return true;

  fmt = GET_RTX_FORMAT (GET_CODE (op));
  for (i = GET_RTX_LENGTH (GET_CODE (op)) - 1; i >= 0; i--)
    {
      if (fmt[i] == 'E')
	{
	  int j;

	  for (j = XVECLEN (op, i) - 1; j >= 0; j--)
	    if (symbolic_reference_mentioned_p (XVECEXP (op, i, j)))
	      return true;
	}

      else if (fmt[i] == 'e' && symbolic_reference_mentioned_p (XEXP (op, i)))
	return true;
    }

  return false;
}

/* Return true if it is appropriate to emit `ret' instructions in the
   body of a function.  Do this only if the epilogue is simple, needing a
   couple of insns.  Prior to reloading, we can't tell how many registers
   must be saved, so return false then.  Return false if there is no frame
   marker to de-allocate.  */

bool
ix86_can_use_return_insn_p (void)
{
  if (ix86_function_naked (current_function_decl))
    return false;

  /* Don't use `ret' instruction in interrupt handler.  */
  if (! reload_completed
      || frame_pointer_needed
      || cfun->machine->func_type != TYPE_NORMAL)
    return 0;

  /* Don't allow more than 32k pop, since that's all we can do
     with one instruction.  */
  if (crtl->args.pops_args && crtl->args.size >= 32768)
    return 0;

  struct ix86_frame &frame = cfun->machine->frame;
  return (frame.stack_pointer_offset == UNITS_PER_WORD
	  && (frame.nregs + frame.nsseregs) == 0);
}

/* Value should be nonzero if functions must have frame pointers.
   Zero means the frame pointer need not be set up (and parms may
   be accessed via the stack pointer) in functions that seem suitable.  */

static bool
ix86_frame_pointer_required (void)
{
  /* If we accessed previous frames, then the generated code expects
     to be able to access the saved ebp value in our frame.  */
  if (cfun->machine->accesses_prev_frame)
    return true;

  /* Several x86 os'es need a frame pointer for other reasons,
     usually pertaining to setjmp.  */
  if (SUBTARGET_FRAME_POINTER_REQUIRED)
    return true;

  /* For older 32-bit runtimes setjmp requires valid frame-pointer.  */
  if (TARGET_32BIT_MS_ABI && cfun->calls_setjmp)
    return true;

  /* Win64 SEH, very large frames need a frame-pointer as maximum stack
     allocation is 4GB.  */
  if (TARGET_64BIT_MS_ABI && get_frame_size () > SEH_MAX_FRAME_SIZE)
    return true;

  /* SSE saves require frame-pointer when stack is misaligned.  */
  if (TARGET_64BIT_MS_ABI && ix86_incoming_stack_boundary < 128)
    return true;
  
  /* In ix86_option_override_internal, TARGET_OMIT_LEAF_FRAME_POINTER
     turns off the frame pointer by default.  Turn it back on now if
     we've not got a leaf function.  */
  if (TARGET_OMIT_LEAF_FRAME_POINTER
      && (!crtl->is_leaf
	  || ix86_current_function_calls_tls_descriptor))
    return true;

  if (crtl->profile && !flag_fentry)
    return true;

  return false;
}

/* Record that the current function accesses previous call frames.  */

void
ix86_setup_frame_addresses (void)
{
  cfun->machine->accesses_prev_frame = 1;
}

#ifndef USE_HIDDEN_LINKONCE
# if defined(HAVE_GAS_HIDDEN) && (SUPPORTS_ONE_ONLY - 0)
#  define USE_HIDDEN_LINKONCE 1
# else
#  define USE_HIDDEN_LINKONCE 0
# endif
#endif

/* Label count for call and return thunks.  It is used to make unique
   labels in call and return thunks.  */
static int indirectlabelno;

/* True if call thunk function is needed.  */
static bool indirect_thunk_needed = false;

/* Bit masks of integer registers, which contain branch target, used
   by call thunk functions.  */
static int indirect_thunks_used;

/* True if return thunk function is needed.  */
static bool indirect_return_needed = false;

/* True if return thunk function via CX is needed.  */
static bool indirect_return_via_cx;

#ifndef INDIRECT_LABEL
# define INDIRECT_LABEL "LIND"
#endif

/* Indicate what prefix is needed for an indirect branch.  */
enum indirect_thunk_prefix
{
  indirect_thunk_prefix_none,
  indirect_thunk_prefix_nt
};

/* Return the prefix needed for an indirect branch INSN.  */

enum indirect_thunk_prefix
indirect_thunk_need_prefix (rtx_insn *insn)
{
  enum indirect_thunk_prefix need_prefix;
  if ((cfun->machine->indirect_branch_type
	    == indirect_branch_thunk_extern)
	   && ix86_notrack_prefixed_insn_p (insn))
    {
      /* NOTRACK prefix is only used with external thunk so that it
	 can be properly updated to support CET at run-time.  */
      need_prefix = indirect_thunk_prefix_nt;
    }
  else
    need_prefix = indirect_thunk_prefix_none;
  return need_prefix;
}

/* Fills in the label name that should be used for the indirect thunk.  */

static void
indirect_thunk_name (char name[32], unsigned int regno,
		     enum indirect_thunk_prefix need_prefix,
		     bool ret_p)
{
  if (regno != INVALID_REGNUM && regno != CX_REG && ret_p)
    gcc_unreachable ();

  if (USE_HIDDEN_LINKONCE)
    {
      const char *prefix;

      if (need_prefix == indirect_thunk_prefix_nt
	  && regno != INVALID_REGNUM)
	{
	  /* NOTRACK prefix is only used with external thunk via
	     register so that NOTRACK prefix can be added to indirect
	     branch via register to support CET at run-time.  */
	  prefix = "_nt";
	}
      else
	prefix = "";

      const char *ret = ret_p ? "return" : "indirect";

      if (regno != INVALID_REGNUM)
	{
	  const char *reg_prefix;
	  if (LEGACY_INT_REGNO_P (regno))
	    reg_prefix = TARGET_64BIT ? "r" : "e";
	  else
	    reg_prefix = "";
	  sprintf (name, "__x86_%s_thunk%s_%s%s",
		   ret, prefix, reg_prefix, reg_names[regno]);
	}
      else
	sprintf (name, "__x86_%s_thunk%s", ret, prefix);
    }
  else
    {
      if (regno != INVALID_REGNUM)
	ASM_GENERATE_INTERNAL_LABEL (name, "LITR", regno);
      else
	{
	  if (ret_p)
	    ASM_GENERATE_INTERNAL_LABEL (name, "LRT", 0);
	  else
	    ASM_GENERATE_INTERNAL_LABEL (name, "LIT", 0);
	}
    }
}

/* Output a call and return thunk for indirect branch.  If REGNO != -1,
   the function address is in REGNO and the call and return thunk looks like:

	call	L2
   L1:
	pause
	lfence
	jmp	L1
   L2:
	mov	%REG, (%sp)
	ret

   Otherwise, the function address is on the top of stack and the
   call and return thunk looks like:

	call L2
  L1:
	pause
	lfence
	jmp L1
  L2:
	lea WORD_SIZE(%sp), %sp
	ret
 */

static void
output_indirect_thunk (unsigned int regno)
{
  char indirectlabel1[32];
  char indirectlabel2[32];

  ASM_GENERATE_INTERNAL_LABEL (indirectlabel1, INDIRECT_LABEL,
			       indirectlabelno++);
  ASM_GENERATE_INTERNAL_LABEL (indirectlabel2, INDIRECT_LABEL,
			       indirectlabelno++);

  /* Call */
  fputs ("\tcall\t", asm_out_file);
  assemble_name_raw (asm_out_file, indirectlabel2);
  fputc ('\n', asm_out_file);

  ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, indirectlabel1);

  /* AMD and Intel CPUs prefer each a different instruction as loop filler.
     Usage of both pause + lfence is compromise solution.  */
  fprintf (asm_out_file, "\tpause\n\tlfence\n");

  /* Jump.  */
  fputs ("\tjmp\t", asm_out_file);
  assemble_name_raw (asm_out_file, indirectlabel1);
  fputc ('\n', asm_out_file);

  ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, indirectlabel2);

  /* The above call insn pushed a word to stack.  Adjust CFI info.  */
  if (flag_asynchronous_unwind_tables && dwarf2out_do_frame ())
    {
      if (! dwarf2out_do_cfi_asm ())
	{
	  dw_cfi_ref xcfi = ggc_cleared_alloc<dw_cfi_node> ();
	  xcfi->dw_cfi_opc = DW_CFA_advance_loc4;
	  xcfi->dw_cfi_oprnd1.dw_cfi_addr = ggc_strdup (indirectlabel2);
	  vec_safe_push (cfun->fde->dw_fde_cfi, xcfi);
	}
      dw_cfi_ref xcfi = ggc_cleared_alloc<dw_cfi_node> ();
      xcfi->dw_cfi_opc = DW_CFA_def_cfa_offset;
      xcfi->dw_cfi_oprnd1.dw_cfi_offset = 2 * UNITS_PER_WORD;
      vec_safe_push (cfun->fde->dw_fde_cfi, xcfi);
      dwarf2out_emit_cfi (xcfi);
    }

  if (regno != INVALID_REGNUM)
    {
      /* MOV.  */
      rtx xops[2];
      xops[0] = gen_rtx_MEM (word_mode, stack_pointer_rtx);
      xops[1] = gen_rtx_REG (word_mode, regno);
      output_asm_insn ("mov\t{%1, %0|%0, %1}", xops);
    }
  else
    {
      /* LEA.  */
      rtx xops[2];
      xops[0] = stack_pointer_rtx;
      xops[1] = plus_constant (Pmode, stack_pointer_rtx, UNITS_PER_WORD);
      output_asm_insn ("lea\t{%E1, %0|%0, %E1}", xops);
    }

  fputs ("\tret\n", asm_out_file);
}

/* Output a funtion with a call and return thunk for indirect branch.
   If REGNO != INVALID_REGNUM, the function address is in REGNO.
   Otherwise, the function address is on the top of stack.  Thunk is
   used for function return if RET_P is true.  */

static void
output_indirect_thunk_function (enum indirect_thunk_prefix need_prefix,
				unsigned int regno, bool ret_p)
{
  char name[32];
  tree decl;

  /* Create __x86_indirect_thunk.  */
  indirect_thunk_name (name, regno, need_prefix, ret_p);
  decl = build_decl (BUILTINS_LOCATION, FUNCTION_DECL,
		     get_identifier (name),
		     build_function_type_list (void_type_node, NULL_TREE));
  DECL_RESULT (decl) = build_decl (BUILTINS_LOCATION, RESULT_DECL,
				   NULL_TREE, void_type_node);
  TREE_PUBLIC (decl) = 1;
  TREE_STATIC (decl) = 1;
  DECL_IGNORED_P (decl) = 1;

#if TARGET_MACHO
  if (TARGET_MACHO)
    {
      switch_to_section (darwin_sections[picbase_thunk_section]);
      fputs ("\t.weak_definition\t", asm_out_file);
      assemble_name (asm_out_file, name);
      fputs ("\n\t.private_extern\t", asm_out_file);
      assemble_name (asm_out_file, name);
      putc ('\n', asm_out_file);
      ASM_OUTPUT_LABEL (asm_out_file, name);
      DECL_WEAK (decl) = 1;
    }
  else
#endif
    if (USE_HIDDEN_LINKONCE)
      {
	cgraph_node::create (decl)->set_comdat_group (DECL_ASSEMBLER_NAME (decl));

	targetm.asm_out.unique_section (decl, 0);
	switch_to_section (get_named_section (decl, NULL, 0));

	targetm.asm_out.globalize_label (asm_out_file, name);
	fputs ("\t.hidden\t", asm_out_file);
	assemble_name (asm_out_file, name);
	putc ('\n', asm_out_file);
	ASM_DECLARE_FUNCTION_NAME (asm_out_file, name, decl);
      }
    else
      {
	switch_to_section (text_section);
	ASM_OUTPUT_LABEL (asm_out_file, name);
      }

  DECL_INITIAL (decl) = make_node (BLOCK);
  current_function_decl = decl;
  allocate_struct_function (decl, false);
  init_function_start (decl);
  /* We're about to hide the function body from callees of final_* by
     emitting it directly; tell them we're a thunk, if they care.  */
  cfun->is_thunk = true;
  first_function_block_is_cold = false;
  /* Make sure unwind info is emitted for the thunk if needed.  */
  final_start_function (emit_barrier (), asm_out_file, 1);

  output_indirect_thunk (regno);

  final_end_function ();
  init_insn_lengths ();
  free_after_compilation (cfun);
  set_cfun (NULL);
  current_function_decl = NULL;
}

static int pic_labels_used;

/* Fills in the label name that should be used for a pc thunk for
   the given register.  */

static void
get_pc_thunk_name (char name[32], unsigned int regno)
{
  gcc_assert (!TARGET_64BIT);

  if (USE_HIDDEN_LINKONCE)
    sprintf (name, "__x86.get_pc_thunk.%s", reg_names[regno]);
  else
    ASM_GENERATE_INTERNAL_LABEL (name, "LPR", regno);
}


/* This function generates code for -fpic that loads %ebx with
   the return address of the caller and then returns.  */

static void
ix86_code_end (void)
{
  rtx xops[2];
  unsigned int regno;

  if (indirect_return_needed)
    output_indirect_thunk_function (indirect_thunk_prefix_none,
				    INVALID_REGNUM, true);
  if (indirect_return_via_cx)
    output_indirect_thunk_function (indirect_thunk_prefix_none,
				    CX_REG, true);
  if (indirect_thunk_needed)
    output_indirect_thunk_function (indirect_thunk_prefix_none,
				    INVALID_REGNUM, false);

  for (regno = FIRST_REX_INT_REG; regno <= LAST_REX_INT_REG; regno++)
    {
      unsigned int i = regno - FIRST_REX_INT_REG + LAST_INT_REG + 1;
      if ((indirect_thunks_used & (1 << i)))
	output_indirect_thunk_function (indirect_thunk_prefix_none,
					regno, false);
    }

  for (regno = FIRST_INT_REG; regno <= LAST_INT_REG; regno++)
    {
      char name[32];
      tree decl;

      if ((indirect_thunks_used & (1 << regno)))
	output_indirect_thunk_function (indirect_thunk_prefix_none,
					regno, false);

      if (!(pic_labels_used & (1 << regno)))
	continue;

      get_pc_thunk_name (name, regno);

      decl = build_decl (BUILTINS_LOCATION, FUNCTION_DECL,
			 get_identifier (name),
			 build_function_type_list (void_type_node, NULL_TREE));
      DECL_RESULT (decl) = build_decl (BUILTINS_LOCATION, RESULT_DECL,
				       NULL_TREE, void_type_node);
      TREE_PUBLIC (decl) = 1;
      TREE_STATIC (decl) = 1;
      DECL_IGNORED_P (decl) = 1;

#if TARGET_MACHO
      if (TARGET_MACHO)
	{
	  switch_to_section (darwin_sections[picbase_thunk_section]);
	  fputs ("\t.weak_definition\t", asm_out_file);
	  assemble_name (asm_out_file, name);
	  fputs ("\n\t.private_extern\t", asm_out_file);
	  assemble_name (asm_out_file, name);
	  putc ('\n', asm_out_file);
	  ASM_OUTPUT_LABEL (asm_out_file, name);
	  DECL_WEAK (decl) = 1;
	}
      else
#endif
      if (USE_HIDDEN_LINKONCE)
	{
	  cgraph_node::create (decl)->set_comdat_group (DECL_ASSEMBLER_NAME (decl));

	  targetm.asm_out.unique_section (decl, 0);
	  switch_to_section (get_named_section (decl, NULL, 0));

	  targetm.asm_out.globalize_label (asm_out_file, name);
	  fputs ("\t.hidden\t", asm_out_file);
	  assemble_name (asm_out_file, name);
	  putc ('\n', asm_out_file);
	  ASM_DECLARE_FUNCTION_NAME (asm_out_file, name, decl);
	}
      else
	{
	  switch_to_section (text_section);
	  ASM_OUTPUT_LABEL (asm_out_file, name);
	}

      DECL_INITIAL (decl) = make_node (BLOCK);
      current_function_decl = decl;
      allocate_struct_function (decl, false);
      init_function_start (decl);
      /* We're about to hide the function body from callees of final_* by
	 emitting it directly; tell them we're a thunk, if they care.  */
      cfun->is_thunk = true;
      first_function_block_is_cold = false;
      /* Make sure unwind info is emitted for the thunk if needed.  */
      final_start_function (emit_barrier (), asm_out_file, 1);

      /* Pad stack IP move with 4 instructions (two NOPs count
	 as one instruction).  */
      if (TARGET_PAD_SHORT_FUNCTION)
	{
	  int i = 8;

	  while (i--)
	    fputs ("\tnop\n", asm_out_file);
	}

      xops[0] = gen_rtx_REG (Pmode, regno);
      xops[1] = gen_rtx_MEM (Pmode, stack_pointer_rtx);
      output_asm_insn ("mov%z0\t{%1, %0|%0, %1}", xops);
      output_asm_insn ("%!ret", NULL);
      final_end_function ();
      init_insn_lengths ();
      free_after_compilation (cfun);
      set_cfun (NULL);
      current_function_decl = NULL;
    }

  if (flag_split_stack)
    file_end_indicate_split_stack ();
}

/* Emit code for the SET_GOT patterns.  */

const char *
output_set_got (rtx dest, rtx label)
{
  rtx xops[3];

  xops[0] = dest;

  if (TARGET_VXWORKS_RTP && flag_pic)
    {
      /* Load (*VXWORKS_GOTT_BASE) into the PIC register.  */
      xops[2] = gen_rtx_MEM (Pmode,
			     gen_rtx_SYMBOL_REF (Pmode, VXWORKS_GOTT_BASE));
      output_asm_insn ("mov{l}\t{%2, %0|%0, %2}", xops);

      /* Load (*VXWORKS_GOTT_BASE)[VXWORKS_GOTT_INDEX] into the PIC register.
	 Use %P and a local symbol in order to print VXWORKS_GOTT_INDEX as
	 an unadorned address.  */
      xops[2] = gen_rtx_SYMBOL_REF (Pmode, VXWORKS_GOTT_INDEX);
      SYMBOL_REF_FLAGS (xops[2]) |= SYMBOL_FLAG_LOCAL;
      output_asm_insn ("mov{l}\t{%P2(%0), %0|%0, DWORD PTR %P2[%0]}", xops);
      return "";
    }

  xops[1] = gen_rtx_SYMBOL_REF (Pmode, GOT_SYMBOL_NAME);

  if (flag_pic)
    {
      char name[32];
      get_pc_thunk_name (name, REGNO (dest));
      pic_labels_used |= 1 << REGNO (dest);

      xops[2] = gen_rtx_SYMBOL_REF (Pmode, ggc_strdup (name));
      xops[2] = gen_rtx_MEM (QImode, xops[2]);
      output_asm_insn ("%!call\t%X2", xops);

#if TARGET_MACHO
      /* Output the Mach-O "canonical" pic base label name ("Lxx$pb") here.
         This is what will be referenced by the Mach-O PIC subsystem.  */
      if (machopic_should_output_picbase_label () || !label)
	ASM_OUTPUT_LABEL (asm_out_file, MACHOPIC_FUNCTION_BASE_NAME);

      /* When we are restoring the pic base at the site of a nonlocal label,
         and we decided to emit the pic base above, we will still output a
         local label used for calculating the correction offset (even though
         the offset will be 0 in that case).  */
      if (label)
        targetm.asm_out.internal_label (asm_out_file, "L",
					   CODE_LABEL_NUMBER (label));
#endif
    }
  else
    {
      if (TARGET_MACHO)
	/* We don't need a pic base, we're not producing pic.  */
	gcc_unreachable ();

      xops[2] = gen_rtx_LABEL_REF (Pmode, label ? label : gen_label_rtx ());
      output_asm_insn ("mov%z0\t{%2, %0|%0, %2}", xops);
      targetm.asm_out.internal_label (asm_out_file, "L",
				      CODE_LABEL_NUMBER (XEXP (xops[2], 0)));
    }

  if (!TARGET_MACHO)
    output_asm_insn ("add%z0\t{%1, %0|%0, %1}", xops);

  return "";
}

/* Generate an "push" pattern for input ARG.  */

static rtx
gen_push (rtx arg)
{
  struct machine_function *m = cfun->machine;

  if (m->fs.cfa_reg == stack_pointer_rtx)
    m->fs.cfa_offset += UNITS_PER_WORD;
  m->fs.sp_offset += UNITS_PER_WORD;

  if (REG_P (arg) && GET_MODE (arg) != word_mode)
    arg = gen_rtx_REG (word_mode, REGNO (arg));

  return gen_rtx_SET (gen_rtx_MEM (word_mode,
				   gen_rtx_PRE_DEC (Pmode,
						    stack_pointer_rtx)),
		      arg);
}

/* Generate an "pop" pattern for input ARG.  */

static rtx
gen_pop (rtx arg)
{
  if (REG_P (arg) && GET_MODE (arg) != word_mode)
    arg = gen_rtx_REG (word_mode, REGNO (arg));

  return gen_rtx_SET (arg,
		      gen_rtx_MEM (word_mode,
				   gen_rtx_POST_INC (Pmode,
						     stack_pointer_rtx)));
}

/* Return >= 0 if there is an unused call-clobbered register available
   for the entire function.  */

static unsigned int
ix86_select_alt_pic_regnum (void)
{
  if (ix86_use_pseudo_pic_reg ())
    return INVALID_REGNUM;

  if (crtl->is_leaf
      && !crtl->profile
      && !ix86_current_function_calls_tls_descriptor)
    {
      int i, drap;
      /* Can't use the same register for both PIC and DRAP.  */
      if (crtl->drap_reg)
	drap = REGNO (crtl->drap_reg);
      else
	drap = -1;
      for (i = 2; i >= 0; --i)
        if (i != drap && !df_regs_ever_live_p (i))
	  return i;
    }

  return INVALID_REGNUM;
}

/* Return true if REGNO is used by the epilogue.  */

bool
ix86_epilogue_uses (int regno)
{
  /* If there are no caller-saved registers, we preserve all registers,
     except for MMX and x87 registers which aren't supported when saving
     and restoring registers.  Don't explicitly save SP register since
     it is always preserved.  */
  return (epilogue_completed
	  && cfun->machine->no_caller_saved_registers
	  && !fixed_regs[regno]
	  && !STACK_REGNO_P (regno)
	  && !MMX_REGNO_P (regno));
}

/* Return nonzero if register REGNO can be used as a scratch register
   in peephole2.  */

static bool
ix86_hard_regno_scratch_ok (unsigned int regno)
{
  /* If there are no caller-saved registers, we can't use any register
     as a scratch register after epilogue and use REGNO as scratch
     register only if it has been used before to avoid saving and
     restoring it.  */
  return (!cfun->machine->no_caller_saved_registers
	  || (!epilogue_completed
	      && df_regs_ever_live_p (regno)));
}

/* Return TRUE if we need to save REGNO.  */

static bool
ix86_save_reg (unsigned int regno, bool maybe_eh_return, bool ignore_outlined)
{
  /* If there are no caller-saved registers, we preserve all registers,
     except for MMX and x87 registers which aren't supported when saving
     and restoring registers.  Don't explicitly save SP register since
     it is always preserved.  */
  if (cfun->machine->no_caller_saved_registers)
    {
      /* Don't preserve registers used for function return value.  */
      rtx reg = crtl->return_rtx;
      if (reg)
	{
	  unsigned int i = REGNO (reg);
	  unsigned int nregs = REG_NREGS (reg);
	  while (nregs-- > 0)
	    if ((i + nregs) == regno)
	      return false;
	}

      return (df_regs_ever_live_p (regno)
	      && !fixed_regs[regno]
	      && !STACK_REGNO_P (regno)
	      && !MMX_REGNO_P (regno)
	      && (regno != HARD_FRAME_POINTER_REGNUM
		  || !frame_pointer_needed));
    }

  if (regno == REAL_PIC_OFFSET_TABLE_REGNUM
      && pic_offset_table_rtx)
    {
      if (ix86_use_pseudo_pic_reg ())
	{
	  /* REAL_PIC_OFFSET_TABLE_REGNUM used by call to
	  _mcount in prologue.  */
	  if (!TARGET_64BIT && flag_pic && crtl->profile)
	    return true;
	}
      else if (df_regs_ever_live_p (REAL_PIC_OFFSET_TABLE_REGNUM)
	       || crtl->profile
	       || crtl->calls_eh_return
	       || crtl->uses_const_pool
	       || cfun->has_nonlocal_label)
        return ix86_select_alt_pic_regnum () == INVALID_REGNUM;
    }

  if (crtl->calls_eh_return && maybe_eh_return)
    {
      unsigned i;
      for (i = 0; ; i++)
	{
	  unsigned test = EH_RETURN_DATA_REGNO (i);
	  if (test == INVALID_REGNUM)
	    break;
	  if (test == regno)
	    return true;
	}
    }

  if (ignore_outlined && cfun->machine->call_ms2sysv)
    {
      unsigned count = cfun->machine->call_ms2sysv_extra_regs
		       + xlogue_layout::MIN_REGS;
      if (xlogue_layout::is_stub_managed_reg (regno, count))
	return false;
    }

  if (crtl->drap_reg
      && regno == REGNO (crtl->drap_reg)
      && !cfun->machine->no_drap_save_restore)
    return true;

  return (df_regs_ever_live_p (regno)
	  && !call_used_regs[regno]
	  && !fixed_regs[regno]
	  && (regno != HARD_FRAME_POINTER_REGNUM || !frame_pointer_needed));
}

/* Return number of saved general prupose registers.  */

static int
ix86_nsaved_regs (void)
{
  int nregs = 0;
  int regno;

  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (GENERAL_REGNO_P (regno) && ix86_save_reg (regno, true, true))
      nregs ++;
  return nregs;
}

/* Return number of saved SSE registers.  */

static int
ix86_nsaved_sseregs (void)
{
  int nregs = 0;
  int regno;

  if (!TARGET_64BIT_MS_ABI)
    return 0;
  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (SSE_REGNO_P (regno) && ix86_save_reg (regno, true, true))
      nregs ++;
  return nregs;
}

/* Given FROM and TO register numbers, say whether this elimination is
   allowed.  If stack alignment is needed, we can only replace argument
   pointer with hard frame pointer, or replace frame pointer with stack
   pointer.  Otherwise, frame pointer elimination is automatically
   handled and all other eliminations are valid.  */

static bool
ix86_can_eliminate (const int from, const int to)
{
  if (stack_realign_fp)
    return ((from == ARG_POINTER_REGNUM
	     && to == HARD_FRAME_POINTER_REGNUM)
	    || (from == FRAME_POINTER_REGNUM
		&& to == STACK_POINTER_REGNUM));
  else
    return to == STACK_POINTER_REGNUM ? !frame_pointer_needed : true;
}

/* Return the offset between two registers, one to be eliminated, and the other
   its replacement, at the start of a routine.  */

HOST_WIDE_INT
ix86_initial_elimination_offset (int from, int to)
{
  struct ix86_frame &frame = cfun->machine->frame;

  if (from == ARG_POINTER_REGNUM && to == HARD_FRAME_POINTER_REGNUM)
    return frame.hard_frame_pointer_offset;
  else if (from == FRAME_POINTER_REGNUM
	   && to == HARD_FRAME_POINTER_REGNUM)
    return frame.hard_frame_pointer_offset - frame.frame_pointer_offset;
  else
    {
      gcc_assert (to == STACK_POINTER_REGNUM);

      if (from == ARG_POINTER_REGNUM)
	return frame.stack_pointer_offset;

      gcc_assert (from == FRAME_POINTER_REGNUM);
      return frame.stack_pointer_offset - frame.frame_pointer_offset;
    }
}

/* In a dynamically-aligned function, we can't know the offset from
   stack pointer to frame pointer, so we must ensure that setjmp
   eliminates fp against the hard fp (%ebp) rather than trying to
   index from %esp up to the top of the frame across a gap that is
   of unknown (at compile-time) size.  */
static rtx
ix86_builtin_setjmp_frame_value (void)
{
  return stack_realign_fp ? hard_frame_pointer_rtx : virtual_stack_vars_rtx;
}

/* Emits a warning for unsupported msabi to sysv pro/epilogues.  */
static void warn_once_call_ms2sysv_xlogues (const char *feature)
{
  static bool warned_once = false;
  if (!warned_once)
    {
      warning (0, "-mcall-ms2sysv-xlogues is not compatible with %s",
	       feature);
      warned_once = true;
    }
}

/* Return the probing interval for -fstack-clash-protection.  */

static HOST_WIDE_INT
get_probe_interval (void)
{
  if (flag_stack_clash_protection)
    return (HOST_WIDE_INT_1U
	    << PARAM_VALUE (PARAM_STACK_CLASH_PROTECTION_PROBE_INTERVAL));
  else
    return (HOST_WIDE_INT_1U << STACK_CHECK_PROBE_INTERVAL_EXP);
}

/* When using -fsplit-stack, the allocation routines set a field in
   the TCB to the bottom of the stack plus this much space, measured
   in bytes.  */

#define SPLIT_STACK_AVAILABLE 256

/* Fill structure ix86_frame about frame of currently computed function.  */

static void
ix86_compute_frame_layout (void)
{
  struct ix86_frame *frame = &cfun->machine->frame;
  struct machine_function *m = cfun->machine;
  unsigned HOST_WIDE_INT stack_alignment_needed;
  HOST_WIDE_INT offset;
  unsigned HOST_WIDE_INT preferred_alignment;
  HOST_WIDE_INT size = get_frame_size ();
  HOST_WIDE_INT to_allocate;

  /* m->call_ms2sysv is initially enabled in ix86_expand_call for all 64-bit
   * ms_abi functions that call a sysv function.  We now need to prune away
   * cases where it should be disabled.  */
  if (TARGET_64BIT && m->call_ms2sysv)
    {
      gcc_assert (TARGET_64BIT_MS_ABI);
      gcc_assert (TARGET_CALL_MS2SYSV_XLOGUES);
      gcc_assert (!TARGET_SEH);
      gcc_assert (TARGET_SSE);
      gcc_assert (!ix86_using_red_zone ());

      if (crtl->calls_eh_return)
	{
	  gcc_assert (!reload_completed);
	  m->call_ms2sysv = false;
	  warn_once_call_ms2sysv_xlogues ("__builtin_eh_return");
	}

      else if (ix86_static_chain_on_stack)
	{
	  gcc_assert (!reload_completed);
	  m->call_ms2sysv = false;
	  warn_once_call_ms2sysv_xlogues ("static call chains");
	}

      /* Finally, compute which registers the stub will manage.  */
      else
	{
	  unsigned count = xlogue_layout::count_stub_managed_regs ();
	  m->call_ms2sysv_extra_regs = count - xlogue_layout::MIN_REGS;
	  m->call_ms2sysv_pad_in = 0;
	}
    }

  frame->nregs = ix86_nsaved_regs ();
  frame->nsseregs = ix86_nsaved_sseregs ();

  /* 64-bit MS ABI seem to require stack alignment to be always 16,
     except for function prologues, leaf functions and when the defult
     incoming stack boundary is overriden at command line or via
     force_align_arg_pointer attribute.

     Darwin's ABI specifies 128b alignment for both 32 and  64 bit variants
     at call sites, including profile function calls.
 */
  if (((TARGET_64BIT_MS_ABI || TARGET_MACHO)
        && crtl->preferred_stack_boundary < 128)
      && (!crtl->is_leaf || cfun->calls_alloca != 0
	  || ix86_current_function_calls_tls_descriptor
	  || (TARGET_MACHO && crtl->profile)
	  || ix86_incoming_stack_boundary < 128))
    {
      crtl->preferred_stack_boundary = 128;
      crtl->stack_alignment_needed = 128;
    }

  stack_alignment_needed = crtl->stack_alignment_needed / BITS_PER_UNIT;
  preferred_alignment = crtl->preferred_stack_boundary / BITS_PER_UNIT;

  gcc_assert (!size || stack_alignment_needed);
  gcc_assert (preferred_alignment >= STACK_BOUNDARY / BITS_PER_UNIT);
  gcc_assert (preferred_alignment <= stack_alignment_needed);

  /* The only ABI saving SSE regs should be 64-bit ms_abi.  */
  gcc_assert (TARGET_64BIT || !frame->nsseregs);
  if (TARGET_64BIT && m->call_ms2sysv)
    {
      gcc_assert (stack_alignment_needed >= 16);
      gcc_assert (!frame->nsseregs);
    }

  /* For SEH we have to limit the amount of code movement into the prologue.
     At present we do this via a BLOCKAGE, at which point there's very little
     scheduling that can be done, which means that there's very little point
     in doing anything except PUSHs.  */
  if (TARGET_SEH)
    m->use_fast_prologue_epilogue = false;
  else if (!optimize_bb_for_size_p (ENTRY_BLOCK_PTR_FOR_FN (cfun)))
    {
      int count = frame->nregs;
      struct cgraph_node *node = cgraph_node::get (current_function_decl);

      /* The fast prologue uses move instead of push to save registers.  This
         is significantly longer, but also executes faster as modern hardware
         can execute the moves in parallel, but can't do that for push/pop.

	 Be careful about choosing what prologue to emit:  When function takes
	 many instructions to execute we may use slow version as well as in
	 case function is known to be outside hot spot (this is known with
	 feedback only).  Weight the size of function by number of registers
	 to save as it is cheap to use one or two push instructions but very
	 slow to use many of them.  */
      if (count)
	count = (count - 1) * FAST_PROLOGUE_INSN_COUNT;
      if (node->frequency < NODE_FREQUENCY_NORMAL
	  || (flag_branch_probabilities
	      && node->frequency < NODE_FREQUENCY_HOT))
	m->use_fast_prologue_epilogue = false;
      else
	m->use_fast_prologue_epilogue
	   = !expensive_function_p (count);
    }

  frame->save_regs_using_mov
    = (TARGET_PROLOGUE_USING_MOVE && m->use_fast_prologue_epilogue
       /* If static stack checking is enabled and done with probes,
	  the registers need to be saved before allocating the frame.  */
       && flag_stack_check != STATIC_BUILTIN_STACK_CHECK);

  /* Skip return address and error code in exception handler.  */
  offset = INCOMING_FRAME_SP_OFFSET;

  /* Skip pushed static chain.  */
  if (ix86_static_chain_on_stack)
    offset += UNITS_PER_WORD;

  /* Skip saved base pointer.  */
  if (frame_pointer_needed)
    offset += UNITS_PER_WORD;
  frame->hfp_save_offset = offset;

  /* The traditional frame pointer location is at the top of the frame.  */
  frame->hard_frame_pointer_offset = offset;

  /* Register save area */
  offset += frame->nregs * UNITS_PER_WORD;
  frame->reg_save_offset = offset;

  /* On SEH target, registers are pushed just before the frame pointer
     location.  */
  if (TARGET_SEH)
    frame->hard_frame_pointer_offset = offset;

  /* Calculate the size of the va-arg area (not including padding, if any).  */
  frame->va_arg_size = ix86_varargs_gpr_size + ix86_varargs_fpr_size;

  /* Also adjust stack_realign_offset for the largest alignment of
     stack slot actually used.  */
  if (stack_realign_fp
      || (cfun->machine->max_used_stack_alignment != 0
	  && (offset % cfun->machine->max_used_stack_alignment) != 0))
    {
      /* We may need a 16-byte aligned stack for the remainder of the
	 register save area, but the stack frame for the local function
	 may require a greater alignment if using AVX/2/512.  In order
	 to avoid wasting space, we first calculate the space needed for
	 the rest of the register saves, add that to the stack pointer,
	 and then realign the stack to the boundary of the start of the
	 frame for the local function.  */
      HOST_WIDE_INT space_needed = 0;
      HOST_WIDE_INT sse_reg_space_needed = 0;

      if (TARGET_64BIT)
	{
	  if (m->call_ms2sysv)
	    {
	      m->call_ms2sysv_pad_in = 0;
	      space_needed = xlogue_layout::get_instance ().get_stack_space_used ();
	    }

	  else if (frame->nsseregs)
	    /* The only ABI that has saved SSE registers (Win64) also has a
	       16-byte aligned default stack.  However, many programs violate
	       the ABI, and Wine64 forces stack realignment to compensate.  */
	    space_needed = frame->nsseregs * 16;

	  sse_reg_space_needed = space_needed = ROUND_UP (space_needed, 16);

	  /* 64-bit frame->va_arg_size should always be a multiple of 16, but
	     rounding to be pedantic.  */
	  space_needed = ROUND_UP (space_needed + frame->va_arg_size, 16);
	}
      else
	space_needed = frame->va_arg_size;

      /* Record the allocation size required prior to the realignment AND.  */
      frame->stack_realign_allocate = space_needed;

      /* The re-aligned stack starts at frame->stack_realign_offset.  Values
	 before this point are not directly comparable with values below
	 this point.  Use sp_valid_at to determine if the stack pointer is
	 valid for a given offset, fp_valid_at for the frame pointer, or
	 choose_baseaddr to have a base register chosen for you.

	 Note that the result of (frame->stack_realign_offset
	 & (stack_alignment_needed - 1)) may not equal zero.  */
      offset = ROUND_UP (offset + space_needed, stack_alignment_needed);
      frame->stack_realign_offset = offset - space_needed;
      frame->sse_reg_save_offset = frame->stack_realign_offset
							+ sse_reg_space_needed;
    }
  else
    {
      frame->stack_realign_offset = offset;

      if (TARGET_64BIT && m->call_ms2sysv)
	{
	  m->call_ms2sysv_pad_in = !!(offset & UNITS_PER_WORD);
	  offset += xlogue_layout::get_instance ().get_stack_space_used ();
	}

      /* Align and set SSE register save area.  */
      else if (frame->nsseregs)
	{
	  /* If the incoming stack boundary is at least 16 bytes, or DRAP is
	     required and the DRAP re-alignment boundary is at least 16 bytes,
	     then we want the SSE register save area properly aligned.  */
	  if (ix86_incoming_stack_boundary >= 128
		  || (stack_realign_drap && stack_alignment_needed >= 16))
	    offset = ROUND_UP (offset, 16);
	  offset += frame->nsseregs * 16;
	}
      frame->sse_reg_save_offset = offset;
      offset += frame->va_arg_size;
    }

  /* Align start of frame for local function.  When a function call
     is removed, it may become a leaf function.  But if argument may
     be passed on stack, we need to align the stack when there is no
     tail call.  */
  if (m->call_ms2sysv
      || frame->va_arg_size != 0
      || size != 0
      || !crtl->is_leaf
      || (!crtl->tail_call_emit
	  && cfun->machine->outgoing_args_on_stack)
      || cfun->calls_alloca
      || ix86_current_function_calls_tls_descriptor)
    offset = ROUND_UP (offset, stack_alignment_needed);

  /* Frame pointer points here.  */
  frame->frame_pointer_offset = offset;

  offset += size;

  /* Add outgoing arguments area.  Can be skipped if we eliminated
     all the function calls as dead code.
     Skipping is however impossible when function calls alloca.  Alloca
     expander assumes that last crtl->outgoing_args_size
     of stack frame are unused.  */
  if (ACCUMULATE_OUTGOING_ARGS
      && (!crtl->is_leaf || cfun->calls_alloca
	  || ix86_current_function_calls_tls_descriptor))
    {
      offset += crtl->outgoing_args_size;
      frame->outgoing_arguments_size = crtl->outgoing_args_size;
    }
  else
    frame->outgoing_arguments_size = 0;

  /* Align stack boundary.  Only needed if we're calling another function
     or using alloca.  */
  if (!crtl->is_leaf || cfun->calls_alloca
      || ix86_current_function_calls_tls_descriptor)
    offset = ROUND_UP (offset, preferred_alignment);

  /* We've reached end of stack frame.  */
  frame->stack_pointer_offset = offset;

  /* Size prologue needs to allocate.  */
  to_allocate = offset - frame->sse_reg_save_offset;

  if ((!to_allocate && frame->nregs <= 1)
      || (TARGET_64BIT && to_allocate >= HOST_WIDE_INT_C (0x80000000))
      /* If stack clash probing needs a loop, then it needs a
	 scratch register.  But the returned register is only guaranteed
	 to be safe to use after register saves are complete.  So if
	 stack clash protections are enabled and the allocated frame is
	 larger than the probe interval, then use pushes to save
	 callee saved registers.  */
      || (flag_stack_clash_protection && to_allocate > get_probe_interval ()))
    frame->save_regs_using_mov = false;

  if (ix86_using_red_zone ()
      && crtl->sp_is_unchanging
      && crtl->is_leaf
      && !ix86_pc_thunk_call_expanded
      && !ix86_current_function_calls_tls_descriptor)
    {
      frame->red_zone_size = to_allocate;
      if (frame->save_regs_using_mov)
	frame->red_zone_size += frame->nregs * UNITS_PER_WORD;
      if (frame->red_zone_size > RED_ZONE_SIZE - RED_ZONE_RESERVE)
	frame->red_zone_size = RED_ZONE_SIZE - RED_ZONE_RESERVE;
    }
  else
    frame->red_zone_size = 0;
  frame->stack_pointer_offset -= frame->red_zone_size;

  /* The SEH frame pointer location is near the bottom of the frame.
     This is enforced by the fact that the difference between the
     stack pointer and the frame pointer is limited to 240 bytes in
     the unwind data structure.  */
  if (TARGET_SEH)
    {
      HOST_WIDE_INT diff;

      /* If we can leave the frame pointer where it is, do so.  Also, returns
	 the establisher frame for __builtin_frame_address (0).  */
      diff = frame->stack_pointer_offset - frame->hard_frame_pointer_offset;
      if (diff <= SEH_MAX_FRAME_SIZE
	  && (diff > 240 || (diff & 15) != 0)
	  && !crtl->accesses_prior_frames)
	{
	  /* Ideally we'd determine what portion of the local stack frame
	     (within the constraint of the lowest 240) is most heavily used.
	     But without that complication, simply bias the frame pointer
	     by 128 bytes so as to maximize the amount of the local stack
	     frame that is addressable with 8-bit offsets.  */
	  frame->hard_frame_pointer_offset = frame->stack_pointer_offset - 128;
	}
    }
}

/* This is semi-inlined memory_address_length, but simplified
   since we know that we're always dealing with reg+offset, and
   to avoid having to create and discard all that rtl.  */

static inline int
choose_baseaddr_len (unsigned int regno, HOST_WIDE_INT offset)
{
  int len = 4;

  if (offset == 0)
    {
      /* EBP and R13 cannot be encoded without an offset.  */
      len = (regno == BP_REG || regno == R13_REG);
    }
  else if (IN_RANGE (offset, -128, 127))
    len = 1;

  /* ESP and R12 must be encoded with a SIB byte.  */
  if (regno == SP_REG || regno == R12_REG)
    len++;

  return len;
}

/* Determine if the stack pointer is valid for accessing the CFA_OFFSET in
   the frame save area.  The register is saved at CFA - CFA_OFFSET.  */

static bool
sp_valid_at (HOST_WIDE_INT cfa_offset)
{
  const struct machine_frame_state &fs = cfun->machine->fs;
  if (fs.sp_realigned && cfa_offset <= fs.sp_realigned_offset)
    {
      /* Validate that the cfa_offset isn't in a "no-man's land".  */
      gcc_assert (cfa_offset <= fs.sp_realigned_fp_last);
      return false;
    }
  return fs.sp_valid;
}

/* Determine if the frame pointer is valid for accessing the CFA_OFFSET in
   the frame save area.  The register is saved at CFA - CFA_OFFSET.  */

static inline bool
fp_valid_at (HOST_WIDE_INT cfa_offset)
{
  const struct machine_frame_state &fs = cfun->machine->fs;
  if (fs.sp_realigned && cfa_offset > fs.sp_realigned_fp_last)
    {
      /* Validate that the cfa_offset isn't in a "no-man's land".  */
      gcc_assert (cfa_offset >= fs.sp_realigned_offset);
      return false;
    }
  return fs.fp_valid;
}

/* Choose a base register based upon alignment requested, speed and/or
   size.  */

static void
choose_basereg (HOST_WIDE_INT cfa_offset, rtx &base_reg,
		HOST_WIDE_INT &base_offset,
		unsigned int align_reqested, unsigned int *align)
{
  const struct machine_function *m = cfun->machine;
  unsigned int hfp_align;
  unsigned int drap_align;
  unsigned int sp_align;
  bool hfp_ok  = fp_valid_at (cfa_offset);
  bool drap_ok = m->fs.drap_valid;
  bool sp_ok   = sp_valid_at (cfa_offset);

  hfp_align = drap_align = sp_align = INCOMING_STACK_BOUNDARY;

  /* Filter out any registers that don't meet the requested alignment
     criteria.  */
  if (align_reqested)
    {
      if (m->fs.realigned)
	hfp_align = drap_align = sp_align = crtl->stack_alignment_needed;
      /* SEH unwind code does do not currently support REG_CFA_EXPRESSION
	 notes (which we would need to use a realigned stack pointer),
	 so disable on SEH targets.  */
      else if (m->fs.sp_realigned)
	sp_align = crtl->stack_alignment_needed;

      hfp_ok = hfp_ok && hfp_align >= align_reqested;
      drap_ok = drap_ok && drap_align >= align_reqested;
      sp_ok = sp_ok && sp_align >= align_reqested;
    }

  if (m->use_fast_prologue_epilogue)
    {
      /* Choose the base register most likely to allow the most scheduling
         opportunities.  Generally FP is valid throughout the function,
         while DRAP must be reloaded within the epilogue.  But choose either
         over the SP due to increased encoding size.  */

      if (hfp_ok)
	{
	  base_reg = hard_frame_pointer_rtx;
	  base_offset = m->fs.fp_offset - cfa_offset;
	}
      else if (drap_ok)
	{
	  base_reg = crtl->drap_reg;
	  base_offset = 0 - cfa_offset;
	}
      else if (sp_ok)
	{
	  base_reg = stack_pointer_rtx;
	  base_offset = m->fs.sp_offset - cfa_offset;
	}
    }
  else
    {
      HOST_WIDE_INT toffset;
      int len = 16, tlen;

      /* Choose the base register with the smallest address encoding.
         With a tie, choose FP > DRAP > SP.  */
      if (sp_ok)
	{
	  base_reg = stack_pointer_rtx;
	  base_offset = m->fs.sp_offset - cfa_offset;
          len = choose_baseaddr_len (STACK_POINTER_REGNUM, base_offset);
	}
      if (drap_ok)
	{
	  toffset = 0 - cfa_offset;
	  tlen = choose_baseaddr_len (REGNO (crtl->drap_reg), toffset);
	  if (tlen <= len)
	    {
	      base_reg = crtl->drap_reg;
	      base_offset = toffset;
	      len = tlen;
	    }
	}
      if (hfp_ok)
	{
	  toffset = m->fs.fp_offset - cfa_offset;
	  tlen = choose_baseaddr_len (HARD_FRAME_POINTER_REGNUM, toffset);
	  if (tlen <= len)
	    {
	      base_reg = hard_frame_pointer_rtx;
	      base_offset = toffset;
	      len = tlen;
	    }
	}
    }

    /* Set the align return value.  */
    if (align)
      {
	if (base_reg == stack_pointer_rtx)
	  *align = sp_align;
	else if (base_reg == crtl->drap_reg)
	  *align = drap_align;
	else if (base_reg == hard_frame_pointer_rtx)
	  *align = hfp_align;
      }
}

/* Return an RTX that points to CFA_OFFSET within the stack frame and
   the alignment of address.  If ALIGN is non-null, it should point to
   an alignment value (in bits) that is preferred or zero and will
   recieve the alignment of the base register that was selected,
   irrespective of rather or not CFA_OFFSET is a multiple of that
   alignment value.  If it is possible for the base register offset to be
   non-immediate then SCRATCH_REGNO should specify a scratch register to
   use.

   The valid base registers are taken from CFUN->MACHINE->FS.  */

static rtx
choose_baseaddr (HOST_WIDE_INT cfa_offset, unsigned int *align,
		 unsigned int scratch_regno = INVALID_REGNUM)
{
  rtx base_reg = NULL;
  HOST_WIDE_INT base_offset = 0;

  /* If a specific alignment is requested, try to get a base register
     with that alignment first.  */
  if (align && *align)
    choose_basereg (cfa_offset, base_reg, base_offset, *align, align);

  if (!base_reg)
    choose_basereg (cfa_offset, base_reg, base_offset, 0, align);

  gcc_assert (base_reg != NULL);

  rtx base_offset_rtx = GEN_INT (base_offset);

  if (!x86_64_immediate_operand (base_offset_rtx, Pmode))
    {
      gcc_assert (scratch_regno != INVALID_REGNUM);

      rtx scratch_reg = gen_rtx_REG (Pmode, scratch_regno);
      emit_move_insn (scratch_reg, base_offset_rtx);

      return gen_rtx_PLUS (Pmode, base_reg, scratch_reg);
    }

  return plus_constant (Pmode, base_reg, base_offset);
}

/* Emit code to save registers in the prologue.  */

static void
ix86_emit_save_regs (void)
{
  unsigned int regno;
  rtx_insn *insn;

  for (regno = FIRST_PSEUDO_REGISTER - 1; regno-- > 0; )
    if (GENERAL_REGNO_P (regno) && ix86_save_reg (regno, true, true))
      {
	insn = emit_insn (gen_push (gen_rtx_REG (word_mode, regno)));
	RTX_FRAME_RELATED_P (insn) = 1;
      }
}

/* Emit a single register save at CFA - CFA_OFFSET.  */

static void
ix86_emit_save_reg_using_mov (machine_mode mode, unsigned int regno,
			      HOST_WIDE_INT cfa_offset)
{
  struct machine_function *m = cfun->machine;
  rtx reg = gen_rtx_REG (mode, regno);
  rtx mem, addr, base, insn;
  unsigned int align = GET_MODE_ALIGNMENT (mode);

  addr = choose_baseaddr (cfa_offset, &align);
  mem = gen_frame_mem (mode, addr);

  /* The location aligment depends upon the base register.  */
  align = MIN (GET_MODE_ALIGNMENT (mode), align);
  gcc_assert (! (cfa_offset & (align / BITS_PER_UNIT - 1)));
  set_mem_align (mem, align);

  insn = emit_insn (gen_rtx_SET (mem, reg));
  RTX_FRAME_RELATED_P (insn) = 1;

  base = addr;
  if (GET_CODE (base) == PLUS)
    base = XEXP (base, 0);
  gcc_checking_assert (REG_P (base));

  /* When saving registers into a re-aligned local stack frame, avoid
     any tricky guessing by dwarf2out.  */
  if (m->fs.realigned)
    {
      gcc_checking_assert (stack_realign_drap);

      if (regno == REGNO (crtl->drap_reg))
	{
	  /* A bit of a hack.  We force the DRAP register to be saved in
	     the re-aligned stack frame, which provides us with a copy
	     of the CFA that will last past the prologue.  Install it.  */
	  gcc_checking_assert (cfun->machine->fs.fp_valid);
	  addr = plus_constant (Pmode, hard_frame_pointer_rtx,
				cfun->machine->fs.fp_offset - cfa_offset);
	  mem = gen_rtx_MEM (mode, addr);
	  add_reg_note (insn, REG_CFA_DEF_CFA, mem);
	}
      else
	{
	  /* The frame pointer is a stable reference within the
	     aligned frame.  Use it.  */
	  gcc_checking_assert (cfun->machine->fs.fp_valid);
	  addr = plus_constant (Pmode, hard_frame_pointer_rtx,
				cfun->machine->fs.fp_offset - cfa_offset);
	  mem = gen_rtx_MEM (mode, addr);
	  add_reg_note (insn, REG_CFA_EXPRESSION, gen_rtx_SET (mem, reg));
	}
    }

  else if (base == stack_pointer_rtx && m->fs.sp_realigned
	   && cfa_offset >= m->fs.sp_realigned_offset)
    {
      gcc_checking_assert (stack_realign_fp);
      add_reg_note (insn, REG_CFA_EXPRESSION, gen_rtx_SET (mem, reg));
    }

  /* The memory may not be relative to the current CFA register,
     which means that we may need to generate a new pattern for
     use by the unwind info.  */
  else if (base != m->fs.cfa_reg)
    {
      addr = plus_constant (Pmode, m->fs.cfa_reg,
			    m->fs.cfa_offset - cfa_offset);
      mem = gen_rtx_MEM (mode, addr);
      add_reg_note (insn, REG_CFA_OFFSET, gen_rtx_SET (mem, reg));
    }
}

/* Emit code to save registers using MOV insns.
   First register is stored at CFA - CFA_OFFSET.  */
static void
ix86_emit_save_regs_using_mov (HOST_WIDE_INT cfa_offset)
{
  unsigned int regno;

  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (GENERAL_REGNO_P (regno) && ix86_save_reg (regno, true, true))
      {
        ix86_emit_save_reg_using_mov (word_mode, regno, cfa_offset);
	cfa_offset -= UNITS_PER_WORD;
      }
}

/* Emit code to save SSE registers using MOV insns.
   First register is stored at CFA - CFA_OFFSET.  */
static void
ix86_emit_save_sse_regs_using_mov (HOST_WIDE_INT cfa_offset)
{
  unsigned int regno;

  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (SSE_REGNO_P (regno) && ix86_save_reg (regno, true, true))
      {
	ix86_emit_save_reg_using_mov (V4SFmode, regno, cfa_offset);
	cfa_offset -= GET_MODE_SIZE (V4SFmode);
      }
}

static GTY(()) rtx queued_cfa_restores;

/* Add a REG_CFA_RESTORE REG note to INSN or queue them until next stack
   manipulation insn.  The value is on the stack at CFA - CFA_OFFSET.
   Don't add the note if the previously saved value will be left untouched
   within stack red-zone till return, as unwinders can find the same value
   in the register and on the stack.  */

static void
ix86_add_cfa_restore_note (rtx_insn *insn, rtx reg, HOST_WIDE_INT cfa_offset)
{
  if (!crtl->shrink_wrapped
      && cfa_offset <= cfun->machine->fs.red_zone_offset)
    return;

  if (insn)
    {
      add_reg_note (insn, REG_CFA_RESTORE, reg);
      RTX_FRAME_RELATED_P (insn) = 1;
    }
  else
    queued_cfa_restores
      = alloc_reg_note (REG_CFA_RESTORE, reg, queued_cfa_restores);
}

/* Add queued REG_CFA_RESTORE notes if any to INSN.  */

static void
ix86_add_queued_cfa_restore_notes (rtx insn)
{
  rtx last;
  if (!queued_cfa_restores)
    return;
  for (last = queued_cfa_restores; XEXP (last, 1); last = XEXP (last, 1))
    ;
  XEXP (last, 1) = REG_NOTES (insn);
  REG_NOTES (insn) = queued_cfa_restores;
  queued_cfa_restores = NULL_RTX;
  RTX_FRAME_RELATED_P (insn) = 1;
}

/* Expand prologue or epilogue stack adjustment.
   The pattern exist to put a dependency on all ebp-based memory accesses.
   STYLE should be negative if instructions should be marked as frame related,
   zero if %r11 register is live and cannot be freely used and positive
   otherwise.  */

static rtx
pro_epilogue_adjust_stack (rtx dest, rtx src, rtx offset,
			   int style, bool set_cfa)
{
  struct machine_function *m = cfun->machine;
  rtx insn;
  bool add_frame_related_expr = false;

  if (Pmode == SImode)
    insn = gen_pro_epilogue_adjust_stack_si_add (dest, src, offset);
  else if (x86_64_immediate_operand (offset, DImode))
    insn = gen_pro_epilogue_adjust_stack_di_add (dest, src, offset);
  else
    {
      rtx tmp;
      /* r11 is used by indirect sibcall return as well, set before the
	 epilogue and used after the epilogue.  */
      if (style)
        tmp = gen_rtx_REG (DImode, R11_REG);
      else
	{
	  gcc_assert (src != hard_frame_pointer_rtx
		      && dest != hard_frame_pointer_rtx);
	  tmp = hard_frame_pointer_rtx;
	}
      insn = emit_insn (gen_rtx_SET (tmp, offset));
      if (style < 0)
	add_frame_related_expr = true;

      insn = gen_pro_epilogue_adjust_stack_di_add (dest, src, tmp);
    }

  insn = emit_insn (insn);
  if (style >= 0)
    ix86_add_queued_cfa_restore_notes (insn);

  if (set_cfa)
    {
      rtx r;

      gcc_assert (m->fs.cfa_reg == src);
      m->fs.cfa_offset += INTVAL (offset);
      m->fs.cfa_reg = dest;

      r = gen_rtx_PLUS (Pmode, src, offset);
      r = gen_rtx_SET (dest, r);
      add_reg_note (insn, REG_CFA_ADJUST_CFA, r);
      RTX_FRAME_RELATED_P (insn) = 1;
    }
  else if (style < 0)
    {
      RTX_FRAME_RELATED_P (insn) = 1;
      if (add_frame_related_expr)
	{
	  rtx r = gen_rtx_PLUS (Pmode, src, offset);
	  r = gen_rtx_SET (dest, r);
	  add_reg_note (insn, REG_FRAME_RELATED_EXPR, r);
	}
    }

  if (dest == stack_pointer_rtx)
    {
      HOST_WIDE_INT ooffset = m->fs.sp_offset;
      bool valid = m->fs.sp_valid;
      bool realigned = m->fs.sp_realigned;

      if (src == hard_frame_pointer_rtx)
	{
	  valid = m->fs.fp_valid;
	  realigned = false;
	  ooffset = m->fs.fp_offset;
	}
      else if (src == crtl->drap_reg)
	{
	  valid = m->fs.drap_valid;
	  realigned = false;
	  ooffset = 0;
	}
      else
	{
	  /* Else there are two possibilities: SP itself, which we set
	     up as the default above.  Or EH_RETURN_STACKADJ_RTX, which is
	     taken care of this by hand along the eh_return path.  */
	  gcc_checking_assert (src == stack_pointer_rtx
			       || offset == const0_rtx);
	}

      m->fs.sp_offset = ooffset - INTVAL (offset);
      m->fs.sp_valid = valid;
      m->fs.sp_realigned = realigned;
    }
  return insn;
}

/* Find an available register to be used as dynamic realign argument
   pointer regsiter.  Such a register will be written in prologue and
   used in begin of body, so it must not be
	1. parameter passing register.
	2. GOT pointer.
   We reuse static-chain register if it is available.  Otherwise, we
   use DI for i386 and R13 for x86-64.  We chose R13 since it has
   shorter encoding.

   Return: the regno of chosen register.  */

static unsigned int
find_drap_reg (void)
{
  tree decl = cfun->decl;

  /* Always use callee-saved register if there are no caller-saved
     registers.  */
  if (TARGET_64BIT)
    {
      /* Use R13 for nested function or function need static chain.
	 Since function with tail call may use any caller-saved
	 registers in epilogue, DRAP must not use caller-saved
	 register in such case.  */
      if (DECL_STATIC_CHAIN (decl)
	  || cfun->machine->no_caller_saved_registers
	  || crtl->tail_call_emit)
	return R13_REG;

      return R10_REG;
    }
  else
    {
      /* Use DI for nested function or function need static chain.
	 Since function with tail call may use any caller-saved
	 registers in epilogue, DRAP must not use caller-saved
	 register in such case.  */
      if (DECL_STATIC_CHAIN (decl)
	  || cfun->machine->no_caller_saved_registers
	  || crtl->tail_call_emit)
	return DI_REG;

      /* Reuse static chain register if it isn't used for parameter
         passing.  */
      if (ix86_function_regparm (TREE_TYPE (decl), decl) <= 2)
	{
	  unsigned int ccvt = ix86_get_callcvt (TREE_TYPE (decl));
	  if ((ccvt & (IX86_CALLCVT_FASTCALL | IX86_CALLCVT_THISCALL)) == 0)
	    return CX_REG;
	}
      return DI_REG;
    }
}

/* Handle a "force_align_arg_pointer" attribute.  */

static tree
ix86_handle_force_align_arg_pointer_attribute (tree *node, tree name,
					       tree, int, bool *no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_TYPE
      && TREE_CODE (*node) != METHOD_TYPE
      && TREE_CODE (*node) != FIELD_DECL
      && TREE_CODE (*node) != TYPE_DECL)
    {
      warning (OPT_Wattributes, "%qE attribute only applies to functions",
	       name);
      *no_add_attrs = true;
    }

  return NULL_TREE;
}

/* Return minimum incoming stack alignment.  */

static unsigned int
ix86_minimum_incoming_stack_boundary (bool sibcall)
{
  unsigned int incoming_stack_boundary;

  /* Stack of interrupt handler is aligned to 128 bits in 64bit mode.  */
  if (cfun->machine->func_type != TYPE_NORMAL)
    incoming_stack_boundary = TARGET_64BIT ? 128 : MIN_STACK_BOUNDARY;
  /* Prefer the one specified at command line. */
  else if (ix86_user_incoming_stack_boundary)
    incoming_stack_boundary = ix86_user_incoming_stack_boundary;
  /* In 32bit, use MIN_STACK_BOUNDARY for incoming stack boundary
     if -mstackrealign is used, it isn't used for sibcall check and
     estimated stack alignment is 128bit.  */
  else if (!sibcall
	   && ix86_force_align_arg_pointer
	   && crtl->stack_alignment_estimated == 128)
    incoming_stack_boundary = MIN_STACK_BOUNDARY;
  else
    incoming_stack_boundary = ix86_default_incoming_stack_boundary;

  /* Incoming stack alignment can be changed on individual functions
     via force_align_arg_pointer attribute.  We use the smallest
     incoming stack boundary.  */
  if (incoming_stack_boundary > MIN_STACK_BOUNDARY
      && lookup_attribute (ix86_force_align_arg_pointer_string,
			   TYPE_ATTRIBUTES (TREE_TYPE (current_function_decl))))
    incoming_stack_boundary = MIN_STACK_BOUNDARY;

  /* The incoming stack frame has to be aligned at least at
     parm_stack_boundary.  */
  if (incoming_stack_boundary < crtl->parm_stack_boundary)
    incoming_stack_boundary = crtl->parm_stack_boundary;

  /* Stack at entrance of main is aligned by runtime.  We use the
     smallest incoming stack boundary. */
  if (incoming_stack_boundary > MAIN_STACK_BOUNDARY
      && DECL_NAME (current_function_decl)
      && MAIN_NAME_P (DECL_NAME (current_function_decl))
      && DECL_FILE_SCOPE_P (current_function_decl))
    incoming_stack_boundary = MAIN_STACK_BOUNDARY;

  return incoming_stack_boundary;
}

/* Update incoming stack boundary and estimated stack alignment.  */

static void
ix86_update_stack_boundary (void)
{
  ix86_incoming_stack_boundary
    = ix86_minimum_incoming_stack_boundary (false);

  /* x86_64 vararg needs 16byte stack alignment for register save area.  */
  if (TARGET_64BIT
      && cfun->stdarg
      && crtl->stack_alignment_estimated < 128)
    crtl->stack_alignment_estimated = 128;

  /* __tls_get_addr needs to be called with 16-byte aligned stack.  */
  if (ix86_tls_descriptor_calls_expanded_in_cfun
      && crtl->preferred_stack_boundary < 128)
    crtl->preferred_stack_boundary = 128;
}

/* Handle the TARGET_GET_DRAP_RTX hook.  Return NULL if no DRAP is
   needed or an rtx for DRAP otherwise.  */

static rtx
ix86_get_drap_rtx (void)
{
  /* We must use DRAP if there are outgoing arguments on stack and
     ACCUMULATE_OUTGOING_ARGS is false.  */
  if (ix86_force_drap
      || (cfun->machine->outgoing_args_on_stack
	  && !ACCUMULATE_OUTGOING_ARGS))
    crtl->need_drap = true;

  if (stack_realign_drap)
    {
      /* Assign DRAP to vDRAP and returns vDRAP */
      unsigned int regno = find_drap_reg ();
      rtx drap_vreg;
      rtx arg_ptr;
      rtx_insn *seq, *insn;

      arg_ptr = gen_rtx_REG (Pmode, regno);
      crtl->drap_reg = arg_ptr;

      start_sequence ();
      drap_vreg = copy_to_reg (arg_ptr);
      seq = get_insns ();
      end_sequence ();

      insn = emit_insn_before (seq, NEXT_INSN (entry_of_function ()));
      if (!optimize)
	{
	  add_reg_note (insn, REG_CFA_SET_VDRAP, drap_vreg);
	  RTX_FRAME_RELATED_P (insn) = 1;
	}
      return drap_vreg;
    }
  else
    return NULL;
}

/* Handle the TARGET_INTERNAL_ARG_POINTER hook.  */

static rtx
ix86_internal_arg_pointer (void)
{
  return virtual_incoming_args_rtx;
}

struct scratch_reg {
  rtx reg;
  bool saved;
};

/* Return a short-lived scratch register for use on function entry.
   In 32-bit mode, it is valid only after the registers are saved
   in the prologue.  This register must be released by means of
   release_scratch_register_on_entry once it is dead.  */

static void
get_scratch_register_on_entry (struct scratch_reg *sr)
{
  int regno;

  sr->saved = false;

  if (TARGET_64BIT)
    {
      /* We always use R11 in 64-bit mode.  */
      regno = R11_REG;
    }
  else
    {
      tree decl = current_function_decl, fntype = TREE_TYPE (decl);
      bool fastcall_p
	= lookup_attribute ("fastcall", TYPE_ATTRIBUTES (fntype)) != NULL_TREE;
      bool thiscall_p
	= lookup_attribute ("thiscall", TYPE_ATTRIBUTES (fntype)) != NULL_TREE;
      bool static_chain_p = DECL_STATIC_CHAIN (decl);
      int regparm = ix86_function_regparm (fntype, decl);
      int drap_regno
	= crtl->drap_reg ? REGNO (crtl->drap_reg) : INVALID_REGNUM;

      /* 'fastcall' sets regparm to 2, uses ecx/edx for arguments and eax
	  for the static chain register.  */
      if ((regparm < 1 || (fastcall_p && !static_chain_p))
	  && drap_regno != AX_REG)
	regno = AX_REG;
      /* 'thiscall' sets regparm to 1, uses ecx for arguments and edx
	  for the static chain register.  */
      else if (thiscall_p && !static_chain_p && drap_regno != AX_REG)
        regno = AX_REG;
      else if (regparm < 2 && !thiscall_p && drap_regno != DX_REG)
	regno = DX_REG;
      /* ecx is the static chain register.  */
      else if (regparm < 3 && !fastcall_p && !thiscall_p
	       && !static_chain_p
	       && drap_regno != CX_REG)
	regno = CX_REG;
      else if (ix86_save_reg (BX_REG, true, false))
	regno = BX_REG;
      /* esi is the static chain register.  */
      else if (!(regparm == 3 && static_chain_p)
	       && ix86_save_reg (SI_REG, true, false))
	regno = SI_REG;
      else if (ix86_save_reg (DI_REG, true, false))
	regno = DI_REG;
      else
	{
	  regno = (drap_regno == AX_REG ? DX_REG : AX_REG);
	  sr->saved = true;
	}
    }

  sr->reg = gen_rtx_REG (Pmode, regno);
  if (sr->saved)
    {
      rtx_insn *insn = emit_insn (gen_push (sr->reg));
      RTX_FRAME_RELATED_P (insn) = 1;
    }
}

/* Release a scratch register obtained from the preceding function.

   If RELEASE_VIA_POP is true, we just pop the register off the stack
   to release it.  This is what non-Linux systems use with -fstack-check.

   Otherwise we use OFFSET to locate the saved register and the
   allocated stack space becomes part of the local frame and is
   deallocated by the epilogue.  */

static void
release_scratch_register_on_entry (struct scratch_reg *sr, HOST_WIDE_INT offset,
				   bool release_via_pop)
{
  if (sr->saved)
    {
      if (release_via_pop)
	{
	  struct machine_function *m = cfun->machine;
	  rtx x, insn = emit_insn (gen_pop (sr->reg));

	  /* The RX FRAME_RELATED_P mechanism doesn't know about pop.  */
	  RTX_FRAME_RELATED_P (insn) = 1;
	  x = gen_rtx_PLUS (Pmode, stack_pointer_rtx, GEN_INT (UNITS_PER_WORD));
	  x = gen_rtx_SET (stack_pointer_rtx, x);
	  add_reg_note (insn, REG_FRAME_RELATED_EXPR, x);
	  m->fs.sp_offset -= UNITS_PER_WORD;
	}
      else
	{
	  rtx x = gen_rtx_PLUS (Pmode, stack_pointer_rtx, GEN_INT (offset));
	  x = gen_rtx_SET (sr->reg, gen_rtx_MEM (word_mode, x));
	  emit_insn (x);
	}
    }
}

/* Emit code to adjust the stack pointer by SIZE bytes while probing it.

   This differs from the next routine in that it tries hard to prevent
   attacks that jump the stack guard.  Thus it is never allowed to allocate
   more than PROBE_INTERVAL bytes of stack space without a suitable
   probe.

   INT_REGISTERS_SAVED is true if integer registers have already been
   pushed on the stack.  */

static void
ix86_adjust_stack_and_probe_stack_clash (HOST_WIDE_INT size,
					 const bool int_registers_saved)
{
  struct machine_function *m = cfun->machine;

  /* If this function does not statically allocate stack space, then
     no probes are needed.  */
  if (!size)
    {
      /* However, the allocation of space via pushes for register
	 saves could be viewed as allocating space, but without the
	 need to probe.  */
      if (m->frame.nregs || m->frame.nsseregs || frame_pointer_needed)
        dump_stack_clash_frame_info (NO_PROBE_SMALL_FRAME, true);
      else
	dump_stack_clash_frame_info (NO_PROBE_NO_FRAME, false);
      return;
    }

  /* If we are a noreturn function, then we have to consider the
     possibility that we're called via a jump rather than a call.

     Thus we don't have the implicit probe generated by saving the
     return address into the stack at the call.  Thus, the stack
     pointer could be anywhere in the guard page.  The safe thing
     to do is emit a probe now.

     The probe can be avoided if we have already emitted any callee
     register saves into the stack or have a frame pointer (which will
     have been saved as well).  Those saves will function as implicit
     probes.

     ?!? This should be revamped to work like aarch64 and s390 where
     we track the offset from the most recent probe.  Normally that
     offset would be zero.  For a noreturn function we would reset
     it to PROBE_INTERVAL - (STACK_BOUNDARY / BITS_PER_UNIT).   Then
     we just probe when we cross PROBE_INTERVAL.  */
  if (TREE_THIS_VOLATILE (cfun->decl)
      && !(m->frame.nregs || m->frame.nsseregs || frame_pointer_needed))
    {
      /* We can safely use any register here since we're just going to push
	 its value and immediately pop it back.  But we do try and avoid
	 argument passing registers so as not to introduce dependencies in
	 the pipeline.  For 32 bit we use %esi and for 64 bit we use %rax.  */
      rtx dummy_reg = gen_rtx_REG (word_mode, TARGET_64BIT ? AX_REG : SI_REG);
      rtx_insn *insn_push = emit_insn (gen_push (dummy_reg));
      rtx_insn *insn_pop = emit_insn (gen_pop (dummy_reg));
      m->fs.sp_offset -= UNITS_PER_WORD;
      if (m->fs.cfa_reg == stack_pointer_rtx)
	{
	  m->fs.cfa_offset -= UNITS_PER_WORD;
	  rtx x = plus_constant (Pmode, stack_pointer_rtx, -UNITS_PER_WORD);
	  x = gen_rtx_SET (stack_pointer_rtx, x);
	  add_reg_note (insn_push, REG_CFA_ADJUST_CFA, x);
	  RTX_FRAME_RELATED_P (insn_push) = 1;
	  x = plus_constant (Pmode, stack_pointer_rtx, UNITS_PER_WORD);
	  x = gen_rtx_SET (stack_pointer_rtx, x);
	  add_reg_note (insn_pop, REG_CFA_ADJUST_CFA, x);
	  RTX_FRAME_RELATED_P (insn_pop) = 1;
	}
      emit_insn (gen_blockage ());
    }

  /* If we allocate less than the size of the guard statically,
     then no probing is necessary, but we do need to allocate
     the stack.  */
  if (size < (1 << PARAM_VALUE (PARAM_STACK_CLASH_PROTECTION_GUARD_SIZE)))
    {
      pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
			         GEN_INT (-size), -1,
			         m->fs.cfa_reg == stack_pointer_rtx);
      dump_stack_clash_frame_info (NO_PROBE_SMALL_FRAME, true);
      return;
    }

  /* We're allocating a large enough stack frame that we need to
     emit probes.  Either emit them inline or in a loop depending
     on the size.  */
  HOST_WIDE_INT probe_interval = get_probe_interval ();
  if (size <= 4 * probe_interval)
    {
      HOST_WIDE_INT i;
      for (i = probe_interval; i <= size; i += probe_interval)
	{
	  /* Allocate PROBE_INTERVAL bytes.  */
	  rtx insn
	    = pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
					 GEN_INT (-probe_interval), -1,
					 m->fs.cfa_reg == stack_pointer_rtx);
	  add_reg_note (insn, REG_STACK_CHECK, const0_rtx);

	  /* And probe at *sp.  */
	  emit_stack_probe (stack_pointer_rtx);
	  emit_insn (gen_blockage ());
	}

      /* We need to allocate space for the residual, but we do not need
	 to probe the residual.  */
      HOST_WIDE_INT residual = (i - probe_interval - size);
      if (residual)
	pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				   GEN_INT (residual), -1,
				   m->fs.cfa_reg == stack_pointer_rtx);
      dump_stack_clash_frame_info (PROBE_INLINE, residual != 0);
    }
  else
    {
      /* We expect the GP registers to be saved when probes are used
	 as the probing sequences might need a scratch register and
	 the routine to allocate one assumes the integer registers
	 have already been saved.  */
      gcc_assert (int_registers_saved);

      struct scratch_reg sr;
      get_scratch_register_on_entry (&sr);

      /* If we needed to save a register, then account for any space
	 that was pushed (we are not going to pop the register when
	 we do the restore).  */
      if (sr.saved)
	size -= UNITS_PER_WORD;

      /* Step 1: round SIZE down to a multiple of the interval.  */
      HOST_WIDE_INT rounded_size = size & -probe_interval;

      /* Step 2: compute final value of the loop counter.  Use lea if
	 possible.  */
      rtx addr = plus_constant (Pmode, stack_pointer_rtx, -rounded_size);
      rtx insn;
      if (address_no_seg_operand (addr, Pmode))
	insn = emit_insn (gen_rtx_SET (sr.reg, addr));
      else
	{
	  emit_move_insn (sr.reg, GEN_INT (-rounded_size));
	  insn = emit_insn (gen_rtx_SET (sr.reg,
					 gen_rtx_PLUS (Pmode, sr.reg,
						       stack_pointer_rtx)));
	}
      if (m->fs.cfa_reg == stack_pointer_rtx)
	{
	  add_reg_note (insn, REG_CFA_DEF_CFA,
			plus_constant (Pmode, sr.reg,
				       m->fs.cfa_offset + rounded_size));
	  RTX_FRAME_RELATED_P (insn) = 1;
	}

      /* Step 3: the loop.  */
      rtx size_rtx = GEN_INT (rounded_size);
      insn = emit_insn (ix86_gen_adjust_stack_and_probe (sr.reg, sr.reg,
							 size_rtx));
      if (m->fs.cfa_reg == stack_pointer_rtx)
	{
	  m->fs.cfa_offset += rounded_size;
	  add_reg_note (insn, REG_CFA_DEF_CFA,
			plus_constant (Pmode, stack_pointer_rtx,
				       m->fs.cfa_offset));
	  RTX_FRAME_RELATED_P (insn) = 1;
	}
      m->fs.sp_offset += rounded_size;
      emit_insn (gen_blockage ());

      /* Step 4: adjust SP if we cannot assert at compile-time that SIZE
	 is equal to ROUNDED_SIZE.  */

      if (size != rounded_size)
	pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				   GEN_INT (rounded_size - size), -1,
				   m->fs.cfa_reg == stack_pointer_rtx);
      dump_stack_clash_frame_info (PROBE_LOOP, size != rounded_size);

      /* This does not deallocate the space reserved for the scratch
	 register.  That will be deallocated in the epilogue.  */
      release_scratch_register_on_entry (&sr, size, false);
    }

  /* Make sure nothing is scheduled before we are done.  */
  emit_insn (gen_blockage ());
}

/* Emit code to adjust the stack pointer by SIZE bytes while probing it.

   INT_REGISTERS_SAVED is true if integer registers have already been
   pushed on the stack.  */

static void
ix86_adjust_stack_and_probe (HOST_WIDE_INT size,
			     const bool int_registers_saved)
{
  /* We skip the probe for the first interval + a small dope of 4 words and
     probe that many bytes past the specified size to maintain a protection
     area at the botton of the stack.  */
  const int dope = 4 * UNITS_PER_WORD;
  rtx size_rtx = GEN_INT (size), last;

  /* See if we have a constant small number of probes to generate.  If so,
     that's the easy case.  The run-time loop is made up of 9 insns in the
     generic case while the compile-time loop is made up of 3+2*(n-1) insns
     for n # of intervals.  */
  if (size <= 4 * get_probe_interval ())
    {
      HOST_WIDE_INT i, adjust;
      bool first_probe = true;

      /* Adjust SP and probe at PROBE_INTERVAL + N * PROBE_INTERVAL for
	 values of N from 1 until it exceeds SIZE.  If only one probe is
	 needed, this will not generate any code.  Then adjust and probe
	 to PROBE_INTERVAL + SIZE.  */
      for (i = get_probe_interval (); i < size; i += get_probe_interval ())
	{
	  if (first_probe)
	    {
	      adjust = 2 * get_probe_interval () + dope;
	      first_probe = false;
	    }
	  else
	    adjust = get_probe_interval ();

	  emit_insn (gen_rtx_SET (stack_pointer_rtx,
				  plus_constant (Pmode, stack_pointer_rtx,
						 -adjust)));
	  emit_stack_probe (stack_pointer_rtx);
	}

      if (first_probe)
	adjust = size + get_probe_interval () + dope;
      else
        adjust = size + get_probe_interval () - i;

      emit_insn (gen_rtx_SET (stack_pointer_rtx,
			      plus_constant (Pmode, stack_pointer_rtx,
					     -adjust)));
      emit_stack_probe (stack_pointer_rtx);

      /* Adjust back to account for the additional first interval.  */
      last = emit_insn (gen_rtx_SET (stack_pointer_rtx,
				     plus_constant (Pmode, stack_pointer_rtx,
						    (get_probe_interval ()
						     + dope))));
    }

  /* Otherwise, do the same as above, but in a loop.  Note that we must be
     extra careful with variables wrapping around because we might be at
     the very top (or the very bottom) of the address space and we have
     to be able to handle this case properly; in particular, we use an
     equality test for the loop condition.  */
  else
    {
      /* We expect the GP registers to be saved when probes are used
	 as the probing sequences might need a scratch register and
	 the routine to allocate one assumes the integer registers
	 have already been saved.  */
      gcc_assert (int_registers_saved);

      HOST_WIDE_INT rounded_size;
      struct scratch_reg sr;

      get_scratch_register_on_entry (&sr);

      /* If we needed to save a register, then account for any space
	 that was pushed (we are not going to pop the register when
	 we do the restore).  */
      if (sr.saved)
	size -= UNITS_PER_WORD;

      /* Step 1: round SIZE to the previous multiple of the interval.  */

      rounded_size = ROUND_DOWN (size, get_probe_interval ());


      /* Step 2: compute initial and final value of the loop counter.  */

      /* SP = SP_0 + PROBE_INTERVAL.  */
      emit_insn (gen_rtx_SET (stack_pointer_rtx,
			      plus_constant (Pmode, stack_pointer_rtx,
					     - (get_probe_interval () + dope))));

      /* LAST_ADDR = SP_0 + PROBE_INTERVAL + ROUNDED_SIZE.  */
      if (rounded_size <= (HOST_WIDE_INT_1 << 31))
	emit_insn (gen_rtx_SET (sr.reg,
				plus_constant (Pmode, stack_pointer_rtx,
					       -rounded_size)));
      else
	{
	  emit_move_insn (sr.reg, GEN_INT (-rounded_size));
	  emit_insn (gen_rtx_SET (sr.reg,
				  gen_rtx_PLUS (Pmode, sr.reg,
						stack_pointer_rtx)));
	}


      /* Step 3: the loop

	 do
	   {
	     SP = SP + PROBE_INTERVAL
	     probe at SP
	   }
	 while (SP != LAST_ADDR)

	 adjusts SP and probes to PROBE_INTERVAL + N * PROBE_INTERVAL for
	 values of N from 1 until it is equal to ROUNDED_SIZE.  */

      emit_insn (ix86_gen_adjust_stack_and_probe (sr.reg, sr.reg, size_rtx));


      /* Step 4: adjust SP and probe at PROBE_INTERVAL + SIZE if we cannot
	 assert at compile-time that SIZE is equal to ROUNDED_SIZE.  */

      if (size != rounded_size)
	{
	  emit_insn (gen_rtx_SET (stack_pointer_rtx,
			          plus_constant (Pmode, stack_pointer_rtx,
						 rounded_size - size)));
	  emit_stack_probe (stack_pointer_rtx);
	}

      /* Adjust back to account for the additional first interval.  */
      last = emit_insn (gen_rtx_SET (stack_pointer_rtx,
				     plus_constant (Pmode, stack_pointer_rtx,
						    (get_probe_interval ()
						     + dope))));

      /* This does not deallocate the space reserved for the scratch
	 register.  That will be deallocated in the epilogue.  */
      release_scratch_register_on_entry (&sr, size, false);
    }

  /* Even if the stack pointer isn't the CFA register, we need to correctly
     describe the adjustments made to it, in particular differentiate the
     frame-related ones from the frame-unrelated ones.  */
  if (size > 0)
    {
      rtx expr = gen_rtx_SEQUENCE (VOIDmode, rtvec_alloc (2));
      XVECEXP (expr, 0, 0)
	= gen_rtx_SET (stack_pointer_rtx,
		       plus_constant (Pmode, stack_pointer_rtx, -size));
      XVECEXP (expr, 0, 1)
	= gen_rtx_SET (stack_pointer_rtx,
		       plus_constant (Pmode, stack_pointer_rtx,
				      get_probe_interval () + dope + size));
      add_reg_note (last, REG_FRAME_RELATED_EXPR, expr);
      RTX_FRAME_RELATED_P (last) = 1;

      cfun->machine->fs.sp_offset += size;
    }

  /* Make sure nothing is scheduled before we are done.  */
  emit_insn (gen_blockage ());
}

/* Adjust the stack pointer up to REG while probing it.  */

const char *
output_adjust_stack_and_probe (rtx reg)
{
  static int labelno = 0;
  char loop_lab[32];
  rtx xops[2];

  ASM_GENERATE_INTERNAL_LABEL (loop_lab, "LPSRL", labelno++);

  /* Loop.  */
  ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, loop_lab);

  /* SP = SP + PROBE_INTERVAL.  */
  xops[0] = stack_pointer_rtx;
  xops[1] = GEN_INT (get_probe_interval ());
  output_asm_insn ("sub%z0\t{%1, %0|%0, %1}", xops);

  /* Probe at SP.  */
  xops[1] = const0_rtx;
  output_asm_insn ("or%z0\t{%1, (%0)|DWORD PTR [%0], %1}", xops);

  /* Test if SP == LAST_ADDR.  */
  xops[0] = stack_pointer_rtx;
  xops[1] = reg;
  output_asm_insn ("cmp%z0\t{%1, %0|%0, %1}", xops);

  /* Branch.  */
  fputs ("\tjne\t", asm_out_file);
  assemble_name_raw (asm_out_file, loop_lab);
  fputc ('\n', asm_out_file);

  return "";
}

/* Emit code to probe a range of stack addresses from FIRST to FIRST+SIZE,
   inclusive.  These are offsets from the current stack pointer.

   INT_REGISTERS_SAVED is true if integer registers have already been
   pushed on the stack.  */

static void
ix86_emit_probe_stack_range (HOST_WIDE_INT first, HOST_WIDE_INT size,
			     const bool int_registers_saved)
{
  /* See if we have a constant small number of probes to generate.  If so,
     that's the easy case.  The run-time loop is made up of 6 insns in the
     generic case while the compile-time loop is made up of n insns for n #
     of intervals.  */
  if (size <= 6 * get_probe_interval ())
    {
      HOST_WIDE_INT i;

      /* Probe at FIRST + N * PROBE_INTERVAL for values of N from 1 until
	 it exceeds SIZE.  If only one probe is needed, this will not
	 generate any code.  Then probe at FIRST + SIZE.  */
      for (i = get_probe_interval (); i < size; i += get_probe_interval ())
	emit_stack_probe (plus_constant (Pmode, stack_pointer_rtx,
					 -(first + i)));

      emit_stack_probe (plus_constant (Pmode, stack_pointer_rtx,
				       -(first + size)));
    }

  /* Otherwise, do the same as above, but in a loop.  Note that we must be
     extra careful with variables wrapping around because we might be at
     the very top (or the very bottom) of the address space and we have
     to be able to handle this case properly; in particular, we use an
     equality test for the loop condition.  */
  else
    {
      /* We expect the GP registers to be saved when probes are used
	 as the probing sequences might need a scratch register and
	 the routine to allocate one assumes the integer registers
	 have already been saved.  */
      gcc_assert (int_registers_saved);

      HOST_WIDE_INT rounded_size, last;
      struct scratch_reg sr;

      get_scratch_register_on_entry (&sr);


      /* Step 1: round SIZE to the previous multiple of the interval.  */

      rounded_size = ROUND_DOWN (size, get_probe_interval ());


      /* Step 2: compute initial and final value of the loop counter.  */

      /* TEST_OFFSET = FIRST.  */
      emit_move_insn (sr.reg, GEN_INT (-first));

      /* LAST_OFFSET = FIRST + ROUNDED_SIZE.  */
      last = first + rounded_size;


      /* Step 3: the loop

	 do
	   {
	     TEST_ADDR = TEST_ADDR + PROBE_INTERVAL
	     probe at TEST_ADDR
	   }
	 while (TEST_ADDR != LAST_ADDR)

         probes at FIRST + N * PROBE_INTERVAL for values of N from 1
         until it is equal to ROUNDED_SIZE.  */

      emit_insn (ix86_gen_probe_stack_range (sr.reg, sr.reg, GEN_INT (-last)));


      /* Step 4: probe at FIRST + SIZE if we cannot assert at compile-time
	 that SIZE is equal to ROUNDED_SIZE.  */

      if (size != rounded_size)
	emit_stack_probe (plus_constant (Pmode,
					 gen_rtx_PLUS (Pmode,
						       stack_pointer_rtx,
						       sr.reg),
					 rounded_size - size));

      release_scratch_register_on_entry (&sr, size, true);
    }

  /* Make sure nothing is scheduled before we are done.  */
  emit_insn (gen_blockage ());
}

/* Probe a range of stack addresses from REG to END, inclusive.  These are
   offsets from the current stack pointer.  */

const char *
output_probe_stack_range (rtx reg, rtx end)
{
  static int labelno = 0;
  char loop_lab[32];
  rtx xops[3];

  ASM_GENERATE_INTERNAL_LABEL (loop_lab, "LPSRL", labelno++);

  /* Loop.  */
  ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, loop_lab);

  /* TEST_ADDR = TEST_ADDR + PROBE_INTERVAL.  */
  xops[0] = reg;
  xops[1] = GEN_INT (get_probe_interval ());
  output_asm_insn ("sub%z0\t{%1, %0|%0, %1}", xops);

  /* Probe at TEST_ADDR.  */
  xops[0] = stack_pointer_rtx;
  xops[1] = reg;
  xops[2] = const0_rtx;
  output_asm_insn ("or%z0\t{%2, (%0,%1)|DWORD PTR [%0+%1], %2}", xops);

  /* Test if TEST_ADDR == LAST_ADDR.  */
  xops[0] = reg;
  xops[1] = end;
  output_asm_insn ("cmp%z0\t{%1, %0|%0, %1}", xops);

  /* Branch.  */
  fputs ("\tjne\t", asm_out_file);
  assemble_name_raw (asm_out_file, loop_lab);
  fputc ('\n', asm_out_file);

  return "";
}

/* Return true if stack frame is required.  Update STACK_ALIGNMENT
   to the largest alignment, in bits, of stack slot used if stack
   frame is required and CHECK_STACK_SLOT is true.  */

static bool
ix86_find_max_used_stack_alignment (unsigned int &stack_alignment,
				    bool check_stack_slot)
{
  HARD_REG_SET set_up_by_prologue, prologue_used;
  basic_block bb;

  CLEAR_HARD_REG_SET (prologue_used);
  CLEAR_HARD_REG_SET (set_up_by_prologue);
  add_to_hard_reg_set (&set_up_by_prologue, Pmode, STACK_POINTER_REGNUM);
  add_to_hard_reg_set (&set_up_by_prologue, Pmode, ARG_POINTER_REGNUM);
  add_to_hard_reg_set (&set_up_by_prologue, Pmode,
		       HARD_FRAME_POINTER_REGNUM);

  /* The preferred stack alignment is the minimum stack alignment.  */
  if (stack_alignment > crtl->preferred_stack_boundary)
    stack_alignment = crtl->preferred_stack_boundary;

  bool require_stack_frame = false;

  FOR_EACH_BB_FN (bb, cfun)
    {
      rtx_insn *insn;
      FOR_BB_INSNS (bb, insn)
	if (NONDEBUG_INSN_P (insn)
	    && requires_stack_frame_p (insn, prologue_used,
				       set_up_by_prologue))
	  {
	    require_stack_frame = true;

	    if (check_stack_slot)
	      {
		/* Find the maximum stack alignment.  */
		subrtx_iterator::array_type array;
		FOR_EACH_SUBRTX (iter, array, PATTERN (insn), ALL)
		  if (MEM_P (*iter)
		      && (reg_mentioned_p (stack_pointer_rtx,
					   *iter)
			  || reg_mentioned_p (frame_pointer_rtx,
					      *iter)))
		    {
		      unsigned int alignment = MEM_ALIGN (*iter);
		      if (alignment > stack_alignment)
			stack_alignment = alignment;
		    }
	      }
	  }
    }

  return require_stack_frame;
}

/* Finalize stack_realign_needed and frame_pointer_needed flags, which
   will guide prologue/epilogue to be generated in correct form.  */

static void
ix86_finalize_stack_frame_flags (void)
{
  /* Check if stack realign is really needed after reload, and
     stores result in cfun */
  unsigned int incoming_stack_boundary
    = (crtl->parm_stack_boundary > ix86_incoming_stack_boundary
       ? crtl->parm_stack_boundary : ix86_incoming_stack_boundary);
  unsigned int stack_alignment
    = (crtl->is_leaf && !ix86_current_function_calls_tls_descriptor
       ? crtl->max_used_stack_slot_alignment
       : crtl->stack_alignment_needed);
  unsigned int stack_realign
    = (incoming_stack_boundary < stack_alignment);
  bool recompute_frame_layout_p = false;

  if (crtl->stack_realign_finalized)
    {
      /* After stack_realign_needed is finalized, we can't no longer
	 change it.  */
      gcc_assert (crtl->stack_realign_needed == stack_realign);
      return;
    }

  /* If the only reason for frame_pointer_needed is that we conservatively
     assumed stack realignment might be needed or -fno-omit-frame-pointer
     is used, but in the end nothing that needed the stack alignment had
     been spilled nor stack access, clear frame_pointer_needed and say we
     don't need stack realignment.  */
  if ((stack_realign || (!flag_omit_frame_pointer && optimize))
      && frame_pointer_needed
      && crtl->is_leaf
      && crtl->sp_is_unchanging
      && !ix86_current_function_calls_tls_descriptor
      && !crtl->accesses_prior_frames
      && !cfun->calls_alloca
      && !crtl->calls_eh_return
      /* See ira_setup_eliminable_regset for the rationale.  */
      && !(STACK_CHECK_MOVING_SP
	   && flag_stack_check
	   && flag_exceptions
	   && cfun->can_throw_non_call_exceptions)
      && !ix86_frame_pointer_required ()
      && get_frame_size () == 0
      && ix86_nsaved_sseregs () == 0
      && ix86_varargs_gpr_size + ix86_varargs_fpr_size == 0)
    {
      if (ix86_find_max_used_stack_alignment (stack_alignment,
					      stack_realign))
	{
	  /* Stack frame is required.  If stack alignment needed is less
	     than incoming stack boundary, don't realign stack.  */
	  stack_realign = incoming_stack_boundary < stack_alignment;
	  if (!stack_realign)
	    {
	      crtl->max_used_stack_slot_alignment
		= incoming_stack_boundary;
	      crtl->stack_alignment_needed
		= incoming_stack_boundary;
	      /* Also update preferred_stack_boundary for leaf
	         functions.  */
	      crtl->preferred_stack_boundary
		= incoming_stack_boundary;
	    }
	}
      else
	{
	  /* If drap has been set, but it actually isn't live at the
	     start of the function, there is no reason to set it up.  */
	  if (crtl->drap_reg)
	    {
	      basic_block bb = ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb;
	      if (! REGNO_REG_SET_P (DF_LR_IN (bb),
				     REGNO (crtl->drap_reg)))
		{
		  crtl->drap_reg = NULL_RTX;
		  crtl->need_drap = false;
		}
	    }
	  else
	    cfun->machine->no_drap_save_restore = true;

	  frame_pointer_needed = false;
	  stack_realign = false;
	  crtl->max_used_stack_slot_alignment = incoming_stack_boundary;
	  crtl->stack_alignment_needed = incoming_stack_boundary;
	  crtl->stack_alignment_estimated = incoming_stack_boundary;
	  if (crtl->preferred_stack_boundary > incoming_stack_boundary)
	    crtl->preferred_stack_boundary = incoming_stack_boundary;
	  df_finish_pass (true);
	  df_scan_alloc (NULL);
	  df_scan_blocks ();
	  df_compute_regs_ever_live (true);
	  df_analyze ();

	  if (flag_var_tracking)
	    {
	      /* Since frame pointer is no longer available, replace it with
		 stack pointer - UNITS_PER_WORD in debug insns.  */
	      df_ref ref, next;
	      for (ref = DF_REG_USE_CHAIN (HARD_FRAME_POINTER_REGNUM);
		   ref; ref = next)
		{
		  next = DF_REF_NEXT_REG (ref);
		  if (!DF_REF_INSN_INFO (ref))
		    continue;

		  /* Make sure the next ref is for a different instruction,
		     so that we're not affected by the rescan.  */
		  rtx_insn *insn = DF_REF_INSN (ref);
		  while (next && DF_REF_INSN (next) == insn)
		    next = DF_REF_NEXT_REG (next);

		  if (DEBUG_INSN_P (insn))
		    {
		      bool changed = false;
		      for (; ref != next; ref = DF_REF_NEXT_REG (ref))
			{
			  rtx *loc = DF_REF_LOC (ref);
			  if (*loc == hard_frame_pointer_rtx)
			    {
			      *loc = plus_constant (Pmode,
						    stack_pointer_rtx,
						    -UNITS_PER_WORD);
			      changed = true;
			    }
			}
		      if (changed)
			df_insn_rescan (insn);
		    }
		}
	    }

	  recompute_frame_layout_p = true;
	}
    }
  else if (crtl->max_used_stack_slot_alignment >= 128)
    {
      /* We don't need to realign stack.  max_used_stack_alignment is
	 used to decide how stack frame should be aligned.  This is
	 independent of any psABIs nor 32-bit vs 64-bit.  It is always
	 safe to compute max_used_stack_alignment.  We compute it only
	 if 128-bit aligned load/store may be generated on misaligned
	 stack slot which will lead to segfault.   */
      if (ix86_find_max_used_stack_alignment (stack_alignment, true))
	cfun->machine->max_used_stack_alignment
	  = stack_alignment / BITS_PER_UNIT;
    }

  if (crtl->stack_realign_needed != stack_realign)
    recompute_frame_layout_p = true;
  crtl->stack_realign_needed = stack_realign;
  crtl->stack_realign_finalized = true;
  if (recompute_frame_layout_p)
    ix86_compute_frame_layout ();
}

/* Delete SET_GOT right after entry block if it is allocated to reg.  */

static void
ix86_elim_entry_set_got (rtx reg)
{
  basic_block bb = ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb;
  rtx_insn *c_insn = BB_HEAD (bb);
  if (!NONDEBUG_INSN_P (c_insn))
    c_insn = next_nonnote_nondebug_insn (c_insn);
  if (c_insn && NONJUMP_INSN_P (c_insn))
    {
      rtx pat = PATTERN (c_insn);
      if (GET_CODE (pat) == PARALLEL)
	{
	  rtx vec = XVECEXP (pat, 0, 0);
	  if (GET_CODE (vec) == SET
	      && XINT (XEXP (vec, 1), 1) == UNSPEC_SET_GOT
	      && REGNO (XEXP (vec, 0)) == REGNO (reg))
	    delete_insn (c_insn);
	}
    }
}

static rtx
gen_frame_set (rtx reg, rtx frame_reg, int offset, bool store)
{
  rtx addr, mem;

  if (offset)
    addr = gen_rtx_PLUS (Pmode, frame_reg, GEN_INT (offset));
  mem = gen_frame_mem (GET_MODE (reg), offset ? addr : frame_reg);
  return gen_rtx_SET (store ? mem : reg, store ? reg : mem);
}

static inline rtx
gen_frame_load (rtx reg, rtx frame_reg, int offset)
{
  return gen_frame_set (reg, frame_reg, offset, false);
}

static inline rtx
gen_frame_store (rtx reg, rtx frame_reg, int offset)
{
  return gen_frame_set (reg, frame_reg, offset, true);
}

static void
ix86_emit_outlined_ms2sysv_save (const struct ix86_frame &frame)
{
  struct machine_function *m = cfun->machine;
  const unsigned ncregs = NUM_X86_64_MS_CLOBBERED_REGS
			  + m->call_ms2sysv_extra_regs;
  rtvec v = rtvec_alloc (ncregs + 1);
  unsigned int align, i, vi = 0;
  rtx_insn *insn;
  rtx sym, addr;
  rtx rax = gen_rtx_REG (word_mode, AX_REG);
  const struct xlogue_layout &xlogue = xlogue_layout::get_instance ();

  /* AL should only be live with sysv_abi.  */
  gcc_assert (!ix86_eax_live_at_start_p ());
  gcc_assert (m->fs.sp_offset >= frame.sse_reg_save_offset);

  /* Setup RAX as the stub's base pointer.  We use stack_realign_offset rather
     we've actually realigned the stack or not.  */
  align = GET_MODE_ALIGNMENT (V4SFmode);
  addr = choose_baseaddr (frame.stack_realign_offset
			  + xlogue.get_stub_ptr_offset (), &align, AX_REG);
  gcc_assert (align >= GET_MODE_ALIGNMENT (V4SFmode));

  emit_insn (gen_rtx_SET (rax, addr));

  /* Get the stub symbol.  */
  sym = xlogue.get_stub_rtx (frame_pointer_needed ? XLOGUE_STUB_SAVE_HFP
						  : XLOGUE_STUB_SAVE);
  RTVEC_ELT (v, vi++) = gen_rtx_USE (VOIDmode, sym);

  for (i = 0; i < ncregs; ++i)
    {
      const xlogue_layout::reginfo &r = xlogue.get_reginfo (i);
      rtx reg = gen_rtx_REG ((SSE_REGNO_P (r.regno) ? V4SFmode : word_mode),
			     r.regno);
      RTVEC_ELT (v, vi++) = gen_frame_store (reg, rax, -r.offset);
    }

  gcc_assert (vi == (unsigned)GET_NUM_ELEM (v));

  insn = emit_insn (gen_rtx_PARALLEL (VOIDmode, v));
  RTX_FRAME_RELATED_P (insn) = true;
}

/* Expand the prologue into a bunch of separate insns.  */

void
ix86_expand_prologue (void)
{
  struct machine_function *m = cfun->machine;
  rtx insn, t;
  HOST_WIDE_INT allocate;
  bool int_registers_saved;
  bool sse_registers_saved;
  bool save_stub_call_needed;
  rtx static_chain = NULL_RTX;

  if (ix86_function_naked (current_function_decl))
    return;

  ix86_finalize_stack_frame_flags ();

  /* DRAP should not coexist with stack_realign_fp */
  gcc_assert (!(crtl->drap_reg && stack_realign_fp));

  memset (&m->fs, 0, sizeof (m->fs));

  /* Initialize CFA state for before the prologue.  */
  m->fs.cfa_reg = stack_pointer_rtx;
  m->fs.cfa_offset = INCOMING_FRAME_SP_OFFSET;

  /* Track SP offset to the CFA.  We continue tracking this after we've
     swapped the CFA register away from SP.  In the case of re-alignment
     this is fudged; we're interested to offsets within the local frame.  */
  m->fs.sp_offset = INCOMING_FRAME_SP_OFFSET;
  m->fs.sp_valid = true;
  m->fs.sp_realigned = false;

  const struct ix86_frame &frame = cfun->machine->frame;

  if (!TARGET_64BIT && ix86_function_ms_hook_prologue (current_function_decl))
    {
      /* We should have already generated an error for any use of
         ms_hook on a nested function.  */
      gcc_checking_assert (!ix86_static_chain_on_stack);

      /* Check if profiling is active and we shall use profiling before
         prologue variant. If so sorry.  */
      if (crtl->profile && flag_fentry != 0)
        sorry ("ms_hook_prologue attribute isn%'t compatible "
	       "with -mfentry for 32-bit");

      /* In ix86_asm_output_function_label we emitted:
	 8b ff     movl.s %edi,%edi
	 55        push   %ebp
	 8b ec     movl.s %esp,%ebp

	 This matches the hookable function prologue in Win32 API
	 functions in Microsoft Windows XP Service Pack 2 and newer.
	 Wine uses this to enable Windows apps to hook the Win32 API
	 functions provided by Wine.

	 What that means is that we've already set up the frame pointer.  */

      if (frame_pointer_needed
	  && !(crtl->drap_reg && crtl->stack_realign_needed))
	{
	  rtx push, mov;

	  /* We've decided to use the frame pointer already set up.
	     Describe this to the unwinder by pretending that both
	     push and mov insns happen right here.

	     Putting the unwind info here at the end of the ms_hook
	     is done so that we can make absolutely certain we get
	     the required byte sequence at the start of the function,
	     rather than relying on an assembler that can produce
	     the exact encoding required.

	     However it does mean (in the unpatched case) that we have
	     a 1 insn window where the asynchronous unwind info is
	     incorrect.  However, if we placed the unwind info at
	     its correct location we would have incorrect unwind info
	     in the patched case.  Which is probably all moot since
	     I don't expect Wine generates dwarf2 unwind info for the
	     system libraries that use this feature.  */

	  insn = emit_insn (gen_blockage ());

	  push = gen_push (hard_frame_pointer_rtx);
	  mov = gen_rtx_SET (hard_frame_pointer_rtx,
			     stack_pointer_rtx);
	  RTX_FRAME_RELATED_P (push) = 1;
	  RTX_FRAME_RELATED_P (mov) = 1;

	  RTX_FRAME_RELATED_P (insn) = 1;
	  add_reg_note (insn, REG_FRAME_RELATED_EXPR,
			gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, push, mov)));

	  /* Note that gen_push incremented m->fs.cfa_offset, even
	     though we didn't emit the push insn here.  */
	  m->fs.cfa_reg = hard_frame_pointer_rtx;
	  m->fs.fp_offset = m->fs.cfa_offset;
	  m->fs.fp_valid = true;
	}
      else
	{
	  /* The frame pointer is not needed so pop %ebp again.
	     This leaves us with a pristine state.  */
	  emit_insn (gen_pop (hard_frame_pointer_rtx));
	}
    }

  /* The first insn of a function that accepts its static chain on the
     stack is to push the register that would be filled in by a direct
     call.  This insn will be skipped by the trampoline.  */
  else if (ix86_static_chain_on_stack)
    {
      static_chain = ix86_static_chain (cfun->decl, false);
      insn = emit_insn (gen_push (static_chain));
      emit_insn (gen_blockage ());

      /* We don't want to interpret this push insn as a register save,
	 only as a stack adjustment.  The real copy of the register as
	 a save will be done later, if needed.  */
      t = plus_constant (Pmode, stack_pointer_rtx, -UNITS_PER_WORD);
      t = gen_rtx_SET (stack_pointer_rtx, t);
      add_reg_note (insn, REG_CFA_ADJUST_CFA, t);
      RTX_FRAME_RELATED_P (insn) = 1;
    }

  /* Emit prologue code to adjust stack alignment and setup DRAP, in case
     of DRAP is needed and stack realignment is really needed after reload */
  if (stack_realign_drap)
    {
      int align_bytes = crtl->stack_alignment_needed / BITS_PER_UNIT;

      /* Can't use DRAP in interrupt function.  */
      if (cfun->machine->func_type != TYPE_NORMAL)
	sorry ("Dynamic Realign Argument Pointer (DRAP) not supported "
	       "in interrupt service routine.  This may be worked "
	       "around by avoiding functions with aggregate return.");

      /* Only need to push parameter pointer reg if it is caller saved.  */
      if (!call_used_regs[REGNO (crtl->drap_reg)])
	{
	  /* Push arg pointer reg */
	  insn = emit_insn (gen_push (crtl->drap_reg));
	  RTX_FRAME_RELATED_P (insn) = 1;
	}

      /* Grab the argument pointer.  */
      t = plus_constant (Pmode, stack_pointer_rtx, m->fs.sp_offset);
      insn = emit_insn (gen_rtx_SET (crtl->drap_reg, t));
      RTX_FRAME_RELATED_P (insn) = 1;
      m->fs.cfa_reg = crtl->drap_reg;
      m->fs.cfa_offset = 0;

      /* Align the stack.  */
      insn = emit_insn (ix86_gen_andsp (stack_pointer_rtx,
					stack_pointer_rtx,
					GEN_INT (-align_bytes)));
      RTX_FRAME_RELATED_P (insn) = 1;

      /* Replicate the return address on the stack so that return
	 address can be reached via (argp - 1) slot.  This is needed
	 to implement macro RETURN_ADDR_RTX and intrinsic function
	 expand_builtin_return_addr etc.  */
      t = plus_constant (Pmode, crtl->drap_reg, -UNITS_PER_WORD);
      t = gen_frame_mem (word_mode, t);
      insn = emit_insn (gen_push (t));
      RTX_FRAME_RELATED_P (insn) = 1;

      /* For the purposes of frame and register save area addressing,
	 we've started over with a new frame.  */
      m->fs.sp_offset = INCOMING_FRAME_SP_OFFSET;
      m->fs.realigned = true;

      if (static_chain)
	{
	  /* Replicate static chain on the stack so that static chain
	     can be reached via (argp - 2) slot.  This is needed for
	     nested function with stack realignment.  */
	  insn = emit_insn (gen_push (static_chain));
	  RTX_FRAME_RELATED_P (insn) = 1;
	}
    }

  int_registers_saved = (frame.nregs == 0);
  sse_registers_saved = (frame.nsseregs == 0);
  save_stub_call_needed = (m->call_ms2sysv);
  gcc_assert (sse_registers_saved || !save_stub_call_needed);

  if (frame_pointer_needed && !m->fs.fp_valid)
    {
      /* Note: AT&T enter does NOT have reversed args.  Enter is probably
         slower on all targets.  Also sdb didn't like it.  */
      insn = emit_insn (gen_push (hard_frame_pointer_rtx));
      RTX_FRAME_RELATED_P (insn) = 1;

      /* Push registers now, before setting the frame pointer
	 on SEH target.  */
      if (!int_registers_saved
	  && TARGET_SEH
	  && !frame.save_regs_using_mov)
	{
	  ix86_emit_save_regs ();
	  int_registers_saved = true;
	  gcc_assert (m->fs.sp_offset == frame.reg_save_offset);
	}

      if (m->fs.sp_offset == frame.hard_frame_pointer_offset)
	{
	  insn = emit_move_insn (hard_frame_pointer_rtx, stack_pointer_rtx);
	  RTX_FRAME_RELATED_P (insn) = 1;

	  if (m->fs.cfa_reg == stack_pointer_rtx)
	    m->fs.cfa_reg = hard_frame_pointer_rtx;
	  m->fs.fp_offset = m->fs.sp_offset;
	  m->fs.fp_valid = true;
	}
    }

  if (!int_registers_saved)
    {
      /* If saving registers via PUSH, do so now.  */
      if (!frame.save_regs_using_mov)
	{
	  ix86_emit_save_regs ();
	  int_registers_saved = true;
	  gcc_assert (m->fs.sp_offset == frame.reg_save_offset);
	}

      /* When using red zone we may start register saving before allocating
	 the stack frame saving one cycle of the prologue.  However, avoid
	 doing this if we have to probe the stack; at least on x86_64 the
	 stack probe can turn into a call that clobbers a red zone location. */
      else if (ix86_using_red_zone ()
	       && (! TARGET_STACK_PROBE
		   || frame.stack_pointer_offset < CHECK_STACK_LIMIT))
	{
	  ix86_emit_save_regs_using_mov (frame.reg_save_offset);
	  int_registers_saved = true;
	}
    }

  if (stack_realign_fp)
    {
      int align_bytes = crtl->stack_alignment_needed / BITS_PER_UNIT;
      gcc_assert (align_bytes > MIN_STACK_BOUNDARY / BITS_PER_UNIT);

      /* Record last valid frame pointer offset.  */
      m->fs.sp_realigned_fp_last = frame.reg_save_offset;

      /* The computation of the size of the re-aligned stack frame means
	 that we must allocate the size of the register save area before
	 performing the actual alignment.  Otherwise we cannot guarantee
	 that there's enough storage above the realignment point.  */
      allocate = frame.reg_save_offset - m->fs.sp_offset
		 + frame.stack_realign_allocate;
      if (allocate)
        pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				   GEN_INT (-allocate), -1, false);

      /* Align the stack.  */
      insn = emit_insn (ix86_gen_andsp (stack_pointer_rtx,
					stack_pointer_rtx,
					GEN_INT (-align_bytes)));
      m->fs.sp_offset = ROUND_UP (m->fs.sp_offset, align_bytes);
      m->fs.sp_realigned_offset = m->fs.sp_offset
					      - frame.stack_realign_allocate;
      /* The stack pointer may no longer be equal to CFA - m->fs.sp_offset.
	 Beyond this point, stack access should be done via choose_baseaddr or
	 by using sp_valid_at and fp_valid_at to determine the correct base
	 register.  Henceforth, any CFA offset should be thought of as logical
	 and not physical.  */
      gcc_assert (m->fs.sp_realigned_offset >= m->fs.sp_realigned_fp_last);
      gcc_assert (m->fs.sp_realigned_offset == frame.stack_realign_offset);
      m->fs.sp_realigned = true;

      /* SEH unwind emit doesn't currently support REG_CFA_EXPRESSION, which
	 is needed to describe where a register is saved using a realigned
	 stack pointer, so we need to invalidate the stack pointer for that
	 target.  */
      if (TARGET_SEH)
	m->fs.sp_valid = false;

      /* If SP offset is non-immediate after allocation of the stack frame,
	 then emit SSE saves or stub call prior to allocating the rest of the
	 stack frame.  This is less efficient for the out-of-line stub because
	 we can't combine allocations across the call barrier, but it's better
	 than using a scratch register.  */
      else if (!x86_64_immediate_operand (GEN_INT (frame.stack_pointer_offset
						   - m->fs.sp_realigned_offset),
					  Pmode))
	{
	  if (!sse_registers_saved)
	    {
	      ix86_emit_save_sse_regs_using_mov (frame.sse_reg_save_offset);
	      sse_registers_saved = true;
	    }
	  else if (save_stub_call_needed)
	    {
	      ix86_emit_outlined_ms2sysv_save (frame);
	      save_stub_call_needed = false;
	    }
	}
    }

  allocate = frame.stack_pointer_offset - m->fs.sp_offset;

  if (flag_stack_usage_info)
    {
      /* We start to count from ARG_POINTER.  */
      HOST_WIDE_INT stack_size = frame.stack_pointer_offset;

      /* If it was realigned, take into account the fake frame.  */
      if (stack_realign_drap)
	{
	  if (ix86_static_chain_on_stack)
	    stack_size += UNITS_PER_WORD;

	  if (!call_used_regs[REGNO (crtl->drap_reg)])
	    stack_size += UNITS_PER_WORD;

	  /* This over-estimates by 1 minimal-stack-alignment-unit but
	     mitigates that by counting in the new return address slot.  */
	  current_function_dynamic_stack_size
	    += crtl->stack_alignment_needed / BITS_PER_UNIT;
	}

      current_function_static_stack_size = stack_size;
    }

  /* On SEH target with very large frame size, allocate an area to save
     SSE registers (as the very large allocation won't be described).  */
  if (TARGET_SEH
      && frame.stack_pointer_offset > SEH_MAX_FRAME_SIZE
      && !sse_registers_saved)
    {
      HOST_WIDE_INT sse_size
	= frame.sse_reg_save_offset - frame.reg_save_offset;

      gcc_assert (int_registers_saved);

      /* No need to do stack checking as the area will be immediately
	 written.  */
      pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
			         GEN_INT (-sse_size), -1,
				 m->fs.cfa_reg == stack_pointer_rtx);
      allocate -= sse_size;
      ix86_emit_save_sse_regs_using_mov (frame.sse_reg_save_offset);
      sse_registers_saved = true;
    }

  /* The stack has already been decremented by the instruction calling us
     so probe if the size is non-negative to preserve the protection area.  */
  if (allocate >= 0
      && (flag_stack_check == STATIC_BUILTIN_STACK_CHECK
	  || flag_stack_clash_protection))
    {
      if (flag_stack_clash_protection)
	{
	  ix86_adjust_stack_and_probe_stack_clash (allocate,
						   int_registers_saved);
	  allocate = 0;
	}
      else if (STACK_CHECK_MOVING_SP)
	{
	  if (!(crtl->is_leaf && !cfun->calls_alloca
		&& allocate <= get_probe_interval ()))
	    {
	      ix86_adjust_stack_and_probe (allocate, int_registers_saved);
	      allocate = 0;
	    }
	}
      else
	{
	  HOST_WIDE_INT size = allocate;

	  if (TARGET_64BIT && size >= HOST_WIDE_INT_C (0x80000000))
	    size = 0x80000000 - get_stack_check_protect () - 1;

	  if (TARGET_STACK_PROBE)
	    {
	      if (crtl->is_leaf && !cfun->calls_alloca)
		{
		  if (size > get_probe_interval ())
		    ix86_emit_probe_stack_range (0, size, int_registers_saved);
		}
	      else
		ix86_emit_probe_stack_range (0,
					     size + get_stack_check_protect (),
					     int_registers_saved);
	    }
	  else
	    {
	      if (crtl->is_leaf && !cfun->calls_alloca)
		{
		  if (size > get_probe_interval ()
		      && size > get_stack_check_protect ())
		    ix86_emit_probe_stack_range (get_stack_check_protect (),
						 (size
						  - get_stack_check_protect ()),
						 int_registers_saved);
		}
	      else
		ix86_emit_probe_stack_range (get_stack_check_protect (), size,
					     int_registers_saved);
	    }
	}
    }

  if (allocate == 0)
    ;
  else if (!ix86_target_stack_probe ()
	   || frame.stack_pointer_offset < CHECK_STACK_LIMIT)
    {
      pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
			         GEN_INT (-allocate), -1,
			         m->fs.cfa_reg == stack_pointer_rtx);
    }
  else
    {
      rtx eax = gen_rtx_REG (Pmode, AX_REG);
      rtx r10 = NULL;
      rtx (*adjust_stack_insn)(rtx, rtx, rtx);
      const bool sp_is_cfa_reg = (m->fs.cfa_reg == stack_pointer_rtx);
      bool eax_live = ix86_eax_live_at_start_p ();
      bool r10_live = false;

      if (TARGET_64BIT)
        r10_live = (DECL_STATIC_CHAIN (current_function_decl) != 0);

      if (eax_live)
	{
	  insn = emit_insn (gen_push (eax));
	  allocate -= UNITS_PER_WORD;
	  /* Note that SEH directives need to continue tracking the stack
	     pointer even after the frame pointer has been set up.  */
	  if (sp_is_cfa_reg || TARGET_SEH)
	    {
	      if (sp_is_cfa_reg)
		m->fs.cfa_offset += UNITS_PER_WORD;
	      RTX_FRAME_RELATED_P (insn) = 1;
	      add_reg_note (insn, REG_FRAME_RELATED_EXPR,
			    gen_rtx_SET (stack_pointer_rtx,
					 plus_constant (Pmode, stack_pointer_rtx,
							-UNITS_PER_WORD)));
	    }
	}

      if (r10_live)
	{
	  r10 = gen_rtx_REG (Pmode, R10_REG);
	  insn = emit_insn (gen_push (r10));
	  allocate -= UNITS_PER_WORD;
	  if (sp_is_cfa_reg || TARGET_SEH)
	    {
	      if (sp_is_cfa_reg)
		m->fs.cfa_offset += UNITS_PER_WORD;
	      RTX_FRAME_RELATED_P (insn) = 1;
	      add_reg_note (insn, REG_FRAME_RELATED_EXPR,
			    gen_rtx_SET (stack_pointer_rtx,
					 plus_constant (Pmode, stack_pointer_rtx,
							-UNITS_PER_WORD)));
	    }
	}

      emit_move_insn (eax, GEN_INT (allocate));
      emit_insn (ix86_gen_allocate_stack_worker (eax, eax));

      /* Use the fact that AX still contains ALLOCATE.  */
      adjust_stack_insn = (Pmode == DImode
			   ? gen_pro_epilogue_adjust_stack_di_sub
			   : gen_pro_epilogue_adjust_stack_si_sub);

      insn = emit_insn (adjust_stack_insn (stack_pointer_rtx,
					   stack_pointer_rtx, eax));

      if (sp_is_cfa_reg || TARGET_SEH)
	{
	  if (sp_is_cfa_reg)
	    m->fs.cfa_offset += allocate;
	  RTX_FRAME_RELATED_P (insn) = 1;
	  add_reg_note (insn, REG_FRAME_RELATED_EXPR,
			gen_rtx_SET (stack_pointer_rtx,
				     plus_constant (Pmode, stack_pointer_rtx,
						    -allocate)));
	}
      m->fs.sp_offset += allocate;

      /* Use stack_pointer_rtx for relative addressing so that code works for
	 realigned stack.  But this means that we need a blockage to prevent
	 stores based on the frame pointer from being scheduled before.  */
      if (r10_live && eax_live)
        {
	  t = gen_rtx_PLUS (Pmode, stack_pointer_rtx, eax);
	  emit_move_insn (gen_rtx_REG (word_mode, R10_REG),
			  gen_frame_mem (word_mode, t));
	  t = plus_constant (Pmode, t, UNITS_PER_WORD);
	  emit_move_insn (gen_rtx_REG (word_mode, AX_REG),
			  gen_frame_mem (word_mode, t));
	  emit_insn (gen_memory_blockage ());
	}
      else if (eax_live || r10_live)
	{
	  t = gen_rtx_PLUS (Pmode, stack_pointer_rtx, eax);
	  emit_move_insn (gen_rtx_REG (word_mode,
				       (eax_live ? AX_REG : R10_REG)),
			  gen_frame_mem (word_mode, t));
	  emit_insn (gen_memory_blockage ());
	}
    }
  gcc_assert (m->fs.sp_offset == frame.stack_pointer_offset);

  /* If we havn't already set up the frame pointer, do so now.  */
  if (frame_pointer_needed && !m->fs.fp_valid)
    {
      insn = ix86_gen_add3 (hard_frame_pointer_rtx, stack_pointer_rtx,
			    GEN_INT (frame.stack_pointer_offset
				     - frame.hard_frame_pointer_offset));
      insn = emit_insn (insn);
      RTX_FRAME_RELATED_P (insn) = 1;
      add_reg_note (insn, REG_CFA_ADJUST_CFA, NULL);

      if (m->fs.cfa_reg == stack_pointer_rtx)
	m->fs.cfa_reg = hard_frame_pointer_rtx;
      m->fs.fp_offset = frame.hard_frame_pointer_offset;
      m->fs.fp_valid = true;
    }

  if (!int_registers_saved)
    ix86_emit_save_regs_using_mov (frame.reg_save_offset);
  if (!sse_registers_saved)
    ix86_emit_save_sse_regs_using_mov (frame.sse_reg_save_offset);
  else if (save_stub_call_needed)
    ix86_emit_outlined_ms2sysv_save (frame);

  /* For the mcount profiling on 32 bit PIC mode we need to emit SET_GOT
     in PROLOGUE.  */
  if (!TARGET_64BIT && pic_offset_table_rtx && crtl->profile && !flag_fentry)
    {
      rtx pic = gen_rtx_REG (Pmode, REAL_PIC_OFFSET_TABLE_REGNUM);
      insn = emit_insn (gen_set_got (pic));
      RTX_FRAME_RELATED_P (insn) = 1;
      add_reg_note (insn, REG_CFA_FLUSH_QUEUE, NULL_RTX);
      emit_insn (gen_prologue_use (pic));
      /* Deleting already emmitted SET_GOT if exist and allocated to
	 REAL_PIC_OFFSET_TABLE_REGNUM.  */
      ix86_elim_entry_set_got (pic);
    }

  if (crtl->drap_reg && !crtl->stack_realign_needed)
    {
      /* vDRAP is setup but after reload it turns out stack realign
         isn't necessary, here we will emit prologue to setup DRAP
         without stack realign adjustment */
      t = choose_baseaddr (0, NULL);
      emit_insn (gen_rtx_SET (crtl->drap_reg, t));
    }

  /* Prevent instructions from being scheduled into register save push
     sequence when access to the redzone area is done through frame pointer.
     The offset between the frame pointer and the stack pointer is calculated
     relative to the value of the stack pointer at the end of the function
     prologue, and moving instructions that access redzone area via frame
     pointer inside push sequence violates this assumption.  */
  if (frame_pointer_needed && frame.red_zone_size)
    emit_insn (gen_memory_blockage ());

  /* SEH requires that the prologue end within 256 bytes of the start of
     the function.  Prevent instruction schedules that would extend that.
     Further, prevent alloca modifications to the stack pointer from being
     combined with prologue modifications.  */
  if (TARGET_SEH)
    emit_insn (gen_prologue_use (stack_pointer_rtx));
}

/* Emit code to restore REG using a POP insn.  */

static void
ix86_emit_restore_reg_using_pop (rtx reg)
{
  struct machine_function *m = cfun->machine;
  rtx_insn *insn = emit_insn (gen_pop (reg));

  ix86_add_cfa_restore_note (insn, reg, m->fs.sp_offset);
  m->fs.sp_offset -= UNITS_PER_WORD;

  if (m->fs.cfa_reg == crtl->drap_reg
      && REGNO (reg) == REGNO (crtl->drap_reg))
    {
      /* Previously we'd represented the CFA as an expression
	 like *(%ebp - 8).  We've just popped that value from
	 the stack, which means we need to reset the CFA to
	 the drap register.  This will remain until we restore
	 the stack pointer.  */
      add_reg_note (insn, REG_CFA_DEF_CFA, reg);
      RTX_FRAME_RELATED_P (insn) = 1;

      /* This means that the DRAP register is valid for addressing too.  */
      m->fs.drap_valid = true;
      return;
    }

  if (m->fs.cfa_reg == stack_pointer_rtx)
    {
      rtx x = plus_constant (Pmode, stack_pointer_rtx, UNITS_PER_WORD);
      x = gen_rtx_SET (stack_pointer_rtx, x);
      add_reg_note (insn, REG_CFA_ADJUST_CFA, x);
      RTX_FRAME_RELATED_P (insn) = 1;

      m->fs.cfa_offset -= UNITS_PER_WORD;
    }

  /* When the frame pointer is the CFA, and we pop it, we are
     swapping back to the stack pointer as the CFA.  This happens
     for stack frames that don't allocate other data, so we assume
     the stack pointer is now pointing at the return address, i.e.
     the function entry state, which makes the offset be 1 word.  */
  if (reg == hard_frame_pointer_rtx)
    {
      m->fs.fp_valid = false;
      if (m->fs.cfa_reg == hard_frame_pointer_rtx)
	{
	  m->fs.cfa_reg = stack_pointer_rtx;
	  m->fs.cfa_offset -= UNITS_PER_WORD;

	  add_reg_note (insn, REG_CFA_DEF_CFA,
			gen_rtx_PLUS (Pmode, stack_pointer_rtx,
				      GEN_INT (m->fs.cfa_offset)));
	  RTX_FRAME_RELATED_P (insn) = 1;
	}
    }
}

/* Emit code to restore saved registers using POP insns.  */

static void
ix86_emit_restore_regs_using_pop (void)
{
  unsigned int regno;

  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (GENERAL_REGNO_P (regno) && ix86_save_reg (regno, false, true))
      ix86_emit_restore_reg_using_pop (gen_rtx_REG (word_mode, regno));
}

/* Emit code and notes for the LEAVE instruction.  If insn is non-null,
   omits the emit and only attaches the notes.  */

static void
ix86_emit_leave (rtx_insn *insn)
{
  struct machine_function *m = cfun->machine;
  if (!insn)
    insn = emit_insn (ix86_gen_leave ());

  ix86_add_queued_cfa_restore_notes (insn);

  gcc_assert (m->fs.fp_valid);
  m->fs.sp_valid = true;
  m->fs.sp_realigned = false;
  m->fs.sp_offset = m->fs.fp_offset - UNITS_PER_WORD;
  m->fs.fp_valid = false;

  if (m->fs.cfa_reg == hard_frame_pointer_rtx)
    {
      m->fs.cfa_reg = stack_pointer_rtx;
      m->fs.cfa_offset = m->fs.sp_offset;

      add_reg_note (insn, REG_CFA_DEF_CFA,
		    plus_constant (Pmode, stack_pointer_rtx,
				   m->fs.sp_offset));
      RTX_FRAME_RELATED_P (insn) = 1;
    }
  ix86_add_cfa_restore_note (insn, hard_frame_pointer_rtx,
			     m->fs.fp_offset);
}

/* Emit code to restore saved registers using MOV insns.
   First register is restored from CFA - CFA_OFFSET.  */
static void
ix86_emit_restore_regs_using_mov (HOST_WIDE_INT cfa_offset,
				  bool maybe_eh_return)
{
  struct machine_function *m = cfun->machine;
  unsigned int regno;

  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (GENERAL_REGNO_P (regno) && ix86_save_reg (regno, maybe_eh_return, true))
      {
	rtx reg = gen_rtx_REG (word_mode, regno);
	rtx mem;
	rtx_insn *insn;

	mem = choose_baseaddr (cfa_offset, NULL);
	mem = gen_frame_mem (word_mode, mem);
	insn = emit_move_insn (reg, mem);

        if (m->fs.cfa_reg == crtl->drap_reg && regno == REGNO (crtl->drap_reg))
	  {
	    /* Previously we'd represented the CFA as an expression
	       like *(%ebp - 8).  We've just popped that value from
	       the stack, which means we need to reset the CFA to
	       the drap register.  This will remain until we restore
	       the stack pointer.  */
	    add_reg_note (insn, REG_CFA_DEF_CFA, reg);
	    RTX_FRAME_RELATED_P (insn) = 1;

	    /* This means that the DRAP register is valid for addressing.  */
	    m->fs.drap_valid = true;
	  }
	else
	  ix86_add_cfa_restore_note (NULL, reg, cfa_offset);

	cfa_offset -= UNITS_PER_WORD;
      }
}

/* Emit code to restore saved registers using MOV insns.
   First register is restored from CFA - CFA_OFFSET.  */
static void
ix86_emit_restore_sse_regs_using_mov (HOST_WIDE_INT cfa_offset,
				      bool maybe_eh_return)
{
  unsigned int regno;

  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (SSE_REGNO_P (regno) && ix86_save_reg (regno, maybe_eh_return, true))
      {
	rtx reg = gen_rtx_REG (V4SFmode, regno);
	rtx mem;
	unsigned int align = GET_MODE_ALIGNMENT (V4SFmode);

	mem = choose_baseaddr (cfa_offset, &align);
	mem = gen_rtx_MEM (V4SFmode, mem);

	/* The location aligment depends upon the base register.  */
	align = MIN (GET_MODE_ALIGNMENT (V4SFmode), align);
	gcc_assert (! (cfa_offset & (align / BITS_PER_UNIT - 1)));
	set_mem_align (mem, align);
	emit_insn (gen_rtx_SET (reg, mem));

	ix86_add_cfa_restore_note (NULL, reg, cfa_offset);

	cfa_offset -= GET_MODE_SIZE (V4SFmode);
      }
}

static void
ix86_emit_outlined_ms2sysv_restore (const struct ix86_frame &frame,
				  bool use_call, int style)
{
  struct machine_function *m = cfun->machine;
  const unsigned ncregs = NUM_X86_64_MS_CLOBBERED_REGS
			  + m->call_ms2sysv_extra_regs;
  rtvec v;
  unsigned int elems_needed, align, i, vi = 0;
  rtx_insn *insn;
  rtx sym, tmp;
  rtx rsi = gen_rtx_REG (word_mode, SI_REG);
  rtx r10 = NULL_RTX;
  const struct xlogue_layout &xlogue = xlogue_layout::get_instance ();
  HOST_WIDE_INT stub_ptr_offset = xlogue.get_stub_ptr_offset ();
  HOST_WIDE_INT rsi_offset = frame.stack_realign_offset + stub_ptr_offset;
  rtx rsi_frame_load = NULL_RTX;
  HOST_WIDE_INT rsi_restore_offset = (HOST_WIDE_INT)-1;
  enum xlogue_stub stub;

  gcc_assert (!m->fs.fp_valid || frame_pointer_needed);

  /* If using a realigned stack, we should never start with padding.  */
  gcc_assert (!stack_realign_fp || !xlogue.get_stack_align_off_in ());

  /* Setup RSI as the stub's base pointer.  */
  align = GET_MODE_ALIGNMENT (V4SFmode);
  tmp = choose_baseaddr (rsi_offset, &align, SI_REG);
  gcc_assert (align >= GET_MODE_ALIGNMENT (V4SFmode));

  emit_insn (gen_rtx_SET (rsi, tmp));

  /* Get a symbol for the stub.  */
  if (frame_pointer_needed)
    stub = use_call ? XLOGUE_STUB_RESTORE_HFP
		    : XLOGUE_STUB_RESTORE_HFP_TAIL;
  else
    stub = use_call ? XLOGUE_STUB_RESTORE
		    : XLOGUE_STUB_RESTORE_TAIL;
  sym = xlogue.get_stub_rtx (stub);

  elems_needed = ncregs;
  if (use_call)
    elems_needed += 1;
  else
    elems_needed += frame_pointer_needed ? 5 : 3;
  v = rtvec_alloc (elems_needed);

  /* We call the epilogue stub when we need to pop incoming args or we are
     doing a sibling call as the tail.  Otherwise, we will emit a jmp to the
     epilogue stub and it is the tail-call.  */
  if (use_call)
      RTVEC_ELT (v, vi++) = gen_rtx_USE (VOIDmode, sym);
  else
    {
      RTVEC_ELT (v, vi++) = ret_rtx;
      RTVEC_ELT (v, vi++) = gen_rtx_USE (VOIDmode, sym);
      if (frame_pointer_needed)
	{
	  rtx rbp = gen_rtx_REG (DImode, BP_REG);
	  gcc_assert (m->fs.fp_valid);
	  gcc_assert (m->fs.cfa_reg == hard_frame_pointer_rtx);

	  tmp = gen_rtx_PLUS (DImode, rbp, GEN_INT (8));
	  RTVEC_ELT (v, vi++) = gen_rtx_SET (stack_pointer_rtx, tmp);
	  RTVEC_ELT (v, vi++) = gen_rtx_SET (rbp, gen_rtx_MEM (DImode, rbp));
	  tmp = gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (VOIDmode));
	  RTVEC_ELT (v, vi++) = gen_rtx_CLOBBER (VOIDmode, tmp);
	}
      else
	{
	  /* If no hard frame pointer, we set R10 to the SP restore value.  */
	  gcc_assert (!m->fs.fp_valid);
	  gcc_assert (m->fs.cfa_reg == stack_pointer_rtx);
	  gcc_assert (m->fs.sp_valid);

	  r10 = gen_rtx_REG (DImode, R10_REG);
	  tmp = gen_rtx_PLUS (Pmode, rsi, GEN_INT (stub_ptr_offset));
	  emit_insn (gen_rtx_SET (r10, tmp));

	  RTVEC_ELT (v, vi++) = gen_rtx_SET (stack_pointer_rtx, r10);
	}
    }

  /* Generate frame load insns and restore notes.  */
  for (i = 0; i < ncregs; ++i)
    {
      const xlogue_layout::reginfo &r = xlogue.get_reginfo (i);
      machine_mode mode = SSE_REGNO_P (r.regno) ? V4SFmode : word_mode;
      rtx reg, frame_load;

      reg = gen_rtx_REG (mode, r.regno);
      frame_load = gen_frame_load (reg, rsi, r.offset);

      /* Save RSI frame load insn & note to add last.  */
      if (r.regno == SI_REG)
	{
	  gcc_assert (!rsi_frame_load);
	  rsi_frame_load = frame_load;
	  rsi_restore_offset = r.offset;
	}
      else
	{
	  RTVEC_ELT (v, vi++) = frame_load;
	  ix86_add_cfa_restore_note (NULL, reg, r.offset);
	}
    }

  /* Add RSI frame load & restore note at the end.  */
  gcc_assert (rsi_frame_load);
  gcc_assert (rsi_restore_offset != (HOST_WIDE_INT)-1);
  RTVEC_ELT (v, vi++) = rsi_frame_load;
  ix86_add_cfa_restore_note (NULL, gen_rtx_REG (DImode, SI_REG),
			     rsi_restore_offset);

  /* Finally, for tail-call w/o a hard frame pointer, set SP to R10.  */
  if (!use_call && !frame_pointer_needed)
    {
      gcc_assert (m->fs.sp_valid);
      gcc_assert (!m->fs.sp_realigned);

      /* At this point, R10 should point to frame.stack_realign_offset.  */
      if (m->fs.cfa_reg == stack_pointer_rtx)
	m->fs.cfa_offset += m->fs.sp_offset - frame.stack_realign_offset;
      m->fs.sp_offset = frame.stack_realign_offset;
    }

  gcc_assert (vi == (unsigned int)GET_NUM_ELEM (v));
  tmp = gen_rtx_PARALLEL (VOIDmode, v);
  if (use_call)
      insn = emit_insn (tmp);
  else
    {
      insn = emit_jump_insn (tmp);
      JUMP_LABEL (insn) = ret_rtx;

      if (frame_pointer_needed)
	ix86_emit_leave (insn);
      else
	{
	  /* Need CFA adjust note.  */
	  tmp = gen_rtx_SET (stack_pointer_rtx, r10);
	  add_reg_note (insn, REG_CFA_ADJUST_CFA, tmp);
	}
    }

  RTX_FRAME_RELATED_P (insn) = true;
  ix86_add_queued_cfa_restore_notes (insn);

  /* If we're not doing a tail-call, we need to adjust the stack.  */
  if (use_call && m->fs.sp_valid)
    {
      HOST_WIDE_INT dealloc = m->fs.sp_offset - frame.stack_realign_offset;
      pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				GEN_INT (dealloc), style,
				m->fs.cfa_reg == stack_pointer_rtx);
    }
}

/* Restore function stack, frame, and registers.  */

void
ix86_expand_epilogue (int style)
{
  struct machine_function *m = cfun->machine;
  struct machine_frame_state frame_state_save = m->fs;
  bool restore_regs_via_mov;
  bool using_drap;
  bool restore_stub_is_tail = false;

  if (ix86_function_naked (current_function_decl))
    {
      /* The program should not reach this point.  */
      emit_insn (gen_ud2 ());
      return;
    }

  ix86_finalize_stack_frame_flags ();
  const struct ix86_frame &frame = cfun->machine->frame;

  m->fs.sp_realigned = stack_realign_fp;
  m->fs.sp_valid = stack_realign_fp
		   || !frame_pointer_needed
		   || crtl->sp_is_unchanging;
  gcc_assert (!m->fs.sp_valid
	      || m->fs.sp_offset == frame.stack_pointer_offset);

  /* The FP must be valid if the frame pointer is present.  */
  gcc_assert (frame_pointer_needed == m->fs.fp_valid);
  gcc_assert (!m->fs.fp_valid
	      || m->fs.fp_offset == frame.hard_frame_pointer_offset);

  /* We must have *some* valid pointer to the stack frame.  */
  gcc_assert (m->fs.sp_valid || m->fs.fp_valid);

  /* The DRAP is never valid at this point.  */
  gcc_assert (!m->fs.drap_valid);

  /* See the comment about red zone and frame
     pointer usage in ix86_expand_prologue.  */
  if (frame_pointer_needed && frame.red_zone_size)
    emit_insn (gen_memory_blockage ());

  using_drap = crtl->drap_reg && crtl->stack_realign_needed;
  gcc_assert (!using_drap || m->fs.cfa_reg == crtl->drap_reg);

  /* Determine the CFA offset of the end of the red-zone.  */
  m->fs.red_zone_offset = 0;
  if (ix86_using_red_zone () && crtl->args.pops_args < 65536)
    {
      /* The red-zone begins below return address and error code in
	 exception handler.  */
      m->fs.red_zone_offset = RED_ZONE_SIZE + INCOMING_FRAME_SP_OFFSET;

      /* When the register save area is in the aligned portion of
         the stack, determine the maximum runtime displacement that
	 matches up with the aligned frame.  */
      if (stack_realign_drap)
	m->fs.red_zone_offset -= (crtl->stack_alignment_needed / BITS_PER_UNIT
				  + UNITS_PER_WORD);
    }

  HOST_WIDE_INT reg_save_offset = frame.reg_save_offset;

  /* Special care must be taken for the normal return case of a function
     using eh_return: the eax and edx registers are marked as saved, but
     not restored along this path.  Adjust the save location to match.  */
  if (crtl->calls_eh_return && style != 2)
    reg_save_offset -= 2 * UNITS_PER_WORD;

  /* EH_RETURN requires the use of moves to function properly.  */
  if (crtl->calls_eh_return)
    restore_regs_via_mov = true;
  /* SEH requires the use of pops to identify the epilogue.  */
  else if (TARGET_SEH)
    restore_regs_via_mov = false;
  /* If we're only restoring one register and sp cannot be used then
     using a move instruction to restore the register since it's
     less work than reloading sp and popping the register.  */
  else if (!sp_valid_at (frame.hfp_save_offset) && frame.nregs <= 1)
    restore_regs_via_mov = true;
  else if (TARGET_EPILOGUE_USING_MOVE
	   && cfun->machine->use_fast_prologue_epilogue
	   && (frame.nregs > 1
	       || m->fs.sp_offset != reg_save_offset))
    restore_regs_via_mov = true;
  else if (frame_pointer_needed
	   && !frame.nregs
	   && m->fs.sp_offset != reg_save_offset)
    restore_regs_via_mov = true;
  else if (frame_pointer_needed
	   && TARGET_USE_LEAVE
	   && cfun->machine->use_fast_prologue_epilogue
	   && frame.nregs == 1)
    restore_regs_via_mov = true;
  else
    restore_regs_via_mov = false;

  if (restore_regs_via_mov || frame.nsseregs)
    {
      /* Ensure that the entire register save area is addressable via
	 the stack pointer, if we will restore SSE regs via sp.  */
      if (TARGET_64BIT
	  && m->fs.sp_offset > 0x7fffffff
	  && sp_valid_at (frame.stack_realign_offset + 1)
	  && (frame.nsseregs + frame.nregs) != 0)
	{
	  pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				     GEN_INT (m->fs.sp_offset
					      - frame.sse_reg_save_offset),
				     style,
				     m->fs.cfa_reg == stack_pointer_rtx);
	}
    }

  /* If there are any SSE registers to restore, then we have to do it
     via moves, since there's obviously no pop for SSE regs.  */
  if (frame.nsseregs)
    ix86_emit_restore_sse_regs_using_mov (frame.sse_reg_save_offset,
					  style == 2);

  if (m->call_ms2sysv)
    {
      int pop_incoming_args = crtl->args.pops_args && crtl->args.size;

      /* We cannot use a tail-call for the stub if:
	 1. We have to pop incoming args,
	 2. We have additional int regs to restore, or
	 3. A sibling call will be the tail-call, or
	 4. We are emitting an eh_return_internal epilogue.

	 TODO: Item 4 has not yet tested!

	 If any of the above are true, we will call the stub rather than
	 jump to it.  */
      restore_stub_is_tail = !(pop_incoming_args || frame.nregs || style != 1);
      ix86_emit_outlined_ms2sysv_restore (frame, !restore_stub_is_tail, style);
    }

  /* If using out-of-line stub that is a tail-call, then...*/
  if (m->call_ms2sysv && restore_stub_is_tail)
    {
      /* TODO: parinoid tests. (remove eventually)  */
      gcc_assert (m->fs.sp_valid);
      gcc_assert (!m->fs.sp_realigned);
      gcc_assert (!m->fs.fp_valid);
      gcc_assert (!m->fs.realigned);
      gcc_assert (m->fs.sp_offset == UNITS_PER_WORD);
      gcc_assert (!crtl->drap_reg);
      gcc_assert (!frame.nregs);
    }
  else if (restore_regs_via_mov)
    {
      rtx t;

      if (frame.nregs)
	ix86_emit_restore_regs_using_mov (reg_save_offset, style == 2);

      /* eh_return epilogues need %ecx added to the stack pointer.  */
      if (style == 2)
	{
	  rtx sa = EH_RETURN_STACKADJ_RTX;
	  rtx_insn *insn;

	  /* %ecx can't be used for both DRAP register and eh_return.  */
	  if (crtl->drap_reg)
	    gcc_assert (REGNO (crtl->drap_reg) != CX_REG);

	  /* regparm nested functions don't work with eh_return.  */
	  gcc_assert (!ix86_static_chain_on_stack);

	  if (frame_pointer_needed)
	    {
	      t = gen_rtx_PLUS (Pmode, hard_frame_pointer_rtx, sa);
	      t = plus_constant (Pmode, t, m->fs.fp_offset - UNITS_PER_WORD);
	      emit_insn (gen_rtx_SET (sa, t));

	      t = gen_frame_mem (Pmode, hard_frame_pointer_rtx);
	      insn = emit_move_insn (hard_frame_pointer_rtx, t);

	      /* Note that we use SA as a temporary CFA, as the return
		 address is at the proper place relative to it.  We
		 pretend this happens at the FP restore insn because
		 prior to this insn the FP would be stored at the wrong
		 offset relative to SA, and after this insn we have no
		 other reasonable register to use for the CFA.  We don't
		 bother resetting the CFA to the SP for the duration of
		 the return insn, unless the control flow instrumentation
		 is done.  In this case the SP is used later and we have
		 to reset CFA to SP.  */
	      add_reg_note (insn, REG_CFA_DEF_CFA,
			    plus_constant (Pmode, sa, UNITS_PER_WORD));
	      ix86_add_queued_cfa_restore_notes (insn);
	      add_reg_note (insn, REG_CFA_RESTORE, hard_frame_pointer_rtx);
	      RTX_FRAME_RELATED_P (insn) = 1;

	      m->fs.cfa_reg = sa;
	      m->fs.cfa_offset = UNITS_PER_WORD;
	      m->fs.fp_valid = false;

	      pro_epilogue_adjust_stack (stack_pointer_rtx, sa,
					 const0_rtx, style,
					 flag_cf_protection);
	    }
	  else
	    {
	      t = gen_rtx_PLUS (Pmode, stack_pointer_rtx, sa);
	      t = plus_constant (Pmode, t, m->fs.sp_offset - UNITS_PER_WORD);
	      insn = emit_insn (gen_rtx_SET (stack_pointer_rtx, t));
	      ix86_add_queued_cfa_restore_notes (insn);

	      gcc_assert (m->fs.cfa_reg == stack_pointer_rtx);
	      if (m->fs.cfa_offset != UNITS_PER_WORD)
		{
		  m->fs.cfa_offset = UNITS_PER_WORD;
		  add_reg_note (insn, REG_CFA_DEF_CFA,
				plus_constant (Pmode, stack_pointer_rtx,
					       UNITS_PER_WORD));
		  RTX_FRAME_RELATED_P (insn) = 1;
		}
	    }
	  m->fs.sp_offset = UNITS_PER_WORD;
	  m->fs.sp_valid = true;
	  m->fs.sp_realigned = false;
	}
    }
  else
    {
      /* SEH requires that the function end with (1) a stack adjustment
	 if necessary, (2) a sequence of pops, and (3) a return or
	 jump instruction.  Prevent insns from the function body from
	 being scheduled into this sequence.  */
      if (TARGET_SEH)
	{
	  /* Prevent a catch region from being adjacent to the standard
	     epilogue sequence.  Unfortunately neither crtl->uses_eh_lsda
	     nor several other flags that would be interesting to test are
	     set up yet.  */
	  if (flag_non_call_exceptions)
	    emit_insn (gen_nops (const1_rtx));
	  else
	    emit_insn (gen_blockage ());
	}

      /* First step is to deallocate the stack frame so that we can
	 pop the registers.  If the stack pointer was realigned, it needs
	 to be restored now.  Also do it on SEH target for very large
	 frame as the emitted instructions aren't allowed by the ABI
	 in epilogues.  */
      if (!m->fs.sp_valid || m->fs.sp_realigned
 	  || (TARGET_SEH
	      && (m->fs.sp_offset - reg_save_offset
		  >= SEH_MAX_FRAME_SIZE)))
	{
	  pro_epilogue_adjust_stack (stack_pointer_rtx, hard_frame_pointer_rtx,
				     GEN_INT (m->fs.fp_offset
					      - reg_save_offset),
				     style, false);
	}
      else if (m->fs.sp_offset != reg_save_offset)
	{
	  pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				     GEN_INT (m->fs.sp_offset
					      - reg_save_offset),
				     style,
				     m->fs.cfa_reg == stack_pointer_rtx);
	}

      ix86_emit_restore_regs_using_pop ();
    }

  /* If we used a stack pointer and haven't already got rid of it,
     then do so now.  */
  if (m->fs.fp_valid)
    {
      /* If the stack pointer is valid and pointing at the frame
	 pointer store address, then we only need a pop.  */
      if (sp_valid_at (frame.hfp_save_offset)
	  && m->fs.sp_offset == frame.hfp_save_offset)
	ix86_emit_restore_reg_using_pop (hard_frame_pointer_rtx);
      /* Leave results in shorter dependency chains on CPUs that are
	 able to grok it fast.  */
      else if (TARGET_USE_LEAVE
	       || optimize_bb_for_size_p (EXIT_BLOCK_PTR_FOR_FN (cfun))
	       || !cfun->machine->use_fast_prologue_epilogue)
	ix86_emit_leave (NULL);
      else
        {
	  pro_epilogue_adjust_stack (stack_pointer_rtx,
				     hard_frame_pointer_rtx,
				     const0_rtx, style, !using_drap);
	  ix86_emit_restore_reg_using_pop (hard_frame_pointer_rtx);
        }
    }

  if (using_drap)
    {
      int param_ptr_offset = UNITS_PER_WORD;
      rtx_insn *insn;

      gcc_assert (stack_realign_drap);

      if (ix86_static_chain_on_stack)
	param_ptr_offset += UNITS_PER_WORD;
      if (!call_used_regs[REGNO (crtl->drap_reg)])
	param_ptr_offset += UNITS_PER_WORD;

      insn = emit_insn (gen_rtx_SET
			(stack_pointer_rtx,
			 gen_rtx_PLUS (Pmode,
				       crtl->drap_reg,
				       GEN_INT (-param_ptr_offset))));
      m->fs.cfa_reg = stack_pointer_rtx;
      m->fs.cfa_offset = param_ptr_offset;
      m->fs.sp_offset = param_ptr_offset;
      m->fs.realigned = false;

      add_reg_note (insn, REG_CFA_DEF_CFA,
		    gen_rtx_PLUS (Pmode, stack_pointer_rtx,
				  GEN_INT (param_ptr_offset)));
      RTX_FRAME_RELATED_P (insn) = 1;

      if (!call_used_regs[REGNO (crtl->drap_reg)])
	ix86_emit_restore_reg_using_pop (crtl->drap_reg);
    }

  /* At this point the stack pointer must be valid, and we must have
     restored all of the registers.  We may not have deallocated the
     entire stack frame.  We've delayed this until now because it may
     be possible to merge the local stack deallocation with the
     deallocation forced by ix86_static_chain_on_stack.   */
  gcc_assert (m->fs.sp_valid);
  gcc_assert (!m->fs.sp_realigned);
  gcc_assert (!m->fs.fp_valid);
  gcc_assert (!m->fs.realigned);
  if (m->fs.sp_offset != UNITS_PER_WORD)
    {
      pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				 GEN_INT (m->fs.sp_offset - UNITS_PER_WORD),
				 style, true);
    }
  else
    ix86_add_queued_cfa_restore_notes (get_last_insn ());

  /* Sibcall epilogues don't want a return instruction.  */
  if (style == 0)
    {
      m->fs = frame_state_save;
      return;
    }

  if (cfun->machine->func_type != TYPE_NORMAL)
    emit_jump_insn (gen_interrupt_return ());
  else if (crtl->args.pops_args && crtl->args.size)
    {
      rtx popc = GEN_INT (crtl->args.pops_args);

      /* i386 can only pop 64K bytes.  If asked to pop more, pop return
	 address, do explicit add, and jump indirectly to the caller.  */

      if (crtl->args.pops_args >= 65536)
	{
	  rtx ecx = gen_rtx_REG (SImode, CX_REG);
	  rtx_insn *insn;

	  /* There is no "pascal" calling convention in any 64bit ABI.  */
	  gcc_assert (!TARGET_64BIT);

	  insn = emit_insn (gen_pop (ecx));
	  m->fs.cfa_offset -= UNITS_PER_WORD;
	  m->fs.sp_offset -= UNITS_PER_WORD;

	  rtx x = plus_constant (Pmode, stack_pointer_rtx, UNITS_PER_WORD);
	  x = gen_rtx_SET (stack_pointer_rtx, x);
	  add_reg_note (insn, REG_CFA_ADJUST_CFA, x);
	  add_reg_note (insn, REG_CFA_REGISTER, gen_rtx_SET (ecx, pc_rtx));
	  RTX_FRAME_RELATED_P (insn) = 1;

	  pro_epilogue_adjust_stack (stack_pointer_rtx, stack_pointer_rtx,
				     popc, -1, true);
	  emit_jump_insn (gen_simple_return_indirect_internal (ecx));
	}
      else
	emit_jump_insn (gen_simple_return_pop_internal (popc));
    }
  else if (!m->call_ms2sysv || !restore_stub_is_tail)
    {
      /* In case of return from EH a simple return cannot be used
	 as a return address will be compared with a shadow stack
	 return address.  Use indirect jump instead.  */
      if (style == 2 && flag_cf_protection)
	{
	  /* Register used in indirect jump must be in word_mode.  But
	     Pmode may not be the same as word_mode for x32.  */
	  rtx ecx = gen_rtx_REG (word_mode, CX_REG);
	  rtx_insn *insn;

	  insn = emit_insn (gen_pop (ecx));
	  m->fs.cfa_offset -= UNITS_PER_WORD;
	  m->fs.sp_offset -= UNITS_PER_WORD;

	  rtx x = plus_constant (Pmode, stack_pointer_rtx, UNITS_PER_WORD);
	  x = gen_rtx_SET (stack_pointer_rtx, x);
	  add_reg_note (insn, REG_CFA_ADJUST_CFA, x);
	  add_reg_note (insn, REG_CFA_REGISTER, gen_rtx_SET (ecx, pc_rtx));
	  RTX_FRAME_RELATED_P (insn) = 1;

	  emit_jump_insn (gen_simple_return_indirect_internal (ecx));
	}
      else
	emit_jump_insn (gen_simple_return_internal ());
    }

  /* Restore the state back to the state from the prologue,
     so that it's correct for the next epilogue.  */
  m->fs = frame_state_save;
}

/* Reset from the function's potential modifications.  */

static void
ix86_output_function_epilogue (FILE *file ATTRIBUTE_UNUSED)
{
  if (pic_offset_table_rtx
      && !ix86_use_pseudo_pic_reg ())
    SET_REGNO (pic_offset_table_rtx, REAL_PIC_OFFSET_TABLE_REGNUM);

  if (TARGET_MACHO)
    {
      rtx_insn *insn = get_last_insn ();
      rtx_insn *deleted_debug_label = NULL;

      /* Mach-O doesn't support labels at the end of objects, so if
         it looks like we might want one, take special action.
        First, collect any sequence of deleted debug labels.  */
      while (insn
	     && NOTE_P (insn)
	     && NOTE_KIND (insn) != NOTE_INSN_DELETED_LABEL)
	{
	  /* Don't insert a nop for NOTE_INSN_DELETED_DEBUG_LABEL
	     notes only, instead set their CODE_LABEL_NUMBER to -1,
	     otherwise there would be code generation differences
	     in between -g and -g0.  */
	  if (NOTE_P (insn) && NOTE_KIND (insn)
	      == NOTE_INSN_DELETED_DEBUG_LABEL)
	    deleted_debug_label = insn;
	  insn = PREV_INSN (insn);
	}

      /* If we have:
	 label:
	    barrier
	  then this needs to be detected, so skip past the barrier.  */

      if (insn && BARRIER_P (insn))
	insn = PREV_INSN (insn);

      /* Up to now we've only seen notes or barriers.  */
      if (insn)
	{
	  if (LABEL_P (insn)
	      || (NOTE_P (insn)
		  && NOTE_KIND (insn) == NOTE_INSN_DELETED_LABEL))
	    /* Trailing label.  */
	    fputs ("\tnop\n", file);
	  else if (cfun && ! cfun->is_thunk)
	    {
	      /* See if we have a completely empty function body, skipping
	         the special case of the picbase thunk emitted as asm.  */
	      while (insn && ! INSN_P (insn))
		insn = PREV_INSN (insn);
	      /* If we don't find any insns, we've got an empty function body;
		 I.e. completely empty - without a return or branch.  This is
		 taken as the case where a function body has been removed
		 because it contains an inline __builtin_unreachable().  GCC
		 declares that reaching __builtin_unreachable() means UB so
		 we're not obliged to do anything special; however, we want
		 non-zero-sized function bodies.  To meet this, and help the
		 user out, let's trap the case.  */
	      if (insn == NULL)
		fputs ("\tud2\n", file);
	    }
	}
      else if (deleted_debug_label)
	for (insn = deleted_debug_label; insn; insn = NEXT_INSN (insn))
	  if (NOTE_KIND (insn) == NOTE_INSN_DELETED_DEBUG_LABEL)
	    CODE_LABEL_NUMBER (insn) = -1;
    }
}

/* Return a scratch register to use in the split stack prologue.  The
   split stack prologue is used for -fsplit-stack.  It is the first
   instructions in the function, even before the regular prologue.
   The scratch register can be any caller-saved register which is not
   used for parameters or for the static chain.  */

static unsigned int
split_stack_prologue_scratch_regno (void)
{
  if (TARGET_64BIT)
    return R11_REG;
  else
    {
      bool is_fastcall, is_thiscall;
      int regparm;

      is_fastcall = (lookup_attribute ("fastcall",
				       TYPE_ATTRIBUTES (TREE_TYPE (cfun->decl)))
		     != NULL);
      is_thiscall = (lookup_attribute ("thiscall",
				       TYPE_ATTRIBUTES (TREE_TYPE (cfun->decl)))
		     != NULL);
      regparm = ix86_function_regparm (TREE_TYPE (cfun->decl), cfun->decl);

      if (is_fastcall)
	{
	  if (DECL_STATIC_CHAIN (cfun->decl))
	    {
	      sorry ("-fsplit-stack does not support fastcall with "
		     "nested function");
	      return INVALID_REGNUM;
	    }
	  return AX_REG;
	}
      else if (is_thiscall)
        {
	  if (!DECL_STATIC_CHAIN (cfun->decl))
	    return DX_REG;
	  return AX_REG;
	}
      else if (regparm < 3)
	{
	  if (!DECL_STATIC_CHAIN (cfun->decl))
	    return CX_REG;
	  else
	    {
	      if (regparm >= 2)
		{
		  sorry ("-fsplit-stack does not support 2 register "
			 "parameters for a nested function");
		  return INVALID_REGNUM;
		}
	      return DX_REG;
	    }
	}
      else
	{
	  /* FIXME: We could make this work by pushing a register
	     around the addition and comparison.  */
	  sorry ("-fsplit-stack does not support 3 register parameters");
	  return INVALID_REGNUM;
	}
    }
}

/* A SYMBOL_REF for the function which allocates new stackspace for
   -fsplit-stack.  */

static GTY(()) rtx split_stack_fn;

/* A SYMBOL_REF for the more stack function when using the large
   model.  */

static GTY(()) rtx split_stack_fn_large;

/* Return location of the stack guard value in the TLS block.  */

rtx
ix86_split_stack_guard (void)
{
  int offset;
  addr_space_t as = DEFAULT_TLS_SEG_REG;
  rtx r;

  gcc_assert (flag_split_stack);

#ifdef TARGET_THREAD_SPLIT_STACK_OFFSET
  offset = TARGET_THREAD_SPLIT_STACK_OFFSET;
#else
  gcc_unreachable ();
#endif

  r = GEN_INT (offset);
  r = gen_const_mem (Pmode, r);
  set_mem_addr_space (r, as);

  return r;
}

/* Handle -fsplit-stack.  These are the first instructions in the
   function, even before the regular prologue.  */

void
ix86_expand_split_stack_prologue (void)
{
  HOST_WIDE_INT allocate;
  unsigned HOST_WIDE_INT args_size;
  rtx_code_label *label;
  rtx limit, current, allocate_rtx, call_fusage;
  rtx_insn *call_insn;
  rtx scratch_reg = NULL_RTX;
  rtx_code_label *varargs_label = NULL;
  rtx fn;

  gcc_assert (flag_split_stack && reload_completed);

  ix86_finalize_stack_frame_flags ();
  struct ix86_frame &frame = cfun->machine->frame;
  allocate = frame.stack_pointer_offset - INCOMING_FRAME_SP_OFFSET;

  /* This is the label we will branch to if we have enough stack
     space.  We expect the basic block reordering pass to reverse this
     branch if optimizing, so that we branch in the unlikely case.  */
  label = gen_label_rtx ();

  /* We need to compare the stack pointer minus the frame size with
     the stack boundary in the TCB.  The stack boundary always gives
     us SPLIT_STACK_AVAILABLE bytes, so if we need less than that we
     can compare directly.  Otherwise we need to do an addition.  */

  limit = ix86_split_stack_guard ();

  if (allocate < SPLIT_STACK_AVAILABLE)
    current = stack_pointer_rtx;
  else
    {
      unsigned int scratch_regno;
      rtx offset;

      /* We need a scratch register to hold the stack pointer minus
	 the required frame size.  Since this is the very start of the
	 function, the scratch register can be any caller-saved
	 register which is not used for parameters.  */
      offset = GEN_INT (- allocate);
      scratch_regno = split_stack_prologue_scratch_regno ();
      if (scratch_regno == INVALID_REGNUM)
	return;
      scratch_reg = gen_rtx_REG (Pmode, scratch_regno);
      if (!TARGET_64BIT || x86_64_immediate_operand (offset, Pmode))
	{
	  /* We don't use ix86_gen_add3 in this case because it will
	     want to split to lea, but when not optimizing the insn
	     will not be split after this point.  */
	  emit_insn (gen_rtx_SET (scratch_reg,
				  gen_rtx_PLUS (Pmode, stack_pointer_rtx,
						offset)));
	}
      else
	{
	  emit_move_insn (scratch_reg, offset);
	  emit_insn (ix86_gen_add3 (scratch_reg, scratch_reg,
				    stack_pointer_rtx));
	}
      current = scratch_reg;
    }

  ix86_expand_branch (GEU, current, limit, label);
  rtx_insn *jump_insn = get_last_insn ();
  JUMP_LABEL (jump_insn) = label;

  /* Mark the jump as very likely to be taken.  */
  add_reg_br_prob_note (jump_insn, profile_probability::very_likely ());

  if (split_stack_fn == NULL_RTX)
    {
      split_stack_fn = gen_rtx_SYMBOL_REF (Pmode, "__morestack");
      SYMBOL_REF_FLAGS (split_stack_fn) |= SYMBOL_FLAG_LOCAL;
    }
  fn = split_stack_fn;

  /* Get more stack space.  We pass in the desired stack space and the
     size of the arguments to copy to the new stack.  In 32-bit mode
     we push the parameters; __morestack will return on a new stack
     anyhow.  In 64-bit mode we pass the parameters in r10 and
     r11.  */
  allocate_rtx = GEN_INT (allocate);
  args_size = crtl->args.size >= 0 ? (HOST_WIDE_INT) crtl->args.size : 0;
  call_fusage = NULL_RTX;
  rtx pop = NULL_RTX;
  if (TARGET_64BIT)
    {
      rtx reg10, reg11;

      reg10 = gen_rtx_REG (Pmode, R10_REG);
      reg11 = gen_rtx_REG (Pmode, R11_REG);

      /* If this function uses a static chain, it will be in %r10.
	 Preserve it across the call to __morestack.  */
      if (DECL_STATIC_CHAIN (cfun->decl))
	{
	  rtx rax;

	  rax = gen_rtx_REG (word_mode, AX_REG);
	  emit_move_insn (rax, gen_rtx_REG (word_mode, R10_REG));
	  use_reg (&call_fusage, rax);
	}

      if ((ix86_cmodel == CM_LARGE || ix86_cmodel == CM_LARGE_PIC)
          && !TARGET_PECOFF)
	{
	  HOST_WIDE_INT argval;

	  gcc_assert (Pmode == DImode);
	  /* When using the large model we need to load the address
	     into a register, and we've run out of registers.  So we
	     switch to a different calling convention, and we call a
	     different function: __morestack_large.  We pass the
	     argument size in the upper 32 bits of r10 and pass the
	     frame size in the lower 32 bits.  */
	  gcc_assert ((allocate & HOST_WIDE_INT_C (0xffffffff)) == allocate);
	  gcc_assert ((args_size & 0xffffffff) == args_size);

	  if (split_stack_fn_large == NULL_RTX)
	    {
	      split_stack_fn_large
		= gen_rtx_SYMBOL_REF (Pmode, "__morestack_large_model");
	      SYMBOL_REF_FLAGS (split_stack_fn_large) |= SYMBOL_FLAG_LOCAL;
	    }
	  if (ix86_cmodel == CM_LARGE_PIC)
	    {
	      rtx_code_label *label;
	      rtx x;

	      label = gen_label_rtx ();
	      emit_label (label);
	      LABEL_PRESERVE_P (label) = 1;
	      emit_insn (gen_set_rip_rex64 (reg10, label));
	      emit_insn (gen_set_got_offset_rex64 (reg11, label));
	      emit_insn (ix86_gen_add3 (reg10, reg10, reg11));
	      x = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, split_stack_fn_large),
				  UNSPEC_GOT);
	      x = gen_rtx_CONST (Pmode, x);
	      emit_move_insn (reg11, x);
	      x = gen_rtx_PLUS (Pmode, reg10, reg11);
	      x = gen_const_mem (Pmode, x);
	      emit_move_insn (reg11, x);
	    }
	  else
	    emit_move_insn (reg11, split_stack_fn_large);

	  fn = reg11;

	  argval = ((args_size << 16) << 16) + allocate;
	  emit_move_insn (reg10, GEN_INT (argval));
	}
      else
	{
	  emit_move_insn (reg10, allocate_rtx);
	  emit_move_insn (reg11, GEN_INT (args_size));
	  use_reg (&call_fusage, reg11);
	}

      use_reg (&call_fusage, reg10);
    }
  else
    {
      rtx_insn *insn = emit_insn (gen_push (GEN_INT (args_size)));
      add_reg_note (insn, REG_ARGS_SIZE, GEN_INT (UNITS_PER_WORD));
      insn = emit_insn (gen_push (allocate_rtx));
      add_reg_note (insn, REG_ARGS_SIZE, GEN_INT (2 * UNITS_PER_WORD));
      pop = GEN_INT (2 * UNITS_PER_WORD);
    }
  call_insn = ix86_expand_call (NULL_RTX, gen_rtx_MEM (QImode, fn),
				GEN_INT (UNITS_PER_WORD), constm1_rtx,
				pop, false);
  add_function_usage_to (call_insn, call_fusage);
  if (!TARGET_64BIT)
    add_reg_note (call_insn, REG_ARGS_SIZE, GEN_INT (0));
  /* Indicate that this function can't jump to non-local gotos.  */
  make_reg_eh_region_note_nothrow_nononlocal (call_insn);

  /* In order to make call/return prediction work right, we now need
     to execute a return instruction.  See
     libgcc/config/i386/morestack.S for the details on how this works.

     For flow purposes gcc must not see this as a return
     instruction--we need control flow to continue at the subsequent
     label.  Therefore, we use an unspec.  */
  gcc_assert (crtl->args.pops_args < 65536);
  rtx_insn *ret_insn
    = emit_insn (gen_split_stack_return (GEN_INT (crtl->args.pops_args)));

  if ((flag_cf_protection & CF_BRANCH))
    {
      /* Insert ENDBR since __morestack will jump back here via indirect
	 call.  */
      rtx cet_eb = gen_nop_endbr ();
      emit_insn_after (cet_eb, ret_insn);
    }

  /* If we are in 64-bit mode and this function uses a static chain,
     we saved %r10 in %rax before calling _morestack.  */
  if (TARGET_64BIT && DECL_STATIC_CHAIN (cfun->decl))
    emit_move_insn (gen_rtx_REG (word_mode, R10_REG),
		    gen_rtx_REG (word_mode, AX_REG));

  /* If this function calls va_start, we need to store a pointer to
     the arguments on the old stack, because they may not have been
     all copied to the new stack.  At this point the old stack can be
     found at the frame pointer value used by __morestack, because
     __morestack has set that up before calling back to us.  Here we
     store that pointer in a scratch register, and in
     ix86_expand_prologue we store the scratch register in a stack
     slot.  */
  if (cfun->machine->split_stack_varargs_pointer != NULL_RTX)
    {
      unsigned int scratch_regno;
      rtx frame_reg;
      int words;

      scratch_regno = split_stack_prologue_scratch_regno ();
      scratch_reg = gen_rtx_REG (Pmode, scratch_regno);
      frame_reg = gen_rtx_REG (Pmode, BP_REG);

      /* 64-bit:
	 fp -> old fp value
	       return address within this function
	       return address of caller of this function
	       stack arguments
	 So we add three words to get to the stack arguments.

	 32-bit:
	 fp -> old fp value
	       return address within this function
               first argument to __morestack
               second argument to __morestack
               return address of caller of this function
               stack arguments
         So we add five words to get to the stack arguments.
      */
      words = TARGET_64BIT ? 3 : 5;
      emit_insn (gen_rtx_SET (scratch_reg,
			      gen_rtx_PLUS (Pmode, frame_reg,
					    GEN_INT (words * UNITS_PER_WORD))));

      varargs_label = gen_label_rtx ();
      emit_jump_insn (gen_jump (varargs_label));
      JUMP_LABEL (get_last_insn ()) = varargs_label;

      emit_barrier ();
    }

  emit_label (label);
  LABEL_NUSES (label) = 1;

  /* If this function calls va_start, we now have to set the scratch
     register for the case where we do not call __morestack.  In this
     case we need to set it based on the stack pointer.  */
  if (cfun->machine->split_stack_varargs_pointer != NULL_RTX)
    {
      emit_insn (gen_rtx_SET (scratch_reg,
			      gen_rtx_PLUS (Pmode, stack_pointer_rtx,
					    GEN_INT (UNITS_PER_WORD))));

      emit_label (varargs_label);
      LABEL_NUSES (varargs_label) = 1;
    }
}

/* We may have to tell the dataflow pass that the split stack prologue
   is initializing a scratch register.  */

static void
ix86_live_on_entry (bitmap regs)
{
  if (cfun->machine->split_stack_varargs_pointer != NULL_RTX)
    {
      gcc_assert (flag_split_stack);
      bitmap_set_bit (regs, split_stack_prologue_scratch_regno ());
    }
}

/* Extract the parts of an RTL expression that is a valid memory address
   for an instruction.  Return 0 if the structure of the address is
   grossly off.  Return -1 if the address contains ASHIFT, so it is not
   strictly valid, but still used for computing length of lea instruction.  */

int
ix86_decompose_address (rtx addr, struct ix86_address *out)
{
  rtx base = NULL_RTX, index = NULL_RTX, disp = NULL_RTX;
  rtx base_reg, index_reg;
  HOST_WIDE_INT scale = 1;
  rtx scale_rtx = NULL_RTX;
  rtx tmp;
  int retval = 1;
  addr_space_t seg = ADDR_SPACE_GENERIC;

  /* Allow zero-extended SImode addresses,
     they will be emitted with addr32 prefix.  */
  if (TARGET_64BIT && GET_MODE (addr) == DImode)
    {
      if (GET_CODE (addr) == ZERO_EXTEND
	  && GET_MODE (XEXP (addr, 0)) == SImode)
	{
	  addr = XEXP (addr, 0);
	  if (CONST_INT_P (addr))
	    return 0;
	}	      
      else if (GET_CODE (addr) == AND
	       && const_32bit_mask (XEXP (addr, 1), DImode))
	{
	  addr = lowpart_subreg (SImode, XEXP (addr, 0), DImode);
	  if (addr == NULL_RTX)
	    return 0;

	  if (CONST_INT_P (addr))
	    return 0;
	}
    }

  /* Allow SImode subregs of DImode addresses,
     they will be emitted with addr32 prefix.  */
  if (TARGET_64BIT && GET_MODE (addr) == SImode)
    {
      if (SUBREG_P (addr)
	  && GET_MODE (SUBREG_REG (addr)) == DImode)
	{
	  addr = SUBREG_REG (addr);
	  if (CONST_INT_P (addr))
	    return 0;
	}
    }

  if (REG_P (addr))
    base = addr;
  else if (SUBREG_P (addr))
    {
      if (REG_P (SUBREG_REG (addr)))
	base = addr;
      else
	return 0;
    }
  else if (GET_CODE (addr) == PLUS)
    {
      rtx addends[4], op;
      int n = 0, i;

      op = addr;
      do
	{
	  if (n >= 4)
	    return 0;
	  addends[n++] = XEXP (op, 1);
	  op = XEXP (op, 0);
	}
      while (GET_CODE (op) == PLUS);
      if (n >= 4)
	return 0;
      addends[n] = op;

      for (i = n; i >= 0; --i)
	{
	  op = addends[i];
	  switch (GET_CODE (op))
	    {
	    case MULT:
	      if (index)
		return 0;
	      index = XEXP (op, 0);
	      scale_rtx = XEXP (op, 1);
	      break;

	    case ASHIFT:
	      if (index)
		return 0;
	      index = XEXP (op, 0);
	      tmp = XEXP (op, 1);
	      if (!CONST_INT_P (tmp))
		return 0;
	      scale = INTVAL (tmp);
	      if ((unsigned HOST_WIDE_INT) scale > 3)
		return 0;
	      scale = 1 << scale;
	      break;

	    case ZERO_EXTEND:
	      op = XEXP (op, 0);
	      if (GET_CODE (op) != UNSPEC)
		return 0;
	      /* FALLTHRU */

	    case UNSPEC:
	      if (XINT (op, 1) == UNSPEC_TP
	          && TARGET_TLS_DIRECT_SEG_REFS
	          && seg == ADDR_SPACE_GENERIC)
		seg = DEFAULT_TLS_SEG_REG;
	      else
		return 0;
	      break;

	    case SUBREG:
	      if (!REG_P (SUBREG_REG (op)))
		return 0;
	      /* FALLTHRU */

	    case REG:
	      if (!base)
		base = op;
	      else if (!index)
		index = op;
	      else
		return 0;
	      break;

	    case CONST:
	    case CONST_INT:
	    case SYMBOL_REF:
	    case LABEL_REF:
	      if (disp)
		return 0;
	      disp = op;
	      break;

	    default:
	      return 0;
	    }
	}
    }
  else if (GET_CODE (addr) == MULT)
    {
      index = XEXP (addr, 0);		/* index*scale */
      scale_rtx = XEXP (addr, 1);
    }
  else if (GET_CODE (addr) == ASHIFT)
    {
      /* We're called for lea too, which implements ashift on occasion.  */
      index = XEXP (addr, 0);
      tmp = XEXP (addr, 1);
      if (!CONST_INT_P (tmp))
	return 0;
      scale = INTVAL (tmp);
      if ((unsigned HOST_WIDE_INT) scale > 3)
	return 0;
      scale = 1 << scale;
      retval = -1;
    }
  else
    disp = addr;			/* displacement */

  if (index)
    {
      if (REG_P (index))
	;
      else if (SUBREG_P (index)
	       && REG_P (SUBREG_REG (index)))
	;
      else
	return 0;
    }

  /* Extract the integral value of scale.  */
  if (scale_rtx)
    {
      if (!CONST_INT_P (scale_rtx))
	return 0;
      scale = INTVAL (scale_rtx);
    }

  base_reg = base && SUBREG_P (base) ? SUBREG_REG (base) : base;
  index_reg = index && SUBREG_P (index) ? SUBREG_REG (index) : index;

  /* Avoid useless 0 displacement.  */
  if (disp == const0_rtx && (base || index))
    disp = NULL_RTX;

  /* Allow arg pointer and stack pointer as index if there is not scaling.  */
  if (base_reg && index_reg && scale == 1
      && (REGNO (index_reg) == ARG_POINTER_REGNUM
	  || REGNO (index_reg) == FRAME_POINTER_REGNUM
	  || REGNO (index_reg) == SP_REG))
    {
      std::swap (base, index);
      std::swap (base_reg, index_reg);
    }

  /* Special case: %ebp cannot be encoded as a base without a displacement.
     Similarly %r13.  */
  if (!disp && base_reg
      && (REGNO (base_reg) == ARG_POINTER_REGNUM
	  || REGNO (base_reg) == FRAME_POINTER_REGNUM
	  || REGNO (base_reg) == BP_REG
	  || REGNO (base_reg) == R13_REG))
    disp = const0_rtx;

  /* Special case: on K6, [%esi] makes the instruction vector decoded.
     Avoid this by transforming to [%esi+0].
     Reload calls address legitimization without cfun defined, so we need
     to test cfun for being non-NULL. */
  if (TARGET_K6 && cfun && optimize_function_for_speed_p (cfun)
      && base_reg && !index_reg && !disp
      && REGNO (base_reg) == SI_REG)
    disp = const0_rtx;

  /* Special case: encode reg+reg instead of reg*2.  */
  if (!base && index && scale == 2)
    base = index, base_reg = index_reg, scale = 1;

  /* Special case: scaling cannot be encoded without base or displacement.  */
  if (!base && !disp && index && scale != 1)
    disp = const0_rtx;

  out->base = base;
  out->index = index;
  out->disp = disp;
  out->scale = scale;
  out->seg = seg;

  return retval;
}

/* Return cost of the memory address x.
   For i386, it is better to use a complex address than let gcc copy
   the address into a reg and make a new pseudo.  But not if the address
   requires to two regs - that would mean more pseudos with longer
   lifetimes.  */
static int
ix86_address_cost (rtx x, machine_mode, addr_space_t, bool)
{
  struct ix86_address parts;
  int cost = 1;
  int ok = ix86_decompose_address (x, &parts);

  gcc_assert (ok);

  if (parts.base && SUBREG_P (parts.base))
    parts.base = SUBREG_REG (parts.base);
  if (parts.index && SUBREG_P (parts.index))
    parts.index = SUBREG_REG (parts.index);

  /* Attempt to minimize number of registers in the address by increasing
     address cost for each used register.  We don't increase address cost
     for "pic_offset_table_rtx".  When a memopt with "pic_offset_table_rtx"
     is not invariant itself it most likely means that base or index is not
     invariant.  Therefore only "pic_offset_table_rtx" could be hoisted out,
     which is not profitable for x86.  */
  if (parts.base
      && (!REG_P (parts.base) || REGNO (parts.base) >= FIRST_PSEUDO_REGISTER)
      && (current_pass->type == GIMPLE_PASS
	  || !pic_offset_table_rtx
	  || !REG_P (parts.base)
	  || REGNO (pic_offset_table_rtx) != REGNO (parts.base)))
    cost++;

  if (parts.index
      && (!REG_P (parts.index) || REGNO (parts.index) >= FIRST_PSEUDO_REGISTER)
      && (current_pass->type == GIMPLE_PASS
	  || !pic_offset_table_rtx
	  || !REG_P (parts.index)
	  || REGNO (pic_offset_table_rtx) != REGNO (parts.index)))
    cost++;

  /* AMD-K6 don't like addresses with ModR/M set to 00_xxx_100b,
     since it's predecode logic can't detect the length of instructions
     and it degenerates to vector decoded.  Increase cost of such
     addresses here.  The penalty is minimally 2 cycles.  It may be worthwhile
     to split such addresses or even refuse such addresses at all.

     Following addressing modes are affected:
      [base+scale*index]
      [scale*index+disp]
      [base+index]

     The first and last case  may be avoidable by explicitly coding the zero in
     memory address, but I don't have AMD-K6 machine handy to check this
     theory.  */

  if (TARGET_K6
      && ((!parts.disp && parts.base && parts.index && parts.scale != 1)
	  || (parts.disp && !parts.base && parts.index && parts.scale != 1)
	  || (!parts.disp && parts.base && parts.index && parts.scale == 1)))
    cost += 10;

  return cost;
}

/* Allow {LABEL | SYMBOL}_REF - SYMBOL_REF-FOR-PICBASE for Mach-O as
   this is used for to form addresses to local data when -fPIC is in
   use.  */

static bool
darwin_local_data_pic (rtx disp)
{
  return (GET_CODE (disp) == UNSPEC
	  && XINT (disp, 1) == UNSPEC_MACHOPIC_OFFSET);
}

/* True if operand X should be loaded from GOT.  */

bool
ix86_force_load_from_GOT_p (rtx x)
{
  return ((TARGET_64BIT || HAVE_AS_IX86_GOT32X)
	  && !TARGET_PECOFF && !TARGET_MACHO
	  && !flag_pic
	  && ix86_cmodel != CM_LARGE
	  && GET_CODE (x) == SYMBOL_REF
	  && SYMBOL_REF_FUNCTION_P (x)
	  && (!flag_plt
	      || (SYMBOL_REF_DECL (x)
		  && lookup_attribute ("noplt",
				       DECL_ATTRIBUTES (SYMBOL_REF_DECL (x)))))
	  && !SYMBOL_REF_LOCAL_P (x));
}

/* Determine if a given RTX is a valid constant.  We already know this
   satisfies CONSTANT_P.  */

static bool
ix86_legitimate_constant_p (machine_mode mode, rtx x)
{
  switch (GET_CODE (x))
    {
    case CONST:
      x = XEXP (x, 0);

      if (GET_CODE (x) == PLUS)
	{
	  if (!CONST_INT_P (XEXP (x, 1)))
	    return false;
	  x = XEXP (x, 0);
	}

      if (TARGET_MACHO && darwin_local_data_pic (x))
	return true;

      /* Only some unspecs are valid as "constants".  */
      if (GET_CODE (x) == UNSPEC)
	switch (XINT (x, 1))
	  {
	  case UNSPEC_GOT:
	  case UNSPEC_GOTOFF:
	  case UNSPEC_PLTOFF:
	    return TARGET_64BIT;
	  case UNSPEC_TPOFF:
	  case UNSPEC_NTPOFF:
	    x = XVECEXP (x, 0, 0);
	    return (GET_CODE (x) == SYMBOL_REF
		    && SYMBOL_REF_TLS_MODEL (x) == TLS_MODEL_LOCAL_EXEC);
	  case UNSPEC_DTPOFF:
	    x = XVECEXP (x, 0, 0);
	    return (GET_CODE (x) == SYMBOL_REF
		    && SYMBOL_REF_TLS_MODEL (x) == TLS_MODEL_LOCAL_DYNAMIC);
	  default:
	    return false;
	  }

      /* We must have drilled down to a symbol.  */
      if (GET_CODE (x) == LABEL_REF)
	return true;
      if (GET_CODE (x) != SYMBOL_REF)
	return false;
      /* FALLTHRU */

    case SYMBOL_REF:
      /* TLS symbols are never valid.  */
      if (SYMBOL_REF_TLS_MODEL (x))
	return false;

      /* DLLIMPORT symbols are never valid.  */
      if (TARGET_DLLIMPORT_DECL_ATTRIBUTES
	  && SYMBOL_REF_DLLIMPORT_P (x))
	return false;

#if TARGET_MACHO
      /* mdynamic-no-pic */
      if (MACHO_DYNAMIC_NO_PIC_P)
	return machopic_symbol_defined_p (x);
#endif

      /* External function address should be loaded
	 via the GOT slot to avoid PLT.  */
      if (ix86_force_load_from_GOT_p (x))
	return false;

      break;

    CASE_CONST_SCALAR_INT:
      switch (mode)
	{
	case E_TImode:
	  if (TARGET_64BIT)
	    return true;
	  /* FALLTHRU */
	case E_OImode:
	case E_XImode:
	  if (!standard_sse_constant_p (x, mode))
	    return false;
	default:
	  break;
	}
      break;

    case CONST_VECTOR:
      if (!standard_sse_constant_p (x, mode))
	return false;

    default:
      break;
    }

  /* Otherwise we handle everything else in the move patterns.  */
  return true;
}

/* Determine if it's legal to put X into the constant pool.  This
   is not possible for the address of thread-local symbols, which
   is checked above.  */

static bool
ix86_cannot_force_const_mem (machine_mode mode, rtx x)
{
  /* We can put any immediate constant in memory.  */
  switch (GET_CODE (x))
    {
    CASE_CONST_ANY:
      return false;

    default:
      break;
    }

  return !ix86_legitimate_constant_p (mode, x);
}

/*  Nonzero if the symbol is marked as dllimport, or as stub-variable,
    otherwise zero.  */

static bool
is_imported_p (rtx x)
{
  if (!TARGET_DLLIMPORT_DECL_ATTRIBUTES
      || GET_CODE (x) != SYMBOL_REF)
    return false;

  return SYMBOL_REF_DLLIMPORT_P (x) || SYMBOL_REF_STUBVAR_P (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.  */

bool
legitimate_pic_operand_p (rtx x)
{
  rtx inner;

  switch (GET_CODE (x))
    {
    case CONST:
      inner = XEXP (x, 0);
      if (GET_CODE (inner) == PLUS
	  && CONST_INT_P (XEXP (inner, 1)))
	inner = XEXP (inner, 0);

      /* Only some unspecs are valid as "constants".  */
      if (GET_CODE (inner) == UNSPEC)
	switch (XINT (inner, 1))
	  {
	  case UNSPEC_GOT:
	  case UNSPEC_GOTOFF:
	  case UNSPEC_PLTOFF:
	    return TARGET_64BIT;
	  case UNSPEC_TPOFF:
	    x = XVECEXP (inner, 0, 0);
	    return (GET_CODE (x) == SYMBOL_REF
		    && SYMBOL_REF_TLS_MODEL (x) == TLS_MODEL_LOCAL_EXEC);
	  case UNSPEC_MACHOPIC_OFFSET:
	    return legitimate_pic_address_disp_p (x);
	  default:
	    return false;
	  }
      /* FALLTHRU */

    case SYMBOL_REF:
    case LABEL_REF:
      return legitimate_pic_address_disp_p (x);

    default:
      return true;
    }
}

/* Determine if a given CONST RTX is a valid memory displacement
   in PIC mode.  */

bool
legitimate_pic_address_disp_p (rtx disp)
{
  bool saw_plus;

  /* In 64bit mode we can allow direct addresses of symbols and labels
     when they are not dynamic symbols.  */
  if (TARGET_64BIT)
    {
      rtx op0 = disp, op1;

      switch (GET_CODE (disp))
	{
	case LABEL_REF:
	  return true;

	case CONST:
	  if (GET_CODE (XEXP (disp, 0)) != PLUS)
	    break;
	  op0 = XEXP (XEXP (disp, 0), 0);
	  op1 = XEXP (XEXP (disp, 0), 1);
	  if (!CONST_INT_P (op1))
	    break;
	  if (GET_CODE (op0) == UNSPEC
	      && (XINT (op0, 1) == UNSPEC_DTPOFF
		  || XINT (op0, 1) == UNSPEC_NTPOFF)
	      && trunc_int_for_mode (INTVAL (op1), SImode) == INTVAL (op1))
	    return true;
	  if (INTVAL (op1) >= 16*1024*1024
	      || INTVAL (op1) < -16*1024*1024)
	    break;
	  if (GET_CODE (op0) == LABEL_REF)
	    return true;
	  if (GET_CODE (op0) == CONST
	      && GET_CODE (XEXP (op0, 0)) == UNSPEC
	      && XINT (XEXP (op0, 0), 1) == UNSPEC_PCREL)
	    return true;
	  if (GET_CODE (op0) == UNSPEC
	      && XINT (op0, 1) == UNSPEC_PCREL)
	    return true;
	  if (GET_CODE (op0) != SYMBOL_REF)
	    break;
	  /* FALLTHRU */

	case SYMBOL_REF:
	  /* TLS references should always be enclosed in UNSPEC.
	     The dllimported symbol needs always to be resolved.  */
	  if (SYMBOL_REF_TLS_MODEL (op0)
	      || (TARGET_DLLIMPORT_DECL_ATTRIBUTES && SYMBOL_REF_DLLIMPORT_P (op0)))
	    return false;

	  if (TARGET_PECOFF)
	    {
	      if (is_imported_p (op0))
		return true;

	      if (SYMBOL_REF_FAR_ADDR_P (op0)
		  || !SYMBOL_REF_LOCAL_P (op0))
		break;

	      /* Function-symbols need to be resolved only for
	         large-model.
	         For the small-model we don't need to resolve anything
	         here.  */
	      if ((ix86_cmodel != CM_LARGE_PIC
	           && SYMBOL_REF_FUNCTION_P (op0))
		  || ix86_cmodel == CM_SMALL_PIC)
		return true;
	      /* Non-external symbols don't need to be resolved for
	         large, and medium-model.  */
	      if ((ix86_cmodel == CM_LARGE_PIC
		   || ix86_cmodel == CM_MEDIUM_PIC)
		  && !SYMBOL_REF_EXTERNAL_P (op0))
		return true;
	    }
	  else if (!SYMBOL_REF_FAR_ADDR_P (op0)
		   && (SYMBOL_REF_LOCAL_P (op0)
		       || (HAVE_LD_PIE_COPYRELOC
			   && flag_pie
			   && !SYMBOL_REF_WEAK (op0)
			   && !SYMBOL_REF_FUNCTION_P (op0)))
		   && ix86_cmodel != CM_LARGE_PIC)
	    return true;
	  break;

	default:
	  break;
	}
    }
  if (GET_CODE (disp) != CONST)
    return false;
  disp = XEXP (disp, 0);

  if (TARGET_64BIT)
    {
      /* We are unsafe to allow PLUS expressions.  This limit allowed distance
         of GOT tables.  We should not need these anyway.  */
      if (GET_CODE (disp) != UNSPEC
	  || (XINT (disp, 1) != UNSPEC_GOTPCREL
	      && XINT (disp, 1) != UNSPEC_GOTOFF
	      && XINT (disp, 1) != UNSPEC_PCREL
	      && XINT (disp, 1) != UNSPEC_PLTOFF))
	return false;

      if (GET_CODE (XVECEXP (disp, 0, 0)) != SYMBOL_REF
	  && GET_CODE (XVECEXP (disp, 0, 0)) != LABEL_REF)
	return false;
      return true;
    }

  saw_plus = false;
  if (GET_CODE (disp) == PLUS)
    {
      if (!CONST_INT_P (XEXP (disp, 1)))
	return false;
      disp = XEXP (disp, 0);
      saw_plus = true;
    }

  if (TARGET_MACHO && darwin_local_data_pic (disp))
    return true;

  if (GET_CODE (disp) != UNSPEC)
    return false;

  switch (XINT (disp, 1))
    {
    case UNSPEC_GOT:
      if (saw_plus)
	return false;
      /* We need to check for both symbols and labels because VxWorks loads
	 text labels with @GOT rather than @GOTOFF.  See gotoff_operand for
	 details.  */
      return (GET_CODE (XVECEXP (disp, 0, 0)) == SYMBOL_REF
	      || GET_CODE (XVECEXP (disp, 0, 0)) == LABEL_REF);
    case UNSPEC_GOTOFF:
      /* Refuse GOTOFF in 64bit mode since it is always 64bit when used.
	 While ABI specify also 32bit relocation but we don't produce it in
	 small PIC model at all.  */
      if ((GET_CODE (XVECEXP (disp, 0, 0)) == SYMBOL_REF
	   || GET_CODE (XVECEXP (disp, 0, 0)) == LABEL_REF)
	  && !TARGET_64BIT)
        return !TARGET_PECOFF && gotoff_operand (XVECEXP (disp, 0, 0), Pmode);
      return false;
    case UNSPEC_GOTTPOFF:
    case UNSPEC_GOTNTPOFF:
    case UNSPEC_INDNTPOFF:
      if (saw_plus)
	return false;
      disp = XVECEXP (disp, 0, 0);
      return (GET_CODE (disp) == SYMBOL_REF
	      && SYMBOL_REF_TLS_MODEL (disp) == TLS_MODEL_INITIAL_EXEC);
    case UNSPEC_NTPOFF:
      disp = XVECEXP (disp, 0, 0);
      return (GET_CODE (disp) == SYMBOL_REF
	      && SYMBOL_REF_TLS_MODEL (disp) == TLS_MODEL_LOCAL_EXEC);
    case UNSPEC_DTPOFF:
      disp = XVECEXP (disp, 0, 0);
      return (GET_CODE (disp) == SYMBOL_REF
	      && SYMBOL_REF_TLS_MODEL (disp) == TLS_MODEL_LOCAL_DYNAMIC);
    }

  return false;
}

/* Determine if op is suitable RTX for an address register.
   Return naked register if a register or a register subreg is
   found, otherwise return NULL_RTX.  */

static rtx
ix86_validate_address_register (rtx op)
{
  machine_mode mode = GET_MODE (op);

  /* Only SImode or DImode registers can form the address.  */
  if (mode != SImode && mode != DImode)
    return NULL_RTX;

  if (REG_P (op))
    return op;
  else if (SUBREG_P (op))
    {
      rtx reg = SUBREG_REG (op);

      if (!REG_P (reg))
	return NULL_RTX;

      mode = GET_MODE (reg);

      /* Don't allow SUBREGs that span more than a word.  It can
	 lead to spill failures when the register is one word out
	 of a two word structure.  */
      if (GET_MODE_SIZE (mode) > UNITS_PER_WORD)
	return NULL_RTX;

      /* Allow only SUBREGs of non-eliminable hard registers.  */
      if (register_no_elim_operand (reg, mode))
	return reg;
    }

  /* Op is not a register.  */
  return NULL_RTX;
}

/* Recognizes RTL expressions that are valid memory addresses for an
   instruction.  The MODE argument is the machine mode for the MEM
   expression that wants to use this address.

   It only recognizes address in canonical form.  LEGITIMIZE_ADDRESS should
   convert common non-canonical forms to canonical form so that they will
   be recognized.  */

static bool
ix86_legitimate_address_p (machine_mode, rtx addr, bool strict)
{
  struct ix86_address parts;
  rtx base, index, disp;
  HOST_WIDE_INT scale;
  addr_space_t seg;

  if (ix86_decompose_address (addr, &parts) <= 0)
    /* Decomposition failed.  */
    return false;

  base = parts.base;
  index = parts.index;
  disp = parts.disp;
  scale = parts.scale;
  seg = parts.seg;

  /* Validate base register.  */
  if (base)
    {
      rtx reg = ix86_validate_address_register (base);

      if (reg == NULL_RTX)
	return false;

      if ((strict && ! REG_OK_FOR_BASE_STRICT_P (reg))
	  || (! strict && ! REG_OK_FOR_BASE_NONSTRICT_P (reg)))
	/* Base is not valid.  */
	return false;
    }

  /* Validate index register.  */
  if (index)
    {
      rtx reg = ix86_validate_address_register (index);

      if (reg == NULL_RTX)
	return false;

      if ((strict && ! REG_OK_FOR_INDEX_STRICT_P (reg))
	  || (! strict && ! REG_OK_FOR_INDEX_NONSTRICT_P (reg)))
	/* Index is not valid.  */
	return false;
    }

  /* Index and base should have the same mode.  */
  if (base && index
      && GET_MODE (base) != GET_MODE (index))
    return false;

  /* Address override works only on the (%reg) part of %fs:(%reg).  */
  if (seg != ADDR_SPACE_GENERIC
      && ((base && GET_MODE (base) != word_mode)
	  || (index && GET_MODE (index) != word_mode)))
    return false;

  /* Validate scale factor.  */
  if (scale != 1)
    {
      if (!index)
	/* Scale without index.  */
	return false;

      if (scale != 2 && scale != 4 && scale != 8)
	/* Scale is not a valid multiplier.  */
	return false;
    }

  /* Validate displacement.  */
  if (disp)
    {
      if (GET_CODE (disp) == CONST
	  && GET_CODE (XEXP (disp, 0)) == UNSPEC
	  && XINT (XEXP (disp, 0), 1) != UNSPEC_MACHOPIC_OFFSET)
	switch (XINT (XEXP (disp, 0), 1))
	  {
	  /* Refuse GOTOFF and GOT in 64bit mode since it is always 64bit
	     when used.  While ABI specify also 32bit relocations, we
	     don't produce them at all and use IP relative instead.
	     Allow GOT in 32bit mode for both PIC and non-PIC if symbol
	     should be loaded via GOT.  */
	  case UNSPEC_GOT:
	    if (!TARGET_64BIT
		&& ix86_force_load_from_GOT_p (XVECEXP (XEXP (disp, 0), 0, 0)))
	      goto is_legitimate_pic;
	    /* FALLTHRU */
	  case UNSPEC_GOTOFF:
	    gcc_assert (flag_pic);
	    if (!TARGET_64BIT)
	      goto is_legitimate_pic;

	    /* 64bit address unspec.  */
	    return false;

	  case UNSPEC_GOTPCREL:
	    if (ix86_force_load_from_GOT_p (XVECEXP (XEXP (disp, 0), 0, 0)))
	      goto is_legitimate_pic;
	    /* FALLTHRU */
	  case UNSPEC_PCREL:
	    gcc_assert (flag_pic);
	    goto is_legitimate_pic;

	  case UNSPEC_GOTTPOFF:
	  case UNSPEC_GOTNTPOFF:
	  case UNSPEC_INDNTPOFF:
	  case UNSPEC_NTPOFF:
	  case UNSPEC_DTPOFF:
	    break;

	  default:
	    /* Invalid address unspec.  */
	    return false;
	  }

      else if (SYMBOLIC_CONST (disp)
	       && (flag_pic
		   || (TARGET_MACHO
#if TARGET_MACHO
		       && MACHOPIC_INDIRECT
		       && !machopic_operand_p (disp)
#endif
	       )))
	{

	is_legitimate_pic:
	  if (TARGET_64BIT && (index || base))
	    {
	      /* foo@dtpoff(%rX) is ok.  */
	      if (GET_CODE (disp) != CONST
		  || GET_CODE (XEXP (disp, 0)) != PLUS
		  || GET_CODE (XEXP (XEXP (disp, 0), 0)) != UNSPEC
		  || !CONST_INT_P (XEXP (XEXP (disp, 0), 1))
		  || (XINT (XEXP (XEXP (disp, 0), 0), 1) != UNSPEC_DTPOFF
		      && XINT (XEXP (XEXP (disp, 0), 0), 1) != UNSPEC_NTPOFF))
		/* Non-constant pic memory reference.  */
		return false;
	    }
	  else if ((!TARGET_MACHO || flag_pic)
		    && ! legitimate_pic_address_disp_p (disp))
	    /* Displacement is an invalid pic construct.  */
	    return false;
#if TARGET_MACHO
	  else if (MACHO_DYNAMIC_NO_PIC_P
		   && !ix86_legitimate_constant_p (Pmode, disp))
	    /* displacment must be referenced via non_lazy_pointer */
	    return false;
#endif

          /* This code used to verify that a symbolic pic displacement
	     includes the pic_offset_table_rtx register.

	     While this is good idea, unfortunately these constructs may
	     be created by "adds using lea" optimization for incorrect
	     code like:

	     int a;
	     int foo(int i)
	       {
	         return *(&a+i);
	       }

	     This code is nonsensical, but results in addressing
	     GOT table with pic_offset_table_rtx base.  We can't
	     just refuse it easily, since it gets matched by
	     "addsi3" pattern, that later gets split to lea in the
	     case output register differs from input.  While this
	     can be handled by separate addsi pattern for this case
	     that never results in lea, this seems to be easier and
	     correct fix for crash to disable this test.  */
	}
      else if (GET_CODE (disp) != LABEL_REF
	       && !CONST_INT_P (disp)
	       && (GET_CODE (disp) != CONST
		   || !ix86_legitimate_constant_p (Pmode, disp))
	       && (GET_CODE (disp) != SYMBOL_REF
		   || !ix86_legitimate_constant_p (Pmode, disp)))
	/* Displacement is not constant.  */
	return false;
      else if (TARGET_64BIT
	       && !x86_64_immediate_operand (disp, VOIDmode))
	/* Displacement is out of range.  */
	return false;
      /* In x32 mode, constant addresses are sign extended to 64bit, so
	 we have to prevent addresses from 0x80000000 to 0xffffffff.  */
      else if (TARGET_X32 && !(index || base)
	       && CONST_INT_P (disp)
	       && val_signbit_known_set_p (SImode, INTVAL (disp)))
	return false;
    }

  /* Everything looks valid.  */
  return true;
}

/* Determine if a given RTX is a valid constant address.  */

bool
constant_address_p (rtx x)
{
  return CONSTANT_P (x) && ix86_legitimate_address_p (Pmode, x, 1);
}

/* Return a unique alias set for the GOT.  */

static alias_set_type
ix86_GOT_alias_set (void)
{
  static alias_set_type set = -1;
  if (set == -1)
    set = new_alias_set ();
  return set;
}

/* Return a legitimate reference for ORIG (an address) using the
   register REG.  If REG is 0, a new pseudo is generated.

   There are two types of references that must be handled:

   1. Global data references must load the address from the GOT, via
      the PIC reg.  An insn is emitted to do this load, and the reg is
      returned.

   2. Static data references, constant pool addresses, and code labels
      compute the address as an offset from the GOT, whose base is in
      the PIC reg.  Static data objects have SYMBOL_FLAG_LOCAL set to
      differentiate them from global data objects.  The returned
      address is the PIC reg + an unspec constant.

   TARGET_LEGITIMATE_ADDRESS_P rejects symbolic references unless the PIC
   reg also appears in the address.  */

static rtx
legitimize_pic_address (rtx orig, rtx reg)
{
  rtx addr = orig;
  rtx new_rtx = orig;

#if TARGET_MACHO
  if (TARGET_MACHO && !TARGET_64BIT)
    {
      if (reg == 0)
	reg = gen_reg_rtx (Pmode);
      /* Use the generic Mach-O PIC machinery.  */
      return machopic_legitimize_pic_address (orig, GET_MODE (orig), reg);
    }
#endif

  if (TARGET_64BIT && TARGET_DLLIMPORT_DECL_ATTRIBUTES)
    {
      rtx tmp = legitimize_pe_coff_symbol (addr, true);
      if (tmp)
        return tmp;
    }

  if (TARGET_64BIT && legitimate_pic_address_disp_p (addr))
    new_rtx = addr;
  else if ((!TARGET_64BIT
	    || /* TARGET_64BIT && */ ix86_cmodel != CM_SMALL_PIC)
	   && !TARGET_PECOFF
	   && gotoff_operand (addr, Pmode))
    {
      /* This symbol may be referenced via a displacement
	 from the PIC base address (@GOTOFF).  */
      if (GET_CODE (addr) == CONST)
	addr = XEXP (addr, 0);

      if (GET_CODE (addr) == PLUS)
	  {
            new_rtx = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, XEXP (addr, 0)),
				      UNSPEC_GOTOFF);
	    new_rtx = gen_rtx_PLUS (Pmode, new_rtx, XEXP (addr, 1));
	  }
	else
          new_rtx = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOTOFF);

      new_rtx = gen_rtx_CONST (Pmode, new_rtx);

      if (TARGET_64BIT)
	new_rtx = copy_to_suggested_reg (new_rtx, reg, Pmode);

      if (reg != 0)
	{
 	  gcc_assert (REG_P (reg));
	  new_rtx = expand_simple_binop (Pmode, PLUS, pic_offset_table_rtx,
					 new_rtx, reg, 1, OPTAB_DIRECT);
 	}
      else
	new_rtx = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new_rtx);
    }
  else if ((GET_CODE (addr) == SYMBOL_REF && SYMBOL_REF_TLS_MODEL (addr) == 0)
	   /* We can't use @GOTOFF for text labels
	      on VxWorks, see gotoff_operand.  */
	   || (TARGET_VXWORKS_RTP && GET_CODE (addr) == LABEL_REF))
    {
      rtx tmp = legitimize_pe_coff_symbol (addr, true);
      if (tmp)
        return tmp;

      /* For x64 PE-COFF there is no GOT table,
	 so we use address directly.  */
      if (TARGET_64BIT && TARGET_PECOFF)
	{
	  new_rtx = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_PCREL);
	  new_rtx = gen_rtx_CONST (Pmode, new_rtx);
	}
      else if (TARGET_64BIT && ix86_cmodel != CM_LARGE_PIC)
	{
	  new_rtx = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr),
				    UNSPEC_GOTPCREL);
	  new_rtx = gen_rtx_CONST (Pmode, new_rtx);
	  new_rtx = gen_const_mem (Pmode, new_rtx);
	  set_mem_alias_set (new_rtx, ix86_GOT_alias_set ());
	}
      else
	{
	  /* This symbol must be referenced via a load
	     from the Global Offset Table (@GOT).  */
	  new_rtx = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr), UNSPEC_GOT);
	  new_rtx = gen_rtx_CONST (Pmode, new_rtx);
	  if (TARGET_64BIT)
	    new_rtx = force_reg (Pmode, new_rtx);
	  new_rtx = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new_rtx);
	  new_rtx = gen_const_mem (Pmode, new_rtx);
	  set_mem_alias_set (new_rtx, ix86_GOT_alias_set ());
	}

      new_rtx = copy_to_suggested_reg (new_rtx, reg, Pmode);
    }
  else
    {
      if (CONST_INT_P (addr)
	  && !x86_64_immediate_operand (addr, VOIDmode))
	new_rtx = copy_to_suggested_reg (addr, reg, Pmode);
      else if (GET_CODE (addr) == CONST)
	{
	  addr = XEXP (addr, 0);

	  /* We must match stuff we generate before.  Assume the only
	     unspecs that can get here are ours.  Not that we could do
	     anything with them anyway....  */
	  if (GET_CODE (addr) == UNSPEC
	      || (GET_CODE (addr) == PLUS
		  && GET_CODE (XEXP (addr, 0)) == UNSPEC))
	    return orig;
	  gcc_assert (GET_CODE (addr) == PLUS);
	}

      if (GET_CODE (addr) == PLUS)
	{
	  rtx op0 = XEXP (addr, 0), op1 = XEXP (addr, 1);

	  /* Check first to see if this is a constant
	     offset from a @GOTOFF symbol reference.  */
	  if (!TARGET_PECOFF
	      && gotoff_operand (op0, Pmode)
	      && CONST_INT_P (op1))
	    {
	      if (!TARGET_64BIT)
		{
		  new_rtx = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op0),
					    UNSPEC_GOTOFF);
		  new_rtx = gen_rtx_PLUS (Pmode, new_rtx, op1);
		  new_rtx = gen_rtx_CONST (Pmode, new_rtx);

		  if (reg != 0)
		    {
		      gcc_assert (REG_P (reg));
		      new_rtx = expand_simple_binop (Pmode, PLUS,
						     pic_offset_table_rtx,
						     new_rtx, reg, 1,
						     OPTAB_DIRECT);
		    }
		  else
		    new_rtx
		      = gen_rtx_PLUS (Pmode, pic_offset_table_rtx, new_rtx);
		}
	      else
		{
		  if (INTVAL (op1) < -16*1024*1024
		      || INTVAL (op1) >= 16*1024*1024)
		    {
		      if (!x86_64_immediate_operand (op1, Pmode))
			op1 = force_reg (Pmode, op1);

		      new_rtx
			= gen_rtx_PLUS (Pmode, force_reg (Pmode, op0), op1);
		    }
		}
	    }
	  else
	    {
	      rtx base = legitimize_pic_address (op0, reg);
	      machine_mode mode = GET_MODE (base);
	      new_rtx
	        = legitimize_pic_address (op1, base == reg ? NULL_RTX : reg);

	      if (CONST_INT_P (new_rtx))
		{
		  if (INTVAL (new_rtx) < -16*1024*1024
		      || INTVAL (new_rtx) >= 16*1024*1024)
		    {
		      if (!x86_64_immediate_operand (new_rtx, mode))
			new_rtx = force_reg (mode, new_rtx);

		      new_rtx
		        = gen_rtx_PLUS (mode, force_reg (mode, base), new_rtx);
		    }
		  else
		    new_rtx = plus_constant (mode, base, INTVAL (new_rtx));
		}
	      else
		{
		  /* For %rip addressing, we have to use
		     just disp32, not base nor index.  */
		  if (TARGET_64BIT
		      && (GET_CODE (base) == SYMBOL_REF
			  || GET_CODE (base) == LABEL_REF))
		    base = force_reg (mode, base);
		  if (GET_CODE (new_rtx) == PLUS
		      && CONSTANT_P (XEXP (new_rtx, 1)))
		    {
		      base = gen_rtx_PLUS (mode, base, XEXP (new_rtx, 0));
		      new_rtx = XEXP (new_rtx, 1);
		    }
		  new_rtx = gen_rtx_PLUS (mode, base, new_rtx);
		}
	    }
	}
    }
  return new_rtx;
}

/* Load the thread pointer.  If TO_REG is true, force it into a register.  */

static rtx
get_thread_pointer (machine_mode tp_mode, bool to_reg)
{
  rtx tp = gen_rtx_UNSPEC (ptr_mode, gen_rtvec (1, const0_rtx), UNSPEC_TP);

  if (GET_MODE (tp) != tp_mode)
    {
      gcc_assert (GET_MODE (tp) == SImode);
      gcc_assert (tp_mode == DImode);

      tp = gen_rtx_ZERO_EXTEND (tp_mode, tp);
    }

  if (to_reg)
    tp = copy_to_mode_reg (tp_mode, tp);

  return tp;
}

/* Construct the SYMBOL_REF for the tls_get_addr function.  */

static GTY(()) rtx ix86_tls_symbol;

static rtx
ix86_tls_get_addr (void)
{
  if (!ix86_tls_symbol)
    {
      const char *sym
	= ((TARGET_ANY_GNU_TLS && !TARGET_64BIT)
	   ? "___tls_get_addr" : "__tls_get_addr");

      ix86_tls_symbol = gen_rtx_SYMBOL_REF (Pmode, sym);
    }

  if (ix86_cmodel == CM_LARGE_PIC && !TARGET_PECOFF)
    {
      rtx unspec = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, ix86_tls_symbol),
				   UNSPEC_PLTOFF);
      return gen_rtx_PLUS (Pmode, pic_offset_table_rtx,
			   gen_rtx_CONST (Pmode, unspec));
    }

  return ix86_tls_symbol;
}

/* Construct the SYMBOL_REF for the _TLS_MODULE_BASE_ symbol.  */

static GTY(()) rtx ix86_tls_module_base_symbol;

rtx
ix86_tls_module_base (void)
{
  if (!ix86_tls_module_base_symbol)
    {
      ix86_tls_module_base_symbol
	= gen_rtx_SYMBOL_REF (Pmode, "_TLS_MODULE_BASE_");

      SYMBOL_REF_FLAGS (ix86_tls_module_base_symbol)
	|= TLS_MODEL_GLOBAL_DYNAMIC << SYMBOL_FLAG_TLS_SHIFT;
    }

  return ix86_tls_module_base_symbol;
}

/* A subroutine of ix86_legitimize_address and ix86_expand_move.  FOR_MOV is
   false if we expect this to be used for a memory address and true if
   we expect to load the address into a register.  */

static rtx
legitimize_tls_address (rtx x, enum tls_model model, bool for_mov)
{
  rtx dest, base, off;
  rtx pic = NULL_RTX, tp = NULL_RTX;
  machine_mode tp_mode = Pmode;
  int type;

  /* Fall back to global dynamic model if tool chain cannot support local
     dynamic.  */
  if (TARGET_SUN_TLS && !TARGET_64BIT
      && !HAVE_AS_IX86_TLSLDMPLT && !HAVE_AS_IX86_TLSLDM
      && model == TLS_MODEL_LOCAL_DYNAMIC)
    model = TLS_MODEL_GLOBAL_DYNAMIC;

  switch (model)
    {
    case TLS_MODEL_GLOBAL_DYNAMIC:
      dest = gen_reg_rtx (Pmode);

      if (!TARGET_64BIT)
	{
	  if (flag_pic && !TARGET_PECOFF)
	    pic = pic_offset_table_rtx;
	  else
	    {
	      pic = gen_reg_rtx (Pmode);
	      emit_insn (gen_set_got (pic));
	    }
	}

      if (TARGET_GNU2_TLS)
	{
	  if (TARGET_64BIT)
	    emit_insn (gen_tls_dynamic_gnu2_64 (dest, x));
	  else
	    emit_insn (gen_tls_dynamic_gnu2_32 (dest, x, pic));

	  tp = get_thread_pointer (Pmode, true);
	  dest = force_reg (Pmode, gen_rtx_PLUS (Pmode, tp, dest));

	  if (GET_MODE (x) != Pmode)
	    x = gen_rtx_ZERO_EXTEND (Pmode, x);

	  set_unique_reg_note (get_last_insn (), REG_EQUAL, x);
	}
      else
	{
	  rtx caddr = ix86_tls_get_addr ();

	  if (TARGET_64BIT)
	    {
	      rtx rax = gen_rtx_REG (Pmode, AX_REG);
	      rtx_insn *insns;

	      start_sequence ();
	      emit_call_insn
		(ix86_gen_tls_global_dynamic_64 (rax, x, caddr));
	      insns = get_insns ();
	      end_sequence ();

	      if (GET_MODE (x) != Pmode)
		x = gen_rtx_ZERO_EXTEND (Pmode, x);

	      RTL_CONST_CALL_P (insns) = 1;
	      emit_libcall_block (insns, dest, rax, x);
	    }
	  else
	    emit_insn (gen_tls_global_dynamic_32 (dest, x, pic, caddr));
	}
      break;

    case TLS_MODEL_LOCAL_DYNAMIC:
      base = gen_reg_rtx (Pmode);

      if (!TARGET_64BIT)
	{
	  if (flag_pic)
	    pic = pic_offset_table_rtx;
	  else
	    {
	      pic = gen_reg_rtx (Pmode);
	      emit_insn (gen_set_got (pic));
	    }
	}

      if (TARGET_GNU2_TLS)
	{
	  rtx tmp = ix86_tls_module_base ();

	  if (TARGET_64BIT)
	    emit_insn (gen_tls_dynamic_gnu2_64 (base, tmp));
	  else
	    emit_insn (gen_tls_dynamic_gnu2_32 (base, tmp, pic));

	  tp = get_thread_pointer (Pmode, true);
	  set_unique_reg_note (get_last_insn (), REG_EQUAL,
			       gen_rtx_MINUS (Pmode, tmp, tp));
	}
      else
	{
	  rtx caddr = ix86_tls_get_addr ();

	  if (TARGET_64BIT)
	    {
	      rtx rax = gen_rtx_REG (Pmode, AX_REG);
	      rtx_insn *insns;
	      rtx eqv;

	      start_sequence ();
	      emit_call_insn
		(ix86_gen_tls_local_dynamic_base_64 (rax, caddr));
	      insns = get_insns ();
	      end_sequence ();

	      /* Attach a unique REG_EQUAL, to allow the RTL optimizers to
		 share the LD_BASE result with other LD model accesses.  */
	      eqv = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, const0_rtx),
				    UNSPEC_TLS_LD_BASE);

	      RTL_CONST_CALL_P (insns) = 1;
	      emit_libcall_block (insns, base, rax, eqv);
	    }
	  else
	    emit_insn (gen_tls_local_dynamic_base_32 (base, pic, caddr));
	}

      off = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, x), UNSPEC_DTPOFF);
      off = gen_rtx_CONST (Pmode, off);

      dest = force_reg (Pmode, gen_rtx_PLUS (Pmode, base, off));

      if (TARGET_GNU2_TLS)
	{
	  dest = force_reg (Pmode, gen_rtx_PLUS (Pmode, dest, tp));

	  if (GET_MODE (x) != Pmode)
	    x = gen_rtx_ZERO_EXTEND (Pmode, x);

	  set_unique_reg_note (get_last_insn (), REG_EQUAL, x);
	}
      break;

    case TLS_MODEL_INITIAL_EXEC:
      if (TARGET_64BIT)
	{
	  if (TARGET_SUN_TLS && !TARGET_X32)
	    {
	      /* The Sun linker took the AMD64 TLS spec literally
		 and can only handle %rax as destination of the
		 initial executable code sequence.  */

	      dest = gen_reg_rtx (DImode);
	      emit_insn (gen_tls_initial_exec_64_sun (dest, x));
	      return dest;
	    }

	  /* Generate DImode references to avoid %fs:(%reg32)
	     problems and linker IE->LE relaxation bug.  */
	  tp_mode = DImode;
	  pic = NULL;
	  type = UNSPEC_GOTNTPOFF;
	}
      else if (flag_pic)
	{
	  pic = pic_offset_table_rtx;
	  type = TARGET_ANY_GNU_TLS ? UNSPEC_GOTNTPOFF : UNSPEC_GOTTPOFF;
	}
      else if (!TARGET_ANY_GNU_TLS)
	{
	  pic = gen_reg_rtx (Pmode);
	  emit_insn (gen_set_got (pic));
	  type = UNSPEC_GOTTPOFF;
	}
      else
	{
	  pic = NULL;
	  type = UNSPEC_INDNTPOFF;
	}

      off = gen_rtx_UNSPEC (tp_mode, gen_rtvec (1, x), type);
      off = gen_rtx_CONST (tp_mode, off);
      if (pic)
	off = gen_rtx_PLUS (tp_mode, pic, off);
      off = gen_const_mem (tp_mode, off);
      set_mem_alias_set (off, ix86_GOT_alias_set ());

      if (TARGET_64BIT || TARGET_ANY_GNU_TLS)
	{
	  base = get_thread_pointer (tp_mode,
				     for_mov || !TARGET_TLS_DIRECT_SEG_REFS);
	  off = force_reg (tp_mode, off);
	  dest = gen_rtx_PLUS (tp_mode, base, off);
	  if (tp_mode != Pmode)
	    dest = convert_to_mode (Pmode, dest, 1);
	}
      else
	{
	  base = get_thread_pointer (Pmode, true);
	  dest = gen_reg_rtx (Pmode);
	  emit_insn (ix86_gen_sub3 (dest, base, off));
	}
      break;

    case TLS_MODEL_LOCAL_EXEC:
      off = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, x),
			    (TARGET_64BIT || TARGET_ANY_GNU_TLS)
			    ? UNSPEC_NTPOFF : UNSPEC_TPOFF);
      off = gen_rtx_CONST (Pmode, off);

      if (TARGET_64BIT || TARGET_ANY_GNU_TLS)
	{
	  base = get_thread_pointer (Pmode,
				     for_mov || !TARGET_TLS_DIRECT_SEG_REFS);
	  return gen_rtx_PLUS (Pmode, base, off);
	}
      else
	{
	  base = get_thread_pointer (Pmode, true);
	  dest = gen_reg_rtx (Pmode);
	  emit_insn (ix86_gen_sub3 (dest, base, off));
	}
      break;

    default:
      gcc_unreachable ();
    }

  return dest;
}

/* Return true if OP refers to a TLS address.  */
bool
ix86_tls_address_pattern_p (rtx op)
{
  subrtx_var_iterator::array_type array;
  FOR_EACH_SUBRTX_VAR (iter, array, op, ALL)
    {
      rtx op = *iter;
      if (MEM_P (op))
	{
	  rtx *x = &XEXP (op, 0);
	  while (GET_CODE (*x) == PLUS)
	    {
	      int i;
	      for (i = 0; i < 2; i++)
		{
		  rtx u = XEXP (*x, i);
		  if (GET_CODE (u) == ZERO_EXTEND)
		    u = XEXP (u, 0);
		  if (GET_CODE (u) == UNSPEC
		      && XINT (u, 1) == UNSPEC_TP)
		    return true;
		}
	      x = &XEXP (*x, 0);
	    }

	  iter.skip_subrtxes ();
	}
    }

  return false;
}

/* Rewrite *LOC so that it refers to a default TLS address space.  */
void
ix86_rewrite_tls_address_1 (rtx *loc)
{
  subrtx_ptr_iterator::array_type array;
  FOR_EACH_SUBRTX_PTR (iter, array, loc, ALL)
    {
      rtx *loc = *iter;
      if (MEM_P (*loc))
	{
	  rtx addr = XEXP (*loc, 0);
	  rtx *x = &addr;
	  while (GET_CODE (*x) == PLUS)
	    {
	      int i;
	      for (i = 0; i < 2; i++)
		{
		  rtx u = XEXP (*x, i);
		  if (GET_CODE (u) == ZERO_EXTEND)
		    u = XEXP (u, 0);
		  if (GET_CODE (u) == UNSPEC
		      && XINT (u, 1) == UNSPEC_TP)
		    {
		      addr_space_t as = DEFAULT_TLS_SEG_REG;

		      *x = XEXP (*x, 1 - i);

		      *loc = replace_equiv_address_nv (*loc, addr, true);
		      set_mem_addr_space (*loc, as);
		      return;
		    }
		}
	      x = &XEXP (*x, 0);
	    }

	  iter.skip_subrtxes ();
	}
    }
}

/* Rewrite instruction pattern involvning TLS address
   so that it refers to a default TLS address space.  */
rtx
ix86_rewrite_tls_address (rtx pattern)
{
  pattern = copy_insn (pattern);
  ix86_rewrite_tls_address_1 (&pattern);
  return pattern;
}

/* Create or return the unique __imp_DECL dllimport symbol corresponding
   to symbol DECL if BEIMPORT is true.  Otherwise create or return the
   unique refptr-DECL symbol corresponding to symbol DECL.  */

struct dllimport_hasher : ggc_cache_ptr_hash<tree_map>
{
  static inline hashval_t hash (tree_map *m) { return m->hash; }
  static inline bool
  equal (tree_map *a, tree_map *b)
  {
    return a->base.from == b->base.from;
  }

  static int
  keep_cache_entry (tree_map *&m)
  {
    return ggc_marked_p (m->base.from);
  }
};

static GTY((cache)) hash_table<dllimport_hasher> *dllimport_map;

static tree
get_dllimport_decl (tree decl, bool beimport)
{
  struct tree_map *h, in;
  const char *name;
  const char *prefix;
  size_t namelen, prefixlen;
  char *imp_name;
  tree to;
  rtx rtl;

  if (!dllimport_map)
    dllimport_map = hash_table<dllimport_hasher>::create_ggc (512);

  in.hash = htab_hash_pointer (decl);
  in.base.from = decl;
  tree_map **loc = dllimport_map->find_slot_with_hash (&in, in.hash, INSERT);
  h = *loc;
  if (h)
    return h->to;

  *loc = h = ggc_alloc<tree_map> ();
  h->hash = in.hash;
  h->base.from = decl;
  h->to = to = build_decl (DECL_SOURCE_LOCATION (decl),
			   VAR_DECL, NULL, ptr_type_node);
  DECL_ARTIFICIAL (to) = 1;
  DECL_IGNORED_P (to) = 1;
  DECL_EXTERNAL (to) = 1;
  TREE_READONLY (to) = 1;

  name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
  name = targetm.strip_name_encoding (name);
  if (beimport)
    prefix = name[0] == FASTCALL_PREFIX || user_label_prefix[0] == 0
      ? "*__imp_" : "*__imp__";
  else
    prefix = user_label_prefix[0] == 0 ? "*.refptr." : "*refptr.";
  namelen = strlen (name);
  prefixlen = strlen (prefix);
  imp_name = (char *) alloca (namelen + prefixlen + 1);
  memcpy (imp_name, prefix, prefixlen);
  memcpy (imp_name + prefixlen, name, namelen + 1);

  name = ggc_alloc_string (imp_name, namelen + prefixlen);
  rtl = gen_rtx_SYMBOL_REF (Pmode, name);
  SET_SYMBOL_REF_DECL (rtl, to);
  SYMBOL_REF_FLAGS (rtl) = SYMBOL_FLAG_LOCAL | SYMBOL_FLAG_STUBVAR;
  if (!beimport)
    {
      SYMBOL_REF_FLAGS (rtl) |= SYMBOL_FLAG_EXTERNAL;
#ifdef SUB_TARGET_RECORD_STUB
      SUB_TARGET_RECORD_STUB (name);
#endif
    }      

  rtl = gen_const_mem (Pmode, rtl);
  set_mem_alias_set (rtl, ix86_GOT_alias_set ());

  SET_DECL_RTL (to, rtl);
  SET_DECL_ASSEMBLER_NAME (to, get_identifier (name));

  return to;
}

/* Expand SYMBOL into its corresponding far-address symbol.
   WANT_REG is true if we require the result be a register.  */

static rtx
legitimize_pe_coff_extern_decl (rtx symbol, bool want_reg)
{
  tree imp_decl;
  rtx x;

  gcc_assert (SYMBOL_REF_DECL (symbol));
  imp_decl = get_dllimport_decl (SYMBOL_REF_DECL (symbol), false);

  x = DECL_RTL (imp_decl);
  if (want_reg)
    x = force_reg (Pmode, x);
  return x;
}

/* Expand SYMBOL into its corresponding dllimport symbol.  WANT_REG is
   true if we require the result be a register.  */

static rtx
legitimize_dllimport_symbol (rtx symbol, bool want_reg)
{
  tree imp_decl;
  rtx x;

  gcc_assert (SYMBOL_REF_DECL (symbol));
  imp_decl = get_dllimport_decl (SYMBOL_REF_DECL (symbol), true);

  x = DECL_RTL (imp_decl);
  if (want_reg)
    x = force_reg (Pmode, x);
  return x;
}

/* Expand SYMBOL into its corresponding dllimport or refptr symbol.  WANT_REG 
   is true if we require the result be a register.  */

static rtx
legitimize_pe_coff_symbol (rtx addr, bool inreg)
{
  if (!TARGET_PECOFF)
    return NULL_RTX;

  if (TARGET_DLLIMPORT_DECL_ATTRIBUTES)
    {
      if (GET_CODE (addr) == SYMBOL_REF && SYMBOL_REF_DLLIMPORT_P (addr))
	return legitimize_dllimport_symbol (addr, inreg);
      if (GET_CODE (addr) == CONST
	  && GET_CODE (XEXP (addr, 0)) == PLUS
	  && GET_CODE (XEXP (XEXP (addr, 0), 0)) == SYMBOL_REF
	  && SYMBOL_REF_DLLIMPORT_P (XEXP (XEXP (addr, 0), 0)))
	{
	  rtx t = legitimize_dllimport_symbol (XEXP (XEXP (addr, 0), 0), inreg);
	  return gen_rtx_PLUS (Pmode, t, XEXP (XEXP (addr, 0), 1));
	}
    }

  if (ix86_cmodel != CM_LARGE_PIC && ix86_cmodel != CM_MEDIUM_PIC)
    return NULL_RTX;
  if (GET_CODE (addr) == SYMBOL_REF
      && !is_imported_p (addr)
      && SYMBOL_REF_EXTERNAL_P (addr)
      && SYMBOL_REF_DECL (addr))
    return legitimize_pe_coff_extern_decl (addr, inreg);

  if (GET_CODE (addr) == CONST
      && GET_CODE (XEXP (addr, 0)) == PLUS
      && GET_CODE (XEXP (XEXP (addr, 0), 0)) == SYMBOL_REF
      && !is_imported_p (XEXP (XEXP (addr, 0), 0))
      && SYMBOL_REF_EXTERNAL_P (XEXP (XEXP (addr, 0), 0))
      && SYMBOL_REF_DECL (XEXP (XEXP (addr, 0), 0)))
    {
      rtx t = legitimize_pe_coff_extern_decl (XEXP (XEXP (addr, 0), 0), inreg);
      return gen_rtx_PLUS (Pmode, t, XEXP (XEXP (addr, 0), 1));
    }
  return NULL_RTX;
}

/* Try machine-dependent ways of modifying an illegitimate address
   to be legitimate.  If we find one, return the new, valid address.
   This macro is used in only one place: `memory_address' in explow.c.

   OLDX is the address as it was before break_out_memory_refs was called.
   In some cases it is useful to look at this to decide what needs to be done.

   It is always safe for this macro to do nothing.  It exists to recognize
   opportunities to optimize the output.

   For the 80386, we handle X+REG by loading X into a register R and
   using R+REG.  R will go in a general reg and indexing will be used.
   However, if REG is a broken-out memory address or multiplication,
   nothing needs to be done because REG can certainly go in a general reg.

   When -fpic is used, special handling is needed for symbolic references.
   See comments by legitimize_pic_address in i386.c for details.  */

static rtx
ix86_legitimize_address (rtx x, rtx, machine_mode mode)
{
  bool changed = false;
  unsigned log;

  log = GET_CODE (x) == SYMBOL_REF ? SYMBOL_REF_TLS_MODEL (x) : 0;
  if (log)
    return legitimize_tls_address (x, (enum tls_model) log, false);
  if (GET_CODE (x) == CONST
      && GET_CODE (XEXP (x, 0)) == PLUS
      && GET_CODE (XEXP (XEXP (x, 0), 0)) == SYMBOL_REF
      && (log = SYMBOL_REF_TLS_MODEL (XEXP (XEXP (x, 0), 0))))
    {
      rtx t = legitimize_tls_address (XEXP (XEXP (x, 0), 0),
				      (enum tls_model) log, false);
      return gen_rtx_PLUS (Pmode, t, XEXP (XEXP (x, 0), 1));
    }

  if (TARGET_DLLIMPORT_DECL_ATTRIBUTES)
    {
      rtx tmp = legitimize_pe_coff_symbol (x, true);
      if (tmp)
        return tmp;
    }

  if (flag_pic && SYMBOLIC_CONST (x))
    return legitimize_pic_address (x, 0);

#if TARGET_MACHO
  if (MACHO_DYNAMIC_NO_PIC_P && SYMBOLIC_CONST (x))
    return machopic_indirect_data_reference (x, 0);
#endif

  /* Canonicalize shifts by 0, 1, 2, 3 into multiply */
  if (GET_CODE (x) == ASHIFT
      && CONST_INT_P (XEXP (x, 1))
      && (unsigned HOST_WIDE_INT) INTVAL (XEXP (x, 1)) < 4)
    {
      changed = true;
      log = INTVAL (XEXP (x, 1));
      x = gen_rtx_MULT (Pmode, force_reg (Pmode, XEXP (x, 0)),
			GEN_INT (1 << log));
    }

  if (GET_CODE (x) == PLUS)
    {
      /* Canonicalize shifts by 0, 1, 2, 3 into multiply.  */

      if (GET_CODE (XEXP (x, 0)) == ASHIFT
	  && CONST_INT_P (XEXP (XEXP (x, 0), 1))
	  && (unsigned HOST_WIDE_INT) INTVAL (XEXP (XEXP (x, 0), 1)) < 4)
	{
	  changed = true;
	  log = INTVAL (XEXP (XEXP (x, 0), 1));
	  XEXP (x, 0) = gen_rtx_MULT (Pmode,
				      force_reg (Pmode, XEXP (XEXP (x, 0), 0)),
				      GEN_INT (1 << log));
	}

      if (GET_CODE (XEXP (x, 1)) == ASHIFT
	  && CONST_INT_P (XEXP (XEXP (x, 1), 1))
	  && (unsigned HOST_WIDE_INT) INTVAL (XEXP (XEXP (x, 1), 1)) < 4)
	{
	  changed = true;
	  log = INTVAL (XEXP (XEXP (x, 1), 1));
	  XEXP (x, 1) = gen_rtx_MULT (Pmode,
				      force_reg (Pmode, XEXP (XEXP (x, 1), 0)),
				      GEN_INT (1 << log));
	}

      /* Put multiply first if it isn't already.  */
      if (GET_CODE (XEXP (x, 1)) == MULT)
	{
	  std::swap (XEXP (x, 0), XEXP (x, 1));
	  changed = true;
	}

      /* Canonicalize (plus (mult (reg) (const)) (plus (reg) (const)))
	 into (plus (plus (mult (reg) (const)) (reg)) (const)).  This can be
	 created by virtual register instantiation, register elimination, and
	 similar optimizations.  */
      if (GET_CODE (XEXP (x, 0)) == MULT && GET_CODE (XEXP (x, 1)) == PLUS)
	{
	  changed = true;
	  x = gen_rtx_PLUS (Pmode,
			    gen_rtx_PLUS (Pmode, XEXP (x, 0),
					  XEXP (XEXP (x, 1), 0)),
			    XEXP (XEXP (x, 1), 1));
	}

      /* Canonicalize
	 (plus (plus (mult (reg) (const)) (plus (reg) (const))) const)
	 into (plus (plus (mult (reg) (const)) (reg)) (const)).  */
      else if (GET_CODE (x) == PLUS && GET_CODE (XEXP (x, 0)) == PLUS
	       && GET_CODE (XEXP (XEXP (x, 0), 0)) == MULT
	       && GET_CODE (XEXP (XEXP (x, 0), 1)) == PLUS
	       && CONSTANT_P (XEXP (x, 1)))
	{
	  rtx constant;
	  rtx other = NULL_RTX;

	  if (CONST_INT_P (XEXP (x, 1)))
	    {
	      constant = XEXP (x, 1);
	      other = XEXP (XEXP (XEXP (x, 0), 1), 1);
	    }
	  else if (CONST_INT_P (XEXP (XEXP (XEXP (x, 0), 1), 1)))
	    {
	      constant = XEXP (XEXP (XEXP (x, 0), 1), 1);
	      other = XEXP (x, 1);
	    }
	  else
	    constant = 0;

	  if (constant)
	    {
	      changed = true;
	      x = gen_rtx_PLUS (Pmode,
				gen_rtx_PLUS (Pmode, XEXP (XEXP (x, 0), 0),
					      XEXP (XEXP (XEXP (x, 0), 1), 0)),
				plus_constant (Pmode, other,
					       INTVAL (constant)));
	    }
	}

      if (changed && ix86_legitimate_address_p (mode, x, false))
	return x;

      if (GET_CODE (XEXP (x, 0)) == MULT)
	{
	  changed = true;
	  XEXP (x, 0) = copy_addr_to_reg (XEXP (x, 0));
	}

      if (GET_CODE (XEXP (x, 1)) == MULT)
	{
	  changed = true;
	  XEXP (x, 1) = copy_addr_to_reg (XEXP (x, 1));
	}

      if (changed
	  && REG_P (XEXP (x, 1))
	  && REG_P (XEXP (x, 0)))
	return x;

      if (flag_pic && SYMBOLIC_CONST (XEXP (x, 1)))
	{
	  changed = true;
	  x = legitimize_pic_address (x, 0);
	}

      if (changed && ix86_legitimate_address_p (mode, x, false))
	return x;

      if (REG_P (XEXP (x, 0)))
	{
	  rtx temp = gen_reg_rtx (Pmode);
	  rtx val  = force_operand (XEXP (x, 1), temp);
	  if (val != temp)
	    {
	      val = convert_to_mode (Pmode, val, 1);
	      emit_move_insn (temp, val);
	    }

	  XEXP (x, 1) = temp;
	  return x;
	}

      else if (REG_P (XEXP (x, 1)))
	{
	  rtx temp = gen_reg_rtx (Pmode);
	  rtx val  = force_operand (XEXP (x, 0), temp);
	  if (val != temp)
	    {
	      val = convert_to_mode (Pmode, val, 1);
	      emit_move_insn (temp, val);
	    }

	  XEXP (x, 0) = temp;
	  return x;
	}
    }

  return x;
}

/* Print an integer constant expression in assembler syntax.  Addition
   and subtraction are the only arithmetic that may appear in these
   expressions.  FILE is the stdio stream to write to, X is the rtx, and
   CODE is the operand print code from the output string.  */

static void
output_pic_addr_const (FILE *file, rtx x, int code)
{
  char buf[256];

  switch (GET_CODE (x))
    {
    case PC:
      gcc_assert (flag_pic);
      putc ('.', file);
      break;

    case SYMBOL_REF:
      if (TARGET_64BIT || ! TARGET_MACHO_BRANCH_ISLANDS)
	output_addr_const (file, x);
      else
	{
	  const char *name = XSTR (x, 0);

	  /* Mark the decl as referenced so that cgraph will
	     output the function.  */
	  if (SYMBOL_REF_DECL (x))
	    mark_decl_referenced (SYMBOL_REF_DECL (x));

#if TARGET_MACHO
	  if (MACHOPIC_INDIRECT
	      && machopic_classify_symbol (x) == MACHOPIC_UNDEFINED_FUNCTION)
	    name = machopic_indirection_name (x, /*stub_p=*/true);
#endif
	  assemble_name (file, name);
	}
      if (!TARGET_MACHO && !(TARGET_64BIT && TARGET_PECOFF)
	  && code == 'P' && ! SYMBOL_REF_LOCAL_P (x))
	fputs ("@PLT", file);
      break;

    case LABEL_REF:
      x = XEXP (x, 0);
      /* FALLTHRU */
    case CODE_LABEL:
      ASM_GENERATE_INTERNAL_LABEL (buf, "L", CODE_LABEL_NUMBER (x));
      assemble_name (asm_out_file, buf);
      break;

    case CONST_INT:
      fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x));
      break;

    case CONST:
      /* This used to output parentheses around the expression,
	 but that does not work on the 386 (either ATT or BSD assembler).  */
      output_pic_addr_const (file, XEXP (x, 0), code);
      break;

    case CONST_DOUBLE:
      /* We can't handle floating point constants;
	 TARGET_PRINT_OPERAND must handle them.  */
      output_operand_lossage ("floating constant misused");
      break;

    case PLUS:
      /* Some assemblers need integer constants to appear first.  */
      if (CONST_INT_P (XEXP (x, 0)))
	{
	  output_pic_addr_const (file, XEXP (x, 0), code);
	  putc ('+', file);
	  output_pic_addr_const (file, XEXP (x, 1), code);
	}
      else
	{
	  gcc_assert (CONST_INT_P (XEXP (x, 1)));
	  output_pic_addr_const (file, XEXP (x, 1), code);
	  putc ('+', file);
	  output_pic_addr_const (file, XEXP (x, 0), code);
	}
      break;

    case MINUS:
      if (!TARGET_MACHO)
	putc (ASSEMBLER_DIALECT == ASM_INTEL ? '(' : '[', file);
      output_pic_addr_const (file, XEXP (x, 0), code);
      putc ('-', file);
      output_pic_addr_const (file, XEXP (x, 1), code);
      if (!TARGET_MACHO)
	putc (ASSEMBLER_DIALECT == ASM_INTEL ? ')' : ']', file);
      break;

    case UNSPEC:
      gcc_assert (XVECLEN (x, 0) == 1);
      output_pic_addr_const (file, XVECEXP (x, 0, 0), code);
      switch (XINT (x, 1))
	{
	case UNSPEC_GOT:
	  fputs ("@GOT", file);
	  break;
	case UNSPEC_GOTOFF:
	  fputs ("@GOTOFF", file);
	  break;
	case UNSPEC_PLTOFF:
	  fputs ("@PLTOFF", file);
	  break;
	case UNSPEC_PCREL:
	  fputs (ASSEMBLER_DIALECT == ASM_ATT ?
		 "(%rip)" : "[rip]", file);
	  break;
	case UNSPEC_GOTPCREL:
	  fputs (ASSEMBLER_DIALECT == ASM_ATT ?
		 "@GOTPCREL(%rip)" : "@GOTPCREL[rip]", file);
	  break;
	case UNSPEC_GOTTPOFF:
	  /* FIXME: This might be @TPOFF in Sun ld too.  */
	  fputs ("@gottpoff", file);
	  break;
	case UNSPEC_TPOFF:
	  fputs ("@tpoff", file);
	  break;
	case UNSPEC_NTPOFF:
	  if (TARGET_64BIT)
	    fputs ("@tpoff", file);
	  else
	    fputs ("@ntpoff", file);
	  break;
	case UNSPEC_DTPOFF:
	  fputs ("@dtpoff", file);
	  break;
	case UNSPEC_GOTNTPOFF:
	  if (TARGET_64BIT)
	    fputs (ASSEMBLER_DIALECT == ASM_ATT ?
		   "@gottpoff(%rip)": "@gottpoff[rip]", file);
	  else
	    fputs ("@gotntpoff", file);
	  break;
	case UNSPEC_INDNTPOFF:
	  fputs ("@indntpoff", file);
	  break;
#if TARGET_MACHO
	case UNSPEC_MACHOPIC_OFFSET:
	  putc ('-', file);
	  machopic_output_function_base_name (file);
	  break;
#endif
	default:
	  output_operand_lossage ("invalid UNSPEC as operand");
	  break;
	}
       break;

    default:
      output_operand_lossage ("invalid expression as operand");
    }
}

/* This is called from dwarf2out.c via TARGET_ASM_OUTPUT_DWARF_DTPREL.
   We need to emit DTP-relative relocations.  */

static void ATTRIBUTE_UNUSED
i386_output_dwarf_dtprel (FILE *file, int size, rtx x)
{
  fputs (ASM_LONG, file);
  output_addr_const (file, x);
  fputs ("@dtpoff", file);
  switch (size)
    {
    case 4:
      break;
    case 8:
      fputs (", 0", file);
      break;
    default:
      gcc_unreachable ();
   }
}

/* Return true if X is a representation of the PIC register.  This copes
   with calls from ix86_find_base_term, where the register might have
   been replaced by a cselib value.  */

static bool
ix86_pic_register_p (rtx x)
{
  if (GET_CODE (x) == VALUE && CSELIB_VAL_PTR (x))
    return (pic_offset_table_rtx
	    && rtx_equal_for_cselib_p (x, pic_offset_table_rtx));
  else if (GET_CODE (x) == UNSPEC && XINT (x, 1) == UNSPEC_SET_GOT)
    return true;
  else if (!REG_P (x))
    return false;
  else if (pic_offset_table_rtx)
    {
      if (REGNO (x) == REGNO (pic_offset_table_rtx))
	return true;
      if (HARD_REGISTER_P (x)
	  && !HARD_REGISTER_P (pic_offset_table_rtx)
	  && ORIGINAL_REGNO (x) == REGNO (pic_offset_table_rtx))
	return true;
      return false;
    }
  else
    return REGNO (x) == PIC_OFFSET_TABLE_REGNUM;
}

/* Helper function for ix86_delegitimize_address.
   Attempt to delegitimize TLS local-exec accesses.  */

static rtx
ix86_delegitimize_tls_address (rtx orig_x)
{
  rtx x = orig_x, unspec;
  struct ix86_address addr;

  if (!TARGET_TLS_DIRECT_SEG_REFS)
    return orig_x;
  if (MEM_P (x))
    x = XEXP (x, 0);
  if (GET_CODE (x) != PLUS || GET_MODE (x) != Pmode)
    return orig_x;
  if (ix86_decompose_address (x, &addr) == 0
      || addr.seg != DEFAULT_TLS_SEG_REG
      || addr.disp == NULL_RTX
      || GET_CODE (addr.disp) != CONST)
    return orig_x;
  unspec = XEXP (addr.disp, 0);
  if (GET_CODE (unspec) == PLUS && CONST_INT_P (XEXP (unspec, 1)))
    unspec = XEXP (unspec, 0);
  if (GET_CODE (unspec) != UNSPEC || XINT (unspec, 1) != UNSPEC_NTPOFF)
    return orig_x;
  x = XVECEXP (unspec, 0, 0);
  gcc_assert (GET_CODE (x) == SYMBOL_REF);
  if (unspec != XEXP (addr.disp, 0))
    x = gen_rtx_PLUS (Pmode, x, XEXP (XEXP (addr.disp, 0), 1));
  if (addr.index)
    {
      rtx idx = addr.index;
      if (addr.scale != 1)
	idx = gen_rtx_MULT (Pmode, idx, GEN_INT (addr.scale));
      x = gen_rtx_PLUS (Pmode, idx, x);
    }
  if (addr.base)
    x = gen_rtx_PLUS (Pmode, addr.base, x);
  if (MEM_P (orig_x))
    x = replace_equiv_address_nv (orig_x, x);
  return x;
}

/* In the name of slightly smaller debug output, and to cater to
   general assembler lossage, recognize PIC+GOTOFF and turn it back
   into a direct symbol reference.

   On Darwin, this is necessary to avoid a crash, because Darwin
   has a different PIC label for each routine but the DWARF debugging
   information is not associated with any particular routine, so it's
   necessary to remove references to the PIC label from RTL stored by
   the DWARF output code.

   This helper is used in the normal ix86_delegitimize_address
   entrypoint (e.g. used in the target delegitimization hook) and
   in ix86_find_base_term.  As compile time memory optimization, we
   avoid allocating rtxes that will not change anything on the outcome
   of the callers (find_base_value and find_base_term).  */

static inline rtx
ix86_delegitimize_address_1 (rtx x, bool base_term_p)
{
  rtx orig_x = delegitimize_mem_from_attrs (x);
  /* addend is NULL or some rtx if x is something+GOTOFF where
     something doesn't include the PIC register.  */
  rtx addend = NULL_RTX;
  /* reg_addend is NULL or a multiple of some register.  */
  rtx reg_addend = NULL_RTX;
  /* const_addend is NULL or a const_int.  */
  rtx const_addend = NULL_RTX;
  /* This is the result, or NULL.  */
  rtx result = NULL_RTX;

  x = orig_x;

  if (MEM_P (x))
    x = XEXP (x, 0);

  if (TARGET_64BIT)
    {
      if (GET_CODE (x) == CONST
          && GET_CODE (XEXP (x, 0)) == PLUS
          && GET_MODE (XEXP (x, 0)) == Pmode
          && CONST_INT_P (XEXP (XEXP (x, 0), 1))
          && GET_CODE (XEXP (XEXP (x, 0), 0)) == UNSPEC
          && XINT (XEXP (XEXP (x, 0), 0), 1) == UNSPEC_PCREL)
        {
	  /* find_base_{value,term} only care about MEMs with arg_pointer_rtx
	     base.  A CONST can't be arg_pointer_rtx based.  */
	  if (base_term_p && MEM_P (orig_x))
	    return orig_x;
	  rtx x2 = XVECEXP (XEXP (XEXP (x, 0), 0), 0, 0);
	  x = gen_rtx_PLUS (Pmode, XEXP (XEXP (x, 0), 1), x2);
	  if (MEM_P (orig_x))
	    x = replace_equiv_address_nv (orig_x, x);
	  return x;
	}

      if (GET_CODE (x) == CONST
	  && GET_CODE (XEXP (x, 0)) == UNSPEC
	  && (XINT (XEXP (x, 0), 1) == UNSPEC_GOTPCREL
	      || XINT (XEXP (x, 0), 1) == UNSPEC_PCREL)
	  && (MEM_P (orig_x) || XINT (XEXP (x, 0), 1) == UNSPEC_PCREL))
	{
	  x = XVECEXP (XEXP (x, 0), 0, 0);
	  if (GET_MODE (orig_x) != GET_MODE (x) && MEM_P (orig_x))
	    {
	      x = lowpart_subreg (GET_MODE (orig_x), x, GET_MODE (x));
	      if (x == NULL_RTX)
		return orig_x;
	    }
	  return x;
	}

      if (ix86_cmodel != CM_MEDIUM_PIC && ix86_cmodel != CM_LARGE_PIC)
	return ix86_delegitimize_tls_address (orig_x);

      /* Fall thru into the code shared with -m32 for -mcmodel=large -fpic
	 and -mcmodel=medium -fpic.  */
    }

  if (GET_CODE (x) != PLUS
      || GET_CODE (XEXP (x, 1)) != CONST)
    return ix86_delegitimize_tls_address (orig_x);

  if (ix86_pic_register_p (XEXP (x, 0)))
    /* %ebx + GOT/GOTOFF */
    ;
  else if (GET_CODE (XEXP (x, 0)) == PLUS)
    {
      /* %ebx + %reg * scale + GOT/GOTOFF */
      reg_addend = XEXP (x, 0);
      if (ix86_pic_register_p (XEXP (reg_addend, 0)))
	reg_addend = XEXP (reg_addend, 1);
      else if (ix86_pic_register_p (XEXP (reg_addend, 1)))
	reg_addend = XEXP (reg_addend, 0);
      else
	{
	  reg_addend = NULL_RTX;
	  addend = XEXP (x, 0);
	}
    }
  else
    addend = XEXP (x, 0);

  x = XEXP (XEXP (x, 1), 0);
  if (GET_CODE (x) == PLUS
      && CONST_INT_P (XEXP (x, 1)))
    {
      const_addend = XEXP (x, 1);
      x = XEXP (x, 0);
    }

  if (GET_CODE (x) == UNSPEC
      && ((XINT (x, 1) == UNSPEC_GOT && MEM_P (orig_x) && !addend)
	  || (XINT (x, 1) == UNSPEC_GOTOFF && !MEM_P (orig_x))
	  || (XINT (x, 1) == UNSPEC_PLTOFF && ix86_cmodel == CM_LARGE_PIC
	      && !MEM_P (orig_x) && !addend)))
    result = XVECEXP (x, 0, 0);

  if (!TARGET_64BIT && TARGET_MACHO && darwin_local_data_pic (x)
      && !MEM_P (orig_x))
    result = XVECEXP (x, 0, 0);

  if (! result)
    return ix86_delegitimize_tls_address (orig_x);

  /* For (PLUS something CONST_INT) both find_base_{value,term} just
     recurse on the first operand.  */
  if (const_addend && !base_term_p)
    result = gen_rtx_CONST (Pmode, gen_rtx_PLUS (Pmode, result, const_addend));
  if (reg_addend)
    result = gen_rtx_PLUS (Pmode, reg_addend, result);
  if (addend)
    {
      /* If the rest of original X doesn't involve the PIC register, add
	 addend and subtract pic_offset_table_rtx.  This can happen e.g.
	 for code like:
	 leal (%ebx, %ecx, 4), %ecx
	 ...
	 movl foo@GOTOFF(%ecx), %edx
	 in which case we return (%ecx - %ebx) + foo
	 or (%ecx - _GLOBAL_OFFSET_TABLE_) + foo if pseudo_pic_reg
	 and reload has completed.  Don't do the latter for debug,
	 as _GLOBAL_OFFSET_TABLE_ can't be expressed in the assembly.  */
      if (pic_offset_table_rtx
	  && (!reload_completed || !ix86_use_pseudo_pic_reg ()))
        result = gen_rtx_PLUS (Pmode, gen_rtx_MINUS (Pmode, copy_rtx (addend),
						     pic_offset_table_rtx),
			       result);
      else if (base_term_p
	       && pic_offset_table_rtx
	       && !TARGET_MACHO
	       && !TARGET_VXWORKS_RTP)
	{
	  rtx tmp = gen_rtx_SYMBOL_REF (Pmode, GOT_SYMBOL_NAME);
	  tmp = gen_rtx_MINUS (Pmode, copy_rtx (addend), tmp);
	  result = gen_rtx_PLUS (Pmode, tmp, result);
	}
      else
	return orig_x;
    }
  if (GET_MODE (orig_x) != Pmode && MEM_P (orig_x))
    {
      result = lowpart_subreg (GET_MODE (orig_x), result, Pmode);
      if (result == NULL_RTX)
	return orig_x;
    }
  return result;
}

/* The normal instantiation of the above template.  */

static rtx
ix86_delegitimize_address (rtx x)
{
  return ix86_delegitimize_address_1 (x, false);
}

/* If X is a machine specific address (i.e. a symbol or label being
   referenced as a displacement from the GOT implemented using an
   UNSPEC), then return the base term.  Otherwise return X.  */

rtx
ix86_find_base_term (rtx x)
{
  rtx term;

  if (TARGET_64BIT)
    {
      if (GET_CODE (x) != CONST)
	return x;
      term = XEXP (x, 0);
      if (GET_CODE (term) == PLUS
	  && CONST_INT_P (XEXP (term, 1)))
	term = XEXP (term, 0);
      if (GET_CODE (term) != UNSPEC
	  || (XINT (term, 1) != UNSPEC_GOTPCREL
	      && XINT (term, 1) != UNSPEC_PCREL))
	return x;

      return XVECEXP (term, 0, 0);
    }

  return ix86_delegitimize_address_1 (x, true);
}

/* Return true if X shouldn't be emitted into the debug info.
   Disallow UNSPECs other than @gotoff - we can't emit _GLOBAL_OFFSET_TABLE_
   symbol easily into the .debug_info section, so we need not to
   delegitimize, but instead assemble as @gotoff.
   Disallow _GLOBAL_OFFSET_TABLE_ SYMBOL_REF - the assembler magically
   assembles that as _GLOBAL_OFFSET_TABLE_-. expression.  */

static bool
ix86_const_not_ok_for_debug_p (rtx x)
{
  if (GET_CODE (x) == UNSPEC && XINT (x, 1) != UNSPEC_GOTOFF)
    return true;

  if (SYMBOL_REF_P (x) && strcmp (XSTR (x, 0), GOT_SYMBOL_NAME) == 0)
    return true;

  return false;
}

static void
put_condition_code (enum rtx_code code, machine_mode mode, bool reverse,
		    bool fp, FILE *file)
{
  const char *suffix;

  if (mode == CCFPmode)
    {
      code = ix86_fp_compare_code_to_integer (code);
      mode = CCmode;
    }
  if (reverse)
    code = reverse_condition (code);

  switch (code)
    {
    case EQ:
      gcc_assert (mode != CCGZmode);
      switch (mode)
	{
	case E_CCAmode:
	  suffix = "a";
	  break;
	case E_CCCmode:
	  suffix = "c";
	  break;
	case E_CCOmode:
	  suffix = "o";
	  break;
	case E_CCPmode:
	  suffix = "p";
	  break;
	case E_CCSmode:
	  suffix = "s";
	  break;
	default:
	  suffix = "e";
	  break;
	}
      break;
    case NE:
      gcc_assert (mode != CCGZmode);
      switch (mode)
	{
	case E_CCAmode:
	  suffix = "na";
	  break;
	case E_CCCmode:
	  suffix = "nc";
	  break;
	case E_CCOmode:
	  suffix = "no";
	  break;
	case E_CCPmode:
	  suffix = "np";
	  break;
	case E_CCSmode:
	  suffix = "ns";
	  break;
	default:
	  suffix = "ne";
	  break;
	}
      break;
    case GT:
      gcc_assert (mode == CCmode || mode == CCNOmode || mode == CCGCmode);
      suffix = "g";
      break;
    case GTU:
      /* ??? Use "nbe" instead of "a" for fcmov lossage on some assemblers.
	 Those same assemblers have the same but opposite lossage on cmov.  */
      if (mode == CCmode)
	suffix = fp ? "nbe" : "a";
      else
	gcc_unreachable ();
      break;
    case LT:
      switch (mode)
	{
	case E_CCNOmode:
	case E_CCGOCmode:
	  suffix = "s";
	  break;

	case E_CCmode:
	case E_CCGCmode:
	case E_CCGZmode:
	  suffix = "l";
	  break;

	default:
	  gcc_unreachable ();
	}
      break;
    case LTU:
      if (mode == CCmode || mode == CCGZmode)
	suffix = "b";
      else if (mode == CCCmode)
	suffix = fp ? "b" : "c";
      else
	gcc_unreachable ();
      break;
    case GE:
      switch (mode)
	{
	case E_CCNOmode:
	case E_CCGOCmode:
	  suffix = "ns";
	  break;

	case E_CCmode:
	case E_CCGCmode:
	case E_CCGZmode:
	  suffix = "ge";
	  break;

	default:
	  gcc_unreachable ();
	}
      break;
    case GEU:
      if (mode == CCmode || mode == CCGZmode)
	suffix = "nb";
      else if (mode == CCCmode)
	suffix = fp ? "nb" : "nc";
      else
	gcc_unreachable ();
      break;
    case LE:
      gcc_assert (mode == CCmode || mode == CCGCmode || mode == CCNOmode);
      suffix = "le";
      break;
    case LEU:
      if (mode == CCmode)
	suffix = "be";
      else
	gcc_unreachable ();
      break;
    case UNORDERED:
      suffix = fp ? "u" : "p";
      break;
    case ORDERED:
      suffix = fp ? "nu" : "np";
      break;
    default:
      gcc_unreachable ();
    }
  fputs (suffix, file);
}

/* Print the name of register X to FILE based on its machine mode and number.
   If CODE is 'w', pretend the mode is HImode.
   If CODE is 'b', pretend the mode is QImode.
   If CODE is 'k', pretend the mode is SImode.
   If CODE is 'q', pretend the mode is DImode.
   If CODE is 'x', pretend the mode is V4SFmode.
   If CODE is 't', pretend the mode is V8SFmode.
   If CODE is 'g', pretend the mode is V16SFmode.
   If CODE is 'h', pretend the reg is the 'high' byte register.
   If CODE is 'y', print "st(0)" instead of "st", if the reg is stack op.
   If CODE is 'd', duplicate the operand for AVX instruction.
   If CODE is 'V', print naked full integer register name without %.
 */

void
print_reg (rtx x, int code, FILE *file)
{
  const char *reg;
  int msize;
  unsigned int regno;
  bool duplicated;

  if (ASSEMBLER_DIALECT == ASM_ATT && code != 'V')
    putc ('%', file);

  if (x == pc_rtx)
    {
      gcc_assert (TARGET_64BIT);
      fputs ("rip", file);
      return;
    }

  if (code == 'y' && STACK_TOP_P (x))
    {
      fputs ("st(0)", file);
      return;
    }

  if (code == 'w')
    msize = 2;
  else if (code == 'b')
    msize = 1;
  else if (code == 'k')
    msize = 4;
  else if (code == 'q')
    msize = 8;
  else if (code == 'h')
    msize = 0;
  else if (code == 'x')
    msize = 16;
  else if (code == 't')
    msize = 32;
  else if (code == 'g')
    msize = 64;
  else
    msize = GET_MODE_SIZE (GET_MODE (x));

  regno = REGNO (x);

  if (regno == ARG_POINTER_REGNUM
      || regno == FRAME_POINTER_REGNUM
      || regno == FPSR_REG)
    {
      output_operand_lossage
	("invalid use of register '%s'", reg_names[regno]);
      return;
    }
  else if (regno == FLAGS_REG)
    {
      output_operand_lossage ("invalid use of asm flag output");
      return;
    }

  if (code == 'V')
    {
      if (GENERAL_REGNO_P (regno))
	msize = GET_MODE_SIZE (word_mode);
      else
	error ("'V' modifier on non-integer register");
    }

  duplicated = code == 'd' && TARGET_AVX;

  switch (msize)
    {
    case 16:
    case 12:
    case 8:
      if (GENERAL_REGNO_P (regno) && msize > GET_MODE_SIZE (word_mode))
	warning (0, "unsupported size for integer register");
      /* FALLTHRU */
    case 4:
      if (LEGACY_INT_REGNO_P (regno))
	putc (msize > 4 && TARGET_64BIT ? 'r' : 'e', file);
      /* FALLTHRU */
    case 2:
    normal:
      reg = hi_reg_name[regno];
      break;
    case 1:
      if (regno >= ARRAY_SIZE (qi_reg_name))
	goto normal;
      if (!ANY_QI_REGNO_P (regno))
	error ("unsupported size for integer register");
      reg = qi_reg_name[regno];
      break;
    case 0:
      if (regno >= ARRAY_SIZE (qi_high_reg_name))
	goto normal;
      reg = qi_high_reg_name[regno];
      break;
    case 32:
    case 64:
      if (SSE_REGNO_P (regno))
	{
	  gcc_assert (!duplicated);
	  putc (msize == 32 ? 'y' : 'z', file);
	  reg = hi_reg_name[regno] + 1;
	  break;
	}
      goto normal;
    default:
      gcc_unreachable ();
    }

  fputs (reg, file);

  /* Irritatingly, AMD extended registers use
     different naming convention: "r%d[bwd]"  */
  if (REX_INT_REGNO_P (regno))
    {
      gcc_assert (TARGET_64BIT);
      switch (msize)
	{
	  case 0:
	    error ("extended registers have no high halves");
	    break;
	  case 1:
	    putc ('b', file);
	    break;
	  case 2:
	    putc ('w', file);
	    break;
	  case 4:
	    putc ('d', file);
	    break;
	  case 8:
	    /* no suffix */
	    break;
	  default:
	    error ("unsupported operand size for extended register");
	    break;
	}
      return;
    }

  if (duplicated)
    {
      if (ASSEMBLER_DIALECT == ASM_ATT)
	fprintf (file, ", %%%s", reg);
      else
	fprintf (file, ", %s", reg);
    }
}

/* Meaning of CODE:
   L,W,B,Q,S,T -- print the opcode suffix for specified size of operand.
   C -- print opcode suffix for set/cmov insn.
   c -- like C, but print reversed condition
   F,f -- likewise, but for floating-point.
   O -- if HAVE_AS_IX86_CMOV_SUN_SYNTAX, expand to "w.", "l." or "q.",
	otherwise nothing
   R -- print embedded rounding and sae.
   r -- print only sae.
   z -- print the opcode suffix for the size of the current operand.
   Z -- likewise, with special suffixes for x87 instructions.
   * -- print a star (in certain assembler syntax)
   A -- print an absolute memory reference.
   E -- print address with DImode register names if TARGET_64BIT.
   w -- print the operand as if it's a "word" (HImode) even if it isn't.
   s -- print a shift double count, followed by the assemblers argument
	delimiter.
   b -- print the QImode name of the register for the indicated operand.
	%b0 would print %al if operands[0] is reg 0.
   w --  likewise, print the HImode name of the register.
   k --  likewise, print the SImode name of the register.
   q --  likewise, print the DImode name of the register.
   x --  likewise, print the V4SFmode name of the register.
   t --  likewise, print the V8SFmode name of the register.
   g --  likewise, print the V16SFmode name of the register.
   h -- print the QImode name for a "high" register, either ah, bh, ch or dh.
   y -- print "st(0)" instead of "st" as a register.
   d -- print duplicated register operand for AVX instruction.
   D -- print condition for SSE cmp instruction.
   P -- if PIC, print an @PLT suffix.
   p -- print raw symbol name.
   X -- don't print any sort of PIC '@' suffix for a symbol.
   & -- print some in-use local-dynamic symbol name.
   H -- print a memory address offset by 8; used for sse high-parts
   Y -- print condition for XOP pcom* instruction.
   V -- print naked full integer register name without %.
   + -- print a branch hint as 'cs' or 'ds' prefix
   ; -- print a semicolon (after prefixes due to bug in older gas).
   ~ -- print "i" if TARGET_AVX2, "f" otherwise.
   ^ -- print addr32 prefix if TARGET_64BIT and Pmode != word_mode
   ! -- print NOTRACK prefix for jxx/call/ret instructions if required.
 */

void
ix86_print_operand (FILE *file, rtx x, int code)
{
  if (code)
    {
      switch (code)
	{
	case 'A':
	  switch (ASSEMBLER_DIALECT)
	    {
	    case ASM_ATT:
	      putc ('*', file);
	      break;

	    case ASM_INTEL:
	      /* Intel syntax. For absolute addresses, registers should not
		 be surrounded by braces.  */
	      if (!REG_P (x))
		{
		  putc ('[', file);
		  ix86_print_operand (file, x, 0);
		  putc (']', file);
		  return;
		}
	      break;

	    default:
	      gcc_unreachable ();
	    }

	  ix86_print_operand (file, x, 0);
	  return;

	case 'E':
	  /* Wrap address in an UNSPEC to declare special handling.  */
	  if (TARGET_64BIT)
	    x = gen_rtx_UNSPEC (DImode, gen_rtvec (1, x), UNSPEC_LEA_ADDR);

	  output_address (VOIDmode, x);
	  return;

	case 'L':
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('l', file);
	  return;

	case 'W':
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('w', file);
	  return;

	case 'B':
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('b', file);
	  return;

	case 'Q':
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('l', file);
	  return;

	case 'S':
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('s', file);
	  return;

	case 'T':
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('t', file);
	  return;

	case 'O':
#ifdef HAVE_AS_IX86_CMOV_SUN_SYNTAX
	  if (ASSEMBLER_DIALECT != ASM_ATT)
	    return;

	  switch (GET_MODE_SIZE (GET_MODE (x)))
	    {
	    case 2:
	      putc ('w', file);
	      break;
  
	    case 4:
	      putc ('l', file);
	      break;

	    case 8:
	      putc ('q', file);
	      break;

	    default:
	      output_operand_lossage ("invalid operand size for operand "
				      "code 'O'");
	      return;
	    }

	  putc ('.', file);
#endif
	  return;

	case 'z':
	  if (GET_MODE_CLASS (GET_MODE (x)) == MODE_INT)
	    {
	      /* Opcodes don't get size suffixes if using Intel opcodes.  */
	      if (ASSEMBLER_DIALECT == ASM_INTEL)
		return;

	      switch (GET_MODE_SIZE (GET_MODE (x)))
		{
		case 1:
		  putc ('b', file);
		  return;

		case 2:
		  putc ('w', file);
		  return;

		case 4:
		  putc ('l', file);
		  return;

		case 8:
		  putc ('q', file);
		  return;

		default:
		  output_operand_lossage ("invalid operand size for operand "
					  "code 'z'");
		  return;
		}
	    }

	  if (GET_MODE_CLASS (GET_MODE (x)) == MODE_FLOAT)
	    warning (0, "non-integer operand used with operand code 'z'");
	  /* FALLTHRU */

	case 'Z':
	  /* 387 opcodes don't get size suffixes if using Intel opcodes.  */
	  if (ASSEMBLER_DIALECT == ASM_INTEL)
	    return;

	  if (GET_MODE_CLASS (GET_MODE (x)) == MODE_INT)
	    {
	      switch (GET_MODE_SIZE (GET_MODE (x)))
		{
		case 2:
#ifdef HAVE_AS_IX86_FILDS
		  putc ('s', file);
#endif
		  return;

		case 4:
		  putc ('l', file);
		  return;

		case 8:
#ifdef HAVE_AS_IX86_FILDQ
		  putc ('q', file);
#else
		  fputs ("ll", file);
#endif
		  return;

		default:
		  break;
		}
	    }
	  else if (GET_MODE_CLASS (GET_MODE (x)) == MODE_FLOAT)
	    {
	      /* 387 opcodes don't get size suffixes
		 if the operands are registers.  */
	      if (STACK_REG_P (x))
		return;

	      switch (GET_MODE_SIZE (GET_MODE (x)))
		{
		case 4:
		  putc ('s', file);
		  return;

		case 8:
		  putc ('l', file);
		  return;

		case 12:
		case 16:
		  putc ('t', file);
		  return;

		default:
		  break;
		}
	    }
	  else
	    {
	      output_operand_lossage ("invalid operand type used with "
				      "operand code 'Z'");
	      return;
	    }

	  output_operand_lossage ("invalid operand size for operand code 'Z'");
	  return;

	case 'd':
	case 'b':
	case 'w':
	case 'k':
	case 'q':
	case 'h':
	case 't':
	case 'g':
	case 'y':
	case 'x':
	case 'X':
	case 'P':
	case 'p':
	case 'V':
	  break;

	case 's':
	  if (CONST_INT_P (x) || ! SHIFT_DOUBLE_OMITS_COUNT)
	    {
	      ix86_print_operand (file, x, 0);
	      fputs (", ", file);
	    }
	  return;

	case 'Y':
	  switch (GET_CODE (x))
	    {
	    case NE:
	      fputs ("neq", file);
	      break;
	    case EQ:
	      fputs ("eq", file);
	      break;
	    case GE:
	    case GEU:
	      fputs (INTEGRAL_MODE_P (GET_MODE (x)) ? "ge" : "unlt", file);
	      break;
	    case GT:
	    case GTU:
	      fputs (INTEGRAL_MODE_P (GET_MODE (x)) ? "gt" : "unle", file);
	      break;
	    case LE:
	    case LEU:
	      fputs ("le", file);
	      break;
	    case LT:
	    case LTU:
	      fputs ("lt", file);
	      break;
	    case UNORDERED:
	      fputs ("unord", file);
	      break;
	    case ORDERED:
	      fputs ("ord", file);
	      break;
	    case UNEQ:
	      fputs ("ueq", file);
	      break;
	    case UNGE:
	      fputs ("nlt", file);
	      break;
	    case UNGT:
	      fputs ("nle", file);
	      break;
	    case UNLE:
	      fputs ("ule", file);
	      break;
	    case UNLT:
	      fputs ("ult", file);
	      break;
	    case LTGT:
	      fputs ("une", file);
	      break;
	    default:
	      output_operand_lossage ("operand is not a condition code, "
				      "invalid operand code 'Y'");
	      return;
	    }
	  return;

	case 'D':
	  /* Little bit of braindamage here.  The SSE compare instructions
	     does use completely different names for the comparisons that the
	     fp conditional moves.  */
	  switch (GET_CODE (x))
	    {
	    case UNEQ:
	      if (TARGET_AVX)
		{
		  fputs ("eq_us", file);
		  break;
		}
	     /* FALLTHRU */
	    case EQ:
	      fputs ("eq", file);
	      break;
	    case UNLT:
	      if (TARGET_AVX)
		{
		  fputs ("nge", file);
		  break;
		}
	     /* FALLTHRU */
	    case LT:
	      fputs ("lt", file);
	      break;
	    case UNLE:
	      if (TARGET_AVX)
		{
		  fputs ("ngt", file);
		  break;
		}
	     /* FALLTHRU */
	    case LE:
	      fputs ("le", file);
	      break;
	    case UNORDERED:
	      fputs ("unord", file);
	      break;
	    case LTGT:
	      if (TARGET_AVX)
		{
		  fputs ("neq_oq", file);
		  break;
		}
	     /* FALLTHRU */
	    case NE:
	      fputs ("neq", file);
	      break;
	    case GE:
	      if (TARGET_AVX)
		{
		  fputs ("ge", file);
		  break;
		}
	     /* FALLTHRU */
	    case UNGE:
	      fputs ("nlt", file);
	      break;
	    case GT:
	      if (TARGET_AVX)
		{
		  fputs ("gt", file);
		  break;
		}
	     /* FALLTHRU */
	    case UNGT:
	      fputs ("nle", file);
	      break;
	    case ORDERED:
	      fputs ("ord", file);
	      break;
	    default:
	      output_operand_lossage ("operand is not a condition code, "
				      "invalid operand code 'D'");
	      return;
	    }
	  return;

	case 'F':
	case 'f':
#ifdef HAVE_AS_IX86_CMOV_SUN_SYNTAX
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('.', file);
	  gcc_fallthrough ();
#endif

	case 'C':
	case 'c':
	  if (!COMPARISON_P (x))
	    {
	      output_operand_lossage ("operand is not a condition code, "
				      "invalid operand code '%c'", code);
	      return;
	    }
	  put_condition_code (GET_CODE (x), GET_MODE (XEXP (x, 0)),
			      code == 'c' || code == 'f',
			      code == 'F' || code == 'f',
			      file);
	  return;

	case 'H':
	  if (!offsettable_memref_p (x))
	    {
	      output_operand_lossage ("operand is not an offsettable memory "
				      "reference, invalid operand code 'H'");
	      return;
	    }
	  /* It doesn't actually matter what mode we use here, as we're
	     only going to use this for printing.  */
	  x = adjust_address_nv (x, DImode, 8);
	  /* Output 'qword ptr' for intel assembler dialect.  */
	  if (ASSEMBLER_DIALECT == ASM_INTEL)
	    code = 'q';
	  break;

	case 'K':
	  if (!CONST_INT_P (x))
	    {
	      output_operand_lossage ("operand is not an integer, invalid "
				      "operand code 'K'");
	      return;
	    }

	  if (INTVAL (x) & IX86_HLE_ACQUIRE)
#ifdef HAVE_AS_IX86_HLE
	    fputs ("xacquire ", file);
#else
	    fputs ("\n" ASM_BYTE "0xf2\n\t", file);
#endif
	  else if (INTVAL (x) & IX86_HLE_RELEASE)
#ifdef HAVE_AS_IX86_HLE
	    fputs ("xrelease ", file);
#else
	    fputs ("\n" ASM_BYTE "0xf3\n\t", file);
#endif
	  /* We do not want to print value of the operand.  */
	  return;

	case 'N':
	  if (x == const0_rtx || x == CONST0_RTX (GET_MODE (x)))
	    fputs ("{z}", file);
	  return;

	case 'r':
	  if (!CONST_INT_P (x) || INTVAL (x) != ROUND_SAE)
	    {
	      output_operand_lossage ("operand is not a specific integer, "
				      "invalid operand code 'r'");
	      return;
	    }

	  if (ASSEMBLER_DIALECT == ASM_INTEL)
	    fputs (", ", file);

	  fputs ("{sae}", file);

	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    fputs (", ", file);

	  return;

	case 'R':
	  if (!CONST_INT_P (x))
	    {
	      output_operand_lossage ("operand is not an integer, invalid "
				      "operand code 'R'");
	      return;
	    }

	  if (ASSEMBLER_DIALECT == ASM_INTEL)
	    fputs (", ", file);

	  switch (INTVAL (x))
	    {
	    case ROUND_NEAREST_INT | ROUND_SAE:
	      fputs ("{rn-sae}", file);
	      break;
	    case ROUND_NEG_INF | ROUND_SAE:
	      fputs ("{rd-sae}", file);
	      break;
	    case ROUND_POS_INF | ROUND_SAE:
	      fputs ("{ru-sae}", file);
	      break;
	    case ROUND_ZERO | ROUND_SAE:
	      fputs ("{rz-sae}", file);
	      break;
	    default:
	      output_operand_lossage ("operand is not a specific integer, "
				      "invalid operand code 'R'");
	    }

	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    fputs (", ", file);

	  return;

	case '*':
	  if (ASSEMBLER_DIALECT == ASM_ATT)
	    putc ('*', file);
	  return;

	case '&':
	  {
	    const char *name = get_some_local_dynamic_name ();
	    if (name == NULL)
	      output_operand_lossage ("'%%&' used without any "
				      "local dynamic TLS references");
	    else
	      assemble_name (file, name);
	    return;
	  }

	case '+':
	  {
	    rtx x;

	    if (!optimize
	        || optimize_function_for_size_p (cfun)
		|| !TARGET_BRANCH_PREDICTION_HINTS)
	      return;

	    x = find_reg_note (current_output_insn, REG_BR_PROB, 0);
	    if (x)
	      {
		int pred_val = profile_probability::from_reg_br_prob_note
				 (XINT (x, 0)).to_reg_br_prob_base ();

		if (pred_val < REG_BR_PROB_BASE * 45 / 100
		    || pred_val > REG_BR_PROB_BASE * 55 / 100)
		  {
		    bool taken = pred_val > REG_BR_PROB_BASE / 2;
		    bool cputaken
		      = final_forward_branch_p (current_output_insn) == 0;

		    /* Emit hints only in the case default branch prediction
		       heuristics would fail.  */
		    if (taken != cputaken)
		      {
			/* We use 3e (DS) prefix for taken branches and
			   2e (CS) prefix for not taken branches.  */
			if (taken)
			  fputs ("ds ; ", file);
			else
			  fputs ("cs ; ", file);
		      }
		  }
	      }
	    return;
	  }

	case ';':
#ifndef HAVE_AS_IX86_REP_LOCK_PREFIX
	  putc (';', file);
#endif
	  return;

	case '~':
	  putc (TARGET_AVX2 ? 'i' : 'f', file);
	  return;

	case '^':
	  if (TARGET_64BIT && Pmode != word_mode)
	    fputs ("addr32 ", file);
	  return;

	case '!':
	  if (ix86_notrack_prefixed_insn_p (current_output_insn))
	    fputs ("notrack ", file);
	  return;

	default:
	  output_operand_lossage ("invalid operand code '%c'", code);
	}
    }

  if (REG_P (x))
    print_reg (x, code, file);

  else if (MEM_P (x))
    {
      rtx addr = XEXP (x, 0);

      /* No `byte ptr' prefix for call instructions ... */
      if (ASSEMBLER_DIALECT == ASM_INTEL && code != 'X' && code != 'P')
	{
	  machine_mode mode = GET_MODE (x);
	  const char *size;

	  /* Check for explicit size override codes.  */
	  if (code == 'b')
	    size = "BYTE";
	  else if (code == 'w')
	    size = "WORD";
	  else if (code == 'k')
	    size = "DWORD";
	  else if (code == 'q')
	    size = "QWORD";
	  else if (code == 'x')
	    size = "XMMWORD";
	  else if (code == 't')
	    size = "YMMWORD";
	  else if (code == 'g')
	    size = "ZMMWORD";
	  else if (mode == BLKmode)
	    /* ... or BLKmode operands, when not overridden.  */
	    size = NULL;
	  else
	    switch (GET_MODE_SIZE (mode))
	      {
	      case 1: size = "BYTE"; break;
	      case 2: size = "WORD"; break;
	      case 4: size = "DWORD"; break;
	      case 8: size = "QWORD"; break;
	      case 12: size = "TBYTE"; break;
	      case 16:
		if (mode == XFmode)
		  size = "TBYTE";
		else
		  size = "XMMWORD";
		break;
	      case 32: size = "YMMWORD"; break;
	      case 64: size = "ZMMWORD"; break;
	      default:
		gcc_unreachable ();
	      }
	  if (size)
	    {
	      fputs (size, file);
	      fputs (" PTR ", file);
	    }
	}

      if (this_is_asm_operands && ! address_operand (addr, VOIDmode))
	output_operand_lossage ("invalid constraints for operand");
      else
	ix86_print_operand_address_as
	  (file, addr, MEM_ADDR_SPACE (x), code == 'p' || code == 'P');
    }

  else if (CONST_DOUBLE_P (x) && GET_MODE (x) == SFmode)
    {
      long l;

      REAL_VALUE_TO_TARGET_SINGLE (*CONST_DOUBLE_REAL_VALUE (x), l);

      if (ASSEMBLER_DIALECT == ASM_ATT)
	putc ('$', file);
      /* Sign extend 32bit SFmode immediate to 8 bytes.  */
      if (code == 'q')
	fprintf (file, "0x%08" HOST_LONG_LONG_FORMAT "x",
		 (unsigned long long) (int) l);
      else
	fprintf (file, "0x%08x", (unsigned int) l);
    }

  else if (CONST_DOUBLE_P (x) && GET_MODE (x) == DFmode)
    {
      long l[2];

      REAL_VALUE_TO_TARGET_DOUBLE (*CONST_DOUBLE_REAL_VALUE (x), l);

      if (ASSEMBLER_DIALECT == ASM_ATT)
	putc ('$', file);
      fprintf (file, "0x%lx%08lx", l[1] & 0xffffffff, l[0] & 0xffffffff);
    }

  /* These float cases don't actually occur as immediate operands.  */
  else if (CONST_DOUBLE_P (x) && GET_MODE (x) == XFmode)
    {
      char dstr[30];

      real_to_decimal (dstr, CONST_DOUBLE_REAL_VALUE (x), sizeof (dstr), 0, 1);
      fputs (dstr, file);
    }

  else
    {
      /* We have patterns that allow zero sets of memory, for instance.
	 In 64-bit mode, we should probably support all 8-byte vectors,
	 since we can in fact encode that into an immediate.  */
      if (GET_CODE (x) == CONST_VECTOR)
	{
	  if (x != CONST0_RTX (GET_MODE (x)))
	    output_operand_lossage ("invalid vector immediate");
	  x = const0_rtx;
	}

      if (code != 'P' && code != 'p')
	{
	  if (CONST_INT_P (x))
	    {
	      if (ASSEMBLER_DIALECT == ASM_ATT)
		putc ('$', file);
	    }
	  else if (GET_CODE (x) == CONST || GET_CODE (x) == SYMBOL_REF
		   || GET_CODE (x) == LABEL_REF)
	    {
	      if (ASSEMBLER_DIALECT == ASM_ATT)
		putc ('$', file);
	      else
		fputs ("OFFSET FLAT:", file);
	    }
	}
      if (CONST_INT_P (x))
	fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (x));
      else if (flag_pic || MACHOPIC_INDIRECT)
	output_pic_addr_const (file, x, code);
      else
	output_addr_const (file, x);
    }
}

static bool
ix86_print_operand_punct_valid_p (unsigned char code)
{
  return (code == '*' || code == '+' || code == '&' || code == ';'
	  || code == '~' || code == '^' || code == '!');
}

/* Print a memory operand whose address is ADDR.  */

static void
ix86_print_operand_address_as (FILE *file, rtx addr,
			       addr_space_t as, bool no_rip)
{
  struct ix86_address parts;
  rtx base, index, disp;
  int scale;
  int ok;
  bool vsib = false;
  int code = 0;

  if (GET_CODE (addr) == UNSPEC && XINT (addr, 1) == UNSPEC_VSIBADDR)
    {
      ok = ix86_decompose_address (XVECEXP (addr, 0, 0), &parts);
      gcc_assert (parts.index == NULL_RTX);
      parts.index = XVECEXP (addr, 0, 1);
      parts.scale = INTVAL (XVECEXP (addr, 0, 2));
      addr = XVECEXP (addr, 0, 0);
      vsib = true;
    }
  else if (GET_CODE (addr) == UNSPEC && XINT (addr, 1) == UNSPEC_LEA_ADDR)
    {
      gcc_assert (TARGET_64BIT);
      ok = ix86_decompose_address (XVECEXP (addr, 0, 0), &parts);
      code = 'q';
    }
  else
    ok = ix86_decompose_address (addr, &parts);

  gcc_assert (ok);

  base = parts.base;
  index = parts.index;
  disp = parts.disp;
  scale = parts.scale;

  if (ADDR_SPACE_GENERIC_P (as))
    as = parts.seg;
  else
    gcc_assert (ADDR_SPACE_GENERIC_P (parts.seg));

  if (!ADDR_SPACE_GENERIC_P (as))
    {
      if (ASSEMBLER_DIALECT == ASM_ATT)
	putc ('%', file);

      switch (as)
	{
	case ADDR_SPACE_SEG_FS:
	  fputs ("fs:", file);
	  break;
	case ADDR_SPACE_SEG_GS:
	  fputs ("gs:", file);
	  break;
	default:
	  gcc_unreachable ();
	}
    }

  /* Use one byte shorter RIP relative addressing for 64bit mode.  */
  if (TARGET_64BIT && !base && !index && !no_rip)
    {
      rtx symbol = disp;

      if (GET_CODE (disp) == CONST
	  && GET_CODE (XEXP (disp, 0)) == PLUS
	  && CONST_INT_P (XEXP (XEXP (disp, 0), 1)))
	symbol = XEXP (XEXP (disp, 0), 0);

      if (GET_CODE (symbol) == LABEL_REF
	  || (GET_CODE (symbol) == SYMBOL_REF
	      && SYMBOL_REF_TLS_MODEL (symbol) == 0))
	base = pc_rtx;
    }

  if (!base && !index)
    {
      /* Displacement only requires special attention.  */
      if (CONST_INT_P (disp))
	{
	  if (ASSEMBLER_DIALECT == ASM_INTEL && ADDR_SPACE_GENERIC_P (as))
	    fputs ("ds:", file);
	  fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (disp));
	}
      /* Load the external function address via the GOT slot to avoid PLT.  */
      else if (GET_CODE (disp) == CONST
	       && GET_CODE (XEXP (disp, 0)) == UNSPEC
	       && (XINT (XEXP (disp, 0), 1) == UNSPEC_GOTPCREL
		   || XINT (XEXP (disp, 0), 1) == UNSPEC_GOT)
	       && ix86_force_load_from_GOT_p (XVECEXP (XEXP (disp, 0), 0, 0)))
	output_pic_addr_const (file, disp, 0);
      else if (flag_pic)
	output_pic_addr_const (file, disp, 0);
      else
	output_addr_const (file, disp);
    }
  else
    {
      /* Print SImode register names to force addr32 prefix.  */
      if (SImode_address_operand (addr, VOIDmode))
	{
	  if (flag_checking)
	    {
	      gcc_assert (TARGET_64BIT);
	      switch (GET_CODE (addr))
		{
		case SUBREG:
		  gcc_assert (GET_MODE (addr) == SImode);
		  gcc_assert (GET_MODE (SUBREG_REG (addr)) == DImode);
		  break;
		case ZERO_EXTEND:
		case AND:
		  gcc_assert (GET_MODE (addr) == DImode);
		  break;
		default:
		  gcc_unreachable ();
		}
	    }
	  gcc_assert (!code);
	  code = 'k';
	}
      else if (code == 0
	       && TARGET_X32
	       && disp
	       && CONST_INT_P (disp)
	       && INTVAL (disp) < -16*1024*1024)
	{
	  /* X32 runs in 64-bit mode, where displacement, DISP, in
	     address DISP(%r64), is encoded as 32-bit immediate sign-
	     extended from 32-bit to 64-bit.  For -0x40000300(%r64),
	     address is %r64 + 0xffffffffbffffd00.  When %r64 <
	     0x40000300, like 0x37ffe064, address is 0xfffffffff7ffdd64,
	     which is invalid for x32.  The correct address is %r64
	     - 0x40000300 == 0xf7ffdd64.  To properly encode
	     -0x40000300(%r64) for x32, we zero-extend negative
	     displacement by forcing addr32 prefix which truncates
	     0xfffffffff7ffdd64 to 0xf7ffdd64.  In theory, we should
	     zero-extend all negative displacements, including -1(%rsp).
	     However, for small negative displacements, sign-extension
	     won't cause overflow.  We only zero-extend negative
	     displacements if they < -16*1024*1024, which is also used
	     to check legitimate address displacements for PIC.  */
	  code = 'k';
	}

      /* Since the upper 32 bits of RSP are always zero for x32,
	 we can encode %esp as %rsp to avoid 0x67 prefix if
	 there is no index register.  */
      if (TARGET_X32 && Pmode == SImode
	  && !index && base && REG_P (base) && REGNO (base) == SP_REG)
	code = 'q';

      if (ASSEMBLER_DIALECT == ASM_ATT)
	{
	  if (disp)
	    {
	      if (flag_pic)
		output_pic_addr_const (file, disp, 0);
	      else if (GET_CODE (disp) == LABEL_REF)
		output_asm_label (disp);
	      else
		output_addr_const (file, disp);
	    }

	  putc ('(', file);
	  if (base)
	    print_reg (base, code, file);
	  if (index)
	    {
	      putc (',', file);
	      print_reg (index, vsib ? 0 : code, file);
	      if (scale != 1 || vsib)
		fprintf (file, ",%d", scale);
	    }
	  putc (')', file);
	}
      else
	{
	  rtx offset = NULL_RTX;

	  if (disp)
	    {
	      /* Pull out the offset of a symbol; print any symbol itself.  */
	      if (GET_CODE (disp) == CONST
		  && GET_CODE (XEXP (disp, 0)) == PLUS
		  && CONST_INT_P (XEXP (XEXP (disp, 0), 1)))
		{
		  offset = XEXP (XEXP (disp, 0), 1);
		  disp = gen_rtx_CONST (VOIDmode,
					XEXP (XEXP (disp, 0), 0));
		}

	      if (flag_pic)
		output_pic_addr_const (file, disp, 0);
	      else if (GET_CODE (disp) == LABEL_REF)
		output_asm_label (disp);
	      else if (CONST_INT_P (disp))
		offset = disp;
	      else
		output_addr_const (file, disp);
	    }

	  putc ('[', file);
	  if (base)
	    {
	      print_reg (base, code, file);
	      if (offset)
		{
		  if (INTVAL (offset) >= 0)
		    putc ('+', file);
		  fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (offset));
		}
	    }
	  else if (offset)
	    fprintf (file, HOST_WIDE_INT_PRINT_DEC, INTVAL (offset));
	  else
	    putc ('0', file);

	  if (index)
	    {
	      putc ('+', file);
	      print_reg (index, vsib ? 0 : code, file);
	      if (scale != 1 || vsib)
		fprintf (file, "*%d", scale);
	    }
	  putc (']', file);
	}
    }
}

static void
ix86_print_operand_address (FILE *file, machine_mode /*mode*/, rtx addr)
{
  ix86_print_operand_address_as (file, addr, ADDR_SPACE_GENERIC, false);
}

/* Implementation of TARGET_ASM_OUTPUT_ADDR_CONST_EXTRA.  */

static bool
i386_asm_output_addr_const_extra (FILE *file, rtx x)
{
  rtx op;

  if (GET_CODE (x) != UNSPEC)
    return false;

  op = XVECEXP (x, 0, 0);
  switch (XINT (x, 1))
    {
    case UNSPEC_GOTOFF:
      output_addr_const (file, op);
      fputs ("@gotoff", file);
      break;
    case UNSPEC_GOTTPOFF:
      output_addr_const (file, op);
      /* FIXME: This might be @TPOFF in Sun ld.  */
      fputs ("@gottpoff", file);
      break;
    case UNSPEC_TPOFF:
      output_addr_const (file, op);
      fputs ("@tpoff", file);
      break;
    case UNSPEC_NTPOFF:
      output_addr_const (file, op);
      if (TARGET_64BIT)
	fputs ("@tpoff", file);
      else
	fputs ("@ntpoff", file);
      break;
    case UNSPEC_DTPOFF:
      output_addr_const (file, op);
      fputs ("@dtpoff", file);
      break;
    case UNSPEC_GOTNTPOFF:
      output_addr_const (file, op);
      if (TARGET_64BIT)
	fputs (ASSEMBLER_DIALECT == ASM_ATT ?
	       "@gottpoff(%rip)" : "@gottpoff[rip]", file);
      else
	fputs ("@gotntpoff", file);
      break;
    case UNSPEC_INDNTPOFF:
      output_addr_const (file, op);
      fputs ("@indntpoff", file);
      break;
#if TARGET_MACHO
    case UNSPEC_MACHOPIC_OFFSET:
      output_addr_const (file, op);
      putc ('-', file);
      machopic_output_function_base_name (file);
      break;
#endif

    default:
      return false;
    }

  return true;
}

/* Split one or more double-mode RTL references into pairs of half-mode
   references.  The RTL can be REG, offsettable MEM, integer constant, or
   CONST_DOUBLE.  "operands" is a pointer to an array of double-mode RTLs to
   split and "num" is its length.  lo_half and hi_half are output arrays
   that parallel "operands".  */

void
split_double_mode (machine_mode mode, rtx operands[],
		   int num, rtx lo_half[], rtx hi_half[])
{
  machine_mode half_mode;
  unsigned int byte;

  switch (mode)
    {
    case E_TImode:
      half_mode = DImode;
      break;
    case E_DImode:
      half_mode = SImode;
      break;
    default:
      gcc_unreachable ();
    }

  byte = GET_MODE_SIZE (half_mode);

  while (num--)
    {
      rtx op = operands[num];

      /* simplify_subreg refuse to split volatile memory addresses,
         but we still have to handle it.  */
      if (MEM_P (op))
	{
	  lo_half[num] = adjust_address (op, half_mode, 0);
	  hi_half[num] = adjust_address (op, half_mode, byte);
	}
      else
	{
	  lo_half[num] = simplify_gen_subreg (half_mode, op,
					      GET_MODE (op) == VOIDmode
					      ? mode : GET_MODE (op), 0);
	  hi_half[num] = simplify_gen_subreg (half_mode, op,
					      GET_MODE (op) == VOIDmode
					      ? mode : GET_MODE (op), byte);
	}
    }
}

/* Output code to perform a 387 binary operation in INSN, one of PLUS,
   MINUS, MULT or DIV.  OPERANDS are the insn operands, where operands[3]
   is the expression of the binary operation.  The output may either be
   emitted here, or returned to the caller, like all output_* functions.

   There is no guarantee that the operands are the same mode, as they
   might be within FLOAT or FLOAT_EXTEND expressions.  */

#ifndef SYSV386_COMPAT
/* Set to 1 for compatibility with brain-damaged assemblers.  No-one
   wants to fix the assemblers because that causes incompatibility
   with gcc.  No-one wants to fix gcc because that causes
   incompatibility with assemblers...  You can use the option of
   -DSYSV386_COMPAT=0 if you recompile both gcc and gas this way.  */
#define SYSV386_COMPAT 1
#endif

const char *
output_387_binary_op (rtx_insn *insn, rtx *operands)
{
  static char buf[40];
  const char *p;
  bool is_sse
    = (SSE_REG_P (operands[0])
       || SSE_REG_P (operands[1]) || SSE_REG_P (operands[2]));

  if (is_sse)
    p = "%v";
  else if (GET_MODE_CLASS (GET_MODE (operands[1])) == MODE_INT
	   || GET_MODE_CLASS (GET_MODE (operands[2])) == MODE_INT)
    p = "fi";
  else
    p = "f";

  strcpy (buf, p);

  switch (GET_CODE (operands[3]))
    {
    case PLUS:
      p = "add"; break;
    case MINUS:
      p = "sub"; break;
    case MULT:
      p = "mul"; break;
    case DIV:
      p = "div"; break;
    default:
      gcc_unreachable ();
    }

  strcat (buf, p);

  if (is_sse)
   {
     p = (GET_MODE (operands[0]) == SFmode) ? "ss" : "sd";
     strcat (buf, p);

     if (TARGET_AVX)
       p = "\t{%2, %1, %0|%0, %1, %2}";
     else
       p = "\t{%2, %0|%0, %2}";

     strcat (buf, p);
     return buf;
   }

  /* Even if we do not want to check the inputs, this documents input
     constraints.  Which helps in understanding the following code.  */
  if (flag_checking)
    {
      if (STACK_REG_P (operands[0])
	  && ((REG_P (operands[1])
	       && REGNO (operands[0]) == REGNO (operands[1])
	       && (STACK_REG_P (operands[2]) || MEM_P (operands[2])))
	      || (REG_P (operands[2])
		  && REGNO (operands[0]) == REGNO (operands[2])
		  && (STACK_REG_P (operands[1]) || MEM_P (operands[1]))))
	  && (STACK_TOP_P (operands[1]) || STACK_TOP_P (operands[2])))
	; /* ok */
      else
	gcc_unreachable ();
    }

  switch (GET_CODE (operands[3]))
    {
    case MULT:
    case PLUS:
      if (REG_P (operands[2]) && REGNO (operands[0]) == REGNO (operands[2]))
	std::swap (operands[1], operands[2]);

      /* know operands[0] == operands[1].  */

      if (MEM_P (operands[2]))
	{
	  p = "%Z2\t%2";
	  break;
	}

      if (find_regno_note (insn, REG_DEAD, REGNO (operands[2])))
	{
	  if (STACK_TOP_P (operands[0]))
	    /* How is it that we are storing to a dead operand[2]?
	       Well, presumably operands[1] is dead too.  We can't
	       store the result to st(0) as st(0) gets popped on this
	       instruction.  Instead store to operands[2] (which I
	       think has to be st(1)).  st(1) will be popped later.
	       gcc <= 2.8.1 didn't have this check and generated
	       assembly code that the Unixware assembler rejected.  */
	    p = "p\t{%0, %2|%2, %0}";	/* st(1) = st(0) op st(1); pop */
	  else
	    p = "p\t{%2, %0|%0, %2}";	/* st(r1) = st(r1) op st(0); pop */
	  break;
	}

      if (STACK_TOP_P (operands[0]))
	p = "\t{%y2, %0|%0, %y2}";	/* st(0) = st(0) op st(r2) */
      else
	p = "\t{%2, %0|%0, %2}";	/* st(r1) = st(r1) op st(0) */
      break;

    case MINUS:
    case DIV:
      if (MEM_P (operands[1]))
	{
	  p = "r%Z1\t%1";
	  break;
	}

      if (MEM_P (operands[2]))
	{
	  p = "%Z2\t%2";
	  break;
	}

      if (find_regno_note (insn, REG_DEAD, REGNO (operands[2])))
	{
#if SYSV386_COMPAT
	  /* The SystemV/386 SVR3.2 assembler, and probably all AT&T
	     derived assemblers, confusingly reverse the direction of
	     the operation for fsub{r} and fdiv{r} when the
	     destination register is not st(0).  The Intel assembler
	     doesn't have this brain damage.  Read !SYSV386_COMPAT to
	     figure out what the hardware really does.  */
	  if (STACK_TOP_P (operands[0]))
	    p = "{p\t%0, %2|rp\t%2, %0}";
	  else
	    p = "{rp\t%2, %0|p\t%0, %2}";
#else
	  if (STACK_TOP_P (operands[0]))
	    /* As above for fmul/fadd, we can't store to st(0).  */
	    p = "rp\t{%0, %2|%2, %0}";	/* st(1) = st(0) op st(1); pop */
	  else
	    p = "p\t{%2, %0|%0, %2}";	/* st(r1) = st(r1) op st(0); pop */
#endif
	  break;
	}

      if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
	{
#if SYSV386_COMPAT
	  if (STACK_TOP_P (operands[0]))
	    p = "{rp\t%0, %1|p\t%1, %0}";
	  else
	    p = "{p\t%1, %0|rp\t%0, %1}";
#else
	  if (STACK_TOP_P (operands[0]))
	    p = "p\t{%0, %1|%1, %0}";	/* st(1) = st(1) op st(0); pop */
	  else
	    p = "rp\t{%1, %0|%0, %1}";	/* st(r2) = st(0) op st(r2); pop */
#endif
	  break;
	}

      if (STACK_TOP_P (operands[0]))
	{
	  if (STACK_TOP_P (operands[1]))
	    p = "\t{%y2, %0|%0, %y2}";	/* st(0) = st(0) op st(r2) */
	  else
	    p = "r\t{%y1, %0|%0, %y1}";	/* st(0) = st(r1) op st(0) */
	  break;
	}
      else if (STACK_TOP_P (operands[1]))
	{
#if SYSV386_COMPAT
	  p = "{\t%1, %0|r\t%0, %1}";
#else
	  p = "r\t{%1, %0|%0, %1}";	/* st(r2) = st(0) op st(r2) */
#endif
	}
      else
	{
#if SYSV386_COMPAT
	  p = "{r\t%2, %0|\t%0, %2}";
#else
	  p = "\t{%2, %0|%0, %2}";	/* st(r1) = st(r1) op st(0) */
#endif
	}
      break;

    default:
      gcc_unreachable ();
    }

  strcat (buf, p);
  return buf;
}

/* Return needed mode for entity in optimize_mode_switching pass.  */

static int
ix86_dirflag_mode_needed (rtx_insn *insn)
{
  if (CALL_P (insn))
    {
      if (cfun->machine->func_type == TYPE_NORMAL)
	return X86_DIRFLAG_ANY;
      else
	/* No need to emit CLD in interrupt handler for TARGET_CLD.  */
	return TARGET_CLD ? X86_DIRFLAG_ANY : X86_DIRFLAG_RESET;
    }

  if (recog_memoized (insn) < 0)
    return X86_DIRFLAG_ANY;

  if (get_attr_type (insn) == TYPE_STR)
    {
      /* Emit cld instruction if stringops are used in the function.  */
      if (cfun->machine->func_type == TYPE_NORMAL)
	return TARGET_CLD ? X86_DIRFLAG_RESET : X86_DIRFLAG_ANY;
      else
	return X86_DIRFLAG_RESET;
    }

  return X86_DIRFLAG_ANY;
}

/* Check if a 256bit or 512 bit AVX register is referenced inside of EXP.   */

static bool
ix86_check_avx_upper_register (const_rtx exp)
{
  return SSE_REG_P (exp) && GET_MODE_BITSIZE (GET_MODE (exp)) > 128;
}

/* Return needed mode for entity in optimize_mode_switching pass.  */

static int
ix86_avx_u128_mode_needed (rtx_insn *insn)
{
  if (CALL_P (insn))
    {
      rtx link;

      /* Needed mode is set to AVX_U128_CLEAN if there are
	 no 256bit or 512bit modes used in function arguments. */
      for (link = CALL_INSN_FUNCTION_USAGE (insn);
	   link;
	   link = XEXP (link, 1))
	{
	  if (GET_CODE (XEXP (link, 0)) == USE)
	    {
	      rtx arg = XEXP (XEXP (link, 0), 0);

	      if (ix86_check_avx_upper_register (arg))
		return AVX_U128_DIRTY;
	    }
	}

      return AVX_U128_CLEAN;
    }

  /* Require DIRTY mode if a 256bit or 512bit AVX register is referenced.
     Hardware changes state only when a 256bit register is written to,
     but we need to prevent the compiler from moving optimal insertion
     point above eventual read from 256bit or 512 bit register.  */
  subrtx_iterator::array_type array;
  FOR_EACH_SUBRTX (iter, array, PATTERN (insn), NONCONST)
    if (ix86_check_avx_upper_register (*iter))
      return AVX_U128_DIRTY;

  return AVX_U128_ANY;
}

/* Return mode that i387 must be switched into
   prior to the execution of insn.  */

static int
ix86_i387_mode_needed (int entity, rtx_insn *insn)
{
  enum attr_i387_cw mode;

  /* The mode UNINITIALIZED is used to store control word after a
     function call or ASM pattern.  The mode ANY specify that function
     has no requirements on the control word and make no changes in the
     bits we are interested in.  */

  if (CALL_P (insn)
      || (NONJUMP_INSN_P (insn)
	  && (asm_noperands (PATTERN (insn)) >= 0
	      || GET_CODE (PATTERN (insn)) == ASM_INPUT)))
    return I387_CW_UNINITIALIZED;

  if (recog_memoized (insn) < 0)
    return I387_CW_ANY;

  mode = get_attr_i387_cw (insn);

  switch (entity)
    {
    case I387_TRUNC:
      if (mode == I387_CW_TRUNC)
	return mode;
      break;

    case I387_FLOOR:
      if (mode == I387_CW_FLOOR)
	return mode;
      break;

    case I387_CEIL:
      if (mode == I387_CW_CEIL)
	return mode;
      break;

    default:
      gcc_unreachable ();
    }

  return I387_CW_ANY;
}

/* Return mode that entity must be switched into
   prior to the execution of insn.  */

static int
ix86_mode_needed (int entity, rtx_insn *insn)
{
  switch (entity)
    {
    case X86_DIRFLAG:
      return ix86_dirflag_mode_needed (insn);
    case AVX_U128:
      return ix86_avx_u128_mode_needed (insn);
    case I387_TRUNC:
    case I387_FLOOR:
    case I387_CEIL:
      return ix86_i387_mode_needed (entity, insn);
    default:
      gcc_unreachable ();
    }
  return 0;
}

/* Check if a 256bit or 512bit AVX register is referenced in stores.   */
 
static void
ix86_check_avx_upper_stores (rtx dest, const_rtx, void *data)
 {
   if (ix86_check_avx_upper_register (dest))
    {
      bool *used = (bool *) data;
      *used = true;
    }
 } 

/* Calculate mode of upper 128bit AVX registers after the insn.  */

static int
ix86_avx_u128_mode_after (int mode, rtx_insn *insn)
{
  rtx pat = PATTERN (insn);

  if (vzeroupper_pattern (pat, VOIDmode)
      || vzeroall_pattern (pat, VOIDmode))
    return AVX_U128_CLEAN;

  /* We know that state is clean after CALL insn if there are no
     256bit or 512bit registers used in the function return register. */
  if (CALL_P (insn))
    {
      bool avx_upper_reg_found = false;
      note_stores (pat, ix86_check_avx_upper_stores, &avx_upper_reg_found);

      return avx_upper_reg_found ? AVX_U128_DIRTY : AVX_U128_CLEAN;
    }

  /* Otherwise, return current mode.  Remember that if insn
     references AVX 256bit or 512bit registers, the mode was already
     changed to DIRTY from MODE_NEEDED.  */
  return mode;
}

/* Return the mode that an insn results in.  */

static int
ix86_mode_after (int entity, int mode, rtx_insn *insn)
{
  switch (entity)
    {
    case X86_DIRFLAG:
      return mode;
    case AVX_U128:
      return ix86_avx_u128_mode_after (mode, insn);
    case I387_TRUNC:
    case I387_FLOOR:
    case I387_CEIL:
      return mode;
    default:
      gcc_unreachable ();
    }
}

static int
ix86_dirflag_mode_entry (void)
{
  /* For TARGET_CLD or in the interrupt handler we can't assume
     direction flag state at function entry.  */
  if (TARGET_CLD
      || cfun->machine->func_type != TYPE_NORMAL)
    return X86_DIRFLAG_ANY;

  return X86_DIRFLAG_RESET;
}

static int
ix86_avx_u128_mode_entry (void)
{
  tree arg;

  /* Entry mode is set to AVX_U128_DIRTY if there are
     256bit or 512bit modes used in function arguments.  */
  for (arg = DECL_ARGUMENTS (current_function_decl); arg;
       arg = TREE_CHAIN (arg))
    {
      rtx incoming = DECL_INCOMING_RTL (arg);

      if (incoming && ix86_check_avx_upper_register (incoming))
	return AVX_U128_DIRTY;
    }

  return AVX_U128_CLEAN;
}

/* Return a mode that ENTITY is assumed to be
   switched to at function entry.  */

static int
ix86_mode_entry (int entity)
{
  switch (entity)
    {
    case X86_DIRFLAG:
      return ix86_dirflag_mode_entry ();
    case AVX_U128:
      return ix86_avx_u128_mode_entry ();
    case I387_TRUNC:
    case I387_FLOOR:
    case I387_CEIL:
      return I387_CW_ANY;
    default:
      gcc_unreachable ();
    }
}

static int
ix86_avx_u128_mode_exit (void)
{
  rtx reg = crtl->return_rtx;

  /* Exit mode is set to AVX_U128_DIRTY if there are 256bit
     or 512 bit modes used in the function return register. */
  if (reg && ix86_check_avx_upper_register (reg))
    return AVX_U128_DIRTY;

  /* Exit mode is set to AVX_U128_DIRTY if there are 256bit or 512bit
     modes used in function arguments, otherwise return AVX_U128_CLEAN.
   */
  return ix86_avx_u128_mode_entry ();
}

/* Return a mode that ENTITY is assumed to be
   switched to at function exit.  */

static int
ix86_mode_exit (int entity)
{
  switch (entity)
    {
    case X86_DIRFLAG:
      return X86_DIRFLAG_ANY;
    case AVX_U128:
      return ix86_avx_u128_mode_exit ();
    case I387_TRUNC:
    case I387_FLOOR:
    case I387_CEIL:
      return I387_CW_ANY;
    default:
      gcc_unreachable ();
    }
}

static int
ix86_mode_priority (int, int n)
{
  return n;
}

/* Output code to initialize control word copies used by trunc?f?i and
   rounding patterns.  CURRENT_MODE is set to current control word,
   while NEW_MODE is set to new control word.  */

static void
emit_i387_cw_initialization (int mode)
{
  rtx stored_mode = assign_386_stack_local (HImode, SLOT_CW_STORED);
  rtx new_mode;

  enum ix86_stack_slot slot;

  rtx reg = gen_reg_rtx (HImode);

  emit_insn (gen_x86_fnstcw_1 (stored_mode));
  emit_move_insn (reg, copy_rtx (stored_mode));

  switch (mode)
    {
    case I387_CW_TRUNC:
      /* round toward zero (truncate) */
      emit_insn (gen_iorhi3 (reg, reg, GEN_INT (0x0c00)));
      slot = SLOT_CW_TRUNC;
      break;

    case I387_CW_FLOOR:
      /* round down toward -oo */
      emit_insn (gen_andhi3 (reg, reg, GEN_INT (~0x0c00)));
      emit_insn (gen_iorhi3 (reg, reg, GEN_INT (0x0400)));
      slot = SLOT_CW_FLOOR;
      break;

    case I387_CW_CEIL:
      /* round up toward +oo */
      emit_insn (gen_andhi3 (reg, reg, GEN_INT (~0x0c00)));
      emit_insn (gen_iorhi3 (reg, reg, GEN_INT (0x0800)));
      slot = SLOT_CW_CEIL;
      break;

    default:
      gcc_unreachable ();
    }

  gcc_assert (slot < MAX_386_STACK_LOCALS);

  new_mode = assign_386_stack_local (HImode, slot);
  emit_move_insn (new_mode, reg);
}

/* Generate one or more insns to set ENTITY to MODE.  */

static void
ix86_emit_mode_set (int entity, int mode, int prev_mode ATTRIBUTE_UNUSED,
		    HARD_REG_SET regs_live ATTRIBUTE_UNUSED)
{
  switch (entity)
    {
    case X86_DIRFLAG:
      if (mode == X86_DIRFLAG_RESET)
	emit_insn (gen_cld ());
      break;
    case AVX_U128:
      if (mode == AVX_U128_CLEAN)
	emit_insn (gen_avx_vzeroupper ());
      break;
    case I387_TRUNC:
    case I387_FLOOR:
    case I387_CEIL:
      if (mode != I387_CW_ANY
	  && mode != I387_CW_UNINITIALIZED)
	emit_i387_cw_initialization (mode);
      break;
    default:
      gcc_unreachable ();
    }
}

/* Output code for INSN to convert a float to a signed int.  OPERANDS
   are the insn operands.  The output may be [HSD]Imode and the input
   operand may be [SDX]Fmode.  */

const char *
output_fix_trunc (rtx_insn *insn, rtx *operands, bool fisttp)
{
  bool stack_top_dies = find_regno_note (insn, REG_DEAD, FIRST_STACK_REG);
  bool dimode_p = GET_MODE (operands[0]) == DImode;
  int round_mode = get_attr_i387_cw (insn);

  static char buf[40];
  const char *p;

  /* Jump through a hoop or two for DImode, since the hardware has no
     non-popping instruction.  We used to do this a different way, but
     that was somewhat fragile and broke with post-reload splitters.  */
  if ((dimode_p || fisttp) && !stack_top_dies)
    output_asm_insn ("fld\t%y1", operands);

  gcc_assert (STACK_TOP_P (operands[1]));
  gcc_assert (MEM_P (operands[0]));
  gcc_assert (GET_MODE (operands[1]) != TFmode);

  if (fisttp)
    return "fisttp%Z0\t%0";

  strcpy (buf, "fist");

  if (round_mode != I387_CW_ANY)
    output_asm_insn ("fldcw\t%3", operands);

  p = "p%Z0\t%0";
  strcat (buf, p + !(stack_top_dies || dimode_p));

  output_asm_insn (buf, operands);

  if (round_mode != I387_CW_ANY)
    output_asm_insn ("fldcw\t%2", operands);

  return "";
}

/* Output code for x87 ffreep insn.  The OPNO argument, which may only
   have the values zero or one, indicates the ffreep insn's operand
   from the OPERANDS array.  */

static const char *
output_387_ffreep (rtx *operands ATTRIBUTE_UNUSED, int opno)
{
  if (TARGET_USE_FFREEP)
#ifdef HAVE_AS_IX86_FFREEP
    return opno ? "ffreep\t%y1" : "ffreep\t%y0";
#else
    {
      static char retval[32];
      int regno = REGNO (operands[opno]);

      gcc_assert (STACK_REGNO_P (regno));

      regno -= FIRST_STACK_REG;

      snprintf (retval, sizeof (retval), ASM_SHORT "0xc%ddf", regno);
      return retval;
    }
#endif

  return opno ? "fstp\t%y1" : "fstp\t%y0";
}


/* Output code for INSN to compare OPERANDS.  EFLAGS_P is 1 when fcomi
   should be used.  UNORDERED_P is true when fucom should be used.  */

const char *
output_fp_compare (rtx_insn *insn, rtx *operands,
		   bool eflags_p, bool unordered_p)
{
  rtx *xops = eflags_p ? &operands[0] : &operands[1];
  bool stack_top_dies;

  static char buf[40];
  const char *p;

  gcc_assert (STACK_TOP_P (xops[0]));

  stack_top_dies = find_regno_note (insn, REG_DEAD, FIRST_STACK_REG);

  if (eflags_p)
    {
      p = unordered_p ? "fucomi" : "fcomi";
      strcpy (buf, p);

      p = "p\t{%y1, %0|%0, %y1}";
      strcat (buf, p + !stack_top_dies);

      return buf;
    }

  if (STACK_REG_P (xops[1])
      && stack_top_dies
      && find_regno_note (insn, REG_DEAD, FIRST_STACK_REG + 1))
    {
      gcc_assert (REGNO (xops[1]) == FIRST_STACK_REG + 1);

      /* If both the top of the 387 stack die, and the other operand
	 is also a stack register that dies, then this must be a
	 `fcompp' float compare.  */
      p = unordered_p ? "fucompp" : "fcompp";
      strcpy (buf, p);
    }
  else if (const0_operand (xops[1], VOIDmode))
    {
      gcc_assert (!unordered_p);
      strcpy (buf, "ftst");
    }
  else
    {
      if (GET_MODE_CLASS (GET_MODE (xops[1])) == MODE_INT)
	{
	  gcc_assert (!unordered_p);
	  p = "ficom";
	}
      else
	p = unordered_p ? "fucom" : "fcom";

      strcpy (buf, p);

      p = "p%Z2\t%y2";
      strcat (buf, p + !stack_top_dies);
    }

  output_asm_insn (buf, operands);
  return "fnstsw\t%0";
}

void
ix86_output_addr_vec_elt (FILE *file, int value)
{
  const char *directive = ASM_LONG;

#ifdef ASM_QUAD
  if (TARGET_LP64)
    directive = ASM_QUAD;
#else
  gcc_assert (!TARGET_64BIT);
#endif

  fprintf (file, "%s%s%d\n", directive, LPREFIX, value);
}

void
ix86_output_addr_diff_elt (FILE *file, int value, int rel)
{
  const char *directive = ASM_LONG;

#ifdef ASM_QUAD
  if (TARGET_64BIT && CASE_VECTOR_MODE == DImode)
    directive = ASM_QUAD;
#else
  gcc_assert (!TARGET_64BIT);
#endif
  /* We can't use @GOTOFF for text labels on VxWorks; see gotoff_operand.  */
  if (TARGET_64BIT || TARGET_VXWORKS_RTP)
    fprintf (file, "%s%s%d-%s%d\n",
	     directive, LPREFIX, value, LPREFIX, rel);
#if TARGET_MACHO
  else if (TARGET_MACHO)
    {
      fprintf (file, ASM_LONG "%s%d-", LPREFIX, value);
      machopic_output_function_base_name (file);
      putc ('\n', file);
    }
#endif
  else if (HAVE_AS_GOTOFF_IN_DATA)
    fprintf (file, ASM_LONG "%s%d@GOTOFF\n", LPREFIX, value);
  else
    asm_fprintf (file, ASM_LONG "%U%s+[.-%s%d]\n",
		 GOT_SYMBOL_NAME, LPREFIX, value);
}

/* Generate either "mov $0, reg" or "xor reg, reg", as appropriate
   for the target.  */

void
ix86_expand_clear (rtx dest)
{
  rtx tmp;

  /* We play register width games, which are only valid after reload.  */
  gcc_assert (reload_completed);

  /* Avoid HImode and its attendant prefix byte.  */
  if (GET_MODE_SIZE (GET_MODE (dest)) < 4)
    dest = gen_rtx_REG (SImode, REGNO (dest));
  tmp = gen_rtx_SET (dest, const0_rtx);

  if (!TARGET_USE_MOV0 || optimize_insn_for_size_p ())
    {
      rtx clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
      tmp = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, tmp, clob));
    }

  emit_insn (tmp);
}

void
ix86_expand_move (machine_mode mode, rtx operands[])
{
  rtx op0, op1;
  rtx tmp, addend = NULL_RTX;
  enum tls_model model;

  op0 = operands[0];
  op1 = operands[1];

  switch (GET_CODE (op1))
    {
    case CONST:
      tmp = XEXP (op1, 0);

      if (GET_CODE (tmp) != PLUS
	  || GET_CODE (XEXP (tmp, 0)) != SYMBOL_REF)
	break;

      op1 = XEXP (tmp, 0);
      addend = XEXP (tmp, 1);
      /* FALLTHRU */

    case SYMBOL_REF:
      model = SYMBOL_REF_TLS_MODEL (op1);

      if (model)
	op1 = legitimize_tls_address (op1, model, true);
      else if (ix86_force_load_from_GOT_p (op1))
	{
	  /* Load the external function address via GOT slot to avoid PLT.  */
	  op1 = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, op1),
				(TARGET_64BIT
				 ? UNSPEC_GOTPCREL
				 : UNSPEC_GOT));
	  op1 = gen_rtx_CONST (Pmode, op1);
	  op1 = gen_const_mem (Pmode, op1);
	  set_mem_alias_set (op1, ix86_GOT_alias_set ());
	}
      else
	{
	  tmp = legitimize_pe_coff_symbol (op1, addend != NULL_RTX);
	  if (tmp)
	    {
	      op1 = tmp;
	      if (!addend)
		break;
	    }
	  else
	    {
	      op1 = operands[1];
	      break;
	    }
	}

      if (addend)
	{
	  op1 = force_operand (op1, NULL_RTX);
	  op1 = expand_simple_binop (Pmode, PLUS, op1, addend,
				     op0, 1, OPTAB_DIRECT);
	}
      else
	op1 = force_operand (op1, op0);

      if (op1 == op0)
	return;

      op1 = convert_to_mode (mode, op1, 1);

    default:
      break;
    }

  if ((flag_pic || MACHOPIC_INDIRECT)
      && symbolic_operand (op1, mode))
    {
      if (TARGET_MACHO && !TARGET_64BIT)
	{
#if TARGET_MACHO
	  /* dynamic-no-pic */
	  if (MACHOPIC_INDIRECT)
	    {
	      rtx temp = (op0 && REG_P (op0) && mode == Pmode)
			 ? op0 : gen_reg_rtx (Pmode);
	      op1 = machopic_indirect_data_reference (op1, temp);
	      if (MACHOPIC_PURE)
		op1 = machopic_legitimize_pic_address (op1, mode,
						       temp == op1 ? 0 : temp);
	    }
	  if (op0 != op1 && GET_CODE (op0) != MEM)
	    {
	      rtx insn = gen_rtx_SET (op0, op1);
	      emit_insn (insn);
	      return;
	    }
	  if (GET_CODE (op0) == MEM)
	    op1 = force_reg (Pmode, op1);
	  else
	    {
	      rtx temp = op0;
	      if (GET_CODE (temp) != REG)
		temp = gen_reg_rtx (Pmode);
	      temp = legitimize_pic_address (op1, temp);
	      if (temp == op0)
	    return;
	      op1 = temp;
	    }
      /* dynamic-no-pic */
#endif
	}
      else
	{
	  if (MEM_P (op0))
	    op1 = force_reg (mode, op1);
	  else if (!(TARGET_64BIT && x86_64_movabs_operand (op1, DImode)))
	    {
	      rtx reg = can_create_pseudo_p () ? NULL_RTX : op0;
	      op1 = legitimize_pic_address (op1, reg);
	      if (op0 == op1)
		return;
	      op1 = convert_to_mode (mode, op1, 1);
	    }
	}
    }
  else
    {
      if (MEM_P (op0)
	  && (PUSH_ROUNDING (GET_MODE_SIZE (mode)) != GET_MODE_SIZE (mode)
	      || !push_operand (op0, mode))
	  && MEM_P (op1))
	op1 = force_reg (mode, op1);

      if (push_operand (op0, mode)
	  && ! general_no_elim_operand (op1, mode))
	op1 = copy_to_mode_reg (mode, op1);

      /* Force large constants in 64bit compilation into register
	 to get them CSEed.  */
      if (can_create_pseudo_p ()
	  && (mode == DImode) && TARGET_64BIT
	  && immediate_operand (op1, mode)
	  && !x86_64_zext_immediate_operand (op1, VOIDmode)
	  && !register_operand (op0, mode)
	  && optimize)
	op1 = copy_to_mode_reg (mode, op1);

      if (can_create_pseudo_p ()
	  && CONST_DOUBLE_P (op1))
	{
	  /* If we are loading a floating point constant to a register,
	     force the value to memory now, since we'll get better code
	     out the back end.  */

	  op1 = validize_mem (force_const_mem (mode, op1));
	  if (!register_operand (op0, mode))
	    {
	      rtx temp = gen_reg_rtx (mode);
	      emit_insn (gen_rtx_SET (temp, op1));
	      emit_move_insn (op0, temp);
	      return;
	    }
	}
    }

  emit_insn (gen_rtx_SET (op0, op1));
}

void
ix86_expand_vector_move (machine_mode mode, rtx operands[])
{
  rtx op0 = operands[0], op1 = operands[1];
  /* Use GET_MODE_BITSIZE instead of GET_MODE_ALIGNMENT for IA MCU
     psABI since the biggest alignment is 4 byte for IA MCU psABI.  */
  unsigned int align = (TARGET_IAMCU
			? GET_MODE_BITSIZE (mode)
			: GET_MODE_ALIGNMENT (mode));

  if (push_operand (op0, VOIDmode))
    op0 = emit_move_resolve_push (mode, op0);

  /* Force constants other than zero into memory.  We do not know how
     the instructions used to build constants modify the upper 64 bits
     of the register, once we have that information we may be able
     to handle some of them more efficiently.  */
  if (can_create_pseudo_p ()
      && (CONSTANT_P (op1)
	  || (SUBREG_P (op1)
	      && CONSTANT_P (SUBREG_REG (op1))))
      && ((register_operand (op0, mode)
	   && !standard_sse_constant_p (op1, mode))
	  /* ix86_expand_vector_move_misalign() does not like constants.  */
	  || (SSE_REG_MODE_P (mode)
	      && MEM_P (op0)
	      && MEM_ALIGN (op0) < align)))
    {
      if (SUBREG_P (op1))
	{
	  machine_mode imode = GET_MODE (SUBREG_REG (op1));
	  rtx r = force_const_mem (imode, SUBREG_REG (op1));
	  if (r)
	    r = validize_mem (r);
	  else
	    r = force_reg (imode, SUBREG_REG (op1));
	  op1 = simplify_gen_subreg (mode, r, imode, SUBREG_BYTE (op1));
	}
      else
	op1 = validize_mem (force_const_mem (mode, op1));
    }

  /* We need to check memory alignment for SSE mode since attribute
     can make operands unaligned.  */
  if (can_create_pseudo_p ()
      && SSE_REG_MODE_P (mode)
      && ((MEM_P (op0) && (MEM_ALIGN (op0) < align))
	  || (MEM_P (op1) && (MEM_ALIGN (op1) < align))))
    {
      rtx tmp[2];

      /* ix86_expand_vector_move_misalign() does not like both
	 arguments in memory.  */
      if (!register_operand (op0, mode)
	  && !register_operand (op1, mode))
	op1 = force_reg (mode, op1);

      tmp[0] = op0; tmp[1] = op1;
      ix86_expand_vector_move_misalign (mode, tmp);
      return;
    }

  /* Make operand1 a register if it isn't already.  */
  if (can_create_pseudo_p ()
      && !register_operand (op0, mode)
      && !register_operand (op1, mode))
    {
      emit_move_insn (op0, force_reg (GET_MODE (op0), op1));
      return;
    }

  emit_insn (gen_rtx_SET (op0, op1));
}

/* Split 32-byte AVX unaligned load and store if needed.  */

static void
ix86_avx256_split_vector_move_misalign (rtx op0, rtx op1)
{
  rtx m;
  rtx (*extract) (rtx, rtx, rtx);
  machine_mode mode;

  if ((MEM_P (op1) && !TARGET_AVX256_SPLIT_UNALIGNED_LOAD)
      || (MEM_P (op0) && !TARGET_AVX256_SPLIT_UNALIGNED_STORE))
    {
      emit_insn (gen_rtx_SET (op0, op1));
      return;
    }

  rtx orig_op0 = NULL_RTX;
  mode = GET_MODE (op0);
  switch (GET_MODE_CLASS (mode))
    {
    case MODE_VECTOR_INT:
    case MODE_INT:
      if (mode != V32QImode)
	{
	  if (!MEM_P (op0))
	    {
	      orig_op0 = op0;
	      op0 = gen_reg_rtx (V32QImode);
	    }
	  else
	    op0 = gen_lowpart (V32QImode, op0);
	  op1 = gen_lowpart (V32QImode, op1);
	  mode = V32QImode;
	}
      break;
    case MODE_VECTOR_FLOAT:
      break;
    default:
      gcc_unreachable ();
    }

  switch (mode)
    {
    default:
      gcc_unreachable ();
    case E_V32QImode:
      extract = gen_avx_vextractf128v32qi;
      mode = V16QImode;
      break;
    case E_V8SFmode:
      extract = gen_avx_vextractf128v8sf;
      mode = V4SFmode;
      break;
    case E_V4DFmode:
      extract = gen_avx_vextractf128v4df;
      mode = V2DFmode;
      break;
    }

  if (MEM_P (op1))
    {
      rtx r = gen_reg_rtx (mode);
      m = adjust_address (op1, mode, 0);
      emit_move_insn (r, m);
      m = adjust_address (op1, mode, 16);
      r = gen_rtx_VEC_CONCAT (GET_MODE (op0), r, m);
      emit_move_insn (op0, r);
    }
  else if (MEM_P (op0))
    {
      m = adjust_address (op0, mode, 0);
      emit_insn (extract (m, op1, const0_rtx));
      m = adjust_address (op0, mode, 16);
      emit_insn (extract (m, copy_rtx (op1), const1_rtx));
    }
  else
    gcc_unreachable ();

  if (orig_op0)
    emit_move_insn (orig_op0, gen_lowpart (GET_MODE (orig_op0), op0));
}

/* Implement the movmisalign patterns for SSE.  Non-SSE modes go
   straight to ix86_expand_vector_move.  */
/* Code generation for scalar reg-reg moves of single and double precision data:
     if (x86_sse_partial_reg_dependency == true | x86_sse_split_regs == true)
       movaps reg, reg
     else
       movss reg, reg
     if (x86_sse_partial_reg_dependency == true)
       movapd reg, reg
     else
       movsd reg, reg

   Code generation for scalar loads of double precision data:
     if (x86_sse_split_regs == true)
       movlpd mem, reg      (gas syntax)
     else
       movsd mem, reg

   Code generation for unaligned packed loads of single precision data
   (x86_sse_unaligned_move_optimal overrides x86_sse_partial_reg_dependency):
     if (x86_sse_unaligned_move_optimal)
       movups mem, reg

     if (x86_sse_partial_reg_dependency == true)
       {
         xorps  reg, reg
         movlps mem, reg
         movhps mem+8, reg
       }
     else
       {
         movlps mem, reg
         movhps mem+8, reg
       }

   Code generation for unaligned packed loads of double precision data
   (x86_sse_unaligned_move_optimal overrides x86_sse_split_regs):
     if (x86_sse_unaligned_move_optimal)
       movupd mem, reg

     if (x86_sse_split_regs == true)
       {
         movlpd mem, reg
         movhpd mem+8, reg
       }
     else
       {
         movsd  mem, reg
         movhpd mem+8, reg
       }
 */

void
ix86_expand_vector_move_misalign (machine_mode mode, rtx operands[])
{
  rtx op0, op1, m;

  op0 = operands[0];
  op1 = operands[1];

  /* Use unaligned load/store for AVX512 or when optimizing for size.  */
  if (GET_MODE_SIZE (mode) == 64 || optimize_insn_for_size_p ())
    {
      emit_insn (gen_rtx_SET (op0, op1));
      return;
    }

  if (TARGET_AVX)
    {
      if (GET_MODE_SIZE (mode) == 32)
	ix86_avx256_split_vector_move_misalign (op0, op1);
      else
	/* Always use 128-bit mov<mode>_internal pattern for AVX.  */
	emit_insn (gen_rtx_SET (op0, op1));
      return;
    }

  if (TARGET_SSE_UNALIGNED_LOAD_OPTIMAL
      || TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL)
    {
      emit_insn (gen_rtx_SET (op0, op1));
      return;
    }

  /* ??? If we have typed data, then it would appear that using
     movdqu is the only way to get unaligned data loaded with
     integer type.  */
  if (TARGET_SSE2 && GET_MODE_CLASS (mode) == MODE_VECTOR_INT)
    {
      emit_insn (gen_rtx_SET (op0, op1));
      return;
    }

  if (MEM_P (op1))
    {
      if (TARGET_SSE2 && mode == V2DFmode)
        {
          rtx zero;

	  /* When SSE registers are split into halves, we can avoid
	     writing to the top half twice.  */
	  if (TARGET_SSE_SPLIT_REGS)
	    {
	      emit_clobber (op0);
	      zero = op0;
	    }
	  else
	    {
	      /* ??? Not sure about the best option for the Intel chips.
		 The following would seem to satisfy; the register is
		 entirely cleared, breaking the dependency chain.  We
		 then store to the upper half, with a dependency depth
		 of one.  A rumor has it that Intel recommends two movsd
		 followed by an unpacklpd, but this is unconfirmed.  And
		 given that the dependency depth of the unpacklpd would
		 still be one, I'm not sure why this would be better.  */
	      zero = CONST0_RTX (V2DFmode);
	    }

	  m = adjust_address (op1, DFmode, 0);
	  emit_insn (gen_sse2_loadlpd (op0, zero, m));
	  m = adjust_address (op1, DFmode, 8);
	  emit_insn (gen_sse2_loadhpd (op0, op0, m));
	}
      else
        {
	  rtx t;

	  if (mode != V4SFmode)
	    t = gen_reg_rtx (V4SFmode);
	  else
	    t = op0;
	    
	  if (TARGET_SSE_PARTIAL_REG_DEPENDENCY)
	    emit_move_insn (t, CONST0_RTX (V4SFmode));
	  else
	    emit_clobber (t);

	  m = adjust_address (op1, V2SFmode, 0);
	  emit_insn (gen_sse_loadlps (t, t, m));
	  m = adjust_address (op1, V2SFmode, 8);
	  emit_insn (gen_sse_loadhps (t, t, m));
	  if (mode != V4SFmode)
	    emit_move_insn (op0, gen_lowpart (mode, t));
	}
    }
  else if (MEM_P (op0))
    {
      if (TARGET_SSE2 && mode == V2DFmode)
	{
	  m = adjust_address (op0, DFmode, 0);
	  emit_insn (gen_sse2_storelpd (m, op1));
	  m = adjust_address (op0, DFmode, 8);
	  emit_insn (gen_sse2_storehpd (m, op1));
	}
      else
	{
	  if (mode != V4SFmode)
	    op1 = gen_lowpart (V4SFmode, op1);

	  m = adjust_address (op0, V2SFmode, 0);
	  emit_insn (gen_sse_storelps (m, op1));
	  m = adjust_address (op0, V2SFmode, 8);
	  emit_insn (gen_sse_storehps (m, copy_rtx (op1)));
	}
    }
  else
    gcc_unreachable ();
}

/* Helper function of ix86_fixup_binary_operands to canonicalize
   operand order.  Returns true if the operands should be swapped.  */

static bool
ix86_swap_binary_operands_p (enum rtx_code code, machine_mode mode,
			     rtx operands[])
{
  rtx dst = operands[0];
  rtx src1 = operands[1];
  rtx src2 = operands[2];

  /* If the operation is not commutative, we can't do anything.  */
  if (GET_RTX_CLASS (code) != RTX_COMM_ARITH
      && GET_RTX_CLASS (code) != RTX_COMM_COMPARE)
    return false;

  /* Highest priority is that src1 should match dst.  */
  if (rtx_equal_p (dst, src1))
    return false;
  if (rtx_equal_p (dst, src2))
    return true;

  /* Next highest priority is that immediate constants come second.  */
  if (immediate_operand (src2, mode))
    return false;
  if (immediate_operand (src1, mode))
    return true;

  /* Lowest priority is that memory references should come second.  */
  if (MEM_P (src2))
    return false;
  if (MEM_P (src1))
    return true;

  return false;
}


/* Fix up OPERANDS to satisfy ix86_binary_operator_ok.  Return the
   destination to use for the operation.  If different from the true
   destination in operands[0], a copy operation will be required.  */

rtx
ix86_fixup_binary_operands (enum rtx_code code, machine_mode mode,
			    rtx operands[])
{
  rtx dst = operands[0];
  rtx src1 = operands[1];
  rtx src2 = operands[2];

  /* Canonicalize operand order.  */
  if (ix86_swap_binary_operands_p (code, mode, operands))
    {
      /* It is invalid to swap operands of different modes.  */
      gcc_assert (GET_MODE (src1) == GET_MODE (src2));

      std::swap (src1, src2);
    }

  /* Both source operands cannot be in memory.  */
  if (MEM_P (src1) && MEM_P (src2))
    {
      /* Optimization: Only read from memory once.  */
      if (rtx_equal_p (src1, src2))
	{
	  src2 = force_reg (mode, src2);
	  src1 = src2;
	}
      else if (rtx_equal_p (dst, src1))
	src2 = force_reg (mode, src2);
      else
	src1 = force_reg (mode, src1);
    }

  /* If the destination is memory, and we do not have matching source
     operands, do things in registers.  */
  if (MEM_P (dst) && !rtx_equal_p (dst, src1))
    dst = gen_reg_rtx (mode);

  /* Source 1 cannot be a constant.  */
  if (CONSTANT_P (src1))
    src1 = force_reg (mode, src1);

  /* Source 1 cannot be a non-matching memory.  */
  if (MEM_P (src1) && !rtx_equal_p (dst, src1))
    src1 = force_reg (mode, src1);

  /* Improve address combine.  */
  if (code == PLUS
      && GET_MODE_CLASS (mode) == MODE_INT
      && MEM_P (src2))
    src2 = force_reg (mode, src2);

  operands[1] = src1;
  operands[2] = src2;
  return dst;
}

/* Similarly, but assume that the destination has already been
   set up properly.  */

void
ix86_fixup_binary_operands_no_copy (enum rtx_code code,
				    machine_mode mode, rtx operands[])
{
  rtx dst = ix86_fixup_binary_operands (code, mode, operands);
  gcc_assert (dst == operands[0]);
}

/* Attempt to expand a binary operator.  Make the expansion closer to the
   actual machine, then just general_operand, which will allow 3 separate
   memory references (one output, two input) in a single insn.  */

void
ix86_expand_binary_operator (enum rtx_code code, machine_mode mode,
			     rtx operands[])
{
  rtx src1, src2, dst, op, clob;

  dst = ix86_fixup_binary_operands (code, mode, operands);
  src1 = operands[1];
  src2 = operands[2];

 /* Emit the instruction.  */

  op = gen_rtx_SET (dst, gen_rtx_fmt_ee (code, mode, src1, src2));

  if (reload_completed
      && code == PLUS
      && !rtx_equal_p (dst, src1))
    {
      /* This is going to be an LEA; avoid splitting it later.  */
      emit_insn (op);
    }
  else
    {
      clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
      emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, op, clob)));
    }

  /* Fix up the destination if needed.  */
  if (dst != operands[0])
    emit_move_insn (operands[0], dst);
}

/* Expand vector logical operation CODE (AND, IOR, XOR) in MODE with
   the given OPERANDS.  */

void
ix86_expand_vector_logical_operator (enum rtx_code code, machine_mode mode,
				     rtx operands[])
{
  rtx op1 = NULL_RTX, op2 = NULL_RTX;
  if (SUBREG_P (operands[1]))
    {
      op1 = operands[1];
      op2 = operands[2];
    }
  else if (SUBREG_P (operands[2]))
    {
      op1 = operands[2];
      op2 = operands[1];
    }
  /* Optimize (__m128i) d | (__m128i) e and similar code
     when d and e are float vectors into float vector logical
     insn.  In C/C++ without using intrinsics there is no other way
     to express vector logical operation on float vectors than
     to cast them temporarily to integer vectors.  */
  if (op1
      && !TARGET_SSE_PACKED_SINGLE_INSN_OPTIMAL
      && (SUBREG_P (op2) || GET_CODE (op2) == CONST_VECTOR)
      && GET_MODE_CLASS (GET_MODE (SUBREG_REG (op1))) == MODE_VECTOR_FLOAT
      && GET_MODE_SIZE (GET_MODE (SUBREG_REG (op1))) == GET_MODE_SIZE (mode)
      && SUBREG_BYTE (op1) == 0
      && (GET_CODE (op2) == CONST_VECTOR
	  || (GET_MODE (SUBREG_REG (op1)) == GET_MODE (SUBREG_REG (op2))
	      && SUBREG_BYTE (op2) == 0))
      && can_create_pseudo_p ())
    {
      rtx dst;
      switch (GET_MODE (SUBREG_REG (op1)))
	{
	case E_V4SFmode:
	case E_V8SFmode:
	case E_V16SFmode:
	case E_V2DFmode:
	case E_V4DFmode:
	case E_V8DFmode:
	  dst = gen_reg_rtx (GET_MODE (SUBREG_REG (op1)));
	  if (GET_CODE (op2) == CONST_VECTOR)
	    {
	      op2 = gen_lowpart (GET_MODE (dst), op2);
	      op2 = force_reg (GET_MODE (dst), op2);
	    }
	  else
	    {
	      op1 = operands[1];
	      op2 = SUBREG_REG (operands[2]);
	      if (!vector_operand (op2, GET_MODE (dst)))
		op2 = force_reg (GET_MODE (dst), op2);
	    }
	  op1 = SUBREG_REG (op1);
	  if (!vector_operand (op1, GET_MODE (dst)))
	    op1 = force_reg (GET_MODE (dst), op1);
	  emit_insn (gen_rtx_SET (dst,
				  gen_rtx_fmt_ee (code, GET_MODE (dst),
						  op1, op2)));
	  emit_move_insn (operands[0], gen_lowpart (mode, dst));
	  return;
	default:
	  break;
	}
    }
  if (!vector_operand (operands[1], mode))
    operands[1] = force_reg (mode, operands[1]);
  if (!vector_operand (operands[2], mode))
    operands[2] = force_reg (mode, operands[2]);
  ix86_fixup_binary_operands_no_copy (code, mode, operands);
  emit_insn (gen_rtx_SET (operands[0],
			  gen_rtx_fmt_ee (code, mode, operands[1],
					  operands[2])));
}

/* Return TRUE or FALSE depending on whether the binary operator meets the
   appropriate constraints.  */

bool
ix86_binary_operator_ok (enum rtx_code code, machine_mode mode,
			 rtx operands[3])
{
  rtx dst = operands[0];
  rtx src1 = operands[1];
  rtx src2 = operands[2];

  /* Both source operands cannot be in memory.  */
  if (MEM_P (src1) && MEM_P (src2))
    return false;

  /* Canonicalize operand order for commutative operators.  */
  if (ix86_swap_binary_operands_p (code, mode, operands))
    std::swap (src1, src2);

  /* If the destination is memory, we must have a matching source operand.  */
  if (MEM_P (dst) && !rtx_equal_p (dst, src1))
    return false;

  /* Source 1 cannot be a constant.  */
  if (CONSTANT_P (src1))
    return false;

  /* Source 1 cannot be a non-matching memory.  */
  if (MEM_P (src1) && !rtx_equal_p (dst, src1))
    /* Support "andhi/andsi/anddi" as a zero-extending move.  */
    return (code == AND
	    && (mode == HImode
		|| mode == SImode
		|| (TARGET_64BIT && mode == DImode))
	    && satisfies_constraint_L (src2));

  return true;
}

/* Attempt to expand a unary operator.  Make the expansion closer to the
   actual machine, then just general_operand, which will allow 2 separate
   memory references (one output, one input) in a single insn.  */

void
ix86_expand_unary_operator (enum rtx_code code, machine_mode mode,
			    rtx operands[])
{
  bool matching_memory = false;
  rtx src, dst, op, clob;

  dst = operands[0];
  src = operands[1];

  /* If the destination is memory, and we do not have matching source
     operands, do things in registers.  */
  if (MEM_P (dst))
    {
      if (rtx_equal_p (dst, src))
	matching_memory = true;
      else
	dst = gen_reg_rtx (mode);
    }

  /* When source operand is memory, destination must match.  */
  if (MEM_P (src) && !matching_memory)
    src = force_reg (mode, src);

  /* Emit the instruction.  */

  op = gen_rtx_SET (dst, gen_rtx_fmt_e (code, mode, src));

  if (code == NOT)
    emit_insn (op);
  else
    {
      clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
      emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, op, clob)));
    }

  /* Fix up the destination if needed.  */
  if (dst != operands[0])
    emit_move_insn (operands[0], dst);
}

/* Split 32bit/64bit divmod with 8bit unsigned divmod if dividend and
   divisor are within the range [0-255].  */

void
ix86_split_idivmod (machine_mode mode, rtx operands[],
		    bool signed_p)
{
  rtx_code_label *end_label, *qimode_label;
  rtx div, mod;
  rtx_insn *insn;
  rtx scratch, tmp0, tmp1, tmp2;
  rtx (*gen_divmod4_1) (rtx, rtx, rtx, rtx);
  rtx (*gen_zero_extend) (rtx, rtx);
  rtx (*gen_test_ccno_1) (rtx, rtx);

  switch (mode)
    {
    case E_SImode:
      if (GET_MODE (operands[0]) == SImode)
	{
	  if (GET_MODE (operands[1]) == SImode)
	    gen_divmod4_1 = signed_p ? gen_divmodsi4_1 : gen_udivmodsi4_1;
	  else
	    gen_divmod4_1
	      = signed_p ? gen_divmodsi4_zext_2 : gen_udivmodsi4_zext_2;
	  gen_zero_extend = gen_zero_extendqisi2;
	}
      else
	{
	  gen_divmod4_1
	    = signed_p ? gen_divmodsi4_zext_1 : gen_udivmodsi4_zext_1;
	  gen_zero_extend = gen_zero_extendqidi2;
	}
      gen_test_ccno_1 = gen_testsi_ccno_1;
      break;
    case E_DImode:
      gen_divmod4_1 = signed_p ? gen_divmoddi4_1 : gen_udivmoddi4_1;
      gen_test_ccno_1 = gen_testdi_ccno_1;
      gen_zero_extend = gen_zero_extendqidi2;
      break;
    default:
      gcc_unreachable ();
    }

  end_label = gen_label_rtx ();
  qimode_label = gen_label_rtx ();

  scratch = gen_reg_rtx (mode);

  /* Use 8bit unsigned divimod if dividend and divisor are within
     the range [0-255].  */
  emit_move_insn (scratch, operands[2]);
  scratch = expand_simple_binop (mode, IOR, scratch, operands[3],
				 scratch, 1, OPTAB_DIRECT);
  emit_insn (gen_test_ccno_1 (scratch, GEN_INT (-0x100)));
  tmp0 = gen_rtx_REG (CCNOmode, FLAGS_REG);
  tmp0 = gen_rtx_EQ (VOIDmode, tmp0, const0_rtx);
  tmp0 = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp0,
			       gen_rtx_LABEL_REF (VOIDmode, qimode_label),
			       pc_rtx);
  insn = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp0));
  predict_jump (REG_BR_PROB_BASE * 50 / 100);
  JUMP_LABEL (insn) = qimode_label;

  /* Generate original signed/unsigned divimod.  */
  div = gen_divmod4_1 (operands[0], operands[1],
		       operands[2], operands[3]);
  emit_insn (div);

  /* Branch to the end.  */
  emit_jump_insn (gen_jump (end_label));
  emit_barrier ();

  /* Generate 8bit unsigned divide.  */
  emit_label (qimode_label);
  /* Don't use operands[0] for result of 8bit divide since not all
     registers support QImode ZERO_EXTRACT.  */
  tmp0 = lowpart_subreg (HImode, scratch, mode);
  tmp1 = lowpart_subreg (HImode, operands[2], mode);
  tmp2 = lowpart_subreg (QImode, operands[3], mode);
  emit_insn (gen_udivmodhiqi3 (tmp0, tmp1, tmp2));

  if (signed_p)
    {
      div = gen_rtx_DIV (mode, operands[2], operands[3]);
      mod = gen_rtx_MOD (mode, operands[2], operands[3]);
    }
  else
    {
      div = gen_rtx_UDIV (mode, operands[2], operands[3]);
      mod = gen_rtx_UMOD (mode, operands[2], operands[3]);
    }
  if (mode == SImode)
    {
      if (GET_MODE (operands[0]) != SImode)
	div = gen_rtx_ZERO_EXTEND (DImode, div);
      if (GET_MODE (operands[1]) != SImode)
	mod = gen_rtx_ZERO_EXTEND (DImode, mod);
    }

  /* Extract remainder from AH.  */
  tmp1 = gen_rtx_ZERO_EXTRACT (GET_MODE (operands[1]),
			       tmp0, GEN_INT (8), GEN_INT (8));
  if (REG_P (operands[1]))
    insn = emit_move_insn (operands[1], tmp1);
  else
    {
      /* Need a new scratch register since the old one has result
	 of 8bit divide.  */
      scratch = gen_reg_rtx (GET_MODE (operands[1]));
      emit_move_insn (scratch, tmp1);
      insn = emit_move_insn (operands[1], scratch);
    }
  set_unique_reg_note (insn, REG_EQUAL, mod);

  /* Zero extend quotient from AL.  */
  tmp1 = gen_lowpart (QImode, tmp0);
  insn = emit_insn (gen_zero_extend (operands[0], tmp1));
  set_unique_reg_note (insn, REG_EQUAL, div);

  emit_label (end_label);
}

#define LEA_MAX_STALL (3)
#define LEA_SEARCH_THRESHOLD (LEA_MAX_STALL << 1)

/* Increase given DISTANCE in half-cycles according to
   dependencies between PREV and NEXT instructions.
   Add 1 half-cycle if there is no dependency and
   go to next cycle if there is some dependecy.  */

static unsigned int
increase_distance (rtx_insn *prev, rtx_insn *next, unsigned int distance)
{
  df_ref def, use;

  if (!prev || !next)
    return distance + (distance & 1) + 2;

  if (!DF_INSN_USES (next) || !DF_INSN_DEFS (prev))
    return distance + 1;

  FOR_EACH_INSN_USE (use, next)
    FOR_EACH_INSN_DEF (def, prev)
      if (!DF_REF_IS_ARTIFICIAL (def)
	  && DF_REF_REGNO (use) == DF_REF_REGNO (def))
	return distance + (distance & 1) + 2;

  return distance + 1;
}

/* Function checks if instruction INSN defines register number
   REGNO1 or REGNO2.  */

static bool
insn_defines_reg (unsigned int regno1, unsigned int regno2,
		  rtx_insn *insn)
{
  df_ref def;

  FOR_EACH_INSN_DEF (def, insn)
    if (DF_REF_REG_DEF_P (def)
	&& !DF_REF_IS_ARTIFICIAL (def)
	&& (regno1 == DF_REF_REGNO (def)
	    || regno2 == DF_REF_REGNO (def)))
      return true;

  return false;
}

/* Function checks if instruction INSN uses register number
   REGNO as a part of address expression.  */

static bool
insn_uses_reg_mem (unsigned int regno, rtx insn)
{
  df_ref use;

  FOR_EACH_INSN_USE (use, insn)
    if (DF_REF_REG_MEM_P (use) && regno == DF_REF_REGNO (use))
      return true;

  return false;
}

/* Search backward for non-agu definition of register number REGNO1
   or register number REGNO2 in basic block starting from instruction
   START up to head of basic block or instruction INSN.

   Function puts true value into *FOUND var if definition was found
   and false otherwise.

   Distance in half-cycles between START and found instruction or head
   of BB is added to DISTANCE and returned.  */

static int
distance_non_agu_define_in_bb (unsigned int regno1, unsigned int regno2,
			       rtx_insn *insn, int distance,
			       rtx_insn *start, bool *found)
{
  basic_block bb = start ? BLOCK_FOR_INSN (start) : NULL;
  rtx_insn *prev = start;
  rtx_insn *next = NULL;

  *found = false;

  while (prev
	 && prev != insn
	 && distance < LEA_SEARCH_THRESHOLD)
    {
      if (NONDEBUG_INSN_P (prev) && NONJUMP_INSN_P (prev))
	{
	  distance = increase_distance (prev, next, distance);
	  if (insn_defines_reg (regno1, regno2, prev))
	    {
	      if (recog_memoized (prev) < 0
		  || get_attr_type (prev) != TYPE_LEA)
		{
		  *found = true;
		  return distance;
		}
	    }

	  next = prev;
	}
      if (prev == BB_HEAD (bb))
	break;

      prev = PREV_INSN (prev);
    }

  return distance;
}

/* Search backward for non-agu definition of register number REGNO1
   or register number REGNO2 in INSN's basic block until
   1. Pass LEA_SEARCH_THRESHOLD instructions, or
   2. Reach neighbor BBs boundary, or
   3. Reach agu definition.
   Returns the distance between the non-agu definition point and INSN.
   If no definition point, returns -1.  */

static int
distance_non_agu_define (unsigned int regno1, unsigned int regno2,
			 rtx_insn *insn)
{
  basic_block bb = BLOCK_FOR_INSN (insn);
  int distance = 0;
  bool found = false;

  if (insn != BB_HEAD (bb))
    distance = distance_non_agu_define_in_bb (regno1, regno2, insn,
					      distance, PREV_INSN (insn),
					      &found);

  if (!found && distance < LEA_SEARCH_THRESHOLD)
    {
      edge e;
      edge_iterator ei;
      bool simple_loop = false;

      FOR_EACH_EDGE (e, ei, bb->preds)
	if (e->src == bb)
	  {
	    simple_loop = true;
	    break;
	  }

      if (simple_loop)
	distance = distance_non_agu_define_in_bb (regno1, regno2,
						  insn, distance,
						  BB_END (bb), &found);
      else
	{
	  int shortest_dist = -1;
	  bool found_in_bb = false;

	  FOR_EACH_EDGE (e, ei, bb->preds)
	    {
	      int bb_dist
		= distance_non_agu_define_in_bb (regno1, regno2,
						 insn, distance,
						 BB_END (e->src),
						 &found_in_bb);
	      if (found_in_bb)
		{
		  if (shortest_dist < 0)
		    shortest_dist = bb_dist;
		  else if (bb_dist > 0)
		    shortest_dist = MIN (bb_dist, shortest_dist);

		  found = true;
		}
	    }

	  distance = shortest_dist;
	}
    }

  /* get_attr_type may modify recog data.  We want to make sure
     that recog data is valid for instruction INSN, on which
     distance_non_agu_define is called.  INSN is unchanged here.  */
  extract_insn_cached (insn);

  if (!found)
    return -1;

  return distance >> 1;
}

/* Return the distance in half-cycles between INSN and the next
   insn that uses register number REGNO in memory address added
   to DISTANCE.  Return -1 if REGNO0 is set.

   Put true value into *FOUND if register usage was found and
   false otherwise.
   Put true value into *REDEFINED if register redefinition was
   found and false otherwise.  */

static int
distance_agu_use_in_bb (unsigned int regno,
			rtx_insn *insn, int distance, rtx_insn *start,
			bool *found, bool *redefined)
{
  basic_block bb = NULL;
  rtx_insn *next = start;
  rtx_insn *prev = NULL;

  *found = false;
  *redefined = false;

  if (start != NULL_RTX)
    {
      bb = BLOCK_FOR_INSN (start);
      if (start != BB_HEAD (bb))
	/* If insn and start belong to the same bb, set prev to insn,
	   so the call to increase_distance will increase the distance
	   between insns by 1.  */
	prev = insn;
    }

  while (next
	 && next != insn
	 && distance < LEA_SEARCH_THRESHOLD)
    {
      if (NONDEBUG_INSN_P (next) && NONJUMP_INSN_P (next))
	{
	  distance = increase_distance(prev, next, distance);
	  if (insn_uses_reg_mem (regno, next))
	    {
	      /* Return DISTANCE if OP0 is used in memory
		 address in NEXT.  */
	      *found = true;
	      return distance;
	    }

	  if (insn_defines_reg (regno, INVALID_REGNUM, next))
	    {
	      /* Return -1 if OP0 is set in NEXT.  */
	      *redefined = true;
	      return -1;
	    }

	  prev = next;
	}

      if (next == BB_END (bb))
	break;

      next = NEXT_INSN (next);
    }

  return distance;
}

/* Return the distance between INSN and the next insn that uses
   register number REGNO0 in memory address.  Return -1 if no such
   a use is found within LEA_SEARCH_THRESHOLD or REGNO0 is set.  */

static int
distance_agu_use (unsigned int regno0, rtx_insn *insn)
{
  basic_block bb = BLOCK_FOR_INSN (insn);
  int distance = 0;
  bool found = false;
  bool redefined = false;

  if (insn != BB_END (bb))
    distance = distance_agu_use_in_bb (regno0, insn, distance,
				       NEXT_INSN (insn),
				       &found, &redefined);

  if (!found && !redefined && distance < LEA_SEARCH_THRESHOLD)
    {
      edge e;
      edge_iterator ei;
      bool simple_loop = false;

      FOR_EACH_EDGE (e, ei, bb->succs)
        if (e->dest == bb)
	  {
	    simple_loop = true;
	    break;
	  }

      if (simple_loop)
	distance = distance_agu_use_in_bb (regno0, insn,
					   distance, BB_HEAD (bb),
					   &found, &redefined);
      else
	{
	  int shortest_dist = -1;
	  bool found_in_bb = false;
	  bool redefined_in_bb = false;

	  FOR_EACH_EDGE (e, ei, bb->succs)
	    {
	      int bb_dist
		= distance_agu_use_in_bb (regno0, insn,
					  distance, BB_HEAD (e->dest),
					  &found_in_bb, &redefined_in_bb);
	      if (found_in_bb)
		{
		  if (shortest_dist < 0)
		    shortest_dist = bb_dist;
		  else if (bb_dist > 0)
		    shortest_dist = MIN (bb_dist, shortest_dist);

		  found = true;
		}
	    }

	  distance = shortest_dist;
	}
    }

  if (!found || redefined)
    return -1;

  return distance >> 1;
}

/* Define this macro to tune LEA priority vs ADD, it take effect when
   there is a dilemma of choicing LEA or ADD
   Negative value: ADD is more preferred than LEA
   Zero: Netrual
   Positive value: LEA is more preferred than ADD*/
#define IX86_LEA_PRIORITY 0

/* Return true if usage of lea INSN has performance advantage
   over a sequence of instructions.  Instructions sequence has
   SPLIT_COST cycles higher latency than lea latency.  */

static bool
ix86_lea_outperforms (rtx_insn *insn, unsigned int regno0, unsigned int regno1,
		      unsigned int regno2, int split_cost, bool has_scale)
{
  int dist_define, dist_use;

  /* For Silvermont if using a 2-source or 3-source LEA for
     non-destructive destination purposes, or due to wanting
     ability to use SCALE, the use of LEA is justified.  */
  if (TARGET_SILVERMONT || TARGET_GOLDMONT || TARGET_GOLDMONT_PLUS
      || TARGET_TREMONT || TARGET_INTEL)
    {
      if (has_scale)
	return true;
      if (split_cost < 1)
	return false;
      if (regno0 == regno1 || regno0 == regno2)
	return false;
      return true;
    }

  dist_define = distance_non_agu_define (regno1, regno2, insn);
  dist_use = distance_agu_use (regno0, insn);

  if (dist_define < 0 || dist_define >= LEA_MAX_STALL)
    {
      /* If there is no non AGU operand definition, no AGU
	 operand usage and split cost is 0 then both lea
	 and non lea variants have same priority.  Currently
	 we prefer lea for 64 bit code and non lea on 32 bit
	 code.  */
      if (dist_use < 0 && split_cost == 0)
	return TARGET_64BIT || IX86_LEA_PRIORITY;
      else
	return true;
    }

  /* With longer definitions distance lea is more preferable.
     Here we change it to take into account splitting cost and
     lea priority.  */
  dist_define += split_cost + IX86_LEA_PRIORITY;

  /* If there is no use in memory addess then we just check
     that split cost exceeds AGU stall.  */
  if (dist_use < 0)
    return dist_define > LEA_MAX_STALL;

  /* If this insn has both backward non-agu dependence and forward
     agu dependence, the one with short distance takes effect.  */
  return dist_define >= dist_use;
}

/* Return true if it is legal to clobber flags by INSN and
   false otherwise.  */

static bool
ix86_ok_to_clobber_flags (rtx_insn *insn)
{
  basic_block bb = BLOCK_FOR_INSN (insn);
  df_ref use;
  bitmap live;

  while (insn)
    {
      if (NONDEBUG_INSN_P (insn))
	{
	  FOR_EACH_INSN_USE (use, insn)
	    if (DF_REF_REG_USE_P (use) && DF_REF_REGNO (use) == FLAGS_REG)
	      return false;

	  if (insn_defines_reg (FLAGS_REG, INVALID_REGNUM, insn))
	    return true;
	}

      if (insn == BB_END (bb))
	break;

      insn = NEXT_INSN (insn);
    }

  live = df_get_live_out(bb);
  return !REGNO_REG_SET_P (live, FLAGS_REG);
}

/* Return true if we need to split op0 = op1 + op2 into a sequence of
   move and add to avoid AGU stalls.  */

bool
ix86_avoid_lea_for_add (rtx_insn *insn, rtx operands[])
{
  unsigned int regno0, regno1, regno2;

  /* Check if we need to optimize.  */
  if (!TARGET_OPT_AGU || optimize_function_for_size_p (cfun))
    return false;

  /* Check it is correct to split here.  */
  if (!ix86_ok_to_clobber_flags(insn))
    return false;

  regno0 = true_regnum (operands[0]);
  regno1 = true_regnum (operands[1]);
  regno2 = true_regnum (operands[2]);

  /* We need to split only adds with non destructive
     destination operand.  */
  if (regno0 == regno1 || regno0 == regno2)
    return false;
  else
    return !ix86_lea_outperforms (insn, regno0, regno1, regno2, 1, false);
}

/* Return true if we should emit lea instruction instead of mov
   instruction.  */

bool
ix86_use_lea_for_mov (rtx_insn *insn, rtx operands[])
{
  unsigned int regno0, regno1;

  /* Check if we need to optimize.  */
  if (!TARGET_OPT_AGU || optimize_function_for_size_p (cfun))
    return false;

  /* Use lea for reg to reg moves only.  */
  if (!REG_P (operands[0]) || !REG_P (operands[1]))
    return false;

  regno0 = true_regnum (operands[0]);
  regno1 = true_regnum (operands[1]);

  return ix86_lea_outperforms (insn, regno0, regno1, INVALID_REGNUM, 0, false);
}

/* Return true if we need to split lea into a sequence of
   instructions to avoid AGU stalls. */

bool
ix86_avoid_lea_for_addr (rtx_insn *insn, rtx operands[])
{
  unsigned int regno0, regno1, regno2;
  int split_cost;
  struct ix86_address parts;
  int ok;

  /* Check we need to optimize.  */
  if (!TARGET_AVOID_LEA_FOR_ADDR || optimize_function_for_size_p (cfun))
    return false;

  /* The "at least two components" test below might not catch simple
     move or zero extension insns if parts.base is non-NULL and parts.disp
     is const0_rtx as the only components in the address, e.g. if the
     register is %rbp or %r13.  As this test is much cheaper and moves or
     zero extensions are the common case, do this check first.  */
  if (REG_P (operands[1])
      || (SImode_address_operand (operands[1], VOIDmode)
	  && REG_P (XEXP (operands[1], 0))))
    return false;

  /* Check if it is OK to split here.  */
  if (!ix86_ok_to_clobber_flags (insn))
    return false;

  ok = ix86_decompose_address (operands[1], &parts);
  gcc_assert (ok);

  /* There should be at least two components in the address.  */
  if ((parts.base != NULL_RTX) + (parts.index != NULL_RTX)
      + (parts.disp != NULL_RTX) + (parts.scale > 1) < 2)
    return false;

  /* We should not split into add if non legitimate pic
     operand is used as displacement. */
  if (parts.disp && flag_pic && !LEGITIMATE_PIC_OPERAND_P (parts.disp))
    return false;

  regno0 = true_regnum (operands[0]) ;
  regno1 = INVALID_REGNUM;
  regno2 = INVALID_REGNUM;

  if (parts.base)
    regno1 = true_regnum (parts.base);
  if (parts.index)
    regno2 = true_regnum (parts.index);

  split_cost = 0;

  /* Compute how many cycles we will add to execution time
     if split lea into a sequence of instructions.  */
  if (parts.base || parts.index)
    {
      /* Have to use mov instruction if non desctructive
	 destination form is used.  */
      if (regno1 != regno0 && regno2 != regno0)
	split_cost += 1;

      /* Have to add index to base if both exist.  */
      if (parts.base && parts.index)
	split_cost += 1;

      /* Have to use shift and adds if scale is 2 or greater.  */
      if (parts.scale > 1)
	{
	  if (regno0 != regno1)
	    split_cost += 1;
	  else if (regno2 == regno0)
	    split_cost += 4;
	  else
	    split_cost += parts.scale;
	}

      /* Have to use add instruction with immediate if
	 disp is non zero.  */
      if (parts.disp && parts.disp != const0_rtx)
	split_cost += 1;

      /* Subtract the price of lea.  */
      split_cost -= 1;
    }

  return !ix86_lea_outperforms (insn, regno0, regno1, regno2, split_cost,
				parts.scale > 1);
}

/* Emit x86 binary operand CODE in mode MODE, where the first operand
   matches destination.  RTX includes clobber of FLAGS_REG.  */

static void
ix86_emit_binop (enum rtx_code code, machine_mode mode,
		 rtx dst, rtx src)
{
  rtx op, clob;

  op = gen_rtx_SET (dst, gen_rtx_fmt_ee (code, mode, dst, src));
  clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
  
  emit_insn (gen_rtx_PARALLEL (VOIDmode, gen_rtvec (2, op, clob)));
}

/* Return true if regno1 def is nearest to the insn.  */

static bool
find_nearest_reg_def (rtx_insn *insn, int regno1, int regno2)
{
  rtx_insn *prev = insn;
  rtx_insn *start = BB_HEAD (BLOCK_FOR_INSN (insn));

  if (insn == start)
    return false;
  while (prev && prev != start)
    {
      if (!INSN_P (prev) || !NONDEBUG_INSN_P (prev))
	{
	  prev = PREV_INSN (prev);
	  continue;
	}
      if (insn_defines_reg (regno1, INVALID_REGNUM, prev))
	return true;
      else if (insn_defines_reg (regno2, INVALID_REGNUM, prev))
	return false;
      prev = PREV_INSN (prev);
    }

  /* None of the regs is defined in the bb.  */
  return false;
}

/* Split lea instructions into a sequence of instructions
   which are executed on ALU to avoid AGU stalls.
   It is assumed that it is allowed to clobber flags register
   at lea position.  */

void
ix86_split_lea_for_addr (rtx_insn *insn, rtx operands[], machine_mode mode)
{
  unsigned int regno0, regno1, regno2;
  struct ix86_address parts;
  rtx target, tmp;
  int ok, adds;

  ok = ix86_decompose_address (operands[1], &parts);
  gcc_assert (ok);

  target = gen_lowpart (mode, operands[0]);

  regno0 = true_regnum (target);
  regno1 = INVALID_REGNUM;
  regno2 = INVALID_REGNUM;

  if (parts.base)
    {
      parts.base = gen_lowpart (mode, parts.base);
      regno1 = true_regnum (parts.base);
    }

  if (parts.index)
    {
      parts.index = gen_lowpart (mode, parts.index);
      regno2 = true_regnum (parts.index);
    }

  if (parts.disp)
    parts.disp = gen_lowpart (mode, parts.disp);

  if (parts.scale > 1)
    {
      /* Case r1 = r1 + ...  */
      if (regno1 == regno0)
	{
	  /* If we have a case r1 = r1 + C * r2 then we
	     should use multiplication which is very
	     expensive.  Assume cost model is wrong if we
	     have such case here.  */
	  gcc_assert (regno2 != regno0);

	  for (adds = parts.scale; adds > 0; adds--)
	    ix86_emit_binop (PLUS, mode, target, parts.index);
	}
      else
	{
	  /* r1 = r2 + r3 * C case.  Need to move r3 into r1.  */
	  if (regno0 != regno2)
	    emit_insn (gen_rtx_SET (target, parts.index));

	  /* Use shift for scaling.  */
	  ix86_emit_binop (ASHIFT, mode, target,
			   GEN_INT (exact_log2 (parts.scale)));

	  if (parts.base)
	    ix86_emit_binop (PLUS, mode, target, parts.base);

	  if (parts.disp && parts.disp != const0_rtx)
	    ix86_emit_binop (PLUS, mode, target, parts.disp);
	}
    }
  else if (!parts.base && !parts.index)
    {
      gcc_assert(parts.disp);
      emit_insn (gen_rtx_SET (target, parts.disp));
    }
  else
    {
      if (!parts.base)
	{
	  if (regno0 != regno2)
	    emit_insn (gen_rtx_SET (target, parts.index));
	}
      else if (!parts.index)
	{
	  if (regno0 != regno1)
	    emit_insn (gen_rtx_SET (target, parts.base));
	}
      else
	{
	  if (regno0 == regno1)
	    tmp = parts.index;
	  else if (regno0 == regno2)
	    tmp = parts.base;
	  else
	    {
	      rtx tmp1;

	      /* Find better operand for SET instruction, depending
		 on which definition is farther from the insn.  */
	      if (find_nearest_reg_def (insn, regno1, regno2))
		tmp = parts.index, tmp1 = parts.base;
	      else
		tmp = parts.base, tmp1 = parts.index;

	      emit_insn (gen_rtx_SET (target, tmp));

	      if (parts.disp && parts.disp != const0_rtx)
		ix86_emit_binop (PLUS, mode, target, parts.disp);

	      ix86_emit_binop (PLUS, mode, target, tmp1);
	      return;
	    }

	  ix86_emit_binop (PLUS, mode, target, tmp);
	}

      if (parts.disp && parts.disp != const0_rtx)
	ix86_emit_binop (PLUS, mode, target, parts.disp);
    }
}

/* Return true if it is ok to optimize an ADD operation to LEA
   operation to avoid flag register consumation.  For most processors,
   ADD is faster than LEA.  For the processors like BONNELL, if the
   destination register of LEA holds an actual address which will be
   used soon, LEA is better and otherwise ADD is better.  */

bool
ix86_lea_for_add_ok (rtx_insn *insn, rtx operands[])
{
  unsigned int regno0 = true_regnum (operands[0]);
  unsigned int regno1 = true_regnum (operands[1]);
  unsigned int regno2 = true_regnum (operands[2]);

  /* If a = b + c, (a!=b && a!=c), must use lea form. */
  if (regno0 != regno1 && regno0 != regno2)
    return true;

  if (!TARGET_OPT_AGU || optimize_function_for_size_p (cfun))
    return false;

  return ix86_lea_outperforms (insn, regno0, regno1, regno2, 0, false);
}

/* Return true if destination reg of SET_BODY is shift count of
   USE_BODY.  */

static bool
ix86_dep_by_shift_count_body (const_rtx set_body, const_rtx use_body)
{
  rtx set_dest;
  rtx shift_rtx;
  int i;

  /* Retrieve destination of SET_BODY.  */
  switch (GET_CODE (set_body))
    {
    case SET:
      set_dest = SET_DEST (set_body);
      if (!set_dest || !REG_P (set_dest))
	return false;
      break;
    case PARALLEL:
      for (i = XVECLEN (set_body, 0) - 1; i >= 0; i--)
	if (ix86_dep_by_shift_count_body (XVECEXP (set_body, 0, i),
					  use_body))
	  return true;
      /* FALLTHROUGH */
    default:
      return false;
    }

  /* Retrieve shift count of USE_BODY.  */
  switch (GET_CODE (use_body))
    {
    case SET:
      shift_rtx = XEXP (use_body, 1);
      break;
    case PARALLEL:
      for (i = XVECLEN (use_body, 0) - 1; i >= 0; i--)
	if (ix86_dep_by_shift_count_body (set_body,
					  XVECEXP (use_body, 0, i)))
	  return true;
      /* FALLTHROUGH */
    default:
      return false;
    }

  if (shift_rtx
      && (GET_CODE (shift_rtx) == ASHIFT
	  || GET_CODE (shift_rtx) == LSHIFTRT
	  || GET_CODE (shift_rtx) == ASHIFTRT
	  || GET_CODE (shift_rtx) == ROTATE
	  || GET_CODE (shift_rtx) == ROTATERT))
    {
      rtx shift_count = XEXP (shift_rtx, 1);

      /* Return true if shift count is dest of SET_BODY.  */
      if (REG_P (shift_count))
	{
	  /* Add check since it can be invoked before register
	     allocation in pre-reload schedule.  */
	  if (reload_completed
	      && true_regnum (set_dest) == true_regnum (shift_count))
	    return true;
	  else if (REGNO(set_dest) == REGNO(shift_count))
	    return true;
	}
    }

  return false;
}

/* Return true if destination reg of SET_INSN is shift count of
   USE_INSN.  */

bool
ix86_dep_by_shift_count (const_rtx set_insn, const_rtx use_insn)
{
  return ix86_dep_by_shift_count_body (PATTERN (set_insn),
				       PATTERN (use_insn));
}

/* Return TRUE or FALSE depending on whether the unary operator meets the
   appropriate constraints.  */

bool
ix86_unary_operator_ok (enum rtx_code,
			machine_mode,
			rtx operands[2])
{
  /* If one of operands is memory, source and destination must match.  */
  if ((MEM_P (operands[0])
       || MEM_P (operands[1]))
      && ! rtx_equal_p (operands[0], operands[1]))
    return false;
  return true;
}

/* Return TRUE if the operands to a vec_interleave_{high,low}v2df
   are ok, keeping in mind the possible movddup alternative.  */

bool
ix86_vec_interleave_v2df_operator_ok (rtx operands[3], bool high)
{
  if (MEM_P (operands[0]))
    return rtx_equal_p (operands[0], operands[1 + high]);
  if (MEM_P (operands[1]) && MEM_P (operands[2]))
    return TARGET_SSE3 && rtx_equal_p (operands[1], operands[2]);
  return true;
}

/* Post-reload splitter for converting an SF or DFmode value in an
   SSE register into an unsigned SImode.  */

void
ix86_split_convert_uns_si_sse (rtx operands[])
{
  machine_mode vecmode;
  rtx value, large, zero_or_two31, input, two31, x;

  large = operands[1];
  zero_or_two31 = operands[2];
  input = operands[3];
  two31 = operands[4];
  vecmode = GET_MODE (large);
  value = gen_rtx_REG (vecmode, REGNO (operands[0]));

  /* Load up the value into the low element.  We must ensure that the other
     elements are valid floats -- zero is the easiest such value.  */
  if (MEM_P (input))
    {
      if (vecmode == V4SFmode)
	emit_insn (gen_vec_setv4sf_0 (value, CONST0_RTX (V4SFmode), input));
      else
	emit_insn (gen_sse2_loadlpd (value, CONST0_RTX (V2DFmode), input));
    }
  else
    {
      input = gen_rtx_REG (vecmode, REGNO (input));
      emit_move_insn (value, CONST0_RTX (vecmode));
      if (vecmode == V4SFmode)
	emit_insn (gen_sse_movss (value, value, input));
      else
	emit_insn (gen_sse2_movsd (value, value, input));
    }

  emit_move_insn (large, two31);
  emit_move_insn (zero_or_two31, MEM_P (two31) ? large : two31);

  x = gen_rtx_fmt_ee (LE, vecmode, large, value);
  emit_insn (gen_rtx_SET (large, x));

  x = gen_rtx_AND (vecmode, zero_or_two31, large);
  emit_insn (gen_rtx_SET (zero_or_two31, x));

  x = gen_rtx_MINUS (vecmode, value, zero_or_two31);
  emit_insn (gen_rtx_SET (value, x));

  large = gen_rtx_REG (V4SImode, REGNO (large));
  emit_insn (gen_ashlv4si3 (large, large, GEN_INT (31)));

  x = gen_rtx_REG (V4SImode, REGNO (value));
  if (vecmode == V4SFmode)
    emit_insn (gen_fix_truncv4sfv4si2 (x, value));
  else
    emit_insn (gen_sse2_cvttpd2dq (x, value));
  value = x;

  emit_insn (gen_xorv4si3 (value, value, large));
}

/* Convert an unsigned DImode value into a DFmode, using only SSE.
   Expects the 64-bit DImode to be supplied in a pair of integral
   registers.  Requires SSE2; will use SSE3 if available.  For x86_32,
   -mfpmath=sse, !optimize_size only.  */

void
ix86_expand_convert_uns_didf_sse (rtx target, rtx input)
{
  REAL_VALUE_TYPE bias_lo_rvt, bias_hi_rvt;
  rtx int_xmm, fp_xmm;
  rtx biases, exponents;
  rtx x;

  int_xmm = gen_reg_rtx (V4SImode);
  if (TARGET_INTER_UNIT_MOVES_TO_VEC)
    emit_insn (gen_movdi_to_sse (int_xmm, input));
  else if (TARGET_SSE_SPLIT_REGS)
    {
      emit_clobber (int_xmm);
      emit_move_insn (gen_lowpart (DImode, int_xmm), input);
    }
  else
    {
      x = gen_reg_rtx (V2DImode);
      ix86_expand_vector_init_one_nonzero (false, V2DImode, x, input, 0);
      emit_move_insn (int_xmm, gen_lowpart (V4SImode, x));
    }

  x = gen_rtx_CONST_VECTOR (V4SImode,
			    gen_rtvec (4, GEN_INT (0x43300000UL),
				       GEN_INT (0x45300000UL),
				       const0_rtx, const0_rtx));
  exponents = validize_mem (force_const_mem (V4SImode, x));

  /* int_xmm = {0x45300000UL, fp_xmm/hi, 0x43300000, fp_xmm/lo } */
  emit_insn (gen_vec_interleave_lowv4si (int_xmm, int_xmm, exponents));

  /* Concatenating (juxtaposing) (0x43300000UL ## fp_value_low_xmm)
     yields a valid DF value equal to (0x1.0p52 + double(fp_value_lo_xmm)).
     Similarly (0x45300000UL ## fp_value_hi_xmm) yields
     (0x1.0p84 + double(fp_value_hi_xmm)).
     Note these exponents differ by 32.  */

  fp_xmm = copy_to_mode_reg (V2DFmode, gen_lowpart (V2DFmode, int_xmm));

  /* Subtract off those 0x1.0p52 and 0x1.0p84 biases, to produce values
     in [0,2**32-1] and [0]+[2**32,2**64-1] respectively.  */
  real_ldexp (&bias_lo_rvt, &dconst1, 52);
  real_ldexp (&bias_hi_rvt, &dconst1, 84);
  biases = const_double_from_real_value (bias_lo_rvt, DFmode);
  x = const_double_from_real_value (bias_hi_rvt, DFmode);
  biases = gen_rtx_CONST_VECTOR (V2DFmode, gen_rtvec (2, biases, x));
  biases = validize_mem (force_const_mem (V2DFmode, biases));
  emit_insn (gen_subv2df3 (fp_xmm, fp_xmm, biases));

  /* Add the upper and lower DFmode values together.  */
  if (TARGET_SSE3)
    emit_insn (gen_sse3_haddv2df3 (fp_xmm, fp_xmm, fp_xmm));
  else
    {
      x = copy_to_mode_reg (V2DFmode, fp_xmm);
      emit_insn (gen_vec_interleave_highv2df (fp_xmm, fp_xmm, fp_xmm));
      emit_insn (gen_addv2df3 (fp_xmm, fp_xmm, x));
    }

  ix86_expand_vector_extract (false, target, fp_xmm, 0);
}

/* Not used, but eases macroization of patterns.  */
void
ix86_expand_convert_uns_sixf_sse (rtx, rtx)
{
  gcc_unreachable ();
}

/* Convert an unsigned SImode value into a DFmode.  Only currently used
   for SSE, but applicable anywhere.  */

void
ix86_expand_convert_uns_sidf_sse (rtx target, rtx input)
{
  REAL_VALUE_TYPE TWO31r;
  rtx x, fp;

  x = expand_simple_binop (SImode, PLUS, input, GEN_INT (-2147483647 - 1),
			   NULL, 1, OPTAB_DIRECT);

  fp = gen_reg_rtx (DFmode);
  emit_insn (gen_floatsidf2 (fp, x));

  real_ldexp (&TWO31r, &dconst1, 31);
  x = const_double_from_real_value (TWO31r, DFmode);

  x = expand_simple_binop (DFmode, PLUS, fp, x, target, 0, OPTAB_DIRECT);
  if (x != target)
    emit_move_insn (target, x);
}

/* Convert a signed DImode value into a DFmode.  Only used for SSE in
   32-bit mode; otherwise we have a direct convert instruction.  */

void
ix86_expand_convert_sign_didf_sse (rtx target, rtx input)
{
  REAL_VALUE_TYPE TWO32r;
  rtx fp_lo, fp_hi, x;

  fp_lo = gen_reg_rtx (DFmode);
  fp_hi = gen_reg_rtx (DFmode);

  emit_insn (gen_floatsidf2 (fp_hi, gen_highpart (SImode, input)));

  real_ldexp (&TWO32r, &dconst1, 32);
  x = const_double_from_real_value (TWO32r, DFmode);
  fp_hi = expand_simple_binop (DFmode, MULT, fp_hi, x, fp_hi, 0, OPTAB_DIRECT);

  ix86_expand_convert_uns_sidf_sse (fp_lo, gen_lowpart (SImode, input));

  x = expand_simple_binop (DFmode, PLUS, fp_hi, fp_lo, target,
			   0, OPTAB_DIRECT);
  if (x != target)
    emit_move_insn (target, x);
}

/* Convert an unsigned SImode value into a SFmode, using only SSE.
   For x86_32, -mfpmath=sse, !optimize_size only.  */
void
ix86_expand_convert_uns_sisf_sse (rtx target, rtx input)
{
  REAL_VALUE_TYPE ONE16r;
  rtx fp_hi, fp_lo, int_hi, int_lo, x;

  real_ldexp (&ONE16r, &dconst1, 16);
  x = const_double_from_real_value (ONE16r, SFmode);
  int_lo = expand_simple_binop (SImode, AND, input, GEN_INT(0xffff),
				      NULL, 0, OPTAB_DIRECT);
  int_hi = expand_simple_binop (SImode, LSHIFTRT, input, GEN_INT(16),
				      NULL, 0, OPTAB_DIRECT);
  fp_hi = gen_reg_rtx (SFmode);
  fp_lo = gen_reg_rtx (SFmode);
  emit_insn (gen_floatsisf2 (fp_hi, int_hi));
  emit_insn (gen_floatsisf2 (fp_lo, int_lo));
  fp_hi = expand_simple_binop (SFmode, MULT, fp_hi, x, fp_hi,
			       0, OPTAB_DIRECT);
  fp_hi = expand_simple_binop (SFmode, PLUS, fp_hi, fp_lo, target,
			       0, OPTAB_DIRECT);
  if (!rtx_equal_p (target, fp_hi))
    emit_move_insn (target, fp_hi);
}

/* floatunsv{4,8}siv{4,8}sf2 expander.  Expand code to convert
   a vector of unsigned ints VAL to vector of floats TARGET.  */

void
ix86_expand_vector_convert_uns_vsivsf (rtx target, rtx val)
{
  rtx tmp[8];
  REAL_VALUE_TYPE TWO16r;
  machine_mode intmode = GET_MODE (val);
  machine_mode fltmode = GET_MODE (target);
  rtx (*cvt) (rtx, rtx);

  if (intmode == V4SImode)
    cvt = gen_floatv4siv4sf2;
  else
    cvt = gen_floatv8siv8sf2;
  tmp[0] = ix86_build_const_vector (intmode, 1, GEN_INT (0xffff));
  tmp[0] = force_reg (intmode, tmp[0]);
  tmp[1] = expand_simple_binop (intmode, AND, val, tmp[0], NULL_RTX, 1,
				OPTAB_DIRECT);
  tmp[2] = expand_simple_binop (intmode, LSHIFTRT, val, GEN_INT (16),
				NULL_RTX, 1, OPTAB_DIRECT);
  tmp[3] = gen_reg_rtx (fltmode);
  emit_insn (cvt (tmp[3], tmp[1]));
  tmp[4] = gen_reg_rtx (fltmode);
  emit_insn (cvt (tmp[4], tmp[2]));
  real_ldexp (&TWO16r, &dconst1, 16);
  tmp[5] = const_double_from_real_value (TWO16r, SFmode);
  tmp[5] = force_reg (fltmode, ix86_build_const_vector (fltmode, 1, tmp[5]));
  tmp[6] = expand_simple_binop (fltmode, MULT, tmp[4], tmp[5], NULL_RTX, 1,
				OPTAB_DIRECT);
  tmp[7] = expand_simple_binop (fltmode, PLUS, tmp[3], tmp[6], target, 1,
				OPTAB_DIRECT);
  if (tmp[7] != target)
    emit_move_insn (target, tmp[7]);
}

/* Adjust a V*SFmode/V*DFmode value VAL so that *sfix_trunc* resp. fix_trunc*
   pattern can be used on it instead of *ufix_trunc* resp. fixuns_trunc*.
   This is done by doing just signed conversion if < 0x1p31, and otherwise by
   subtracting 0x1p31 first and xoring in 0x80000000 from *XORP afterwards.  */

rtx
ix86_expand_adjust_ufix_to_sfix_si (rtx val, rtx *xorp)
{
  REAL_VALUE_TYPE TWO31r;
  rtx two31r, tmp[4];
  machine_mode mode = GET_MODE (val);
  machine_mode scalarmode = GET_MODE_INNER (mode);
  machine_mode intmode = GET_MODE_SIZE (mode) == 32 ? V8SImode : V4SImode;
  rtx (*cmp) (rtx, rtx, rtx, rtx);
  int i;

  for (i = 0; i < 3; i++)
    tmp[i] = gen_reg_rtx (mode);
  real_ldexp (&TWO31r, &dconst1, 31);
  two31r = const_double_from_real_value (TWO31r, scalarmode);
  two31r = ix86_build_const_vector (mode, 1, two31r);
  two31r = force_reg (mode, two31r);
  switch (mode)
    {
    case E_V8SFmode: cmp = gen_avx_maskcmpv8sf3; break;
    case E_V4SFmode: cmp = gen_sse_maskcmpv4sf3; break;
    case E_V4DFmode: cmp = gen_avx_maskcmpv4df3; break;
    case E_V2DFmode: cmp = gen_sse2_maskcmpv2df3; break;
    default: gcc_unreachable ();
    }
  tmp[3] = gen_rtx_LE (mode, two31r, val);
  emit_insn (cmp (tmp[0], two31r, val, tmp[3]));
  tmp[1] = expand_simple_binop (mode, AND, tmp[0], two31r, tmp[1],
				0, OPTAB_DIRECT);
  if (intmode == V4SImode || TARGET_AVX2)
    *xorp = expand_simple_binop (intmode, ASHIFT,
				 gen_lowpart (intmode, tmp[0]),
				 GEN_INT (31), NULL_RTX, 0,
				 OPTAB_DIRECT);
  else
    {
      rtx two31 = GEN_INT (HOST_WIDE_INT_1U << 31);
      two31 = ix86_build_const_vector (intmode, 1, two31);
      *xorp = expand_simple_binop (intmode, AND,
				   gen_lowpart (intmode, tmp[0]),
				   two31, NULL_RTX, 0,
				   OPTAB_DIRECT);
    }
  return expand_simple_binop (mode, MINUS, val, tmp[1], tmp[2],
			      0, OPTAB_DIRECT);
}

/* A subroutine of ix86_build_signbit_mask.  If VECT is true,
   then replicate the value for all elements of the vector
   register.  */

rtx
ix86_build_const_vector (machine_mode mode, bool vect, rtx value)
{
  int i, n_elt;
  rtvec v;
  machine_mode scalar_mode;

  switch (mode)
    {
    case E_V64QImode:
    case E_V32QImode:
    case E_V16QImode:
    case E_V32HImode:
    case E_V16HImode:
    case E_V8HImode:
    case E_V16SImode:
    case E_V8SImode:
    case E_V4SImode:
    case E_V8DImode:
    case E_V4DImode:
    case E_V2DImode:
      gcc_assert (vect);
      /* FALLTHRU */
    case E_V16SFmode:
    case E_V8SFmode:
    case E_V4SFmode:
    case E_V8DFmode:
    case E_V4DFmode:
    case E_V2DFmode:
      n_elt = GET_MODE_NUNITS (mode);
      v = rtvec_alloc (n_elt);
      scalar_mode = GET_MODE_INNER (mode);

      RTVEC_ELT (v, 0) = value;

      for (i = 1; i < n_elt; ++i)
	RTVEC_ELT (v, i) = vect ? value : CONST0_RTX (scalar_mode);

      return gen_rtx_CONST_VECTOR (mode, v);

    default:
      gcc_unreachable ();
    }
}

/* A subroutine of ix86_expand_fp_absneg_operator, copysign expanders
   and ix86_expand_int_vcond.  Create a mask for the sign bit in MODE
   for an SSE register.  If VECT is true, then replicate the mask for
   all elements of the vector register.  If INVERT is true, then create
   a mask excluding the sign bit.  */

rtx
ix86_build_signbit_mask (machine_mode mode, bool vect, bool invert)
{
  machine_mode vec_mode, imode;
  wide_int w;
  rtx mask, v;

  switch (mode)
    {
    case E_V16SImode:
    case E_V16SFmode:
    case E_V8SImode:
    case E_V4SImode:
    case E_V8SFmode:
    case E_V4SFmode:
      vec_mode = mode;
      imode = SImode;
      break;

    case E_V8DImode:
    case E_V4DImode:
    case E_V2DImode:
    case E_V8DFmode:
    case E_V4DFmode:
    case E_V2DFmode:
      vec_mode = mode;
      imode = DImode;
      break;

    case E_TImode:
    case E_TFmode:
      vec_mode = VOIDmode;
      imode = TImode;
      break;

    default:
      gcc_unreachable ();
    }

  machine_mode inner_mode = GET_MODE_INNER (mode);
  w = wi::set_bit_in_zero (GET_MODE_BITSIZE (inner_mode) - 1,
			   GET_MODE_BITSIZE (inner_mode));
  if (invert)
    w = wi::bit_not (w);

  /* Force this value into the low part of a fp vector constant.  */
  mask = immed_wide_int_const (w, imode);
  mask = gen_lowpart (inner_mode, mask);

  if (vec_mode == VOIDmode)
    return force_reg (inner_mode, mask);

  v = ix86_build_const_vector (vec_mode, vect, mask);
  return force_reg (vec_mode, v);
}

/* Generate code for floating point ABS or NEG.  */

void
ix86_expand_fp_absneg_operator (enum rtx_code code, machine_mode mode,
				rtx operands[])
{
  rtx mask, set, dst, src;
  bool use_sse = false;
  bool vector_mode = VECTOR_MODE_P (mode);
  machine_mode vmode = mode;

  if (vector_mode)
    use_sse = true;
  else if (mode == TFmode)
    use_sse = true;
  else if (TARGET_SSE_MATH)
    {
      use_sse = SSE_FLOAT_MODE_P (mode);
      if (mode == SFmode)
	vmode = V4SFmode;
      else if (mode == DFmode)
	vmode = V2DFmode;
    }

  /* NEG and ABS performed with SSE use bitwise mask operations.
     Create the appropriate mask now.  */
  if (use_sse)
    mask = ix86_build_signbit_mask (vmode, vector_mode, code == ABS);
  else
    mask = NULL_RTX;

  dst = operands[0];
  src = operands[1];

  set = gen_rtx_fmt_e (code, mode, src);
  set = gen_rtx_SET (dst, set);

  if (mask)
    {
      rtx use, clob;
      rtvec par;

      use = gen_rtx_USE (VOIDmode, mask);
      if (vector_mode)
	par = gen_rtvec (2, set, use);
      else
	{
          clob = gen_rtx_CLOBBER (VOIDmode, gen_rtx_REG (CCmode, FLAGS_REG));
	  par = gen_rtvec (3, set, use, clob);
        }
      emit_insn (gen_rtx_PARALLEL (VOIDmode, par));
    }
  else
    emit_insn (set);
}

/* Expand a copysign operation.  Special case operand 0 being a constant.  */

void
ix86_expand_copysign (rtx operands[])
{
  machine_mode mode, vmode;
  rtx dest, op0, op1, mask, nmask;

  dest = operands[0];
  op0 = operands[1];
  op1 = operands[2];

  mode = GET_MODE (dest);

  if (mode == SFmode)
    vmode = V4SFmode;
  else if (mode == DFmode)
    vmode = V2DFmode;
  else
    vmode = mode;

  if (CONST_DOUBLE_P (op0))
    {
      rtx (*copysign_insn)(rtx, rtx, rtx, rtx);

      if (real_isneg (CONST_DOUBLE_REAL_VALUE (op0)))
	op0 = simplify_unary_operation (ABS, mode, op0, mode);

      if (mode == SFmode || mode == DFmode)
	{
	  if (op0 == CONST0_RTX (mode))
	    op0 = CONST0_RTX (vmode);
	  else
	    {
	      rtx v = ix86_build_const_vector (vmode, false, op0);

	      op0 = force_reg (vmode, v);
	    }
	}
      else if (op0 != CONST0_RTX (mode))
	op0 = force_reg (mode, op0);

      mask = ix86_build_signbit_mask (vmode, 0, 0);

      if (mode == SFmode)
	copysign_insn = gen_copysignsf3_const;
      else if (mode == DFmode)
	copysign_insn = gen_copysigndf3_const;
      else
	copysign_insn = gen_copysigntf3_const;

      emit_insn (copysign_insn (dest, op0, op1, mask));
    }
  else
    {
      rtx (*copysign_insn)(rtx, rtx, rtx, rtx, rtx, rtx);

      nmask = ix86_build_signbit_mask (vmode, 0, 1);
      mask = ix86_build_signbit_mask (vmode, 0, 0);

      if (mode == SFmode)
	copysign_insn = gen_copysignsf3_var;
      else if (mode == DFmode)
	copysign_insn = gen_copysigndf3_var;
      else
	copysign_insn = gen_copysigntf3_var;

      emit_insn (copysign_insn (dest, NULL_RTX, op0, op1, nmask, mask));
    }
}

/* Deconstruct a copysign operation into bit masks.  Operand 0 is known to
   be a constant, and so has already been expanded into a vector constant.  */

void
ix86_split_copysign_const (rtx operands[])
{
  machine_mode mode, vmode;
  rtx dest, op0, mask, x;

  dest = operands[0];
  op0 = operands[1];
  mask = operands[3];

  mode = GET_MODE (dest);
  vmode = GET_MODE (mask);

  dest = lowpart_subreg (vmode, dest, mode);
  x = gen_rtx_AND (vmode, dest, mask);
  emit_insn (gen_rtx_SET (dest, x));

  if (op0 != CONST0_RTX (vmode))
    {
      x = gen_rtx_IOR (vmode, dest, op0);
      emit_insn (gen_rtx_SET (dest, x));
    }
}

/* Deconstruct a copysign operation into bit masks.  Operand 0 is variable,
   so we have to do two masks.  */

void
ix86_split_copysign_var (rtx operands[])
{
  machine_mode mode, vmode;
  rtx dest, scratch, op0, op1, mask, nmask, x;

  dest = operands[0];
  scratch = operands[1];
  op0 = operands[2];
  op1 = operands[3];
  nmask = operands[4];
  mask = operands[5];

  mode = GET_MODE (dest);
  vmode = GET_MODE (mask);

  if (rtx_equal_p (op0, op1))
    {
      /* Shouldn't happen often (it's useless, obviously), but when it does
	 we'd generate incorrect code if we continue below.  */
      emit_move_insn (dest, op0);
      return;
    }

  if (REG_P (mask) && REGNO (dest) == REGNO (mask))	/* alternative 0 */
    {
      gcc_assert (REGNO (op1) == REGNO (scratch));

      x = gen_rtx_AND (vmode, scratch, mask);
      emit_insn (gen_rtx_SET (scratch, x));

      dest = mask;
      op0 = lowpart_subreg (vmode, op0, mode);
      x = gen_rtx_NOT (vmode, dest);
      x = gen_rtx_AND (vmode, x, op0);
      emit_insn (gen_rtx_SET (dest, x));
    }
  else
    {
      if (REGNO (op1) == REGNO (scratch))		/* alternative 1,3 */
	{
	  x = gen_rtx_AND (vmode, scratch, mask);
	}
      else						/* alternative 2,4 */
	{
          gcc_assert (REGNO (mask) == REGNO (scratch));
          op1 = lowpart_subreg (vmode, op1, mode);
	  x = gen_rtx_AND (vmode, scratch, op1);
	}
      emit_insn (gen_rtx_SET (scratch, x));

      if (REGNO (op0) == REGNO (dest))			/* alternative 1,2 */
	{
	  dest = lowpart_subreg (vmode, op0, mode);
	  x = gen_rtx_AND (vmode, dest, nmask);
	}
      else						/* alternative 3,4 */
	{
          gcc_assert (REGNO (nmask) == REGNO (dest));
	  dest = nmask;
	  op0 = lowpart_subreg (vmode, op0, mode);
	  x = gen_rtx_AND (vmode, dest, op0);
	}
      emit_insn (gen_rtx_SET (dest, x));
    }

  x = gen_rtx_IOR (vmode, dest, scratch);
  emit_insn (gen_rtx_SET (dest, x));
}

/* Expand an xorsign operation.  */

void
ix86_expand_xorsign (rtx operands[])
{
  rtx (*xorsign_insn)(rtx, rtx, rtx, rtx);
  machine_mode mode, vmode;
  rtx dest, op0, op1, mask;

  dest = operands[0];
  op0 = operands[1];
  op1 = operands[2];

  mode = GET_MODE (dest);

  if (mode == SFmode)
    {
      xorsign_insn = gen_xorsignsf3_1;
      vmode = V4SFmode;
    }
  else if (mode == DFmode)
    {
      xorsign_insn = gen_xorsigndf3_1;
      vmode = V2DFmode;
    }
  else
    gcc_unreachable ();

  mask = ix86_build_signbit_mask (vmode, 0, 0);

  emit_insn (xorsign_insn (dest, op0, op1, mask));
}

/* Deconstruct an xorsign operation into bit masks.  */

void
ix86_split_xorsign (rtx operands[])
{
  machine_mode mode, vmode;
  rtx dest, op0, mask, x;

  dest = operands[0];
  op0 = operands[1];
  mask = operands[3];

  mode = GET_MODE (dest);
  vmode = GET_MODE (mask);

  dest = lowpart_subreg (vmode, dest, mode);
  x = gen_rtx_AND (vmode, dest, mask);
  emit_insn (gen_rtx_SET (dest, x));

  op0 = lowpart_subreg (vmode, op0, mode);
  x = gen_rtx_XOR (vmode, dest, op0);
  emit_insn (gen_rtx_SET (dest, x));
}

/* Return TRUE or FALSE depending on whether the first SET in INSN
   has source and destination with matching CC modes, and that the
   CC mode is at least as constrained as REQ_MODE.  */

bool
ix86_match_ccmode (rtx insn, machine_mode req_mode)
{
  rtx set;
  machine_mode set_mode;

  set = PATTERN (insn);
  if (GET_CODE (set) == PARALLEL)
    set = XVECEXP (set, 0, 0);
  gcc_assert (GET_CODE (set) == SET);
  gcc_assert (GET_CODE (SET_SRC (set)) == COMPARE);

  set_mode = GET_MODE (SET_DEST (set));
  switch (set_mode)
    {
    case E_CCNOmode:
      if (req_mode != CCNOmode
	  && (req_mode != CCmode
	      || XEXP (SET_SRC (set), 1) != const0_rtx))
	return false;
      break;
    case E_CCmode:
      if (req_mode == CCGCmode)
	return false;
      /* FALLTHRU */
    case E_CCGCmode:
      if (req_mode == CCGOCmode || req_mode == CCNOmode)
	return false;
      /* FALLTHRU */
    case E_CCGOCmode:
      if (req_mode == CCZmode)
	return false;
      /* FALLTHRU */
    case E_CCZmode:
      break;

    case E_CCGZmode:

    case E_CCAmode:
    case E_CCCmode:
    case E_CCOmode:
    case E_CCPmode:
    case E_CCSmode:
      if (set_mode != req_mode)
	return false;
      break;

    default:
      gcc_unreachable ();
    }

  return GET_MODE (SET_SRC (set)) == set_mode;
}

/* Generate insn patterns to do an integer compare of OPERANDS.  */

static rtx
ix86_expand_int_compare (enum rtx_code code, rtx op0, rtx op1)
{
  machine_mode cmpmode;
  rtx tmp, flags;

  cmpmode = SELECT_CC_MODE (code, op0, op1);
  flags = gen_rtx_REG (cmpmode, FLAGS_REG);

  /* This is very simple, but making the interface the same as in the
     FP case makes the rest of the code easier.  */
  tmp = gen_rtx_COMPARE (cmpmode, op0, op1);
  emit_insn (gen_rtx_SET (flags, tmp));

  /* Return the test that should be put into the flags user, i.e.
     the bcc, scc, or cmov instruction.  */
  return gen_rtx_fmt_ee (code, VOIDmode, flags, const0_rtx);
}

/* Figure out whether to use unordered fp comparisons.  */

static bool
ix86_unordered_fp_compare (enum rtx_code code)
{
  if (!TARGET_IEEE_FP)
    return false;

  switch (code)
    {
    case GT:
    case GE:
    case LT:
    case LE:
      return false;

    case EQ:
    case NE:

    case LTGT:
    case UNORDERED:
    case ORDERED:
    case UNLT:
    case UNLE:
    case UNGT:
    case UNGE:
    case UNEQ:
      return true;

    default:
      gcc_unreachable ();
    }
}

machine_mode
ix86_cc_mode (enum rtx_code code, rtx op0, rtx op1)
{
  machine_mode mode = GET_MODE (op0);

  if (SCALAR_FLOAT_MODE_P (mode))
    {
      gcc_assert (!DECIMAL_FLOAT_MODE_P (mode));
      return CCFPmode;
    }

  switch (code)
    {
      /* Only zero flag is needed.  */
    case EQ:			/* ZF=0 */
    case NE:			/* ZF!=0 */
      return CCZmode;
      /* Codes needing carry flag.  */
    case GEU:			/* CF=0 */
    case LTU:			/* CF=1 */
      /* Detect overflow checks.  They need just the carry flag.  */
      if (GET_CODE (op0) == PLUS
	  && (rtx_equal_p (op1, XEXP (op0, 0))
	      || rtx_equal_p (op1, XEXP (op0, 1))))
	return CCCmode;
      else
	return CCmode;
    case GTU:			/* CF=0 & ZF=0 */
    case LEU:			/* CF=1 | ZF=1 */
      return CCmode;
      /* Codes possibly doable only with sign flag when
         comparing against zero.  */
    case GE:			/* SF=OF   or   SF=0 */
    case LT:			/* SF<>OF  or   SF=1 */
      if (op1 == const0_rtx)
	return CCGOCmode;
      else
	/* For other cases Carry flag is not required.  */
	return CCGCmode;
      /* Codes doable only with sign flag when comparing
         against zero, but we miss jump instruction for it
         so we need to use relational tests against overflow
         that thus needs to be zero.  */
    case GT:			/* ZF=0 & SF=OF */
    case LE:			/* ZF=1 | SF<>OF */
      if (op1 == const0_rtx)
	return CCNOmode;
      else
	return CCGCmode;
      /* strcmp pattern do (use flags) and combine may ask us for proper
	 mode.  */
    case USE:
      return CCmode;
    default:
      gcc_unreachable ();
    }
}

/* Return the fixed registers used for condition codes.  */

static bool
ix86_fixed_condition_code_regs (unsigned int *p1, unsigned int *p2)
{
  *p1 = FLAGS_REG;
  *p2 = INVALID_REGNUM;
  return true;
}

/* If two condition code modes are compatible, return a condition code
   mode which is compatible with both.  Otherwise, return
   VOIDmode.  */

static machine_mode
ix86_cc_modes_compatible (machine_mode m1, machine_mode m2)
{
  if (m1 == m2)
    return m1;

  if (GET_MODE_CLASS (m1) != MODE_CC || GET_MODE_CLASS (m2) != MODE_CC)
    return VOIDmode;

  if ((m1 == CCGCmode && m2 == CCGOCmode)
      || (m1 == CCGOCmode && m2 == CCGCmode))
    return CCGCmode;

  if ((m1 == CCNOmode && m2 == CCGOCmode)
      || (m1 == CCGOCmode && m2 == CCNOmode))
    return CCNOmode;

  if (m1 == CCZmode
      && (m2 == CCGCmode || m2 == CCGOCmode || m2 == CCNOmode))
    return m2;
  else if (m2 == CCZmode
	   && (m1 == CCGCmode || m1 == CCGOCmode || m1 == CCNOmode))
    return m1;

  switch (m1)
    {
    default:
      gcc_unreachable ();

    case E_CCmode:
    case E_CCGCmode:
    case E_CCGOCmode:
    case E_CCNOmode:
    case E_CCAmode:
    case E_CCCmode:
    case E_CCOmode:
    case E_CCPmode:
    case E_CCSmode:
    case E_CCZmode:
      switch (m2)
	{
	default:
	  return VOIDmode;

	case E_CCmode:
	case E_CCGCmode:
	case E_CCGOCmode:
	case E_CCNOmode:
	case E_CCAmode:
	case E_CCCmode:
	case E_CCOmode:
	case E_CCPmode:
	case E_CCSmode:
	case E_CCZmode:
	  return CCmode;
	}

    case E_CCFPmode:
      /* These are only compatible with themselves, which we already
	 checked above.  */
      return VOIDmode;
    }
}


/* Return a comparison we can do and that it is equivalent to
   swap_condition (code) apart possibly from orderedness.
   But, never change orderedness if TARGET_IEEE_FP, returning
   UNKNOWN in that case if necessary.  */

static enum rtx_code
ix86_fp_swap_condition (enum rtx_code code)
{
  switch (code)
    {
    case GT:                   /* GTU - CF=0 & ZF=0 */
      return TARGET_IEEE_FP ? UNKNOWN : UNLT;
    case GE:                   /* GEU - CF=0 */
      return TARGET_IEEE_FP ? UNKNOWN : UNLE;
    case UNLT:                 /* LTU - CF=1 */
      return TARGET_IEEE_FP ? UNKNOWN : GT;
    case UNLE:                 /* LEU - CF=1 | ZF=1 */
      return TARGET_IEEE_FP ? UNKNOWN : GE;
    default:
      return swap_condition (code);
    }
}

/* Return cost of comparison CODE using the best strategy for performance.
   All following functions do use number of instructions as a cost metrics.
   In future this should be tweaked to compute bytes for optimize_size and
   take into account performance of various instructions on various CPUs.  */

static int
ix86_fp_comparison_cost (enum rtx_code code)
{
  int arith_cost;

  /* The cost of code using bit-twiddling on %ah.  */
  switch (code)
    {
    case UNLE:
    case UNLT:
    case LTGT:
    case GT:
    case GE:
    case UNORDERED:
    case ORDERED:
    case UNEQ:
      arith_cost = 4;
      break;
    case LT:
    case NE:
    case EQ:
    case UNGE:
      arith_cost = TARGET_IEEE_FP ? 5 : 4;
      break;
    case LE:
    case UNGT:
      arith_cost = TARGET_IEEE_FP ? 6 : 4;
      break;
    default:
      gcc_unreachable ();
    }

  switch (ix86_fp_comparison_strategy (code))
    {
    case IX86_FPCMP_COMI:
      return arith_cost > 4 ? 3 : 2;
    case IX86_FPCMP_SAHF:
      return arith_cost > 4 ? 4 : 3;
    default:
      return arith_cost;
    }
}

/* Return strategy to use for floating-point.  We assume that fcomi is always
   preferrable where available, since that is also true when looking at size
   (2 bytes, vs. 3 for fnstsw+sahf and at least 5 for fnstsw+test).  */

enum ix86_fpcmp_strategy
ix86_fp_comparison_strategy (enum rtx_code)
{
  /* Do fcomi/sahf based test when profitable.  */

  if (TARGET_CMOVE)
    return IX86_FPCMP_COMI;

  if (TARGET_SAHF && (TARGET_USE_SAHF || optimize_insn_for_size_p ()))
    return IX86_FPCMP_SAHF;

  return IX86_FPCMP_ARITH;
}

/* Swap, force into registers, or otherwise massage the two operands
   to a fp comparison.  The operands are updated in place; the new
   comparison code is returned.  */

static enum rtx_code
ix86_prepare_fp_compare_args (enum rtx_code code, rtx *pop0, rtx *pop1)
{
  bool unordered_compare = ix86_unordered_fp_compare (code);
  rtx op0 = *pop0, op1 = *pop1;
  machine_mode op_mode = GET_MODE (op0);
  bool is_sse = TARGET_SSE_MATH && SSE_FLOAT_MODE_P (op_mode);

  /* All of the unordered compare instructions only work on registers.
     The same is true of the fcomi compare instructions.  The XFmode
     compare instructions require registers except when comparing
     against zero or when converting operand 1 from fixed point to
     floating point.  */

  if (!is_sse
      && (unordered_compare
	  || (op_mode == XFmode
	      && ! (standard_80387_constant_p (op0) == 1
		    || standard_80387_constant_p (op1) == 1)
	      && GET_CODE (op1) != FLOAT)
	  || ix86_fp_comparison_strategy (code) == IX86_FPCMP_COMI))
    {
      op0 = force_reg (op_mode, op0);
      op1 = force_reg (op_mode, op1);
    }
  else
    {
      /* %%% We only allow op1 in memory; op0 must be st(0).  So swap
	 things around if they appear profitable, otherwise force op0
	 into a register.  */

      if (standard_80387_constant_p (op0) == 0
	  || (MEM_P (op0)
	      && ! (standard_80387_constant_p (op1) == 0
		    || MEM_P (op1))))
	{
	  enum rtx_code new_code = ix86_fp_swap_condition (code);
	  if (new_code != UNKNOWN)
	    {
	      std::swap (op0, op1);
	      code = new_code;
	    }
	}

      if (!REG_P (op0))
	op0 = force_reg (op_mode, op0);

      if (CONSTANT_P (op1))
	{
	  int tmp = standard_80387_constant_p (op1);
	  if (tmp == 0)
	    op1 = validize_mem (force_const_mem (op_mode, op1));
	  else if (tmp == 1)
	    {
	      if (TARGET_CMOVE)
		op1 = force_reg (op_mode, op1);
	    }
	  else
	    op1 = force_reg (op_mode, op1);
	}
    }

  /* Try to rearrange the comparison to make it cheaper.  */
  if (ix86_fp_comparison_cost (code)
      > ix86_fp_comparison_cost (swap_condition (code))
      && (REG_P (op1) || can_create_pseudo_p ()))
    {
      std::swap (op0, op1);
      code = swap_condition (code);
      if (!REG_P (op0))
	op0 = force_reg (op_mode, op0);
    }

  *pop0 = op0;
  *pop1 = op1;
  return code;
}

/* Convert comparison codes we use to represent FP comparison to integer
   code that will result in proper branch.  Return UNKNOWN if no such code
   is available.  */

enum rtx_code
ix86_fp_compare_code_to_integer (enum rtx_code code)
{
  switch (code)
    {
    case GT:
      return GTU;
    case GE:
      return GEU;
    case ORDERED:
    case UNORDERED:
      return code;
    case UNEQ:
      return EQ;
    case UNLT:
      return LTU;
    case UNLE:
      return LEU;
    case LTGT:
      return NE;
    default:
      return UNKNOWN;
    }
}

/* Generate insn patterns to do a floating point compare of OPERANDS.  */

static rtx
ix86_expand_fp_compare (enum rtx_code code, rtx op0, rtx op1)
{
  bool unordered_compare = ix86_unordered_fp_compare (code);
  machine_mode cmp_mode;
  rtx tmp, scratch;

  code = ix86_prepare_fp_compare_args (code, &op0, &op1);

  tmp = gen_rtx_COMPARE (CCFPmode, op0, op1);
  if (unordered_compare)
    tmp = gen_rtx_UNSPEC (CCFPmode, gen_rtvec (1, tmp), UNSPEC_NOTRAP);

  /* Do fcomi/sahf based test when profitable.  */
  switch (ix86_fp_comparison_strategy (code))
    {
    case IX86_FPCMP_COMI:
      cmp_mode = CCFPmode;
      emit_insn (gen_rtx_SET (gen_rtx_REG (CCFPmode, FLAGS_REG), tmp));
      break;

    case IX86_FPCMP_SAHF:
      cmp_mode = CCFPmode;
      tmp = gen_rtx_UNSPEC (HImode, gen_rtvec (1, tmp), UNSPEC_FNSTSW);
      scratch = gen_reg_rtx (HImode);
      emit_insn (gen_rtx_SET (scratch, tmp));
      emit_insn (gen_x86_sahf_1 (scratch));
      break;

    case IX86_FPCMP_ARITH:
      cmp_mode = CCNOmode;
      tmp = gen_rtx_UNSPEC (HImode, gen_rtvec (1, tmp), UNSPEC_FNSTSW);
      scratch = gen_reg_rtx (HImode);
      emit_insn (gen_rtx_SET (scratch, tmp));

      /* In the unordered case, we have to check C2 for NaN's, which
	 doesn't happen to work out to anything nice combination-wise.
	 So do some bit twiddling on the value we've got in AH to come
	 up with an appropriate set of condition codes.  */

      switch (code)
	{
	case GT:
	case UNGT:
	  if (code == GT || !TARGET_IEEE_FP)
	    {
	      emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x45)));
	      code = EQ;
	    }
	  else
	    {
	      emit_insn (gen_andqi_ext_1 (scratch, scratch, GEN_INT (0x45)));
	      emit_insn (gen_addqi_ext_1 (scratch, scratch, constm1_rtx));
	      emit_insn (gen_cmpqi_ext_3 (scratch, GEN_INT (0x44)));
	      cmp_mode = CCmode;
	      code = GEU;
	    }
	  break;
	case LT:
	case UNLT:
	  if (code == LT && TARGET_IEEE_FP)
	    {
	      emit_insn (gen_andqi_ext_1 (scratch, scratch, GEN_INT (0x45)));
	      emit_insn (gen_cmpqi_ext_3 (scratch, const1_rtx));
	      cmp_mode = CCmode;
	      code = EQ;
	    }
	  else
	    {
	      emit_insn (gen_testqi_ext_1_ccno (scratch, const1_rtx));
	      code = NE;
	    }
	  break;
	case GE:
	case UNGE:
	  if (code == GE || !TARGET_IEEE_FP)
	    {
	      emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x05)));
	      code = EQ;
	    }
	  else
	    {
	      emit_insn (gen_andqi_ext_1 (scratch, scratch, GEN_INT (0x45)));
	      emit_insn (gen_xorqi_ext_1_cc (scratch, scratch, const1_rtx));
	      code = NE;
	    }
	  break;
	case LE:
	case UNLE:
	  if (code == LE && TARGET_IEEE_FP)
	    {
	      emit_insn (gen_andqi_ext_1 (scratch, scratch, GEN_INT (0x45)));
	      emit_insn (gen_addqi_ext_1 (scratch, scratch, constm1_rtx));
	      emit_insn (gen_cmpqi_ext_3 (scratch, GEN_INT (0x40)));
	      cmp_mode = CCmode;
	      code = LTU;
	    }
	  else
	    {
	      emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x45)));
	      code = NE;
	    }
	  break;
	case EQ:
	case UNEQ:
	  if (code == EQ && TARGET_IEEE_FP)
	    {
	      emit_insn (gen_andqi_ext_1 (scratch, scratch, GEN_INT (0x45)));
	      emit_insn (gen_cmpqi_ext_3 (scratch, GEN_INT (0x40)));
	      cmp_mode = CCmode;
	      code = EQ;
	    }
	  else
	    {
	      emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x40)));
	      code = NE;
	    }
	  break;
	case NE:
	case LTGT:
	  if (code == NE && TARGET_IEEE_FP)
	    {
	      emit_insn (gen_andqi_ext_1 (scratch, scratch, GEN_INT (0x45)));
	      emit_insn (gen_xorqi_ext_1_cc (scratch, scratch,
					     GEN_INT (0x40)));
	      code = NE;
	    }
	  else
	    {
	      emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x40)));
	      code = EQ;
	    }
	  break;

	case UNORDERED:
	  emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x04)));
	  code = NE;
	  break;
	case ORDERED:
	  emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x04)));
	  code = EQ;
	  break;

	default:
	  gcc_unreachable ();
	}
	break;

    default:
      gcc_unreachable();
    }

  /* Return the test that should be put into the flags user, i.e.
     the bcc, scc, or cmov instruction.  */
  return gen_rtx_fmt_ee (code, VOIDmode,
			 gen_rtx_REG (cmp_mode, FLAGS_REG),
			 const0_rtx);
}

static rtx
ix86_expand_compare (enum rtx_code code, rtx op0, rtx op1)
{
  rtx ret;

  if (GET_MODE_CLASS (GET_MODE (op0)) == MODE_CC)
    ret = gen_rtx_fmt_ee (code, VOIDmode, op0, op1);

  else if (SCALAR_FLOAT_MODE_P (GET_MODE (op0)))
    {
      gcc_assert (!DECIMAL_FLOAT_MODE_P (GET_MODE (op0)));
      ret = ix86_expand_fp_compare (code, op0, op1);
    }
  else
    ret = ix86_expand_int_compare (code, op0, op1);

  return ret;
}

void
ix86_expand_branch (enum rtx_code code, rtx op0, rtx op1, rtx label)
{
  machine_mode mode = GET_MODE (op0);
  rtx tmp;

  /* Handle special case - vector comparsion with boolean result, transform
     it using ptest instruction.  */
  if (GET_MODE_CLASS (mode) == MODE_VECTOR_INT)
    {
      rtx flag = gen_rtx_REG (CCZmode, FLAGS_REG);
      machine_mode p_mode = GET_MODE_SIZE (mode) == 32 ? V4DImode : V2DImode;

      gcc_assert (code == EQ || code == NE);
      /* Generate XOR since we can't check that one operand is zero vector.  */
      tmp = gen_reg_rtx (mode);
      emit_insn (gen_rtx_SET (tmp, gen_rtx_XOR (mode, op0, op1)));
      tmp = gen_lowpart (p_mode, tmp);
      emit_insn (gen_rtx_SET (gen_rtx_REG (CCmode, FLAGS_REG),
			      gen_rtx_UNSPEC (CCmode,
					      gen_rtvec (2, tmp, tmp),
					      UNSPEC_PTEST)));
      tmp = gen_rtx_fmt_ee (code, VOIDmode, flag, const0_rtx);
      tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
				  gen_rtx_LABEL_REF (VOIDmode, label),
				  pc_rtx);
      emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
      return;
    }

  switch (mode)
    {
    case E_SFmode:
    case E_DFmode:
    case E_XFmode:
    case E_QImode:
    case E_HImode:
    case E_SImode:
      simple:
      tmp = ix86_expand_compare (code, op0, op1);
      tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
				  gen_rtx_LABEL_REF (VOIDmode, label),
				  pc_rtx);
      emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
      return;

    case E_DImode:
      if (TARGET_64BIT)
	goto simple;
      /* For 32-bit target DI comparison may be performed on
	 SSE registers.  To allow this we should avoid split
	 to SI mode which is achieved by doing xor in DI mode
	 and then comparing with zero (which is recognized by
	 STV pass).  We don't compare using xor when optimizing
	 for size.  */
      if (!optimize_insn_for_size_p ()
	  && TARGET_STV
	  && (code == EQ || code == NE))
	{
	  op0 = force_reg (mode, gen_rtx_XOR (mode, op0, op1));
	  op1 = const0_rtx;
	}
      /* FALLTHRU */
    case E_TImode:
      /* Expand DImode branch into multiple compare+branch.  */
      {
	rtx lo[2], hi[2];
	rtx_code_label *label2;
	enum rtx_code code1, code2, code3;
	machine_mode submode;

	if (CONSTANT_P (op0) && !CONSTANT_P (op1))
	  {
	    std::swap (op0, op1);
	    code = swap_condition (code);
	  }

	split_double_mode (mode, &op0, 1, lo+0, hi+0);
	split_double_mode (mode, &op1, 1, lo+1, hi+1);

	submode = mode == DImode ? SImode : DImode;

	/* When comparing for equality, we can use (hi0^hi1)|(lo0^lo1) to
	   avoid two branches.  This costs one extra insn, so disable when
	   optimizing for size.  */

	if ((code == EQ || code == NE)
	    && (!optimize_insn_for_size_p ()
	        || hi[1] == const0_rtx || lo[1] == const0_rtx))
	  {
	    rtx xor0, xor1;

	    xor1 = hi[0];
	    if (hi[1] != const0_rtx)
	      xor1 = expand_binop (submode, xor_optab, xor1, hi[1],
				   NULL_RTX, 0, OPTAB_WIDEN);

	    xor0 = lo[0];
	    if (lo[1] != const0_rtx)
	      xor0 = expand_binop (submode, xor_optab, xor0, lo[1],
				   NULL_RTX, 0, OPTAB_WIDEN);

	    tmp = expand_binop (submode, ior_optab, xor1, xor0,
				NULL_RTX, 0, OPTAB_WIDEN);

	    ix86_expand_branch (code, tmp, const0_rtx, label);
	    return;
	  }

	/* Otherwise, if we are doing less-than or greater-or-equal-than,
	   op1 is a constant and the low word is zero, then we can just
	   examine the high word.  Similarly for low word -1 and
	   less-or-equal-than or greater-than.  */

	if (CONST_INT_P (hi[1]))
	  switch (code)
	    {
	    case LT: case LTU: case GE: case GEU:
	      if (lo[1] == const0_rtx)
		{
		  ix86_expand_branch (code, hi[0], hi[1], label);
		  return;
		}
	      break;
	    case LE: case LEU: case GT: case GTU:
	      if (lo[1] == constm1_rtx)
		{
		  ix86_expand_branch (code, hi[0], hi[1], label);
		  return;
		}
	      break;
	    default:
	      break;
	    }

	/* Emulate comparisons that do not depend on Zero flag with
	   double-word subtraction.  Note that only Overflow, Sign
	   and Carry flags are valid, so swap arguments and condition
	   of comparisons that would otherwise test Zero flag.  */

	switch (code)
	  {
	  case LE: case LEU: case GT: case GTU:
	    std::swap (lo[0], lo[1]);
	    std::swap (hi[0], hi[1]);
	    code = swap_condition (code);
	    /* FALLTHRU */

	  case LT: case LTU: case GE: case GEU:
	    {
	      rtx (*cmp_insn) (rtx, rtx);
	      rtx (*sbb_insn) (rtx, rtx, rtx);
	      bool uns = (code == LTU || code == GEU);

	      if (TARGET_64BIT)
		{
		  cmp_insn = gen_cmpdi_1;
		  sbb_insn
		    = uns ? gen_subdi3_carry_ccc : gen_subdi3_carry_ccgz;
		}
	      else
		{
		  cmp_insn = gen_cmpsi_1;
		  sbb_insn
		    = uns ? gen_subsi3_carry_ccc : gen_subsi3_carry_ccgz;
		}

	      if (!nonimmediate_operand (lo[0], submode))
		lo[0] = force_reg (submode, lo[0]);
	      if (!x86_64_general_operand (lo[1], submode))
		lo[1] = force_reg (submode, lo[1]);

	      if (!register_operand (hi[0], submode))
		hi[0] = force_reg (submode, hi[0]);
	      if ((uns && !nonimmediate_operand (hi[1], submode))
		  || (!uns && !x86_64_general_operand (hi[1], submode)))
		hi[1] = force_reg (submode, hi[1]);

	      emit_insn (cmp_insn (lo[0], lo[1]));
	      emit_insn (sbb_insn (gen_rtx_SCRATCH (submode), hi[0], hi[1]));

	      tmp = gen_rtx_REG (uns ? CCCmode : CCGZmode, FLAGS_REG);

	      ix86_expand_branch (code, tmp, const0_rtx, label);
	      return;
	    }

	  default:
	    break;
	  }

	/* Otherwise, we need two or three jumps.  */

	label2 = gen_label_rtx ();

	code1 = code;
	code2 = swap_condition (code);
	code3 = unsigned_condition (code);

	switch (code)
	  {
	  case LT: case GT: case LTU: case GTU:
	    break;

	  case LE:   code1 = LT;  code2 = GT;  break;
	  case GE:   code1 = GT;  code2 = LT;  break;
	  case LEU:  code1 = LTU; code2 = GTU; break;
	  case GEU:  code1 = GTU; code2 = LTU; break;

	  case EQ:   code1 = UNKNOWN; code2 = NE;  break;
	  case NE:   code2 = UNKNOWN; break;

	  default:
	    gcc_unreachable ();
	  }

	/*
	 * a < b =>
	 *    if (hi(a) < hi(b)) goto true;
	 *    if (hi(a) > hi(b)) goto false;
	 *    if (lo(a) < lo(b)) goto true;
	 *  false:
	 */

	if (code1 != UNKNOWN)
	  ix86_expand_branch (code1, hi[0], hi[1], label);
	if (code2 != UNKNOWN)
	  ix86_expand_branch (code2, hi[0], hi[1], label2);

	ix86_expand_branch (code3, lo[0], lo[1], label);

	if (code2 != UNKNOWN)
	  emit_label (label2);
	return;
      }

    default:
      gcc_assert (GET_MODE_CLASS (GET_MODE (op0)) == MODE_CC);
      goto simple;
    }
}

void
ix86_expand_setcc (rtx dest, enum rtx_code code, rtx op0, rtx op1)
{
  rtx ret;

  gcc_assert (GET_MODE (dest) == QImode);

  ret = ix86_expand_compare (code, op0, op1);
  PUT_MODE (ret, QImode);
  emit_insn (gen_rtx_SET (dest, ret));
}

/* Expand comparison setting or clearing carry flag.  Return true when
   successful and set pop for the operation.  */
static bool
ix86_expand_carry_flag_compare (enum rtx_code code, rtx op0, rtx op1, rtx *pop)
{
  machine_mode mode
    = GET_MODE (op0) != VOIDmode ? GET_MODE (op0) : GET_MODE (op1);

  /* Do not handle double-mode compares that go through special path.  */
  if (mode == (TARGET_64BIT ? TImode : DImode))
    return false;

  if (SCALAR_FLOAT_MODE_P (mode))
    {
      rtx compare_op;
      rtx_insn *compare_seq;

      gcc_assert (!DECIMAL_FLOAT_MODE_P (mode));

      /* Shortcut:  following common codes never translate
	 into carry flag compares.  */
      if (code == EQ || code == NE || code == UNEQ || code == LTGT
	  || code == ORDERED || code == UNORDERED)
	return false;

      /* These comparisons require zero flag; swap operands so they won't.  */
      if ((code == GT || code == UNLE || code == LE || code == UNGT)
	  && !TARGET_IEEE_FP)
	{
	  std::swap (op0, op1);
	  code = swap_condition (code);
	}

      /* Try to expand the comparison and verify that we end up with
	 carry flag based comparison.  This fails to be true only when
	 we decide to expand comparison using arithmetic that is not
	 too common scenario.  */
      start_sequence ();
      compare_op = ix86_expand_fp_compare (code, op0, op1);
      compare_seq = get_insns ();
      end_sequence ();

      if (GET_MODE (XEXP (compare_op, 0)) == CCFPmode)
        code = ix86_fp_compare_code_to_integer (GET_CODE (compare_op));
      else
	code = GET_CODE (compare_op);

      if (code != LTU && code != GEU)
	return false;

      emit_insn (compare_seq);
      *pop = compare_op;
      return true;
    }

  if (!INTEGRAL_MODE_P (mode))
    return false;

  switch (code)
    {
    case LTU:
    case GEU:
      break;

    /* Convert a==0 into (unsigned)a<1.  */
    case EQ:
    case NE:
      if (op1 != const0_rtx)
	return false;
      op1 = const1_rtx;
      code = (code == EQ ? LTU : GEU);
      break;

    /* Convert a>b into b<a or a>=b-1.  */
    case GTU:
    case LEU:
      if (CONST_INT_P (op1))
	{
	  op1 = gen_int_mode (INTVAL (op1) + 1, GET_MODE (op0));
	  /* Bail out on overflow.  We still can swap operands but that
	     would force loading of the constant into register.  */
	  if (op1 == const0_rtx
	      || !x86_64_immediate_operand (op1, GET_MODE (op1)))
	    return false;
	  code = (code == GTU ? GEU : LTU);
	}
      else
	{
	  std::swap (op0, op1);
	  code = (code == GTU ? LTU : GEU);
	}
      break;

    /* Convert a>=0 into (unsigned)a<0x80000000.  */
    case LT:
    case GE:
      if (mode == DImode || op1 != const0_rtx)
	return false;
      op1 = gen_int_mode (1 << (GET_MODE_BITSIZE (mode) - 1), mode);
      code = (code == LT ? GEU : LTU);
      break;
    case LE:
    case GT:
      if (mode == DImode || op1 != constm1_rtx)
	return false;
      op1 = gen_int_mode (1 << (GET_MODE_BITSIZE (mode) - 1), mode);
      code = (code == LE ? GEU : LTU);
      break;

    default:
      return false;
    }
  /* Swapping operands may cause constant to appear as first operand.  */
  if (!nonimmediate_operand (op0, VOIDmode))
    {
      if (!can_create_pseudo_p ())
	return false;
      op0 = force_reg (mode, op0);
    }
  *pop = ix86_expand_compare (code, op0, op1);
  gcc_assert (GET_CODE (*pop) == LTU || GET_CODE (*pop) == GEU);
  return true;
}

bool
ix86_expand_int_movcc (rtx operands[])
{
  enum rtx_code code = GET_CODE (operands[1]), compare_code;
  rtx_insn *compare_seq;
  rtx compare_op;
  machine_mode mode = GET_MODE (operands[0]);
  bool sign_bit_compare_p = false;
  rtx op0 = XEXP (operands[1], 0);
  rtx op1 = XEXP (operands[1], 1);

  if (GET_MODE (op0) == TImode
      || (GET_MODE (op0) == DImode
	  && !TARGET_64BIT))
    return false;

  start_sequence ();
  compare_op = ix86_expand_compare (code, op0, op1);
  compare_seq = get_insns ();
  end_sequence ();

  compare_code = GET_CODE (compare_op);

  if ((op1 == const0_rtx && (code == GE || code == LT))
      || (op1 == constm1_rtx && (code == GT || code == LE)))
    sign_bit_compare_p = true;

  /* Don't attempt mode expansion here -- if we had to expand 5 or 6
     HImode insns, we'd be swallowed in word prefix ops.  */

  if ((mode != HImode || TARGET_FAST_PREFIX)
      && (mode != (TARGET_64BIT ? TImode : DImode))
      && CONST_INT_P (operands[2])
      && CONST_INT_P (operands[3]))
    {
      rtx out = operands[0];
      HOST_WIDE_INT ct = INTVAL (operands[2]);
      HOST_WIDE_INT cf = INTVAL (operands[3]);
      HOST_WIDE_INT diff;

      diff = ct - cf;
      /*  Sign bit compares are better done using shifts than we do by using
	  sbb.  */
      if (sign_bit_compare_p
	  || ix86_expand_carry_flag_compare (code, op0, op1, &compare_op))
	{
	  /* Detect overlap between destination and compare sources.  */
	  rtx tmp = out;

          if (!sign_bit_compare_p)
	    {
	      rtx flags;
	      bool fpcmp = false;

	      compare_code = GET_CODE (compare_op);

	      flags = XEXP (compare_op, 0);

	      if (GET_MODE (flags) == CCFPmode)
		{
		  fpcmp = true;
		  compare_code
		    = ix86_fp_compare_code_to_integer (compare_code);
		}

	      /* To simplify rest of code, restrict to the GEU case.  */
	      if (compare_code == LTU)
		{
		  std::swap (ct, cf);
		  compare_code = reverse_condition (compare_code);
		  code = reverse_condition (code);
		}
	      else
		{
		  if (fpcmp)
		    PUT_CODE (compare_op,
			      reverse_condition_maybe_unordered
			        (GET_CODE (compare_op)));
		  else
		    PUT_CODE (compare_op,
			      reverse_condition (GET_CODE (compare_op)));
		}
	      diff = ct - cf;

	      if (reg_overlap_mentioned_p (out, op0)
		  || reg_overlap_mentioned_p (out, op1))
		tmp = gen_reg_rtx (mode);

	      if (mode == DImode)
		emit_insn (gen_x86_movdicc_0_m1 (tmp, flags, compare_op));
	      else
		emit_insn (gen_x86_movsicc_0_m1	(gen_lowpart (SImode, tmp),
						 flags, compare_op));
	    }
	  else
	    {
	      if (code == GT || code == GE)
		code = reverse_condition (code);
	      else
		{
		  std::swap (ct, cf);
		  diff = ct - cf;
		}
	      tmp = emit_store_flag (tmp, code, op0, op1, VOIDmode, 0, -1);
	    }

	  if (diff == 1)
	    {
	      /*
	       * cmpl op0,op1
	       * sbbl dest,dest
	       * [addl dest, ct]
	       *
	       * Size 5 - 8.
	       */
	      if (ct)
		tmp = expand_simple_binop (mode, PLUS,
					   tmp, GEN_INT (ct),
					   copy_rtx (tmp), 1, OPTAB_DIRECT);
	    }
	  else if (cf == -1)
	    {
	      /*
	       * cmpl op0,op1
	       * sbbl dest,dest
	       * orl $ct, dest
	       *
	       * Size 8.
	       */
	      tmp = expand_simple_binop (mode, IOR,
					 tmp, GEN_INT (ct),
					 copy_rtx (tmp), 1, OPTAB_DIRECT);
	    }
	  else if (diff == -1 && ct)
	    {
	      /*
	       * cmpl op0,op1
	       * sbbl dest,dest
	       * notl dest
	       * [addl dest, cf]
	       *
	       * Size 8 - 11.
	       */
	      tmp = expand_simple_unop (mode, NOT, tmp, copy_rtx (tmp), 1);
	      if (cf)
		tmp = expand_simple_binop (mode, PLUS,
					   copy_rtx (tmp), GEN_INT (cf),
					   copy_rtx (tmp), 1, OPTAB_DIRECT);
	    }
	  else
	    {
	      /*
	       * cmpl op0,op1
	       * sbbl dest,dest
	       * [notl dest]
	       * andl cf - ct, dest
	       * [addl dest, ct]
	       *
	       * Size 8 - 11.
	       */

	      if (cf == 0)
		{
		  cf = ct;
		  ct = 0;
		  tmp = expand_simple_unop (mode, NOT, tmp, copy_rtx (tmp), 1);
		}

	      tmp = expand_simple_binop (mode, AND,
					 copy_rtx (tmp),
					 gen_int_mode (cf - ct, mode),
					 copy_rtx (tmp), 1, OPTAB_DIRECT);
	      if (ct)
		tmp = expand_simple_binop (mode, PLUS,
					   copy_rtx (tmp), GEN_INT (ct),
					   copy_rtx (tmp), 1, OPTAB_DIRECT);
	    }

	  if (!rtx_equal_p (tmp, out))
	    emit_move_insn (copy_rtx (out), copy_rtx (tmp));

	  return true;
	}

      if (diff < 0)
	{
	  machine_mode cmp_mode = GET_MODE (op0);
	  enum rtx_code new_code;

	  if (SCALAR_FLOAT_MODE_P (cmp_mode))
	    {
	      gcc_assert (!DECIMAL_FLOAT_MODE_P (cmp_mode));

	      /* We may be reversing unordered compare to normal compare, that
		 is not valid in general (we may convert non-trapping condition
		 to trapping one), however on i386 we currently emit all
		 comparisons unordered.  */
	      new_code = reverse_condition_maybe_unordered (code);
	    }
	  else
	    new_code = ix86_reverse_condition (code, cmp_mode);
	  if (new_code != UNKNOWN)
	    {
	      std::swap (ct, cf);
	      diff = -diff;
	      code = new_code;
	    }
	}

      compare_code = UNKNOWN;
      if (GET_MODE_CLASS (GET_MODE (op0)) == MODE_INT
	  && CONST_INT_P (op1))
	{
	  if (op1 == const0_rtx
	      && (code == LT || code == GE))
	    compare_code = code;
	  else if (op1 == constm1_rtx)
	    {
	      if (code == LE)
		compare_code = LT;
	      else if (code == GT)
		compare_code = GE;
	    }
	}

      /* Optimize dest = (op0 < 0) ? -1 : cf.  */
      if (compare_code != UNKNOWN
	  && GET_MODE (op0) == GET_MODE (out)
	  && (cf == -1 || ct == -1))
	{
	  /* If lea code below could be used, only optimize
	     if it results in a 2 insn sequence.  */

	  if (! (diff == 1 || diff == 2 || diff == 4 || diff == 8
		 || diff == 3 || diff == 5 || diff == 9)
	      || (compare_code == LT && ct == -1)
	      || (compare_code == GE && cf == -1))
	    {
	      /*
	       * notl op1	(if necessary)
	       * sarl $31, op1
	       * orl cf, op1
	       */
	      if (ct != -1)
		{
		  cf = ct;
		  ct = -1;
		  code = reverse_condition (code);
		}

	      out = emit_store_flag (out, code, op0, op1, VOIDmode, 0, -1);

	      out = expand_simple_binop (mode, IOR,
					 out, GEN_INT (cf),
					 out, 1, OPTAB_DIRECT);
	      if (out != operands[0])
		emit_move_insn (operands[0], out);

	      return true;
	    }
	}


      if ((diff == 1 || diff == 2 || diff == 4 || diff == 8
	   || diff == 3 || diff == 5 || diff == 9)
	  && ((mode != QImode && mode != HImode) || !TARGET_PARTIAL_REG_STALL)
	  && (mode != DImode
	      || x86_64_immediate_operand (GEN_INT (cf), VOIDmode)))
	{
	  /*
	   * xorl dest,dest
	   * cmpl op1,op2
	   * setcc dest
	   * lea cf(dest*(ct-cf)),dest
	   *
	   * Size 14.
	   *
	   * This also catches the degenerate setcc-only case.
	   */

	  rtx tmp;
	  int nops;

	  out = emit_store_flag (out, code, op0, op1, VOIDmode, 0, 1);

	  nops = 0;
	  /* On x86_64 the lea instruction operates on Pmode, so we need
	     to get arithmetics done in proper mode to match.  */
	  if (diff == 1)
	    tmp = copy_rtx (out);
	  else
	    {
	      rtx out1;
	      out1 = copy_rtx (out);
	      tmp = gen_rtx_MULT (mode, out1, GEN_INT (diff & ~1));
	      nops++;
	      if (diff & 1)
		{
		  tmp = gen_rtx_PLUS (mode, tmp, out1);
		  nops++;
		}
	    }
	  if (cf != 0)
	    {
	      tmp = gen_rtx_PLUS (mode, tmp, GEN_INT (cf));
	      nops++;
	    }
	  if (!rtx_equal_p (tmp, out))
	    {
	      if (nops == 1)
		out = force_operand (tmp, copy_rtx (out));
	      else
		emit_insn (gen_rtx_SET (copy_rtx (out), copy_rtx (tmp)));
	    }
	  if (!rtx_equal_p (out, operands[0]))
	    emit_move_insn (operands[0], copy_rtx (out));

	  return true;
	}

      /*
       * General case:			Jumpful:
       *   xorl dest,dest		cmpl op1, op2
       *   cmpl op1, op2		movl ct, dest
       *   setcc dest			jcc 1f
       *   decl dest			movl cf, dest
       *   andl (cf-ct),dest		1:
       *   addl ct,dest
       *
       * Size 20.			Size 14.
       *
       * This is reasonably steep, but branch mispredict costs are
       * high on modern cpus, so consider failing only if optimizing
       * for space.
       */

      if ((!TARGET_CMOVE || (mode == QImode && TARGET_PARTIAL_REG_STALL))
	  && BRANCH_COST (optimize_insn_for_speed_p (),
		  	  false) >= 2)
	{
	  if (cf == 0)
	    {
	      machine_mode cmp_mode = GET_MODE (op0);
	      enum rtx_code new_code;

	      if (SCALAR_FLOAT_MODE_P (cmp_mode))
		{
		  gcc_assert (!DECIMAL_FLOAT_MODE_P (cmp_mode));

		  /* We may be reversing unordered compare to normal compare,
		     that is not valid in general (we may convert non-trapping
		     condition to trapping one), however on i386 we currently
		     emit all comparisons unordered.  */
		  new_code = reverse_condition_maybe_unordered (code);
		}
	      else
		{
		  new_code = ix86_reverse_condition (code, cmp_mode);
		  if (compare_code != UNKNOWN && new_code != UNKNOWN)
		    compare_code = reverse_condition (compare_code);
		}

	      if (new_code != UNKNOWN)
		{
		  cf = ct;
		  ct = 0;
		  code = new_code;
		}
	    }

	  if (compare_code != UNKNOWN)
	    {
	      /* notl op1	(if needed)
		 sarl $31, op1
		 andl (cf-ct), op1
		 addl ct, op1

		 For x < 0 (resp. x <= -1) there will be no notl,
		 so if possible swap the constants to get rid of the
		 complement.
		 True/false will be -1/0 while code below (store flag
		 followed by decrement) is 0/-1, so the constants need
		 to be exchanged once more.  */

	      if (compare_code == GE || !cf)
		{
		  code = reverse_condition (code);
		  compare_code = LT;
		}
	      else
		std::swap (ct, cf);

	      out = emit_store_flag (out, code, op0, op1, VOIDmode, 0, -1);
	    }
	  else
	    {
	      out = emit_store_flag (out, code, op0, op1, VOIDmode, 0, 1);

	      out = expand_simple_binop (mode, PLUS, copy_rtx (out),
					 constm1_rtx,
					 copy_rtx (out), 1, OPTAB_DIRECT);
	    }

	  out = expand_simple_binop (mode, AND, copy_rtx (out),
				     gen_int_mode (cf - ct, mode),
				     copy_rtx (out), 1, OPTAB_DIRECT);
	  if (ct)
	    out = expand_simple_binop (mode, PLUS, copy_rtx (out), GEN_INT (ct),
				       copy_rtx (out), 1, OPTAB_DIRECT);
	  if (!rtx_equal_p (out, operands[0]))
	    emit_move_insn (operands[0], copy_rtx (out));

	  return true;
	}
    }

  if (!TARGET_CMOVE || (mode == QImode && TARGET_PARTIAL_REG_STALL))
    {
      /* Try a few things more with specific constants and a variable.  */

      optab op;
      rtx var, orig_out, out, tmp;

      if (BRANCH_COST (optimize_insn_for_speed_p (), false) <= 2)
	return false;

      /* If one of the two operands is an interesting constant, load a
	 constant with the above and mask it in with a logical operation.  */

      if (CONST_INT_P (operands[2]))
	{
	  var = operands[3];
	  if (INTVAL (operands[2]) == 0 && operands[3] != constm1_rtx)
	    operands[3] = constm1_rtx, op = and_optab;
	  else if (INTVAL (operands[2]) == -1 && operands[3] != const0_rtx)
	    operands[3] = const0_rtx, op = ior_optab;
	  else
	    return false;
	}
      else if (CONST_INT_P (operands[3]))
	{
	  var = operands[2];
	  if (INTVAL (operands[3]) == 0 && operands[2] != constm1_rtx)
	    operands[2] = constm1_rtx, op = and_optab;
	  else if (INTVAL (operands[3]) == -1 && operands[3] != const0_rtx)
	    operands[2] = const0_rtx, op = ior_optab;
	  else
	    return false;
	}
      else
        return false;

      orig_out = operands[0];
      tmp = gen_reg_rtx (mode);
      operands[0] = tmp;

      /* Recurse to get the constant loaded.  */
      if (!ix86_expand_int_movcc (operands))
        return false;

      /* Mask in the interesting variable.  */
      out = expand_binop (mode, op, var, tmp, orig_out, 0,
			  OPTAB_WIDEN);
      if (!rtx_equal_p (out, orig_out))
	emit_move_insn (copy_rtx (orig_out), copy_rtx (out));

      return true;
    }

  /*
   * For comparison with above,
   *
   * movl cf,dest
   * movl ct,tmp
   * cmpl op1,op2
   * cmovcc tmp,dest
   *
   * Size 15.
   */

  if (! nonimmediate_operand (operands[2], mode))
    operands[2] = force_reg (mode, operands[2]);
  if (! nonimmediate_operand (operands[3], mode))
    operands[3] = force_reg (mode, operands[3]);

  if (! register_operand (operands[2], VOIDmode)
      && (mode == QImode
          || ! register_operand (operands[3], VOIDmode)))
    operands[2] = force_reg (mode, operands[2]);

  if (mode == QImode
      && ! register_operand (operands[3], VOIDmode))
    operands[3] = force_reg (mode, operands[3]);

  emit_insn (compare_seq);
  emit_insn (gen_rtx_SET (operands[0],
			  gen_rtx_IF_THEN_ELSE (mode,
						compare_op, operands[2],
						operands[3])));
  return true;
}

/* Swap, force into registers, or otherwise massage the two operands
   to an sse comparison with a mask result.  Thus we differ a bit from
   ix86_prepare_fp_compare_args which expects to produce a flags result.

   The DEST operand exists to help determine whether to commute commutative
   operators.  The POP0/POP1 operands are updated in place.  The new
   comparison code is returned, or UNKNOWN if not implementable.  */

static enum rtx_code
ix86_prepare_sse_fp_compare_args (rtx dest, enum rtx_code code,
				  rtx *pop0, rtx *pop1)
{
  switch (code)
    {
    case LTGT:
    case UNEQ:
      /* AVX supports all the needed comparisons.  */
      if (TARGET_AVX)
	break;
      /* We have no LTGT as an operator.  We could implement it with
	 NE & ORDERED, but this requires an extra temporary.  It's
	 not clear that it's worth it.  */
      return UNKNOWN;

    case LT:
    case LE:
    case UNGT:
    case UNGE:
      /* These are supported directly.  */
      break;

    case EQ:
    case NE:
    case UNORDERED:
    case ORDERED:
      /* AVX has 3 operand comparisons, no need to swap anything.  */
      if (TARGET_AVX)
	break;
      /* For commutative operators, try to canonicalize the destination
	 operand to be first in the comparison - this helps reload to
	 avoid extra moves.  */
      if (!dest || !rtx_equal_p (dest, *pop1))
	break;
      /* FALLTHRU */

    case GE:
    case GT:
    case UNLE:
    case UNLT:
      /* These are not supported directly before AVX, and furthermore
	 ix86_expand_sse_fp_minmax only optimizes LT/UNGE.  Swap the
	 comparison operands to transform into something that is
	 supported.  */
      std::swap (*pop0, *pop1);
      code = swap_condition (code);
      break;

    default:
      gcc_unreachable ();
    }

  return code;
}

/* Detect conditional moves that exactly match min/max operational
   semantics.  Note that this is IEEE safe, as long as we don't
   interchange the operands.

   Returns FALSE if this conditional move doesn't match a MIN/MAX,
   and TRUE if the operation is successful and instructions are emitted.  */

static bool
ix86_expand_sse_fp_minmax (rtx dest, enum rtx_code code, rtx cmp_op0,
			   rtx cmp_op1, rtx if_true, rtx if_false)
{
  machine_mode mode;
  bool is_min;
  rtx tmp;

  if (code == LT)
    ;
  else if (code == UNGE)
    std::swap (if_true, if_false);
  else
    return false;

  if (rtx_equal_p (cmp_op0, if_true) && rtx_equal_p (cmp_op1, if_false))
    is_min = true;
  else if (rtx_equal_p (cmp_op1, if_true) && rtx_equal_p (cmp_op0, if_false))
    is_min = false;
  else
    return false;

  mode = GET_MODE (dest);

  /* We want to check HONOR_NANS and HONOR_SIGNED_ZEROS here,
     but MODE may be a vector mode and thus not appropriate.  */
  if (!flag_finite_math_only || flag_signed_zeros)
    {
      int u = is_min ? UNSPEC_IEEE_MIN : UNSPEC_IEEE_MAX;
      rtvec v;

      if_true = force_reg (mode, if_true);
      v = gen_rtvec (2, if_true, if_false);
      tmp = gen_rtx_UNSPEC (mode, v, u);
    }
  else
    {
      code = is_min ? SMIN : SMAX;
      tmp = gen_rtx_fmt_ee (code, mode, if_true, if_false);
    }

  emit_insn (gen_rtx_SET (dest, tmp));
  return true;
}

/* Expand an SSE comparison.  Return the register with the result.  */

static rtx
ix86_expand_sse_cmp (rtx dest, enum rtx_code code, rtx cmp_op0, rtx cmp_op1,
		     rtx op_true, rtx op_false)
{
  machine_mode mode = GET_MODE (dest);
  machine_mode cmp_ops_mode = GET_MODE (cmp_op0);

  /* In general case result of comparison can differ from operands' type.  */
  machine_mode cmp_mode;

  /* In AVX512F the result of comparison is an integer mask.  */
  bool maskcmp = false;
  rtx x;

  if (GET_MODE_SIZE (cmp_ops_mode) == 64)
    {
      unsigned int nbits = GET_MODE_NUNITS (cmp_ops_mode);
      cmp_mode = int_mode_for_size (nbits, 0).require ();
      maskcmp = true;
    }
  else
    cmp_mode = cmp_ops_mode;

  cmp_op0 = force_reg (cmp_ops_mode, cmp_op0);

  int (*op1_predicate)(rtx, machine_mode)
    = VECTOR_MODE_P (cmp_ops_mode) ? vector_operand : nonimmediate_operand;

  if (!op1_predicate (cmp_op1, cmp_ops_mode))
    cmp_op1 = force_reg (cmp_ops_mode, cmp_op1);

  if (optimize
      || (maskcmp && cmp_mode != mode)
      || (op_true && reg_overlap_mentioned_p (dest, op_true))
      || (op_false && reg_overlap_mentioned_p (dest, op_false)))
    dest = gen_reg_rtx (maskcmp ? cmp_mode : mode);

  /* Compare patterns for int modes are unspec in AVX512F only.  */
  if (maskcmp && (code == GT || code == EQ))
    {
      rtx (*gen)(rtx, rtx, rtx);

      switch (cmp_ops_mode)
	{
	case E_V64QImode:
	  gcc_assert (TARGET_AVX512BW);
	  gen = code == GT ? gen_avx512bw_gtv64qi3 : gen_avx512bw_eqv64qi3_1;
	  break;
	case E_V32HImode:
	  gcc_assert (TARGET_AVX512BW);
	  gen = code == GT ? gen_avx512bw_gtv32hi3 : gen_avx512bw_eqv32hi3_1;
	  break;
	case E_V16SImode:
	  gen = code == GT ? gen_avx512f_gtv16si3 : gen_avx512f_eqv16si3_1;
	  break;
	case E_V8DImode:
	  gen = code == GT ? gen_avx512f_gtv8di3 : gen_avx512f_eqv8di3_1;
	  break;
	default:
	  gen = NULL;
	}

      if (gen)
	{
	  emit_insn (gen (dest, cmp_op0, cmp_op1));
	  return dest;
	}
    }
  x = gen_rtx_fmt_ee (code, cmp_mode, cmp_op0, cmp_op1);

  if (cmp_mode != mode && !maskcmp)
    {
      x = force_reg (cmp_ops_mode, x);
      convert_move (dest, x, false);
    }
  else
    emit_insn (gen_rtx_SET (dest, x));

  return dest;
}

/* Expand DEST = CMP ? OP_TRUE : OP_FALSE into a sequence of logical
   operations.  This is used for both scalar and vector conditional moves.  */

void
ix86_expand_sse_movcc (rtx dest, rtx cmp, rtx op_true, rtx op_false)
{
  machine_mode mode = GET_MODE (dest);
  machine_mode cmpmode = GET_MODE (cmp);

  /* In AVX512F the result of comparison is an integer mask.  */
  bool maskcmp = (mode != cmpmode && TARGET_AVX512F);

  rtx t2, t3, x;

  /* If we have an integer mask and FP value then we need
     to cast mask to FP mode.  */
  if (mode != cmpmode && VECTOR_MODE_P (cmpmode))
    {
      cmp = force_reg (cmpmode, cmp);
      cmp = gen_rtx_SUBREG (mode, cmp, 0);
    }

  if (maskcmp)
    {
      rtx (*gen) (rtx, rtx) = NULL;
      if ((op_true == CONST0_RTX (mode)
	   && vector_all_ones_operand (op_false, mode))
	  || (op_false == CONST0_RTX (mode)
	      && vector_all_ones_operand (op_true, mode)))
	switch (mode)
	  {
	  case E_V64QImode:
	    if (TARGET_AVX512BW)
	      gen = gen_avx512bw_cvtmask2bv64qi;
	    break;
	  case E_V32QImode:
	    if (TARGET_AVX512VL && TARGET_AVX512BW)
	      gen = gen_avx512vl_cvtmask2bv32qi;
	    break;
	  case E_V16QImode:
	    if (TARGET_AVX512VL && TARGET_AVX512BW)
	      gen = gen_avx512vl_cvtmask2bv16qi;
	    break;
	  case E_V32HImode:
	    if (TARGET_AVX512BW)
	      gen = gen_avx512bw_cvtmask2wv32hi;
	    break;
	  case E_V16HImode:
	    if (TARGET_AVX512VL && TARGET_AVX512BW)
	      gen = gen_avx512vl_cvtmask2wv16hi;
	    break;
	  case E_V8HImode:
	    if (TARGET_AVX512VL && TARGET_AVX512BW)
	      gen = gen_avx512vl_cvtmask2wv8hi;
	    break;
	  case E_V16SImode:
	    if (TARGET_AVX512DQ)
	      gen = gen_avx512f_cvtmask2dv16si;
	    break;
	  case E_V8SImode:
	    if (TARGET_AVX512VL && TARGET_AVX512DQ)
	      gen = gen_avx512vl_cvtmask2dv8si;
	    break;
	  case E_V4SImode:
	    if (TARGET_AVX512VL && TARGET_AVX512DQ)
	      gen = gen_avx512vl_cvtmask2dv4si;
	    break;
	  case E_V8DImode:
	    if (TARGET_AVX512DQ)
	      gen = gen_avx512f_cvtmask2qv8di;
	    break;
	  case E_V4DImode:
	    if (TARGET_AVX512VL && TARGET_AVX512DQ)
	      gen = gen_avx512vl_cvtmask2qv4di;
	    break;
	  case E_V2DImode:
	    if (TARGET_AVX512VL && TARGET_AVX512DQ)
	      gen = gen_avx512vl_cvtmask2qv2di;
	    break;
	  default:
	    break;
	  }
      if (gen && SCALAR_INT_MODE_P (cmpmode))
	{
	  cmp = force_reg (cmpmode, cmp);
	  if (op_true == CONST0_RTX (mode))
	    {
	      rtx (*gen_not) (rtx, rtx);
	      switch (cmpmode)
		{
		case E_QImode: gen_not = gen_knotqi; break;
		case E_HImode: gen_not = gen_knothi; break;
		case E_SImode: gen_not = gen_knotsi; break;
		case E_DImode: gen_not = gen_knotdi; break;
		default: gcc_unreachable ();
		}
	      rtx n = gen_reg_rtx (cmpmode);
	      emit_insn (gen_not (n, cmp));
	      cmp = n;
	    }
	  emit_insn (gen (dest, cmp));
	  return;
	}
    }
  else if (vector_all_ones_operand (op_true, mode)
	   && op_false == CONST0_RTX (mode))
    {
      emit_insn (gen_rtx_SET (dest, cmp));
      return;
    }
  else if (op_false == CONST0_RTX (mode))
    {
      op_true = force_reg (mode, op_true);
      x = gen_rtx_AND (mode, cmp, op_true);
      emit_insn (gen_rtx_SET (dest, x));
      return;
    }
  else if (op_true == CONST0_RTX (mode))
    {
      op_false = force_reg (mode, op_false);
      x = gen_rtx_NOT (mode, cmp);
      x = gen_rtx_AND (mode, x, op_false);
      emit_insn (gen_rtx_SET (dest, x));
      return;
    }
  else if (INTEGRAL_MODE_P (mode) && op_true == CONSTM1_RTX (mode))
    {
      op_false = force_reg (mode, op_false);
      x = gen_rtx_IOR (mode, cmp, op_false);
      emit_insn (gen_rtx_SET (dest, x));
      return;
    }
  else if (TARGET_XOP)
    {
      op_true = force_reg (mode, op_true);

      if (!nonimmediate_operand (op_false, mode))
	op_false = force_reg (mode, op_false);

      emit_insn (gen_rtx_SET (dest, gen_rtx_IF_THEN_ELSE (mode, cmp,
							  op_true,
							  op_false)));
      return;
    }

  rtx (*gen) (rtx, rtx, rtx, rtx) = NULL;
  rtx d = dest;

  if (!vector_operand (op_true, mode))
    op_true = force_reg (mode, op_true);

  op_false = force_reg (mode, op_false);

  switch (mode)
    {
    case E_V4SFmode:
      if (TARGET_SSE4_1)
	gen = gen_sse4_1_blendvps;
      break;
    case E_V2DFmode:
      if (TARGET_SSE4_1)
	gen = gen_sse4_1_blendvpd;
      break;
    case E_SFmode:
      if (TARGET_SSE4_1)
	{
	  gen = gen_sse4_1_blendvss;
	  op_true = force_reg (mode, op_true);
	}
      break;
    case E_DFmode:
      if (TARGET_SSE4_1)
	{
	  gen = gen_sse4_1_blendvsd;
	  op_true = force_reg (mode, op_true);
	}
      break;
    case E_V16QImode:
    case E_V8HImode:
    case E_V4SImode:
    case E_V2DImode:
      if (TARGET_SSE4_1)
	{
	  gen = gen_sse4_1_pblendvb;
	  if (mode != V16QImode)
	    d = gen_reg_rtx (V16QImode);
	  op_false = gen_lowpart (V16QImode, op_false);
	  op_true = gen_lowpart (V16QImode, op_true);
	  cmp = gen_lowpart (V16QImode, cmp);
	}
      break;
    case E_V8SFmode:
      if (TARGET_AVX)
	gen = gen_avx_blendvps256;
      break;
    case E_V4DFmode:
      if (TARGET_AVX)
	gen = gen_avx_blendvpd256;
      break;
    case E_V32QImode:
    case E_V16HImode:
    case E_V8SImode:
    case E_V4DImode:
      if (TARGET_AVX2)
	{
	  gen = gen_avx2_pblendvb;
	  if (mode != V32QImode)
	    d = gen_reg_rtx (V32QImode);
	  op_false = gen_lowpart (V32QImode, op_false);
	  op_true = gen_lowpart (V32QImode, op_true);
	  cmp = gen_lowpart (V32QImode, cmp);
	}
      break;

    case E_V64QImode:
      gen = gen_avx512bw_blendmv64qi;
      break;
    case E_V32HImode:
      gen = gen_avx512bw_blendmv32hi;
      break;
    case E_V16SImode:
      gen = gen_avx512f_blendmv16si;
      break;
    case E_V8DImode:
      gen = gen_avx512f_blendmv8di;
      break;
    case E_V8DFmode:
      gen = gen_avx512f_blendmv8df;
      break;
    case E_V16SFmode:
      gen = gen_avx512f_blendmv16sf;
      break;

    default:
      break;
    }

  if (gen != NULL)
    {
      emit_insn (gen (d, op_false, op_true, cmp));
      if (d != dest)
	emit_move_insn (dest, gen_lowpart (GET_MODE (dest), d));
    }
  else
    {
      op_true = force_reg (mode, op_true);

      t2 = gen_reg_rtx (mode);
      if (optimize)
	t3 = gen_reg_rtx (mode);
      else
	t3 = dest;

      x = gen_rtx_AND (mode, op_true, cmp);
      emit_insn (gen_rtx_SET (t2, x));

      x = gen_rtx_NOT (mode, cmp);
      x = gen_rtx_AND (mode, x, op_false);
      emit_insn (gen_rtx_SET (t3, x));

      x = gen_rtx_IOR (mode, t3, t2);
      emit_insn (gen_rtx_SET (dest, x));
    }
}

/* Expand a floating-point conditional move.  Return true if successful.  */

bool
ix86_expand_fp_movcc (rtx operands[])
{
  machine_mode mode = GET_MODE (operands[0]);
  enum rtx_code code = GET_CODE (operands[1]);
  rtx tmp, compare_op;
  rtx op0 = XEXP (operands[1], 0);
  rtx op1 = XEXP (operands[1], 1);

  if (TARGET_SSE_MATH && SSE_FLOAT_MODE_P (mode))
    {
      machine_mode cmode;

      /* Since we've no cmove for sse registers, don't force bad register
	 allocation just to gain access to it.  Deny movcc when the
	 comparison mode doesn't match the move mode.  */
      cmode = GET_MODE (op0);
      if (cmode == VOIDmode)
	cmode = GET_MODE (op1);
      if (cmode != mode)
	return false;

      code = ix86_prepare_sse_fp_compare_args (operands[0], code, &op0, &op1);
      if (code == UNKNOWN)
	return false;

      if (ix86_expand_sse_fp_minmax (operands[0], code, op0, op1,
				     operands[2], operands[3]))
	return true;

      tmp = ix86_expand_sse_cmp (operands[0], code, op0, op1,
				 operands[2], operands[3]);
      ix86_expand_sse_movcc (operands[0], tmp, operands[2], operands[3]);
      return true;
    }

  if (GET_MODE (op0) == TImode
      || (GET_MODE (op0) == DImode
	  && !TARGET_64BIT))
    return false;

  /* The floating point conditional move instructions don't directly
     support conditions resulting from a signed integer comparison.  */

  compare_op = ix86_expand_compare (code, op0, op1);
  if (!fcmov_comparison_operator (compare_op, VOIDmode))
    {
      tmp = gen_reg_rtx (QImode);
      ix86_expand_setcc (tmp, code, op0, op1);

      compare_op = ix86_expand_compare (NE, tmp, const0_rtx);
    }

  emit_insn (gen_rtx_SET (operands[0],
			  gen_rtx_IF_THEN_ELSE (mode, compare_op,
						operands[2], operands[3])));

  return true;
}

/* Helper for ix86_cmp_code_to_pcmp_immediate for int modes.  */

static int
ix86_int_cmp_code_to_pcmp_immediate (enum rtx_code code)
{
  switch (code)
    {
    case EQ:
      return 0;
    case LT:
    case LTU:
      return 1;
    case LE:
    case LEU:
      return 2;
    case NE:
      return 4;
    case GE:
    case GEU:
      return 5;
    case GT:
    case GTU:
      return 6;
    default:
      gcc_unreachable ();
    }
}

/* Helper for ix86_cmp_code_to_pcmp_immediate for fp modes.  */

static int
ix86_fp_cmp_code_to_pcmp_immediate (enum rtx_code code)
{
  switch (code)
    {
    case EQ:
      return 0x00;
    case NE:
      return 0x04;
    case GT:
      return 0x0e;
    case LE:
      return 0x02;
    case GE:
      return 0x0d;
    case LT:
      return 0x01;
    case UNLE:
      return 0x0a;
    case UNLT:
      return 0x09;
    case UNGE:
      return 0x05;
    case UNGT:
      return 0x06;
    case UNEQ:
      return 0x18;
    case LTGT:
      return 0x0c;
    case ORDERED:
      return 0x07;
    case UNORDERED:
      return 0x03;
    default:
      gcc_unreachable ();
    }
}

/* Return immediate value to be used in UNSPEC_PCMP
   for comparison CODE in MODE.  */

static int
ix86_cmp_code_to_pcmp_immediate (enum rtx_code code, machine_mode mode)
{
  if (FLOAT_MODE_P (mode))
    return ix86_fp_cmp_code_to_pcmp_immediate (code);
  return ix86_int_cmp_code_to_pcmp_immediate (code);
}

/* Expand AVX-512 vector comparison.  */

bool
ix86_expand_mask_vec_cmp (rtx operands[])
{
  machine_mode mask_mode = GET_MODE (operands[0]);
  machine_mode cmp_mode = GET_MODE (operands[2]);
  enum rtx_code code = GET_CODE (operands[1]);
  rtx imm = GEN_INT (ix86_cmp_code_to_pcmp_immediate (code, cmp_mode));
  int unspec_code;
  rtx unspec;

  switch (code)
    {
    case LEU:
    case GTU:
    case GEU:
    case LTU:
      unspec_code = UNSPEC_UNSIGNED_PCMP;
      break;

    default:
      unspec_code = UNSPEC_PCMP;
    }

  unspec = gen_rtx_UNSPEC (mask_mode, gen_rtvec (3, operands[2],
						 operands[3], imm),
			   unspec_code);
  emit_insn (gen_rtx_SET (operands[0], unspec));

  return true;
}

/* Expand fp vector comparison.  */

bool
ix86_expand_fp_vec_cmp (rtx operands[])
{
  enum rtx_code code = GET_CODE (operands[1]);
  rtx cmp;

  code = ix86_prepare_sse_fp_compare_args (operands[0], code,
					   &operands[2], &operands[3]);
  if (code == UNKNOWN)
    {
      rtx temp;
      switch (GET_CODE (operands[1]))
	{
	case LTGT:
	  temp = ix86_expand_sse_cmp (operands[0], ORDERED, operands[2],
				      operands[3], NULL, NULL);
	  cmp = ix86_expand_sse_cmp (operands[0], NE, operands[2],
				     operands[3], NULL, NULL);
	  code = AND;
	  break;
	case UNEQ:
	  temp = ix86_expand_sse_cmp (operands[0], UNORDERED, operands[2],
				      operands[3], NULL, NULL);
	  cmp = ix86_expand_sse_cmp (operands[0], EQ, operands[2],
				     operands[3], NULL, NULL);
	  code = IOR;
	  break;
	default:
	  gcc_unreachable ();
	}
      cmp = expand_simple_binop (GET_MODE (cmp), code, temp, cmp, cmp, 1,
				 OPTAB_DIRECT);
    }
  else
    cmp = ix86_expand_sse_cmp (operands[0], code, operands[2], operands[3],
			       operands[1], operands[2]);

  if (operands[0] != cmp)
    emit_move_insn (operands[0], cmp);

  return true;
}

static rtx
ix86_expand_int_sse_cmp (rtx dest, enum rtx_code code, rtx cop0, rtx cop1,
			 rtx op_true, rtx op_false, bool *negate)
{
  machine_mode data_mode = GET_MODE (dest);
  machine_mode mode = GET_MODE (cop0);
  rtx x;

  *negate = false;

  /* XOP supports all of the comparisons on all 128-bit vector int types.  */
  if (TARGET_XOP
      && (mode == V16QImode || mode == V8HImode
	  || mode == V4SImode || mode == V2DImode))
    ;
  else
    {
      /* Canonicalize the comparison to EQ, GT, GTU.  */
      switch (code)
	{
	case EQ:
	case GT:
	case GTU:
	  break;

	case NE:
	case LE:
	case LEU:
	  code = reverse_condition (code);
	  *negate = true;
	  break;

	case GE:
	case GEU:
	  code = reverse_condition (code);
	  *negate = true;
	  /* FALLTHRU */

	case LT:
	case LTU:
	  std::swap (cop0, cop1);
	  code = swap_condition (code);
	  break;

	default:
	  gcc_unreachable ();
	}

      /* Only SSE4.1/SSE4.2 supports V2DImode.  */
      if (mode == V2DImode)
	{
	  switch (code)
	    {
	    case EQ:
	      /* SSE4.1 supports EQ.  */
	      if (!TARGET_SSE4_1)
		return NULL;
	      break;

	    case GT:
	    case GTU:
	      /* SSE4.2 supports GT/GTU.  */
	      if (!TARGET_SSE4_2)
		return NULL;
	      break;

	    default:
	      gcc_unreachable ();
	    }
	}

      rtx optrue = op_true ? op_true : CONSTM1_RTX (data_mode);
      rtx opfalse = op_false ? op_false : CONST0_RTX (data_mode);
      if (*negate)
	std::swap (optrue, opfalse);

      /* Transform x > y ? 0 : -1 (i.e. x <= y ? -1 : 0 or x <= y) when
	 not using integer masks into min (x, y) == x ? -1 : 0 (i.e.
	 min (x, y) == x).  While we add one instruction (the minimum),
	 we remove the need for two instructions in the negation, as the
	 result is done this way.
	 When using masks, do it for SI/DImode element types, as it is shorter
	 than the two subtractions.  */
      if ((code != EQ
	   && GET_MODE_SIZE (mode) != 64
	   && vector_all_ones_operand (opfalse, data_mode)
	   && optrue == CONST0_RTX (data_mode))
	  || (code == GTU
	      && GET_MODE_SIZE (GET_MODE_INNER (mode)) >= 4
	      /* Don't do it if not using integer masks and we'd end up with
		 the right values in the registers though.  */
	      && (GET_MODE_SIZE (mode) == 64
		  || !vector_all_ones_operand (optrue, data_mode)
		  || opfalse != CONST0_RTX (data_mode))))
	{
	  rtx (*gen) (rtx, rtx, rtx) = NULL;

	  switch (mode)
	    {
	    case E_V16SImode:
	      gen = (code == GTU) ? gen_uminv16si3 : gen_sminv16si3;
	      break;
	    case E_V8DImode:
	      gen = (code == GTU) ? gen_uminv8di3 : gen_sminv8di3;
	      cop0 = force_reg (mode, cop0);
	      cop1 = force_reg (mode, cop1);
	      break;
	    case E_V32QImode:
	      if (TARGET_AVX2)
		gen = (code == GTU) ? gen_uminv32qi3 : gen_sminv32qi3;
	      break;
	    case E_V16HImode:
	      if (TARGET_AVX2)
		gen = (code == GTU) ? gen_uminv16hi3 : gen_sminv16hi3;
	      break;
	    case E_V8SImode:
	      if (TARGET_AVX2)
		gen = (code == GTU) ? gen_uminv8si3 : gen_sminv8si3;
	      break;
	    case E_V4DImode:
	      if (TARGET_AVX512VL)
		{
		  gen = (code == GTU) ? gen_uminv4di3 : gen_sminv4di3;
		  cop0 = force_reg (mode, cop0);
		  cop1 = force_reg (mode, cop1);
		}
	      break;
	    case E_V16QImode:
	      if (code == GTU && TARGET_SSE2)
		gen = gen_uminv16qi3;
	      else if (code == GT && TARGET_SSE4_1)
		gen = gen_sminv16qi3;
	      break;
	    case E_V8HImode:
	      if (code == GTU && TARGET_SSE4_1)
		gen = gen_uminv8hi3;
	      else if (code == GT && TARGET_SSE2)
		gen = gen_sminv8hi3;
	      break;
	    case E_V4SImode:
	      if (TARGET_SSE4_1)
		gen = (code == GTU) ? gen_uminv4si3 : gen_sminv4si3;
	      break;
	    case E_V2DImode:
	      if (TARGET_AVX512VL)
		{
		  gen = (code == GTU) ? gen_uminv2di3 : gen_sminv2di3;
		  cop0 = force_reg (mode, cop0);
		  cop1 = force_reg (mode, cop1);
		}
	      break;
	    default:
	      break;
	    }

	  if (gen)
	    {
	      rtx tem = gen_reg_rtx (mode);
	      if (!vector_operand (cop0, mode))
		cop0 = force_reg (mode, cop0);
	      if (!vector_operand (cop1, mode))
		cop1 = force_reg (mode, cop1);
	      *negate = !*negate;
	      emit_insn (gen (tem, cop0, cop1));
	      cop1 = tem;
	      code = EQ;
	    }
	}

      /* Unsigned parallel compare is not supported by the hardware.
	 Play some tricks to turn this into a signed comparison
	 against 0.  */
      if (code == GTU)
	{
	  cop0 = force_reg (mode, cop0);

	  switch (mode)
	    {
	    case E_V16SImode:
	    case E_V8DImode:
	    case E_V8SImode:
	    case E_V4DImode:
	    case E_V4SImode:
	    case E_V2DImode:
		{
		  rtx t1, t2, mask;
		  rtx (*gen_sub3) (rtx, rtx, rtx);

		  switch (mode)
		    {
		    case E_V16SImode: gen_sub3 = gen_subv16si3; break;
		    case E_V8DImode: gen_sub3 = gen_subv8di3; break;
		    case E_V8SImode: gen_sub3 = gen_subv8si3; break;
		    case E_V4DImode: gen_sub3 = gen_subv4di3; break;
		    case E_V4SImode: gen_sub3 = gen_subv4si3; break;
		    case E_V2DImode: gen_sub3 = gen_subv2di3; break;
		    default:
		      gcc_unreachable ();
		    }
		  /* Subtract (-(INT MAX) - 1) from both operands to make
		     them signed.  */
		  mask = ix86_build_signbit_mask (mode, true, false);
		  t1 = gen_reg_rtx (mode);
		  emit_insn (gen_sub3 (t1, cop0, mask));

		  t2 = gen_reg_rtx (mode);
		  emit_insn (gen_sub3 (t2, cop1, mask));

		  cop0 = t1;
		  cop1 = t2;
		  code = GT;
		}
	      break;

	    case E_V64QImode:
	    case E_V32HImode:
	    case E_V32QImode:
	    case E_V16HImode:
	    case E_V16QImode:
	    case E_V8HImode:
	      /* Perform a parallel unsigned saturating subtraction.  */
	      x = gen_reg_rtx (mode);
	      emit_insn (gen_rtx_SET (x, gen_rtx_US_MINUS (mode, cop0,
							   cop1)));

	      cop0 = x;
	      cop1 = CONST0_RTX (mode);
	      code = EQ;
	      *negate = !*negate;
	      break;

	    default:
	      gcc_unreachable ();
	    }
	}
    }

  if (*negate)
    std::swap (op_true, op_false);

  /* Allow the comparison to be done in one mode, but the movcc to
     happen in another mode.  */
  if (data_mode == mode)
    {
      x = ix86_expand_sse_cmp (dest, code, cop0, cop1,
			       op_true, op_false);
    }
  else
    {
      gcc_assert (GET_MODE_SIZE (data_mode) == GET_MODE_SIZE (mode));
      x = ix86_expand_sse_cmp (gen_reg_rtx (mode), code, cop0, cop1,
			       op_true, op_false);
      if (GET_MODE (x) == mode)
	x = gen_lowpart (data_mode, x);
    }

  return x;
}

/* Expand integer vector comparison.  */

bool
ix86_expand_int_vec_cmp (rtx operands[])
{
  rtx_code code = GET_CODE (operands[1]);
  bool negate = false;
  rtx cmp = ix86_expand_int_sse_cmp (operands[0], code, operands[2],
				     operands[3], NULL, NULL, &negate);

  if (!cmp)
    return false;

  if (negate)
    cmp = ix86_expand_int_sse_cmp (operands[0], EQ, cmp,
				   CONST0_RTX (GET_MODE (cmp)),
				   NULL, NULL, &negate);

  gcc_assert (!negate);

  if (operands[0] != cmp)
    emit_move_insn (operands[0], cmp);

  return true;
}

/* Expand a floating-point vector conditional move; a vcond operation
   rather than a movcc operation.  */

bool
ix86_expand_fp_vcond (rtx operands[])
{
  enum rtx_code code = GET_CODE (operands[3]);
  rtx cmp;

  code = ix86_prepare_sse_fp_compare_args (operands[0], code,
					   &operands[4], &operands[5]);
  if (code == UNKNOWN)
    {
      rtx temp;
      switch (GET_CODE (operands[3]))
	{
	case LTGT:
	  temp = ix86_expand_sse_cmp (operands[0], ORDERED, operands[4],
				      operands[5], operands[0], operands[0]);
	  cmp = ix86_expand_sse_cmp (operands[0], NE, operands[4],
				     operands[5], operands[1], operands[2]);
	  code = AND;
	  break;
	case UNEQ:
	  temp = ix86_expand_sse_cmp (operands[0], UNORDERED, operands[4],
				      operands[5], operands[0], operands[0]);
	  cmp = ix86_expand_sse_cmp (operands[0], EQ, operands[4],
				     operands[5], operands[1], operands[2]);
	  code = IOR;
	  break;
	default:
	  gcc_unreachable ();
	}
      cmp = expand_simple_binop (GET_MODE (cmp), code, temp, cmp, cmp, 1,
				 OPTAB_DIRECT);
      ix86_expand_sse_movcc (operands[0], cmp, operands[1], operands[2]);
      return true;
    }

  if (ix86_expand_sse_fp_minmax (operands[0], code, operands[4],
				 operands[5], operands[1], operands[2]))
    return true;

  cmp = ix86_expand_sse_cmp (operands[0], code, operands[4], operands[5],
			     operands[1], operands[2]);
  ix86_expand_sse_movcc (operands[0], cmp, operands[1], operands[2]);
  return true;
}

/* Expand a signed/unsigned integral vector conditional move.  */

bool
ix86_expand_int_vcond (rtx operands[])
{
  machine_mode data_mode = GET_MODE (operands[0]);
  machine_mode mode = GET_MODE (operands[4]);
  enum rtx_code code = GET_CODE (operands[3]);
  bool negate = false;
  rtx x, cop0, cop1;

  cop0 = operands[4];
  cop1 = operands[5];

  /* Try to optimize x < 0 ? -1 : 0 into (signed) x >> 31
     and x < 0 ? 1 : 0 into (unsigned) x >> 31.  */
  if ((code == LT || code == GE)
      && data_mode == mode
      && cop1 == CONST0_RTX (mode)
      && operands[1 + (code == LT)] == CONST0_RTX (data_mode)
      && GET_MODE_UNIT_SIZE (data_mode) > 1
      && GET_MODE_UNIT_SIZE (data_mode) <= 8
      && (GET_MODE_SIZE (data_mode) == 16
	  || (TARGET_AVX2 && GET_MODE_SIZE (data_mode) == 32)))
    {
      rtx negop = operands[2 - (code == LT)];
      int shift = GET_MODE_UNIT_BITSIZE (data_mode) - 1;
      if (negop == CONST1_RTX (data_mode))
	{
	  rtx res = expand_simple_binop (mode, LSHIFTRT, cop0, GEN_INT (shift),
					 operands[0], 1, OPTAB_DIRECT);
	  if (res != operands[0])
	    emit_move_insn (operands[0], res);
	  return true;
	}
      else if (GET_MODE_INNER (data_mode) != DImode
	       && vector_all_ones_operand (negop, data_mode))
	{
	  rtx res = expand_simple_binop (mode, ASHIFTRT, cop0, GEN_INT (shift),
					 operands[0], 0, OPTAB_DIRECT);
	  if (res != operands[0])
	    emit_move_insn (operands[0], res);
	  return true;
	}
    }

  if (!nonimmediate_operand (cop1, mode))
    cop1 = force_reg (mode, cop1);
  if (!general_operand (operands[1], data_mode))
    operands[1] = force_reg (data_mode, operands[1]);
  if (!general_operand (operands[2], data_mode))
    operands[2] = force_reg (data_mode, operands[2]);

  x = ix86_expand_int_sse_cmp (operands[0], code, cop0, cop1,
			       operands[1], operands[2], &negate);

  if (!x)
    return false;

  ix86_expand_sse_movcc (operands[0], x, operands[1+negate],
			 operands[2-negate]);
  return true;
}

/* AVX512F does support 64-byte integer vector operations,
   thus the longest vector we are faced with is V64QImode.  */
#define MAX_VECT_LEN	64

struct expand_vec_perm_d
{
  rtx target, op0, op1;
  unsigned char perm[MAX_VECT_LEN];
  machine_mode vmode;
  unsigned char nelt;
  bool one_operand_p;
  bool testing_p;
};

static bool
ix86_expand_vec_perm_vpermt2 (rtx target, rtx mask, rtx op0, rtx op1,
			      struct expand_vec_perm_d *d)
{
  /* ix86_expand_vec_perm_vpermt2 is called from both const and non-const
     expander, so args are either in d, or in op0, op1 etc.  */
  machine_mode mode = GET_MODE (d ? d->op0 : op0);
  machine_mode maskmode = mode;
  rtx (*gen) (rtx, rtx, rtx, rtx) = NULL;

  switch (mode)
    {
    case E_V8HImode:
      if (TARGET_AVX512VL && TARGET_AVX512BW)
	gen = gen_avx512vl_vpermt2varv8hi3;
      break;
    case E_V16HImode:
      if (TARGET_AVX512VL && TARGET_AVX512BW)
	gen = gen_avx512vl_vpermt2varv16hi3;
      break;
    case E_V64QImode:
      if (TARGET_AVX512VBMI)
	gen = gen_avx512bw_vpermt2varv64qi3;
      break;
    case E_V32HImode:
      if (TARGET_AVX512BW)
	gen = gen_avx512bw_vpermt2varv32hi3;
      break;
    case E_V4SImode:
      if (TARGET_AVX512VL)
	gen = gen_avx512vl_vpermt2varv4si3;
      break;
    case E_V8SImode:
      if (TARGET_AVX512VL)
	gen = gen_avx512vl_vpermt2varv8si3;
      break;
    case E_V16SImode:
      if (TARGET_AVX512F)
	gen = gen_avx512f_vpermt2varv16si3;
      break;
    case E_V4SFmode:
      if (TARGET_AVX512VL)
	{
	  gen = gen_avx512vl_vpermt2varv4sf3;
	  maskmode = V4SImode;
	}
      break;
    case E_V8SFmode:
      if (TARGET_AVX512VL)
	{
	  gen = gen_avx512vl_vpermt2varv8sf3;
	  maskmode = V8SImode;
	}
      break;
    case E_V16SFmode:
      if (TARGET_AVX512F)
	{
	  gen = gen_avx512f_vpermt2varv16sf3;
	  maskmode = V16SImode;
	}
      break;
    case E_V2DImode:
      if (TARGET_AVX512VL)
	gen = gen_avx512vl_vpermt2varv2di3;
      break;
    case E_V4DImode:
      if (TARGET_AVX512VL)
	gen = gen_avx512vl_vpermt2varv4di3;
      break;
    case E_V8DImode:
      if (TARGET_AVX512F)
	gen = gen_avx512f_vpermt2varv8di3;
      break;
    case E_V2DFmode:
      if (TARGET_AVX512VL)
	{
	  gen = gen_avx512vl_vpermt2varv2df3;
	  maskmode = V2DImode;
	}
      break;
    case E_V4DFmode:
      if (TARGET_AVX512VL)
	{
	  gen = gen_avx512vl_vpermt2varv4df3;
	  maskmode = V4DImode;
	}
      break;
    case E_V8DFmode:
      if (TARGET_AVX512F)
	{
	  gen = gen_avx512f_vpermt2varv8df3;
	  maskmode = V8DImode;
	}
      break;
    default:
      break;
    }

  if (gen == NULL)
    return false;

  /* ix86_expand_vec_perm_vpermt2 is called from both const and non-const
     expander, so args are either in d, or in op0, op1 etc.  */
  if (d)
    {
      rtx vec[64];
      target = d->target;
      op0 = d->op0;
      op1 = d->op1;
      for (int i = 0; i < d->nelt; ++i)
	vec[i] = GEN_INT (d->perm[i]);
      mask = gen_rtx_CONST_VECTOR (maskmode, gen_rtvec_v (d->nelt, vec));
    }

  emit_insn (gen (target, force_reg (maskmode, mask), op0, op1));
  return true;
}

/* Expand a variable vector permutation.  */

void
ix86_expand_vec_perm (rtx operands[])
{
  rtx target = operands[0];
  rtx op0 = operands[1];
  rtx op1 = operands[2];
  rtx mask = operands[3];
  rtx t1, t2, t3, t4, t5, t6, t7, t8, vt, vt2, vec[32];
  machine_mode mode = GET_MODE (op0);
  machine_mode maskmode = GET_MODE (mask);
  int w, e, i;
  bool one_operand_shuffle = rtx_equal_p (op0, op1);

  /* Number of elements in the vector.  */
  w = GET_MODE_NUNITS (mode);
  e = GET_MODE_UNIT_SIZE (mode);
  gcc_assert (w <= 64);

  if (TARGET_AVX512F && one_operand_shuffle)
    {
      rtx (*gen) (rtx, rtx, rtx) = NULL;
      switch (mode)
	{
	case E_V16SImode:
	  gen =gen_avx512f_permvarv16si;
	  break;
	case E_V16SFmode:
	  gen = gen_avx512f_permvarv16sf;
	  break;
	case E_V8DImode:
	  gen = gen_avx512f_permvarv8di;
	  break;
	case E_V8DFmode:
	  gen = gen_avx512f_permvarv8df;
	  break;
	default:
	  break;
	}
      if (gen != NULL)
	{
	  emit_insn (gen (target, op0, mask));
	  return;
	}
    }

  if (ix86_expand_vec_perm_vpermt2 (target, mask, op0, op1, NULL))
    return;

  if (TARGET_AVX2)
    {
      if (mode == V4DImode || mode == V4DFmode || mode == V16HImode)
	{
	  /* Unfortunately, the VPERMQ and VPERMPD instructions only support
	     an constant shuffle operand.  With a tiny bit of effort we can
	     use VPERMD instead.  A re-interpretation stall for V4DFmode is
	     unfortunate but there's no avoiding it.
	     Similarly for V16HImode we don't have instructions for variable
	     shuffling, while for V32QImode we can use after preparing suitable
	     masks vpshufb; vpshufb; vpermq; vpor.  */

	  if (mode == V16HImode)
	    {
	      maskmode = mode = V32QImode;
	      w = 32;
	      e = 1;
	    }
	  else
	    {
	      maskmode = mode = V8SImode;
	      w = 8;
	      e = 4;
	    }
	  t1 = gen_reg_rtx (maskmode);

	  /* Replicate the low bits of the V4DImode mask into V8SImode:
	       mask = { A B C D }
	       t1 = { A A B B C C D D }.  */
	  for (i = 0; i < w / 2; ++i)
	    vec[i*2 + 1] = vec[i*2] = GEN_INT (i * 2);
	  vt = gen_rtx_CONST_VECTOR (maskmode, gen_rtvec_v (w, vec));
	  vt = force_reg (maskmode, vt);
	  mask = gen_lowpart (maskmode, mask);
	  if (maskmode == V8SImode)
	    emit_insn (gen_avx2_permvarv8si (t1, mask, vt));
	  else
	    emit_insn (gen_avx2_pshufbv32qi3 (t1, mask, vt));

	  /* Multiply the shuffle indicies by two.  */
	  t1 = expand_simple_binop (maskmode, PLUS, t1, t1, t1, 1,
				    OPTAB_DIRECT);

	  /* Add one to the odd shuffle indicies:
		t1 = { A*2, A*2+1, B*2, B*2+1, ... }.  */
	  for (i = 0; i < w / 2; ++i)
	    {
	      vec[i * 2] = const0_rtx;
	      vec[i * 2 + 1] = const1_rtx;
	    }
	  vt = gen_rtx_CONST_VECTOR (maskmode, gen_rtvec_v (w, vec));
	  vt = validize_mem (force_const_mem (maskmode, vt));
	  t1 = expand_simple_binop (maskmode, PLUS, t1, vt, t1, 1,
				    OPTAB_DIRECT);

	  /* Continue as if V8SImode (resp. V32QImode) was used initially.  */
	  operands[3] = mask = t1;
	  target = gen_reg_rtx (mode);
	  op0 = gen_lowpart (mode, op0);
	  op1 = gen_lowpart (mode, op1);
	}

      switch (mode)
	{
	case E_V8SImode:
	  /* The VPERMD and VPERMPS instructions already properly ignore
	     the high bits of the shuffle elements.  No need for us to
	     perform an AND ourselves.  */
	  if (one_operand_shuffle)
	    {
	      emit_insn (gen_avx2_permvarv8si (target, op0, mask));
	      if (target != operands[0])
		emit_move_insn (operands[0],
				gen_lowpart (GET_MODE (operands[0]), target));
	    }
	  else
	    {
	      t1 = gen_reg_rtx (V8SImode);
	      t2 = gen_reg_rtx (V8SImode);
	      emit_insn (gen_avx2_permvarv8si (t1, op0, mask));
	      emit_insn (gen_avx2_permvarv8si (t2, op1, mask));
	      goto merge_two;
	    }
	  return;

	case E_V8SFmode:
	  mask = gen_lowpart (V8SImode, mask);
	  if (one_operand_shuffle)
	    emit_insn (gen_avx2_permvarv8sf (target, op0, mask));
	  else
	    {
	      t1 = gen_reg_rtx (V8SFmode);
	      t2 = gen_reg_rtx (V8SFmode);
	      emit_insn (gen_avx2_permvarv8sf (t1, op0, mask));
	      emit_insn (gen_avx2_permvarv8sf (t2, op1, mask));
	      goto merge_two;
	    }
	  return;

        case E_V4SImode:
	  /* By combining the two 128-bit input vectors into one 256-bit
	     input vector, we can use VPERMD and VPERMPS for the full
	     two-operand shuffle.  */
	  t1 = gen_reg_rtx (V8SImode);
	  t2 = gen_reg_rtx (V8SImode);
	  emit_insn (gen_avx_vec_concatv8si (t1, op0, op1));
	  emit_insn (gen_avx_vec_concatv8si (t2, mask, mask));
	  emit_insn (gen_avx2_permvarv8si (t1, t1, t2));
	  emit_insn (gen_avx_vextractf128v8si (target, t1, const0_rtx));
	  return;

        case E_V4SFmode:
	  t1 = gen_reg_rtx (V8SFmode);
	  t2 = gen_reg_rtx (V8SImode);
	  mask = gen_lowpart (V4SImode, mask);
	  emit_insn (gen_avx_vec_concatv8sf (t1, op0, op1));
	  emit_insn (gen_avx_vec_concatv8si (t2, mask, mask));
	  emit_insn (gen_avx2_permvarv8sf (t1, t1, t2));
	  emit_insn (gen_avx_vextractf128v8sf (target, t1, const0_rtx));
	  return;

	case E_V32QImode:
	  t1 = gen_reg_rtx (V32QImode);
	  t2 = gen_reg_rtx (V32QImode);
	  t3 = gen_reg_rtx (V32QImode);
	  vt2 = GEN_INT (-128);
	  vt = gen_const_vec_duplicate (V32QImode, vt2);
	  vt = force_reg (V32QImode, vt);
	  for (i = 0; i < 32; i++)
	    vec[i] = i < 16 ? vt2 : const0_rtx;
	  vt2 = gen_rtx_CONST_VECTOR (V32QImode, gen_rtvec_v (32, vec));
	  vt2 = force_reg (V32QImode, vt2);
	  /* From mask create two adjusted masks, which contain the same
	     bits as mask in the low 7 bits of each vector element.
	     The first mask will have the most significant bit clear
	     if it requests element from the same 128-bit lane
	     and MSB set if it requests element from the other 128-bit lane.
	     The second mask will have the opposite values of the MSB,
	     and additionally will have its 128-bit lanes swapped.
	     E.g. { 07 12 1e 09 ... | 17 19 05 1f ... } mask vector will have
	     t1   { 07 92 9e 09 ... | 17 19 85 1f ... } and
	     t3   { 97 99 05 9f ... | 87 12 1e 89 ... } where each ...
	     stands for other 12 bytes.  */
	  /* The bit whether element is from the same lane or the other
	     lane is bit 4, so shift it up by 3 to the MSB position.  */
	  t5 = gen_reg_rtx (V4DImode);
	  emit_insn (gen_ashlv4di3 (t5, gen_lowpart (V4DImode, mask),
				    GEN_INT (3)));
	  /* Clear MSB bits from the mask just in case it had them set.  */
	  emit_insn (gen_avx2_andnotv32qi3 (t2, vt, mask));
	  /* After this t1 will have MSB set for elements from other lane.  */
	  emit_insn (gen_xorv32qi3 (t1, gen_lowpart (V32QImode, t5), vt2));
	  /* Clear bits other than MSB.  */
	  emit_insn (gen_andv32qi3 (t1, t1, vt));
	  /* Or in the lower bits from mask into t3.  */
	  emit_insn (gen_iorv32qi3 (t3, t1, t2));
	  /* And invert MSB bits in t1, so MSB is set for elements from the same
	     lane.  */
	  emit_insn (gen_xorv32qi3 (t1, t1, vt));
	  /* Swap 128-bit lanes in t3.  */
	  t6 = gen_reg_rtx (V4DImode);
	  emit_insn (gen_avx2_permv4di_1 (t6, gen_lowpart (V4DImode, t3),
					  const2_rtx, GEN_INT (3),
					  const0_rtx, const1_rtx));
	  /* And or in the lower bits from mask into t1.  */
	  emit_insn (gen_iorv32qi3 (t1, t1, t2));
	  if (one_operand_shuffle)
	    {
	      /* Each of these shuffles will put 0s in places where
		 element from the other 128-bit lane is needed, otherwise
		 will shuffle in the requested value.  */
	      emit_insn (gen_avx2_pshufbv32qi3 (t3, op0,
						gen_lowpart (V32QImode, t6)));
	      emit_insn (gen_avx2_pshufbv32qi3 (t1, op0, t1));
	      /* For t3 the 128-bit lanes are swapped again.  */
	      t7 = gen_reg_rtx (V4DImode);
	      emit_insn (gen_avx2_permv4di_1 (t7, gen_lowpart (V4DImode, t3),
					      const2_rtx, GEN_INT (3),
					      const0_rtx, const1_rtx));
	      /* And oring both together leads to the result.  */
	      emit_insn (gen_iorv32qi3 (target, t1,
					gen_lowpart (V32QImode, t7)));
	      if (target != operands[0])
		emit_move_insn (operands[0],
				gen_lowpart (GET_MODE (operands[0]), target));
	      return;
	    }

	  t4 = gen_reg_rtx (V32QImode);
	  /* Similarly to the above one_operand_shuffle code,
	     just for repeated twice for each operand.  merge_two:
	     code will merge the two results together.  */
	  emit_insn (gen_avx2_pshufbv32qi3 (t4, op0,
					    gen_lowpart (V32QImode, t6)));
	  emit_insn (gen_avx2_pshufbv32qi3 (t3, op1,
					    gen_lowpart (V32QImode, t6)));
	  emit_insn (gen_avx2_pshufbv32qi3 (t2, op0, t1));
	  emit_insn (gen_avx2_pshufbv32qi3 (t1, op1, t1));
	  t7 = gen_reg_rtx (V4DImode);
	  emit_insn (gen_avx2_permv4di_1 (t7, gen_lowpart (V4DImode, t4),
					  const2_rtx, GEN_INT (3),
					  const0_rtx, const1_rtx));
	  t8 = gen_reg_rtx (V4DImode);
	  emit_insn (gen_avx2_permv4di_1 (t8, gen_lowpart (V4DImode, t3),
					  const2_rtx, GEN_INT (3),
					  const0_rtx, const1_rtx));
	  emit_insn (gen_iorv32qi3 (t4, t2, gen_lowpart (V32QImode, t7)));
	  emit_insn (gen_iorv32qi3 (t3, t1, gen_lowpart (V32QImode, t8)));
	  t1 = t4;
	  t2 = t3;
	  goto merge_two;

	default:
	  gcc_assert (GET_MODE_SIZE (mode) <= 16);
	  break;
	}
    }

  if (TARGET_XOP)
    {
      /* The XOP VPPERM insn supports three inputs.  By ignoring the 
	 one_operand_shuffle special case, we avoid creating another
	 set of constant vectors in memory.  */
      one_operand_shuffle = false;

      /* mask = mask & {2*w-1, ...} */
      vt = GEN_INT (2*w - 1);
    }
  else
    {
      /* mask = mask & {w-1, ...} */
      vt = GEN_INT (w - 1);
    }

  vt = gen_const_vec_duplicate (maskmode, vt);
  mask = expand_simple_binop (maskmode, AND, mask, vt,
			      NULL_RTX, 0, OPTAB_DIRECT);

  /* For non-QImode operations, convert the word permutation control
     into a byte permutation control.  */
  if (mode != V16QImode)
    {
      mask = expand_simple_binop (maskmode, ASHIFT, mask,
				  GEN_INT (exact_log2 (e)),
				  NULL_RTX, 0, OPTAB_DIRECT);

      /* Convert mask to vector of chars.  */
      mask = force_reg (V16QImode, gen_lowpart (V16QImode, mask));

      /* Replicate each of the input bytes into byte positions:
	 (v2di) --> {0,0,0,0,0,0,0,0, 8,8,8,8,8,8,8,8}
	 (v4si) --> {0,0,0,0, 4,4,4,4, 8,8,8,8, 12,12,12,12}
	 (v8hi) --> {0,0, 2,2, 4,4, 6,6, ...}.  */
      for (i = 0; i < 16; ++i)
	vec[i] = GEN_INT (i/e * e);
      vt = gen_rtx_CONST_VECTOR (V16QImode, gen_rtvec_v (16, vec));
      vt = validize_mem (force_const_mem (V16QImode, vt));
      if (TARGET_XOP)
	emit_insn (gen_xop_pperm (mask, mask, mask, vt));
      else
	emit_insn (gen_ssse3_pshufbv16qi3 (mask, mask, vt));

      /* Convert it into the byte positions by doing
	 mask = mask + {0,1,..,16/w, 0,1,..,16/w, ...}  */
      for (i = 0; i < 16; ++i)
	vec[i] = GEN_INT (i % e);
      vt = gen_rtx_CONST_VECTOR (V16QImode, gen_rtvec_v (16, vec));
      vt = validize_mem (force_const_mem (V16QImode, vt));
      emit_insn (gen_addv16qi3 (mask, mask, vt));
    }

  /* The actual shuffle operations all operate on V16QImode.  */
  op0 = gen_lowpart (V16QImode, op0);
  op1 = gen_lowpart (V16QImode, op1);

  if (TARGET_XOP)
    {
      if (GET_MODE (target) != V16QImode)
	target = gen_reg_rtx (V16QImode);
      emit_insn (gen_xop_pperm (target, op0, op1, mask));
      if (target != operands[0])
	emit_move_insn (operands[0],
			gen_lowpart (GET_MODE (operands[0]), target));
    }
  else if (one_operand_shuffle)
    {
      if (GET_MODE (target) != V16QImode)
	target = gen_reg_rtx (V16QImode);
      emit_insn (gen_ssse3_pshufbv16qi3 (target, op0, mask));
      if (target != operands[0])
	emit_move_insn (operands[0],
			gen_lowpart (GET_MODE (operands[0]), target));
    }
  else
    {
      rtx xops[6];
      bool ok;

      /* Shuffle the two input vectors independently.  */
      t1 = gen_reg_rtx (V16QImode);
      t2 = gen_reg_rtx (V16QImode);
      emit_insn (gen_ssse3_pshufbv16qi3 (t1, op0, mask));
      emit_insn (gen_ssse3_pshufbv16qi3 (t2, op1, mask));

 merge_two:
      /* Then merge them together.  The key is whether any given control
         element contained a bit set that indicates the second word.  */
      mask = operands[3];
      vt = GEN_INT (w);
      if (maskmode == V2DImode && !TARGET_SSE4_1)
	{
	  /* Without SSE4.1, we don't have V2DImode EQ.  Perform one
	     more shuffle to convert the V2DI input mask into a V4SI
	     input mask.  At which point the masking that expand_int_vcond
	     will work as desired.  */
	  rtx t3 = gen_reg_rtx (V4SImode);
	  emit_insn (gen_sse2_pshufd_1 (t3, gen_lowpart (V4SImode, mask),
				        const0_rtx, const0_rtx,
				        const2_rtx, const2_rtx));
	  mask = t3;
	  maskmode = V4SImode;
	  e = w = 4;
	}

      vt = gen_const_vec_duplicate (maskmode, vt);
      vt = force_reg (maskmode, vt);
      mask = expand_simple_binop (maskmode, AND, mask, vt,
				  NULL_RTX, 0, OPTAB_DIRECT);

      if (GET_MODE (target) != mode)
	target = gen_reg_rtx (mode);
      xops[0] = target;
      xops[1] = gen_lowpart (mode, t2);
      xops[2] = gen_lowpart (mode, t1);
      xops[3] = gen_rtx_EQ (maskmode, mask, vt);
      xops[4] = mask;
      xops[5] = vt;
      ok = ix86_expand_int_vcond (xops);
      gcc_assert (ok);
      if (target != operands[0])
	emit_move_insn (operands[0],
			gen_lowpart (GET_MODE (operands[0]), target));
    }
}

/* Unpack OP[1] into the next wider integer vector type.  UNSIGNED_P is
   true if we should do zero extension, else sign extension.  HIGH_P is
   true if we want the N/2 high elements, else the low elements.  */

void
ix86_expand_sse_unpack (rtx dest, rtx src, bool unsigned_p, bool high_p)
{
  machine_mode imode = GET_MODE (src);
  rtx tmp;

  if (TARGET_SSE4_1)
    {
      rtx (*unpack)(rtx, rtx);
      rtx (*extract)(rtx, rtx) = NULL;
      machine_mode halfmode = BLKmode;

      switch (imode)
	{
	case E_V64QImode:
	  if (unsigned_p)
	    unpack = gen_avx512bw_zero_extendv32qiv32hi2;
	  else
	    unpack = gen_avx512bw_sign_extendv32qiv32hi2;
	  halfmode = V32QImode;
	  extract
	    = high_p ? gen_vec_extract_hi_v64qi : gen_vec_extract_lo_v64qi;
	  break;
	case E_V32QImode:
	  if (unsigned_p)
	    unpack = gen_avx2_zero_extendv16qiv16hi2;
	  else
	    unpack = gen_avx2_sign_extendv16qiv16hi2;
	  halfmode = V16QImode;
	  extract
	    = high_p ? gen_vec_extract_hi_v32qi : gen_vec_extract_lo_v32qi;
	  break;
	case E_V32HImode:
	  if (unsigned_p)
	    unpack = gen_avx512f_zero_extendv16hiv16si2;
	  else
	    unpack = gen_avx512f_sign_extendv16hiv16si2;
	  halfmode = V16HImode;
	  extract
	    = high_p ? gen_vec_extract_hi_v32hi : gen_vec_extract_lo_v32hi;
	  break;
	case E_V16HImode:
	  if (unsigned_p)
	    unpack = gen_avx2_zero_extendv8hiv8si2;
	  else
	    unpack = gen_avx2_sign_extendv8hiv8si2;
	  halfmode = V8HImode;
	  extract
	    = high_p ? gen_vec_extract_hi_v16hi : gen_vec_extract_lo_v16hi;
	  break;
	case E_V16SImode:
	  if (unsigned_p)
	    unpack = gen_avx512f_zero_extendv8siv8di2;
	  else
	    unpack = gen_avx512f_sign_extendv8siv8di2;
	  halfmode = V8SImode;
	  extract
	    = high_p ? gen_vec_extract_hi_v16si : gen_vec_extract_lo_v16si;
	  break;
	case E_V8SImode:
	  if (unsigned_p)
	    unpack = gen_avx2_zero_extendv4siv4di2;
	  else
	    unpack = gen_avx2_sign_extendv4siv4di2;
	  halfmode = V4SImode;
	  extract
	    = high_p ? gen_vec_extract_hi_v8si : gen_vec_extract_lo_v8si;
	  break;
	case E_V16QImode:
	  if (unsigned_p)
	    unpack = gen_sse4_1_zero_extendv8qiv8hi2;
	  else
	    unpack = gen_sse4_1_sign_extendv8qiv8hi2;
	  break;
	case E_V8HImode:
	  if (unsigned_p)
	    unpack = gen_sse4_1_zero_extendv4hiv4si2;
	  else
	    unpack = gen_sse4_1_sign_extendv4hiv4si2;
	  break;
	case E_V4SImode:
	  if (unsigned_p)
	    unpack = gen_sse4_1_zero_extendv2siv2di2;
	  else
	    unpack = gen_sse4_1_sign_extendv2siv2di2;
	  break;
	default:
	  gcc_unreachable ();
	}

      if (GET_MODE_SIZE (imode) >= 32)
	{
	  tmp = gen_reg_rtx (halfmode);
	  emit_insn (extract (tmp, src));
	}
      else if (high_p)
	{
	  /* Shift higher 8 bytes to lower 8 bytes.  */
	  tmp = gen_reg_rtx (V1TImode);
	  emit_insn (gen_sse2_lshrv1ti3 (tmp, gen_lowpart (V1TImode, src),
					 GEN_INT (64)));
	  tmp = gen_lowpart (imode, tmp);
	}
      else
	tmp = src;

      emit_insn (unpack (dest, tmp));
    }
  else
    {
      rtx (*unpack)(rtx, rtx, rtx);

      switch (imode)
	{
	case E_V16QImode:
	  if (high_p)
	    unpack = gen_vec_interleave_highv16qi;
	  else
	    unpack = gen_vec_interleave_lowv16qi;
	  break;
	case E_V8HImode:
	  if (high_p)
	    unpack = gen_vec_interleave_highv8hi;
	  else
	    unpack = gen_vec_interleave_lowv8hi;
	  break;
	case E_V4SImode:
	  if (high_p)
	    unpack = gen_vec_interleave_highv4si;
	  else
	    unpack = gen_vec_interleave_lowv4si;
	  break;
	default:
	  gcc_unreachable ();
	}

      if (unsigned_p)
	tmp = force_reg (imode, CONST0_RTX (imode));
      else
	tmp = ix86_expand_sse_cmp (gen_reg_rtx (imode), GT, CONST0_RTX (imode),
				   src, pc_rtx, pc_rtx);

      rtx tmp2 = gen_reg_rtx (imode);
      emit_insn (unpack (tmp2, src, tmp));
      emit_move_insn (dest, gen_lowpart (GET_MODE (dest), tmp2));
    }
}

/* Expand conditional increment or decrement using adb/sbb instructions.
   The default case using setcc followed by the conditional move can be
   done by generic code.  */
bool
ix86_expand_int_addcc (rtx operands[])
{
  enum rtx_code code = GET_CODE (operands[1]);
  rtx flags;
  rtx (*insn)(rtx, rtx, rtx, rtx, rtx);
  rtx compare_op;
  rtx val = const0_rtx;
  bool fpcmp = false;
  machine_mode mode;
  rtx op0 = XEXP (operands[1], 0);
  rtx op1 = XEXP (operands[1], 1);

  if (operands[3] != const1_rtx
      && operands[3] != constm1_rtx)
    return false;
  if (!ix86_expand_carry_flag_compare (code, op0, op1, &compare_op))
     return false;
  code = GET_CODE (compare_op);

  flags = XEXP (compare_op, 0);

  if (GET_MODE (flags) == CCFPmode)
    {
      fpcmp = true;
      code = ix86_fp_compare_code_to_integer (code);
    }

  if (code != LTU)
    {
      val = constm1_rtx;
      if (fpcmp)
	PUT_CODE (compare_op,
		  reverse_condition_maybe_unordered
		    (GET_CODE (compare_op)));
      else
	PUT_CODE (compare_op, reverse_condition (GET_CODE (compare_op)));
    }

  mode = GET_MODE (operands[0]);

  /* Construct either adc or sbb insn.  */
  if ((code == LTU) == (operands[3] == constm1_rtx))
    {
      switch (mode)
	{
	  case E_QImode:
	    insn = gen_subqi3_carry;
	    break;
	  case E_HImode:
	    insn = gen_subhi3_carry;
	    break;
	  case E_SImode:
	    insn = gen_subsi3_carry;
	    break;
	  case E_DImode:
	    insn = gen_subdi3_carry;
	    break;
	  default:
	    gcc_unreachable ();
	}
    }
  else
    {
      switch (mode)
	{
	  case E_QImode:
	    insn = gen_addqi3_carry;
	    break;
	  case E_HImode:
	    insn = gen_addhi3_carry;
	    break;
	  case E_SImode:
	    insn = gen_addsi3_carry;
	    break;
	  case E_DImode:
	    insn = gen_adddi3_carry;
	    break;
	  default:
	    gcc_unreachable ();
	}
    }
  emit_insn (insn (operands[0], operands[2], val, flags, compare_op));

  return true;
}


/* Split operands 0 and 1 into half-mode parts.  Similar to split_double_mode,
   but works for floating pointer parameters and nonoffsetable memories.
   For pushes, it returns just stack offsets; the values will be saved
   in the right order.  Maximally three parts are generated.  */

static int
ix86_split_to_parts (rtx operand, rtx *parts, machine_mode mode)
{
  int size;

  if (!TARGET_64BIT)
    size = mode==XFmode ? 3 : GET_MODE_SIZE (mode) / 4;
  else
    size = (GET_MODE_SIZE (mode) + 4) / 8;

  gcc_assert (!REG_P (operand) || !MMX_REGNO_P (REGNO (operand)));
  gcc_assert (size >= 2 && size <= 4);

  /* Optimize constant pool reference to immediates.  This is used by fp
     moves, that force all constants to memory to allow combining.  */
  if (MEM_P (operand) && MEM_READONLY_P (operand))
    operand = avoid_constant_pool_reference (operand);

  if (MEM_P (operand) && !offsettable_memref_p (operand))
    {
      /* The only non-offsetable memories we handle are pushes.  */
      int ok = push_operand (operand, VOIDmode);

      gcc_assert (ok);

      operand = copy_rtx (operand);
      PUT_MODE (operand, word_mode);
      parts[0] = parts[1] = parts[2] = parts[3] = operand;
      return size;
    }

  if (GET_CODE (operand) == CONST_VECTOR)
    {
      scalar_int_mode imode = int_mode_for_mode (mode).require ();
      /* Caution: if we looked through a constant pool memory above,
	 the operand may actually have a different mode now.  That's
	 ok, since we want to pun this all the way back to an integer.  */
      operand = simplify_subreg (imode, operand, GET_MODE (operand), 0);
      gcc_assert (operand != NULL);
      mode = imode;
    }

  if (!TARGET_64BIT)
    {
      if (mode == DImode)
	split_double_mode (mode, &operand, 1, &parts[0], &parts[1]);
      else
	{
	  int i;

	  if (REG_P (operand))
	    {
	      gcc_assert (reload_completed);
	      for (i = 0; i < size; i++)
		parts[i] = gen_rtx_REG (SImode, REGNO (operand) + i);
	    }
	  else if (offsettable_memref_p (operand))
	    {
	      operand = adjust_address (operand, SImode, 0);
	      parts[0] = operand;
	      for (i = 1; i < size; i++)
		parts[i] = adjust_address (operand, SImode, 4 * i);
	    }
	  else if (CONST_DOUBLE_P (operand))
	    {
	      const REAL_VALUE_TYPE *r;
	      long l[4];

	      r = CONST_DOUBLE_REAL_VALUE (operand);
	      switch (mode)
		{
		case E_TFmode:
		  real_to_target (l, r, mode);
		  parts[3] = gen_int_mode (l[3], SImode);
		  parts[2] = gen_int_mode (l[2], SImode);
		  break;
		case E_XFmode:
		  /* We can't use REAL_VALUE_TO_TARGET_LONG_DOUBLE since
		     long double may not be 80-bit.  */
		  real_to_target (l, r, mode);
		  parts[2] = gen_int_mode (l[2], SImode);
		  break;
		case E_DFmode:
		  REAL_VALUE_TO_TARGET_DOUBLE (*r, l);
		  break;
		default:
		  gcc_unreachable ();
		}
	      parts[1] = gen_int_mode (l[1], SImode);
	      parts[0] = gen_int_mode (l[0], SImode);
	    }
	  else
	    gcc_unreachable ();
	}
    }
  else
    {
      if (mode == TImode)
	split_double_mode (mode, &operand, 1, &parts[0], &parts[1]);
      if (mode == XFmode || mode == TFmode)
	{
	  machine_mode upper_mode = mode==XFmode ? SImode : DImode;
	  if (REG_P (operand))
	    {
	      gcc_assert (reload_completed);
	      parts[0] = gen_rtx_REG (DImode, REGNO (operand) + 0);
	      parts[1] = gen_rtx_REG (upper_mode, REGNO (operand) + 1);
	    }
	  else if (offsettable_memref_p (operand))
	    {
	      operand = adjust_address (operand, DImode, 0);
	      parts[0] = operand;
	      parts[1] = adjust_address (operand, upper_mode, 8);
	    }
	  else if (CONST_DOUBLE_P (operand))
	    {
	      long l[4];

	      real_to_target (l, CONST_DOUBLE_REAL_VALUE (operand), mode);

	      /* real_to_target puts 32-bit pieces in each long.  */
	      parts[0] = gen_int_mode ((l[0] & HOST_WIDE_INT_C (0xffffffff))
				       | ((l[1] & HOST_WIDE_INT_C (0xffffffff))
					  << 32), DImode);

	      if (upper_mode == SImode)
	        parts[1] = gen_int_mode (l[2], SImode);
	      else
	        parts[1]
		  = gen_int_mode ((l[2] & HOST_WIDE_INT_C (0xffffffff))
				  | ((l[3] & HOST_WIDE_INT_C (0xffffffff))
				     << 32), DImode);
	    }
	  else
	    gcc_unreachable ();
	}
    }

  return size;
}

/* Emit insns to perform a move or push of DI, DF, XF, and TF values.
   Return false when normal moves are needed; true when all required
   insns have been emitted.  Operands 2-4 contain the input values
   int the correct order; operands 5-7 contain the output values.  */

void
ix86_split_long_move (rtx operands[])
{
  rtx part[2][4];
  int nparts, i, j;
  int push = 0;
  int collisions = 0;
  machine_mode mode = GET_MODE (operands[0]);
  bool collisionparts[4];

  /* The DFmode expanders may ask us to move double.
     For 64bit target this is single move.  By hiding the fact
     here we simplify i386.md splitters.  */
  if (TARGET_64BIT && GET_MODE_SIZE (GET_MODE (operands[0])) == 8)
    {
      /* Optimize constant pool reference to immediates.  This is used by
	 fp moves, that force all constants to memory to allow combining.  */

      if (MEM_P (operands[1])
	  && GET_CODE (XEXP (operands[1], 0)) == SYMBOL_REF
	  && CONSTANT_POOL_ADDRESS_P (XEXP (operands[1], 0)))
	operands[1] = get_pool_constant (XEXP (operands[1], 0));
      if (push_operand (operands[0], VOIDmode))
	{
	  operands[0] = copy_rtx (operands[0]);
	  PUT_MODE (operands[0], word_mode);
	}
      else
        operands[0] = gen_lowpart (DImode, operands[0]);
      operands[1] = gen_lowpart (DImode, operands[1]);
      emit_move_insn (operands[0], operands[1]);
      return;
    }

  /* The only non-offsettable memory we handle is push.  */
  if (push_operand (operands[0], VOIDmode))
    push = 1;
  else
    gcc_assert (!MEM_P (operands[0])
		|| offsettable_memref_p (operands[0]));

  nparts = ix86_split_to_parts (operands[1], part[1], GET_MODE (operands[0]));
  ix86_split_to_parts (operands[0], part[0], GET_MODE (operands[0]));

  /* When emitting push, take care for source operands on the stack.  */
  if (push && MEM_P (operands[1])
      && reg_overlap_mentioned_p (stack_pointer_rtx, operands[1]))
    {
      rtx src_base = XEXP (part[1][nparts - 1], 0);

      /* Compensate for the stack decrement by 4.  */
      if (!TARGET_64BIT && nparts == 3
	  && mode == XFmode && TARGET_128BIT_LONG_DOUBLE)
	src_base = plus_constant (Pmode, src_base, 4);

      /* src_base refers to the stack pointer and is
	 automatically decreased by emitted push.  */
      for (i = 0; i < nparts; i++)
	part[1][i] = change_address (part[1][i],
				     GET_MODE (part[1][i]), src_base);
    }

  /* We need to do copy in the right order in case an address register
     of the source overlaps the destination.  */
  if (REG_P (part[0][0]) && MEM_P (part[1][0]))
    {
      rtx tmp;

      for (i = 0; i < nparts; i++)
	{
	  collisionparts[i]
	    = reg_overlap_mentioned_p (part[0][i], XEXP (part[1][0], 0));
	  if (collisionparts[i])
	    collisions++;
	}

      /* Collision in the middle part can be handled by reordering.  */
      if (collisions == 1 && nparts == 3 && collisionparts [1])
	{
	  std::swap (part[0][1], part[0][2]);
	  std::swap (part[1][1], part[1][2]);
	}
      else if (collisions == 1
	       && nparts == 4
	       && (collisionparts [1] || collisionparts [2]))
	{
	  if (collisionparts [1])
	    {
	      std::swap (part[0][1], part[0][2]);
	      std::swap (part[1][1], part[1][2]);
	    }
	  else
	    {
	      std::swap (part[0][2], part[0][3]);
	      std::swap (part[1][2], part[1][3]);
	    }
	}

      /* If there are more collisions, we can't handle it by reordering.
	 Do an lea to the last part and use only one colliding move.  */
      else if (collisions > 1)
	{
	  rtx base, addr;

	  collisions = 1;

	  base = part[0][nparts - 1];

	  /* Handle the case when the last part isn't valid for lea.
	     Happens in 64-bit mode storing the 12-byte XFmode.  */
	  if (GET_MODE (base) != Pmode)
	    base = gen_rtx_REG (Pmode, REGNO (base));

	  addr = XEXP (part[1][0], 0);
	  if (TARGET_TLS_DIRECT_SEG_REFS)
	    {
	      struct ix86_address parts;
	      int ok = ix86_decompose_address (addr, &parts);
	      gcc_assert (ok);
	      /* It is not valid to use %gs: or %fs: in lea.  */
	      gcc_assert (parts.seg == ADDR_SPACE_GENERIC);
	    }
	  emit_insn (gen_rtx_SET (base, addr));
	  part[1][0] = replace_equiv_address (part[1][0], base);
	  for (i = 1; i < nparts; i++)
	    {
	      tmp = plus_constant (Pmode, base, UNITS_PER_WORD * i);
	      part[1][i] = replace_equiv_address (part[1][i], tmp);
	    }
	}
    }

  if (push)
    {
      if (!TARGET_64BIT)
	{
	  if (nparts == 3)
	    {
	      if (TARGET_128BIT_LONG_DOUBLE && mode == XFmode)
                emit_insn (ix86_gen_add3 (stack_pointer_rtx,
					  stack_pointer_rtx, GEN_INT (-4)));
	      emit_move_insn (part[0][2], part[1][2]);
	    }
	  else if (nparts == 4)
	    {
	      emit_move_insn (part[0][3], part[1][3]);
	      emit_move_insn (part[0][2], part[1][2]);
	    }
	}
      else
	{
	  /* In 64bit mode we don't have 32bit push available.  In case this is
	     register, it is OK - we will just use larger counterpart.  We also
	     retype memory - these comes from attempt to avoid REX prefix on
	     moving of second half of TFmode value.  */
	  if (GET_MODE (part[1][1]) == SImode)
	    {
	      switch (GET_CODE (part[1][1]))
		{
		case MEM:
		  part[1][1] = adjust_address (part[1][1], DImode, 0);
		  break;

		case REG:
		  part[1][1] = gen_rtx_REG (DImode, REGNO (part[1][1]));
		  break;

		default:
		  gcc_unreachable ();
		}

	      if (GET_MODE (part[1][0]) == SImode)
		part[1][0] = part[1][1];
	    }
	}
      emit_move_insn (part[0][1], part[1][1]);
      emit_move_insn (part[0][0], part[1][0]);
      return;
    }

  /* Choose correct order to not overwrite the source before it is copied.  */
  if ((REG_P (part[0][0])
       && REG_P (part[1][1])
       && (REGNO (part[0][0]) == REGNO (part[1][1])
	   || (nparts == 3
	       && REGNO (part[0][0]) == REGNO (part[1][2]))
	   || (nparts == 4
	       && REGNO (part[0][0]) == REGNO (part[1][3]))))
      || (collisions > 0
	  && reg_overlap_mentioned_p (part[0][0], XEXP (part[1][0], 0))))
    {
      for (i = 0, j = nparts - 1; i < nparts; i++, j--)
	{
	  operands[2 + i] = part[0][j];
	  operands[6 + i] = part[1][j];
	}
    }
  else
    {
      for (i = 0; i < nparts; i++)
	{
	  operands[2 + i] = part[0][i];
	  operands[6 + i] = part[1][i];
	}
    }

  /* If optimizing for size, attempt to locally unCSE nonzero constants.  */
  if (optimize_insn_for_size_p ())
    {
      for (j = 0; j < nparts - 1; j++)
	if (CONST_INT_P (operands[6 + j])
	    && operands[6 + j] != const0_rtx
	    && REG_P (operands[2 + j]))
	  for (i = j; i < nparts - 1; i++)
	    if (CONST_INT_P (operands[7 + i])
		&& INTVAL (operands[7 + i]) == INTVAL (operands[6 + j]))
	      operands[7 + i] = operands[2 + j];
    }

  for (i = 0; i < nparts; i++)
    emit_move_insn (operands[2 + i], operands[6 + i]);

  return;
}

/* Helper function of ix86_split_ashl used to generate an SImode/DImode
   left shift by a constant, either using a single shift or
   a sequence of add instructions.  */

static void
ix86_expand_ashl_const (rtx operand, int count, machine_mode mode)
{
  rtx (*insn)(rtx, rtx, rtx);

  if (count == 1
      || (count * ix86_cost->add <= ix86_cost->shift_const
	  && !optimize_insn_for_size_p ()))
    {
      insn = mode == DImode ? gen_addsi3 : gen_adddi3;
      while (count-- > 0)
	emit_insn (insn (operand, operand, operand));
    }
  else
    {
      insn = mode == DImode ? gen_ashlsi3 : gen_ashldi3;
      emit_insn (insn (operand, operand, GEN_INT (count)));
    }
}

void
ix86_split_ashl (rtx *operands, rtx scratch, machine_mode mode)
{
  rtx (*gen_ashl3)(rtx, rtx, rtx);
  rtx (*gen_shld)(rtx, rtx, rtx);
  int half_width = GET_MODE_BITSIZE (mode) >> 1;

  rtx low[2], high[2];
  int count;

  if (CONST_INT_P (operands[2]))
    {
      split_double_mode (mode, operands, 2, low, high);
      count = INTVAL (operands[2]) & (GET_MODE_BITSIZE (mode) - 1);

      if (count >= half_width)
	{
	  emit_move_insn (high[0], low[1]);
	  emit_move_insn (low[0], const0_rtx);

	  if (count > half_width)
	    ix86_expand_ashl_const (high[0], count - half_width, mode);
	}
      else
	{
	  gen_shld = mode == DImode ? gen_x86_shld : gen_x86_64_shld;

	  if (!rtx_equal_p (operands[0], operands[1]))
	    emit_move_insn (operands[0], operands[1]);

	  emit_insn (gen_shld (high[0], low[0], GEN_INT (count)));
	  ix86_expand_ashl_const (low[0], count, mode);
	}
      return;
    }

  split_double_mode (mode, operands, 1, low, high);

  gen_ashl3 = mode == DImode ? gen_ashlsi3 : gen_ashldi3;

  if (operands[1] == const1_rtx)
    {
      /* Assuming we've chosen a QImode capable registers, then 1 << N
	 can be done with two 32/64-bit shifts, no branches, no cmoves.  */
      if (ANY_QI_REG_P (low[0]) && ANY_QI_REG_P (high[0]))
	{
	  rtx s, d, flags = gen_rtx_REG (CCZmode, FLAGS_REG);

	  ix86_expand_clear (low[0]);
	  ix86_expand_clear (high[0]);
	  emit_insn (gen_testqi_ccz_1 (operands[2], GEN_INT (half_width)));

	  d = gen_lowpart (QImode, low[0]);
	  d = gen_rtx_STRICT_LOW_PART (VOIDmode, d);
	  s = gen_rtx_EQ (QImode, flags, const0_rtx);
	  emit_insn (gen_rtx_SET (d, s));

	  d = gen_lowpart (QImode, high[0]);
	  d = gen_rtx_STRICT_LOW_PART (VOIDmode, d);
	  s = gen_rtx_NE (QImode, flags, const0_rtx);
	  emit_insn (gen_rtx_SET (d, s));
	}

      /* Otherwise, we can get the same results by manually performing
	 a bit extract operation on bit 5/6, and then performing the two
	 shifts.  The two methods of getting 0/1 into low/high are exactly
	 the same size.  Avoiding the shift in the bit extract case helps
	 pentium4 a bit; no one else seems to care much either way.  */
      else
	{
	  machine_mode half_mode;
	  rtx (*gen_lshr3)(rtx, rtx, rtx);
	  rtx (*gen_and3)(rtx, rtx, rtx);
	  rtx (*gen_xor3)(rtx, rtx, rtx);
	  HOST_WIDE_INT bits;
	  rtx x;

	  if (mode == DImode)
	    {
	      half_mode = SImode;
	      gen_lshr3 = gen_lshrsi3;
	      gen_and3 = gen_andsi3;
	      gen_xor3 = gen_xorsi3;
	      bits = 5;
	    }
	  else
	    {
	      half_mode = DImode;
	      gen_lshr3 = gen_lshrdi3;
	      gen_and3 = gen_anddi3;
	      gen_xor3 = gen_xordi3;
	      bits = 6;
	    }

	  if (TARGET_PARTIAL_REG_STALL && !optimize_insn_for_size_p ())
	    x = gen_rtx_ZERO_EXTEND (half_mode, operands[2]);
	  else
	    x = gen_lowpart (half_mode, operands[2]);
	  emit_insn (gen_rtx_SET (high[0], x));

	  emit_insn (gen_lshr3 (high[0], high[0], GEN_INT (bits)));
	  emit_insn (gen_and3 (high[0], high[0], const1_rtx));
	  emit_move_insn (low[0], high[0]);
	  emit_insn (gen_xor3 (low[0], low[0], const1_rtx));
	}

      emit_insn (gen_ashl3 (low[0], low[0], operands[2]));
      emit_insn (gen_ashl3 (high[0], high[0], operands[2]));
      return;
    }

  if (operands[1] == constm1_rtx)
    {
      /* For -1 << N, we can avoid the shld instruction, because we
	 know that we're shifting 0...31/63 ones into a -1.  */
      emit_move_insn (low[0], constm1_rtx);
      if (optimize_insn_for_size_p ())
	emit_move_insn (high[0], low[0]);
      else
	emit_move_insn (high[0], constm1_rtx);
    }
  else
    {
      gen_shld = mode == DImode ? gen_x86_shld : gen_x86_64_shld;

      if (!rtx_equal_p (operands[0], operands[1]))
	emit_move_insn (operands[0], operands[1]);

      split_double_mode (mode, operands, 1, low, high);
      emit_insn (gen_shld (high[0], low[0], operands[2]));
    }

  emit_insn (gen_ashl3 (low[0], low[0], operands[2]));

  if (TARGET_CMOVE && scratch)
    {
      rtx (*gen_x86_shift_adj_1)(rtx, rtx, rtx, rtx)
	= mode == DImode ? gen_x86_shiftsi_adj_1 : gen_x86_shiftdi_adj_1;

      ix86_expand_clear (scratch);
      emit_insn (gen_x86_shift_adj_1 (high[0], low[0], operands[2], scratch));
    }
  else
    {
      rtx (*gen_x86_shift_adj_2)(rtx, rtx, rtx)
	= mode == DImode ? gen_x86_shiftsi_adj_2 : gen_x86_shiftdi_adj_2;

      emit_insn (gen_x86_shift_adj_2 (high[0], low[0], operands[2]));
    }
}

void
ix86_split_ashr (rtx *operands, rtx scratch, machine_mode mode)
{
  rtx (*gen_ashr3)(rtx, rtx, rtx)
    = mode == DImode ? gen_ashrsi3 : gen_ashrdi3;
  rtx (*gen_shrd)(rtx, rtx, rtx);
  int half_width = GET_MODE_BITSIZE (mode) >> 1;

  rtx low[2], high[2];
  int count;

  if (CONST_INT_P (operands[2]))
    {
      split_double_mode (mode, operands, 2, low, high);
      count = INTVAL (operands[2]) & (GET_MODE_BITSIZE (mode) - 1);

      if (count == GET_MODE_BITSIZE (mode) - 1)
	{
	  emit_move_insn (high[0], high[1]);
	  emit_insn (gen_ashr3 (high[0], high[0],
				GEN_INT (half_width - 1)));
	  emit_move_insn (low[0], high[0]);

	}
      else if (count >= half_width)
	{
	  emit_move_insn (low[0], high[1]);
	  emit_move_insn (high[0], low[0]);
	  emit_insn (gen_ashr3 (high[0], high[0],
				GEN_INT (half_width - 1)));

	  if (count > half_width)
	    emit_insn (gen_ashr3 (low[0], low[0],
				  GEN_INT (count - half_width)));
	}
      else
	{
	  gen_shrd = mode == DImode ? gen_x86_shrd : gen_x86_64_shrd;

	  if (!rtx_equal_p (operands[0], operands[1]))
	    emit_move_insn (operands[0], operands[1]);

	  emit_insn (gen_shrd (low[0], high[0], GEN_INT (count)));
	  emit_insn (gen_ashr3 (high[0], high[0], GEN_INT (count)));
	}
    }
  else
    {
      gen_shrd = mode == DImode ? gen_x86_shrd : gen_x86_64_shrd;

     if (!rtx_equal_p (operands[0], operands[1]))
	emit_move_insn (operands[0], operands[1]);

      split_double_mode (mode, operands, 1, low, high);

      emit_insn (gen_shrd (low[0], high[0], operands[2]));
      emit_insn (gen_ashr3 (high[0], high[0], operands[2]));

      if (TARGET_CMOVE && scratch)
	{
	  rtx (*gen_x86_shift_adj_1)(rtx, rtx, rtx, rtx)
	    = mode == DImode ? gen_x86_shiftsi_adj_1 : gen_x86_shiftdi_adj_1;

	  emit_move_insn (scratch, high[0]);
	  emit_insn (gen_ashr3 (scratch, scratch,
				GEN_INT (half_width - 1)));
	  emit_insn (gen_x86_shift_adj_1 (low[0], high[0], operands[2],
					  scratch));
	}
      else
	{
	  rtx (*gen_x86_shift_adj_3)(rtx, rtx, rtx)
	    = mode == DImode ? gen_x86_shiftsi_adj_3 : gen_x86_shiftdi_adj_3;

	  emit_insn (gen_x86_shift_adj_3 (low[0], high[0], operands[2]));
	}
    }
}

void
ix86_split_lshr (rtx *operands, rtx scratch, machine_mode mode)
{
  rtx (*gen_lshr3)(rtx, rtx, rtx)
    = mode == DImode ? gen_lshrsi3 : gen_lshrdi3;
  rtx (*gen_shrd)(rtx, rtx, rtx);
  int half_width = GET_MODE_BITSIZE (mode) >> 1;

  rtx low[2], high[2];
  int count;

  if (CONST_INT_P (operands[2]))
    {
      split_double_mode (mode, operands, 2, low, high);
      count = INTVAL (operands[2]) & (GET_MODE_BITSIZE (mode) - 1);

      if (count >= half_width)
	{
	  emit_move_insn (low[0], high[1]);
	  ix86_expand_clear (high[0]);

	  if (count > half_width)
	    emit_insn (gen_lshr3 (low[0], low[0],
				  GEN_INT (count - half_width)));
	}
      else
	{
	  gen_shrd = mode == DImode ? gen_x86_shrd : gen_x86_64_shrd;

	  if (!rtx_equal_p (operands[0], operands[1]))
	    emit_move_insn (operands[0], operands[1]);

	  emit_insn (gen_shrd (low[0], high[0], GEN_INT (count)));
	  emit_insn (gen_lshr3 (high[0], high[0], GEN_INT (count)));
	}
    }
  else
    {
      gen_shrd = mode == DImode ? gen_x86_shrd : gen_x86_64_shrd;

      if (!rtx_equal_p (operands[0], operands[1]))
	emit_move_insn (operands[0], operands[1]);

      split_double_mode (mode, operands, 1, low, high);

      emit_insn (gen_shrd (low[0], high[0], operands[2]));
      emit_insn (gen_lshr3 (high[0], high[0], operands[2]));

      if (TARGET_CMOVE && scratch)
	{
	  rtx (*gen_x86_shift_adj_1)(rtx, rtx, rtx, rtx)
	    = mode == DImode ? gen_x86_shiftsi_adj_1 : gen_x86_shiftdi_adj_1;

	  ix86_expand_clear (scratch);
	  emit_insn (gen_x86_shift_adj_1 (low[0], high[0], operands[2],
					  scratch));
	}
      else
	{
	  rtx (*gen_x86_shift_adj_2)(rtx, rtx, rtx)
	    = mode == DImode ? gen_x86_shiftsi_adj_2 : gen_x86_shiftdi_adj_2;

	  emit_insn (gen_x86_shift_adj_2 (low[0], high[0], operands[2]));
	}
    }
}

/* Predict just emitted jump instruction to be taken with probability PROB.  */
static void
predict_jump (int prob)
{
  rtx_insn *insn = get_last_insn ();
  gcc_assert (JUMP_P (insn));
  add_reg_br_prob_note (insn, profile_probability::from_reg_br_prob_base (prob));
}

/* Helper function for the string operations below.  Dest VARIABLE whether
   it is aligned to VALUE bytes.  If true, jump to the label.  */
static rtx_code_label *
ix86_expand_aligntest (rtx variable, int value, bool epilogue)
{
  rtx_code_label *label = gen_label_rtx ();
  rtx tmpcount = gen_reg_rtx (GET_MODE (variable));
  if (GET_MODE (variable) == DImode)
    emit_insn (gen_anddi3 (tmpcount, variable, GEN_INT (value)));
  else
    emit_insn (gen_andsi3 (tmpcount, variable, GEN_INT (value)));
  emit_cmp_and_jump_insns (tmpcount, const0_rtx, EQ, 0, GET_MODE (variable),
			   1, label);
  if (epilogue)
    predict_jump (REG_BR_PROB_BASE * 50 / 100);
  else
    predict_jump (REG_BR_PROB_BASE * 90 / 100);
  return label;
}

/* Adjust COUNTER by the VALUE.  */
static void
ix86_adjust_counter (rtx countreg, HOST_WIDE_INT value)
{
  rtx (*gen_add)(rtx, rtx, rtx)
    = GET_MODE (countreg) == DImode ? gen_adddi3 : gen_addsi3;

  emit_insn (gen_add (countreg, countreg, GEN_INT (-value)));
}

/* Zero extend possibly SImode EXP to Pmode register.  */
rtx
ix86_zero_extend_to_Pmode (rtx exp)
{
  return force_reg (Pmode, convert_to_mode (Pmode, exp, 1));
}

/* Divide COUNTREG by SCALE.  */
static rtx
scale_counter (rtx countreg, int scale)
{
  rtx sc;

  if (scale == 1)
    return countreg;
  if (CONST_INT_P (countreg))
    return GEN_INT (INTVAL (countreg) / scale);
  gcc_assert (REG_P (countreg));

  sc = expand_simple_binop (GET_MODE (countreg), LSHIFTRT, countreg,
			    GEN_INT (exact_log2 (scale)),
			    NULL, 1, OPTAB_DIRECT);
  return sc;
}

/* Return mode for the memcpy/memset loop counter.  Prefer SImode over
   DImode for constant loop counts.  */

static machine_mode
counter_mode (rtx count_exp)
{
  if (GET_MODE (count_exp) != VOIDmode)
    return GET_MODE (count_exp);
  if (!CONST_INT_P (count_exp))
    return Pmode;
  if (TARGET_64BIT && (INTVAL (count_exp) & ~0xffffffff))
    return DImode;
  return SImode;
}

/* Copy the address to a Pmode register.  This is used for x32 to
   truncate DImode TLS address to a SImode register. */

static rtx
ix86_copy_addr_to_reg (rtx addr)
{
  rtx reg;
  if (GET_MODE (addr) == Pmode || GET_MODE (addr) == VOIDmode)
    {
      reg = copy_addr_to_reg (addr);
      REG_POINTER (reg) = 1;
      return reg;
    }
  else
    {
      gcc_assert (GET_MODE (addr) == DImode && Pmode == SImode);
      reg = copy_to_mode_reg (DImode, addr);
      REG_POINTER (reg) = 1;
      return gen_rtx_SUBREG (SImode, reg, 0);
    }
}

/* When ISSETMEM is FALSE, output simple loop to move memory pointer to SRCPTR
   to DESTPTR via chunks of MODE unrolled UNROLL times, overall size is COUNT
   specified in bytes.  When ISSETMEM is TRUE, output the equivalent loop to set
   memory by VALUE (supposed to be in MODE).

   The size is rounded down to whole number of chunk size moved at once.
   SRCMEM and DESTMEM provide MEMrtx to feed proper aliasing info.  */


static void
expand_set_or_movmem_via_loop (rtx destmem, rtx srcmem,
			       rtx destptr, rtx srcptr, rtx value,
			       rtx count, machine_mode mode, int unroll,
			       int expected_size, bool issetmem)
{
  rtx_code_label *out_label, *top_label;
  rtx iter, tmp;
  machine_mode iter_mode = counter_mode (count);
  int piece_size_n = GET_MODE_SIZE (mode) * unroll;
  rtx piece_size = GEN_INT (piece_size_n);
  rtx piece_size_mask = GEN_INT (~((GET_MODE_SIZE (mode) * unroll) - 1));
  rtx size;
  int i;

  top_label = gen_label_rtx ();
  out_label = gen_label_rtx ();
  iter = gen_reg_rtx (iter_mode);

  size = expand_simple_binop (iter_mode, AND, count, piece_size_mask,
			      NULL, 1, OPTAB_DIRECT);
  /* Those two should combine.  */
  if (piece_size == const1_rtx)
    {
      emit_cmp_and_jump_insns (size, const0_rtx, EQ, NULL_RTX, iter_mode,
			       true, out_label);
      predict_jump (REG_BR_PROB_BASE * 10 / 100);
    }
  emit_move_insn (iter, const0_rtx);

  emit_label (top_label);

  tmp = convert_modes (Pmode, iter_mode, iter, true);

  /* This assert could be relaxed - in this case we'll need to compute
     smallest power of two, containing in PIECE_SIZE_N and pass it to
     offset_address.  */
  gcc_assert ((piece_size_n & (piece_size_n - 1)) == 0);
  destmem = offset_address (destmem, tmp, piece_size_n);
  destmem = adjust_address (destmem, mode, 0);

  if (!issetmem)
    {
      srcmem = offset_address (srcmem, copy_rtx (tmp), piece_size_n);
      srcmem = adjust_address (srcmem, mode, 0);

      /* When unrolling for chips that reorder memory reads and writes,
	 we can save registers by using single temporary.
	 Also using 4 temporaries is overkill in 32bit mode.  */
      if (!TARGET_64BIT && 0)
	{
	  for (i = 0; i < unroll; i++)
	    {
	      if (i)
		{
		  destmem = adjust_address (copy_rtx (destmem), mode,
					    GET_MODE_SIZE (mode));
		  srcmem = adjust_address (copy_rtx (srcmem), mode,
					   GET_MODE_SIZE (mode));
		}
	      emit_move_insn (destmem, srcmem);
	    }
	}
      else
	{
	  rtx tmpreg[4];
	  gcc_assert (unroll <= 4);
	  for (i = 0; i < unroll; i++)
	    {
	      tmpreg[i] = gen_reg_rtx (mode);
	      if (i)
		srcmem = adjust_address (copy_rtx (srcmem), mode,
					 GET_MODE_SIZE (mode));
	      emit_move_insn (tmpreg[i], srcmem);
	    }
	  for (i = 0; i < unroll; i++)
	    {
	      if (i)
		destmem = adjust_address (copy_rtx (destmem), mode,
					  GET_MODE_SIZE (mode));
	      emit_move_insn (destmem, tmpreg[i]);
	    }
	}
    }
  else
    for (i = 0; i < unroll; i++)
      {
	if (i)
	  destmem = adjust_address (copy_rtx (destmem), mode,
				    GET_MODE_SIZE (mode));
	emit_move_insn (destmem, value);
      }

  tmp = expand_simple_binop (iter_mode, PLUS, iter, piece_size, iter,
			     true, OPTAB_LIB_WIDEN);
  if (tmp != iter)
    emit_move_insn (iter, tmp);

  emit_cmp_and_jump_insns (iter, size, LT, NULL_RTX, iter_mode,
			   true, top_label);
  if (expected_size != -1)
    {
      expected_size /= GET_MODE_SIZE (mode) * unroll;
      if (expected_size == 0)
	predict_jump (0);
      else if (expected_size > REG_BR_PROB_BASE)
	predict_jump (REG_BR_PROB_BASE - 1);
      else
        predict_jump (REG_BR_PROB_BASE - (REG_BR_PROB_BASE + expected_size / 2)
		      / expected_size);
    }
  else
    predict_jump (REG_BR_PROB_BASE * 80 / 100);
  iter = ix86_zero_extend_to_Pmode (iter);
  tmp = expand_simple_binop (Pmode, PLUS, destptr, iter, destptr,
			     true, OPTAB_LIB_WIDEN);
  if (tmp != destptr)
    emit_move_insn (destptr, tmp);
  if (!issetmem)
    {
      tmp = expand_simple_binop (Pmode, PLUS, srcptr, iter, srcptr,
				 true, OPTAB_LIB_WIDEN);
      if (tmp != srcptr)
	emit_move_insn (srcptr, tmp);
    }
  emit_label (out_label);
}

/* Output "rep; mov" or "rep; stos" instruction depending on ISSETMEM argument.
   When ISSETMEM is true, arguments SRCMEM and SRCPTR are ignored.
   When ISSETMEM is false, arguments VALUE and ORIG_VALUE are ignored.
   For setmem case, VALUE is a promoted to a wider size ORIG_VALUE.
   ORIG_VALUE is the original value passed to memset to fill the memory with.
   Other arguments have same meaning as for previous function.  */

static void
expand_set_or_movmem_via_rep (rtx destmem, rtx srcmem,
			   rtx destptr, rtx srcptr, rtx value, rtx orig_value,
			   rtx count,
			   machine_mode mode, bool issetmem)
{
  rtx destexp;
  rtx srcexp;
  rtx countreg;
  HOST_WIDE_INT rounded_count;

  /* If possible, it is shorter to use rep movs.
     TODO: Maybe it is better to move this logic to decide_alg.  */
  if (mode == QImode && CONST_INT_P (count) && !(INTVAL (count) & 3)
      && (!issetmem || orig_value == const0_rtx))
    mode = SImode;

  if (destptr != XEXP (destmem, 0) || GET_MODE (destmem) != BLKmode)
    destmem = adjust_automodify_address_nv (destmem, BLKmode, destptr, 0);

  countreg = ix86_zero_extend_to_Pmode (scale_counter (count,
						       GET_MODE_SIZE (mode)));
  if (mode != QImode)
    {
      destexp = gen_rtx_ASHIFT (Pmode, countreg,
				GEN_INT (exact_log2 (GET_MODE_SIZE (mode))));
      destexp = gen_rtx_PLUS (Pmode, destexp, destptr);
    }
  else
    destexp = gen_rtx_PLUS (Pmode, destptr, countreg);
  if ((!issetmem || orig_value == const0_rtx) && CONST_INT_P (count))
    {
      rounded_count
	= ROUND_DOWN (INTVAL (count), (HOST_WIDE_INT) GET_MODE_SIZE (mode));
      destmem = shallow_copy_rtx (destmem);
      set_mem_size (destmem, rounded_count);
    }
  else if (MEM_SIZE_KNOWN_P (destmem))
    clear_mem_size (destmem);

  if (issetmem)
    {
      value = force_reg (mode, gen_lowpart (mode, value));
      emit_insn (gen_rep_stos (destptr, countreg, destmem, value, destexp));
    }
  else
    {
      if (srcptr != XEXP (srcmem, 0) || GET_MODE (srcmem) != BLKmode)
	srcmem = adjust_automodify_address_nv (srcmem, BLKmode, srcptr, 0);
      if (mode != QImode)
	{
	  srcexp = gen_rtx_ASHIFT (Pmode, countreg,
				   GEN_INT (exact_log2 (GET_MODE_SIZE (mode))));
	  srcexp = gen_rtx_PLUS (Pmode, srcexp, srcptr);
	}
      else
	srcexp = gen_rtx_PLUS (Pmode, srcptr, countreg);
      if (CONST_INT_P (count))
	{
	  rounded_count
	    = ROUND_DOWN (INTVAL (count), (HOST_WIDE_INT) GET_MODE_SIZE (mode));
	  srcmem = shallow_copy_rtx (srcmem);
	  set_mem_size (srcmem, rounded_count);
	}
      else
	{
	  if (MEM_SIZE_KNOWN_P (srcmem))
	    clear_mem_size (srcmem);
	}
      emit_insn (gen_rep_mov (destptr, destmem, srcptr, srcmem, countreg,
			      destexp, srcexp));
    }
}

/* This function emits moves to copy SIZE_TO_MOVE bytes from SRCMEM to
   DESTMEM.
   SRC is passed by pointer to be updated on return.
   Return value is updated DST.  */
static rtx
emit_memmov (rtx destmem, rtx *srcmem, rtx destptr, rtx srcptr,
	     HOST_WIDE_INT size_to_move)
{
  rtx dst = destmem, src = *srcmem, adjust, tempreg;
  enum insn_code code;
  machine_mode move_mode;
  int piece_size, i;

  /* Find the widest mode in which we could perform moves.
     Start with the biggest power of 2 less than SIZE_TO_MOVE and half
     it until move of such size is supported.  */
  piece_size = 1 << floor_log2 (size_to_move);
  while (!int_mode_for_size (piece_size * BITS_PER_UNIT, 0).exists (&move_mode)
	 || (code = optab_handler (mov_optab, move_mode)) == CODE_FOR_nothing)
    {
      gcc_assert (piece_size > 1);
      piece_size >>= 1;
    }

  /* Find the corresponding vector mode with the same size as MOVE_MODE.
     MOVE_MODE is an integer mode at the moment (SI, DI, TI, etc.).  */
  if (GET_MODE_SIZE (move_mode) > GET_MODE_SIZE (word_mode))
    {
      int nunits = GET_MODE_SIZE (move_mode) / GET_MODE_SIZE (word_mode);
      if (!mode_for_vector (word_mode, nunits).exists (&move_mode)
	  || (code = optab_handler (mov_optab, move_mode)) == CODE_FOR_nothing)
	{
	  move_mode = word_mode;
	  piece_size = GET_MODE_SIZE (move_mode);
	  code = optab_handler (mov_optab, move_mode);
	}
    }
  gcc_assert (code != CODE_FOR_nothing);

  dst = adjust_automodify_address_nv (dst, move_mode, destptr, 0);
  src = adjust_automodify_address_nv (src, move_mode, srcptr, 0);

  /* Emit moves.  We'll need SIZE_TO_MOVE/PIECE_SIZES moves.  */
  gcc_assert (size_to_move % piece_size == 0);
  adjust = GEN_INT (piece_size);
  for (i = 0; i < size_to_move; i += piece_size)
    {
      /* We move from memory to memory, so we'll need to do it via
	 a temporary register.  */
      tempreg = gen_reg_rtx (move_mode);
      emit_insn (GEN_FCN (code) (tempreg, src));
      emit_insn (GEN_FCN (code) (dst, tempreg));

      emit_move_insn (destptr,
		      gen_rtx_PLUS (Pmode, copy_rtx (destptr), adjust));
      emit_move_insn (srcptr,
		      gen_rtx_PLUS (Pmode, copy_rtx (srcptr), adjust));

      dst = adjust_automodify_address_nv (dst, move_mode, destptr,
					  piece_size);
      src = adjust_automodify_address_nv (src, move_mode, srcptr,
					  piece_size);
    }

  /* Update DST and SRC rtx.  */
  *srcmem = src;
  return dst;
}

/* Output code to copy at most count & (max_size - 1) bytes from SRC to DEST.  */
static void
expand_movmem_epilogue (rtx destmem, rtx srcmem,
			rtx destptr, rtx srcptr, rtx count, int max_size)
{
  rtx src, dest;
  if (CONST_INT_P (count))
    {
      HOST_WIDE_INT countval = INTVAL (count);
      HOST_WIDE_INT epilogue_size = countval % max_size;
      int i;

      /* For now MAX_SIZE should be a power of 2.  This assert could be
	 relaxed, but it'll require a bit more complicated epilogue
	 expanding.  */
      gcc_assert ((max_size & (max_size - 1)) == 0);
      for (i = max_size; i >= 1; i >>= 1)
	{
	  if (epilogue_size & i)
	    destmem = emit_memmov (destmem, &srcmem, destptr, srcptr, i);
	}
      return;
    }
  if (max_size > 8)
    {
      count = expand_simple_binop (GET_MODE (count), AND, count, GEN_INT (max_size - 1),
				    count, 1, OPTAB_DIRECT);
      expand_set_or_movmem_via_loop (destmem, srcmem, destptr, srcptr, NULL,
				     count, QImode, 1, 4, false);
      return;
    }

  /* When there are stringops, we can cheaply increase dest and src pointers.
     Otherwise we save code size by maintaining offset (zero is readily
     available from preceding rep operation) and using x86 addressing modes.
   */
  if (TARGET_SINGLE_STRINGOP)
    {
      if (max_size > 4)
	{
	  rtx_code_label *label = ix86_expand_aligntest (count, 4, true);
	  src = change_address (srcmem, SImode, srcptr);
	  dest = change_address (destmem, SImode, destptr);
	  emit_insn (gen_strmov (destptr, dest, srcptr, src));
	  emit_label (label);
	  LABEL_NUSES (label) = 1;
	}
      if (max_size > 2)
	{
	  rtx_code_label *label = ix86_expand_aligntest (count, 2, true);
	  src = change_address (srcmem, HImode, srcptr);
	  dest = change_address (destmem, HImode, destptr);
	  emit_insn (gen_strmov (destptr, dest, srcptr, src));
	  emit_label (label);
	  LABEL_NUSES (label) = 1;
	}
      if (max_size > 1)
	{
	  rtx_code_label *label = ix86_expand_aligntest (count, 1, true);
	  src = change_address (srcmem, QImode, srcptr);
	  dest = change_address (destmem, QImode, destptr);
	  emit_insn (gen_strmov (destptr, dest, srcptr, src));
	  emit_label (label);
	  LABEL_NUSES (label) = 1;
	}
    }
  else
    {
      rtx offset = force_reg (Pmode, const0_rtx);
      rtx tmp;

      if (max_size > 4)
	{
	  rtx_code_label *label = ix86_expand_aligntest (count, 4, true);
	  src = change_address (srcmem, SImode, srcptr);
	  dest = change_address (destmem, SImode, destptr);
	  emit_move_insn (dest, src);
	  tmp = expand_simple_binop (Pmode, PLUS, offset, GEN_INT (4), NULL,
				     true, OPTAB_LIB_WIDEN);
	  if (tmp != offset)
	    emit_move_insn (offset, tmp);
	  emit_label (label);
	  LABEL_NUSES (label) = 1;
	}
      if (max_size > 2)
	{
	  rtx_code_label *label = ix86_expand_aligntest (count, 2, true);
	  tmp = gen_rtx_PLUS (Pmode, srcptr, offset);
	  src = change_address (srcmem, HImode, tmp);
	  tmp = gen_rtx_PLUS (Pmode, destptr, offset);
	  dest = change_address (destmem, HImode, tmp);
	  emit_move_insn (dest, src);
	  tmp = expand_simple_binop (Pmode, PLUS, offset, GEN_INT (2), tmp,
				     true, OPTAB_LIB_WIDEN);
	  if (tmp != offset)
	    emit_move_insn (offset, tmp);
	  emit_label (label);
	  LABEL_NUSES (label) = 1;
	}
      if (max_size > 1)
	{
	  rtx_code_label *label = ix86_expand_aligntest (count, 1, true);
	  tmp = gen_rtx_PLUS (Pmode, srcptr, offset);
	  src = change_address (srcmem, QImode, tmp);
	  tmp = gen_rtx_PLUS (Pmode, destptr, offset);
	  dest = change_address (destmem, QImode, tmp);
	  emit_move_insn (dest, src);
	  emit_label (label);
	  LABEL_NUSES (label) = 1;
	}
    }
}

/* This function emits moves to fill SIZE_TO_MOVE bytes starting from DESTMEM
   with value PROMOTED_VAL.
   SRC is passed by pointer to be updated on return.
   Return value is updated DST.  */
static rtx
emit_memset (rtx destmem, rtx destptr, rtx promoted_val,
	     HOST_WIDE_INT size_to_move)
{
  rtx dst = destmem, adjust;
  enum insn_code code;
  machine_mode move_mode;
  int piece_size, i;

  /* Find the widest mode in which we could perform moves.
     Start with the biggest power of 2 less than SIZE_TO_MOVE and half
     it until move of such size is supported.  */
  move_mode = GET_MODE (promoted_val);
  if (move_mode == VOIDmode)
    move_mode = QImode;
  if (size_to_move < GET_MODE_SIZE (move_mode))
    {
      unsigned int move_bits = size_to_move * BITS_PER_UNIT;
      move_mode = int_mode_for_size (move_bits, 0).require ();
      promoted_val = gen_lowpart (move_mode, promoted_val);
    }
  piece_size = GET_MODE_SIZE (move_mode);
  code = optab_handler (mov_optab, move_mode);
  gcc_assert (code != CODE_FOR_nothing && promoted_val != NULL_RTX);

  dst = adjust_automodify_address_nv (dst, move_mode, destptr, 0);

  /* Emit moves.  We'll need SIZE_TO_MOVE/PIECE_SIZES moves.  */
  gcc_assert (size_to_move % piece_size == 0);
  adjust = GEN_INT (piece_size);
  for (i = 0; i < size_to_move; i += piece_size)
    {
      if (piece_size <= GET_MODE_SIZE (word_mode))
	{
	  emit_insn (gen_strset (destptr, dst, promoted_val));
	  dst = adjust_automodify_address_nv (dst, move_mode, destptr,
					      piece_size);
	  continue;
	}

      emit_insn (GEN_FCN (code) (dst, promoted_val));

      emit_move_insn (destptr,
		      gen_rtx_PLUS (Pmode, copy_rtx (destptr), adjust));

      dst = adjust_automodify_address_nv (dst, move_mode, destptr,
					  piece_size);
    }

  /* Update DST rtx.  */
  return dst;
}
/* Output code to set at most count & (max_size - 1) bytes starting by DEST.  */
static void
expand_setmem_epilogue_via_loop (rtx destmem, rtx destptr, rtx value,
				 rtx count, int max_size)
{
  count = expand_simple_binop (counter_mode (count), AND, count,
			       GEN_INT (max_size - 1), count, 1, OPTAB_DIRECT);
  expand_set_or_movmem_via_loop (destmem, NULL, destptr, NULL,
				 gen_lowpart (QImode, value), count, QImode,
				 1, max_size / 2, true);
}

/* Output code to set at most count & (max_size - 1) bytes starting by DEST.  */
static void
expand_setmem_epilogue (rtx destmem, rtx destptr, rtx value, rtx vec_value,
			rtx count, int max_size)
{
  rtx dest;

  if (CONST_INT_P (count))
    {
      HOST_WIDE_INT countval = INTVAL (count);
      HOST_WIDE_INT epilogue_size = countval % max_size;
      int i;

      /* For now MAX_SIZE should be a power of 2.  This assert could be
	 relaxed, but it'll require a bit more complicated epilogue
	 expanding.  */
      gcc_assert ((max_size & (max_size - 1)) == 0);
      for (i = max_size; i >= 1; i >>= 1)
	{
	  if (epilogue_size & i)
	    {
	      if (vec_value && i > GET_MODE_SIZE (GET_MODE (value)))
		destmem = emit_memset (destmem, destptr, vec_value, i);
	      else
		destmem = emit_memset (destmem, destptr, value, i);
	    }
	}
      return;
    }
  if (max_size > 32)
    {
      expand_setmem_epilogue_via_loop (destmem, destptr, value, count, max_size);
      return;
    }
  if (max_size > 16)
    {
      rtx_code_label *label = ix86_expand_aligntest (count, 16, true);
      if (TARGET_64BIT)
	{
	  dest = change_address (destmem, DImode, destptr);
	  emit_insn (gen_strset (destptr, dest, value));
	  dest = adjust_automodify_address_nv (dest, DImode, destptr, 8);
	  emit_insn (gen_strset (destptr, dest, value));
	}
      else
	{
	  dest = change_address (destmem, SImode, destptr);
	  emit_insn (gen_strset (destptr, dest, value));
	  dest = adjust_automodify_address_nv (dest, SImode, destptr, 4);
	  emit_insn (gen_strset (destptr, dest, value));
	  dest = adjust_automodify_address_nv (dest, SImode, destptr, 8);
	  emit_insn (gen_strset (destptr, dest, value));
	  dest = adjust_automodify_address_nv (dest, SImode, destptr, 12);
	  emit_insn (gen_strset (destptr, dest, value));
	}
      emit_label (label);
      LABEL_NUSES (label) = 1;
    }
  if (max_size > 8)
    {
      rtx_code_label *label = ix86_expand_aligntest (count, 8, true);
      if (TARGET_64BIT)
	{
	  dest = change_address (destmem, DImode, destptr);
	  emit_insn (gen_strset (destptr, dest, value));
	}
      else
	{
	  dest = change_address (destmem, SImode, destptr);
	  emit_insn (gen_strset (destptr, dest, value));
	  dest = adjust_automodify_address_nv (dest, SImode, destptr, 4);
	  emit_insn (gen_strset (destptr, dest, value));
	}
      emit_label (label);
      LABEL_NUSES (label) = 1;
    }
  if (max_size > 4)
    {
      rtx_code_label *label = ix86_expand_aligntest (count, 4, true);
      dest = change_address (destmem, SImode, destptr);
      emit_insn (gen_strset (destptr, dest, gen_lowpart (SImode, value)));
      emit_label (label);
      LABEL_NUSES (label) = 1;
    }
  if (max_size > 2)
    {
      rtx_code_label *label = ix86_expand_aligntest (count, 2, true);
      dest = change_address (destmem, HImode, destptr);
      emit_insn (gen_strset (destptr, dest, gen_lowpart (HImode, value)));
      emit_label (label);
      LABEL_NUSES (label) = 1;
    }
  if (max_size > 1)
    {
      rtx_code_label *label = ix86_expand_aligntest (count, 1, true);
      dest = change_address (destmem, QImode, destptr);
      emit_insn (gen_strset (destptr, dest, gen_lowpart (QImode, value)));
      emit_label (label);
      LABEL_NUSES (label) = 1;
    }
}

/* Depending on ISSETMEM, copy enough from SRCMEM to DESTMEM or set enough to
   DESTMEM to align it to DESIRED_ALIGNMENT.  Original alignment is ALIGN.
   Depending on ISSETMEM, either arguments SRCMEM/SRCPTR or VALUE/VEC_VALUE are
   ignored.
   Return value is updated DESTMEM.  */
static rtx
expand_set_or_movmem_prologue (rtx destmem, rtx srcmem,
				  rtx destptr, rtx srcptr, rtx value,
				  rtx vec_value, rtx count, int align,
				  int desired_alignment, bool issetmem)
{
  int i;
  for (i = 1; i < desired_alignment; i <<= 1)
    {
      if (align <= i)
	{
	  rtx_code_label *label = ix86_expand_aligntest (destptr, i, false);
	  if (issetmem)
	    {
	      if (vec_value && i > GET_MODE_SIZE (GET_MODE (value)))
		destmem = emit_memset (destmem, destptr, vec_value, i);
	      else
		destmem = emit_memset (destmem, destptr, value, i);
	    }
	  else
	    destmem = emit_memmov (destmem, &srcmem, destptr, srcptr, i);
	  ix86_adjust_counter (count, i);
	  emit_label (label);
	  LABEL_NUSES (label) = 1;
	  set_mem_align (destmem, i * 2 * BITS_PER_UNIT);
	}
    }
  return destmem;
}

/* Test if COUNT&SIZE is nonzero and if so, expand movme
   or setmem sequence that is valid for SIZE..2*SIZE-1 bytes
   and jump to DONE_LABEL.  */
static void
expand_small_movmem_or_setmem (rtx destmem, rtx srcmem,
			       rtx destptr, rtx srcptr,
			       rtx value, rtx vec_value,
			       rtx count, int size,
			       rtx done_label, bool issetmem)
{
  rtx_code_label *label = ix86_expand_aligntest (count, size, false);
  machine_mode mode = int_mode_for_size (size * BITS_PER_UNIT, 1).else_blk ();
  rtx modesize;
  int n;

  /* If we do not have vector value to copy, we must reduce size.  */
  if (issetmem)
    {
      if (!vec_value)
	{
	  if (GET_MODE (value) == VOIDmode && size > 8)
	    mode = Pmode;
	  else if (GET_MODE_SIZE (mode) > GET_MODE_SIZE (GET_MODE (value)))
	    mode = GET_MODE (value);
	}
      else
	mode = GET_MODE (vec_value), value = vec_value;
    }
  else
    {
      /* Choose appropriate vector mode.  */
      if (size >= 32)
	mode = TARGET_AVX ? V32QImode : TARGET_SSE ? V16QImode : DImode;
      else if (size >= 16)
	mode = TARGET_SSE ? V16QImode : DImode;
      srcmem = change_address (srcmem, mode, srcptr);
    }
  destmem = change_address (destmem, mode, destptr);
  modesize = GEN_INT (GET_MODE_SIZE (mode));
  gcc_assert (GET_MODE_SIZE (mode) <= size);
  for (n = 0; n * GET_MODE_SIZE (mode) < size; n++)
    {
      if (issetmem)
	emit_move_insn (destmem, gen_lowpart (mode, value));
      else
	{
          emit_move_insn (destmem, srcmem);
          srcmem = offset_address (srcmem, modesize, GET_MODE_SIZE (mode));
	}
      destmem = offset_address (destmem, modesize, GET_MODE_SIZE (mode));
    }

  destmem = offset_address (destmem, count, 1);
  destmem = offset_address (destmem, GEN_INT (-2 * size),
			    GET_MODE_SIZE (mode));
  if (!issetmem)
    {
      srcmem = offset_address (srcmem, count, 1);
      srcmem = offset_address (srcmem, GEN_INT (-2 * size),
			       GET_MODE_SIZE (mode));
    }
  for (n = 0; n * GET_MODE_SIZE (mode) < size; n++)
    {
      if (issetmem)
	emit_move_insn (destmem, gen_lowpart (mode, value));
      else
	{
	  emit_move_insn (destmem, srcmem);
	  srcmem = offset_address (srcmem, modesize, GET_MODE_SIZE (mode));
	}
      destmem = offset_address (destmem, modesize, GET_MODE_SIZE (mode));
    }
  emit_jump_insn (gen_jump (done_label));
  emit_barrier ();

  emit_label (label);
  LABEL_NUSES (label) = 1;
}

/* Handle small memcpy (up to SIZE that is supposed to be small power of 2.
   and get ready for the main memcpy loop by copying iniital DESIRED_ALIGN-ALIGN
   bytes and last SIZE bytes adjusitng DESTPTR/SRCPTR/COUNT in a way we can
   proceed with an loop copying SIZE bytes at once. Do moves in MODE.
   DONE_LABEL is a label after the whole copying sequence. The label is created
   on demand if *DONE_LABEL is NULL.
   MIN_SIZE is minimal size of block copied.  This value gets adjusted for new
   bounds after the initial copies. 

   DESTMEM/SRCMEM are memory expressions pointing to the copies block,
   DESTPTR/SRCPTR are pointers to the block. DYNAMIC_CHECK indicate whether
   we will dispatch to a library call for large blocks.

   In pseudocode we do:

   if (COUNT < SIZE)
     {
       Assume that SIZE is 4. Bigger sizes are handled analogously
       if (COUNT & 4)
	 {
	    copy 4 bytes from SRCPTR to DESTPTR
	    copy 4 bytes from SRCPTR + COUNT - 4 to DESTPTR + COUNT - 4
	    goto done_label
	 }
       if (!COUNT)
	 goto done_label;
       copy 1 byte from SRCPTR to DESTPTR
       if (COUNT & 2)
	 {
	    copy 2 bytes from SRCPTR to DESTPTR
	    copy 2 bytes from SRCPTR + COUNT - 2 to DESTPTR + COUNT - 2
	 }
     }
   else
     {
       copy at least DESIRED_ALIGN-ALIGN bytes from SRCPTR to DESTPTR
       copy SIZE bytes from SRCPTR + COUNT - SIZE to DESTPTR + COUNT -SIZE

       OLD_DESPTR = DESTPTR;
       Align DESTPTR up to DESIRED_ALIGN
       SRCPTR += DESTPTR - OLD_DESTPTR
       COUNT -= DEST_PTR - OLD_DESTPTR
       if (DYNAMIC_CHECK)
	 Round COUNT down to multiple of SIZE
       << optional caller supplied zero size guard is here >>
       << optional caller supplied dynamic check is here >>
       << caller supplied main copy loop is here >>
     }
   done_label:
  */
static void
expand_set_or_movmem_prologue_epilogue_by_misaligned_moves (rtx destmem, rtx srcmem,
							    rtx *destptr, rtx *srcptr,
							    machine_mode mode,
							    rtx value, rtx vec_value,
							    rtx *count,
							    rtx_code_label **done_label,
							    int size,
							    int desired_align,
							    int align,
							    unsigned HOST_WIDE_INT *min_size,
							    bool dynamic_check,
							    bool issetmem)
{
  rtx_code_label *loop_label = NULL, *label;
  int n;
  rtx modesize;
  int prolog_size = 0;
  rtx mode_value;

  /* Chose proper value to copy.  */
  if (issetmem && VECTOR_MODE_P (mode))
    mode_value = vec_value;
  else
    mode_value = value;
  gcc_assert (GET_MODE_SIZE (mode) <= size);

  /* See if block is big or small, handle small blocks.  */
  if (!CONST_INT_P (*count) && *min_size < (unsigned HOST_WIDE_INT)size)
    {
      int size2 = size;
      loop_label = gen_label_rtx ();

      if (!*done_label)
	*done_label = gen_label_rtx ();

      emit_cmp_and_jump_insns (*count, GEN_INT (size2), GE, 0, GET_MODE (*count),
			       1, loop_label);
      size2 >>= 1;

      /* Handle sizes > 3.  */
      for (;size2 > 2; size2 >>= 1)
	expand_small_movmem_or_setmem (destmem, srcmem,
				       *destptr, *srcptr,
				       value, vec_value,
				       *count,
				       size2, *done_label, issetmem);
      /* Nothing to copy?  Jump to DONE_LABEL if so */
      emit_cmp_and_jump_insns (*count, const0_rtx, EQ, 0, GET_MODE (*count),
			       1, *done_label);

      /* Do a byte copy.  */
      destmem = change_address (destmem, QImode, *destptr);
      if (issetmem)
	emit_move_insn (destmem, gen_lowpart (QImode, value));
      else
	{
          srcmem = change_address (srcmem, QImode, *srcptr);
          emit_move_insn (destmem, srcmem);
	}

      /* Handle sizes 2 and 3.  */
      label = ix86_expand_aligntest (*count, 2, false);
      destmem = change_address (destmem, HImode, *destptr);
      destmem = offset_address (destmem, *count, 1);
      destmem = offset_address (destmem, GEN_INT (-2), 2);
      if (issetmem)
        emit_move_insn (destmem, gen_lowpart (HImode, value));
      else
	{
	  srcmem = change_address (srcmem, HImode, *srcptr);
	  srcmem = offset_address (srcmem, *count, 1);
	  srcmem = offset_address (srcmem, GEN_INT (-2), 2);
	  emit_move_insn (destmem, srcmem);
	}

      emit_label (label);
      LABEL_NUSES (label) = 1;
      emit_jump_insn (gen_jump (*done_label));
      emit_barrier ();
    }
  else
    gcc_assert (*min_size >= (unsigned HOST_WIDE_INT)size
		|| UINTVAL (*count) >= (unsigned HOST_WIDE_INT)size);

  /* Start memcpy for COUNT >= SIZE.  */
  if (loop_label)
    {
       emit_label (loop_label);
       LABEL_NUSES (loop_label) = 1;
    }

  /* Copy first desired_align bytes.  */
  if (!issetmem)
    srcmem = change_address (srcmem, mode, *srcptr);
  destmem = change_address (destmem, mode, *destptr);
  modesize = GEN_INT (GET_MODE_SIZE (mode));
  for (n = 0; prolog_size < desired_align - align; n++)
    {
      if (issetmem)
        emit_move_insn (destmem, mode_value);
      else
	{
          emit_move_insn (destmem, srcmem);
          srcmem = offset_address (srcmem, modesize, GET_MODE_SIZE (mode));
	}
      destmem = offset_address (destmem, modesize, GET_MODE_SIZE (mode));
      prolog_size += GET_MODE_SIZE (mode);
    }


  /* Copy last SIZE bytes.  */
  destmem = offset_address (destmem, *count, 1);
  destmem = offset_address (destmem,
			    GEN_INT (-size - prolog_size),
			    1);
  if (issetmem)
    emit_move_insn (destmem, mode_value);
  else
    {
      srcmem = offset_address (srcmem, *count, 1);
      srcmem = offset_address (srcmem,
			       GEN_INT (-size - prolog_size),
			       1);
      emit_move_insn (destmem, srcmem);
    }
  for (n = 1; n * GET_MODE_SIZE (mode) < size; n++)
    {
      destmem = offset_address (destmem, modesize, 1);
      if (issetmem)
	emit_move_insn (destmem, mode_value);
      else
	{
          srcmem = offset_address (srcmem, modesize, 1);
          emit_move_insn (destmem, srcmem);
	}
    }

  /* Align destination.  */
  if (desired_align > 1 && desired_align > align)
    {
      rtx saveddest = *destptr;

      gcc_assert (desired_align <= size);
      /* Align destptr up, place it to new register.  */
      *destptr = expand_simple_binop (GET_MODE (*destptr), PLUS, *destptr,
				      GEN_INT (prolog_size),
				      NULL_RTX, 1, OPTAB_DIRECT);
      if (REG_P (*destptr) && REG_P (saveddest) && REG_POINTER (saveddest))
	REG_POINTER (*destptr) = 1;
      *destptr = expand_simple_binop (GET_MODE (*destptr), AND, *destptr,
				      GEN_INT (-desired_align),
				      *destptr, 1, OPTAB_DIRECT);
      /* See how many bytes we skipped.  */
      saveddest = expand_simple_binop (GET_MODE (*destptr), MINUS, saveddest,
				       *destptr,
				       saveddest, 1, OPTAB_DIRECT);
      /* Adjust srcptr and count.  */
      if (!issetmem)
	*srcptr = expand_simple_binop (GET_MODE (*srcptr), MINUS, *srcptr,
				       saveddest, *srcptr, 1, OPTAB_DIRECT);
      *count = expand_simple_binop (GET_MODE (*count), PLUS, *count,
				    saveddest, *count, 1, OPTAB_DIRECT);
      /* We copied at most size + prolog_size.  */
      if (*min_size > (unsigned HOST_WIDE_INT)(size + prolog_size))
	*min_size
	  = ROUND_DOWN (*min_size - size, (unsigned HOST_WIDE_INT)size);
      else
	*min_size = 0;

      /* Our loops always round down the block size, but for dispatch to
         library we need precise value.  */
      if (dynamic_check)
	*count = expand_simple_binop (GET_MODE (*count), AND, *count,
				      GEN_INT (-size), *count, 1, OPTAB_DIRECT);
    }
  else
    {
      gcc_assert (prolog_size == 0);
      /* Decrease count, so we won't end up copying last word twice.  */
      if (!CONST_INT_P (*count))
	*count = expand_simple_binop (GET_MODE (*count), PLUS, *count,
				      constm1_rtx, *count, 1, OPTAB_DIRECT);
      else
	*count = GEN_INT (ROUND_DOWN (UINTVAL (*count) - 1,
				      (unsigned HOST_WIDE_INT)size));
      if (*min_size)
	*min_size = ROUND_DOWN (*min_size - 1, (unsigned HOST_WIDE_INT)size);
    }
}


/* This function is like the previous one, except here we know how many bytes
   need to be copied.  That allows us to update alignment not only of DST, which
   is returned, but also of SRC, which is passed as a pointer for that
   reason.  */
static rtx
expand_set_or_movmem_constant_prologue (rtx dst, rtx *srcp, rtx destreg,
					   rtx srcreg, rtx value, rtx vec_value,
					   int desired_align, int align_bytes,
					   bool issetmem)
{
  rtx src = NULL;
  rtx orig_dst = dst;
  rtx orig_src = NULL;
  int piece_size = 1;
  int copied_bytes = 0;

  if (!issetmem)
    {
      gcc_assert (srcp != NULL);
      src = *srcp;
      orig_src = src;
    }

  for (piece_size = 1;
       piece_size <= desired_align && copied_bytes < align_bytes;
       piece_size <<= 1)
    {
      if (align_bytes & piece_size)
	{
	  if (issetmem)
	    {
	      if (vec_value && piece_size > GET_MODE_SIZE (GET_MODE (value)))
		dst = emit_memset (dst, destreg, vec_value, piece_size);
	      else
		dst = emit_memset (dst, destreg, value, piece_size);
	    }
	  else
	    dst = emit_memmov (dst, &src, destreg, srcreg, piece_size);
	  copied_bytes += piece_size;
	}
    }
  if (MEM_ALIGN (dst) < (unsigned int) desired_align * BITS_PER_UNIT)
    set_mem_align (dst, desired_align * BITS_PER_UNIT);
  if (MEM_SIZE_KNOWN_P (orig_dst))
    set_mem_size (dst, MEM_SIZE (orig_dst) - align_bytes);

  if (!issetmem)
    {
      int src_align_bytes = get_mem_align_offset (src, desired_align
						       * BITS_PER_UNIT);
      if (src_align_bytes >= 0)
	src_align_bytes = desired_align - src_align_bytes;
      if (src_align_bytes >= 0)
	{
	  unsigned int src_align;
	  for (src_align = desired_align; src_align >= 2; src_align >>= 1)
	    {
	      if ((src_align_bytes & (src_align - 1))
		   == (align_bytes & (src_align - 1)))
		break;
	    }
	  if (src_align > (unsigned int) desired_align)
	    src_align = desired_align;
	  if (MEM_ALIGN (src) < src_align * BITS_PER_UNIT)
	    set_mem_align (src, src_align * BITS_PER_UNIT);
	}
      if (MEM_SIZE_KNOWN_P (orig_src))
	set_mem_size (src, MEM_SIZE (orig_src) - align_bytes);
      *srcp = src;
    }

  return dst;
}

/* Return true if ALG can be used in current context.  
   Assume we expand memset if MEMSET is true.  */
static bool
alg_usable_p (enum stringop_alg alg, bool memset, bool have_as)
{
  if (alg == no_stringop)
    return false;
  if (alg == vector_loop)
    return TARGET_SSE || TARGET_AVX;
  /* Algorithms using the rep prefix want at least edi and ecx;
     additionally, memset wants eax and memcpy wants esi.  Don't
     consider such algorithms if the user has appropriated those
     registers for their own purposes, or if we have a non-default
     address space, since some string insns cannot override the segment.  */
  if (alg == rep_prefix_1_byte
      || alg == rep_prefix_4_byte
      || alg == rep_prefix_8_byte)
    {
      if (have_as)
	return false;
      if (fixed_regs[CX_REG]
	  || fixed_regs[DI_REG]
	  || (memset ? fixed_regs[AX_REG] : fixed_regs[SI_REG]))
	return false;
    }
  return true;
}

/* Given COUNT and EXPECTED_SIZE, decide on codegen of string operation.  */
static enum stringop_alg
decide_alg (HOST_WIDE_INT count, HOST_WIDE_INT expected_size,
	    unsigned HOST_WIDE_INT min_size, unsigned HOST_WIDE_INT max_size,
	    bool memset, bool zero_memset, bool have_as,
	    int *dynamic_check, bool *noalign, bool recur)
{
  const struct stringop_algs *algs;
  bool optimize_for_speed;
  int max = 0;
  const struct processor_costs *cost;
  int i;
  bool any_alg_usable_p = false;

  *noalign = false;
  *dynamic_check = -1;

  /* Even if the string operation call is cold, we still might spend a lot
     of time processing large blocks.  */
  if (optimize_function_for_size_p (cfun)
      || (optimize_insn_for_size_p ()
 	  && (max_size < 256
              || (expected_size != -1 && expected_size < 256))))
    optimize_for_speed = false;
  else
    optimize_for_speed = true;

  cost = optimize_for_speed ? ix86_cost : &ix86_size_cost;
  if (memset)
    algs = &cost->memset[TARGET_64BIT != 0];
  else
    algs = &cost->memcpy[TARGET_64BIT != 0];

  /* See maximal size for user defined algorithm.  */
  for (i = 0; i < MAX_STRINGOP_ALGS; i++)
    {
      enum stringop_alg candidate = algs->size[i].alg;
      bool usable = alg_usable_p (candidate, memset, have_as);
      any_alg_usable_p |= usable;

      if (candidate != libcall && candidate && usable)
	max = algs->size[i].max;
    }

  /* If expected size is not known but max size is small enough
     so inline version is a win, set expected size into
     the range.  */
  if (((max > 1 && (unsigned HOST_WIDE_INT) max >= max_size) || max == -1)
      && expected_size == -1)
    expected_size = min_size / 2 + max_size / 2;

  /* If user specified the algorithm, honor it if possible.  */
  if (ix86_stringop_alg != no_stringop
      && alg_usable_p (ix86_stringop_alg, memset, have_as))
    return ix86_stringop_alg;
  /* rep; movq or rep; movl is the smallest variant.  */
  else if (!optimize_for_speed)
    {
      *noalign = true;
      if (!count || (count & 3) || (memset && !zero_memset))
	return alg_usable_p (rep_prefix_1_byte, memset, have_as)
	       ? rep_prefix_1_byte : loop_1_byte;
      else
	return alg_usable_p (rep_prefix_4_byte, memset, have_as)
	       ? rep_prefix_4_byte : loop;
    }
  /* Very tiny blocks are best handled via the loop, REP is expensive to
     setup.  */
  else if (expected_size != -1 && expected_size < 4)
    return loop_1_byte;
  else if (expected_size != -1)
    {
      enum stringop_alg alg = libcall;
      bool alg_noalign = false;
      for (i = 0; i < MAX_STRINGOP_ALGS; i++)
	{
	  /* We get here if the algorithms that were not libcall-based
	     were rep-prefix based and we are unable to use rep prefixes
	     based on global register usage.  Break out of the loop and
	     use the heuristic below.  */
	  if (algs->size[i].max == 0)
	    break;
	  if (algs->size[i].max >= expected_size || algs->size[i].max == -1)
	    {
	      enum stringop_alg candidate = algs->size[i].alg;

	      if (candidate != libcall
		  && alg_usable_p (candidate, memset, have_as))
		{
		  alg = candidate;
		  alg_noalign = algs->size[i].noalign;
		}
	      /* Honor TARGET_INLINE_ALL_STRINGOPS by picking
		 last non-libcall inline algorithm.  */
	      if (TARGET_INLINE_ALL_STRINGOPS)
		{
		  /* When the current size is best to be copied by a libcall,
		     but we are still forced to inline, run the heuristic below
		     that will pick code for medium sized blocks.  */
		  if (alg != libcall)
		    {
		      *noalign = alg_noalign;
		      return alg;
		    }
		  else if (!any_alg_usable_p)
		    break;
		}
	      else if (alg_usable_p (candidate, memset, have_as))
		{
		  *noalign = algs->size[i].noalign;
		  return candidate;
		}
	    }
	}
    }
  /* When asked to inline the call anyway, try to pick meaningful choice.
     We look for maximal size of block that is faster to copy by hand and
     take blocks of at most of that size guessing that average size will
     be roughly half of the block.

     If this turns out to be bad, we might simply specify the preferred
     choice in ix86_costs.  */
  if ((TARGET_INLINE_ALL_STRINGOPS || TARGET_INLINE_STRINGOPS_DYNAMICALLY)
      && (algs->unknown_size == libcall
	  || !alg_usable_p (algs->unknown_size, memset, have_as)))
    {
      enum stringop_alg alg;
      HOST_WIDE_INT new_expected_size = (max > 0 ? max : 4096) / 2;

      /* If there aren't any usable algorithms or if recursing already,
	 then recursing on smaller sizes or same size isn't going to
	 find anything.  Just return the simple byte-at-a-time copy loop.  */
      if (!any_alg_usable_p || recur)
	{
	  /* Pick something reasonable.  */
	  if (TARGET_INLINE_STRINGOPS_DYNAMICALLY && !recur)
	    *dynamic_check = 128;
	  return loop_1_byte;
	}
      alg = decide_alg (count, new_expected_size, min_size, max_size, memset,
			zero_memset, have_as, dynamic_check, noalign, true);
      gcc_assert (*dynamic_check == -1);
      if (TARGET_INLINE_STRINGOPS_DYNAMICALLY)
	*dynamic_check = max;
      else
	gcc_assert (alg != libcall);
      return alg;
    }
  return (alg_usable_p (algs->unknown_size, memset, have_as)
	  ? algs->unknown_size : libcall);
}

/* Decide on alignment.  We know that the operand is already aligned to ALIGN
   (ALIGN can be based on profile feedback and thus it is not 100% guaranteed).  */
static int
decide_alignment (int align,
		  enum stringop_alg alg,
		  int expected_size,
		  machine_mode move_mode)
{
  int desired_align = 0;

  gcc_assert (alg != no_stringop);

  if (alg == libcall)
    return 0;
  if (move_mode == VOIDmode)
    return 0;

  desired_align = GET_MODE_SIZE (move_mode);
  /* PentiumPro has special logic triggering for 8 byte aligned blocks.
     copying whole cacheline at once.  */
  if (TARGET_PENTIUMPRO
      && (alg == rep_prefix_4_byte || alg == rep_prefix_1_byte))
    desired_align = 8;

  if (optimize_size)
    desired_align = 1;
  if (desired_align < align)
    desired_align = align;
  if (expected_size != -1 && expected_size < 4)
    desired_align = align;

  return desired_align;
}


/* Helper function for memcpy.  For QImode value 0xXY produce
   0xXYXYXYXY of wide specified by MODE.  This is essentially
   a * 0x10101010, but we can do slightly better than
   synth_mult by unwinding the sequence by hand on CPUs with
   slow multiply.  */
static rtx
promote_duplicated_reg (machine_mode mode, rtx val)
{
  machine_mode valmode = GET_MODE (val);
  rtx tmp;
  int nops = mode == DImode ? 3 : 2;

  gcc_assert (mode == SImode || mode == DImode || val == const0_rtx);
  if (val == const0_rtx)
    return copy_to_mode_reg (mode, CONST0_RTX (mode));
  if (CONST_INT_P (val))
    {
      HOST_WIDE_INT v = INTVAL (val) & 255;

      v |= v << 8;
      v |= v << 16;
      if (mode == DImode)
        v |= (v << 16) << 16;
      return copy_to_mode_reg (mode, gen_int_mode (v, mode));
    }

  if (valmode == VOIDmode)
    valmode = QImode;
  if (valmode != QImode)
    val = gen_lowpart (QImode, val);
  if (mode == QImode)
    return val;
  if (!TARGET_PARTIAL_REG_STALL)
    nops--;
  if (ix86_cost->mult_init[mode == DImode ? 3 : 2]
      + ix86_cost->mult_bit * (mode == DImode ? 8 : 4)
      <= (ix86_cost->shift_const + ix86_cost->add) * nops
          + (COSTS_N_INSNS (TARGET_PARTIAL_REG_STALL == 0)))
    {
      rtx reg = convert_modes (mode, QImode, val, true);
      tmp = promote_duplicated_reg (mode, const1_rtx);
      return expand_simple_binop (mode, MULT, reg, tmp, NULL, 1,
				  OPTAB_DIRECT);
    }
  else
    {
      rtx reg = convert_modes (mode, QImode, val, true);

      if (!TARGET_PARTIAL_REG_STALL)
	if (mode == SImode)
	  emit_insn (gen_insvsi_1 (reg, reg));
	else
	  emit_insn (gen_insvdi_1 (reg, reg));
      else
	{
	  tmp = expand_simple_binop (mode, ASHIFT, reg, GEN_INT (8),
				     NULL, 1, OPTAB_DIRECT);
	  reg = expand_simple_binop (mode, IOR, reg, tmp, reg, 1,
				     OPTAB_DIRECT);
	}
      tmp = expand_simple_binop (mode, ASHIFT, reg, GEN_INT (16),
			         NULL, 1, OPTAB_DIRECT);
      reg = expand_simple_binop (mode, IOR, reg, tmp, reg, 1, OPTAB_DIRECT);
      if (mode == SImode)
	return reg;
      tmp = expand_simple_binop (mode, ASHIFT, reg, GEN_INT (32),
				 NULL, 1, OPTAB_DIRECT);
      reg = expand_simple_binop (mode, IOR, reg, tmp, reg, 1, OPTAB_DIRECT);
      return reg;
    }
}

/* Duplicate value VAL using promote_duplicated_reg into maximal size that will
   be needed by main loop copying SIZE_NEEDED chunks and prologue getting
   alignment from ALIGN to DESIRED_ALIGN.  */
static rtx
promote_duplicated_reg_to_size (rtx val, int size_needed, int desired_align,
				int align)
{
  rtx promoted_val;

  if (TARGET_64BIT
      && (size_needed > 4 || (desired_align > align && desired_align > 4)))
    promoted_val = promote_duplicated_reg (DImode, val);
  else if (size_needed > 2 || (desired_align > align && desired_align > 2))
    promoted_val = promote_duplicated_reg (SImode, val);
  else if (size_needed > 1 || (desired_align > align && desired_align > 1))
    promoted_val = promote_duplicated_reg (HImode, val);
  else
    promoted_val = val;

  return promoted_val;
}

/* Expand string move (memcpy) ot store (memset) operation.  Use i386 string
   operations when profitable.  The code depends upon architecture, block size
   and alignment, but always has one of the following overall structures:

   Aligned move sequence:

     1) Prologue guard: Conditional that jumps up to epilogues for small
	blocks that can be handled by epilogue alone.  This is faster
	but also needed for correctness, since prologue assume the block
	is larger than the desired alignment.

	Optional dynamic check for size and libcall for large
	blocks is emitted here too, with -minline-stringops-dynamically.

     2) Prologue: copy first few bytes in order to get destination
	aligned to DESIRED_ALIGN.  It is emitted only when ALIGN is less
	than DESIRED_ALIGN and up to DESIRED_ALIGN - ALIGN bytes can be
	copied.  We emit either a jump tree on power of two sized
	blocks, or a byte loop.

     3) Main body: the copying loop itself, copying in SIZE_NEEDED chunks
	with specified algorithm.

     4) Epilogue: code copying tail of the block that is too small to be
	handled by main body (or up to size guarded by prologue guard). 

  Misaligned move sequence

     1) missaligned move prologue/epilogue containing:
        a) Prologue handling small memory blocks and jumping to done_label
	   (skipped if blocks are known to be large enough)
	b) Signle move copying first DESIRED_ALIGN-ALIGN bytes if alignment is
           needed by single possibly misaligned move
	   (skipped if alignment is not needed)
        c) Copy of last SIZE_NEEDED bytes by possibly misaligned moves

     2) Zero size guard dispatching to done_label, if needed

     3) dispatch to library call, if needed,

     3) Main body: the copying loop itself, copying in SIZE_NEEDED chunks
	with specified algorithm.  */
bool
ix86_expand_set_or_movmem (rtx dst, rtx src, rtx count_exp, rtx val_exp,
			   rtx align_exp, rtx expected_align_exp,
			   rtx expected_size_exp, rtx min_size_exp,
			   rtx max_size_exp, rtx probable_max_size_exp,
			   bool issetmem)
{
  rtx destreg;
  rtx srcreg = NULL;
  rtx_code_label *label = NULL;
  rtx tmp;
  rtx_code_label *jump_around_label = NULL;
  HOST_WIDE_INT align = 1;
  unsigned HOST_WIDE_INT count = 0;
  HOST_WIDE_INT expected_size = -1;
  int size_needed = 0, epilogue_size_needed;
  int desired_align = 0, align_bytes = 0;
  enum stringop_alg alg;
  rtx promoted_val = NULL;
  rtx vec_promoted_val = NULL;
  bool force_loopy_epilogue = false;
  int dynamic_check;
  bool need_zero_guard = false;
  bool noalign;
  machine_mode move_mode = VOIDmode;
  machine_mode wider_mode;
  int unroll_factor = 1;
  /* TODO: Once value ranges are available, fill in proper data.  */
  unsigned HOST_WIDE_INT min_size = 0;
  unsigned HOST_WIDE_INT max_size = -1;
  unsigned HOST_WIDE_INT probable_max_size = -1;
  bool misaligned_prologue_used = false;
  bool have_as;

  if (CONST_INT_P (align_exp))
    align = INTVAL (align_exp);
  /* i386 can do misaligned access on reasonably increased cost.  */
  if (CONST_INT_P (expected_align_exp)
      && INTVAL (expected_align_exp) > align)
    align = INTVAL (expected_align_exp);
  /* ALIGN is the minimum of destination and source alignment, but we care here
     just about destination alignment.  */
  else if (!issetmem
	   && MEM_ALIGN (dst) > (unsigned HOST_WIDE_INT) align * BITS_PER_UNIT)
    align = MEM_ALIGN (dst) / BITS_PER_UNIT;

  if (CONST_INT_P (count_exp))
    {
      min_size = max_size = probable_max_size = count = expected_size
	= INTVAL (count_exp);
      /* When COUNT is 0, there is nothing to do.  */
      if (!count)
	return true;
    }
  else
    {
      if (min_size_exp)
	min_size = INTVAL (min_size_exp);
      if (max_size_exp)
	max_size = INTVAL (max_size_exp);
      if (probable_max_size_exp)
	probable_max_size = INTVAL (probable_max_size_exp);
      if (CONST_INT_P (expected_size_exp))
	expected_size = INTVAL (expected_size_exp);
     }

  /* Make sure we don't need to care about overflow later on.  */
  if (count > (HOST_WIDE_INT_1U << 30))
    return false;

  have_as = !ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (dst));
  if (!issetmem)
    have_as |= !ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (src));

  /* Step 0: Decide on preferred algorithm, desired alignment and
     size of chunks to be copied by main loop.  */
  alg = decide_alg (count, expected_size, min_size, probable_max_size,
		    issetmem,
		    issetmem && val_exp == const0_rtx, have_as,
		    &dynamic_check, &noalign, false);

  if (dump_file)
    fprintf (dump_file, "Selected stringop expansion strategy: %s\n",
	     stringop_alg_names[alg]);

  if (alg == libcall)
    return false;
  gcc_assert (alg != no_stringop);

  /* For now vector-version of memset is generated only for memory zeroing, as
     creating of promoted vector value is very cheap in this case.  */
  if (issetmem && alg == vector_loop && val_exp != const0_rtx)
    alg = unrolled_loop;

  if (!count)
    count_exp = copy_to_mode_reg (GET_MODE (count_exp), count_exp);
  destreg = ix86_copy_addr_to_reg (XEXP (dst, 0));
  if (!issetmem)
    srcreg = ix86_copy_addr_to_reg (XEXP (src, 0));

  unroll_factor = 1;
  move_mode = word_mode;
  switch (alg)
    {
    case libcall:
    case no_stringop:
    case last_alg:
      gcc_unreachable ();
    case loop_1_byte:
      need_zero_guard = true;
      move_mode = QImode;
      break;
    case loop:
      need_zero_guard = true;
      break;
    case unrolled_loop:
      need_zero_guard = true;
      unroll_factor = (TARGET_64BIT ? 4 : 2);
      break;
    case vector_loop:
      need_zero_guard = true;
      unroll_factor = 4;
      /* Find the widest supported mode.  */
      move_mode = word_mode;
      while (GET_MODE_WIDER_MODE (move_mode).exists (&wider_mode)
	     && optab_handler (mov_optab, wider_mode) != CODE_FOR_nothing)
	move_mode = wider_mode;

      if (TARGET_AVX128_OPTIMAL && GET_MODE_BITSIZE (move_mode) > 128)
	move_mode = TImode;

      /* Find the corresponding vector mode with the same size as MOVE_MODE.
	 MOVE_MODE is an integer mode at the moment (SI, DI, TI, etc.).  */
      if (GET_MODE_SIZE (move_mode) > GET_MODE_SIZE (word_mode))
	{
	  int nunits = GET_MODE_SIZE (move_mode) / GET_MODE_SIZE (word_mode);
	  if (!mode_for_vector (word_mode, nunits).exists (&move_mode)
	      || optab_handler (mov_optab, move_mode) == CODE_FOR_nothing)
	    move_mode = word_mode;
	}
      gcc_assert (optab_handler (mov_optab, move_mode) != CODE_FOR_nothing);
      break;
    case rep_prefix_8_byte:
      move_mode = DImode;
      break;
    case rep_prefix_4_byte:
      move_mode = SImode;
      break;
    case rep_prefix_1_byte:
      move_mode = QImode;
      break;
    }
  size_needed = GET_MODE_SIZE (move_mode) * unroll_factor;
  epilogue_size_needed = size_needed;

  /* If we are going to call any library calls conditionally, make sure any
     pending stack adjustment happen before the first conditional branch,
     otherwise they will be emitted before the library call only and won't
     happen from the other branches.  */
  if (dynamic_check != -1)
    do_pending_stack_adjust ();

  desired_align = decide_alignment (align, alg, expected_size, move_mode);
  if (!TARGET_ALIGN_STRINGOPS || noalign)
    align = desired_align;

  /* Step 1: Prologue guard.  */

  /* Alignment code needs count to be in register.  */
  if (CONST_INT_P (count_exp) && desired_align > align)
    {
      if (INTVAL (count_exp) > desired_align
	  && INTVAL (count_exp) > size_needed)
	{
	  align_bytes
	    = get_mem_align_offset (dst, desired_align * BITS_PER_UNIT);
	  if (align_bytes <= 0)
	    align_bytes = 0;
	  else
	    align_bytes = desired_align - align_bytes;
	}
      if (align_bytes == 0)
	count_exp = force_reg (counter_mode (count_exp), count_exp);
    }
  gcc_assert (desired_align >= 1 && align >= 1);

  /* Misaligned move sequences handle both prologue and epilogue at once.
     Default code generation results in a smaller code for large alignments
     and also avoids redundant job when sizes are known precisely.  */
  misaligned_prologue_used
    = (TARGET_MISALIGNED_MOVE_STRING_PRO_EPILOGUES
       && MAX (desired_align, epilogue_size_needed) <= 32
       && desired_align <= epilogue_size_needed
       && ((desired_align > align && !align_bytes)
	   || (!count && epilogue_size_needed > 1)));

  /* Do the cheap promotion to allow better CSE across the
     main loop and epilogue (ie one load of the big constant in the
     front of all code.  
     For now the misaligned move sequences do not have fast path
     without broadcasting.  */
  if (issetmem && ((CONST_INT_P (val_exp) || misaligned_prologue_used)))
    {
      if (alg == vector_loop)
	{
	  gcc_assert (val_exp == const0_rtx);
	  vec_promoted_val = promote_duplicated_reg (move_mode, val_exp);
	  promoted_val = promote_duplicated_reg_to_size (val_exp,
							 GET_MODE_SIZE (word_mode),
							 desired_align, align);
	}
      else
	{
	  promoted_val = promote_duplicated_reg_to_size (val_exp, size_needed,
							 desired_align, align);
	}
    }
  /* Misaligned move sequences handles both prologues and epilogues at once.
     Default code generation results in smaller code for large alignments and
     also avoids redundant job when sizes are known precisely.  */
  if (misaligned_prologue_used)
    {
      /* Misaligned move prologue handled small blocks by itself.  */
      expand_set_or_movmem_prologue_epilogue_by_misaligned_moves
	   (dst, src, &destreg, &srcreg,
	    move_mode, promoted_val, vec_promoted_val,
	    &count_exp,
	    &jump_around_label,
            desired_align < align
	    ? MAX (desired_align, epilogue_size_needed) : epilogue_size_needed,
	    desired_align, align, &min_size, dynamic_check, issetmem);
      if (!issetmem)
        src = change_address (src, BLKmode, srcreg);
      dst = change_address (dst, BLKmode, destreg);
      set_mem_align (dst, desired_align * BITS_PER_UNIT);
      epilogue_size_needed = 0;
      if (need_zero_guard
	  && min_size < (unsigned HOST_WIDE_INT) size_needed)
	{
	  /* It is possible that we copied enough so the main loop will not
	     execute.  */
	  gcc_assert (size_needed > 1);
	  if (jump_around_label == NULL_RTX)
	    jump_around_label = gen_label_rtx ();
	  emit_cmp_and_jump_insns (count_exp,
				   GEN_INT (size_needed),
				   LTU, 0, counter_mode (count_exp), 1, jump_around_label);
	  if (expected_size == -1
	      || expected_size < (desired_align - align) / 2 + size_needed)
	    predict_jump (REG_BR_PROB_BASE * 20 / 100);
	  else
	    predict_jump (REG_BR_PROB_BASE * 60 / 100);
	}
    }
  /* Ensure that alignment prologue won't copy past end of block.  */
  else if (size_needed > 1 || (desired_align > 1 && desired_align > align))
    {
      epilogue_size_needed = MAX (size_needed - 1, desired_align - align);
      /* Epilogue always copies COUNT_EXP & EPILOGUE_SIZE_NEEDED bytes.
	 Make sure it is power of 2.  */
      epilogue_size_needed = 1 << (floor_log2 (epilogue_size_needed) + 1);

      /* To improve performance of small blocks, we jump around the VAL
	 promoting mode.  This mean that if the promoted VAL is not constant,
	 we might not use it in the epilogue and have to use byte
	 loop variant.  */
      if (issetmem && epilogue_size_needed > 2 && !promoted_val)
	force_loopy_epilogue = true;
      if ((count && count < (unsigned HOST_WIDE_INT) epilogue_size_needed)
	  || max_size < (unsigned HOST_WIDE_INT) epilogue_size_needed)
	{
	  /* If main algorithm works on QImode, no epilogue is needed.
	     For small sizes just don't align anything.  */
	  if (size_needed == 1)
	    desired_align = align;
	  else
	    goto epilogue;
	}
      else if (!count
	       && min_size < (unsigned HOST_WIDE_INT) epilogue_size_needed)
	{
	  label = gen_label_rtx ();
	  emit_cmp_and_jump_insns (count_exp,
				   GEN_INT (epilogue_size_needed),
				   LTU, 0, counter_mode (count_exp), 1, label);
	  if (expected_size == -1 || expected_size < epilogue_size_needed)
	    predict_jump (REG_BR_PROB_BASE * 60 / 100);
	  else
	    predict_jump (REG_BR_PROB_BASE * 20 / 100);
	}
    }

  /* Emit code to decide on runtime whether library call or inline should be
     used.  */
  if (dynamic_check != -1)
    {
      if (!issetmem && CONST_INT_P (count_exp))
	{
	  if (UINTVAL (count_exp) >= (unsigned HOST_WIDE_INT)dynamic_check)
	    {
	      emit_block_copy_via_libcall (dst, src, count_exp);
	      count_exp = const0_rtx;
	      goto epilogue;
	    }
	}
      else
	{
	  rtx_code_label *hot_label = gen_label_rtx ();
	  if (jump_around_label == NULL_RTX)
	    jump_around_label = gen_label_rtx ();
	  emit_cmp_and_jump_insns (count_exp, GEN_INT (dynamic_check - 1),
				   LEU, 0, counter_mode (count_exp),
				   1, hot_label);
	  predict_jump (REG_BR_PROB_BASE * 90 / 100);
	  if (issetmem)
	    set_storage_via_libcall (dst, count_exp, val_exp);
	  else
	    emit_block_copy_via_libcall (dst, src, count_exp);
	  emit_jump (jump_around_label);
	  emit_label (hot_label);
	}
    }

  /* Step 2: Alignment prologue.  */
  /* Do the expensive promotion once we branched off the small blocks.  */
  if (issetmem && !promoted_val)
    promoted_val = promote_duplicated_reg_to_size (val_exp, size_needed,
						   desired_align, align);

  if (desired_align > align && !misaligned_prologue_used)
    {
      if (align_bytes == 0)
	{
	  /* Except for the first move in prologue, we no longer know
	     constant offset in aliasing info.  It don't seems to worth
	     the pain to maintain it for the first move, so throw away
	     the info early.  */
	  dst = change_address (dst, BLKmode, destreg);
	  if (!issetmem)
	    src = change_address (src, BLKmode, srcreg);
	  dst = expand_set_or_movmem_prologue (dst, src, destreg, srcreg,
					    promoted_val, vec_promoted_val,
					    count_exp, align, desired_align,
					    issetmem);
	  /* At most desired_align - align bytes are copied.  */
	  if (min_size < (unsigned)(desired_align - align))
	    min_size = 0;
	  else
	    min_size -= desired_align - align;
	}
      else
	{
	  /* If we know how many bytes need to be stored before dst is
	     sufficiently aligned, maintain aliasing info accurately.  */
	  dst = expand_set_or_movmem_constant_prologue (dst, &src, destreg,
							   srcreg,
							   promoted_val,
							   vec_promoted_val,
							   desired_align,
							   align_bytes,
							   issetmem);

	  count_exp = plus_constant (counter_mode (count_exp),
				     count_exp, -align_bytes);
	  count -= align_bytes;
	  min_size -= align_bytes;
	  max_size -= align_bytes;
	}
      if (need_zero_guard
	  && min_size < (unsigned HOST_WIDE_INT) size_needed
	  && (count < (unsigned HOST_WIDE_INT) size_needed
	      || (align_bytes == 0
		  && count < ((unsigned HOST_WIDE_INT) size_needed
			      + desired_align - align))))
	{
	  /* It is possible that we copied enough so the main loop will not
	     execute.  */
	  gcc_assert (size_needed > 1);
	  if (label == NULL_RTX)
	    label = gen_label_rtx ();
	  emit_cmp_and_jump_insns (count_exp,
				   GEN_INT (size_needed),
				   LTU, 0, counter_mode (count_exp), 1, label);
	  if (expected_size == -1
	      || expected_size < (desired_align - align) / 2 + size_needed)
	    predict_jump (REG_BR_PROB_BASE * 20 / 100);
	  else
	    predict_jump (REG_BR_PROB_BASE * 60 / 100);
	}
    }
  if (label && size_needed == 1)
    {
      emit_label (label);
      LABEL_NUSES (label) = 1;
      label = NULL;
      epilogue_size_needed = 1;
      if (issetmem)
	promoted_val = val_exp;
    }
  else if (label == NULL_RTX && !misaligned_prologue_used)
    epilogue_size_needed = size_needed;

  /* Step 3: Main loop.  */

  switch (alg)
    {
    case libcall:
    case no_stringop:
    case last_alg:
      gcc_unreachable ();
    case loop_1_byte:
    case loop:
    case unrolled_loop:
      expand_set_or_movmem_via_loop (dst, src, destreg, srcreg, promoted_val,
				     count_exp, move_mode, unroll_factor,
				     expected_size, issetmem);
      break;
    case vector_loop:
      expand_set_or_movmem_via_loop (dst, src, destreg, srcreg,
				     vec_promoted_val, count_exp, move_mode,
				     unroll_factor, expected_size, issetmem);
      break;
    case rep_prefix_8_byte:
    case rep_prefix_4_byte:
    case rep_prefix_1_byte:
      expand_set_or_movmem_via_rep (dst, src, destreg, srcreg, promoted_val,
				       val_exp, count_exp, move_mode, issetmem);
      break;
    }
  /* Adjust properly the offset of src and dest memory for aliasing.  */
  if (CONST_INT_P (count_exp))
    {
      if (!issetmem)
	src = adjust_automodify_address_nv (src, BLKmode, srcreg,
					    (count / size_needed) * size_needed);
      dst = adjust_automodify_address_nv (dst, BLKmode, destreg,
					  (count / size_needed) * size_needed);
    }
  else
    {
      if (!issetmem)
	src = change_address (src, BLKmode, srcreg);
      dst = change_address (dst, BLKmode, destreg);
    }

  /* Step 4: Epilogue to copy the remaining bytes.  */
 epilogue:
  if (label)
    {
      /* When the main loop is done, COUNT_EXP might hold original count,
	 while we want to copy only COUNT_EXP & SIZE_NEEDED bytes.
	 Epilogue code will actually copy COUNT_EXP & EPILOGUE_SIZE_NEEDED
	 bytes. Compensate if needed.  */

      if (size_needed < epilogue_size_needed)
	{
	  tmp = expand_simple_binop (counter_mode (count_exp), AND, count_exp,
				     GEN_INT (size_needed - 1), count_exp, 1,
				     OPTAB_DIRECT);
	  if (tmp != count_exp)
	    emit_move_insn (count_exp, tmp);
	}
      emit_label (label);
      LABEL_NUSES (label) = 1;
    }

  if (count_exp != const0_rtx && epilogue_size_needed > 1)
    {
      if (force_loopy_epilogue)
	expand_setmem_epilogue_via_loop (dst, destreg, val_exp, count_exp,
					 epilogue_size_needed);
      else
	{
	  if (issetmem)
	    expand_setmem_epilogue (dst, destreg, promoted_val,
				    vec_promoted_val, count_exp,
				    epilogue_size_needed);
	  else
	    expand_movmem_epilogue (dst, src, destreg, srcreg, count_exp,
				    epilogue_size_needed);
	}
    }
  if (jump_around_label)
    emit_label (jump_around_label);
  return true;
}


/* Expand the appropriate insns for doing strlen if not just doing
   repnz; scasb

   out = result, initialized with the start address
   align_rtx = alignment of the address.
   scratch = scratch register, initialized with the startaddress when
	not aligned, otherwise undefined

   This is just the body. It needs the initializations mentioned above and
   some address computing at the end.  These things are done in i386.md.  */

static void
ix86_expand_strlensi_unroll_1 (rtx out, rtx src, rtx align_rtx)
{
  int align;
  rtx tmp;
  rtx_code_label *align_2_label = NULL;
  rtx_code_label *align_3_label = NULL;
  rtx_code_label *align_4_label = gen_label_rtx ();
  rtx_code_label *end_0_label = gen_label_rtx ();
  rtx mem;
  rtx tmpreg = gen_reg_rtx (SImode);
  rtx scratch = gen_reg_rtx (SImode);
  rtx cmp;

  align = 0;
  if (CONST_INT_P (align_rtx))
    align = INTVAL (align_rtx);

  /* Loop to check 1..3 bytes for null to get an aligned pointer.  */

  /* Is there a known alignment and is it less than 4?  */
  if (align < 4)
    {
      rtx scratch1 = gen_reg_rtx (Pmode);
      emit_move_insn (scratch1, out);
      /* Is there a known alignment and is it not 2? */
      if (align != 2)
	{
	  align_3_label = gen_label_rtx (); /* Label when aligned to 3-byte */
	  align_2_label = gen_label_rtx (); /* Label when aligned to 2-byte */

	  /* Leave just the 3 lower bits.  */
	  align_rtx = expand_binop (Pmode, and_optab, scratch1, GEN_INT (3),
				    NULL_RTX, 0, OPTAB_WIDEN);

	  emit_cmp_and_jump_insns (align_rtx, const0_rtx, EQ, NULL,
				   Pmode, 1, align_4_label);
	  emit_cmp_and_jump_insns (align_rtx, const2_rtx, EQ, NULL,
				   Pmode, 1, align_2_label);
	  emit_cmp_and_jump_insns (align_rtx, const2_rtx, GTU, NULL,
				   Pmode, 1, align_3_label);
	}
      else
        {
	  /* Since the alignment is 2, we have to check 2 or 0 bytes;
	     check if is aligned to 4 - byte.  */

	  align_rtx = expand_binop (Pmode, and_optab, scratch1, const2_rtx,
				    NULL_RTX, 0, OPTAB_WIDEN);

	  emit_cmp_and_jump_insns (align_rtx, const0_rtx, EQ, NULL,
				   Pmode, 1, align_4_label);
        }

      mem = change_address (src, QImode, out);

      /* Now compare the bytes.  */

      /* Compare the first n unaligned byte on a byte per byte basis.  */
      emit_cmp_and_jump_insns (mem, const0_rtx, EQ, NULL,
			       QImode, 1, end_0_label);

      /* Increment the address.  */
      emit_insn (ix86_gen_add3 (out, out, const1_rtx));

      /* Not needed with an alignment of 2 */
      if (align != 2)
	{
	  emit_label (align_2_label);

	  emit_cmp_and_jump_insns (mem, const0_rtx, EQ, NULL, QImode, 1,
				   end_0_label);

	  emit_insn (ix86_gen_add3 (out, out, const1_rtx));

	  emit_label (align_3_label);
	}

      emit_cmp_and_jump_insns (mem, const0_rtx, EQ, NULL, QImode, 1,
			       end_0_label);

      emit_insn (ix86_gen_add3 (out, out, const1_rtx));
    }

  /* Generate loop to check 4 bytes at a time.  It is not a good idea to
     align this loop.  It gives only huge programs, but does not help to
     speed up.  */
  emit_label (align_4_label);

  mem = change_address (src, SImode, out);
  emit_move_insn (scratch, mem);
  emit_insn (ix86_gen_add3 (out, out, GEN_INT (4)));

  /* This formula yields a nonzero result iff one of the bytes is zero.
     This saves three branches inside loop and many cycles.  */

  emit_insn (gen_addsi3 (tmpreg, scratch, GEN_INT (-0x01010101)));
  emit_insn (gen_one_cmplsi2 (scratch, scratch));
  emit_insn (gen_andsi3 (tmpreg, tmpreg, scratch));
  emit_insn (gen_andsi3 (tmpreg, tmpreg,
			 gen_int_mode (0x80808080, SImode)));
  emit_cmp_and_jump_insns (tmpreg, const0_rtx, EQ, 0, SImode, 1,
			   align_4_label);

  if (TARGET_CMOVE)
    {
       rtx reg = gen_reg_rtx (SImode);
       rtx reg2 = gen_reg_rtx (Pmode);
       emit_move_insn (reg, tmpreg);
       emit_insn (gen_lshrsi3 (reg, reg, GEN_INT (16)));

       /* If zero is not in the first two bytes, move two bytes forward.  */
       emit_insn (gen_testsi_ccno_1 (tmpreg, GEN_INT (0x8080)));
       tmp = gen_rtx_REG (CCNOmode, FLAGS_REG);
       tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
       emit_insn (gen_rtx_SET (tmpreg,
			       gen_rtx_IF_THEN_ELSE (SImode, tmp,
						     reg,
						     tmpreg)));
       /* Emit lea manually to avoid clobbering of flags.  */
       emit_insn (gen_rtx_SET (reg2, gen_rtx_PLUS (Pmode, out, const2_rtx)));

       tmp = gen_rtx_REG (CCNOmode, FLAGS_REG);
       tmp = gen_rtx_EQ (VOIDmode, tmp, const0_rtx);
       emit_insn (gen_rtx_SET (out,
			       gen_rtx_IF_THEN_ELSE (Pmode, tmp,
						     reg2,
						     out)));
    }
  else
    {
       rtx_code_label *end_2_label = gen_label_rtx ();
       /* Is zero in the first two bytes? */

       emit_insn (gen_testsi_ccno_1 (tmpreg, GEN_INT (0x8080)));
       tmp = gen_rtx_REG (CCNOmode, FLAGS_REG);
       tmp = gen_rtx_NE (VOIDmode, tmp, const0_rtx);
       tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
                            gen_rtx_LABEL_REF (VOIDmode, end_2_label),
                            pc_rtx);
       tmp = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
       JUMP_LABEL (tmp) = end_2_label;

       /* Not in the first two.  Move two bytes forward.  */
       emit_insn (gen_lshrsi3 (tmpreg, tmpreg, GEN_INT (16)));
       emit_insn (ix86_gen_add3 (out, out, const2_rtx));

       emit_label (end_2_label);

    }

  /* Avoid branch in fixing the byte.  */
  tmpreg = gen_lowpart (QImode, tmpreg);
  emit_insn (gen_addqi3_cconly_overflow (tmpreg, tmpreg));
  tmp = gen_rtx_REG (CCmode, FLAGS_REG);
  cmp = gen_rtx_LTU (VOIDmode, tmp, const0_rtx);
  emit_insn (ix86_gen_sub3_carry (out, out, GEN_INT (3), tmp, cmp));

  emit_label (end_0_label);
}

/* Expand strlen.  */

bool
ix86_expand_strlen (rtx out, rtx src, rtx eoschar, rtx align)
{
  rtx addr, scratch1, scratch2, scratch3, scratch4;

  /* The generic case of strlen expander is long.  Avoid it's
     expanding unless TARGET_INLINE_ALL_STRINGOPS.  */

  if (TARGET_UNROLL_STRLEN && eoschar == const0_rtx && optimize > 1
      && !TARGET_INLINE_ALL_STRINGOPS
      && !optimize_insn_for_size_p ()
      && (!CONST_INT_P (align) || INTVAL (align) < 4))
    return false;

  addr = force_reg (Pmode, XEXP (src, 0));
  scratch1 = gen_reg_rtx (Pmode);

  if (TARGET_UNROLL_STRLEN && eoschar == const0_rtx && optimize > 1
      && !optimize_insn_for_size_p ())
    {
      /* Well it seems that some optimizer does not combine a call like
         foo(strlen(bar), strlen(bar));
         when the move and the subtraction is done here.  It does calculate
         the length just once when these instructions are done inside of
         output_strlen_unroll().  But I think since &bar[strlen(bar)] is
         often used and I use one fewer register for the lifetime of
         output_strlen_unroll() this is better.  */

      emit_move_insn (out, addr);

      ix86_expand_strlensi_unroll_1 (out, src, align);

      /* strlensi_unroll_1 returns the address of the zero at the end of
         the string, like memchr(), so compute the length by subtracting
         the start address.  */
      emit_insn (ix86_gen_sub3 (out, out, addr));
    }
  else
    {
      rtx unspec;

      /* Can't use this if the user has appropriated eax, ecx, or edi.  */
      if (fixed_regs[AX_REG] || fixed_regs[CX_REG] || fixed_regs[DI_REG])
        return false;
      /* Can't use this for non-default address spaces.  */
      if (!ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (src)))
	return false;

      scratch2 = gen_reg_rtx (Pmode);
      scratch3 = gen_reg_rtx (Pmode);
      scratch4 = force_reg (Pmode, constm1_rtx);

      emit_move_insn (scratch3, addr);
      eoschar = force_reg (QImode, eoschar);

      src = replace_equiv_address_nv (src, scratch3);

      /* If .md starts supporting :P, this can be done in .md.  */
      unspec = gen_rtx_UNSPEC (Pmode, gen_rtvec (4, src, eoschar, align,
						 scratch4), UNSPEC_SCAS);
      emit_insn (gen_strlenqi_1 (scratch1, scratch3, unspec));
      emit_insn (ix86_gen_one_cmpl2 (scratch2, scratch1));
      emit_insn (ix86_gen_add3 (out, scratch2, constm1_rtx));
    }
  return true;
}

/* For given symbol (function) construct code to compute address of it's PLT
   entry in large x86-64 PIC model.  */
static rtx
construct_plt_address (rtx symbol)
{
  rtx tmp, unspec;

  gcc_assert (GET_CODE (symbol) == SYMBOL_REF);
  gcc_assert (ix86_cmodel == CM_LARGE_PIC && !TARGET_PECOFF);
  gcc_assert (Pmode == DImode);

  tmp = gen_reg_rtx (Pmode);
  unspec = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, symbol), UNSPEC_PLTOFF);

  emit_move_insn (tmp, gen_rtx_CONST (Pmode, unspec));
  emit_insn (ix86_gen_add3 (tmp, tmp, pic_offset_table_rtx));
  return tmp;
}

rtx_insn *
ix86_expand_call (rtx retval, rtx fnaddr, rtx callarg1,
		  rtx callarg2,
		  rtx pop, bool sibcall)
{
  rtx vec[3];
  rtx use = NULL, call;
  unsigned int vec_len = 0;
  tree fndecl;

  if (GET_CODE (XEXP (fnaddr, 0)) == SYMBOL_REF)
    {
      fndecl = SYMBOL_REF_DECL (XEXP (fnaddr, 0));
      if (fndecl
	  && (lookup_attribute ("interrupt",
				TYPE_ATTRIBUTES (TREE_TYPE (fndecl)))))
	error ("interrupt service routine can't be called directly");
    }
  else
    fndecl = NULL_TREE;

  if (pop == const0_rtx)
    pop = NULL;
  gcc_assert (!TARGET_64BIT || !pop);

  if (TARGET_MACHO && !TARGET_64BIT)
    {
#if TARGET_MACHO
      if (flag_pic && GET_CODE (XEXP (fnaddr, 0)) == SYMBOL_REF)
	fnaddr = machopic_indirect_call_target (fnaddr);
#endif
    }
  else
    {
      /* Static functions and indirect calls don't need the pic register.  Also,
	 check if PLT was explicitly avoided via no-plt or "noplt" attribute, making
	 it an indirect call.  */
      rtx addr = XEXP (fnaddr, 0);
      if (flag_pic
	  && GET_CODE (addr) == SYMBOL_REF
	  && !SYMBOL_REF_LOCAL_P (addr))
	{
	  if (flag_plt
	      && (SYMBOL_REF_DECL (addr) == NULL_TREE
		  || !lookup_attribute ("noplt",
					DECL_ATTRIBUTES (SYMBOL_REF_DECL (addr)))))
	    {
	      if (!TARGET_64BIT
		  || (ix86_cmodel == CM_LARGE_PIC
		      && DEFAULT_ABI != MS_ABI))
		{
		  use_reg (&use, gen_rtx_REG (Pmode,
					      REAL_PIC_OFFSET_TABLE_REGNUM));
		  if (ix86_use_pseudo_pic_reg ())
		    emit_move_insn (gen_rtx_REG (Pmode,
						 REAL_PIC_OFFSET_TABLE_REGNUM),
				    pic_offset_table_rtx);
		}
	    }
	  else if (!TARGET_PECOFF && !TARGET_MACHO)
	    {
	      if (TARGET_64BIT)
		{
		  fnaddr = gen_rtx_UNSPEC (Pmode,
					   gen_rtvec (1, addr),
					   UNSPEC_GOTPCREL);
		  fnaddr = gen_rtx_CONST (Pmode, fnaddr);
		}
	      else
		{
		  fnaddr = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, addr),
					   UNSPEC_GOT);
		  fnaddr = gen_rtx_CONST (Pmode, fnaddr);
		  fnaddr = gen_rtx_PLUS (Pmode, pic_offset_table_rtx,
					 fnaddr);
		}
	      fnaddr = gen_const_mem (Pmode, fnaddr);
	      /* Pmode may not be the same as word_mode for x32, which
		 doesn't support indirect branch via 32-bit memory slot.
		 Since x32 GOT slot is 64 bit with zero upper 32 bits,
		 indirect branch via x32 GOT slot is OK.  */
	      if (GET_MODE (fnaddr) != word_mode)
		fnaddr = gen_rtx_ZERO_EXTEND (word_mode, fnaddr);
	      fnaddr = gen_rtx_MEM (QImode, fnaddr);
	    }
	}
    }

  /* Skip setting up RAX register for -mskip-rax-setup when there are no
     parameters passed in vector registers.  */
  if (TARGET_64BIT
      && (INTVAL (callarg2) > 0
	  || (INTVAL (callarg2) == 0
	      && (TARGET_SSE || !flag_skip_rax_setup))))
    {
      rtx al = gen_rtx_REG (QImode, AX_REG);
      emit_move_insn (al, callarg2);
      use_reg (&use, al);
    }

  if (ix86_cmodel == CM_LARGE_PIC
      && !TARGET_PECOFF
      && MEM_P (fnaddr)
      && GET_CODE (XEXP (fnaddr, 0)) == SYMBOL_REF
      && !local_symbolic_operand (XEXP (fnaddr, 0), VOIDmode))
    fnaddr = gen_rtx_MEM (QImode, construct_plt_address (XEXP (fnaddr, 0)));
  /* Since x32 GOT slot is 64 bit with zero upper 32 bits, indirect
     branch via x32 GOT slot is OK.  */
  else if (!(TARGET_X32
	     && MEM_P (fnaddr)
	     && GET_CODE (XEXP (fnaddr, 0)) == ZERO_EXTEND
	     && GOT_memory_operand (XEXP (XEXP (fnaddr, 0), 0), Pmode))
	   && (sibcall
	       ? !sibcall_insn_operand (XEXP (fnaddr, 0), word_mode)
	       : !call_insn_operand (XEXP (fnaddr, 0), word_mode)))
    {
      fnaddr = convert_to_mode (word_mode, XEXP (fnaddr, 0), 1);
      fnaddr = gen_rtx_MEM (QImode, copy_to_mode_reg (word_mode, fnaddr));
    }

  call = gen_rtx_CALL (VOIDmode, fnaddr, callarg1);

  if (retval)
    call = gen_rtx_SET (retval, call);
  vec[vec_len++] = call;

  if (pop)
    {
      pop = gen_rtx_PLUS (Pmode, stack_pointer_rtx, pop);
      pop = gen_rtx_SET (stack_pointer_rtx, pop);
      vec[vec_len++] = pop;
    }

  if (cfun->machine->no_caller_saved_registers
      && (!fndecl
	  || (!TREE_THIS_VOLATILE (fndecl)
	      && !lookup_attribute ("no_caller_saved_registers",
				    TYPE_ATTRIBUTES (TREE_TYPE (fndecl))))))
    {
      static const char ix86_call_used_regs[] = CALL_USED_REGISTERS;
      bool is_64bit_ms_abi = (TARGET_64BIT
			      && ix86_function_abi (fndecl) == MS_ABI);
      char c_mask = CALL_USED_REGISTERS_MASK (is_64bit_ms_abi);

      /* If there are no caller-saved registers, add all registers
	 that are clobbered by the call which returns.  */
      for (int i = 0; i < FIRST_PSEUDO_REGISTER; i++)
	if (!fixed_regs[i]
	    && (ix86_call_used_regs[i] == 1
		|| (ix86_call_used_regs[i] & c_mask))
	    && !STACK_REGNO_P (i)
	    && !MMX_REGNO_P (i))
	  clobber_reg (&use,
		       gen_rtx_REG (GET_MODE (regno_reg_rtx[i]), i));
    }
  else if (TARGET_64BIT_MS_ABI
	   && (!callarg2 || INTVAL (callarg2) != -2))
    {
      unsigned i;

      for (i = 0; i < NUM_X86_64_MS_CLOBBERED_REGS; i++)
	{
	  int regno = x86_64_ms_sysv_extra_clobbered_registers[i];
	  machine_mode mode = SSE_REGNO_P (regno) ? TImode : DImode;

	  clobber_reg (&use, gen_rtx_REG (mode, regno));
	}

      /* Set here, but it may get cleared later.  */
      if (TARGET_CALL_MS2SYSV_XLOGUES)
	{
	  if (!TARGET_SSE)
	    ;

	  /* Don't break hot-patched functions.  */
	  else if (ix86_function_ms_hook_prologue (current_function_decl))
	    ;

	  /* TODO: Cases not yet examined.  */
	  else if (flag_split_stack)
	    warn_once_call_ms2sysv_xlogues ("-fsplit-stack");

	  else
	    {
	      gcc_assert (!reload_completed);
	      cfun->machine->call_ms2sysv = true;
	    }
	}
    }

  if (vec_len > 1)
    call = gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (vec_len, vec));
  rtx_insn *call_insn = emit_call_insn (call);
  if (use)
    CALL_INSN_FUNCTION_USAGE (call_insn) = use;

  return call_insn;
}

/* Return true if the function being called was marked with attribute
   "noplt" or using -fno-plt and we are compiling for non-PIC.  We need
   to handle the non-PIC case in the backend because there is no easy
   interface for the front-end to force non-PLT calls to use the GOT.
   This is currently used only with 64-bit or 32-bit GOT32X ELF targets
   to call the function marked "noplt" indirectly.  */

static bool
ix86_nopic_noplt_attribute_p (rtx call_op)
{
  if (flag_pic || ix86_cmodel == CM_LARGE
      || !(TARGET_64BIT || HAVE_AS_IX86_GOT32X)
      || TARGET_MACHO || TARGET_SEH || TARGET_PECOFF
      || SYMBOL_REF_LOCAL_P (call_op))
    return false;

  tree symbol_decl = SYMBOL_REF_DECL (call_op);

  if (!flag_plt
      || (symbol_decl != NULL_TREE
          && lookup_attribute ("noplt", DECL_ATTRIBUTES (symbol_decl))))
    return true;

  return false;
}

/* Output indirect branch via a call and return thunk.  CALL_OP is a
   register which contains the branch target.  XASM is the assembly
   template for CALL_OP.  Branch is a tail call if SIBCALL_P is true.
   A normal call is converted to:

	call __x86_indirect_thunk_reg

   and a tail call is converted to:

	jmp __x86_indirect_thunk_reg
 */

static void
ix86_output_indirect_branch_via_reg (rtx call_op, bool sibcall_p)
{
  char thunk_name_buf[32];
  char *thunk_name;
  enum indirect_thunk_prefix need_prefix
    = indirect_thunk_need_prefix (current_output_insn);
  int regno = REGNO (call_op);

  if (cfun->machine->indirect_branch_type
      != indirect_branch_thunk_inline)
    {
      if (cfun->machine->indirect_branch_type == indirect_branch_thunk)
	{
	  int i = regno;
	  if (i >= FIRST_REX_INT_REG)
	    i -= (FIRST_REX_INT_REG - LAST_INT_REG - 1);
	  indirect_thunks_used |= 1 << i;
	}
      indirect_thunk_name (thunk_name_buf, regno, need_prefix, false);
      thunk_name = thunk_name_buf;
    }
  else
    thunk_name = NULL;

  if (sibcall_p)
    {
      if (thunk_name != NULL)
	fprintf (asm_out_file, "\tjmp\t%s\n", thunk_name);
      else
	output_indirect_thunk (regno);
    }
  else
    {
      if (thunk_name != NULL)
	{
	  fprintf (asm_out_file, "\tcall\t%s\n", thunk_name);
	  return;
	}

      char indirectlabel1[32];
      char indirectlabel2[32];

      ASM_GENERATE_INTERNAL_LABEL (indirectlabel1,
				   INDIRECT_LABEL,
				   indirectlabelno++);
      ASM_GENERATE_INTERNAL_LABEL (indirectlabel2,
				   INDIRECT_LABEL,
				   indirectlabelno++);

      /* Jump.  */
      fputs ("\tjmp\t", asm_out_file);
      assemble_name_raw (asm_out_file, indirectlabel2);
      fputc ('\n', asm_out_file);

      ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, indirectlabel1);

      if (thunk_name != NULL)
	fprintf (asm_out_file, "\tjmp\t%s\n", thunk_name);
      else
	output_indirect_thunk (regno);

      ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, indirectlabel2);

      /* Call.  */
      fputs ("\tcall\t", asm_out_file);
      assemble_name_raw (asm_out_file, indirectlabel1);
      fputc ('\n', asm_out_file);
    }
}

/* Output indirect branch via a call and return thunk.  CALL_OP is
   the branch target.  XASM is the assembly template for CALL_OP.
   Branch is a tail call if SIBCALL_P is true.  A normal call is
   converted to:

	jmp L2
   L1:
	push CALL_OP
	jmp __x86_indirect_thunk
   L2:
	call L1

   and a tail call is converted to:

	push CALL_OP
	jmp __x86_indirect_thunk
 */

static void
ix86_output_indirect_branch_via_push (rtx call_op, const char *xasm,
				      bool sibcall_p)
{
  char thunk_name_buf[32];
  char *thunk_name;
  char push_buf[64];
  enum indirect_thunk_prefix need_prefix
    = indirect_thunk_need_prefix (current_output_insn);
  int regno = -1;

  if (cfun->machine->indirect_branch_type
      != indirect_branch_thunk_inline)
    {
      if (cfun->machine->indirect_branch_type == indirect_branch_thunk)
	indirect_thunk_needed = true;
      indirect_thunk_name (thunk_name_buf, regno, need_prefix, false);
      thunk_name = thunk_name_buf;
    }
  else
    thunk_name = NULL;

  snprintf (push_buf, sizeof (push_buf), "push{%c}\t%s",
	    TARGET_64BIT ? 'q' : 'l', xasm);

  if (sibcall_p)
    {
      output_asm_insn (push_buf, &call_op);
      if (thunk_name != NULL)
	fprintf (asm_out_file, "\tjmp\t%s\n", thunk_name);
      else
	output_indirect_thunk (regno);
    }
  else
    {
      char indirectlabel1[32];
      char indirectlabel2[32];

      ASM_GENERATE_INTERNAL_LABEL (indirectlabel1,
				   INDIRECT_LABEL,
				   indirectlabelno++);
      ASM_GENERATE_INTERNAL_LABEL (indirectlabel2,
				   INDIRECT_LABEL,
				   indirectlabelno++);

      /* Jump.  */
      fputs ("\tjmp\t", asm_out_file);
      assemble_name_raw (asm_out_file, indirectlabel2);
      fputc ('\n', asm_out_file);

      ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, indirectlabel1);

      /* An external function may be called via GOT, instead of PLT.  */
      if (MEM_P (call_op))
	{
	  struct ix86_address parts;
	  rtx addr = XEXP (call_op, 0);
	  if (ix86_decompose_address (addr, &parts)
	      && parts.base == stack_pointer_rtx)
	    {
	      /* Since call will adjust stack by -UNITS_PER_WORD,
		 we must convert "disp(stack, index, scale)" to
		 "disp+UNITS_PER_WORD(stack, index, scale)".  */
	      if (parts.index)
		{
		  addr = gen_rtx_MULT (Pmode, parts.index,
				       GEN_INT (parts.scale));
		  addr = gen_rtx_PLUS (Pmode, stack_pointer_rtx,
				       addr);
		}
	      else
		addr = stack_pointer_rtx;

	      rtx disp;
	      if (parts.disp != NULL_RTX)
		disp = plus_constant (Pmode, parts.disp,
				      UNITS_PER_WORD);
	      else
		disp = GEN_INT (UNITS_PER_WORD);

	      addr = gen_rtx_PLUS (Pmode, addr, disp);
	      call_op = gen_rtx_MEM (GET_MODE (call_op), addr);
	    }
	}

      output_asm_insn (push_buf, &call_op);

      if (thunk_name != NULL)
	fprintf (asm_out_file, "\tjmp\t%s\n", thunk_name);
      else
	output_indirect_thunk (regno);

      ASM_OUTPUT_INTERNAL_LABEL (asm_out_file, indirectlabel2);

      /* Call.  */
      fputs ("\tcall\t", asm_out_file);
      assemble_name_raw (asm_out_file, indirectlabel1);
      fputc ('\n', asm_out_file);
    }
}

/* Output indirect branch via a call and return thunk.  CALL_OP is
   the branch target.  XASM is the assembly template for CALL_OP.
   Branch is a tail call if SIBCALL_P is true.   */

static void
ix86_output_indirect_branch (rtx call_op, const char *xasm,
			     bool sibcall_p)
{
  if (REG_P (call_op))
    ix86_output_indirect_branch_via_reg (call_op, sibcall_p);
  else
    ix86_output_indirect_branch_via_push (call_op, xasm, sibcall_p);
}

/* Output indirect jump.  CALL_OP is the jump target.  */

const char *
ix86_output_indirect_jmp (rtx call_op)
{
  if (cfun->machine->indirect_branch_type != indirect_branch_keep)
    {
      /* We can't have red-zone since "call" in the indirect thunk
         pushes the return address onto stack, destroying red-zone.  */
      if (ix86_red_zone_size != 0)
	gcc_unreachable ();

      ix86_output_indirect_branch (call_op, "%0", true);
      return "";
    }
  else
    return "%!jmp\t%A0";
}

/* Output return instrumentation for current function if needed.  */

static void
output_return_instrumentation (void)
{
  if (ix86_instrument_return != instrument_return_none
      && flag_fentry
      && !DECL_NO_INSTRUMENT_FUNCTION_ENTRY_EXIT (cfun->decl))
    {
      if (ix86_flag_record_return)
	fprintf (asm_out_file, "1:\n");
      switch (ix86_instrument_return)
	{
	case instrument_return_call:
	  fprintf (asm_out_file, "\tcall\t__return__\n");
	  break;
	case instrument_return_nop5:
	  /* 5 byte nop: nopl 0(%[re]ax,%[re]ax,1)  */
	  fprintf (asm_out_file, ASM_BYTE "0x0f, 0x1f, 0x44, 0x00, 0x00\n");
	  break;
	case instrument_return_none:
	  break;
	}

      if (ix86_flag_record_return)
	{
	  fprintf (asm_out_file, "\t.section __return_loc, \"a\",@progbits\n");
	  fprintf (asm_out_file, "\t.%s 1b\n", TARGET_64BIT ? "quad" : "long");
	  fprintf (asm_out_file, "\t.previous\n");
	}
    }
}

/* Output function return.  CALL_OP is the jump target.  Add a REP
   prefix to RET if LONG_P is true and function return is kept.  */

const char *
ix86_output_function_return (bool long_p)
{
  output_return_instrumentation ();

  if (cfun->machine->function_return_type != indirect_branch_keep)
    {
      char thunk_name[32];
      enum indirect_thunk_prefix need_prefix
	= indirect_thunk_need_prefix (current_output_insn);

      if (cfun->machine->function_return_type
	  != indirect_branch_thunk_inline)
	{
	  bool need_thunk = (cfun->machine->function_return_type
			     == indirect_branch_thunk);
	  indirect_thunk_name (thunk_name, INVALID_REGNUM, need_prefix,
			       true);
	  indirect_return_needed |= need_thunk;
	  fprintf (asm_out_file, "\tjmp\t%s\n", thunk_name);
	}
      else
	output_indirect_thunk (INVALID_REGNUM);

      return "";
    }

  if (!long_p)
    return "%!ret";

  return "rep%; ret";
}

/* Output indirect function return.  RET_OP is the function return
   target.  */

const char *
ix86_output_indirect_function_return (rtx ret_op)
{
  if (cfun->machine->function_return_type != indirect_branch_keep)
    {
      char thunk_name[32];
      enum indirect_thunk_prefix need_prefix
	= indirect_thunk_need_prefix (current_output_insn);
      unsigned int regno = REGNO (ret_op);
      gcc_assert (regno == CX_REG);

      if (cfun->machine->function_return_type
	  != indirect_branch_thunk_inline)
	{
	  bool need_thunk = (cfun->machine->function_return_type
			     == indirect_branch_thunk);
	  indirect_thunk_name (thunk_name, regno, need_prefix, true);

	  if (need_thunk)
	    {
	      indirect_return_via_cx = true;
	      indirect_thunks_used |= 1 << CX_REG;
	    }
	  fprintf (asm_out_file, "\tjmp\t%s\n", thunk_name);
	}
      else
	output_indirect_thunk (regno);

      return "";
    }
  else
    return "%!jmp\t%A0";
}

/* Split simple return with popping POPC bytes from stack to indirect
   branch with stack adjustment .  */

void
ix86_split_simple_return_pop_internal (rtx popc)
{
  struct machine_function *m = cfun->machine;
  rtx ecx = gen_rtx_REG (SImode, CX_REG);
  rtx_insn *insn;

  /* There is no "pascal" calling convention in any 64bit ABI.  */
  gcc_assert (!TARGET_64BIT);

  insn = emit_insn (gen_pop (ecx));
  m->fs.cfa_offset -= UNITS_PER_WORD;
  m->fs.sp_offset -= UNITS_PER_WORD;

  rtx x = plus_constant (Pmode, stack_pointer_rtx, UNITS_PER_WORD);
  x = gen_rtx_SET (stack_pointer_rtx, x);
  add_reg_note (insn, REG_CFA_ADJUST_CFA, x);
  add_reg_note (insn, REG_CFA_REGISTER, gen_rtx_SET (ecx, pc_rtx));
  RTX_FRAME_RELATED_P (insn) = 1;

  x = gen_rtx_PLUS (Pmode, stack_pointer_rtx, popc);
  x = gen_rtx_SET (stack_pointer_rtx, x);
  insn = emit_insn (x);
  add_reg_note (insn, REG_CFA_ADJUST_CFA, x);
  RTX_FRAME_RELATED_P (insn) = 1;

  /* Now return address is in ECX.  */
  emit_jump_insn (gen_simple_return_indirect_internal (ecx));
}

/* Output the assembly for a call instruction.  */

const char *
ix86_output_call_insn (rtx_insn *insn, rtx call_op)
{
  bool direct_p = constant_call_address_operand (call_op, VOIDmode);
  bool output_indirect_p
    = (!TARGET_SEH
       && cfun->machine->indirect_branch_type != indirect_branch_keep);
  bool seh_nop_p = false;
  const char *xasm;

  if (SIBLING_CALL_P (insn))
    {
      output_return_instrumentation ();
      if (direct_p)
	{
	  if (ix86_nopic_noplt_attribute_p (call_op))
	    {
	      direct_p = false;
	      if (TARGET_64BIT)
		{
		  if (output_indirect_p)
		    xasm = "{%p0@GOTPCREL(%%rip)|[QWORD PTR %p0@GOTPCREL[rip]]}";
		  else
		    xasm = "%!jmp\t{*%p0@GOTPCREL(%%rip)|[QWORD PTR %p0@GOTPCREL[rip]]}";
		}
	      else
		{
		  if (output_indirect_p)
		    xasm = "{%p0@GOT|[DWORD PTR %p0@GOT]}";
		  else
		    xasm = "%!jmp\t{*%p0@GOT|[DWORD PTR %p0@GOT]}";
		}
	    }
	  else
	    xasm = "%!jmp\t%P0";
	}
      /* SEH epilogue detection requires the indirect branch case
	 to include REX.W.  */
      else if (TARGET_SEH)
	xasm = "%!rex.W jmp\t%A0";
      else
	{
	  if (output_indirect_p)
	    xasm = "%0";
	  else
	    xasm = "%!jmp\t%A0";
	}

      if (output_indirect_p && !direct_p)
	ix86_output_indirect_branch (call_op, xasm, true);
      else
	output_asm_insn (xasm, &call_op);
      return "";
    }

  /* SEH unwinding can require an extra nop to be emitted in several
     circumstances.  Determine if we have one of those.  */
  if (TARGET_SEH)
    {
      rtx_insn *i;

      for (i = NEXT_INSN (insn); i ; i = NEXT_INSN (i))
	{
	  /* Prevent a catch region from being adjacent to a jump that would
	     be interpreted as an epilogue sequence by the unwinder.  */
	  if (JUMP_P(i) && CROSSING_JUMP_P (i))
	    {
	      seh_nop_p = true;
	      break;
	    }
	    
	  /* If we get to another real insn, we don't need the nop.  */
	  if (INSN_P (i))
	    break;

	  /* If we get to the epilogue note, prevent a catch region from
	     being adjacent to the standard epilogue sequence.  If non-
	     call-exceptions, we'll have done this during epilogue emission. */
	  if (NOTE_P (i) && NOTE_KIND (i) == NOTE_INSN_EPILOGUE_BEG
	      && !flag_non_call_exceptions
	      && !can_throw_internal (insn))
	    {
	      seh_nop_p = true;
	      break;
	    }
	}

      /* If we didn't find a real insn following the call, prevent the
	 unwinder from looking into the next function.  */
      if (i == NULL)
	seh_nop_p = true;
    }

  if (direct_p)
    {
      if (ix86_nopic_noplt_attribute_p (call_op))
	{
	  direct_p = false;
	  if (TARGET_64BIT)
	    {
	      if (output_indirect_p)
		xasm = "{%p0@GOTPCREL(%%rip)|[QWORD PTR %p0@GOTPCREL[rip]]}";
	      else
		xasm = "%!call\t{*%p0@GOTPCREL(%%rip)|[QWORD PTR %p0@GOTPCREL[rip]]}";
	    }
	  else
	    {
	      if (output_indirect_p)
		xasm = "{%p0@GOT|[DWORD PTR %p0@GOT]}";
	      else
		xasm = "%!call\t{*%p0@GOT|[DWORD PTR %p0@GOT]}";
	    }
	}
      else
	xasm = "%!call\t%P0";
    }
  else
    {
      if (output_indirect_p)
	xasm = "%0";
      else
	xasm = "%!call\t%A0";
    }

  if (output_indirect_p && !direct_p)
    ix86_output_indirect_branch (call_op, xasm, false);
  else
    output_asm_insn (xasm, &call_op);

  if (seh_nop_p)
    return "nop";

  return "";
}

/* Clear stack slot assignments remembered from previous functions.
   This is called from INIT_EXPANDERS once before RTL is emitted for each
   function.  */

static struct machine_function *
ix86_init_machine_status (void)
{
  struct machine_function *f;

  f = ggc_cleared_alloc<machine_function> ();
  f->call_abi = ix86_abi;

  return f;
}

/* Return a MEM corresponding to a stack slot with mode MODE.
   Allocate a new slot if necessary.

   The RTL for a function can have several slots available: N is
   which slot to use.  */

rtx
assign_386_stack_local (machine_mode mode, enum ix86_stack_slot n)
{
  struct stack_local_entry *s;

  gcc_assert (n < MAX_386_STACK_LOCALS);

  for (s = ix86_stack_locals; s; s = s->next)
    if (s->mode == mode && s->n == n)
      return validize_mem (copy_rtx (s->rtl));

  s = ggc_alloc<stack_local_entry> ();
  s->n = n;
  s->mode = mode;
  s->rtl = assign_stack_local (mode, GET_MODE_SIZE (mode), 0);

  s->next = ix86_stack_locals;
  ix86_stack_locals = s;
  return validize_mem (copy_rtx (s->rtl));
}

static void
ix86_instantiate_decls (void)
{
  struct stack_local_entry *s;

  for (s = ix86_stack_locals; s; s = s->next)
    if (s->rtl != NULL_RTX)
      instantiate_decl_rtl (s->rtl);
}

/* Check whether x86 address PARTS is a pc-relative address.  */

bool
ix86_rip_relative_addr_p (struct ix86_address *parts)
{
  rtx base, index, disp;

  base = parts->base;
  index = parts->index;
  disp = parts->disp;

  if (disp && !base && !index)
    {
      if (TARGET_64BIT)
	{
	  rtx symbol = disp;

	  if (GET_CODE (disp) == CONST)
	    symbol = XEXP (disp, 0);
	  if (GET_CODE (symbol) == PLUS
	      && CONST_INT_P (XEXP (symbol, 1)))
	    symbol = XEXP (symbol, 0);

	  if (GET_CODE (symbol) == LABEL_REF
	      || (GET_CODE (symbol) == SYMBOL_REF
		  && SYMBOL_REF_TLS_MODEL (symbol) == 0)
	      || (GET_CODE (symbol) == UNSPEC
		  && (XINT (symbol, 1) == UNSPEC_GOTPCREL
		      || XINT (symbol, 1) == UNSPEC_PCREL
		      || XINT (symbol, 1) == UNSPEC_GOTNTPOFF)))
	    return true;
	}
    }
  return false;
}

/* Calculate the length of the memory address in the instruction encoding.
   Includes addr32 prefix, does not include the one-byte modrm, opcode,
   or other prefixes.  We never generate addr32 prefix for LEA insn.  */

int
memory_address_length (rtx addr, bool lea)
{
  struct ix86_address parts;
  rtx base, index, disp;
  int len;
  int ok;

  if (GET_CODE (addr) == PRE_DEC
      || GET_CODE (addr) == POST_INC
      || GET_CODE (addr) == PRE_MODIFY
      || GET_CODE (addr) == POST_MODIFY)
    return 0;

  ok = ix86_decompose_address (addr, &parts);
  gcc_assert (ok);

  len = (parts.seg == ADDR_SPACE_GENERIC) ? 0 : 1;

  /*  If this is not LEA instruction, add the length of addr32 prefix.  */
  if (TARGET_64BIT && !lea
      && (SImode_address_operand (addr, VOIDmode)
	  || (parts.base && GET_MODE (parts.base) == SImode)
	  || (parts.index && GET_MODE (parts.index) == SImode)))
    len++;

  base = parts.base;
  index = parts.index;
  disp = parts.disp;

  if (base && SUBREG_P (base))
    base = SUBREG_REG (base);
  if (index && SUBREG_P (index))
    index = SUBREG_REG (index);

  gcc_assert (base == NULL_RTX || REG_P (base));
  gcc_assert (index == NULL_RTX || REG_P (index));

  /* Rule of thumb:
       - esp as the base always wants an index,
       - ebp as the base always wants a displacement,
       - r12 as the base always wants an index,
       - r13 as the base always wants a displacement.  */

  /* Register Indirect.  */
  if (base && !index && !disp)
    {
      /* esp (for its index) and ebp (for its displacement) need
	 the two-byte modrm form.  Similarly for r12 and r13 in 64-bit
	 code.  */
      if (base == arg_pointer_rtx
	  || base == frame_pointer_rtx
	  || REGNO (base) == SP_REG
	  || REGNO (base) == BP_REG
	  || REGNO (base) == R12_REG
	  || REGNO (base) == R13_REG)
	len++;
    }

  /* Direct Addressing.  In 64-bit mode mod 00 r/m 5
     is not disp32, but disp32(%rip), so for disp32
     SIB byte is needed, unless print_operand_address
     optimizes it into disp32(%rip) or (%rip) is implied
     by UNSPEC.  */
  else if (disp && !base && !index)
    {
      len += 4;
      if (!ix86_rip_relative_addr_p (&parts))
	len++;
    }
  else
    {
      /* Find the length of the displacement constant.  */
      if (disp)
	{
	  if (base && satisfies_constraint_K (disp))
	    len += 1;
	  else
	    len += 4;
	}
      /* ebp always wants a displacement.  Similarly r13.  */
      else if (base && (REGNO (base) == BP_REG || REGNO (base) == R13_REG))
	len++;

      /* An index requires the two-byte modrm form....  */
      if (index
	  /* ...like esp (or r12), which always wants an index.  */
	  || base == arg_pointer_rtx
	  || base == frame_pointer_rtx
	  || (base && (REGNO (base) == SP_REG || REGNO (base) == R12_REG)))
	len++;
    }

  return len;
}

/* Compute default value for "length_immediate" attribute.  When SHORTFORM
   is set, expect that insn have 8bit immediate alternative.  */
int
ix86_attr_length_immediate_default (rtx_insn *insn, bool shortform)
{
  int len = 0;
  int i;
  extract_insn_cached (insn);
  for (i = recog_data.n_operands - 1; i >= 0; --i)
    if (CONSTANT_P (recog_data.operand[i]))
      {
        enum attr_mode mode = get_attr_mode (insn);

	gcc_assert (!len);
	if (shortform && CONST_INT_P (recog_data.operand[i]))
	  {
	    HOST_WIDE_INT ival = INTVAL (recog_data.operand[i]);
	    switch (mode)
	      {
	      case MODE_QI:
		len = 1;
		continue;
	      case MODE_HI:
		ival = trunc_int_for_mode (ival, HImode);
		break;
	      case MODE_SI:
		ival = trunc_int_for_mode (ival, SImode);
		break;
	      default:
		break;
	      }
	    if (IN_RANGE (ival, -128, 127))
	      {
		len = 1;
		continue;
	      }
	  }
	switch (mode)
	  {
	  case MODE_QI:
	    len = 1;
	    break;
	  case MODE_HI:
	    len = 2;
	    break;
	  case MODE_SI:
	    len = 4;
	    break;
	  /* Immediates for DImode instructions are encoded
	     as 32bit sign extended values.  */
	  case MODE_DI:
	    len = 4;
	    break;
	  default:
	    fatal_insn ("unknown insn mode", insn);
	}
      }
  return len;
}

/* Compute default value for "length_address" attribute.  */
int
ix86_attr_length_address_default (rtx_insn *insn)
{
  int i;

  if (get_attr_type (insn) == TYPE_LEA)
    {
      rtx set = PATTERN (insn), addr;

      if (GET_CODE (set) == PARALLEL)
	set = XVECEXP (set, 0, 0);

      gcc_assert (GET_CODE (set) == SET);

      addr = SET_SRC (set);

      return memory_address_length (addr, true);
    }

  extract_insn_cached (insn);
  for (i = recog_data.n_operands - 1; i >= 0; --i)
    {
      rtx op = recog_data.operand[i];
      if (MEM_P (op))
	{
	  constrain_operands_cached (insn, reload_completed);
	  if (which_alternative != -1)
	    {
	      const char *constraints = recog_data.constraints[i];
	      int alt = which_alternative;

	      while (*constraints == '=' || *constraints == '+')
		constraints++;
	      while (alt-- > 0)
	        while (*constraints++ != ',')
		  ;
	      /* Skip ignored operands.  */
	      if (*constraints == 'X')
		continue;
	    }

	  int len = memory_address_length (XEXP (op, 0), false);

	  /* Account for segment prefix for non-default addr spaces.  */
	  if (!ADDR_SPACE_GENERIC_P (MEM_ADDR_SPACE (op)))
	    len++;

	  return len;
	}
    }
  return 0;
}

/* Compute default value for "length_vex" attribute. It includes
   2 or 3 byte VEX prefix and 1 opcode byte.  */

int
ix86_attr_length_vex_default (rtx_insn *insn, bool has_0f_opcode,
			      bool has_vex_w)
{
  int i;

  /* Only 0f opcode can use 2 byte VEX prefix and  VEX W bit uses 3
     byte VEX prefix.  */
  if (!has_0f_opcode || has_vex_w)
    return 3 + 1;

 /* We can always use 2 byte VEX prefix in 32bit.  */
  if (!TARGET_64BIT)
    return 2 + 1;

  extract_insn_cached (insn);

  for (i = recog_data.n_operands - 1; i >= 0; --i)
    if (REG_P (recog_data.operand[i]))
      {
	/* REX.W bit uses 3 byte VEX prefix.  */
	if (GET_MODE (recog_data.operand[i]) == DImode
	    && GENERAL_REG_P (recog_data.operand[i]))
	  return 3 + 1;
      }
    else
      {
	/* REX.X or REX.B bits use 3 byte VEX prefix.  */
	if (MEM_P (recog_data.operand[i])
	    && x86_extended_reg_mentioned_p (recog_data.operand[i]))
	  return 3 + 1;
      }

  return 2 + 1;
}


static bool
ix86_class_likely_spilled_p (reg_class_t);

/* Returns true if lhs of insn is HW function argument register and set up
   is_spilled to true if it is likely spilled HW register.  */
static bool
insn_is_function_arg (rtx insn, bool* is_spilled)
{
  rtx dst;

  if (!NONDEBUG_INSN_P (insn))
    return false;
  /* Call instructions are not movable, ignore it.  */
  if (CALL_P (insn))
    return false;
  insn = PATTERN (insn);
  if (GET_CODE (insn) == PARALLEL)
    insn = XVECEXP (insn, 0, 0);
  if (GET_CODE (insn) != SET)
    return false;
  dst = SET_DEST (insn);
  if (REG_P (dst) && HARD_REGISTER_P (dst)
      && ix86_function_arg_regno_p (REGNO (dst)))
    {
      /* Is it likely spilled HW register?  */
      if (!TEST_HARD_REG_BIT (fixed_reg_set, REGNO (dst))
	  && ix86_class_likely_spilled_p (REGNO_REG_CLASS (REGNO (dst))))
	*is_spilled = true;
      return true;
    }
  return false;
}

/* Add output dependencies for chain of function adjacent arguments if only
   there is a move to likely spilled HW register.  Return first argument
   if at least one dependence was added or NULL otherwise.  */
static rtx_insn *
add_parameter_dependencies (rtx_insn *call, rtx_insn *head)
{
  rtx_insn *insn;
  rtx_insn *last = call;
  rtx_insn *first_arg = NULL;
  bool is_spilled = false;

  head = PREV_INSN (head);

  /* Find nearest to call argument passing instruction.  */
  while (true)
    {
      last = PREV_INSN (last);
      if (last == head)
	return NULL;
      if (!NONDEBUG_INSN_P (last))
	continue;
      if (insn_is_function_arg (last, &is_spilled))
	break;
      return NULL;
    }

  first_arg = last;
  while (true)
    {
      insn = PREV_INSN (last);
      if (!INSN_P (insn))
	break;
      if (insn == head)
	break;
      if (!NONDEBUG_INSN_P (insn))
	{
	  last = insn;
	  continue;
	}
      if (insn_is_function_arg (insn, &is_spilled))
	{
	  /* Add output depdendence between two function arguments if chain
	     of output arguments contains likely spilled HW registers.  */
	  if (is_spilled)
	    add_dependence (first_arg, insn, REG_DEP_OUTPUT);
	  first_arg = last = insn;
	}
      else
	break;
    }
  if (!is_spilled)
    return NULL;
  return first_arg;
}

/* Add output or anti dependency from insn to first_arg to restrict its code
   motion.  */
static void
avoid_func_arg_motion (rtx_insn *first_arg, rtx_insn *insn)
{
  rtx set;
  rtx tmp;

  set = single_set (insn);
  if (!set)
    return;
  tmp = SET_DEST (set);
  if (REG_P (tmp))
    {
      /* Add output dependency to the first function argument.  */
      add_dependence (first_arg, insn, REG_DEP_OUTPUT);
      return;
    }
  /* Add anti dependency.  */
  add_dependence (first_arg, insn, REG_DEP_ANTI);
}

/* Avoid cross block motion of function argument through adding dependency
   from the first non-jump instruction in bb.  */
static void
add_dependee_for_func_arg (rtx_insn *arg, basic_block bb)
{
  rtx_insn *insn = BB_END (bb);

  while (insn)
    {
      if (NONDEBUG_INSN_P (insn) && NONJUMP_INSN_P (insn))
	{
	  rtx set = single_set (insn);
	  if (set)
	    {
	      avoid_func_arg_motion (arg, insn);
	      return;
	    }
	}
      if (insn == BB_HEAD (bb))
	return;
      insn = PREV_INSN (insn);
    }
}

/* Hook for pre-reload schedule - avoid motion of function arguments
   passed in likely spilled HW registers.  */
static void
ix86_dependencies_evaluation_hook (rtx_insn *head, rtx_insn *tail)
{
  rtx_insn *insn;
  rtx_insn *first_arg = NULL;
  if (reload_completed)
    return;
  while (head != tail && DEBUG_INSN_P (head))
    head = NEXT_INSN (head);
  for (insn = tail; insn != head; insn = PREV_INSN (insn))
    if (INSN_P (insn) && CALL_P (insn))
      {
	first_arg = add_parameter_dependencies (insn, head);
	if (first_arg)
	  {
	    /* Add dependee for first argument to predecessors if only
	       region contains more than one block.  */
	    basic_block bb =  BLOCK_FOR_INSN (insn);
	    int rgn = CONTAINING_RGN (bb->index);
	    int nr_blks = RGN_NR_BLOCKS (rgn);
	    /* Skip trivial regions and region head blocks that can have
	       predecessors outside of region.  */
	    if (nr_blks > 1 && BLOCK_TO_BB (bb->index) != 0)
	      {
		edge e;
		edge_iterator ei;

		/* Regions are SCCs with the exception of selective
		   scheduling with pipelining of outer blocks enabled.
		   So also check that immediate predecessors of a non-head
		   block are in the same region.  */
		FOR_EACH_EDGE (e, ei, bb->preds)
		  {
		    /* Avoid creating of loop-carried dependencies through
		       using topological ordering in the region.  */
		    if (rgn == CONTAINING_RGN (e->src->index)
			&& BLOCK_TO_BB (bb->index) > BLOCK_TO_BB (e->src->index))
		      add_dependee_for_func_arg (first_arg, e->src); 
		  }
	      }
	    insn = first_arg;
	    if (insn == head)
	      break;
	  }
      }
    else if (first_arg)
      avoid_func_arg_motion (first_arg, insn);
}

/* Hook for pre-reload schedule - set priority of moves from likely spilled
   HW registers to maximum, to schedule them at soon as possible. These are
   moves from function argument registers at the top of the function entry
   and moves from function return value registers after call.  */
static int
ix86_adjust_priority (rtx_insn *insn, int priority)
{
  rtx set;

  if (reload_completed)
    return priority;

  if (!NONDEBUG_INSN_P (insn))
    return priority;

  set = single_set (insn);
  if (set)
    {
      rtx tmp = SET_SRC (set);
      if (REG_P (tmp)
          && HARD_REGISTER_P (tmp)
          && !TEST_HARD_REG_BIT (fixed_reg_set, REGNO (tmp))
          && ix86_class_likely_spilled_p (REGNO_REG_CLASS (REGNO (tmp))))
	return current_sched_info->sched_max_insns_priority;
    }

  return priority;
}

/* Prepare for scheduling pass.  */
static void
ix86_sched_init_global (FILE *, int, int)
{
  /* Install scheduling hooks for current CPU.  Some of these hooks are used
     in time-critical parts of the scheduler, so we only set them up when
     they are actually used.  */
  switch (ix86_tune)
    {
    case PROCESSOR_CORE2:
    case PROCESSOR_NEHALEM:
    case PROCESSOR_SANDYBRIDGE:
    case PROCESSOR_HASWELL:
    case PROCESSOR_GENERIC:
      /* Do not perform multipass scheduling for pre-reload schedule
         to save compile time.  */
      if (reload_completed)
	{
	  ix86_core2i7_init_hooks ();
	  break;
	}
      /* Fall through.  */
    default:
      targetm.sched.dfa_post_advance_cycle = NULL;
      targetm.sched.first_cycle_multipass_init = NULL;
      targetm.sched.first_cycle_multipass_begin = NULL;
      targetm.sched.first_cycle_multipass_issue = NULL;
      targetm.sched.first_cycle_multipass_backtrack = NULL;
      targetm.sched.first_cycle_multipass_end = NULL;
      targetm.sched.first_cycle_multipass_fini = NULL;
      break;
    }
}


/* Implement TARGET_STATIC_RTX_ALIGNMENT.  */

static HOST_WIDE_INT
ix86_static_rtx_alignment (machine_mode mode)
{
  if (mode == DFmode)
    return 64;
  if (ALIGN_MODE_128 (mode))
    return MAX (128, GET_MODE_ALIGNMENT (mode));
  return GET_MODE_ALIGNMENT (mode);
}

/* Implement TARGET_CONSTANT_ALIGNMENT.  */

static HOST_WIDE_INT
ix86_constant_alignment (const_tree exp, HOST_WIDE_INT align)
{
  if (TREE_CODE (exp) == REAL_CST || TREE_CODE (exp) == VECTOR_CST
      || TREE_CODE (exp) == INTEGER_CST)
    {
      machine_mode mode = TYPE_MODE (TREE_TYPE (exp));
      HOST_WIDE_INT mode_align = ix86_static_rtx_alignment (mode);
      return MAX (mode_align, align);
    }
  else if (!optimize_size && TREE_CODE (exp) == STRING_CST
	   && TREE_STRING_LENGTH (exp) >= 31 && align < BITS_PER_WORD)
    return BITS_PER_WORD;

  return align;
}

/* Implement TARGET_EMPTY_RECORD_P.  */

static bool
ix86_is_empty_record (const_tree type)
{
  if (!TARGET_64BIT)
    return false;
  return default_is_empty_record (type);
}

/* Implement TARGET_WARN_PARAMETER_PASSING_ABI.  */

static void
ix86_warn_parameter_passing_abi (cumulative_args_t cum_v, tree type)
{
  CUMULATIVE_ARGS *cum = get_cumulative_args (cum_v);

  if (!cum->warn_empty)
    return;

  if (!TYPE_EMPTY_P (type))
    return;

  /* Don't warn if the function isn't visible outside of the TU.  */
  if (cum->decl && !TREE_PUBLIC (cum->decl))
    return;

  const_tree ctx = get_ultimate_context (cum->decl);
  if (ctx != NULL_TREE
      && !TRANSLATION_UNIT_WARN_EMPTY_P (ctx))
    return;

  /* If the actual size of the type is zero, then there is no change
     in how objects of this size are passed.  */
  if (int_size_in_bytes (type) == 0)
    return;

  warning (OPT_Wabi, "empty class %qT parameter passing ABI "
	   "changes in -fabi-version=12 (GCC 8)", type);

  /* Only warn once.  */
  cum->warn_empty = false;
}

/* Compute the alignment for a variable for Intel MCU psABI.  TYPE is
   the data type, and ALIGN is the alignment that the object would
   ordinarily have.  */

static int
iamcu_alignment (tree type, int align)
{
  machine_mode mode;

  if (align < 32 || TYPE_USER_ALIGN (type))
    return align;

  /* Intel MCU psABI specifies scalar types > 4 bytes aligned to 4
     bytes.  */
  mode = TYPE_MODE (strip_array_types (type));
  switch (GET_MODE_CLASS (mode))
    {
    case MODE_INT:
    case MODE_COMPLEX_INT:
    case MODE_COMPLEX_FLOAT:
    case MODE_FLOAT:
    case MODE_DECIMAL_FLOAT:
      return 32;
    default:
      return align;
    }
}

/* Compute the alignment for a static variable.
   TYPE is the data type, and ALIGN is the alignment that
   the object would ordinarily have.  The value of this function is used
   instead of that alignment to align the object.  */

int
ix86_data_alignment (tree type, int align, bool opt)
{
  /* GCC 4.8 and earlier used to incorrectly assume this alignment even
     for symbols from other compilation units or symbols that don't need
     to bind locally.  In order to preserve some ABI compatibility with
     those compilers, ensure we don't decrease alignment from what we
     used to assume.  */

  int max_align_compat = MIN (256, MAX_OFILE_ALIGNMENT);

  /* A data structure, equal or greater than the size of a cache line
     (64 bytes in the Pentium 4 and other recent Intel processors, including
     processors based on Intel Core microarchitecture) should be aligned
     so that its base address is a multiple of a cache line size.  */

  int max_align
    = MIN ((unsigned) ix86_tune_cost->prefetch_block * 8, MAX_OFILE_ALIGNMENT);

  if (max_align < BITS_PER_WORD)
    max_align = BITS_PER_WORD;

  switch (ix86_align_data_type)
    {
    case ix86_align_data_type_abi: opt = false; break;
    case ix86_align_data_type_compat: max_align = BITS_PER_WORD; break;
    case ix86_align_data_type_cacheline: break;
    }

  if (TARGET_IAMCU)
    align = iamcu_alignment (type, align);

  if (opt
      && AGGREGATE_TYPE_P (type)
      && TYPE_SIZE (type)
      && TREE_CODE (TYPE_SIZE (type)) == INTEGER_CST)
    {
      if (wi::geu_p (wi::to_wide (TYPE_SIZE (type)), max_align_compat)
	  && align < max_align_compat)
	align = max_align_compat;
      if (wi::geu_p (wi::to_wide (TYPE_SIZE (type)), max_align)
	  && align < max_align)
	align = max_align;
    }

  /* x86-64 ABI requires arrays greater than 16 bytes to be aligned
     to 16byte boundary.  */
  if (TARGET_64BIT)
    {
      if ((opt ? AGGREGATE_TYPE_P (type) : TREE_CODE (type) == ARRAY_TYPE)
	  && TYPE_SIZE (type)
	  && TREE_CODE (TYPE_SIZE (type)) == INTEGER_CST
	  && wi::geu_p (wi::to_wide (TYPE_SIZE (type)), 128)
	  && align < 128)
	return 128;
    }

  if (!opt)
    return align;

  if (TREE_CODE (type) == ARRAY_TYPE)
    {
      if (TYPE_MODE (TREE_TYPE (type)) == DFmode && align < 64)
	return 64;
      if (ALIGN_MODE_128 (TYPE_MODE (TREE_TYPE (type))) && align < 128)
	return 128;
    }
  else if (TREE_CODE (type) == COMPLEX_TYPE)
    {

      if (TYPE_MODE (type) == DCmode && align < 64)
	return 64;
      if ((TYPE_MODE (type) == XCmode
	   || TYPE_MODE (type) == TCmode) && align < 128)
	return 128;
    }
  else if ((TREE_CODE (type) == RECORD_TYPE
	    || TREE_CODE (type) == UNION_TYPE
	    || TREE_CODE (type) == QUAL_UNION_TYPE)
	   && TYPE_FIELDS (type))
    {
      if (DECL_MODE (TYPE_FIELDS (type)) == DFmode && align < 64)
	return 64;
      if (ALIGN_MODE_128 (DECL_MODE (TYPE_FIELDS (type))) && align < 128)
	return 128;
    }
  else if (TREE_CODE (type) == REAL_TYPE || TREE_CODE (type) == VECTOR_TYPE
	   || TREE_CODE (type) == INTEGER_TYPE)
    {
      if (TYPE_MODE (type) == DFmode && align < 64)
	return 64;
      if (ALIGN_MODE_128 (TYPE_MODE (type)) && align < 128)
	return 128;
    }

  return align;
}

/* Compute the alignment for a local variable or a stack slot.  EXP is
   the data type or decl itself, MODE is the widest mode available and
   ALIGN is the alignment that the object would ordinarily have.  The
   value of this macro is used instead of that alignment to align the
   object.  */

unsigned int
ix86_local_alignment (tree exp, machine_mode mode,
		      unsigned int align)
{
  tree type, decl;

  if (exp && DECL_P (exp))
    {
      type = TREE_TYPE (exp);
      decl = exp;
    }
  else
    {
      type = exp;
      decl = NULL;
    }

  /* Don't do dynamic stack realignment for long long objects with
     -mpreferred-stack-boundary=2.  */
  if (!TARGET_64BIT
      && align == 64
      && ix86_preferred_stack_boundary < 64
      && (mode == DImode || (type && TYPE_MODE (type) == DImode))
      && (!type || !TYPE_USER_ALIGN (type))
      && (!decl || !DECL_USER_ALIGN (decl)))
    align = 32;

  /* If TYPE is NULL, we are allocating a stack slot for caller-save
     register in MODE.  We will return the largest alignment of XF
     and DF.  */
  if (!type)
    {
      if (mode == XFmode && align < GET_MODE_ALIGNMENT (DFmode))
	align = GET_MODE_ALIGNMENT (DFmode);
      return align;
    }

  /* Don't increase alignment for Intel MCU psABI.  */
  if (TARGET_IAMCU)
    return align;

  /* x86-64 ABI requires arrays greater than 16 bytes to be aligned
     to 16byte boundary.  Exact wording is:

     An array uses the same alignment as its elements, except that a local or
     global array variable of length at least 16 bytes or
     a C99 variable-length array variable always has alignment of at least 16 bytes.

     This was added to allow use of aligned SSE instructions at arrays.  This
     rule is meant for static storage (where compiler cannot do the analysis
     by itself).  We follow it for automatic variables only when convenient.
     We fully control everything in the function compiled and functions from
     other unit cannot rely on the alignment.

     Exclude va_list type.  It is the common case of local array where
     we cannot benefit from the alignment.  

     TODO: Probably one should optimize for size only when var is not escaping.  */
  if (TARGET_64BIT && optimize_function_for_speed_p (cfun)
      && TARGET_SSE)
    {
      if (AGGREGATE_TYPE_P (type)
	  && (va_list_type_node == NULL_TREE
	      || (TYPE_MAIN_VARIANT (type)
		  != TYPE_MAIN_VARIANT (va_list_type_node)))
	  && TYPE_SIZE (type)
	  && TREE_CODE (TYPE_SIZE (type)) == INTEGER_CST
	  && wi::geu_p (wi::to_wide (TYPE_SIZE (type)), 128)
	  && align < 128)
	return 128;
    }
  if (TREE_CODE (type) == ARRAY_TYPE)
    {
      if (TYPE_MODE (TREE_TYPE (type)) == DFmode && align < 64)
	return 64;
      if (ALIGN_MODE_128 (TYPE_MODE (TREE_TYPE (type))) && align < 128)
	return 128;
    }
  else if (TREE_CODE (type) == COMPLEX_TYPE)
    {
      if (TYPE_MODE (type) == DCmode && align < 64)
	return 64;
      if ((TYPE_MODE (type) == XCmode
	   || TYPE_MODE (type) == TCmode) && align < 128)
	return 128;
    }
  else if ((TREE_CODE (type) == RECORD_TYPE
	    || TREE_CODE (type) == UNION_TYPE
	    || TREE_CODE (type) == QUAL_UNION_TYPE)
	   && TYPE_FIELDS (type))
    {
      if (DECL_MODE (TYPE_FIELDS (type)) == DFmode && align < 64)
	return 64;
      if (ALIGN_MODE_128 (DECL_MODE (TYPE_FIELDS (type))) && align < 128)
	return 128;
    }
  else if (TREE_CODE (type) == REAL_TYPE || TREE_CODE (type) == VECTOR_TYPE
	   || TREE_CODE (type) == INTEGER_TYPE)
    {

      if (TYPE_MODE (type) == DFmode && align < 64)
	return 64;
      if (ALIGN_MODE_128 (TYPE_MODE (type)) && align < 128)
	return 128;
    }
  return align;
}

/* Compute the minimum required alignment for dynamic stack realignment
   purposes for a local variable, parameter or a stack slot.  EXP is
   the data type or decl itself, MODE is its mode and ALIGN is the
   alignment that the object would ordinarily have.  */

unsigned int
ix86_minimum_alignment (tree exp, machine_mode mode,
			unsigned int align)
{
  tree type, decl;

  if (exp && DECL_P (exp))
    {
      type = TREE_TYPE (exp);
      decl = exp;
    }
  else
    {
      type = exp;
      decl = NULL;
    }

  if (TARGET_64BIT || align != 64 || ix86_preferred_stack_boundary >= 64)
    return align;

  /* Don't do dynamic stack realignment for long long objects with
     -mpreferred-stack-boundary=2.  */
  if ((mode == DImode || (type && TYPE_MODE (type) == DImode))
      && (!type || !TYPE_USER_ALIGN (type))
      && (!decl || !DECL_USER_ALIGN (decl)))
    {
      gcc_checking_assert (!TARGET_STV);
      return 32;
    }

  return align;
}

/* Find a location for the static chain incoming to a nested function.
   This is a register, unless all free registers are used by arguments.  */

static rtx
ix86_static_chain (const_tree fndecl_or_type, bool incoming_p)
{
  unsigned regno;

  if (TARGET_64BIT)
    {
      /* We always use R10 in 64-bit mode.  */
      regno = R10_REG;
    }
  else
    {
      const_tree fntype, fndecl;
      unsigned int ccvt;

      /* By default in 32-bit mode we use ECX to pass the static chain.  */
      regno = CX_REG;

      if (TREE_CODE (fndecl_or_type) == FUNCTION_DECL)
	{
          fntype = TREE_TYPE (fndecl_or_type);
	  fndecl = fndecl_or_type;
	}
      else
	{
	  fntype = fndecl_or_type;
	  fndecl = NULL;
	}

      ccvt = ix86_get_callcvt (fntype);
      if ((ccvt & IX86_CALLCVT_FASTCALL) != 0)
	{
	  /* Fastcall functions use ecx/edx for arguments, which leaves
	     us with EAX for the static chain.
	     Thiscall functions use ecx for arguments, which also
	     leaves us with EAX for the static chain.  */
	  regno = AX_REG;
	}
      else if ((ccvt & IX86_CALLCVT_THISCALL) != 0)
	{
	  /* Thiscall functions use ecx for arguments, which leaves
	     us with EAX and EDX for the static chain.
	     We are using for abi-compatibility EAX.  */
	  regno = AX_REG;
	}
      else if (ix86_function_regparm (fntype, fndecl) == 3)
	{
	  /* For regparm 3, we have no free call-clobbered registers in
	     which to store the static chain.  In order to implement this,
	     we have the trampoline push the static chain to the stack.
	     However, we can't push a value below the return address when
	     we call the nested function directly, so we have to use an
	     alternate entry point.  For this we use ESI, and have the
	     alternate entry point push ESI, so that things appear the
	     same once we're executing the nested function.  */
	  if (incoming_p)
	    {
	      if (fndecl == current_function_decl
		  && !ix86_static_chain_on_stack)
		{
		  gcc_assert (!reload_completed);
		  ix86_static_chain_on_stack = true;
		}
	      return gen_frame_mem (SImode,
				    plus_constant (Pmode,
						   arg_pointer_rtx, -8));
	    }
	  regno = SI_REG;
	}
    }

  return gen_rtx_REG (Pmode, regno);
}

/* Emit RTL insns to initialize the variable parts of a trampoline.
   FNDECL is the decl of the target address; M_TRAMP is a MEM for
   the trampoline, and CHAIN_VALUE is an RTX for the static chain
   to be passed to the target function.  */

static void
ix86_trampoline_init (rtx m_tramp, tree fndecl, rtx chain_value)
{
  rtx mem, fnaddr;
  int opcode;
  int offset = 0;
  bool need_endbr = (flag_cf_protection & CF_BRANCH);

  fnaddr = XEXP (DECL_RTL (fndecl), 0);

  if (TARGET_64BIT)
    {
      int size;

      if (need_endbr)
	{
	  /* Insert ENDBR64.  */
	  mem = adjust_address (m_tramp, SImode, offset);
	  emit_move_insn (mem, gen_int_mode (0xfa1e0ff3, SImode));
	  offset += 4;
	}

      /* Load the function address to r11.  Try to load address using
	 the shorter movl instead of movabs.  We may want to support
	 movq for kernel mode, but kernel does not use trampolines at
	 the moment.  FNADDR is a 32bit address and may not be in
	 DImode when ptr_mode == SImode.  Always use movl in this
	 case.  */
      if (ptr_mode == SImode
	  || x86_64_zext_immediate_operand (fnaddr, VOIDmode))
	{
	  fnaddr = copy_addr_to_reg (fnaddr);

	  mem = adjust_address (m_tramp, HImode, offset);
	  emit_move_insn (mem, gen_int_mode (0xbb41, HImode));

	  mem = adjust_address (m_tramp, SImode, offset + 2);
	  emit_move_insn (mem, gen_lowpart (SImode, fnaddr));
	  offset += 6;
	}
      else
	{
	  mem = adjust_address (m_tramp, HImode, offset);
	  emit_move_insn (mem, gen_int_mode (0xbb49, HImode));

	  mem = adjust_address (m_tramp, DImode, offset + 2);
	  emit_move_insn (mem, fnaddr);
	  offset += 10;
	}

      /* Load static chain using movabs to r10.  Use the shorter movl
         instead of movabs when ptr_mode == SImode.  */
      if (ptr_mode == SImode)
	{
	  opcode = 0xba41;
	  size = 6;
	}
      else
	{
	  opcode = 0xba49;
	  size = 10;
	}

      mem = adjust_address (m_tramp, HImode, offset);
      emit_move_insn (mem, gen_int_mode (opcode, HImode));

      mem = adjust_address (m_tramp, ptr_mode, offset + 2);
      emit_move_insn (mem, chain_value);
      offset += size;

      /* Jump to r11; the last (unused) byte is a nop, only there to
	 pad the write out to a single 32-bit store.  */
      mem = adjust_address (m_tramp, SImode, offset);
      emit_move_insn (mem, gen_int_mode (0x90e3ff49, SImode));
      offset += 4;
    }
  else
    {
      rtx disp, chain;

      /* Depending on the static chain location, either load a register
	 with a constant, or push the constant to the stack.  All of the
	 instructions are the same size.  */
      chain = ix86_static_chain (fndecl, true);
      if (REG_P (chain))
	{
	  switch (REGNO (chain))
	    {
	    case AX_REG:
	      opcode = 0xb8; break;
	    case CX_REG:
	      opcode = 0xb9; break;
	    default:
	      gcc_unreachable ();
	    }
	}
      else
	opcode = 0x68;

      if (need_endbr)
	{
	  /* Insert ENDBR32.  */
	  mem = adjust_address (m_tramp, SImode, offset);
	  emit_move_insn (mem, gen_int_mode (0xfb1e0ff3, SImode));
	  offset += 4;
	}

      mem = adjust_address (m_tramp, QImode, offset);
      emit_move_insn (mem, gen_int_mode (opcode, QImode));

      mem = adjust_address (m_tramp, SImode, offset + 1);
      emit_move_insn (mem, chain_value);
      offset += 5;

      mem = adjust_address (m_tramp, QImode, offset);
      emit_move_insn (mem, gen_int_mode (0xe9, QImode));

      mem = adjust_address (m_tramp, SImode, offset + 1);

      /* Compute offset from the end of the jmp to the target function.
	 In the case in which the trampoline stores the static chain on
	 the stack, we need to skip the first insn which pushes the
	 (call-saved) register static chain; this push is 1 byte.  */
      offset += 5;
      disp = expand_binop (SImode, sub_optab, fnaddr,
			   plus_constant (Pmode, XEXP (m_tramp, 0),
					  offset - (MEM_P (chain) ? 1 : 0)),
			   NULL_RTX, 1, OPTAB_DIRECT);
      emit_move_insn (mem, disp);
    }

  gcc_assert (offset <= TRAMPOLINE_SIZE);

#ifdef HAVE_ENABLE_EXECUTE_STACK
#ifdef CHECK_EXECUTE_STACK_ENABLED
  if (CHECK_EXECUTE_STACK_ENABLED)
#endif
  emit_library_call (gen_rtx_SYMBOL_REF (Pmode, "__enable_execute_stack"),
		     LCT_NORMAL, VOIDmode, XEXP (m_tramp, 0), Pmode);
#endif
}

static bool
ix86_allocate_stack_slots_for_args (void)
{
  /* Naked functions should not allocate stack slots for arguments.  */
  return !ix86_function_naked (current_function_decl);
}

static bool
ix86_warn_func_return (tree decl)
{
  /* Naked functions are implemented entirely in assembly, including the
     return sequence, so suppress warnings about this.  */
  return !ix86_function_naked (decl);
}

/* The following file contains several enumerations and data structures
   built from the definitions in i386-builtin-types.def.  */

#include "i386-builtin-types.inc"

/* Table for the ix86 builtin non-function types.  */
static GTY(()) tree ix86_builtin_type_tab[(int) IX86_BT_LAST_CPTR + 1];

/* Retrieve an element from the above table, building some of
   the types lazily.  */

static tree
ix86_get_builtin_type (enum ix86_builtin_type tcode)
{
  unsigned int index;
  tree type, itype;

  gcc_assert ((unsigned)tcode < ARRAY_SIZE(ix86_builtin_type_tab));

  type = ix86_builtin_type_tab[(int) tcode];
  if (type != NULL)
    return type;

  gcc_assert (tcode > IX86_BT_LAST_PRIM);
  if (tcode <= IX86_BT_LAST_VECT)
    {
      machine_mode mode;

      index = tcode - IX86_BT_LAST_PRIM - 1;
      itype = ix86_get_builtin_type (ix86_builtin_type_vect_base[index]);
      mode = ix86_builtin_type_vect_mode[index];

      type = build_vector_type_for_mode (itype, mode);
    }
  else
    {
      int quals;

      index = tcode - IX86_BT_LAST_VECT - 1;
      if (tcode <= IX86_BT_LAST_PTR)
	quals = TYPE_UNQUALIFIED;
      else
	quals = TYPE_QUAL_CONST;

      itype = ix86_get_builtin_type (ix86_builtin_type_ptr_base[index]);
      if (quals != TYPE_UNQUALIFIED)
	itype = build_qualified_type (itype, quals);

      type = build_pointer_type (itype);
    }

  ix86_builtin_type_tab[(int) tcode] = type;
  return type;
}

/* Table for the ix86 builtin function types.  */
static GTY(()) tree ix86_builtin_func_type_tab[(int) IX86_BT_LAST_ALIAS + 1];

/* Retrieve an element from the above table, building some of
   the types lazily.  */

static tree
ix86_get_builtin_func_type (enum ix86_builtin_func_type tcode)
{
  tree type;

  gcc_assert ((unsigned)tcode < ARRAY_SIZE (ix86_builtin_func_type_tab));

  type = ix86_builtin_func_type_tab[(int) tcode];
  if (type != NULL)
    return type;

  if (tcode <= IX86_BT_LAST_FUNC)
    {
      unsigned start = ix86_builtin_func_start[(int) tcode];
      unsigned after = ix86_builtin_func_start[(int) tcode + 1];
      tree rtype, atype, args = void_list_node;
      unsigned i;

      rtype = ix86_get_builtin_type (ix86_builtin_func_args[start]);
      for (i = after - 1; i > start; --i)
	{
	  atype = ix86_get_builtin_type (ix86_builtin_func_args[i]);
	  args = tree_cons (NULL, atype, args);
	}

      type = build_function_type (rtype, args);
    }
  else
    {
      unsigned index = tcode - IX86_BT_LAST_FUNC - 1;
      enum ix86_builtin_func_type icode;

      icode = ix86_builtin_func_alias_base[index];
      type = ix86_get_builtin_func_type (icode);
    }

  ix86_builtin_func_type_tab[(int) tcode] = type;
  return type;
}


/* Codes for all the SSE/MMX builtins.  Builtins not mentioned in any
   bdesc_* arrays below should come first, then builtins for each bdesc_*
   array in ascending order, so that we can use direct array accesses.  */
enum ix86_builtins
{
  IX86_BUILTIN_MASKMOVQ,
  IX86_BUILTIN_LDMXCSR,
  IX86_BUILTIN_STMXCSR,
  IX86_BUILTIN_MASKMOVDQU,
  IX86_BUILTIN_PSLLDQ128,
  IX86_BUILTIN_CLFLUSH,
  IX86_BUILTIN_MONITOR,
  IX86_BUILTIN_MWAIT,
  IX86_BUILTIN_UMONITOR,
  IX86_BUILTIN_UMWAIT,
  IX86_BUILTIN_TPAUSE,
  IX86_BUILTIN_CLZERO,
  IX86_BUILTIN_CLDEMOTE,
  IX86_BUILTIN_VEC_INIT_V2SI,
  IX86_BUILTIN_VEC_INIT_V4HI,
  IX86_BUILTIN_VEC_INIT_V8QI,
  IX86_BUILTIN_VEC_EXT_V2DF,
  IX86_BUILTIN_VEC_EXT_V2DI,
  IX86_BUILTIN_VEC_EXT_V4SF,
  IX86_BUILTIN_VEC_EXT_V4SI,
  IX86_BUILTIN_VEC_EXT_V8HI,
  IX86_BUILTIN_VEC_EXT_V2SI,
  IX86_BUILTIN_VEC_EXT_V4HI,
  IX86_BUILTIN_VEC_EXT_V16QI,
  IX86_BUILTIN_VEC_SET_V2DI,
  IX86_BUILTIN_VEC_SET_V4SF,
  IX86_BUILTIN_VEC_SET_V4SI,
  IX86_BUILTIN_VEC_SET_V8HI,
  IX86_BUILTIN_VEC_SET_V4HI,
  IX86_BUILTIN_VEC_SET_V16QI,
  IX86_BUILTIN_GATHERSIV2DF,
  IX86_BUILTIN_GATHERSIV4DF,
  IX86_BUILTIN_GATHERDIV2DF,
  IX86_BUILTIN_GATHERDIV4DF,
  IX86_BUILTIN_GATHERSIV4SF,
  IX86_BUILTIN_GATHERSIV8SF,
  IX86_BUILTIN_GATHERDIV4SF,
  IX86_BUILTIN_GATHERDIV8SF,
  IX86_BUILTIN_GATHERSIV2DI,
  IX86_BUILTIN_GATHERSIV4DI,
  IX86_BUILTIN_GATHERDIV2DI,
  IX86_BUILTIN_GATHERDIV4DI,
  IX86_BUILTIN_GATHERSIV4SI,
  IX86_BUILTIN_GATHERSIV8SI,
  IX86_BUILTIN_GATHERDIV4SI,
  IX86_BUILTIN_GATHERDIV8SI,
  IX86_BUILTIN_VFMSUBSD3_MASK3,
  IX86_BUILTIN_VFMSUBSS3_MASK3,
  IX86_BUILTIN_GATHER3SIV8SF,
  IX86_BUILTIN_GATHER3SIV4SF,
  IX86_BUILTIN_GATHER3SIV4DF,
  IX86_BUILTIN_GATHER3SIV2DF,
  IX86_BUILTIN_GATHER3DIV8SF,
  IX86_BUILTIN_GATHER3DIV4SF,
  IX86_BUILTIN_GATHER3DIV4DF,
  IX86_BUILTIN_GATHER3DIV2DF,
  IX86_BUILTIN_GATHER3SIV8SI,
  IX86_BUILTIN_GATHER3SIV4SI,
  IX86_BUILTIN_GATHER3SIV4DI,
  IX86_BUILTIN_GATHER3SIV2DI,
  IX86_BUILTIN_GATHER3DIV8SI,
  IX86_BUILTIN_GATHER3DIV4SI,
  IX86_BUILTIN_GATHER3DIV4DI,
  IX86_BUILTIN_GATHER3DIV2DI,
  IX86_BUILTIN_SCATTERSIV8SF,
  IX86_BUILTIN_SCATTERSIV4SF,
  IX86_BUILTIN_SCATTERSIV4DF,
  IX86_BUILTIN_SCATTERSIV2DF,
  IX86_BUILTIN_SCATTERDIV8SF,
  IX86_BUILTIN_SCATTERDIV4SF,
  IX86_BUILTIN_SCATTERDIV4DF,
  IX86_BUILTIN_SCATTERDIV2DF,
  IX86_BUILTIN_SCATTERSIV8SI,
  IX86_BUILTIN_SCATTERSIV4SI,
  IX86_BUILTIN_SCATTERSIV4DI,
  IX86_BUILTIN_SCATTERSIV2DI,
  IX86_BUILTIN_SCATTERDIV8SI,
  IX86_BUILTIN_SCATTERDIV4SI,
  IX86_BUILTIN_SCATTERDIV4DI,
  IX86_BUILTIN_SCATTERDIV2DI,
  /* Alternate 4 and 8 element gather/scatter for the vectorizer
     where all operands are 32-byte or 64-byte wide respectively.  */
  IX86_BUILTIN_GATHERALTSIV4DF,
  IX86_BUILTIN_GATHERALTDIV8SF,
  IX86_BUILTIN_GATHERALTSIV4DI,
  IX86_BUILTIN_GATHERALTDIV8SI,
  IX86_BUILTIN_GATHER3ALTDIV16SF,
  IX86_BUILTIN_GATHER3ALTDIV16SI,
  IX86_BUILTIN_GATHER3ALTSIV4DF,
  IX86_BUILTIN_GATHER3ALTDIV8SF,
  IX86_BUILTIN_GATHER3ALTSIV4DI,
  IX86_BUILTIN_GATHER3ALTDIV8SI,
  IX86_BUILTIN_GATHER3ALTSIV8DF,
  IX86_BUILTIN_GATHER3ALTSIV8DI,
  IX86_BUILTIN_GATHER3DIV16SF,
  IX86_BUILTIN_GATHER3DIV16SI,
  IX86_BUILTIN_GATHER3DIV8DF,
  IX86_BUILTIN_GATHER3DIV8DI,
  IX86_BUILTIN_GATHER3SIV16SF,
  IX86_BUILTIN_GATHER3SIV16SI,
  IX86_BUILTIN_GATHER3SIV8DF,
  IX86_BUILTIN_GATHER3SIV8DI,
  IX86_BUILTIN_SCATTERALTSIV8DF,
  IX86_BUILTIN_SCATTERALTDIV16SF,
  IX86_BUILTIN_SCATTERALTSIV8DI,
  IX86_BUILTIN_SCATTERALTDIV16SI,
  IX86_BUILTIN_SCATTERALTSIV4DF,
  IX86_BUILTIN_SCATTERALTDIV8SF,
  IX86_BUILTIN_SCATTERALTSIV4DI,
  IX86_BUILTIN_SCATTERALTDIV8SI,
  IX86_BUILTIN_SCATTERALTSIV2DF,
  IX86_BUILTIN_SCATTERALTDIV4SF,
  IX86_BUILTIN_SCATTERALTSIV2DI,
  IX86_BUILTIN_SCATTERALTDIV4SI,
  IX86_BUILTIN_SCATTERDIV16SF,
  IX86_BUILTIN_SCATTERDIV16SI,
  IX86_BUILTIN_SCATTERDIV8DF,
  IX86_BUILTIN_SCATTERDIV8DI,
  IX86_BUILTIN_SCATTERSIV16SF,
  IX86_BUILTIN_SCATTERSIV16SI,
  IX86_BUILTIN_SCATTERSIV8DF,
  IX86_BUILTIN_SCATTERSIV8DI,
  IX86_BUILTIN_GATHERPFQPD,
  IX86_BUILTIN_GATHERPFDPS,
  IX86_BUILTIN_GATHERPFDPD,
  IX86_BUILTIN_GATHERPFQPS,
  IX86_BUILTIN_SCATTERPFDPD,
  IX86_BUILTIN_SCATTERPFDPS,
  IX86_BUILTIN_SCATTERPFQPD,
  IX86_BUILTIN_SCATTERPFQPS,
  IX86_BUILTIN_CLWB,
  IX86_BUILTIN_CLFLUSHOPT,
  IX86_BUILTIN_INFQ,
  IX86_BUILTIN_HUGE_VALQ,
  IX86_BUILTIN_NANQ,
  IX86_BUILTIN_NANSQ,
  IX86_BUILTIN_XABORT,
  IX86_BUILTIN_ADDCARRYX32,
  IX86_BUILTIN_ADDCARRYX64,
  IX86_BUILTIN_SBB32,
  IX86_BUILTIN_SBB64,
  IX86_BUILTIN_RDRAND16_STEP,
  IX86_BUILTIN_RDRAND32_STEP,
  IX86_BUILTIN_RDRAND64_STEP,
  IX86_BUILTIN_RDSEED16_STEP,
  IX86_BUILTIN_RDSEED32_STEP,
  IX86_BUILTIN_RDSEED64_STEP,
  IX86_BUILTIN_MONITORX,
  IX86_BUILTIN_MWAITX,
  IX86_BUILTIN_CFSTRING,
  IX86_BUILTIN_CPU_INIT,
  IX86_BUILTIN_CPU_IS,
  IX86_BUILTIN_CPU_SUPPORTS,
  IX86_BUILTIN_READ_FLAGS,
  IX86_BUILTIN_WRITE_FLAGS,

  /* All the remaining builtins are tracked in bdesc_* arrays in
     i386-builtin.def.  Don't add any IX86_BUILTIN_* enumerators after
     this point.  */
#define BDESC(mask, mask2, icode, name, code, comparison, flag)	\
  code,
#define BDESC_FIRST(kind, kindu, mask, mask2, icode, name, code, comparison, flag) \
  code,									\
  IX86_BUILTIN__BDESC_##kindu##_FIRST = code,
#define BDESC_END(kind, next_kind)

#include "i386-builtin.def"

#undef BDESC
#undef BDESC_FIRST
#undef BDESC_END

  IX86_BUILTIN_MAX,

  IX86_BUILTIN__BDESC_MAX_FIRST = IX86_BUILTIN_MAX,

  /* Now just the aliases for bdesc_* start/end.  */
#define BDESC(mask, mask2, icode, name, code, comparison, flag)
#define BDESC_FIRST(kind, kindu, mask, mask2, icode, name, code, comparison, flag)
#define BDESC_END(kind, next_kind) \
  IX86_BUILTIN__BDESC_##kind##_LAST					    \
    = IX86_BUILTIN__BDESC_##next_kind##_FIRST - 1,

#include "i386-builtin.def"

#undef BDESC
#undef BDESC_FIRST
#undef BDESC_END

  /* Just to make sure there is no comma after the last enumerator.  */
  IX86_BUILTIN__BDESC_MAX_LAST = IX86_BUILTIN__BDESC_MAX_FIRST
};

/* Table for the ix86 builtin decls.  */
static GTY(()) tree ix86_builtins[(int) IX86_BUILTIN_MAX];

/* Table of all of the builtin functions that are possible with different ISA's
   but are waiting to be built until a function is declared to use that
   ISA.  */
struct builtin_isa {
  HOST_WIDE_INT isa;		/* isa_flags this builtin is defined for */
  HOST_WIDE_INT isa2;		/* additional isa_flags this builtin is defined for */
  const char *name;		/* function name */
  enum ix86_builtin_func_type tcode; /* type to use in the declaration */
  unsigned char const_p:1;	/* true if the declaration is constant */
  unsigned char pure_p:1;	/* true if the declaration has pure attribute */
  bool set_and_not_built_p;
};

static struct builtin_isa ix86_builtins_isa[(int) IX86_BUILTIN_MAX];

/* Bits that can still enable any inclusion of a builtin.  */
static HOST_WIDE_INT deferred_isa_values = 0;
static HOST_WIDE_INT deferred_isa_values2 = 0;

/* Add an ix86 target builtin function with CODE, NAME and TYPE.  Save the
   MASK and MASK2 of which isa_flags and ix86_isa_flags2 to use in the
   ix86_builtins_isa array.  Stores the function decl in the ix86_builtins
   array.  Returns the function decl or NULL_TREE, if the builtin was not
   added.

   If the front end has a special hook for builtin functions, delay adding
   builtin functions that aren't in the current ISA until the ISA is changed
   with function specific optimization.  Doing so, can save about 300K for the
   default compiler.  When the builtin is expanded, check at that time whether
   it is valid.

   If the front end doesn't have a special hook, record all builtins, even if
   it isn't an instruction set in the current ISA in case the user uses
   function specific options for a different ISA, so that we don't get scope
   errors if a builtin is added in the middle of a function scope.  */

static inline tree
def_builtin (HOST_WIDE_INT mask, HOST_WIDE_INT mask2,
	     const char *name,
	     enum ix86_builtin_func_type tcode,
	     enum ix86_builtins code)
{
  tree decl = NULL_TREE;

  /* An instruction may be 64bit only regardless of ISAs.  */
  if (!(mask & OPTION_MASK_ISA_64BIT) || TARGET_64BIT)
    {
      ix86_builtins_isa[(int) code].isa = mask;
      ix86_builtins_isa[(int) code].isa2 = mask2;

      mask &= ~OPTION_MASK_ISA_64BIT;

      /* Filter out the masks most often ored together with others.  */
      if ((mask & ix86_isa_flags & OPTION_MASK_ISA_AVX512VL)
	  && mask != OPTION_MASK_ISA_AVX512VL)
	mask &= ~OPTION_MASK_ISA_AVX512VL;
      if ((mask & ix86_isa_flags & OPTION_MASK_ISA_AVX512BW)
	  && mask != OPTION_MASK_ISA_AVX512BW)
	mask &= ~OPTION_MASK_ISA_AVX512BW;

      if (((mask2 == 0 || (mask2 & ix86_isa_flags2) != 0)
	   && (mask == 0 || (mask & ix86_isa_flags) != 0))
	  || (lang_hooks.builtin_function
	      == lang_hooks.builtin_function_ext_scope))
	{
	  tree type = ix86_get_builtin_func_type (tcode);
	  decl = add_builtin_function (name, type, code, BUILT_IN_MD,
				       NULL, NULL_TREE);
	  ix86_builtins[(int) code] = decl;
	  ix86_builtins_isa[(int) code].set_and_not_built_p = false;
	}
      else
	{
	  /* Just MASK and MASK2 where set_and_not_built_p == true can potentially
	     include a builtin.  */
	  deferred_isa_values |= mask;
	  deferred_isa_values2 |= mask2;
	  ix86_builtins[(int) code] = NULL_TREE;
	  ix86_builtins_isa[(int) code].tcode = tcode;
	  ix86_builtins_isa[(int) code].name = name;
	  ix86_builtins_isa[(int) code].const_p = false;
	  ix86_builtins_isa[(int) code].pure_p = false;
	  ix86_builtins_isa[(int) code].set_and_not_built_p = true;
	}
    }

  return decl;
}

/* Like def_builtin, but also marks the function decl "const".  */

static inline tree
def_builtin_const (HOST_WIDE_INT mask, HOST_WIDE_INT mask2, const char *name,
		   enum ix86_builtin_func_type tcode, enum ix86_builtins code)
{
  tree decl = def_builtin (mask, mask2, name, tcode, code);
  if (decl)
    TREE_READONLY (decl) = 1;
  else
    ix86_builtins_isa[(int) code].const_p = true;

  return decl;
}

/* Like def_builtin, but also marks the function decl "pure".  */

static inline tree
def_builtin_pure (HOST_WIDE_INT mask, HOST_WIDE_INT mask2, const char *name,
		  enum ix86_builtin_func_type tcode, enum ix86_builtins code)
{
  tree decl = def_builtin (mask, mask2, name, tcode, code);
  if (decl)
    DECL_PURE_P (decl) = 1;
  else
    ix86_builtins_isa[(int) code].pure_p = true;

  return decl;
}

/* Add any new builtin functions for a given ISA that may not have been
   declared.  This saves a bit of space compared to adding all of the
   declarations to the tree, even if we didn't use them.  */

static void
ix86_add_new_builtins (HOST_WIDE_INT isa, HOST_WIDE_INT isa2)
{
  isa &= ~OPTION_MASK_ISA_64BIT;

  if ((isa & deferred_isa_values) == 0
      && (isa2 & deferred_isa_values2) == 0)
    return;

  /* Bits in ISA value can be removed from potential isa values.  */
  deferred_isa_values &= ~isa;
  deferred_isa_values2 &= ~isa2;

  int i;
  tree saved_current_target_pragma = current_target_pragma;
  current_target_pragma = NULL_TREE;

  for (i = 0; i < (int)IX86_BUILTIN_MAX; i++)
    {
      if (((ix86_builtins_isa[i].isa & isa) != 0
	   || (ix86_builtins_isa[i].isa2 & isa2) != 0)
	  && ix86_builtins_isa[i].set_and_not_built_p)
	{
	  tree decl, type;

	  /* Don't define the builtin again.  */
	  ix86_builtins_isa[i].set_and_not_built_p = false;

	  type = ix86_get_builtin_func_type (ix86_builtins_isa[i].tcode);
	  decl = add_builtin_function_ext_scope (ix86_builtins_isa[i].name,
						 type, i, BUILT_IN_MD, NULL,
						 NULL_TREE);

	  ix86_builtins[i] = decl;
	  if (ix86_builtins_isa[i].const_p)
	    TREE_READONLY (decl) = 1;
	}
    }

  current_target_pragma = saved_current_target_pragma;
}

/* Bits for builtin_description.flag.  */

/* Set when we don't support the comparison natively, and should
   swap_comparison in order to support it.  */
#define BUILTIN_DESC_SWAP_OPERANDS	1

struct builtin_description
{
  const HOST_WIDE_INT mask;
  const HOST_WIDE_INT mask2;
  const enum insn_code icode;
  const char *const name;
  const enum ix86_builtins code;
  const enum rtx_code comparison;
  const int flag;
};

#define MULTI_ARG_4_DF2_DI_I	V2DF_FTYPE_V2DF_V2DF_V2DI_INT
#define MULTI_ARG_4_DF2_DI_I1	V4DF_FTYPE_V4DF_V4DF_V4DI_INT
#define MULTI_ARG_4_SF2_SI_I	V4SF_FTYPE_V4SF_V4SF_V4SI_INT
#define MULTI_ARG_4_SF2_SI_I1	V8SF_FTYPE_V8SF_V8SF_V8SI_INT
#define MULTI_ARG_3_SF		V4SF_FTYPE_V4SF_V4SF_V4SF
#define MULTI_ARG_3_DF		V2DF_FTYPE_V2DF_V2DF_V2DF
#define MULTI_ARG_3_SF2		V8SF_FTYPE_V8SF_V8SF_V8SF
#define MULTI_ARG_3_DF2		V4DF_FTYPE_V4DF_V4DF_V4DF
#define MULTI_ARG_3_DI		V2DI_FTYPE_V2DI_V2DI_V2DI
#define MULTI_ARG_3_SI		V4SI_FTYPE_V4SI_V4SI_V4SI
#define MULTI_ARG_3_SI_DI	V4SI_FTYPE_V4SI_V4SI_V2DI
#define MULTI_ARG_3_HI		V8HI_FTYPE_V8HI_V8HI_V8HI
#define MULTI_ARG_3_HI_SI	V8HI_FTYPE_V8HI_V8HI_V4SI
#define MULTI_ARG_3_QI		V16QI_FTYPE_V16QI_V16QI_V16QI
#define MULTI_ARG_3_DI2		V4DI_FTYPE_V4DI_V4DI_V4DI
#define MULTI_ARG_3_SI2		V8SI_FTYPE_V8SI_V8SI_V8SI
#define MULTI_ARG_3_HI2		V16HI_FTYPE_V16HI_V16HI_V16HI
#define MULTI_ARG_3_QI2		V32QI_FTYPE_V32QI_V32QI_V32QI
#define MULTI_ARG_2_SF		V4SF_FTYPE_V4SF_V4SF
#define MULTI_ARG_2_DF		V2DF_FTYPE_V2DF_V2DF
#define MULTI_ARG_2_DI		V2DI_FTYPE_V2DI_V2DI
#define MULTI_ARG_2_SI		V4SI_FTYPE_V4SI_V4SI
#define MULTI_ARG_2_HI		V8HI_FTYPE_V8HI_V8HI
#define MULTI_ARG_2_QI		V16QI_FTYPE_V16QI_V16QI
#define MULTI_ARG_2_DI_IMM	V2DI_FTYPE_V2DI_SI
#define MULTI_ARG_2_SI_IMM	V4SI_FTYPE_V4SI_SI
#define MULTI_ARG_2_HI_IMM	V8HI_FTYPE_V8HI_SI
#define MULTI_ARG_2_QI_IMM	V16QI_FTYPE_V16QI_SI
#define MULTI_ARG_2_DI_CMP	V2DI_FTYPE_V2DI_V2DI_CMP
#define MULTI_ARG_2_SI_CMP	V4SI_FTYPE_V4SI_V4SI_CMP
#define MULTI_ARG_2_HI_CMP	V8HI_FTYPE_V8HI_V8HI_CMP
#define MULTI_ARG_2_QI_CMP	V16QI_FTYPE_V16QI_V16QI_CMP
#define MULTI_ARG_2_SF_TF	V4SF_FTYPE_V4SF_V4SF_TF
#define MULTI_ARG_2_DF_TF	V2DF_FTYPE_V2DF_V2DF_TF
#define MULTI_ARG_2_DI_TF	V2DI_FTYPE_V2DI_V2DI_TF
#define MULTI_ARG_2_SI_TF	V4SI_FTYPE_V4SI_V4SI_TF
#define MULTI_ARG_2_HI_TF	V8HI_FTYPE_V8HI_V8HI_TF
#define MULTI_ARG_2_QI_TF	V16QI_FTYPE_V16QI_V16QI_TF
#define MULTI_ARG_1_SF		V4SF_FTYPE_V4SF
#define MULTI_ARG_1_DF		V2DF_FTYPE_V2DF
#define MULTI_ARG_1_SF2		V8SF_FTYPE_V8SF
#define MULTI_ARG_1_DF2		V4DF_FTYPE_V4DF
#define MULTI_ARG_1_DI		V2DI_FTYPE_V2DI
#define MULTI_ARG_1_SI		V4SI_FTYPE_V4SI
#define MULTI_ARG_1_HI		V8HI_FTYPE_V8HI
#define MULTI_ARG_1_QI		V16QI_FTYPE_V16QI
#define MULTI_ARG_1_SI_DI	V2DI_FTYPE_V4SI
#define MULTI_ARG_1_HI_DI	V2DI_FTYPE_V8HI
#define MULTI_ARG_1_HI_SI	V4SI_FTYPE_V8HI
#define MULTI_ARG_1_QI_DI	V2DI_FTYPE_V16QI
#define MULTI_ARG_1_QI_SI	V4SI_FTYPE_V16QI
#define MULTI_ARG_1_QI_HI	V8HI_FTYPE_V16QI

#define BDESC(mask, mask2, icode, name, code, comparison, flag)	\
  { mask, mask2, icode, name, code, comparison, flag },
#define BDESC_FIRST(kind, kindu, mask, mask2, icode, name, code, comparison, flag) \
static const struct builtin_description bdesc_##kind[] =		    \
{									    \
  BDESC (mask, mask2, icode, name, code, comparison, flag)
#define BDESC_END(kind, next_kind) \
};

#include "i386-builtin.def"

#undef BDESC
#undef BDESC_FIRST
#undef BDESC_END


/* TM vector builtins.  */

/* Reuse the existing x86-specific `struct builtin_description' cause
   we're lazy.  Add casts to make them fit.  */
static const struct builtin_description bdesc_tm[] =
{
  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_WM64", (enum ix86_builtins) BUILT_IN_TM_STORE_M64, UNKNOWN, VOID_FTYPE_PV2SI_V2SI },
  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_WaRM64", (enum ix86_builtins) BUILT_IN_TM_STORE_WAR_M64, UNKNOWN, VOID_FTYPE_PV2SI_V2SI },
  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_WaWM64", (enum ix86_builtins) BUILT_IN_TM_STORE_WAW_M64, UNKNOWN, VOID_FTYPE_PV2SI_V2SI },
  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_RM64", (enum ix86_builtins) BUILT_IN_TM_LOAD_M64, UNKNOWN, V2SI_FTYPE_PCV2SI },
  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_RaRM64", (enum ix86_builtins) BUILT_IN_TM_LOAD_RAR_M64, UNKNOWN, V2SI_FTYPE_PCV2SI },
  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_RaWM64", (enum ix86_builtins) BUILT_IN_TM_LOAD_RAW_M64, UNKNOWN, V2SI_FTYPE_PCV2SI },
  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_RfWM64", (enum ix86_builtins) BUILT_IN_TM_LOAD_RFW_M64, UNKNOWN, V2SI_FTYPE_PCV2SI },

  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_WM128", (enum ix86_builtins) BUILT_IN_TM_STORE_M128, UNKNOWN, VOID_FTYPE_PV4SF_V4SF },
  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_WaRM128", (enum ix86_builtins) BUILT_IN_TM_STORE_WAR_M128, UNKNOWN, VOID_FTYPE_PV4SF_V4SF },
  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_WaWM128", (enum ix86_builtins) BUILT_IN_TM_STORE_WAW_M128, UNKNOWN, VOID_FTYPE_PV4SF_V4SF },
  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_RM128", (enum ix86_builtins) BUILT_IN_TM_LOAD_M128, UNKNOWN, V4SF_FTYPE_PCV4SF },
  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_RaRM128", (enum ix86_builtins) BUILT_IN_TM_LOAD_RAR_M128, UNKNOWN, V4SF_FTYPE_PCV4SF },
  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_RaWM128", (enum ix86_builtins) BUILT_IN_TM_LOAD_RAW_M128, UNKNOWN, V4SF_FTYPE_PCV4SF },
  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_RfWM128", (enum ix86_builtins) BUILT_IN_TM_LOAD_RFW_M128, UNKNOWN, V4SF_FTYPE_PCV4SF },

  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_WM256", (enum ix86_builtins) BUILT_IN_TM_STORE_M256, UNKNOWN, VOID_FTYPE_PV8SF_V8SF },
  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_WaRM256", (enum ix86_builtins) BUILT_IN_TM_STORE_WAR_M256, UNKNOWN, VOID_FTYPE_PV8SF_V8SF },
  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_WaWM256", (enum ix86_builtins) BUILT_IN_TM_STORE_WAW_M256, UNKNOWN, VOID_FTYPE_PV8SF_V8SF },
  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_RM256", (enum ix86_builtins) BUILT_IN_TM_LOAD_M256, UNKNOWN, V8SF_FTYPE_PCV8SF },
  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_RaRM256", (enum ix86_builtins) BUILT_IN_TM_LOAD_RAR_M256, UNKNOWN, V8SF_FTYPE_PCV8SF },
  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_RaWM256", (enum ix86_builtins) BUILT_IN_TM_LOAD_RAW_M256, UNKNOWN, V8SF_FTYPE_PCV8SF },
  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_RfWM256", (enum ix86_builtins) BUILT_IN_TM_LOAD_RFW_M256, UNKNOWN, V8SF_FTYPE_PCV8SF },

  { OPTION_MASK_ISA_MMX, 0, CODE_FOR_nothing, "__builtin__ITM_LM64", (enum ix86_builtins) BUILT_IN_TM_LOG_M64, UNKNOWN, VOID_FTYPE_PCVOID },
  { OPTION_MASK_ISA_SSE, 0, CODE_FOR_nothing, "__builtin__ITM_LM128", (enum ix86_builtins) BUILT_IN_TM_LOG_M128, UNKNOWN, VOID_FTYPE_PCVOID },
  { OPTION_MASK_ISA_AVX, 0, CODE_FOR_nothing, "__builtin__ITM_LM256", (enum ix86_builtins) BUILT_IN_TM_LOG_M256, UNKNOWN, VOID_FTYPE_PCVOID },
};

/* Initialize the transactional memory vector load/store builtins.  */

static void
ix86_init_tm_builtins (void)
{
  enum ix86_builtin_func_type ftype;
  const struct builtin_description *d;
  size_t i;
  tree decl;
  tree attrs_load, attrs_type_load, attrs_store, attrs_type_store;
  tree attrs_log, attrs_type_log;

  if (!flag_tm)
    return;

  /* If there are no builtins defined, we must be compiling in a
     language without trans-mem support.  */
  if (!builtin_decl_explicit_p (BUILT_IN_TM_LOAD_1))
    return;

  /* Use whatever attributes a normal TM load has.  */
  decl = builtin_decl_explicit (BUILT_IN_TM_LOAD_1);
  attrs_load = DECL_ATTRIBUTES (decl);
  attrs_type_load = TYPE_ATTRIBUTES (TREE_TYPE (decl));
  /* Use whatever attributes a normal TM store has.  */
  decl = builtin_decl_explicit (BUILT_IN_TM_STORE_1);
  attrs_store = DECL_ATTRIBUTES (decl);
  attrs_type_store = TYPE_ATTRIBUTES (TREE_TYPE (decl));
  /* Use whatever attributes a normal TM log has.  */
  decl = builtin_decl_explicit (BUILT_IN_TM_LOG);
  attrs_log = DECL_ATTRIBUTES (decl);
  attrs_type_log = TYPE_ATTRIBUTES (TREE_TYPE (decl));

  for (i = 0, d = bdesc_tm;
       i < ARRAY_SIZE (bdesc_tm);
       i++, d++)
    {
      if ((d->mask & ix86_isa_flags) != 0
	  || (lang_hooks.builtin_function
	      == lang_hooks.builtin_function_ext_scope))
	{
	  tree type, attrs, attrs_type;
	  enum built_in_function code = (enum built_in_function) d->code;

	  ftype = (enum ix86_builtin_func_type) d->flag;
	  type = ix86_get_builtin_func_type (ftype);

	  if (BUILTIN_TM_LOAD_P (code))
	    {
	      attrs = attrs_load;
	      attrs_type = attrs_type_load;
	    }
	  else if (BUILTIN_TM_STORE_P (code))
	    {
	      attrs = attrs_store;
	      attrs_type = attrs_type_store;
	    }
	  else
	    {
	      attrs = attrs_log;
	      attrs_type = attrs_type_log;
	    }
	  decl = add_builtin_function (d->name, type, code, BUILT_IN_NORMAL,
				       /* The builtin without the prefix for
					  calling it directly.  */
				       d->name + strlen ("__builtin_"),
				       attrs);
	  /* add_builtin_function() will set the DECL_ATTRIBUTES, now
	     set the TYPE_ATTRIBUTES.  */
	  decl_attributes (&TREE_TYPE (decl), attrs_type, ATTR_FLAG_BUILT_IN);

	  set_builtin_decl (code, decl, false);
	}
    }
}

/* Macros for verification of enum ix86_builtins order.  */
#define BDESC_VERIFY(x, y, z) \
  gcc_checking_assert ((x) == (enum ix86_builtins) ((y) + (z)))
#define BDESC_VERIFYS(x, y, z) \
  STATIC_ASSERT ((x) == (enum ix86_builtins) ((y) + (z)))

BDESC_VERIFYS (IX86_BUILTIN__BDESC_PCMPESTR_FIRST,
	       IX86_BUILTIN__BDESC_COMI_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN__BDESC_PCMPISTR_FIRST,
	       IX86_BUILTIN__BDESC_PCMPESTR_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN__BDESC_SPECIAL_ARGS_FIRST,
	       IX86_BUILTIN__BDESC_PCMPISTR_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN__BDESC_ARGS_FIRST,
	       IX86_BUILTIN__BDESC_SPECIAL_ARGS_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN__BDESC_ROUND_ARGS_FIRST,
	       IX86_BUILTIN__BDESC_ARGS_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN__BDESC_MULTI_ARG_FIRST,
	       IX86_BUILTIN__BDESC_ROUND_ARGS_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN__BDESC_CET_FIRST,
	       IX86_BUILTIN__BDESC_MULTI_ARG_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN__BDESC_CET_NORMAL_FIRST,
	       IX86_BUILTIN__BDESC_CET_LAST, 1);
BDESC_VERIFYS (IX86_BUILTIN_MAX,
	       IX86_BUILTIN__BDESC_CET_NORMAL_LAST, 1);

/* Set up all the MMX/SSE builtins, even builtins for instructions that are not
   in the current target ISA to allow the user to compile particular modules
   with different target specific options that differ from the command line
   options.  */
static void
ix86_init_mmx_sse_builtins (void)
{
  const struct builtin_description * d;
  enum ix86_builtin_func_type ftype;
  size_t i;

  /* Add all special builtins with variable number of operands.  */
  for (i = 0, d = bdesc_special_args;
       i < ARRAY_SIZE (bdesc_special_args);
       i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_SPECIAL_ARGS_FIRST, i);
      if (d->name == 0)
	continue;

      ftype = (enum ix86_builtin_func_type) d->flag;
      def_builtin (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_SPECIAL_ARGS_LAST,
		 IX86_BUILTIN__BDESC_SPECIAL_ARGS_FIRST,
		 ARRAY_SIZE (bdesc_special_args) - 1);

  /* Add all builtins with variable number of operands.  */
  for (i = 0, d = bdesc_args;
       i < ARRAY_SIZE (bdesc_args);
       i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_ARGS_FIRST, i);
      if (d->name == 0)
	continue;

      ftype = (enum ix86_builtin_func_type) d->flag;
      def_builtin_const (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_ARGS_LAST,
		 IX86_BUILTIN__BDESC_ARGS_FIRST,
		 ARRAY_SIZE (bdesc_args) - 1);

  /* Add all builtins with rounding.  */
  for (i = 0, d = bdesc_round_args;
       i < ARRAY_SIZE (bdesc_round_args);
       i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_ROUND_ARGS_FIRST, i);
      if (d->name == 0)
	continue;

      ftype = (enum ix86_builtin_func_type) d->flag;
      def_builtin_const (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_ROUND_ARGS_LAST,
		 IX86_BUILTIN__BDESC_ROUND_ARGS_FIRST,
		 ARRAY_SIZE (bdesc_round_args) - 1);

  /* pcmpestr[im] insns.  */
  for (i = 0, d = bdesc_pcmpestr;
       i < ARRAY_SIZE (bdesc_pcmpestr);
       i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_PCMPESTR_FIRST, i);
      if (d->code == IX86_BUILTIN_PCMPESTRM128)
	ftype = V16QI_FTYPE_V16QI_INT_V16QI_INT_INT;
      else
	ftype = INT_FTYPE_V16QI_INT_V16QI_INT_INT;
      def_builtin_const (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_PCMPESTR_LAST,
		 IX86_BUILTIN__BDESC_PCMPESTR_FIRST,
		 ARRAY_SIZE (bdesc_pcmpestr) - 1);

  /* pcmpistr[im] insns.  */
  for (i = 0, d = bdesc_pcmpistr;
       i < ARRAY_SIZE (bdesc_pcmpistr);
       i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_PCMPISTR_FIRST, i);
      if (d->code == IX86_BUILTIN_PCMPISTRM128)
	ftype = V16QI_FTYPE_V16QI_V16QI_INT;
      else
	ftype = INT_FTYPE_V16QI_V16QI_INT;
      def_builtin_const (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_PCMPISTR_LAST,
		 IX86_BUILTIN__BDESC_PCMPISTR_FIRST,
		 ARRAY_SIZE (bdesc_pcmpistr) - 1);

  /* comi/ucomi insns.  */
  for (i = 0, d = bdesc_comi; i < ARRAY_SIZE (bdesc_comi); i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_COMI_FIRST, i);
      if (d->mask == OPTION_MASK_ISA_SSE2)
	ftype = INT_FTYPE_V2DF_V2DF;
      else
	ftype = INT_FTYPE_V4SF_V4SF;
      def_builtin_const (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_COMI_LAST,
		 IX86_BUILTIN__BDESC_COMI_FIRST,
		 ARRAY_SIZE (bdesc_comi) - 1);

  /* SSE */
  def_builtin (OPTION_MASK_ISA_SSE, 0,  "__builtin_ia32_ldmxcsr",
	       VOID_FTYPE_UNSIGNED, IX86_BUILTIN_LDMXCSR);
  def_builtin_pure (OPTION_MASK_ISA_SSE, 0, "__builtin_ia32_stmxcsr",
		    UNSIGNED_FTYPE_VOID, IX86_BUILTIN_STMXCSR);

  /* SSE or 3DNow!A */
  def_builtin (OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A
	       /* As it uses V4HImode, we have to require -mmmx too.  */
	       | OPTION_MASK_ISA_MMX, 0,
	       "__builtin_ia32_maskmovq", VOID_FTYPE_V8QI_V8QI_PCHAR,
	       IX86_BUILTIN_MASKMOVQ);

  /* SSE2 */
  def_builtin (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_maskmovdqu",
	       VOID_FTYPE_V16QI_V16QI_PCHAR, IX86_BUILTIN_MASKMOVDQU);

  def_builtin (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_clflush",
	       VOID_FTYPE_PCVOID, IX86_BUILTIN_CLFLUSH);
  x86_mfence = def_builtin (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_mfence",
			    VOID_FTYPE_VOID, IX86_BUILTIN_MFENCE);

  /* SSE3.  */
  def_builtin (OPTION_MASK_ISA_SSE3, 0, "__builtin_ia32_monitor",
	       VOID_FTYPE_PCVOID_UNSIGNED_UNSIGNED, IX86_BUILTIN_MONITOR);
  def_builtin (OPTION_MASK_ISA_SSE3, 0, "__builtin_ia32_mwait",
	       VOID_FTYPE_UNSIGNED_UNSIGNED, IX86_BUILTIN_MWAIT);

  /* AES */
  def_builtin_const (OPTION_MASK_ISA_AES | OPTION_MASK_ISA_SSE2, 0,
		     "__builtin_ia32_aesenc128",
		     V2DI_FTYPE_V2DI_V2DI, IX86_BUILTIN_AESENC128);
  def_builtin_const (OPTION_MASK_ISA_AES | OPTION_MASK_ISA_SSE2, 0,
		     "__builtin_ia32_aesenclast128",
		     V2DI_FTYPE_V2DI_V2DI, IX86_BUILTIN_AESENCLAST128);
  def_builtin_const (OPTION_MASK_ISA_AES | OPTION_MASK_ISA_SSE2, 0,
		     "__builtin_ia32_aesdec128",
		     V2DI_FTYPE_V2DI_V2DI, IX86_BUILTIN_AESDEC128);
  def_builtin_const (OPTION_MASK_ISA_AES | OPTION_MASK_ISA_SSE2, 0,
		     "__builtin_ia32_aesdeclast128",
		     V2DI_FTYPE_V2DI_V2DI, IX86_BUILTIN_AESDECLAST128);
  def_builtin_const (OPTION_MASK_ISA_AES | OPTION_MASK_ISA_SSE2, 0,
		     "__builtin_ia32_aesimc128",
		     V2DI_FTYPE_V2DI, IX86_BUILTIN_AESIMC128);
  def_builtin_const (OPTION_MASK_ISA_AES | OPTION_MASK_ISA_SSE2, 0,
		     "__builtin_ia32_aeskeygenassist128",
		     V2DI_FTYPE_V2DI_INT, IX86_BUILTIN_AESKEYGENASSIST128);

  /* PCLMUL */
  def_builtin_const (OPTION_MASK_ISA_PCLMUL | OPTION_MASK_ISA_SSE2, 0,
		     "__builtin_ia32_pclmulqdq128",
		     V2DI_FTYPE_V2DI_V2DI_INT, IX86_BUILTIN_PCLMULQDQ128);

  /* RDRND */
  def_builtin (OPTION_MASK_ISA_RDRND, 0, "__builtin_ia32_rdrand16_step",
	       INT_FTYPE_PUSHORT, IX86_BUILTIN_RDRAND16_STEP);
  def_builtin (OPTION_MASK_ISA_RDRND, 0,  "__builtin_ia32_rdrand32_step",
	       INT_FTYPE_PUNSIGNED, IX86_BUILTIN_RDRAND32_STEP);
  def_builtin (OPTION_MASK_ISA_RDRND | OPTION_MASK_ISA_64BIT, 0,
	       "__builtin_ia32_rdrand64_step", INT_FTYPE_PULONGLONG,
	       IX86_BUILTIN_RDRAND64_STEP);

  /* AVX2 */
  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv2df",
		    V2DF_FTYPE_V2DF_PCDOUBLE_V4SI_V2DF_INT,
		    IX86_BUILTIN_GATHERSIV2DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv4df",
		    V4DF_FTYPE_V4DF_PCDOUBLE_V4SI_V4DF_INT,
		    IX86_BUILTIN_GATHERSIV4DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv2df",
		    V2DF_FTYPE_V2DF_PCDOUBLE_V2DI_V2DF_INT,
		    IX86_BUILTIN_GATHERDIV2DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv4df",
		    V4DF_FTYPE_V4DF_PCDOUBLE_V4DI_V4DF_INT,
		    IX86_BUILTIN_GATHERDIV4DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv4sf",
		    V4SF_FTYPE_V4SF_PCFLOAT_V4SI_V4SF_INT,
		    IX86_BUILTIN_GATHERSIV4SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv8sf",
		    V8SF_FTYPE_V8SF_PCFLOAT_V8SI_V8SF_INT,
		    IX86_BUILTIN_GATHERSIV8SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv4sf",
		    V4SF_FTYPE_V4SF_PCFLOAT_V2DI_V4SF_INT,
		    IX86_BUILTIN_GATHERDIV4SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv4sf256",
		    V4SF_FTYPE_V4SF_PCFLOAT_V4DI_V4SF_INT,
		    IX86_BUILTIN_GATHERDIV8SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv2di",
		    V2DI_FTYPE_V2DI_PCINT64_V4SI_V2DI_INT,
		    IX86_BUILTIN_GATHERSIV2DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv4di",
		    V4DI_FTYPE_V4DI_PCINT64_V4SI_V4DI_INT,
		    IX86_BUILTIN_GATHERSIV4DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv2di",
		    V2DI_FTYPE_V2DI_PCINT64_V2DI_V2DI_INT,
		    IX86_BUILTIN_GATHERDIV2DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv4di",
		    V4DI_FTYPE_V4DI_PCINT64_V4DI_V4DI_INT,
		    IX86_BUILTIN_GATHERDIV4DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv4si",
		    V4SI_FTYPE_V4SI_PCINT_V4SI_V4SI_INT,
		    IX86_BUILTIN_GATHERSIV4SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gathersiv8si",
		    V8SI_FTYPE_V8SI_PCINT_V8SI_V8SI_INT,
		    IX86_BUILTIN_GATHERSIV8SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv4si",
		    V4SI_FTYPE_V4SI_PCINT_V2DI_V4SI_INT,
		    IX86_BUILTIN_GATHERDIV4SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatherdiv4si256",
		    V4SI_FTYPE_V4SI_PCINT_V4DI_V4SI_INT,
		    IX86_BUILTIN_GATHERDIV8SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatheraltsiv4df ",
		    V4DF_FTYPE_V4DF_PCDOUBLE_V8SI_V4DF_INT,
		    IX86_BUILTIN_GATHERALTSIV4DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatheraltdiv8sf ",
		    V8SF_FTYPE_V8SF_PCFLOAT_V4DI_V8SF_INT,
		    IX86_BUILTIN_GATHERALTDIV8SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatheraltsiv4di ",
		    V4DI_FTYPE_V4DI_PCINT64_V8SI_V4DI_INT,
		    IX86_BUILTIN_GATHERALTSIV4DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX2, 0, "__builtin_ia32_gatheraltdiv8si ",
		    V8SI_FTYPE_V8SI_PCINT_V4DI_V8SI_INT,
		    IX86_BUILTIN_GATHERALTDIV8SI);

  /* AVX512F */
  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gathersiv16sf",
		    V16SF_FTYPE_V16SF_PCVOID_V16SI_HI_INT,
		    IX86_BUILTIN_GATHER3SIV16SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gathersiv8df",
		    V8DF_FTYPE_V8DF_PCVOID_V8SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV8DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gatherdiv16sf",
		    V8SF_FTYPE_V8SF_PCVOID_V8DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV16SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gatherdiv8df",
		    V8DF_FTYPE_V8DF_PCVOID_V8DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV8DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gathersiv16si",
		    V16SI_FTYPE_V16SI_PCVOID_V16SI_HI_INT,
		    IX86_BUILTIN_GATHER3SIV16SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gathersiv8di",
		    V8DI_FTYPE_V8DI_PCVOID_V8SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV8DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gatherdiv16si",
		    V8SI_FTYPE_V8SI_PCVOID_V8DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV16SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gatherdiv8di",
		    V8DI_FTYPE_V8DI_PCVOID_V8DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV8DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gather3altsiv8df ",
		    V8DF_FTYPE_V8DF_PCDOUBLE_V16SI_QI_INT,
		    IX86_BUILTIN_GATHER3ALTSIV8DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gather3altdiv16sf ",
		    V16SF_FTYPE_V16SF_PCFLOAT_V8DI_HI_INT,
		    IX86_BUILTIN_GATHER3ALTDIV16SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gather3altsiv8di ",
		    V8DI_FTYPE_V8DI_PCINT64_V16SI_QI_INT,
		    IX86_BUILTIN_GATHER3ALTSIV8DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_gather3altdiv16si ",
		    V16SI_FTYPE_V16SI_PCINT_V8DI_HI_INT,
		    IX86_BUILTIN_GATHER3ALTDIV16SI);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scattersiv16sf",
	       VOID_FTYPE_PVOID_HI_V16SI_V16SF_INT,
	       IX86_BUILTIN_SCATTERSIV16SF);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scattersiv8df",
	       VOID_FTYPE_PVOID_QI_V8SI_V8DF_INT,
	       IX86_BUILTIN_SCATTERSIV8DF);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatterdiv16sf",
	       VOID_FTYPE_PVOID_QI_V8DI_V8SF_INT,
	       IX86_BUILTIN_SCATTERDIV16SF);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatterdiv8df",
	       VOID_FTYPE_PVOID_QI_V8DI_V8DF_INT,
	       IX86_BUILTIN_SCATTERDIV8DF);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scattersiv16si",
	       VOID_FTYPE_PVOID_HI_V16SI_V16SI_INT,
	       IX86_BUILTIN_SCATTERSIV16SI);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scattersiv8di",
	       VOID_FTYPE_PVOID_QI_V8SI_V8DI_INT,
	       IX86_BUILTIN_SCATTERSIV8DI);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatterdiv16si",
	       VOID_FTYPE_PVOID_QI_V8DI_V8SI_INT,
	       IX86_BUILTIN_SCATTERDIV16SI);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatterdiv8di",
	       VOID_FTYPE_PVOID_QI_V8DI_V8DI_INT,
	       IX86_BUILTIN_SCATTERDIV8DI);

  /* AVX512VL */
  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv2df",
		    V2DF_FTYPE_V2DF_PCVOID_V4SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV2DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv4df",
		    V4DF_FTYPE_V4DF_PCVOID_V4SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV4DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div2df",
		    V2DF_FTYPE_V2DF_PCVOID_V2DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV2DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div4df",
		    V4DF_FTYPE_V4DF_PCVOID_V4DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV4DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv4sf",
		    V4SF_FTYPE_V4SF_PCVOID_V4SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV4SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv8sf",
		    V8SF_FTYPE_V8SF_PCVOID_V8SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV8SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div4sf",
		    V4SF_FTYPE_V4SF_PCVOID_V2DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV4SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div8sf",
		    V4SF_FTYPE_V4SF_PCVOID_V4DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV8SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv2di",
		    V2DI_FTYPE_V2DI_PCVOID_V4SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV2DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv4di",
		    V4DI_FTYPE_V4DI_PCVOID_V4SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV4DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div2di",
		    V2DI_FTYPE_V2DI_PCVOID_V2DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV2DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div4di",
		    V4DI_FTYPE_V4DI_PCVOID_V4DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV4DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv4si",
		    V4SI_FTYPE_V4SI_PCVOID_V4SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV4SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3siv8si",
		    V8SI_FTYPE_V8SI_PCVOID_V8SI_QI_INT,
		    IX86_BUILTIN_GATHER3SIV8SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div4si",
		    V4SI_FTYPE_V4SI_PCVOID_V2DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV4SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3div8si",
		    V4SI_FTYPE_V4SI_PCVOID_V4DI_QI_INT,
		    IX86_BUILTIN_GATHER3DIV8SI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3altsiv4df ",
		    V4DF_FTYPE_V4DF_PCDOUBLE_V8SI_QI_INT,
		    IX86_BUILTIN_GATHER3ALTSIV4DF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3altdiv8sf ",
		    V8SF_FTYPE_V8SF_PCFLOAT_V4DI_QI_INT,
		    IX86_BUILTIN_GATHER3ALTDIV8SF);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3altsiv4di ",
		    V4DI_FTYPE_V4DI_PCINT64_V8SI_QI_INT,
		    IX86_BUILTIN_GATHER3ALTSIV4DI);

  def_builtin_pure (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_gather3altdiv8si ",
		    V8SI_FTYPE_V8SI_PCINT_V4DI_QI_INT,
		    IX86_BUILTIN_GATHER3ALTDIV8SI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv8sf",
	       VOID_FTYPE_PVOID_QI_V8SI_V8SF_INT,
	       IX86_BUILTIN_SCATTERSIV8SF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv4sf",
	       VOID_FTYPE_PVOID_QI_V4SI_V4SF_INT,
	       IX86_BUILTIN_SCATTERSIV4SF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv4df",
	       VOID_FTYPE_PVOID_QI_V4SI_V4DF_INT,
	       IX86_BUILTIN_SCATTERSIV4DF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv2df",
	       VOID_FTYPE_PVOID_QI_V4SI_V2DF_INT,
	       IX86_BUILTIN_SCATTERSIV2DF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv8sf",
	       VOID_FTYPE_PVOID_QI_V4DI_V4SF_INT,
	       IX86_BUILTIN_SCATTERDIV8SF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv4sf",
	       VOID_FTYPE_PVOID_QI_V2DI_V4SF_INT,
	       IX86_BUILTIN_SCATTERDIV4SF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv4df",
	       VOID_FTYPE_PVOID_QI_V4DI_V4DF_INT,
	       IX86_BUILTIN_SCATTERDIV4DF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv2df",
	       VOID_FTYPE_PVOID_QI_V2DI_V2DF_INT,
	       IX86_BUILTIN_SCATTERDIV2DF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv8si",
	       VOID_FTYPE_PVOID_QI_V8SI_V8SI_INT,
	       IX86_BUILTIN_SCATTERSIV8SI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv4si",
	       VOID_FTYPE_PVOID_QI_V4SI_V4SI_INT,
	       IX86_BUILTIN_SCATTERSIV4SI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv4di",
	       VOID_FTYPE_PVOID_QI_V4SI_V4DI_INT,
	       IX86_BUILTIN_SCATTERSIV4DI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scattersiv2di",
	       VOID_FTYPE_PVOID_QI_V4SI_V2DI_INT,
	       IX86_BUILTIN_SCATTERSIV2DI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv8si",
	       VOID_FTYPE_PVOID_QI_V4DI_V4SI_INT,
	       IX86_BUILTIN_SCATTERDIV8SI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv4si",
	       VOID_FTYPE_PVOID_QI_V2DI_V4SI_INT,
	       IX86_BUILTIN_SCATTERDIV4SI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv4di",
	       VOID_FTYPE_PVOID_QI_V4DI_V4DI_INT,
	       IX86_BUILTIN_SCATTERDIV4DI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatterdiv2di",
	       VOID_FTYPE_PVOID_QI_V2DI_V2DI_INT,
	       IX86_BUILTIN_SCATTERDIV2DI);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatteraltsiv8df ",
	       VOID_FTYPE_PDOUBLE_QI_V16SI_V8DF_INT,
	       IX86_BUILTIN_SCATTERALTSIV8DF);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatteraltdiv16sf ",
	       VOID_FTYPE_PFLOAT_HI_V8DI_V16SF_INT,
	       IX86_BUILTIN_SCATTERALTDIV16SF);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatteraltsiv8di ",
	       VOID_FTYPE_PLONGLONG_QI_V16SI_V8DI_INT,
	       IX86_BUILTIN_SCATTERALTSIV8DI);

  def_builtin (OPTION_MASK_ISA_AVX512F, 0, "__builtin_ia32_scatteraltdiv16si ",
	       VOID_FTYPE_PINT_HI_V8DI_V16SI_INT,
	       IX86_BUILTIN_SCATTERALTDIV16SI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltsiv4df ",
	       VOID_FTYPE_PDOUBLE_QI_V8SI_V4DF_INT,
	       IX86_BUILTIN_SCATTERALTSIV4DF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltdiv8sf ",
	       VOID_FTYPE_PFLOAT_QI_V4DI_V8SF_INT,
	       IX86_BUILTIN_SCATTERALTDIV8SF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltsiv4di ",
	       VOID_FTYPE_PLONGLONG_QI_V8SI_V4DI_INT,
	       IX86_BUILTIN_SCATTERALTSIV4DI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltdiv8si ",
	       VOID_FTYPE_PINT_QI_V4DI_V8SI_INT,
	       IX86_BUILTIN_SCATTERALTDIV8SI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltsiv2df ",
	       VOID_FTYPE_PDOUBLE_QI_V4SI_V2DF_INT,
	       IX86_BUILTIN_SCATTERALTSIV2DF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltdiv4sf ",
	       VOID_FTYPE_PFLOAT_QI_V2DI_V4SF_INT,
	       IX86_BUILTIN_SCATTERALTDIV4SF);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltsiv2di ",
	       VOID_FTYPE_PLONGLONG_QI_V4SI_V2DI_INT,
	       IX86_BUILTIN_SCATTERALTSIV2DI);

  def_builtin (OPTION_MASK_ISA_AVX512VL, 0, "__builtin_ia32_scatteraltdiv4si ",
	       VOID_FTYPE_PINT_QI_V2DI_V4SI_INT,
	       IX86_BUILTIN_SCATTERALTDIV4SI);

  /* AVX512PF */
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_gatherpfdpd",
	       VOID_FTYPE_QI_V8SI_PCVOID_INT_INT,
	       IX86_BUILTIN_GATHERPFDPD);
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_gatherpfdps",
	       VOID_FTYPE_HI_V16SI_PCVOID_INT_INT,
	       IX86_BUILTIN_GATHERPFDPS);
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_gatherpfqpd",
	       VOID_FTYPE_QI_V8DI_PCVOID_INT_INT,
	       IX86_BUILTIN_GATHERPFQPD);
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_gatherpfqps",
	       VOID_FTYPE_QI_V8DI_PCVOID_INT_INT,
	       IX86_BUILTIN_GATHERPFQPS);
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_scatterpfdpd",
	       VOID_FTYPE_QI_V8SI_PCVOID_INT_INT,
	       IX86_BUILTIN_SCATTERPFDPD);
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_scatterpfdps",
	       VOID_FTYPE_HI_V16SI_PCVOID_INT_INT,
	       IX86_BUILTIN_SCATTERPFDPS);
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_scatterpfqpd",
	       VOID_FTYPE_QI_V8DI_PCVOID_INT_INT,
	       IX86_BUILTIN_SCATTERPFQPD);
  def_builtin (OPTION_MASK_ISA_AVX512PF, 0, "__builtin_ia32_scatterpfqps",
	       VOID_FTYPE_QI_V8DI_PCVOID_INT_INT,
	       IX86_BUILTIN_SCATTERPFQPS);

  /* SHA */
  def_builtin_const (OPTION_MASK_ISA_SHA, 0, "__builtin_ia32_sha1msg1",
		     V4SI_FTYPE_V4SI_V4SI, IX86_BUILTIN_SHA1MSG1);
  def_builtin_const (OPTION_MASK_ISA_SHA, 0, "__builtin_ia32_sha1msg2",
		     V4SI_FTYPE_V4SI_V4SI, IX86_BUILTIN_SHA1MSG2);
  def_builtin_const (OPTION_MASK_ISA_SHA, 0, "__builtin_ia32_sha1nexte",
		     V4SI_FTYPE_V4SI_V4SI, IX86_BUILTIN_SHA1NEXTE);
  def_builtin_const (OPTION_MASK_ISA_SHA, 0, "__builtin_ia32_sha1rnds4",
		     V4SI_FTYPE_V4SI_V4SI_INT, IX86_BUILTIN_SHA1RNDS4);
  def_builtin_const (OPTION_MASK_ISA_SHA, 0, "__builtin_ia32_sha256msg1",
		     V4SI_FTYPE_V4SI_V4SI, IX86_BUILTIN_SHA256MSG1);
  def_builtin_const (OPTION_MASK_ISA_SHA, 0, "__builtin_ia32_sha256msg2",
		     V4SI_FTYPE_V4SI_V4SI, IX86_BUILTIN_SHA256MSG2);
  def_builtin_const (OPTION_MASK_ISA_SHA, 0, "__builtin_ia32_sha256rnds2",
		     V4SI_FTYPE_V4SI_V4SI_V4SI, IX86_BUILTIN_SHA256RNDS2);

  /* RTM.  */
  def_builtin (OPTION_MASK_ISA_RTM, 0, "__builtin_ia32_xabort",
	       VOID_FTYPE_UNSIGNED, IX86_BUILTIN_XABORT);

  /* MMX access to the vec_init patterns.  */
  def_builtin_const (OPTION_MASK_ISA_MMX, 0, "__builtin_ia32_vec_init_v2si",
		     V2SI_FTYPE_INT_INT, IX86_BUILTIN_VEC_INIT_V2SI);

  def_builtin_const (OPTION_MASK_ISA_MMX, 0, "__builtin_ia32_vec_init_v4hi",
		     V4HI_FTYPE_HI_HI_HI_HI,
		     IX86_BUILTIN_VEC_INIT_V4HI);

  def_builtin_const (OPTION_MASK_ISA_MMX, 0, "__builtin_ia32_vec_init_v8qi",
		     V8QI_FTYPE_QI_QI_QI_QI_QI_QI_QI_QI,
		     IX86_BUILTIN_VEC_INIT_V8QI);

  /* Access to the vec_extract patterns.  */
  def_builtin_const (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_vec_ext_v2df",
		     DOUBLE_FTYPE_V2DF_INT, IX86_BUILTIN_VEC_EXT_V2DF);
  def_builtin_const (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_vec_ext_v2di",
		     DI_FTYPE_V2DI_INT, IX86_BUILTIN_VEC_EXT_V2DI);
  def_builtin_const (OPTION_MASK_ISA_SSE, 0, "__builtin_ia32_vec_ext_v4sf",
		     FLOAT_FTYPE_V4SF_INT, IX86_BUILTIN_VEC_EXT_V4SF);
  def_builtin_const (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_vec_ext_v4si",
		     SI_FTYPE_V4SI_INT, IX86_BUILTIN_VEC_EXT_V4SI);
  def_builtin_const (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_vec_ext_v8hi",
		     HI_FTYPE_V8HI_INT, IX86_BUILTIN_VEC_EXT_V8HI);

  def_builtin_const (OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A
		     /* As it uses V4HImode, we have to require -mmmx too.  */
		     | OPTION_MASK_ISA_MMX, 0,
		     "__builtin_ia32_vec_ext_v4hi",
		     HI_FTYPE_V4HI_INT, IX86_BUILTIN_VEC_EXT_V4HI);

  def_builtin_const (OPTION_MASK_ISA_MMX, 0, "__builtin_ia32_vec_ext_v2si",
		     SI_FTYPE_V2SI_INT, IX86_BUILTIN_VEC_EXT_V2SI);

  def_builtin_const (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_vec_ext_v16qi",
		     QI_FTYPE_V16QI_INT, IX86_BUILTIN_VEC_EXT_V16QI);

  /* Access to the vec_set patterns.  */
  def_builtin_const (OPTION_MASK_ISA_SSE4_1 | OPTION_MASK_ISA_64BIT, 0,
		     "__builtin_ia32_vec_set_v2di",
		     V2DI_FTYPE_V2DI_DI_INT, IX86_BUILTIN_VEC_SET_V2DI);

  def_builtin_const (OPTION_MASK_ISA_SSE4_1, 0, "__builtin_ia32_vec_set_v4sf",
		     V4SF_FTYPE_V4SF_FLOAT_INT, IX86_BUILTIN_VEC_SET_V4SF);

  def_builtin_const (OPTION_MASK_ISA_SSE4_1, 0, "__builtin_ia32_vec_set_v4si",
		     V4SI_FTYPE_V4SI_SI_INT, IX86_BUILTIN_VEC_SET_V4SI);

  def_builtin_const (OPTION_MASK_ISA_SSE2, 0, "__builtin_ia32_vec_set_v8hi",
		     V8HI_FTYPE_V8HI_HI_INT, IX86_BUILTIN_VEC_SET_V8HI);

  def_builtin_const (OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A
		     /* As it uses V4HImode, we have to require -mmmx too.  */
		     | OPTION_MASK_ISA_MMX, 0,
		     "__builtin_ia32_vec_set_v4hi",
		     V4HI_FTYPE_V4HI_HI_INT, IX86_BUILTIN_VEC_SET_V4HI);

  def_builtin_const (OPTION_MASK_ISA_SSE4_1, 0, "__builtin_ia32_vec_set_v16qi",
		     V16QI_FTYPE_V16QI_QI_INT, IX86_BUILTIN_VEC_SET_V16QI);

  /* RDSEED */
  def_builtin (OPTION_MASK_ISA_RDSEED, 0, "__builtin_ia32_rdseed_hi_step",
	       INT_FTYPE_PUSHORT, IX86_BUILTIN_RDSEED16_STEP);
  def_builtin (OPTION_MASK_ISA_RDSEED, 0, "__builtin_ia32_rdseed_si_step",
	       INT_FTYPE_PUNSIGNED, IX86_BUILTIN_RDSEED32_STEP);
  def_builtin (OPTION_MASK_ISA_RDSEED | OPTION_MASK_ISA_64BIT, 0,
	       "__builtin_ia32_rdseed_di_step",
	       INT_FTYPE_PULONGLONG, IX86_BUILTIN_RDSEED64_STEP);

  /* ADCX */
  def_builtin (0, 0, "__builtin_ia32_addcarryx_u32",
	       UCHAR_FTYPE_UCHAR_UINT_UINT_PUNSIGNED, IX86_BUILTIN_ADDCARRYX32);
  def_builtin (OPTION_MASK_ISA_64BIT, 0,
	       "__builtin_ia32_addcarryx_u64",
	       UCHAR_FTYPE_UCHAR_ULONGLONG_ULONGLONG_PULONGLONG,
	       IX86_BUILTIN_ADDCARRYX64);

  /* SBB */
  def_builtin (0, 0, "__builtin_ia32_sbb_u32",
	       UCHAR_FTYPE_UCHAR_UINT_UINT_PUNSIGNED, IX86_BUILTIN_SBB32);
  def_builtin (OPTION_MASK_ISA_64BIT, 0,
	       "__builtin_ia32_sbb_u64",
	       UCHAR_FTYPE_UCHAR_ULONGLONG_ULONGLONG_PULONGLONG,
	       IX86_BUILTIN_SBB64);

  /* Read/write FLAGS.  */
  if (TARGET_64BIT)
    {
      def_builtin (OPTION_MASK_ISA_64BIT, 0, "__builtin_ia32_readeflags_u64",
		   UINT64_FTYPE_VOID, IX86_BUILTIN_READ_FLAGS);
      def_builtin (OPTION_MASK_ISA_64BIT, 0, "__builtin_ia32_writeeflags_u64",
		   VOID_FTYPE_UINT64, IX86_BUILTIN_WRITE_FLAGS);
    }
  else
    {
      def_builtin (0, 0, "__builtin_ia32_readeflags_u32",
		   UNSIGNED_FTYPE_VOID, IX86_BUILTIN_READ_FLAGS);
      def_builtin (0, 0, "__builtin_ia32_writeeflags_u32",
		   VOID_FTYPE_UNSIGNED, IX86_BUILTIN_WRITE_FLAGS);
    }

  /* CLFLUSHOPT.  */
  def_builtin (OPTION_MASK_ISA_CLFLUSHOPT, 0, "__builtin_ia32_clflushopt",
	       VOID_FTYPE_PCVOID, IX86_BUILTIN_CLFLUSHOPT);

  /* CLWB.  */
  def_builtin (OPTION_MASK_ISA_CLWB, 0, "__builtin_ia32_clwb",
	       VOID_FTYPE_PCVOID, IX86_BUILTIN_CLWB);

  /* MONITORX and MWAITX.  */
  def_builtin (0, OPTION_MASK_ISA_MWAITX, "__builtin_ia32_monitorx",
		VOID_FTYPE_PCVOID_UNSIGNED_UNSIGNED, IX86_BUILTIN_MONITORX);
  def_builtin (0, OPTION_MASK_ISA_MWAITX, "__builtin_ia32_mwaitx",
		VOID_FTYPE_UNSIGNED_UNSIGNED_UNSIGNED, IX86_BUILTIN_MWAITX);

  /* CLZERO.  */
  def_builtin (0, OPTION_MASK_ISA_CLZERO, "__builtin_ia32_clzero",
		VOID_FTYPE_PCVOID, IX86_BUILTIN_CLZERO);

  /* WAITPKG.  */
  def_builtin (0, OPTION_MASK_ISA_WAITPKG, "__builtin_ia32_umonitor",
	       VOID_FTYPE_PVOID, IX86_BUILTIN_UMONITOR);
  def_builtin (0, OPTION_MASK_ISA_WAITPKG, "__builtin_ia32_umwait",
	       UINT8_FTYPE_UNSIGNED_UINT64, IX86_BUILTIN_UMWAIT);
  def_builtin (0, OPTION_MASK_ISA_WAITPKG, "__builtin_ia32_tpause",
	       UINT8_FTYPE_UNSIGNED_UINT64, IX86_BUILTIN_TPAUSE);

  /* CLDEMOTE.  */
  def_builtin (0, OPTION_MASK_ISA_CLDEMOTE, "__builtin_ia32_cldemote",
	       VOID_FTYPE_PCVOID, IX86_BUILTIN_CLDEMOTE);

  /* Add FMA4 multi-arg argument instructions */
  for (i = 0, d = bdesc_multi_arg; i < ARRAY_SIZE (bdesc_multi_arg); i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_MULTI_ARG_FIRST, i);
      if (d->name == 0)
	continue;

      ftype = (enum ix86_builtin_func_type) d->flag;
      def_builtin_const (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_MULTI_ARG_LAST,
		 IX86_BUILTIN__BDESC_MULTI_ARG_FIRST,
		 ARRAY_SIZE (bdesc_multi_arg) - 1);

  /* Add CET inrinsics.  */
  for (i = 0, d = bdesc_cet; i < ARRAY_SIZE (bdesc_cet); i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_CET_FIRST, i);
      if (d->name == 0)
	continue;

      ftype = (enum ix86_builtin_func_type) d->flag;
      def_builtin (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_CET_LAST,
		 IX86_BUILTIN__BDESC_CET_FIRST,
		 ARRAY_SIZE (bdesc_cet) - 1);

  for (i = 0, d = bdesc_cet_rdssp;
       i < ARRAY_SIZE (bdesc_cet_rdssp);
       i++, d++)
    {
      BDESC_VERIFY (d->code, IX86_BUILTIN__BDESC_CET_NORMAL_FIRST, i);
      if (d->name == 0)
	continue;

      ftype = (enum ix86_builtin_func_type) d->flag;
      def_builtin (d->mask, d->mask2, d->name, ftype, d->code);
    }
  BDESC_VERIFYS (IX86_BUILTIN__BDESC_CET_NORMAL_LAST,
		 IX86_BUILTIN__BDESC_CET_NORMAL_FIRST,
		 ARRAY_SIZE (bdesc_cet_rdssp) - 1);
}

#undef BDESC_VERIFY
#undef BDESC_VERIFYS

/* This adds a condition to the basic_block NEW_BB in function FUNCTION_DECL
   to return a pointer to VERSION_DECL if the outcome of the expression
   formed by PREDICATE_CHAIN is true.  This function will be called during
   version dispatch to decide which function version to execute.  It returns
   the basic block at the end, to which more conditions can be added.  */

static basic_block
add_condition_to_bb (tree function_decl, tree version_decl,
		     tree predicate_chain, basic_block new_bb)
{
  gimple *return_stmt;
  tree convert_expr, result_var;
  gimple *convert_stmt;
  gimple *call_cond_stmt;
  gimple *if_else_stmt;

  basic_block bb1, bb2, bb3;
  edge e12, e23;

  tree cond_var, and_expr_var = NULL_TREE;
  gimple_seq gseq;

  tree predicate_decl, predicate_arg;

  push_cfun (DECL_STRUCT_FUNCTION (function_decl));

  gcc_assert (new_bb != NULL);
  gseq = bb_seq (new_bb);


  convert_expr = build1 (CONVERT_EXPR, ptr_type_node,
	     		 build_fold_addr_expr (version_decl));
  result_var = create_tmp_var (ptr_type_node);
  convert_stmt = gimple_build_assign (result_var, convert_expr); 
  return_stmt = gimple_build_return (result_var);

  if (predicate_chain == NULL_TREE)
    {
      gimple_seq_add_stmt (&gseq, convert_stmt);
      gimple_seq_add_stmt (&gseq, return_stmt);
      set_bb_seq (new_bb, gseq);
      gimple_set_bb (convert_stmt, new_bb);
      gimple_set_bb (return_stmt, new_bb);
      pop_cfun ();
      return new_bb;
    }

  while (predicate_chain != NULL)
    {
      cond_var = create_tmp_var (integer_type_node);
      predicate_decl = TREE_PURPOSE (predicate_chain);
      predicate_arg = TREE_VALUE (predicate_chain);
      call_cond_stmt = gimple_build_call (predicate_decl, 1, predicate_arg);
      gimple_call_set_lhs (call_cond_stmt, cond_var);

      gimple_set_block (call_cond_stmt, DECL_INITIAL (function_decl));
      gimple_set_bb (call_cond_stmt, new_bb);
      gimple_seq_add_stmt (&gseq, call_cond_stmt);

      predicate_chain = TREE_CHAIN (predicate_chain);
      
      if (and_expr_var == NULL)
        and_expr_var = cond_var;
      else
	{
	  gimple *assign_stmt;
	  /* Use MIN_EXPR to check if any integer is zero?.
	     and_expr_var = min_expr <cond_var, and_expr_var>  */
	  assign_stmt = gimple_build_assign (and_expr_var,
			  build2 (MIN_EXPR, integer_type_node,
				  cond_var, and_expr_var));

	  gimple_set_block (assign_stmt, DECL_INITIAL (function_decl));
	  gimple_set_bb (assign_stmt, new_bb);
	  gimple_seq_add_stmt (&gseq, assign_stmt);
	}
    }

  if_else_stmt = gimple_build_cond (GT_EXPR, and_expr_var,
	  		            integer_zero_node,
				    NULL_TREE, NULL_TREE);
  gimple_set_block (if_else_stmt, DECL_INITIAL (function_decl));
  gimple_set_bb (if_else_stmt, new_bb);
  gimple_seq_add_stmt (&gseq, if_else_stmt);

  gimple_seq_add_stmt (&gseq, convert_stmt);
  gimple_seq_add_stmt (&gseq, return_stmt);
  set_bb_seq (new_bb, gseq);

  bb1 = new_bb;
  e12 = split_block (bb1, if_else_stmt);
  bb2 = e12->dest;
  e12->flags &= ~EDGE_FALLTHRU;
  e12->flags |= EDGE_TRUE_VALUE;

  e23 = split_block (bb2, return_stmt);

  gimple_set_bb (convert_stmt, bb2);
  gimple_set_bb (return_stmt, bb2);

  bb3 = e23->dest;
  make_edge (bb1, bb3, EDGE_FALSE_VALUE); 

  remove_edge (e23);
  make_edge (bb2, EXIT_BLOCK_PTR_FOR_FN (cfun), 0);

  pop_cfun ();

  return bb3;
}

/* This parses the attribute arguments to target in DECL and determines
   the right builtin to use to match the platform specification.
   It returns the priority value for this version decl.  If PREDICATE_LIST
   is not NULL, it stores the list of cpu features that need to be checked
   before dispatching this function.  */

static unsigned int
get_builtin_code_for_version (tree decl, tree *predicate_list)
{
  tree attrs;
  struct cl_target_option cur_target;
  tree target_node;
  struct cl_target_option *new_target;
  const char *arg_str = NULL;
  const char *attrs_str = NULL;
  char *tok_str = NULL;
  char *token;

  /* Priority of i386 features, greater value is higher priority.   This is
     used to decide the order in which function dispatch must happen.  For
     instance, a version specialized for SSE4.2 should be checked for dispatch
     before a version for SSE3, as SSE4.2 implies SSE3.  */
  enum feature_priority
  {
    P_ZERO = 0,
    P_MMX,
    P_SSE,
    P_SSE2,
    P_SSE3,
    P_SSSE3,
    P_PROC_SSSE3,
    P_SSE4_A,
    P_PROC_SSE4_A,
    P_SSE4_1,
    P_SSE4_2,
    P_PROC_SSE4_2,
    P_POPCNT,
    P_AES,
    P_PCLMUL,
    P_AVX,
    P_PROC_AVX,
    P_BMI,
    P_PROC_BMI,
    P_FMA4,
    P_XOP,
    P_PROC_XOP,
    P_FMA,    
    P_PROC_FMA,
    P_BMI2,
    P_AVX2,
    P_PROC_AVX2,
    P_AVX512F,
    P_PROC_AVX512F
  };

  enum feature_priority priority = P_ZERO;

  /* These are the target attribute strings for which a dispatcher is
     available, from fold_builtin_cpu.  */

  static struct _feature_list
    {
      const char *const name;
      const enum feature_priority priority;
    }
  const feature_list[] =
    {
      {"mmx", P_MMX},
      {"sse", P_SSE},
      {"sse2", P_SSE2},
      {"sse3", P_SSE3},
      {"sse4a", P_SSE4_A},
      {"ssse3", P_SSSE3},
      {"sse4.1", P_SSE4_1},
      {"sse4.2", P_SSE4_2},
      {"popcnt", P_POPCNT},
      {"aes", P_AES},
      {"pclmul", P_PCLMUL},
      {"avx", P_AVX},
      {"bmi", P_BMI},
      {"fma4", P_FMA4},
      {"xop", P_XOP},
      {"fma", P_FMA},
      {"bmi2", P_BMI2},
      {"avx2", P_AVX2},
      {"avx512f", P_AVX512F}
    };


  static unsigned int NUM_FEATURES
    = sizeof (feature_list) / sizeof (struct _feature_list);

  unsigned int i;

  tree predicate_chain = NULL_TREE;
  tree predicate_decl, predicate_arg;

  attrs = lookup_attribute ("target", DECL_ATTRIBUTES (decl));
  gcc_assert (attrs != NULL);

  attrs = TREE_VALUE (TREE_VALUE (attrs));

  gcc_assert (TREE_CODE (attrs) == STRING_CST);
  attrs_str = TREE_STRING_POINTER (attrs);

  /* Return priority zero for default function.  */
  if (strcmp (attrs_str, "default") == 0)
    return 0;

  /* Handle arch= if specified.  For priority, set it to be 1 more than
     the best instruction set the processor can handle.  For instance, if
     there is a version for atom and a version for ssse3 (the highest ISA
     priority for atom), the atom version must be checked for dispatch
     before the ssse3 version. */
  if (strstr (attrs_str, "arch=") != NULL)
    {
      cl_target_option_save (&cur_target, &global_options);
      target_node = ix86_valid_target_attribute_tree (attrs, &global_options,
						      &global_options_set);
    
      gcc_assert (target_node);
      if (target_node == error_mark_node)
	return 0;
      new_target = TREE_TARGET_OPTION (target_node);
      gcc_assert (new_target);
      
      if (new_target->arch_specified && new_target->arch > 0)
	{
	  switch (new_target->arch)
	    {
	    case PROCESSOR_CORE2:
	      arg_str = "core2";
	      priority = P_PROC_SSSE3;
	      break;
	    case PROCESSOR_NEHALEM:
	      if (new_target->x_ix86_isa_flags & OPTION_MASK_ISA_AES)
		{
		  arg_str = "westmere";
		  priority = P_AES;
		}
	      else
		{
		  /* We translate "arch=corei7" and "arch=nehalem" to
		     "corei7" so that it will be mapped to M_INTEL_COREI7
		     as cpu type to cover all M_INTEL_COREI7_XXXs.  */
		  arg_str = "corei7";
		  priority = P_PROC_SSE4_2;
		}
	      break;
	    case PROCESSOR_SANDYBRIDGE:
	      if (new_target->x_ix86_isa_flags & OPTION_MASK_ISA_F16C)
		arg_str = "ivybridge";
	      else
		arg_str = "sandybridge";
	      priority = P_PROC_AVX;
	      break;
	    case PROCESSOR_HASWELL:
	      if (new_target->x_ix86_isa_flags & OPTION_MASK_ISA_ADX)
		arg_str = "broadwell";
	      else
		arg_str = "haswell";
	      priority = P_PROC_AVX2;
	      break;
	    case PROCESSOR_SKYLAKE:
	      arg_str = "skylake";
	      priority = P_PROC_AVX2;
	      break;
	    case PROCESSOR_SKYLAKE_AVX512:
	      arg_str = "skylake-avx512";
	      priority = P_PROC_AVX512F;
	      break;
	    case PROCESSOR_CANNONLAKE:
	      arg_str = "cannonlake";
	      priority = P_PROC_AVX512F;
	      break;
	    case PROCESSOR_ICELAKE_CLIENT:
	      arg_str = "icelake-client";
	      priority = P_PROC_AVX512F;
	      break;
	    case PROCESSOR_ICELAKE_SERVER:
	      arg_str = "icelake-server";
	      priority = P_PROC_AVX512F;
	      break;
	    case PROCESSOR_CASCADELAKE:
	      arg_str = "cascadelake";
	      priority = P_PROC_AVX512F;
	      break;
	    case PROCESSOR_BONNELL:
	      arg_str = "bonnell";
	      priority = P_PROC_SSSE3;
	      break;
	    case PROCESSOR_KNL:
	      arg_str = "knl";
	      priority = P_PROC_AVX512F;
	      break;
	    case PROCESSOR_KNM:
	      arg_str = "knm";
	      priority = P_PROC_AVX512F;
	      break;
	    case PROCESSOR_SILVERMONT:
	      arg_str = "silvermont";
	      priority = P_PROC_SSE4_2;
	      break;
	    case PROCESSOR_GOLDMONT:
	      arg_str = "goldmont";
	      priority = P_PROC_SSE4_2;
	      break;
	    case PROCESSOR_GOLDMONT_PLUS:
	      arg_str = "goldmont-plus";
	      priority = P_PROC_SSE4_2;
	      break;
	    case PROCESSOR_TREMONT:
	      arg_str = "tremont";
	      priority = P_PROC_SSE4_2;
	      break;
	    case PROCESSOR_AMDFAM10:
	      arg_str = "amdfam10h";
	      priority = P_PROC_SSE4_A;
	      break;
	    case PROCESSOR_BTVER1:
	      arg_str = "btver1";
	      priority = P_PROC_SSE4_A;
	      break;
	    case PROCESSOR_BTVER2:
	      arg_str = "btver2";
	      priority = P_PROC_BMI;
	      break;
	    case PROCESSOR_BDVER1:
	      arg_str = "bdver1";
	      priority = P_PROC_XOP;
	      break;
	    case PROCESSOR_BDVER2:
	      arg_str = "bdver2";
	      priority = P_PROC_FMA;
	      break;
	    case PROCESSOR_BDVER3:
	      arg_str = "bdver3";
	      priority = P_PROC_FMA;
	      break;
	    case PROCESSOR_BDVER4:
	      arg_str = "bdver4";
	      priority = P_PROC_AVX2;
	      break;
	    case PROCESSOR_ZNVER1:
	      arg_str = "znver1";
	      priority = P_PROC_AVX2;
	      break;
	    case PROCESSOR_ZNVER2:
	      arg_str = "znver2";
	      priority = P_PROC_AVX2;
	      break;
	    }
	}

      cl_target_option_restore (&global_options, &cur_target);
	
      if (predicate_list && arg_str == NULL)
	{
	  error_at (DECL_SOURCE_LOCATION (decl),
	    	"No dispatcher found for the versioning attributes");
	  return 0;
	}
    
      if (predicate_list)
	{
          predicate_decl = ix86_builtins [(int) IX86_BUILTIN_CPU_IS];
          /* For a C string literal the length includes the trailing NULL.  */
          predicate_arg = build_string_literal (strlen (arg_str) + 1, arg_str);
          predicate_chain = tree_cons (predicate_decl, predicate_arg,
				       predicate_chain);
	}
    }

  /* Process feature name.  */
  tok_str =  (char *) xmalloc (strlen (attrs_str) + 1);
  strcpy (tok_str, attrs_str);
  token = strtok (tok_str, ",");
  predicate_decl = ix86_builtins [(int) IX86_BUILTIN_CPU_SUPPORTS];

  while (token != NULL)
    {
      /* Do not process "arch="  */
      if (strncmp (token, "arch=", 5) == 0)
	{
	  token = strtok (NULL, ",");
	  continue;
	}
      for (i = 0; i < NUM_FEATURES; ++i)
	{
	  if (strcmp (token, feature_list[i].name) == 0)
	    {
	      if (predicate_list)
		{
		  predicate_arg = build_string_literal (
				  strlen (feature_list[i].name) + 1,
				  feature_list[i].name);
		  predicate_chain = tree_cons (predicate_decl, predicate_arg,
					       predicate_chain);
		}
	      /* Find the maximum priority feature.  */
	      if (feature_list[i].priority > priority)
		priority = feature_list[i].priority;

	      break;
	    }
	}
      if (predicate_list && i == NUM_FEATURES)
	{
	  error_at (DECL_SOURCE_LOCATION (decl),
		    "No dispatcher found for %s", token);
	  return 0;
	}
      token = strtok (NULL, ",");
    }
  free (tok_str);

  if (predicate_list && predicate_chain == NULL_TREE)
    {
      error_at (DECL_SOURCE_LOCATION (decl),
	        "No dispatcher found for the versioning attributes : %s",
	        attrs_str);
      return 0;
    }
  else if (predicate_list)
    {
      predicate_chain = nreverse (predicate_chain);
      *predicate_list = predicate_chain;
    }

  return priority; 
}

/* This compares the priority of target features in function DECL1
   and DECL2.  It returns positive value if DECL1 is higher priority,
   negative value if DECL2 is higher priority and 0 if they are the
   same.  */

static int
ix86_compare_version_priority (tree decl1, tree decl2)
{
  unsigned int priority1 = get_builtin_code_for_version (decl1, NULL);
  unsigned int priority2 = get_builtin_code_for_version (decl2, NULL);

  return (int)priority1 - (int)priority2;
}

/* V1 and V2 point to function versions with different priorities
   based on the target ISA.  This function compares their priorities.  */
 
static int
feature_compare (const void *v1, const void *v2)
{
  typedef struct _function_version_info
    {
      tree version_decl;
      tree predicate_chain;
      unsigned int dispatch_priority;
    } function_version_info;

  const function_version_info c1 = *(const function_version_info *)v1;
  const function_version_info c2 = *(const function_version_info *)v2;
  return (c2.dispatch_priority - c1.dispatch_priority);
}

/* This function generates the dispatch function for
   multi-versioned functions.  DISPATCH_DECL is the function which will
   contain the dispatch logic.  FNDECLS are the function choices for
   dispatch, and is a tree chain.  EMPTY_BB is the basic block pointer
   in DISPATCH_DECL in which the dispatch code is generated.  */

static int
dispatch_function_versions (tree dispatch_decl,
			    void *fndecls_p,
			    basic_block *empty_bb)
{
  tree default_decl;
  gimple *ifunc_cpu_init_stmt;
  gimple_seq gseq;
  int ix;
  tree ele;
  vec<tree> *fndecls;
  unsigned int num_versions = 0;
  unsigned int actual_versions = 0;
  unsigned int i;

  struct _function_version_info
    {
      tree version_decl;
      tree predicate_chain;
      unsigned int dispatch_priority;
    }*function_version_info;

  gcc_assert (dispatch_decl != NULL
	      && fndecls_p != NULL
	      && empty_bb != NULL);

  /*fndecls_p is actually a vector.  */
  fndecls = static_cast<vec<tree> *> (fndecls_p);

  /* At least one more version other than the default.  */
  num_versions = fndecls->length ();
  gcc_assert (num_versions >= 2);

  function_version_info = (struct _function_version_info *)
    XNEWVEC (struct _function_version_info, (num_versions - 1));

  /* The first version in the vector is the default decl.  */
  default_decl = (*fndecls)[0];

  push_cfun (DECL_STRUCT_FUNCTION (dispatch_decl));

  gseq = bb_seq (*empty_bb);
  /* Function version dispatch is via IFUNC.  IFUNC resolvers fire before
     constructors, so explicity call __builtin_cpu_init here.  */
  ifunc_cpu_init_stmt = gimple_build_call_vec (
                     ix86_builtins [(int) IX86_BUILTIN_CPU_INIT], vNULL);
  gimple_seq_add_stmt (&gseq, ifunc_cpu_init_stmt);
  gimple_set_bb (ifunc_cpu_init_stmt, *empty_bb);
  set_bb_seq (*empty_bb, gseq);

  pop_cfun ();


  for (ix = 1; fndecls->iterate (ix, &ele); ++ix)
    {
      tree version_decl = ele;
      tree predicate_chain = NULL_TREE;
      unsigned int priority;
      /* Get attribute string, parse it and find the right predicate decl.
         The predicate function could be a lengthy combination of many
	 features, like arch-type and various isa-variants.  */
      priority = get_builtin_code_for_version (version_decl,
	 			               &predicate_chain);

      if (predicate_chain == NULL_TREE)
	continue;

      function_version_info [actual_versions].version_decl = version_decl;
      function_version_info [actual_versions].predicate_chain
	 = predicate_chain;
      function_version_info [actual_versions].dispatch_priority = priority;
      actual_versions++;
    }

  /* Sort the versions according to descending order of dispatch priority.  The
     priority is based on the ISA.  This is not a perfect solution.  There
     could still be ambiguity.  If more than one function version is suitable
     to execute,  which one should be dispatched?  In future, allow the user
     to specify a dispatch  priority next to the version.  */
  qsort (function_version_info, actual_versions,
         sizeof (struct _function_version_info), feature_compare);

  for  (i = 0; i < actual_versions; ++i)
    *empty_bb = add_condition_to_bb (dispatch_decl,
				     function_version_info[i].version_decl,
				     function_version_info[i].predicate_chain,
				     *empty_bb);

  /* dispatch default version at the end.  */
  *empty_bb = add_condition_to_bb (dispatch_decl, default_decl,
				   NULL, *empty_bb);

  free (function_version_info);
  return 0;
}

/* This function changes the assembler name for functions that are
   versions.  If DECL is a function version and has a "target"
   attribute, it appends the attribute string to its assembler name.  */

static tree
ix86_mangle_function_version_assembler_name (tree decl, tree id)
{
  tree version_attr;
  const char *orig_name, *version_string;
  char *attr_str, *assembler_name;

  if (DECL_DECLARED_INLINE_P (decl)
      && lookup_attribute ("gnu_inline",
			   DECL_ATTRIBUTES (decl)))
    error_at (DECL_SOURCE_LOCATION (decl),
	      "Function versions cannot be marked as gnu_inline,"
	      " bodies have to be generated");

  if (DECL_VIRTUAL_P (decl)
      || DECL_VINDEX (decl))
    sorry ("Virtual function multiversioning not supported");

  version_attr = lookup_attribute ("target", DECL_ATTRIBUTES (decl));

  /* target attribute string cannot be NULL.  */
  gcc_assert (version_attr != NULL_TREE);

  orig_name = IDENTIFIER_POINTER (id);
  version_string
    = TREE_STRING_POINTER (TREE_VALUE (TREE_VALUE (version_attr)));

  if (strcmp (version_string, "default") == 0)
    return id;

  attr_str = sorted_attr_string (TREE_VALUE (version_attr));
  assembler_name = XNEWVEC (char, strlen (orig_name) + strlen (attr_str) + 2);

  sprintf (assembler_name, "%s.%s", orig_name, attr_str);

  /* Allow assembler name to be modified if already set.  */
  if (DECL_ASSEMBLER_NAME_SET_P (decl))
    SET_DECL_RTL (decl, NULL);

  tree ret = get_identifier (assembler_name);
  XDELETEVEC (attr_str);
  XDELETEVEC (assembler_name);
  return ret;
}


static tree 
ix86_mangle_decl_assembler_name (tree decl, tree id)
{
  /* For function version, add the target suffix to the assembler name.  */
  if (TREE_CODE (decl) == FUNCTION_DECL
      && DECL_FUNCTION_VERSIONED (decl))
    id = ix86_mangle_function_version_assembler_name (decl, id);
#ifdef SUBTARGET_MANGLE_DECL_ASSEMBLER_NAME
  id = SUBTARGET_MANGLE_DECL_ASSEMBLER_NAME (decl, id);
#endif

  return id;
}

/* Make a dispatcher declaration for the multi-versioned function DECL.
   Calls to DECL function will be replaced with calls to the dispatcher
   by the front-end.  Returns the decl of the dispatcher function.  */

static tree
ix86_get_function_versions_dispatcher (void *decl)
{
  tree fn = (tree) decl;
  struct cgraph_node *node = NULL;
  struct cgraph_node *default_node = NULL;
  struct cgraph_function_version_info *node_v = NULL;
  struct cgraph_function_version_info *first_v = NULL;

  tree dispatch_decl = NULL;

  struct cgraph_function_version_info *default_version_info = NULL;
 
  gcc_assert (fn != NULL && DECL_FUNCTION_VERSIONED (fn));

  node = cgraph_node::get (fn);
  gcc_assert (node != NULL);

  node_v = node->function_version ();
  gcc_assert (node_v != NULL);
 
  if (node_v->dispatcher_resolver != NULL)
    return node_v->dispatcher_resolver;

  /* Find the default version and make it the first node.  */
  first_v = node_v;
  /* Go to the beginning of the chain.  */
  while (first_v->prev != NULL)
    first_v = first_v->prev;
  default_version_info = first_v;
  while (default_version_info != NULL)
    {
      if (is_function_default_version
	    (default_version_info->this_node->decl))
        break;
      default_version_info = default_version_info->next;
    }

  /* If there is no default node, just return NULL.  */
  if (default_version_info == NULL)
    return NULL;

  /* Make default info the first node.  */
  if (first_v != default_version_info)
    {
      default_version_info->prev->next = default_version_info->next;
      if (default_version_info->next)
        default_version_info->next->prev = default_version_info->prev;
      first_v->prev = default_version_info;
      default_version_info->next = first_v;
      default_version_info->prev = NULL;
    }

  default_node = default_version_info->this_node;

#if defined (ASM_OUTPUT_TYPE_DIRECTIVE)
  if (targetm.has_ifunc_p ())
    {
      struct cgraph_function_version_info *it_v = NULL;
      struct cgraph_node *dispatcher_node = NULL;
      struct cgraph_function_version_info *dispatcher_version_info = NULL;

      /* Right now, the dispatching is done via ifunc.  */
      dispatch_decl = make_dispatcher_decl (default_node->decl);

      dispatcher_node = cgraph_node::get_create (dispatch_decl);
      gcc_assert (dispatcher_node != NULL);
      dispatcher_node->dispatcher_function = 1;
      dispatcher_version_info
	= dispatcher_node->insert_new_function_version ();
      dispatcher_version_info->next = default_version_info;
      dispatcher_node->definition = 1;

      /* Set the dispatcher for all the versions.  */
      it_v = default_version_info;
      while (it_v != NULL)
	{
	  it_v->dispatcher_resolver = dispatch_decl;
	  it_v = it_v->next;
	}
    }
  else
#endif
    {
      error_at (DECL_SOURCE_LOCATION (default_node->decl),
		"multiversioning needs ifunc which is not supported "
		"on this target");
    }

  return dispatch_decl;
}

/* Make the resolver function decl to dispatch the versions of
   a multi-versioned function,  DEFAULT_DECL.  IFUNC_ALIAS_DECL is
   ifunc alias that will point to the created resolver.  Create an
   empty basic block in the resolver and store the pointer in
   EMPTY_BB.  Return the decl of the resolver function.  */

static tree
make_resolver_func (const tree default_decl,
		    const tree ifunc_alias_decl,
		    basic_block *empty_bb)
{
  char *resolver_name;
  tree decl, type, decl_name, t;

  /* IFUNC's have to be globally visible.  So, if the default_decl is
     not, then the name of the IFUNC should be made unique.  */
  if (TREE_PUBLIC (default_decl) == 0)
    {
      char *ifunc_name = make_unique_name (default_decl, "ifunc", true);
      symtab->change_decl_assembler_name (ifunc_alias_decl,
					  get_identifier (ifunc_name));
      XDELETEVEC (ifunc_name);
    }

  resolver_name = make_unique_name (default_decl, "resolver", false);

  /* The resolver function should return a (void *). */
  type = build_function_type_list (ptr_type_node, NULL_TREE);

  decl = build_fn_decl (resolver_name, type);
  decl_name = get_identifier (resolver_name);
  SET_DECL_ASSEMBLER_NAME (decl, decl_name);

  DECL_NAME (decl) = decl_name;
  TREE_USED (decl) = 1;
  DECL_ARTIFICIAL (decl) = 1;
  DECL_IGNORED_P (decl) = 1;
  TREE_PUBLIC (decl) = 0;
  DECL_UNINLINABLE (decl) = 1;

  /* Resolver is not external, body is generated.  */
  DECL_EXTERNAL (decl) = 0;
  DECL_EXTERNAL (ifunc_alias_decl) = 0;

  DECL_CONTEXT (decl) = NULL_TREE;
  DECL_INITIAL (decl) = make_node (BLOCK);
  DECL_STATIC_CONSTRUCTOR (decl) = 0;

  if (DECL_COMDAT_GROUP (default_decl)
      || TREE_PUBLIC (default_decl))
    {
      /* In this case, each translation unit with a call to this
	 versioned function will put out a resolver.  Ensure it
	 is comdat to keep just one copy.  */
      DECL_COMDAT (decl) = 1;
      make_decl_one_only (decl, DECL_ASSEMBLER_NAME (decl));
    }
  /* Build result decl and add to function_decl. */
  t = build_decl (UNKNOWN_LOCATION, RESULT_DECL, NULL_TREE, ptr_type_node);
  DECL_ARTIFICIAL (t) = 1;
  DECL_IGNORED_P (t) = 1;
  DECL_RESULT (decl) = t;

  gimplify_function_tree (decl);
  push_cfun (DECL_STRUCT_FUNCTION (decl));
  *empty_bb = init_lowered_empty_function (decl, false,
					   profile_count::uninitialized ());

  cgraph_node::add_new_function (decl, true);
  symtab->call_cgraph_insertion_hooks (cgraph_node::get_create (decl));

  pop_cfun ();

  gcc_assert (ifunc_alias_decl != NULL);
  /* Mark ifunc_alias_decl as "ifunc" with resolver as resolver_name.  */
  DECL_ATTRIBUTES (ifunc_alias_decl)
    = make_attribute ("ifunc", resolver_name,
		      DECL_ATTRIBUTES (ifunc_alias_decl));

  /* Create the alias for dispatch to resolver here.  */
  cgraph_node::create_same_body_alias (ifunc_alias_decl, decl);
  XDELETEVEC (resolver_name);
  return decl;
}

/* Generate the dispatching code body to dispatch multi-versioned function
   DECL.  The target hook is called to process the "target" attributes and
   provide the code to dispatch the right function at run-time.  NODE points
   to the dispatcher decl whose body will be created.  */

static tree 
ix86_generate_version_dispatcher_body (void *node_p)
{
  tree resolver_decl;
  basic_block empty_bb;
  tree default_ver_decl;
  struct cgraph_node *versn;
  struct cgraph_node *node;

  struct cgraph_function_version_info *node_version_info = NULL;
  struct cgraph_function_version_info *versn_info = NULL;

  node = (cgraph_node *)node_p;

  node_version_info = node->function_version ();
  gcc_assert (node->dispatcher_function
	      && node_version_info != NULL);

  if (node_version_info->dispatcher_resolver)
    return node_version_info->dispatcher_resolver;

  /* The first version in the chain corresponds to the default version.  */
  default_ver_decl = node_version_info->next->this_node->decl;

  /* node is going to be an alias, so remove the finalized bit.  */
  node->definition = false;

  resolver_decl = make_resolver_func (default_ver_decl,
				      node->decl, &empty_bb);

  node_version_info->dispatcher_resolver = resolver_decl;

  push_cfun (DECL_STRUCT_FUNCTION (resolver_decl));

  auto_vec<tree, 2> fn_ver_vec;

  for (versn_info = node_version_info->next; versn_info;
       versn_info = versn_info->next)
    {
      versn = versn_info->this_node;
      /* Check for virtual functions here again, as by this time it should
	 have been determined if this function needs a vtable index or
	 not.  This happens for methods in derived classes that override
	 virtual methods in base classes but are not explicitly marked as
	 virtual.  */
      if (DECL_VINDEX (versn->decl))
	sorry ("Virtual function multiversioning not supported");

      fn_ver_vec.safe_push (versn->decl);
    }

  dispatch_function_versions (resolver_decl, &fn_ver_vec, &empty_bb);
  cgraph_edge::rebuild_edges ();
  pop_cfun ();
  return resolver_decl;
}
/* This builds the processor_model struct type defined in
   libgcc/config/i386/cpuinfo.c  */

static tree
build_processor_model_struct (void)
{
  const char *field_name[] = {"__cpu_vendor", "__cpu_type", "__cpu_subtype",
			      "__cpu_features"};
  tree field = NULL_TREE, field_chain = NULL_TREE;
  int i;
  tree type = make_node (RECORD_TYPE);

  /* The first 3 fields are unsigned int.  */
  for (i = 0; i < 3; ++i)
    {
      field = build_decl (UNKNOWN_LOCATION, FIELD_DECL,
			  get_identifier (field_name[i]), unsigned_type_node);
      if (field_chain != NULL_TREE)
	DECL_CHAIN (field) = field_chain;
      field_chain = field;
    }

  /* The last field is an array of unsigned integers of size one.  */
  field = build_decl (UNKNOWN_LOCATION, FIELD_DECL,
		      get_identifier (field_name[3]),
		      build_array_type (unsigned_type_node,
					build_index_type (size_one_node)));
  if (field_chain != NULL_TREE)
    DECL_CHAIN (field) = field_chain;
  field_chain = field;

  finish_builtin_struct (type, "__processor_model", field_chain, NULL_TREE);
  return type;
}

/* Returns a extern, comdat VAR_DECL of type TYPE and name NAME. */

static tree
make_var_decl (tree type, const char *name)
{
  tree new_decl;

  new_decl = build_decl (UNKNOWN_LOCATION,
	                 VAR_DECL,
	  	         get_identifier(name),
		         type);

  DECL_EXTERNAL (new_decl) = 1;
  TREE_STATIC (new_decl) = 1;
  TREE_PUBLIC (new_decl) = 1;
  DECL_INITIAL (new_decl) = 0;
  DECL_ARTIFICIAL (new_decl) = 0;
  DECL_PRESERVE_P (new_decl) = 1;

  make_decl_one_only (new_decl, DECL_ASSEMBLER_NAME (new_decl));
  assemble_variable (new_decl, 0, 0, 0);

  return new_decl;
}

/* FNDECL is a __builtin_cpu_is or a __builtin_cpu_supports call that is folded
   into an integer defined in libgcc/config/i386/cpuinfo.c */

static tree
fold_builtin_cpu (tree fndecl, tree *args)
{
  unsigned int i;
  enum ix86_builtins fn_code = (enum ix86_builtins)
				DECL_FUNCTION_CODE (fndecl);
  tree param_string_cst = NULL;

  /* This is the order of bit-fields in __processor_features in cpuinfo.c */
  enum processor_features
  {
    F_CMOV = 0,
    F_MMX,
    F_POPCNT,
    F_SSE,
    F_SSE2,
    F_SSE3,
    F_SSSE3,
    F_SSE4_1,
    F_SSE4_2,
    F_AVX,
    F_AVX2,
    F_SSE4_A,
    F_FMA4,
    F_XOP,
    F_FMA,
    F_AVX512F,
    F_BMI,
    F_BMI2,
    F_AES,
    F_PCLMUL,
    F_AVX512VL,
    F_AVX512BW,
    F_AVX512DQ,
    F_AVX512CD,
    F_AVX512ER,
    F_AVX512PF,
    F_AVX512VBMI,
    F_AVX512IFMA,
    F_AVX5124VNNIW,
    F_AVX5124FMAPS,
    F_AVX512VPOPCNTDQ,
    F_AVX512VBMI2,
    F_GFNI,
    F_VPCLMULQDQ,
    F_AVX512VNNI,
    F_AVX512BITALG,
    F_MAX
  };

  /* These are the values for vendor types and cpu types  and subtypes
     in cpuinfo.c.  Cpu types and subtypes should be subtracted by
     the corresponding start value.  */
  enum processor_model
  {
    M_INTEL = 1,
    M_AMD,
    M_CPU_TYPE_START,
    M_INTEL_BONNELL,
    M_INTEL_CORE2,
    M_INTEL_COREI7,
    M_AMDFAM10H,
    M_AMDFAM15H,
    M_INTEL_SILVERMONT,
    M_INTEL_KNL,
    M_AMD_BTVER1,
    M_AMD_BTVER2,    
    M_AMDFAM17H,
    M_INTEL_KNM,
    M_INTEL_GOLDMONT,
    M_INTEL_GOLDMONT_PLUS,
    M_INTEL_TREMONT,
    M_CPU_SUBTYPE_START,
    M_INTEL_COREI7_NEHALEM,
    M_INTEL_COREI7_WESTMERE,
    M_INTEL_COREI7_SANDYBRIDGE,
    M_AMDFAM10H_BARCELONA,
    M_AMDFAM10H_SHANGHAI,
    M_AMDFAM10H_ISTANBUL,
    M_AMDFAM15H_BDVER1,
    M_AMDFAM15H_BDVER2,
    M_AMDFAM15H_BDVER3,
    M_AMDFAM15H_BDVER4,
    M_AMDFAM17H_ZNVER1,
    M_INTEL_COREI7_IVYBRIDGE,
    M_INTEL_COREI7_HASWELL,
    M_INTEL_COREI7_BROADWELL,
    M_INTEL_COREI7_SKYLAKE,
    M_INTEL_COREI7_SKYLAKE_AVX512,
    M_INTEL_COREI7_CANNONLAKE,
    M_INTEL_COREI7_ICELAKE_CLIENT,
    M_INTEL_COREI7_ICELAKE_SERVER,
    M_AMDFAM17H_ZNVER2,
    M_INTEL_COREI7_CASCADELAKE
  };

  static struct _arch_names_table
    {
      const char *const name;
      const enum processor_model model;
    }
  const arch_names_table[] =
    {
      {"amd", M_AMD},
      {"intel", M_INTEL},
      {"atom", M_INTEL_BONNELL},
      {"slm", M_INTEL_SILVERMONT},
      {"core2", M_INTEL_CORE2},
      {"corei7", M_INTEL_COREI7},
      {"nehalem", M_INTEL_COREI7_NEHALEM},
      {"westmere", M_INTEL_COREI7_WESTMERE},
      {"sandybridge", M_INTEL_COREI7_SANDYBRIDGE},
      {"ivybridge", M_INTEL_COREI7_IVYBRIDGE},
      {"haswell", M_INTEL_COREI7_HASWELL},
      {"broadwell", M_INTEL_COREI7_BROADWELL},
      {"skylake", M_INTEL_COREI7_SKYLAKE},
      {"skylake-avx512", M_INTEL_COREI7_SKYLAKE_AVX512},
      {"cannonlake", M_INTEL_COREI7_CANNONLAKE},
      {"icelake-client", M_INTEL_COREI7_ICELAKE_CLIENT},
      {"icelake-server", M_INTEL_COREI7_ICELAKE_SERVER},
      {"cascadelake", M_INTEL_COREI7_CASCADELAKE},
      {"bonnell", M_INTEL_BONNELL},
      {"silvermont", M_INTEL_SILVERMONT},
      {"goldmont", M_INTEL_GOLDMONT},
      {"goldmont-plus", M_INTEL_GOLDMONT_PLUS},
      {"tremont", M_INTEL_TREMONT},
      {"knl", M_INTEL_KNL},
      {"knm", M_INTEL_KNM},
      {"amdfam10h", M_AMDFAM10H},
      {"barcelona", M_AMDFAM10H_BARCELONA},
      {"shanghai", M_AMDFAM10H_SHANGHAI},
      {"istanbul", M_AMDFAM10H_ISTANBUL},
      {"btver1", M_AMD_BTVER1},      
      {"amdfam15h", M_AMDFAM15H},
      {"bdver1", M_AMDFAM15H_BDVER1},
      {"bdver2", M_AMDFAM15H_BDVER2},
      {"bdver3", M_AMDFAM15H_BDVER3},
      {"bdver4", M_AMDFAM15H_BDVER4},
      {"btver2", M_AMD_BTVER2},
      {"amdfam17h", M_AMDFAM17H},
      {"znver1", M_AMDFAM17H_ZNVER1},
      {"znver2", M_AMDFAM17H_ZNVER2},
    };

  static struct _isa_names_table
    {
      const char *const name;
      const enum processor_features feature;
    }
  const isa_names_table[] =
    {
      {"cmov",    F_CMOV},
      {"mmx",     F_MMX},
      {"popcnt",  F_POPCNT},
      {"sse",     F_SSE},
      {"sse2",    F_SSE2},
      {"sse3",    F_SSE3},
      {"ssse3",   F_SSSE3},
      {"sse4a",   F_SSE4_A},
      {"sse4.1",  F_SSE4_1},
      {"sse4.2",  F_SSE4_2},
      {"avx",     F_AVX},
      {"fma4",    F_FMA4},
      {"xop",     F_XOP},
      {"fma",     F_FMA},
      {"avx2",    F_AVX2},
      {"avx512f", F_AVX512F},
      {"bmi",     F_BMI},
      {"bmi2",    F_BMI2},
      {"aes",     F_AES},
      {"pclmul",  F_PCLMUL},
      {"avx512vl",F_AVX512VL},
      {"avx512bw",F_AVX512BW},
      {"avx512dq",F_AVX512DQ},
      {"avx512cd",F_AVX512CD},
      {"avx512er",F_AVX512ER},
      {"avx512pf",F_AVX512PF},
      {"avx512vbmi",F_AVX512VBMI},
      {"avx512ifma",F_AVX512IFMA},
      {"avx5124vnniw",F_AVX5124VNNIW},
      {"avx5124fmaps",F_AVX5124FMAPS},
      {"avx512vpopcntdq",F_AVX512VPOPCNTDQ},
      {"avx512vbmi2", F_AVX512VBMI2},
      {"gfni", F_GFNI},
      {"vpclmulqdq", F_VPCLMULQDQ},
      {"avx512vnni", F_AVX512VNNI},
      {"avx512bitalg", F_AVX512BITALG}
    };

  tree __processor_model_type = build_processor_model_struct ();
  tree __cpu_model_var = make_var_decl (__processor_model_type,
					"__cpu_model");


  varpool_node::add (__cpu_model_var);

  gcc_assert ((args != NULL) && (*args != NULL));

  param_string_cst = *args;
  while (param_string_cst
	 && TREE_CODE (param_string_cst) !=  STRING_CST)
    {
      /* *args must be a expr that can contain other EXPRS leading to a
	 STRING_CST.   */
      if (!EXPR_P (param_string_cst))
 	{
	  error ("Parameter to builtin must be a string constant or literal");
	  return integer_zero_node;
	}
      param_string_cst = TREE_OPERAND (EXPR_CHECK (param_string_cst), 0);
    }

  gcc_assert (param_string_cst);

  if (fn_code == IX86_BUILTIN_CPU_IS)
    {
      tree ref;
      tree field;
      tree final;

      unsigned int field_val = 0;
      unsigned int NUM_ARCH_NAMES
	= sizeof (arch_names_table) / sizeof (struct _arch_names_table);

      for (i = 0; i < NUM_ARCH_NAMES; i++)
	if (strcmp (arch_names_table[i].name,
	    TREE_STRING_POINTER (param_string_cst)) == 0)
	  break;

      if (i == NUM_ARCH_NAMES)
	{
	  error ("Parameter to builtin not valid: %s",
	         TREE_STRING_POINTER (param_string_cst));
	  return integer_zero_node;
	}

      field = TYPE_FIELDS (__processor_model_type);
      field_val = arch_names_table[i].model;

      /* CPU types are stored in the next field.  */
      if (field_val > M_CPU_TYPE_START
	  && field_val < M_CPU_SUBTYPE_START)
	{
	  field = DECL_CHAIN (field);
	  field_val -= M_CPU_TYPE_START;
	}

      /* CPU subtypes are stored in the next field.  */
      if (field_val > M_CPU_SUBTYPE_START)
	{
	  field = DECL_CHAIN ( DECL_CHAIN (field));
	  field_val -= M_CPU_SUBTYPE_START;
	}

      /* Get the appropriate field in __cpu_model.  */
      ref = build3 (COMPONENT_REF, TREE_TYPE (field), __cpu_model_var,
		    field, NULL_TREE);

      /* Check the value.  */
      final = build2 (EQ_EXPR, unsigned_type_node, ref,
		      build_int_cstu (unsigned_type_node, field_val));
      return build1 (CONVERT_EXPR, integer_type_node, final);
    }
  else if (fn_code == IX86_BUILTIN_CPU_SUPPORTS)
    {
      tree ref;
      tree array_elt;
      tree field;
      tree final;

      unsigned int field_val = 0;
      unsigned int NUM_ISA_NAMES
	= sizeof (isa_names_table) / sizeof (struct _isa_names_table);

      for (i = 0; i < NUM_ISA_NAMES; i++)
	if (strcmp (isa_names_table[i].name,
	    TREE_STRING_POINTER (param_string_cst)) == 0)
	  break;

      if (i == NUM_ISA_NAMES)
	{
	  error ("Parameter to builtin not valid: %s",
	       	 TREE_STRING_POINTER (param_string_cst));
	  return integer_zero_node;
	}

      if (isa_names_table[i].feature >= 32)
	{
	  tree __cpu_features2_var = make_var_decl (unsigned_type_node,
						    "__cpu_features2");

	  varpool_node::add (__cpu_features2_var);
	  field_val = (1U << (isa_names_table[i].feature - 32));
	  /* Return __cpu_features2 & field_val  */
	  final = build2 (BIT_AND_EXPR, unsigned_type_node,
			  __cpu_features2_var,
			  build_int_cstu (unsigned_type_node, field_val));
	  return build1 (CONVERT_EXPR, integer_type_node, final);
	}

      field = TYPE_FIELDS (__processor_model_type);
      /* Get the last field, which is __cpu_features.  */
      while (DECL_CHAIN (field))
        field = DECL_CHAIN (field);

      /* Get the appropriate field: __cpu_model.__cpu_features  */
      ref = build3 (COMPONENT_REF, TREE_TYPE (field), __cpu_model_var,
		    field, NULL_TREE);

      /* Access the 0th element of __cpu_features array.  */
      array_elt = build4 (ARRAY_REF, unsigned_type_node, ref,
			  integer_zero_node, NULL_TREE, NULL_TREE);

      field_val = (1U << isa_names_table[i].feature);
      /* Return __cpu_model.__cpu_features[0] & field_val  */
      final = build2 (BIT_AND_EXPR, unsigned_type_node, array_elt,
		      build_int_cstu (unsigned_type_node, field_val));
      return build1 (CONVERT_EXPR, integer_type_node, final);
    }
  gcc_unreachable ();
}

/* Return the shift count of a vector by scalar shift builtin second argument
   ARG1.  */
static tree
ix86_vector_shift_count (tree arg1)
{
  if (tree_fits_uhwi_p (arg1))
    return arg1;
  else if (TREE_CODE (arg1) == VECTOR_CST && CHAR_BIT == 8)
    {
      /* The count argument is weird, passed in as various 128-bit
	 (or 64-bit) vectors, the low 64 bits from it are the count.  */
      unsigned char buf[16];
      int len = native_encode_expr (arg1, buf, 16);
      if (len == 0)
	return NULL_TREE;
      tree t = native_interpret_expr (uint64_type_node, buf, len);
      if (t && tree_fits_uhwi_p (t))
	return t;
    }
  return NULL_TREE;
}

static tree
ix86_fold_builtin (tree fndecl, int n_args,
		   tree *args, bool ignore ATTRIBUTE_UNUSED)
{
  if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
    {
      enum ix86_builtins fn_code = (enum ix86_builtins)
				   DECL_FUNCTION_CODE (fndecl);
      enum rtx_code rcode;
      bool is_vshift;
      unsigned HOST_WIDE_INT mask;

      switch (fn_code)
	{
	case IX86_BUILTIN_CPU_IS:
	case IX86_BUILTIN_CPU_SUPPORTS:
	  gcc_assert (n_args == 1);
	  return fold_builtin_cpu (fndecl, args);

	case IX86_BUILTIN_NANQ:
	case IX86_BUILTIN_NANSQ:
	  {
	    tree type = TREE_TYPE (TREE_TYPE (fndecl));
	    const char *str = c_getstr (*args);
	    int quiet = fn_code == IX86_BUILTIN_NANQ;
	    REAL_VALUE_TYPE real;

	    if (str && real_nan (&real, str, quiet, TYPE_MODE (type)))
	      return build_real (type, real);
	    return NULL_TREE;
	  }

	case IX86_BUILTIN_INFQ:
	case IX86_BUILTIN_HUGE_VALQ:
	  {
	    tree type = TREE_TYPE (TREE_TYPE (fndecl));
	    REAL_VALUE_TYPE inf;
	    real_inf (&inf);
	    return build_real (type, inf);
	  }

	case IX86_BUILTIN_TZCNT16:
	case IX86_BUILTIN_CTZS:
	case IX86_BUILTIN_TZCNT32:
	case IX86_BUILTIN_TZCNT64:
	  gcc_assert (n_args == 1);
	  if (TREE_CODE (args[0]) == INTEGER_CST)
	    {
	      tree type = TREE_TYPE (TREE_TYPE (fndecl));
	      tree arg = args[0];
	      if (fn_code == IX86_BUILTIN_TZCNT16
		  || fn_code == IX86_BUILTIN_CTZS)
		arg = fold_convert (short_unsigned_type_node, arg);
	      if (integer_zerop (arg))
		return build_int_cst (type, TYPE_PRECISION (TREE_TYPE (arg)));
	      else
		return fold_const_call (CFN_CTZ, type, arg);
	    }
	  break;

	case IX86_BUILTIN_LZCNT16:
	case IX86_BUILTIN_CLZS:
	case IX86_BUILTIN_LZCNT32:
	case IX86_BUILTIN_LZCNT64:
	  gcc_assert (n_args == 1);
	  if (TREE_CODE (args[0]) == INTEGER_CST)
	    {
	      tree type = TREE_TYPE (TREE_TYPE (fndecl));
	      tree arg = args[0];
	      if (fn_code == IX86_BUILTIN_LZCNT16
		  || fn_code == IX86_BUILTIN_CLZS)
		arg = fold_convert (short_unsigned_type_node, arg);
	      if (integer_zerop (arg))
		return build_int_cst (type, TYPE_PRECISION (TREE_TYPE (arg)));
	      else
		return fold_const_call (CFN_CLZ, type, arg);
	    }
	  break;

	case IX86_BUILTIN_BEXTR32:
	case IX86_BUILTIN_BEXTR64:
	case IX86_BUILTIN_BEXTRI32:
	case IX86_BUILTIN_BEXTRI64:
	  gcc_assert (n_args == 2);
	  if (tree_fits_uhwi_p (args[1]))
	    {
	      unsigned HOST_WIDE_INT res = 0;
	      unsigned int prec = TYPE_PRECISION (TREE_TYPE (args[0]));
	      unsigned int start = tree_to_uhwi (args[1]);
	      unsigned int len = (start & 0xff00) >> 8;
	      start &= 0xff;
	      if (start >= prec || len == 0)
		res = 0;
	      else if (!tree_fits_uhwi_p (args[0]))
		break;
	      else
		res = tree_to_uhwi (args[0]) >> start;
	      if (len > prec)
		len = prec;
	      if (len < HOST_BITS_PER_WIDE_INT)
		res &= (HOST_WIDE_INT_1U << len) - 1;
	      return build_int_cstu (TREE_TYPE (TREE_TYPE (fndecl)), res);
	    }
	  break;

	case IX86_BUILTIN_BZHI32:
	case IX86_BUILTIN_BZHI64:
	  gcc_assert (n_args == 2);
	  if (tree_fits_uhwi_p (args[1]))
	    {
	      unsigned int idx = tree_to_uhwi (args[1]) & 0xff;
	      if (idx >= TYPE_PRECISION (TREE_TYPE (args[0])))
		return args[0];
	      if (idx == 0)
		return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), 0);
	      if (!tree_fits_uhwi_p (args[0]))
		break;
	      unsigned HOST_WIDE_INT res = tree_to_uhwi (args[0]);
	      res &= ~(HOST_WIDE_INT_M1U << idx);
	      return build_int_cstu (TREE_TYPE (TREE_TYPE (fndecl)), res);
	    }
	  break;

	case IX86_BUILTIN_PDEP32:
	case IX86_BUILTIN_PDEP64:
	  gcc_assert (n_args == 2);
	  if (tree_fits_uhwi_p (args[0]) && tree_fits_uhwi_p (args[1]))
	    {
	      unsigned HOST_WIDE_INT src = tree_to_uhwi (args[0]);
	      unsigned HOST_WIDE_INT mask = tree_to_uhwi (args[1]);
	      unsigned HOST_WIDE_INT res = 0;
	      unsigned HOST_WIDE_INT m, k = 1;
	      for (m = 1; m; m <<= 1)
		if ((mask & m) != 0)
		  {
		    if ((src & k) != 0)
		      res |= m;
		    k <<= 1;
		  }
	      return build_int_cstu (TREE_TYPE (TREE_TYPE (fndecl)), res);
	    }
	  break;

	case IX86_BUILTIN_PEXT32:
	case IX86_BUILTIN_PEXT64:
	  gcc_assert (n_args == 2);
	  if (tree_fits_uhwi_p (args[0]) && tree_fits_uhwi_p (args[1]))
	    {
	      unsigned HOST_WIDE_INT src = tree_to_uhwi (args[0]);
	      unsigned HOST_WIDE_INT mask = tree_to_uhwi (args[1]);
	      unsigned HOST_WIDE_INT res = 0;
	      unsigned HOST_WIDE_INT m, k = 1;
	      for (m = 1; m; m <<= 1)
		if ((mask & m) != 0)
		  {
		    if ((src & m) != 0)
		      res |= k;
		    k <<= 1;
		  }
	      return build_int_cstu (TREE_TYPE (TREE_TYPE (fndecl)), res);
	    }
	  break;

	case IX86_BUILTIN_MOVMSKPS:
	case IX86_BUILTIN_PMOVMSKB:
	case IX86_BUILTIN_MOVMSKPD:
	case IX86_BUILTIN_PMOVMSKB128:
	case IX86_BUILTIN_MOVMSKPD256:
	case IX86_BUILTIN_MOVMSKPS256:
	case IX86_BUILTIN_PMOVMSKB256:
	  gcc_assert (n_args == 1);
	  if (TREE_CODE (args[0]) == VECTOR_CST)
	    {
	      HOST_WIDE_INT res = 0;
	      for (unsigned i = 0; i < VECTOR_CST_NELTS (args[0]); ++i)
		{
		  tree e = VECTOR_CST_ELT (args[0], i);
		  if (TREE_CODE (e) == INTEGER_CST && !TREE_OVERFLOW (e))
		    {
		      if (wi::neg_p (wi::to_wide (e)))
			res |= HOST_WIDE_INT_1 << i;
		    }
		  else if (TREE_CODE (e) == REAL_CST && !TREE_OVERFLOW (e))
		    {
		      if (TREE_REAL_CST (e).sign)
			res |= HOST_WIDE_INT_1 << i;
		    }
		  else
		    return NULL_TREE;
		}
	      return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), res);
	    }
	  break;

	case IX86_BUILTIN_PSLLD:
	case IX86_BUILTIN_PSLLD128:
	case IX86_BUILTIN_PSLLD128_MASK:
	case IX86_BUILTIN_PSLLD256:
	case IX86_BUILTIN_PSLLD256_MASK:
	case IX86_BUILTIN_PSLLD512:
	case IX86_BUILTIN_PSLLDI:
	case IX86_BUILTIN_PSLLDI128:
	case IX86_BUILTIN_PSLLDI128_MASK:
	case IX86_BUILTIN_PSLLDI256:
	case IX86_BUILTIN_PSLLDI256_MASK:
	case IX86_BUILTIN_PSLLDI512:
	case IX86_BUILTIN_PSLLQ:
	case IX86_BUILTIN_PSLLQ128:
	case IX86_BUILTIN_PSLLQ128_MASK:
	case IX86_BUILTIN_PSLLQ256:
	case IX86_BUILTIN_PSLLQ256_MASK:
	case IX86_BUILTIN_PSLLQ512:
	case IX86_BUILTIN_PSLLQI:
	case IX86_BUILTIN_PSLLQI128:
	case IX86_BUILTIN_PSLLQI128_MASK:
	case IX86_BUILTIN_PSLLQI256:
	case IX86_BUILTIN_PSLLQI256_MASK:
	case IX86_BUILTIN_PSLLQI512:
	case IX86_BUILTIN_PSLLW:
	case IX86_BUILTIN_PSLLW128:
	case IX86_BUILTIN_PSLLW128_MASK:
	case IX86_BUILTIN_PSLLW256:
	case IX86_BUILTIN_PSLLW256_MASK:
	case IX86_BUILTIN_PSLLW512_MASK:
	case IX86_BUILTIN_PSLLWI:
	case IX86_BUILTIN_PSLLWI128:
	case IX86_BUILTIN_PSLLWI128_MASK:
	case IX86_BUILTIN_PSLLWI256:
	case IX86_BUILTIN_PSLLWI256_MASK:
	case IX86_BUILTIN_PSLLWI512_MASK:
	  rcode = ASHIFT;
	  is_vshift = false;
	  goto do_shift;
	case IX86_BUILTIN_PSRAD:
	case IX86_BUILTIN_PSRAD128:
	case IX86_BUILTIN_PSRAD128_MASK:
	case IX86_BUILTIN_PSRAD256:
	case IX86_BUILTIN_PSRAD256_MASK:
	case IX86_BUILTIN_PSRAD512:
	case IX86_BUILTIN_PSRADI:
	case IX86_BUILTIN_PSRADI128:
	case IX86_BUILTIN_PSRADI128_MASK:
	case IX86_BUILTIN_PSRADI256:
	case IX86_BUILTIN_PSRADI256_MASK:
	case IX86_BUILTIN_PSRADI512:
	case IX86_BUILTIN_PSRAQ128_MASK:
	case IX86_BUILTIN_PSRAQ256_MASK:
	case IX86_BUILTIN_PSRAQ512:
	case IX86_BUILTIN_PSRAQI128_MASK:
	case IX86_BUILTIN_PSRAQI256_MASK:
	case IX86_BUILTIN_PSRAQI512:
	case IX86_BUILTIN_PSRAW:
	case IX86_BUILTIN_PSRAW128:
	case IX86_BUILTIN_PSRAW128_MASK:
	case IX86_BUILTIN_PSRAW256:
	case IX86_BUILTIN_PSRAW256_MASK:
	case IX86_BUILTIN_PSRAW512:
	case IX86_BUILTIN_PSRAWI:
	case IX86_BUILTIN_PSRAWI128:
	case IX86_BUILTIN_PSRAWI128_MASK:
	case IX86_BUILTIN_PSRAWI256:
	case IX86_BUILTIN_PSRAWI256_MASK:
	case IX86_BUILTIN_PSRAWI512:
	  rcode = ASHIFTRT;
	  is_vshift = false;
	  goto do_shift;
	case IX86_BUILTIN_PSRLD:
	case IX86_BUILTIN_PSRLD128:
	case IX86_BUILTIN_PSRLD128_MASK:
	case IX86_BUILTIN_PSRLD256:
	case IX86_BUILTIN_PSRLD256_MASK:
	case IX86_BUILTIN_PSRLD512:
	case IX86_BUILTIN_PSRLDI:
	case IX86_BUILTIN_PSRLDI128:
	case IX86_BUILTIN_PSRLDI128_MASK:
	case IX86_BUILTIN_PSRLDI256:
	case IX86_BUILTIN_PSRLDI256_MASK:
	case IX86_BUILTIN_PSRLDI512:
	case IX86_BUILTIN_PSRLQ:
	case IX86_BUILTIN_PSRLQ128:
	case IX86_BUILTIN_PSRLQ128_MASK:
	case IX86_BUILTIN_PSRLQ256:
	case IX86_BUILTIN_PSRLQ256_MASK:
	case IX86_BUILTIN_PSRLQ512:
	case IX86_BUILTIN_PSRLQI:
	case IX86_BUILTIN_PSRLQI128:
	case IX86_BUILTIN_PSRLQI128_MASK:
	case IX86_BUILTIN_PSRLQI256:
	case IX86_BUILTIN_PSRLQI256_MASK:
	case IX86_BUILTIN_PSRLQI512:
	case IX86_BUILTIN_PSRLW:
	case IX86_BUILTIN_PSRLW128:
	case IX86_BUILTIN_PSRLW128_MASK:
	case IX86_BUILTIN_PSRLW256:
	case IX86_BUILTIN_PSRLW256_MASK:
	case IX86_BUILTIN_PSRLW512:
	case IX86_BUILTIN_PSRLWI:
	case IX86_BUILTIN_PSRLWI128:
	case IX86_BUILTIN_PSRLWI128_MASK:
	case IX86_BUILTIN_PSRLWI256:
	case IX86_BUILTIN_PSRLWI256_MASK:
	case IX86_BUILTIN_PSRLWI512:
	  rcode = LSHIFTRT;
	  is_vshift = false;
	  goto do_shift;
	case IX86_BUILTIN_PSLLVV16HI:
	case IX86_BUILTIN_PSLLVV16SI:
	case IX86_BUILTIN_PSLLVV2DI:
	case IX86_BUILTIN_PSLLVV2DI_MASK:
	case IX86_BUILTIN_PSLLVV32HI:
	case IX86_BUILTIN_PSLLVV4DI:
	case IX86_BUILTIN_PSLLVV4DI_MASK:
	case IX86_BUILTIN_PSLLVV4SI:
	case IX86_BUILTIN_PSLLVV4SI_MASK:
	case IX86_BUILTIN_PSLLVV8DI:
	case IX86_BUILTIN_PSLLVV8HI:
	case IX86_BUILTIN_PSLLVV8SI:
	case IX86_BUILTIN_PSLLVV8SI_MASK:
	  rcode = ASHIFT;
	  is_vshift = true;
	  goto do_shift;
	case IX86_BUILTIN_PSRAVQ128:
	case IX86_BUILTIN_PSRAVQ256:
	case IX86_BUILTIN_PSRAVV16HI:
	case IX86_BUILTIN_PSRAVV16SI:
	case IX86_BUILTIN_PSRAVV32HI:
	case IX86_BUILTIN_PSRAVV4SI:
	case IX86_BUILTIN_PSRAVV4SI_MASK:
	case IX86_BUILTIN_PSRAVV8DI:
	case IX86_BUILTIN_PSRAVV8HI:
	case IX86_BUILTIN_PSRAVV8SI:
	case IX86_BUILTIN_PSRAVV8SI_MASK:
	  rcode = ASHIFTRT;
	  is_vshift = true;
	  goto do_shift;
	case IX86_BUILTIN_PSRLVV16HI:
	case IX86_BUILTIN_PSRLVV16SI:
	case IX86_BUILTIN_PSRLVV2DI:
	case IX86_BUILTIN_PSRLVV2DI_MASK:
	case IX86_BUILTIN_PSRLVV32HI:
	case IX86_BUILTIN_PSRLVV4DI:
	case IX86_BUILTIN_PSRLVV4DI_MASK:
	case IX86_BUILTIN_PSRLVV4SI:
	case IX86_BUILTIN_PSRLVV4SI_MASK:
	case IX86_BUILTIN_PSRLVV8DI:
	case IX86_BUILTIN_PSRLVV8HI:
	case IX86_BUILTIN_PSRLVV8SI:
	case IX86_BUILTIN_PSRLVV8SI_MASK:
	  rcode = LSHIFTRT;
	  is_vshift = true;
	  goto do_shift;

	do_shift:
	  gcc_assert (n_args >= 2);
	  if (TREE_CODE (args[0]) != VECTOR_CST)
	    break;
	  mask = HOST_WIDE_INT_M1U;
	  if (n_args > 2)
	    {
	      /* This is masked shift.  */
	      if (!tree_fits_uhwi_p (args[n_args - 1])
		  || TREE_SIDE_EFFECTS (args[n_args - 2]))
		break;
	      mask = tree_to_uhwi (args[n_args - 1]);
	      unsigned elems = TYPE_VECTOR_SUBPARTS (TREE_TYPE (args[0]));
	      mask |= HOST_WIDE_INT_M1U << elems;
	      if (mask != HOST_WIDE_INT_M1U
		  && TREE_CODE (args[n_args - 2]) != VECTOR_CST)
		break;
	      if (mask == (HOST_WIDE_INT_M1U << elems))
		return args[n_args - 2];
	    }
	  if (is_vshift && TREE_CODE (args[1]) != VECTOR_CST)
	    break;
	  if (tree tem = (is_vshift ? integer_one_node
			  : ix86_vector_shift_count (args[1])))
	    {
	      unsigned HOST_WIDE_INT count = tree_to_uhwi (tem);
	      unsigned HOST_WIDE_INT prec
		= TYPE_PRECISION (TREE_TYPE (TREE_TYPE (args[0])));
	      if (count == 0 && mask == HOST_WIDE_INT_M1U)
		return args[0];
	      if (count >= prec)
		{
		  if (rcode == ASHIFTRT)
		    count = prec - 1;
		  else if (mask == HOST_WIDE_INT_M1U)
		    return build_zero_cst (TREE_TYPE (args[0]));
		}
	      tree countt = NULL_TREE;
	      if (!is_vshift)
		{
		  if (count >= prec)
		    countt = integer_zero_node;
		  else
		    countt = build_int_cst (integer_type_node, count);
		}
	      tree_vector_builder builder;
	      builder.new_unary_operation (TREE_TYPE (args[0]), args[0],
					   false);
	      unsigned int cnt = builder.encoded_nelts ();
	      for (unsigned int i = 0; i < cnt; ++i)
		{
		  tree elt = VECTOR_CST_ELT (args[0], i);
		  if (TREE_CODE (elt) != INTEGER_CST || TREE_OVERFLOW (elt))
		    return NULL_TREE;
		  tree type = TREE_TYPE (elt);
		  if (rcode == LSHIFTRT)
		    elt = fold_convert (unsigned_type_for (type), elt);
		  if (is_vshift)
		    {
		      countt = VECTOR_CST_ELT (args[1], i);
		      if (TREE_CODE (countt) != INTEGER_CST
			  || TREE_OVERFLOW (countt))
			return NULL_TREE;
		      if (wi::neg_p (wi::to_wide (countt))
			  || wi::to_widest (countt) >= prec)
			{
			  if (rcode == ASHIFTRT)
			    countt = build_int_cst (TREE_TYPE (countt),
						    prec - 1);
			  else
			    {
			      elt = build_zero_cst (TREE_TYPE (elt));
			      countt = build_zero_cst (TREE_TYPE (countt));
			    }
			}
		    }
		  else if (count >= prec)
		    elt = build_zero_cst (TREE_TYPE (elt));
		  elt = const_binop (rcode == ASHIFT
				     ? LSHIFT_EXPR : RSHIFT_EXPR,
				     TREE_TYPE (elt), elt, countt);
		  if (!elt || TREE_CODE (elt) != INTEGER_CST)
		    return NULL_TREE;
		  if (rcode == LSHIFTRT)
		    elt = fold_convert (type, elt);
		  if ((mask & (HOST_WIDE_INT_1U << i)) == 0)
		    {
		      elt = VECTOR_CST_ELT (args[n_args - 2], i);
		      if (TREE_CODE (elt) != INTEGER_CST
			  || TREE_OVERFLOW (elt))
			return NULL_TREE;
		    }
		  builder.quick_push (elt);
		}
	      return builder.build ();
	    }
	  break;

	default:
	  break;
	}
    }

#ifdef SUBTARGET_FOLD_BUILTIN
  return SUBTARGET_FOLD_BUILTIN (fndecl, n_args, args, ignore);
#endif

  return NULL_TREE;
}

/* Fold a MD builtin (use ix86_fold_builtin for folding into
   constant) in GIMPLE.  */

bool
ix86_gimple_fold_builtin (gimple_stmt_iterator *gsi)
{
  gimple *stmt = gsi_stmt (*gsi);
  tree fndecl = gimple_call_fndecl (stmt);
  gcc_checking_assert (fndecl && fndecl_built_in_p (fndecl, BUILT_IN_MD));
  int n_args = gimple_call_num_args (stmt);
  enum ix86_builtins fn_code = (enum ix86_builtins) DECL_FUNCTION_CODE (fndecl);
  tree decl = NULL_TREE;
  tree arg0, arg1;
  enum rtx_code rcode;
  unsigned HOST_WIDE_INT count;
  bool is_vshift;

  switch (fn_code)
    {
    case IX86_BUILTIN_TZCNT32:
      decl = builtin_decl_implicit (BUILT_IN_CTZ);
      goto fold_tzcnt_lzcnt;

    case IX86_BUILTIN_TZCNT64:
      decl = builtin_decl_implicit (BUILT_IN_CTZLL);
      goto fold_tzcnt_lzcnt;

    case IX86_BUILTIN_LZCNT32:
      decl = builtin_decl_implicit (BUILT_IN_CLZ);
      goto fold_tzcnt_lzcnt;

    case IX86_BUILTIN_LZCNT64:
      decl = builtin_decl_implicit (BUILT_IN_CLZLL);
      goto fold_tzcnt_lzcnt;

    fold_tzcnt_lzcnt:
      gcc_assert (n_args == 1);
      arg0 = gimple_call_arg (stmt, 0);
      if (TREE_CODE (arg0) == SSA_NAME && decl && gimple_call_lhs (stmt))
	{
	  int prec = TYPE_PRECISION (TREE_TYPE (arg0));
	  /* If arg0 is provably non-zero, optimize into generic
	     __builtin_c[tl]z{,ll} function the middle-end handles
	     better.  */
	  if (!expr_not_equal_to (arg0, wi::zero (prec)))
	    return false;

	  location_t loc = gimple_location (stmt);
	  gimple *g = gimple_build_call (decl, 1, arg0);
	  gimple_set_location (g, loc);
	  tree lhs = make_ssa_name (integer_type_node);
	  gimple_call_set_lhs (g, lhs);
	  gsi_insert_before (gsi, g, GSI_SAME_STMT);
	  g = gimple_build_assign (gimple_call_lhs (stmt), NOP_EXPR, lhs);
	  gimple_set_location (g, loc);
	  gsi_replace (gsi, g, false);
	  return true;
	}
      break;

    case IX86_BUILTIN_BZHI32:
    case IX86_BUILTIN_BZHI64:
      gcc_assert (n_args == 2);
      arg1 = gimple_call_arg (stmt, 1);
      if (tree_fits_uhwi_p (arg1) && gimple_call_lhs (stmt))
	{
	  unsigned int idx = tree_to_uhwi (arg1) & 0xff;
	  arg0 = gimple_call_arg (stmt, 0);
	  if (idx < TYPE_PRECISION (TREE_TYPE (arg0)))
	    break;
	  location_t loc = gimple_location (stmt);
	  gimple *g = gimple_build_assign (gimple_call_lhs (stmt), arg0);
	  gimple_set_location (g, loc);
	  gsi_replace (gsi, g, false);
	  return true;
	}
      break;

    case IX86_BUILTIN_PDEP32:
    case IX86_BUILTIN_PDEP64:
    case IX86_BUILTIN_PEXT32:
    case IX86_BUILTIN_PEXT64:
      gcc_assert (n_args == 2);
      arg1 = gimple_call_arg (stmt, 1);
      if (integer_all_onesp (arg1) && gimple_call_lhs (stmt))
	{
	  location_t loc = gimple_location (stmt);
	  arg0 = gimple_call_arg (stmt, 0);
	  gimple *g = gimple_build_assign (gimple_call_lhs (stmt), arg0);
	  gimple_set_location (g, loc);
	  gsi_replace (gsi, g, false);
	  return true;
	}
      break;

    case IX86_BUILTIN_PSLLD:
    case IX86_BUILTIN_PSLLD128:
    case IX86_BUILTIN_PSLLD128_MASK:
    case IX86_BUILTIN_PSLLD256:
    case IX86_BUILTIN_PSLLD256_MASK:
    case IX86_BUILTIN_PSLLD512:
    case IX86_BUILTIN_PSLLDI:
    case IX86_BUILTIN_PSLLDI128:
    case IX86_BUILTIN_PSLLDI128_MASK:
    case IX86_BUILTIN_PSLLDI256:
    case IX86_BUILTIN_PSLLDI256_MASK:
    case IX86_BUILTIN_PSLLDI512:
    case IX86_BUILTIN_PSLLQ:
    case IX86_BUILTIN_PSLLQ128:
    case IX86_BUILTIN_PSLLQ128_MASK:
    case IX86_BUILTIN_PSLLQ256:
    case IX86_BUILTIN_PSLLQ256_MASK:
    case IX86_BUILTIN_PSLLQ512:
    case IX86_BUILTIN_PSLLQI:
    case IX86_BUILTIN_PSLLQI128:
    case IX86_BUILTIN_PSLLQI128_MASK:
    case IX86_BUILTIN_PSLLQI256:
    case IX86_BUILTIN_PSLLQI256_MASK:
    case IX86_BUILTIN_PSLLQI512:
    case IX86_BUILTIN_PSLLW:
    case IX86_BUILTIN_PSLLW128:
    case IX86_BUILTIN_PSLLW128_MASK:
    case IX86_BUILTIN_PSLLW256:
    case IX86_BUILTIN_PSLLW256_MASK:
    case IX86_BUILTIN_PSLLW512_MASK:
    case IX86_BUILTIN_PSLLWI:
    case IX86_BUILTIN_PSLLWI128:
    case IX86_BUILTIN_PSLLWI128_MASK:
    case IX86_BUILTIN_PSLLWI256:
    case IX86_BUILTIN_PSLLWI256_MASK:
    case IX86_BUILTIN_PSLLWI512_MASK:
      rcode = ASHIFT;
      is_vshift = false;
      goto do_shift;
    case IX86_BUILTIN_PSRAD:
    case IX86_BUILTIN_PSRAD128:
    case IX86_BUILTIN_PSRAD128_MASK:
    case IX86_BUILTIN_PSRAD256:
    case IX86_BUILTIN_PSRAD256_MASK:
    case IX86_BUILTIN_PSRAD512:
    case IX86_BUILTIN_PSRADI:
    case IX86_BUILTIN_PSRADI128:
    case IX86_BUILTIN_PSRADI128_MASK:
    case IX86_BUILTIN_PSRADI256:
    case IX86_BUILTIN_PSRADI256_MASK:
    case IX86_BUILTIN_PSRADI512:
    case IX86_BUILTIN_PSRAQ128_MASK:
    case IX86_BUILTIN_PSRAQ256_MASK:
    case IX86_BUILTIN_PSRAQ512:
    case IX86_BUILTIN_PSRAQI128_MASK:
    case IX86_BUILTIN_PSRAQI256_MASK:
    case IX86_BUILTIN_PSRAQI512:
    case IX86_BUILTIN_PSRAW:
    case IX86_BUILTIN_PSRAW128:
    case IX86_BUILTIN_PSRAW128_MASK:
    case IX86_BUILTIN_PSRAW256:
    case IX86_BUILTIN_PSRAW256_MASK:
    case IX86_BUILTIN_PSRAW512:
    case IX86_BUILTIN_PSRAWI:
    case IX86_BUILTIN_PSRAWI128:
    case IX86_BUILTIN_PSRAWI128_MASK:
    case IX86_BUILTIN_PSRAWI256:
    case IX86_BUILTIN_PSRAWI256_MASK:
    case IX86_BUILTIN_PSRAWI512:
      rcode = ASHIFTRT;
      is_vshift = false;
      goto do_shift;
    case IX86_BUILTIN_PSRLD:
    case IX86_BUILTIN_PSRLD128:
    case IX86_BUILTIN_PSRLD128_MASK:
    case IX86_BUILTIN_PSRLD256:
    case IX86_BUILTIN_PSRLD256_MASK:
    case IX86_BUILTIN_PSRLD512:
    case IX86_BUILTIN_PSRLDI:
    case IX86_BUILTIN_PSRLDI128:
    case IX86_BUILTIN_PSRLDI128_MASK:
    case IX86_BUILTIN_PSRLDI256:
    case IX86_BUILTIN_PSRLDI256_MASK:
    case IX86_BUILTIN_PSRLDI512:
    case IX86_BUILTIN_PSRLQ:
    case IX86_BUILTIN_PSRLQ128:
    case IX86_BUILTIN_PSRLQ128_MASK:
    case IX86_BUILTIN_PSRLQ256:
    case IX86_BUILTIN_PSRLQ256_MASK:
    case IX86_BUILTIN_PSRLQ512:
    case IX86_BUILTIN_PSRLQI:
    case IX86_BUILTIN_PSRLQI128:
    case IX86_BUILTIN_PSRLQI128_MASK:
    case IX86_BUILTIN_PSRLQI256:
    case IX86_BUILTIN_PSRLQI256_MASK:
    case IX86_BUILTIN_PSRLQI512:
    case IX86_BUILTIN_PSRLW:
    case IX86_BUILTIN_PSRLW128:
    case IX86_BUILTIN_PSRLW128_MASK:
    case IX86_BUILTIN_PSRLW256:
    case IX86_BUILTIN_PSRLW256_MASK:
    case IX86_BUILTIN_PSRLW512:
    case IX86_BUILTIN_PSRLWI:
    case IX86_BUILTIN_PSRLWI128:
    case IX86_BUILTIN_PSRLWI128_MASK:
    case IX86_BUILTIN_PSRLWI256:
    case IX86_BUILTIN_PSRLWI256_MASK:
    case IX86_BUILTIN_PSRLWI512:
      rcode = LSHIFTRT;
      is_vshift = false;
      goto do_shift;
    case IX86_BUILTIN_PSLLVV16HI:
    case IX86_BUILTIN_PSLLVV16SI:
    case IX86_BUILTIN_PSLLVV2DI:
    case IX86_BUILTIN_PSLLVV2DI_MASK:
    case IX86_BUILTIN_PSLLVV32HI:
    case IX86_BUILTIN_PSLLVV4DI:
    case IX86_BUILTIN_PSLLVV4DI_MASK:
    case IX86_BUILTIN_PSLLVV4SI:
    case IX86_BUILTIN_PSLLVV4SI_MASK:
    case IX86_BUILTIN_PSLLVV8DI:
    case IX86_BUILTIN_PSLLVV8HI:
    case IX86_BUILTIN_PSLLVV8SI:
    case IX86_BUILTIN_PSLLVV8SI_MASK:
      rcode = ASHIFT;
      is_vshift = true;
      goto do_shift;
    case IX86_BUILTIN_PSRAVQ128:
    case IX86_BUILTIN_PSRAVQ256:
    case IX86_BUILTIN_PSRAVV16HI:
    case IX86_BUILTIN_PSRAVV16SI:
    case IX86_BUILTIN_PSRAVV32HI:
    case IX86_BUILTIN_PSRAVV4SI:
    case IX86_BUILTIN_PSRAVV4SI_MASK:
    case IX86_BUILTIN_PSRAVV8DI:
    case IX86_BUILTIN_PSRAVV8HI:
    case IX86_BUILTIN_PSRAVV8SI:
    case IX86_BUILTIN_PSRAVV8SI_MASK:
      rcode = ASHIFTRT;
      is_vshift = true;
      goto do_shift;
    case IX86_BUILTIN_PSRLVV16HI:
    case IX86_BUILTIN_PSRLVV16SI:
    case IX86_BUILTIN_PSRLVV2DI:
    case IX86_BUILTIN_PSRLVV2DI_MASK:
    case IX86_BUILTIN_PSRLVV32HI:
    case IX86_BUILTIN_PSRLVV4DI:
    case IX86_BUILTIN_PSRLVV4DI_MASK:
    case IX86_BUILTIN_PSRLVV4SI:
    case IX86_BUILTIN_PSRLVV4SI_MASK:
    case IX86_BUILTIN_PSRLVV8DI:
    case IX86_BUILTIN_PSRLVV8HI:
    case IX86_BUILTIN_PSRLVV8SI:
    case IX86_BUILTIN_PSRLVV8SI_MASK:
      rcode = LSHIFTRT;
      is_vshift = true;
      goto do_shift;

    do_shift:
      gcc_assert (n_args >= 2);
      arg0 = gimple_call_arg (stmt, 0);
      arg1 = gimple_call_arg (stmt, 1);
      if (n_args > 2)
	{
	  /* This is masked shift.  Only optimize if the mask is all ones.  */
	  tree argl = gimple_call_arg (stmt, n_args - 1);
	  if (!tree_fits_uhwi_p (argl))
	    break;
	  unsigned HOST_WIDE_INT mask = tree_to_uhwi (argl);
	  unsigned elems = TYPE_VECTOR_SUBPARTS (TREE_TYPE (arg0));
	  if ((mask | (HOST_WIDE_INT_M1U << elems)) != HOST_WIDE_INT_M1U)
	    break;
	}
      if (is_vshift)
	{
	  if (TREE_CODE (arg1) != VECTOR_CST)
	    break;
	  count = TYPE_PRECISION (TREE_TYPE (TREE_TYPE (arg0)));
	  if (integer_zerop (arg1))
	    count = 0;
	  else if (rcode == ASHIFTRT)
	    break;
	  else
	    for (unsigned int i = 0; i < VECTOR_CST_NELTS (arg1); ++i)
	      {
		tree elt = VECTOR_CST_ELT (arg1, i);
		if (!wi::neg_p (wi::to_wide (elt))
		    && wi::to_widest (elt) < count)
		  return false;
	      }
	}
      else
	{
	  arg1 = ix86_vector_shift_count (arg1);
	  if (!arg1)
	    break;
	  count = tree_to_uhwi (arg1);
	}
      if (count == 0)
	{
	  /* Just return the first argument for shift by 0.  */
	  location_t loc = gimple_location (stmt);
	  gimple *g = gimple_build_assign (gimple_call_lhs (stmt), arg0);
	  gimple_set_location (g, loc);
	  gsi_replace (gsi, g, false);
	  return true;
	}
      if (rcode != ASHIFTRT
	  && count >= TYPE_PRECISION (TREE_TYPE (TREE_TYPE (arg0))))
	{
	  /* For shift counts equal or greater than precision, except for
	     arithmetic right shift the result is zero.  */
	  location_t loc = gimple_location (stmt);
	  gimple *g = gimple_build_assign (gimple_call_lhs (stmt),
					   build_zero_cst (TREE_TYPE (arg0)));
	  gimple_set_location (g, loc);
	  gsi_replace (gsi, g, false);
	  return true;
	}
      break;

    default:
      break;
    }

  return false;
}

/* Make builtins to detect cpu type and features supported.  NAME is
   the builtin name, CODE is the builtin code, and FTYPE is the function
   type of the builtin.  */

static void
make_cpu_type_builtin (const char* name, int code,
		       enum ix86_builtin_func_type ftype, bool is_const)
{
  tree decl;
  tree type;

  type = ix86_get_builtin_func_type (ftype);
  decl = add_builtin_function (name, type, code, BUILT_IN_MD,
			       NULL, NULL_TREE);
  gcc_assert (decl != NULL_TREE);
  ix86_builtins[(int) code] = decl;
  TREE_READONLY (decl) = is_const;
}

/* Make builtins to get CPU type and features supported.  The created
   builtins are :

   __builtin_cpu_init (), to detect cpu type and features,
   __builtin_cpu_is ("<CPUNAME>"), to check if cpu is of type <CPUNAME>,
   __builtin_cpu_supports ("<FEATURE>"), to check if cpu supports <FEATURE>
   */

static void
ix86_init_platform_type_builtins (void)
{
  make_cpu_type_builtin ("__builtin_cpu_init", IX86_BUILTIN_CPU_INIT,
			 INT_FTYPE_VOID, false);
  make_cpu_type_builtin ("__builtin_cpu_is", IX86_BUILTIN_CPU_IS,
			 INT_FTYPE_PCCHAR, true);
  make_cpu_type_builtin ("__builtin_cpu_supports", IX86_BUILTIN_CPU_SUPPORTS,
			 INT_FTYPE_PCCHAR, true);
}

/* Internal method for ix86_init_builtins.  */

static void
ix86_init_builtins_va_builtins_abi (void)
{
  tree ms_va_ref, sysv_va_ref;
  tree fnvoid_va_end_ms, fnvoid_va_end_sysv;
  tree fnvoid_va_start_ms, fnvoid_va_start_sysv;
  tree fnvoid_va_copy_ms, fnvoid_va_copy_sysv;
  tree fnattr_ms = NULL_TREE, fnattr_sysv = NULL_TREE;

  if (!TARGET_64BIT)
    return;
  fnattr_ms = build_tree_list (get_identifier ("ms_abi"), NULL_TREE);
  fnattr_sysv = build_tree_list (get_identifier ("sysv_abi"), NULL_TREE);
  ms_va_ref = build_reference_type (ms_va_list_type_node);
  sysv_va_ref = build_pointer_type (TREE_TYPE (sysv_va_list_type_node));

  fnvoid_va_end_ms = build_function_type_list (void_type_node, ms_va_ref,
					       NULL_TREE);
  fnvoid_va_start_ms
    = build_varargs_function_type_list (void_type_node, ms_va_ref, NULL_TREE);
  fnvoid_va_end_sysv
    = build_function_type_list (void_type_node, sysv_va_ref, NULL_TREE);
  fnvoid_va_start_sysv
    = build_varargs_function_type_list (void_type_node, sysv_va_ref,
					NULL_TREE);
  fnvoid_va_copy_ms
    = build_function_type_list (void_type_node, ms_va_ref,
				ms_va_list_type_node, NULL_TREE);
  fnvoid_va_copy_sysv
    = build_function_type_list (void_type_node, sysv_va_ref,
				sysv_va_ref, NULL_TREE);

  add_builtin_function ("__builtin_ms_va_start", fnvoid_va_start_ms,
  			BUILT_IN_VA_START, BUILT_IN_NORMAL, NULL, fnattr_ms);
  add_builtin_function ("__builtin_ms_va_end", fnvoid_va_end_ms,
  			BUILT_IN_VA_END, BUILT_IN_NORMAL, NULL, fnattr_ms);
  add_builtin_function ("__builtin_ms_va_copy", fnvoid_va_copy_ms,
			BUILT_IN_VA_COPY, BUILT_IN_NORMAL, NULL, fnattr_ms);
  add_builtin_function ("__builtin_sysv_va_start", fnvoid_va_start_sysv,
  			BUILT_IN_VA_START, BUILT_IN_NORMAL, NULL, fnattr_sysv);
  add_builtin_function ("__builtin_sysv_va_end", fnvoid_va_end_sysv,
  			BUILT_IN_VA_END, BUILT_IN_NORMAL, NULL, fnattr_sysv);
  add_builtin_function ("__builtin_sysv_va_copy", fnvoid_va_copy_sysv,
			BUILT_IN_VA_COPY, BUILT_IN_NORMAL, NULL, fnattr_sysv);
}

static void
ix86_init_builtin_types (void)
{
  tree float80_type_node, const_string_type_node;

  /* The __float80 type.  */
  float80_type_node = long_double_type_node;
  if (TYPE_MODE (float80_type_node) != XFmode)
    {
      if (float64x_type_node != NULL_TREE
	  && TYPE_MODE (float64x_type_node) == XFmode)
	float80_type_node = float64x_type_node;
      else
	{
	  /* The __float80 type.  */
	  float80_type_node = make_node (REAL_TYPE);

	  TYPE_PRECISION (float80_type_node) = 80;
	  layout_type (float80_type_node);
	}
    }
  lang_hooks.types.register_builtin_type (float80_type_node, "__float80");

  /* The __float128 type.  The node has already been created as
     _Float128, so we only need to register the __float128 name for
     it.  */
  lang_hooks.types.register_builtin_type (float128_type_node, "__float128");

  const_string_type_node
    = build_pointer_type (build_qualified_type
			  (char_type_node, TYPE_QUAL_CONST));

  /* This macro is built by i386-builtin-types.awk.  */
  DEFINE_BUILTIN_PRIMITIVE_TYPES;
}

static void
ix86_init_builtins (void)
{
  tree ftype, decl;

  ix86_init_builtin_types ();

  /* Builtins to get CPU type and features. */
  ix86_init_platform_type_builtins ();

  /* TFmode support builtins.  */
  def_builtin_const (0, 0, "__builtin_infq",
		     FLOAT128_FTYPE_VOID, IX86_BUILTIN_INFQ);
  def_builtin_const (0, 0, "__builtin_huge_valq",
		     FLOAT128_FTYPE_VOID, IX86_BUILTIN_HUGE_VALQ);

  ftype = ix86_get_builtin_func_type (FLOAT128_FTYPE_CONST_STRING);
  decl = add_builtin_function ("__builtin_nanq", ftype, IX86_BUILTIN_NANQ,
			       BUILT_IN_MD, "nanq", NULL_TREE);
  TREE_READONLY (decl) = 1;
  ix86_builtins[(int) IX86_BUILTIN_NANQ] = decl;

  decl = add_builtin_function ("__builtin_nansq", ftype, IX86_BUILTIN_NANSQ,
			       BUILT_IN_MD, "nansq", NULL_TREE);
  TREE_READONLY (decl) = 1;
  ix86_builtins[(int) IX86_BUILTIN_NANSQ] = decl;

  /* We will expand them to normal call if SSE isn't available since
     they are used by libgcc. */
  ftype = ix86_get_builtin_func_type (FLOAT128_FTYPE_FLOAT128);
  decl = add_builtin_function ("__builtin_fabsq", ftype, IX86_BUILTIN_FABSQ,
			       BUILT_IN_MD, "__fabstf2", NULL_TREE);
  TREE_READONLY (decl) = 1;
  ix86_builtins[(int) IX86_BUILTIN_FABSQ] = decl;

  ftype = ix86_get_builtin_func_type (FLOAT128_FTYPE_FLOAT128_FLOAT128);
  decl = add_builtin_function ("__builtin_copysignq", ftype,
			       IX86_BUILTIN_COPYSIGNQ, BUILT_IN_MD,
			       "__copysigntf3", NULL_TREE);
  TREE_READONLY (decl) = 1;
  ix86_builtins[(int) IX86_BUILTIN_COPYSIGNQ] = decl;

  ix86_init_tm_builtins ();
  ix86_init_mmx_sse_builtins ();

  if (TARGET_LP64)
    ix86_init_builtins_va_builtins_abi ();

#ifdef SUBTARGET_INIT_BUILTINS
  SUBTARGET_INIT_BUILTINS;
#endif
}

/* Return the ix86 builtin for CODE.  */

static tree
ix86_builtin_decl (unsigned code, bool)
{
  if (code >= IX86_BUILTIN_MAX)
    return error_mark_node;

  return ix86_builtins[code];
}

/* Errors in the source file can cause expand_expr to return const0_rtx
   where we expect a vector.  To avoid crashing, use one of the vector
   clear instructions.  */
static rtx
safe_vector_operand (rtx x, machine_mode mode)
{
  if (x == const0_rtx)
    x = CONST0_RTX (mode);
  return x;
}

/* Fixup modeless constants to fit required mode.  */
static rtx
fixup_modeless_constant (rtx x, machine_mode mode)
{
  if (GET_MODE (x) == VOIDmode)
    x = convert_to_mode (mode, x, 1);
  return x;
}

/* Subroutine of ix86_expand_builtin to take care of binop insns.  */

static rtx
ix86_expand_binop_builtin (enum insn_code icode, tree exp, rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  machine_mode tmode = insn_data[icode].operand[0].mode;
  machine_mode mode0 = insn_data[icode].operand[1].mode;
  machine_mode mode1 = insn_data[icode].operand[2].mode;

  if (VECTOR_MODE_P (mode0))
    op0 = safe_vector_operand (op0, mode0);
  if (VECTOR_MODE_P (mode1))
    op1 = safe_vector_operand (op1, mode1);

  if (optimize || !target
      || GET_MODE (target) != tmode
      || !insn_data[icode].operand[0].predicate (target, tmode))
    target = gen_reg_rtx (tmode);

  if (GET_MODE (op1) == SImode && mode1 == TImode)
    {
      rtx x = gen_reg_rtx (V4SImode);
      emit_insn (gen_sse2_loadd (x, op1));
      op1 = gen_lowpart (TImode, x);
    }

  if (!insn_data[icode].operand[1].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);
  if (!insn_data[icode].operand[2].predicate (op1, mode1))
    op1 = copy_to_mode_reg (mode1, op1);

  pat = GEN_FCN (icode) (target, op0, op1);
  if (! pat)
    return 0;

  emit_insn (pat);

  return target;
}

/* Subroutine of ix86_expand_builtin to take care of 2-4 argument insns.  */

static rtx
ix86_expand_multi_arg_builtin (enum insn_code icode, tree exp, rtx target,
			       enum ix86_builtin_func_type m_type,
			       enum rtx_code sub_code)
{
  rtx pat;
  int i;
  int nargs;
  bool comparison_p = false;
  bool tf_p = false;
  bool last_arg_constant = false;
  int num_memory = 0;
  struct {
    rtx op;
    machine_mode mode;
  } args[4];

  machine_mode tmode = insn_data[icode].operand[0].mode;

  switch (m_type)
    {
    case MULTI_ARG_4_DF2_DI_I:
    case MULTI_ARG_4_DF2_DI_I1:
    case MULTI_ARG_4_SF2_SI_I:
    case MULTI_ARG_4_SF2_SI_I1:
      nargs = 4;
      last_arg_constant = true;
      break;

    case MULTI_ARG_3_SF:
    case MULTI_ARG_3_DF:
    case MULTI_ARG_3_SF2:
    case MULTI_ARG_3_DF2:
    case MULTI_ARG_3_DI:
    case MULTI_ARG_3_SI:
    case MULTI_ARG_3_SI_DI:
    case MULTI_ARG_3_HI:
    case MULTI_ARG_3_HI_SI:
    case MULTI_ARG_3_QI:
    case MULTI_ARG_3_DI2:
    case MULTI_ARG_3_SI2:
    case MULTI_ARG_3_HI2:
    case MULTI_ARG_3_QI2:
      nargs = 3;
      break;

    case MULTI_ARG_2_SF:
    case MULTI_ARG_2_DF:
    case MULTI_ARG_2_DI:
    case MULTI_ARG_2_SI:
    case MULTI_ARG_2_HI:
    case MULTI_ARG_2_QI:
      nargs = 2;
      break;

    case MULTI_ARG_2_DI_IMM:
    case MULTI_ARG_2_SI_IMM:
    case MULTI_ARG_2_HI_IMM:
    case MULTI_ARG_2_QI_IMM:
      nargs = 2;
      last_arg_constant = true;
      break;

    case MULTI_ARG_1_SF:
    case MULTI_ARG_1_DF:
    case MULTI_ARG_1_SF2:
    case MULTI_ARG_1_DF2:
    case MULTI_ARG_1_DI:
    case MULTI_ARG_1_SI:
    case MULTI_ARG_1_HI:
    case MULTI_ARG_1_QI:
    case MULTI_ARG_1_SI_DI:
    case MULTI_ARG_1_HI_DI:
    case MULTI_ARG_1_HI_SI:
    case MULTI_ARG_1_QI_DI:
    case MULTI_ARG_1_QI_SI:
    case MULTI_ARG_1_QI_HI:
      nargs = 1;
      break;

    case MULTI_ARG_2_DI_CMP:
    case MULTI_ARG_2_SI_CMP:
    case MULTI_ARG_2_HI_CMP:
    case MULTI_ARG_2_QI_CMP:
      nargs = 2;
      comparison_p = true;
      break;

    case MULTI_ARG_2_SF_TF:
    case MULTI_ARG_2_DF_TF:
    case MULTI_ARG_2_DI_TF:
    case MULTI_ARG_2_SI_TF:
    case MULTI_ARG_2_HI_TF:
    case MULTI_ARG_2_QI_TF:
      nargs = 2;
      tf_p = true;
      break;

    default:
      gcc_unreachable ();
    }

  if (optimize || !target
      || GET_MODE (target) != tmode
      || !insn_data[icode].operand[0].predicate (target, tmode))
    target = gen_reg_rtx (tmode);
  else if (memory_operand (target, tmode))
    num_memory++;

  gcc_assert (nargs <= 4);

  for (i = 0; i < nargs; i++)
    {
      tree arg = CALL_EXPR_ARG (exp, i);
      rtx op = expand_normal (arg);
      int adjust = (comparison_p) ? 1 : 0;
      machine_mode mode = insn_data[icode].operand[i+adjust+1].mode;

      if (last_arg_constant && i == nargs - 1)
	{
	  if (!insn_data[icode].operand[i + 1].predicate (op, mode))
	    {
	      enum insn_code new_icode = icode;
	      switch (icode)
		{
		case CODE_FOR_xop_vpermil2v2df3:
		case CODE_FOR_xop_vpermil2v4sf3:
		case CODE_FOR_xop_vpermil2v4df3:
		case CODE_FOR_xop_vpermil2v8sf3:
		  error ("the last argument must be a 2-bit immediate");
		  return gen_reg_rtx (tmode);
		case CODE_FOR_xop_rotlv2di3:
		  new_icode = CODE_FOR_rotlv2di3;
		  goto xop_rotl;
		case CODE_FOR_xop_rotlv4si3:
		  new_icode = CODE_FOR_rotlv4si3;
		  goto xop_rotl;
		case CODE_FOR_xop_rotlv8hi3:
		  new_icode = CODE_FOR_rotlv8hi3;
		  goto xop_rotl;
		case CODE_FOR_xop_rotlv16qi3:
		  new_icode = CODE_FOR_rotlv16qi3;
		xop_rotl:
		  if (CONST_INT_P (op))
		    {
		      int mask = GET_MODE_UNIT_BITSIZE (tmode) - 1;
		      op = GEN_INT (INTVAL (op) & mask);
		      gcc_checking_assert
			(insn_data[icode].operand[i + 1].predicate (op, mode));
		    }
		  else
		    {
		      gcc_checking_assert
			(nargs == 2
			 && insn_data[new_icode].operand[0].mode == tmode
			 && insn_data[new_icode].operand[1].mode == tmode
			 && insn_data[new_icode].operand[2].mode == mode
			 && insn_data[new_icode].operand[0].predicate
			    == insn_data[icode].operand[0].predicate
			 && insn_data[new_icode].operand[1].predicate
			    == insn_data[icode].operand[1].predicate);
		      icode = new_icode;
		      goto non_constant;
		    }
		  break;
		default:
		  gcc_unreachable ();
		}
	    }
	}
      else
	{
	non_constant:
	  if (VECTOR_MODE_P (mode))
	    op = safe_vector_operand (op, mode);

	  /* If we aren't optimizing, only allow one memory operand to be
	     generated.  */
	  if (memory_operand (op, mode))
	    num_memory++;

	  gcc_assert (GET_MODE (op) == mode || GET_MODE (op) == VOIDmode);

	  if (optimize
	      || !insn_data[icode].operand[i+adjust+1].predicate (op, mode)
	      || num_memory > 1)
	    op = force_reg (mode, op);
	}

      args[i].op = op;
      args[i].mode = mode;
    }

  switch (nargs)
    {
    case 1:
      pat = GEN_FCN (icode) (target, args[0].op);
      break;

    case 2:
      if (tf_p)
	pat = GEN_FCN (icode) (target, args[0].op, args[1].op,
			       GEN_INT ((int)sub_code));
      else if (! comparison_p)
	pat = GEN_FCN (icode) (target, args[0].op, args[1].op);
      else
	{
	  rtx cmp_op = gen_rtx_fmt_ee (sub_code, GET_MODE (target),
				       args[0].op,
				       args[1].op);

	  pat = GEN_FCN (icode) (target, cmp_op, args[0].op, args[1].op);
	}
      break;

    case 3:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op, args[2].op);
      break;

    case 4:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op, args[2].op, args[3].op);
      break;

    default:
      gcc_unreachable ();
    }

  if (! pat)
    return 0;

  emit_insn (pat);
  return target;
}

/* Subroutine of ix86_expand_args_builtin to take care of scalar unop
   insns with vec_merge.  */

static rtx
ix86_expand_unop_vec_merge_builtin (enum insn_code icode, tree exp,
				    rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  rtx op1, op0 = expand_normal (arg0);
  machine_mode tmode = insn_data[icode].operand[0].mode;
  machine_mode mode0 = insn_data[icode].operand[1].mode;

  if (optimize || !target
      || GET_MODE (target) != tmode
      || !insn_data[icode].operand[0].predicate (target, tmode))
    target = gen_reg_rtx (tmode);

  if (VECTOR_MODE_P (mode0))
    op0 = safe_vector_operand (op0, mode0);

  if ((optimize && !register_operand (op0, mode0))
      || !insn_data[icode].operand[1].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);

  op1 = op0;
  if (!insn_data[icode].operand[2].predicate (op1, mode0))
    op1 = copy_to_mode_reg (mode0, op1);

  pat = GEN_FCN (icode) (target, op0, op1);
  if (! pat)
    return 0;
  emit_insn (pat);
  return target;
}

/* Subroutine of ix86_expand_builtin to take care of comparison insns.  */

static rtx
ix86_expand_sse_compare (const struct builtin_description *d,
			 tree exp, rtx target, bool swap)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  rtx op2;
  machine_mode tmode = insn_data[d->icode].operand[0].mode;
  machine_mode mode0 = insn_data[d->icode].operand[1].mode;
  machine_mode mode1 = insn_data[d->icode].operand[2].mode;
  enum rtx_code comparison = d->comparison;

  if (VECTOR_MODE_P (mode0))
    op0 = safe_vector_operand (op0, mode0);
  if (VECTOR_MODE_P (mode1))
    op1 = safe_vector_operand (op1, mode1);

  /* Swap operands if we have a comparison that isn't available in
     hardware.  */
  if (swap)
    std::swap (op0, op1);

  if (optimize || !target
      || GET_MODE (target) != tmode
      || !insn_data[d->icode].operand[0].predicate (target, tmode))
    target = gen_reg_rtx (tmode);

  if ((optimize && !register_operand (op0, mode0))
      || !insn_data[d->icode].operand[1].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);
  if ((optimize && !register_operand (op1, mode1))
      || !insn_data[d->icode].operand[2].predicate (op1, mode1))
    op1 = copy_to_mode_reg (mode1, op1);

  op2 = gen_rtx_fmt_ee (comparison, mode0, op0, op1);
  pat = GEN_FCN (d->icode) (target, op0, op1, op2);
  if (! pat)
    return 0;
  emit_insn (pat);
  return target;
}

/* Subroutine of ix86_expand_builtin to take care of comi insns.  */

static rtx
ix86_expand_sse_comi (const struct builtin_description *d, tree exp,
		      rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  machine_mode mode0 = insn_data[d->icode].operand[0].mode;
  machine_mode mode1 = insn_data[d->icode].operand[1].mode;
  enum rtx_code comparison = d->comparison;

  if (VECTOR_MODE_P (mode0))
    op0 = safe_vector_operand (op0, mode0);
  if (VECTOR_MODE_P (mode1))
    op1 = safe_vector_operand (op1, mode1);

  /* Swap operands if we have a comparison that isn't available in
     hardware.  */
  if (d->flag & BUILTIN_DESC_SWAP_OPERANDS)
    std::swap (op0, op1);

  target = gen_reg_rtx (SImode);
  emit_move_insn (target, const0_rtx);
  target = gen_rtx_SUBREG (QImode, target, 0);

  if ((optimize && !register_operand (op0, mode0))
      || !insn_data[d->icode].operand[0].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);
  if ((optimize && !register_operand (op1, mode1))
      || !insn_data[d->icode].operand[1].predicate (op1, mode1))
    op1 = copy_to_mode_reg (mode1, op1);

  pat = GEN_FCN (d->icode) (op0, op1);
  if (! pat)
    return 0;
  emit_insn (pat);
  emit_insn (gen_rtx_SET (gen_rtx_STRICT_LOW_PART (VOIDmode, target),
			  gen_rtx_fmt_ee (comparison, QImode,
					  SET_DEST (pat),
					  const0_rtx)));

  return SUBREG_REG (target);
}

/* Subroutines of ix86_expand_args_builtin to take care of round insns.  */

static rtx
ix86_expand_sse_round (const struct builtin_description *d, tree exp,
		       rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  rtx op1, op0 = expand_normal (arg0);
  machine_mode tmode = insn_data[d->icode].operand[0].mode;
  machine_mode mode0 = insn_data[d->icode].operand[1].mode;

  if (optimize || target == 0
      || GET_MODE (target) != tmode
      || !insn_data[d->icode].operand[0].predicate (target, tmode))
    target = gen_reg_rtx (tmode);

  if (VECTOR_MODE_P (mode0))
    op0 = safe_vector_operand (op0, mode0);

  if ((optimize && !register_operand (op0, mode0))
      || !insn_data[d->icode].operand[0].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);

  op1 = GEN_INT (d->comparison);

  pat = GEN_FCN (d->icode) (target, op0, op1);
  if (! pat)
    return 0;
  emit_insn (pat);
  return target;
}

static rtx
ix86_expand_sse_round_vec_pack_sfix (const struct builtin_description *d,
				     tree exp, rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  rtx op2;
  machine_mode tmode = insn_data[d->icode].operand[0].mode;
  machine_mode mode0 = insn_data[d->icode].operand[1].mode;
  machine_mode mode1 = insn_data[d->icode].operand[2].mode;

  if (optimize || target == 0
      || GET_MODE (target) != tmode
      || !insn_data[d->icode].operand[0].predicate (target, tmode))
    target = gen_reg_rtx (tmode);

  op0 = safe_vector_operand (op0, mode0);
  op1 = safe_vector_operand (op1, mode1);

  if ((optimize && !register_operand (op0, mode0))
      || !insn_data[d->icode].operand[0].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);
  if ((optimize && !register_operand (op1, mode1))
      || !insn_data[d->icode].operand[1].predicate (op1, mode1))
    op1 = copy_to_mode_reg (mode1, op1);

  op2 = GEN_INT (d->comparison);

  pat = GEN_FCN (d->icode) (target, op0, op1, op2);
  if (! pat)
    return 0;
  emit_insn (pat);
  return target;
}

/* Subroutine of ix86_expand_builtin to take care of ptest insns.  */

static rtx
ix86_expand_sse_ptest (const struct builtin_description *d, tree exp,
		       rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  machine_mode mode0 = insn_data[d->icode].operand[0].mode;
  machine_mode mode1 = insn_data[d->icode].operand[1].mode;
  enum rtx_code comparison = d->comparison;

  if (VECTOR_MODE_P (mode0))
    op0 = safe_vector_operand (op0, mode0);
  if (VECTOR_MODE_P (mode1))
    op1 = safe_vector_operand (op1, mode1);

  target = gen_reg_rtx (SImode);
  emit_move_insn (target, const0_rtx);
  target = gen_rtx_SUBREG (QImode, target, 0);

  if ((optimize && !register_operand (op0, mode0))
      || !insn_data[d->icode].operand[0].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);
  if ((optimize && !register_operand (op1, mode1))
      || !insn_data[d->icode].operand[1].predicate (op1, mode1))
    op1 = copy_to_mode_reg (mode1, op1);

  pat = GEN_FCN (d->icode) (op0, op1);
  if (! pat)
    return 0;
  emit_insn (pat);
  emit_insn (gen_rtx_SET (gen_rtx_STRICT_LOW_PART (VOIDmode, target),
			  gen_rtx_fmt_ee (comparison, QImode,
					  SET_DEST (pat),
					  const0_rtx)));

  return SUBREG_REG (target);
}

/* Subroutine of ix86_expand_builtin to take care of pcmpestr[im] insns.  */

static rtx
ix86_expand_sse_pcmpestr (const struct builtin_description *d,
			  tree exp, rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  tree arg2 = CALL_EXPR_ARG (exp, 2);
  tree arg3 = CALL_EXPR_ARG (exp, 3);
  tree arg4 = CALL_EXPR_ARG (exp, 4);
  rtx scratch0, scratch1;
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  rtx op2 = expand_normal (arg2);
  rtx op3 = expand_normal (arg3);
  rtx op4 = expand_normal (arg4);
  machine_mode tmode0, tmode1, modev2, modei3, modev4, modei5, modeimm;

  tmode0 = insn_data[d->icode].operand[0].mode;
  tmode1 = insn_data[d->icode].operand[1].mode;
  modev2 = insn_data[d->icode].operand[2].mode;
  modei3 = insn_data[d->icode].operand[3].mode;
  modev4 = insn_data[d->icode].operand[4].mode;
  modei5 = insn_data[d->icode].operand[5].mode;
  modeimm = insn_data[d->icode].operand[6].mode;

  if (VECTOR_MODE_P (modev2))
    op0 = safe_vector_operand (op0, modev2);
  if (VECTOR_MODE_P (modev4))
    op2 = safe_vector_operand (op2, modev4);

  if (!insn_data[d->icode].operand[2].predicate (op0, modev2))
    op0 = copy_to_mode_reg (modev2, op0);
  if (!insn_data[d->icode].operand[3].predicate (op1, modei3))
    op1 = copy_to_mode_reg (modei3, op1);
  if ((optimize && !register_operand (op2, modev4))
      || !insn_data[d->icode].operand[4].predicate (op2, modev4))
    op2 = copy_to_mode_reg (modev4, op2);
  if (!insn_data[d->icode].operand[5].predicate (op3, modei5))
    op3 = copy_to_mode_reg (modei5, op3);

  if (!insn_data[d->icode].operand[6].predicate (op4, modeimm))
    {
      error ("the fifth argument must be an 8-bit immediate");
      return const0_rtx;
    }

  if (d->code == IX86_BUILTIN_PCMPESTRI128)
    {
      if (optimize || !target
	  || GET_MODE (target) != tmode0
	  || !insn_data[d->icode].operand[0].predicate (target, tmode0))
	target = gen_reg_rtx (tmode0);

      scratch1 = gen_reg_rtx (tmode1);

      pat = GEN_FCN (d->icode) (target, scratch1, op0, op1, op2, op3, op4);
    }
  else if (d->code == IX86_BUILTIN_PCMPESTRM128)
    {
      if (optimize || !target
	  || GET_MODE (target) != tmode1
	  || !insn_data[d->icode].operand[1].predicate (target, tmode1))
	target = gen_reg_rtx (tmode1);

      scratch0 = gen_reg_rtx (tmode0);

      pat = GEN_FCN (d->icode) (scratch0, target, op0, op1, op2, op3, op4);
    }
  else
    {
      gcc_assert (d->flag);

      scratch0 = gen_reg_rtx (tmode0);
      scratch1 = gen_reg_rtx (tmode1);

      pat = GEN_FCN (d->icode) (scratch0, scratch1, op0, op1, op2, op3, op4);
    }

  if (! pat)
    return 0;

  emit_insn (pat);

  if (d->flag)
    {
      target = gen_reg_rtx (SImode);
      emit_move_insn (target, const0_rtx);
      target = gen_rtx_SUBREG (QImode, target, 0);

      emit_insn
	(gen_rtx_SET (gen_rtx_STRICT_LOW_PART (VOIDmode, target),
		      gen_rtx_fmt_ee (EQ, QImode,
				      gen_rtx_REG ((machine_mode) d->flag,
						   FLAGS_REG),
				      const0_rtx)));
      return SUBREG_REG (target);
    }
  else
    return target;
}


/* Subroutine of ix86_expand_builtin to take care of pcmpistr[im] insns.  */

static rtx
ix86_expand_sse_pcmpistr (const struct builtin_description *d,
			  tree exp, rtx target)
{
  rtx pat;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  tree arg2 = CALL_EXPR_ARG (exp, 2);
  rtx scratch0, scratch1;
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  rtx op2 = expand_normal (arg2);
  machine_mode tmode0, tmode1, modev2, modev3, modeimm;

  tmode0 = insn_data[d->icode].operand[0].mode;
  tmode1 = insn_data[d->icode].operand[1].mode;
  modev2 = insn_data[d->icode].operand[2].mode;
  modev3 = insn_data[d->icode].operand[3].mode;
  modeimm = insn_data[d->icode].operand[4].mode;

  if (VECTOR_MODE_P (modev2))
    op0 = safe_vector_operand (op0, modev2);
  if (VECTOR_MODE_P (modev3))
    op1 = safe_vector_operand (op1, modev3);

  if (!insn_data[d->icode].operand[2].predicate (op0, modev2))
    op0 = copy_to_mode_reg (modev2, op0);
  if ((optimize && !register_operand (op1, modev3))
      || !insn_data[d->icode].operand[3].predicate (op1, modev3))
    op1 = copy_to_mode_reg (modev3, op1);

  if (!insn_data[d->icode].operand[4].predicate (op2, modeimm))
    {
      error ("the third argument must be an 8-bit immediate");
      return const0_rtx;
    }

  if (d->code == IX86_BUILTIN_PCMPISTRI128)
    {
      if (optimize || !target
	  || GET_MODE (target) != tmode0
	  || !insn_data[d->icode].operand[0].predicate (target, tmode0))
	target = gen_reg_rtx (tmode0);

      scratch1 = gen_reg_rtx (tmode1);

      pat = GEN_FCN (d->icode) (target, scratch1, op0, op1, op2);
    }
  else if (d->code == IX86_BUILTIN_PCMPISTRM128)
    {
      if (optimize || !target
	  || GET_MODE (target) != tmode1
	  || !insn_data[d->icode].operand[1].predicate (target, tmode1))
	target = gen_reg_rtx (tmode1);

      scratch0 = gen_reg_rtx (tmode0);

      pat = GEN_FCN (d->icode) (scratch0, target, op0, op1, op2);
    }
  else
    {
      gcc_assert (d->flag);

      scratch0 = gen_reg_rtx (tmode0);
      scratch1 = gen_reg_rtx (tmode1);

      pat = GEN_FCN (d->icode) (scratch0, scratch1, op0, op1, op2);
    }

  if (! pat)
    return 0;

  emit_insn (pat);

  if (d->flag)
    {
      target = gen_reg_rtx (SImode);
      emit_move_insn (target, const0_rtx);
      target = gen_rtx_SUBREG (QImode, target, 0);

      emit_insn
	(gen_rtx_SET (gen_rtx_STRICT_LOW_PART (VOIDmode, target),
		      gen_rtx_fmt_ee (EQ, QImode,
				      gen_rtx_REG ((machine_mode) d->flag,
						   FLAGS_REG),
				      const0_rtx)));
      return SUBREG_REG (target);
    }
  else
    return target;
}

/* Subroutine of ix86_expand_builtin to take care of insns with
   variable number of operands.  */

static rtx
ix86_expand_args_builtin (const struct builtin_description *d,
			  tree exp, rtx target)
{
  rtx pat, real_target;
  unsigned int i, nargs;
  unsigned int nargs_constant = 0;
  unsigned int mask_pos = 0;
  int num_memory = 0;
  struct
    {
      rtx op;
      machine_mode mode;
    } args[6];
  bool second_arg_count = false;
  enum insn_code icode = d->icode;
  const struct insn_data_d *insn_p = &insn_data[icode];
  machine_mode tmode = insn_p->operand[0].mode;
  machine_mode rmode = VOIDmode;
  bool swap = false;
  enum rtx_code comparison = d->comparison;

  switch ((enum ix86_builtin_func_type) d->flag)
    {
    case V2DF_FTYPE_V2DF_ROUND:
    case V4DF_FTYPE_V4DF_ROUND:
    case V8DF_FTYPE_V8DF_ROUND:
    case V4SF_FTYPE_V4SF_ROUND:
    case V8SF_FTYPE_V8SF_ROUND:
    case V16SF_FTYPE_V16SF_ROUND:
    case V4SI_FTYPE_V4SF_ROUND:
    case V8SI_FTYPE_V8SF_ROUND:
    case V16SI_FTYPE_V16SF_ROUND:
      return ix86_expand_sse_round (d, exp, target);
    case V4SI_FTYPE_V2DF_V2DF_ROUND:
    case V8SI_FTYPE_V4DF_V4DF_ROUND:
    case V16SI_FTYPE_V8DF_V8DF_ROUND:
      return ix86_expand_sse_round_vec_pack_sfix (d, exp, target);
    case INT_FTYPE_V8SF_V8SF_PTEST:
    case INT_FTYPE_V4DI_V4DI_PTEST:
    case INT_FTYPE_V4DF_V4DF_PTEST:
    case INT_FTYPE_V4SF_V4SF_PTEST:
    case INT_FTYPE_V2DI_V2DI_PTEST:
    case INT_FTYPE_V2DF_V2DF_PTEST:
      return ix86_expand_sse_ptest (d, exp, target);
    case FLOAT128_FTYPE_FLOAT128:
    case FLOAT_FTYPE_FLOAT:
    case INT_FTYPE_INT:
    case UINT_FTYPE_UINT:
    case UINT16_FTYPE_UINT16:
    case UINT64_FTYPE_INT:
    case UINT64_FTYPE_UINT64:
    case INT64_FTYPE_INT64:
    case INT64_FTYPE_V4SF:
    case INT64_FTYPE_V2DF:
    case INT_FTYPE_V16QI:
    case INT_FTYPE_V8QI:
    case INT_FTYPE_V8SF:
    case INT_FTYPE_V4DF:
    case INT_FTYPE_V4SF:
    case INT_FTYPE_V2DF:
    case INT_FTYPE_V32QI:
    case V16QI_FTYPE_V16QI:
    case V8SI_FTYPE_V8SF:
    case V8SI_FTYPE_V4SI:
    case V8HI_FTYPE_V8HI:
    case V8HI_FTYPE_V16QI:
    case V8QI_FTYPE_V8QI:
    case V8SF_FTYPE_V8SF:
    case V8SF_FTYPE_V8SI:
    case V8SF_FTYPE_V4SF:
    case V8SF_FTYPE_V8HI:
    case V4SI_FTYPE_V4SI:
    case V4SI_FTYPE_V16QI:
    case V4SI_FTYPE_V4SF:
    case V4SI_FTYPE_V8SI:
    case V4SI_FTYPE_V8HI:
    case V4SI_FTYPE_V4DF:
    case V4SI_FTYPE_V2DF:
    case V4HI_FTYPE_V4HI:
    case V4DF_FTYPE_V4DF:
    case V4DF_FTYPE_V4SI:
    case V4DF_FTYPE_V4SF:
    case V4DF_FTYPE_V2DF:
    case V4SF_FTYPE_V4SF:
    case V4SF_FTYPE_V4SI:
    case V4SF_FTYPE_V8SF:
    case V4SF_FTYPE_V4DF:
    case V4SF_FTYPE_V8HI:
    case V4SF_FTYPE_V2DF:
    case V2DI_FTYPE_V2DI:
    case V2DI_FTYPE_V16QI:
    case V2DI_FTYPE_V8HI:
    case V2DI_FTYPE_V4SI:
    case V2DF_FTYPE_V2DF:
    case V2DF_FTYPE_V4SI:
    case V2DF_FTYPE_V4DF:
    case V2DF_FTYPE_V4SF:
    case V2DF_FTYPE_V2SI:
    case V2SI_FTYPE_V2SI:
    case V2SI_FTYPE_V4SF:
    case V2SI_FTYPE_V2SF:
    case V2SI_FTYPE_V2DF:
    case V2SF_FTYPE_V2SF:
    case V2SF_FTYPE_V2SI:
    case V32QI_FTYPE_V32QI:
    case V32QI_FTYPE_V16QI:
    case V16HI_FTYPE_V16HI:
    case V16HI_FTYPE_V8HI:
    case V8SI_FTYPE_V8SI:
    case V16HI_FTYPE_V16QI:
    case V8SI_FTYPE_V16QI:
    case V4DI_FTYPE_V16QI:
    case V8SI_FTYPE_V8HI:
    case V4DI_FTYPE_V8HI:
    case V4DI_FTYPE_V4SI:
    case V4DI_FTYPE_V2DI:
    case UQI_FTYPE_UQI:
    case UHI_FTYPE_UHI:
    case USI_FTYPE_USI:
    case USI_FTYPE_UQI:
    case USI_FTYPE_UHI:
    case UDI_FTYPE_UDI:
    case UHI_FTYPE_V16QI:
    case USI_FTYPE_V32QI:
    case UDI_FTYPE_V64QI:
    case V16QI_FTYPE_UHI:
    case V32QI_FTYPE_USI:
    case V64QI_FTYPE_UDI:
    case V8HI_FTYPE_UQI:
    case V16HI_FTYPE_UHI:
    case V32HI_FTYPE_USI:
    case V4SI_FTYPE_UQI:
    case V8SI_FTYPE_UQI:
    case V4SI_FTYPE_UHI:
    case V8SI_FTYPE_UHI:
    case UQI_FTYPE_V8HI:
    case UHI_FTYPE_V16HI:
    case USI_FTYPE_V32HI:
    case UQI_FTYPE_V4SI:
    case UQI_FTYPE_V8SI:
    case UHI_FTYPE_V16SI:
    case UQI_FTYPE_V2DI:
    case UQI_FTYPE_V4DI:
    case UQI_FTYPE_V8DI:
    case V16SI_FTYPE_UHI:
    case V2DI_FTYPE_UQI:
    case V4DI_FTYPE_UQI:
    case V16SI_FTYPE_INT:
    case V16SF_FTYPE_V8SF:
    case V16SI_FTYPE_V8SI:
    case V16SF_FTYPE_V4SF:
    case V16SI_FTYPE_V4SI:
    case V16SI_FTYPE_V16SF:
    case V16SI_FTYPE_V16SI:
    case V64QI_FTYPE_V64QI:
    case V32HI_FTYPE_V32HI:
    case V16SF_FTYPE_V16SF:
    case V8DI_FTYPE_UQI:
    case V8DI_FTYPE_V8DI:
    case V8DF_FTYPE_V4DF:
    case V8DF_FTYPE_V2DF:
    case V8DF_FTYPE_V8DF:
    case V4DI_FTYPE_V4DI:
      nargs = 1;
      break;
    case V4SF_FTYPE_V4SF_VEC_MERGE:
    case V2DF_FTYPE_V2DF_VEC_MERGE:
      return ix86_expand_unop_vec_merge_builtin (icode, exp, target);
    case FLOAT128_FTYPE_FLOAT128_FLOAT128:
    case V16QI_FTYPE_V16QI_V16QI:
    case V16QI_FTYPE_V8HI_V8HI:
    case V16SF_FTYPE_V16SF_V16SF:
    case V8QI_FTYPE_V8QI_V8QI:
    case V8QI_FTYPE_V4HI_V4HI:
    case V8HI_FTYPE_V8HI_V8HI:
    case V8HI_FTYPE_V16QI_V16QI:
    case V8HI_FTYPE_V4SI_V4SI:
    case V8SF_FTYPE_V8SF_V8SF:
    case V8SF_FTYPE_V8SF_V8SI:
    case V8DF_FTYPE_V8DF_V8DF:
    case V4SI_FTYPE_V4SI_V4SI:
    case V4SI_FTYPE_V8HI_V8HI:
    case V4SI_FTYPE_V2DF_V2DF:
    case V4HI_FTYPE_V4HI_V4HI:
    case V4HI_FTYPE_V8QI_V8QI:
    case V4HI_FTYPE_V2SI_V2SI:
    case V4DF_FTYPE_V4DF_V4DF:
    case V4DF_FTYPE_V4DF_V4DI:
    case V4SF_FTYPE_V4SF_V4SF:
    case V4SF_FTYPE_V4SF_V4SI:
    case V4SF_FTYPE_V4SF_V2SI:
    case V4SF_FTYPE_V4SF_V2DF:
    case V4SF_FTYPE_V4SF_UINT:
    case V4SF_FTYPE_V4SF_DI:
    case V4SF_FTYPE_V4SF_SI:
    case V2DI_FTYPE_V2DI_V2DI:
    case V2DI_FTYPE_V16QI_V16QI:
    case V2DI_FTYPE_V4SI_V4SI:
    case V2DI_FTYPE_V2DI_V16QI:
    case V2SI_FTYPE_V2SI_V2SI:
    case V2SI_FTYPE_V4HI_V4HI:
    case V2SI_FTYPE_V2SF_V2SF:
    case V2DF_FTYPE_V2DF_V2DF:
    case V2DF_FTYPE_V2DF_V4SF:
    case V2DF_FTYPE_V2DF_V2DI:
    case V2DF_FTYPE_V2DF_DI:
    case V2DF_FTYPE_V2DF_SI:
    case V2DF_FTYPE_V2DF_UINT:
    case V2SF_FTYPE_V2SF_V2SF:
    case V1DI_FTYPE_V1DI_V1DI:
    case V1DI_FTYPE_V8QI_V8QI:
    case V1DI_FTYPE_V2SI_V2SI:
    case V32QI_FTYPE_V16HI_V16HI:
    case V16HI_FTYPE_V8SI_V8SI:
    case V64QI_FTYPE_V64QI_V64QI:
    case V32QI_FTYPE_V32QI_V32QI:
    case V16HI_FTYPE_V32QI_V32QI:
    case V16HI_FTYPE_V16HI_V16HI:
    case V8SI_FTYPE_V4DF_V4DF:
    case V8SI_FTYPE_V8SI_V8SI:
    case V8SI_FTYPE_V16HI_V16HI:
    case V4DI_FTYPE_V4DI_V4DI:
    case V4DI_FTYPE_V8SI_V8SI:
    case V8DI_FTYPE_V64QI_V64QI:
      if (comparison == UNKNOWN)
	return ix86_expand_binop_builtin (icode, exp, target);
      nargs = 2;
      break;
    case V4SF_FTYPE_V4SF_V4SF_SWAP:
    case V2DF_FTYPE_V2DF_V2DF_SWAP:
      gcc_assert (comparison != UNKNOWN);
      nargs = 2;
      swap = true;
      break;
    case V16HI_FTYPE_V16HI_V8HI_COUNT:
    case V16HI_FTYPE_V16HI_SI_COUNT:
    case V8SI_FTYPE_V8SI_V4SI_COUNT:
    case V8SI_FTYPE_V8SI_SI_COUNT:
    case V4DI_FTYPE_V4DI_V2DI_COUNT:
    case V4DI_FTYPE_V4DI_INT_COUNT:
    case V8HI_FTYPE_V8HI_V8HI_COUNT:
    case V8HI_FTYPE_V8HI_SI_COUNT:
    case V4SI_FTYPE_V4SI_V4SI_COUNT:
    case V4SI_FTYPE_V4SI_SI_COUNT:
    case V4HI_FTYPE_V4HI_V4HI_COUNT:
    case V4HI_FTYPE_V4HI_SI_COUNT:
    case V2DI_FTYPE_V2DI_V2DI_COUNT:
    case V2DI_FTYPE_V2DI_SI_COUNT:
    case V2SI_FTYPE_V2SI_V2SI_COUNT:
    case V2SI_FTYPE_V2SI_SI_COUNT:
    case V1DI_FTYPE_V1DI_V1DI_COUNT:
    case V1DI_FTYPE_V1DI_SI_COUNT:
      nargs = 2;
      second_arg_count = true;
      break;
    case V16HI_FTYPE_V16HI_INT_V16HI_UHI_COUNT:
    case V16HI_FTYPE_V16HI_V8HI_V16HI_UHI_COUNT:
    case V16SI_FTYPE_V16SI_INT_V16SI_UHI_COUNT:
    case V16SI_FTYPE_V16SI_V4SI_V16SI_UHI_COUNT:
    case V2DI_FTYPE_V2DI_INT_V2DI_UQI_COUNT:
    case V2DI_FTYPE_V2DI_V2DI_V2DI_UQI_COUNT:
    case V32HI_FTYPE_V32HI_INT_V32HI_USI_COUNT:
    case V32HI_FTYPE_V32HI_V8HI_V32HI_USI_COUNT:
    case V4DI_FTYPE_V4DI_INT_V4DI_UQI_COUNT:
    case V4DI_FTYPE_V4DI_V2DI_V4DI_UQI_COUNT:
    case V4SI_FTYPE_V4SI_INT_V4SI_UQI_COUNT:
    case V4SI_FTYPE_V4SI_V4SI_V4SI_UQI_COUNT:
    case V8DI_FTYPE_V8DI_INT_V8DI_UQI_COUNT:
    case V8DI_FTYPE_V8DI_V2DI_V8DI_UQI_COUNT:
    case V8HI_FTYPE_V8HI_INT_V8HI_UQI_COUNT:
    case V8HI_FTYPE_V8HI_V8HI_V8HI_UQI_COUNT:
    case V8SI_FTYPE_V8SI_INT_V8SI_UQI_COUNT:
    case V8SI_FTYPE_V8SI_V4SI_V8SI_UQI_COUNT:
      nargs = 4;
      second_arg_count = true;
      break;
    case UINT64_FTYPE_UINT64_UINT64:
    case UINT_FTYPE_UINT_UINT:
    case UINT_FTYPE_UINT_USHORT:
    case UINT_FTYPE_UINT_UCHAR:
    case UINT16_FTYPE_UINT16_INT:
    case UINT8_FTYPE_UINT8_INT:
    case UQI_FTYPE_UQI_UQI:
    case UHI_FTYPE_UHI_UHI:
    case USI_FTYPE_USI_USI:
    case UDI_FTYPE_UDI_UDI:
    case V16SI_FTYPE_V8DF_V8DF:
      nargs = 2;
      break;
    case V2DI_FTYPE_V2DI_INT_CONVERT:
      nargs = 2;
      rmode = V1TImode;
      nargs_constant = 1;
      break;
    case V4DI_FTYPE_V4DI_INT_CONVERT:
      nargs = 2;
      rmode = V2TImode;
      nargs_constant = 1;
      break;
    case V8DI_FTYPE_V8DI_INT_CONVERT:
      nargs = 2;
      rmode = V4TImode;
      nargs_constant = 1;
      break;
    case V8HI_FTYPE_V8HI_INT:
    case V8HI_FTYPE_V8SF_INT:
    case V16HI_FTYPE_V16SF_INT:
    case V8HI_FTYPE_V4SF_INT:
    case V8SF_FTYPE_V8SF_INT:
    case V4SF_FTYPE_V16SF_INT:
    case V16SF_FTYPE_V16SF_INT:
    case V4SI_FTYPE_V4SI_INT:
    case V4SI_FTYPE_V8SI_INT:
    case V4HI_FTYPE_V4HI_INT:
    case V4DF_FTYPE_V4DF_INT:
    case V4DF_FTYPE_V8DF_INT:
    case V4SF_FTYPE_V4SF_INT:
    case V4SF_FTYPE_V8SF_INT:
    case V2DI_FTYPE_V2DI_INT:
    case V2DF_FTYPE_V2DF_INT:
    case V2DF_FTYPE_V4DF_INT:
    case V16HI_FTYPE_V16HI_INT:
    case V8SI_FTYPE_V8SI_INT:
    case V16SI_FTYPE_V16SI_INT:
    case V4SI_FTYPE_V16SI_INT:
    case V4DI_FTYPE_V4DI_INT:
    case V2DI_FTYPE_V4DI_INT:
    case V4DI_FTYPE_V8DI_INT:
    case QI_FTYPE_V4SF_INT:
    case QI_FTYPE_V2DF_INT:
    case UQI_FTYPE_UQI_UQI_CONST:
    case UHI_FTYPE_UHI_UQI:
    case USI_FTYPE_USI_UQI:
    case UDI_FTYPE_UDI_UQI:
      nargs = 2;
      nargs_constant = 1;
      break;
    case V16QI_FTYPE_V16QI_V16QI_V16QI:
    case V8SF_FTYPE_V8SF_V8SF_V8SF:
    case V4DF_FTYPE_V4DF_V4DF_V4DF:
    case V4SF_FTYPE_V4SF_V4SF_V4SF:
    case V2DF_FTYPE_V2DF_V2DF_V2DF:
    case V32QI_FTYPE_V32QI_V32QI_V32QI:
    case UHI_FTYPE_V16SI_V16SI_UHI:
    case UQI_FTYPE_V8DI_V8DI_UQI:
    case V16HI_FTYPE_V16SI_V16HI_UHI:
    case V16QI_FTYPE_V16SI_V16QI_UHI:
    case V16QI_FTYPE_V8DI_V16QI_UQI:
    case V16SF_FTYPE_V16SF_V16SF_UHI:
    case V16SF_FTYPE_V4SF_V16SF_UHI:
    case V16SI_FTYPE_SI_V16SI_UHI:
    case V16SI_FTYPE_V16HI_V16SI_UHI:
    case V16SI_FTYPE_V16QI_V16SI_UHI:
    case V8SF_FTYPE_V4SF_V8SF_UQI:
    case V4DF_FTYPE_V2DF_V4DF_UQI:
    case V8SI_FTYPE_V4SI_V8SI_UQI:
    case V8SI_FTYPE_SI_V8SI_UQI:
    case V4SI_FTYPE_V4SI_V4SI_UQI:
    case V4SI_FTYPE_SI_V4SI_UQI:
    case V4DI_FTYPE_V2DI_V4DI_UQI:
    case V4DI_FTYPE_DI_V4DI_UQI:
    case V2DI_FTYPE_V2DI_V2DI_UQI:
    case V2DI_FTYPE_DI_V2DI_UQI:
    case V64QI_FTYPE_V64QI_V64QI_UDI:
    case V64QI_FTYPE_V16QI_V64QI_UDI:
    case V64QI_FTYPE_QI_V64QI_UDI:
    case V32QI_FTYPE_V32QI_V32QI_USI:
    case V32QI_FTYPE_V16QI_V32QI_USI:
    case V32QI_FTYPE_QI_V32QI_USI:
    case V16QI_FTYPE_V16QI_V16QI_UHI:
    case V16QI_FTYPE_QI_V16QI_UHI:
    case V32HI_FTYPE_V8HI_V32HI_USI:
    case V32HI_FTYPE_HI_V32HI_USI:
    case V16HI_FTYPE_V8HI_V16HI_UHI:
    case V16HI_FTYPE_HI_V16HI_UHI:
    case V8HI_FTYPE_V8HI_V8HI_UQI:
    case V8HI_FTYPE_HI_V8HI_UQI:
    case V8SF_FTYPE_V8HI_V8SF_UQI:
    case V4SF_FTYPE_V8HI_V4SF_UQI:
    case V8SI_FTYPE_V8SF_V8SI_UQI:
    case V4SI_FTYPE_V4SF_V4SI_UQI:
    case V4DI_FTYPE_V4SF_V4DI_UQI:
    case V2DI_FTYPE_V4SF_V2DI_UQI:
    case V4SF_FTYPE_V4DI_V4SF_UQI:
    case V4SF_FTYPE_V2DI_V4SF_UQI:
    case V4DF_FTYPE_V4DI_V4DF_UQI:
    case V2DF_FTYPE_V2DI_V2DF_UQI:
    case V16QI_FTYPE_V8HI_V16QI_UQI:
    case V16QI_FTYPE_V16HI_V16QI_UHI:
    case V16QI_FTYPE_V4SI_V16QI_UQI:
    case V16QI_FTYPE_V8SI_V16QI_UQI:
    case V8HI_FTYPE_V4SI_V8HI_UQI:
    case V8HI_FTYPE_V8SI_V8HI_UQI:
    case V16QI_FTYPE_V2DI_V16QI_UQI:
    case V16QI_FTYPE_V4DI_V16QI_UQI:
    case V8HI_FTYPE_V2DI_V8HI_UQI:
    case V8HI_FTYPE_V4DI_V8HI_UQI:
    case V4SI_FTYPE_V2DI_V4SI_UQI:
    case V4SI_FTYPE_V4DI_V4SI_UQI:
    case V32QI_FTYPE_V32HI_V32QI_USI:
    case UHI_FTYPE_V16QI_V16QI_UHI:
    case USI_FTYPE_V32QI_V32QI_USI:
    case UDI_FTYPE_V64QI_V64QI_UDI:
    case UQI_FTYPE_V8HI_V8HI_UQI:
    case UHI_FTYPE_V16HI_V16HI_UHI:
    case USI_FTYPE_V32HI_V32HI_USI:
    case UQI_FTYPE_V4SI_V4SI_UQI:
    case UQI_FTYPE_V8SI_V8SI_UQI:
    case UQI_FTYPE_V2DI_V2DI_UQI:
    case UQI_FTYPE_V4DI_V4DI_UQI:
    case V4SF_FTYPE_V2DF_V4SF_UQI:
    case V4SF_FTYPE_V4DF_V4SF_UQI:
    case V16SI_FTYPE_V16SI_V16SI_UHI:
    case V16SI_FTYPE_V4SI_V16SI_UHI:
    case V2DI_FTYPE_V4SI_V2DI_UQI:
    case V2DI_FTYPE_V8HI_V2DI_UQI:
    case V2DI_FTYPE_V16QI_V2DI_UQI:
    case V4DI_FTYPE_V4DI_V4DI_UQI:
    case V4DI_FTYPE_V4SI_V4DI_UQI:
    case V4DI_FTYPE_V8HI_V4DI_UQI:
    case V4DI_FTYPE_V16QI_V4DI_UQI:
    case V4DI_FTYPE_V4DF_V4DI_UQI:
    case V2DI_FTYPE_V2DF_V2DI_UQI:
    case V4SI_FTYPE_V4DF_V4SI_UQI:
    case V4SI_FTYPE_V2DF_V4SI_UQI:
    case V4SI_FTYPE_V8HI_V4SI_UQI:
    case V4SI_FTYPE_V16QI_V4SI_UQI:
    case V4DI_FTYPE_V4DI_V4DI_V4DI:
    case V8DF_FTYPE_V2DF_V8DF_UQI:
    case V8DF_FTYPE_V4DF_V8DF_UQI:
    case V8DF_FTYPE_V8DF_V8DF_UQI:
    case V8SF_FTYPE_V8SF_V8SF_UQI:
    case V8SF_FTYPE_V8SI_V8SF_UQI:
    case V4DF_FTYPE_V4DF_V4DF_UQI:
    case V4SF_FTYPE_V4SF_V4SF_UQI:
    case V2DF_FTYPE_V2DF_V2DF_UQI:
    case V2DF_FTYPE_V4SF_V2DF_UQI:
    case V2DF_FTYPE_V4SI_V2DF_UQI:
    case V4SF_FTYPE_V4SI_V4SF_UQI:
    case V4DF_FTYPE_V4SF_V4DF_UQI:
    case V4DF_FTYPE_V4SI_V4DF_UQI:
    case V8SI_FTYPE_V8SI_V8SI_UQI:
    case V8SI_FTYPE_V8HI_V8SI_UQI:
    case V8SI_FTYPE_V16QI_V8SI_UQI:
    case V8DF_FTYPE_V8SI_V8DF_UQI:
    case V8DI_FTYPE_DI_V8DI_UQI:
    case V16SF_FTYPE_V8SF_V16SF_UHI:
    case V16SI_FTYPE_V8SI_V16SI_UHI:
    case V16HI_FTYPE_V16HI_V16HI_UHI:
    case V8HI_FTYPE_V16QI_V8HI_UQI:
    case V16HI_FTYPE_V16QI_V16HI_UHI:
    case V32HI_FTYPE_V32HI_V32HI_USI:
    case V32HI_FTYPE_V32QI_V32HI_USI:
    case V8DI_FTYPE_V16QI_V8DI_UQI:
    case V8DI_FTYPE_V2DI_V8DI_UQI:
    case V8DI_FTYPE_V4DI_V8DI_UQI:
    case V8DI_FTYPE_V8DI_V8DI_UQI:
    case V8DI_FTYPE_V8HI_V8DI_UQI:
    case V8DI_FTYPE_V8SI_V8DI_UQI:
    case V8HI_FTYPE_V8DI_V8HI_UQI:
    case V8SI_FTYPE_V8DI_V8SI_UQI:
    case V4SI_FTYPE_V4SI_V4SI_V4SI:
    case V16SI_FTYPE_V16SI_V16SI_V16SI:
    case V8DI_FTYPE_V8DI_V8DI_V8DI:
    case V32HI_FTYPE_V32HI_V32HI_V32HI:
    case V2DI_FTYPE_V2DI_V2DI_V2DI:
    case V16HI_FTYPE_V16HI_V16HI_V16HI:
    case V8SI_FTYPE_V8SI_V8SI_V8SI:
    case V8HI_FTYPE_V8HI_V8HI_V8HI:
      nargs = 3;
      break;
    case V32QI_FTYPE_V32QI_V32QI_INT:
    case V16HI_FTYPE_V16HI_V16HI_INT:
    case V16QI_FTYPE_V16QI_V16QI_INT:
    case V4DI_FTYPE_V4DI_V4DI_INT:
    case V8HI_FTYPE_V8HI_V8HI_INT:
    case V8SI_FTYPE_V8SI_V8SI_INT:
    case V8SI_FTYPE_V8SI_V4SI_INT:
    case V8SF_FTYPE_V8SF_V8SF_INT:
    case V8SF_FTYPE_V8SF_V4SF_INT:
    case V4SI_FTYPE_V4SI_V4SI_INT:
    case V4DF_FTYPE_V4DF_V4DF_INT:
    case V16SF_FTYPE_V16SF_V16SF_INT:
    case V16SF_FTYPE_V16SF_V4SF_INT:
    case V16SI_FTYPE_V16SI_V4SI_INT:
    case V4DF_FTYPE_V4DF_V2DF_INT:
    case V4SF_FTYPE_V4SF_V4SF_INT:
    case V2DI_FTYPE_V2DI_V2DI_INT:
    case V4DI_FTYPE_V4DI_V2DI_INT:
    case V2DF_FTYPE_V2DF_V2DF_INT:
    case UQI_FTYPE_V8DI_V8UDI_INT:
    case UQI_FTYPE_V8DF_V8DF_INT:
    case UQI_FTYPE_V2DF_V2DF_INT:
    case UQI_FTYPE_V4SF_V4SF_INT:
    case UHI_FTYPE_V16SI_V16SI_INT:
    case UHI_FTYPE_V16SF_V16SF_INT:
    case V64QI_FTYPE_V64QI_V64QI_INT:
    case V32HI_FTYPE_V32HI_V32HI_INT:
    case V16SI_FTYPE_V16SI_V16SI_INT:
    case V8DI_FTYPE_V8DI_V8DI_INT:
      nargs = 3;
      nargs_constant = 1;
      break;
    case V4DI_FTYPE_V4DI_V4DI_INT_CONVERT:
      nargs = 3;
      rmode = V4DImode;
      nargs_constant = 1;
      break;
    case V2DI_FTYPE_V2DI_V2DI_INT_CONVERT:
      nargs = 3;
      rmode = V2DImode;
      nargs_constant = 1;
      break;
    case V1DI_FTYPE_V1DI_V1DI_INT_CONVERT:
      nargs = 3;
      rmode = DImode;
      nargs_constant = 1;
      break;
    case V2DI_FTYPE_V2DI_UINT_UINT:
      nargs = 3;
      nargs_constant = 2;
      break;
    case V8DI_FTYPE_V8DI_V8DI_INT_CONVERT:
      nargs = 3;
      rmode = V8DImode;
      nargs_constant = 1;
      break;
    case V8DI_FTYPE_V8DI_V8DI_INT_V8DI_UDI_CONVERT:
      nargs = 5;
      rmode = V8DImode;
      mask_pos = 2;
      nargs_constant = 1;
      break;
    case QI_FTYPE_V8DF_INT_UQI:
    case QI_FTYPE_V4DF_INT_UQI:
    case QI_FTYPE_V2DF_INT_UQI:
    case HI_FTYPE_V16SF_INT_UHI:
    case QI_FTYPE_V8SF_INT_UQI:
    case QI_FTYPE_V4SF_INT_UQI:
    case V4SI_FTYPE_V4SI_V4SI_UHI:
    case V8SI_FTYPE_V8SI_V8SI_UHI:
      nargs = 3;
      mask_pos = 1;
      nargs_constant = 1;
      break;
    case V4DI_FTYPE_V4DI_V4DI_INT_V4DI_USI_CONVERT:
      nargs = 5;
      rmode = V4DImode;
      mask_pos = 2;
      nargs_constant = 1;
      break;
    case V2DI_FTYPE_V2DI_V2DI_INT_V2DI_UHI_CONVERT:
      nargs = 5;
      rmode = V2DImode;
      mask_pos = 2;
      nargs_constant = 1;
      break;
    case V32QI_FTYPE_V32QI_V32QI_V32QI_USI:
    case V32HI_FTYPE_V32HI_V32HI_V32HI_USI:
    case V32HI_FTYPE_V64QI_V64QI_V32HI_USI:
    case V16SI_FTYPE_V32HI_V32HI_V16SI_UHI:
    case V64QI_FTYPE_V64QI_V64QI_V64QI_UDI:
    case V32HI_FTYPE_V32HI_V8HI_V32HI_USI:
    case V16HI_FTYPE_V16HI_V8HI_V16HI_UHI:
    case V8SI_FTYPE_V8SI_V4SI_V8SI_UQI:
    case V4DI_FTYPE_V4DI_V2DI_V4DI_UQI:
    case V64QI_FTYPE_V32HI_V32HI_V64QI_UDI:
    case V32QI_FTYPE_V16HI_V16HI_V32QI_USI:
    case V16QI_FTYPE_V8HI_V8HI_V16QI_UHI:
    case V32HI_FTYPE_V16SI_V16SI_V32HI_USI:
    case V16HI_FTYPE_V8SI_V8SI_V16HI_UHI:
    case V8HI_FTYPE_V4SI_V4SI_V8HI_UQI:
    case V4DF_FTYPE_V4DF_V4DI_V4DF_UQI:
    case V8SF_FTYPE_V8SF_V8SI_V8SF_UQI:
    case V4SF_FTYPE_V4SF_V4SI_V4SF_UQI:
    case V2DF_FTYPE_V2DF_V2DI_V2DF_UQI:
    case V2DI_FTYPE_V4SI_V4SI_V2DI_UQI:
    case V4DI_FTYPE_V8SI_V8SI_V4DI_UQI:
    case V4DF_FTYPE_V4DI_V4DF_V4DF_UQI:
    case V8SF_FTYPE_V8SI_V8SF_V8SF_UQI:
    case V2DF_FTYPE_V2DI_V2DF_V2DF_UQI:
    case V4SF_FTYPE_V4SI_V4SF_V4SF_UQI:
    case V16SF_FTYPE_V16SF_V16SF_V16SF_UHI:
    case V16SF_FTYPE_V16SF_V16SI_V16SF_UHI:
    case V16SF_FTYPE_V16SI_V16SF_V16SF_UHI:
    case V16SI_FTYPE_V16SI_V16SI_V16SI_UHI:
    case V16SI_FTYPE_V16SI_V4SI_V16SI_UHI:
    case V8HI_FTYPE_V8HI_V8HI_V8HI_UQI:
    case V8SI_FTYPE_V8SI_V8SI_V8SI_UQI:
    case V4SI_FTYPE_V4SI_V4SI_V4SI_UQI:
    case V8SF_FTYPE_V8SF_V8SF_V8SF_UQI:
    case V16QI_FTYPE_V16QI_V16QI_V16QI_UHI:
    case V16HI_FTYPE_V16HI_V16HI_V16HI_UHI:
    case V2DI_FTYPE_V2DI_V2DI_V2DI_UQI:
    case V2DF_FTYPE_V2DF_V2DF_V2DF_UQI:
    case V4DI_FTYPE_V4DI_V4DI_V4DI_UQI:
    case V4DF_FTYPE_V4DF_V4DF_V4DF_UQI:
    case V4SF_FTYPE_V4SF_V4SF_V4SF_UQI:
    case V8DF_FTYPE_V8DF_V8DF_V8DF_UQI:
    case V8DF_FTYPE_V8DF_V8DI_V8DF_UQI:
    case V8DF_FTYPE_V8DI_V8DF_V8DF_UQI:
    case V8DI_FTYPE_V16SI_V16SI_V8DI_UQI:
    case V8DI_FTYPE_V8DI_V2DI_V8DI_UQI:
    case V8DI_FTYPE_V8DI_V8DI_V8DI_UQI:
    case V8HI_FTYPE_V16QI_V16QI_V8HI_UQI:
    case V16HI_FTYPE_V32QI_V32QI_V16HI_UHI:
    case V8SI_FTYPE_V16HI_V16HI_V8SI_UQI:
    case V4SI_FTYPE_V8HI_V8HI_V4SI_UQI:
      nargs = 4;
      break;
    case V2DF_FTYPE_V2DF_V2DF_V2DI_INT:
    case V4DF_FTYPE_V4DF_V4DF_V4DI_INT:
    case V4SF_FTYPE_V4SF_V4SF_V4SI_INT:
    case V8SF_FTYPE_V8SF_V8SF_V8SI_INT:
    case V16SF_FTYPE_V16SF_V16SF_V16SI_INT:
      nargs = 4;
      nargs_constant = 1;
      break;
    case UQI_FTYPE_V4DI_V4DI_INT_UQI:
    case UQI_FTYPE_V8SI_V8SI_INT_UQI:
    case QI_FTYPE_V4DF_V4DF_INT_UQI:
    case QI_FTYPE_V8SF_V8SF_INT_UQI:
    case UQI_FTYPE_V2DI_V2DI_INT_UQI:
    case UQI_FTYPE_V4SI_V4SI_INT_UQI:
    case UQI_FTYPE_V2DF_V2DF_INT_UQI:
    case UQI_FTYPE_V4SF_V4SF_INT_UQI:
    case UDI_FTYPE_V64QI_V64QI_INT_UDI:
    case USI_FTYPE_V32QI_V32QI_INT_USI:
    case UHI_FTYPE_V16QI_V16QI_INT_UHI:
    case USI_FTYPE_V32HI_V32HI_INT_USI:
    case UHI_FTYPE_V16HI_V16HI_INT_UHI:
    case UQI_FTYPE_V8HI_V8HI_INT_UQI:
    case V32HI_FTYPE_V32HI_V32HI_V32HI_INT:
    case V16HI_FTYPE_V16HI_V16HI_V16HI_INT:
    case V8HI_FTYPE_V8HI_V8HI_V8HI_INT:
    case V8SI_FTYPE_V8SI_V8SI_V8SI_INT:
    case V4DI_FTYPE_V4DI_V4DI_V4DI_INT:
    case V8DI_FTYPE_V8DI_V8DI_V8DI_INT:
    case V16SI_FTYPE_V16SI_V16SI_V16SI_INT:
    case V2DI_FTYPE_V2DI_V2DI_V2DI_INT:
    case V4SI_FTYPE_V4SI_V4SI_V4SI_INT:
      nargs = 4;
      mask_pos = 1;
      nargs_constant = 1;
      break;
    case V2DI_FTYPE_V2DI_V2DI_UINT_UINT:
      nargs = 4;
      nargs_constant = 2;
      break;
    case UCHAR_FTYPE_UCHAR_UINT_UINT_PUNSIGNED:
    case UCHAR_FTYPE_UCHAR_ULONGLONG_ULONGLONG_PULONGLONG:
      nargs = 4;
      break;
    case UQI_FTYPE_V8DI_V8DI_INT_UQI:
    case UHI_FTYPE_V16SI_V16SI_INT_UHI:
      mask_pos = 1;
      nargs = 4;
      nargs_constant = 1;
      break;
    case V8SF_FTYPE_V8SF_INT_V8SF_UQI:
    case V4SF_FTYPE_V4SF_INT_V4SF_UQI:
    case V2DF_FTYPE_V4DF_INT_V2DF_UQI:
    case V2DI_FTYPE_V4DI_INT_V2DI_UQI:
    case V8SF_FTYPE_V16SF_INT_V8SF_UQI:
    case V8SI_FTYPE_V16SI_INT_V8SI_UQI:
    case V2DF_FTYPE_V8DF_INT_V2DF_UQI:
    case V2DI_FTYPE_V8DI_INT_V2DI_UQI:
    case V4SF_FTYPE_V8SF_INT_V4SF_UQI:
    case V4SI_FTYPE_V8SI_INT_V4SI_UQI:
    case V8HI_FTYPE_V8SF_INT_V8HI_UQI:
    case V8HI_FTYPE_V4SF_INT_V8HI_UQI:
    case V32HI_FTYPE_V32HI_INT_V32HI_USI:
    case V16HI_FTYPE_V16HI_INT_V16HI_UHI:
    case V8HI_FTYPE_V8HI_INT_V8HI_UQI:
    case V4DI_FTYPE_V4DI_INT_V4DI_UQI:
    case V2DI_FTYPE_V2DI_INT_V2DI_UQI:
    case V8SI_FTYPE_V8SI_INT_V8SI_UQI:
    case V4SI_FTYPE_V4SI_INT_V4SI_UQI:
    case V4DF_FTYPE_V4DF_INT_V4DF_UQI:
    case V2DF_FTYPE_V2DF_INT_V2DF_UQI:
    case V8DF_FTYPE_V8DF_INT_V8DF_UQI:
    case V16SF_FTYPE_V16SF_INT_V16SF_UHI:
    case V16HI_FTYPE_V16SF_INT_V16HI_UHI:
    case V16SI_FTYPE_V16SI_INT_V16SI_UHI:
    case V4SI_FTYPE_V16SI_INT_V4SI_UQI:
    case V4DI_FTYPE_V8DI_INT_V4DI_UQI:
    case V4DF_FTYPE_V8DF_INT_V4DF_UQI:
    case V4SF_FTYPE_V16SF_INT_V4SF_UQI:
    case V8DI_FTYPE_V8DI_INT_V8DI_UQI:
      nargs = 4;
      mask_pos = 2;
      nargs_constant = 1;
      break;
    case V16SF_FTYPE_V16SF_V4SF_INT_V16SF_UHI:
    case V16SI_FTYPE_V16SI_V4SI_INT_V16SI_UHI:
    case V8DF_FTYPE_V8DF_V8DF_INT_V8DF_UQI:
    case V8DI_FTYPE_V8DI_V8DI_INT_V8DI_UQI:
    case V16SF_FTYPE_V16SF_V16SF_INT_V16SF_UHI:
    case V16SI_FTYPE_V16SI_V16SI_INT_V16SI_UHI:
    case V4SF_FTYPE_V4SF_V4SF_INT_V4SF_UQI:
    case V2DF_FTYPE_V2DF_V2DF_INT_V2DF_UQI:
    case V8DF_FTYPE_V8DF_V4DF_INT_V8DF_UQI:
    case V8DI_FTYPE_V8DI_V4DI_INT_V8DI_UQI:
    case V4DF_FTYPE_V4DF_V4DF_INT_V4DF_UQI:
    case V8SF_FTYPE_V8SF_V8SF_INT_V8SF_UQI:
    case V8DF_FTYPE_V8DF_V2DF_INT_V8DF_UQI:
    case V8DI_FTYPE_V8DI_V2DI_INT_V8DI_UQI:
    case V8SI_FTYPE_V8SI_V8SI_INT_V8SI_UQI:
    case V4DI_FTYPE_V4DI_V4DI_INT_V4DI_UQI:
    case V4SI_FTYPE_V4SI_V4SI_INT_V4SI_UQI:
    case V2DI_FTYPE_V2DI_V2DI_INT_V2DI_UQI:
    case V32HI_FTYPE_V64QI_V64QI_INT_V32HI_USI:
    case V16HI_FTYPE_V32QI_V32QI_INT_V16HI_UHI:
    case V8HI_FTYPE_V16QI_V16QI_INT_V8HI_UQI:
    case V16SF_FTYPE_V16SF_V8SF_INT_V16SF_UHI:
    case V16SI_FTYPE_V16SI_V8SI_INT_V16SI_UHI:
    case V8SF_FTYPE_V8SF_V4SF_INT_V8SF_UQI:
    case V8SI_FTYPE_V8SI_V4SI_INT_V8SI_UQI:
    case V4DI_FTYPE_V4DI_V2DI_INT_V4DI_UQI:
    case V4DF_FTYPE_V4DF_V2DF_INT_V4DF_UQI:
      nargs = 5;
      mask_pos = 2;
      nargs_constant = 1;
      break;
    case V8DI_FTYPE_V8DI_V8DI_V8DI_INT_UQI:
    case V16SI_FTYPE_V16SI_V16SI_V16SI_INT_UHI:
    case V2DF_FTYPE_V2DF_V2DF_V2DI_INT_UQI:
    case V4SF_FTYPE_V4SF_V4SF_V4SI_INT_UQI:
    case V8SF_FTYPE_V8SF_V8SF_V8SI_INT_UQI:
    case V8SI_FTYPE_V8SI_V8SI_V8SI_INT_UQI:
    case V4DF_FTYPE_V4DF_V4DF_V4DI_INT_UQI:
    case V4DI_FTYPE_V4DI_V4DI_V4DI_INT_UQI:
    case V4SI_FTYPE_V4SI_V4SI_V4SI_INT_UQI:
    case V2DI_FTYPE_V2DI_V2DI_V2DI_INT_UQI:
      nargs = 5;
      mask_pos = 1;
      nargs_constant = 1;
      break;
    case V64QI_FTYPE_V64QI_V64QI_INT_V64QI_UDI:
    case V32QI_FTYPE_V32QI_V32QI_INT_V32QI_USI:
    case V16QI_FTYPE_V16QI_V16QI_INT_V16QI_UHI:
    case V32HI_FTYPE_V32HI_V32HI_INT_V32HI_INT:
    case V16SI_FTYPE_V16SI_V16SI_INT_V16SI_INT:
    case V8DI_FTYPE_V8DI_V8DI_INT_V8DI_INT:
    case V16HI_FTYPE_V16HI_V16HI_INT_V16HI_INT:
    case V8SI_FTYPE_V8SI_V8SI_INT_V8SI_INT:
    case V4DI_FTYPE_V4DI_V4DI_INT_V4DI_INT:
    case V8HI_FTYPE_V8HI_V8HI_INT_V8HI_INT:
    case V4SI_FTYPE_V4SI_V4SI_INT_V4SI_INT:
    case V2DI_FTYPE_V2DI_V2DI_INT_V2DI_INT:
      nargs = 5;
      mask_pos = 1;
      nargs_constant = 2;
      break;

    default:
      gcc_unreachable ();
    }

  gcc_assert (nargs <= ARRAY_SIZE (args));

  if (comparison != UNKNOWN)
    {
      gcc_assert (nargs == 2);
      return ix86_expand_sse_compare (d, exp, target, swap);
    }

  if (rmode == VOIDmode || rmode == tmode)
    {
      if (optimize
	  || target == 0
	  || GET_MODE (target) != tmode
	  || !insn_p->operand[0].predicate (target, tmode))
	target = gen_reg_rtx (tmode);
      else if (memory_operand (target, tmode))
	num_memory++;
      real_target = target;
    }
  else
    {
      real_target = gen_reg_rtx (tmode);
      target = lowpart_subreg (rmode, real_target, tmode);
    }

  for (i = 0; i < nargs; i++)
    {
      tree arg = CALL_EXPR_ARG (exp, i);
      rtx op = expand_normal (arg);
      machine_mode mode = insn_p->operand[i + 1].mode;
      bool match = insn_p->operand[i + 1].predicate (op, mode);

      if (second_arg_count && i == 1)
	{
	  /* SIMD shift insns take either an 8-bit immediate or
	     register as count.  But builtin functions take int as
	     count.  If count doesn't match, we put it in register.
	     The instructions are using 64-bit count, if op is just
	     32-bit, zero-extend it, as negative shift counts
	     are undefined behavior and zero-extension is more
	     efficient.  */
	  if (!match)
	    {
	      if (SCALAR_INT_MODE_P (GET_MODE (op)))
		op = convert_modes (mode, GET_MODE (op), op, 1);
	      else
		op = lowpart_subreg (mode, op, GET_MODE (op));
	      if (!insn_p->operand[i + 1].predicate (op, mode))
		op = copy_to_reg (op);
	    }
	}
      else if ((mask_pos && (nargs - i - mask_pos) == nargs_constant) ||
	       (!mask_pos && (nargs - i) <= nargs_constant))
	{
	  if (!match)
	    switch (icode)
	      {
	      case CODE_FOR_avx_vinsertf128v4di:
	      case CODE_FOR_avx_vextractf128v4di:
		error ("the last argument must be an 1-bit immediate");
		return const0_rtx;

	      case CODE_FOR_avx512f_cmpv8di3_mask:
	      case CODE_FOR_avx512f_cmpv16si3_mask:
	      case CODE_FOR_avx512f_ucmpv8di3_mask:
	      case CODE_FOR_avx512f_ucmpv16si3_mask:
	      case CODE_FOR_avx512vl_cmpv4di3_mask:
	      case CODE_FOR_avx512vl_cmpv8si3_mask:
	      case CODE_FOR_avx512vl_ucmpv4di3_mask:
	      case CODE_FOR_avx512vl_ucmpv8si3_mask:
	      case CODE_FOR_avx512vl_cmpv2di3_mask:
	      case CODE_FOR_avx512vl_cmpv4si3_mask:
	      case CODE_FOR_avx512vl_ucmpv2di3_mask:
	      case CODE_FOR_avx512vl_ucmpv4si3_mask:
		error ("the last argument must be a 3-bit immediate");
		return const0_rtx;

	      case CODE_FOR_sse4_1_roundsd:
	      case CODE_FOR_sse4_1_roundss:

	      case CODE_FOR_sse4_1_roundpd:
	      case CODE_FOR_sse4_1_roundps:
	      case CODE_FOR_avx_roundpd256:
	      case CODE_FOR_avx_roundps256:

	      case CODE_FOR_sse4_1_roundpd_vec_pack_sfix:
	      case CODE_FOR_sse4_1_roundps_sfix:
	      case CODE_FOR_avx_roundpd_vec_pack_sfix256:
	      case CODE_FOR_avx_roundps_sfix256:

	      case CODE_FOR_sse4_1_blendps:
	      case CODE_FOR_avx_blendpd256:
	      case CODE_FOR_avx_vpermilv4df:
	      case CODE_FOR_avx_vpermilv4df_mask:
	      case CODE_FOR_avx512f_getmantv8df_mask:
	      case CODE_FOR_avx512f_getmantv16sf_mask:
	      case CODE_FOR_avx512vl_getmantv8sf_mask:
	      case CODE_FOR_avx512vl_getmantv4df_mask:
	      case CODE_FOR_avx512vl_getmantv4sf_mask:
	      case CODE_FOR_avx512vl_getmantv2df_mask:
	      case CODE_FOR_avx512dq_rangepv8df_mask_round:
	      case CODE_FOR_avx512dq_rangepv16sf_mask_round:
	      case CODE_FOR_avx512dq_rangepv4df_mask:
	      case CODE_FOR_avx512dq_rangepv8sf_mask:
	      case CODE_FOR_avx512dq_rangepv2df_mask:
	      case CODE_FOR_avx512dq_rangepv4sf_mask:
	      case CODE_FOR_avx_shufpd256_mask:
		error ("the last argument must be a 4-bit immediate");
		return const0_rtx;

	      case CODE_FOR_sha1rnds4:
	      case CODE_FOR_sse4_1_blendpd:
	      case CODE_FOR_avx_vpermilv2df:
	      case CODE_FOR_avx_vpermilv2df_mask:
	      case CODE_FOR_xop_vpermil2v2df3:
	      case CODE_FOR_xop_vpermil2v4sf3:
	      case CODE_FOR_xop_vpermil2v4df3:
	      case CODE_FOR_xop_vpermil2v8sf3:
	      case CODE_FOR_avx512f_vinsertf32x4_mask:
	      case CODE_FOR_avx512f_vinserti32x4_mask:
	      case CODE_FOR_avx512f_vextractf32x4_mask:
	      case CODE_FOR_avx512f_vextracti32x4_mask:
	      case CODE_FOR_sse2_shufpd:
	      case CODE_FOR_sse2_shufpd_mask:
	      case CODE_FOR_avx512dq_shuf_f64x2_mask:
	      case CODE_FOR_avx512dq_shuf_i64x2_mask:
	      case CODE_FOR_avx512vl_shuf_i32x4_mask:
	      case CODE_FOR_avx512vl_shuf_f32x4_mask:
		error ("the last argument must be a 2-bit immediate");
		return const0_rtx;

	      case CODE_FOR_avx_vextractf128v4df:
	      case CODE_FOR_avx_vextractf128v8sf:
	      case CODE_FOR_avx_vextractf128v8si:
	      case CODE_FOR_avx_vinsertf128v4df:
	      case CODE_FOR_avx_vinsertf128v8sf:
	      case CODE_FOR_avx_vinsertf128v8si:
	      case CODE_FOR_avx512f_vinsertf64x4_mask:
	      case CODE_FOR_avx512f_vinserti64x4_mask:
	      case CODE_FOR_avx512f_vextractf64x4_mask:
	      case CODE_FOR_avx512f_vextracti64x4_mask:
	      case CODE_FOR_avx512dq_vinsertf32x8_mask:
	      case CODE_FOR_avx512dq_vinserti32x8_mask:
	      case CODE_FOR_avx512vl_vinsertv4df:
	      case CODE_FOR_avx512vl_vinsertv4di:
	      case CODE_FOR_avx512vl_vinsertv8sf:
	      case CODE_FOR_avx512vl_vinsertv8si:
		error ("the last argument must be a 1-bit immediate");
		return const0_rtx;

	      case CODE_FOR_avx_vmcmpv2df3:
	      case CODE_FOR_avx_vmcmpv4sf3:
	      case CODE_FOR_avx_cmpv2df3:
	      case CODE_FOR_avx_cmpv4sf3:
	      case CODE_FOR_avx_cmpv4df3:
	      case CODE_FOR_avx_cmpv8sf3:
	      case CODE_FOR_avx512f_cmpv8df3_mask:
	      case CODE_FOR_avx512f_cmpv16sf3_mask:
	      case CODE_FOR_avx512f_vmcmpv2df3_mask:
	      case CODE_FOR_avx512f_vmcmpv4sf3_mask:
		error ("the last argument must be a 5-bit immediate");
		return const0_rtx;

	      default:
		switch (nargs_constant)
		  {
		  case 2:
		    if ((mask_pos && (nargs - i - mask_pos) == nargs_constant) ||
			(!mask_pos && (nargs - i) == nargs_constant))
		      {
			error ("the next to last argument must be an 8-bit immediate");
			break;
		      }
		    /* FALLTHRU */
		  case 1:
		    error ("the last argument must be an 8-bit immediate");
		    break;
		  default:
		    gcc_unreachable ();
		  }
		return const0_rtx;
	      }
	}
      else
	{
	  if (VECTOR_MODE_P (mode))
	    op = safe_vector_operand (op, mode);

	  /* If we aren't optimizing, only allow one memory operand to
	     be generated.  */
	  if (memory_operand (op, mode))
	    num_memory++;

	  op = fixup_modeless_constant (op, mode);

	  if (GET_MODE (op) == mode || GET_MODE (op) == VOIDmode)
	    {
	      if (optimize || !match || num_memory > 1)
		op = copy_to_mode_reg (mode, op);
	    }
	  else
	    {
	      op = copy_to_reg (op);
	      op = lowpart_subreg (mode, op, GET_MODE (op));
	    }
	}

      args[i].op = op;
      args[i].mode = mode;
    }

  switch (nargs)
    {
    case 1:
      pat = GEN_FCN (icode) (real_target, args[0].op);
      break;
    case 2:
      pat = GEN_FCN (icode) (real_target, args[0].op, args[1].op);
      break;
    case 3:
      pat = GEN_FCN (icode) (real_target, args[0].op, args[1].op,
			     args[2].op);
      break;
    case 4:
      pat = GEN_FCN (icode) (real_target, args[0].op, args[1].op,
			     args[2].op, args[3].op);
      break;
    case 5:
      pat = GEN_FCN (icode) (real_target, args[0].op, args[1].op,
			     args[2].op, args[3].op, args[4].op);
      break;
    case 6:
      pat = GEN_FCN (icode) (real_target, args[0].op, args[1].op,
			     args[2].op, args[3].op, args[4].op,
			     args[5].op);
      break;
    default:
      gcc_unreachable ();
    }

  if (! pat)
    return 0;

  emit_insn (pat);
  return target;
}

/* Transform pattern of following layout:
     (set A
       (unspec [B C] UNSPEC_EMBEDDED_ROUNDING))
     )
   into:
     (set (A B)) */

static rtx
ix86_erase_embedded_rounding (rtx pat)
{
  if (GET_CODE (pat) == INSN)
    pat = PATTERN (pat);

  gcc_assert (GET_CODE (pat) == SET);
  rtx src = SET_SRC (pat);
  gcc_assert (XVECLEN (src, 0) == 2);
  rtx p0 = XVECEXP (src, 0, 0);
  gcc_assert (GET_CODE (src) == UNSPEC
	      && XINT (src, 1) == UNSPEC_EMBEDDED_ROUNDING);
  rtx res = gen_rtx_SET (SET_DEST (pat), p0);
  return res;
}

/* Subroutine of ix86_expand_round_builtin to take care of comi insns
   with rounding.  */
static rtx
ix86_expand_sse_comi_round (const struct builtin_description *d,
			    tree exp, rtx target)
{
  rtx pat, set_dst;
  tree arg0 = CALL_EXPR_ARG (exp, 0);
  tree arg1 = CALL_EXPR_ARG (exp, 1);
  tree arg2 = CALL_EXPR_ARG (exp, 2);
  tree arg3 = CALL_EXPR_ARG (exp, 3);
  rtx op0 = expand_normal (arg0);
  rtx op1 = expand_normal (arg1);
  rtx op2 = expand_normal (arg2);
  rtx op3 = expand_normal (arg3);
  enum insn_code icode = d->icode;
  const struct insn_data_d *insn_p = &insn_data[icode];
  machine_mode mode0 = insn_p->operand[0].mode;
  machine_mode mode1 = insn_p->operand[1].mode;
  enum rtx_code comparison = UNEQ;
  bool need_ucomi = false;

  /* See avxintrin.h for values.  */
  enum rtx_code comi_comparisons[32] =
    {
      UNEQ, GT, GE, UNORDERED, LTGT, UNLE, UNLT, ORDERED, UNEQ, UNLT,
      UNLE, LT, LTGT, GE, GT, LT, UNEQ, GT, GE, UNORDERED, LTGT, UNLE,
      UNLT, ORDERED, UNEQ, UNLT, UNLE, LT, LTGT, GE, GT, LT
    };
  bool need_ucomi_values[32] =
    {
      true,  false, false, true,  true,  false, false, true,
      true,  false, false, true,  true,  false, false, true,
      false, true,  true,  false, false, true,  true,  false,
      false, true,  true,  false, false, true,  true,  false
    };

  if (!CONST_INT_P (op2))
    {
      error ("the third argument must be comparison constant");
      return const0_rtx;
    }
  if (INTVAL (op2) < 0 || INTVAL (op2) >= 32)
    {
      error ("incorrect comparison mode");
      return const0_rtx;
    }

  if (!insn_p->operand[2].predicate (op3, SImode))
    {
      error ("incorrect rounding operand");
      return const0_rtx;
    }

  comparison = comi_comparisons[INTVAL (op2)];
  need_ucomi = need_ucomi_values[INTVAL (op2)];

  if (VECTOR_MODE_P (mode0))
    op0 = safe_vector_operand (op0, mode0);
  if (VECTOR_MODE_P (mode1))
    op1 = safe_vector_operand (op1, mode1);

  target = gen_reg_rtx (SImode);
  emit_move_insn (target, const0_rtx);
  target = gen_rtx_SUBREG (QImode, target, 0);

  if ((optimize && !register_operand (op0, mode0))
      || !insn_p->operand[0].predicate (op0, mode0))
    op0 = copy_to_mode_reg (mode0, op0);
  if ((optimize && !register_operand (op1, mode1))
      || !insn_p->operand[1].predicate (op1, mode1))
    op1 = copy_to_mode_reg (mode1, op1);

  if (need_ucomi)
    icode = icode == CODE_FOR_sse_comi_round
		     ? CODE_FOR_sse_ucomi_round
		     : CODE_FOR_sse2_ucomi_round;

  pat = GEN_FCN (icode) (op0, op1, op3);
  if (! pat)
    return 0;

  /* Rounding operand can be either NO_ROUND or ROUND_SAE at this point.  */
  if (INTVAL (op3) == NO_ROUND)
    {
      pat = ix86_erase_embedded_rounding (pat);
      if (! pat)
	return 0;

      set_dst = SET_DEST (pat);
    }
  else
    {
      gcc_assert (GET_CODE (pat) == SET);
      set_dst = SET_DEST (pat);
    }

  emit_insn (pat);
  emit_insn (gen_rtx_SET (gen_rtx_STRICT_LOW_PART (VOIDmode, target),
			  gen_rtx_fmt_ee (comparison, QImode,
					  set_dst,
					  const0_rtx)));

  return SUBREG_REG (target);
}

static rtx
ix86_expand_round_builtin (const struct builtin_description *d,
			   tree exp, rtx target)
{
  rtx pat;
  unsigned int i, nargs;
  struct
    {
      rtx op;
      machine_mode mode;
    } args[6];
  enum insn_code icode = d->icode;
  const struct insn_data_d *insn_p = &insn_data[icode];
  machine_mode tmode = insn_p->operand[0].mode;
  unsigned int nargs_constant = 0;
  unsigned int redundant_embed_rnd = 0;

  switch ((enum ix86_builtin_func_type) d->flag)
    {
    case UINT64_FTYPE_V2DF_INT:
    case UINT64_FTYPE_V4SF_INT:
    case UINT_FTYPE_V2DF_INT:
    case UINT_FTYPE_V4SF_INT:
    case INT64_FTYPE_V2DF_INT:
    case INT64_FTYPE_V4SF_INT:
    case INT_FTYPE_V2DF_INT:
    case INT_FTYPE_V4SF_INT:
      nargs = 2;
      break;
    case V4SF_FTYPE_V4SF_UINT_INT:
    case V4SF_FTYPE_V4SF_UINT64_INT:
    case V2DF_FTYPE_V2DF_UINT64_INT:
    case V4SF_FTYPE_V4SF_INT_INT:
    case V4SF_FTYPE_V4SF_INT64_INT:
    case V2DF_FTYPE_V2DF_INT64_INT:
    case V4SF_FTYPE_V4SF_V4SF_INT:
    case V2DF_FTYPE_V2DF_V2DF_INT:
    case V4SF_FTYPE_V4SF_V2DF_INT:
    case V2DF_FTYPE_V2DF_V4SF_INT:
      nargs = 3;
      break;
    case V8SF_FTYPE_V8DF_V8SF_QI_INT:
    case V8DF_FTYPE_V8DF_V8DF_QI_INT:
    case V8SI_FTYPE_V8DF_V8SI_QI_INT:
    case V8DI_FTYPE_V8DF_V8DI_QI_INT:
    case V8SF_FTYPE_V8DI_V8SF_QI_INT:
    case V8DF_FTYPE_V8DI_V8DF_QI_INT:
    case V16SF_FTYPE_V16SF_V16SF_HI_INT:
    case V8DI_FTYPE_V8SF_V8DI_QI_INT:
    case V16SF_FTYPE_V16SI_V16SF_HI_INT:
    case V16SI_FTYPE_V16SF_V16SI_HI_INT:
    case V8DF_FTYPE_V8SF_V8DF_QI_INT:
    case V16SF_FTYPE_V16HI_V16SF_HI_INT:
    case V2DF_FTYPE_V2DF_V2DF_V2DF_INT:
    case V4SF_FTYPE_V4SF_V4SF_V4SF_INT:
      nargs = 4;
      break;
    case V4SF_FTYPE_V4SF_V4SF_INT_INT:
    case V2DF_FTYPE_V2DF_V2DF_INT_INT:
      nargs_constant = 2;
      nargs = 4;
      break;
    case INT_FTYPE_V4SF_V4SF_INT_INT:
    case INT_FTYPE_V2DF_V2DF_INT_INT:
      return ix86_expand_sse_comi_round (d, exp, target);
    case V8DF_FTYPE_V8DF_V8DF_V8DF_UQI_INT:
    case V2DF_FTYPE_V2DF_V2DF_V2DF_UQI_INT:
    case V4SF_FTYPE_V4SF_V4SF_V4SF_UQI_INT:
    case V16SF_FTYPE_V16SF_V16SF_V16SF_HI_INT:
    case V2DF_FTYPE_V2DF_V2DF_V2DF_QI_INT:
    case V2DF_FTYPE_V2DF_V4SF_V2DF_QI_INT:
    case V4SF_FTYPE_V4SF_V4SF_V4SF_QI_INT:
    case V4SF_FTYPE_V4SF_V2DF_V4SF_QI_INT:
      nargs = 5;
      break;
    case V16SF_FTYPE_V16SF_INT_V16SF_HI_INT:
    case V8DF_FTYPE_V8DF_INT_V8DF_QI_INT:
      nargs_constant = 4;
      nargs = 5;
      break;
    case UQI_FTYPE_V8DF_V8DF_INT_UQI_INT:
    case UQI_FTYPE_V2DF_V2DF_INT_UQI_INT:
    case UHI_FTYPE_V16SF_V16SF_INT_UHI_INT:
    case UQI_FTYPE_V4SF_V4SF_INT_UQI_INT:
      nargs_constant = 3;
      nargs = 5;
      break;
    case V16SF_FTYPE_V16SF_V16SF_INT_V16SF_HI_INT:
    case V8DF_FTYPE_V8DF_V8DF_INT_V8DF_QI_INT:
    case V4SF_FTYPE_V4SF_V4SF_INT_V4SF_QI_INT:
    case V2DF_FTYPE_V2DF_V2DF_INT_V2DF_QI_INT:
    case V2DF_FTYPE_V2DF_V2DF_INT_V2DF_UQI_INT:
    case V4SF_FTYPE_V4SF_V4SF_INT_V4SF_UQI_INT:
      nargs = 6;
      nargs_constant = 4;
      break;
    case V8DF_FTYPE_V8DF_V8DF_V8DI_INT_QI_INT:
    case V16SF_FTYPE_V16SF_V16SF_V16SI_INT_HI_INT:
    case V2DF_FTYPE_V2DF_V2DF_V2DI_INT_QI_INT:
    case V4SF_FTYPE_V4SF_V4SF_V4SI_INT_QI_INT:
      nargs = 6;
      nargs_constant = 3;
      break;
    default:
      gcc_unreachable ();
    }
  gcc_assert (nargs <= ARRAY_SIZE (args));

  if (optimize
      || target == 0
      || GET_MODE (target) != tmode
      || !insn_p->operand[0].predicate (target, tmode))
    target = gen_reg_rtx (tmode);

  for (i = 0; i < nargs; i++)
    {
      tree arg = CALL_EXPR_ARG (exp, i);
      rtx op = expand_normal (arg);
      machine_mode mode = insn_p->operand[i + 1].mode;
      bool match = insn_p->operand[i + 1].predicate (op, mode);

      if (i == nargs - nargs_constant)
	{
	  if (!match)
	    {
	      switch (icode)
		{
		case CODE_FOR_avx512f_getmantv8df_mask_round:
		case CODE_FOR_avx512f_getmantv16sf_mask_round:
		case CODE_FOR_avx512f_vgetmantv2df_round:
		case CODE_FOR_avx512f_vgetmantv2df_mask_round:
		case CODE_FOR_avx512f_vgetmantv4sf_round:
		case CODE_FOR_avx512f_vgetmantv4sf_mask_round:
		  error ("the immediate argument must be a 4-bit immediate");
		  return const0_rtx;
		case CODE_FOR_avx512f_cmpv8df3_mask_round:
		case CODE_FOR_avx512f_cmpv16sf3_mask_round:
		case CODE_FOR_avx512f_vmcmpv2df3_mask_round:
		case CODE_FOR_avx512f_vmcmpv4sf3_mask_round:
		  error ("the immediate argument must be a 5-bit immediate");
		  return const0_rtx;
		default:
		  error ("the immediate argument must be an 8-bit immediate");
		  return const0_rtx;
		}
	    }
	}
      else if (i == nargs-1)
	{
	  if (!insn_p->operand[nargs].predicate (op, SImode))
	    {
	      error ("incorrect rounding operand");
	      return const0_rtx;
	    }

	  /* If there is no rounding use normal version of the pattern.  */
	  if (INTVAL (op) == NO_ROUND)
	    redundant_embed_rnd = 1;
	}
      else
	{
	  if (VECTOR_MODE_P (mode))
	    op = safe_vector_operand (op, mode);

	  op = fixup_modeless_constant (op, mode);

	  if (GET_MODE (op) == mode || GET_MODE (op) == VOIDmode)
	    {
	      if (optimize || !match)
		op = copy_to_mode_reg (mode, op);
	    }
	  else
	    {
	      op = copy_to_reg (op);
	      op = lowpart_subreg (mode, op, GET_MODE (op));
	    }
	}

      args[i].op = op;
      args[i].mode = mode;
    }

  switch (nargs)
    {
    case 1:
      pat = GEN_FCN (icode) (target, args[0].op);
      break;
    case 2:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op);
      break;
    case 3:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op,
			     args[2].op);
      break;
    case 4:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op,
			     args[2].op, args[3].op);
      break;
    case 5:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op,
			     args[2].op, args[3].op, args[4].op);
      break;
    case 6:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op,
			     args[2].op, args[3].op, args[4].op,
			     args[5].op);
      break;
    default:
      gcc_unreachable ();
    }

  if (!pat)
    return 0;

  if (redundant_embed_rnd)
    pat = ix86_erase_embedded_rounding (pat);

  emit_insn (pat);
  return target;
}

/* Subroutine of ix86_expand_builtin to take care of special insns
   with variable number of operands.  */

static rtx
ix86_expand_special_args_builtin (const struct builtin_description *d,
				  tree exp, rtx target)
{
  tree arg;
  rtx pat, op;
  unsigned int i, nargs, arg_adjust, memory;
  bool aligned_mem = false;
  struct
    {
      rtx op;
      machine_mode mode;
    } args[3];
  enum insn_code icode = d->icode;
  bool last_arg_constant = false;
  const struct insn_data_d *insn_p = &insn_data[icode];
  machine_mode tmode = insn_p->operand[0].mode;
  enum { load, store } klass;

  switch ((enum ix86_builtin_func_type) d->flag)
    {
    case VOID_FTYPE_VOID:
      emit_insn (GEN_FCN (icode) (target));
      return 0;
    case VOID_FTYPE_UINT64:
    case VOID_FTYPE_UNSIGNED:
      nargs = 0;
      klass = store;
      memory = 0;
      break;

    case INT_FTYPE_VOID:
    case USHORT_FTYPE_VOID:
    case UINT64_FTYPE_VOID:
    case UINT_FTYPE_VOID:
    case UNSIGNED_FTYPE_VOID:
      nargs = 0;
      klass = load;
      memory = 0;
      break;
    case UINT64_FTYPE_PUNSIGNED:
    case V2DI_FTYPE_PV2DI:
    case V4DI_FTYPE_PV4DI:
    case V32QI_FTYPE_PCCHAR:
    case V16QI_FTYPE_PCCHAR:
    case V8SF_FTYPE_PCV4SF:
    case V8SF_FTYPE_PCFLOAT:
    case V4SF_FTYPE_PCFLOAT:
    case V4DF_FTYPE_PCV2DF:
    case V4DF_FTYPE_PCDOUBLE:
    case V2DF_FTYPE_PCDOUBLE:
    case VOID_FTYPE_PVOID:
    case V8DI_FTYPE_PV8DI:
      nargs = 1;
      klass = load;
      memory = 0;
      switch (icode)
	{
	case CODE_FOR_sse4_1_movntdqa:
	case CODE_FOR_avx2_movntdqa:
	case CODE_FOR_avx512f_movntdqa:
	  aligned_mem = true;
	  break;
	default:
	  break;
	}
      break;
    case VOID_FTYPE_PV2SF_V4SF:
    case VOID_FTYPE_PV8DI_V8DI:
    case VOID_FTYPE_PV4DI_V4DI:
    case VOID_FTYPE_PV2DI_V2DI:
    case VOID_FTYPE_PCHAR_V32QI:
    case VOID_FTYPE_PCHAR_V16QI:
    case VOID_FTYPE_PFLOAT_V16SF:
    case VOID_FTYPE_PFLOAT_V8SF:
    case VOID_FTYPE_PFLOAT_V4SF:
    case VOID_FTYPE_PDOUBLE_V8DF:
    case VOID_FTYPE_PDOUBLE_V4DF:
    case VOID_FTYPE_PDOUBLE_V2DF:
    case VOID_FTYPE_PLONGLONG_LONGLONG:
    case VOID_FTYPE_PULONGLONG_ULONGLONG:
    case VOID_FTYPE_PUNSIGNED_UNSIGNED:
    case VOID_FTYPE_PINT_INT:
      nargs = 1;
      klass = store;
      /* Reserve memory operand for target.  */
      memory = ARRAY_SIZE (args);
      switch (icode)
	{
	/* These builtins and instructions require the memory
	   to be properly aligned.  */
	case CODE_FOR_avx_movntv4di:
	case CODE_FOR_sse2_movntv2di:
	case CODE_FOR_avx_movntv8sf:
	case CODE_FOR_sse_movntv4sf:
	case CODE_FOR_sse4a_vmmovntv4sf:
	case CODE_FOR_avx_movntv4df:
	case CODE_FOR_sse2_movntv2df:
	case CODE_FOR_sse4a_vmmovntv2df:
	case CODE_FOR_sse2_movntidi:
	case CODE_FOR_sse_movntq:
	case CODE_FOR_sse2_movntisi:
	case CODE_FOR_avx512f_movntv16sf:
	case CODE_FOR_avx512f_movntv8df:
	case CODE_FOR_avx512f_movntv8di:
	  aligned_mem = true;
	  break;
	default:
	  break;
	}
      break;
    case VOID_FTYPE_PVOID_PCVOID:
	nargs = 1;
	klass = store;
	memory = 0;

	break;
    case V4SF_FTYPE_V4SF_PCV2SF:
    case V2DF_FTYPE_V2DF_PCDOUBLE:
      nargs = 2;
      klass = load;
      memory = 1;
      break;
    case V8SF_FTYPE_PCV8SF_V8SI:
    case V4DF_FTYPE_PCV4DF_V4DI:
    case V4SF_FTYPE_PCV4SF_V4SI:
    case V2DF_FTYPE_PCV2DF_V2DI:
    case V8SI_FTYPE_PCV8SI_V8SI:
    case V4DI_FTYPE_PCV4DI_V4DI:
    case V4SI_FTYPE_PCV4SI_V4SI:
    case V2DI_FTYPE_PCV2DI_V2DI:
    case VOID_FTYPE_INT_INT64:
      nargs = 2;
      klass = load;
      memory = 0;
      break;
    case VOID_FTYPE_PV8DF_V8DF_UQI:
    case VOID_FTYPE_PV4DF_V4DF_UQI:
    case VOID_FTYPE_PV2DF_V2DF_UQI:
    case VOID_FTYPE_PV16SF_V16SF_UHI:
    case VOID_FTYPE_PV8SF_V8SF_UQI:
    case VOID_FTYPE_PV4SF_V4SF_UQI:
    case VOID_FTYPE_PV8DI_V8DI_UQI:
    case VOID_FTYPE_PV4DI_V4DI_UQI:
    case VOID_FTYPE_PV2DI_V2DI_UQI:
    case VOID_FTYPE_PV16SI_V16SI_UHI:
    case VOID_FTYPE_PV8SI_V8SI_UQI:
    case VOID_FTYPE_PV4SI_V4SI_UQI:
    case VOID_FTYPE_PV64QI_V64QI_UDI:
    case VOID_FTYPE_PV32HI_V32HI_USI:
    case VOID_FTYPE_PV32QI_V32QI_USI:
    case VOID_FTYPE_PV16QI_V16QI_UHI:
    case VOID_FTYPE_PV16HI_V16HI_UHI:
    case VOID_FTYPE_PV8HI_V8HI_UQI:
      switch (icode)
	{
	/* These builtins and instructions require the memory
	   to be properly aligned.  */
	case CODE_FOR_avx512f_storev16sf_mask:
	case CODE_FOR_avx512f_storev16si_mask:
	case CODE_FOR_avx512f_storev8df_mask:
	case CODE_FOR_avx512f_storev8di_mask:
	case CODE_FOR_avx512vl_storev8sf_mask:
	case CODE_FOR_avx512vl_storev8si_mask:
	case CODE_FOR_avx512vl_storev4df_mask:
	case CODE_FOR_avx512vl_storev4di_mask:
	case CODE_FOR_avx512vl_storev4sf_mask:
	case CODE_FOR_avx512vl_storev4si_mask:
	case CODE_FOR_avx512vl_storev2df_mask:
	case CODE_FOR_avx512vl_storev2di_mask:
	  aligned_mem = true;
	  break;
	default:
	  break;
	}
      /* FALLTHRU */
    case VOID_FTYPE_PV8SF_V8SI_V8SF:
    case VOID_FTYPE_PV4DF_V4DI_V4DF:
    case VOID_FTYPE_PV4SF_V4SI_V4SF:
    case VOID_FTYPE_PV2DF_V2DI_V2DF:
    case VOID_FTYPE_PV8SI_V8SI_V8SI:
    case VOID_FTYPE_PV4DI_V4DI_V4DI:
    case VOID_FTYPE_PV4SI_V4SI_V4SI:
    case VOID_FTYPE_PV2DI_V2DI_V2DI:
    case VOID_FTYPE_PV8SI_V8DI_UQI:
    case VOID_FTYPE_PV8HI_V8DI_UQI:
    case VOID_FTYPE_PV16HI_V16SI_UHI:
    case VOID_FTYPE_PV16QI_V8DI_UQI:
    case VOID_FTYPE_PV16QI_V16SI_UHI:
    case VOID_FTYPE_PV4SI_V4DI_UQI:
    case VOID_FTYPE_PV4SI_V2DI_UQI:
    case VOID_FTYPE_PV8HI_V4DI_UQI:
    case VOID_FTYPE_PV8HI_V2DI_UQI:
    case VOID_FTYPE_PV8HI_V8SI_UQI:
    case VOID_FTYPE_PV8HI_V4SI_UQI:
    case VOID_FTYPE_PV16QI_V4DI_UQI:
    case VOID_FTYPE_PV16QI_V2DI_UQI:
    case VOID_FTYPE_PV16QI_V8SI_UQI:
    case VOID_FTYPE_PV16QI_V4SI_UQI:
    case VOID_FTYPE_PCHAR_V64QI_UDI:
    case VOID_FTYPE_PCHAR_V32QI_USI:
    case VOID_FTYPE_PCHAR_V16QI_UHI:
    case VOID_FTYPE_PSHORT_V32HI_USI:
    case VOID_FTYPE_PSHORT_V16HI_UHI:
    case VOID_FTYPE_PSHORT_V8HI_UQI:
    case VOID_FTYPE_PINT_V16SI_UHI:
    case VOID_FTYPE_PINT_V8SI_UQI:
    case VOID_FTYPE_PINT_V4SI_UQI:
    case VOID_FTYPE_PINT64_V8DI_UQI:
    case VOID_FTYPE_PINT64_V4DI_UQI:
    case VOID_FTYPE_PINT64_V2DI_UQI:
    case VOID_FTYPE_PDOUBLE_V8DF_UQI:
    case VOID_FTYPE_PDOUBLE_V4DF_UQI:
    case VOID_FTYPE_PDOUBLE_V2DF_UQI:
    case VOID_FTYPE_PFLOAT_V16SF_UHI:
    case VOID_FTYPE_PFLOAT_V8SF_UQI:
    case VOID_FTYPE_PFLOAT_V4SF_UQI:
    case VOID_FTYPE_PV32QI_V32HI_USI:
    case VOID_FTYPE_PV16QI_V16HI_UHI:
    case VOID_FTYPE_PV8QI_V8HI_UQI:
      nargs = 2;
      klass = store;
      /* Reserve memory operand for target.  */
      memory = ARRAY_SIZE (args);
      break;
    case V4SF_FTYPE_PCV4SF_V4SF_UQI:
    case V8SF_FTYPE_PCV8SF_V8SF_UQI:
    case V16SF_FTYPE_PCV16SF_V16SF_UHI:
    case V4SI_FTYPE_PCV4SI_V4SI_UQI:
    case V8SI_FTYPE_PCV8SI_V8SI_UQI:
    case V16SI_FTYPE_PCV16SI_V16SI_UHI:
    case V2DF_FTYPE_PCV2DF_V2DF_UQI:
    case V4DF_FTYPE_PCV4DF_V4DF_UQI:
    case V8DF_FTYPE_PCV8DF_V8DF_UQI:
    case V2DI_FTYPE_PCV2DI_V2DI_UQI:
    case V4DI_FTYPE_PCV4DI_V4DI_UQI:
    case V8DI_FTYPE_PCV8DI_V8DI_UQI:
    case V64QI_FTYPE_PCV64QI_V64QI_UDI:
    case V32HI_FTYPE_PCV32HI_V32HI_USI:
    case V32QI_FTYPE_PCV32QI_V32QI_USI:
    case V16QI_FTYPE_PCV16QI_V16QI_UHI:
    case V16HI_FTYPE_PCV16HI_V16HI_UHI:
    case V8HI_FTYPE_PCV8HI_V8HI_UQI:
      switch (icode)
	{
	/* These builtins and instructions require the memory
	   to be properly aligned.  */
	case CODE_FOR_avx512f_loadv16sf_mask:
	case CODE_FOR_avx512f_loadv16si_mask:
	case CODE_FOR_avx512f_loadv8df_mask:
	case CODE_FOR_avx512f_loadv8di_mask:
	case CODE_FOR_avx512vl_loadv8sf_mask:
	case CODE_FOR_avx512vl_loadv8si_mask:
	case CODE_FOR_avx512vl_loadv4df_mask:
	case CODE_FOR_avx512vl_loadv4di_mask:
	case CODE_FOR_avx512vl_loadv4sf_mask:
	case CODE_FOR_avx512vl_loadv4si_mask:
	case CODE_FOR_avx512vl_loadv2df_mask:
	case CODE_FOR_avx512vl_loadv2di_mask:
	case CODE_FOR_avx512bw_loadv64qi_mask:
	case CODE_FOR_avx512vl_loadv32qi_mask:
	case CODE_FOR_avx512vl_loadv16qi_mask:
	case CODE_FOR_avx512bw_loadv32hi_mask:
	case CODE_FOR_avx512vl_loadv16hi_mask:
	case CODE_FOR_avx512vl_loadv8hi_mask:
	  aligned_mem = true;
	  break;
	default:
	  break;
	}
      /* FALLTHRU */
    case V64QI_FTYPE_PCCHAR_V64QI_UDI:
    case V32QI_FTYPE_PCCHAR_V32QI_USI:
    case V16QI_FTYPE_PCCHAR_V16QI_UHI:
    case V32HI_FTYPE_PCSHORT_V32HI_USI:
    case V16HI_FTYPE_PCSHORT_V16HI_UHI:
    case V8HI_FTYPE_PCSHORT_V8HI_UQI:
    case V16SI_FTYPE_PCINT_V16SI_UHI:
    case V8SI_FTYPE_PCINT_V8SI_UQI:
    case V4SI_FTYPE_PCINT_V4SI_UQI:
    case V8DI_FTYPE_PCINT64_V8DI_UQI:
    case V4DI_FTYPE_PCINT64_V4DI_UQI:
    case V2DI_FTYPE_PCINT64_V2DI_UQI:
    case V8DF_FTYPE_PCDOUBLE_V8DF_UQI:
    case V4DF_FTYPE_PCDOUBLE_V4DF_UQI:
    case V2DF_FTYPE_PCDOUBLE_V2DF_UQI:
    case V16SF_FTYPE_PCFLOAT_V16SF_UHI:
    case V8SF_FTYPE_PCFLOAT_V8SF_UQI:
    case V4SF_FTYPE_PCFLOAT_V4SF_UQI:
      nargs = 3;
      klass = load;
      memory = 0;
      break;
    case VOID_FTYPE_UINT_UINT_UINT:
    case VOID_FTYPE_UINT64_UINT_UINT:
    case UCHAR_FTYPE_UINT_UINT_UINT:
    case UCHAR_FTYPE_UINT64_UINT_UINT:
      nargs = 3;
      klass = load;
      memory = ARRAY_SIZE (args);
      last_arg_constant = true;
      break;
    default:
      gcc_unreachable ();
    }

  gcc_assert (nargs <= ARRAY_SIZE (args));

  if (klass == store)
    {
      arg = CALL_EXPR_ARG (exp, 0);
      op = expand_normal (arg);
      gcc_assert (target == 0);
      if (memory)
	{
	  op = ix86_zero_extend_to_Pmode (op);
	  target = gen_rtx_MEM (tmode, op);
	  /* target at this point has just BITS_PER_UNIT MEM_ALIGN
	     on it.  Try to improve it using get_pointer_alignment,
	     and if the special builtin is one that requires strict
	     mode alignment, also from it's GET_MODE_ALIGNMENT.
	     Failure to do so could lead to ix86_legitimate_combined_insn
	     rejecting all changes to such insns.  */
	  unsigned int align = get_pointer_alignment (arg);
	  if (aligned_mem && align < GET_MODE_ALIGNMENT (tmode))
	    align = GET_MODE_ALIGNMENT (tmode);
	  if (MEM_ALIGN (target) < align)
	    set_mem_align (target, align);
	}
      else
	target = force_reg (tmode, op);
      arg_adjust = 1;
    }
  else
    {
      arg_adjust = 0;
      if (optimize
	  || target == 0
	  || !register_operand (target, tmode)
	  || GET_MODE (target) != tmode)
	target = gen_reg_rtx (tmode);
    }

  for (i = 0; i < nargs; i++)
    {
      machine_mode mode = insn_p->operand[i + 1].mode;
      bool match;

      arg = CALL_EXPR_ARG (exp, i + arg_adjust);
      op = expand_normal (arg);
      match = insn_p->operand[i + 1].predicate (op, mode);

      if (last_arg_constant && (i + 1) == nargs)
	{
	  if (!match)
	    {
	      if (icode == CODE_FOR_lwp_lwpvalsi3
		  || icode == CODE_FOR_lwp_lwpinssi3
		  || icode == CODE_FOR_lwp_lwpvaldi3
		  || icode == CODE_FOR_lwp_lwpinsdi3)
		error ("the last argument must be a 32-bit immediate");
	      else
		error ("the last argument must be an 8-bit immediate");
	      return const0_rtx;
	    }
	}
      else
	{
	  if (i == memory)
	    {
	      /* This must be the memory operand.  */
	      op = ix86_zero_extend_to_Pmode (op);
	      op = gen_rtx_MEM (mode, op);
	      /* op at this point has just BITS_PER_UNIT MEM_ALIGN
		 on it.  Try to improve it using get_pointer_alignment,
		 and if the special builtin is one that requires strict
		 mode alignment, also from it's GET_MODE_ALIGNMENT.
		 Failure to do so could lead to ix86_legitimate_combined_insn
		 rejecting all changes to such insns.  */
	      unsigned int align = get_pointer_alignment (arg);
	      if (aligned_mem && align < GET_MODE_ALIGNMENT (mode))
		align = GET_MODE_ALIGNMENT (mode);
	      if (MEM_ALIGN (op) < align)
		set_mem_align (op, align);
	    }
	  else
	    {
	      /* This must be register.  */
	      if (VECTOR_MODE_P (mode))
		op = safe_vector_operand (op, mode);

	      op = fixup_modeless_constant (op, mode);

	      if (GET_MODE (op) == mode || GET_MODE (op) == VOIDmode)
		op = copy_to_mode_reg (mode, op);
	      else
	        {
	          op = copy_to_reg (op);
	          op = lowpart_subreg (mode, op, GET_MODE (op));
	        }
	    }
	}

      args[i].op = op;
      args[i].mode = mode;
    }

  switch (nargs)
    {
    case 0:
      pat = GEN_FCN (icode) (target);
      break;
    case 1:
      pat = GEN_FCN (icode) (target, args[0].op);
      break;
    case 2:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op);
      break;
    case 3:
      pat = GEN_FCN (icode) (target, args[0].op, args[1].op, args[2].op);
      break;
    default:
      gcc_unreachable ();
    }

  if (! pat)
    return 0;
  emit_insn (pat);
  return klass == store ? 0 : target;
}

/* Return the integer constant in ARG.  Constrain it to be in the range
   of the subparts of VEC_TYPE; issue an error if not.  */

static int
get_element_number (tree vec_type, tree arg)
{
  unsigned HOST_WIDE_INT elt, max = TYPE_VECTOR_SUBPARTS (vec_type) - 1;

  if (!tree_fits_uhwi_p (arg)
      || (elt = tree_to_uhwi (arg), elt > max))
    {
      error ("selector must be an integer constant in the range 0..%wi", max);
      return 0;
    }

  return elt;
}

/* A subroutine of ix86_expand_builtin.  These builtins are a wrapper around
   ix86_expand_vector_init.  We DO have language-level syntax for this, in
   the form of  (type){ init-list }.  Except that since we can't place emms
   instructions from inside the compiler, we can't allow the use of MMX
   registers unless the user explicitly asks for it.  So we do *not* define
   vec_set/vec_extract/vec_init patterns for MMX modes in mmx.md.  Instead
   we have builtins invoked by mmintrin.h that gives us license to emit
   these sorts of instructions.  */

static rtx
ix86_expand_vec_init_builtin (tree type, tree exp, rtx target)
{
  machine_mode tmode = TYPE_MODE (type);
  machine_mode inner_mode = GET_MODE_INNER (tmode);
  int i, n_elt = GET_MODE_NUNITS (tmode);
  rtvec v = rtvec_alloc (n_elt);

  gcc_assert (VECTOR_MODE_P (tmode));
  gcc_assert (call_expr_nargs (exp) == n_elt);

  for (i = 0; i < n_elt; ++i)
    {
      rtx x = expand_normal (CALL_EXPR_ARG (exp, i));
      RTVEC_ELT (v, i) = gen_lowpart (inner_mode, x);
    }

  if (!target || !register_operand (target, tmode))
    target = gen_reg_rtx (tmode);

  ix86_expand_vector_init (true, target, gen_rtx_PARALLEL (tmode, v));
  return target;
}

/* A subroutine of ix86_expand_builtin.  These builtins are a wrapper around
   ix86_expand_vector_extract.  They would be redundant (for non-MMX) if we
   had a language-level syntax for referencing vector elements.  */

static rtx
ix86_expand_vec_ext_builtin (tree exp, rtx target)
{
  machine_mode tmode, mode0;
  tree arg0, arg1;
  int elt;
  rtx op0;

  arg0 = CALL_EXPR_ARG (exp, 0);
  arg1 = CALL_EXPR_ARG (exp, 1);

  op0 = expand_normal (arg0);
  elt = get_element_number (TREE_TYPE (arg0), arg1);

  tmode = TYPE_MODE (TREE_TYPE (TREE_TYPE (arg0)));
  mode0 = TYPE_MODE (TREE_TYPE (arg0));
  gcc_assert (VECTOR_MODE_P (mode0));

  op0 = force_reg (mode0, op0);

  if (optimize || !target || !register_operand (target, tmode))
    target = gen_reg_rtx (tmode);

  ix86_expand_vector_extract (true, target, op0, elt);

  return target;
}

/* A subroutine of ix86_expand_builtin.  These builtins are a wrapper around
   ix86_expand_vector_set.  They would be redundant (for non-MMX) if we had
   a language-level syntax for referencing vector elements.  */

static rtx
ix86_expand_vec_set_builtin (tree exp)
{
  machine_mode tmode, mode1;
  tree arg0, arg1, arg2;
  int elt;
  rtx op0, op1, target;

  arg0 = CALL_EXPR_ARG (exp, 0);
  arg1 = CALL_EXPR_ARG (exp, 1);
  arg2 = CALL_EXPR_ARG (exp, 2);

  tmode = TYPE_MODE (TREE_TYPE (arg0));
  mode1 = TYPE_MODE (TREE_TYPE (TREE_TYPE (arg0)));
  gcc_assert (VECTOR_MODE_P (tmode));

  op0 = expand_expr (arg0, NULL_RTX, tmode, EXPAND_NORMAL);
  op1 = expand_expr (arg1, NULL_RTX, mode1, EXPAND_NORMAL);
  elt = get_element_number (TREE_TYPE (arg0), arg2);

  if (GET_MODE (op1) != mode1 && GET_MODE (op1) != VOIDmode)
    op1 = convert_modes (mode1, GET_MODE (op1), op1, true);

  op0 = force_reg (tmode, op0);
  op1 = force_reg (mode1, op1);

  /* OP0 is the source of these builtin functions and shouldn't be
     modified.  Create a copy, use it and return it as target.  */
  target = gen_reg_rtx (tmode);
  emit_move_insn (target, op0);
  ix86_expand_vector_set (true, target, op1, elt);

  return target;
}

/* Expand an expression EXP that calls a built-in function,
   with result going to TARGET if that's convenient
   (and in mode MODE if that's convenient).
   SUBTARGET may be used as the target for computing one of EXP's operands.
   IGNORE is nonzero if the value is to be ignored.  */

static rtx
ix86_expand_builtin (tree exp, rtx target, rtx subtarget,
		     machine_mode mode, int ignore)
{
  size_t i;
  enum insn_code icode, icode2;
  tree fndecl = TREE_OPERAND (CALL_EXPR_FN (exp), 0);
  tree arg0, arg1, arg2, arg3, arg4;
  rtx op0, op1, op2, op3, op4, pat, pat2, insn;
  machine_mode mode0, mode1, mode2, mode3, mode4;
  unsigned int fcode = DECL_FUNCTION_CODE (fndecl);

  /* For CPU builtins that can be folded, fold first and expand the fold.  */
  switch (fcode)
    {
    case IX86_BUILTIN_CPU_INIT:
      {
	/* Make it call __cpu_indicator_init in libgcc. */
	tree call_expr, fndecl, type;
        type = build_function_type_list (integer_type_node, NULL_TREE); 
	fndecl = build_fn_decl ("__cpu_indicator_init", type);
	call_expr = build_call_expr (fndecl, 0); 
	return expand_expr (call_expr, target, mode, EXPAND_NORMAL);
      }
    case IX86_BUILTIN_CPU_IS:
    case IX86_BUILTIN_CPU_SUPPORTS:
      {
	tree arg0 = CALL_EXPR_ARG (exp, 0);
	tree fold_expr = fold_builtin_cpu (fndecl, &arg0);
	gcc_assert (fold_expr != NULL_TREE);
	return expand_expr (fold_expr, target, mode, EXPAND_NORMAL);
      }
    }

  HOST_WIDE_INT isa = ix86_isa_flags;
  HOST_WIDE_INT isa2 = ix86_isa_flags2;
  HOST_WIDE_INT bisa = ix86_builtins_isa[fcode].isa;
  HOST_WIDE_INT bisa2 = ix86_builtins_isa[fcode].isa2;
  /* The general case is we require all the ISAs specified in bisa{,2}
     to be enabled.
     The exceptions are:
     OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A
     OPTION_MASK_ISA_SSE4_2 | OPTION_MASK_ISA_CRC32
     OPTION_MASK_ISA_FMA | OPTION_MASK_ISA_FMA4
     where for each this pair it is sufficient if either of the ISAs is
     enabled, plus if it is ored with other options also those others.  */
  if (((bisa & (OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A))
       == (OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A))
      && (isa & (OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A)) != 0)
    isa |= (OPTION_MASK_ISA_SSE | OPTION_MASK_ISA_3DNOW_A);
  if (((bisa & (OPTION_MASK_ISA_SSE4_2 | OPTION_MASK_ISA_CRC32))
       == (OPTION_MASK_ISA_SSE4_2 | OPTION_MASK_ISA_CRC32))
      && (isa & (OPTION_MASK_ISA_SSE4_2 | OPTION_MASK_ISA_CRC32)) != 0)
    isa |= (OPTION_MASK_ISA_SSE4_2 | OPTION_MASK_ISA_CRC32);
  if (((bisa & (OPTION_MASK_ISA_FMA | OPTION_MASK_ISA_FMA4))
       == (OPTION_MASK_ISA_FMA | OPTION_MASK_ISA_FMA4))
      && (isa & (OPTION_MASK_ISA_FMA | OPTION_MASK_ISA_FMA4)) != 0)
    isa |= (OPTION_MASK_ISA_FMA | OPTION_MASK_ISA_FMA4);
  if ((bisa & isa) != bisa || (bisa2 & isa2) != bisa2)
    {
      char *opts = ix86_target_string (bisa, bisa2, 0, 0, NULL, NULL,
				       (enum fpmath_unit) 0, false);
      if (!opts)
	error ("%qE needs unknown isa option", fndecl);
      else
	{
	  gcc_assert (opts != NULL);
	  error ("%qE needs isa option %s", fndecl, opts);
	  free (opts);
	}
      return expand_call (exp, target, ignore);
    }

  switch (fcode)
    {
    case IX86_BUILTIN_MASKMOVQ:
    case IX86_BUILTIN_MASKMOVDQU:
      icode = (fcode == IX86_BUILTIN_MASKMOVQ
	       ? CODE_FOR_mmx_maskmovq
	       : CODE_FOR_sse2_maskmovdqu);
      /* Note the arg order is different from the operand order.  */
      arg1 = CALL_EXPR_ARG (exp, 0);
      arg2 = CALL_EXPR_ARG (exp, 1);
      arg0 = CALL_EXPR_ARG (exp, 2);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      op2 = expand_normal (arg2);
      mode0 = insn_data[icode].operand[0].mode;
      mode1 = insn_data[icode].operand[1].mode;
      mode2 = insn_data[icode].operand[2].mode;

      op0 = ix86_zero_extend_to_Pmode (op0);
      op0 = gen_rtx_MEM (mode1, op0);

      if (!insn_data[icode].operand[0].predicate (op0, mode0))
	op0 = copy_to_mode_reg (mode0, op0);
      if (!insn_data[icode].operand[1].predicate (op1, mode1))
	op1 = copy_to_mode_reg (mode1, op1);
      if (!insn_data[icode].operand[2].predicate (op2, mode2))
	op2 = copy_to_mode_reg (mode2, op2);
      pat = GEN_FCN (icode) (op0, op1, op2);
      if (! pat)
	return 0;
      emit_insn (pat);
      return 0;

    case IX86_BUILTIN_LDMXCSR:
      op0 = expand_normal (CALL_EXPR_ARG (exp, 0));
      target = assign_386_stack_local (SImode, SLOT_TEMP);
      emit_move_insn (target, op0);
      emit_insn (gen_sse_ldmxcsr (target));
      return 0;

    case IX86_BUILTIN_STMXCSR:
      target = assign_386_stack_local (SImode, SLOT_TEMP);
      emit_insn (gen_sse_stmxcsr (target));
      return copy_to_mode_reg (SImode, target);

    case IX86_BUILTIN_CLFLUSH:
	arg0 = CALL_EXPR_ARG (exp, 0);
	op0 = expand_normal (arg0);
	icode = CODE_FOR_sse2_clflush;
	if (!insn_data[icode].operand[0].predicate (op0, Pmode))
	  op0 = ix86_zero_extend_to_Pmode (op0);

	emit_insn (gen_sse2_clflush (op0));
	return 0;

    case IX86_BUILTIN_CLWB:
	arg0 = CALL_EXPR_ARG (exp, 0);
	op0 = expand_normal (arg0);
	icode = CODE_FOR_clwb;
	if (!insn_data[icode].operand[0].predicate (op0, Pmode))
	  op0 = ix86_zero_extend_to_Pmode (op0);

	emit_insn (gen_clwb (op0));
	return 0;

    case IX86_BUILTIN_CLFLUSHOPT:
	arg0 = CALL_EXPR_ARG (exp, 0);
	op0 = expand_normal (arg0);
	icode = CODE_FOR_clflushopt;
	if (!insn_data[icode].operand[0].predicate (op0, Pmode))
	  op0 = ix86_zero_extend_to_Pmode (op0);

	emit_insn (gen_clflushopt (op0));
	return 0;

    case IX86_BUILTIN_MONITOR:
    case IX86_BUILTIN_MONITORX:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      arg2 = CALL_EXPR_ARG (exp, 2);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      op2 = expand_normal (arg2);
      if (!REG_P (op0))
	op0 = ix86_zero_extend_to_Pmode (op0);
      if (!REG_P (op1))
	op1 = copy_to_mode_reg (SImode, op1);
      if (!REG_P (op2))
	op2 = copy_to_mode_reg (SImode, op2);

      emit_insn (fcode == IX86_BUILTIN_MONITOR 
		 ? ix86_gen_monitor (op0, op1, op2)
		 : ix86_gen_monitorx (op0, op1, op2));
      return 0;

    case IX86_BUILTIN_MWAIT:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      if (!REG_P (op0))
	op0 = copy_to_mode_reg (SImode, op0);
      if (!REG_P (op1))
	op1 = copy_to_mode_reg (SImode, op1);
      emit_insn (gen_sse3_mwait (op0, op1));
      return 0;

    case IX86_BUILTIN_MWAITX:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      arg2 = CALL_EXPR_ARG (exp, 2);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      op2 = expand_normal (arg2);
      if (!REG_P (op0))
	op0 = copy_to_mode_reg (SImode, op0);
      if (!REG_P (op1))
	op1 = copy_to_mode_reg (SImode, op1);
      if (!REG_P (op2))
	op2 = copy_to_mode_reg (SImode, op2);
      emit_insn (gen_mwaitx (op0, op1, op2));
      return 0;

    case IX86_BUILTIN_UMONITOR:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);

      op0 = ix86_zero_extend_to_Pmode (op0);

      insn = (TARGET_64BIT
	      ? gen_umonitor_di (op0)
	      : gen_umonitor_si (op0));

      emit_insn (insn);
      return 0;

    case IX86_BUILTIN_UMWAIT:
    case IX86_BUILTIN_TPAUSE:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);

      if (!REG_P (op0))
	op0 = copy_to_mode_reg (SImode, op0);

      op1 = force_reg (DImode, op1);

      if (TARGET_64BIT)
	{
	  op2 = expand_simple_binop (DImode, LSHIFTRT, op1, GEN_INT (32),
				     NULL, 1, OPTAB_DIRECT);
	  switch (fcode)
	    {
	    case IX86_BUILTIN_UMWAIT:
	      icode = CODE_FOR_umwait_rex64;
	      break;
	    case IX86_BUILTIN_TPAUSE:
	      icode = CODE_FOR_tpause_rex64;
	      break;
	    default:
	      gcc_unreachable ();
	    }

	  op2 = gen_lowpart (SImode, op2);
	  op1 = gen_lowpart (SImode, op1);
	  pat = GEN_FCN (icode) (op0, op1, op2);
	}
      else
	{
	  switch (fcode)
	    {
	    case IX86_BUILTIN_UMWAIT:
	      icode = CODE_FOR_umwait;
	      break;
	    case IX86_BUILTIN_TPAUSE:
	      icode = CODE_FOR_tpause;
	      break;
	    default:
	      gcc_unreachable ();
	    }
	  pat = GEN_FCN (icode) (op0, op1);
	}

      if (!pat)
	return 0;

      emit_insn (pat);

      if (target == 0
	  || !register_operand (target, QImode))
	target = gen_reg_rtx (QImode);

      pat = gen_rtx_EQ (QImode, gen_rtx_REG (CCCmode, FLAGS_REG),
			const0_rtx);
      emit_insn (gen_rtx_SET (target, pat));

      return target;

    case IX86_BUILTIN_CLZERO:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);
      if (!REG_P (op0))
	op0 = ix86_zero_extend_to_Pmode (op0);
      emit_insn (ix86_gen_clzero (op0));
      return 0;

    case IX86_BUILTIN_CLDEMOTE:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);
      icode = CODE_FOR_cldemote;
      if (!insn_data[icode].operand[0].predicate (op0, Pmode))
	op0 = ix86_zero_extend_to_Pmode (op0);

      emit_insn (gen_cldemote (op0));
      return 0;

    case IX86_BUILTIN_VEC_INIT_V2SI:
    case IX86_BUILTIN_VEC_INIT_V4HI:
    case IX86_BUILTIN_VEC_INIT_V8QI:
      return ix86_expand_vec_init_builtin (TREE_TYPE (exp), exp, target);

    case IX86_BUILTIN_VEC_EXT_V2DF:
    case IX86_BUILTIN_VEC_EXT_V2DI:
    case IX86_BUILTIN_VEC_EXT_V4SF:
    case IX86_BUILTIN_VEC_EXT_V4SI:
    case IX86_BUILTIN_VEC_EXT_V8HI:
    case IX86_BUILTIN_VEC_EXT_V2SI:
    case IX86_BUILTIN_VEC_EXT_V4HI:
    case IX86_BUILTIN_VEC_EXT_V16QI:
      return ix86_expand_vec_ext_builtin (exp, target);

    case IX86_BUILTIN_VEC_SET_V2DI:
    case IX86_BUILTIN_VEC_SET_V4SF:
    case IX86_BUILTIN_VEC_SET_V4SI:
    case IX86_BUILTIN_VEC_SET_V8HI:
    case IX86_BUILTIN_VEC_SET_V4HI:
    case IX86_BUILTIN_VEC_SET_V16QI:
      return ix86_expand_vec_set_builtin (exp);

    case IX86_BUILTIN_NANQ:
    case IX86_BUILTIN_NANSQ:
      return expand_call (exp, target, ignore);

    case IX86_BUILTIN_RDPID:

      op0 = gen_reg_rtx (word_mode);

      if (TARGET_64BIT)
	{
	  insn = gen_rdpid_rex64 (op0);
	  op0 = convert_to_mode (SImode, op0, 1);
	}
      else
	insn = gen_rdpid (op0);

      emit_insn (insn);

      if (target == 0
	  || !register_operand (target, SImode))
	target = gen_reg_rtx (SImode);

      emit_move_insn (target, op0);
      return target;

    case IX86_BUILTIN_RDPMC:
    case IX86_BUILTIN_RDTSC:
    case IX86_BUILTIN_RDTSCP:
    case IX86_BUILTIN_XGETBV:

      op0 = gen_reg_rtx (DImode);
      op1 = gen_reg_rtx (DImode);

      if (fcode == IX86_BUILTIN_RDPMC)
	{
	  arg0 = CALL_EXPR_ARG (exp, 0);
	  op2 = expand_normal (arg0);
	  if (!register_operand (op2, SImode))
	    op2 = copy_to_mode_reg (SImode, op2);

	  insn = (TARGET_64BIT
		  ? gen_rdpmc_rex64 (op0, op1, op2)
		  : gen_rdpmc (op0, op2));
	  emit_insn (insn);
	}
      else if (fcode == IX86_BUILTIN_XGETBV)
	{
	  arg0 = CALL_EXPR_ARG (exp, 0);
	  op2 = expand_normal (arg0);
	  if (!register_operand (op2, SImode))
	    op2 = copy_to_mode_reg (SImode, op2);

	  insn = (TARGET_64BIT
		  ? gen_xgetbv_rex64 (op0, op1, op2)
		  : gen_xgetbv (op0, op2));
	  emit_insn (insn);
	}
      else if (fcode == IX86_BUILTIN_RDTSC)
	{
	  insn = (TARGET_64BIT
		  ? gen_rdtsc_rex64 (op0, op1)
		  : gen_rdtsc (op0));
	  emit_insn (insn);
	}
      else
	{
	  op2 = gen_reg_rtx (SImode);

	  insn = (TARGET_64BIT
		  ? gen_rdtscp_rex64 (op0, op1, op2)
		  : gen_rdtscp (op0, op2));
	  emit_insn (insn);

	  arg0 = CALL_EXPR_ARG (exp, 0);
	  op4 = expand_normal (arg0);
	  if (!address_operand (op4, VOIDmode))
	    {
	      op4 = convert_memory_address (Pmode, op4);
	      op4 = copy_addr_to_reg (op4);
	    }
	  emit_move_insn (gen_rtx_MEM (SImode, op4), op2);
	}

      if (target == 0
	  || !register_operand (target, DImode))
        target = gen_reg_rtx (DImode);

      if (TARGET_64BIT)
	{
	  op1 = expand_simple_binop (DImode, ASHIFT, op1, GEN_INT (32),
				     op1, 1, OPTAB_DIRECT);
	  op0 = expand_simple_binop (DImode, IOR, op0, op1,
				     op0, 1, OPTAB_DIRECT);
	}

      emit_move_insn (target, op0);
      return target;

    case IX86_BUILTIN_MOVDIR64B:

      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);

      op0 = ix86_zero_extend_to_Pmode (op0);
      if (!address_operand (op1, VOIDmode))
      {
	op1 = convert_memory_address (Pmode, op1);
	op1 = copy_addr_to_reg (op1);
      }
      op1 = gen_rtx_MEM (XImode, op1);

      insn = (TARGET_64BIT
		? gen_movdir64b_di (op0, op1)
		: gen_movdir64b_si (op0, op1));
      emit_insn (insn);
      return 0;

    case IX86_BUILTIN_FXSAVE:
    case IX86_BUILTIN_FXRSTOR:
    case IX86_BUILTIN_FXSAVE64:
    case IX86_BUILTIN_FXRSTOR64:
    case IX86_BUILTIN_FNSTENV:
    case IX86_BUILTIN_FLDENV:
      mode0 = BLKmode;
      switch (fcode)
	{
	case IX86_BUILTIN_FXSAVE:
	  icode = CODE_FOR_fxsave;
	  break;
	case IX86_BUILTIN_FXRSTOR:
	  icode = CODE_FOR_fxrstor;
	  break;
	case IX86_BUILTIN_FXSAVE64:
	  icode = CODE_FOR_fxsave64;
	  break;
	case IX86_BUILTIN_FXRSTOR64:
	  icode = CODE_FOR_fxrstor64;
	  break;
	case IX86_BUILTIN_FNSTENV:
	  icode = CODE_FOR_fnstenv;
	  break;
	case IX86_BUILTIN_FLDENV:
	  icode = CODE_FOR_fldenv;
	  break;
	default:
	  gcc_unreachable ();
	}

      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);

      if (!address_operand (op0, VOIDmode))
	{
	  op0 = convert_memory_address (Pmode, op0);
	  op0 = copy_addr_to_reg (op0);
	}
      op0 = gen_rtx_MEM (mode0, op0);

      pat = GEN_FCN (icode) (op0);
      if (pat)
	emit_insn (pat);
      return 0;

    case IX86_BUILTIN_XSETBV:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);

      if (!REG_P (op0))
	op0 = copy_to_mode_reg (SImode, op0);

      op1 = force_reg (DImode, op1);

      if (TARGET_64BIT)
	{
	  op2 = expand_simple_binop (DImode, LSHIFTRT, op1, GEN_INT (32),
				     NULL, 1, OPTAB_DIRECT);

	  icode = CODE_FOR_xsetbv_rex64;

	  op2 = gen_lowpart (SImode, op2);
	  op1 = gen_lowpart (SImode, op1);
	  pat = GEN_FCN (icode) (op0, op1, op2);
	}
      else
	{
	  icode = CODE_FOR_xsetbv;

	  pat = GEN_FCN (icode) (op0, op1);
	}
      if (pat)
	emit_insn (pat);
      return 0;

    case IX86_BUILTIN_XSAVE:
    case IX86_BUILTIN_XRSTOR:
    case IX86_BUILTIN_XSAVE64:
    case IX86_BUILTIN_XRSTOR64:
    case IX86_BUILTIN_XSAVEOPT:
    case IX86_BUILTIN_XSAVEOPT64:
    case IX86_BUILTIN_XSAVES:
    case IX86_BUILTIN_XRSTORS:
    case IX86_BUILTIN_XSAVES64:
    case IX86_BUILTIN_XRSTORS64:
    case IX86_BUILTIN_XSAVEC:
    case IX86_BUILTIN_XSAVEC64:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);

      if (!address_operand (op0, VOIDmode))
	{
	  op0 = convert_memory_address (Pmode, op0);
	  op0 = copy_addr_to_reg (op0);
	}
      op0 = gen_rtx_MEM (BLKmode, op0);

      op1 = force_reg (DImode, op1);

      if (TARGET_64BIT)
	{
	  op2 = expand_simple_binop (DImode, LSHIFTRT, op1, GEN_INT (32),
				     NULL, 1, OPTAB_DIRECT);
	  switch (fcode)
	    {
	    case IX86_BUILTIN_XSAVE:
	      icode = CODE_FOR_xsave_rex64;
	      break;
	    case IX86_BUILTIN_XRSTOR:
	      icode = CODE_FOR_xrstor_rex64;
	      break;
	    case IX86_BUILTIN_XSAVE64:
	      icode = CODE_FOR_xsave64;
	      break;
	    case IX86_BUILTIN_XRSTOR64:
	      icode = CODE_FOR_xrstor64;
	      break;
	    case IX86_BUILTIN_XSAVEOPT:
	      icode = CODE_FOR_xsaveopt_rex64;
	      break;
	    case IX86_BUILTIN_XSAVEOPT64:
	      icode = CODE_FOR_xsaveopt64;
	      break;
	    case IX86_BUILTIN_XSAVES:
	      icode = CODE_FOR_xsaves_rex64;
	      break;
	    case IX86_BUILTIN_XRSTORS:
	      icode = CODE_FOR_xrstors_rex64;
	      break;
	    case IX86_BUILTIN_XSAVES64:
	      icode = CODE_FOR_xsaves64;
	      break;
	    case IX86_BUILTIN_XRSTORS64:
	      icode = CODE_FOR_xrstors64;
	      break;
	    case IX86_BUILTIN_XSAVEC:
	      icode = CODE_FOR_xsavec_rex64;
	      break;
	    case IX86_BUILTIN_XSAVEC64:
	      icode = CODE_FOR_xsavec64;
	      break;
	    default:
	      gcc_unreachable ();
	    }

	  op2 = gen_lowpart (SImode, op2);
	  op1 = gen_lowpart (SImode, op1);
	  pat = GEN_FCN (icode) (op0, op1, op2);
	}
      else
	{
	  switch (fcode)
	    {
	    case IX86_BUILTIN_XSAVE:
	      icode = CODE_FOR_xsave;
	      break;
	    case IX86_BUILTIN_XRSTOR:
	      icode = CODE_FOR_xrstor;
	      break;
	    case IX86_BUILTIN_XSAVEOPT:
	      icode = CODE_FOR_xsaveopt;
	      break;
	    case IX86_BUILTIN_XSAVES:
	      icode = CODE_FOR_xsaves;
	      break;
	    case IX86_BUILTIN_XRSTORS:
	      icode = CODE_FOR_xrstors;
	      break;
	    case IX86_BUILTIN_XSAVEC:
	      icode = CODE_FOR_xsavec;
	      break;
	    default:
	      gcc_unreachable ();
	    }
	  pat = GEN_FCN (icode) (op0, op1);
	}

      if (pat)
	emit_insn (pat);
      return 0;

    case IX86_BUILTIN_LLWPCB:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);
      icode = CODE_FOR_lwp_llwpcb;
      if (!insn_data[icode].operand[0].predicate (op0, Pmode))
	op0 = ix86_zero_extend_to_Pmode (op0);
      emit_insn (gen_lwp_llwpcb (op0));
      return 0;

    case IX86_BUILTIN_SLWPCB:
      icode = CODE_FOR_lwp_slwpcb;
      if (!target
	  || !insn_data[icode].operand[0].predicate (target, Pmode))
	target = gen_reg_rtx (Pmode);
      emit_insn (gen_lwp_slwpcb (target));
      return target;

    case IX86_BUILTIN_BEXTRI32:
    case IX86_BUILTIN_BEXTRI64:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      icode = (fcode == IX86_BUILTIN_BEXTRI32
	  ? CODE_FOR_tbm_bextri_si
	  : CODE_FOR_tbm_bextri_di);
      if (!CONST_INT_P (op1))
        {
          error ("last argument must be an immediate");
          return const0_rtx;
        }
      else
        {
          unsigned char length = (INTVAL (op1) >> 8) & 0xFF;
          unsigned char lsb_index = INTVAL (op1) & 0xFF;
          op1 = GEN_INT (length);
          op2 = GEN_INT (lsb_index);

	  mode1 = insn_data[icode].operand[1].mode;
	  if (!insn_data[icode].operand[1].predicate (op0, mode1))
	    op0 = copy_to_mode_reg (mode1, op0);

	  mode0 = insn_data[icode].operand[0].mode;
	  if (target == 0
	      || !register_operand (target, mode0))
	    target = gen_reg_rtx (mode0);

          pat = GEN_FCN (icode) (target, op0, op1, op2);
          if (pat)
            emit_insn (pat);
          return target;
        }

    case IX86_BUILTIN_RDRAND16_STEP:
      icode = CODE_FOR_rdrandhi_1;
      mode0 = HImode;
      goto rdrand_step;

    case IX86_BUILTIN_RDRAND32_STEP:
      icode = CODE_FOR_rdrandsi_1;
      mode0 = SImode;
      goto rdrand_step;

    case IX86_BUILTIN_RDRAND64_STEP:
      icode = CODE_FOR_rdranddi_1;
      mode0 = DImode;

rdrand_step:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op1 = expand_normal (arg0);
      if (!address_operand (op1, VOIDmode))
	{
	  op1 = convert_memory_address (Pmode, op1);
	  op1 = copy_addr_to_reg (op1);
	}

      op0 = gen_reg_rtx (mode0);
      emit_insn (GEN_FCN (icode) (op0));

      emit_move_insn (gen_rtx_MEM (mode0, op1), op0);

      op1 = gen_reg_rtx (SImode);
      emit_move_insn (op1, CONST1_RTX (SImode));

      /* Emit SImode conditional move.  */
      if (mode0 == HImode)
	{
	  if (TARGET_ZERO_EXTEND_WITH_AND
	      && optimize_function_for_speed_p (cfun))
	    {
	      op2 = force_reg (SImode, const0_rtx);

	      emit_insn (gen_movstricthi
			 (gen_lowpart (HImode, op2), op0));
	    }
	  else
	    {
	      op2 = gen_reg_rtx (SImode);

	      emit_insn (gen_zero_extendhisi2 (op2, op0));
	    }
	}
      else if (mode0 == SImode)
	op2 = op0;
      else
	op2 = gen_rtx_SUBREG (SImode, op0, 0);

      if (target == 0
	  || !register_operand (target, SImode))
	target = gen_reg_rtx (SImode);

      pat = gen_rtx_GEU (VOIDmode, gen_rtx_REG (CCCmode, FLAGS_REG),
			 const0_rtx);
      emit_insn (gen_rtx_SET (target,
			      gen_rtx_IF_THEN_ELSE (SImode, pat, op2, op1)));
      return target;

    case IX86_BUILTIN_RDSEED16_STEP:
      icode = CODE_FOR_rdseedhi_1;
      mode0 = HImode;
      goto rdseed_step;

    case IX86_BUILTIN_RDSEED32_STEP:
      icode = CODE_FOR_rdseedsi_1;
      mode0 = SImode;
      goto rdseed_step;

    case IX86_BUILTIN_RDSEED64_STEP:
      icode = CODE_FOR_rdseeddi_1;
      mode0 = DImode;

rdseed_step:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op1 = expand_normal (arg0);
      if (!address_operand (op1, VOIDmode))
	{
	  op1 = convert_memory_address (Pmode, op1);
	  op1 = copy_addr_to_reg (op1);
	}

      op0 = gen_reg_rtx (mode0);
      emit_insn (GEN_FCN (icode) (op0));

      emit_move_insn (gen_rtx_MEM (mode0, op1), op0);

      op2 = gen_reg_rtx (QImode);

      pat = gen_rtx_LTU (QImode, gen_rtx_REG (CCCmode, FLAGS_REG),
                         const0_rtx);
      emit_insn (gen_rtx_SET (op2, pat));

      if (target == 0
	  || !register_operand (target, SImode))
        target = gen_reg_rtx (SImode);

      emit_insn (gen_zero_extendqisi2 (target, op2));
      return target;

    case IX86_BUILTIN_SBB32:
      icode = CODE_FOR_subborrowsi;
      icode2 = CODE_FOR_subborrowsi_0;
      mode0 = SImode;
      mode1 = DImode;
      mode2 = CCmode;
      goto handlecarry;

    case IX86_BUILTIN_SBB64:
      icode = CODE_FOR_subborrowdi;
      icode2 = CODE_FOR_subborrowdi_0;
      mode0 = DImode;
      mode1 = TImode;
      mode2 = CCmode;
      goto handlecarry;

    case IX86_BUILTIN_ADDCARRYX32:
      icode = CODE_FOR_addcarrysi;
      icode2 = CODE_FOR_addcarrysi_0;
      mode0 = SImode;
      mode1 = DImode;
      mode2 = CCCmode;
      goto handlecarry;

    case IX86_BUILTIN_ADDCARRYX64:
      icode = CODE_FOR_addcarrydi;
      icode2 = CODE_FOR_addcarrydi_0;
      mode0 = DImode;
      mode1 = TImode;
      mode2 = CCCmode;

    handlecarry:
      arg0 = CALL_EXPR_ARG (exp, 0); /* unsigned char c_in.  */
      arg1 = CALL_EXPR_ARG (exp, 1); /* unsigned int src1.  */
      arg2 = CALL_EXPR_ARG (exp, 2); /* unsigned int src2.  */
      arg3 = CALL_EXPR_ARG (exp, 3); /* unsigned int *sum_out.  */

      op1 = expand_normal (arg0);
      if (!integer_zerop (arg0))
	op1 = copy_to_mode_reg (QImode, convert_to_mode (QImode, op1, 1));

      op2 = expand_normal (arg1);
      if (!register_operand (op2, mode0))
	op2 = copy_to_mode_reg (mode0, op2);

      op3 = expand_normal (arg2);
      if (!register_operand (op3, mode0))
	op3 = copy_to_mode_reg (mode0, op3);

      op4 = expand_normal (arg3);
      if (!address_operand (op4, VOIDmode))
	{
	  op4 = convert_memory_address (Pmode, op4);
	  op4 = copy_addr_to_reg (op4);
	}

      op0 = gen_reg_rtx (mode0);
      if (integer_zerop (arg0))
	{
	  /* If arg0 is 0, optimize right away into add or sub
	     instruction that sets CCCmode flags.  */
	  op1 = gen_rtx_REG (mode2, FLAGS_REG);
	  emit_insn (GEN_FCN (icode2) (op0, op2, op3));
	}
      else
	{
	  /* Generate CF from input operand.  */
	  emit_insn (gen_addqi3_cconly_overflow (op1, constm1_rtx));

	  /* Generate instruction that consumes CF.  */
	  op1 = gen_rtx_REG (CCCmode, FLAGS_REG);
	  pat = gen_rtx_LTU (mode1, op1, const0_rtx);
	  pat2 = gen_rtx_LTU (mode0, op1, const0_rtx);
	  emit_insn (GEN_FCN (icode) (op0, op2, op3, op1, pat, pat2));
	}

      /* Return current CF value.  */
      if (target == 0)
        target = gen_reg_rtx (QImode);

      pat = gen_rtx_LTU (QImode, op1, const0_rtx);
      emit_insn (gen_rtx_SET (target, pat));

      /* Store the result.  */
      emit_move_insn (gen_rtx_MEM (mode0, op4), op0);

      return target;

    case IX86_BUILTIN_READ_FLAGS:
      emit_insn (gen_push (gen_rtx_REG (word_mode, FLAGS_REG)));

      if (optimize
	  || target == NULL_RTX
	  || !nonimmediate_operand (target, word_mode)
	  || GET_MODE (target) != word_mode)
	target = gen_reg_rtx (word_mode);

      emit_insn (gen_pop (target));
      return target;

    case IX86_BUILTIN_WRITE_FLAGS:

      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);
      if (!general_no_elim_operand (op0, word_mode))
	op0 = copy_to_mode_reg (word_mode, op0);

      emit_insn (gen_push (op0));
      emit_insn (gen_pop (gen_rtx_REG (word_mode, FLAGS_REG)));
      return 0;

    case IX86_BUILTIN_KTESTC8:
      icode = CODE_FOR_ktestqi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KTESTZ8:
      icode = CODE_FOR_ktestqi;
      mode3 = CCZmode;
      goto kortest;

    case IX86_BUILTIN_KTESTC16:
      icode = CODE_FOR_ktesthi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KTESTZ16:
      icode = CODE_FOR_ktesthi;
      mode3 = CCZmode;
      goto kortest;

    case IX86_BUILTIN_KTESTC32:
      icode = CODE_FOR_ktestsi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KTESTZ32:
      icode = CODE_FOR_ktestsi;
      mode3 = CCZmode;
      goto kortest;

    case IX86_BUILTIN_KTESTC64:
      icode = CODE_FOR_ktestdi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KTESTZ64:
      icode = CODE_FOR_ktestdi;
      mode3 = CCZmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTC8:
      icode = CODE_FOR_kortestqi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTZ8:
      icode = CODE_FOR_kortestqi;
      mode3 = CCZmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTC16:
      icode = CODE_FOR_kortesthi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTZ16:
      icode = CODE_FOR_kortesthi;
      mode3 = CCZmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTC32:
      icode = CODE_FOR_kortestsi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTZ32:
      icode = CODE_FOR_kortestsi;
      mode3 = CCZmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTC64:
      icode = CODE_FOR_kortestdi;
      mode3 = CCCmode;
      goto kortest;

    case IX86_BUILTIN_KORTESTZ64:
      icode = CODE_FOR_kortestdi;
      mode3 = CCZmode;

    kortest:
      arg0 = CALL_EXPR_ARG (exp, 0); /* Mask reg src1.  */
      arg1 = CALL_EXPR_ARG (exp, 1); /* Mask reg src2.  */
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);

      mode0 = insn_data[icode].operand[0].mode;
      mode1 = insn_data[icode].operand[1].mode;

      if (GET_MODE (op0) != VOIDmode)
	op0 = force_reg (GET_MODE (op0), op0);

      op0 = gen_lowpart (mode0, op0);

      if (!insn_data[icode].operand[0].predicate (op0, mode0))
	op0 = copy_to_mode_reg (mode0, op0);

      if (GET_MODE (op1) != VOIDmode)
	op1 = force_reg (GET_MODE (op1), op1);

      op1 = gen_lowpart (mode1, op1);

      if (!insn_data[icode].operand[1].predicate (op1, mode1))
	op1 = copy_to_mode_reg (mode1, op1);

      target = gen_reg_rtx (QImode);

      /* Emit kortest.  */
      emit_insn (GEN_FCN (icode) (op0, op1));
      /* And use setcc to return result from flags.  */
      ix86_expand_setcc (target, EQ,
			 gen_rtx_REG (mode3, FLAGS_REG), const0_rtx);
      return target;

    case IX86_BUILTIN_GATHERSIV2DF:
      icode = CODE_FOR_avx2_gathersiv2df;
      goto gather_gen;
    case IX86_BUILTIN_GATHERSIV4DF:
      icode = CODE_FOR_avx2_gathersiv4df;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV2DF:
      icode = CODE_FOR_avx2_gatherdiv2df;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV4DF:
      icode = CODE_FOR_avx2_gatherdiv4df;
      goto gather_gen;
    case IX86_BUILTIN_GATHERSIV4SF:
      icode = CODE_FOR_avx2_gathersiv4sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHERSIV8SF:
      icode = CODE_FOR_avx2_gathersiv8sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV4SF:
      icode = CODE_FOR_avx2_gatherdiv4sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV8SF:
      icode = CODE_FOR_avx2_gatherdiv8sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHERSIV2DI:
      icode = CODE_FOR_avx2_gathersiv2di;
      goto gather_gen;
    case IX86_BUILTIN_GATHERSIV4DI:
      icode = CODE_FOR_avx2_gathersiv4di;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV2DI:
      icode = CODE_FOR_avx2_gatherdiv2di;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV4DI:
      icode = CODE_FOR_avx2_gatherdiv4di;
      goto gather_gen;
    case IX86_BUILTIN_GATHERSIV4SI:
      icode = CODE_FOR_avx2_gathersiv4si;
      goto gather_gen;
    case IX86_BUILTIN_GATHERSIV8SI:
      icode = CODE_FOR_avx2_gathersiv8si;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV4SI:
      icode = CODE_FOR_avx2_gatherdiv4si;
      goto gather_gen;
    case IX86_BUILTIN_GATHERDIV8SI:
      icode = CODE_FOR_avx2_gatherdiv8si;
      goto gather_gen;
    case IX86_BUILTIN_GATHERALTSIV4DF:
      icode = CODE_FOR_avx2_gathersiv4df;
      goto gather_gen;
    case IX86_BUILTIN_GATHERALTDIV8SF:
      icode = CODE_FOR_avx2_gatherdiv8sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHERALTSIV4DI:
      icode = CODE_FOR_avx2_gathersiv4di;
      goto gather_gen;
    case IX86_BUILTIN_GATHERALTDIV8SI:
      icode = CODE_FOR_avx2_gatherdiv8si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV16SF:
      icode = CODE_FOR_avx512f_gathersiv16sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV8DF:
      icode = CODE_FOR_avx512f_gathersiv8df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV16SF:
      icode = CODE_FOR_avx512f_gatherdiv16sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV8DF:
      icode = CODE_FOR_avx512f_gatherdiv8df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV16SI:
      icode = CODE_FOR_avx512f_gathersiv16si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV8DI:
      icode = CODE_FOR_avx512f_gathersiv8di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV16SI:
      icode = CODE_FOR_avx512f_gatherdiv16si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV8DI:
      icode = CODE_FOR_avx512f_gatherdiv8di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTSIV8DF:
      icode = CODE_FOR_avx512f_gathersiv8df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTDIV16SF:
      icode = CODE_FOR_avx512f_gatherdiv16sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTSIV8DI:
      icode = CODE_FOR_avx512f_gathersiv8di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTDIV16SI:
      icode = CODE_FOR_avx512f_gatherdiv16si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV2DF:
      icode = CODE_FOR_avx512vl_gathersiv2df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV4DF:
      icode = CODE_FOR_avx512vl_gathersiv4df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV2DF:
      icode = CODE_FOR_avx512vl_gatherdiv2df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV4DF:
      icode = CODE_FOR_avx512vl_gatherdiv4df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV4SF:
      icode = CODE_FOR_avx512vl_gathersiv4sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV8SF:
      icode = CODE_FOR_avx512vl_gathersiv8sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV4SF:
      icode = CODE_FOR_avx512vl_gatherdiv4sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV8SF:
      icode = CODE_FOR_avx512vl_gatherdiv8sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV2DI:
      icode = CODE_FOR_avx512vl_gathersiv2di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV4DI:
      icode = CODE_FOR_avx512vl_gathersiv4di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV2DI:
      icode = CODE_FOR_avx512vl_gatherdiv2di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV4DI:
      icode = CODE_FOR_avx512vl_gatherdiv4di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV4SI:
      icode = CODE_FOR_avx512vl_gathersiv4si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3SIV8SI:
      icode = CODE_FOR_avx512vl_gathersiv8si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV4SI:
      icode = CODE_FOR_avx512vl_gatherdiv4si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3DIV8SI:
      icode = CODE_FOR_avx512vl_gatherdiv8si;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTSIV4DF:
      icode = CODE_FOR_avx512vl_gathersiv4df;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTDIV8SF:
      icode = CODE_FOR_avx512vl_gatherdiv8sf;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTSIV4DI:
      icode = CODE_FOR_avx512vl_gathersiv4di;
      goto gather_gen;
    case IX86_BUILTIN_GATHER3ALTDIV8SI:
      icode = CODE_FOR_avx512vl_gatherdiv8si;
      goto gather_gen;
    case IX86_BUILTIN_SCATTERSIV16SF:
      icode = CODE_FOR_avx512f_scattersiv16sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV8DF:
      icode = CODE_FOR_avx512f_scattersiv8df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV16SF:
      icode = CODE_FOR_avx512f_scatterdiv16sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV8DF:
      icode = CODE_FOR_avx512f_scatterdiv8df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV16SI:
      icode = CODE_FOR_avx512f_scattersiv16si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV8DI:
      icode = CODE_FOR_avx512f_scattersiv8di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV16SI:
      icode = CODE_FOR_avx512f_scatterdiv16si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV8DI:
      icode = CODE_FOR_avx512f_scatterdiv8di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV8SF:
      icode = CODE_FOR_avx512vl_scattersiv8sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV4SF:
      icode = CODE_FOR_avx512vl_scattersiv4sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV4DF:
      icode = CODE_FOR_avx512vl_scattersiv4df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV2DF:
      icode = CODE_FOR_avx512vl_scattersiv2df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV8SF:
      icode = CODE_FOR_avx512vl_scatterdiv8sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV4SF:
      icode = CODE_FOR_avx512vl_scatterdiv4sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV4DF:
      icode = CODE_FOR_avx512vl_scatterdiv4df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV2DF:
      icode = CODE_FOR_avx512vl_scatterdiv2df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV8SI:
      icode = CODE_FOR_avx512vl_scattersiv8si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV4SI:
      icode = CODE_FOR_avx512vl_scattersiv4si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV4DI:
      icode = CODE_FOR_avx512vl_scattersiv4di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERSIV2DI:
      icode = CODE_FOR_avx512vl_scattersiv2di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV8SI:
      icode = CODE_FOR_avx512vl_scatterdiv8si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV4SI:
      icode = CODE_FOR_avx512vl_scatterdiv4si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV4DI:
      icode = CODE_FOR_avx512vl_scatterdiv4di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERDIV2DI:
      icode = CODE_FOR_avx512vl_scatterdiv2di;
      goto scatter_gen;
    case IX86_BUILTIN_GATHERPFDPD:
      icode = CODE_FOR_avx512pf_gatherpfv8sidf;
      goto vec_prefetch_gen;
    case IX86_BUILTIN_SCATTERALTSIV8DF:
      icode = CODE_FOR_avx512f_scattersiv8df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTDIV16SF:
      icode = CODE_FOR_avx512f_scatterdiv16sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTSIV8DI:
      icode = CODE_FOR_avx512f_scattersiv8di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTDIV16SI:
      icode = CODE_FOR_avx512f_scatterdiv16si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTSIV4DF:
      icode = CODE_FOR_avx512vl_scattersiv4df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTDIV8SF:
      icode = CODE_FOR_avx512vl_scatterdiv8sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTSIV4DI:
      icode = CODE_FOR_avx512vl_scattersiv4di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTDIV8SI:
      icode = CODE_FOR_avx512vl_scatterdiv8si;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTSIV2DF:
      icode = CODE_FOR_avx512vl_scattersiv2df;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTDIV4SF:
      icode = CODE_FOR_avx512vl_scatterdiv4sf;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTSIV2DI:
      icode = CODE_FOR_avx512vl_scattersiv2di;
      goto scatter_gen;
    case IX86_BUILTIN_SCATTERALTDIV4SI:
      icode = CODE_FOR_avx512vl_scatterdiv4si;
      goto scatter_gen;
    case IX86_BUILTIN_GATHERPFDPS:
      icode = CODE_FOR_avx512pf_gatherpfv16sisf;
      goto vec_prefetch_gen;
    case IX86_BUILTIN_GATHERPFQPD:
      icode = CODE_FOR_avx512pf_gatherpfv8didf;
      goto vec_prefetch_gen;
    case IX86_BUILTIN_GATHERPFQPS:
      icode = CODE_FOR_avx512pf_gatherpfv8disf;
      goto vec_prefetch_gen;
    case IX86_BUILTIN_SCATTERPFDPD:
      icode = CODE_FOR_avx512pf_scatterpfv8sidf;
      goto vec_prefetch_gen;
    case IX86_BUILTIN_SCATTERPFDPS:
      icode = CODE_FOR_avx512pf_scatterpfv16sisf;
      goto vec_prefetch_gen;
    case IX86_BUILTIN_SCATTERPFQPD:
      icode = CODE_FOR_avx512pf_scatterpfv8didf;
      goto vec_prefetch_gen;
    case IX86_BUILTIN_SCATTERPFQPS:
      icode = CODE_FOR_avx512pf_scatterpfv8disf;
      goto vec_prefetch_gen;

    gather_gen:
      rtx half;
      rtx (*gen) (rtx, rtx);

      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      arg2 = CALL_EXPR_ARG (exp, 2);
      arg3 = CALL_EXPR_ARG (exp, 3);
      arg4 = CALL_EXPR_ARG (exp, 4);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      op2 = expand_normal (arg2);
      op3 = expand_normal (arg3);
      op4 = expand_normal (arg4);
      /* Note the arg order is different from the operand order.  */
      mode0 = insn_data[icode].operand[1].mode;
      mode2 = insn_data[icode].operand[3].mode;
      mode3 = insn_data[icode].operand[4].mode;
      mode4 = insn_data[icode].operand[5].mode;

      if (target == NULL_RTX
	  || GET_MODE (target) != insn_data[icode].operand[0].mode
	  || !insn_data[icode].operand[0].predicate (target,
						     GET_MODE (target)))
	subtarget = gen_reg_rtx (insn_data[icode].operand[0].mode);
      else
	subtarget = target;

      switch (fcode)
	{
	case IX86_BUILTIN_GATHER3ALTSIV8DF:
	case IX86_BUILTIN_GATHER3ALTSIV8DI:
	  half = gen_reg_rtx (V8SImode);
	  if (!nonimmediate_operand (op2, V16SImode))
	    op2 = copy_to_mode_reg (V16SImode, op2);
	  emit_insn (gen_vec_extract_lo_v16si (half, op2));
	  op2 = half;
	  break;
	case IX86_BUILTIN_GATHER3ALTSIV4DF:
	case IX86_BUILTIN_GATHER3ALTSIV4DI:
	case IX86_BUILTIN_GATHERALTSIV4DF:
	case IX86_BUILTIN_GATHERALTSIV4DI:
	  half = gen_reg_rtx (V4SImode);
	  if (!nonimmediate_operand (op2, V8SImode))
	    op2 = copy_to_mode_reg (V8SImode, op2);
	  emit_insn (gen_vec_extract_lo_v8si (half, op2));
	  op2 = half;
	  break;
	case IX86_BUILTIN_GATHER3ALTDIV16SF:
	case IX86_BUILTIN_GATHER3ALTDIV16SI:
	  half = gen_reg_rtx (mode0);
	  if (mode0 == V8SFmode)
	    gen = gen_vec_extract_lo_v16sf;
	  else
	    gen = gen_vec_extract_lo_v16si;
	  if (!nonimmediate_operand (op0, GET_MODE (op0)))
	    op0 = copy_to_mode_reg (GET_MODE (op0), op0);
	  emit_insn (gen (half, op0));
	  op0 = half;
	  op3 = lowpart_subreg (QImode, op3, HImode);
	  break;
	case IX86_BUILTIN_GATHER3ALTDIV8SF:
	case IX86_BUILTIN_GATHER3ALTDIV8SI:
	case IX86_BUILTIN_GATHERALTDIV8SF:
	case IX86_BUILTIN_GATHERALTDIV8SI:
	  half = gen_reg_rtx (mode0);
	  if (mode0 == V4SFmode)
	    gen = gen_vec_extract_lo_v8sf;
	  else
	    gen = gen_vec_extract_lo_v8si;
	  if (!nonimmediate_operand (op0, GET_MODE (op0)))
	    op0 = copy_to_mode_reg (GET_MODE (op0), op0);
	  emit_insn (gen (half, op0));
	  op0 = half;
	  if (VECTOR_MODE_P (GET_MODE (op3)))
	    {
	      half = gen_reg_rtx (mode0);
	      if (!nonimmediate_operand (op3, GET_MODE (op3)))
		op3 = copy_to_mode_reg (GET_MODE (op3), op3);
	      emit_insn (gen (half, op3));
	      op3 = half;
	    }
	  break;
	default:
	  break;
	}

      /* Force memory operand only with base register here.  But we
	 don't want to do it on memory operand for other builtin
	 functions.  */
      op1 = ix86_zero_extend_to_Pmode (op1);

      if (!insn_data[icode].operand[1].predicate (op0, mode0))
	op0 = copy_to_mode_reg (mode0, op0);
      if (!insn_data[icode].operand[2].predicate (op1, Pmode))
	op1 = copy_to_mode_reg (Pmode, op1);
      if (!insn_data[icode].operand[3].predicate (op2, mode2))
	op2 = copy_to_mode_reg (mode2, op2);

      op3 = fixup_modeless_constant (op3, mode3);

      if (GET_MODE (op3) == mode3 || GET_MODE (op3) == VOIDmode)
	{
	  if (!insn_data[icode].operand[4].predicate (op3, mode3))
	    op3 = copy_to_mode_reg (mode3, op3);
	}
      else
	{
	  op3 = copy_to_reg (op3);
	  op3 = lowpart_subreg (mode3, op3, GET_MODE (op3));
	}
      if (!insn_data[icode].operand[5].predicate (op4, mode4))
	{
          error ("the last argument must be scale 1, 2, 4, 8");
          return const0_rtx;
	}

      /* Optimize.  If mask is known to have all high bits set,
	 replace op0 with pc_rtx to signal that the instruction
	 overwrites the whole destination and doesn't use its
	 previous contents.  */
      if (optimize)
	{
	  if (TREE_CODE (arg3) == INTEGER_CST)
	    {
	      if (integer_all_onesp (arg3))
		op0 = pc_rtx;
	    }
	  else if (TREE_CODE (arg3) == VECTOR_CST)
	    {
	      unsigned int negative = 0;
	      for (i = 0; i < VECTOR_CST_NELTS (arg3); ++i)
		{
		  tree cst = VECTOR_CST_ELT (arg3, i);
		  if (TREE_CODE (cst) == INTEGER_CST
		      && tree_int_cst_sign_bit (cst))
		    negative++;
		  else if (TREE_CODE (cst) == REAL_CST
			   && REAL_VALUE_NEGATIVE (TREE_REAL_CST (cst)))
		    negative++;
		}
	      if (negative == TYPE_VECTOR_SUBPARTS (TREE_TYPE (arg3)))
		op0 = pc_rtx;
	    }
	  else if (TREE_CODE (arg3) == SSA_NAME
		   && TREE_CODE (TREE_TYPE (arg3)) == VECTOR_TYPE)
	    {
	      /* Recognize also when mask is like:
		 __v2df src = _mm_setzero_pd ();
		 __v2df mask = _mm_cmpeq_pd (src, src);
		 or
		 __v8sf src = _mm256_setzero_ps ();
		 __v8sf mask = _mm256_cmp_ps (src, src, _CMP_EQ_OQ);
		 as that is a cheaper way to load all ones into
		 a register than having to load a constant from
		 memory.  */
	      gimple *def_stmt = SSA_NAME_DEF_STMT (arg3);
	      if (is_gimple_call (def_stmt))
		{
		  tree fndecl = gimple_call_fndecl (def_stmt);
		  if (fndecl
		      && fndecl_built_in_p (fndecl, BUILT_IN_MD))
		    switch ((unsigned int) DECL_FUNCTION_CODE (fndecl))
		      {
		      case IX86_BUILTIN_CMPPD:
		      case IX86_BUILTIN_CMPPS:
		      case IX86_BUILTIN_CMPPD256:
		      case IX86_BUILTIN_CMPPS256:
			if (!integer_zerop (gimple_call_arg (def_stmt, 2)))
			  break;
			/* FALLTHRU */
		      case IX86_BUILTIN_CMPEQPD:
		      case IX86_BUILTIN_CMPEQPS:
			if (initializer_zerop (gimple_call_arg (def_stmt, 0))
			    && initializer_zerop (gimple_call_arg (def_stmt,
								   1)))
			  op0 = pc_rtx;
			break;
		      default:
			break;
		      }
		}
	    }
	}

      pat = GEN_FCN (icode) (subtarget, op0, op1, op2, op3, op4);
      if (! pat)
	return const0_rtx;
      emit_insn (pat);

      switch (fcode)
	{
	case IX86_BUILTIN_GATHER3DIV16SF:
	  if (target == NULL_RTX)
	    target = gen_reg_rtx (V8SFmode);
	  emit_insn (gen_vec_extract_lo_v16sf (target, subtarget));
	  break;
	case IX86_BUILTIN_GATHER3DIV16SI:
	  if (target == NULL_RTX)
	    target = gen_reg_rtx (V8SImode);
	  emit_insn (gen_vec_extract_lo_v16si (target, subtarget));
	  break;
	case IX86_BUILTIN_GATHER3DIV8SF:
	case IX86_BUILTIN_GATHERDIV8SF:
	  if (target == NULL_RTX)
	    target = gen_reg_rtx (V4SFmode);
	  emit_insn (gen_vec_extract_lo_v8sf (target, subtarget));
	  break;
	case IX86_BUILTIN_GATHER3DIV8SI:
	case IX86_BUILTIN_GATHERDIV8SI:
	  if (target == NULL_RTX)
	    target = gen_reg_rtx (V4SImode);
	  emit_insn (gen_vec_extract_lo_v8si (target, subtarget));
	  break;
	default:
	  target = subtarget;
	  break;
	}
      return target;

    scatter_gen:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      arg2 = CALL_EXPR_ARG (exp, 2);
      arg3 = CALL_EXPR_ARG (exp, 3);
      arg4 = CALL_EXPR_ARG (exp, 4);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      op2 = expand_normal (arg2);
      op3 = expand_normal (arg3);
      op4 = expand_normal (arg4);
      mode1 = insn_data[icode].operand[1].mode;
      mode2 = insn_data[icode].operand[2].mode;
      mode3 = insn_data[icode].operand[3].mode;
      mode4 = insn_data[icode].operand[4].mode;

      /* Scatter instruction stores operand op3 to memory with
	 indices from op2 and scale from op4 under writemask op1.
	 If index operand op2 has more elements then source operand
	 op3 one need to use only its low half. And vice versa.  */
      switch (fcode)
	{
	case IX86_BUILTIN_SCATTERALTSIV8DF:
	case IX86_BUILTIN_SCATTERALTSIV8DI:
	  half = gen_reg_rtx (V8SImode);
	  if (!nonimmediate_operand (op2, V16SImode))
	    op2 = copy_to_mode_reg (V16SImode, op2);
	  emit_insn (gen_vec_extract_lo_v16si (half, op2));
	  op2 = half;
	  break;
	case IX86_BUILTIN_SCATTERALTDIV16SF:
	case IX86_BUILTIN_SCATTERALTDIV16SI:
	  half = gen_reg_rtx (mode3);
	  if (mode3 == V8SFmode)
	    gen = gen_vec_extract_lo_v16sf;
	  else
	    gen = gen_vec_extract_lo_v16si;
	  if (!nonimmediate_operand (op3, GET_MODE (op3)))
	    op3 = copy_to_mode_reg (GET_MODE (op3), op3);
	  emit_insn (gen (half, op3));
	  op3 = half;
	  break;
	case IX86_BUILTIN_SCATTERALTSIV4DF:
	case IX86_BUILTIN_SCATTERALTSIV4DI:
	  half = gen_reg_rtx (V4SImode);
	  if (!nonimmediate_operand (op2, V8SImode))
	    op2 = copy_to_mode_reg (V8SImode, op2);
	  emit_insn (gen_vec_extract_lo_v8si (half, op2));
	  op2 = half;
	  break;
	case IX86_BUILTIN_SCATTERALTDIV8SF:
	case IX86_BUILTIN_SCATTERALTDIV8SI:
	  half = gen_reg_rtx (mode3);
	  if (mode3 == V4SFmode)
	    gen = gen_vec_extract_lo_v8sf;
	  else
	    gen = gen_vec_extract_lo_v8si;
	  if (!nonimmediate_operand (op3, GET_MODE (op3)))
	    op3 = copy_to_mode_reg (GET_MODE (op3), op3);
	  emit_insn (gen (half, op3));
	  op3 = half;
	  break;
	case IX86_BUILTIN_SCATTERALTSIV2DF:
	case IX86_BUILTIN_SCATTERALTSIV2DI:
	  if (!nonimmediate_operand (op2, V4SImode))
	    op2 = copy_to_mode_reg (V4SImode, op2);
	  break;
	case IX86_BUILTIN_SCATTERALTDIV4SF:
	case IX86_BUILTIN_SCATTERALTDIV4SI:
	  if (!nonimmediate_operand (op3, GET_MODE (op3)))
	    op3 = copy_to_mode_reg (GET_MODE (op3), op3);
	  break;
	default:
	  break;
	}

      /* Force memory operand only with base register here.  But we
	 don't want to do it on memory operand for other builtin
	 functions.  */
      op0 = force_reg (Pmode, convert_to_mode (Pmode, op0, 1));

      if (!insn_data[icode].operand[0].predicate (op0, Pmode))
	op0 = copy_to_mode_reg (Pmode, op0);

      op1 = fixup_modeless_constant (op1, mode1);

      if (GET_MODE (op1) == mode1 || GET_MODE (op1) == VOIDmode)
	{
	  if (!insn_data[icode].operand[1].predicate (op1, mode1))
	    op1 = copy_to_mode_reg (mode1, op1);
	}
      else
	{
	  op1 = copy_to_reg (op1);
	  op1 = lowpart_subreg (mode1, op1, GET_MODE (op1));
	}

      if (!insn_data[icode].operand[2].predicate (op2, mode2))
	op2 = copy_to_mode_reg (mode2, op2);

      if (!insn_data[icode].operand[3].predicate (op3, mode3))
	op3 = copy_to_mode_reg (mode3, op3);

      if (!insn_data[icode].operand[4].predicate (op4, mode4))
	{
	  error ("the last argument must be scale 1, 2, 4, 8");
	  return const0_rtx;
	}

      pat = GEN_FCN (icode) (op0, op1, op2, op3, op4);
      if (! pat)
	return const0_rtx;

      emit_insn (pat);
      return 0;

    vec_prefetch_gen:
      arg0 = CALL_EXPR_ARG (exp, 0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      arg2 = CALL_EXPR_ARG (exp, 2);
      arg3 = CALL_EXPR_ARG (exp, 3);
      arg4 = CALL_EXPR_ARG (exp, 4);
      op0 = expand_normal (arg0);
      op1 = expand_normal (arg1);
      op2 = expand_normal (arg2);
      op3 = expand_normal (arg3);
      op4 = expand_normal (arg4);
      mode0 = insn_data[icode].operand[0].mode;
      mode1 = insn_data[icode].operand[1].mode;
      mode3 = insn_data[icode].operand[3].mode;
      mode4 = insn_data[icode].operand[4].mode;

      op0 = fixup_modeless_constant (op0, mode0);

      if (GET_MODE (op0) == mode0 || GET_MODE (op0) == VOIDmode)
	{
	  if (!insn_data[icode].operand[0].predicate (op0, mode0))
	    op0 = copy_to_mode_reg (mode0, op0);
	}
      else
	{
	  op0 = copy_to_reg (op0);
	  op0 = lowpart_subreg (mode0, op0, GET_MODE (op0));
	}

      if (!insn_data[icode].operand[1].predicate (op1, mode1))
	op1 = copy_to_mode_reg (mode1, op1);

      /* Force memory operand only with base register here.  But we
	 don't want to do it on memory operand for other builtin
	 functions.  */
      op2 = force_reg (Pmode, convert_to_mode (Pmode, op2, 1));

      if (!insn_data[icode].operand[2].predicate (op2, Pmode))
	op2 = copy_to_mode_reg (Pmode, op2);

      if (!insn_data[icode].operand[3].predicate (op3, mode3))
	{
	  error ("the forth argument must be scale 1, 2, 4, 8");
	  return const0_rtx;
	}

      if (!insn_data[icode].operand[4].predicate (op4, mode4))
	{
	  error ("incorrect hint operand");
	  return const0_rtx;
	}

      pat = GEN_FCN (icode) (op0, op1, op2, op3, op4);
      if (! pat)
	return const0_rtx;

      emit_insn (pat);

      return 0;

    case IX86_BUILTIN_XABORT:
      icode = CODE_FOR_xabort;
      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);
      mode0 = insn_data[icode].operand[0].mode;
      if (!insn_data[icode].operand[0].predicate (op0, mode0))
	{
	  error ("the xabort's argument must be an 8-bit immediate");
	  return const0_rtx;
	}
      emit_insn (gen_xabort (op0));
      return 0;

    case IX86_BUILTIN_RSTORSSP:
    case IX86_BUILTIN_CLRSSBSY:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);
      icode = (fcode == IX86_BUILTIN_RSTORSSP
	  ? CODE_FOR_rstorssp
	  : CODE_FOR_clrssbsy);
      if (!address_operand (op0, VOIDmode))
	{
	  op1 = convert_memory_address (Pmode, op0);
	  op0 = copy_addr_to_reg (op1);
	}
      emit_insn (GEN_FCN (icode) (gen_rtx_MEM (Pmode, op0)));
      return 0;

    case IX86_BUILTIN_WRSSD:
    case IX86_BUILTIN_WRSSQ:
    case IX86_BUILTIN_WRUSSD:
    case IX86_BUILTIN_WRUSSQ:
      arg0 = CALL_EXPR_ARG (exp, 0);
      op0 = expand_normal (arg0);
      arg1 = CALL_EXPR_ARG (exp, 1);
      op1 = expand_normal (arg1);
      switch (fcode)
	{
	case IX86_BUILTIN_WRSSD:
	  icode = CODE_FOR_wrsssi;
	  mode = SImode;
	  break;
	case IX86_BUILTIN_WRSSQ:
	  icode = CODE_FOR_wrssdi;
	  mode = DImode;
	  break;
	case IX86_BUILTIN_WRUSSD:
	  icode = CODE_FOR_wrusssi;
	  mode = SImode;
	  break;
	case IX86_BUILTIN_WRUSSQ:
	  icode = CODE_FOR_wrussdi;
	  mode = DImode;
	  break;
	}
      op0 = force_reg (mode, op0);
      if (!address_operand (op1, VOIDmode))
	{
	  op2 = convert_memory_address (Pmode, op1);
	  op1 = copy_addr_to_reg (op2);
	}
      emit_insn (GEN_FCN (icode) (op0, gen_rtx_MEM (mode, op1)));
      return 0;

    default:
      break;
    }

  if (fcode >= IX86_BUILTIN__BDESC_SPECIAL_ARGS_FIRST
      && fcode <= IX86_BUILTIN__BDESC_SPECIAL_ARGS_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_SPECIAL_ARGS_FIRST;
      return ix86_expand_special_args_builtin (bdesc_special_args + i, exp,
					       target);
    }

  if (fcode >= IX86_BUILTIN__BDESC_ARGS_FIRST
      && fcode <= IX86_BUILTIN__BDESC_ARGS_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_ARGS_FIRST;
      rtx (*fcn) (rtx, rtx, rtx, rtx) = NULL;
      rtx (*fcn_mask) (rtx, rtx, rtx, rtx, rtx);
      rtx (*fcn_maskz) (rtx, rtx, rtx, rtx, rtx, rtx);
      int masked = 1;
      machine_mode mode, wide_mode, nar_mode;

      nar_mode  = V4SFmode;
      mode      = V16SFmode;
      wide_mode = V64SFmode;
      fcn_mask  = gen_avx5124fmaddps_4fmaddps_mask;
      fcn_maskz = gen_avx5124fmaddps_4fmaddps_maskz;

      switch (fcode)
	{
	case IX86_BUILTIN_4FMAPS:
	  fcn = gen_avx5124fmaddps_4fmaddps;
	  masked = 0;
	  goto v4fma_expand;

	case IX86_BUILTIN_4DPWSSD:
	  nar_mode  = V4SImode;
	  mode      = V16SImode;
	  wide_mode = V64SImode;
	  fcn = gen_avx5124vnniw_vp4dpwssd;
	  masked = 0;
	  goto v4fma_expand;

	case IX86_BUILTIN_4DPWSSDS:
	  nar_mode  = V4SImode;
	  mode      = V16SImode;
	  wide_mode = V64SImode;
	  fcn = gen_avx5124vnniw_vp4dpwssds;
	  masked = 0;
	  goto v4fma_expand;

	case IX86_BUILTIN_4FNMAPS:
	  fcn = gen_avx5124fmaddps_4fnmaddps;
	  masked = 0;
	  goto v4fma_expand;

	case IX86_BUILTIN_4FNMAPS_MASK:
	  fcn_mask  = gen_avx5124fmaddps_4fnmaddps_mask;
	  fcn_maskz = gen_avx5124fmaddps_4fnmaddps_maskz;
	  goto v4fma_expand;

	case IX86_BUILTIN_4DPWSSD_MASK:
	  nar_mode  = V4SImode;
	  mode      = V16SImode;
	  wide_mode = V64SImode;
	  fcn_mask  = gen_avx5124vnniw_vp4dpwssd_mask;
	  fcn_maskz = gen_avx5124vnniw_vp4dpwssd_maskz;
	  goto v4fma_expand;

	case IX86_BUILTIN_4DPWSSDS_MASK:
	  nar_mode  = V4SImode;
	  mode      = V16SImode;
	  wide_mode = V64SImode;
	  fcn_mask  = gen_avx5124vnniw_vp4dpwssds_mask;
	  fcn_maskz = gen_avx5124vnniw_vp4dpwssds_maskz;
	  goto v4fma_expand;

	case IX86_BUILTIN_4FMAPS_MASK:
	  {
	    tree args[4];
	    rtx ops[4];
	    rtx wide_reg;
	    rtx accum;
	    rtx addr;
	    rtx mem;

v4fma_expand:
	    wide_reg = gen_reg_rtx (wide_mode);
	    for (i = 0; i < 4; i++)
	      {
		args[i] = CALL_EXPR_ARG (exp, i);
		ops[i] = expand_normal (args[i]);

		emit_move_insn (gen_rtx_SUBREG (mode, wide_reg, i * 64),
				ops[i]);
	      }

	    accum = expand_normal (CALL_EXPR_ARG (exp, 4));
	    accum = force_reg (mode, accum);

	    addr = expand_normal (CALL_EXPR_ARG (exp, 5));
	    addr = force_reg (Pmode, addr);

	    mem = gen_rtx_MEM (nar_mode, addr);

	    target = gen_reg_rtx (mode);

	    emit_move_insn (target, accum);

	    if (! masked)
	      emit_insn (fcn (target, accum, wide_reg, mem));
	    else
	      {
		rtx merge, mask;
		merge = expand_normal (CALL_EXPR_ARG (exp, 6));

		mask = expand_normal (CALL_EXPR_ARG (exp, 7));

		if (CONST_INT_P (mask))
		  mask = fixup_modeless_constant (mask, HImode);

		mask = force_reg (HImode, mask);

		if (GET_MODE (mask) != HImode)
		  mask = gen_rtx_SUBREG (HImode, mask, 0);

		/* If merge is 0 then we're about to emit z-masked variant.  */
		if (const0_operand (merge, mode))
		  emit_insn (fcn_maskz (target, accum, wide_reg, mem, merge, mask));
		/* If merge is the same as accum then emit merge-masked variant.  */
		else if (CALL_EXPR_ARG (exp, 6) == CALL_EXPR_ARG (exp, 4))
		  {
		    merge = force_reg (mode, merge);
		    emit_insn (fcn_mask (target, wide_reg, mem, merge, mask));
		  }
		/* Merge with something unknown might happen if we z-mask w/ -O0.  */
		else
		  {
		    target = gen_reg_rtx (mode);
		    emit_move_insn (target, merge);
		    emit_insn (fcn_mask (target, wide_reg, mem, target, mask));
		  }
	      }
	    return target;
	  }

	case IX86_BUILTIN_4FNMASS:
	  fcn = gen_avx5124fmaddps_4fnmaddss;
	  masked = 0;
	  goto s4fma_expand;

	case IX86_BUILTIN_4FMASS:
	  fcn = gen_avx5124fmaddps_4fmaddss;
	  masked = 0;
	  goto s4fma_expand;

	case IX86_BUILTIN_4FNMASS_MASK:
	  fcn_mask = gen_avx5124fmaddps_4fnmaddss_mask;
	  fcn_maskz = gen_avx5124fmaddps_4fnmaddss_maskz;
	  goto s4fma_expand;

	case IX86_BUILTIN_4FMASS_MASK:
	  {
	    tree args[4];
	    rtx ops[4];
	    rtx wide_reg;
	    rtx accum;
	    rtx addr;
	    rtx mem;

	    fcn_mask = gen_avx5124fmaddps_4fmaddss_mask;
	    fcn_maskz = gen_avx5124fmaddps_4fmaddss_maskz;

s4fma_expand:
	    mode = V4SFmode;
	    wide_reg = gen_reg_rtx (V64SFmode);
	    for (i = 0; i < 4; i++)
	      {
		rtx tmp;
		args[i] = CALL_EXPR_ARG (exp, i);
		ops[i] = expand_normal (args[i]);

		tmp = gen_reg_rtx (SFmode);
		emit_move_insn (tmp, gen_rtx_SUBREG (SFmode, ops[i], 0));

		emit_move_insn (gen_rtx_SUBREG (V16SFmode, wide_reg, i * 64),
				gen_rtx_SUBREG (V16SFmode, tmp, 0));
	      }

	    accum = expand_normal (CALL_EXPR_ARG (exp, 4));
	    accum = force_reg (V4SFmode, accum);

	    addr = expand_normal (CALL_EXPR_ARG (exp, 5));
	    addr = force_reg (Pmode, addr);

	    mem = gen_rtx_MEM (V4SFmode, addr);

	    target = gen_reg_rtx (V4SFmode);

	    emit_move_insn (target, accum);

	    if (! masked)
	      emit_insn (fcn (target, accum, wide_reg, mem));
	    else
	      {
		rtx merge, mask;
		merge = expand_normal (CALL_EXPR_ARG (exp, 6));

		mask = expand_normal (CALL_EXPR_ARG (exp, 7));

		if (CONST_INT_P (mask))
		  mask = fixup_modeless_constant (mask, QImode);

		mask = force_reg (QImode, mask);

		if (GET_MODE (mask) != QImode)
		  mask = gen_rtx_SUBREG (QImode, mask, 0);

		/* If merge is 0 then we're about to emit z-masked variant.  */
		if (const0_operand (merge, mode))
		  emit_insn (fcn_maskz (target, accum, wide_reg, mem, merge, mask));
		/* If merge is the same as accum then emit merge-masked
		   variant.  */
		else if (CALL_EXPR_ARG (exp, 6) == CALL_EXPR_ARG (exp, 4))
		  {
		    merge = force_reg (mode, merge);
		    emit_insn (fcn_mask (target, wide_reg, mem, merge, mask));
		  }
		/* Merge with something unknown might happen if we z-mask
		   w/ -O0.  */
		else
		  {
		    target = gen_reg_rtx (mode);
		    emit_move_insn (target, merge);
		    emit_insn (fcn_mask (target, wide_reg, mem, target, mask));
		  }
		}
	      return target;
	    }
	  case IX86_BUILTIN_RDPID:
	    return ix86_expand_special_args_builtin (bdesc_args + i, exp,
						     target);
	  case IX86_BUILTIN_FABSQ:
	  case IX86_BUILTIN_COPYSIGNQ:
	    if (!TARGET_SSE)
	      /* Emit a normal call if SSE isn't available.  */
	      return expand_call (exp, target, ignore);
	    /* FALLTHRU */
	  default:
	    return ix86_expand_args_builtin (bdesc_args + i, exp, target);
	  }
    }

  if (fcode >= IX86_BUILTIN__BDESC_COMI_FIRST
      && fcode <= IX86_BUILTIN__BDESC_COMI_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_COMI_FIRST;
      return ix86_expand_sse_comi (bdesc_comi + i, exp, target);
    }

  if (fcode >= IX86_BUILTIN__BDESC_ROUND_ARGS_FIRST
      && fcode <= IX86_BUILTIN__BDESC_ROUND_ARGS_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_ROUND_ARGS_FIRST;
      return ix86_expand_round_builtin (bdesc_round_args + i, exp, target);
    }

  if (fcode >= IX86_BUILTIN__BDESC_PCMPESTR_FIRST
      && fcode <= IX86_BUILTIN__BDESC_PCMPESTR_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_PCMPESTR_FIRST;
      return ix86_expand_sse_pcmpestr (bdesc_pcmpestr + i, exp, target);
    }

  if (fcode >= IX86_BUILTIN__BDESC_PCMPISTR_FIRST
      && fcode <= IX86_BUILTIN__BDESC_PCMPISTR_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_PCMPISTR_FIRST;
      return ix86_expand_sse_pcmpistr (bdesc_pcmpistr + i, exp, target);
    }

  if (fcode >= IX86_BUILTIN__BDESC_MULTI_ARG_FIRST
      && fcode <= IX86_BUILTIN__BDESC_MULTI_ARG_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_MULTI_ARG_FIRST;
      const struct builtin_description *d = bdesc_multi_arg + i;
      return ix86_expand_multi_arg_builtin (d->icode, exp, target,
					    (enum ix86_builtin_func_type)
					    d->flag, d->comparison);
    }

  if (fcode >= IX86_BUILTIN__BDESC_CET_FIRST
      && fcode <= IX86_BUILTIN__BDESC_CET_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_CET_FIRST;
      return ix86_expand_special_args_builtin (bdesc_cet + i, exp,
					       target);
    }

  if (fcode >= IX86_BUILTIN__BDESC_CET_NORMAL_FIRST
      && fcode <= IX86_BUILTIN__BDESC_CET_NORMAL_LAST)
    {
      i = fcode - IX86_BUILTIN__BDESC_CET_NORMAL_FIRST;
      return ix86_expand_special_args_builtin (bdesc_cet_rdssp + i, exp,
				       target);
    }

  gcc_unreachable ();
}

/* This returns the target-specific builtin with code CODE if
   current_function_decl has visibility on this builtin, which is checked
   using isa flags.  Returns NULL_TREE otherwise.  */

static tree ix86_get_builtin (enum ix86_builtins code)
{
  struct cl_target_option *opts;
  tree target_tree = NULL_TREE;

  /* Determine the isa flags of current_function_decl.  */

  if (current_function_decl)
    target_tree = DECL_FUNCTION_SPECIFIC_TARGET (current_function_decl);

  if (target_tree == NULL)
    target_tree = target_option_default_node;

  opts = TREE_TARGET_OPTION (target_tree);

  if ((ix86_builtins_isa[(int) code].isa & opts->x_ix86_isa_flags)
      || (ix86_builtins_isa[(int) code].isa2 & opts->x_ix86_isa_flags2))
    return ix86_builtin_decl (code, true);
  else
    return NULL_TREE;
}

/* Returns a function decl for a vectorized version of the combined function
   with combined_fn code FN and the result vector type TYPE, or NULL_TREE
   if it is not available.  */

static tree
ix86_builtin_vectorized_function (unsigned int fn, tree type_out,
				  tree type_in)
{
  machine_mode in_mode, out_mode;
  int in_n, out_n;

  if (TREE_CODE (type_out) != VECTOR_TYPE
      || TREE_CODE (type_in) != VECTOR_TYPE)
    return NULL_TREE;

  out_mode = TYPE_MODE (TREE_TYPE (type_out));
  out_n = TYPE_VECTOR_SUBPARTS (type_out);
  in_mode = TYPE_MODE (TREE_TYPE (type_in));
  in_n = TYPE_VECTOR_SUBPARTS (type_in);

  switch (fn)
    {
    CASE_CFN_EXP2:
      if (out_mode == SFmode && in_mode == SFmode)
	{
	  if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_EXP2PS);
	}
      break;

    CASE_CFN_IFLOOR:
    CASE_CFN_LFLOOR:
    CASE_CFN_LLFLOOR:
      /* The round insn does not trap on denormals.  */
      if (flag_trapping_math || !TARGET_SSE4_1)
	break;

      if (out_mode == SImode && in_mode == DFmode)
	{
	  if (out_n == 4 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPD_VEC_PACK_SFIX);
	  else if (out_n == 8 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPD_VEC_PACK_SFIX256);
	  else if (out_n == 16 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPD_VEC_PACK_SFIX512);
	}
      if (out_mode == SImode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPS_SFIX);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPS_SFIX256);
	  else if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPS_SFIX512);
	}
      break;

    CASE_CFN_ICEIL:
    CASE_CFN_LCEIL:
    CASE_CFN_LLCEIL:
      /* The round insn does not trap on denormals.  */
      if (flag_trapping_math || !TARGET_SSE4_1)
	break;

      if (out_mode == SImode && in_mode == DFmode)
	{
	  if (out_n == 4 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPD_VEC_PACK_SFIX);
	  else if (out_n == 8 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPD_VEC_PACK_SFIX256);
	  else if (out_n == 16 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPD_VEC_PACK_SFIX512);
	}
      if (out_mode == SImode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPS_SFIX);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPS_SFIX256);
	  else if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPS_SFIX512);
	}
      break;

    CASE_CFN_IRINT:
    CASE_CFN_LRINT:
    CASE_CFN_LLRINT:
      if (out_mode == SImode && in_mode == DFmode)
	{
	  if (out_n == 4 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_VEC_PACK_SFIX);
	  else if (out_n == 8 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_VEC_PACK_SFIX256);
	  else if (out_n == 16 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_VEC_PACK_SFIX512);
	}
      if (out_mode == SImode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_CVTPS2DQ);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_CVTPS2DQ256);
	  else if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_CVTPS2DQ512);
	}
      break;

    CASE_CFN_IROUND:
    CASE_CFN_LROUND:
    CASE_CFN_LLROUND:
      /* The round insn does not trap on denormals.  */
      if (flag_trapping_math || !TARGET_SSE4_1)
	break;

      if (out_mode == SImode && in_mode == DFmode)
	{
	  if (out_n == 4 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_ROUNDPD_AZ_VEC_PACK_SFIX);
	  else if (out_n == 8 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_ROUNDPD_AZ_VEC_PACK_SFIX256);
	  else if (out_n == 16 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_ROUNDPD_AZ_VEC_PACK_SFIX512);
	}
      if (out_mode == SImode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_ROUNDPS_AZ_SFIX);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_ROUNDPS_AZ_SFIX256);
	  else if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_ROUNDPS_AZ_SFIX512);
	}
      break;

    CASE_CFN_FLOOR:
      /* The round insn does not trap on denormals.  */
      if (flag_trapping_math || !TARGET_SSE4_1)
	break;

      if (out_mode == DFmode && in_mode == DFmode)
	{
	  if (out_n == 2 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPD);
	  else if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPD256);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPD512);
	}
      if (out_mode == SFmode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPS);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPS256);
	  else if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_FLOORPS512);
	}
      break;

    CASE_CFN_CEIL:
      /* The round insn does not trap on denormals.  */
      if (flag_trapping_math || !TARGET_SSE4_1)
	break;

      if (out_mode == DFmode && in_mode == DFmode)
	{
	  if (out_n == 2 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPD);
	  else if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPD256);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPD512);
	}
      if (out_mode == SFmode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPS);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPS256);
	  else if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_CEILPS512);
	}
      break;

    CASE_CFN_TRUNC:
      /* The round insn does not trap on denormals.  */
      if (flag_trapping_math || !TARGET_SSE4_1)
	break;

      if (out_mode == DFmode && in_mode == DFmode)
	{
	  if (out_n == 2 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_TRUNCPD);
	  else if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_TRUNCPD256);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_TRUNCPD512);
	}
      if (out_mode == SFmode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_TRUNCPS);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_TRUNCPS256);
	  else if (out_n == 16 && in_n == 16)
	    return ix86_get_builtin (IX86_BUILTIN_TRUNCPS512);
	}
      break;

    CASE_CFN_RINT:
      /* The round insn does not trap on denormals.  */
      if (flag_trapping_math || !TARGET_SSE4_1)
	break;

      if (out_mode == DFmode && in_mode == DFmode)
	{
	  if (out_n == 2 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_RINTPD);
	  else if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_RINTPD256);
	}
      if (out_mode == SFmode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_RINTPS);
	  else if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_RINTPS256);
	}
      break;

    CASE_CFN_FMA:
      if (out_mode == DFmode && in_mode == DFmode)
	{
	  if (out_n == 2 && in_n == 2)
	    return ix86_get_builtin (IX86_BUILTIN_VFMADDPD);
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_VFMADDPD256);
	}
      if (out_mode == SFmode && in_mode == SFmode)
	{
	  if (out_n == 4 && in_n == 4)
	    return ix86_get_builtin (IX86_BUILTIN_VFMADDPS);
	  if (out_n == 8 && in_n == 8)
	    return ix86_get_builtin (IX86_BUILTIN_VFMADDPS256);
	}
      break;

    default:
      break;
    }

  /* Dispatch to a handler for a vectorization library.  */
  if (ix86_veclib_handler)
    return ix86_veclib_handler (combined_fn (fn), type_out, type_in);

  return NULL_TREE;
}

/* Handler for an SVML-style interface to
   a library with vectorized intrinsics.  */

static tree
ix86_veclibabi_svml (combined_fn fn, tree type_out, tree type_in)
{
  char name[20];
  tree fntype, new_fndecl, args;
  unsigned arity;
  const char *bname;
  machine_mode el_mode, in_mode;
  int n, in_n;

  /* The SVML is suitable for unsafe math only.  */
  if (!flag_unsafe_math_optimizations)
    return NULL_TREE;

  el_mode = TYPE_MODE (TREE_TYPE (type_out));
  n = TYPE_VECTOR_SUBPARTS (type_out);
  in_mode = TYPE_MODE (TREE_TYPE (type_in));
  in_n = TYPE_VECTOR_SUBPARTS (type_in);
  if (el_mode != in_mode
      || n != in_n)
    return NULL_TREE;

  switch (fn)
    {
    CASE_CFN_EXP:
    CASE_CFN_LOG:
    CASE_CFN_LOG10:
    CASE_CFN_POW:
    CASE_CFN_TANH:
    CASE_CFN_TAN:
    CASE_CFN_ATAN:
    CASE_CFN_ATAN2:
    CASE_CFN_ATANH:
    CASE_CFN_CBRT:
    CASE_CFN_SINH:
    CASE_CFN_SIN:
    CASE_CFN_ASINH:
    CASE_CFN_ASIN:
    CASE_CFN_COSH:
    CASE_CFN_COS:
    CASE_CFN_ACOSH:
    CASE_CFN_ACOS:
      if ((el_mode != DFmode || n != 2)
	  && (el_mode != SFmode || n != 4))
	return NULL_TREE;
      break;

    default:
      return NULL_TREE;
    }

  tree fndecl = mathfn_built_in (TREE_TYPE (type_in), fn);
  bname = IDENTIFIER_POINTER (DECL_NAME (fndecl));

  if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_LOGF)
    strcpy (name, "vmlsLn4");
  else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_LOG)
    strcpy (name, "vmldLn2");
  else if (n == 4)
    {
      sprintf (name, "vmls%s", bname+10);
      name[strlen (name)-1] = '4';
    }
  else
    sprintf (name, "vmld%s2", bname+10);

  /* Convert to uppercase. */
  name[4] &= ~0x20;

  arity = 0;
  for (args = DECL_ARGUMENTS (fndecl); args; args = TREE_CHAIN (args))
    arity++;

  if (arity == 1)
    fntype = build_function_type_list (type_out, type_in, NULL);
  else
    fntype = build_function_type_list (type_out, type_in, type_in, NULL);

  /* Build a function declaration for the vectorized function.  */
  new_fndecl = build_decl (BUILTINS_LOCATION,
			   FUNCTION_DECL, get_identifier (name), fntype);
  TREE_PUBLIC (new_fndecl) = 1;
  DECL_EXTERNAL (new_fndecl) = 1;
  DECL_IS_NOVOPS (new_fndecl) = 1;
  TREE_READONLY (new_fndecl) = 1;

  return new_fndecl;
}

/* Handler for an ACML-style interface to
   a library with vectorized intrinsics.  */

static tree
ix86_veclibabi_acml (combined_fn fn, tree type_out, tree type_in)
{
  char name[20] = "__vr.._";
  tree fntype, new_fndecl, args;
  unsigned arity;
  const char *bname;
  machine_mode el_mode, in_mode;
  int n, in_n;

  /* The ACML is 64bits only and suitable for unsafe math only as
     it does not correctly support parts of IEEE with the required
     precision such as denormals.  */
  if (!TARGET_64BIT
      || !flag_unsafe_math_optimizations)
    return NULL_TREE;

  el_mode = TYPE_MODE (TREE_TYPE (type_out));
  n = TYPE_VECTOR_SUBPARTS (type_out);
  in_mode = TYPE_MODE (TREE_TYPE (type_in));
  in_n = TYPE_VECTOR_SUBPARTS (type_in);
  if (el_mode != in_mode
      || n != in_n)
    return NULL_TREE;

  switch (fn)
    {
    CASE_CFN_SIN:
    CASE_CFN_COS:
    CASE_CFN_EXP:
    CASE_CFN_LOG:
    CASE_CFN_LOG2:
    CASE_CFN_LOG10:
      if (el_mode == DFmode && n == 2)
	{
	  name[4] = 'd';
	  name[5] = '2';
	}
      else if (el_mode == SFmode && n == 4)
	{
	  name[4] = 's';
	  name[5] = '4';
	}
      else
	return NULL_TREE;
      break;

    default:
      return NULL_TREE;
    }

  tree fndecl = mathfn_built_in (TREE_TYPE (type_in), fn);
  bname = IDENTIFIER_POINTER (DECL_NAME (fndecl));
  sprintf (name + 7, "%s", bname+10);

  arity = 0;
  for (args = DECL_ARGUMENTS (fndecl); args; args = TREE_CHAIN (args))
    arity++;

  if (arity == 1)
    fntype = build_function_type_list (type_out, type_in, NULL);
  else
    fntype = build_function_type_list (type_out, type_in, type_in, NULL);

  /* Build a function declaration for the vectorized function.  */
  new_fndecl = build_decl (BUILTINS_LOCATION,
			   FUNCTION_DECL, get_identifier (name), fntype);
  TREE_PUBLIC (new_fndecl) = 1;
  DECL_EXTERNAL (new_fndecl) = 1;
  DECL_IS_NOVOPS (new_fndecl) = 1;
  TREE_READONLY (new_fndecl) = 1;

  return new_fndecl;
}

/* Returns a decl of a function that implements gather load with
   memory type MEM_VECTYPE and index type INDEX_VECTYPE and SCALE.
   Return NULL_TREE if it is not available.  */

static tree
ix86_vectorize_builtin_gather (const_tree mem_vectype,
			       const_tree index_type, int scale)
{
  bool si;
  enum ix86_builtins code;

  if (! TARGET_AVX2 || !TARGET_USE_GATHER)
    return NULL_TREE;

  if ((TREE_CODE (index_type) != INTEGER_TYPE
       && !POINTER_TYPE_P (index_type))
      || (TYPE_MODE (index_type) != SImode
	  && TYPE_MODE (index_type) != DImode))
    return NULL_TREE;

  if (TYPE_PRECISION (index_type) > POINTER_SIZE)
    return NULL_TREE;

  /* v*gather* insn sign extends index to pointer mode.  */
  if (TYPE_PRECISION (index_type) < POINTER_SIZE
      && TYPE_UNSIGNED (index_type))
    return NULL_TREE;

  if (scale <= 0
      || scale > 8
      || (scale & (scale - 1)) != 0)
    return NULL_TREE;

  si = TYPE_MODE (index_type) == SImode;
  switch (TYPE_MODE (mem_vectype))
    {
    case E_V2DFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3SIV2DF : IX86_BUILTIN_GATHER3DIV2DF;
      else
	code = si ? IX86_BUILTIN_GATHERSIV2DF : IX86_BUILTIN_GATHERDIV2DF;
      break;
    case E_V4DFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3ALTSIV4DF : IX86_BUILTIN_GATHER3DIV4DF;
      else
	code = si ? IX86_BUILTIN_GATHERALTSIV4DF : IX86_BUILTIN_GATHERDIV4DF;
      break;
    case E_V2DImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3SIV2DI : IX86_BUILTIN_GATHER3DIV2DI;
      else
	code = si ? IX86_BUILTIN_GATHERSIV2DI : IX86_BUILTIN_GATHERDIV2DI;
      break;
    case E_V4DImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3ALTSIV4DI : IX86_BUILTIN_GATHER3DIV4DI;
      else
	code = si ? IX86_BUILTIN_GATHERALTSIV4DI : IX86_BUILTIN_GATHERDIV4DI;
      break;
    case E_V4SFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3SIV4SF : IX86_BUILTIN_GATHER3DIV4SF;
      else
	code = si ? IX86_BUILTIN_GATHERSIV4SF : IX86_BUILTIN_GATHERDIV4SF;
      break;
    case E_V8SFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3SIV8SF : IX86_BUILTIN_GATHER3ALTDIV8SF;
      else
	code = si ? IX86_BUILTIN_GATHERSIV8SF : IX86_BUILTIN_GATHERALTDIV8SF;
      break;
    case E_V4SImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3SIV4SI : IX86_BUILTIN_GATHER3DIV4SI;
      else
	code = si ? IX86_BUILTIN_GATHERSIV4SI : IX86_BUILTIN_GATHERDIV4SI;
      break;
    case E_V8SImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_GATHER3SIV8SI : IX86_BUILTIN_GATHER3ALTDIV8SI;
      else
	code = si ? IX86_BUILTIN_GATHERSIV8SI : IX86_BUILTIN_GATHERALTDIV8SI;
      break;
    case E_V8DFmode:
      if (TARGET_AVX512F)
	code = si ? IX86_BUILTIN_GATHER3ALTSIV8DF : IX86_BUILTIN_GATHER3DIV8DF;
      else
	return NULL_TREE;
      break;
    case E_V8DImode:
      if (TARGET_AVX512F)
	code = si ? IX86_BUILTIN_GATHER3ALTSIV8DI : IX86_BUILTIN_GATHER3DIV8DI;
      else
	return NULL_TREE;
      break;
    case E_V16SFmode:
      if (TARGET_AVX512F)
	code = si ? IX86_BUILTIN_GATHER3SIV16SF : IX86_BUILTIN_GATHER3ALTDIV16SF;
      else
	return NULL_TREE;
      break;
    case E_V16SImode:
      if (TARGET_AVX512F)
	code = si ? IX86_BUILTIN_GATHER3SIV16SI : IX86_BUILTIN_GATHER3ALTDIV16SI;
      else
	return NULL_TREE;
      break;
    default:
      return NULL_TREE;
    }

  return ix86_get_builtin (code);
}

/* Returns a decl of a function that implements scatter store with
   register type VECTYPE and index type INDEX_TYPE and SCALE.
   Return NULL_TREE if it is not available.  */

static tree
ix86_vectorize_builtin_scatter (const_tree vectype,
				const_tree index_type, int scale)
{
  bool si;
  enum ix86_builtins code;

  if (!TARGET_AVX512F)
    return NULL_TREE;

  if ((TREE_CODE (index_type) != INTEGER_TYPE
       && !POINTER_TYPE_P (index_type))
      || (TYPE_MODE (index_type) != SImode
	  && TYPE_MODE (index_type) != DImode))
    return NULL_TREE;

  if (TYPE_PRECISION (index_type) > POINTER_SIZE)
    return NULL_TREE;

  /* v*scatter* insn sign extends index to pointer mode.  */
  if (TYPE_PRECISION (index_type) < POINTER_SIZE
      && TYPE_UNSIGNED (index_type))
    return NULL_TREE;

  /* Scale can be 1, 2, 4 or 8.  */
  if (scale <= 0
      || scale > 8
      || (scale & (scale - 1)) != 0)
    return NULL_TREE;

  si = TYPE_MODE (index_type) == SImode;
  switch (TYPE_MODE (vectype))
    {
    case E_V8DFmode:
      code = si ? IX86_BUILTIN_SCATTERALTSIV8DF : IX86_BUILTIN_SCATTERDIV8DF;
      break;
    case E_V8DImode:
      code = si ? IX86_BUILTIN_SCATTERALTSIV8DI : IX86_BUILTIN_SCATTERDIV8DI;
      break;
    case E_V16SFmode:
      code = si ? IX86_BUILTIN_SCATTERSIV16SF : IX86_BUILTIN_SCATTERALTDIV16SF;
      break;
    case E_V16SImode:
      code = si ? IX86_BUILTIN_SCATTERSIV16SI : IX86_BUILTIN_SCATTERALTDIV16SI;
      break;
    case E_V4DFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERALTSIV4DF : IX86_BUILTIN_SCATTERDIV4DF;
      else
	return NULL_TREE;
      break;
    case E_V4DImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERALTSIV4DI : IX86_BUILTIN_SCATTERDIV4DI;
      else
	return NULL_TREE;
      break;
    case E_V8SFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERSIV8SF : IX86_BUILTIN_SCATTERALTDIV8SF;
      else
	return NULL_TREE;
      break;
    case E_V8SImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERSIV8SI : IX86_BUILTIN_SCATTERALTDIV8SI;
      else
	return NULL_TREE;
      break;
    case E_V2DFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERALTSIV2DF : IX86_BUILTIN_SCATTERDIV2DF;
      else
	return NULL_TREE;
      break;
    case E_V2DImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERALTSIV2DI : IX86_BUILTIN_SCATTERDIV2DI;
      else
	return NULL_TREE;
      break;
    case E_V4SFmode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERSIV4SF : IX86_BUILTIN_SCATTERALTDIV4SF;
      else
	return NULL_TREE;
      break;
    case E_V4SImode:
      if (TARGET_AVX512VL)
	code = si ? IX86_BUILTIN_SCATTERSIV4SI : IX86_BUILTIN_SCATTERALTDIV4SI;
      else
	return NULL_TREE;
      break;
    default:
      return NULL_TREE;
    }

  return ix86_builtins[code];
}

/* Return true if it is safe to use the rsqrt optabs to optimize
   1.0/sqrt.  */

static bool
use_rsqrt_p ()
{
  return (TARGET_SSE_MATH
	  && flag_finite_math_only
	  && !flag_trapping_math
	  && flag_unsafe_math_optimizations);
}

/* Returns a code for a target-specific builtin that implements
   reciprocal of the function, or NULL_TREE if not available.  */

static tree
ix86_builtin_reciprocal (tree fndecl)
{
  switch (DECL_FUNCTION_CODE (fndecl))
    {
      /* Vectorized version of sqrt to rsqrt conversion.  */
    case IX86_BUILTIN_SQRTPS_NR:
      return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR);

    case IX86_BUILTIN_SQRTPS_NR256:
      return ix86_get_builtin (IX86_BUILTIN_RSQRTPS_NR256);

    default:
      return NULL_TREE;
    }
}

/* Helper for avx_vpermilps256_operand et al.  This is also used by
   the expansion functions to turn the parallel back into a mask.
   The return value is 0 for no match and the imm8+1 for a match.  */

int
avx_vpermilp_parallel (rtx par, machine_mode mode)
{
  unsigned i, nelt = GET_MODE_NUNITS (mode);
  unsigned mask = 0;
  unsigned char ipar[16] = {};  /* Silence -Wuninitialized warning.  */

  if (XVECLEN (par, 0) != (int) nelt)
    return 0;

  /* Validate that all of the elements are constants, and not totally
     out of range.  Copy the data into an integral array to make the
     subsequent checks easier.  */
  for (i = 0; i < nelt; ++i)
    {
      rtx er = XVECEXP (par, 0, i);
      unsigned HOST_WIDE_INT ei;

      if (!CONST_INT_P (er))
	return 0;
      ei = INTVAL (er);
      if (ei >= nelt)
	return 0;
      ipar[i] = ei;
    }

  switch (mode)
    {
    case E_V8DFmode:
      /* In the 512-bit DFmode case, we can only move elements within
         a 128-bit lane.  First fill the second part of the mask,
	 then fallthru.  */
      for (i = 4; i < 6; ++i)
	{
	  if (ipar[i] < 4 || ipar[i] >= 6)
	    return 0;
	  mask |= (ipar[i] - 4) << i;
	}
      for (i = 6; i < 8; ++i)
	{
	  if (ipar[i] < 6)
	    return 0;
	  mask |= (ipar[i] - 6) << i;
	}
      /* FALLTHRU */

    case E_V4DFmode:
      /* In the 256-bit DFmode case, we can only move elements within
         a 128-bit lane.  */
      for (i = 0; i < 2; ++i)
	{
	  if (ipar[i] >= 2)
	    return 0;
	  mask |= ipar[i] << i;
	}
      for (i = 2; i < 4; ++i)
	{
	  if (ipar[i] < 2)
	    return 0;
	  mask |= (ipar[i] - 2) << i;
	}
      break;

    case E_V16SFmode:
      /* In 512 bit SFmode case, permutation in the upper 256 bits
	 must mirror the permutation in the lower 256-bits.  */
      for (i = 0; i < 8; ++i)
	if (ipar[i] + 8 != ipar[i + 8])
	  return 0;
      /* FALLTHRU */

    case E_V8SFmode:
      /* In 256 bit SFmode case, we have full freedom of
         movement within the low 128-bit lane, but the high 128-bit
         lane must mirror the exact same pattern.  */
      for (i = 0; i < 4; ++i)
	if (ipar[i] + 4 != ipar[i + 4])
	  return 0;
      nelt = 4;
      /* FALLTHRU */

    case E_V2DFmode:
    case E_V4SFmode:
      /* In the 128-bit case, we've full freedom in the placement of
	 the elements from the source operand.  */
      for (i = 0; i < nelt; ++i)
	mask |= ipar[i] << (i * (nelt / 2));
      break;

    default:
      gcc_unreachable ();
    }

  /* Make sure success has a non-zero value by adding one.  */
  return mask + 1;
}

/* Helper for avx_vperm2f128_v4df_operand et al.  This is also used by
   the expansion functions to turn the parallel back into a mask.
   The return value is 0 for no match and the imm8+1 for a match.  */

int
avx_vperm2f128_parallel (rtx par, machine_mode mode)
{
  unsigned i, nelt = GET_MODE_NUNITS (mode), nelt2 = nelt / 2;
  unsigned mask = 0;
  unsigned char ipar[8] = {};  /* Silence -Wuninitialized warning.  */

  if (XVECLEN (par, 0) != (int) nelt)
    return 0;

  /* Validate that all of the elements are constants, and not totally
     out of range.  Copy the data into an integral array to make the
     subsequent checks easier.  */
  for (i = 0; i < nelt; ++i)
    {
      rtx er = XVECEXP (par, 0, i);
      unsigned HOST_WIDE_INT ei;

      if (!CONST_INT_P (er))
	return 0;
      ei = INTVAL (er);
      if (ei >= 2 * nelt)
	return 0;
      ipar[i] = ei;
    }

  /* Validate that the halves of the permute are halves.  */
  for (i = 0; i < nelt2 - 1; ++i)
    if (ipar[i] + 1 != ipar[i + 1])
      return 0;
  for (i = nelt2; i < nelt - 1; ++i)
    if (ipar[i] + 1 != ipar[i + 1])
      return 0;

  /* Reconstruct the mask.  */
  for (i = 0; i < 2; ++i)
    {
      unsigned e = ipar[i * nelt2];
      if (e % nelt2)
	return 0;
      e /= nelt2;
      mask |= e << (i * 4);
    }

  /* Make sure success has a non-zero value by adding one.  */
  return mask + 1;
}

/* Return a register priority for hard reg REGNO.  */
static int
ix86_register_priority (int hard_regno)
{
  /* ebp and r13 as the base always wants a displacement, r12 as the
     base always wants an index.  So discourage their usage in an
     address.  */
  if (hard_regno == R12_REG || hard_regno == R13_REG)
    return 0;
  if (hard_regno == BP_REG)
    return 1;
  /* New x86-64 int registers result in bigger code size.  Discourage
     them.  */
  if (IN_RANGE (hard_regno, FIRST_REX_INT_REG, LAST_REX_INT_REG))
    return 2;
  /* New x86-64 SSE registers result in bigger code size.  Discourage
     them.  */
  if (IN_RANGE (hard_regno, FIRST_REX_SSE_REG, LAST_REX_SSE_REG))
    return 2;
  if (IN_RANGE (hard_regno, FIRST_EXT_REX_SSE_REG, LAST_EXT_REX_SSE_REG))
    return 1;
  /* Usage of AX register results in smaller code.  Prefer it.  */
  if (hard_regno == AX_REG)
    return 4;
  return 3;
}

/* Implement TARGET_PREFERRED_RELOAD_CLASS.

   Put float CONST_DOUBLE in the constant pool instead of fp regs.
   QImode must go into class Q_REGS.
   Narrow ALL_REGS to GENERAL_REGS.  This supports allowing movsf and
   movdf to do mem-to-mem moves through integer regs.  */

static reg_class_t
ix86_preferred_reload_class (rtx x, reg_class_t regclass)
{
  machine_mode mode = GET_MODE (x);

  /* We're only allowed to return a subclass of CLASS.  Many of the
     following checks fail for NO_REGS, so eliminate that early.  */
  if (regclass == NO_REGS)
    return NO_REGS;

  /* All classes can load zeros.  */
  if (x == CONST0_RTX (mode))
    return regclass;

  /* Force constants into memory if we are loading a (nonzero) constant into
     an MMX, SSE or MASK register.  This is because there are no MMX/SSE/MASK
     instructions to load from a constant.  */
  if (CONSTANT_P (x)
      && (MAYBE_MMX_CLASS_P (regclass)
	  || MAYBE_SSE_CLASS_P (regclass)
	  || MAYBE_MASK_CLASS_P (regclass)))
    return NO_REGS;

  /* Floating-point constants need more complex checks.  */
  if (CONST_DOUBLE_P (x))
    {
      /* General regs can load everything.  */
      if (INTEGER_CLASS_P (regclass))
        return regclass;

      /* Floats can load 0 and 1 plus some others.  Note that we eliminated
	 zero above.  We only want to wind up preferring 80387 registers if
	 we plan on doing computation with them.  */
      if (IS_STACK_MODE (mode)
	  && standard_80387_constant_p (x) > 0)
	{
	  /* Limit class to FP regs.  */
	  if (FLOAT_CLASS_P (regclass))
	    return FLOAT_REGS;
	}

      return NO_REGS;
    }

  /* Prefer SSE regs only, if we can use them for math.  */
  if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
    return SSE_CLASS_P (regclass) ? regclass : NO_REGS;

  /* Generally when we see PLUS here, it's the function invariant
     (plus soft-fp const_int).  Which can only be computed into general
     regs.  */
  if (GET_CODE (x) == PLUS)
    return INTEGER_CLASS_P (regclass) ? regclass : NO_REGS;

  /* QImode constants are easy to load, but non-constant QImode data
     must go into Q_REGS.  */
  if (GET_MODE (x) == QImode && !CONSTANT_P (x))
    {
      if (Q_CLASS_P (regclass))
	return regclass;
      else if (reg_class_subset_p (Q_REGS, regclass))
	return Q_REGS;
      else
	return NO_REGS;
    }

  return regclass;
}

/* Discourage putting floating-point values in SSE registers unless
   SSE math is being used, and likewise for the 387 registers.  */
static reg_class_t
ix86_preferred_output_reload_class (rtx x, reg_class_t regclass)
{
  machine_mode mode = GET_MODE (x);

  /* Restrict the output reload class to the register bank that we are doing
     math on.  If we would like not to return a subset of CLASS, reject this
     alternative: if reload cannot do this, it will still use its choice.  */
  mode = GET_MODE (x);
  if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
    return MAYBE_SSE_CLASS_P (regclass) ? ALL_SSE_REGS : NO_REGS;

  if (IS_STACK_MODE (mode))
    return FLOAT_CLASS_P (regclass) ? regclass : NO_REGS;

  return regclass;
}

static reg_class_t
ix86_secondary_reload (bool in_p, rtx x, reg_class_t rclass,
		       machine_mode mode, secondary_reload_info *sri)
{
  /* Double-word spills from general registers to non-offsettable memory
     references (zero-extended addresses) require special handling.  */
  if (TARGET_64BIT
      && MEM_P (x)
      && GET_MODE_SIZE (mode) > UNITS_PER_WORD
      && INTEGER_CLASS_P (rclass)
      && !offsettable_memref_p (x))
    {
      sri->icode = (in_p
		    ? CODE_FOR_reload_noff_load
		    : CODE_FOR_reload_noff_store);
      /* Add the cost of moving address to a temporary.  */
      sri->extra_cost = 1;

      return NO_REGS;
    }

  /* QImode spills from non-QI registers require
     intermediate register on 32bit targets.  */
  if (mode == QImode
      && ((!TARGET_64BIT && !in_p
	   && INTEGER_CLASS_P (rclass)
	   && MAYBE_NON_Q_CLASS_P (rclass))
	  || (!TARGET_AVX512DQ
	      && MAYBE_MASK_CLASS_P (rclass))))
    {
      int regno = true_regnum (x);

      /* Return Q_REGS if the operand is in memory.  */
      if (regno == -1)
	return Q_REGS;

      return NO_REGS;
    }

  /* This condition handles corner case where an expression involving
     pointers gets vectorized.  We're trying to use the address of a
     stack slot as a vector initializer.

     (set (reg:V2DI 74 [ vect_cst_.2 ])
          (vec_duplicate:V2DI (reg/f:DI 20 frame)))

     Eventually frame gets turned into sp+offset like this:

     (set (reg:V2DI 21 xmm0 [orig:74 vect_cst_.2 ] [74])
          (vec_duplicate:V2DI (plus:DI (reg/f:DI 7 sp)
	                               (const_int 392 [0x188]))))

     That later gets turned into:

     (set (reg:V2DI 21 xmm0 [orig:74 vect_cst_.2 ] [74])
          (vec_duplicate:V2DI (plus:DI (reg/f:DI 7 sp)
	    (mem/u/c/i:DI (symbol_ref/u:DI ("*.LC0") [flags 0x2]) [0 S8 A64]))))

     We'll have the following reload recorded:

     Reload 0: reload_in (DI) =
           (plus:DI (reg/f:DI 7 sp)
            (mem/u/c/i:DI (symbol_ref/u:DI ("*.LC0") [flags 0x2]) [0 S8 A64]))
     reload_out (V2DI) = (reg:V2DI 21 xmm0 [orig:74 vect_cst_.2 ] [74])
     SSE_REGS, RELOAD_OTHER (opnum = 0), can't combine
     reload_in_reg: (plus:DI (reg/f:DI 7 sp) (const_int 392 [0x188]))
     reload_out_reg: (reg:V2DI 21 xmm0 [orig:74 vect_cst_.2 ] [74])
     reload_reg_rtx: (reg:V2DI 22 xmm1)

     Which isn't going to work since SSE instructions can't handle scalar
     additions.  Returning GENERAL_REGS forces the addition into integer
     register and reload can handle subsequent reloads without problems.  */

  if (in_p && GET_CODE (x) == PLUS
      && SSE_CLASS_P (rclass)
      && SCALAR_INT_MODE_P (mode))
    return GENERAL_REGS;

  return NO_REGS;
}

/* Implement TARGET_CLASS_LIKELY_SPILLED_P.  */

static bool
ix86_class_likely_spilled_p (reg_class_t rclass)
{
  switch (rclass)
    {
      case AREG:
      case DREG:
      case CREG:
      case BREG:
      case AD_REGS:
      case SIREG:
      case DIREG:
      case SSE_FIRST_REG:
      case FP_TOP_REG:
      case FP_SECOND_REG:
	return true;

      default:
	break;
    }

  return false;
}

/* If we are copying between registers from different register sets
   (e.g. FP and integer), we may need a memory location.

   The function can't work reliably when one of the CLASSES is a class
   containing registers from multiple sets.  We avoid this by never combining
   different sets in a single alternative in the machine description.
   Ensure that this constraint holds to avoid unexpected surprises.

   When STRICT is false, we are being called from REGISTER_MOVE_COST,
   so do not enforce these sanity checks.

   To optimize register_move_cost performance, define inline variant.  */

static inline bool
inline_secondary_memory_needed (machine_mode mode, reg_class_t class1,
				reg_class_t class2, int strict)
{
  if (lra_in_progress && (class1 == NO_REGS || class2 == NO_REGS))
    return false;

  if (MAYBE_FLOAT_CLASS_P (class1) != FLOAT_CLASS_P (class1)
      || MAYBE_FLOAT_CLASS_P (class2) != FLOAT_CLASS_P (class2)
      || MAYBE_SSE_CLASS_P (class1) != SSE_CLASS_P (class1)
      || MAYBE_SSE_CLASS_P (class2) != SSE_CLASS_P (class2)
      || MAYBE_MMX_CLASS_P (class1) != MMX_CLASS_P (class1)
      || MAYBE_MMX_CLASS_P (class2) != MMX_CLASS_P (class2)
      || MAYBE_MASK_CLASS_P (class1) != MASK_CLASS_P (class1)
      || MAYBE_MASK_CLASS_P (class2) != MASK_CLASS_P (class2))
    {
      gcc_assert (!strict || lra_in_progress);
      return true;
    }

  if (FLOAT_CLASS_P (class1) != FLOAT_CLASS_P (class2))
    return true;

  /* Between mask and general, we have moves no larger than word size.  */
  if ((MASK_CLASS_P (class1) != MASK_CLASS_P (class2))
      && (GET_MODE_SIZE (mode) > UNITS_PER_WORD))
  return true;

  /* ??? This is a lie.  We do have moves between mmx/general, and for
     mmx/sse2.  But by saying we need secondary memory we discourage the
     register allocator from using the mmx registers unless needed.  */
  if (MMX_CLASS_P (class1) != MMX_CLASS_P (class2))
    return true;

  if (SSE_CLASS_P (class1) != SSE_CLASS_P (class2))
    {
      /* SSE1 doesn't have any direct moves from other classes.  */
      if (!TARGET_SSE2)
	return true;

      /* If the target says that inter-unit moves are more expensive
	 than moving through memory, then don't generate them.  */
      if ((SSE_CLASS_P (class1) && !TARGET_INTER_UNIT_MOVES_FROM_VEC)
	  || (SSE_CLASS_P (class2) && !TARGET_INTER_UNIT_MOVES_TO_VEC))
	return true;

      /* Between SSE and general, we have moves no larger than word size.  */
      if (GET_MODE_SIZE (mode) > UNITS_PER_WORD)
	return true;
    }

  return false;
}

/* Implement TARGET_SECONDARY_MEMORY_NEEDED.  */

static bool
ix86_secondary_memory_needed (machine_mode mode, reg_class_t class1,
			      reg_class_t class2)
{
  return inline_secondary_memory_needed (mode, class1, class2, true);
}

/* Implement TARGET_SECONDARY_MEMORY_NEEDED_MODE.

   get_secondary_mem widens integral modes to BITS_PER_WORD.
   There is no need to emit full 64 bit move on 64 bit targets
   for integral modes that can be moved using 32 bit move.  */

static machine_mode
ix86_secondary_memory_needed_mode (machine_mode mode)
{
  if (GET_MODE_BITSIZE (mode) < 32 && INTEGRAL_MODE_P (mode))
    return mode_for_size (32, GET_MODE_CLASS (mode), 0).require ();
  return mode;
}

/* Implement the TARGET_CLASS_MAX_NREGS hook.

   On the 80386, this is the size of MODE in words,
   except in the FP regs, where a single reg is always enough.  */

static unsigned char
ix86_class_max_nregs (reg_class_t rclass, machine_mode mode)
{
  if (MAYBE_INTEGER_CLASS_P (rclass))
    {
      if (mode == XFmode)
	return (TARGET_64BIT ? 2 : 3);
      else if (mode == XCmode)
	return (TARGET_64BIT ? 4 : 6);
      else
	return CEIL (GET_MODE_SIZE (mode), UNITS_PER_WORD);
    }
  else
    {
      if (COMPLEX_MODE_P (mode))
	return 2;
      else
	return 1;
    }
}

/* Implement TARGET_CAN_CHANGE_MODE_CLASS.  */

static bool
ix86_can_change_mode_class (machine_mode from, machine_mode to,
			    reg_class_t regclass)
{
  if (from == to)
    return true;

  /* x87 registers can't do subreg at all, as all values are reformatted
     to extended precision.  */
  if (MAYBE_FLOAT_CLASS_P (regclass))
    return false;

  if (MAYBE_SSE_CLASS_P (regclass) || MAYBE_MMX_CLASS_P (regclass))
    {
      /* Vector registers do not support QI or HImode loads.  If we don't
	 disallow a change to these modes, reload will assume it's ok to
	 drop the subreg from (subreg:SI (reg:HI 100) 0).  This affects
	 the vec_dupv4hi pattern.  */
      if (GET_MODE_SIZE (from) < 4)
	return false;
    }

  return true;
}

/* Return index of MODE in the sse load/store tables.  */

static inline int
sse_store_index (machine_mode mode)
{
      switch (GET_MODE_SIZE (mode))
	{
	  case 4:
	    return 0;
	  case 8:
	    return 1;
	  case 16:
	    return 2;
	  case 32:
	    return 3;
	  case 64:
	    return 4;
	  default:
	    return -1;
	}
}

/* Return the cost of moving data of mode M between a
   register and memory.  A value of 2 is the default; this cost is
   relative to those in `REGISTER_MOVE_COST'.

   This function is used extensively by register_move_cost that is used to
   build tables at startup.  Make it inline in this case.
   When IN is 2, return maximum of in and out move cost.

   If moving between registers and memory is more expensive than
   between two registers, you should define this macro to express the
   relative cost.

   Model also increased moving costs of QImode registers in non
   Q_REGS classes.
 */
static inline int
inline_memory_move_cost (machine_mode mode, enum reg_class regclass, int in)
{
  int cost;
  if (FLOAT_CLASS_P (regclass))
    {
      int index;
      switch (mode)
	{
	  case E_SFmode:
	    index = 0;
	    break;
	  case E_DFmode:
	    index = 1;
	    break;
	  case E_XFmode:
	    index = 2;
	    break;
	  default:
	    return 100;
	}
      if (in == 2)
        return MAX (ix86_cost->fp_load [index], ix86_cost->fp_store [index]);
      return in ? ix86_cost->fp_load [index] : ix86_cost->fp_store [index];
    }
  if (SSE_CLASS_P (regclass))
    {
      int index = sse_store_index (mode);
      if (index == -1)
	return 100;
      if (in == 2)
        return MAX (ix86_cost->sse_load [index], ix86_cost->sse_store [index]);
      return in ? ix86_cost->sse_load [index] : ix86_cost->sse_store [index];
    }
  if (MMX_CLASS_P (regclass))
    {
      int index;
      switch (GET_MODE_SIZE (mode))
	{
	  case 4:
	    index = 0;
	    break;
	  case 8:
	    index = 1;
	    break;
	  default:
	    return 100;
	}
      if (in == 2)
        return MAX (ix86_cost->mmx_load [index], ix86_cost->mmx_store [index]);
      return in ? ix86_cost->mmx_load [index] : ix86_cost->mmx_store [index];
    }
  switch (GET_MODE_SIZE (mode))
    {
      case 1:
	if (Q_CLASS_P (regclass) || TARGET_64BIT)
	  {
	    if (!in)
	      return ix86_cost->int_store[0];
	    if (TARGET_PARTIAL_REG_DEPENDENCY
	        && optimize_function_for_speed_p (cfun))
	      cost = ix86_cost->movzbl_load;
	    else
	      cost = ix86_cost->int_load[0];
	    if (in == 2)
	      return MAX (cost, ix86_cost->int_store[0]);
	    return cost;
	  }
	else
	  {
	   if (in == 2)
	     return MAX (ix86_cost->movzbl_load, ix86_cost->int_store[0] + 4);
	   if (in)
	     return ix86_cost->movzbl_load;
	   else
	     return ix86_cost->int_store[0] + 4;
	  }
	break;
      case 2:
	if (in == 2)
	  return MAX (ix86_cost->int_load[1], ix86_cost->int_store[1]);
	return in ? ix86_cost->int_load[1] : ix86_cost->int_store[1];
      default:
	if (in == 2)
	  cost = MAX (ix86_cost->int_load[2], ix86_cost->int_store[2]);
	else if (in)
	  cost = ix86_cost->int_load[2];
	else
	  cost = ix86_cost->int_store[2];
	/* Multiply with the number of GPR moves needed.  */
	return cost * CEIL ((int) GET_MODE_SIZE (mode), UNITS_PER_WORD);
    }
}

static int
ix86_memory_move_cost (machine_mode mode, reg_class_t regclass, bool in)
{
  return inline_memory_move_cost (mode, (enum reg_class) regclass, in ? 1 : 0);
}


/* Return the cost of moving data from a register in class CLASS1 to
   one in class CLASS2.

   It is not required that the cost always equal 2 when FROM is the same as TO;
   on some machines it is expensive to move between registers if they are not
   general registers.  */

static int
ix86_register_move_cost (machine_mode mode, reg_class_t class1_i,
			 reg_class_t class2_i)
{
  enum reg_class class1 = (enum reg_class) class1_i;
  enum reg_class class2 = (enum reg_class) class2_i;

  /* In case we require secondary memory, compute cost of the store followed
     by load.  In order to avoid bad register allocation choices, we need
     for this to be *at least* as high as the symmetric MEMORY_MOVE_COST.  */

  if (inline_secondary_memory_needed (mode, class1, class2, false))
    {
      int cost = 1;

      cost += inline_memory_move_cost (mode, class1, 2);
      cost += inline_memory_move_cost (mode, class2, 2);

      /* In case of copying from general_purpose_register we may emit multiple
         stores followed by single load causing memory size mismatch stall.
         Count this as arbitrarily high cost of 20.  */
      if (GET_MODE_BITSIZE (mode) > BITS_PER_WORD
	  && TARGET_MEMORY_MISMATCH_STALL
	  && targetm.class_max_nregs (class1, mode)
	     > targetm.class_max_nregs (class2, mode))
	cost += 20;

      /* In the case of FP/MMX moves, the registers actually overlap, and we
	 have to switch modes in order to treat them differently.  */
      if ((MMX_CLASS_P (class1) && MAYBE_FLOAT_CLASS_P (class2))
          || (MMX_CLASS_P (class2) && MAYBE_FLOAT_CLASS_P (class1)))
	cost += 20;

      return cost;
    }

  /* Moves between SSE/MMX and integer unit are expensive.  */
  if (MMX_CLASS_P (class1) != MMX_CLASS_P (class2)
      || SSE_CLASS_P (class1) != SSE_CLASS_P (class2))

    /* ??? By keeping returned value relatively high, we limit the number
       of moves between integer and MMX/SSE registers for all targets.
       Additionally, high value prevents problem with x86_modes_tieable_p(),
       where integer modes in MMX/SSE registers are not tieable
       because of missing QImode and HImode moves to, from or between
       MMX/SSE registers.  */
    return MAX (8, MMX_CLASS_P (class1) || MMX_CLASS_P (class2)
		? ix86_cost->mmxsse_to_integer : ix86_cost->ssemmx_to_integer);

  if (MAYBE_FLOAT_CLASS_P (class1))
    return ix86_cost->fp_move;
  if (MAYBE_SSE_CLASS_P (class1))
    {
      if (GET_MODE_BITSIZE (mode) <= 128)
	return ix86_cost->xmm_move;
      if (GET_MODE_BITSIZE (mode) <= 256)
	return ix86_cost->ymm_move;
      return ix86_cost->zmm_move;
    }
  if (MAYBE_MMX_CLASS_P (class1))
    return ix86_cost->mmx_move;
  return 2;
}

/* Implement TARGET_HARD_REGNO_NREGS.  This is ordinarily the length in
   words of a value of mode MODE but can be less for certain modes in
   special long registers.

   Actually there are no two word move instructions for consecutive
   registers.  And only registers 0-3 may have mov byte instructions
   applied to them.  */

static unsigned int
ix86_hard_regno_nregs (unsigned int regno, machine_mode mode)
{
  if (GENERAL_REGNO_P (regno))
    {
      if (mode == XFmode)
	return TARGET_64BIT ? 2 : 3;
      if (mode == XCmode)
	return TARGET_64BIT ? 4 : 6;
      return CEIL (GET_MODE_SIZE (mode), UNITS_PER_WORD);
    }
  if (COMPLEX_MODE_P (mode))
    return 2;
  if (mode == V64SFmode || mode == V64SImode)
    return 4;
  return 1;
}

/* Implement TARGET_HARD_REGNO_MODE_OK.  */

static bool
ix86_hard_regno_mode_ok (unsigned int regno, machine_mode mode)
{
  /* Flags and only flags can only hold CCmode values.  */
  if (CC_REGNO_P (regno))
    return GET_MODE_CLASS (mode) == MODE_CC;
  if (GET_MODE_CLASS (mode) == MODE_CC
      || GET_MODE_CLASS (mode) == MODE_RANDOM
      || GET_MODE_CLASS (mode) == MODE_PARTIAL_INT)
    return false;
  if (STACK_REGNO_P (regno))
    return VALID_FP_MODE_P (mode);
  if (MASK_REGNO_P (regno))
    return (VALID_MASK_REG_MODE (mode)
	    || (TARGET_AVX512BW
		&& VALID_MASK_AVX512BW_MODE (mode)));
  if (SSE_REGNO_P (regno))
    {
      /* We implement the move patterns for all vector modes into and
	 out of SSE registers, even when no operation instructions
	 are available.  */

      /* For AVX-512 we allow, regardless of regno:
	  - XI mode
	  - any of 512-bit wide vector mode
	  - any scalar mode.  */
      if (TARGET_AVX512F
	  && (mode == XImode
	      || VALID_AVX512F_REG_MODE (mode)
	      || VALID_AVX512F_SCALAR_MODE (mode)))
	return true;

      /* For AVX-5124FMAPS or AVX-5124VNNIW
	 allow V64SF and V64SI modes for special regnos.  */
      if ((TARGET_AVX5124FMAPS || TARGET_AVX5124VNNIW)
	  && (mode == V64SFmode || mode == V64SImode)
	  && MOD4_SSE_REGNO_P (regno))
	return true;

      /* TODO check for QI/HI scalars.  */
      /* AVX512VL allows sse regs16+ for 128/256 bit modes.  */
      if (TARGET_AVX512VL
	  && (mode == OImode
	      || mode == TImode
	      || VALID_AVX256_REG_MODE (mode)
	      || VALID_AVX512VL_128_REG_MODE (mode)))
	return true;

      /* xmm16-xmm31 are only available for AVX-512.  */
      if (EXT_REX_SSE_REGNO_P (regno))
	return false;

      /* OImode and AVX modes are available only when AVX is enabled.  */
      return ((TARGET_AVX
	       && VALID_AVX256_REG_OR_OI_MODE (mode))
	      || VALID_SSE_REG_MODE (mode)
	      || VALID_SSE2_REG_MODE (mode)
	      || VALID_MMX_REG_MODE (mode)
	      || VALID_MMX_REG_MODE_3DNOW (mode));
    }
  if (MMX_REGNO_P (regno))
    {
      /* We implement the move patterns for 3DNOW modes even in MMX mode,
	 so if the register is available at all, then we can move data of
	 the given mode into or out of it.  */
      return (VALID_MMX_REG_MODE (mode)
	      || VALID_MMX_REG_MODE_3DNOW (mode));
    }

  if (mode == QImode)
    {
      /* Take care for QImode values - they can be in non-QI regs,
	 but then they do cause partial register stalls.  */
      if (ANY_QI_REGNO_P (regno))
	return true;
      if (!TARGET_PARTIAL_REG_STALL)
	return true;
      /* LRA checks if the hard register is OK for the given mode.
	 QImode values can live in non-QI regs, so we allow all
	 registers here.  */
      if (lra_in_progress)
       return true;
      return !can_create_pseudo_p ();
    }
  /* We handle both integer and floats in the general purpose registers.  */
  else if (VALID_INT_MODE_P (mode))
    return true;
  else if (VALID_FP_MODE_P (mode))
    return true;
  else if (VALID_DFP_MODE_P (mode))
    return true;
  /* Lots of MMX code casts 8 byte vector modes to DImode.  If we then go
     on to use that value in smaller contexts, this can easily force a
     pseudo to be allocated to GENERAL_REGS.  Since this is no worse than
     supporting DImode, allow it.  */
  else if (VALID_MMX_REG_MODE_3DNOW (mode) || VALID_MMX_REG_MODE (mode))
    return true;

  return false;
}

/* Implement TARGET_HARD_REGNO_CALL_PART_CLOBBERED.  The only ABI that
   saves SSE registers across calls is Win64 (thus no need to check the
   current ABI here), and with AVX enabled Win64 only guarantees that
   the low 16 bytes are saved.  */

static bool
ix86_hard_regno_call_part_clobbered (rtx_insn *insn ATTRIBUTE_UNUSED,
				     unsigned int regno, machine_mode mode)
{
  return SSE_REGNO_P (regno) && GET_MODE_SIZE (mode) > 16;
}

/* A subroutine of ix86_modes_tieable_p.  Return true if MODE is a
   tieable integer mode.  */

static bool
ix86_tieable_integer_mode_p (machine_mode mode)
{
  switch (mode)
    {
    case E_HImode:
    case E_SImode:
      return true;

    case E_QImode:
      return TARGET_64BIT || !TARGET_PARTIAL_REG_STALL;

    case E_DImode:
      return TARGET_64BIT;

    default:
      return false;
    }
}

/* Implement TARGET_MODES_TIEABLE_P.

   Return true if MODE1 is accessible in a register that can hold MODE2
   without copying.  That is, all register classes that can hold MODE2
   can also hold MODE1.  */

static bool
ix86_modes_tieable_p (machine_mode mode1, machine_mode mode2)
{
  if (mode1 == mode2)
    return true;

  if (ix86_tieable_integer_mode_p (mode1)
      && ix86_tieable_integer_mode_p (mode2))
    return true;

  /* MODE2 being XFmode implies fp stack or general regs, which means we
     can tie any smaller floating point modes to it.  Note that we do not
     tie this with TFmode.  */
  if (mode2 == XFmode)
    return mode1 == SFmode || mode1 == DFmode;

  /* MODE2 being DFmode implies fp stack, general or sse regs, which means
     that we can tie it with SFmode.  */
  if (mode2 == DFmode)
    return mode1 == SFmode;

  /* If MODE2 is only appropriate for an SSE register, then tie with
     any other mode acceptable to SSE registers.  */
  if (GET_MODE_SIZE (mode2) == 64
      && ix86_hard_regno_mode_ok (FIRST_SSE_REG, mode2))
    return (GET_MODE_SIZE (mode1) == 64
	    && ix86_hard_regno_mode_ok (FIRST_SSE_REG, mode1));
  if (GET_MODE_SIZE (mode2) == 32
      && ix86_hard_regno_mode_ok (FIRST_SSE_REG, mode2))
    return (GET_MODE_SIZE (mode1) == 32
	    && ix86_hard_regno_mode_ok (FIRST_SSE_REG, mode1));
  if (GET_MODE_SIZE (mode2) == 16
      && ix86_hard_regno_mode_ok (FIRST_SSE_REG, mode2))
    return (GET_MODE_SIZE (mode1) == 16
	    && ix86_hard_regno_mode_ok (FIRST_SSE_REG, mode1));

  /* If MODE2 is appropriate for an MMX register, then tie
     with any other mode acceptable to MMX registers.  */
  if (GET_MODE_SIZE (mode2) == 8
      && ix86_hard_regno_mode_ok (FIRST_MMX_REG, mode2))
    return (GET_MODE_SIZE (mode1) == 8
	    && ix86_hard_regno_mode_ok (FIRST_MMX_REG, mode1));

  return false;
}

/* Return the cost of moving between two registers of mode MODE.  */

static int
ix86_set_reg_reg_cost (machine_mode mode)
{
  unsigned int units = UNITS_PER_WORD;

  switch (GET_MODE_CLASS (mode))
    {
    default:
      break;

    case MODE_CC:
      units = GET_MODE_SIZE (CCmode);
      break;

    case MODE_FLOAT:
      if ((TARGET_SSE && mode == TFmode)
	  || (TARGET_80387 && mode == XFmode)
	  || ((TARGET_80387 || TARGET_SSE2) && mode == DFmode)
	  || ((TARGET_80387 || TARGET_SSE) && mode == SFmode))
	units = GET_MODE_SIZE (mode);
      break;

    case MODE_COMPLEX_FLOAT:
      if ((TARGET_SSE && mode == TCmode)
	  || (TARGET_80387 && mode == XCmode)
	  || ((TARGET_80387 || TARGET_SSE2) && mode == DCmode)
	  || ((TARGET_80387 || TARGET_SSE) && mode == SCmode))
	units = GET_MODE_SIZE (mode);
      break;

    case MODE_VECTOR_INT:
    case MODE_VECTOR_FLOAT:
      if ((TARGET_AVX512F && VALID_AVX512F_REG_MODE (mode))
	  || (TARGET_AVX && VALID_AVX256_REG_MODE (mode))
	  || (TARGET_SSE2 && VALID_SSE2_REG_MODE (mode))
	  || (TARGET_SSE && VALID_SSE_REG_MODE (mode))
	  || (TARGET_MMX && VALID_MMX_REG_MODE (mode)))
	units = GET_MODE_SIZE (mode);
    }

  /* Return the cost of moving between two registers of mode MODE,
     assuming that the move will be in pieces of at most UNITS bytes.  */
  return COSTS_N_INSNS (CEIL (GET_MODE_SIZE (mode), units));
}

/* Return cost of vector operation in MODE given that scalar version has
   COST.  */

static int
ix86_vec_cost (machine_mode mode, int cost)
{
  if (!VECTOR_MODE_P (mode))
    return cost;

  if (GET_MODE_BITSIZE (mode) == 128
      && TARGET_SSE_SPLIT_REGS)
    return cost * 2;
  if (GET_MODE_BITSIZE (mode) > 128
      && TARGET_AVX128_OPTIMAL)
    return cost * GET_MODE_BITSIZE (mode) / 128;
  return cost;
}

/* Return cost of multiplication in MODE.  */

static int
ix86_multiplication_cost (const struct processor_costs *cost,
			  enum machine_mode mode)
{
  machine_mode inner_mode = mode;
  if (VECTOR_MODE_P (mode))
    inner_mode = GET_MODE_INNER (mode);

  if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
    return inner_mode == DFmode ? cost->mulsd : cost->mulss;
  else if (X87_FLOAT_MODE_P (mode))
    return cost->fmul;
  else if (FLOAT_MODE_P (mode))
    return  ix86_vec_cost (mode,
			   inner_mode == DFmode ? cost->mulsd : cost->mulss);
  else if (GET_MODE_CLASS (mode) == MODE_VECTOR_INT)
    {
      /* vpmullq is used in this case. No emulation is needed.  */
      if (TARGET_AVX512DQ)
	return ix86_vec_cost (mode, cost->mulss);

      /* V*QImode is emulated with 7-13 insns.  */
      if (mode == V16QImode || mode == V32QImode)
	{
	  int extra = 11;
	  if (TARGET_XOP && mode == V16QImode)
	    extra = 5;
	  else if (TARGET_SSSE3)
	    extra = 6;
	  return ix86_vec_cost (mode, cost->mulss * 2 + cost->sse_op * extra);
	}
      /* V*DImode is emulated with 5-8 insns.  */
      else if (mode == V2DImode || mode == V4DImode)
	{
	  if (TARGET_XOP && mode == V2DImode)
	    return ix86_vec_cost (mode, cost->mulss * 2 + cost->sse_op * 3);
	  else
	    return ix86_vec_cost (mode, cost->mulss * 3 + cost->sse_op * 5);
	}
      /* Without sse4.1, we don't have PMULLD; it's emulated with 7
	 insns, including two PMULUDQ.  */
      else if (mode == V4SImode && !(TARGET_SSE4_1 || TARGET_AVX))
	return ix86_vec_cost (mode, cost->mulss * 2 + cost->sse_op * 5);
      else
	return ix86_vec_cost (mode, cost->mulss);
    }
  else
    return (cost->mult_init[MODE_INDEX (mode)] + cost->mult_bit * 7);
}

/* Return cost of multiplication in MODE.  */

static int
ix86_division_cost (const struct processor_costs *cost,
			  enum machine_mode mode)
{
  machine_mode inner_mode = mode;
  if (VECTOR_MODE_P (mode))
    inner_mode = GET_MODE_INNER (mode);

  if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
    return inner_mode == DFmode ? cost->divsd : cost->divss;
  else if (X87_FLOAT_MODE_P (mode))
    return cost->fdiv;
  else if (FLOAT_MODE_P (mode))
    return ix86_vec_cost (mode,
			  inner_mode == DFmode ? cost->divsd : cost->divss);
  else
    return cost->divide[MODE_INDEX (mode)];
}

/* Return cost of shift in MODE.
   If CONSTANT_OP1 is true, the op1 value is known and set in OP1_VAL.
   AND_IN_OP1 specify in op1 is result of and and SHIFT_AND_TRUNCATE
   if op1 is a result of subreg.

   SKIP_OP0/1 is set to true if cost of OP0/1 should be ignored.  */

static int
ix86_shift_rotate_cost (const struct processor_costs *cost,
			enum machine_mode mode, bool constant_op1,
			HOST_WIDE_INT op1_val,
			bool speed,
			bool and_in_op1,
			bool shift_and_truncate,
			bool *skip_op0, bool *skip_op1)
{
  if (skip_op0)
    *skip_op0 = *skip_op1 = false;
  if (GET_MODE_CLASS (mode) == MODE_VECTOR_INT)
    {
      /* V*QImode is emulated with 1-11 insns.  */
      if (mode == V16QImode || mode == V32QImode)
	{
	  int count = 11;
	  if (TARGET_XOP && mode == V16QImode)
	    {
	      /* For XOP we use vpshab, which requires a broadcast of the
		 value to the variable shift insn.  For constants this
		 means a V16Q const in mem; even when we can perform the
		 shift with one insn set the cost to prefer paddb.  */
	      if (constant_op1)
		{
		  if (skip_op1)
		    *skip_op1 = true;
		  return ix86_vec_cost (mode,
					cost->sse_op
					+ (speed
					   ? 2
					   : COSTS_N_BYTES
					       (GET_MODE_UNIT_SIZE (mode))));
		}
	      count = 3;
	    }
	  else if (TARGET_SSSE3)
	    count = 7;
	  return ix86_vec_cost (mode, cost->sse_op * count);
	}
      else
	return ix86_vec_cost (mode, cost->sse_op);
    }
  if (GET_MODE_SIZE (mode) > UNITS_PER_WORD)
    {
      if (constant_op1)
	{
	  if (op1_val > 32)
	    return cost->shift_const + COSTS_N_INSNS (2);
	  else
	    return cost->shift_const * 2;
	}
      else
	{
	  if (and_in_op1)
	    return cost->shift_var * 2;
	  else
	    return cost->shift_var * 6 + COSTS_N_INSNS (2);
	}
    }
  else
    {
      if (constant_op1)
	return cost->shift_const;
      else if (shift_and_truncate)
	{
	  if (skip_op0)
	    *skip_op0 = *skip_op1 = true;
	  /* Return the cost after shift-and truncation.  */
	  return cost->shift_var;
	}
      else
	return cost->shift_var;
    }
  return cost->shift_const;
}

/* Compute a (partial) cost for rtx X.  Return true if the complete
   cost has been computed, and false if subexpressions should be
   scanned.  In either case, *TOTAL contains the cost result.  */

static bool
ix86_rtx_costs (rtx x, machine_mode mode, int outer_code_i, int opno,
		int *total, bool speed)
{
  rtx mask;
  enum rtx_code code = GET_CODE (x);
  enum rtx_code outer_code = (enum rtx_code) outer_code_i;
  const struct processor_costs *cost = speed ? ix86_cost : &ix86_size_cost;
  int src_cost;

  switch (code)
    {
    case SET:
      if (register_operand (SET_DEST (x), VOIDmode)
	  && register_operand (SET_SRC (x), VOIDmode))
	{
	  *total = ix86_set_reg_reg_cost (GET_MODE (SET_DEST (x)));
	  return true;
	}

      if (register_operand (SET_SRC (x), VOIDmode))
	/* Avoid potentially incorrect high cost from rtx_costs
	   for non-tieable SUBREGs.  */
	src_cost = 0;
      else
	{
	  src_cost = rtx_cost (SET_SRC (x), mode, SET, 1, speed);

	  if (CONSTANT_P (SET_SRC (x)))
	    /* Constant costs assume a base value of COSTS_N_INSNS (1) and add
	       a small value, possibly zero for cheap constants.  */
	    src_cost += COSTS_N_INSNS (1);
	}

      *total = src_cost + rtx_cost (SET_DEST (x), mode, SET, 0, speed);
      return true;

    case CONST_INT:
    case CONST:
    case LABEL_REF:
    case SYMBOL_REF:
      if (x86_64_immediate_operand (x, VOIDmode))
	*total = 0;
     else
	*total = 1;
      return true;

    case CONST_DOUBLE:
      if (IS_STACK_MODE (mode))
	switch (standard_80387_constant_p (x))
	  {
	  case -1:
	  case 0:
	    break;
	  case 1: /* 0.0 */
	    *total = 1;
	    return true;
	  default: /* Other constants */
	    *total = 2;
	    return true;
	  }
      /* FALLTHRU */

    case CONST_VECTOR:
      switch (standard_sse_constant_p (x, mode))
	{
	case 0:
	  break;
	case 1:  /* 0: xor eliminates false dependency */
	  *total = 0;
	  return true;
	default: /* -1: cmp contains false dependency */
	  *total = 1;
	  return true;
	}
      /* FALLTHRU */

    case CONST_WIDE_INT:
      /* Fall back to (MEM (SYMBOL_REF)), since that's where
	 it'll probably end up.  Add a penalty for size.  */
      *total = (COSTS_N_INSNS (1)
		+ (!TARGET_64BIT && flag_pic)
		+ (GET_MODE_SIZE (mode) <= 4
		   ? 0 : GET_MODE_SIZE (mode) <= 8 ? 1 : 2));
      return true;

    case ZERO_EXTEND:
      /* The zero extensions is often completely free on x86_64, so make
	 it as cheap as possible.  */
      if (TARGET_64BIT && mode == DImode
	  && GET_MODE (XEXP (x, 0)) == SImode)
	*total = 1;
      else if (TARGET_ZERO_EXTEND_WITH_AND)
	*total = cost->add;
      else
	*total = cost->movzx;
      return false;

    case SIGN_EXTEND:
      *total = cost->movsx;
      return false;

    case ASHIFT:
      if (SCALAR_INT_MODE_P (mode)
	  && GET_MODE_SIZE (mode) < UNITS_PER_WORD
	  && CONST_INT_P (XEXP (x, 1)))
	{
	  HOST_WIDE_INT value = INTVAL (XEXP (x, 1));
	  if (value == 1)
	    {
	      *total = cost->add;
	      return false;
	    }
	  if ((value == 2 || value == 3)
	      && cost->lea <= cost->shift_const)
	    {
	      *total = cost->lea;
	      return false;
	    }
	}
      /* FALLTHRU */

    case ROTATE:
    case ASHIFTRT:
    case LSHIFTRT:
    case ROTATERT:
      bool skip_op0, skip_op1;
      *total = ix86_shift_rotate_cost (cost, mode, CONSTANT_P (XEXP (x, 1)),
				       CONST_INT_P (XEXP (x, 1))
					 ? INTVAL (XEXP (x, 1)) : -1,
				       speed,
				       GET_CODE (XEXP (x, 1)) == AND,
				       SUBREG_P (XEXP (x, 1))
				       && GET_CODE (XEXP (XEXP (x, 1), 0)) == AND,
				       &skip_op0, &skip_op1);
      if (skip_op0 || skip_op1)
	{
	  if (!skip_op0)
	    *total += rtx_cost (XEXP (x, 0), mode, code, 0, speed);
	  if (!skip_op1)
	    *total += rtx_cost (XEXP (x, 1), mode, code, 0, speed);
	  return true;
	}
      return false;

    case FMA:
      {
	rtx sub;

        gcc_assert (FLOAT_MODE_P (mode));
        gcc_assert (TARGET_FMA || TARGET_FMA4 || TARGET_AVX512F);

        *total = ix86_vec_cost (mode,
				GET_MODE_INNER (mode) == SFmode
				? cost->fmass : cost->fmasd);
	*total += rtx_cost (XEXP (x, 1), mode, FMA, 1, speed);

        /* Negate in op0 or op2 is free: FMS, FNMA, FNMS.  */
	sub = XEXP (x, 0);
	if (GET_CODE (sub) == NEG)
	  sub = XEXP (sub, 0);
	*total += rtx_cost (sub, mode, FMA, 0, speed);

	sub = XEXP (x, 2);
	if (GET_CODE (sub) == NEG)
	  sub = XEXP (sub, 0);
	*total += rtx_cost (sub, mode, FMA, 2, speed);
	return true;
      }

    case MULT:
      if (!FLOAT_MODE_P (mode) && !VECTOR_MODE_P (mode))
	{
	  rtx op0 = XEXP (x, 0);
	  rtx op1 = XEXP (x, 1);
	  int nbits;
	  if (CONST_INT_P (XEXP (x, 1)))
	    {
	      unsigned HOST_WIDE_INT value = INTVAL (XEXP (x, 1));
	      for (nbits = 0; value != 0; value &= value - 1)
	        nbits++;
	    }
	  else
	    /* This is arbitrary.  */
	    nbits = 7;

	  /* Compute costs correctly for widening multiplication.  */
	  if ((GET_CODE (op0) == SIGN_EXTEND || GET_CODE (op0) == ZERO_EXTEND)
	      && GET_MODE_SIZE (GET_MODE (XEXP (op0, 0))) * 2
	         == GET_MODE_SIZE (mode))
	    {
	      int is_mulwiden = 0;
	      machine_mode inner_mode = GET_MODE (op0);

	      if (GET_CODE (op0) == GET_CODE (op1))
		is_mulwiden = 1, op1 = XEXP (op1, 0);
	      else if (CONST_INT_P (op1))
		{
		  if (GET_CODE (op0) == SIGN_EXTEND)
		    is_mulwiden = trunc_int_for_mode (INTVAL (op1), inner_mode)
			          == INTVAL (op1);
		  else
		    is_mulwiden = !(INTVAL (op1) & ~GET_MODE_MASK (inner_mode));
	        }

	      if (is_mulwiden)
	        op0 = XEXP (op0, 0), mode = GET_MODE (op0);
	    }

  	  *total = (cost->mult_init[MODE_INDEX (mode)]
		    + nbits * cost->mult_bit
	            + rtx_cost (op0, mode, outer_code, opno, speed)
		    + rtx_cost (op1, mode, outer_code, opno, speed));

          return true;
	}
      *total = ix86_multiplication_cost (cost, mode);
      return false;

    case DIV:
    case UDIV:
    case MOD:
    case UMOD:
      *total = ix86_division_cost (cost, mode);
      return false;

    case PLUS:
      if (GET_MODE_CLASS (mode) == MODE_INT
	  && GET_MODE_SIZE (mode) <= UNITS_PER_WORD)
	{
	  if (GET_CODE (XEXP (x, 0)) == PLUS
	      && GET_CODE (XEXP (XEXP (x, 0), 0)) == MULT
	      && CONST_INT_P (XEXP (XEXP (XEXP (x, 0), 0), 1))
	      && CONSTANT_P (XEXP (x, 1)))
	    {
	      HOST_WIDE_INT val = INTVAL (XEXP (XEXP (XEXP (x, 0), 0), 1));
	      if (val == 2 || val == 4 || val == 8)
		{
		  *total = cost->lea;
		  *total += rtx_cost (XEXP (XEXP (x, 0), 1), mode,
				      outer_code, opno, speed);
		  *total += rtx_cost (XEXP (XEXP (XEXP (x, 0), 0), 0), mode,
				      outer_code, opno, speed);
		  *total += rtx_cost (XEXP (x, 1), mode,
				      outer_code, opno, speed);
		  return true;
		}
	    }
	  else if (GET_CODE (XEXP (x, 0)) == MULT
		   && CONST_INT_P (XEXP (XEXP (x, 0), 1)))
	    {
	      HOST_WIDE_INT val = INTVAL (XEXP (XEXP (x, 0), 1));
	      if (val == 2 || val == 4 || val == 8)
		{
		  *total = cost->lea;
		  *total += rtx_cost (XEXP (XEXP (x, 0), 0), mode,
				      outer_code, opno, speed);
		  *total += rtx_cost (XEXP (x, 1), mode,
				      outer_code, opno, speed);
		  return true;
		}
	    }
	  else if (GET_CODE (XEXP (x, 0)) == PLUS)
	    {
	      /* Add with carry, ignore the cost of adding a carry flag.  */
	      if (ix86_carry_flag_operator (XEXP (XEXP (x, 0), 0), mode))
		*total = cost->add;
	      else
		{
		  *total = cost->lea;
		  *total += rtx_cost (XEXP (XEXP (x, 0), 0), mode,
				      outer_code, opno, speed);
		}

	      *total += rtx_cost (XEXP (XEXP (x, 0), 1), mode,
				  outer_code, opno, speed);
	      *total += rtx_cost (XEXP (x, 1), mode,
				  outer_code, opno, speed);
	      return true;
	    }
	}
      /* FALLTHRU */

    case MINUS:
      /* Subtract with borrow, ignore the cost of subtracting a carry flag.  */
      if (GET_MODE_CLASS (mode) == MODE_INT
	  && GET_MODE_SIZE (mode) <= UNITS_PER_WORD
	  && GET_CODE (XEXP (x, 0)) == MINUS
	  && ix86_carry_flag_operator (XEXP (XEXP (x, 0), 1), mode))
	{
	  *total = cost->add;
	  *total += rtx_cost (XEXP (XEXP (x, 0), 0), mode,
			      outer_code, opno, speed);
	  *total += rtx_cost (XEXP (x, 1), mode,
			      outer_code, opno, speed);
	  return true;
	}

      if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
	{
	  *total = cost->addss;
	  return false;
	}
      else if (X87_FLOAT_MODE_P (mode))
	{
	  *total = cost->fadd;
	  return false;
	}
      else if (FLOAT_MODE_P (mode))
	{
	  *total = ix86_vec_cost (mode, cost->addss);
	  return false;
	}
      /* FALLTHRU */

    case AND:
    case IOR:
    case XOR:
      if (GET_MODE_CLASS (mode) == MODE_INT
	  && GET_MODE_SIZE (mode) > UNITS_PER_WORD)
	{
	  *total = (cost->add * 2
		    + (rtx_cost (XEXP (x, 0), mode, outer_code, opno, speed)
		       << (GET_MODE (XEXP (x, 0)) != DImode))
		    + (rtx_cost (XEXP (x, 1), mode, outer_code, opno, speed)
	               << (GET_MODE (XEXP (x, 1)) != DImode)));
	  return true;
	}
      /* FALLTHRU */

    case NEG:
      if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
	{
	  *total = cost->sse_op;
	  return false;
	}
      else if (X87_FLOAT_MODE_P (mode))
	{
	  *total = cost->fchs;
	  return false;
	}
      else if (FLOAT_MODE_P (mode))
	{
	  *total = ix86_vec_cost (mode, cost->sse_op);
	  return false;
	}
      /* FALLTHRU */

    case NOT:
      if (GET_MODE_CLASS (mode) == MODE_VECTOR_INT)
	*total = ix86_vec_cost (mode, cost->sse_op);
      else if (GET_MODE_SIZE (mode) > UNITS_PER_WORD)
	*total = cost->add * 2;
      else
	*total = cost->add;
      return false;

    case COMPARE:
      if (GET_CODE (XEXP (x, 0)) == ZERO_EXTRACT
	  && XEXP (XEXP (x, 0), 1) == const1_rtx
	  && CONST_INT_P (XEXP (XEXP (x, 0), 2))
	  && XEXP (x, 1) == const0_rtx)
	{
	  /* This kind of construct is implemented using test[bwl].
	     Treat it as if we had an AND.  */
	  mode = GET_MODE (XEXP (XEXP (x, 0), 0));
	  *total = (cost->add
		    + rtx_cost (XEXP (XEXP (x, 0), 0), mode, outer_code,
				opno, speed)
		    + rtx_cost (const1_rtx, mode, outer_code, opno, speed));
	  return true;
	}

      /* The embedded comparison operand is completely free.  */
      if (!general_operand (XEXP (x, 0), GET_MODE (XEXP (x, 0)))
	  && XEXP (x, 1) == const0_rtx)
	*total = 0;

      return false;

    case FLOAT_EXTEND:
      if (!(SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH))
	*total = 0;
      else
        *total = ix86_vec_cost (mode, cost->addss);
      return false;

    case FLOAT_TRUNCATE:
      if (!(SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH))
	*total = cost->fadd;
      else
        *total = ix86_vec_cost (mode, cost->addss);
      return false;

    case ABS:
      /* SSE requires memory load for the constant operand. It may make
	 sense to account for this.  Of course the constant operand may or
	 may not be reused. */
      if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
	*total = cost->sse_op;
      else if (X87_FLOAT_MODE_P (mode))
	*total = cost->fabs;
      else if (FLOAT_MODE_P (mode))
	*total = ix86_vec_cost (mode, cost->sse_op);
      return false;

    case SQRT:
      if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
	*total = mode == SFmode ? cost->sqrtss : cost->sqrtsd;
      else if (X87_FLOAT_MODE_P (mode))
	*total = cost->fsqrt;
      else if (FLOAT_MODE_P (mode))
	*total = ix86_vec_cost (mode,
				mode == SFmode ? cost->sqrtss : cost->sqrtsd);
      return false;

    case UNSPEC:
      if (XINT (x, 1) == UNSPEC_TP)
	*total = 0;
      return false;

    case VEC_SELECT:
    case VEC_CONCAT:
    case VEC_DUPLICATE:
      /* ??? Assume all of these vector manipulation patterns are
	 recognizable.  In which case they all pretty much have the
	 same cost.  */
     *total = cost->sse_op;
     return true;
    case VEC_MERGE:
      mask = XEXP (x, 2);
      /* This is masked instruction, assume the same cost,
	 as nonmasked variant.  */
      if (TARGET_AVX512F && register_operand (mask, GET_MODE (mask)))
	*total = rtx_cost (XEXP (x, 0), mode, outer_code, opno, speed);
      else
	*total = cost->sse_op;
      return true;

    default:
      return false;
    }
}

#if TARGET_MACHO

static int current_machopic_label_num;

/* Given a symbol name and its associated stub, write out the
   definition of the stub.  */

void
machopic_output_stub (FILE *file, const char *symb, const char *stub)
{
  unsigned int length;
  char *binder_name, *symbol_name, lazy_ptr_name[32];
  int label = ++current_machopic_label_num;

  /* For 64-bit we shouldn't get here.  */
  gcc_assert (!TARGET_64BIT);

  /* Lose our funky encoding stuff so it doesn't contaminate the stub.  */
  symb = targetm.strip_name_encoding (symb);

  length = strlen (stub);
  binder_name = XALLOCAVEC (char, length + 32);
  GEN_BINDER_NAME_FOR_STUB (binder_name, stub, length);

  length = strlen (symb);
  symbol_name = XALLOCAVEC (char, length + 32);
  GEN_SYMBOL_NAME_FOR_SYMBOL (symbol_name, symb, length);

  sprintf (lazy_ptr_name, "L%d$lz", label);

  if (MACHOPIC_ATT_STUB)
    switch_to_section (darwin_sections[machopic_picsymbol_stub3_section]);
  else if (MACHOPIC_PURE)
    switch_to_section (darwin_sections[machopic_picsymbol_stub2_section]);
  else
    switch_to_section (darwin_sections[machopic_symbol_stub_section]);

  fprintf (file, "%s:\n", stub);
  fprintf (file, "\t.indirect_symbol %s\n", symbol_name);

  if (MACHOPIC_ATT_STUB)
    {
      fprintf (file, "\thlt ; hlt ; hlt ; hlt ; hlt\n");
    }
  else if (MACHOPIC_PURE)
    {
      /* PIC stub.  */
      /* 25-byte PIC stub using "CALL get_pc_thunk".  */
      rtx tmp = gen_rtx_REG (SImode, 2 /* ECX */);
      output_set_got (tmp, NULL_RTX);	/* "CALL ___<cpu>.get_pc_thunk.cx".  */
      fprintf (file, "LPC$%d:\tmovl\t%s-LPC$%d(%%ecx),%%ecx\n",
	       label, lazy_ptr_name, label);
      fprintf (file, "\tjmp\t*%%ecx\n");
    }
  else
    fprintf (file, "\tjmp\t*%s\n", lazy_ptr_name);

  /* The AT&T-style ("self-modifying") stub is not lazily bound, thus
     it needs no stub-binding-helper.  */
  if (MACHOPIC_ATT_STUB)
    return;

  fprintf (file, "%s:\n", binder_name);

  if (MACHOPIC_PURE)
    {
      fprintf (file, "\tlea\t%s-%s(%%ecx),%%ecx\n", lazy_ptr_name, binder_name);
      fprintf (file, "\tpushl\t%%ecx\n");
    }
  else
    fprintf (file, "\tpushl\t$%s\n", lazy_ptr_name);

  fputs ("\tjmp\tdyld_stub_binding_helper\n", file);

  /* N.B. Keep the correspondence of these
     'symbol_ptr/symbol_ptr2/symbol_ptr3' sections consistent with the
     old-pic/new-pic/non-pic stubs; altering this will break
     compatibility with existing dylibs.  */
  if (MACHOPIC_PURE)
    {
      /* 25-byte PIC stub using "CALL get_pc_thunk".  */
      switch_to_section (darwin_sections[machopic_lazy_symbol_ptr2_section]);
    }
  else
    /* 16-byte -mdynamic-no-pic stub.  */
    switch_to_section(darwin_sections[machopic_lazy_symbol_ptr3_section]);

  fprintf (file, "%s:\n", lazy_ptr_name);
  fprintf (file, "\t.indirect_symbol %s\n", symbol_name);
  fprintf (file, ASM_LONG "%s\n", binder_name);
}
#endif /* TARGET_MACHO */

/* Order the registers for register allocator.  */

void
x86_order_regs_for_local_alloc (void)
{
   int pos = 0;
   int i;

   /* First allocate the local general purpose registers.  */
   for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
     if (GENERAL_REGNO_P (i) && call_used_regs[i])
	reg_alloc_order [pos++] = i;

   /* Global general purpose registers.  */
   for (i = 0; i < FIRST_PSEUDO_REGISTER; i++)
     if (GENERAL_REGNO_P (i) && !call_used_regs[i])
	reg_alloc_order [pos++] = i;

   /* x87 registers come first in case we are doing FP math
      using them.  */
   if (!TARGET_SSE_MATH)
     for (i = FIRST_STACK_REG; i <= LAST_STACK_REG; i++)
       reg_alloc_order [pos++] = i;

   /* SSE registers.  */
   for (i = FIRST_SSE_REG; i <= LAST_SSE_REG; i++)
     reg_alloc_order [pos++] = i;
   for (i = FIRST_REX_SSE_REG; i <= LAST_REX_SSE_REG; i++)
     reg_alloc_order [pos++] = i;

   /* Extended REX SSE registers.  */
   for (i = FIRST_EXT_REX_SSE_REG; i <= LAST_EXT_REX_SSE_REG; i++)
     reg_alloc_order [pos++] = i;

   /* Mask register.  */
   for (i = FIRST_MASK_REG; i <= LAST_MASK_REG; i++)
     reg_alloc_order [pos++] = i;

   /* x87 registers.  */
   if (TARGET_SSE_MATH)
     for (i = FIRST_STACK_REG; i <= LAST_STACK_REG; i++)
       reg_alloc_order [pos++] = i;

   for (i = FIRST_MMX_REG; i <= LAST_MMX_REG; i++)
     reg_alloc_order [pos++] = i;

   /* Initialize the rest of array as we do not allocate some registers
      at all.  */
   while (pos < FIRST_PSEUDO_REGISTER)
     reg_alloc_order [pos++] = 0;
}

/* Handle a "callee_pop_aggregate_return" attribute; arguments as
   in struct attribute_spec handler.  */
static tree
ix86_handle_callee_pop_aggregate_return (tree *node, tree name, tree args, int,
					 bool *no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_TYPE
      && TREE_CODE (*node) != METHOD_TYPE
      && TREE_CODE (*node) != FIELD_DECL
      && TREE_CODE (*node) != TYPE_DECL)
    {
      warning (OPT_Wattributes, "%qE attribute only applies to functions",
	       name);
      *no_add_attrs = true;
      return NULL_TREE;
    }
  if (TARGET_64BIT)
    {
      warning (OPT_Wattributes, "%qE attribute only available for 32-bit",
	       name);
      *no_add_attrs = true;
      return NULL_TREE;
    }
  if (is_attribute_p ("callee_pop_aggregate_return", name))
    {
      tree cst;

      cst = TREE_VALUE (args);
      if (TREE_CODE (cst) != INTEGER_CST)
	{
	  warning (OPT_Wattributes,
		   "%qE attribute requires an integer constant argument",
		   name);
	  *no_add_attrs = true;
	}
      else if (compare_tree_int (cst, 0) != 0
	       && compare_tree_int (cst, 1) != 0)
	{
	  warning (OPT_Wattributes,
		   "argument to %qE attribute is neither zero, nor one",
		   name);
	  *no_add_attrs = true;
	}

      return NULL_TREE;
    }

  return NULL_TREE;
}

/* Handle a "ms_abi" or "sysv" attribute; arguments as in
   struct attribute_spec.handler.  */
static tree
ix86_handle_abi_attribute (tree *node, tree name, tree, int,
			   bool *no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_TYPE
      && TREE_CODE (*node) != METHOD_TYPE
      && TREE_CODE (*node) != FIELD_DECL
      && TREE_CODE (*node) != TYPE_DECL)
    {
      warning (OPT_Wattributes, "%qE attribute only applies to functions",
	       name);
      *no_add_attrs = true;
      return NULL_TREE;
    }

  /* Can combine regparm with all attributes but fastcall.  */
  if (is_attribute_p ("ms_abi", name))
    {
      if (lookup_attribute ("sysv_abi", TYPE_ATTRIBUTES (*node)))
        {
	  error ("ms_abi and sysv_abi attributes are not compatible");
	}

      return NULL_TREE;
    }
  else if (is_attribute_p ("sysv_abi", name))
    {
      if (lookup_attribute ("ms_abi", TYPE_ATTRIBUTES (*node)))
        {
	  error ("ms_abi and sysv_abi attributes are not compatible");
	}

      return NULL_TREE;
    }

  return NULL_TREE;
}

/* Handle a "ms_struct" or "gcc_struct" attribute; arguments as in
   struct attribute_spec.handler.  */
static tree
ix86_handle_struct_attribute (tree *node, tree name, tree, int,
			      bool *no_add_attrs)
{
  tree *type = NULL;
  if (DECL_P (*node))
    {
      if (TREE_CODE (*node) == TYPE_DECL)
	type = &TREE_TYPE (*node);
    }
  else
    type = node;

  if (!(type && RECORD_OR_UNION_TYPE_P (*type)))
    {
      warning (OPT_Wattributes, "%qE attribute ignored",
	       name);
      *no_add_attrs = true;
    }

  else if ((is_attribute_p ("ms_struct", name)
	    && lookup_attribute ("gcc_struct", TYPE_ATTRIBUTES (*type)))
	   || ((is_attribute_p ("gcc_struct", name)
		&& lookup_attribute ("ms_struct", TYPE_ATTRIBUTES (*type)))))
    {
      warning (OPT_Wattributes, "%qE incompatible attribute ignored",
               name);
      *no_add_attrs = true;
    }

  return NULL_TREE;
}

static tree
ix86_handle_fndecl_attribute (tree *node, tree name, tree args, int,
			      bool *no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_DECL)
    {
      warning (OPT_Wattributes, "%qE attribute only applies to functions",
               name);
      *no_add_attrs = true;
    }

  if (is_attribute_p ("indirect_branch", name))
    {
      tree cst = TREE_VALUE (args);
      if (TREE_CODE (cst) != STRING_CST)
	{
	  warning (OPT_Wattributes,
		   "%qE attribute requires a string constant argument",
		   name);
	  *no_add_attrs = true;
	}
      else if (strcmp (TREE_STRING_POINTER (cst), "keep") != 0
	       && strcmp (TREE_STRING_POINTER (cst), "thunk") != 0
	       && strcmp (TREE_STRING_POINTER (cst), "thunk-inline") != 0
	       && strcmp (TREE_STRING_POINTER (cst), "thunk-extern") != 0)
	{
	  warning (OPT_Wattributes,
		   "argument to %qE attribute is not "
		   "(keep|thunk|thunk-inline|thunk-extern)", name);
	  *no_add_attrs = true;
	}
    }

  if (is_attribute_p ("function_return", name))
    {
      tree cst = TREE_VALUE (args);
      if (TREE_CODE (cst) != STRING_CST)
	{
	  warning (OPT_Wattributes,
		   "%qE attribute requires a string constant argument",
		   name);
	  *no_add_attrs = true;
	}
      else if (strcmp (TREE_STRING_POINTER (cst), "keep") != 0
	       && strcmp (TREE_STRING_POINTER (cst), "thunk") != 0
	       && strcmp (TREE_STRING_POINTER (cst), "thunk-inline") != 0
	       && strcmp (TREE_STRING_POINTER (cst), "thunk-extern") != 0)
	{
	  warning (OPT_Wattributes,
		   "argument to %qE attribute is not "
		   "(keep|thunk|thunk-inline|thunk-extern)", name);
	  *no_add_attrs = true;
	}
    }

  return NULL_TREE;
}

static tree
ix86_handle_no_caller_saved_registers_attribute (tree *, tree, tree,
						 int, bool *)
{
  return NULL_TREE;
}

static tree
ix86_handle_interrupt_attribute (tree *node, tree, tree, int, bool *)
{
  /* DECL_RESULT and DECL_ARGUMENTS do not exist there yet,
     but the function type contains args and return type data.  */
  tree func_type = *node;
  tree return_type = TREE_TYPE (func_type);

  int nargs = 0;
  tree current_arg_type = TYPE_ARG_TYPES (func_type);
  while (current_arg_type
	 && ! VOID_TYPE_P (TREE_VALUE (current_arg_type)))
    {
      if (nargs == 0)
	{
	  if (! POINTER_TYPE_P (TREE_VALUE (current_arg_type)))
	    error ("interrupt service routine should have a pointer "
		   "as the first argument");
	}
      else if (nargs == 1)
	{
	  if (TREE_CODE (TREE_VALUE (current_arg_type)) != INTEGER_TYPE
	      || TYPE_MODE (TREE_VALUE (current_arg_type)) != word_mode)
	    error ("interrupt service routine should have unsigned %s"
		   "int as the second argument",
		   TARGET_64BIT
		   ? (TARGET_X32 ? "long long " : "long ")
		   : "");
	}
      nargs++;
      current_arg_type = TREE_CHAIN (current_arg_type);
    }
  if (!nargs || nargs > 2)
    error ("interrupt service routine can only have a pointer argument "
	   "and an optional integer argument");
  if (! VOID_TYPE_P (return_type))
    error ("interrupt service routine can't have non-void return value");

  return NULL_TREE;
}

static bool
ix86_ms_bitfield_layout_p (const_tree record_type)
{
  return ((TARGET_MS_BITFIELD_LAYOUT
	   && !lookup_attribute ("gcc_struct", TYPE_ATTRIBUTES (record_type)))
          || lookup_attribute ("ms_struct", TYPE_ATTRIBUTES (record_type)));
}

/* Returns an expression indicating where the this parameter is
   located on entry to the FUNCTION.  */

static rtx
x86_this_parameter (tree function)
{
  tree type = TREE_TYPE (function);
  bool aggr = aggregate_value_p (TREE_TYPE (type), type) != 0;
  int nregs;

  if (TARGET_64BIT)
    {
      const int *parm_regs;

      if (ix86_function_type_abi (type) == MS_ABI)
        parm_regs = x86_64_ms_abi_int_parameter_registers;
      else
        parm_regs = x86_64_int_parameter_registers;
      return gen_rtx_REG (Pmode, parm_regs[aggr]);
    }

  nregs = ix86_function_regparm (type, function);

  if (nregs > 0 && !stdarg_p (type))
    {
      int regno;
      unsigned int ccvt = ix86_get_callcvt (type);

      if ((ccvt & IX86_CALLCVT_FASTCALL) != 0)
	regno = aggr ? DX_REG : CX_REG;
      else if ((ccvt & IX86_CALLCVT_THISCALL) != 0)
        {
	  regno = CX_REG;
	  if (aggr)
	    return gen_rtx_MEM (SImode,
				plus_constant (Pmode, stack_pointer_rtx, 4));
	}
      else
        {
	  regno = AX_REG;
	  if (aggr)
	    {
	      regno = DX_REG;
	      if (nregs == 1)
		return gen_rtx_MEM (SImode,
				    plus_constant (Pmode,
						   stack_pointer_rtx, 4));
	    }
	}
      return gen_rtx_REG (SImode, regno);
    }

  return gen_rtx_MEM (SImode, plus_constant (Pmode, stack_pointer_rtx,
					     aggr ? 8 : 4));
}

/* Determine whether x86_output_mi_thunk can succeed.  */

static bool
x86_can_output_mi_thunk (const_tree, HOST_WIDE_INT, HOST_WIDE_INT vcall_offset,
			 const_tree function)
{
  /* 64-bit can handle anything.  */
  if (TARGET_64BIT)
    return true;

  /* For 32-bit, everything's fine if we have one free register.  */
  if (ix86_function_regparm (TREE_TYPE (function), function) < 3)
    return true;

  /* Need a free register for vcall_offset.  */
  if (vcall_offset)
    return false;

  /* Need a free register for GOT references.  */
  if (flag_pic && !targetm.binds_local_p (function))
    return false;

  /* Otherwise ok.  */
  return true;
}

/* Output the assembler code for a thunk function.  THUNK_DECL is the
   declaration for the thunk function itself, FUNCTION is the decl for
   the target function.  DELTA is an immediate constant offset to be
   added to THIS.  If VCALL_OFFSET is nonzero, the word at
   *(*this + vcall_offset) should be added to THIS.  */

static void
x86_output_mi_thunk (FILE *file, tree, HOST_WIDE_INT delta,
		     HOST_WIDE_INT vcall_offset, tree function)
{
  rtx this_param = x86_this_parameter (function);
  rtx this_reg, tmp, fnaddr;
  unsigned int tmp_regno;
  rtx_insn *insn;

  if (TARGET_64BIT)
    tmp_regno = R10_REG;
  else
    {
      unsigned int ccvt = ix86_get_callcvt (TREE_TYPE (function));
      if ((ccvt & IX86_CALLCVT_FASTCALL) != 0)
	tmp_regno = AX_REG;
      else if ((ccvt & IX86_CALLCVT_THISCALL) != 0)
	tmp_regno = DX_REG;
      else
	tmp_regno = CX_REG;
    }

  emit_note (NOTE_INSN_PROLOGUE_END);

  /* CET is enabled, insert EB instruction.  */
  if ((flag_cf_protection & CF_BRANCH))
    emit_insn (gen_nop_endbr ());

  /* If VCALL_OFFSET, we'll need THIS in a register.  Might as well
     pull it in now and let DELTA benefit.  */
  if (REG_P (this_param))
    this_reg = this_param;
  else if (vcall_offset)
    {
      /* Put the this parameter into %eax.  */
      this_reg = gen_rtx_REG (Pmode, AX_REG);
      emit_move_insn (this_reg, this_param);
    }
  else
    this_reg = NULL_RTX;

  /* Adjust the this parameter by a fixed constant.  */
  if (delta)
    {
      rtx delta_rtx = GEN_INT (delta);
      rtx delta_dst = this_reg ? this_reg : this_param;

      if (TARGET_64BIT)
	{
	  if (!x86_64_general_operand (delta_rtx, Pmode))
	    {
	      tmp = gen_rtx_REG (Pmode, tmp_regno);
	      emit_move_insn (tmp, delta_rtx);
	      delta_rtx = tmp;
	    }
	}

      ix86_emit_binop (PLUS, Pmode, delta_dst, delta_rtx);
    }

  /* Adjust the this parameter by a value stored in the vtable.  */
  if (vcall_offset)
    {
      rtx vcall_addr, vcall_mem, this_mem;

      tmp = gen_rtx_REG (Pmode, tmp_regno);

      this_mem = gen_rtx_MEM (ptr_mode, this_reg);
      if (Pmode != ptr_mode)
	this_mem = gen_rtx_ZERO_EXTEND (Pmode, this_mem);
      emit_move_insn (tmp, this_mem);

      /* Adjust the this parameter.  */
      vcall_addr = plus_constant (Pmode, tmp, vcall_offset);
      if (TARGET_64BIT
	  && !ix86_legitimate_address_p (ptr_mode, vcall_addr, true))
	{
	  rtx tmp2 = gen_rtx_REG (Pmode, R11_REG);
	  emit_move_insn (tmp2, GEN_INT (vcall_offset));
	  vcall_addr = gen_rtx_PLUS (Pmode, tmp, tmp2);
	}

      vcall_mem = gen_rtx_MEM (ptr_mode, vcall_addr);
      if (Pmode != ptr_mode)
	emit_insn (gen_addsi_1_zext (this_reg,
				     gen_rtx_REG (ptr_mode,
						  REGNO (this_reg)),
				     vcall_mem));
      else
	ix86_emit_binop (PLUS, Pmode, this_reg, vcall_mem);
    }

  /* If necessary, drop THIS back to its stack slot.  */
  if (this_reg && this_reg != this_param)
    emit_move_insn (this_param, this_reg);

  fnaddr = XEXP (DECL_RTL (function), 0);
  if (TARGET_64BIT)
    {
      if (!flag_pic || targetm.binds_local_p (function)
	  || TARGET_PECOFF)
	;
      else
	{
	  tmp = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, fnaddr), UNSPEC_GOTPCREL);
	  tmp = gen_rtx_CONST (Pmode, tmp);
	  fnaddr = gen_const_mem (Pmode, tmp);
	}
    }
  else
    {
      if (!flag_pic || targetm.binds_local_p (function))
	;
#if TARGET_MACHO
      else if (TARGET_MACHO)
	{
	  fnaddr = machopic_indirect_call_target (DECL_RTL (function));
	  fnaddr = XEXP (fnaddr, 0);
	}
#endif /* TARGET_MACHO */
      else
	{
	  tmp = gen_rtx_REG (Pmode, CX_REG);
	  output_set_got (tmp, NULL_RTX);

	  fnaddr = gen_rtx_UNSPEC (Pmode, gen_rtvec (1, fnaddr), UNSPEC_GOT);
	  fnaddr = gen_rtx_CONST (Pmode, fnaddr);
	  fnaddr = gen_rtx_PLUS (Pmode, tmp, fnaddr);
	  fnaddr = gen_const_mem (Pmode, fnaddr);
	}
    }

  /* Our sibling call patterns do not allow memories, because we have no
     predicate that can distinguish between frame and non-frame memory.
     For our purposes here, we can get away with (ab)using a jump pattern,
     because we're going to do no optimization.  */
  if (MEM_P (fnaddr))
    {
      if (sibcall_insn_operand (fnaddr, word_mode))
	{
	  fnaddr = XEXP (DECL_RTL (function), 0);
	  tmp = gen_rtx_MEM (QImode, fnaddr);
	  tmp = gen_rtx_CALL (VOIDmode, tmp, const0_rtx);
	  tmp = emit_call_insn (tmp);
	  SIBLING_CALL_P (tmp) = 1;
	}
      else
	emit_jump_insn (gen_indirect_jump (fnaddr));
    }
  else
    {
      if (ix86_cmodel == CM_LARGE_PIC && SYMBOLIC_CONST (fnaddr))
	{
	  // CM_LARGE_PIC always uses pseudo PIC register which is
	  // uninitialized.  Since FUNCTION is local and calling it
	  // doesn't go through PLT, we use scratch register %r11 as
	  // PIC register and initialize it here.
	  pic_offset_table_rtx = gen_rtx_REG (Pmode, R11_REG);
	  ix86_init_large_pic_reg (tmp_regno);
	  fnaddr = legitimize_pic_address (fnaddr,
					   gen_rtx_REG (Pmode, tmp_regno));
	}

      if (!sibcall_insn_operand (fnaddr, word_mode))
	{
	  tmp = gen_rtx_REG (word_mode, tmp_regno);
	  if (GET_MODE (fnaddr) != word_mode)
	    fnaddr = gen_rtx_ZERO_EXTEND (word_mode, fnaddr);
	  emit_move_insn (tmp, fnaddr);
	  fnaddr = tmp;
	}

      tmp = gen_rtx_MEM (QImode, fnaddr);
      tmp = gen_rtx_CALL (VOIDmode, tmp, const0_rtx);
      tmp = emit_call_insn (tmp);
      SIBLING_CALL_P (tmp) = 1;
    }
  emit_barrier ();

  /* Emit just enough of rest_of_compilation to get the insns emitted.
     Note that use_thunk calls assemble_start_function et al.  */
  insn = get_insns ();
  shorten_branches (insn);
  final_start_function (insn, file, 1);
  final (insn, file, 1);
  final_end_function ();
}

static void
x86_file_start (void)
{
  default_file_start ();
  if (TARGET_16BIT)
    fputs ("\t.code16gcc\n", asm_out_file);
#if TARGET_MACHO
  darwin_file_start ();
#endif
  if (X86_FILE_START_VERSION_DIRECTIVE)
    fputs ("\t.version\t\"01.01\"\n", asm_out_file);
  if (X86_FILE_START_FLTUSED)
    fputs ("\t.global\t__fltused\n", asm_out_file);
  if (ix86_asm_dialect == ASM_INTEL)
    fputs ("\t.intel_syntax noprefix\n", asm_out_file);
}

int
x86_field_alignment (tree type, int computed)
{
  machine_mode mode;

  if (TARGET_64BIT || TARGET_ALIGN_DOUBLE)
    return computed;
  if (TARGET_IAMCU)
    return iamcu_alignment (type, computed);
  mode = TYPE_MODE (strip_array_types (type));
  if (mode == DFmode || mode == DCmode
      || GET_MODE_CLASS (mode) == MODE_INT
      || GET_MODE_CLASS (mode) == MODE_COMPLEX_INT)
    return MIN (32, computed);
  return computed;
}

/* Print call to TARGET to FILE.  */

static void
x86_print_call_or_nop (FILE *file, const char *target)
{
  if (flag_nop_mcount || !strcmp (target, "nop"))
    /* 5 byte nop: nopl 0(%[re]ax,%[re]ax,1) */
    fprintf (file, "1:" ASM_BYTE "0x0f, 0x1f, 0x44, 0x00, 0x00\n");
  else
    fprintf (file, "1:\tcall\t%s\n", target);
}

static bool
current_fentry_name (const char **name)
{
  tree attr = lookup_attribute ("fentry_name",
				DECL_ATTRIBUTES (current_function_decl));
  if (!attr)
    return false;
  *name = TREE_STRING_POINTER (TREE_VALUE (TREE_VALUE (attr)));
  return true;
}

static bool
current_fentry_section (const char **name)
{
  tree attr = lookup_attribute ("fentry_section",
				DECL_ATTRIBUTES (current_function_decl));
  if (!attr)
    return false;
  *name = TREE_STRING_POINTER (TREE_VALUE (TREE_VALUE (attr)));
  return true;
}

/* Output assembler code to FILE to increment profiler label # LABELNO
   for profiling a function entry.  */
void
x86_function_profiler (FILE *file, int labelno ATTRIBUTE_UNUSED)
{
  if (cfun->machine->endbr_queued_at_entrance)
    fprintf (file, "\t%s\n", TARGET_64BIT ? "endbr64" : "endbr32");

  const char *mcount_name = MCOUNT_NAME;

  if (current_fentry_name (&mcount_name))
    ;
  else if (fentry_name)
    mcount_name = fentry_name;
  else if (flag_fentry)
    mcount_name = MCOUNT_NAME_BEFORE_PROLOGUE;

  if (TARGET_64BIT)
    {
#ifndef NO_PROFILE_COUNTERS
      fprintf (file, "\tleaq\t%sP%d(%%rip),%%r11\n", LPREFIX, labelno);
#endif

      if (!TARGET_PECOFF && flag_pic)
	fprintf (file, "1:\tcall\t*%s@GOTPCREL(%%rip)\n", mcount_name);
      else
	x86_print_call_or_nop (file, mcount_name);
    }
  else if (flag_pic)
    {
#ifndef NO_PROFILE_COUNTERS
      fprintf (file, "\tleal\t%sP%d@GOTOFF(%%ebx),%%" PROFILE_COUNT_REGISTER "\n",
	       LPREFIX, labelno);
#endif
      fprintf (file, "1:\tcall\t*%s@GOT(%%ebx)\n", mcount_name);
    }
  else
    {
#ifndef NO_PROFILE_COUNTERS
      fprintf (file, "\tmovl\t$%sP%d,%%" PROFILE_COUNT_REGISTER "\n",
	       LPREFIX, labelno);
#endif
      x86_print_call_or_nop (file, mcount_name);
    }

  if (flag_record_mcount
	|| lookup_attribute ("fentry_section",
                                DECL_ATTRIBUTES (current_function_decl)))
    {
      const char *sname = "__mcount_loc";

      if (current_fentry_section (&sname))
	;
      else if (fentry_section)
	sname = fentry_section;

      fprintf (file, "\t.section %s, \"a\",@progbits\n", sname);
      fprintf (file, "\t.%s 1b\n", TARGET_64BIT ? "quad" : "long");
      fprintf (file, "\t.previous\n");
    }
}

/* We don't have exact information about the insn sizes, but we may assume
   quite safely that we are informed about all 1 byte insns and memory
   address sizes.  This is enough to eliminate unnecessary padding in
   99% of cases.  */

int
ix86_min_insn_size (rtx_insn *insn)
{
  int l = 0, len;

  if (!INSN_P (insn) || !active_insn_p (insn))
    return 0;

  /* Discard alignments we've emit and jump instructions.  */
  if (GET_CODE (PATTERN (insn)) == UNSPEC_VOLATILE
      && XINT (PATTERN (insn), 1) == UNSPECV_ALIGN)
    return 0;

  /* Important case - calls are always 5 bytes.
     It is common to have many calls in the row.  */
  if (CALL_P (insn)
      && symbolic_reference_mentioned_p (PATTERN (insn))
      && !SIBLING_CALL_P (insn))
    return 5;
  len = get_attr_length (insn);
  if (len <= 1)
    return 1;

  /* For normal instructions we rely on get_attr_length being exact,
     with a few exceptions.  */
  if (!JUMP_P (insn))
    {
      enum attr_type type = get_attr_type (insn);

      switch (type)
	{
	case TYPE_MULTI:
	  if (GET_CODE (PATTERN (insn)) == ASM_INPUT
	      || asm_noperands (PATTERN (insn)) >= 0)
	    return 0;
	  break;
	case TYPE_OTHER:
	case TYPE_FCMP:
	  break;
	default:
	  /* Otherwise trust get_attr_length.  */
	  return len;
	}

      l = get_attr_length_address (insn);
      if (l < 4 && symbolic_reference_mentioned_p (PATTERN (insn)))
	l = 4;
    }
  if (l)
    return 1+l;
  else
    return 2;
}

#ifdef ASM_OUTPUT_MAX_SKIP_PAD

/* AMD K8 core mispredicts jumps when there are more than 3 jumps in 16 byte
   window.  */

static void
ix86_avoid_jump_mispredicts (void)
{
  rtx_insn *insn, *start = get_insns ();
  int nbytes = 0, njumps = 0;
  bool isjump = false;

  /* Look for all minimal intervals of instructions containing 4 jumps.
     The intervals are bounded by START and INSN.  NBYTES is the total
     size of instructions in the interval including INSN and not including
     START.  When the NBYTES is smaller than 16 bytes, it is possible
     that the end of START and INSN ends up in the same 16byte page.

     The smallest offset in the page INSN can start is the case where START
     ends on the offset 0.  Offset of INSN is then NBYTES - sizeof (INSN).
     We add p2align to 16byte window with maxskip 15 - NBYTES + sizeof (INSN).

     Don't consider asm goto as jump, while it can contain a jump, it doesn't
     have to, control transfer to label(s) can be performed through other
     means, and also we estimate minimum length of all asm stmts as 0.  */
  for (insn = start; insn; insn = NEXT_INSN (insn))
    {
      int min_size;

      if (LABEL_P (insn))
	{
	  align_flags alignment = label_to_alignment (insn);
	  int align = alignment.levels[0].log;
	  int max_skip = alignment.levels[0].maxskip;

	  if (max_skip > 15)
	    max_skip = 15;
	  /* If align > 3, only up to 16 - max_skip - 1 bytes can be
	     already in the current 16 byte page, because otherwise
	     ASM_OUTPUT_MAX_SKIP_ALIGN could skip max_skip or fewer
	     bytes to reach 16 byte boundary.  */
	  if (align <= 0
	      || (align <= 3 && max_skip != (1 << align) - 1))
	    max_skip = 0;
	  if (dump_file)
	    fprintf (dump_file, "Label %i with max_skip %i\n",
		     INSN_UID (insn), max_skip);
	  if (max_skip)
	    {
	      while (nbytes + max_skip >= 16)
		{
		  start = NEXT_INSN (start);
		  if ((JUMP_P (start) && asm_noperands (PATTERN (start)) < 0)
		      || CALL_P (start))
		    njumps--, isjump = true;
		  else
		    isjump = false;
		  nbytes -= ix86_min_insn_size (start);
		}
	    }
	  continue;
	}

      min_size = ix86_min_insn_size (insn);
      nbytes += min_size;
      if (dump_file)
	fprintf (dump_file, "Insn %i estimated to %i bytes\n",
		 INSN_UID (insn), min_size);
      if ((JUMP_P (insn) && asm_noperands (PATTERN (insn)) < 0)
	  || CALL_P (insn))
	njumps++;
      else
	continue;

      while (njumps > 3)
	{
	  start = NEXT_INSN (start);
	  if ((JUMP_P (start) && asm_noperands (PATTERN (start)) < 0)
	      || CALL_P (start))
	    njumps--, isjump = true;
	  else
	    isjump = false;
	  nbytes -= ix86_min_insn_size (start);
	}
      gcc_assert (njumps >= 0);
      if (dump_file)
        fprintf (dump_file, "Interval %i to %i has %i bytes\n",
		 INSN_UID (start), INSN_UID (insn), nbytes);

      if (njumps == 3 && isjump && nbytes < 16)
	{
	  int padsize = 15 - nbytes + ix86_min_insn_size (insn);

	  if (dump_file)
	    fprintf (dump_file, "Padding insn %i by %i bytes!\n",
		     INSN_UID (insn), padsize);
          emit_insn_before (gen_pad (GEN_INT (padsize)), insn);
	}
    }
}
#endif

/* AMD Athlon works faster
   when RET is not destination of conditional jump or directly preceded
   by other jump instruction.  We avoid the penalty by inserting NOP just
   before the RET instructions in such cases.  */
static void
ix86_pad_returns (void)
{
  edge e;
  edge_iterator ei;

  FOR_EACH_EDGE (e, ei, EXIT_BLOCK_PTR_FOR_FN (cfun)->preds)
    {
      basic_block bb = e->src;
      rtx_insn *ret = BB_END (bb);
      rtx_insn *prev;
      bool replace = false;

      if (!JUMP_P (ret) || !ANY_RETURN_P (PATTERN (ret))
	  || optimize_bb_for_size_p (bb))
	continue;
      for (prev = PREV_INSN (ret); prev; prev = PREV_INSN (prev))
	if (active_insn_p (prev) || LABEL_P (prev))
	  break;
      if (prev && LABEL_P (prev))
	{
	  edge e;
	  edge_iterator ei;

	  FOR_EACH_EDGE (e, ei, bb->preds)
	    if (EDGE_FREQUENCY (e) && e->src->index >= 0
		&& !(e->flags & EDGE_FALLTHRU))
	      {
		replace = true;
		break;
	      }
	}
      if (!replace)
	{
	  prev = prev_active_insn (ret);
	  if (prev
	      && ((JUMP_P (prev) && any_condjump_p (prev))
		  || CALL_P (prev)))
	    replace = true;
	  /* Empty functions get branch mispredict even when
	     the jump destination is not visible to us.  */
	  if (!prev && !optimize_function_for_size_p (cfun))
	    replace = true;
	}
      if (replace)
	{
	  emit_jump_insn_before (gen_simple_return_internal_long (), ret);
	  delete_insn (ret);
	}
    }
}

/* Count the minimum number of instructions in BB.  Return 4 if the
   number of instructions >= 4.  */

static int
ix86_count_insn_bb (basic_block bb)
{
  rtx_insn *insn;
  int insn_count = 0;

  /* Count number of instructions in this block.  Return 4 if the number
     of instructions >= 4.  */
  FOR_BB_INSNS (bb, insn)
    {
      /* Only happen in exit blocks.  */
      if (JUMP_P (insn)
	  && ANY_RETURN_P (PATTERN (insn)))
	break;

      if (NONDEBUG_INSN_P (insn)
	  && GET_CODE (PATTERN (insn)) != USE
	  && GET_CODE (PATTERN (insn)) != CLOBBER)
	{
	  insn_count++;
	  if (insn_count >= 4)
	    return insn_count;
	}
    }

  return insn_count;
}


/* Count the minimum number of instructions in code path in BB.
   Return 4 if the number of instructions >= 4.  */

static int
ix86_count_insn (basic_block bb)
{
  edge e;
  edge_iterator ei;
  int min_prev_count;

  /* Only bother counting instructions along paths with no
     more than 2 basic blocks between entry and exit.  Given
     that BB has an edge to exit, determine if a predecessor
     of BB has an edge from entry.  If so, compute the number
     of instructions in the predecessor block.  If there
     happen to be multiple such blocks, compute the minimum.  */
  min_prev_count = 4;
  FOR_EACH_EDGE (e, ei, bb->preds)
    {
      edge prev_e;
      edge_iterator prev_ei;

      if (e->src == ENTRY_BLOCK_PTR_FOR_FN (cfun))
	{
	  min_prev_count = 0;
	  break;
	}
      FOR_EACH_EDGE (prev_e, prev_ei, e->src->preds)
	{
	  if (prev_e->src == ENTRY_BLOCK_PTR_FOR_FN (cfun))
	    {
	      int count = ix86_count_insn_bb (e->src);
	      if (count < min_prev_count)
		min_prev_count = count;
	      break;
	    }
	}
    }

  if (min_prev_count < 4)
    min_prev_count += ix86_count_insn_bb (bb);

  return min_prev_count;
}

/* Pad short function to 4 instructions.   */

static void
ix86_pad_short_function (void)
{
  edge e;
  edge_iterator ei;

  FOR_EACH_EDGE (e, ei, EXIT_BLOCK_PTR_FOR_FN (cfun)->preds)
    {
      rtx_insn *ret = BB_END (e->src);
      if (JUMP_P (ret) && ANY_RETURN_P (PATTERN (ret)))
	{
	  int insn_count = ix86_count_insn (e->src);

	  /* Pad short function.  */
	  if (insn_count < 4)
	    {
	      rtx_insn *insn = ret;

	      /* Find epilogue.  */
	      while (insn
		     && (!NOTE_P (insn)
			 || NOTE_KIND (insn) != NOTE_INSN_EPILOGUE_BEG))
		insn = PREV_INSN (insn);

	      if (!insn)
		insn = ret;

	      /* Two NOPs count as one instruction.  */
	      insn_count = 2 * (4 - insn_count);
	      emit_insn_before (gen_nops (GEN_INT (insn_count)), insn);
	    }
	}
    }
}

/* Fix up a Windows system unwinder issue.  If an EH region falls through into
   the epilogue, the Windows system unwinder will apply epilogue logic and
   produce incorrect offsets.  This can be avoided by adding a nop between
   the last insn that can throw and the first insn of the epilogue.  */

static void
ix86_seh_fixup_eh_fallthru (void)
{
  edge e;
  edge_iterator ei;

  FOR_EACH_EDGE (e, ei, EXIT_BLOCK_PTR_FOR_FN (cfun)->preds)
    {
      rtx_insn *insn, *next;

      /* Find the beginning of the epilogue.  */
      for (insn = BB_END (e->src); insn != NULL; insn = PREV_INSN (insn))
	if (NOTE_P (insn) && NOTE_KIND (insn) == NOTE_INSN_EPILOGUE_BEG)
	  break;
      if (insn == NULL)
	continue;

      /* We only care about preceding insns that can throw.  */
      insn = prev_active_insn (insn);
      if (insn == NULL || !can_throw_internal (insn))
	continue;

      /* Do not separate calls from their debug information.  */
      for (next = NEXT_INSN (insn); next != NULL; next = NEXT_INSN (next))
	if (NOTE_P (next) && NOTE_KIND (next) == NOTE_INSN_VAR_LOCATION)
	  insn = next;
	else
	  break;

      emit_insn_after (gen_nops (const1_rtx), insn);
    }
}

/* Implement machine specific optimizations.  We implement padding of returns
   for K8 CPUs and pass to avoid 4 jumps in the single 16 byte window.  */
static void
ix86_reorg (void)
{
  /* We are freeing block_for_insn in the toplev to keep compatibility
     with old MDEP_REORGS that are not CFG based.  Recompute it now.  */
  compute_bb_for_insn ();

  if (TARGET_SEH && current_function_has_exception_handlers ())
    ix86_seh_fixup_eh_fallthru ();

  if (optimize && optimize_function_for_speed_p (cfun))
    {
      if (TARGET_PAD_SHORT_FUNCTION)
	ix86_pad_short_function ();
      else if (TARGET_PAD_RETURNS)
	ix86_pad_returns ();
#ifdef ASM_OUTPUT_MAX_SKIP_PAD
      if (TARGET_FOUR_JUMP_LIMIT)
	ix86_avoid_jump_mispredicts ();
#endif
    }
}

/* Return nonzero when QImode register that must be represented via REX prefix
   is used.  */
bool
x86_extended_QIreg_mentioned_p (rtx_insn *insn)
{
  int i;
  extract_insn_cached (insn);
  for (i = 0; i < recog_data.n_operands; i++)
    if (GENERAL_REG_P (recog_data.operand[i])
	&& !QI_REGNO_P (REGNO (recog_data.operand[i])))
       return true;
  return false;
}

/* Return true when INSN mentions register that must be encoded using REX
   prefix.  */
bool
x86_extended_reg_mentioned_p (rtx insn)
{
  subrtx_iterator::array_type array;
  FOR_EACH_SUBRTX (iter, array, INSN_P (insn) ? PATTERN (insn) : insn, NONCONST)
    {
      const_rtx x = *iter;
      if (REG_P (x)
	  && (REX_INT_REGNO_P (REGNO (x)) || REX_SSE_REGNO_P (REGNO (x))))
	return true;
    }
  return false;
}

/* If profitable, negate (without causing overflow) integer constant
   of mode MODE at location LOC.  Return true in this case.  */
bool
x86_maybe_negate_const_int (rtx *loc, machine_mode mode)
{
  HOST_WIDE_INT val;

  if (!CONST_INT_P (*loc))
    return false;

  switch (mode)
    {
    case E_DImode:
      /* DImode x86_64 constants must fit in 32 bits.  */
      gcc_assert (x86_64_immediate_operand (*loc, mode));

      mode = SImode;
      break;

    case E_SImode:
    case E_HImode:
    case E_QImode:
      break;

    default:
      gcc_unreachable ();
    }

  /* Avoid overflows.  */
  if (mode_signbit_p (mode, *loc))
    return false;

  val = INTVAL (*loc);

  /* Make things pretty and `subl $4,%eax' rather than `addl $-4,%eax'.
     Exceptions: -128 encodes smaller than 128, so swap sign and op.  */
  if ((val < 0 && val != -128)
      || val == 128)
    {
      *loc = GEN_INT (-val);
      return true;
    }

  return false;
}

/* Generate an unsigned DImode/SImode to FP conversion.  This is the same code
   optabs would emit if we didn't have TFmode patterns.  */

void
x86_emit_floatuns (rtx operands[2])
{
  rtx_code_label *neglab, *donelab;
  rtx i0, i1, f0, in, out;
  machine_mode mode, inmode;

  inmode = GET_MODE (operands[1]);
  gcc_assert (inmode == SImode || inmode == DImode);

  out = operands[0];
  in = force_reg (inmode, operands[1]);
  mode = GET_MODE (out);
  neglab = gen_label_rtx ();
  donelab = gen_label_rtx ();
  f0 = gen_reg_rtx (mode);

  emit_cmp_and_jump_insns (in, const0_rtx, LT, const0_rtx, inmode, 0, neglab);

  expand_float (out, in, 0);

  emit_jump_insn (gen_jump (donelab));
  emit_barrier ();

  emit_label (neglab);

  i0 = expand_simple_binop (inmode, LSHIFTRT, in, const1_rtx, NULL,
			    1, OPTAB_DIRECT);
  i1 = expand_simple_binop (inmode, AND, in, const1_rtx, NULL,
			    1, OPTAB_DIRECT);
  i0 = expand_simple_binop (inmode, IOR, i0, i1, i0, 1, OPTAB_DIRECT);

  expand_float (f0, i0, 0);

  emit_insn (gen_rtx_SET (out, gen_rtx_PLUS (mode, f0, f0)));

  emit_label (donelab);
}

static bool canonicalize_perm (struct expand_vec_perm_d *d);
static bool expand_vec_perm_1 (struct expand_vec_perm_d *d);
static bool expand_vec_perm_broadcast_1 (struct expand_vec_perm_d *d);
static bool expand_vec_perm_palignr (struct expand_vec_perm_d *d, bool);

/* Get a vector mode of the same size as the original but with elements
   twice as wide.  This is only guaranteed to apply to integral vectors.  */

static inline machine_mode
get_mode_wider_vector (machine_mode o)
{
  /* ??? Rely on the ordering that genmodes.c gives to vectors.  */
  machine_mode n = GET_MODE_WIDER_MODE (o).require ();
  gcc_assert (GET_MODE_NUNITS (o) == GET_MODE_NUNITS (n) * 2);
  gcc_assert (GET_MODE_SIZE (o) == GET_MODE_SIZE (n));
  return n;
}

/* A subroutine of ix86_expand_vector_init_duplicate.  Tries to
   fill target with val via vec_duplicate.  */

static bool
ix86_vector_duplicate_value (machine_mode mode, rtx target, rtx val)
{
  bool ok;
  rtx_insn *insn;
  rtx dup;

  /* First attempt to recognize VAL as-is.  */
  dup = gen_vec_duplicate (mode, val);
  insn = emit_insn (gen_rtx_SET (target, dup));
  if (recog_memoized (insn) < 0)
    {
      rtx_insn *seq;
      machine_mode innermode = GET_MODE_INNER (mode);
      rtx reg;

      /* If that fails, force VAL into a register.  */

      start_sequence ();
      reg = force_reg (innermode, val);
      if (GET_MODE (reg) != innermode)
	reg = gen_lowpart (innermode, reg);
      SET_SRC (PATTERN (insn)) = gen_vec_duplicate (mode, reg);
      seq = get_insns ();
      end_sequence ();
      if (seq)
	emit_insn_before (seq, insn);

      ok = recog_memoized (insn) >= 0;
      gcc_assert (ok);
    }
  return true;
}

/* A subroutine of ix86_expand_vector_init.  Store into TARGET a vector
   with all elements equal to VAR.  Return true if successful.  */

static bool
ix86_expand_vector_init_duplicate (bool mmx_ok, machine_mode mode,
				   rtx target, rtx val)
{
  bool ok;

  switch (mode)
    {
    case E_V2SImode:
    case E_V2SFmode:
      if (!mmx_ok)
	return false;
      /* FALLTHRU */

    case E_V4DFmode:
    case E_V4DImode:
    case E_V8SFmode:
    case E_V8SImode:
    case E_V2DFmode:
    case E_V2DImode:
    case E_V4SFmode:
    case E_V4SImode:
    case E_V16SImode:
    case E_V8DImode:
    case E_V16SFmode:
    case E_V8DFmode:
      return ix86_vector_duplicate_value (mode, target, val);

    case E_V4HImode:
      if (!mmx_ok)
	return false;
      if (TARGET_SSE || TARGET_3DNOW_A)
	{
	  rtx x;

	  val = gen_lowpart (SImode, val);
	  x = gen_rtx_TRUNCATE (HImode, val);
	  x = gen_rtx_VEC_DUPLICATE (mode, x);
	  emit_insn (gen_rtx_SET (target, x));
	  return true;
	}
      goto widen;

    case E_V8QImode:
      if (!mmx_ok)
	return false;
      goto widen;

    case E_V8HImode:
      if (TARGET_AVX2)
	return ix86_vector_duplicate_value (mode, target, val);

      if (TARGET_SSE2)
	{
	  struct expand_vec_perm_d dperm;
	  rtx tmp1, tmp2;

	permute:
	  memset (&dperm, 0, sizeof (dperm));
	  dperm.target = target;
	  dperm.vmode = mode;
	  dperm.nelt = GET_MODE_NUNITS (mode);
	  dperm.op0 = dperm.op1 = gen_reg_rtx (mode);
	  dperm.one_operand_p = true;

	  /* Extend to SImode using a paradoxical SUBREG.  */
	  tmp1 = gen_reg_rtx (SImode);
	  emit_move_insn (tmp1, gen_lowpart (SImode, val));

	  /* Insert the SImode value as low element of a V4SImode vector. */
	  tmp2 = gen_reg_rtx (V4SImode);
	  emit_insn (gen_vec_setv4si_0 (tmp2, CONST0_RTX (V4SImode), tmp1));
	  emit_move_insn (dperm.op0, gen_lowpart (mode, tmp2));

	  ok = (expand_vec_perm_1 (&dperm)
		|| expand_vec_perm_broadcast_1 (&dperm));
	  gcc_assert (ok);
	  return ok;
	}
      goto widen;

    case E_V16QImode:
      if (TARGET_AVX2)
	return ix86_vector_duplicate_value (mode, target, val);

      if (TARGET_SSE2)
	goto permute;
      goto widen;

    widen:
      /* Replicate the value once into the next wider mode and recurse.  */
      {
	machine_mode smode, wsmode, wvmode;
	rtx x;

	smode = GET_MODE_INNER (mode);
	wvmode = get_mode_wider_vector (mode);
	wsmode = GET_MODE_INNER (wvmode);

	val = convert_modes (wsmode, smode, val, true);
	x = expand_simple_binop (wsmode, ASHIFT, val,
				 GEN_INT (GET_MODE_BITSIZE (smode)),
				 NULL_RTX, 1, OPTAB_LIB_WIDEN);
	val = expand_simple_binop (wsmode, IOR, val, x, x, 1, OPTAB_LIB_WIDEN);

	x = gen_reg_rtx (wvmode);
	ok = ix86_expand_vector_init_duplicate (mmx_ok, wvmode, x, val);
	gcc_assert (ok);
	emit_move_insn (target, gen_lowpart (GET_MODE (target), x));
	return ok;
      }

    case E_V16HImode:
    case E_V32QImode:
      if (TARGET_AVX2)
	return ix86_vector_duplicate_value (mode, target, val);
      else
	{
	  machine_mode hvmode = (mode == V16HImode ? V8HImode : V16QImode);
	  rtx x = gen_reg_rtx (hvmode);

	  ok = ix86_expand_vector_init_duplicate (false, hvmode, x, val);
	  gcc_assert (ok);

	  x = gen_rtx_VEC_CONCAT (mode, x, x);
	  emit_insn (gen_rtx_SET (target, x));
	}
      return true;

    case E_V64QImode:
    case E_V32HImode:
      if (TARGET_AVX512BW)
	return ix86_vector_duplicate_value (mode, target, val);
      else
	{
	  machine_mode hvmode = (mode == V32HImode ? V16HImode : V32QImode);
	  rtx x = gen_reg_rtx (hvmode);

	  ok = ix86_expand_vector_init_duplicate (false, hvmode, x, val);
	  gcc_assert (ok);

	  x = gen_rtx_VEC_CONCAT (mode, x, x);
	  emit_insn (gen_rtx_SET (target, x));
	}
      return true;

    default:
      return false;
    }
}

/* A subroutine of ix86_expand_vector_init.  Store into TARGET a vector
   whose ONE_VAR element is VAR, and other elements are zero.  Return true
   if successful.  */

static bool
ix86_expand_vector_init_one_nonzero (bool mmx_ok, machine_mode mode,
				     rtx target, rtx var, int one_var)
{
  machine_mode vsimode;
  rtx new_target;
  rtx x, tmp;
  bool use_vector_set = false;
  rtx (*gen_vec_set_0) (rtx, rtx, rtx) = NULL;

  switch (mode)
    {
    case E_V2DImode:
      /* For SSE4.1, we normally use vector set.  But if the second
	 element is zero and inter-unit moves are OK, we use movq
	 instead.  */
      use_vector_set = (TARGET_64BIT && TARGET_SSE4_1
			&& !(TARGET_INTER_UNIT_MOVES_TO_VEC
			     && one_var == 0));
      break;
    case E_V16QImode:
    case E_V4SImode:
    case E_V4SFmode:
      use_vector_set = TARGET_SSE4_1;
      break;
    case E_V8HImode:
      use_vector_set = TARGET_SSE2;
      break;
    case E_V4HImode:
      use_vector_set = TARGET_SSE || TARGET_3DNOW_A;
      break;
    case E_V32QImode:
    case E_V16HImode:
      use_vector_set = TARGET_AVX;
      break;
    case E_V8SImode:
      use_vector_set = TARGET_AVX;
      gen_vec_set_0 = gen_vec_setv8si_0;
      break;
    case E_V8SFmode:
      use_vector_set = TARGET_AVX;
      gen_vec_set_0 = gen_vec_setv8sf_0;
      break;
    case E_V4DFmode:
      use_vector_set = TARGET_AVX;
      gen_vec_set_0 = gen_vec_setv4df_0;
      break;
    case E_V4DImode:
      /* Use ix86_expand_vector_set in 64bit mode only.  */
      use_vector_set = TARGET_AVX && TARGET_64BIT;
      gen_vec_set_0 = gen_vec_setv4di_0;
      break;
    case E_V16SImode:
      use_vector_set = TARGET_AVX512F && one_var == 0;
      gen_vec_set_0 = gen_vec_setv16si_0;
      break;
    case E_V16SFmode:
      use_vector_set = TARGET_AVX512F && one_var == 0;
      gen_vec_set_0 = gen_vec_setv16sf_0;
      break;
    case E_V8DFmode:
      use_vector_set = TARGET_AVX512F && one_var == 0;
      gen_vec_set_0 = gen_vec_setv8df_0;
      break;
    case E_V8DImode:
      /* Use ix86_expand_vector_set in 64bit mode only.  */
      use_vector_set = TARGET_AVX512F && TARGET_64BIT && one_var == 0;
      gen_vec_set_0 = gen_vec_setv8di_0;
      break;
    default:
      break;
    }

  if (use_vector_set)
    {
      if (gen_vec_set_0 && one_var == 0)
	{
	  var = force_reg (GET_MODE_INNER (mode), var);
	  emit_insn (gen_vec_set_0 (target, CONST0_RTX (mode), var));
	  return true;
	}
      emit_insn (gen_rtx_SET (target, CONST0_RTX (mode)));
      var = force_reg (GET_MODE_INNER (mode), var);
      ix86_expand_vector_set (mmx_ok, target, var, one_var);
      return true;
    }

  switch (mode)
    {
    case E_V2SFmode:
    case E_V2SImode:
      if (!mmx_ok)
	return false;
      /* FALLTHRU */

    case E_V2DFmode:
    case E_V2DImode:
      if (one_var != 0)
	return false;
      var = force_reg (GET_MODE_INNER (mode), var);
      x = gen_rtx_VEC_CONCAT (mode, var, CONST0_RTX (GET_MODE_INNER (mode)));
      emit_insn (gen_rtx_SET (target, x));
      return true;

    case E_V4SFmode:
    case E_V4SImode:
      if (!REG_P (target) || REGNO (target) < FIRST_PSEUDO_REGISTER)
	new_target = gen_reg_rtx (mode);
      else
	new_target = target;
      var = force_reg (GET_MODE_INNER (mode), var);
      x = gen_rtx_VEC_DUPLICATE (mode, var);
      x = gen_rtx_VEC_MERGE (mode, x, CONST0_RTX (mode), const1_rtx);
      emit_insn (gen_rtx_SET (new_target, x));
      if (one_var != 0)
	{
	  /* We need to shuffle the value to the correct position, so
	     create a new pseudo to store the intermediate result.  */

	  /* With SSE2, we can use the integer shuffle insns.  */
	  if (mode != V4SFmode && TARGET_SSE2)
	    {
	      emit_insn (gen_sse2_pshufd_1 (new_target, new_target,
					    const1_rtx,
					    GEN_INT (one_var == 1 ? 0 : 1),
					    GEN_INT (one_var == 2 ? 0 : 1),
					    GEN_INT (one_var == 3 ? 0 : 1)));
	      if (target != new_target)
		emit_move_insn (target, new_target);
	      return true;
	    }

	  /* Otherwise convert the intermediate result to V4SFmode and
	     use the SSE1 shuffle instructions.  */
	  if (mode != V4SFmode)
	    {
	      tmp = gen_reg_rtx (V4SFmode);
	      emit_move_insn (tmp, gen_lowpart (V4SFmode, new_target));
	    }
	  else
	    tmp = new_target;

	  emit_insn (gen_sse_shufps_v4sf (tmp, tmp, tmp,
				       const1_rtx,
				       GEN_INT (one_var == 1 ? 0 : 1),
				       GEN_INT (one_var == 2 ? 0+4 : 1+4),
				       GEN_INT (one_var == 3 ? 0+4 : 1+4)));

	  if (mode != V4SFmode)
	    emit_move_insn (target, gen_lowpart (V4SImode, tmp));
	  else if (tmp != target)
	    emit_move_insn (target, tmp);
	}
      else if (target != new_target)
	emit_move_insn (target, new_target);
      return true;

    case E_V8HImode:
    case E_V16QImode:
      vsimode = V4SImode;
      goto widen;
    case E_V4HImode:
    case E_V8QImode:
      if (!mmx_ok)
	return false;
      vsimode = V2SImode;
      goto widen;
    widen:
      if (one_var != 0)
	return false;

      /* Zero extend the variable element to SImode and recurse.  */
      var = convert_modes (SImode, GET_MODE_INNER (mode), var, true);

      x = gen_reg_rtx (vsimode);
      if (!ix86_expand_vector_init_one_nonzero (mmx_ok, vsimode, x,
						var, one_var))
	gcc_unreachable ();

      emit_move_insn (target, gen_lowpart (mode, x));
      return true;

    default:
      return false;
    }
}

/* A subroutine of ix86_expand_vector_init.  Store into TARGET a vector
   consisting of the values in VALS.  It is known that all elements
   except ONE_VAR are constants.  Return true if successful.  */

static bool
ix86_expand_vector_init_one_var (bool mmx_ok, machine_mode mode,
				 rtx target, rtx vals, int one_var)
{
  rtx var = XVECEXP (vals, 0, one_var);
  machine_mode wmode;
  rtx const_vec, x;

  const_vec = copy_rtx (vals);
  XVECEXP (const_vec, 0, one_var) = CONST0_RTX (GET_MODE_INNER (mode));
  const_vec = gen_rtx_CONST_VECTOR (mode, XVEC (const_vec, 0));

  switch (mode)
    {
    case E_V2DFmode:
    case E_V2DImode:
    case E_V2SFmode:
    case E_V2SImode:
      /* For the two element vectors, it's just as easy to use
	 the general case.  */
      return false;

    case E_V4DImode:
      /* Use ix86_expand_vector_set in 64bit mode only.  */
      if (!TARGET_64BIT)
	return false;
      /* FALLTHRU */
    case E_V4DFmode:
    case E_V8SFmode:
    case E_V8SImode:
    case E_V16HImode:
    case E_V32QImode:
    case E_V4SFmode:
    case E_V4SImode:
    case E_V8HImode:
    case E_V4HImode:
      break;

    case E_V16QImode:
      if (TARGET_SSE4_1)
	break;
      wmode = V8HImode;
      goto widen;
    case E_V8QImode:
      wmode = V4HImode;
      goto widen;
    widen:
      /* There's no way to set one QImode entry easily.  Combine
	 the variable value with its adjacent constant value, and
	 promote to an HImode set.  */
      x = XVECEXP (vals, 0, one_var ^ 1);
      if (one_var & 1)
	{
	  var = convert_modes (HImode, QImode, var, true);
	  var = expand_simple_binop (HImode, ASHIFT, var, GEN_INT (8),
				     NULL_RTX, 1, OPTAB_LIB_WIDEN);
	  x = GEN_INT (INTVAL (x) & 0xff);
	}
      else
	{
	  var = convert_modes (HImode, QImode, var, true);
	  x = gen_int_mode (UINTVAL (x) << 8, HImode);
	}
      if (x != const0_rtx)
	var = expand_simple_binop (HImode, IOR, var, x, var,
				   1, OPTAB_LIB_WIDEN);

      x = gen_reg_rtx (wmode);
      emit_move_insn (x, gen_lowpart (wmode, const_vec));
      ix86_expand_vector_set (mmx_ok, x, var, one_var >> 1);

      emit_move_insn (target, gen_lowpart (mode, x));
      return true;

    default:
      return false;
    }

  emit_move_insn (target, const_vec);
  ix86_expand_vector_set (mmx_ok, target, var, one_var);
  return true;
}

/* A subroutine of ix86_expand_vector_init_general.  Use vector
   concatenate to handle the most general case: all values variable,
   and none identical.  */

static void
ix86_expand_vector_init_concat (machine_mode mode,
				rtx target, rtx *ops, int n)
{
  machine_mode cmode, hmode = VOIDmode, gmode = VOIDmode;
  rtx first[16], second[8], third[4];
  rtvec v;
  int i, j;

  switch (n)
    {
    case 2:
      switch (mode)
	{
	case E_V16SImode:
	  cmode = V8SImode;
	  break;
	case E_V16SFmode:
	  cmode = V8SFmode;
	  break;
	case E_V8DImode:
	  cmode = V4DImode;
	  break;
	case E_V8DFmode:
	  cmode = V4DFmode;
	  break;
	case E_V8SImode:
	  cmode = V4SImode;
	  break;
	case E_V8SFmode:
	  cmode = V4SFmode;
	  break;
	case E_V4DImode:
	  cmode = V2DImode;
	  break;
	case E_V4DFmode:
	  cmode = V2DFmode;
	  break;
	case E_V4SImode:
	  cmode = V2SImode;
	  break;
	case E_V4SFmode:
	  cmode = V2SFmode;
	  break;
	case E_V2DImode:
	  cmode = DImode;
	  break;
	case E_V2SImode:
	  cmode = SImode;
	  break;
	case E_V2DFmode:
	  cmode = DFmode;
	  break;
	case E_V2SFmode:
	  cmode = SFmode;
	  break;
	default:
	  gcc_unreachable ();
	}

      if (!register_operand (ops[1], cmode))
	ops[1] = force_reg (cmode, ops[1]);
      if (!register_operand (ops[0], cmode))
	ops[0] = force_reg (cmode, ops[0]);
      emit_insn (gen_rtx_SET (target, gen_rtx_VEC_CONCAT (mode, ops[0],
							  ops[1])));
      break;

    case 4:
      switch (mode)
	{
	case E_V4DImode:
	  cmode = V2DImode;
	  break;
	case E_V4DFmode:
	  cmode = V2DFmode;
	  break;
	case E_V4SImode:
	  cmode = V2SImode;
	  break;
	case E_V4SFmode:
	  cmode = V2SFmode;
	  break;
	default:
	  gcc_unreachable ();
	}
      goto half;

    case 8:
      switch (mode)
	{
	case E_V8DImode:
	  cmode = V2DImode;
	  hmode = V4DImode;
	  break;
	case E_V8DFmode:
	  cmode = V2DFmode;
	  hmode = V4DFmode;
	  break;
	case E_V8SImode:
	  cmode = V2SImode;
	  hmode = V4SImode;
	  break;
	case E_V8SFmode:
	  cmode = V2SFmode;
	  hmode = V4SFmode;
	  break;
	default:
	  gcc_unreachable ();
	}
      goto half;

    case 16:
      switch (mode)
	{
	case E_V16SImode:
	  cmode = V2SImode;
	  hmode = V4SImode;
	  gmode = V8SImode;
	  break;
	case E_V16SFmode:
	  cmode = V2SFmode;
	  hmode = V4SFmode;
	  gmode = V8SFmode;
	  break;
	default:
	  gcc_unreachable ();
	}
      goto half;

half:
      /* FIXME: We process inputs backward to help RA.  PR 36222.  */
      i = n - 1;
      j = (n >> 1) - 1;
      for (; i > 0; i -= 2, j--)
	{
	  first[j] = gen_reg_rtx (cmode);
	  v = gen_rtvec (2, ops[i - 1], ops[i]);
	  ix86_expand_vector_init (false, first[j],
				   gen_rtx_PARALLEL (cmode, v));
	}

      n >>= 1;
      if (n > 4)
	{
	  gcc_assert (hmode != VOIDmode);
	  gcc_assert (gmode != VOIDmode);
	  for (i = j = 0; i < n; i += 2, j++)
	    {
	      second[j] = gen_reg_rtx (hmode);
	      ix86_expand_vector_init_concat (hmode, second [j],
					      &first [i], 2);
	    }
	  n >>= 1;
	  for (i = j = 0; i < n; i += 2, j++)
	    {
	      third[j] = gen_reg_rtx (gmode);
	      ix86_expand_vector_init_concat (gmode, third[j],
					      &second[i], 2);
	    }
	  n >>= 1;
	  ix86_expand_vector_init_concat (mode, target, third, n);
	}
      else if (n > 2)
	{
	  gcc_assert (hmode != VOIDmode);
	  for (i = j = 0; i < n; i += 2, j++)
	    {
	      second[j] = gen_reg_rtx (hmode);
	      ix86_expand_vector_init_concat (hmode, second [j],
					      &first [i], 2);
	    }
	  n >>= 1;
	  ix86_expand_vector_init_concat (mode, target, second, n);
	}
      else
	ix86_expand_vector_init_concat (mode, target, first, n);
      break;

    default:
      gcc_unreachable ();
    }
}

/* A subroutine of ix86_expand_vector_init_general.  Use vector
   interleave to handle the most general case: all values variable,
   and none identical.  */

static void
ix86_expand_vector_init_interleave (machine_mode mode,
				    rtx target, rtx *ops, int n)
{
  machine_mode first_imode, second_imode, third_imode, inner_mode;
  int i, j;
  rtx op0, op1;
  rtx (*gen_load_even) (rtx, rtx, rtx);
  rtx (*gen_interleave_first_low) (rtx, rtx, rtx);
  rtx (*gen_interleave_second_low) (rtx, rtx, rtx);

  switch (mode)
    {
    case E_V8HImode:
      gen_load_even = gen_vec_setv8hi;
      gen_interleave_first_low = gen_vec_interleave_lowv4si;
      gen_interleave_second_low = gen_vec_interleave_lowv2di;
      inner_mode = HImode;
      first_imode = V4SImode;
      second_imode = V2DImode;
      third_imode = VOIDmode;
      break;
    case E_V16QImode:
      gen_load_even = gen_vec_setv16qi;
      gen_interleave_first_low = gen_vec_interleave_lowv8hi;
      gen_interleave_second_low = gen_vec_interleave_lowv4si;
      inner_mode = QImode;
      first_imode = V8HImode;
      second_imode = V4SImode;
      third_imode = V2DImode;
      break;
    default:
      gcc_unreachable ();
    }

  for (i = 0; i < n; i++)
    {
      /* Extend the odd elment to SImode using a paradoxical SUBREG.  */
      op0 = gen_reg_rtx (SImode);
      emit_move_insn (op0, gen_lowpart (SImode, ops [i + i]));

      /* Insert the SImode value as low element of V4SImode vector. */
      op1 = gen_reg_rtx (V4SImode);
      op0 = gen_rtx_VEC_MERGE (V4SImode,
			       gen_rtx_VEC_DUPLICATE (V4SImode,
						      op0),
			       CONST0_RTX (V4SImode),
			       const1_rtx);
      emit_insn (gen_rtx_SET (op1, op0));

      /* Cast the V4SImode vector back to a vector in orignal mode.  */
      op0 = gen_reg_rtx (mode);
      emit_move_insn (op0, gen_lowpart (mode, op1));

      /* Load even elements into the second position.  */
      emit_insn (gen_load_even (op0,
				force_reg (inner_mode,
					   ops [i + i + 1]),
				const1_rtx));

      /* Cast vector to FIRST_IMODE vector.  */
      ops[i] = gen_reg_rtx (first_imode);
      emit_move_insn (ops[i], gen_lowpart (first_imode, op0));
    }

  /* Interleave low FIRST_IMODE vectors.  */
  for (i = j = 0; i < n; i += 2, j++)
    {
      op0 = gen_reg_rtx (first_imode);
      emit_insn (gen_interleave_first_low (op0, ops[i], ops[i + 1]));

      /* Cast FIRST_IMODE vector to SECOND_IMODE vector.  */
      ops[j] = gen_reg_rtx (second_imode);
      emit_move_insn (ops[j], gen_lowpart (second_imode, op0));
    }

  /* Interleave low SECOND_IMODE vectors.  */
  switch (second_imode)
    {
    case E_V4SImode:
      for (i = j = 0; i < n / 2; i += 2, j++)
	{
	  op0 = gen_reg_rtx (second_imode);
	  emit_insn (gen_interleave_second_low (op0, ops[i],
						ops[i + 1]));

	  /* Cast the SECOND_IMODE vector to the THIRD_IMODE
	     vector.  */
	  ops[j] = gen_reg_rtx (third_imode);
	  emit_move_insn (ops[j], gen_lowpart (third_imode, op0));
	}
      second_imode = V2DImode;
      gen_interleave_second_low = gen_vec_interleave_lowv2di;
      /* FALLTHRU */

    case E_V2DImode:
      op0 = gen_reg_rtx (second_imode);
      emit_insn (gen_interleave_second_low (op0, ops[0],
					    ops[1]));

      /* Cast the SECOND_IMODE vector back to a vector on original
	 mode.  */
      emit_insn (gen_rtx_SET (target, gen_lowpart (mode, op0)));
      break;

    default:
      gcc_unreachable ();
    }
}

/* A subroutine of ix86_expand_vector_init.  Handle the most general case:
   all values variable, and none identical.  */

static void
ix86_expand_vector_init_general (bool mmx_ok, machine_mode mode,
				 rtx target, rtx vals)
{
  rtx ops[64], op0, op1, op2, op3, op4, op5;
  machine_mode half_mode = VOIDmode;
  machine_mode quarter_mode = VOIDmode;
  int n, i;

  switch (mode)
    {
    case E_V2SFmode:
    case E_V2SImode:
      if (!mmx_ok && !TARGET_SSE)
	break;
      /* FALLTHRU */

    case E_V16SImode:
    case E_V16SFmode:
    case E_V8DFmode:
    case E_V8DImode:
    case E_V8SFmode:
    case E_V8SImode:
    case E_V4DFmode:
    case E_V4DImode:
    case E_V4SFmode:
    case E_V4SImode:
    case E_V2DFmode:
    case E_V2DImode:
      n = GET_MODE_NUNITS (mode);
      for (i = 0; i < n; i++)
	ops[i] = XVECEXP (vals, 0, i);
      ix86_expand_vector_init_concat (mode, target, ops, n);
      return;

    case E_V2TImode:
      for (i = 0; i < 2; i++)
	ops[i] = gen_lowpart (V2DImode, XVECEXP (vals, 0, i));
      op0 = gen_reg_rtx (V4DImode);
      ix86_expand_vector_init_concat (V4DImode, op0, ops, 2);
      emit_move_insn (target, gen_lowpart (GET_MODE (target), op0));
      return;

    case E_V4TImode:
      for (i = 0; i < 4; i++)
	ops[i] = gen_lowpart (V2DImode, XVECEXP (vals, 0, i));
      ops[4] = gen_reg_rtx (V4DImode);
      ix86_expand_vector_init_concat (V4DImode, ops[4], ops, 2);
      ops[5] = gen_reg_rtx (V4DImode);
      ix86_expand_vector_init_concat (V4DImode, ops[5], ops + 2, 2);
      op0 = gen_reg_rtx (V8DImode);
      ix86_expand_vector_init_concat (V8DImode, op0, ops + 4, 2);
      emit_move_insn (target, gen_lowpart (GET_MODE (target), op0));
      return;

    case E_V32QImode:
      half_mode = V16QImode;
      goto half;

    case E_V16HImode:
      half_mode = V8HImode;
      goto half;

half:
      n = GET_MODE_NUNITS (mode);
      for (i = 0; i < n; i++)
	ops[i] = XVECEXP (vals, 0, i);
      op0 = gen_reg_rtx (half_mode);
      op1 = gen_reg_rtx (half_mode);
      ix86_expand_vector_init_interleave (half_mode, op0, ops,
					  n >> 2);
      ix86_expand_vector_init_interleave (half_mode, op1,
					  &ops [n >> 1], n >> 2);
      emit_insn (gen_rtx_SET (target, gen_rtx_VEC_CONCAT (mode, op0, op1)));
      return;

    case E_V64QImode:
      quarter_mode = V16QImode;
      half_mode = V32QImode;
      goto quarter;

    case E_V32HImode:
      quarter_mode = V8HImode;
      half_mode = V16HImode;
      goto quarter;

quarter:
      n = GET_MODE_NUNITS (mode);
      for (i = 0; i < n; i++)
	ops[i] = XVECEXP (vals, 0, i);
      op0 = gen_reg_rtx (quarter_mode);
      op1 = gen_reg_rtx (quarter_mode);
      op2 = gen_reg_rtx (quarter_mode);
      op3 = gen_reg_rtx (quarter_mode);
      op4 = gen_reg_rtx (half_mode);
      op5 = gen_reg_rtx (half_mode);
      ix86_expand_vector_init_interleave (quarter_mode, op0, ops,
					  n >> 3);
      ix86_expand_vector_init_interleave (quarter_mode, op1,
					  &ops [n >> 2], n >> 3);
      ix86_expand_vector_init_interleave (quarter_mode, op2,
					  &ops [n >> 1], n >> 3);
      ix86_expand_vector_init_interleave (quarter_mode, op3,
					  &ops [(n >> 1) | (n >> 2)], n >> 3);
      emit_insn (gen_rtx_SET (op4, gen_rtx_VEC_CONCAT (half_mode, op0, op1)));
      emit_insn (gen_rtx_SET (op5, gen_rtx_VEC_CONCAT (half_mode, op2, op3)));
      emit_insn (gen_rtx_SET (target, gen_rtx_VEC_CONCAT (mode, op4, op5)));
      return;

    case E_V16QImode:
      if (!TARGET_SSE4_1)
	break;
      /* FALLTHRU */

    case E_V8HImode:
      if (!TARGET_SSE2)
	break;

      /* Don't use ix86_expand_vector_init_interleave if we can't
	 move from GPR to SSE register directly.  */
      if (!TARGET_INTER_UNIT_MOVES_TO_VEC)
	break;

      n = GET_MODE_NUNITS (mode);
      for (i = 0; i < n; i++)
	ops[i] = XVECEXP (vals, 0, i);
      ix86_expand_vector_init_interleave (mode, target, ops, n >> 1);
      return;

    case E_V4HImode:
    case E_V8QImode:
      break;

    default:
      gcc_unreachable ();
    }

    {
      int i, j, n_elts, n_words, n_elt_per_word;
      machine_mode inner_mode;
      rtx words[4], shift;

      inner_mode = GET_MODE_INNER (mode);
      n_elts = GET_MODE_NUNITS (mode);
      n_words = GET_MODE_SIZE (mode) / UNITS_PER_WORD;
      n_elt_per_word = n_elts / n_words;
      shift = GEN_INT (GET_MODE_BITSIZE (inner_mode));

      for (i = 0; i < n_words; ++i)
	{
	  rtx word = NULL_RTX;

	  for (j = 0; j < n_elt_per_word; ++j)
	    {
	      rtx elt = XVECEXP (vals, 0, (i+1)*n_elt_per_word - j - 1);
	      elt = convert_modes (word_mode, inner_mode, elt, true);

	      if (j == 0)
		word = elt;
	      else
		{
		  word = expand_simple_binop (word_mode, ASHIFT, word, shift,
					      word, 1, OPTAB_LIB_WIDEN);
		  word = expand_simple_binop (word_mode, IOR, word, elt,
					      word, 1, OPTAB_LIB_WIDEN);
		}
	    }

	  words[i] = word;
	}

      if (n_words == 1)
	emit_move_insn (target, gen_lowpart (mode, words[0]));
      else if (n_words == 2)
	{
	  rtx tmp = gen_reg_rtx (mode);
	  emit_clobber (tmp);
	  emit_move_insn (gen_lowpart (word_mode, tmp), words[0]);
	  emit_move_insn (gen_highpart (word_mode, tmp), words[1]);
	  emit_move_insn (target, tmp);
	}
      else if (n_words == 4)
	{
	  rtx tmp = gen_reg_rtx (V4SImode);
	  gcc_assert (word_mode == SImode);
	  vals = gen_rtx_PARALLEL (V4SImode, gen_rtvec_v (4, words));
	  ix86_expand_vector_init_general (false, V4SImode, tmp, vals);
	  emit_move_insn (target, gen_lowpart (mode, tmp));
	}
      else
	gcc_unreachable ();
    }
}

/* Initialize vector TARGET via VALS.  Suppress the use of MMX
   instructions unless MMX_OK is true.  */

void
ix86_expand_vector_init (bool mmx_ok, rtx target, rtx vals)
{
  machine_mode mode = GET_MODE (target);
  machine_mode inner_mode = GET_MODE_INNER (mode);
  int n_elts = GET_MODE_NUNITS (mode);
  int n_var = 0, one_var = -1;
  bool all_same = true, all_const_zero = true;
  int i;
  rtx x;

  /* Handle first initialization from vector elts.  */
  if (n_elts != XVECLEN (vals, 0))
    {
      rtx subtarget = target;
      x = XVECEXP (vals, 0, 0);
      gcc_assert (GET_MODE_INNER (GET_MODE (x)) == inner_mode);
      if (GET_MODE_NUNITS (GET_MODE (x)) * 2 == n_elts)
	{
	  rtx ops[2] = { XVECEXP (vals, 0, 0), XVECEXP (vals, 0, 1) };
	  if (inner_mode == QImode || inner_mode == HImode)
	    {
	      unsigned int n_bits = n_elts * GET_MODE_SIZE (inner_mode);
	      mode = mode_for_vector (SImode, n_bits / 4).require ();
	      inner_mode = mode_for_vector (SImode, n_bits / 8).require ();
	      ops[0] = gen_lowpart (inner_mode, ops[0]);
	      ops[1] = gen_lowpart (inner_mode, ops[1]);
	      subtarget = gen_reg_rtx (mode);
	    }
	  ix86_expand_vector_init_concat (mode, subtarget, ops, 2);
	  if (subtarget != target)
	    emit_move_insn (target, gen_lowpart (GET_MODE (target), subtarget));
	  return;
	}
      gcc_unreachable ();
    }

  for (i = 0; i < n_elts; ++i)
    {
      x = XVECEXP (vals, 0, i);
      if (!(CONST_SCALAR_INT_P (x)
	    || CONST_DOUBLE_P (x)
	    || CONST_FIXED_P (x)))
	n_var++, one_var = i;
      else if (x != CONST0_RTX (inner_mode))
	all_const_zero = false;
      if (i > 0 && !rtx_equal_p (x, XVECEXP (vals, 0, 0)))
	all_same = false;
    }

  /* Constants are best loaded from the constant pool.  */
  if (n_var == 0)
    {
      emit_move_insn (target, gen_rtx_CONST_VECTOR (mode, XVEC (vals, 0)));
      return;
    }

  /* If all values are identical, broadcast the value.  */
  if (all_same
      && ix86_expand_vector_init_duplicate (mmx_ok, mode, target,
					    XVECEXP (vals, 0, 0)))
    return;

  /* Values where only one field is non-constant are best loaded from
     the pool and overwritten via move later.  */
  if (n_var == 1)
    {
      if (all_const_zero
	  && ix86_expand_vector_init_one_nonzero (mmx_ok, mode, target,
						  XVECEXP (vals, 0, one_var),
						  one_var))
	return;

      if (ix86_expand_vector_init_one_var (mmx_ok, mode, target, vals, one_var))
	return;
    }

  ix86_expand_vector_init_general (mmx_ok, mode, target, vals);
}

void
ix86_expand_vector_set (bool mmx_ok, rtx target, rtx val, int elt)
{
  machine_mode mode = GET_MODE (target);
  machine_mode inner_mode = GET_MODE_INNER (mode);
  machine_mode half_mode;
  bool use_vec_merge = false;
  rtx tmp;
  static rtx (*gen_extract[6][2]) (rtx, rtx)
    = {
	{ gen_vec_extract_lo_v32qi, gen_vec_extract_hi_v32qi },
	{ gen_vec_extract_lo_v16hi, gen_vec_extract_hi_v16hi },
	{ gen_vec_extract_lo_v8si, gen_vec_extract_hi_v8si },
	{ gen_vec_extract_lo_v4di, gen_vec_extract_hi_v4di },
	{ gen_vec_extract_lo_v8sf, gen_vec_extract_hi_v8sf },
	{ gen_vec_extract_lo_v4df, gen_vec_extract_hi_v4df }
      };
  static rtx (*gen_insert[6][2]) (rtx, rtx, rtx)
    = {
	{ gen_vec_set_lo_v32qi, gen_vec_set_hi_v32qi },
	{ gen_vec_set_lo_v16hi, gen_vec_set_hi_v16hi },
	{ gen_vec_set_lo_v8si, gen_vec_set_hi_v8si },
	{ gen_vec_set_lo_v4di, gen_vec_set_hi_v4di },
	{ gen_vec_set_lo_v8sf, gen_vec_set_hi_v8sf },
	{ gen_vec_set_lo_v4df, gen_vec_set_hi_v4df }
      };
  int i, j, n;
  machine_mode mmode = VOIDmode;
  rtx (*gen_blendm) (rtx, rtx, rtx, rtx);

  switch (mode)
    {
    case E_V2SFmode:
    case E_V2SImode:
      if (mmx_ok)
	{
	  tmp = gen_reg_rtx (GET_MODE_INNER (mode));
	  ix86_expand_vector_extract (true, tmp, target, 1 - elt);
	  if (elt == 0)
	    tmp = gen_rtx_VEC_CONCAT (mode, val, tmp);
	  else
	    tmp = gen_rtx_VEC_CONCAT (mode, tmp, val);
	  emit_insn (gen_rtx_SET (target, tmp));
	  return;
	}
      break;

    case E_V2DImode:
      use_vec_merge = TARGET_SSE4_1 && TARGET_64BIT;
      if (use_vec_merge)
	break;

      tmp = gen_reg_rtx (GET_MODE_INNER (mode));
      ix86_expand_vector_extract (false, tmp, target, 1 - elt);
      if (elt == 0)
	tmp = gen_rtx_VEC_CONCAT (mode, val, tmp);
      else
	tmp = gen_rtx_VEC_CONCAT (mode, tmp, val);
      emit_insn (gen_rtx_SET (target, tmp));
      return;

    case E_V2DFmode:
      {
	rtx op0, op1;

	/* For the two element vectors, we implement a VEC_CONCAT with
	   the extraction of the other element.  */

	tmp = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (1, GEN_INT (1 - elt)));
	tmp = gen_rtx_VEC_SELECT (inner_mode, target, tmp);

	if (elt == 0)
	  op0 = val, op1 = tmp;
	else
	  op0 = tmp, op1 = val;

	tmp = gen_rtx_VEC_CONCAT (mode, op0, op1);
	emit_insn (gen_rtx_SET (target, tmp));
      }
      return;

    case E_V4SFmode:
      use_vec_merge = TARGET_SSE4_1;
      if (use_vec_merge)
	break;

      switch (elt)
	{
	case 0:
	  use_vec_merge = true;
	  break;

	case 1:
	  /* tmp = target = A B C D */
	  tmp = copy_to_reg (target);
	  /* target = A A B B */
	  emit_insn (gen_vec_interleave_lowv4sf (target, target, target));
	  /* target = X A B B */
	  ix86_expand_vector_set (false, target, val, 0);
	  /* target = A X C D  */
	  emit_insn (gen_sse_shufps_v4sf (target, target, tmp,
					  const1_rtx, const0_rtx,
					  GEN_INT (2+4), GEN_INT (3+4)));
	  return;

	case 2:
	  /* tmp = target = A B C D */
	  tmp = copy_to_reg (target);
	  /* tmp = X B C D */
	  ix86_expand_vector_set (false, tmp, val, 0);
	  /* target = A B X D */
	  emit_insn (gen_sse_shufps_v4sf (target, target, tmp,
					  const0_rtx, const1_rtx,
					  GEN_INT (0+4), GEN_INT (3+4)));
	  return;

	case 3:
	  /* tmp = target = A B C D */
	  tmp = copy_to_reg (target);
	  /* tmp = X B C D */
	  ix86_expand_vector_set (false, tmp, val, 0);
	  /* target = A B X D */
	  emit_insn (gen_sse_shufps_v4sf (target, target, tmp,
					  const0_rtx, const1_rtx,
					  GEN_INT (2+4), GEN_INT (0+4)));
	  return;

	default:
	  gcc_unreachable ();
	}
      break;

    case E_V4SImode:
      use_vec_merge = TARGET_SSE4_1;
      if (use_vec_merge)
	break;

      /* Element 0 handled by vec_merge below.  */
      if (elt == 0)
	{
	  use_vec_merge = true;
	  break;
	}

      if (TARGET_SSE2)
	{
	  /* With SSE2, use integer shuffles to swap element 0 and ELT,
	     store into element 0, then shuffle them back.  */

	  rtx order[4];

	  order[0] = GEN_INT (elt);
	  order[1] = const1_rtx;
	  order[2] = const2_rtx;
	  order[3] = GEN_INT (3);
	  order[elt] = const0_rtx;

	  emit_insn (gen_sse2_pshufd_1 (target, target, order[0],
					order[1], order[2], order[3]));

	  ix86_expand_vector_set (false, target, val, 0);

	  emit_insn (gen_sse2_pshufd_1 (target, target, order[0],
					order[1], order[2], order[3]));
	}
      else
	{
	  /* For SSE1, we have to reuse the V4SF code.  */
	  rtx t = gen_reg_rtx (V4SFmode);
	  emit_move_insn (t, gen_lowpart (V4SFmode, target));
	  ix86_expand_vector_set (false, t, gen_lowpart (SFmode, val), elt);
	  emit_move_insn (target, gen_lowpart (mode, t));
	}
      return;

    case E_V8HImode:
      use_vec_merge = TARGET_SSE2;
      break;
    case E_V4HImode:
      use_vec_merge = mmx_ok && (TARGET_SSE || TARGET_3DNOW_A);
      break;

    case E_V16QImode:
      use_vec_merge = TARGET_SSE4_1;
      break;

    case E_V8QImode:
      break;

    case E_V32QImode:
      half_mode = V16QImode;
      j = 0;
      n = 16;
      goto half;

    case E_V16HImode:
      half_mode = V8HImode;
      j = 1;
      n = 8;
      goto half;

    case E_V8SImode:
      half_mode = V4SImode;
      j = 2;
      n = 4;
      goto half;

    case E_V4DImode:
      half_mode = V2DImode;
      j = 3;
      n = 2;
      goto half;

    case E_V8SFmode:
      half_mode = V4SFmode;
      j = 4;
      n = 4;
      goto half;

    case E_V4DFmode:
      half_mode = V2DFmode;
      j = 5;
      n = 2;
      goto half;

half:
      /* Compute offset.  */
      i = elt / n;
      elt %= n;

      gcc_assert (i <= 1);

      /* Extract the half.  */
      tmp = gen_reg_rtx (half_mode);
      emit_insn (gen_extract[j][i] (tmp, target));

      /* Put val in tmp at elt.  */
      ix86_expand_vector_set (false, tmp, val, elt);

      /* Put it back.  */
      emit_insn (gen_insert[j][i] (target, target, tmp));
      return;

    case E_V8DFmode:
      if (TARGET_AVX512F)
	{
	  mmode = QImode;
	  gen_blendm = gen_avx512f_blendmv8df;
	}
      break;

    case E_V8DImode:
      if (TARGET_AVX512F)
	{
	  mmode = QImode;
	  gen_blendm = gen_avx512f_blendmv8di;
	}
      break;

    case E_V16SFmode:
      if (TARGET_AVX512F)
	{
	  mmode = HImode;
	  gen_blendm = gen_avx512f_blendmv16sf;
	}
      break;

    case E_V16SImode:
      if (TARGET_AVX512F)
	{
	  mmode = HImode;
	  gen_blendm = gen_avx512f_blendmv16si;
	}
      break;

    case E_V32HImode:
      if (TARGET_AVX512BW)
	{
	  mmode = SImode;
	  gen_blendm = gen_avx512bw_blendmv32hi;
	}
      else if (TARGET_AVX512F)
	{
	  half_mode = E_V8HImode;
	  n = 8;
	  goto quarter;
	}
      break;

    case E_V64QImode:
      if (TARGET_AVX512BW)
	{
	  mmode = DImode;
	  gen_blendm = gen_avx512bw_blendmv64qi;
	}
      else if (TARGET_AVX512F)
	{
	  half_mode = E_V16QImode;
	  n = 16;
	  goto quarter;
	}
      break;

quarter:
      /* Compute offset.  */
      i = elt / n;
      elt %= n;

      gcc_assert (i <= 3);

      {
	/* Extract the quarter.  */
	tmp = gen_reg_rtx (V4SImode);
	rtx tmp2 = gen_lowpart (V16SImode, target);
	rtx mask = gen_reg_rtx (QImode);

	emit_move_insn (mask, constm1_rtx);
	emit_insn (gen_avx512f_vextracti32x4_mask (tmp, tmp2, GEN_INT (i),
						   tmp, mask));

	tmp2 = gen_reg_rtx (half_mode);
	emit_move_insn (tmp2, gen_lowpart (half_mode, tmp));
	tmp = tmp2;

	/* Put val in tmp at elt.  */
	ix86_expand_vector_set (false, tmp, val, elt);

	/* Put it back.  */
	tmp2 = gen_reg_rtx (V16SImode);
	rtx tmp3 = gen_lowpart (V16SImode, target);
	mask = gen_reg_rtx (HImode);
	emit_move_insn (mask, constm1_rtx);
	tmp = gen_lowpart (V4SImode, tmp);
	emit_insn (gen_avx512f_vinserti32x4_mask (tmp2, tmp3, tmp, GEN_INT (i),
						  tmp3, mask));
	emit_move_insn (target, gen_lowpart (mode, tmp2));
      }
      return;

    default:
      break;
    }

  if (mmode != VOIDmode)
    {
      tmp = gen_reg_rtx (mode);
      emit_insn (gen_rtx_SET (tmp, gen_rtx_VEC_DUPLICATE (mode, val)));
      /* The avx512*_blendm<mode> expanders have different operand order
	 from VEC_MERGE.  In VEC_MERGE, the first input operand is used for
	 elements where the mask is set and second input operand otherwise,
	 in {sse,avx}*_*blend* the first input operand is used for elements
	 where the mask is clear and second input operand otherwise.  */
      emit_insn (gen_blendm (target, target, tmp,
			     force_reg (mmode,
					gen_int_mode (HOST_WIDE_INT_1U << elt,
						      mmode))));
    }
  else if (use_vec_merge)
    {
      tmp = gen_rtx_VEC_DUPLICATE (mode, val);
      tmp = gen_rtx_VEC_MERGE (mode, tmp, target,
			       GEN_INT (HOST_WIDE_INT_1U << elt));
      emit_insn (gen_rtx_SET (target, tmp));
    }
  else
    {
      rtx mem = assign_stack_temp (mode, GET_MODE_SIZE (mode));

      emit_move_insn (mem, target);

      tmp = adjust_address (mem, inner_mode, elt * GET_MODE_SIZE (inner_mode));
      emit_move_insn (tmp, val);

      emit_move_insn (target, mem);
    }
}

void
ix86_expand_vector_extract (bool mmx_ok, rtx target, rtx vec, int elt)
{
  machine_mode mode = GET_MODE (vec);
  machine_mode inner_mode = GET_MODE_INNER (mode);
  bool use_vec_extr = false;
  rtx tmp;

  switch (mode)
    {
    case E_V2SImode:
    case E_V2SFmode:
      if (!mmx_ok)
	break;
      /* FALLTHRU */

    case E_V2DFmode:
    case E_V2DImode:
    case E_V2TImode:
    case E_V4TImode:
      use_vec_extr = true;
      break;

    case E_V4SFmode:
      use_vec_extr = TARGET_SSE4_1;
      if (use_vec_extr)
	break;

      switch (elt)
	{
	case 0:
	  tmp = vec;
	  break;

	case 1:
	case 3:
	  tmp = gen_reg_rtx (mode);
	  emit_insn (gen_sse_shufps_v4sf (tmp, vec, vec,
				       GEN_INT (elt), GEN_INT (elt),
				       GEN_INT (elt+4), GEN_INT (elt+4)));
	  break;

	case 2:
	  tmp = gen_reg_rtx (mode);
	  emit_insn (gen_vec_interleave_highv4sf (tmp, vec, vec));
	  break;

	default:
	  gcc_unreachable ();
	}
      vec = tmp;
      use_vec_extr = true;
      elt = 0;
      break;

    case E_V4SImode:
      use_vec_extr = TARGET_SSE4_1;
      if (use_vec_extr)
	break;

      if (TARGET_SSE2)
	{
	  switch (elt)
	    {
	    case 0:
	      tmp = vec;
	      break;

	    case 1:
	    case 3:
	      tmp = gen_reg_rtx (mode);
	      emit_insn (gen_sse2_pshufd_1 (tmp, vec,
					    GEN_INT (elt), GEN_INT (elt),
					    GEN_INT (elt), GEN_INT (elt)));
	      break;

	    case 2:
	      tmp = gen_reg_rtx (mode);
	      emit_insn (gen_vec_interleave_highv4si (tmp, vec, vec));
	      break;

	    default:
	      gcc_unreachable ();
	    }
	  vec = tmp;
	  use_vec_extr = true;
	  elt = 0;
	}
      else
	{
	  /* For SSE1, we have to reuse the V4SF code.  */
	  ix86_expand_vector_extract (false, gen_lowpart (SFmode, target),
				      gen_lowpart (V4SFmode, vec), elt);
	  return;
	}
      break;

    case E_V8HImode:
      use_vec_extr = TARGET_SSE2;
      break;
    case E_V4HImode:
      use_vec_extr = mmx_ok && (TARGET_SSE || TARGET_3DNOW_A);
      break;

    case E_V16QImode:
      use_vec_extr = TARGET_SSE4_1;
      break;

    case E_V8SFmode:
      if (TARGET_AVX)
	{
	  tmp = gen_reg_rtx (V4SFmode);
	  if (elt < 4)
	    emit_insn (gen_vec_extract_lo_v8sf (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v8sf (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 3);
	  return;
	}
      break;

    case E_V4DFmode:
      if (TARGET_AVX)
	{
	  tmp = gen_reg_rtx (V2DFmode);
	  if (elt < 2)
	    emit_insn (gen_vec_extract_lo_v4df (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v4df (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 1);
	  return;
	}
      break;

    case E_V32QImode:
      if (TARGET_AVX)
	{
	  tmp = gen_reg_rtx (V16QImode);
	  if (elt < 16)
	    emit_insn (gen_vec_extract_lo_v32qi (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v32qi (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 15);
	  return;
	}
      break;

    case E_V16HImode:
      if (TARGET_AVX)
	{
	  tmp = gen_reg_rtx (V8HImode);
	  if (elt < 8)
	    emit_insn (gen_vec_extract_lo_v16hi (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v16hi (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 7);
	  return;
	}
      break;

    case E_V8SImode:
      if (TARGET_AVX)
	{
	  tmp = gen_reg_rtx (V4SImode);
	  if (elt < 4)
	    emit_insn (gen_vec_extract_lo_v8si (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v8si (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 3);
	  return;
	}
      break;

    case E_V4DImode:
      if (TARGET_AVX)
	{
	  tmp = gen_reg_rtx (V2DImode);
	  if (elt < 2)
	    emit_insn (gen_vec_extract_lo_v4di (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v4di (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 1);
	  return;
	}
      break;

    case E_V32HImode:
      if (TARGET_AVX512BW)
	{
	  tmp = gen_reg_rtx (V16HImode);
	  if (elt < 16)
	    emit_insn (gen_vec_extract_lo_v32hi (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v32hi (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 15);
	  return;
	}
      break;

    case E_V64QImode:
      if (TARGET_AVX512BW)
	{
	  tmp = gen_reg_rtx (V32QImode);
	  if (elt < 32)
	    emit_insn (gen_vec_extract_lo_v64qi (tmp, vec));
	  else
	    emit_insn (gen_vec_extract_hi_v64qi (tmp, vec));
	  ix86_expand_vector_extract (false, target, tmp, elt & 31);
	  return;
	}
      break;

    case E_V16SFmode:
      tmp = gen_reg_rtx (V8SFmode);
      if (elt < 8)
	emit_insn (gen_vec_extract_lo_v16sf (tmp, vec));
      else
	emit_insn (gen_vec_extract_hi_v16sf (tmp, vec));
      ix86_expand_vector_extract (false, target, tmp, elt & 7);
      return;

    case E_V8DFmode:
      tmp = gen_reg_rtx (V4DFmode);
      if (elt < 4)
	emit_insn (gen_vec_extract_lo_v8df (tmp, vec));
      else
	emit_insn (gen_vec_extract_hi_v8df (tmp, vec));
      ix86_expand_vector_extract (false, target, tmp, elt & 3);
      return;

    case E_V16SImode:
      tmp = gen_reg_rtx (V8SImode);
      if (elt < 8)
	emit_insn (gen_vec_extract_lo_v16si (tmp, vec));
      else
	emit_insn (gen_vec_extract_hi_v16si (tmp, vec));
      ix86_expand_vector_extract (false, target, tmp, elt & 7);
      return;

    case E_V8DImode:
      tmp = gen_reg_rtx (V4DImode);
      if (elt < 4)
	emit_insn (gen_vec_extract_lo_v8di (tmp, vec));
      else
	emit_insn (gen_vec_extract_hi_v8di (tmp, vec));
      ix86_expand_vector_extract (false, target, tmp, elt & 3);
      return;

    case E_V8QImode:
      /* ??? Could extract the appropriate HImode element and shift.  */
    default:
      break;
    }

  if (use_vec_extr)
    {
      tmp = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (1, GEN_INT (elt)));
      tmp = gen_rtx_VEC_SELECT (inner_mode, vec, tmp);

      /* Let the rtl optimizers know about the zero extension performed.  */
      if (inner_mode == QImode || inner_mode == HImode)
	{
	  tmp = gen_rtx_ZERO_EXTEND (SImode, tmp);
	  target = gen_lowpart (SImode, target);
	}

      emit_insn (gen_rtx_SET (target, tmp));
    }
  else
    {
      rtx mem = assign_stack_temp (mode, GET_MODE_SIZE (mode));

      emit_move_insn (mem, vec);

      tmp = adjust_address (mem, inner_mode, elt*GET_MODE_SIZE (inner_mode));
      emit_move_insn (target, tmp);
    }
}

/* Generate code to copy vector bits i / 2 ... i - 1 from vector SRC
   to bits 0 ... i / 2 - 1 of vector DEST, which has the same mode.
   The upper bits of DEST are undefined, though they shouldn't cause
   exceptions (some bits from src or all zeros are ok).  */

static void
emit_reduc_half (rtx dest, rtx src, int i)
{
  rtx tem, d = dest;
  switch (GET_MODE (src))
    {
    case E_V4SFmode:
      if (i == 128)
	tem = gen_sse_movhlps (dest, src, src);
      else
	tem = gen_sse_shufps_v4sf (dest, src, src, const1_rtx, const1_rtx,
				   GEN_INT (1 + 4), GEN_INT (1 + 4));
      break;
    case E_V2DFmode:
      tem = gen_vec_interleave_highv2df (dest, src, src);
      break;
    case E_V16QImode:
    case E_V8HImode:
    case E_V4SImode:
    case E_V2DImode:
      d = gen_reg_rtx (V1TImode);
      tem = gen_sse2_lshrv1ti3 (d, gen_lowpart (V1TImode, src),
				GEN_INT (i / 2));
      break;
    case E_V8SFmode:
      if (i == 256)
	tem = gen_avx_vperm2f128v8sf3 (dest, src, src, const1_rtx);
      else
	tem = gen_avx_shufps256 (dest, src, src,
				 GEN_INT (i == 128 ? 2 + (3 << 2) : 1));
      break;
    case E_V4DFmode:
      if (i == 256)
	tem = gen_avx_vperm2f128v4df3 (dest, src, src, const1_rtx);
      else
	tem = gen_avx_shufpd256 (dest, src, src, const1_rtx);
      break;
    case E_V32QImode:
    case E_V16HImode:
    case E_V8SImode:
    case E_V4DImode:
      if (i == 256)
	{
	  if (GET_MODE (dest) != V4DImode)
	    d = gen_reg_rtx (V4DImode);
	  tem = gen_avx2_permv2ti (d, gen_lowpart (V4DImode, src),
				   gen_lowpart (V4DImode, src),
				   const1_rtx);
	}
      else
	{
	  d = gen_reg_rtx (V2TImode);
	  tem = gen_avx2_lshrv2ti3 (d, gen_lowpart (V2TImode, src),
				    GEN_INT (i / 2));
	}
      break;
    case E_V64QImode:
    case E_V32HImode:
    case E_V16SImode:
    case E_V16SFmode:
    case E_V8DImode:
    case E_V8DFmode:
      if (i > 128)
	tem = gen_avx512f_shuf_i32x4_1 (gen_lowpart (V16SImode, dest),
				      gen_lowpart (V16SImode, src),
				      gen_lowpart (V16SImode, src),
				      GEN_INT (0x4 + (i == 512 ? 4 : 0)),
				      GEN_INT (0x5 + (i == 512 ? 4 : 0)),
				      GEN_INT (0x6 + (i == 512 ? 4 : 0)),
				      GEN_INT (0x7 + (i == 512 ? 4 : 0)),
				      GEN_INT (0xC), GEN_INT (0xD),
				      GEN_INT (0xE), GEN_INT (0xF),
				      GEN_INT (0x10), GEN_INT (0x11),
				      GEN_INT (0x12), GEN_INT (0x13),
				      GEN_INT (0x14), GEN_INT (0x15),
				      GEN_INT (0x16), GEN_INT (0x17));
      else
	tem = gen_avx512f_pshufd_1 (gen_lowpart (V16SImode, dest),
				   gen_lowpart (V16SImode, src),
				   GEN_INT (i == 128 ? 0x2 : 0x1),
				   GEN_INT (0x3),
				   GEN_INT (0x3),
				   GEN_INT (0x3),
				   GEN_INT (i == 128 ? 0x6 : 0x5),
				   GEN_INT (0x7),
				   GEN_INT (0x7),
				   GEN_INT (0x7),
				   GEN_INT (i == 128 ? 0xA : 0x9),
				   GEN_INT (0xB),
				   GEN_INT (0xB),
				   GEN_INT (0xB),
				   GEN_INT (i == 128 ? 0xE : 0xD),
				   GEN_INT (0xF),
				   GEN_INT (0xF),
				   GEN_INT (0xF));
      break;
    default:
      gcc_unreachable ();
    }
  emit_insn (tem);
  if (d != dest)
    emit_move_insn (dest, gen_lowpart (GET_MODE (dest), d));
}

/* Expand a vector reduction.  FN is the binary pattern to reduce;
   DEST is the destination; IN is the input vector.  */

void
ix86_expand_reduc (rtx (*fn) (rtx, rtx, rtx), rtx dest, rtx in)
{
  rtx half, dst, vec = in;
  machine_mode mode = GET_MODE (in);
  int i;

  /* SSE4 has a special instruction for V8HImode UMIN reduction.  */
  if (TARGET_SSE4_1
      && mode == V8HImode
      && fn == gen_uminv8hi3)
    {
      emit_insn (gen_sse4_1_phminposuw (dest, in));
      return;
    }

  for (i = GET_MODE_BITSIZE (mode);
       i > GET_MODE_UNIT_BITSIZE (mode);
       i >>= 1)
    {
      half = gen_reg_rtx (mode);
      emit_reduc_half (half, vec, i);
      if (i == GET_MODE_UNIT_BITSIZE (mode) * 2)
	dst = dest;
      else
	dst = gen_reg_rtx (mode);
      emit_insn (fn (dst, half, vec));
      vec = dst;
    }
}

/* Target hook for scalar_mode_supported_p.  */
static bool
ix86_scalar_mode_supported_p (scalar_mode mode)
{
  if (DECIMAL_FLOAT_MODE_P (mode))
    return default_decimal_float_supported_p ();
  else if (mode == TFmode)
    return true;
  else
    return default_scalar_mode_supported_p (mode);
}

/* Implements target hook vector_mode_supported_p.  */
static bool
ix86_vector_mode_supported_p (machine_mode mode)
{
  if (TARGET_SSE && VALID_SSE_REG_MODE (mode))
    return true;
  if (TARGET_SSE2 && VALID_SSE2_REG_MODE (mode))
    return true;
  if (TARGET_AVX && VALID_AVX256_REG_MODE (mode))
    return true;
  if (TARGET_AVX512F && VALID_AVX512F_REG_MODE (mode))
    return true;
  if (TARGET_MMX && VALID_MMX_REG_MODE (mode))
    return true;
  if (TARGET_3DNOW && VALID_MMX_REG_MODE_3DNOW (mode))
    return true;
  return false;
}

/* Target hook for c_mode_for_suffix.  */
static machine_mode
ix86_c_mode_for_suffix (char suffix)
{
  if (suffix == 'q')
    return TFmode;
  if (suffix == 'w')
    return XFmode;

  return VOIDmode;
}

/* Worker function for TARGET_MD_ASM_ADJUST.

   We implement asm flag outputs, and maintain source compatibility
   with the old cc0-based compiler.  */

static rtx_insn *
ix86_md_asm_adjust (vec<rtx> &outputs, vec<rtx> &/*inputs*/,
		    vec<const char *> &constraints,
		    vec<rtx> &clobbers, HARD_REG_SET &clobbered_regs)
{
  bool saw_asm_flag = false;

  start_sequence ();
  for (unsigned i = 0, n = outputs.length (); i < n; ++i)
    {
      const char *con = constraints[i];
      if (strncmp (con, "=@cc", 4) != 0)
	continue;
      con += 4;
      if (strchr (con, ',') != NULL)
	{
	  error ("alternatives not allowed in asm flag output");
	  continue;
	}

      bool invert = false;
      if (con[0] == 'n')
	invert = true, con++;

      machine_mode mode = CCmode;
      rtx_code code = UNKNOWN;

      switch (con[0])
	{
	case 'a':
	  if (con[1] == 0)
	    mode = CCAmode, code = EQ;
	  else if (con[1] == 'e' && con[2] == 0)
	    mode = CCCmode, code = NE;
	  break;
	case 'b':
	  if (con[1] == 0)
	    mode = CCCmode, code = EQ;
	  else if (con[1] == 'e' && con[2] == 0)
	    mode = CCAmode, code = NE;
	  break;
	case 'c':
	  if (con[1] == 0)
	    mode = CCCmode, code = EQ;
	  break;
	case 'e':
	  if (con[1] == 0)
	    mode = CCZmode, code = EQ;
	  break;
	case 'g':
	  if (con[1] == 0)
	    mode = CCGCmode, code = GT;
	  else if (con[1] == 'e' && con[2] == 0)
	    mode = CCGCmode, code = GE;
	  break;
	case 'l':
	  if (con[1] == 0)
	    mode = CCGCmode, code = LT;
	  else if (con[1] == 'e' && con[2] == 0)
	    mode = CCGCmode, code = LE;
	  break;
	case 'o':
	  if (con[1] == 0)
	    mode = CCOmode, code = EQ;
	  break;
	case 'p':
	  if (con[1] == 0)
	    mode = CCPmode, code = EQ;
	  break;
	case 's':
	  if (con[1] == 0)
	    mode = CCSmode, code = EQ;
	  break;
	case 'z':
	  if (con[1] == 0)
	    mode = CCZmode, code = EQ;
	  break;
	}
      if (code == UNKNOWN)
	{
	  error ("unknown asm flag output %qs", constraints[i]);
	  continue;
	}
      if (invert)
	code = reverse_condition (code);

      rtx dest = outputs[i];
      if (!saw_asm_flag)
	{
	  /* This is the first asm flag output.  Here we put the flags
	     register in as the real output and adjust the condition to
	     allow it.  */
	  constraints[i] = "=Bf";
	  outputs[i] = gen_rtx_REG (CCmode, FLAGS_REG);
	  saw_asm_flag = true;
	}
      else
	{
	  /* We don't need the flags register as output twice.  */
	  constraints[i] = "=X";
	  outputs[i] = gen_rtx_SCRATCH (SImode);
	}

      rtx x = gen_rtx_REG (mode, FLAGS_REG);
      x = gen_rtx_fmt_ee (code, QImode, x, const0_rtx);

      machine_mode dest_mode = GET_MODE (dest);
      if (!SCALAR_INT_MODE_P (dest_mode))
	{
	  error ("invalid type for asm flag output");
	  continue;
	}

      if (dest_mode == DImode && !TARGET_64BIT)
	dest_mode = SImode;

      if (dest_mode != QImode)
	{
	  rtx destqi = gen_reg_rtx (QImode);
	  emit_insn (gen_rtx_SET (destqi, x));

	  if (TARGET_ZERO_EXTEND_WITH_AND
	      && optimize_function_for_speed_p (cfun))
	    {
	      x = force_reg (dest_mode, const0_rtx);

	      emit_insn (gen_movstrictqi
			 (gen_lowpart (QImode, x), destqi));
	    }
	  else
	    x = gen_rtx_ZERO_EXTEND (dest_mode, destqi);
	}

      if (dest_mode != GET_MODE (dest))
	{
	  rtx tmp = gen_reg_rtx (SImode);

	  emit_insn (gen_rtx_SET (tmp, x));
	  emit_insn (gen_zero_extendsidi2 (dest, tmp));
	}
      else
	emit_insn (gen_rtx_SET (dest, x));
    }
  rtx_insn *seq = get_insns ();
  end_sequence ();

  if (saw_asm_flag)
    return seq;
  else
    {
      /* If we had no asm flag outputs, clobber the flags.  */
      clobbers.safe_push (gen_rtx_REG (CCmode, FLAGS_REG));
      SET_HARD_REG_BIT (clobbered_regs, FLAGS_REG);
      return NULL;
    }
}

/* Implements target vector targetm.asm.encode_section_info.  */

static void ATTRIBUTE_UNUSED
ix86_encode_section_info (tree decl, rtx rtl, int first)
{
  default_encode_section_info (decl, rtl, first);

  if (ix86_in_large_data_p (decl))
    SYMBOL_REF_FLAGS (XEXP (rtl, 0)) |= SYMBOL_FLAG_FAR_ADDR;
}

/* Worker function for REVERSE_CONDITION.  */

enum rtx_code
ix86_reverse_condition (enum rtx_code code, machine_mode mode)
{
  return (mode == CCFPmode
	  ? reverse_condition_maybe_unordered (code)
	  : reverse_condition (code));
}

/* Output code to perform an x87 FP register move, from OPERANDS[1]
   to OPERANDS[0].  */

const char *
output_387_reg_move (rtx_insn *insn, rtx *operands)
{
  if (REG_P (operands[0]))
    {
      if (REG_P (operands[1])
	  && find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
	{
	  if (REGNO (operands[0]) == FIRST_STACK_REG)
	    return output_387_ffreep (operands, 0);
	  return "fstp\t%y0";
	}
      if (STACK_TOP_P (operands[0]))
	return "fld%Z1\t%y1";
      return "fst\t%y0";
    }
  else if (MEM_P (operands[0]))
    {
      gcc_assert (REG_P (operands[1]));
      if (find_regno_note (insn, REG_DEAD, REGNO (operands[1])))
	return "fstp%Z0\t%y0";
      else
	{
	  /* There is no non-popping store to memory for XFmode.
	     So if we need one, follow the store with a load.  */
	  if (GET_MODE (operands[0]) == XFmode)
	    return "fstp%Z0\t%y0\n\tfld%Z0\t%y0";
	  else
	    return "fst%Z0\t%y0";
	}
    }
  else
    gcc_unreachable();
}

/* Output code to perform a conditional jump to LABEL, if C2 flag in
   FP status register is set.  */

void
ix86_emit_fp_unordered_jump (rtx label)
{
  rtx reg = gen_reg_rtx (HImode);
  rtx_insn *insn;
  rtx temp;

  emit_insn (gen_x86_fnstsw_1 (reg));

  if (TARGET_SAHF && (TARGET_USE_SAHF || optimize_insn_for_size_p ()))
    {
      emit_insn (gen_x86_sahf_1 (reg));

      temp = gen_rtx_REG (CCmode, FLAGS_REG);
      temp = gen_rtx_UNORDERED (VOIDmode, temp, const0_rtx);
    }
  else
    {
      emit_insn (gen_testqi_ext_1_ccno (reg, GEN_INT (0x04)));

      temp = gen_rtx_REG (CCNOmode, FLAGS_REG);
      temp = gen_rtx_NE (VOIDmode, temp, const0_rtx);
    }

  temp = gen_rtx_IF_THEN_ELSE (VOIDmode, temp,
			      gen_rtx_LABEL_REF (VOIDmode, label),
			      pc_rtx);
  insn = emit_jump_insn (gen_rtx_SET (pc_rtx, temp));
  predict_jump (REG_BR_PROB_BASE * 10 / 100);
  JUMP_LABEL (insn) = label;
}

/* Output code to perform an sinh XFmode calculation.  */

void ix86_emit_i387_sinh (rtx op0, rtx op1)
{
  rtx e1 = gen_reg_rtx (XFmode);
  rtx e2 = gen_reg_rtx (XFmode);
  rtx scratch = gen_reg_rtx (HImode);
  rtx flags = gen_rtx_REG (CCNOmode, FLAGS_REG);
  rtx half = const_double_from_real_value (dconsthalf, XFmode);
  rtx cst1, tmp;
  rtx_code_label *jump_label = gen_label_rtx ();
  rtx_insn *insn;

  /* scratch = fxam (op1) */
  emit_insn (gen_fxamxf2_i387 (scratch, op1));

  /* e1 = expm1 (|op1|) */
  emit_insn (gen_absxf2 (e2, op1));
  emit_insn (gen_expm1xf2 (e1, e2));

  /* e2 = e1 / (e1 + 1.0) + e1 */
  cst1 = force_reg (XFmode, CONST1_RTX (XFmode));
  emit_insn (gen_addxf3 (e2, e1, cst1));
  emit_insn (gen_divxf3 (e2, e1, e2));
  emit_insn (gen_addxf3 (e2, e2, e1));

  /* flags = signbit (op1) */
  emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x02)));

  /* if (flags) then e2 = -e2 */
  tmp = gen_rtx_IF_THEN_ELSE (VOIDmode,
			      gen_rtx_EQ (VOIDmode, flags, const0_rtx),
			      gen_rtx_LABEL_REF (VOIDmode, jump_label),
			      pc_rtx);
  insn = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
  predict_jump (REG_BR_PROB_BASE * 50 / 100);
  JUMP_LABEL (insn) = jump_label;

  emit_insn (gen_negxf2 (e2, e2));

  emit_label (jump_label);
  LABEL_NUSES (jump_label) = 1;

  /* op0 = 0.5 * e2 */
  half = force_reg (XFmode, half);
  emit_insn (gen_mulxf3 (op0, e2, half));
}

/* Output code to perform an cosh XFmode calculation.  */

void ix86_emit_i387_cosh (rtx op0, rtx op1)
{
  rtx e1 = gen_reg_rtx (XFmode);
  rtx e2 = gen_reg_rtx (XFmode);
  rtx half = const_double_from_real_value (dconsthalf, XFmode);
  rtx cst1;

  /* e1 = exp (op1) */
  emit_insn (gen_expxf2 (e1, op1));

  /* e2 = e1 + 1.0 / e1 */
  cst1 = force_reg (XFmode, CONST1_RTX (XFmode));
  emit_insn (gen_divxf3 (e2, cst1, e1));
  emit_insn (gen_addxf3 (e2, e1, e2));

  /* op0 = 0.5 * e2 */
  half = force_reg (XFmode, half);
  emit_insn (gen_mulxf3 (op0, e2, half));
}

/* Output code to perform an tanh XFmode calculation.  */

void ix86_emit_i387_tanh (rtx op0, rtx op1)
{
  rtx e1 = gen_reg_rtx (XFmode);
  rtx e2 = gen_reg_rtx (XFmode);
  rtx scratch = gen_reg_rtx (HImode);
  rtx flags = gen_rtx_REG (CCNOmode, FLAGS_REG);
  rtx cst2, tmp;
  rtx_code_label *jump_label = gen_label_rtx ();
  rtx_insn *insn;

  /* scratch = fxam (op1) */
  emit_insn (gen_fxamxf2_i387 (scratch, op1));

  /* e1 = expm1 (-|2 * op1|) */
  emit_insn (gen_addxf3 (e2, op1, op1));
  emit_insn (gen_absxf2 (e2, e2));
  emit_insn (gen_negxf2 (e2, e2));
  emit_insn (gen_expm1xf2 (e1, e2));

  /* e2 = e1 / (e1 + 2.0) */
  cst2 = force_reg (XFmode, CONST2_RTX (XFmode));
  emit_insn (gen_addxf3 (e2, e1, cst2));
  emit_insn (gen_divxf3 (e2, e1, e2));

  /* flags = signbit (op1) */
  emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x02)));

  /* if (!flags) then e2 = -e2 */
  tmp = gen_rtx_IF_THEN_ELSE (VOIDmode,
			      gen_rtx_NE (VOIDmode, flags, const0_rtx),
			      gen_rtx_LABEL_REF (VOIDmode, jump_label),
			      pc_rtx);
  insn = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
  predict_jump (REG_BR_PROB_BASE * 50 / 100);
  JUMP_LABEL (insn) = jump_label;

  emit_insn (gen_negxf2 (e2, e2));

  emit_label (jump_label);
  LABEL_NUSES (jump_label) = 1;

  emit_move_insn (op0, e2);
}

/* Output code to perform an asinh XFmode calculation.  */

void ix86_emit_i387_asinh (rtx op0, rtx op1)
{
  rtx e1 = gen_reg_rtx (XFmode);
  rtx e2 = gen_reg_rtx (XFmode);
  rtx scratch = gen_reg_rtx (HImode);
  rtx flags = gen_rtx_REG (CCNOmode, FLAGS_REG);
  rtx cst1, tmp;
  rtx_code_label *jump_label = gen_label_rtx ();
  rtx_insn *insn;

  /* e2 = sqrt (op1^2 + 1.0) + 1.0 */
  emit_insn (gen_mulxf3 (e1, op1, op1));
  cst1 = force_reg (XFmode, CONST1_RTX (XFmode));
  emit_insn (gen_addxf3 (e2, e1, cst1));
  emit_insn (gen_sqrtxf2 (e2, e2));
  emit_insn (gen_addxf3 (e2, e2, cst1));

  /* e1 = e1 / e2 */
  emit_insn (gen_divxf3 (e1, e1, e2));

  /* scratch = fxam (op1) */
  emit_insn (gen_fxamxf2_i387 (scratch, op1));

  /* e1 = e1 + |op1| */
  emit_insn (gen_absxf2 (e2, op1));
  emit_insn (gen_addxf3 (e1, e1, e2));

  /* e2 = log1p (e1) */
  ix86_emit_i387_log1p (e2, e1);

  /* flags = signbit (op1) */
  emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x02)));

  /* if (flags) then e2 = -e2 */
  tmp = gen_rtx_IF_THEN_ELSE (VOIDmode,
			      gen_rtx_EQ (VOIDmode, flags, const0_rtx),
			      gen_rtx_LABEL_REF (VOIDmode, jump_label),
			      pc_rtx);
  insn = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
  predict_jump (REG_BR_PROB_BASE * 50 / 100);
  JUMP_LABEL (insn) = jump_label;

  emit_insn (gen_negxf2 (e2, e2));

  emit_label (jump_label);
  LABEL_NUSES (jump_label) = 1;

  emit_move_insn (op0, e2);
}

/* Output code to perform an acosh XFmode calculation.  */

void ix86_emit_i387_acosh (rtx op0, rtx op1)
{
  rtx e1 = gen_reg_rtx (XFmode);
  rtx e2 = gen_reg_rtx (XFmode);
  rtx cst1 = force_reg (XFmode, CONST1_RTX (XFmode));

  /* e2 = sqrt (op1 + 1.0) */
  emit_insn (gen_addxf3 (e2, op1, cst1));
  emit_insn (gen_sqrtxf2 (e2, e2));

  /* e1 = sqrt (op1 - 1.0) */
  emit_insn (gen_subxf3 (e1, op1, cst1));
  emit_insn (gen_sqrtxf2 (e1, e1));

  /* e1 = e1 * e2 */
  emit_insn (gen_mulxf3 (e1, e1, e2));

  /* e1 = e1 + op1 */
  emit_insn (gen_addxf3 (e1, e1, op1));

  /* op0 = log (e1) */
  emit_insn (gen_logxf2 (op0, e1));
}

/* Output code to perform an atanh XFmode calculation.  */

void ix86_emit_i387_atanh (rtx op0, rtx op1)
{
  rtx e1 = gen_reg_rtx (XFmode);
  rtx e2 = gen_reg_rtx (XFmode);
  rtx scratch = gen_reg_rtx (HImode);
  rtx flags = gen_rtx_REG (CCNOmode, FLAGS_REG);
  rtx half = const_double_from_real_value (dconsthalf, XFmode);
  rtx cst1, tmp;
  rtx_code_label *jump_label = gen_label_rtx ();
  rtx_insn *insn;

  /* scratch = fxam (op1) */
  emit_insn (gen_fxamxf2_i387 (scratch, op1));

  /* e2 = |op1| */
  emit_insn (gen_absxf2 (e2, op1));

  /* e1 = -(e2 + e2) / (e2 + 1.0) */
  cst1 = force_reg (XFmode, CONST1_RTX (XFmode));
  emit_insn (gen_addxf3 (e1, e2, cst1));
  emit_insn (gen_addxf3 (e2, e2, e2));
  emit_insn (gen_negxf2 (e2, e2));
  emit_insn (gen_divxf3 (e1, e2, e1));

  /* e2 = log1p (e1) */
  ix86_emit_i387_log1p (e2, e1);

  /* flags = signbit (op1) */
  emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x02)));

  /* if (!flags) then e2 = -e2 */
  tmp = gen_rtx_IF_THEN_ELSE (VOIDmode,
			      gen_rtx_NE (VOIDmode, flags, const0_rtx),
			      gen_rtx_LABEL_REF (VOIDmode, jump_label),
			      pc_rtx);
  insn = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
  predict_jump (REG_BR_PROB_BASE * 50 / 100);
  JUMP_LABEL (insn) = jump_label;

  emit_insn (gen_negxf2 (e2, e2));

  emit_label (jump_label);
  LABEL_NUSES (jump_label) = 1;

  /* op0 = 0.5 * e2 */
  half = force_reg (XFmode, half);
  emit_insn (gen_mulxf3 (op0, e2, half));
}

/* Output code to perform a log1p XFmode calculation.  */

void ix86_emit_i387_log1p (rtx op0, rtx op1)
{
  rtx_code_label *label1 = gen_label_rtx ();
  rtx_code_label *label2 = gen_label_rtx ();

  rtx tmp = gen_reg_rtx (XFmode);
  rtx res = gen_reg_rtx (XFmode);
  rtx cst, cstln2, cst1;
  rtx_insn *insn;

  cst = const_double_from_real_value
    (REAL_VALUE_ATOF ("0.29289321881345247561810596348408353", XFmode), XFmode);
  cstln2 = force_reg (XFmode, standard_80387_constant_rtx (4)); /* fldln2 */

  emit_insn (gen_absxf2 (tmp, op1));

  cst = force_reg (XFmode, cst);
  ix86_expand_branch (GE, tmp, cst, label1);
  predict_jump (REG_BR_PROB_BASE * 10 / 100);
  insn = get_last_insn ();
  JUMP_LABEL (insn) = label1;

  emit_insn (gen_fyl2xp1xf3_i387 (res, op1, cstln2));
  emit_jump (label2);

  emit_label (label1);
  LABEL_NUSES (label1) = 1;

  cst1 = force_reg (XFmode, CONST1_RTX (XFmode));
  emit_insn (gen_rtx_SET (tmp, gen_rtx_PLUS (XFmode, op1, cst1)));
  emit_insn (gen_fyl2xxf3_i387 (res, tmp, cstln2));

  emit_label (label2);
  LABEL_NUSES (label2) = 1;

  emit_move_insn (op0, res);
}

/* Emit code for round calculation.  */
void ix86_emit_i387_round (rtx op0, rtx op1)
{
  machine_mode inmode = GET_MODE (op1);
  machine_mode outmode = GET_MODE (op0);
  rtx e1 = gen_reg_rtx (XFmode);
  rtx e2 = gen_reg_rtx (XFmode);
  rtx scratch = gen_reg_rtx (HImode);
  rtx flags = gen_rtx_REG (CCNOmode, FLAGS_REG);
  rtx half = const_double_from_real_value (dconsthalf, XFmode);
  rtx res = gen_reg_rtx (outmode);
  rtx_code_label *jump_label = gen_label_rtx ();
  rtx (*floor_insn) (rtx, rtx);
  rtx (*neg_insn) (rtx, rtx);
  rtx_insn *insn;
  rtx tmp;

  switch (inmode)
    {
    case E_SFmode:
    case E_DFmode:
      tmp = gen_reg_rtx (XFmode);

      emit_insn (gen_rtx_SET (tmp, gen_rtx_FLOAT_EXTEND (XFmode, op1)));
      op1 = tmp;
      break;
    case E_XFmode:
      break;
    default:
      gcc_unreachable ();
    }

  switch (outmode)
    {
    case E_SFmode:
      floor_insn = gen_frndintxf2_floor;
      neg_insn = gen_negsf2;
      break;
    case E_DFmode:
      floor_insn = gen_frndintxf2_floor;
      neg_insn = gen_negdf2;
      break;
    case E_XFmode:
      floor_insn = gen_frndintxf2_floor;
      neg_insn = gen_negxf2;
      break;
    case E_HImode:
      floor_insn = gen_lfloorxfhi2;
      neg_insn = gen_neghi2;
      break;
    case E_SImode:
      floor_insn = gen_lfloorxfsi2;
      neg_insn = gen_negsi2;
      break;
    case E_DImode:
      floor_insn = gen_lfloorxfdi2;
      neg_insn = gen_negdi2;
      break;
    default:
      gcc_unreachable ();
    }

  /* round(a) = sgn(a) * floor(fabs(a) + 0.5) */

  /* scratch = fxam(op1) */
  emit_insn (gen_fxamxf2_i387 (scratch, op1));

  /* e1 = fabs(op1) */
  emit_insn (gen_absxf2 (e1, op1));

  /* e2 = e1 + 0.5 */
  half = force_reg (XFmode, half);
  emit_insn (gen_rtx_SET (e2, gen_rtx_PLUS (XFmode, e1, half)));

  /* res = floor(e2) */
  switch (outmode)
    {
    case E_SFmode:
    case E_DFmode:
      {
	tmp = gen_reg_rtx (XFmode);

	emit_insn (floor_insn (tmp, e2));
	emit_insn (gen_rtx_SET (res,
				gen_rtx_UNSPEC (outmode, gen_rtvec (1, tmp),
						UNSPEC_TRUNC_NOOP)));
      }
      break;
    default:
      emit_insn (floor_insn (res, e2));
    }

  /* flags = signbit(a) */
  emit_insn (gen_testqi_ext_1_ccno (scratch, GEN_INT (0x02)));

  /* if (flags) then res = -res */
  tmp = gen_rtx_IF_THEN_ELSE (VOIDmode,
			      gen_rtx_EQ (VOIDmode, flags, const0_rtx),
			      gen_rtx_LABEL_REF (VOIDmode, jump_label),
			      pc_rtx);
  insn = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
  predict_jump (REG_BR_PROB_BASE * 50 / 100);
  JUMP_LABEL (insn) = jump_label;

  emit_insn (neg_insn (res, res));

  emit_label (jump_label);
  LABEL_NUSES (jump_label) = 1;

  emit_move_insn (op0, res);
}

/* Output code to perform a Newton-Rhapson approximation of a single precision
   floating point divide [http://en.wikipedia.org/wiki/N-th_root_algorithm].  */

void ix86_emit_swdivsf (rtx res, rtx a, rtx b, machine_mode mode)
{
  rtx x0, x1, e0, e1;

  x0 = gen_reg_rtx (mode);
  e0 = gen_reg_rtx (mode);
  e1 = gen_reg_rtx (mode);
  x1 = gen_reg_rtx (mode);

  /* a / b = a * ((rcp(b) + rcp(b)) - (b * rcp(b) * rcp (b))) */

  b = force_reg (mode, b);

  /* x0 = rcp(b) estimate */
  if (mode == V16SFmode || mode == V8DFmode)
    {
      if (TARGET_AVX512ER)
	{
	  emit_insn (gen_rtx_SET (x0, gen_rtx_UNSPEC (mode, gen_rtvec (1, b),
						      UNSPEC_RCP28)));
	  /* res = a * x0 */
	  emit_insn (gen_rtx_SET (res, gen_rtx_MULT (mode, a, x0)));
	  return;
	}
      else
	emit_insn (gen_rtx_SET (x0, gen_rtx_UNSPEC (mode, gen_rtvec (1, b),
						    UNSPEC_RCP14)));
    }
  else
    emit_insn (gen_rtx_SET (x0, gen_rtx_UNSPEC (mode, gen_rtvec (1, b),
						UNSPEC_RCP)));

  /* e0 = x0 * b */
  emit_insn (gen_rtx_SET (e0, gen_rtx_MULT (mode, x0, b)));

  /* e0 = x0 * e0 */
  emit_insn (gen_rtx_SET (e0, gen_rtx_MULT (mode, x0, e0)));

  /* e1 = x0 + x0 */
  emit_insn (gen_rtx_SET (e1, gen_rtx_PLUS (mode, x0, x0)));

  /* x1 = e1 - e0 */
  emit_insn (gen_rtx_SET (x1, gen_rtx_MINUS (mode, e1, e0)));

  /* res = a * x1 */
  emit_insn (gen_rtx_SET (res, gen_rtx_MULT (mode, a, x1)));
}

/* Output code to perform a Newton-Rhapson approximation of a
   single precision floating point [reciprocal] square root.  */

void ix86_emit_swsqrtsf (rtx res, rtx a, machine_mode mode, bool recip)
{
  rtx x0, e0, e1, e2, e3, mthree, mhalf;
  REAL_VALUE_TYPE r;
  int unspec;

  x0 = gen_reg_rtx (mode);
  e0 = gen_reg_rtx (mode);
  e1 = gen_reg_rtx (mode);
  e2 = gen_reg_rtx (mode);
  e3 = gen_reg_rtx (mode);

  if (TARGET_AVX512ER && mode == V16SFmode)
    {
      if (recip)
	/* res = rsqrt28(a) estimate */
	emit_insn (gen_rtx_SET (res, gen_rtx_UNSPEC (mode, gen_rtvec (1, a),
						     UNSPEC_RSQRT28)));
      else
	{
	  /* x0 = rsqrt28(a) estimate */
	  emit_insn (gen_rtx_SET (x0, gen_rtx_UNSPEC (mode, gen_rtvec (1, a),
						      UNSPEC_RSQRT28)));
	  /* res = rcp28(x0) estimate */
	  emit_insn (gen_rtx_SET (res, gen_rtx_UNSPEC (mode, gen_rtvec (1, x0),
						       UNSPEC_RCP28)));
	}
      return;
    }

  real_from_integer (&r, VOIDmode, -3, SIGNED);
  mthree = const_double_from_real_value (r, SFmode);

  real_arithmetic (&r, NEGATE_EXPR, &dconsthalf, NULL);
  mhalf = const_double_from_real_value (r, SFmode);
  unspec = UNSPEC_RSQRT;

  if (VECTOR_MODE_P (mode))
    {
      mthree = ix86_build_const_vector (mode, true, mthree);
      mhalf = ix86_build_const_vector (mode, true, mhalf);
      /* There is no 512-bit rsqrt.  There is however rsqrt14.  */
      if (GET_MODE_SIZE (mode) == 64)
	unspec = UNSPEC_RSQRT14;
    }

  /* sqrt(a)  = -0.5 * a * rsqrtss(a) * (a * rsqrtss(a) * rsqrtss(a) - 3.0)
     rsqrt(a) = -0.5     * rsqrtss(a) * (a * rsqrtss(a) * rsqrtss(a) - 3.0) */

  a = force_reg (mode, a);

  /* x0 = rsqrt(a) estimate */
  emit_insn (gen_rtx_SET (x0, gen_rtx_UNSPEC (mode, gen_rtvec (1, a),
					      unspec)));

  /* If (a == 0.0) Filter out infinity to prevent NaN for sqrt(0.0).  */
  if (!recip)
    {
      rtx zero = force_reg (mode, CONST0_RTX(mode));
      rtx mask;

      /* Handle masked compare.  */
      if (VECTOR_MODE_P (mode) && GET_MODE_SIZE (mode) == 64)
	{
	  mask = gen_reg_rtx (HImode);
	  /* Imm value 0x4 corresponds to not-equal comparison.  */
	  emit_insn (gen_avx512f_cmpv16sf3 (mask, zero, a, GEN_INT (0x4)));
	  emit_insn (gen_avx512f_blendmv16sf (x0, zero, x0, mask));
	}
      else
	{
	  mask = gen_reg_rtx (mode);
	  emit_insn (gen_rtx_SET (mask, gen_rtx_NE (mode, zero, a)));
	  emit_insn (gen_rtx_SET (x0, gen_rtx_AND (mode, x0, mask)));
	}
    }

  /* e0 = x0 * a */
  emit_insn (gen_rtx_SET (e0, gen_rtx_MULT (mode, x0, a)));
  /* e1 = e0 * x0 */
  emit_insn (gen_rtx_SET (e1, gen_rtx_MULT (mode, e0, x0)));

  /* e2 = e1 - 3. */
  mthree = force_reg (mode, mthree);
  emit_insn (gen_rtx_SET (e2, gen_rtx_PLUS (mode, e1, mthree)));

  mhalf = force_reg (mode, mhalf);
  if (recip)
    /* e3 = -.5 * x0 */
    emit_insn (gen_rtx_SET (e3, gen_rtx_MULT (mode, x0, mhalf)));
  else
    /* e3 = -.5 * e0 */
    emit_insn (gen_rtx_SET (e3, gen_rtx_MULT (mode, e0, mhalf)));
  /* ret = e2 * e3 */
  emit_insn (gen_rtx_SET (res, gen_rtx_MULT (mode, e2, e3)));
}

#ifdef TARGET_SOLARIS
/* Solaris implementation of TARGET_ASM_NAMED_SECTION.  */

static void
i386_solaris_elf_named_section (const char *name, unsigned int flags,
				tree decl)
{
  /* With Binutils 2.15, the "@unwind" marker must be specified on
     every occurrence of the ".eh_frame" section, not just the first
     one.  */
  if (TARGET_64BIT
      && strcmp (name, ".eh_frame") == 0)
    {
      fprintf (asm_out_file, "\t.section\t%s,\"%s\",@unwind\n", name,
	       flags & SECTION_WRITE ? "aw" : "a");
      return;
    }

#ifndef USE_GAS
  if (HAVE_COMDAT_GROUP && flags & SECTION_LINKONCE)
    {
      solaris_elf_asm_comdat_section (name, flags, decl);
      return;
    }

  /* Solaris/x86 as uses the same syntax for the SHF_EXCLUDE flags as the
     SPARC assembler.  One cannot mix single-letter flags and #exclude, so
     only emit the latter here.  */
  if (flags & SECTION_EXCLUDE)
    {
      fprintf (asm_out_file, "\t.section\t%s,#exclude\n", name);
      return;
    }
#endif

  default_elf_asm_named_section (name, flags, decl);
}
#endif /* TARGET_SOLARIS */

/* Return the mangling of TYPE if it is an extended fundamental type.  */

static const char *
ix86_mangle_type (const_tree type)
{
  type = TYPE_MAIN_VARIANT (type);

  if (TREE_CODE (type) != VOID_TYPE && TREE_CODE (type) != BOOLEAN_TYPE
      && TREE_CODE (type) != INTEGER_TYPE && TREE_CODE (type) != REAL_TYPE)
    return NULL;

  switch (TYPE_MODE (type))
    {
    case E_TFmode:
      /* __float128 is "g".  */
      return "g";
    case E_XFmode:
      /* "long double" or __float80 is "e".  */
      return "e";
    default:
      return NULL;
    }
}

static GTY(()) tree ix86_tls_stack_chk_guard_decl;

static tree
ix86_stack_protect_guard (void)
{
  if (TARGET_SSP_TLS_GUARD)
    {
      tree type_node = lang_hooks.types.type_for_mode (ptr_mode, 1);
      int qual = ENCODE_QUAL_ADDR_SPACE (ix86_stack_protector_guard_reg);
      tree type = build_qualified_type (type_node, qual);
      tree t;

      if (global_options_set.x_ix86_stack_protector_guard_symbol_str)
	{
	  t = ix86_tls_stack_chk_guard_decl;

	  if (t == NULL)
	    {
	      rtx x;

	      t = build_decl
		(UNKNOWN_LOCATION, VAR_DECL,
		 get_identifier (ix86_stack_protector_guard_symbol_str),
		 type);
	      TREE_STATIC (t) = 1;
	      TREE_PUBLIC (t) = 1;
	      DECL_EXTERNAL (t) = 1;
	      TREE_USED (t) = 1;
	      TREE_THIS_VOLATILE (t) = 1;
	      DECL_ARTIFICIAL (t) = 1;
	      DECL_IGNORED_P (t) = 1;

	      /* Do not share RTL as the declaration is visible outside of
		 current function.  */
	      x = DECL_RTL (t);
	      RTX_FLAG (x, used) = 1;

	      ix86_tls_stack_chk_guard_decl = t;
	    }
	}
      else
	{
	  tree asptrtype = build_pointer_type (type);

	  t = build_int_cst (asptrtype, ix86_stack_protector_guard_offset);
	  t = build2 (MEM_REF, asptrtype, t,
		      build_int_cst (asptrtype, 0));
	  TREE_THIS_VOLATILE (t) = 1;
	}

      return t;
    }

  return default_stack_protect_guard ();
}

/* For 32-bit code we can save PIC register setup by using
   __stack_chk_fail_local hidden function instead of calling
   __stack_chk_fail directly.  64-bit code doesn't need to setup any PIC
   register, so it is better to call __stack_chk_fail directly.  */

static tree ATTRIBUTE_UNUSED
ix86_stack_protect_fail (void)
{
  return TARGET_64BIT
	 ? default_external_stack_protect_fail ()
	 : default_hidden_stack_protect_fail ();
}

/* Select a format to encode pointers in exception handling data.  CODE
   is 0 for data, 1 for code labels, 2 for function pointers.  GLOBAL is
   true if the symbol may be affected by dynamic relocations.

   ??? All x86 object file formats are capable of representing this.
   After all, the relocation needed is the same as for the call insn.
   Whether or not a particular assembler allows us to enter such, I
   guess we'll have to see.  */
int
asm_preferred_eh_data_format (int code, int global)
{
  if (flag_pic)
    {
      int type = DW_EH_PE_sdata8;
      if (!TARGET_64BIT
	  || ix86_cmodel == CM_SMALL_PIC
	  || (ix86_cmodel == CM_MEDIUM_PIC && (global || code)))
	type = DW_EH_PE_sdata4;
      return (global ? DW_EH_PE_indirect : 0) | DW_EH_PE_pcrel | type;
    }
  if (ix86_cmodel == CM_SMALL
      || (ix86_cmodel == CM_MEDIUM && code))
    return DW_EH_PE_udata4;
  return DW_EH_PE_absptr;
}

/* Expand copysign from SIGN to the positive value ABS_VALUE
   storing in RESULT.  If MASK is non-null, it shall be a mask to mask out
   the sign-bit.  */
static void
ix86_sse_copysign_to_positive (rtx result, rtx abs_value, rtx sign, rtx mask)
{
  machine_mode mode = GET_MODE (sign);
  rtx sgn = gen_reg_rtx (mode);
  if (mask == NULL_RTX)
    {
      machine_mode vmode;

      if (mode == SFmode)
	vmode = V4SFmode;
      else if (mode == DFmode)
	vmode = V2DFmode;
      else
	vmode = mode;

      mask = ix86_build_signbit_mask (vmode, VECTOR_MODE_P (mode), false);
      if (!VECTOR_MODE_P (mode))
	{
	  /* We need to generate a scalar mode mask in this case.  */
	  rtx tmp = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (1, const0_rtx));
	  tmp = gen_rtx_VEC_SELECT (mode, mask, tmp);
	  mask = gen_reg_rtx (mode);
	  emit_insn (gen_rtx_SET (mask, tmp));
	}
    }
  else
    mask = gen_rtx_NOT (mode, mask);
  emit_insn (gen_rtx_SET (sgn, gen_rtx_AND (mode, mask, sign)));
  emit_insn (gen_rtx_SET (result, gen_rtx_IOR (mode, abs_value, sgn)));
}

/* Expand fabs (OP0) and return a new rtx that holds the result.  The
   mask for masking out the sign-bit is stored in *SMASK, if that is
   non-null.  */
static rtx
ix86_expand_sse_fabs (rtx op0, rtx *smask)
{
  machine_mode vmode, mode = GET_MODE (op0);
  rtx xa, mask;

  xa = gen_reg_rtx (mode);
  if (mode == SFmode)
    vmode = V4SFmode;
  else if (mode == DFmode)
    vmode = V2DFmode;
  else
    vmode = mode;
  mask = ix86_build_signbit_mask (vmode, VECTOR_MODE_P (mode), true);
  if (!VECTOR_MODE_P (mode))
    {
      /* We need to generate a scalar mode mask in this case.  */
      rtx tmp = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (1, const0_rtx));
      tmp = gen_rtx_VEC_SELECT (mode, mask, tmp);
      mask = gen_reg_rtx (mode);
      emit_insn (gen_rtx_SET (mask, tmp));
    }
  emit_insn (gen_rtx_SET (xa, gen_rtx_AND (mode, op0, mask)));

  if (smask)
    *smask = mask;

  return xa;
}

/* Expands a comparison of OP0 with OP1 using comparison code CODE,
   swapping the operands if SWAP_OPERANDS is true.  The expanded
   code is a forward jump to a newly created label in case the
   comparison is true.  The generated label rtx is returned.  */
static rtx_code_label *
ix86_expand_sse_compare_and_jump (enum rtx_code code, rtx op0, rtx op1,
                                  bool swap_operands)
{
  bool unordered_compare = ix86_unordered_fp_compare (code);
  rtx_code_label *label;
  rtx tmp, reg;

  if (swap_operands)
    std::swap (op0, op1);

  label = gen_label_rtx ();
  tmp = gen_rtx_COMPARE (CCFPmode, op0, op1);
  if (unordered_compare)
    tmp = gen_rtx_UNSPEC (CCFPmode, gen_rtvec (1, tmp), UNSPEC_NOTRAP);
  reg = gen_rtx_REG (CCFPmode, FLAGS_REG);
  emit_insn (gen_rtx_SET (reg, tmp));
  tmp = gen_rtx_fmt_ee (code, VOIDmode, reg, const0_rtx);
  tmp = gen_rtx_IF_THEN_ELSE (VOIDmode, tmp,
			      gen_rtx_LABEL_REF (VOIDmode, label), pc_rtx);
  tmp = emit_jump_insn (gen_rtx_SET (pc_rtx, tmp));
  JUMP_LABEL (tmp) = label;

  return label;
}

/* Expand a mask generating SSE comparison instruction comparing OP0 with OP1
   using comparison code CODE.  Operands are swapped for the comparison if
   SWAP_OPERANDS is true.  Returns a rtx for the generated mask.  */
static rtx
ix86_expand_sse_compare_mask (enum rtx_code code, rtx op0, rtx op1,
			      bool swap_operands)
{
  rtx (*insn)(rtx, rtx, rtx, rtx);
  machine_mode mode = GET_MODE (op0);
  rtx mask = gen_reg_rtx (mode);

  if (swap_operands)
    std::swap (op0, op1);

  insn = mode == DFmode ? gen_setcc_df_sse : gen_setcc_sf_sse;

  emit_insn (insn (mask, op0, op1,
		   gen_rtx_fmt_ee (code, mode, op0, op1)));
  return mask;
}

/* Generate and return a rtx of mode MODE for 2**n where n is the number
   of bits of the mantissa of MODE, which must be one of DFmode or SFmode.  */
static rtx
ix86_gen_TWO52 (machine_mode mode)
{
  REAL_VALUE_TYPE TWO52r;
  rtx TWO52;

  real_ldexp (&TWO52r, &dconst1, mode == DFmode ? 52 : 23);
  TWO52 = const_double_from_real_value (TWO52r, mode);
  TWO52 = force_reg (mode, TWO52);

  return TWO52;
}

/* Expand SSE sequence for computing lround from OP1 storing
   into OP0.  */
void
ix86_expand_lround (rtx op0, rtx op1)
{
  /* C code for the stuff we're doing below:
       tmp = op1 + copysign (nextafter (0.5, 0.0), op1)
       return (long)tmp;
   */
  machine_mode mode = GET_MODE (op1);
  const struct real_format *fmt;
  REAL_VALUE_TYPE pred_half, half_minus_pred_half;
  rtx adj;

  /* load nextafter (0.5, 0.0) */
  fmt = REAL_MODE_FORMAT (mode);
  real_2expN (&half_minus_pred_half, -(fmt->p) - 1, mode);
  real_arithmetic (&pred_half, MINUS_EXPR, &dconsthalf, &half_minus_pred_half);

  /* adj = copysign (0.5, op1) */
  adj = force_reg (mode, const_double_from_real_value (pred_half, mode));
  ix86_sse_copysign_to_positive (adj, adj, force_reg (mode, op1), NULL_RTX);

  /* adj = op1 + adj */
  adj = expand_simple_binop (mode, PLUS, adj, op1, NULL_RTX, 0, OPTAB_DIRECT);

  /* op0 = (imode)adj */
  expand_fix (op0, adj, 0);
}

/* Expand SSE2 sequence for computing lround from OPERAND1 storing
   into OPERAND0.  */
void
ix86_expand_lfloorceil (rtx op0, rtx op1, bool do_floor)
{
  /* C code for the stuff we're doing below (for do_floor):
	xi = (long)op1;
        xi -= (double)xi > op1 ? 1 : 0;
        return xi;
   */
  machine_mode fmode = GET_MODE (op1);
  machine_mode imode = GET_MODE (op0);
  rtx ireg, freg, tmp;
  rtx_code_label *label;

  /* reg = (long)op1 */
  ireg = gen_reg_rtx (imode);
  expand_fix (ireg, op1, 0);

  /* freg = (double)reg */
  freg = gen_reg_rtx (fmode);
  expand_float (freg, ireg, 0);

  /* ireg = (freg > op1) ? ireg - 1 : ireg */
  label = ix86_expand_sse_compare_and_jump (UNLE,
					    freg, op1, !do_floor);
  tmp = expand_simple_binop (imode, do_floor ? MINUS : PLUS,
			     ireg, const1_rtx, NULL_RTX, 0, OPTAB_DIRECT);
  emit_move_insn (ireg, tmp);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (op0, ireg);
}

/* Expand rint rounding OPERAND1 and storing the result in OPERAND0.  */
void
ix86_expand_rint (rtx operand0, rtx operand1)
{
  /* C code for the stuff we're doing below:
	xa = fabs (operand1);
        if (!isless (xa, 2**52))
	  return operand1;
        two52 = 2**52;
        if (flag_rounding_math)
	  {
	    two52 = copysign (two52, operand1);
	    xa = operand1;
	  }
        xa = xa + two52 - two52;
        return copysign (xa, operand1);
   */
  machine_mode mode = GET_MODE (operand0);
  rtx res, xa, TWO52, two52, mask;
  rtx_code_label *label;

  res = gen_reg_rtx (mode);
  emit_move_insn (res, operand1);

  /* xa = abs (operand1) */
  xa = ix86_expand_sse_fabs (res, &mask);

  /* if (!isless (xa, TWO52)) goto label; */
  TWO52 = ix86_gen_TWO52 (mode);
  label = ix86_expand_sse_compare_and_jump (UNLE, TWO52, xa, false);

  two52 = TWO52;
  if (flag_rounding_math)
    {
      two52 = gen_reg_rtx (mode);
      ix86_sse_copysign_to_positive (two52, TWO52, res, mask);
      xa = res;
    }

  xa = expand_simple_binop (mode, PLUS, xa, two52, NULL_RTX, 0, OPTAB_DIRECT);
  xa = expand_simple_binop (mode, MINUS, xa, two52, xa, 0, OPTAB_DIRECT);

  ix86_sse_copysign_to_positive (res, xa, res, mask);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (operand0, res);
}

/* Expand SSE2 sequence for computing floor or ceil from OPERAND1 storing
   into OPERAND0.  */
void
ix86_expand_floorceildf_32 (rtx operand0, rtx operand1, bool do_floor)
{
  /* C code for the stuff we expand below.
        double xa = fabs (x), x2;
        if (!isless (xa, TWO52))
          return x;
        xa = xa + TWO52 - TWO52;
        x2 = copysign (xa, x);
     Compensate.  Floor:
        if (x2 > x)
          x2 -= 1;
     Compensate.  Ceil:
        if (x2 < x)
          x2 -= -1;
        return x2;
   */
  machine_mode mode = GET_MODE (operand0);
  rtx xa, TWO52, tmp, one, res, mask;
  rtx_code_label *label;

  TWO52 = ix86_gen_TWO52 (mode);

  /* Temporary for holding the result, initialized to the input
     operand to ease control flow.  */
  res = gen_reg_rtx (mode);
  emit_move_insn (res, operand1);

  /* xa = abs (operand1) */
  xa = ix86_expand_sse_fabs (res, &mask);

  /* if (!isless (xa, TWO52)) goto label; */
  label = ix86_expand_sse_compare_and_jump (UNLE, TWO52, xa, false);

  /* xa = xa + TWO52 - TWO52; */
  xa = expand_simple_binop (mode, PLUS, xa, TWO52, NULL_RTX, 0, OPTAB_DIRECT);
  xa = expand_simple_binop (mode, MINUS, xa, TWO52, xa, 0, OPTAB_DIRECT);

  /* xa = copysign (xa, operand1) */
  ix86_sse_copysign_to_positive (xa, xa, res, mask);

  /* generate 1.0 or -1.0 */
  one = force_reg (mode,
	           const_double_from_real_value (do_floor
						 ? dconst1 : dconstm1, mode));

  /* Compensate: xa = xa - (xa > operand1 ? 1 : 0) */
  tmp = ix86_expand_sse_compare_mask (UNGT, xa, res, !do_floor);
  emit_insn (gen_rtx_SET (tmp, gen_rtx_AND (mode, one, tmp)));
  /* We always need to subtract here to preserve signed zero.  */
  tmp = expand_simple_binop (mode, MINUS,
			     xa, tmp, NULL_RTX, 0, OPTAB_DIRECT);
  emit_move_insn (res, tmp);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (operand0, res);
}

/* Expand SSE2 sequence for computing floor or ceil from OPERAND1 storing
   into OPERAND0.  */
void
ix86_expand_floorceil (rtx operand0, rtx operand1, bool do_floor)
{
  /* C code for the stuff we expand below.
	double xa = fabs (x), x2;
        if (!isless (xa, TWO52))
          return x;
	x2 = (double)(long)x;
     Compensate.  Floor:
	if (x2 > x)
	  x2 -= 1;
     Compensate.  Ceil:
	if (x2 < x)
	  x2 += 1;
	if (HONOR_SIGNED_ZEROS (mode))
	  return copysign (x2, x);
	return x2;
   */
  machine_mode mode = GET_MODE (operand0);
  rtx xa, xi, TWO52, tmp, one, res, mask;
  rtx_code_label *label;

  TWO52 = ix86_gen_TWO52 (mode);

  /* Temporary for holding the result, initialized to the input
     operand to ease control flow.  */
  res = gen_reg_rtx (mode);
  emit_move_insn (res, operand1);

  /* xa = abs (operand1) */
  xa = ix86_expand_sse_fabs (res, &mask);

  /* if (!isless (xa, TWO52)) goto label; */
  label = ix86_expand_sse_compare_and_jump (UNLE, TWO52, xa, false);

  /* xa = (double)(long)x */
  xi = gen_reg_rtx (mode == DFmode ? DImode : SImode);
  expand_fix (xi, res, 0);
  expand_float (xa, xi, 0);

  /* generate 1.0 */
  one = force_reg (mode, const_double_from_real_value (dconst1, mode));

  /* Compensate: xa = xa - (xa > operand1 ? 1 : 0) */
  tmp = ix86_expand_sse_compare_mask (UNGT, xa, res, !do_floor);
  emit_insn (gen_rtx_SET (tmp, gen_rtx_AND (mode, one, tmp)));
  tmp = expand_simple_binop (mode, do_floor ? MINUS : PLUS,
			     xa, tmp, NULL_RTX, 0, OPTAB_DIRECT);
  emit_move_insn (res, tmp);

  if (HONOR_SIGNED_ZEROS (mode))
    ix86_sse_copysign_to_positive (res, res, force_reg (mode, operand1), mask);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (operand0, res);
}

/* Expand SSE sequence for computing round from OPERAND1 storing
   into OPERAND0.  Sequence that works without relying on DImode truncation
   via cvttsd2siq that is only available on 64bit targets.  */
void
ix86_expand_rounddf_32 (rtx operand0, rtx operand1)
{
  /* C code for the stuff we expand below.
        double xa = fabs (x), xa2, x2;
        if (!isless (xa, TWO52))
          return x;
     Using the absolute value and copying back sign makes
     -0.0 -> -0.0 correct.
        xa2 = xa + TWO52 - TWO52;
     Compensate.
	dxa = xa2 - xa;
        if (dxa <= -0.5)
          xa2 += 1;
        else if (dxa > 0.5)
          xa2 -= 1;
        x2 = copysign (xa2, x);
        return x2;
   */
  machine_mode mode = GET_MODE (operand0);
  rtx xa, xa2, dxa, TWO52, tmp, half, mhalf, one, res, mask;
  rtx_code_label *label;

  TWO52 = ix86_gen_TWO52 (mode);

  /* Temporary for holding the result, initialized to the input
     operand to ease control flow.  */
  res = gen_reg_rtx (mode);
  emit_move_insn (res, operand1);

  /* xa = abs (operand1) */
  xa = ix86_expand_sse_fabs (res, &mask);

  /* if (!isless (xa, TWO52)) goto label; */
  label = ix86_expand_sse_compare_and_jump (UNLE, TWO52, xa, false);

  /* xa2 = xa + TWO52 - TWO52; */
  xa2 = expand_simple_binop (mode, PLUS, xa, TWO52, NULL_RTX, 0, OPTAB_DIRECT);
  xa2 = expand_simple_binop (mode, MINUS, xa2, TWO52, xa2, 0, OPTAB_DIRECT);

  /* dxa = xa2 - xa; */
  dxa = expand_simple_binop (mode, MINUS, xa2, xa, NULL_RTX, 0, OPTAB_DIRECT);

  /* generate 0.5, 1.0 and -0.5 */
  half = force_reg (mode, const_double_from_real_value (dconsthalf, mode));
  one = expand_simple_binop (mode, PLUS, half, half, NULL_RTX, 0, OPTAB_DIRECT);
  mhalf = expand_simple_binop (mode, MINUS, half, one, NULL_RTX,
			       0, OPTAB_DIRECT);

  /* Compensate.  */
  tmp = gen_reg_rtx (mode);
  /* xa2 = xa2 - (dxa > 0.5 ? 1 : 0) */
  tmp = ix86_expand_sse_compare_mask (UNGT, dxa, half, false);
  emit_insn (gen_rtx_SET (tmp, gen_rtx_AND (mode, one, tmp)));
  xa2 = expand_simple_binop (mode, MINUS, xa2, tmp, NULL_RTX, 0, OPTAB_DIRECT);
  /* xa2 = xa2 + (dxa <= -0.5 ? 1 : 0) */
  tmp = ix86_expand_sse_compare_mask (UNGE, mhalf, dxa, false);
  emit_insn (gen_rtx_SET (tmp, gen_rtx_AND (mode, one, tmp)));
  xa2 = expand_simple_binop (mode, PLUS, xa2, tmp, NULL_RTX, 0, OPTAB_DIRECT);

  /* res = copysign (xa2, operand1) */
  ix86_sse_copysign_to_positive (res, xa2, force_reg (mode, operand1), mask);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (operand0, res);
}

/* Expand SSE sequence for computing trunc from OPERAND1 storing
   into OPERAND0.  */
void
ix86_expand_trunc (rtx operand0, rtx operand1)
{
  /* C code for SSE variant we expand below.
        double xa = fabs (x), x2;
        if (!isless (xa, TWO52))
          return x;
        x2 = (double)(long)x;
	if (HONOR_SIGNED_ZEROS (mode))
	  return copysign (x2, x);
	return x2;
   */
  machine_mode mode = GET_MODE (operand0);
  rtx xa, xi, TWO52, res, mask;
  rtx_code_label *label;

  TWO52 = ix86_gen_TWO52 (mode);

  /* Temporary for holding the result, initialized to the input
     operand to ease control flow.  */
  res = gen_reg_rtx (mode);
  emit_move_insn (res, operand1);

  /* xa = abs (operand1) */
  xa = ix86_expand_sse_fabs (res, &mask);

  /* if (!isless (xa, TWO52)) goto label; */
  label = ix86_expand_sse_compare_and_jump (UNLE, TWO52, xa, false);

  /* x = (double)(long)x */
  xi = gen_reg_rtx (mode == DFmode ? DImode : SImode);
  expand_fix (xi, res, 0);
  expand_float (res, xi, 0);

  if (HONOR_SIGNED_ZEROS (mode))
    ix86_sse_copysign_to_positive (res, res, force_reg (mode, operand1), mask);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (operand0, res);
}

/* Expand SSE sequence for computing trunc from OPERAND1 storing
   into OPERAND0.  */
void
ix86_expand_truncdf_32 (rtx operand0, rtx operand1)
{
  machine_mode mode = GET_MODE (operand0);
  rtx xa, mask, TWO52, one, res, smask, tmp;
  rtx_code_label *label;

  /* C code for SSE variant we expand below.
        double xa = fabs (x), x2;
        if (!isless (xa, TWO52))
          return x;
        xa2 = xa + TWO52 - TWO52;
     Compensate:
        if (xa2 > xa)
          xa2 -= 1.0;
        x2 = copysign (xa2, x);
        return x2;
   */

  TWO52 = ix86_gen_TWO52 (mode);

  /* Temporary for holding the result, initialized to the input
     operand to ease control flow.  */
  res = gen_reg_rtx (mode);
  emit_move_insn (res, operand1);

  /* xa = abs (operand1) */
  xa = ix86_expand_sse_fabs (res, &smask);

  /* if (!isless (xa, TWO52)) goto label; */
  label = ix86_expand_sse_compare_and_jump (UNLE, TWO52, xa, false);

  /* res = xa + TWO52 - TWO52; */
  tmp = expand_simple_binop (mode, PLUS, xa, TWO52, NULL_RTX, 0, OPTAB_DIRECT);
  tmp = expand_simple_binop (mode, MINUS, tmp, TWO52, tmp, 0, OPTAB_DIRECT);
  emit_move_insn (res, tmp);

  /* generate 1.0 */
  one = force_reg (mode, const_double_from_real_value (dconst1, mode));

  /* Compensate: res = xa2 - (res > xa ? 1 : 0)  */
  mask = ix86_expand_sse_compare_mask (UNGT, res, xa, false);
  emit_insn (gen_rtx_SET (mask, gen_rtx_AND (mode, mask, one)));
  tmp = expand_simple_binop (mode, MINUS,
			     res, mask, NULL_RTX, 0, OPTAB_DIRECT);
  emit_move_insn (res, tmp);

  /* res = copysign (res, operand1) */
  ix86_sse_copysign_to_positive (res, res, force_reg (mode, operand1), smask);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (operand0, res);
}

/* Expand SSE sequence for computing round from OPERAND1 storing
   into OPERAND0.  */
void
ix86_expand_round (rtx operand0, rtx operand1)
{
  /* C code for the stuff we're doing below:
        double xa = fabs (x);
        if (!isless (xa, TWO52))
          return x;
        xa = (double)(long)(xa + nextafter (0.5, 0.0));
        return copysign (xa, x);
   */
  machine_mode mode = GET_MODE (operand0);
  rtx res, TWO52, xa, xi, half, mask;
  rtx_code_label *label;
  const struct real_format *fmt;
  REAL_VALUE_TYPE pred_half, half_minus_pred_half;

  /* Temporary for holding the result, initialized to the input
     operand to ease control flow.  */
  res = gen_reg_rtx (mode);
  emit_move_insn (res, operand1);

  TWO52 = ix86_gen_TWO52 (mode);
  xa = ix86_expand_sse_fabs (res, &mask);
  label = ix86_expand_sse_compare_and_jump (UNLE, TWO52, xa, false);

  /* load nextafter (0.5, 0.0) */
  fmt = REAL_MODE_FORMAT (mode);
  real_2expN (&half_minus_pred_half, -(fmt->p) - 1, mode);
  real_arithmetic (&pred_half, MINUS_EXPR, &dconsthalf, &half_minus_pred_half);

  /* xa = xa + 0.5 */
  half = force_reg (mode, const_double_from_real_value (pred_half, mode));
  xa = expand_simple_binop (mode, PLUS, xa, half, NULL_RTX, 0, OPTAB_DIRECT);

  /* xa = (double)(int64_t)xa */
  xi = gen_reg_rtx (mode == DFmode ? DImode : SImode);
  expand_fix (xi, xa, 0);
  expand_float (xa, xi, 0);

  /* res = copysign (xa, operand1) */
  ix86_sse_copysign_to_positive (res, xa, force_reg (mode, operand1), mask);

  emit_label (label);
  LABEL_NUSES (label) = 1;

  emit_move_insn (operand0, res);
}

/* Expand SSE sequence for computing round
   from OP1 storing into OP0 using sse4 round insn.  */
void
ix86_expand_round_sse4 (rtx op0, rtx op1)
{
  machine_mode mode = GET_MODE (op0);
  rtx e1, e2, res, half;
  const struct real_format *fmt;
  REAL_VALUE_TYPE pred_half, half_minus_pred_half;
  rtx (*gen_copysign) (rtx, rtx, rtx);
  rtx (*gen_round) (rtx, rtx, rtx);

  switch (mode)
    {
    case E_SFmode:
      gen_copysign = gen_copysignsf3;
      gen_round = gen_sse4_1_roundsf2;
      break;
    case E_DFmode:
      gen_copysign = gen_copysigndf3;
      gen_round = gen_sse4_1_rounddf2;
      break;
    default:
      gcc_unreachable ();
    }

  /* round (a) = trunc (a + copysign (0.5, a)) */

  /* load nextafter (0.5, 0.0) */
  fmt = REAL_MODE_FORMAT (mode);
  real_2expN (&half_minus_pred_half, -(fmt->p) - 1, mode);
  real_arithmetic (&pred_half, MINUS_EXPR, &dconsthalf, &half_minus_pred_half);
  half = const_double_from_real_value (pred_half, mode);

  /* e1 = copysign (0.5, op1) */
  e1 = gen_reg_rtx (mode);
  emit_insn (gen_copysign (e1, half, op1));

  /* e2 = op1 + e1 */
  e2 = expand_simple_binop (mode, PLUS, op1, e1, NULL_RTX, 0, OPTAB_DIRECT);

  /* res = trunc (e2) */
  res = gen_reg_rtx (mode);
  emit_insn (gen_round (res, e2, GEN_INT (ROUND_TRUNC)));

  emit_move_insn (op0, res);
}

/* Handle fentry_name / fentry_section attribute.  */

static tree
ix86_handle_fentry_name (tree *node, tree name, tree args,
			 int, bool *no_add_attrs)
{
  if (TREE_CODE (*node) == FUNCTION_DECL
      && TREE_CODE (TREE_VALUE (args)) == STRING_CST)
    /* Do nothing else, just set the attribute.  We'll get at
       it later with lookup_attribute.  */
    ;
  else
    {
      warning (OPT_Wattributes, "%qE attribute ignored", name);
      *no_add_attrs = true;
    }

  return NULL_TREE;
}


/* Table of valid machine attributes.  */
static const struct attribute_spec ix86_attribute_table[] =
{
  /* { name, min_len, max_len, decl_req, type_req, fn_type_req,
       affects_type_identity, handler, exclude } */
  /* Stdcall attribute says callee is responsible for popping arguments
     if they are not variable.  */
  { "stdcall",   0, 0, false, true,  true,  true, ix86_handle_cconv_attribute,
    NULL },
  /* Fastcall attribute says callee is responsible for popping arguments
     if they are not variable.  */
  { "fastcall",  0, 0, false, true,  true,  true, ix86_handle_cconv_attribute,
    NULL },
  /* Thiscall attribute says callee is responsible for popping arguments
     if they are not variable.  */
  { "thiscall",  0, 0, false, true,  true,  true, ix86_handle_cconv_attribute,
    NULL },
  /* Cdecl attribute says the callee is a normal C declaration */
  { "cdecl",     0, 0, false, true,  true,  true, ix86_handle_cconv_attribute,
    NULL },
  /* Regparm attribute specifies how many integer arguments are to be
     passed in registers.  */
  { "regparm",   1, 1, false, true,  true,  true, ix86_handle_cconv_attribute,
    NULL },
  /* Sseregparm attribute says we are using x86_64 calling conventions
     for FP arguments.  */
  { "sseregparm", 0, 0, false, true, true,  true, ix86_handle_cconv_attribute,
    NULL },
  /* The transactional memory builtins are implicitly regparm or fastcall
     depending on the ABI.  Override the generic do-nothing attribute that
     these builtins were declared with.  */
  { "*tm regparm", 0, 0, false, true, true, true,
    ix86_handle_tm_regparm_attribute, NULL },
  /* force_align_arg_pointer says this function realigns the stack at entry.  */
  { (const char *)&ix86_force_align_arg_pointer_string, 0, 0,
    false, true,  true, false, ix86_handle_force_align_arg_pointer_attribute,
    NULL },
#if TARGET_DLLIMPORT_DECL_ATTRIBUTES
  { "dllimport", 0, 0, false, false, false, false, handle_dll_attribute,
    NULL },
  { "dllexport", 0, 0, false, false, false, false, handle_dll_attribute,
    NULL },
  { "shared",    0, 0, true,  false, false, false,
    ix86_handle_shared_attribute, NULL },
#endif
  { "ms_struct", 0, 0, false, false,  false, false,
    ix86_handle_struct_attribute, NULL },
  { "gcc_struct", 0, 0, false, false,  false, false,
    ix86_handle_struct_attribute, NULL },
#ifdef SUBTARGET_ATTRIBUTE_TABLE
  SUBTARGET_ATTRIBUTE_TABLE,
#endif
  /* ms_abi and sysv_abi calling convention function attributes.  */
  { "ms_abi", 0, 0, false, true, true, true, ix86_handle_abi_attribute, NULL },
  { "sysv_abi", 0, 0, false, true, true, true, ix86_handle_abi_attribute,
    NULL },
  { "ms_abi va_list", 0, 0, false, false, false, false, NULL, NULL },
  { "sysv_abi va_list", 0, 0, false, false, false, false, NULL, NULL },
  { "ms_hook_prologue", 0, 0, true, false, false, false,
    ix86_handle_fndecl_attribute, NULL },
  { "callee_pop_aggregate_return", 1, 1, false, true, true, true,
    ix86_handle_callee_pop_aggregate_return, NULL },
  { "interrupt", 0, 0, false, true, true, false,
    ix86_handle_interrupt_attribute, NULL },
  { "no_caller_saved_registers", 0, 0, false, true, true, false,
    ix86_handle_no_caller_saved_registers_attribute, NULL },
  { "naked", 0, 0, true, false, false, false,
    ix86_handle_fndecl_attribute, NULL },
  { "indirect_branch", 1, 1, true, false, false, false,
    ix86_handle_fndecl_attribute, NULL },
  { "function_return", 1, 1, true, false, false, false,
    ix86_handle_fndecl_attribute, NULL },
  { "indirect_return", 0, 0, false, true, true, false,
    NULL, NULL },
  { "fentry_name", 1, 1, true, false, false, false,
    ix86_handle_fentry_name, NULL },
  { "fentry_section", 1, 1, true, false, false, false,
    ix86_handle_fentry_name, NULL },
  { "cf_check", 0, 0, true, false, false, false,
    ix86_handle_fndecl_attribute, NULL },

  /* End element.  */
  { NULL, 0, 0, false, false, false, false, NULL, NULL }
};

/* Implement targetm.vectorize.builtin_vectorization_cost.  */
static int
ix86_builtin_vectorization_cost (enum vect_cost_for_stmt type_of_cost,
                                 tree vectype, int)
{
  bool fp = false;
  machine_mode mode = TImode;
  int index;
  if (vectype != NULL)
    {
      fp = FLOAT_TYPE_P (vectype);
      mode = TYPE_MODE (vectype);
    }

  switch (type_of_cost)
    {
      case scalar_stmt:
        return fp ? ix86_cost->addss : COSTS_N_INSNS (1);

      case scalar_load:
	/* load/store costs are relative to register move which is 2. Recompute
 	   it to COSTS_N_INSNS so everything have same base.  */
        return COSTS_N_INSNS (fp ? ix86_cost->sse_load[0]
			      : ix86_cost->int_load [2]) / 2;

      case scalar_store:
        return COSTS_N_INSNS (fp ? ix86_cost->sse_store[0]
			      : ix86_cost->int_store [2]) / 2;

      case vector_stmt:
        return ix86_vec_cost (mode,
			      fp ? ix86_cost->addss : ix86_cost->sse_op);

      case vector_load:
	index = sse_store_index (mode);
	/* See PR82713 - we may end up being called on non-vector type.  */
	if (index < 0)
	  index = 2;
        return COSTS_N_INSNS (ix86_cost->sse_load[index]) / 2;

      case vector_store:
	index = sse_store_index (mode);
	/* See PR82713 - we may end up being called on non-vector type.  */
	if (index < 0)
	  index = 2;
        return COSTS_N_INSNS (ix86_cost->sse_store[index]) / 2;

      case vec_to_scalar:
      case scalar_to_vec:
        return ix86_vec_cost (mode, ix86_cost->sse_op);

      /* We should have separate costs for unaligned loads and gather/scatter.
	 Do that incrementally.  */
      case unaligned_load:
	index = sse_store_index (mode);
	/* See PR82713 - we may end up being called on non-vector type.  */
	if (index < 0)
	  index = 2;
        return COSTS_N_INSNS (ix86_cost->sse_unaligned_load[index]) / 2;

      case unaligned_store:
	index = sse_store_index (mode);
	/* See PR82713 - we may end up being called on non-vector type.  */
	if (index < 0)
	  index = 2;
        return COSTS_N_INSNS (ix86_cost->sse_unaligned_store[index]) / 2;

      case vector_gather_load:
        return ix86_vec_cost (mode,
			      COSTS_N_INSNS
				 (ix86_cost->gather_static
				  + ix86_cost->gather_per_elt
				    * TYPE_VECTOR_SUBPARTS (vectype)) / 2);

      case vector_scatter_store:
        return ix86_vec_cost (mode,
			      COSTS_N_INSNS
				 (ix86_cost->scatter_static
				  + ix86_cost->scatter_per_elt
				    * TYPE_VECTOR_SUBPARTS (vectype)) / 2);

      case cond_branch_taken:
        return ix86_cost->cond_taken_branch_cost;

      case cond_branch_not_taken:
        return ix86_cost->cond_not_taken_branch_cost;

      case vec_perm:
      case vec_promote_demote:
        return ix86_vec_cost (mode, ix86_cost->sse_op);

      case vec_construct:
	{
	  /* N element inserts into SSE vectors.  */
	  int cost = TYPE_VECTOR_SUBPARTS (vectype) * ix86_cost->sse_op;
	  /* One vinserti128 for combining two SSE vectors for AVX256.  */
	  if (GET_MODE_BITSIZE (mode) == 256)
	    cost += ix86_vec_cost (mode, ix86_cost->addss);
	  /* One vinserti64x4 and two vinserti128 for combining SSE
	     and AVX256 vectors to AVX512.  */
	  else if (GET_MODE_BITSIZE (mode) == 512)
	    cost += 3 * ix86_vec_cost (mode, ix86_cost->addss);
	  return cost;
	}

      default:
        gcc_unreachable ();
    }
}

/* A cached (set (nil) (vselect (vconcat (nil) (nil)) (parallel [])))
   insn, so that expand_vselect{,_vconcat} doesn't have to create a fresh
   insn every time.  */

static GTY(()) rtx_insn *vselect_insn;

/* Initialize vselect_insn.  */

static void
init_vselect_insn (void)
{
  unsigned i;
  rtx x;

  x = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (MAX_VECT_LEN));
  for (i = 0; i < MAX_VECT_LEN; ++i)
    XVECEXP (x, 0, i) = const0_rtx;
  x = gen_rtx_VEC_SELECT (V2DFmode, gen_rtx_VEC_CONCAT (V4DFmode, const0_rtx,
							const0_rtx), x);
  x = gen_rtx_SET (const0_rtx, x);
  start_sequence ();
  vselect_insn = emit_insn (x);
  end_sequence ();
}

/* Construct (set target (vec_select op0 (parallel perm))) and
   return true if that's a valid instruction in the active ISA.  */

static bool
expand_vselect (rtx target, rtx op0, const unsigned char *perm,
		unsigned nelt, bool testing_p)
{
  unsigned int i;
  rtx x, save_vconcat;
  int icode;

  if (vselect_insn == NULL_RTX)
    init_vselect_insn ();

  x = XEXP (SET_SRC (PATTERN (vselect_insn)), 1);
  PUT_NUM_ELEM (XVEC (x, 0), nelt);
  for (i = 0; i < nelt; ++i)
    XVECEXP (x, 0, i) = GEN_INT (perm[i]);
  save_vconcat = XEXP (SET_SRC (PATTERN (vselect_insn)), 0);
  XEXP (SET_SRC (PATTERN (vselect_insn)), 0) = op0;
  PUT_MODE (SET_SRC (PATTERN (vselect_insn)), GET_MODE (target));
  SET_DEST (PATTERN (vselect_insn)) = target;
  icode = recog_memoized (vselect_insn);

  if (icode >= 0 && !testing_p)
    emit_insn (copy_rtx (PATTERN (vselect_insn)));

  SET_DEST (PATTERN (vselect_insn)) = const0_rtx;
  XEXP (SET_SRC (PATTERN (vselect_insn)), 0) = save_vconcat;
  INSN_CODE (vselect_insn) = -1;

  return icode >= 0;
}

/* Similar, but generate a vec_concat from op0 and op1 as well.  */

static bool
expand_vselect_vconcat (rtx target, rtx op0, rtx op1,
			const unsigned char *perm, unsigned nelt,
			bool testing_p)
{
  machine_mode v2mode;
  rtx x;
  bool ok;

  if (vselect_insn == NULL_RTX)
    init_vselect_insn ();

  if (!GET_MODE_2XWIDER_MODE (GET_MODE (op0)).exists (&v2mode))
    return false;
  x = XEXP (SET_SRC (PATTERN (vselect_insn)), 0);
  PUT_MODE (x, v2mode);
  XEXP (x, 0) = op0;
  XEXP (x, 1) = op1;
  ok = expand_vselect (target, x, perm, nelt, testing_p);
  XEXP (x, 0) = const0_rtx;
  XEXP (x, 1) = const0_rtx;
  return ok;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to implement D
   using movss or movsd.  */
static bool
expand_vec_perm_movs (struct expand_vec_perm_d *d)
{
  machine_mode vmode = d->vmode;
  unsigned i, nelt = d->nelt;
  rtx x;

  if (d->one_operand_p)
    return false;

  if (!(TARGET_SSE && vmode == V4SFmode)
      && !(TARGET_SSE2 && vmode == V2DFmode))
    return false;

  /* Only the first element is changed.  */
  if (d->perm[0] != nelt && d->perm[0] != 0)
    return false;
  for (i = 1; i < nelt; ++i)
    if (d->perm[i] != i + nelt - d->perm[0])
      return false;

  if (d->testing_p)
    return true;

  if (d->perm[0] == nelt)
    x = gen_rtx_VEC_MERGE (vmode, d->op1, d->op0, GEN_INT (1));
  else
    x = gen_rtx_VEC_MERGE (vmode, d->op0, d->op1, GEN_INT (1));

  emit_insn (gen_rtx_SET (d->target, x));

  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to implement D
   in terms of blendp[sd] / pblendw / pblendvb / vpblendd.  */

static bool
expand_vec_perm_blend (struct expand_vec_perm_d *d)
{
  machine_mode mmode, vmode = d->vmode;
  unsigned i, mask, nelt = d->nelt;
  rtx target, op0, op1, maskop, x;
  rtx rperm[32], vperm;

  if (d->one_operand_p)
    return false;
  if (TARGET_AVX512F && GET_MODE_SIZE (vmode) == 64
      && (TARGET_AVX512BW
	  || GET_MODE_UNIT_SIZE (vmode) >= 4))
    ;
  else if (TARGET_AVX2 && GET_MODE_SIZE (vmode) == 32)
    ;
  else if (TARGET_AVX && (vmode == V4DFmode || vmode == V8SFmode))
    ;
  else if (TARGET_SSE4_1 && GET_MODE_SIZE (vmode) == 16)
    ;
  else
    return false;

  /* This is a blend, not a permute.  Elements must stay in their
     respective lanes.  */
  for (i = 0; i < nelt; ++i)
    {
      unsigned e = d->perm[i];
      if (!(e == i || e == i + nelt))
	return false;
    }

  if (d->testing_p)
    return true;

  /* ??? Without SSE4.1, we could implement this with and/andn/or.  This
     decision should be extracted elsewhere, so that we only try that
     sequence once all budget==3 options have been tried.  */
  target = d->target;
  op0 = d->op0;
  op1 = d->op1;
  mask = 0;

  switch (vmode)
    {
    case E_V8DFmode:
    case E_V16SFmode:
    case E_V4DFmode:
    case E_V8SFmode:
    case E_V2DFmode:
    case E_V4SFmode:
    case E_V8HImode:
    case E_V8SImode:
    case E_V32HImode:
    case E_V64QImode:
    case E_V16SImode:
    case E_V8DImode:
      for (i = 0; i < nelt; ++i)
	mask |= (d->perm[i] >= nelt) << i;
      break;

    case E_V2DImode:
      for (i = 0; i < 2; ++i)
	mask |= (d->perm[i] >= 2 ? 15 : 0) << (i * 4);
      vmode = V8HImode;
      goto do_subreg;

    case E_V4SImode:
      for (i = 0; i < 4; ++i)
	mask |= (d->perm[i] >= 4 ? 3 : 0) << (i * 2);
      vmode = V8HImode;
      goto do_subreg;

    case E_V16QImode:
      /* See if bytes move in pairs so we can use pblendw with
	 an immediate argument, rather than pblendvb with a vector
	 argument.  */
      for (i = 0; i < 16; i += 2)
	if (d->perm[i] + 1 != d->perm[i + 1])
	  {
	  use_pblendvb:
	    for (i = 0; i < nelt; ++i)
	      rperm[i] = (d->perm[i] < nelt ? const0_rtx : constm1_rtx);

	  finish_pblendvb:
	    vperm = gen_rtx_CONST_VECTOR (vmode, gen_rtvec_v (nelt, rperm));
	    vperm = force_reg (vmode, vperm);

	    if (GET_MODE_SIZE (vmode) == 16)
	      emit_insn (gen_sse4_1_pblendvb (target, op0, op1, vperm));
	    else
	      emit_insn (gen_avx2_pblendvb (target, op0, op1, vperm));
	    if (target != d->target)
	      emit_move_insn (d->target, gen_lowpart (d->vmode, target));
	    return true;
	  }

      for (i = 0; i < 8; ++i)
	mask |= (d->perm[i * 2] >= 16) << i;
      vmode = V8HImode;
      /* FALLTHRU */

    do_subreg:
      target = gen_reg_rtx (vmode);
      op0 = gen_lowpart (vmode, op0);
      op1 = gen_lowpart (vmode, op1);
      break;

    case E_V32QImode:
      /* See if bytes move in pairs.  If not, vpblendvb must be used.  */
      for (i = 0; i < 32; i += 2)
	if (d->perm[i] + 1 != d->perm[i + 1])
	  goto use_pblendvb;
      /* See if bytes move in quadruplets.  If yes, vpblendd
	 with immediate can be used.  */
      for (i = 0; i < 32; i += 4)
	if (d->perm[i] + 2 != d->perm[i + 2])
	  break;
      if (i < 32)
	{
	  /* See if bytes move the same in both lanes.  If yes,
	     vpblendw with immediate can be used.  */
	  for (i = 0; i < 16; i += 2)
	    if (d->perm[i] + 16 != d->perm[i + 16])
	      goto use_pblendvb;

	  /* Use vpblendw.  */
	  for (i = 0; i < 16; ++i)
	    mask |= (d->perm[i * 2] >= 32) << i;
	  vmode = V16HImode;
	  goto do_subreg;
	}

      /* Use vpblendd.  */
      for (i = 0; i < 8; ++i)
	mask |= (d->perm[i * 4] >= 32) << i;
      vmode = V8SImode;
      goto do_subreg;

    case E_V16HImode:
      /* See if words move in pairs.  If yes, vpblendd can be used.  */
      for (i = 0; i < 16; i += 2)
	if (d->perm[i] + 1 != d->perm[i + 1])
	  break;
      if (i < 16)
	{
	  /* See if words move the same in both lanes.  If not,
	     vpblendvb must be used.  */
	  for (i = 0; i < 8; i++)
	    if (d->perm[i] + 8 != d->perm[i + 8])
	      {
		/* Use vpblendvb.  */
		for (i = 0; i < 32; ++i)
		  rperm[i] = (d->perm[i / 2] < 16 ? const0_rtx : constm1_rtx);

		vmode = V32QImode;
		nelt = 32;
		target = gen_reg_rtx (vmode);
		op0 = gen_lowpart (vmode, op0);
		op1 = gen_lowpart (vmode, op1);
		goto finish_pblendvb;
	      }

	  /* Use vpblendw.  */
	  for (i = 0; i < 16; ++i)
	    mask |= (d->perm[i] >= 16) << i;
	  break;
	}

      /* Use vpblendd.  */
      for (i = 0; i < 8; ++i)
	mask |= (d->perm[i * 2] >= 16) << i;
      vmode = V8SImode;
      goto do_subreg;

    case E_V4DImode:
      /* Use vpblendd.  */
      for (i = 0; i < 4; ++i)
	mask |= (d->perm[i] >= 4 ? 3 : 0) << (i * 2);
      vmode = V8SImode;
      goto do_subreg;

    default:
      gcc_unreachable ();
    }

  switch (vmode)
    {
    case E_V8DFmode:
    case E_V8DImode:
      mmode = QImode;
      break;
    case E_V16SFmode:
    case E_V16SImode:
      mmode = HImode;
      break;
    case E_V32HImode:
      mmode = SImode;
      break;
    case E_V64QImode:
      mmode = DImode;
      break;
    default:
      mmode = VOIDmode;
    }

  if (mmode != VOIDmode)
    maskop = force_reg (mmode, gen_int_mode (mask, mmode));
  else
    maskop = GEN_INT (mask);

  /* This matches five different patterns with the different modes.  */
  x = gen_rtx_VEC_MERGE (vmode, op1, op0, maskop);
  x = gen_rtx_SET (target, x);
  emit_insn (x);
  if (target != d->target)
    emit_move_insn (d->target, gen_lowpart (d->vmode, target));

  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to implement D
   in terms of the variable form of vpermilps.

   Note that we will have already failed the immediate input vpermilps,
   which requires that the high and low part shuffle be identical; the
   variable form doesn't require that.  */

static bool
expand_vec_perm_vpermil (struct expand_vec_perm_d *d)
{
  rtx rperm[8], vperm;
  unsigned i;

  if (!TARGET_AVX || d->vmode != V8SFmode || !d->one_operand_p)
    return false;

  /* We can only permute within the 128-bit lane.  */
  for (i = 0; i < 8; ++i)
    {
      unsigned e = d->perm[i];
      if (i < 4 ? e >= 4 : e < 4)
	return false;
    }

  if (d->testing_p)
    return true;

  for (i = 0; i < 8; ++i)
    {
      unsigned e = d->perm[i];

      /* Within each 128-bit lane, the elements of op0 are numbered
	 from 0 and the elements of op1 are numbered from 4.  */
      if (e >= 8 + 4)
	e -= 8;
      else if (e >= 4)
	e -= 4;

      rperm[i] = GEN_INT (e);
    }

  vperm = gen_rtx_CONST_VECTOR (V8SImode, gen_rtvec_v (8, rperm));
  vperm = force_reg (V8SImode, vperm);
  emit_insn (gen_avx_vpermilvarv8sf3 (d->target, d->op0, vperm));

  return true;
}

/* Return true if permutation D can be performed as VMODE permutation
   instead.  */

static bool
valid_perm_using_mode_p (machine_mode vmode, struct expand_vec_perm_d *d)
{
  unsigned int i, j, chunk;

  if (GET_MODE_CLASS (vmode) != MODE_VECTOR_INT
      || GET_MODE_CLASS (d->vmode) != MODE_VECTOR_INT
      || GET_MODE_SIZE (vmode) != GET_MODE_SIZE (d->vmode))
    return false;

  if (GET_MODE_NUNITS (vmode) >= d->nelt)
    return true;

  chunk = d->nelt / GET_MODE_NUNITS (vmode);
  for (i = 0; i < d->nelt; i += chunk)
    if (d->perm[i] & (chunk - 1))
      return false;
    else
      for (j = 1; j < chunk; ++j)
	if (d->perm[i] + j != d->perm[i + j])
	  return false;

  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to implement D
   in terms of pshufb, vpperm, vpermq, vpermd, vpermps or vperm2i128.  */

static bool
expand_vec_perm_pshufb (struct expand_vec_perm_d *d)
{
  unsigned i, nelt, eltsz, mask;
  unsigned char perm[64];
  machine_mode vmode = V16QImode;
  rtx rperm[64], vperm, target, op0, op1;

  nelt = d->nelt;

  if (!d->one_operand_p)
    {
      if (!TARGET_XOP || GET_MODE_SIZE (d->vmode) != 16)
	{
	  if (TARGET_AVX2
	      && valid_perm_using_mode_p (V2TImode, d))
	    {
	      if (d->testing_p)
		return true;

	      /* Use vperm2i128 insn.  The pattern uses
		 V4DImode instead of V2TImode.  */
	      target = d->target;
	      if (d->vmode != V4DImode)
		target = gen_reg_rtx (V4DImode);
	      op0 = gen_lowpart (V4DImode, d->op0);
	      op1 = gen_lowpart (V4DImode, d->op1);
	      rperm[0]
		= GEN_INT ((d->perm[0] / (nelt / 2))
			   | ((d->perm[nelt / 2] / (nelt / 2)) * 16));
	      emit_insn (gen_avx2_permv2ti (target, op0, op1, rperm[0]));
	      if (target != d->target)
		emit_move_insn (d->target, gen_lowpart (d->vmode, target));
	      return true;
	    }
	  return false;
	}
    }
  else
    {
      if (GET_MODE_SIZE (d->vmode) == 16)
	{
	  if (!TARGET_SSSE3)
	    return false;
	}
      else if (GET_MODE_SIZE (d->vmode) == 32)
	{
	  if (!TARGET_AVX2)
	    return false;

	  /* V4DImode should be already handled through
	     expand_vselect by vpermq instruction.  */
	  gcc_assert (d->vmode != V4DImode);

	  vmode = V32QImode;
	  if (d->vmode == V8SImode
	      || d->vmode == V16HImode
	      || d->vmode == V32QImode)
	    {
	      /* First see if vpermq can be used for
		 V8SImode/V16HImode/V32QImode.  */
	      if (valid_perm_using_mode_p (V4DImode, d))
		{
		  for (i = 0; i < 4; i++)
		    perm[i] = (d->perm[i * nelt / 4] * 4 / nelt) & 3;
		  if (d->testing_p)
		    return true;
		  target = gen_reg_rtx (V4DImode);
		  if (expand_vselect (target, gen_lowpart (V4DImode, d->op0),
				      perm, 4, false))
		    {
		      emit_move_insn (d->target,
				      gen_lowpart (d->vmode, target));
		      return true;
		    }
		  return false;
		}

	      /* Next see if vpermd can be used.  */
	      if (valid_perm_using_mode_p (V8SImode, d))
		vmode = V8SImode;
	    }
	  /* Or if vpermps can be used.  */
	  else if (d->vmode == V8SFmode)
	    vmode = V8SImode;

	  if (vmode == V32QImode)
	    {
	      /* vpshufb only works intra lanes, it is not
		 possible to shuffle bytes in between the lanes.  */
	      for (i = 0; i < nelt; ++i)
		if ((d->perm[i] ^ i) & (nelt / 2))
		  return false;
	    }
	}
      else if (GET_MODE_SIZE (d->vmode) == 64)
	{
	  if (!TARGET_AVX512BW)
	    return false;

	  /* If vpermq didn't work, vpshufb won't work either.  */
	  if (d->vmode == V8DFmode || d->vmode == V8DImode)
	    return false;

	  vmode = V64QImode;
	  if (d->vmode == V16SImode
	      || d->vmode == V32HImode
	      || d->vmode == V64QImode)
	    {
	      /* First see if vpermq can be used for
		 V16SImode/V32HImode/V64QImode.  */
	      if (valid_perm_using_mode_p (V8DImode, d))
		{
		  for (i = 0; i < 8; i++)
		    perm[i] = (d->perm[i * nelt / 8] * 8 / nelt) & 7;
		  if (d->testing_p)
		    return true;
		  target = gen_reg_rtx (V8DImode);
		  if (expand_vselect (target, gen_lowpart (V8DImode, d->op0),
				      perm, 8, false))
		    {
		      emit_move_insn (d->target,
				      gen_lowpart (d->vmode, target));
		      return true;
		    }
		  return false;
		}

	      /* Next see if vpermd can be used.  */
	      if (valid_perm_using_mode_p (V16SImode, d))
		vmode = V16SImode;
	    }
	  /* Or if vpermps can be used.  */
	  else if (d->vmode == V16SFmode)
	    vmode = V16SImode;
	  if (vmode == V64QImode)
	    {
	      /* vpshufb only works intra lanes, it is not
		 possible to shuffle bytes in between the lanes.  */
	      for (i = 0; i < nelt; ++i)
		if ((d->perm[i] ^ i) & (nelt / 4))
		  return false;
	    }
	}
      else
	return false;
    }

  if (d->testing_p)
    return true;

  if (vmode == V8SImode)
    for (i = 0; i < 8; ++i)
      rperm[i] = GEN_INT ((d->perm[i * nelt / 8] * 8 / nelt) & 7);
  else if (vmode == V16SImode)
    for (i = 0; i < 16; ++i)
      rperm[i] = GEN_INT ((d->perm[i * nelt / 16] * 16 / nelt) & 15);
  else
    {
      eltsz = GET_MODE_UNIT_SIZE (d->vmode);
      if (!d->one_operand_p)
	mask = 2 * nelt - 1;
      else if (vmode == V16QImode)
	mask = nelt - 1;
      else if (vmode == V64QImode)
	mask = nelt / 4 - 1;
      else
	mask = nelt / 2 - 1;

      for (i = 0; i < nelt; ++i)
	{
	  unsigned j, e = d->perm[i] & mask;
	  for (j = 0; j < eltsz; ++j)
	    rperm[i * eltsz + j] = GEN_INT (e * eltsz + j);
	}
    }

  vperm = gen_rtx_CONST_VECTOR (vmode,
				gen_rtvec_v (GET_MODE_NUNITS (vmode), rperm));
  vperm = force_reg (vmode, vperm);

  target = d->target;
  if (d->vmode != vmode)
    target = gen_reg_rtx (vmode);
  op0 = gen_lowpart (vmode, d->op0);
  if (d->one_operand_p)
    {
      if (vmode == V16QImode)
	emit_insn (gen_ssse3_pshufbv16qi3 (target, op0, vperm));
      else if (vmode == V32QImode)
	emit_insn (gen_avx2_pshufbv32qi3 (target, op0, vperm));
      else if (vmode == V64QImode)
	emit_insn (gen_avx512bw_pshufbv64qi3 (target, op0, vperm));
      else if (vmode == V8SFmode)
	emit_insn (gen_avx2_permvarv8sf (target, op0, vperm));
      else if (vmode == V8SImode)
	emit_insn (gen_avx2_permvarv8si (target, op0, vperm));
      else if (vmode == V16SFmode)
	emit_insn (gen_avx512f_permvarv16sf (target, op0, vperm));
      else if (vmode == V16SImode)
	emit_insn (gen_avx512f_permvarv16si (target, op0, vperm));
      else
	gcc_unreachable ();
    }
  else
    {
      op1 = gen_lowpart (vmode, d->op1);
      emit_insn (gen_xop_pperm (target, op0, op1, vperm));
    }
  if (target != d->target)
    emit_move_insn (d->target, gen_lowpart (d->vmode, target));

  return true;
}

/* For V*[QHS]Imode permutations, check if the same permutation
   can't be performed in a 2x, 4x or 8x wider inner mode.  */

static bool
canonicalize_vector_int_perm (const struct expand_vec_perm_d *d,
			      struct expand_vec_perm_d *nd)
{
  int i;
  machine_mode mode = VOIDmode;

  switch (d->vmode)
    {
    case E_V16QImode: mode = V8HImode; break;
    case E_V32QImode: mode = V16HImode; break;
    case E_V64QImode: mode = V32HImode; break;
    case E_V8HImode: mode = V4SImode; break;
    case E_V16HImode: mode = V8SImode; break;
    case E_V32HImode: mode = V16SImode; break;
    case E_V4SImode: mode = V2DImode; break;
    case E_V8SImode: mode = V4DImode; break;
    case E_V16SImode: mode = V8DImode; break;
    default: return false;
    }
  for (i = 0; i < d->nelt; i += 2)
    if ((d->perm[i] & 1) || d->perm[i + 1] != d->perm[i] + 1)
      return false;
  nd->vmode = mode;
  nd->nelt = d->nelt / 2;
  for (i = 0; i < nd->nelt; i++)
    nd->perm[i] = d->perm[2 * i] / 2;
  if (GET_MODE_INNER (mode) != DImode)
    canonicalize_vector_int_perm (nd, nd);
  if (nd != d)
    {
      nd->one_operand_p = d->one_operand_p;
      nd->testing_p = d->testing_p;
      if (d->op0 == d->op1)
	nd->op0 = nd->op1 = gen_lowpart (nd->vmode, d->op0);
      else
	{
	  nd->op0 = gen_lowpart (nd->vmode, d->op0);
	  nd->op1 = gen_lowpart (nd->vmode, d->op1);
	}
      if (d->testing_p)
	nd->target = gen_raw_REG (nd->vmode, LAST_VIRTUAL_REGISTER + 1);
      else
	nd->target = gen_reg_rtx (nd->vmode);
    }
  return true;
}

/* Try to expand one-operand permutation with constant mask.  */

static bool
ix86_expand_vec_one_operand_perm_avx512 (struct expand_vec_perm_d *d)
{
  machine_mode mode = GET_MODE (d->op0);
  machine_mode maskmode = mode;
  rtx (*gen) (rtx, rtx, rtx) = NULL;
  rtx target, op0, mask;
  rtx vec[64];

  if (!rtx_equal_p (d->op0, d->op1))
    return false;

  if (!TARGET_AVX512F)
    return false;

  switch (mode)
    {
    case E_V16SImode:
      gen = gen_avx512f_permvarv16si;
      break;
    case E_V16SFmode:
      gen = gen_avx512f_permvarv16sf;
      maskmode = V16SImode;
      break;
    case E_V8DImode:
      gen = gen_avx512f_permvarv8di;
      break;
    case E_V8DFmode:
      gen = gen_avx512f_permvarv8df;
      maskmode = V8DImode;
      break;
    default:
      return false;
    }

  target = d->target;
  op0 = d->op0;
  for (int i = 0; i < d->nelt; ++i)
    vec[i] = GEN_INT (d->perm[i]);
  mask = gen_rtx_CONST_VECTOR (maskmode, gen_rtvec_v (d->nelt, vec));
  emit_insn (gen (target, op0, force_reg (maskmode, mask)));
  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to instantiate D
   in a single instruction.  */

static bool
expand_vec_perm_1 (struct expand_vec_perm_d *d)
{
  unsigned i, nelt = d->nelt;
  struct expand_vec_perm_d nd;

  /* Check plain VEC_SELECT first, because AVX has instructions that could
     match both SEL and SEL+CONCAT, but the plain SEL will allow a memory
     input where SEL+CONCAT may not.  */
  if (d->one_operand_p)
    {
      int mask = nelt - 1;
      bool identity_perm = true;
      bool broadcast_perm = true;

      for (i = 0; i < nelt; i++)
	{
	  nd.perm[i] = d->perm[i] & mask;
	  if (nd.perm[i] != i)
	    identity_perm = false;
	  if (nd.perm[i])
	    broadcast_perm = false;
	}

      if (identity_perm)
	{
	  if (!d->testing_p)
	    emit_move_insn (d->target, d->op0);
	  return true;
	}
      else if (broadcast_perm && TARGET_AVX2)
	{
	  /* Use vpbroadcast{b,w,d}.  */
	  rtx (*gen) (rtx, rtx) = NULL;
	  switch (d->vmode)
	    {
	    case E_V64QImode:
	      if (TARGET_AVX512BW)
		gen = gen_avx512bw_vec_dupv64qi_1;
	      break;
	    case E_V32QImode:
	      gen = gen_avx2_pbroadcastv32qi_1;
	      break;
	    case E_V32HImode:
	      if (TARGET_AVX512BW)
		gen = gen_avx512bw_vec_dupv32hi_1;
	      break;
	    case E_V16HImode:
	      gen = gen_avx2_pbroadcastv16hi_1;
	      break;
	    case E_V16SImode:
	      if (TARGET_AVX512F)
		gen = gen_avx512f_vec_dupv16si_1;
	      break;
	    case E_V8SImode:
	      gen = gen_avx2_pbroadcastv8si_1;
	      break;
	    case E_V16QImode:
	      gen = gen_avx2_pbroadcastv16qi;
	      break;
	    case E_V8HImode:
	      gen = gen_avx2_pbroadcastv8hi;
	      break;
	    case E_V16SFmode:
	      if (TARGET_AVX512F)
		gen = gen_avx512f_vec_dupv16sf_1;
	      break;
	    case E_V8SFmode:
	      gen = gen_avx2_vec_dupv8sf_1;
	      break;
	    case E_V8DFmode:
	      if (TARGET_AVX512F)
		gen = gen_avx512f_vec_dupv8df_1;
	      break;
	    case E_V8DImode:
	      if (TARGET_AVX512F)
		gen = gen_avx512f_vec_dupv8di_1;
	      break;
	    /* For other modes prefer other shuffles this function creates.  */
	    default: break;
	    }
	  if (gen != NULL)
	    {
	      if (!d->testing_p)
		emit_insn (gen (d->target, d->op0));
	      return true;
	    }
	}

      if (expand_vselect (d->target, d->op0, nd.perm, nelt, d->testing_p))
	return true;

      /* There are plenty of patterns in sse.md that are written for
	 SEL+CONCAT and are not replicated for a single op.  Perhaps
	 that should be changed, to avoid the nastiness here.  */

      /* Recognize interleave style patterns, which means incrementing
	 every other permutation operand.  */
      for (i = 0; i < nelt; i += 2)
	{
	  nd.perm[i] = d->perm[i] & mask;
	  nd.perm[i + 1] = (d->perm[i + 1] & mask) + nelt;
	}
      if (expand_vselect_vconcat (d->target, d->op0, d->op0, nd.perm, nelt,
				  d->testing_p))
	return true;

      /* Recognize shufps, which means adding {0, 0, nelt, nelt}.  */
      if (nelt >= 4)
	{
	  for (i = 0; i < nelt; i += 4)
	    {
	      nd.perm[i + 0] = d->perm[i + 0] & mask;
	      nd.perm[i + 1] = d->perm[i + 1] & mask;
	      nd.perm[i + 2] = (d->perm[i + 2] & mask) + nelt;
	      nd.perm[i + 3] = (d->perm[i + 3] & mask) + nelt;
	    }

	  if (expand_vselect_vconcat (d->target, d->op0, d->op0, nd.perm, nelt,
				      d->testing_p))
	    return true;
	}
    }

  /* Try movss/movsd instructions.  */
  if (expand_vec_perm_movs (d))
    return true;

  /* Finally, try the fully general two operand permute.  */
  if (expand_vselect_vconcat (d->target, d->op0, d->op1, d->perm, nelt,
			      d->testing_p))
    return true;

  /* Recognize interleave style patterns with reversed operands.  */
  if (!d->one_operand_p)
    {
      for (i = 0; i < nelt; ++i)
	{
	  unsigned e = d->perm[i];
	  if (e >= nelt)
	    e -= nelt;
	  else
	    e += nelt;
	  nd.perm[i] = e;
	}

      if (expand_vselect_vconcat (d->target, d->op1, d->op0, nd.perm, nelt,
				  d->testing_p))
	return true;
    }

  /* Try the SSE4.1 blend variable merge instructions.  */
  if (expand_vec_perm_blend (d))
    return true;

  /* Try one of the AVX vpermil variable permutations.  */
  if (expand_vec_perm_vpermil (d))
    return true;

  /* Try the SSSE3 pshufb or XOP vpperm or AVX2 vperm2i128,
     vpshufb, vpermd, vpermps or vpermq variable permutation.  */
  if (expand_vec_perm_pshufb (d))
    return true;

  /* Try the AVX2 vpalignr instruction.  */
  if (expand_vec_perm_palignr (d, true))
    return true;

  /* Try the AVX512F vperm{s,d} instructions.  */
  if (ix86_expand_vec_one_operand_perm_avx512 (d))
    return true;

  /* Try the AVX512F vpermt2/vpermi2 instructions.  */
  if (ix86_expand_vec_perm_vpermt2 (NULL_RTX, NULL_RTX, NULL_RTX, NULL_RTX, d))
    return true;

  /* See if we can get the same permutation in different vector integer
     mode.  */
  if (canonicalize_vector_int_perm (d, &nd) && expand_vec_perm_1 (&nd))
    {
      if (!d->testing_p)
	emit_move_insn (d->target, gen_lowpart (d->vmode, nd.target));
      return true;
    }
  return false;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to implement D
   in terms of a pair of pshuflw + pshufhw instructions.  */

static bool
expand_vec_perm_pshuflw_pshufhw (struct expand_vec_perm_d *d)
{
  unsigned char perm2[MAX_VECT_LEN];
  unsigned i;
  bool ok;

  if (d->vmode != V8HImode || !d->one_operand_p)
    return false;

  /* The two permutations only operate in 64-bit lanes.  */
  for (i = 0; i < 4; ++i)
    if (d->perm[i] >= 4)
      return false;
  for (i = 4; i < 8; ++i)
    if (d->perm[i] < 4)
      return false;

  if (d->testing_p)
    return true;

  /* Emit the pshuflw.  */
  memcpy (perm2, d->perm, 4);
  for (i = 4; i < 8; ++i)
    perm2[i] = i;
  ok = expand_vselect (d->target, d->op0, perm2, 8, d->testing_p);
  gcc_assert (ok);

  /* Emit the pshufhw.  */
  memcpy (perm2 + 4, d->perm + 4, 4);
  for (i = 0; i < 4; ++i)
    perm2[i] = i;
  ok = expand_vselect (d->target, d->target, perm2, 8, d->testing_p);
  gcc_assert (ok);

  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to simplify
   the permutation using the SSSE3 palignr instruction.  This succeeds
   when all of the elements in PERM fit within one vector and we merely
   need to shift them down so that a single vector permutation has a
   chance to succeed.  If SINGLE_INSN_ONLY_P, succeed if only
   the vpalignr instruction itself can perform the requested permutation.  */

static bool
expand_vec_perm_palignr (struct expand_vec_perm_d *d, bool single_insn_only_p)
{
  unsigned i, nelt = d->nelt;
  unsigned min, max, minswap, maxswap;
  bool in_order, ok, swap = false;
  rtx shift, target;
  struct expand_vec_perm_d dcopy;

  /* Even with AVX, palignr only operates on 128-bit vectors,
     in AVX2 palignr operates on both 128-bit lanes.  */
  if ((!TARGET_SSSE3 || GET_MODE_SIZE (d->vmode) != 16)
      && (!TARGET_AVX2 || GET_MODE_SIZE (d->vmode) != 32))
    return false;

  min = 2 * nelt;
  max = 0;
  minswap = 2 * nelt;
  maxswap = 0;
  for (i = 0; i < nelt; ++i)
    {
      unsigned e = d->perm[i];
      unsigned eswap = d->perm[i] ^ nelt;
      if (GET_MODE_SIZE (d->vmode) == 32)
	{
	  e = (e & ((nelt / 2) - 1)) | ((e & nelt) >> 1);
	  eswap = e ^ (nelt / 2);
	}
      if (e < min)
	min = e;
      if (e > max)
	max = e;
      if (eswap < minswap)
	minswap = eswap;
      if (eswap > maxswap)
	maxswap = eswap;
    }
  if (min == 0
      || max - min >= (GET_MODE_SIZE (d->vmode) == 32 ? nelt / 2 : nelt))
    {
      if (d->one_operand_p
	  || minswap == 0
	  || maxswap - minswap >= (GET_MODE_SIZE (d->vmode) == 32
				   ? nelt / 2 : nelt))
	return false;
      swap = true;
      min = minswap;
      max = maxswap;
    }

  /* Given that we have SSSE3, we know we'll be able to implement the
     single operand permutation after the palignr with pshufb for
     128-bit vectors.  If SINGLE_INSN_ONLY_P, in_order has to be computed
     first.  */
  if (d->testing_p && GET_MODE_SIZE (d->vmode) == 16 && !single_insn_only_p)
    return true;

  dcopy = *d;
  if (swap)
    {
      dcopy.op0 = d->op1;
      dcopy.op1 = d->op0;
      for (i = 0; i < nelt; ++i)
	dcopy.perm[i] ^= nelt;
    }

  in_order = true;
  for (i = 0; i < nelt; ++i)
    {
      unsigned e = dcopy.perm[i];
      if (GET_MODE_SIZE (d->vmode) == 32
	  && e >= nelt
	  && (e & (nelt / 2 - 1)) < min)
	e = e - min - (nelt / 2);
      else
	e = e - min;
      if (e != i)
	in_order = false;
      dcopy.perm[i] = e;
    }
  dcopy.one_operand_p = true;

  if (single_insn_only_p && !in_order)
    return false;

  /* For AVX2, test whether we can permute the result in one instruction.  */
  if (d->testing_p)
    {
      if (in_order)
	return true;
      dcopy.op1 = dcopy.op0;
      return expand_vec_perm_1 (&dcopy);
    }

  shift = GEN_INT (min * GET_MODE_UNIT_BITSIZE (d->vmode));
  if (GET_MODE_SIZE (d->vmode) == 16)
    {
      target = gen_reg_rtx (TImode);
      emit_insn (gen_ssse3_palignrti (target, gen_lowpart (TImode, dcopy.op1),
				      gen_lowpart (TImode, dcopy.op0), shift));
    }
  else
    {
      target = gen_reg_rtx (V2TImode);
      emit_insn (gen_avx2_palignrv2ti (target,
				       gen_lowpart (V2TImode, dcopy.op1),
				       gen_lowpart (V2TImode, dcopy.op0),
				       shift));
    }

  dcopy.op0 = dcopy.op1 = gen_lowpart (d->vmode, target);

  /* Test for the degenerate case where the alignment by itself
     produces the desired permutation.  */
  if (in_order)
    {
      emit_move_insn (d->target, dcopy.op0);
      return true;
    }

  ok = expand_vec_perm_1 (&dcopy);
  gcc_assert (ok || GET_MODE_SIZE (d->vmode) == 32);

  return ok;
}

/* A subroutine of ix86_expand_vec_perm_const_1.  Try to simplify
   the permutation using the SSE4_1 pblendv instruction.  Potentially
   reduces permutation from 2 pshufb and or to 1 pshufb and pblendv.  */

static bool
expand_vec_perm_pblendv (struct expand_vec_perm_d *d)
{
  unsigned i, which, nelt = d->nelt;
  struct expand_vec_perm_d dcopy, dcopy1;
  machine_mode vmode = d->vmode;
  bool ok;

  /* Use the same checks as in expand_vec_perm_blend.  */
  if (d->one_operand_p)
    return false;
  if (TARGET_AVX2 && GET_MODE_SIZE (vmode) == 32)
    ;
  else if (TARGET_AVX && (vmode == V4DFmode || vmode == V8SFmode))
    ;
  else if (TARGET_SSE4_1 && GET_MODE_SIZE (vmode) == 16)
    ;
  else
    return false;

  /* Figure out where permutation elements stay not in their
     respective lanes.  */
  for (i = 0, which = 0; i < nelt; ++i)
    {
      unsigned e = d->perm[i];
      if (e != i)
	which |= (e < nelt ? 1 : 2);
    }
  /* We can pblend the part where elements stay not in their
     respective lanes only when these elements are all in one
     half of a permutation.
     {0 1 8 3 4 5 9 7} is ok as 8, 9 are at not at their respective
     lanes, but both 8 and 9 >= 8
     {0 1 8 3 4 5 2 7} is not ok as 2 and 8 are not at their
     respective lanes and 8 >= 8, but 2 not.  */
  if (which != 1 && which != 2)
    return false;
  if (d->testing_p && GET_MODE_SIZE (vmode) == 16)
    return true;

  /* First we apply one operand permutation to the part where
     elements stay not in their respective lanes.  */
  dcopy = *d;
  if (which == 2)
    dcopy.op0 = dcopy.op1 = d->op1;
  else
    dcopy.op0 = dcopy.op1 = d->op0;
  if (!d->testing_p)
    dcopy.target = gen_reg_rtx (vmode);
  dcopy.one_operand_p = true;

  for (i = 0; i < nelt; ++i)
    dcopy.perm[i] = d->perm[i] & (nelt - 1);

  ok = expand_vec_perm_1 (&dcopy);
  if (GET_MODE_SIZE (vmode) != 16 && !ok)
    return false;
  else
    gcc_assert (ok);
  if (d->testing_p)
    return true;

  /* Next we put permuted elements into their positions.  */
  dcopy1 = *d;
  if (which == 2)
    dcopy1.op1 = dcopy.target;
  else
    dcopy1.op0 = dcopy.target;

  for (i = 0; i < nelt; ++i)
    dcopy1.perm[i] = ((d->perm[i] >= nelt) ? (nelt + i) : i);

  ok = expand_vec_perm_blend (&dcopy1);
  gcc_assert (ok);

  return true;
}

static bool expand_vec_perm_interleave3 (struct expand_vec_perm_d *d);

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to simplify
   a two vector permutation into a single vector permutation by using
   an interleave operation to merge the vectors.  */

static bool
expand_vec_perm_interleave2 (struct expand_vec_perm_d *d)
{
  struct expand_vec_perm_d dremap, dfinal;
  unsigned i, nelt = d->nelt, nelt2 = nelt / 2;
  unsigned HOST_WIDE_INT contents;
  unsigned char remap[2 * MAX_VECT_LEN];
  rtx_insn *seq;
  bool ok, same_halves = false;

  if (GET_MODE_SIZE (d->vmode) == 16)
    {
      if (d->one_operand_p)
	return false;
    }
  else if (GET_MODE_SIZE (d->vmode) == 32)
    {
      if (!TARGET_AVX)
	return false;
      /* For 32-byte modes allow even d->one_operand_p.
	 The lack of cross-lane shuffling in some instructions
	 might prevent a single insn shuffle.  */
      dfinal = *d;
      dfinal.testing_p = true;
      /* If expand_vec_perm_interleave3 can expand this into
	 a 3 insn sequence, give up and let it be expanded as
	 3 insn sequence.  While that is one insn longer,
	 it doesn't need a memory operand and in the common
	 case that both interleave low and high permutations
	 with the same operands are adjacent needs 4 insns
	 for both after CSE.  */
      if (expand_vec_perm_interleave3 (&dfinal))
	return false;
    }
  else
    return false;

  /* Examine from whence the elements come.  */
  contents = 0;
  for (i = 0; i < nelt; ++i)
    contents |= HOST_WIDE_INT_1U << d->perm[i];

  memset (remap, 0xff, sizeof (remap));
  dremap = *d;

  if (GET_MODE_SIZE (d->vmode) == 16)
    {
      unsigned HOST_WIDE_INT h1, h2, h3, h4;

      /* Split the two input vectors into 4 halves.  */
      h1 = (HOST_WIDE_INT_1U << nelt2) - 1;
      h2 = h1 << nelt2;
      h3 = h2 << nelt2;
      h4 = h3 << nelt2;

      /* If the elements from the low halves use interleave low, and similarly
	 for interleave high.  If the elements are from mis-matched halves, we
	 can use shufps for V4SF/V4SI or do a DImode shuffle.  */
      if ((contents & (h1 | h3)) == contents)
	{
	  /* punpckl* */
	  for (i = 0; i < nelt2; ++i)
	    {
	      remap[i] = i * 2;
	      remap[i + nelt] = i * 2 + 1;
	      dremap.perm[i * 2] = i;
	      dremap.perm[i * 2 + 1] = i + nelt;
	    }
	  if (!TARGET_SSE2 && d->vmode == V4SImode)
	    dremap.vmode = V4SFmode;
	}
      else if ((contents & (h2 | h4)) == contents)
	{
	  /* punpckh* */
	  for (i = 0; i < nelt2; ++i)
	    {
	      remap[i + nelt2] = i * 2;
	      remap[i + nelt + nelt2] = i * 2 + 1;
	      dremap.perm[i * 2] = i + nelt2;
	      dremap.perm[i * 2 + 1] = i + nelt + nelt2;
	    }
	  if (!TARGET_SSE2 && d->vmode == V4SImode)
	    dremap.vmode = V4SFmode;
	}
      else if ((contents & (h1 | h4)) == contents)
	{
	  /* shufps */
	  for (i = 0; i < nelt2; ++i)
	    {
	      remap[i] = i;
	      remap[i + nelt + nelt2] = i + nelt2;
	      dremap.perm[i] = i;
	      dremap.perm[i + nelt2] = i + nelt + nelt2;
	    }
	  if (nelt != 4)
	    {
	      /* shufpd */
	      dremap.vmode = V2DImode;
	      dremap.nelt = 2;
	      dremap.perm[0] = 0;
	      dremap.perm[1] = 3;
	    }
	}
      else if ((contents & (h2 | h3)) == contents)
	{
	  /* shufps */
	  for (i = 0; i < nelt2; ++i)
	    {
	      remap[i + nelt2] = i;
	      remap[i + nelt] = i + nelt2;
	      dremap.perm[i] = i + nelt2;
	      dremap.perm[i + nelt2] = i + nelt;
	    }
	  if (nelt != 4)
	    {
	      /* shufpd */
	      dremap.vmode = V2DImode;
	      dremap.nelt = 2;
	      dremap.perm[0] = 1;
	      dremap.perm[1] = 2;
	    }
	}
      else
	return false;
    }
  else
    {
      unsigned int nelt4 = nelt / 4, nzcnt = 0;
      unsigned HOST_WIDE_INT q[8];
      unsigned int nonzero_halves[4];

      /* Split the two input vectors into 8 quarters.  */
      q[0] = (HOST_WIDE_INT_1U << nelt4) - 1;
      for (i = 1; i < 8; ++i)
	q[i] = q[0] << (nelt4 * i);
      for (i = 0; i < 4; ++i)
	if (((q[2 * i] | q[2 * i + 1]) & contents) != 0)
	  {
	    nonzero_halves[nzcnt] = i;
	    ++nzcnt;
	  }

      if (nzcnt == 1)
	{
	  gcc_assert (d->one_operand_p);
	  nonzero_halves[1] = nonzero_halves[0];
	  same_halves = true;
	}
      else if (d->one_operand_p)
	{
	  gcc_assert (nonzero_halves[0] == 0);
	  gcc_assert (nonzero_halves[1] == 1);
	}

      if (nzcnt <= 2)
	{
	  if (d->perm[0] / nelt2 == nonzero_halves[1])
	    {
	      /* Attempt to increase the likelihood that dfinal
		 shuffle will be intra-lane.  */
	      std::swap (nonzero_halves[0], nonzero_halves[1]);
	    }

	  /* vperm2f128 or vperm2i128.  */
	  for (i = 0; i < nelt2; ++i)
	    {
	      remap[i + nonzero_halves[1] * nelt2] = i + nelt2;
	      remap[i + nonzero_halves[0] * nelt2] = i;
	      dremap.perm[i + nelt2] = i + nonzero_halves[1] * nelt2;
	      dremap.perm[i] = i + nonzero_halves[0] * nelt2;
	    }

	  if (d->vmode != V8SFmode
	      && d->vmode != V4DFmode
	      && d->vmode != V8SImode)
	    {
	      dremap.vmode = V8SImode;
	      dremap.nelt = 8;
	      for (i = 0; i < 4; ++i)
		{
		  dremap.perm[i] = i + nonzero_halves[0] * 4;
		  dremap.perm[i + 4] = i + nonzero_halves[1] * 4;
		}
	    }
	}
      else if (d->one_operand_p)
	return false;
      else if (TARGET_AVX2
	       && (contents & (q[0] | q[2] | q[4] | q[6])) == contents)
	{
	  /* vpunpckl* */
	  for (i = 0; i < nelt4; ++i)
	    {
	      remap[i] = i * 2;
	      remap[i + nelt] = i * 2 + 1;
	      remap[i + nelt2] = i * 2 + nelt2;
	      remap[i + nelt + nelt2] = i * 2 + nelt2 + 1;
	      dremap.perm[i * 2] = i;
	      dremap.perm[i * 2 + 1] = i + nelt;
	      dremap.perm[i * 2 + nelt2] = i + nelt2;
	      dremap.perm[i * 2 + nelt2 + 1] = i + nelt + nelt2;
	    }
	}
      else if (TARGET_AVX2
	       && (contents & (q[1] | q[3] | q[5] | q[7])) == contents)
	{
	  /* vpunpckh* */
	  for (i = 0; i < nelt4; ++i)
	    {
	      remap[i + nelt4] = i * 2;
	      remap[i + nelt + nelt4] = i * 2 + 1;
	      remap[i + nelt2 + nelt4] = i * 2 + nelt2;
	      remap[i + nelt + nelt2 + nelt4] = i * 2 + nelt2 + 1;
	      dremap.perm[i * 2] = i + nelt4;
	      dremap.perm[i * 2 + 1] = i + nelt + nelt4;
	      dremap.perm[i * 2 + nelt2] = i + nelt2 + nelt4;
	      dremap.perm[i * 2 + nelt2 + 1] = i + nelt + nelt2 + nelt4;
	    }
	}
      else
	return false;
    }

  /* Use the remapping array set up above to move the elements from their
     swizzled locations into their final destinations.  */
  dfinal = *d;
  for (i = 0; i < nelt; ++i)
    {
      unsigned e = remap[d->perm[i]];
      gcc_assert (e < nelt);
      /* If same_halves is true, both halves of the remapped vector are the
	 same.  Avoid cross-lane accesses if possible.  */
      if (same_halves && i >= nelt2)
	{
	  gcc_assert (e < nelt2);
	  dfinal.perm[i] = e + nelt2;
	}
      else
	dfinal.perm[i] = e;
    }
  if (!d->testing_p)
    {
      dremap.target = gen_reg_rtx (dremap.vmode);
      dfinal.op0 = gen_lowpart (dfinal.vmode, dremap.target);
    }
  dfinal.op1 = dfinal.op0;
  dfinal.one_operand_p = true;

  /* Test if the final remap can be done with a single insn.  For V4SFmode or
     V4SImode this *will* succeed.  For V8HImode or V16QImode it may not.  */
  start_sequence ();
  ok = expand_vec_perm_1 (&dfinal);
  seq = get_insns ();
  end_sequence ();

  if (!ok)
    return false;

  if (d->testing_p)
    return true;

  if (dremap.vmode != dfinal.vmode)
    {
      dremap.op0 = gen_lowpart (dremap.vmode, dremap.op0);
      dremap.op1 = gen_lowpart (dremap.vmode, dremap.op1);
    }

  ok = expand_vec_perm_1 (&dremap);
  gcc_assert (ok);

  emit_insn (seq);
  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to simplify
   a single vector cross-lane permutation into vpermq followed
   by any of the single insn permutations.  */

static bool
expand_vec_perm_vpermq_perm_1 (struct expand_vec_perm_d *d)
{
  struct expand_vec_perm_d dremap, dfinal;
  unsigned i, j, nelt = d->nelt, nelt2 = nelt / 2, nelt4 = nelt / 4;
  unsigned contents[2];
  bool ok;

  if (!(TARGET_AVX2
	&& (d->vmode == V32QImode || d->vmode == V16HImode)
	&& d->one_operand_p))
    return false;

  contents[0] = 0;
  contents[1] = 0;
  for (i = 0; i < nelt2; ++i)
    {
      contents[0] |= 1u << (d->perm[i] / nelt4);
      contents[1] |= 1u << (d->perm[i + nelt2] / nelt4);
    }

  for (i = 0; i < 2; ++i)
    {
      unsigned int cnt = 0;
      for (j = 0; j < 4; ++j)
	if ((contents[i] & (1u << j)) != 0 && ++cnt > 2)
	  return false;
    }

  if (d->testing_p)
    return true;

  dremap = *d;
  dremap.vmode = V4DImode;
  dremap.nelt = 4;
  dremap.target = gen_reg_rtx (V4DImode);
  dremap.op0 = gen_lowpart (V4DImode, d->op0);
  dremap.op1 = dremap.op0;
  dremap.one_operand_p = true;
  for (i = 0; i < 2; ++i)
    {
      unsigned int cnt = 0;
      for (j = 0; j < 4; ++j)
	if ((contents[i] & (1u << j)) != 0)
	  dremap.perm[2 * i + cnt++] = j;
      for (; cnt < 2; ++cnt)
	dremap.perm[2 * i + cnt] = 0;
    }

  dfinal = *d;
  dfinal.op0 = gen_lowpart (dfinal.vmode, dremap.target);
  dfinal.op1 = dfinal.op0;
  dfinal.one_operand_p = true;
  for (i = 0, j = 0; i < nelt; ++i)
    {
      if (i == nelt2)
	j = 2;
      dfinal.perm[i] = (d->perm[i] & (nelt4 - 1)) | (j ? nelt2 : 0);
      if ((d->perm[i] / nelt4) == dremap.perm[j])
	;
      else if ((d->perm[i] / nelt4) == dremap.perm[j + 1])
	dfinal.perm[i] |= nelt4;
      else
	gcc_unreachable ();
    }

  ok = expand_vec_perm_1 (&dremap);
  gcc_assert (ok);

  ok = expand_vec_perm_1 (&dfinal);
  gcc_assert (ok);

  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to expand
   a vector permutation using two instructions, vperm2f128 resp.
   vperm2i128 followed by any single in-lane permutation.  */

static bool
expand_vec_perm_vperm2f128 (struct expand_vec_perm_d *d)
{
  struct expand_vec_perm_d dfirst, dsecond;
  unsigned i, j, nelt = d->nelt, nelt2 = nelt / 2, perm;
  bool ok;

  if (!TARGET_AVX
      || GET_MODE_SIZE (d->vmode) != 32
      || (d->vmode != V8SFmode && d->vmode != V4DFmode && !TARGET_AVX2))
    return false;

  dsecond = *d;
  dsecond.one_operand_p = false;
  dsecond.testing_p = true;

  /* ((perm << 2)|perm) & 0x33 is the vperm2[fi]128
     immediate.  For perm < 16 the second permutation uses
     d->op0 as first operand, for perm >= 16 it uses d->op1
     as first operand.  The second operand is the result of
     vperm2[fi]128.  */
  for (perm = 0; perm < 32; perm++)
    {
      /* Ignore permutations which do not move anything cross-lane.  */
      if (perm < 16)
	{
	  /* The second shuffle for e.g. V4DFmode has
	     0123 and ABCD operands.
	     Ignore AB23, as 23 is already in the second lane
	     of the first operand.  */
	  if ((perm & 0xc) == (1 << 2)) continue;
	  /* And 01CD, as 01 is in the first lane of the first
	     operand.  */
	  if ((perm & 3) == 0) continue;
	  /* And 4567, as then the vperm2[fi]128 doesn't change
	     anything on the original 4567 second operand.  */
	  if ((perm & 0xf) == ((3 << 2) | 2)) continue;
	}
      else
	{
	  /* The second shuffle for e.g. V4DFmode has
	     4567 and ABCD operands.
	     Ignore AB67, as 67 is already in the second lane
	     of the first operand.  */
	  if ((perm & 0xc) == (3 << 2)) continue;
	  /* And 45CD, as 45 is in the first lane of the first
	     operand.  */
	  if ((perm & 3) == 2) continue;
	  /* And 0123, as then the vperm2[fi]128 doesn't change
	     anything on the original 0123 first operand.  */
	  if ((perm & 0xf) == (1 << 2)) continue;
	}

      for (i = 0; i < nelt; i++)
	{
	  j = d->perm[i] / nelt2;
	  if (j == ((perm >> (2 * (i >= nelt2))) & 3))
	    dsecond.perm[i] = nelt + (i & nelt2) + (d->perm[i] & (nelt2 - 1));
	  else if (j == (unsigned) (i >= nelt2) + 2 * (perm >= 16))
	    dsecond.perm[i] = d->perm[i] & (nelt - 1);
	  else
	    break;
	}

      if (i == nelt)
	{
	  start_sequence ();
	  ok = expand_vec_perm_1 (&dsecond);
	  end_sequence ();
	}
      else
	ok = false;

      if (ok)
	{
	  if (d->testing_p)
	    return true;

	  /* Found a usable second shuffle.  dfirst will be
	     vperm2f128 on d->op0 and d->op1.  */
	  dsecond.testing_p = false;
	  dfirst = *d;
	  dfirst.target = gen_reg_rtx (d->vmode);
	  for (i = 0; i < nelt; i++)
	    dfirst.perm[i] = (i & (nelt2 - 1))
			     + ((perm >> (2 * (i >= nelt2))) & 3) * nelt2;

	  canonicalize_perm (&dfirst);
	  ok = expand_vec_perm_1 (&dfirst);
	  gcc_assert (ok);

	  /* And dsecond is some single insn shuffle, taking
	     d->op0 and result of vperm2f128 (if perm < 16) or
	     d->op1 and result of vperm2f128 (otherwise).  */
	  if (perm >= 16)
	    dsecond.op0 = dsecond.op1;
	  dsecond.op1 = dfirst.target;

	  ok = expand_vec_perm_1 (&dsecond);
	  gcc_assert (ok);

	  return true;
	}

      /* For one operand, the only useful vperm2f128 permutation is 0x01
	 aka lanes swap.  */
      if (d->one_operand_p)
	return false;
    }

  return false;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to simplify
   a two vector permutation using 2 intra-lane interleave insns
   and cross-lane shuffle for 32-byte vectors.  */

static bool
expand_vec_perm_interleave3 (struct expand_vec_perm_d *d)
{
  unsigned i, nelt;
  rtx (*gen) (rtx, rtx, rtx);

  if (d->one_operand_p)
    return false;
  if (TARGET_AVX2 && GET_MODE_SIZE (d->vmode) == 32)
    ;
  else if (TARGET_AVX && (d->vmode == V8SFmode || d->vmode == V4DFmode))
    ;
  else
    return false;

  nelt = d->nelt;
  if (d->perm[0] != 0 && d->perm[0] != nelt / 2)
    return false;
  for (i = 0; i < nelt; i += 2)
    if (d->perm[i] != d->perm[0] + i / 2
	|| d->perm[i + 1] != d->perm[0] + i / 2 + nelt)
      return false;

  if (d->testing_p)
    return true;

  switch (d->vmode)
    {
    case E_V32QImode:
      if (d->perm[0])
	gen = gen_vec_interleave_highv32qi;
      else
	gen = gen_vec_interleave_lowv32qi;
      break;
    case E_V16HImode:
      if (d->perm[0])
	gen = gen_vec_interleave_highv16hi;
      else
	gen = gen_vec_interleave_lowv16hi;
      break;
    case E_V8SImode:
      if (d->perm[0])
	gen = gen_vec_interleave_highv8si;
      else
	gen = gen_vec_interleave_lowv8si;
      break;
    case E_V4DImode:
      if (d->perm[0])
	gen = gen_vec_interleave_highv4di;
      else
	gen = gen_vec_interleave_lowv4di;
      break;
    case E_V8SFmode:
      if (d->perm[0])
	gen = gen_vec_interleave_highv8sf;
      else
	gen = gen_vec_interleave_lowv8sf;
      break;
    case E_V4DFmode:
      if (d->perm[0])
	gen = gen_vec_interleave_highv4df;
      else
	gen = gen_vec_interleave_lowv4df;
      break;
    default:
      gcc_unreachable ();
    }

  emit_insn (gen (d->target, d->op0, d->op1));
  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Try to implement
   a single vector permutation using a single intra-lane vector
   permutation, vperm2f128 swapping the lanes and vblend* insn blending
   the non-swapped and swapped vectors together.  */

static bool
expand_vec_perm_vperm2f128_vblend (struct expand_vec_perm_d *d)
{
  struct expand_vec_perm_d dfirst, dsecond;
  unsigned i, j, msk, nelt = d->nelt, nelt2 = nelt / 2;
  rtx_insn *seq;
  bool ok;
  rtx (*blend) (rtx, rtx, rtx, rtx) = NULL;

  if (!TARGET_AVX
      || TARGET_AVX2
      || (d->vmode != V8SFmode && d->vmode != V4DFmode)
      || !d->one_operand_p)
    return false;

  dfirst = *d;
  for (i = 0; i < nelt; i++)
    dfirst.perm[i] = 0xff;
  for (i = 0, msk = 0; i < nelt; i++)
    {
      j = (d->perm[i] & nelt2) ? i | nelt2 : i & ~nelt2;
      if (dfirst.perm[j] != 0xff && dfirst.perm[j] != d->perm[i])
	return false;
      dfirst.perm[j] = d->perm[i];
      if (j != i)
	msk |= (1 << i);
    }
  for (i = 0; i < nelt; i++)
    if (dfirst.perm[i] == 0xff)
      dfirst.perm[i] = i;

  if (!d->testing_p)
    dfirst.target = gen_reg_rtx (dfirst.vmode);

  start_sequence ();
  ok = expand_vec_perm_1 (&dfirst);
  seq = get_insns ();
  end_sequence ();

  if (!ok)
    return false;

  if (d->testing_p)
    return true;

  emit_insn (seq);

  dsecond = *d;
  dsecond.op0 = dfirst.target;
  dsecond.op1 = dfirst.target;
  dsecond.one_operand_p = true;
  dsecond.target = gen_reg_rtx (dsecond.vmode);
  for (i = 0; i < nelt; i++)
    dsecond.perm[i] = i ^ nelt2;

  ok = expand_vec_perm_1 (&dsecond);
  gcc_assert (ok);

  blend = d->vmode == V8SFmode ? gen_avx_blendps256 : gen_avx_blendpd256;
  emit_insn (blend (d->target, dfirst.target, dsecond.target, GEN_INT (msk)));
  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Implement a V4DF
   permutation using two vperm2f128, followed by a vshufpd insn blending
   the two vectors together.  */

static bool
expand_vec_perm_2vperm2f128_vshuf (struct expand_vec_perm_d *d)
{
  struct expand_vec_perm_d dfirst, dsecond, dthird;
  bool ok;

  if (!TARGET_AVX || (d->vmode != V4DFmode))
    return false;

  if (d->testing_p)
    return true;

  dfirst = *d;
  dsecond = *d;
  dthird = *d;

  dfirst.perm[0] = (d->perm[0] & ~1);
  dfirst.perm[1] = (d->perm[0] & ~1) + 1;
  dfirst.perm[2] = (d->perm[2] & ~1);
  dfirst.perm[3] = (d->perm[2] & ~1) + 1;
  dsecond.perm[0] = (d->perm[1] & ~1);
  dsecond.perm[1] = (d->perm[1] & ~1) + 1;
  dsecond.perm[2] = (d->perm[3] & ~1);
  dsecond.perm[3] = (d->perm[3] & ~1) + 1;
  dthird.perm[0] = (d->perm[0] % 2);
  dthird.perm[1] = (d->perm[1] % 2) + 4;
  dthird.perm[2] = (d->perm[2] % 2) + 2;
  dthird.perm[3] = (d->perm[3] % 2) + 6;

  dfirst.target = gen_reg_rtx (dfirst.vmode);
  dsecond.target = gen_reg_rtx (dsecond.vmode);
  dthird.op0 = dfirst.target;
  dthird.op1 = dsecond.target;
  dthird.one_operand_p = false;

  canonicalize_perm (&dfirst);
  canonicalize_perm (&dsecond);

  ok = expand_vec_perm_1 (&dfirst)
       && expand_vec_perm_1 (&dsecond)
       && expand_vec_perm_1 (&dthird);

  gcc_assert (ok);

  return true;
}

/* A subroutine of expand_vec_perm_even_odd_1.  Implement the double-word
   permutation with two pshufb insns and an ior.  We should have already
   failed all two instruction sequences.  */

static bool
expand_vec_perm_pshufb2 (struct expand_vec_perm_d *d)
{
  rtx rperm[2][16], vperm, l, h, op, m128;
  unsigned int i, nelt, eltsz;

  if (!TARGET_SSSE3 || GET_MODE_SIZE (d->vmode) != 16)
    return false;
  gcc_assert (!d->one_operand_p);

  if (d->testing_p)
    return true;

  nelt = d->nelt;
  eltsz = GET_MODE_UNIT_SIZE (d->vmode);

  /* Generate two permutation masks.  If the required element is within
     the given vector it is shuffled into the proper lane.  If the required
     element is in the other vector, force a zero into the lane by setting
     bit 7 in the permutation mask.  */
  m128 = GEN_INT (-128);
  for (i = 0; i < nelt; ++i)
    {
      unsigned j, e = d->perm[i];
      unsigned which = (e >= nelt);
      if (e >= nelt)
	e -= nelt;

      for (j = 0; j < eltsz; ++j)
	{
	  rperm[which][i*eltsz + j] = GEN_INT (e*eltsz + j);
	  rperm[1-which][i*eltsz + j] = m128;
	}
    }

  vperm = gen_rtx_CONST_VECTOR (V16QImode, gen_rtvec_v (16, rperm[0]));
  vperm = force_reg (V16QImode, vperm);

  l = gen_reg_rtx (V16QImode);
  op = gen_lowpart (V16QImode, d->op0);
  emit_insn (gen_ssse3_pshufbv16qi3 (l, op, vperm));

  vperm = gen_rtx_CONST_VECTOR (V16QImode, gen_rtvec_v (16, rperm[1]));
  vperm = force_reg (V16QImode, vperm);

  h = gen_reg_rtx (V16QImode);
  op = gen_lowpart (V16QImode, d->op1);
  emit_insn (gen_ssse3_pshufbv16qi3 (h, op, vperm));

  op = d->target;
  if (d->vmode != V16QImode)
    op = gen_reg_rtx (V16QImode);
  emit_insn (gen_iorv16qi3 (op, l, h));
  if (op != d->target)
    emit_move_insn (d->target, gen_lowpart (d->vmode, op));

  return true;
}

/* Implement arbitrary permutation of one V32QImode and V16QImode operand
   with two vpshufb insns, vpermq and vpor.  We should have already failed
   all two or three instruction sequences.  */

static bool
expand_vec_perm_vpshufb2_vpermq (struct expand_vec_perm_d *d)
{
  rtx rperm[2][32], vperm, l, h, hp, op, m128;
  unsigned int i, nelt, eltsz;

  if (!TARGET_AVX2
      || !d->one_operand_p
      || (d->vmode != V32QImode && d->vmode != V16HImode))
    return false;

  if (d->testing_p)
    return true;

  nelt = d->nelt;
  eltsz = GET_MODE_UNIT_SIZE (d->vmode);

  /* Generate two permutation masks.  If the required element is within
     the same lane, it is shuffled in.  If the required element from the
     other lane, force a zero by setting bit 7 in the permutation mask.
     In the other mask the mask has non-negative elements if element
     is requested from the other lane, but also moved to the other lane,
     so that the result of vpshufb can have the two V2TImode halves
     swapped.  */
  m128 = GEN_INT (-128);
  for (i = 0; i < nelt; ++i)
    {
      unsigned j, e = d->perm[i] & (nelt / 2 - 1);
      unsigned which = ((d->perm[i] ^ i) & (nelt / 2)) * eltsz;

      for (j = 0; j < eltsz; ++j)
	{
	  rperm[!!which][(i * eltsz + j) ^ which] = GEN_INT (e * eltsz + j);
	  rperm[!which][(i * eltsz + j) ^ (which ^ 16)] = m128;
	}
    }

  vperm = gen_rtx_CONST_VECTOR (V32QImode, gen_rtvec_v (32, rperm[1]));
  vperm = force_reg (V32QImode, vperm);

  h = gen_reg_rtx (V32QImode);
  op = gen_lowpart (V32QImode, d->op0);
  emit_insn (gen_avx2_pshufbv32qi3 (h, op, vperm));

  /* Swap the 128-byte lanes of h into hp.  */
  hp = gen_reg_rtx (V4DImode);
  op = gen_lowpart (V4DImode, h);
  emit_insn (gen_avx2_permv4di_1 (hp, op, const2_rtx, GEN_INT (3), const0_rtx,
				  const1_rtx));

  vperm = gen_rtx_CONST_VECTOR (V32QImode, gen_rtvec_v (32, rperm[0]));
  vperm = force_reg (V32QImode, vperm);

  l = gen_reg_rtx (V32QImode);
  op = gen_lowpart (V32QImode, d->op0);
  emit_insn (gen_avx2_pshufbv32qi3 (l, op, vperm));

  op = d->target;
  if (d->vmode != V32QImode)
    op = gen_reg_rtx (V32QImode);
  emit_insn (gen_iorv32qi3 (op, l, gen_lowpart (V32QImode, hp)));
  if (op != d->target)
    emit_move_insn (d->target, gen_lowpart (d->vmode, op));

  return true;
}

/* A subroutine of expand_vec_perm_even_odd_1.  Implement extract-even
   and extract-odd permutations of two V32QImode and V16QImode operand
   with two vpshufb insns, vpor and vpermq.  We should have already
   failed all two or three instruction sequences.  */

static bool
expand_vec_perm_vpshufb2_vpermq_even_odd (struct expand_vec_perm_d *d)
{
  rtx rperm[2][32], vperm, l, h, ior, op, m128;
  unsigned int i, nelt, eltsz;

  if (!TARGET_AVX2
      || d->one_operand_p
      || (d->vmode != V32QImode && d->vmode != V16HImode))
    return false;

  for (i = 0; i < d->nelt; ++i)
    if ((d->perm[i] ^ (i * 2)) & (3 * d->nelt / 2))
      return false;

  if (d->testing_p)
    return true;

  nelt = d->nelt;
  eltsz = GET_MODE_UNIT_SIZE (d->vmode);

  /* Generate two permutation masks.  In the first permutation mask
     the first quarter will contain indexes for the first half
     of the op0, the second quarter will contain bit 7 set, third quarter
     will contain indexes for the second half of the op0 and the
     last quarter bit 7 set.  In the second permutation mask
     the first quarter will contain bit 7 set, the second quarter
     indexes for the first half of the op1, the third quarter bit 7 set
     and last quarter indexes for the second half of the op1.
     I.e. the first mask e.g. for V32QImode extract even will be:
     0, 2, ..., 0xe, -128, ..., -128, 0, 2, ..., 0xe, -128, ..., -128
     (all values masked with 0xf except for -128) and second mask
     for extract even will be
     -128, ..., -128, 0, 2, ..., 0xe, -128, ..., -128, 0, 2, ..., 0xe.  */
  m128 = GEN_INT (-128);
  for (i = 0; i < nelt; ++i)
    {
      unsigned j, e = d->perm[i] & (nelt / 2 - 1);
      unsigned which = d->perm[i] >= nelt;
      unsigned xorv = (i >= nelt / 4 && i < 3 * nelt / 4) ? 24 : 0;

      for (j = 0; j < eltsz; ++j)
	{
	  rperm[which][(i * eltsz + j) ^ xorv] = GEN_INT (e * eltsz + j);
	  rperm[1 - which][(i * eltsz + j) ^ xorv] = m128;
	}
    }

  vperm = gen_rtx_CONST_VECTOR (V32QImode, gen_rtvec_v (32, rperm[0]));
  vperm = force_reg (V32QImode, vperm);

  l = gen_reg_rtx (V32QImode);
  op = gen_lowpart (V32QImode, d->op0);
  emit_insn (gen_avx2_pshufbv32qi3 (l, op, vperm));

  vperm = gen_rtx_CONST_VECTOR (V32QImode, gen_rtvec_v (32, rperm[1]));
  vperm = force_reg (V32QImode, vperm);

  h = gen_reg_rtx (V32QImode);
  op = gen_lowpart (V32QImode, d->op1);
  emit_insn (gen_avx2_pshufbv32qi3 (h, op, vperm));

  ior = gen_reg_rtx (V32QImode);
  emit_insn (gen_iorv32qi3 (ior, l, h));

  /* Permute the V4DImode quarters using { 0, 2, 1, 3 } permutation.  */
  op = gen_reg_rtx (V4DImode);
  ior = gen_lowpart (V4DImode, ior);
  emit_insn (gen_avx2_permv4di_1 (op, ior, const0_rtx, const2_rtx,
				  const1_rtx, GEN_INT (3)));
  emit_move_insn (d->target, gen_lowpart (d->vmode, op));

  return true;
}

/* A subroutine of expand_vec_perm_even_odd_1.  Implement extract-even
   and extract-odd permutations of two V16QI, V8HI, V16HI or V32QI operands
   with two "and" and "pack" or two "shift" and "pack" insns.  We should
   have already failed all two instruction sequences.  */

static bool
expand_vec_perm_even_odd_pack (struct expand_vec_perm_d *d)
{
  rtx op, dop0, dop1, t;
  unsigned i, odd, c, s, nelt = d->nelt;
  bool end_perm = false;
  machine_mode half_mode;
  rtx (*gen_and) (rtx, rtx, rtx);
  rtx (*gen_pack) (rtx, rtx, rtx);
  rtx (*gen_shift) (rtx, rtx, rtx);

  if (d->one_operand_p)
    return false;

  switch (d->vmode)
    {
    case E_V8HImode:
      /* Required for "pack".  */
      if (!TARGET_SSE4_1)
        return false;
      c = 0xffff;
      s = 16;
      half_mode = V4SImode;
      gen_and = gen_andv4si3;
      gen_pack = gen_sse4_1_packusdw;
      gen_shift = gen_lshrv4si3;
      break;
    case E_V16QImode:
      /* No check as all instructions are SSE2.  */
      c = 0xff;
      s = 8;
      half_mode = V8HImode;
      gen_and = gen_andv8hi3;
      gen_pack = gen_sse2_packuswb;
      gen_shift = gen_lshrv8hi3;
      break;
    case E_V16HImode:
      if (!TARGET_AVX2)
        return false;
      c = 0xffff;
      s = 16;
      half_mode = V8SImode;
      gen_and = gen_andv8si3;
      gen_pack = gen_avx2_packusdw;
      gen_shift = gen_lshrv8si3;
      end_perm = true;
      break;
    case E_V32QImode:
      if (!TARGET_AVX2)
        return false;
      c = 0xff;
      s = 8;
      half_mode = V16HImode;
      gen_and = gen_andv16hi3;
      gen_pack = gen_avx2_packuswb;
      gen_shift = gen_lshrv16hi3;
      end_perm = true;
      break;
    default:
      /* Only V8HI, V16QI, V16HI and V32QI modes are more profitable than
	 general shuffles.  */
      return false;
    }

  /* Check that permutation is even or odd.  */
  odd = d->perm[0];
  if (odd > 1)
    return false;

  for (i = 1; i < nelt; ++i)
    if (d->perm[i] != 2 * i + odd)
      return false;

  if (d->testing_p)
    return true;

  dop0 = gen_reg_rtx (half_mode);
  dop1 = gen_reg_rtx (half_mode);
  if (odd == 0)
    {
      t = gen_const_vec_duplicate (half_mode, GEN_INT (c));
      t = force_reg (half_mode, t);
      emit_insn (gen_and (dop0, t, gen_lowpart (half_mode, d->op0)));
      emit_insn (gen_and (dop1, t, gen_lowpart (half_mode, d->op1)));
    }
  else
    {
      emit_insn (gen_shift (dop0,
			    gen_lowpart (half_mode, d->op0),
			    GEN_INT (s)));
      emit_insn (gen_shift (dop1,
			    gen_lowpart (half_mode, d->op1),
			    GEN_INT (s)));
    }
  /* In AVX2 for 256 bit case we need to permute pack result.  */
  if (TARGET_AVX2 && end_perm)
    {
      op = gen_reg_rtx (d->vmode);
      t = gen_reg_rtx (V4DImode);
      emit_insn (gen_pack (op, dop0, dop1));
      emit_insn (gen_avx2_permv4di_1 (t,
				      gen_lowpart (V4DImode, op),
				      const0_rtx,
				      const2_rtx,
				      const1_rtx,
				      GEN_INT (3)));
      emit_move_insn (d->target, gen_lowpart (d->vmode, t));
    }
  else
    emit_insn (gen_pack (d->target, dop0, dop1));

  return true;
}

/* A subroutine of expand_vec_perm_even_odd_1.  Implement extract-even
   and extract-odd permutations of two V64QI operands
   with two "shifts", two "truncs" and one "concat" insns for "odd"
   and two "truncs" and one concat insn for "even."
   Have already failed all two instruction sequences.  */

static bool
expand_vec_perm_even_odd_trunc (struct expand_vec_perm_d *d)
{
  rtx t1, t2, t3, t4;
  unsigned i, odd, nelt = d->nelt;

  if (!TARGET_AVX512BW
      || d->one_operand_p
      || d->vmode != V64QImode)
    return false;

  /* Check that permutation is even or odd.  */
  odd = d->perm[0];
  if (odd > 1)
    return false;

  for (i = 1; i < nelt; ++i)
    if (d->perm[i] != 2 * i + odd)
      return false;

  if (d->testing_p)
    return true;


  if (odd)
    {
      t1 = gen_reg_rtx (V32HImode);
      t2 = gen_reg_rtx (V32HImode);
      emit_insn (gen_lshrv32hi3 (t1,
				 gen_lowpart (V32HImode, d->op0),
				 GEN_INT (8)));
      emit_insn (gen_lshrv32hi3 (t2,
				 gen_lowpart (V32HImode, d->op1),
				 GEN_INT (8)));
    }
  else
    {
      t1 = gen_lowpart (V32HImode, d->op0);
      t2 = gen_lowpart (V32HImode, d->op1);
    }

  t3 = gen_reg_rtx (V32QImode);
  t4 = gen_reg_rtx (V32QImode);
  emit_insn (gen_avx512bw_truncatev32hiv32qi2 (t3, t1));
  emit_insn (gen_avx512bw_truncatev32hiv32qi2 (t4, t2));
  emit_insn (gen_avx_vec_concatv64qi (d->target, t3, t4));

  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Implement extract-even
   and extract-odd permutations.  */

static bool
expand_vec_perm_even_odd_1 (struct expand_vec_perm_d *d, unsigned odd)
{
  rtx t1, t2, t3, t4, t5;

  switch (d->vmode)
    {
    case E_V4DFmode:
      if (d->testing_p)
	break;
      t1 = gen_reg_rtx (V4DFmode);
      t2 = gen_reg_rtx (V4DFmode);

      /* Shuffle the lanes around into { 0 1 4 5 } and { 2 3 6 7 }.  */
      emit_insn (gen_avx_vperm2f128v4df3 (t1, d->op0, d->op1, GEN_INT (0x20)));
      emit_insn (gen_avx_vperm2f128v4df3 (t2, d->op0, d->op1, GEN_INT (0x31)));

      /* Now an unpck[lh]pd will produce the result required.  */
      if (odd)
	t3 = gen_avx_unpckhpd256 (d->target, t1, t2);
      else
	t3 = gen_avx_unpcklpd256 (d->target, t1, t2);
      emit_insn (t3);
      break;

    case E_V8SFmode:
      {
	int mask = odd ? 0xdd : 0x88;

	if (d->testing_p)
	  break;
	t1 = gen_reg_rtx (V8SFmode);
	t2 = gen_reg_rtx (V8SFmode);
	t3 = gen_reg_rtx (V8SFmode);

	/* Shuffle within the 128-bit lanes to produce:
	   { 0 2 8 a 4 6 c e } | { 1 3 9 b 5 7 d f }.  */
	emit_insn (gen_avx_shufps256 (t1, d->op0, d->op1,
				      GEN_INT (mask)));

	/* Shuffle the lanes around to produce:
	   { 4 6 c e 0 2 8 a } and { 5 7 d f 1 3 9 b }.  */
	emit_insn (gen_avx_vperm2f128v8sf3 (t2, t1, t1,
					    GEN_INT (0x3)));

	/* Shuffle within the 128-bit lanes to produce:
	   { 0 2 4 6 4 6 0 2 } | { 1 3 5 7 5 7 1 3 }.  */
	emit_insn (gen_avx_shufps256 (t3, t1, t2, GEN_INT (0x44)));

	/* Shuffle within the 128-bit lanes to produce:
	   { 8 a c e c e 8 a } | { 9 b d f d f 9 b }.  */
	emit_insn (gen_avx_shufps256 (t2, t1, t2, GEN_INT (0xee)));

	/* Shuffle the lanes around to produce:
	   { 0 2 4 6 8 a c e } | { 1 3 5 7 9 b d f }.  */
	emit_insn (gen_avx_vperm2f128v8sf3 (d->target, t3, t2,
					    GEN_INT (0x20)));
      }
      break;

    case E_V2DFmode:
    case E_V4SFmode:
    case E_V2DImode:
    case E_V4SImode:
      /* These are always directly implementable by expand_vec_perm_1.  */
      gcc_unreachable ();

    case E_V8HImode:
      if (TARGET_SSE4_1)
	return expand_vec_perm_even_odd_pack (d);
      else if (TARGET_SSSE3 && !TARGET_SLOW_PSHUFB)
	return expand_vec_perm_pshufb2 (d);
      else
	{
	  if (d->testing_p)
	    break;
	  /* We need 2*log2(N)-1 operations to achieve odd/even
	     with interleave. */
	  t1 = gen_reg_rtx (V8HImode);
	  t2 = gen_reg_rtx (V8HImode);
	  emit_insn (gen_vec_interleave_highv8hi (t1, d->op0, d->op1));
	  emit_insn (gen_vec_interleave_lowv8hi (d->target, d->op0, d->op1));
	  emit_insn (gen_vec_interleave_highv8hi (t2, d->target, t1));
	  emit_insn (gen_vec_interleave_lowv8hi (d->target, d->target, t1));
	  if (odd)
	    t3 = gen_vec_interleave_highv8hi (d->target, d->target, t2);
	  else
	    t3 = gen_vec_interleave_lowv8hi (d->target, d->target, t2);
	  emit_insn (t3);
	}
      break;

    case E_V16QImode:
      return expand_vec_perm_even_odd_pack (d);

    case E_V16HImode:
    case E_V32QImode:
      return expand_vec_perm_even_odd_pack (d);

    case E_V64QImode:
      return expand_vec_perm_even_odd_trunc (d);

    case E_V4DImode:
      if (!TARGET_AVX2)
	{
	  struct expand_vec_perm_d d_copy = *d;
	  d_copy.vmode = V4DFmode;
	  if (d->testing_p)
	    d_copy.target = gen_raw_REG (V4DFmode, LAST_VIRTUAL_REGISTER + 1);
	  else
	    d_copy.target = gen_reg_rtx (V4DFmode);
	  d_copy.op0 = gen_lowpart (V4DFmode, d->op0);
	  d_copy.op1 = gen_lowpart (V4DFmode, d->op1);
	  if (expand_vec_perm_even_odd_1 (&d_copy, odd))
	    {
	      if (!d->testing_p)
		emit_move_insn (d->target,
				gen_lowpart (V4DImode, d_copy.target));
	      return true;
	    }
	  return false;
	}

      if (d->testing_p)
	break;

      t1 = gen_reg_rtx (V4DImode);
      t2 = gen_reg_rtx (V4DImode);

      /* Shuffle the lanes around into { 0 1 4 5 } and { 2 3 6 7 }.  */
      emit_insn (gen_avx2_permv2ti (t1, d->op0, d->op1, GEN_INT (0x20)));
      emit_insn (gen_avx2_permv2ti (t2, d->op0, d->op1, GEN_INT (0x31)));

      /* Now an vpunpck[lh]qdq will produce the result required.  */
      if (odd)
	t3 = gen_avx2_interleave_highv4di (d->target, t1, t2);
      else
	t3 = gen_avx2_interleave_lowv4di (d->target, t1, t2);
      emit_insn (t3);
      break;

    case E_V8SImode:
      if (!TARGET_AVX2)
	{
	  struct expand_vec_perm_d d_copy = *d;
	  d_copy.vmode = V8SFmode;
	  if (d->testing_p)
	    d_copy.target = gen_raw_REG (V8SFmode, LAST_VIRTUAL_REGISTER + 1);
	  else
	    d_copy.target = gen_reg_rtx (V8SFmode);
	  d_copy.op0 = gen_lowpart (V8SFmode, d->op0);
	  d_copy.op1 = gen_lowpart (V8SFmode, d->op1);
	  if (expand_vec_perm_even_odd_1 (&d_copy, odd))
	    {
	      if (!d->testing_p)
		emit_move_insn (d->target,
				gen_lowpart (V8SImode, d_copy.target));
	      return true;
	    }
	  return false;
	}

      if (d->testing_p)
	break;

      t1 = gen_reg_rtx (V8SImode);
      t2 = gen_reg_rtx (V8SImode);
      t3 = gen_reg_rtx (V4DImode);
      t4 = gen_reg_rtx (V4DImode);
      t5 = gen_reg_rtx (V4DImode);

      /* Shuffle the lanes around into
	 { 0 1 2 3 8 9 a b } and { 4 5 6 7 c d e f }.  */
      emit_insn (gen_avx2_permv2ti (t3, gen_lowpart (V4DImode, d->op0),
				    gen_lowpart (V4DImode, d->op1),
				    GEN_INT (0x20)));
      emit_insn (gen_avx2_permv2ti (t4, gen_lowpart (V4DImode, d->op0),
				    gen_lowpart (V4DImode, d->op1),
				    GEN_INT (0x31)));

      /* Swap the 2nd and 3rd position in each lane into
	 { 0 2 1 3 8 a 9 b } and { 4 6 5 7 c e d f }.  */
      emit_insn (gen_avx2_pshufdv3 (t1, gen_lowpart (V8SImode, t3),
				    GEN_INT (2 * 4 + 1 * 16 + 3 * 64)));
      emit_insn (gen_avx2_pshufdv3 (t2, gen_lowpart (V8SImode, t4),
				    GEN_INT (2 * 4 + 1 * 16 + 3 * 64)));

      /* Now an vpunpck[lh]qdq will produce
	 { 0 2 4 6 8 a c e } resp. { 1 3 5 7 9 b d f }.  */
      if (odd)
	t3 = gen_avx2_interleave_highv4di (t5, gen_lowpart (V4DImode, t1),
					   gen_lowpart (V4DImode, t2));
      else
	t3 = gen_avx2_interleave_lowv4di (t5, gen_lowpart (V4DImode, t1),
					  gen_lowpart (V4DImode, t2));
      emit_insn (t3);
      emit_move_insn (d->target, gen_lowpart (V8SImode, t5));
      break;

    default:
      gcc_unreachable ();
    }

  return true;
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Pattern match
   extract-even and extract-odd permutations.  */

static bool
expand_vec_perm_even_odd (struct expand_vec_perm_d *d)
{
  unsigned i, odd, nelt = d->nelt;

  odd = d->perm[0];
  if (odd != 0 && odd != 1)
    return false;

  for (i = 1; i < nelt; ++i)
    if (d->perm[i] != 2 * i + odd)
      return false;

  return expand_vec_perm_even_odd_1 (d, odd);
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Implement broadcast
   permutations.  We assume that expand_vec_perm_1 has already failed.  */

static bool
expand_vec_perm_broadcast_1 (struct expand_vec_perm_d *d)
{
  unsigned elt = d->perm[0], nelt2 = d->nelt / 2;
  machine_mode vmode = d->vmode;
  unsigned char perm2[4];
  rtx op0 = d->op0, dest;
  bool ok;

  switch (vmode)
    {
    case E_V4DFmode:
    case E_V8SFmode:
      /* These are special-cased in sse.md so that we can optionally
	 use the vbroadcast instruction.  They expand to two insns
	 if the input happens to be in a register.  */
      gcc_unreachable ();

    case E_V2DFmode:
    case E_V2DImode:
    case E_V4SFmode:
    case E_V4SImode:
      /* These are always implementable using standard shuffle patterns.  */
      gcc_unreachable ();

    case E_V8HImode:
    case E_V16QImode:
      /* These can be implemented via interleave.  We save one insn by
	 stopping once we have promoted to V4SImode and then use pshufd.  */
      if (d->testing_p)
	return true;
      do
	{
	  rtx dest;
	  rtx (*gen) (rtx, rtx, rtx)
	    = vmode == V16QImode ? gen_vec_interleave_lowv16qi
				 : gen_vec_interleave_lowv8hi;

	  if (elt >= nelt2)
	    {
	      gen = vmode == V16QImode ? gen_vec_interleave_highv16qi
				       : gen_vec_interleave_highv8hi;
	      elt -= nelt2;
	    }
	  nelt2 /= 2;

	  dest = gen_reg_rtx (vmode);
	  emit_insn (gen (dest, op0, op0));
	  vmode = get_mode_wider_vector (vmode);
	  op0 = gen_lowpart (vmode, dest);
	}
      while (vmode != V4SImode);

      memset (perm2, elt, 4);
      dest = gen_reg_rtx (V4SImode);
      ok = expand_vselect (dest, op0, perm2, 4, d->testing_p);
      gcc_assert (ok);
      if (!d->testing_p)
	emit_move_insn (d->target, gen_lowpart (d->vmode, dest));
      return true;

    case E_V64QImode:
    case E_V32QImode:
    case E_V16HImode:
    case E_V8SImode:
    case E_V4DImode:
      /* For AVX2 broadcasts of the first element vpbroadcast* or
	 vpermq should be used by expand_vec_perm_1.  */
      gcc_assert (!TARGET_AVX2 || d->perm[0]);
      return false;

    default:
      gcc_unreachable ();
    }
}

/* A subroutine of ix86_expand_vec_perm_builtin_1.  Pattern match
   broadcast permutations.  */

static bool
expand_vec_perm_broadcast (struct expand_vec_perm_d *d)
{
  unsigned i, elt, nelt = d->nelt;

  if (!d->one_operand_p)
    return false;

  elt = d->perm[0];
  for (i = 1; i < nelt; ++i)
    if (d->perm[i] != elt)
      return false;

  return expand_vec_perm_broadcast_1 (d);
}

/* Implement arbitrary permutations of two V64QImode operands
   with 2 vperm[it]2w, 2 vpshufb and one vpor instruction.  */
static bool
expand_vec_perm_vpermt2_vpshub2 (struct expand_vec_perm_d *d)
{
  if (!TARGET_AVX512BW || !(d->vmode == V64QImode))
    return false;

  if (d->testing_p)
    return true;

  struct expand_vec_perm_d ds[2];
  rtx rperm[128], vperm, target0, target1;
  unsigned int i, nelt;
  machine_mode vmode;

  nelt = d->nelt;
  vmode = V64QImode;

  for (i = 0; i < 2; i++)
    {
      ds[i] = *d;
      ds[i].vmode = V32HImode;
      ds[i].nelt = 32;
      ds[i].target = gen_reg_rtx (V32HImode);
      ds[i].op0 = gen_lowpart (V32HImode, d->op0);
      ds[i].op1 = gen_lowpart (V32HImode, d->op1);
    }

  /* Prepare permutations such that the first one takes care of
     putting the even bytes into the right positions or one higher
     positions (ds[0]) and the second one takes care of
     putting the odd bytes into the right positions or one below
     (ds[1]).  */

  for (i = 0; i < nelt; i++)
    {
      ds[i & 1].perm[i / 2] = d->perm[i] / 2;
      if (i & 1)
	{
	  rperm[i] = constm1_rtx;
	  rperm[i + 64] = GEN_INT ((i & 14) + (d->perm[i] & 1));
	}
      else
	{
	  rperm[i] = GEN_INT ((i & 14) + (d->perm[i] & 1));
	  rperm[i + 64] = constm1_rtx;
	}
    }

  bool ok = expand_vec_perm_1 (&ds[0]);
  gcc_assert (ok);
  ds[0].target = gen_lowpart (V64QImode, ds[0].target);

  ok = expand_vec_perm_1 (&ds[1]);
  gcc_assert (ok);
  ds[1].target = gen_lowpart (V64QImode, ds[1].target);

  vperm = gen_rtx_CONST_VECTOR (V64QImode, gen_rtvec_v (64, rperm));
  vperm = force_reg (vmode, vperm);
  target0 = gen_reg_rtx (V64QImode);
  emit_insn (gen_avx512bw_pshufbv64qi3 (target0, ds[0].target, vperm));

  vperm = gen_rtx_CONST_VECTOR (V64QImode, gen_rtvec_v (64, rperm + 64));
  vperm = force_reg (vmode, vperm);
  target1 = gen_reg_rtx (V64QImode);
  emit_insn (gen_avx512bw_pshufbv64qi3 (target1, ds[1].target, vperm));

  emit_insn (gen_iorv64qi3 (d->target, target0, target1));
  return true;
}

/* Implement arbitrary permutation of two V32QImode and V16QImode operands
   with 4 vpshufb insns, 2 vpermq and 3 vpor.  We should have already failed
   all the shorter instruction sequences.  */

static bool
expand_vec_perm_vpshufb4_vpermq2 (struct expand_vec_perm_d *d)
{
  rtx rperm[4][32], vperm, l[2], h[2], op, m128;
  unsigned int i, nelt, eltsz;
  bool used[4];

  if (!TARGET_AVX2
      || d->one_operand_p
      || (d->vmode != V32QImode && d->vmode != V16HImode))
    return false;

  if (d->testing_p)
    return true;

  nelt = d->nelt;
  eltsz = GET_MODE_UNIT_SIZE (d->vmode);

  /* Generate 4 permutation masks.  If the required element is within
     the same lane, it is shuffled in.  If the required element from the
     other lane, force a zero by setting bit 7 in the permutation mask.
     In the other mask the mask has non-negative elements if element
     is requested from the other lane, but also moved to the other lane,
     so that the result of vpshufb can have the two V2TImode halves
     swapped.  */
  m128 = GEN_INT (-128);
  for (i = 0; i < 32; ++i)
    {
      rperm[0][i] = m128;
      rperm[1][i] = m128;
      rperm[2][i] = m128;
      rperm[3][i] = m128;
    }
  used[0] = false;
  used[1] = false;
  used[2] = false;
  used[3] = false;
  for (i = 0; i < nelt; ++i)
    {
      unsigned j, e = d->perm[i] & (nelt / 2 - 1);
      unsigned xlane = ((d->perm[i] ^ i) & (nelt / 2)) * eltsz;
      unsigned int which = ((d->perm[i] & nelt) ? 2 : 0) + (xlane ? 1 : 0);

      for (j = 0; j < eltsz; ++j)
	rperm[which][(i * eltsz + j) ^ xlane] = GEN_INT (e * eltsz + j);
      used[which] = true;
    }

  for (i = 0; i < 2; ++i)
    {
      if (!used[2 * i + 1])
	{
	  h[i] = NULL_RTX;
	  continue;
	}
      vperm = gen_rtx_CONST_VECTOR (V32QImode,
				    gen_rtvec_v (32, rperm[2 * i + 1]));
      vperm = force_reg (V32QImode, vperm);
      h[i] = gen_reg_rtx (V32QImode);
      op = gen_lowpart (V32QImode, i ? d->op1 : d->op0);
      emit_insn (gen_avx2_pshufbv32qi3 (h[i], op, vperm));
    }

  /* Swap the 128-byte lanes of h[X].  */
  for (i = 0; i < 2; ++i)
   {
     if (h[i] == NULL_RTX)
       continue;
     op = gen_reg_rtx (V4DImode);
     emit_insn (gen_avx2_permv4di_1 (op, gen_lowpart (V4DImode, h[i]),
				     const2_rtx, GEN_INT (3), const0_rtx,
				     const1_rtx));
     h[i] = gen_lowpart (V32QImode, op);
   }

  for (i = 0; i < 2; ++i)
    {
      if (!used[2 * i])
	{
	  l[i] = NULL_RTX;
	  continue;
	}
      vperm = gen_rtx_CONST_VECTOR (V32QImode, gen_rtvec_v (32, rperm[2 * i]));
      vperm = force_reg (V32QImode, vperm);
      l[i] = gen_reg_rtx (V32QImode);
      op = gen_lowpart (V32QImode, i ? d->op1 : d->op0);
      emit_insn (gen_avx2_pshufbv32qi3 (l[i], op, vperm));
    }

  for (i = 0; i < 2; ++i)
    {
      if (h[i] && l[i])
	{
	  op = gen_reg_rtx (V32QImode);
	  emit_insn (gen_iorv32qi3 (op, l[i], h[i]));
	  l[i] = op;
	}
      else if (h[i])
	l[i] = h[i];
    }

  gcc_assert (l[0] && l[1]);
  op = d->target;
  if (d->vmode != V32QImode)
    op = gen_reg_rtx (V32QImode);
  emit_insn (gen_iorv32qi3 (op, l[0], l[1]));
  if (op != d->target)
    emit_move_insn (d->target, gen_lowpart (d->vmode, op));
  return true;
}

/* The guts of ix86_vectorize_vec_perm_const.  With all of the interface bits
   taken care of, perform the expansion in D and return true on success.  */

static bool
ix86_expand_vec_perm_const_1 (struct expand_vec_perm_d *d)
{
  /* Try a single instruction expansion.  */
  if (expand_vec_perm_1 (d))
    return true;

  /* Try sequences of two instructions.  */

  if (expand_vec_perm_pshuflw_pshufhw (d))
    return true;

  if (expand_vec_perm_palignr (d, false))
    return true;

  if (expand_vec_perm_interleave2 (d))
    return true;

  if (expand_vec_perm_broadcast (d))
    return true;

  if (expand_vec_perm_vpermq_perm_1 (d))
    return true;

  if (expand_vec_perm_vperm2f128 (d))
    return true;

  if (expand_vec_perm_pblendv (d))
    return true;

  /* Try sequences of three instructions.  */

  if (expand_vec_perm_even_odd_pack (d))
    return true;

  if (expand_vec_perm_2vperm2f128_vshuf (d))
    return true;

  if (expand_vec_perm_pshufb2 (d))
    return true;

  if (expand_vec_perm_interleave3 (d))
    return true;

  if (expand_vec_perm_vperm2f128_vblend (d))
    return true;

  /* Try sequences of four instructions.  */

  if (expand_vec_perm_even_odd_trunc (d))
    return true;
  if (expand_vec_perm_vpshufb2_vpermq (d))
    return true;

  if (expand_vec_perm_vpshufb2_vpermq_even_odd (d))
    return true;

  if (expand_vec_perm_vpermt2_vpshub2 (d))
    return true;

  /* ??? Look for narrow permutations whose element orderings would
     allow the promotion to a wider mode.  */

  /* ??? Look for sequences of interleave or a wider permute that place
     the data into the correct lanes for a half-vector shuffle like
     pshuf[lh]w or vpermilps.  */

  /* ??? Look for sequences of interleave that produce the desired results.
     The combinatorics of punpck[lh] get pretty ugly... */

  if (expand_vec_perm_even_odd (d))
    return true;

  /* Even longer sequences.  */
  if (expand_vec_perm_vpshufb4_vpermq2 (d))
    return true;

  /* See if we can get the same permutation in different vector integer
     mode.  */
  struct expand_vec_perm_d nd;
  if (canonicalize_vector_int_perm (d, &nd) && expand_vec_perm_1 (&nd))
    {
      if (!d->testing_p)
	emit_move_insn (d->target, gen_lowpart (d->vmode, nd.target));
      return true;
    }

  return false;
}

/* If a permutation only uses one operand, make it clear. Returns true
   if the permutation references both operands.  */

static bool
canonicalize_perm (struct expand_vec_perm_d *d)
{
  int i, which, nelt = d->nelt;

  for (i = which = 0; i < nelt; ++i)
      which |= (d->perm[i] < nelt ? 1 : 2);

  d->one_operand_p = true;
  switch (which)
    {
    default:
      gcc_unreachable();

    case 3:
      if (!rtx_equal_p (d->op0, d->op1))
        {
	  d->one_operand_p = false;
	  break;
        }
      /* The elements of PERM do not suggest that only the first operand
	 is used, but both operands are identical.  Allow easier matching
	 of the permutation by folding the permutation into the single
	 input vector.  */
      /* FALLTHRU */

    case 2:
      for (i = 0; i < nelt; ++i)
        d->perm[i] &= nelt - 1;
      d->op0 = d->op1;
      break;

    case 1:
      d->op1 = d->op0;
      break;
    }

  return (which == 3);
}

/* Implement TARGET_VECTORIZE_VEC_PERM_CONST.  */

static bool
ix86_vectorize_vec_perm_const (machine_mode vmode, rtx target, rtx op0,
			       rtx op1, const vec_perm_indices &sel)
{
  struct expand_vec_perm_d d;
  unsigned char perm[MAX_VECT_LEN];
  unsigned int i, nelt, which;
  bool two_args;

  d.target = target;
  d.op0 = op0;
  d.op1 = op1;

  d.vmode = vmode;
  gcc_assert (VECTOR_MODE_P (d.vmode));
  d.nelt = nelt = GET_MODE_NUNITS (d.vmode);
  d.testing_p = !target;

  gcc_assert (sel.length () == nelt);
  gcc_checking_assert (sizeof (d.perm) == sizeof (perm));

  /* Given sufficient ISA support we can just return true here
     for selected vector modes.  */
  switch (d.vmode)
    {
    case E_V16SFmode:
    case E_V16SImode:
    case E_V8DImode:
    case E_V8DFmode:
      if (!TARGET_AVX512F)
	return false;
      /* All implementable with a single vperm[it]2 insn.  */
      if (d.testing_p)
	return true;
      break;
    case E_V32HImode:
      if (!TARGET_AVX512BW)
	return false;
      if (d.testing_p)
	/* All implementable with a single vperm[it]2 insn.  */
	return true;
      break;
    case E_V64QImode:
      if (!TARGET_AVX512BW)
	return false;
      if (d.testing_p)
	/* Implementable with 2 vperm[it]2, 2 vpshufb and 1 or insn.  */
	return true;
      break;
    case E_V8SImode:
    case E_V8SFmode:
    case E_V4DFmode:
    case E_V4DImode:
      if (!TARGET_AVX)
	return false;
      if (d.testing_p && TARGET_AVX512VL)
	/* All implementable with a single vperm[it]2 insn.  */
	return true;
      break;
    case E_V16HImode:
      if (!TARGET_SSE2)
	return false;
      if (d.testing_p && TARGET_AVX2)
	/* Implementable with 4 vpshufb insns, 2 vpermq and 3 vpor insns.  */
	return true;
      break;
    case E_V32QImode:
      if (!TARGET_SSE2)
	return false;
      if (d.testing_p && TARGET_AVX2)
	/* Implementable with 4 vpshufb insns, 2 vpermq and 3 vpor insns.  */
	return true;
      break;
    case E_V8HImode:
    case E_V16QImode:
      if (!TARGET_SSE2)
	return false;
      /* Fall through.  */
    case E_V4SImode:
    case E_V4SFmode:
      if (!TARGET_SSE)
	return false;
      /* All implementable with a single vpperm insn.  */
      if (d.testing_p && TARGET_XOP)
	return true;
      /* All implementable with 2 pshufb + 1 ior.  */
      if (d.testing_p && TARGET_SSSE3)
	return true;
      break;
    case E_V2DImode:
    case E_V2DFmode:
      if (!TARGET_SSE)
	return false;
      /* All implementable with shufpd or unpck[lh]pd.  */
      if (d.testing_p)
	return true;
      break;
    default:
      return false;
    }

  for (i = which = 0; i < nelt; ++i)
    {
      unsigned char e = sel[i];
      gcc_assert (e < 2 * nelt);
      d.perm[i] = e;
      perm[i] = e;
      which |= (e < nelt ? 1 : 2);
    }

  if (d.testing_p)
    {
      /* For all elements from second vector, fold the elements to first.  */
      if (which == 2)
	for (i = 0; i < nelt; ++i)
	  d.perm[i] -= nelt;

      /* Check whether the mask can be applied to the vector type.  */
      d.one_operand_p = (which != 3);

      /* Implementable with shufps or pshufd.  */
      if (d.one_operand_p && (d.vmode == V4SFmode || d.vmode == V4SImode))
	return true;

      /* Otherwise we have to go through the motions and see if we can
	 figure out how to generate the requested permutation.  */
      d.target = gen_raw_REG (d.vmode, LAST_VIRTUAL_REGISTER + 1);
      d.op1 = d.op0 = gen_raw_REG (d.vmode, LAST_VIRTUAL_REGISTER + 2);
      if (!d.one_operand_p)
	d.op1 = gen_raw_REG (d.vmode, LAST_VIRTUAL_REGISTER + 3);

      start_sequence ();
      bool ret = ix86_expand_vec_perm_const_1 (&d);
      end_sequence ();

      return ret;
    }

  two_args = canonicalize_perm (&d);

  if (ix86_expand_vec_perm_const_1 (&d))
    return true;

  /* If the selector says both arguments are needed, but the operands are the
     same, the above tried to expand with one_operand_p and flattened selector.
     If that didn't work, retry without one_operand_p; we succeeded with that
     during testing.  */
  if (two_args && d.one_operand_p)
    {
      d.one_operand_p = false;
      memcpy (d.perm, perm, sizeof (perm));
      return ix86_expand_vec_perm_const_1 (&d);
    }

  return false;
}

void
ix86_expand_vec_extract_even_odd (rtx targ, rtx op0, rtx op1, unsigned odd)
{
  struct expand_vec_perm_d d;
  unsigned i, nelt;

  d.target = targ;
  d.op0 = op0;
  d.op1 = op1;
  d.vmode = GET_MODE (targ);
  d.nelt = nelt = GET_MODE_NUNITS (d.vmode);
  d.one_operand_p = false;
  d.testing_p = false;

  for (i = 0; i < nelt; ++i)
    d.perm[i] = i * 2 + odd;

  /* We'll either be able to implement the permutation directly...  */
  if (expand_vec_perm_1 (&d))
    return;

  /* ... or we use the special-case patterns.  */
  expand_vec_perm_even_odd_1 (&d, odd);
}

static void
ix86_expand_vec_interleave (rtx targ, rtx op0, rtx op1, bool high_p)
{
  struct expand_vec_perm_d d;
  unsigned i, nelt, base;
  bool ok;

  d.target = targ;
  d.op0 = op0;
  d.op1 = op1;
  d.vmode = GET_MODE (targ);
  d.nelt = nelt = GET_MODE_NUNITS (d.vmode);
  d.one_operand_p = false;
  d.testing_p = false;

  base = high_p ? nelt / 2 : 0;
  for (i = 0; i < nelt / 2; ++i)
    {
      d.perm[i * 2] = i + base;
      d.perm[i * 2 + 1] = i + base + nelt;
    }

  /* Note that for AVX this isn't one instruction.  */
  ok = ix86_expand_vec_perm_const_1 (&d);
  gcc_assert (ok);
}


/* Expand a vector operation CODE for a V*QImode in terms of the
   same operation on V*HImode.  */

void
ix86_expand_vecop_qihi (enum rtx_code code, rtx dest, rtx op1, rtx op2)
{
  machine_mode qimode = GET_MODE (dest);
  machine_mode himode;
  rtx (*gen_il) (rtx, rtx, rtx);
  rtx (*gen_ih) (rtx, rtx, rtx);
  rtx op1_l, op1_h, op2_l, op2_h, res_l, res_h;
  struct expand_vec_perm_d d;
  bool ok, full_interleave;
  bool uns_p = false;
  int i;

  switch (qimode)
    {
    case E_V16QImode:
      himode = V8HImode;
      gen_il = gen_vec_interleave_lowv16qi;
      gen_ih = gen_vec_interleave_highv16qi;
      break;
    case E_V32QImode:
      himode = V16HImode;
      gen_il = gen_avx2_interleave_lowv32qi;
      gen_ih = gen_avx2_interleave_highv32qi;
      break;
    case E_V64QImode:
      himode = V32HImode;
      gen_il = gen_avx512bw_interleave_lowv64qi;
      gen_ih = gen_avx512bw_interleave_highv64qi;
      break;
    default:
      gcc_unreachable ();
    }

  op2_l = op2_h = op2;
  switch (code)
    {
    case MULT:
      /* Unpack data such that we've got a source byte in each low byte of
	 each word.  We don't care what goes into the high byte of each word.
	 Rather than trying to get zero in there, most convenient is to let
	 it be a copy of the low byte.  */
      op2_l = gen_reg_rtx (qimode);
      op2_h = gen_reg_rtx (qimode);
      emit_insn (gen_il (op2_l, op2, op2));
      emit_insn (gen_ih (op2_h, op2, op2));

      op1_l = gen_reg_rtx (qimode);
      op1_h = gen_reg_rtx (qimode);
      emit_insn (gen_il (op1_l, op1, op1));
      emit_insn (gen_ih (op1_h, op1, op1));
      full_interleave = qimode == V16QImode;
      break;

    case ASHIFT:
    case LSHIFTRT:
      uns_p = true;
      /* FALLTHRU */
    case ASHIFTRT:
      op1_l = gen_reg_rtx (himode);
      op1_h = gen_reg_rtx (himode);
      ix86_expand_sse_unpack (op1_l, op1, uns_p, false);
      ix86_expand_sse_unpack (op1_h, op1, uns_p, true);
      full_interleave = true;
      break;
    default:
      gcc_unreachable ();
    }

  /* Perform the operation.  */
  res_l = expand_simple_binop (himode, code, op1_l, op2_l, NULL_RTX,
			       1, OPTAB_DIRECT);
  res_h = expand_simple_binop (himode, code, op1_h, op2_h, NULL_RTX,
			       1, OPTAB_DIRECT);
  gcc_assert (res_l && res_h);

  /* Merge the data back into the right place.  */
  d.target = dest;
  d.op0 = gen_lowpart (qimode, res_l);
  d.op1 = gen_lowpart (qimode, res_h);
  d.vmode = qimode;
  d.nelt = GET_MODE_NUNITS (qimode);
  d.one_operand_p = false;
  d.testing_p = false;

  if (full_interleave)
    {
      /* For SSE2, we used an full interleave, so the desired
	 results are in the even elements.  */
      for (i = 0; i < d.nelt; ++i)
	d.perm[i] = i * 2;
    }
  else
    {
      /* For AVX, the interleave used above was not cross-lane.  So the
	 extraction is evens but with the second and third quarter swapped.
	 Happily, that is even one insn shorter than even extraction.
	 For AVX512BW we have 4 lanes.  We extract evens from within a lane,
	 always first from the first and then from the second source operand,
	 the index bits above the low 4 bits remains the same.
	 Thus, for d.nelt == 32 we want permutation
	 0,2,4,..14, 32,34,36,..46, 16,18,20,..30, 48,50,52,..62
	 and for d.nelt == 64 we want permutation
	 0,2,4,..14, 64,66,68,..78, 16,18,20,..30, 80,82,84,..94,
	 32,34,36,..46, 96,98,100,..110, 48,50,52,..62, 112,114,116,..126.  */
      for (i = 0; i < d.nelt; ++i)
	d.perm[i] = ((i * 2) & 14) + ((i & 8) ? d.nelt : 0) + (i & ~15);
    }

  ok = ix86_expand_vec_perm_const_1 (&d);
  gcc_assert (ok);

  set_unique_reg_note (get_last_insn (), REG_EQUAL,
		       gen_rtx_fmt_ee (code, qimode, op1, op2));
}

/* Helper function of ix86_expand_mul_widen_evenodd.  Return true
   if op is CONST_VECTOR with all odd elements equal to their
   preceding element.  */

static bool
const_vector_equal_evenodd_p (rtx op)
{
  machine_mode mode = GET_MODE (op);
  int i, nunits = GET_MODE_NUNITS (mode);
  if (GET_CODE (op) != CONST_VECTOR
      || nunits != CONST_VECTOR_NUNITS (op))
    return false;
  for (i = 0; i < nunits; i += 2)
    if (CONST_VECTOR_ELT (op, i) != CONST_VECTOR_ELT (op, i + 1))
      return false;
  return true;
}

void
ix86_expand_mul_widen_evenodd (rtx dest, rtx op1, rtx op2,
			       bool uns_p, bool odd_p)
{
  machine_mode mode = GET_MODE (op1);
  machine_mode wmode = GET_MODE (dest);
  rtx x;
  rtx orig_op1 = op1, orig_op2 = op2;

  if (!nonimmediate_operand (op1, mode))
    op1 = force_reg (mode, op1);
  if (!nonimmediate_operand (op2, mode))
    op2 = force_reg (mode, op2);

  /* We only play even/odd games with vectors of SImode.  */
  gcc_assert (mode == V4SImode || mode == V8SImode || mode == V16SImode);

  /* If we're looking for the odd results, shift those members down to
     the even slots.  For some cpus this is faster than a PSHUFD.  */
  if (odd_p)
    {
      /* For XOP use vpmacsdqh, but only for smult, as it is only
	 signed.  */
      if (TARGET_XOP && mode == V4SImode && !uns_p)
	{
	  x = force_reg (wmode, CONST0_RTX (wmode));
	  emit_insn (gen_xop_pmacsdqh (dest, op1, op2, x));
	  return;
	}

      x = GEN_INT (GET_MODE_UNIT_BITSIZE (mode));
      if (!const_vector_equal_evenodd_p (orig_op1))
	op1 = expand_binop (wmode, lshr_optab, gen_lowpart (wmode, op1),
			    x, NULL, 1, OPTAB_DIRECT);
      if (!const_vector_equal_evenodd_p (orig_op2))
	op2 = expand_binop (wmode, lshr_optab, gen_lowpart (wmode, op2),
			    x, NULL, 1, OPTAB_DIRECT);
      op1 = gen_lowpart (mode, op1);
      op2 = gen_lowpart (mode, op2);
    }

  if (mode == V16SImode)
    {
      if (uns_p)
	x = gen_vec_widen_umult_even_v16si (dest, op1, op2);
      else
	x = gen_vec_widen_smult_even_v16si (dest, op1, op2);
    }
  else if (mode == V8SImode)
    {
      if (uns_p)
	x = gen_vec_widen_umult_even_v8si (dest, op1, op2);
      else
	x = gen_vec_widen_smult_even_v8si (dest, op1, op2);
    }
  else if (uns_p)
    x = gen_vec_widen_umult_even_v4si (dest, op1, op2);
  else if (TARGET_SSE4_1)
    x = gen_sse4_1_mulv2siv2di3 (dest, op1, op2);
  else
    {
      rtx s1, s2, t0, t1, t2;

      /* The easiest way to implement this without PMULDQ is to go through
	 the motions as if we are performing a full 64-bit multiply.  With
	 the exception that we need to do less shuffling of the elements.  */

      /* Compute the sign-extension, aka highparts, of the two operands.  */
      s1 = ix86_expand_sse_cmp (gen_reg_rtx (mode), GT, CONST0_RTX (mode),
				op1, pc_rtx, pc_rtx);
      s2 = ix86_expand_sse_cmp (gen_reg_rtx (mode), GT, CONST0_RTX (mode),
				op2, pc_rtx, pc_rtx);

      /* Multiply LO(A) * HI(B), and vice-versa.  */
      t1 = gen_reg_rtx (wmode);
      t2 = gen_reg_rtx (wmode);
      emit_insn (gen_vec_widen_umult_even_v4si (t1, s1, op2));
      emit_insn (gen_vec_widen_umult_even_v4si (t2, s2, op1));

      /* Multiply LO(A) * LO(B).  */
      t0 = gen_reg_rtx (wmode);
      emit_insn (gen_vec_widen_umult_even_v4si (t0, op1, op2));

      /* Combine and shift the highparts into place.  */
      t1 = expand_binop (wmode, add_optab, t1, t2, t1, 1, OPTAB_DIRECT);
      t1 = expand_binop (wmode, ashl_optab, t1, GEN_INT (32), t1,
			 1, OPTAB_DIRECT);

      /* Combine high and low parts.  */
      force_expand_binop (wmode, add_optab, t0, t1, dest, 1, OPTAB_DIRECT);
      return;
    }
  emit_insn (x);
}

void
ix86_expand_mul_widen_hilo (rtx dest, rtx op1, rtx op2,
			    bool uns_p, bool high_p)
{
  machine_mode wmode = GET_MODE (dest);
  machine_mode mode = GET_MODE (op1);
  rtx t1, t2, t3, t4, mask;

  switch (mode)
    {
    case E_V4SImode:
      t1 = gen_reg_rtx (mode);
      t2 = gen_reg_rtx (mode);
      if (TARGET_XOP && !uns_p)
	{
	  /* With XOP, we have pmacsdqh, aka mul_widen_odd.  In this case,
	     shuffle the elements once so that all elements are in the right
	     place for immediate use: { A C B D }.  */
	  emit_insn (gen_sse2_pshufd_1 (t1, op1, const0_rtx, const2_rtx,
					const1_rtx, GEN_INT (3)));
	  emit_insn (gen_sse2_pshufd_1 (t2, op2, const0_rtx, const2_rtx,
					const1_rtx, GEN_INT (3)));
	}
      else
	{
	  /* Put the elements into place for the multiply.  */
	  ix86_expand_vec_interleave (t1, op1, op1, high_p);
	  ix86_expand_vec_interleave (t2, op2, op2, high_p);
	  high_p = false;
	}
      ix86_expand_mul_widen_evenodd (dest, t1, t2, uns_p, high_p);
      break;

    case E_V8SImode:
      /* Shuffle the elements between the lanes.  After this we
	 have { A B E F | C D G H } for each operand.  */
      t1 = gen_reg_rtx (V4DImode);
      t2 = gen_reg_rtx (V4DImode);
      emit_insn (gen_avx2_permv4di_1 (t1, gen_lowpart (V4DImode, op1),
				      const0_rtx, const2_rtx,
				      const1_rtx, GEN_INT (3)));
      emit_insn (gen_avx2_permv4di_1 (t2, gen_lowpart (V4DImode, op2),
				      const0_rtx, const2_rtx,
				      const1_rtx, GEN_INT (3)));

      /* Shuffle the elements within the lanes.  After this we
	 have { A A B B | C C D D } or { E E F F | G G H H }.  */
      t3 = gen_reg_rtx (V8SImode);
      t4 = gen_reg_rtx (V8SImode);
      mask = GEN_INT (high_p
		      ? 2 + (2 << 2) + (3 << 4) + (3 << 6)
		      : 0 + (0 << 2) + (1 << 4) + (1 << 6));
      emit_insn (gen_avx2_pshufdv3 (t3, gen_lowpart (V8SImode, t1), mask));
      emit_insn (gen_avx2_pshufdv3 (t4, gen_lowpart (V8SImode, t2), mask));

      ix86_expand_mul_widen_evenodd (dest, t3, t4, uns_p, false);
      break;

    case E_V8HImode:
    case E_V16HImode:
      t1 = expand_binop (mode, smul_optab, op1, op2, NULL_RTX,
			 uns_p, OPTAB_DIRECT);
      t2 = expand_binop (mode,
			 uns_p ? umul_highpart_optab : smul_highpart_optab,
			 op1, op2, NULL_RTX, uns_p, OPTAB_DIRECT);
      gcc_assert (t1 && t2);

      t3 = gen_reg_rtx (mode);
      ix86_expand_vec_interleave (t3, t1, t2, high_p);
      emit_move_insn (dest, gen_lowpart (wmode, t3));
      break;

    case E_V16QImode:
    case E_V32QImode:
    case E_V32HImode:
    case E_V16SImode:
    case E_V64QImode:
      t1 = gen_reg_rtx (wmode);
      t2 = gen_reg_rtx (wmode);
      ix86_expand_sse_unpack (t1, op1, uns_p, high_p);
      ix86_expand_sse_unpack (t2, op2, uns_p, high_p);

      emit_insn (gen_rtx_SET (dest, gen_rtx_MULT (wmode, t1, t2)));
      break;

    default:
      gcc_unreachable ();
    }
}

void
ix86_expand_sse2_mulv4si3 (rtx op0, rtx op1, rtx op2)
{
  rtx res_1, res_2, res_3, res_4;

  res_1 = gen_reg_rtx (V4SImode);
  res_2 = gen_reg_rtx (V4SImode);
  res_3 = gen_reg_rtx (V2DImode);
  res_4 = gen_reg_rtx (V2DImode);
  ix86_expand_mul_widen_evenodd (res_3, op1, op2, true, false);
  ix86_expand_mul_widen_evenodd (res_4, op1, op2, true, true);

  /* Move the results in element 2 down to element 1; we don't care
     what goes in elements 2 and 3.  Then we can merge the parts
     back together with an interleave.

     Note that two other sequences were tried:
     (1) Use interleaves at the start instead of psrldq, which allows
     us to use a single shufps to merge things back at the end.
     (2) Use shufps here to combine the two vectors, then pshufd to
     put the elements in the correct order.
     In both cases the cost of the reformatting stall was too high
     and the overall sequence slower.  */

  emit_insn (gen_sse2_pshufd_1 (res_1, gen_lowpart (V4SImode, res_3),
				const0_rtx, const2_rtx,
				const0_rtx, const0_rtx));
  emit_insn (gen_sse2_pshufd_1 (res_2, gen_lowpart (V4SImode, res_4),
				const0_rtx, const2_rtx,
				const0_rtx, const0_rtx));
  res_1 = emit_insn (gen_vec_interleave_lowv4si (op0, res_1, res_2));

  set_unique_reg_note (res_1, REG_EQUAL, gen_rtx_MULT (V4SImode, op1, op2));
}

void
ix86_expand_sse2_mulvxdi3 (rtx op0, rtx op1, rtx op2)
{
  machine_mode mode = GET_MODE (op0);
  rtx t1, t2, t3, t4, t5, t6;

  if (TARGET_AVX512DQ && mode == V8DImode)
    emit_insn (gen_avx512dq_mulv8di3 (op0, op1, op2));
  else if (TARGET_AVX512DQ && TARGET_AVX512VL && mode == V4DImode)
    emit_insn (gen_avx512dq_mulv4di3 (op0, op1, op2));
  else if (TARGET_AVX512DQ && TARGET_AVX512VL && mode == V2DImode)
    emit_insn (gen_avx512dq_mulv2di3 (op0, op1, op2));
  else if (TARGET_XOP && mode == V2DImode)
    {
      /* op1: A,B,C,D, op2: E,F,G,H */
      op1 = gen_lowpart (V4SImode, op1);
      op2 = gen_lowpart (V4SImode, op2);

      t1 = gen_reg_rtx (V4SImode);
      t2 = gen_reg_rtx (V4SImode);
      t3 = gen_reg_rtx (V2DImode);
      t4 = gen_reg_rtx (V2DImode);

      /* t1: B,A,D,C */
      emit_insn (gen_sse2_pshufd_1 (t1, op1,
				    GEN_INT (1),
				    GEN_INT (0),
				    GEN_INT (3),
				    GEN_INT (2)));

      /* t2: (B*E),(A*F),(D*G),(C*H) */
      emit_insn (gen_mulv4si3 (t2, t1, op2));

      /* t3: (B*E)+(A*F), (D*G)+(C*H) */
      emit_insn (gen_xop_phadddq (t3, t2));

      /* t4: ((B*E)+(A*F))<<32, ((D*G)+(C*H))<<32 */
      emit_insn (gen_ashlv2di3 (t4, t3, GEN_INT (32)));

      /* Multiply lower parts and add all */
      t5 = gen_reg_rtx (V2DImode);
      emit_insn (gen_vec_widen_umult_even_v4si (t5, 
					gen_lowpart (V4SImode, op1),
					gen_lowpart (V4SImode, op2)));
      op0 = expand_binop (mode, add_optab, t5, t4, op0, 1, OPTAB_DIRECT);

    }
  else
    {
      machine_mode nmode;
      rtx (*umul) (rtx, rtx, rtx);

      if (mode == V2DImode)
	{
	  umul = gen_vec_widen_umult_even_v4si;
	  nmode = V4SImode;
	}
      else if (mode == V4DImode)
	{
	  umul = gen_vec_widen_umult_even_v8si;
	  nmode = V8SImode;
	}
      else if (mode == V8DImode)
	{
	  umul = gen_vec_widen_umult_even_v16si;
	  nmode = V16SImode;
	}
      else
	gcc_unreachable ();


      /* Multiply low parts.  */
      t1 = gen_reg_rtx (mode);
      emit_insn (umul (t1, gen_lowpart (nmode, op1), gen_lowpart (nmode, op2)));

      /* Shift input vectors right 32 bits so we can multiply high parts.  */
      t6 = GEN_INT (32);
      t2 = expand_binop (mode, lshr_optab, op1, t6, NULL, 1, OPTAB_DIRECT);
      t3 = expand_binop (mode, lshr_optab, op2, t6, NULL, 1, OPTAB_DIRECT);

      /* Multiply high parts by low parts.  */
      t4 = gen_reg_rtx (mode);
      t5 = gen_reg_rtx (mode);
      emit_insn (umul (t4, gen_lowpart (nmode, t2), gen_lowpart (nmode, op2)));
      emit_insn (umul (t5, gen_lowpart (nmode, t3), gen_lowpart (nmode, op1)));

      /* Combine and shift the highparts back.  */
      t4 = expand_binop (mode, add_optab, t4, t5, t4, 1, OPTAB_DIRECT);
      t4 = expand_binop (mode, ashl_optab, t4, t6, t4, 1, OPTAB_DIRECT);

      /* Combine high and low parts.  */
      force_expand_binop (mode, add_optab, t1, t4, op0, 1, OPTAB_DIRECT);
    }

  set_unique_reg_note (get_last_insn (), REG_EQUAL,
		       gen_rtx_MULT (mode, op1, op2));
}

/* Return 1 if control tansfer instruction INSN
   should be encoded with notrack prefix.  */

static bool
ix86_notrack_prefixed_insn_p (rtx insn)
{
  if (!insn || !((flag_cf_protection & CF_BRANCH)))
    return false;

  if (CALL_P (insn))
    {
      rtx call = get_call_rtx_from (insn);
      gcc_assert (call != NULL_RTX);
      rtx addr = XEXP (call, 0);

      /* Do not emit 'notrack' if it's not an indirect call.  */
      if (MEM_P (addr)
	  && GET_CODE (XEXP (addr, 0)) == SYMBOL_REF)
	return false;
      else
	return find_reg_note (insn, REG_CALL_NOCF_CHECK, 0);
    }

  if (JUMP_P (insn) && !flag_cet_switch)
    {
      rtx target = JUMP_LABEL (insn);
      if (target == NULL_RTX || ANY_RETURN_P (target))
	return false;

      /* Check the jump is a switch table.  */
      rtx_insn *label = as_a<rtx_insn *> (target);
      rtx_insn *table = next_insn (label);
      if (table == NULL_RTX || !JUMP_TABLE_DATA_P (table))
	return false;
      else
	return true;
    }
  return false;
}

/* Calculate integer abs() using only SSE2 instructions.  */

void
ix86_expand_sse2_abs (rtx target, rtx input)
{
  machine_mode mode = GET_MODE (target);
  rtx tmp0, tmp1, x;

  switch (mode)
    {
    case E_V2DImode:
    case E_V4DImode:
      /* For 64-bit signed integer X, with SSE4.2 use
	 pxor t0, t0; pcmpgtq X, t0; pxor t0, X; psubq t0, X.
	 Otherwise handle it similarly to V4SImode, except use 64 as W instead of
	 32 and use logical instead of arithmetic right shift (which is
	 unimplemented) and subtract.  */
      if (TARGET_SSE4_2)
	{
	  tmp0 = gen_reg_rtx (mode);
	  tmp1 = gen_reg_rtx (mode);
	  emit_move_insn (tmp1, CONST0_RTX (mode));
	  if (mode == E_V2DImode)
	    emit_insn (gen_sse4_2_gtv2di3 (tmp0, tmp1, input));
	  else
	    emit_insn (gen_avx2_gtv4di3 (tmp0, tmp1, input));
	}
      else
	{
	  tmp0 = expand_simple_binop (mode, LSHIFTRT, input,
				      GEN_INT (GET_MODE_UNIT_BITSIZE (mode)
					       - 1), NULL, 0, OPTAB_DIRECT);
	  tmp0 = expand_simple_unop (mode, NEG, tmp0, NULL, false);
	}

      tmp1 = expand_simple_binop (mode, XOR, tmp0, input,
				  NULL, 0, OPTAB_DIRECT);
      x = expand_simple_binop (mode, MINUS, tmp1, tmp0,
			       target, 0, OPTAB_DIRECT);
      break;

    case E_V4SImode:
      /* For 32-bit signed integer X, the best way to calculate the absolute
	 value of X is (((signed) X >> (W-1)) ^ X) - ((signed) X >> (W-1)).  */
      tmp0 = expand_simple_binop (mode, ASHIFTRT, input,
				  GEN_INT (GET_MODE_UNIT_BITSIZE (mode) - 1),
				  NULL, 0, OPTAB_DIRECT);
      tmp1 = expand_simple_binop (mode, XOR, tmp0, input,
				  NULL, 0, OPTAB_DIRECT);
      x = expand_simple_binop (mode, MINUS, tmp1, tmp0,
			       target, 0, OPTAB_DIRECT);
      break;

    case E_V8HImode:
      /* For 16-bit signed integer X, the best way to calculate the absolute
	 value of X is max (X, -X), as SSE2 provides the PMAXSW insn.  */
      tmp0 = expand_unop (mode, neg_optab, input, NULL_RTX, 0);

      x = expand_simple_binop (mode, SMAX, tmp0, input,
			       target, 0, OPTAB_DIRECT);
      break;

    case E_V16QImode:
      /* For 8-bit signed integer X, the best way to calculate the absolute
	 value of X is min ((unsigned char) X, (unsigned char) (-X)),
	 as SSE2 provides the PMINUB insn.  */
      tmp0 = expand_unop (mode, neg_optab, input, NULL_RTX, 0);

      x = expand_simple_binop (V16QImode, UMIN, tmp0, input,
			       target, 0, OPTAB_DIRECT);
      break;

    default:
      gcc_unreachable ();
    }

  if (x != target)
    emit_move_insn (target, x);
}

/* Expand an extract from a vector register through pextr insn.
   Return true if successful.  */

bool
ix86_expand_pextr (rtx *operands)
{
  rtx dst = operands[0];
  rtx src = operands[1];

  unsigned int size = INTVAL (operands[2]);
  unsigned int pos = INTVAL (operands[3]);

  if (SUBREG_P (dst))
    {
      /* Reject non-lowpart subregs.  */
      if (SUBREG_BYTE (dst) > 0)
	return false;
      dst = SUBREG_REG (dst);
    }
	
  if (SUBREG_P (src))
    {
      pos += SUBREG_BYTE (src) * BITS_PER_UNIT;
      src = SUBREG_REG (src);
    }

  switch (GET_MODE (src))
    {
    case E_V16QImode:
    case E_V8HImode:
    case E_V4SImode:
    case E_V2DImode:
    case E_V1TImode:
    case E_TImode:
      {
	machine_mode srcmode, dstmode;
	rtx d, pat;

	if (!int_mode_for_size (size, 0).exists (&dstmode))
	  return false;

	switch (dstmode)
	  {
	  case E_QImode:
	    if (!TARGET_SSE4_1)
	      return false;
	    srcmode = V16QImode;
	    break;

	  case E_HImode:
	    if (!TARGET_SSE2)
	      return false;
	    srcmode = V8HImode;
	    break;

	  case E_SImode:
	    if (!TARGET_SSE4_1)
	      return false;
	    srcmode = V4SImode;
	    break;

	  case E_DImode:
	    gcc_assert (TARGET_64BIT);
	    if (!TARGET_SSE4_1)
	      return false;
	    srcmode = V2DImode;
	    break;

	  default:
	    return false;
	  }

	/* Reject extractions from misaligned positions.  */
	if (pos & (size-1))
	  return false;

	if (GET_MODE (dst) == dstmode)
	  d = dst;
	else
	  d = gen_reg_rtx (dstmode);

	/* Construct insn pattern.  */
	pat = gen_rtx_PARALLEL (VOIDmode, gen_rtvec (1, GEN_INT (pos / size)));
	pat = gen_rtx_VEC_SELECT (dstmode, gen_lowpart (srcmode, src), pat);

	/* Let the rtl optimizers know about the zero extension performed.  */
	if (dstmode == QImode || dstmode == HImode)
	  {
	    pat = gen_rtx_ZERO_EXTEND (SImode, pat);
	    d = gen_lowpart (SImode, d);
	  }

	emit_insn (gen_rtx_SET (d, pat));

	if (d != dst)
	  emit_move_insn (dst, gen_lowpart (GET_MODE (dst), d));
	return true;
      }

    default:
      return false;
    }
}

/* Expand an insert into a vector register through pinsr insn.
   Return true if successful.  */

bool
ix86_expand_pinsr (rtx *operands)
{
  rtx dst = operands[0];
  rtx src = operands[3];

  unsigned int size = INTVAL (operands[1]);
  unsigned int pos = INTVAL (operands[2]);

  if (SUBREG_P (dst))
    {
      pos += SUBREG_BYTE (dst) * BITS_PER_UNIT;
      dst = SUBREG_REG (dst);
    }

  switch (GET_MODE (dst))
    {
    case E_V16QImode:
    case E_V8HImode:
    case E_V4SImode:
    case E_V2DImode:
    case E_V1TImode:
    case E_TImode:
      {
	machine_mode srcmode, dstmode;
	rtx (*pinsr)(rtx, rtx, rtx, rtx);
	rtx d;

	if (!int_mode_for_size (size, 0).exists (&srcmode))
	  return false;

	switch (srcmode)
	  {
	  case E_QImode:
	    if (!TARGET_SSE4_1)
	      return false;
	    dstmode = V16QImode;
	    pinsr = gen_sse4_1_pinsrb;
	    break;

	  case E_HImode:
	    if (!TARGET_SSE2)
	      return false;
	    dstmode = V8HImode;
	    pinsr = gen_sse2_pinsrw;
	    break;

	  case E_SImode:
	    if (!TARGET_SSE4_1)
	      return false;
	    dstmode = V4SImode;
	    pinsr = gen_sse4_1_pinsrd;
	    break;

	  case E_DImode:
	    gcc_assert (TARGET_64BIT);
	    if (!TARGET_SSE4_1)
	      return false;
	    dstmode = V2DImode;
	    pinsr = gen_sse4_1_pinsrq;
	    break;

	  default:
	    return false;
	  }

	/* Reject insertions to misaligned positions.  */
	if (pos & (size-1))
	  return false;

	if (SUBREG_P (src))
	  {
	    unsigned int srcpos = SUBREG_BYTE (src);

	    if (srcpos > 0)
	      {
		rtx extr_ops[4];

		extr_ops[0] = gen_reg_rtx (srcmode);
		extr_ops[1] = gen_lowpart (srcmode, SUBREG_REG (src));
		extr_ops[2] = GEN_INT (size);
		extr_ops[3] = GEN_INT (srcpos * BITS_PER_UNIT);

		if (!ix86_expand_pextr (extr_ops))
		  return false;

		src = extr_ops[0];
	      }
	    else
	      src = gen_lowpart (srcmode, SUBREG_REG (src));
	  }

	if (GET_MODE (dst) == dstmode)
	  d = dst;
	else
	  d = gen_reg_rtx (dstmode);

	emit_insn (pinsr (d, gen_lowpart (dstmode, dst),
			  gen_lowpart (srcmode, src),
			  GEN_INT (1 << (pos / size))));
	if (d != dst)
	  emit_move_insn (dst, gen_lowpart (GET_MODE (dst), d));
	return true;
      }

    default:
      return false;
    }
}

/* This function returns the calling abi specific va_list type node.
   It returns  the FNDECL specific va_list type.  */

static tree
ix86_fn_abi_va_list (tree fndecl)
{
  if (!TARGET_64BIT)
    return va_list_type_node;
  gcc_assert (fndecl != NULL_TREE);

  if (ix86_function_abi ((const_tree) fndecl) == MS_ABI)
    return ms_va_list_type_node;
  else
    return sysv_va_list_type_node;
}

/* Returns the canonical va_list type specified by TYPE. If there
   is no valid TYPE provided, it return NULL_TREE.  */

static tree
ix86_canonical_va_list_type (tree type)
{
  if (TARGET_64BIT)
    {
      if (lookup_attribute ("ms_abi va_list", TYPE_ATTRIBUTES (type)))
	return ms_va_list_type_node;

      if ((TREE_CODE (type) == ARRAY_TYPE
	   && integer_zerop (array_type_nelts (type)))
	  || POINTER_TYPE_P (type))
	{
	  tree elem_type = TREE_TYPE (type);
	  if (TREE_CODE (elem_type) == RECORD_TYPE
	      && lookup_attribute ("sysv_abi va_list",
				   TYPE_ATTRIBUTES (elem_type)))
	    return sysv_va_list_type_node;
	}

      return NULL_TREE;
    }

  return std_canonical_va_list_type (type);
}

/* Iterate through the target-specific builtin types for va_list.
   IDX denotes the iterator, *PTREE is set to the result type of
   the va_list builtin, and *PNAME to its internal type.
   Returns zero if there is no element for this index, otherwise
   IDX should be increased upon the next call.
   Note, do not iterate a base builtin's name like __builtin_va_list.
   Used from c_common_nodes_and_builtins.  */

static int
ix86_enum_va_list (int idx, const char **pname, tree *ptree)
{
  if (TARGET_64BIT)
    {
      switch (idx)
	{
	default:
	  break;

	case 0:
	  *ptree = ms_va_list_type_node;
	  *pname = "__builtin_ms_va_list";
	  return 1;

	case 1:
	  *ptree = sysv_va_list_type_node;
	  *pname = "__builtin_sysv_va_list";
	  return 1;
	}
    }

  return 0;
}

#undef TARGET_SCHED_DISPATCH
#define TARGET_SCHED_DISPATCH ix86_bd_has_dispatch
#undef TARGET_SCHED_DISPATCH_DO
#define TARGET_SCHED_DISPATCH_DO ix86_bd_do_dispatch
#undef TARGET_SCHED_REASSOCIATION_WIDTH
#define TARGET_SCHED_REASSOCIATION_WIDTH ix86_reassociation_width
#undef TARGET_SCHED_REORDER
#define TARGET_SCHED_REORDER ix86_atom_sched_reorder
#undef TARGET_SCHED_ADJUST_PRIORITY
#define TARGET_SCHED_ADJUST_PRIORITY ix86_adjust_priority
#undef TARGET_SCHED_DEPENDENCIES_EVALUATION_HOOK
#define TARGET_SCHED_DEPENDENCIES_EVALUATION_HOOK \
  ix86_dependencies_evaluation_hook


/* Implementation of reassociation_width target hook used by
   reassoc phase to identify parallelism level in reassociated
   tree.  Statements tree_code is passed in OPC.  Arguments type
   is passed in MODE.  */

static int
ix86_reassociation_width (unsigned int op, machine_mode mode)
{
  int width = 1;
  /* Vector part.  */
  if (VECTOR_MODE_P (mode))
    {
      int div = 1;
      if (INTEGRAL_MODE_P (mode))
	width = ix86_cost->reassoc_vec_int;
      else if (FLOAT_MODE_P (mode))
	width = ix86_cost->reassoc_vec_fp;

      if (width == 1)
	return 1;

      /* Integer vector instructions execute in FP unit
	 and can execute 3 additions and one multiplication per cycle.  */
      if ((ix86_tune == PROCESSOR_ZNVER1 || ix86_tune == PROCESSOR_ZNVER2)
	   && INTEGRAL_MODE_P (mode) && op != PLUS && op != MINUS)
	return 1;

      /* Account for targets that splits wide vectors into multiple parts.  */
      if (TARGET_AVX128_OPTIMAL && GET_MODE_BITSIZE (mode) > 128)
	div = GET_MODE_BITSIZE (mode) / 128;
      else if (TARGET_SSE_SPLIT_REGS && GET_MODE_BITSIZE (mode) > 64)
	div = GET_MODE_BITSIZE (mode) / 64;
      width = (width + div - 1) / div;
    }
  /* Scalar part.  */
  else if (INTEGRAL_MODE_P (mode))
    width = ix86_cost->reassoc_int;
  else if (FLOAT_MODE_P (mode))
    width = ix86_cost->reassoc_fp;

  /* Avoid using too many registers in 32bit mode.  */
  if (!TARGET_64BIT && width > 2)
    width = 2;
  return width;
}

/* ??? No autovectorization into MMX or 3DNOW until we can reliably
   place emms and femms instructions.  */

static machine_mode
ix86_preferred_simd_mode (scalar_mode mode)
{
  if (!TARGET_SSE)
    return word_mode;

  switch (mode)
    {
    case E_QImode:
      if (TARGET_AVX512BW && !TARGET_PREFER_AVX256)
	return V64QImode;
      else if (TARGET_AVX && !TARGET_PREFER_AVX128)
	return V32QImode;
      else
	return V16QImode;

    case E_HImode:
      if (TARGET_AVX512BW && !TARGET_PREFER_AVX256)
	return V32HImode;
      else if (TARGET_AVX && !TARGET_PREFER_AVX128)
	return V16HImode;
      else
	return V8HImode;

    case E_SImode:
      if (TARGET_AVX512F && !TARGET_PREFER_AVX256)
	return V16SImode;
      else if (TARGET_AVX && !TARGET_PREFER_AVX128)
	return V8SImode;
      else
	return V4SImode;

    case E_DImode:
      if (TARGET_AVX512F && !TARGET_PREFER_AVX256)
	return V8DImode;
      else if (TARGET_AVX && !TARGET_PREFER_AVX128)
	return V4DImode;
      else
	return V2DImode;

    case E_SFmode:
      if (TARGET_AVX512F && !TARGET_PREFER_AVX256)
	return V16SFmode;
      else if (TARGET_AVX && !TARGET_PREFER_AVX128)
	return V8SFmode;
      else
	return V4SFmode;

    case E_DFmode:
      if (TARGET_AVX512F && !TARGET_PREFER_AVX256)
	return V8DFmode;
      else if (TARGET_AVX && !TARGET_PREFER_AVX128)
	return V4DFmode;
      else if (TARGET_SSE2)
	return V2DFmode;
      /* FALLTHRU */

    default:
      return word_mode;
    }
}

/* All CPUs prefer to avoid cross-lane operations so perform reductions
   upper against lower halves up to SSE reg size.  */

static machine_mode
ix86_split_reduction (machine_mode mode)
{
  /* Reduce lowpart against highpart until we reach SSE reg width to
     avoid cross-lane operations.  */
  switch (mode)
    {
    case E_V8DImode:
    case E_V4DImode:
      return V2DImode;
    case E_V16SImode:
    case E_V8SImode:
      return V4SImode;
    case E_V32HImode:
    case E_V16HImode:
      return V8HImode;
    case E_V64QImode:
    case E_V32QImode:
      return V16QImode;
    case E_V16SFmode:
    case E_V8SFmode:
      return V4SFmode;
    case E_V8DFmode:
    case E_V4DFmode:
      return V2DFmode;
    default:
      return mode;
    }
}

/* If AVX is enabled then try vectorizing with both 256bit and 128bit
   vectors.  If AVX512F is enabled then try vectorizing with 512bit,
   256bit and 128bit vectors.  */

static void
ix86_autovectorize_vector_sizes (vector_sizes *sizes)
{
  if (TARGET_AVX512F && !TARGET_PREFER_AVX256)
    {
      sizes->safe_push (64);
      sizes->safe_push (32);
      sizes->safe_push (16);
    }
  else if (TARGET_AVX && !TARGET_PREFER_AVX128)
    {
      sizes->safe_push (32);
      sizes->safe_push (16);
    }
}

/* Implemenation of targetm.vectorize.get_mask_mode.  */

static opt_machine_mode
ix86_get_mask_mode (poly_uint64 nunits, poly_uint64 vector_size)
{
  unsigned elem_size = vector_size / nunits;

  /* Scalar mask case.  */
  if ((TARGET_AVX512F && vector_size == 64)
      || (TARGET_AVX512VL && (vector_size == 32 || vector_size == 16)))
    {
      if (elem_size == 4 || elem_size == 8 || TARGET_AVX512BW)
	return smallest_int_mode_for_size (nunits);
    }

  scalar_int_mode elem_mode
    = smallest_int_mode_for_size (elem_size * BITS_PER_UNIT);

  gcc_assert (elem_size * nunits == vector_size);

  return mode_for_vector (elem_mode, nunits);
}



/* Return class of registers which could be used for pseudo of MODE
   and of class RCLASS for spilling instead of memory.  Return NO_REGS
   if it is not possible or non-profitable.  */

/* Disabled due to PRs 70902, 71453, 71555, 71596 and 71657.  */

static reg_class_t
ix86_spill_class (reg_class_t rclass, machine_mode mode)
{
  if (0 && TARGET_GENERAL_REGS_SSE_SPILL
      && TARGET_SSE2
      && TARGET_INTER_UNIT_MOVES_TO_VEC
      && TARGET_INTER_UNIT_MOVES_FROM_VEC
      && (mode == SImode || (TARGET_64BIT && mode == DImode))
      && INTEGER_CLASS_P (rclass))
    return ALL_SSE_REGS;
  return NO_REGS;
}

/* Implement TARGET_MAX_NOCE_IFCVT_SEQ_COST.  Like the default implementation,
   but returns a lower bound.  */

static unsigned int
ix86_max_noce_ifcvt_seq_cost (edge e)
{
  bool predictable_p = predictable_edge_p (e);

  enum compiler_param param
    = (predictable_p
       ? PARAM_MAX_RTL_IF_CONVERSION_PREDICTABLE_COST
       : PARAM_MAX_RTL_IF_CONVERSION_UNPREDICTABLE_COST);

  /* If we have a parameter set, use that, otherwise take a guess using
     BRANCH_COST.  */
  if (global_options_set.x_param_values[param])
    return PARAM_VALUE (param);
  else
    return BRANCH_COST (true, predictable_p) * COSTS_N_INSNS (2);
}

/* Return true if SEQ is a good candidate as a replacement for the
   if-convertible sequence described in IF_INFO.  */

static bool
ix86_noce_conversion_profitable_p (rtx_insn *seq, struct noce_if_info *if_info)
{
  if (TARGET_ONE_IF_CONV_INSN && if_info->speed_p)
    {
      int cmov_cnt = 0;
      /* Punt if SEQ contains more than one CMOV or FCMOV instruction.
	 Maybe we should allow even more conditional moves as long as they
	 are used far enough not to stall the CPU, or also consider
	 IF_INFO->TEST_BB succ edge probabilities.  */
      for (rtx_insn *insn = seq; insn; insn = NEXT_INSN (insn))
	{
	  rtx set = single_set (insn);
	  if (!set)
	    continue;
	  if (GET_CODE (SET_SRC (set)) != IF_THEN_ELSE)
	    continue;
	  rtx src = SET_SRC (set);
	  machine_mode mode = GET_MODE (src);
	  if (GET_MODE_CLASS (mode) != MODE_INT
	      && GET_MODE_CLASS (mode) != MODE_FLOAT)
	    continue;
	  if ((!REG_P (XEXP (src, 1)) && !MEM_P (XEXP (src, 1)))
	      || (!REG_P (XEXP (src, 2)) && !MEM_P (XEXP (src, 2))))
	    continue;
	  /* insn is CMOV or FCMOV.  */
	  if (++cmov_cnt > 1)
	    return false;
	}
    }
  return default_noce_conversion_profitable_p (seq, if_info);
}

/* Implement targetm.vectorize.init_cost.  */

static void *
ix86_init_cost (struct loop *)
{
  unsigned *cost = XNEWVEC (unsigned, 3);
  cost[vect_prologue] = cost[vect_body] = cost[vect_epilogue] = 0;
  return cost;
}

/* Implement targetm.vectorize.add_stmt_cost.  */

static unsigned
ix86_add_stmt_cost (void *data, int count, enum vect_cost_for_stmt kind,
		    struct _stmt_vec_info *stmt_info, int misalign,
		    enum vect_cost_model_location where)
{
  unsigned *cost = (unsigned *) data;
  unsigned retval = 0;
  bool scalar_p
    = (kind == scalar_stmt || kind == scalar_load || kind == scalar_store);

  tree vectype = stmt_info ? stmt_vectype (stmt_info) : NULL_TREE;
  int stmt_cost = - 1;

  bool fp = false;
  machine_mode mode = scalar_p ? SImode : TImode;

  if (vectype != NULL)
    {
      fp = FLOAT_TYPE_P (vectype);
      mode = TYPE_MODE (vectype);
      if (scalar_p)
	mode = TYPE_MODE (TREE_TYPE (vectype));
    }

  if ((kind == vector_stmt || kind == scalar_stmt)
      && stmt_info
      && stmt_info->stmt && gimple_code (stmt_info->stmt) == GIMPLE_ASSIGN)
    {
      tree_code subcode = gimple_assign_rhs_code (stmt_info->stmt);
      /*machine_mode inner_mode = mode;
      if (VECTOR_MODE_P (mode))
	inner_mode = GET_MODE_INNER (mode);*/

      switch (subcode)
	{
	case PLUS_EXPR:
	case POINTER_PLUS_EXPR:
	case MINUS_EXPR:
	  if (kind == scalar_stmt)
	    {
	      if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
		stmt_cost = ix86_cost->addss;
	      else if (X87_FLOAT_MODE_P (mode))
		stmt_cost = ix86_cost->fadd;
	      else
	        stmt_cost = ix86_cost->add;
	    }
	  else
	    stmt_cost = ix86_vec_cost (mode, fp ? ix86_cost->addss
				       : ix86_cost->sse_op);
	  break;

	case MULT_EXPR:
	case WIDEN_MULT_EXPR:
	case MULT_HIGHPART_EXPR:
	  stmt_cost = ix86_multiplication_cost (ix86_cost, mode);
	  break;
	case NEGATE_EXPR:
	  if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
	    stmt_cost = ix86_cost->sse_op;
	  else if (X87_FLOAT_MODE_P (mode))
	    stmt_cost = ix86_cost->fchs;
	  else if (VECTOR_MODE_P (mode))
	    stmt_cost = ix86_vec_cost (mode, ix86_cost->sse_op);
	  else
	    stmt_cost = ix86_cost->add;
	  break;
	case TRUNC_DIV_EXPR:
	case CEIL_DIV_EXPR:
	case FLOOR_DIV_EXPR:
	case ROUND_DIV_EXPR:
	case TRUNC_MOD_EXPR:
	case CEIL_MOD_EXPR:
	case FLOOR_MOD_EXPR:
	case RDIV_EXPR:
	case ROUND_MOD_EXPR:
	case EXACT_DIV_EXPR:
	  stmt_cost = ix86_division_cost (ix86_cost, mode);
	  break;

	case RSHIFT_EXPR:
	case LSHIFT_EXPR:
	case LROTATE_EXPR:
	case RROTATE_EXPR:
	  {
	    tree op2 = gimple_assign_rhs2 (stmt_info->stmt);
	    stmt_cost = ix86_shift_rotate_cost
			   (ix86_cost, mode,
		            TREE_CODE (op2) == INTEGER_CST,
			    cst_and_fits_in_hwi (op2) ? int_cst_value (op2) : -1,
		            true, false, false, NULL, NULL);
	  }
	  break;
	case NOP_EXPR:
	  /* Only sign-conversions are free.  */
	  if (tree_nop_conversion_p
	        (TREE_TYPE (gimple_assign_lhs (stmt_info->stmt)),
		 TREE_TYPE (gimple_assign_rhs1 (stmt_info->stmt))))
	    stmt_cost = 0;
	  break;

	case BIT_IOR_EXPR:
	case ABS_EXPR:
	case ABSU_EXPR:
	case MIN_EXPR:
	case MAX_EXPR:
	case BIT_XOR_EXPR:
	case BIT_AND_EXPR:
	case BIT_NOT_EXPR:
	  if (SSE_FLOAT_MODE_P (mode) && TARGET_SSE_MATH)
	    stmt_cost = ix86_cost->sse_op;
	  else if (VECTOR_MODE_P (mode))
	    stmt_cost = ix86_vec_cost (mode, ix86_cost->sse_op);
	  else
	    stmt_cost = ix86_cost->add;
	  break;
	default:
	  break;
	}
    }

  combined_fn cfn;
  if ((kind == vector_stmt || kind == scalar_stmt)
      && stmt_info
      && stmt_info->stmt
      && (cfn = gimple_call_combined_fn (stmt_info->stmt)) != CFN_LAST)
    switch (cfn)
      {
      case CFN_FMA:
	stmt_cost = ix86_vec_cost (mode,
				   mode == SFmode ? ix86_cost->fmass
				   : ix86_cost->fmasd);
	break;
      default:
	break;
      }

  /* If we do elementwise loads into a vector then we are bound by
     latency and execution resources for the many scalar loads
     (AGU and load ports).  Try to account for this by scaling the
     construction cost by the number of elements involved.  */
  if (kind == vec_construct
      && stmt_info
      && STMT_VINFO_TYPE (stmt_info) == load_vec_info_type
      && STMT_VINFO_MEMORY_ACCESS_TYPE (stmt_info) == VMAT_ELEMENTWISE
      && TREE_CODE (DR_STEP (STMT_VINFO_DATA_REF (stmt_info))) != INTEGER_CST)
    {
      stmt_cost = ix86_builtin_vectorization_cost (kind, vectype, misalign);
      stmt_cost *= TYPE_VECTOR_SUBPARTS (vectype);
    }
  if (stmt_cost == -1)
    stmt_cost = ix86_builtin_vectorization_cost (kind, vectype, misalign);

  /* Penalize DFmode vector operations for Bonnell.  */
  if (TARGET_BONNELL && kind == vector_stmt
      && vectype && GET_MODE_INNER (TYPE_MODE (vectype)) == DFmode)
    stmt_cost *= 5;  /* FIXME: The value here is arbitrary.  */

  /* Statements in an inner loop relative to the loop being
     vectorized are weighted more heavily.  The value here is
     arbitrary and could potentially be improved with analysis.  */
  if (where == vect_body && stmt_info && stmt_in_inner_loop_p (stmt_info))
    count *= 50;  /* FIXME.  */

  retval = (unsigned) (count * stmt_cost);

  /* We need to multiply all vector stmt cost by 1.7 (estimated cost)
     for Silvermont as it has out of order integer pipeline and can execute
     2 scalar instruction per tick, but has in order SIMD pipeline.  */
  if ((TARGET_SILVERMONT || TARGET_GOLDMONT || TARGET_GOLDMONT_PLUS
       || TARGET_TREMONT || TARGET_INTEL) && stmt_info && stmt_info->stmt)
    {
      tree lhs_op = gimple_get_lhs (stmt_info->stmt);
      if (lhs_op && TREE_CODE (TREE_TYPE (lhs_op)) == INTEGER_TYPE)
	retval = (retval * 17) / 10;
    }

  cost[where] += retval;

  return retval;
}

/* Implement targetm.vectorize.finish_cost.  */

static void
ix86_finish_cost (void *data, unsigned *prologue_cost,
		  unsigned *body_cost, unsigned *epilogue_cost)
{
  unsigned *cost = (unsigned *) data;
  *prologue_cost = cost[vect_prologue];
  *body_cost     = cost[vect_body];
  *epilogue_cost = cost[vect_epilogue];
}

/* Implement targetm.vectorize.destroy_cost_data.  */

static void
ix86_destroy_cost_data (void *data)
{
  free (data);
}

/* Validate target specific memory model bits in VAL. */

static unsigned HOST_WIDE_INT
ix86_memmodel_check (unsigned HOST_WIDE_INT val)
{
  enum memmodel model = memmodel_from_int (val);
  bool strong;

  if (val & ~(unsigned HOST_WIDE_INT)(IX86_HLE_ACQUIRE|IX86_HLE_RELEASE
				      |MEMMODEL_MASK)
      || ((val & IX86_HLE_ACQUIRE) && (val & IX86_HLE_RELEASE)))
    {
      warning (OPT_Winvalid_memory_model,
	       "unknown architecture specific memory model");
      return MEMMODEL_SEQ_CST;
    }
  strong = (is_mm_acq_rel (model) || is_mm_seq_cst (model));
  if (val & IX86_HLE_ACQUIRE && !(is_mm_acquire (model) || strong))
    {
      warning (OPT_Winvalid_memory_model,
              "HLE_ACQUIRE not used with ACQUIRE or stronger memory model");
      return MEMMODEL_SEQ_CST | IX86_HLE_ACQUIRE;
    }
  if (val & IX86_HLE_RELEASE && !(is_mm_release (model) || strong))
    {
      warning (OPT_Winvalid_memory_model,
              "HLE_RELEASE not used with RELEASE or stronger memory model");
      return MEMMODEL_SEQ_CST | IX86_HLE_RELEASE;
    }
  return val;
}

/* Set CLONEI->vecsize_mangle, CLONEI->mask_mode, CLONEI->vecsize_int,
   CLONEI->vecsize_float and if CLONEI->simdlen is 0, also
   CLONEI->simdlen.  Return 0 if SIMD clones shouldn't be emitted,
   or number of vecsize_mangle variants that should be emitted.  */

static int
ix86_simd_clone_compute_vecsize_and_simdlen (struct cgraph_node *node,
					     struct cgraph_simd_clone *clonei,
					     tree base_type, int num)
{
  int ret = 1;

  if (clonei->simdlen
      && (clonei->simdlen < 2
	  || clonei->simdlen > 1024
	  || (clonei->simdlen & (clonei->simdlen - 1)) != 0))
    {
      warning_at (DECL_SOURCE_LOCATION (node->decl), 0,
		  "unsupported simdlen %d", clonei->simdlen);
      return 0;
    }

  tree ret_type = TREE_TYPE (TREE_TYPE (node->decl));
  if (TREE_CODE (ret_type) != VOID_TYPE)
    switch (TYPE_MODE (ret_type))
      {
      case E_QImode:
      case E_HImode:
      case E_SImode:
      case E_DImode:
      case E_SFmode:
      case E_DFmode:
      /* case E_SCmode: */
      /* case E_DCmode: */
	if (!AGGREGATE_TYPE_P (ret_type))
	  break;
	/* FALLTHRU */
      default:
	warning_at (DECL_SOURCE_LOCATION (node->decl), 0,
		    "unsupported return type %qT for simd", ret_type);
	return 0;
      }

  tree t;
  int i;
  tree type_arg_types = TYPE_ARG_TYPES (TREE_TYPE (node->decl));
  bool decl_arg_p = (node->definition || type_arg_types == NULL_TREE);

  for (t = (decl_arg_p ? DECL_ARGUMENTS (node->decl) : type_arg_types), i = 0;
       t && t != void_list_node; t = TREE_CHAIN (t), i++)
    {
      tree arg_type = decl_arg_p ? TREE_TYPE (t) : TREE_VALUE (t);
      switch (TYPE_MODE (arg_type))
	{
	case E_QImode:
	case E_HImode:
	case E_SImode:
	case E_DImode:
	case E_SFmode:
	case E_DFmode:
	/* case E_SCmode: */
	/* case E_DCmode: */
	  if (!AGGREGATE_TYPE_P (arg_type))
	    break;
	  /* FALLTHRU */
	default:
	  if (clonei->args[i].arg_type == SIMD_CLONE_ARG_TYPE_UNIFORM)
	    break;
	  warning_at (DECL_SOURCE_LOCATION (node->decl), 0,
		      "unsupported argument type %qT for simd", arg_type);
	  return 0;
	}
    }

  if (!TREE_PUBLIC (node->decl))
    {
      /* If the function isn't exported, we can pick up just one ISA
	 for the clones.  */
      if (TARGET_AVX512F)
	clonei->vecsize_mangle = 'e';
      else if (TARGET_AVX2)
	clonei->vecsize_mangle = 'd';
      else if (TARGET_AVX)
	clonei->vecsize_mangle = 'c';
      else
	clonei->vecsize_mangle = 'b';
      ret = 1;
    }
  else
    {
      clonei->vecsize_mangle = "bcde"[num];
      ret = 4;
    }
  clonei->mask_mode = VOIDmode;
  switch (clonei->vecsize_mangle)
    {
    case 'b':
      clonei->vecsize_int = 128;
      clonei->vecsize_float = 128;
      break;
    case 'c':
      clonei->vecsize_int = 128;
      clonei->vecsize_float = 256;
      break;
    case 'd':
      clonei->vecsize_int = 256;
      clonei->vecsize_float = 256;
      break;
    case 'e':
      clonei->vecsize_int = 512;
      clonei->vecsize_float = 512;
      if (TYPE_MODE (base_type) == QImode)
	clonei->mask_mode = DImode;
      else
	clonei->mask_mode = SImode;
      break;
    }
  if (clonei->simdlen == 0)
    {
      if (SCALAR_INT_MODE_P (TYPE_MODE (base_type)))
	clonei->simdlen = clonei->vecsize_int;
      else
	clonei->simdlen = clonei->vecsize_float;
      clonei->simdlen /= GET_MODE_BITSIZE (TYPE_MODE (base_type));
    }
  else if (clonei->simdlen > 16)
    {
      /* For compatibility with ICC, use the same upper bounds
	 for simdlen.  In particular, for CTYPE below, use the return type,
	 unless the function returns void, in that case use the characteristic
	 type.  If it is possible for given SIMDLEN to pass CTYPE value
	 in registers (8 [XYZ]MM* regs for 32-bit code, 16 [XYZ]MM* regs
	 for 64-bit code), accept that SIMDLEN, otherwise warn and don't
	 emit corresponding clone.  */
      tree ctype = ret_type;
      if (TREE_CODE (ret_type) == VOID_TYPE)
	ctype = base_type;
      int cnt = GET_MODE_BITSIZE (TYPE_MODE (ctype)) * clonei->simdlen;
      if (SCALAR_INT_MODE_P (TYPE_MODE (ctype)))
	cnt /= clonei->vecsize_int;
      else
	cnt /= clonei->vecsize_float;
      if (cnt > (TARGET_64BIT ? 16 : 8))
	{
	  warning_at (DECL_SOURCE_LOCATION (node->decl), 0,
		      "unsupported simdlen %d", clonei->simdlen);
	  return 0;
	}
      }
  return ret;
}

/* Add target attribute to SIMD clone NODE if needed.  */

static void
ix86_simd_clone_adjust (struct cgraph_node *node)
{
  const char *str = NULL;

  /* Attributes need to be adjusted for definitions, not declarations.  */
  if (!node->definition)
    return;

  gcc_assert (node->decl == cfun->decl);
  switch (node->simdclone->vecsize_mangle)
    {
    case 'b':
      if (!TARGET_SSE2)
	str = "sse2";
      break;
    case 'c':
      if (!TARGET_AVX)
	str = "avx";
      break;
    case 'd':
      if (!TARGET_AVX2)
	str = "avx2";
      break;
    case 'e':
      if (!TARGET_AVX512F)
	str = "avx512f";
      break;
    default:
      gcc_unreachable ();
    }
  if (str == NULL)
    return;
  push_cfun (NULL);
  tree args = build_tree_list (NULL_TREE, build_string (strlen (str), str));
  bool ok = ix86_valid_target_attribute_p (node->decl, NULL, args, 0);
  gcc_assert (ok);
  pop_cfun ();
  ix86_reset_previous_fndecl ();
  ix86_set_current_function (node->decl);
}

/* If SIMD clone NODE can't be used in a vectorized loop
   in current function, return -1, otherwise return a badness of using it
   (0 if it is most desirable from vecsize_mangle point of view, 1
   slightly less desirable, etc.).  */

static int
ix86_simd_clone_usable (struct cgraph_node *node)
{
  switch (node->simdclone->vecsize_mangle)
    {
    case 'b':
      if (!TARGET_SSE2)
	return -1;
      if (!TARGET_AVX)
	return 0;
      return TARGET_AVX2 ? 2 : 1;
    case 'c':
      if (!TARGET_AVX)
	return -1;
      return TARGET_AVX2 ? 1 : 0;
    case 'd':
      if (!TARGET_AVX2)
	return -1;
      return 0;
    case 'e':
      if (!TARGET_AVX512F)
	return -1;
      return 0;
    default:
      gcc_unreachable ();
    }
}

/* This function adjusts the unroll factor based on
   the hardware capabilities. For ex, bdver3 has
   a loop buffer which makes unrolling of smaller
   loops less important. This function decides the
   unroll factor using number of memory references
   (value 32 is used) as a heuristic. */

static unsigned
ix86_loop_unroll_adjust (unsigned nunroll, struct loop *loop)
{
  basic_block *bbs;
  rtx_insn *insn;
  unsigned i;
  unsigned mem_count = 0;

  if (!TARGET_ADJUST_UNROLL)
     return nunroll;

  /* Count the number of memory references within the loop body.
     This value determines the unrolling factor for bdver3 and bdver4
     architectures. */
  subrtx_iterator::array_type array;
  bbs = get_loop_body (loop);
  for (i = 0; i < loop->num_nodes; i++)
    FOR_BB_INSNS (bbs[i], insn)
      if (NONDEBUG_INSN_P (insn))
	FOR_EACH_SUBRTX (iter, array, PATTERN (insn), NONCONST)
	  if (const_rtx x = *iter)
	    if (MEM_P (x))
	      {
		machine_mode mode = GET_MODE (x);
		unsigned int n_words = GET_MODE_SIZE (mode) / UNITS_PER_WORD;
		if (n_words > 4)
		  mem_count += 2;
		else
		  mem_count += 1;
	      }
  free (bbs);

  if (mem_count && mem_count <=32)
    return MIN (nunroll, 32 / mem_count);

  return nunroll;
}


/* Implement TARGET_FLOAT_EXCEPTIONS_ROUNDING_SUPPORTED_P.  */

static bool
ix86_float_exceptions_rounding_supported_p (void)
{
  /* For x87 floating point with standard excess precision handling,
     there is no adddf3 pattern (since x87 floating point only has
     XFmode operations) so the default hook implementation gets this
     wrong.  */
  return TARGET_80387 || TARGET_SSE_MATH;
}

/* Implement TARGET_ATOMIC_ASSIGN_EXPAND_FENV.  */

static void
ix86_atomic_assign_expand_fenv (tree *hold, tree *clear, tree *update)
{
  if (!TARGET_80387 && !TARGET_SSE_MATH)
    return;
  tree exceptions_var = create_tmp_var_raw (integer_type_node);
  if (TARGET_80387)
    {
      tree fenv_index_type = build_index_type (size_int (6));
      tree fenv_type = build_array_type (unsigned_type_node, fenv_index_type);
      tree fenv_var = create_tmp_var_raw (fenv_type);
      TREE_ADDRESSABLE (fenv_var) = 1;
      tree fenv_ptr = build_pointer_type (fenv_type);
      tree fenv_addr = build1 (ADDR_EXPR, fenv_ptr, fenv_var);
      fenv_addr = fold_convert (ptr_type_node, fenv_addr);
      tree fnstenv = ix86_builtins[IX86_BUILTIN_FNSTENV];
      tree fldenv = ix86_builtins[IX86_BUILTIN_FLDENV];
      tree fnstsw = ix86_builtins[IX86_BUILTIN_FNSTSW];
      tree fnclex = ix86_builtins[IX86_BUILTIN_FNCLEX];
      tree hold_fnstenv = build_call_expr (fnstenv, 1, fenv_addr);
      tree hold_fnclex = build_call_expr (fnclex, 0);
      fenv_var = build4 (TARGET_EXPR, fenv_type, fenv_var, hold_fnstenv,
			 NULL_TREE, NULL_TREE);
      *hold = build2 (COMPOUND_EXPR, void_type_node, fenv_var,
		      hold_fnclex);
      *clear = build_call_expr (fnclex, 0);
      tree sw_var = create_tmp_var_raw (short_unsigned_type_node);
      tree fnstsw_call = build_call_expr (fnstsw, 0);
      tree sw_mod = build2 (MODIFY_EXPR, short_unsigned_type_node,
			    sw_var, fnstsw_call);
      tree exceptions_x87 = fold_convert (integer_type_node, sw_var);
      tree update_mod = build2 (MODIFY_EXPR, integer_type_node,
				exceptions_var, exceptions_x87);
      *update = build2 (COMPOUND_EXPR, integer_type_node,
			sw_mod, update_mod);
      tree update_fldenv = build_call_expr (fldenv, 1, fenv_addr);
      *update = build2 (COMPOUND_EXPR, void_type_node, *update, update_fldenv);
    }
  if (TARGET_SSE_MATH)
    {
      tree mxcsr_orig_var = create_tmp_var_raw (unsigned_type_node);
      tree mxcsr_mod_var = create_tmp_var_raw (unsigned_type_node);
      tree stmxcsr = ix86_builtins[IX86_BUILTIN_STMXCSR];
      tree ldmxcsr = ix86_builtins[IX86_BUILTIN_LDMXCSR];
      tree stmxcsr_hold_call = build_call_expr (stmxcsr, 0);
      tree hold_assign_orig = build2 (MODIFY_EXPR, unsigned_type_node,
				      mxcsr_orig_var, stmxcsr_hold_call);
      tree hold_mod_val = build2 (BIT_IOR_EXPR, unsigned_type_node,
				  mxcsr_orig_var,
				  build_int_cst (unsigned_type_node, 0x1f80));
      hold_mod_val = build2 (BIT_AND_EXPR, unsigned_type_node, hold_mod_val,
			     build_int_cst (unsigned_type_node, 0xffffffc0));
      tree hold_assign_mod = build2 (MODIFY_EXPR, unsigned_type_node,
				     mxcsr_mod_var, hold_mod_val);
      tree ldmxcsr_hold_call = build_call_expr (ldmxcsr, 1, mxcsr_mod_var);
      tree hold_all = build2 (COMPOUND_EXPR, unsigned_type_node,
			      hold_assign_orig, hold_assign_mod);
      hold_all = build2 (COMPOUND_EXPR, void_type_node, hold_all,
			 ldmxcsr_hold_call);
      if (*hold)
	*hold = build2 (COMPOUND_EXPR, void_type_node, *hold, hold_all);
      else
	*hold = hold_all;
      tree ldmxcsr_clear_call = build_call_expr (ldmxcsr, 1, mxcsr_mod_var);
      if (*clear)
	*clear = build2 (COMPOUND_EXPR, void_type_node, *clear,
			 ldmxcsr_clear_call);
      else
	*clear = ldmxcsr_clear_call;
      tree stxmcsr_update_call = build_call_expr (stmxcsr, 0);
      tree exceptions_sse = fold_convert (integer_type_node,
					  stxmcsr_update_call);
      if (*update)
	{
	  tree exceptions_mod = build2 (BIT_IOR_EXPR, integer_type_node,
					exceptions_var, exceptions_sse);
	  tree exceptions_assign = build2 (MODIFY_EXPR, integer_type_node,
					   exceptions_var, exceptions_mod);
	  *update = build2 (COMPOUND_EXPR, integer_type_node, *update,
			    exceptions_assign);
	}
      else
	*update = build2 (MODIFY_EXPR, integer_type_node,
			  exceptions_var, exceptions_sse);
      tree ldmxcsr_update_call = build_call_expr (ldmxcsr, 1, mxcsr_orig_var);
      *update = build2 (COMPOUND_EXPR, void_type_node, *update,
			ldmxcsr_update_call);
    }
  tree atomic_feraiseexcept
    = builtin_decl_implicit (BUILT_IN_ATOMIC_FERAISEEXCEPT);
  tree atomic_feraiseexcept_call = build_call_expr (atomic_feraiseexcept,
						    1, exceptions_var);
  *update = build2 (COMPOUND_EXPR, void_type_node, *update,
		    atomic_feraiseexcept_call);
}

#if !TARGET_MACHO && !TARGET_DLLIMPORT_DECL_ATTRIBUTES
/* For i386, common symbol is local only for non-PIE binaries.  For
   x86-64, common symbol is local only for non-PIE binaries or linker
   supports copy reloc in PIE binaries.   */

static bool
ix86_binds_local_p (const_tree exp)
{
  return default_binds_local_p_3 (exp, flag_shlib != 0, true, true,
				  (!flag_pic
				   || (TARGET_64BIT
				       && HAVE_LD_PIE_COPYRELOC != 0)));
}
#endif

/* If MEM is in the form of [base+offset], extract the two parts
   of address and set to BASE and OFFSET, otherwise return false.  */

static bool
extract_base_offset_in_addr (rtx mem, rtx *base, rtx *offset)
{
  rtx addr;

  gcc_assert (MEM_P (mem));

  addr = XEXP (mem, 0);
  
  if (GET_CODE (addr) == CONST)
    addr = XEXP (addr, 0);

  if (REG_P (addr) || GET_CODE (addr) == SYMBOL_REF)
    {
      *base = addr;
      *offset = const0_rtx;
      return true;
    }

  if (GET_CODE (addr) == PLUS
      && (REG_P (XEXP (addr, 0))
	  || GET_CODE (XEXP (addr, 0)) == SYMBOL_REF)
      && CONST_INT_P (XEXP (addr, 1)))
    {
      *base = XEXP (addr, 0);
      *offset = XEXP (addr, 1);
      return true;
    }

  return false;
}

/* Given OPERANDS of consecutive load/store, check if we can merge
   them into move multiple.  LOAD is true if they are load instructions.
   MODE is the mode of memory operands.  */

bool
ix86_operands_ok_for_move_multiple (rtx *operands, bool load,
				    machine_mode mode)
{
  HOST_WIDE_INT offval_1, offval_2, msize;
  rtx mem_1, mem_2, reg_1, reg_2, base_1, base_2, offset_1, offset_2;

  if (load)
    {
      mem_1 = operands[1];
      mem_2 = operands[3];
      reg_1 = operands[0];
      reg_2 = operands[2];
    }
  else
    {
      mem_1 = operands[0];
      mem_2 = operands[2];
      reg_1 = operands[1];
      reg_2 = operands[3];
    }

  gcc_assert (REG_P (reg_1) && REG_P (reg_2));

  if (REGNO (reg_1) != REGNO (reg_2))
    return false;

  /* Check if the addresses are in the form of [base+offset].  */
  if (!extract_base_offset_in_addr (mem_1, &base_1, &offset_1))
    return false;
  if (!extract_base_offset_in_addr (mem_2, &base_2, &offset_2))
    return false;

  /* Check if the bases are the same.  */
  if (!rtx_equal_p (base_1, base_2))
    return false;

  offval_1 = INTVAL (offset_1);
  offval_2 = INTVAL (offset_2);
  msize = GET_MODE_SIZE (mode);
  /* Check if mem_1 is adjacent to mem_2 and mem_1 has lower address.  */
  if (offval_1 + msize != offval_2)
    return false;

  return true;
}

/* Implement the TARGET_OPTAB_SUPPORTED_P hook.  */

static bool
ix86_optab_supported_p (int op, machine_mode mode1, machine_mode,
			optimization_type opt_type)
{
  switch (op)
    {
    case asin_optab:
    case acos_optab:
    case log1p_optab:
    case exp_optab:
    case exp10_optab:
    case exp2_optab:
    case expm1_optab:
    case ldexp_optab:
    case scalb_optab:
    case round_optab:
      return opt_type == OPTIMIZE_FOR_SPEED;

    case rint_optab:
      if (SSE_FLOAT_MODE_P (mode1)
	  && TARGET_SSE_MATH
	  && !flag_trapping_math
	  && !TARGET_SSE4_1)
	return opt_type == OPTIMIZE_FOR_SPEED;
      return true;

    case floor_optab:
    case ceil_optab:
    case btrunc_optab:
      if (SSE_FLOAT_MODE_P (mode1)
	  && TARGET_SSE_MATH
	  && !flag_trapping_math
	  && TARGET_SSE4_1)
	return true;
      return opt_type == OPTIMIZE_FOR_SPEED;

    case rsqrt_optab:
      return opt_type == OPTIMIZE_FOR_SPEED && use_rsqrt_p ();

    default:
      return true;
    }
}

/* Address space support.

   This is not "far pointers" in the 16-bit sense, but an easy way
   to use %fs and %gs segment prefixes.  Therefore:

    (a) All address spaces have the same modes,
    (b) All address spaces have the same addresss forms,
    (c) While %fs and %gs are technically subsets of the generic
        address space, they are probably not subsets of each other.
    (d) Since we have no access to the segment base register values
        without resorting to a system call, we cannot convert a
        non-default address space to a default address space.
        Therefore we do not claim %fs or %gs are subsets of generic.

   Therefore we can (mostly) use the default hooks.  */

/* All use of segmentation is assumed to make address 0 valid.  */

static bool
ix86_addr_space_zero_address_valid (addr_space_t as)
{
  return as != ADDR_SPACE_GENERIC;
}

static void
ix86_init_libfuncs (void)
{
  if (TARGET_64BIT)
    {
      set_optab_libfunc (sdivmod_optab, TImode, "__divmodti4");
      set_optab_libfunc (udivmod_optab, TImode, "__udivmodti4");
    }
  else
    {
      set_optab_libfunc (sdivmod_optab, DImode, "__divmoddi4");
      set_optab_libfunc (udivmod_optab, DImode, "__udivmoddi4");
    }

#if TARGET_MACHO
  darwin_rename_builtins ();
#endif
}

/* Generate call to __divmoddi4.  */

static void
ix86_expand_divmod_libfunc (rtx libfunc, machine_mode mode,
			    rtx op0, rtx op1,
			    rtx *quot_p, rtx *rem_p)
{
  rtx rem = assign_386_stack_local (mode, SLOT_TEMP);

  rtx quot = emit_library_call_value (libfunc, NULL_RTX, LCT_NORMAL,
				      mode, op0, mode, op1, mode,
				      XEXP (rem, 0), Pmode);
  *quot_p = quot;
  *rem_p = rem;
}

/* Set the value of FLT_EVAL_METHOD in float.h.  When using only the
   FPU, assume that the fpcw is set to extended precision; when using
   only SSE, rounding is correct; when using both SSE and the FPU,
   the rounding precision is indeterminate, since either may be chosen
   apparently at random.  */

static enum flt_eval_method
ix86_excess_precision (enum excess_precision_type type)
{
  switch (type)
    {
      case EXCESS_PRECISION_TYPE_FAST:
	/* The fastest type to promote to will always be the native type,
	   whether that occurs with implicit excess precision or
	   otherwise.  */
	return FLT_EVAL_METHOD_PROMOTE_TO_FLOAT;
      case EXCESS_PRECISION_TYPE_STANDARD:
      case EXCESS_PRECISION_TYPE_IMPLICIT:
	/* Otherwise, the excess precision we want when we are
	   in a standards compliant mode, and the implicit precision we
	   provide would be identical were it not for the unpredictable
	   cases.  */
	if (!TARGET_80387)
	  return FLT_EVAL_METHOD_PROMOTE_TO_FLOAT;
	else if (!TARGET_MIX_SSE_I387)
	  {
	    if (!TARGET_SSE_MATH)
	      return FLT_EVAL_METHOD_PROMOTE_TO_LONG_DOUBLE;
	    else if (TARGET_SSE2)
	      return FLT_EVAL_METHOD_PROMOTE_TO_FLOAT;
	  }

	/* If we are in standards compliant mode, but we know we will
	   calculate in unpredictable precision, return
	   FLT_EVAL_METHOD_FLOAT.  There is no reason to introduce explicit
	   excess precision if the target can't guarantee it will honor
	   it.  */
	return (type == EXCESS_PRECISION_TYPE_STANDARD
		? FLT_EVAL_METHOD_PROMOTE_TO_FLOAT
		: FLT_EVAL_METHOD_UNPREDICTABLE);
      default:
	gcc_unreachable ();
    }

  return FLT_EVAL_METHOD_UNPREDICTABLE;
}

/* Implement PUSH_ROUNDING.  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 for 32bit targets
   and -8 for 64bit targets, we need to make sure all stack pointer adjustments
   are in multiple of 4 for 32bit targets and 8 for 64bit targets.  */

poly_int64
ix86_push_rounding (poly_int64 bytes)
{
  return ROUND_UP (bytes, UNITS_PER_WORD);
}

/* Target-specific selftests.  */

#if CHECKING_P

namespace selftest {

/* Verify that hard regs are dumped as expected (in compact mode).  */

static void
ix86_test_dumping_hard_regs ()
{
  ASSERT_RTL_DUMP_EQ ("(reg:SI ax)", gen_raw_REG (SImode, 0));
  ASSERT_RTL_DUMP_EQ ("(reg:SI dx)", gen_raw_REG (SImode, 1));
}

/* Test dumping an insn with repeated references to the same SCRATCH,
   to verify the rtx_reuse code.  */

static void
ix86_test_dumping_memory_blockage ()
{
  set_new_first_and_last_insn (NULL, NULL);

  rtx pat = gen_memory_blockage ();
  rtx_reuse_manager r;
  r.preprocess (pat);

  /* Verify that the repeated references to the SCRATCH show use
     reuse IDS.  The first should be prefixed with a reuse ID,
     and the second should be dumped as a "reuse_rtx" of that ID.
     The expected string assumes Pmode == DImode.  */
  if (Pmode == DImode)
    ASSERT_RTL_DUMP_EQ_WITH_REUSE
      ("(cinsn 1 (set (mem/v:BLK (0|scratch:DI) [0  A8])\n"
       "        (unspec:BLK [\n"
       "                (mem/v:BLK (reuse_rtx 0) [0  A8])\n"
       "            ] UNSPEC_MEMORY_BLOCKAGE)))\n", pat, &r);
}

/* Verify loading an RTL dump; specifically a dump of copying
   a param on x86_64 from a hard reg into the frame.
   This test is target-specific since the dump contains target-specific
   hard reg names.  */

static void
ix86_test_loading_dump_fragment_1 ()
{
  rtl_dump_test t (SELFTEST_LOCATION,
		   locate_file ("x86_64/copy-hard-reg-into-frame.rtl"));

  rtx_insn *insn = get_insn_by_uid (1);

  /* The block structure and indentation here is purely for
     readability; it mirrors the structure of the rtx.  */
  tree mem_expr;
  {
    rtx pat = PATTERN (insn);
    ASSERT_EQ (SET, GET_CODE (pat));
    {
      rtx dest = SET_DEST (pat);
      ASSERT_EQ (MEM, GET_CODE (dest));
      /* Verify the "/c" was parsed.  */
      ASSERT_TRUE (RTX_FLAG (dest, call));
      ASSERT_EQ (SImode, GET_MODE (dest));
      {
	rtx addr = XEXP (dest, 0);
	ASSERT_EQ (PLUS, GET_CODE (addr));
	ASSERT_EQ (DImode, GET_MODE (addr));
	{
	  rtx lhs = XEXP (addr, 0);
	  /* Verify that the "frame" REG was consolidated.  */
	  ASSERT_RTX_PTR_EQ (frame_pointer_rtx, lhs);
	}
	{
	  rtx rhs = XEXP (addr, 1);
	  ASSERT_EQ (CONST_INT, GET_CODE (rhs));
	  ASSERT_EQ (-4, INTVAL (rhs));
	}
      }
      /* Verify the "[1 i+0 S4 A32]" was parsed.  */
      ASSERT_EQ (1, MEM_ALIAS_SET (dest));
      /* "i" should have been handled by synthesizing a global int
	 variable named "i".  */
      mem_expr = MEM_EXPR (dest);
      ASSERT_NE (mem_expr, NULL);
      ASSERT_EQ (VAR_DECL, TREE_CODE (mem_expr));
      ASSERT_EQ (integer_type_node, TREE_TYPE (mem_expr));
      ASSERT_EQ (IDENTIFIER_NODE, TREE_CODE (DECL_NAME (mem_expr)));
      ASSERT_STREQ ("i", IDENTIFIER_POINTER (DECL_NAME (mem_expr)));
      /* "+0".  */
      ASSERT_TRUE (MEM_OFFSET_KNOWN_P (dest));
      ASSERT_EQ (0, MEM_OFFSET (dest));
      /* "S4".  */
      ASSERT_EQ (4, MEM_SIZE (dest));
      /* "A32.  */
      ASSERT_EQ (32, MEM_ALIGN (dest));
    }
    {
      rtx src = SET_SRC (pat);
      ASSERT_EQ (REG, GET_CODE (src));
      ASSERT_EQ (SImode, GET_MODE (src));
      ASSERT_EQ (5, REGNO (src));
      tree reg_expr = REG_EXPR (src);
      /* "i" here should point to the same var as for the MEM_EXPR.  */
      ASSERT_EQ (reg_expr, mem_expr);
    }
  }
}

/* Verify that the RTL loader copes with a call_insn dump.
   This test is target-specific since the dump contains a target-specific
   hard reg name.  */

static void
ix86_test_loading_call_insn ()
{
  /* The test dump includes register "xmm0", where requires TARGET_SSE
     to exist.  */
  if (!TARGET_SSE)
    return;

  rtl_dump_test t (SELFTEST_LOCATION, locate_file ("x86_64/call-insn.rtl"));

  rtx_insn *insn = get_insns ();
  ASSERT_EQ (CALL_INSN, GET_CODE (insn));

  /* "/j".  */
  ASSERT_TRUE (RTX_FLAG (insn, jump));

  rtx pat = PATTERN (insn);
  ASSERT_EQ (CALL, GET_CODE (SET_SRC (pat)));

  /* Verify REG_NOTES.  */
  {
    /* "(expr_list:REG_CALL_DECL".   */
    ASSERT_EQ (EXPR_LIST, GET_CODE (REG_NOTES (insn)));
    rtx_expr_list *note0 = as_a <rtx_expr_list *> (REG_NOTES (insn));
    ASSERT_EQ (REG_CALL_DECL, REG_NOTE_KIND (note0));

    /* "(expr_list:REG_EH_REGION (const_int 0 [0])".  */
    rtx_expr_list *note1 = note0->next ();
    ASSERT_EQ (REG_EH_REGION, REG_NOTE_KIND (note1));

    ASSERT_EQ (NULL, note1->next ());
  }

  /* Verify CALL_INSN_FUNCTION_USAGE.  */
  {
    /* "(expr_list:DF (use (reg:DF 21 xmm0))".  */
    rtx_expr_list *usage
      = as_a <rtx_expr_list *> (CALL_INSN_FUNCTION_USAGE (insn));
    ASSERT_EQ (EXPR_LIST, GET_CODE (usage));
    ASSERT_EQ (DFmode, GET_MODE (usage));
    ASSERT_EQ (USE, GET_CODE (usage->element ()));
    ASSERT_EQ (NULL, usage->next ());
  }
}

/* Verify that the RTL loader copes a dump from print_rtx_function.
   This test is target-specific since the dump contains target-specific
   hard reg names.  */

static void
ix86_test_loading_full_dump ()
{
  rtl_dump_test t (SELFTEST_LOCATION, locate_file ("x86_64/times-two.rtl"));

  ASSERT_STREQ ("times_two", IDENTIFIER_POINTER (DECL_NAME (cfun->decl)));

  rtx_insn *insn_1 = get_insn_by_uid (1);
  ASSERT_EQ (NOTE, GET_CODE (insn_1));

  rtx_insn *insn_7 = get_insn_by_uid (7);
  ASSERT_EQ (INSN, GET_CODE (insn_7));
  ASSERT_EQ (PARALLEL, GET_CODE (PATTERN (insn_7)));

  rtx_insn *insn_15 = get_insn_by_uid (15);
  ASSERT_EQ (INSN, GET_CODE (insn_15));
  ASSERT_EQ (USE, GET_CODE (PATTERN (insn_15)));

  /* Verify crtl->return_rtx.  */
  ASSERT_EQ (REG, GET_CODE (crtl->return_rtx));
  ASSERT_EQ (0, REGNO (crtl->return_rtx));
  ASSERT_EQ (SImode, GET_MODE (crtl->return_rtx));
}

/* Verify that the RTL loader copes with UNSPEC and UNSPEC_VOLATILE insns.
   In particular, verify that it correctly loads the 2nd operand.
   This test is target-specific since these are machine-specific
   operands (and enums).  */

static void
ix86_test_loading_unspec ()
{
  rtl_dump_test t (SELFTEST_LOCATION, locate_file ("x86_64/unspec.rtl"));

  ASSERT_STREQ ("test_unspec", IDENTIFIER_POINTER (DECL_NAME (cfun->decl)));

  ASSERT_TRUE (cfun);

  /* Test of an UNSPEC.  */
   rtx_insn *insn = get_insns ();
  ASSERT_EQ (INSN, GET_CODE (insn));
  rtx set = single_set (insn);
  ASSERT_NE (NULL, set);
  rtx dst = SET_DEST (set);
  ASSERT_EQ (MEM, GET_CODE (dst));
  rtx src = SET_SRC (set);
  ASSERT_EQ (UNSPEC, GET_CODE (src));
  ASSERT_EQ (BLKmode, GET_MODE (src));
  ASSERT_EQ (UNSPEC_MEMORY_BLOCKAGE, XINT (src, 1));

  rtx v0 = XVECEXP (src, 0, 0);

  /* Verify that the two uses of the first SCRATCH have pointer
     equality.  */
  rtx scratch_a = XEXP (dst, 0);
  ASSERT_EQ (SCRATCH, GET_CODE (scratch_a));

  rtx scratch_b = XEXP (v0, 0);
  ASSERT_EQ (SCRATCH, GET_CODE (scratch_b));

  ASSERT_EQ (scratch_a, scratch_b);

  /* Verify that the two mems are thus treated as equal.  */
  ASSERT_TRUE (rtx_equal_p (dst, v0));

  /* Verify the the insn is recognized.  */
  ASSERT_NE(-1, recog_memoized (insn));

  /* Test of an UNSPEC_VOLATILE, which has its own enum values.  */
  insn = NEXT_INSN (insn);
  ASSERT_EQ (INSN, GET_CODE (insn));

  set = single_set (insn);
  ASSERT_NE (NULL, set);

  src = SET_SRC (set);
  ASSERT_EQ (UNSPEC_VOLATILE, GET_CODE (src));
  ASSERT_EQ (UNSPECV_RDTSCP, XINT (src, 1));
}

/* Run all target-specific selftests.  */

static void
ix86_run_selftests (void)
{
  ix86_test_dumping_hard_regs ();
  ix86_test_dumping_memory_blockage ();

  /* Various tests of loading RTL dumps, here because they contain
     ix86-isms (e.g. names of hard regs).  */
  ix86_test_loading_dump_fragment_1 ();
  ix86_test_loading_call_insn ();
  ix86_test_loading_full_dump ();
  ix86_test_loading_unspec ();
}

} // namespace selftest

#endif /* CHECKING_P */

/* Initialize the GCC target structure.  */
#undef TARGET_RETURN_IN_MEMORY
#define TARGET_RETURN_IN_MEMORY ix86_return_in_memory

#undef TARGET_LEGITIMIZE_ADDRESS
#define TARGET_LEGITIMIZE_ADDRESS ix86_legitimize_address

#undef TARGET_ATTRIBUTE_TABLE
#define TARGET_ATTRIBUTE_TABLE ix86_attribute_table
#undef TARGET_FUNCTION_ATTRIBUTE_INLINABLE_P
#define TARGET_FUNCTION_ATTRIBUTE_INLINABLE_P hook_bool_const_tree_true
#if TARGET_DLLIMPORT_DECL_ATTRIBUTES
#  undef TARGET_MERGE_DECL_ATTRIBUTES
#  define TARGET_MERGE_DECL_ATTRIBUTES merge_dllimport_decl_attributes
#endif

#undef TARGET_COMP_TYPE_ATTRIBUTES
#define TARGET_COMP_TYPE_ATTRIBUTES ix86_comp_type_attributes

#undef TARGET_INIT_BUILTINS
#define TARGET_INIT_BUILTINS ix86_init_builtins
#undef TARGET_BUILTIN_DECL
#define TARGET_BUILTIN_DECL ix86_builtin_decl
#undef TARGET_EXPAND_BUILTIN
#define TARGET_EXPAND_BUILTIN ix86_expand_builtin

#undef TARGET_VECTORIZE_BUILTIN_VECTORIZED_FUNCTION
#define TARGET_VECTORIZE_BUILTIN_VECTORIZED_FUNCTION \
  ix86_builtin_vectorized_function

#undef TARGET_VECTORIZE_BUILTIN_GATHER
#define TARGET_VECTORIZE_BUILTIN_GATHER ix86_vectorize_builtin_gather

#undef TARGET_VECTORIZE_BUILTIN_SCATTER
#define TARGET_VECTORIZE_BUILTIN_SCATTER ix86_vectorize_builtin_scatter

#undef TARGET_BUILTIN_RECIPROCAL
#define TARGET_BUILTIN_RECIPROCAL ix86_builtin_reciprocal

#undef TARGET_ASM_FUNCTION_EPILOGUE
#define TARGET_ASM_FUNCTION_EPILOGUE ix86_output_function_epilogue

#undef TARGET_ENCODE_SECTION_INFO
#ifndef SUBTARGET_ENCODE_SECTION_INFO
#define TARGET_ENCODE_SECTION_INFO ix86_encode_section_info
#else
#define TARGET_ENCODE_SECTION_INFO SUBTARGET_ENCODE_SECTION_INFO
#endif

#undef TARGET_ASM_OPEN_PAREN
#define TARGET_ASM_OPEN_PAREN ""
#undef TARGET_ASM_CLOSE_PAREN
#define TARGET_ASM_CLOSE_PAREN ""

#undef TARGET_ASM_BYTE_OP
#define TARGET_ASM_BYTE_OP ASM_BYTE

#undef TARGET_ASM_ALIGNED_HI_OP
#define TARGET_ASM_ALIGNED_HI_OP ASM_SHORT
#undef TARGET_ASM_ALIGNED_SI_OP
#define TARGET_ASM_ALIGNED_SI_OP ASM_LONG
#ifdef ASM_QUAD
#undef TARGET_ASM_ALIGNED_DI_OP
#define TARGET_ASM_ALIGNED_DI_OP ASM_QUAD
#endif

#undef TARGET_PROFILE_BEFORE_PROLOGUE
#define TARGET_PROFILE_BEFORE_PROLOGUE ix86_profile_before_prologue

#undef TARGET_MANGLE_DECL_ASSEMBLER_NAME
#define TARGET_MANGLE_DECL_ASSEMBLER_NAME ix86_mangle_decl_assembler_name

#undef TARGET_ASM_UNALIGNED_HI_OP
#define TARGET_ASM_UNALIGNED_HI_OP TARGET_ASM_ALIGNED_HI_OP
#undef TARGET_ASM_UNALIGNED_SI_OP
#define TARGET_ASM_UNALIGNED_SI_OP TARGET_ASM_ALIGNED_SI_OP
#undef TARGET_ASM_UNALIGNED_DI_OP
#define TARGET_ASM_UNALIGNED_DI_OP TARGET_ASM_ALIGNED_DI_OP

#undef TARGET_PRINT_OPERAND
#define TARGET_PRINT_OPERAND ix86_print_operand
#undef TARGET_PRINT_OPERAND_ADDRESS
#define TARGET_PRINT_OPERAND_ADDRESS ix86_print_operand_address
#undef TARGET_PRINT_OPERAND_PUNCT_VALID_P
#define TARGET_PRINT_OPERAND_PUNCT_VALID_P ix86_print_operand_punct_valid_p
#undef TARGET_ASM_OUTPUT_ADDR_CONST_EXTRA
#define TARGET_ASM_OUTPUT_ADDR_CONST_EXTRA i386_asm_output_addr_const_extra

#undef TARGET_SCHED_INIT_GLOBAL
#define TARGET_SCHED_INIT_GLOBAL ix86_sched_init_global
#undef TARGET_SCHED_ADJUST_COST
#define TARGET_SCHED_ADJUST_COST ix86_adjust_cost
#undef TARGET_SCHED_ISSUE_RATE
#define TARGET_SCHED_ISSUE_RATE ix86_issue_rate
#undef TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD
#define TARGET_SCHED_FIRST_CYCLE_MULTIPASS_DFA_LOOKAHEAD \
  ia32_multipass_dfa_lookahead
#undef TARGET_SCHED_MACRO_FUSION_P
#define TARGET_SCHED_MACRO_FUSION_P ix86_macro_fusion_p
#undef TARGET_SCHED_MACRO_FUSION_PAIR_P
#define TARGET_SCHED_MACRO_FUSION_PAIR_P ix86_macro_fusion_pair_p

#undef TARGET_FUNCTION_OK_FOR_SIBCALL
#define TARGET_FUNCTION_OK_FOR_SIBCALL ix86_function_ok_for_sibcall

#undef TARGET_MEMMODEL_CHECK
#define TARGET_MEMMODEL_CHECK ix86_memmodel_check

#undef TARGET_ATOMIC_ASSIGN_EXPAND_FENV
#define TARGET_ATOMIC_ASSIGN_EXPAND_FENV ix86_atomic_assign_expand_fenv

#ifdef HAVE_AS_TLS
#undef TARGET_HAVE_TLS
#define TARGET_HAVE_TLS true
#endif
#undef TARGET_CANNOT_FORCE_CONST_MEM
#define TARGET_CANNOT_FORCE_CONST_MEM ix86_cannot_force_const_mem
#undef TARGET_USE_BLOCKS_FOR_CONSTANT_P
#define TARGET_USE_BLOCKS_FOR_CONSTANT_P hook_bool_mode_const_rtx_true

#undef TARGET_DELEGITIMIZE_ADDRESS
#define TARGET_DELEGITIMIZE_ADDRESS ix86_delegitimize_address

#undef TARGET_CONST_NOT_OK_FOR_DEBUG_P
#define TARGET_CONST_NOT_OK_FOR_DEBUG_P ix86_const_not_ok_for_debug_p

#undef TARGET_MS_BITFIELD_LAYOUT_P
#define TARGET_MS_BITFIELD_LAYOUT_P ix86_ms_bitfield_layout_p

#if TARGET_MACHO
#undef TARGET_BINDS_LOCAL_P
#define TARGET_BINDS_LOCAL_P darwin_binds_local_p
#else
#undef TARGET_BINDS_LOCAL_P
#define TARGET_BINDS_LOCAL_P ix86_binds_local_p
#endif
#if TARGET_DLLIMPORT_DECL_ATTRIBUTES
#undef TARGET_BINDS_LOCAL_P
#define TARGET_BINDS_LOCAL_P i386_pe_binds_local_p
#endif

#undef TARGET_ASM_OUTPUT_MI_THUNK
#define TARGET_ASM_OUTPUT_MI_THUNK x86_output_mi_thunk
#undef TARGET_ASM_CAN_OUTPUT_MI_THUNK
#define TARGET_ASM_CAN_OUTPUT_MI_THUNK x86_can_output_mi_thunk

#undef TARGET_ASM_FILE_START
#define TARGET_ASM_FILE_START x86_file_start

#undef TARGET_OPTION_OVERRIDE
#define TARGET_OPTION_OVERRIDE ix86_option_override

#undef TARGET_REGISTER_MOVE_COST
#define TARGET_REGISTER_MOVE_COST ix86_register_move_cost
#undef TARGET_MEMORY_MOVE_COST
#define TARGET_MEMORY_MOVE_COST ix86_memory_move_cost
#undef TARGET_RTX_COSTS
#define TARGET_RTX_COSTS ix86_rtx_costs
#undef TARGET_ADDRESS_COST
#define TARGET_ADDRESS_COST ix86_address_cost

#undef TARGET_FLAGS_REGNUM
#define TARGET_FLAGS_REGNUM FLAGS_REG
#undef TARGET_FIXED_CONDITION_CODE_REGS
#define TARGET_FIXED_CONDITION_CODE_REGS ix86_fixed_condition_code_regs
#undef TARGET_CC_MODES_COMPATIBLE
#define TARGET_CC_MODES_COMPATIBLE ix86_cc_modes_compatible

#undef TARGET_MACHINE_DEPENDENT_REORG
#define TARGET_MACHINE_DEPENDENT_REORG ix86_reorg

#undef TARGET_BUILTIN_SETJMP_FRAME_VALUE
#define TARGET_BUILTIN_SETJMP_FRAME_VALUE ix86_builtin_setjmp_frame_value

#undef TARGET_BUILD_BUILTIN_VA_LIST
#define TARGET_BUILD_BUILTIN_VA_LIST ix86_build_builtin_va_list

#undef TARGET_FOLD_BUILTIN
#define TARGET_FOLD_BUILTIN ix86_fold_builtin

#undef TARGET_GIMPLE_FOLD_BUILTIN
#define TARGET_GIMPLE_FOLD_BUILTIN ix86_gimple_fold_builtin

#undef TARGET_COMPARE_VERSION_PRIORITY
#define TARGET_COMPARE_VERSION_PRIORITY ix86_compare_version_priority

#undef TARGET_GENERATE_VERSION_DISPATCHER_BODY
#define TARGET_GENERATE_VERSION_DISPATCHER_BODY \
  ix86_generate_version_dispatcher_body

#undef TARGET_GET_FUNCTION_VERSIONS_DISPATCHER
#define TARGET_GET_FUNCTION_VERSIONS_DISPATCHER \
  ix86_get_function_versions_dispatcher

#undef TARGET_ENUM_VA_LIST_P
#define TARGET_ENUM_VA_LIST_P ix86_enum_va_list

#undef TARGET_FN_ABI_VA_LIST
#define TARGET_FN_ABI_VA_LIST ix86_fn_abi_va_list

#undef TARGET_CANONICAL_VA_LIST_TYPE
#define TARGET_CANONICAL_VA_LIST_TYPE ix86_canonical_va_list_type

#undef TARGET_EXPAND_BUILTIN_VA_START
#define TARGET_EXPAND_BUILTIN_VA_START ix86_va_start

#undef TARGET_MD_ASM_ADJUST
#define TARGET_MD_ASM_ADJUST ix86_md_asm_adjust

#undef TARGET_C_EXCESS_PRECISION
#define TARGET_C_EXCESS_PRECISION ix86_excess_precision
#undef TARGET_PROMOTE_PROTOTYPES
#define TARGET_PROMOTE_PROTOTYPES hook_bool_const_tree_true
#undef TARGET_SETUP_INCOMING_VARARGS
#define TARGET_SETUP_INCOMING_VARARGS ix86_setup_incoming_varargs
#undef TARGET_MUST_PASS_IN_STACK
#define TARGET_MUST_PASS_IN_STACK ix86_must_pass_in_stack
#undef TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS
#define TARGET_ALLOCATE_STACK_SLOTS_FOR_ARGS ix86_allocate_stack_slots_for_args
#undef TARGET_FUNCTION_ARG_ADVANCE
#define TARGET_FUNCTION_ARG_ADVANCE ix86_function_arg_advance
#undef TARGET_FUNCTION_ARG
#define TARGET_FUNCTION_ARG ix86_function_arg
#undef TARGET_INIT_PIC_REG
#define TARGET_INIT_PIC_REG ix86_init_pic_reg
#undef TARGET_USE_PSEUDO_PIC_REG
#define TARGET_USE_PSEUDO_PIC_REG ix86_use_pseudo_pic_reg
#undef TARGET_FUNCTION_ARG_BOUNDARY
#define TARGET_FUNCTION_ARG_BOUNDARY ix86_function_arg_boundary
#undef TARGET_PASS_BY_REFERENCE
#define TARGET_PASS_BY_REFERENCE ix86_pass_by_reference
#undef TARGET_INTERNAL_ARG_POINTER
#define TARGET_INTERNAL_ARG_POINTER ix86_internal_arg_pointer
#undef TARGET_UPDATE_STACK_BOUNDARY
#define TARGET_UPDATE_STACK_BOUNDARY ix86_update_stack_boundary
#undef TARGET_GET_DRAP_RTX
#define TARGET_GET_DRAP_RTX ix86_get_drap_rtx
#undef TARGET_STRICT_ARGUMENT_NAMING
#define TARGET_STRICT_ARGUMENT_NAMING hook_bool_CUMULATIVE_ARGS_true
#undef TARGET_STATIC_CHAIN
#define TARGET_STATIC_CHAIN ix86_static_chain
#undef TARGET_TRAMPOLINE_INIT
#define TARGET_TRAMPOLINE_INIT ix86_trampoline_init
#undef TARGET_RETURN_POPS_ARGS
#define TARGET_RETURN_POPS_ARGS ix86_return_pops_args

#undef TARGET_WARN_FUNC_RETURN
#define TARGET_WARN_FUNC_RETURN ix86_warn_func_return

#undef TARGET_LEGITIMATE_COMBINED_INSN
#define TARGET_LEGITIMATE_COMBINED_INSN ix86_legitimate_combined_insn

#undef TARGET_ASAN_SHADOW_OFFSET
#define TARGET_ASAN_SHADOW_OFFSET ix86_asan_shadow_offset

#undef TARGET_GIMPLIFY_VA_ARG_EXPR
#define TARGET_GIMPLIFY_VA_ARG_EXPR ix86_gimplify_va_arg

#undef TARGET_SCALAR_MODE_SUPPORTED_P
#define TARGET_SCALAR_MODE_SUPPORTED_P ix86_scalar_mode_supported_p

#undef TARGET_VECTOR_MODE_SUPPORTED_P
#define TARGET_VECTOR_MODE_SUPPORTED_P ix86_vector_mode_supported_p

#undef TARGET_C_MODE_FOR_SUFFIX
#define TARGET_C_MODE_FOR_SUFFIX ix86_c_mode_for_suffix

#ifdef HAVE_AS_TLS
#undef TARGET_ASM_OUTPUT_DWARF_DTPREL
#define TARGET_ASM_OUTPUT_DWARF_DTPREL i386_output_dwarf_dtprel
#endif

#ifdef SUBTARGET_INSERT_ATTRIBUTES
#undef TARGET_INSERT_ATTRIBUTES
#define TARGET_INSERT_ATTRIBUTES SUBTARGET_INSERT_ATTRIBUTES
#endif

#undef TARGET_MANGLE_TYPE
#define TARGET_MANGLE_TYPE ix86_mangle_type

#undef TARGET_STACK_PROTECT_GUARD
#define TARGET_STACK_PROTECT_GUARD ix86_stack_protect_guard

#if !TARGET_MACHO
#undef TARGET_STACK_PROTECT_FAIL
#define TARGET_STACK_PROTECT_FAIL ix86_stack_protect_fail
#endif

#undef TARGET_FUNCTION_VALUE
#define TARGET_FUNCTION_VALUE ix86_function_value

#undef TARGET_FUNCTION_VALUE_REGNO_P
#define TARGET_FUNCTION_VALUE_REGNO_P ix86_function_value_regno_p

#undef TARGET_PROMOTE_FUNCTION_MODE
#define TARGET_PROMOTE_FUNCTION_MODE ix86_promote_function_mode

#undef  TARGET_OVERRIDE_OPTIONS_AFTER_CHANGE
#define TARGET_OVERRIDE_OPTIONS_AFTER_CHANGE ix86_override_options_after_change

#undef TARGET_MEMBER_TYPE_FORCES_BLK
#define TARGET_MEMBER_TYPE_FORCES_BLK ix86_member_type_forces_blk

#undef TARGET_INSTANTIATE_DECLS
#define TARGET_INSTANTIATE_DECLS ix86_instantiate_decls

#undef TARGET_SECONDARY_RELOAD
#define TARGET_SECONDARY_RELOAD ix86_secondary_reload
#undef TARGET_SECONDARY_MEMORY_NEEDED
#define TARGET_SECONDARY_MEMORY_NEEDED ix86_secondary_memory_needed
#undef TARGET_SECONDARY_MEMORY_NEEDED_MODE
#define TARGET_SECONDARY_MEMORY_NEEDED_MODE ix86_secondary_memory_needed_mode

#undef TARGET_CLASS_MAX_NREGS
#define TARGET_CLASS_MAX_NREGS ix86_class_max_nregs

#undef TARGET_PREFERRED_RELOAD_CLASS
#define TARGET_PREFERRED_RELOAD_CLASS ix86_preferred_reload_class
#undef TARGET_PREFERRED_OUTPUT_RELOAD_CLASS
#define TARGET_PREFERRED_OUTPUT_RELOAD_CLASS ix86_preferred_output_reload_class
#undef TARGET_CLASS_LIKELY_SPILLED_P
#define TARGET_CLASS_LIKELY_SPILLED_P ix86_class_likely_spilled_p

#undef TARGET_VECTORIZE_BUILTIN_VECTORIZATION_COST
#define TARGET_VECTORIZE_BUILTIN_VECTORIZATION_COST \
  ix86_builtin_vectorization_cost
#undef TARGET_VECTORIZE_VEC_PERM_CONST
#define TARGET_VECTORIZE_VEC_PERM_CONST ix86_vectorize_vec_perm_const
#undef TARGET_VECTORIZE_PREFERRED_SIMD_MODE
#define TARGET_VECTORIZE_PREFERRED_SIMD_MODE \
  ix86_preferred_simd_mode
#undef TARGET_VECTORIZE_SPLIT_REDUCTION
#define TARGET_VECTORIZE_SPLIT_REDUCTION \
  ix86_split_reduction
#undef TARGET_VECTORIZE_AUTOVECTORIZE_VECTOR_SIZES
#define TARGET_VECTORIZE_AUTOVECTORIZE_VECTOR_SIZES \
  ix86_autovectorize_vector_sizes
#undef TARGET_VECTORIZE_GET_MASK_MODE
#define TARGET_VECTORIZE_GET_MASK_MODE ix86_get_mask_mode
#undef TARGET_VECTORIZE_INIT_COST
#define TARGET_VECTORIZE_INIT_COST ix86_init_cost
#undef TARGET_VECTORIZE_ADD_STMT_COST
#define TARGET_VECTORIZE_ADD_STMT_COST ix86_add_stmt_cost
#undef TARGET_VECTORIZE_FINISH_COST
#define TARGET_VECTORIZE_FINISH_COST ix86_finish_cost
#undef TARGET_VECTORIZE_DESTROY_COST_DATA
#define TARGET_VECTORIZE_DESTROY_COST_DATA ix86_destroy_cost_data

#undef TARGET_SET_CURRENT_FUNCTION
#define TARGET_SET_CURRENT_FUNCTION ix86_set_current_function

#undef TARGET_OPTION_VALID_ATTRIBUTE_P
#define TARGET_OPTION_VALID_ATTRIBUTE_P ix86_valid_target_attribute_p

#undef TARGET_OPTION_SAVE
#define TARGET_OPTION_SAVE ix86_function_specific_save

#undef TARGET_OPTION_RESTORE
#define TARGET_OPTION_RESTORE ix86_function_specific_restore

#undef TARGET_OPTION_POST_STREAM_IN
#define TARGET_OPTION_POST_STREAM_IN ix86_function_specific_post_stream_in

#undef TARGET_OPTION_PRINT
#define TARGET_OPTION_PRINT ix86_function_specific_print

#undef TARGET_OPTION_FUNCTION_VERSIONS
#define TARGET_OPTION_FUNCTION_VERSIONS common_function_versions

#undef TARGET_CAN_INLINE_P
#define TARGET_CAN_INLINE_P ix86_can_inline_p

#undef TARGET_LEGITIMATE_ADDRESS_P
#define TARGET_LEGITIMATE_ADDRESS_P ix86_legitimate_address_p

#undef TARGET_REGISTER_PRIORITY
#define TARGET_REGISTER_PRIORITY ix86_register_priority

#undef TARGET_REGISTER_USAGE_LEVELING_P
#define TARGET_REGISTER_USAGE_LEVELING_P hook_bool_void_true

#undef TARGET_LEGITIMATE_CONSTANT_P
#define TARGET_LEGITIMATE_CONSTANT_P ix86_legitimate_constant_p

#undef TARGET_COMPUTE_FRAME_LAYOUT
#define TARGET_COMPUTE_FRAME_LAYOUT ix86_compute_frame_layout

#undef TARGET_FRAME_POINTER_REQUIRED
#define TARGET_FRAME_POINTER_REQUIRED ix86_frame_pointer_required

#undef TARGET_CAN_ELIMINATE
#define TARGET_CAN_ELIMINATE ix86_can_eliminate

#undef TARGET_EXTRA_LIVE_ON_ENTRY
#define TARGET_EXTRA_LIVE_ON_ENTRY ix86_live_on_entry

#undef TARGET_ASM_CODE_END
#define TARGET_ASM_CODE_END ix86_code_end

#undef TARGET_CONDITIONAL_REGISTER_USAGE
#define TARGET_CONDITIONAL_REGISTER_USAGE ix86_conditional_register_usage

#undef TARGET_CANONICALIZE_COMPARISON
#define TARGET_CANONICALIZE_COMPARISON ix86_canonicalize_comparison

#undef TARGET_LOOP_UNROLL_ADJUST
#define TARGET_LOOP_UNROLL_ADJUST ix86_loop_unroll_adjust

/* Disabled due to PRs 70902, 71453, 71555, 71596 and 71657.  */
#undef TARGET_SPILL_CLASS
#define TARGET_SPILL_CLASS ix86_spill_class

#undef TARGET_SIMD_CLONE_COMPUTE_VECSIZE_AND_SIMDLEN
#define TARGET_SIMD_CLONE_COMPUTE_VECSIZE_AND_SIMDLEN \
  ix86_simd_clone_compute_vecsize_and_simdlen

#undef TARGET_SIMD_CLONE_ADJUST
#define TARGET_SIMD_CLONE_ADJUST \
  ix86_simd_clone_adjust

#undef TARGET_SIMD_CLONE_USABLE
#define TARGET_SIMD_CLONE_USABLE \
  ix86_simd_clone_usable

#undef TARGET_FLOAT_EXCEPTIONS_ROUNDING_SUPPORTED_P
#define TARGET_FLOAT_EXCEPTIONS_ROUNDING_SUPPORTED_P \
  ix86_float_exceptions_rounding_supported_p

#undef TARGET_MODE_EMIT
#define TARGET_MODE_EMIT ix86_emit_mode_set

#undef TARGET_MODE_NEEDED
#define TARGET_MODE_NEEDED ix86_mode_needed

#undef TARGET_MODE_AFTER
#define TARGET_MODE_AFTER ix86_mode_after

#undef TARGET_MODE_ENTRY
#define TARGET_MODE_ENTRY ix86_mode_entry

#undef TARGET_MODE_EXIT
#define TARGET_MODE_EXIT ix86_mode_exit

#undef TARGET_MODE_PRIORITY
#define TARGET_MODE_PRIORITY ix86_mode_priority

#undef TARGET_CALL_FUSAGE_CONTAINS_NON_CALLEE_CLOBBERS
#define TARGET_CALL_FUSAGE_CONTAINS_NON_CALLEE_CLOBBERS true

#undef TARGET_SETUP_INCOMING_VARARG_BOUNDS
#define TARGET_SETUP_INCOMING_VARARG_BOUNDS ix86_setup_incoming_vararg_bounds

#undef TARGET_OFFLOAD_OPTIONS
#define TARGET_OFFLOAD_OPTIONS \
  ix86_offload_options

#undef TARGET_ABSOLUTE_BIGGEST_ALIGNMENT
#define TARGET_ABSOLUTE_BIGGEST_ALIGNMENT 512

#undef TARGET_OPTAB_SUPPORTED_P
#define TARGET_OPTAB_SUPPORTED_P ix86_optab_supported_p

#undef TARGET_HARD_REGNO_SCRATCH_OK
#define TARGET_HARD_REGNO_SCRATCH_OK ix86_hard_regno_scratch_ok

#undef TARGET_CUSTOM_FUNCTION_DESCRIPTORS
#define TARGET_CUSTOM_FUNCTION_DESCRIPTORS 1

#undef TARGET_ADDR_SPACE_ZERO_ADDRESS_VALID
#define TARGET_ADDR_SPACE_ZERO_ADDRESS_VALID ix86_addr_space_zero_address_valid

#undef TARGET_INIT_LIBFUNCS
#define TARGET_INIT_LIBFUNCS ix86_init_libfuncs

#undef TARGET_EXPAND_DIVMOD_LIBFUNC
#define TARGET_EXPAND_DIVMOD_LIBFUNC ix86_expand_divmod_libfunc

#undef TARGET_MAX_NOCE_IFCVT_SEQ_COST
#define TARGET_MAX_NOCE_IFCVT_SEQ_COST ix86_max_noce_ifcvt_seq_cost

#undef TARGET_NOCE_CONVERSION_PROFITABLE_P
#define TARGET_NOCE_CONVERSION_PROFITABLE_P ix86_noce_conversion_profitable_p

#undef TARGET_HARD_REGNO_NREGS
#define TARGET_HARD_REGNO_NREGS ix86_hard_regno_nregs
#undef TARGET_HARD_REGNO_MODE_OK
#define TARGET_HARD_REGNO_MODE_OK ix86_hard_regno_mode_ok

#undef TARGET_MODES_TIEABLE_P
#define TARGET_MODES_TIEABLE_P ix86_modes_tieable_p

#undef TARGET_HARD_REGNO_CALL_PART_CLOBBERED
#define TARGET_HARD_REGNO_CALL_PART_CLOBBERED \
  ix86_hard_regno_call_part_clobbered

#undef TARGET_CAN_CHANGE_MODE_CLASS
#define TARGET_CAN_CHANGE_MODE_CLASS ix86_can_change_mode_class

#undef TARGET_STATIC_RTX_ALIGNMENT
#define TARGET_STATIC_RTX_ALIGNMENT ix86_static_rtx_alignment
#undef TARGET_CONSTANT_ALIGNMENT
#define TARGET_CONSTANT_ALIGNMENT ix86_constant_alignment

#undef TARGET_EMPTY_RECORD_P
#define TARGET_EMPTY_RECORD_P ix86_is_empty_record

#undef TARGET_WARN_PARAMETER_PASSING_ABI
#define TARGET_WARN_PARAMETER_PASSING_ABI ix86_warn_parameter_passing_abi

#if CHECKING_P
#undef TARGET_RUN_TARGET_SELFTESTS
#define TARGET_RUN_TARGET_SELFTESTS selftest::ix86_run_selftests
#endif /* #if CHECKING_P */

struct gcc_target targetm = TARGET_INITIALIZER;

#include "gt-i386.h"
