summaryrefslogtreecommitdiff
path: root/gcc/config/i386
diff options
context:
space:
mode:
authorkyukhin <kyukhin@138bc75d-0d04-0410-961f-82ee72b054a4>2014-05-14 12:41:42 +0000
committerkyukhin <kyukhin@138bc75d-0d04-0410-961f-82ee72b054a4>2014-05-14 12:41:42 +0000
commit2ed4442834027d3fd77e9849f8a2c38ffedbb499 (patch)
tree1c4bf26f13325c4aba56d5bec9ba08dc20cacf1a /gcc/config/i386
parent8d1881f54cd2188321f36d49b2276c902c8cd1a0 (diff)
downloadgcc-2ed4442834027d3fd77e9849f8a2c38ffedbb499.tar.gz
gcc/
* common/config/i386/i386-common.c (OPTION_MASK_ISA_CLFLUSHOPT_SET): Define. (OPTION_MASK_ISA_XSAVES_SET): Ditto. (OPTION_MASK_ISA_XSAVEC_SET): Ditto. (OPTION_MASK_ISA_CLFLUSHOPT_UNSET): Ditto. (OPTION_MASK_ISA_XSAVES_UNSET): Ditto. (OPTION_MASK_ISA_XSAVEC_UNSET): Ditto. (ix86_handle_option): Handle OPT_mxsavec, OPT_mxsaves, OPT_mclflushopt. * config.gcc (i[34567]86-*-*): Add clflushoptintrin.h, xsavecintrin.h, xsavesintrin.h. (x86_64-*-*): Ditto. * config/i386/clflushoptintrin.h: New. * config/i386/xsavecintrin.h: Ditto. * config/i386/xsavesintrin.h: Ditto. * config/i386/cpuid.h (bit_CLFLUSHOPT): Define. (bit_XSAVES): Ditto. (bit_XSAVES): Ditto. * config/i386/driver-i386.c (host_detect_local_cpu): Handle -mclflushopt, -mxsavec, -mxsaves, -mno-xsaves, -mno-xsavec, -mno-clflushopt. * config/i386/i386-c.c (ix86_target_macros_internal): Handle OPTION_MASK_ISA_CLFLUSHOPT, OPTION_MASK_ISA_XSAVEC, OPTION_MASK_ISA_XSAVES. * config/i386/i386.c (ix86_target_string): Handle -mclflushopt, -mxsavec, -mxsaves. (PTA_CLFLUSHOPT) Define. (PTA_XSAVEC): Ditto. (PTA_XSAVES): Ditto. (ix86_option_override_internal): Handle new options. (ix86_valid_target_attribute_inner_p): Ditto. (ix86_builtins): Add IX86_BUILTIN_XSAVEC, IX86_BUILTIN_XSAVEC64, IX86_BUILTIN_XSAVES, IX86_BUILTIN_XRSTORS, IX86_BUILTIN_XSAVES64, IX86_BUILTIN_XRSTORS64, IX86_BUILTIN_CLFLUSHOPT. (bdesc_special_args): Add __builtin_ia32_xsaves, __builtin_ia32_xrstors, __builtin_ia32_xsavec, __builtin_ia32_xsaves64, __builtin_ia32_xrstors64, __builtin_ia32_xsavec64. (ix86_init_mmx_sse_builtins): Add __builtin_ia32_clflushopt. (ix86_expand_builtin): Handle new builtins. * config/i386/i386.h (TARGET_CLFLUSHOPT) Define. (TARGET_CLFLUSHOPT_P): Ditto. (TARGET_XSAVEC): Ditto. (TARGET_XSAVEC_P): Ditto. (TARGET_XSAVES): Ditto. (TARGET_XSAVES_P): Ditto. * config/i386/i386.md (ANY_XSAVE): Add UNSPECV_XSAVEC, UNSPECV_XSAVES. (ANY_XSAVE64)" Add UNSPECV_XSAVEC64, UNSPECV_XSAVES64. (attr xsave): Add xsavec, xsavec64, xsaves, xsaves64. (ANY_XRSTOR): New. (ANY_XRSTOR64): Ditto. (xrstor): Ditto. (xrstor): Change into <xrstor>. (xrstor_rex64): Change into <xrstor>_rex64. (xrstor64): Change into <xrstor>64 (clflushopt): New. * config/i386/i386.opt (mclflushopt): New. (mxsavec): Ditto. (mxsaves): Ditto. * config/i386/x86intrin.h: Add clflushoptintrin.h, xsavesintrin.h, xsavecintrin.h. * doc/invoke.texi: Document new options. gcc/testsuite/ * gcc.target/i386/clflushopt-1.c: New. * gcc.target/i386/xsavec-1.c: Ditto. * gcc.target/i386/xsavec64-1.c: Ditto. * gcc.target/i386/xsaves-1.c: Ditto. * gcc.target/i386/xsaves64-1.c: Ditto. * gcc.target/i386/sse-12.c: Test new options. * gcc.target/i386/sse-13.c: Ditto. * gcc.target/i386/sse-14.c: Ditto. * gcc.target/i386/sse-22.c: Ditto. * gcc.target/i386/sse-23.c: Ditto. * g++.dg/other/i386-2.C: Ditto. * g++.dg/other/i386-3.C: Ditto. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@210421 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/config/i386')
-rw-r--r--gcc/config/i386/clflushoptintrin.h49
-rw-r--r--gcc/config/i386/cpuid.h3
-rw-r--r--gcc/config/i386/driver-i386.c12
-rw-r--r--gcc/config/i386/i386-c.c6
-rw-r--r--gcc/config/i386/i386.c83
-rw-r--r--gcc/config/i386/i386.h6
-rw-r--r--gcc/config/i386/i386.md64
-rw-r--r--gcc/config/i386/i386.opt12
-rw-r--r--gcc/config/i386/x86intrin.h6
-rw-r--r--gcc/config/i386/xsavecintrin.h58
-rw-r--r--gcc/config/i386/xsavesintrin.h72
11 files changed, 357 insertions, 14 deletions
diff --git a/gcc/config/i386/clflushoptintrin.h b/gcc/config/i386/clflushoptintrin.h
new file mode 100644
index 00000000000..026561242ab
--- /dev/null
+++ b/gcc/config/i386/clflushoptintrin.h
@@ -0,0 +1,49 @@
+/* Copyright (C) 2013 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.
+
+ Under Section 7 of GPL version 3, you are granted additional
+ permissions described in the GCC Runtime Library Exception, version
+ 3.1, as published by the Free Software Foundation.
+
+ You should have received a copy of the GNU General Public License and
+ a copy of the GCC Runtime Library Exception along with this program;
+ see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
+ <http://www.gnu.org/licenses/>. */
+
+#if !defined _X86INTRIN_H_INCLUDED
+# error "Never use <clflushoptintrin.h> directly; include <x86intrin.h> instead."
+#endif
+
+#ifndef _CLFLUSHOPTINTRIN_H_INCLUDED
+#define _CLFLUSHOPTINTRIN_H_INCLUDED
+
+#ifndef __CLFLUSHOPT__
+#pragma GCC push_options
+#pragma GCC target("clflushopt")
+#define __DISABLE_CLFLUSHOPT__
+#endif /* __CLFLUSHOPT__ */
+
+extern __inline void
+__attribute__((__gnu_inline__, __always_inline__, __artificial__))
+_mm_clflushopt (void *__A)
+{
+ __builtin_ia32_clflushopt (__A);
+}
+
+#ifdef __DISABLE_CLFLUSHOPT__
+#undef __DISABLE_CLFLUSHOPT__
+#pragma GCC pop_options
+#endif /* __DISABLE_CLFLUSHOPT__ */
+
+#endif /* _CLFLUSHOPTINTRIN_H_INCLUDED */
diff --git a/gcc/config/i386/cpuid.h b/gcc/config/i386/cpuid.h
index 8c323ae3a70..7ac22a1683d 100644
--- a/gcc/config/i386/cpuid.h
+++ b/gcc/config/i386/cpuid.h
@@ -75,6 +75,7 @@
#define bit_AVX512F (1 << 16)
#define bit_RDSEED (1 << 18)
#define bit_ADX (1 << 19)
+#define bit_CLFLUSHOPT (1 << 23)
#define bit_AVX512PF (1 << 26)
#define bit_AVX512ER (1 << 27)
#define bit_AVX512CD (1 << 28)
@@ -85,6 +86,8 @@
/* Extended State Enumeration Sub-leaf (%eax == 13, %ecx == 1) */
#define bit_XSAVEOPT (1 << 0)
+#define bit_XSAVEC (1 << 1)
+#define bit_XSAVES (1 << 3)
/* Signatures for different CPU implementations as returned in uses
of cpuid with level 0. */
diff --git a/gcc/config/i386/driver-i386.c b/gcc/config/i386/driver-i386.c
index 1f5a11c9c08..3e8a995f285 100644
--- a/gcc/config/i386/driver-i386.c
+++ b/gcc/config/i386/driver-i386.c
@@ -410,6 +410,7 @@ const char *host_detect_local_cpu (int argc, const char **argv)
unsigned int has_osxsave = 0, has_fxsr = 0, has_xsave = 0, has_xsaveopt = 0;
unsigned int has_avx512er = 0, has_avx512pf = 0, has_avx512cd = 0;
unsigned int has_avx512f = 0, has_sha = 0, has_prefetchwt1 = 0;
+ unsigned int has_clflushopt = 0, has_xsavec = 0, has_xsaves = 0;
bool arch;
@@ -486,6 +487,7 @@ const char *host_detect_local_cpu (int argc, const char **argv)
has_avx512pf = ebx & bit_AVX512PF;
has_avx512cd = ebx & bit_AVX512CD;
has_sha = ebx & bit_SHA;
+ has_clflushopt = ebx & bit_CLFLUSHOPT;
has_prefetchwt1 = ecx & bit_PREFETCHWT1;
}
@@ -495,6 +497,8 @@ const char *host_detect_local_cpu (int argc, const char **argv)
__cpuid_count (13, 1, eax, ebx, ecx, edx);
has_xsaveopt = eax & bit_XSAVEOPT;
+ has_xsavec = eax & bit_XSAVEC;
+ has_xsaves = eax & bit_XSAVES;
}
/* Check cpuid level of extended features. */
@@ -541,6 +545,8 @@ const char *host_detect_local_cpu (int argc, const char **argv)
has_xop = 0;
has_xsave = 0;
has_xsaveopt = 0;
+ has_xsaves = 0;
+ has_xsavec = 0;
}
if (!arch)
@@ -886,6 +892,9 @@ const char *host_detect_local_cpu (int argc, const char **argv)
const char *avx512cd = has_avx512cd ? " -mavx512cd" : " -mno-avx512cd";
const char *avx512pf = has_avx512pf ? " -mavx512pf" : " -mno-avx512pf";
const char *prefetchwt1 = has_prefetchwt1 ? " -mprefetchwt1" : " -mno-prefetchwt1";
+ const char *clflushopt = has_clflushopt ? " -mclflushopt" : " -mno-clflushopt";
+ const char *xsavec = has_xsavec ? " -mxsavec" : " -mno-xsavec";
+ const char *xsaves = has_xsaves ? " -mxsaves" : " -mno-xsaves";
options = concat (options, mmx, mmx3dnow, sse, sse2, sse3, ssse3,
sse4a, cx16, sahf, movbe, aes, sha, pclmul,
@@ -893,7 +902,8 @@ const char *host_detect_local_cpu (int argc, const char **argv)
tbm, avx, avx2, sse4_2, sse4_1, lzcnt, rtm,
hle, rdrnd, f16c, fsgsbase, rdseed, prfchw, adx,
fxsr, xsave, xsaveopt, avx512f, avx512er,
- avx512cd, avx512pf, prefetchwt1, NULL);
+ avx512cd, avx512pf, prefetchwt1, clflushopt,
+ xsavec, xsaves, NULL);
}
done:
diff --git a/gcc/config/i386/i386-c.c b/gcc/config/i386/i386-c.c
index 2c31dc8062d..2c05cec0c4b 100644
--- a/gcc/config/i386/i386-c.c
+++ b/gcc/config/i386/i386-c.c
@@ -393,6 +393,12 @@ ix86_target_macros_internal (HOST_WIDE_INT isa_flag,
def_or_undef (parse_in, "__SSE_MATH__");
if ((fpmath & FPMATH_SSE) && (isa_flag & OPTION_MASK_ISA_SSE2))
def_or_undef (parse_in, "__SSE2_MATH__");
+ if (isa_flag & OPTION_MASK_ISA_CLFLUSHOPT)
+ def_or_undef (parse_in, "__CLFLUSHOPT__");
+ if (isa_flag & OPTION_MASK_ISA_XSAVEC)
+ def_or_undef (parse_in, "__XSAVEC__");
+ if (isa_flag & OPTION_MASK_ISA_XSAVES)
+ def_or_undef (parse_in, "__XSAVES__");
}
diff --git a/gcc/config/i386/i386.c b/gcc/config/i386/i386.c
index 0274288387e..b78f3c0e91a 100644
--- a/gcc/config/i386/i386.c
+++ b/gcc/config/i386/i386.c
@@ -2626,6 +2626,9 @@ ix86_target_string (HOST_WIDE_INT isa, int flags, const char *arch,
{ "-mxsave", OPTION_MASK_ISA_XSAVE },
{ "-mxsaveopt", OPTION_MASK_ISA_XSAVEOPT },
{ "-mprefetchwt1", OPTION_MASK_ISA_PREFETCHWT1 },
+ { "-mclflushopt", OPTION_MASK_ISA_CLFLUSHOPT },
+ { "-mxsavec", OPTION_MASK_ISA_XSAVEC },
+ { "-mxsaves", OPTION_MASK_ISA_XSAVES },
};
/* Flag options. */
@@ -3117,6 +3120,9 @@ ix86_option_override_internal (bool main_args_p,
#define PTA_AVX512CD (HOST_WIDE_INT_1 << 43)
#define PTA_SHA (HOST_WIDE_INT_1 << 45)
#define PTA_PREFETCHWT1 (HOST_WIDE_INT_1 << 46)
+#define PTA_CLFLUSHOPT (HOST_WIDE_INT_1 << 47)
+#define PTA_XSAVEC (HOST_WIDE_INT_1 << 48)
+#define PTA_XSAVES (HOST_WIDE_INT_1 << 49)
#define PTA_CORE2 \
(PTA_64BIT | PTA_MMX | PTA_SSE | PTA_SSE2 | PTA_SSE3 | PTA_SSSE3 \
@@ -3674,6 +3680,15 @@ ix86_option_override_internal (bool main_args_p,
if (processor_alias_table[i].flags & PTA_PREFETCHWT1
&& !(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_CLFLUSHOPT
+ && !(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_XSAVEC
+ && !(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
+ && !(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_PREFETCH_SSE | PTA_SSE))
x86_prefetch_sse = true;
@@ -4557,6 +4572,9 @@ ix86_valid_target_attribute_inner_p (tree args, char *p_strings[],
IX86_ATTR_ISA ("xsave", OPT_mxsave),
IX86_ATTR_ISA ("xsaveopt", OPT_mxsaveopt),
IX86_ATTR_ISA ("prefetchwt1", OPT_mprefetchwt1),
+ IX86_ATTR_ISA ("clflushopt", OPT_mclflushopt),
+ IX86_ATTR_ISA ("xsavec", OPT_mxsavec),
+ IX86_ATTR_ISA ("xsaves", OPT_mxsaves),
/* enum options */
IX86_ATTR_ENUM ("fpmath=", OPT_mfpmath_),
@@ -27311,6 +27329,14 @@ enum ix86_builtins
IX86_BUILTIN_XSAVEOPT,
IX86_BUILTIN_XSAVEOPT64,
+ IX86_BUILTIN_XSAVEC,
+ IX86_BUILTIN_XSAVEC64,
+
+ IX86_BUILTIN_XSAVES,
+ IX86_BUILTIN_XRSTORS,
+ IX86_BUILTIN_XSAVES64,
+ IX86_BUILTIN_XRSTORS64,
+
/* 3DNow! Original */
IX86_BUILTIN_FEMMS,
IX86_BUILTIN_PAVGUSB,
@@ -28506,6 +28532,9 @@ enum ix86_builtins
IX86_BUILTIN_SHA256MSG2,
IX86_BUILTIN_SHA256RNDS2,
+ /* CLFLUSHOPT instructions. */
+ IX86_BUILTIN_CLFLUSHOPT,
+
/* TFmode support builtins. */
IX86_BUILTIN_INFQ,
IX86_BUILTIN_HUGE_VALQ,
@@ -28965,18 +28994,24 @@ static const struct builtin_description bdesc_special_args[] =
/* 3DNow! */
{ OPTION_MASK_ISA_3DNOW, CODE_FOR_mmx_femms, "__builtin_ia32_femms", IX86_BUILTIN_FEMMS, UNKNOWN, (int) VOID_FTYPE_VOID },
- /* FXSR, XSAVE and XSAVEOPT */
+ /* FXSR, XSAVE, XSAVEOPT, XSAVEC and XSAVES. */
{ OPTION_MASK_ISA_FXSR, CODE_FOR_nothing, "__builtin_ia32_fxsave", IX86_BUILTIN_FXSAVE, UNKNOWN, (int) VOID_FTYPE_PVOID },
{ OPTION_MASK_ISA_FXSR, CODE_FOR_nothing, "__builtin_ia32_fxrstor", IX86_BUILTIN_FXRSTOR, UNKNOWN, (int) VOID_FTYPE_PVOID },
{ OPTION_MASK_ISA_XSAVE, CODE_FOR_nothing, "__builtin_ia32_xsave", IX86_BUILTIN_XSAVE, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
{ OPTION_MASK_ISA_XSAVE, CODE_FOR_nothing, "__builtin_ia32_xrstor", IX86_BUILTIN_XRSTOR, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
{ OPTION_MASK_ISA_XSAVEOPT, CODE_FOR_nothing, "__builtin_ia32_xsaveopt", IX86_BUILTIN_XSAVEOPT, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
+ { OPTION_MASK_ISA_XSAVES, CODE_FOR_nothing, "__builtin_ia32_xsaves", IX86_BUILTIN_XSAVES, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
+ { OPTION_MASK_ISA_XSAVES, CODE_FOR_nothing, "__builtin_ia32_xrstors", IX86_BUILTIN_XRSTORS, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
+ { OPTION_MASK_ISA_XSAVEC, CODE_FOR_nothing, "__builtin_ia32_xsavec", IX86_BUILTIN_XSAVEC, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
{ OPTION_MASK_ISA_FXSR | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_fxsave64", IX86_BUILTIN_FXSAVE64, UNKNOWN, (int) VOID_FTYPE_PVOID },
{ OPTION_MASK_ISA_FXSR | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_fxrstor64", IX86_BUILTIN_FXRSTOR64, UNKNOWN, (int) VOID_FTYPE_PVOID },
{ OPTION_MASK_ISA_XSAVE | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_xsave64", IX86_BUILTIN_XSAVE64, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
{ OPTION_MASK_ISA_XSAVE | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_xrstor64", IX86_BUILTIN_XRSTOR64, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
{ OPTION_MASK_ISA_XSAVEOPT | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_xsaveopt64", IX86_BUILTIN_XSAVEOPT64, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
+ { OPTION_MASK_ISA_XSAVES | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_xsaves64", IX86_BUILTIN_XSAVES64, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
+ { OPTION_MASK_ISA_XSAVES | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_xrstors64", IX86_BUILTIN_XRSTORS64, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
+ { OPTION_MASK_ISA_XSAVEC | OPTION_MASK_ISA_64BIT, CODE_FOR_nothing, "__builtin_ia32_xsavec64", IX86_BUILTIN_XSAVEC64, UNKNOWN, (int) VOID_FTYPE_PVOID_INT64 },
/* SSE */
{ OPTION_MASK_ISA_SSE, CODE_FOR_sse_storeups, "__builtin_ia32_storeups", IX86_BUILTIN_STOREUPS, UNKNOWN, (int) VOID_FTYPE_PFLOAT_V4SF },
@@ -31154,6 +31189,9 @@ ix86_init_mmx_sse_builtins (void)
def_builtin (OPTION_MASK_ISA_64BIT, "__builtin_ia32_writeeflags_u64",
VOID_FTYPE_UINT64, IX86_BUILTIN_WRITE_FLAGS);
+ /* CLFLUSHOPT. */
+ def_builtin (OPTION_MASK_ISA_CLFLUSHOPT, "__builtin_ia32_clflushopt",
+ VOID_FTYPE_PCVOID, IX86_BUILTIN_CLFLUSHOPT);
/* Add FMA4 multi-arg argument instructions */
for (i = 0, d = bdesc_multi_arg; i < ARRAY_SIZE (bdesc_multi_arg); i++, d++)
@@ -35086,6 +35124,16 @@ ix86_expand_builtin (tree exp, rtx target, rtx subtarget,
emit_insn (gen_sse2_clflush (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:
arg0 = CALL_EXPR_ARG (exp, 0);
arg1 = CALL_EXPR_ARG (exp, 1);
@@ -35277,6 +35325,12 @@ ix86_expand_builtin (tree exp, rtx target, rtx subtarget,
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);
@@ -35315,6 +35369,24 @@ ix86_expand_builtin (tree exp, rtx target, rtx subtarget,
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 ();
}
@@ -35336,6 +35408,15 @@ ix86_expand_builtin (tree exp, rtx target, rtx subtarget,
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 ();
}
diff --git a/gcc/config/i386/i386.h b/gcc/config/i386/i386.h
index 6e2ac156bdb..a4009d3a83b 100644
--- a/gcc/config/i386/i386.h
+++ b/gcc/config/i386/i386.h
@@ -104,6 +104,12 @@ see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
#define TARGET_AES_P(x) TARGET_ISA_AES_P(x)
#define TARGET_SHA TARGET_ISA_SHA
#define TARGET_SHA_P(x) TARGET_ISA_SHA_P(x)
+#define TARGET_CLFLUSHOPT TARGET_ISA_CLFLUSHOPT
+#define TARGET_CLFLUSHOPT_P(x) TARGET_ISA_CLFLUSHOPT_P(x)
+#define TARGET_XSAVEC TARGET_ISA_XSAVEC
+#define TARGET_XSAVEC_P(x) TARGET_ISA_XSAVEC_P(x)
+#define TARGET_XSAVES TARGET_ISA_XSAVES
+#define TARGET_XSAVES_P(x) TARGET_ISA_XSAVES_P(x)
#define TARGET_PCLMUL TARGET_ISA_PCLMUL
#define TARGET_PCLMUL_P(x) TARGET_ISA_PCLMUL_P(x)
#define TARGET_CMPXCHG16B TARGET_ISA_CX16
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md
index 30dafec52cf..44e80ecc5cf 100644
--- a/gcc/config/i386/i386.md
+++ b/gcc/config/i386/i386.md
@@ -213,6 +213,12 @@
UNSPECV_XRSTOR64
UNSPECV_XSAVEOPT
UNSPECV_XSAVEOPT64
+ UNSPECV_XSAVES
+ UNSPECV_XRSTORS
+ UNSPECV_XSAVES64
+ UNSPECV_XRSTORS64
+ UNSPECV_XSAVEC
+ UNSPECV_XSAVEC64
;; For atomic compound assignments.
UNSPECV_FNSTENV
@@ -233,6 +239,9 @@
UNSPECV_XTEST
UNSPECV_NLGR
+
+ ;; For CLFLUSHOPT support
+ UNSPECV_CLFLUSHOPT
])
;; Constants to represent rounding modes in the ROUND instruction
@@ -17798,17 +17807,39 @@
(define_int_iterator ANY_XSAVE
[UNSPECV_XSAVE
- (UNSPECV_XSAVEOPT "TARGET_XSAVEOPT")])
+ (UNSPECV_XSAVEOPT "TARGET_XSAVEOPT")
+ (UNSPECV_XSAVEC "TARGET_XSAVEC")
+ (UNSPECV_XSAVES "TARGET_XSAVES")])
(define_int_iterator ANY_XSAVE64
[UNSPECV_XSAVE64
- (UNSPECV_XSAVEOPT64 "TARGET_XSAVEOPT")])
+ (UNSPECV_XSAVEOPT64 "TARGET_XSAVEOPT")
+ (UNSPECV_XSAVEC64 "TARGET_XSAVEC")
+ (UNSPECV_XSAVES64 "TARGET_XSAVES")])
(define_int_attr xsave
[(UNSPECV_XSAVE "xsave")
(UNSPECV_XSAVE64 "xsave64")
(UNSPECV_XSAVEOPT "xsaveopt")
- (UNSPECV_XSAVEOPT64 "xsaveopt64")])
+ (UNSPECV_XSAVEOPT64 "xsaveopt64")
+ (UNSPECV_XSAVEC "xsavec")
+ (UNSPECV_XSAVEC64 "xsavec64")
+ (UNSPECV_XSAVES "xsaves")
+ (UNSPECV_XSAVES64 "xsaves64")])
+
+(define_int_iterator ANY_XRSTOR
+ [UNSPECV_XRSTOR
+ (UNSPECV_XRSTORS "TARGET_XSAVES")])
+
+(define_int_iterator ANY_XRSTOR64
+ [UNSPECV_XRSTOR64
+ (UNSPECV_XRSTORS64 "TARGET_XSAVES")])
+
+(define_int_attr xrstor
+ [(UNSPECV_XRSTOR "xrstor")
+ (UNSPECV_XRSTOR64 "xrstor")
+ (UNSPECV_XRSTORS "xrstors")
+ (UNSPECV_XRSTORS64 "xrstors")])
(define_insn "<xsave>"
[(set (match_operand:BLK 0 "memory_operand" "=m")
@@ -17848,39 +17879,39 @@
(set (attr "length")
(symbol_ref "ix86_attr_length_address_default (insn) + 4"))])
-(define_insn "xrstor"
+(define_insn "<xrstor>"
[(unspec_volatile:BLK
[(match_operand:BLK 0 "memory_operand" "m")
(match_operand:DI 1 "register_operand" "A")]
- UNSPECV_XRSTOR)]
+ ANY_XRSTOR)]
"!TARGET_64BIT && TARGET_XSAVE"
- "xrstor\t%0"
+ "<xrstor>\t%0"
[(set_attr "type" "other")
(set_attr "memory" "load")
(set (attr "length")
(symbol_ref "ix86_attr_length_address_default (insn) + 3"))])
-(define_insn "xrstor_rex64"
+(define_insn "<xrstor>_rex64"
[(unspec_volatile:BLK
[(match_operand:BLK 0 "memory_operand" "m")
(match_operand:SI 1 "register_operand" "a")
(match_operand:SI 2 "register_operand" "d")]
- UNSPECV_XRSTOR)]
+ ANY_XRSTOR)]
"TARGET_64BIT && TARGET_XSAVE"
- "xrstor\t%0"
+ "<xrstor>\t%0"
[(set_attr "type" "other")
(set_attr "memory" "load")
(set (attr "length")
(symbol_ref "ix86_attr_length_address_default (insn) + 3"))])
-(define_insn "xrstor64"
+(define_insn "<xrstor>64"
[(unspec_volatile:BLK
[(match_operand:BLK 0 "memory_operand" "m")
(match_operand:SI 1 "register_operand" "a")
(match_operand:SI 2 "register_operand" "d")]
- UNSPECV_XRSTOR64)]
+ ANY_XRSTOR64)]
"TARGET_64BIT && TARGET_XSAVE"
- "xrstor64\t%0"
+ "<xrstor>64\t%0"
[(set_attr "type" "other")
(set_attr "memory" "load")
(set (attr "length")
@@ -18178,6 +18209,15 @@
[(set_attr "type" "other")
(set_attr "length" "3")])
+(define_insn "clflushopt"
+ [(unspec_volatile [(match_operand 0 "address_operand" "p")]
+ UNSPECV_CLFLUSHOPT)]
+ "TARGET_CLFLUSHOPT"
+ "clflushopt\t%a0"
+ [(set_attr "type" "sse")
+ (set_attr "atom_sse_attr" "fence")
+ (set_attr "memory" "unknown")])
+
(include "mmx.md")
(include "sse.md")
(include "sync.md")
diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt
index 0f463a23820..dc1302c5a01 100644
--- a/gcc/config/i386/i386.opt
+++ b/gcc/config/i386/i386.opt
@@ -697,6 +697,10 @@ madx
Target Report Mask(ISA_ADX) Var(ix86_isa_flags) Save
Support flag-preserving add-carry instructions
+mclflushopt
+Target Report Mask(ISA_CLFLUSHOPT) Var(ix86_isa_flags) Save
+Support CLFLUSHOPT instructions
+
mfxsr
Target Report Mask(ISA_FXSR) Var(ix86_isa_flags) Save
Support FXSAVE and FXRSTOR instructions
@@ -709,6 +713,14 @@ mxsaveopt
Target Report Mask(ISA_XSAVEOPT) Var(ix86_isa_flags) Save
Support XSAVEOPT instruction
+mxsavec
+Target Report Mask(ISA_XSAVEC) Var(ix86_isa_flags) Save
+Support XSAVEC instructions
+
+mxsaves
+Target Report Mask(ISA_XSAVES) Var(ix86_isa_flags) Save
+Support XSAVES and XRSTORS instructions
+
mtbm
Target Report Mask(ISA_TBM) Var(ix86_isa_flags) Save
Support TBM built-in functions and code generation
diff --git a/gcc/config/i386/x86intrin.h b/gcc/config/i386/x86intrin.h
index 80e9e6f33de..c84ab88c8c0 100644
--- a/gcc/config/i386/x86intrin.h
+++ b/gcc/config/i386/x86intrin.h
@@ -75,4 +75,10 @@
#include <adxintrin.h>
+#include <clflushoptintrin.h>
+
+#include <xsavesintrin.h>
+
+#include <xsavecintrin.h>
+
#endif /* _X86INTRIN_H_INCLUDED */
diff --git a/gcc/config/i386/xsavecintrin.h b/gcc/config/i386/xsavecintrin.h
new file mode 100644
index 00000000000..99fadd5988e
--- /dev/null
+++ b/gcc/config/i386/xsavecintrin.h
@@ -0,0 +1,58 @@
+/* Copyright (C) 2014 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.
+
+ Under Section 7 of GPL version 3, you are granted additional
+ permissions described in the GCC Runtime Library Exception, version
+ 3.1, as published by the Free Software Foundation.
+
+ You should have received a copy of the GNU General Public License and
+ a copy of the GCC Runtime Library Exception along with this program;
+ see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
+ <http://www.gnu.org/licenses/>. */
+
+#if !defined _X86INTRIN_H_INCLUDED
+# error "Never use <xsavecintrin.h> directly; include <x86intrin.h> instead."
+#endif
+
+#ifndef _XSAVECINTRIN_H_INCLUDED
+#define _XSAVECINTRIN_H_INCLUDED
+
+#ifndef __XSAVEC__
+#pragma GCC push_options
+#pragma GCC target("xsavec")
+#define __DISABLE_XSAVEC__
+#endif /* __XSAVEC__ */
+
+extern __inline void
+__attribute__((__gnu_inline__, __always_inline__, __artificial__))
+_xsavec (void *__P, long long __M)
+{
+ __builtin_ia32_xsavec (__P, __M);
+}
+
+#ifdef __x86_64__
+extern __inline void
+__attribute__((__gnu_inline__, __always_inline__, __artificial__))
+_xsavec64 (void *__P, long long __M)
+{
+ __builtin_ia32_xsavec64 (__P, __M);
+}
+#endif
+
+#ifdef __DISABLE_XSAVEC__
+#undef __DISABLE_XSAVEC__
+#pragma GCC pop_options
+#endif /* __DISABLE_XSAVEC__ */
+
+#endif /* _XSAVECINTRIN_H_INCLUDED */
diff --git a/gcc/config/i386/xsavesintrin.h b/gcc/config/i386/xsavesintrin.h
new file mode 100644
index 00000000000..a08a81ae82d
--- /dev/null
+++ b/gcc/config/i386/xsavesintrin.h
@@ -0,0 +1,72 @@
+/* Copyright (C) 2014 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.
+
+ Under Section 7 of GPL version 3, you are granted additional
+ permissions described in the GCC Runtime Library Exception, version
+ 3.1, as published by the Free Software Foundation.
+
+ You should have received a copy of the GNU General Public License and
+ a copy of the GCC Runtime Library Exception along with this program;
+ see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
+ <http://www.gnu.org/licenses/>. */
+
+#if !defined _X86INTRIN_H_INCLUDED
+# error "Never use <xsavesintrin.h> directly; include <x86intrin.h> instead."
+#endif
+
+#ifndef _XSAVESINTRIN_H_INCLUDED
+#define _XSAVESINTRIN_H_INCLUDED
+
+#ifndef __XSAVES__
+#pragma GCC push_options
+#pragma GCC target("xsaves")
+#define __DISABLE_XSAVES__
+#endif /* __XSAVES__ */
+
+extern __inline void
+__attribute__((__gnu_inline__, __always_inline__, __artificial__))
+_xsaves (void *__P, long long __M)
+{
+ __builtin_ia32_xsaves (__P, __M);
+}
+
+extern __inline void
+__attribute__((__gnu_inline__, __always_inline__, __artificial__))
+_xrstors (void *__P, long long __M)
+{
+ __builtin_ia32_xrstors (__P, __M);
+}
+
+#ifdef __x86_64__
+extern __inline void
+__attribute__((__gnu_inline__, __always_inline__, __artificial__))
+_xrstors64 (void *__P, long long __M)
+{
+ __builtin_ia32_xrstors64 (__P, __M);
+}
+
+extern __inline void
+__attribute__((__gnu_inline__, __always_inline__, __artificial__))
+_xsaves64 (void *__P, long long __M)
+{
+ __builtin_ia32_xsaves64 (__P, __M);
+}
+#endif
+
+#ifdef __DISABLE_XSAVES__
+#undef __DISABLE_XSAVES__
+#pragma GCC pop_options
+#endif /* __DISABLE_XSAVES__ */
+
+#endif /* _XSAVESINTRIN_H_INCLUDED */