aboutsummaryrefslogtreecommitdiff
path: root/gcc/config
diff options
context:
space:
mode:
authorHaochen Jiang <haochen.jiang@intel.com>2022-11-04 09:20:54 +0800
committerHaochen Jiang <haochen.jiang@intel.com>2022-11-04 09:35:52 +0800
commit152834feffa233ade3fc9c9aa6237c9a447ef62c (patch)
tree906e7ed2ce446ea3d699dad20ad3e1685d8552bd /gcc/config
parentd29260ce806a3aa415f3642fe5720901dad78531 (diff)
downloadgcc-152834feffa233ade3fc9c9aa6237c9a447ef62c.zip
gcc-152834feffa233ade3fc9c9aa6237c9a447ef62c.tar.gz
gcc-152834feffa233ade3fc9c9aa6237c9a447ef62c.tar.bz2
Support Intel CMPccXADD
gcc/ChangeLog: * common/config/i386/cpuinfo.h (get_available_features): Detect cmpccxadd. * common/config/i386/i386-common.cc (OPTION_MASK_ISA2_CMPCCXADD_SET, OPTION_MASK_ISA2_CMPCCXADD_UNSET): New. (ix86_handle_option): Handle -mcmpccxadd. * common/config/i386/i386-cpuinfo.h (enum processor_features): Add FEATURE_CMPCCXADD. * common/config/i386/i386-isas.h: Add ISA_NAME_TABLE_ENTRY for cmpccxadd. * config.gcc: Add cmpccxaddintrin.h. * config/i386/cpuid.h (bit_CMPCCXADD): New. * config/i386/i386-builtin-types.def: Add DEF_FUNCTION_TYPE(INT, PINT, INT, INT, INT) and DEF_FUNCTION_TYPE(LONGLONG, PLONGLONG, LONGLONG, LONGLONG, INT). * config/i386/i386-builtin.def (BDESC): Add new builtins. * config/i386/i386-c.cc (ix86_target_macros_internal): Define __CMPCCXADD__. * config/i386/i386-expand.cc (ix86_expand_special_args_builtin): Add new parameter to indicate constant position. Handle INT_FTYPE_PINT_INT_INT_INT and LONGLONG_FTYPE_PLONGLONG_LONGLONG_LONGLONG_INT. * config/i386/i386-isa.def (CMPCCXADD): Add DEF_PTA(CMPCCXADD). * config/i386/i386-options.cc (isa2_opts): Add -mcmpccxadd. (ix86_valid_target_attribute_inner_p): Handle cmpccxadd. * config/i386/i386.opt: Add option -mcmpccxadd. * config/i386/sync.md (cmpccxadd_<mode>): New define insn. * config/i386/x86gprintrin.h: Include cmpccxaddintrin.h. * doc/extend.texi: Document cmpccxadd. * doc/invoke.texi: Document -mcmpccxadd. * doc/sourcebuild.texi: Document target cmpccxadd. * config/i386/cmpccxaddintrin.h: New file. gcc/testsuite/ChangeLog: * g++.dg/other/i386-2.C: Add -mcmpccxadd. * g++.dg/other/i386-3.C: Ditto. * gcc.target/i386/avx-1.c: Ditto. * gcc.target/i386/funcspec-56.inc: Add new target attribute. * gcc.target/i386/sse-13.c: Add -mcmpccxadd. * gcc.target/i386/sse-23.c: Ditto. * gcc.target/i386/x86gprintrin-1.c: Ditto. * gcc.target/i386/x86gprintrin-2.c: Ditto. * gcc.target/i386/x86gprintrin-3.c: Ditto. * gcc.target/i386/x86gprintrin-4.c: Ditto. * gcc.target/i386/x86gprintrin-5.c: Ditto. * lib/target-supports.exp (check_effective_target_cmpccxadd): New. * gcc.target/i386/cmpccxadd-1.c: New test. * gcc.target/i386/cmpccxadd-2.c: Ditto.
Diffstat (limited to 'gcc/config')
-rw-r--r--gcc/config/i386/cmpccxaddintrin.h89
-rw-r--r--gcc/config/i386/cpuid.h1
-rw-r--r--gcc/config/i386/i386-builtin-types.def4
-rw-r--r--gcc/config/i386/i386-builtin.def4
-rw-r--r--gcc/config/i386/i386-c.cc2
-rw-r--r--gcc/config/i386/i386-expand.cc22
-rw-r--r--gcc/config/i386/i386-isa.def1
-rw-r--r--gcc/config/i386/i386-options.cc4
-rw-r--r--gcc/config/i386/i386.opt5
-rw-r--r--gcc/config/i386/sync.md28
-rw-r--r--gcc/config/i386/x86gprintrin.h2
11 files changed, 160 insertions, 2 deletions
diff --git a/gcc/config/i386/cmpccxaddintrin.h b/gcc/config/i386/cmpccxaddintrin.h
new file mode 100644
index 0000000..1afa03b
--- /dev/null
+++ b/gcc/config/i386/cmpccxaddintrin.h
@@ -0,0 +1,89 @@
+/* Copyright (C) 2012-2021 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/>. */
+
+#ifndef _X86GPRINTRIN_H_INCLUDED
+#error "Never use <cmpccxaddintrin.h> directly; include <x86gprintrin.h> instead."
+#endif
+
+#ifndef _CMPCCXADDINTRIN_H_INCLUDED
+#define _CMPCCXADDINTRIN_H_INCLUDED
+
+#ifdef __x86_64__
+
+#ifndef __CMPCCXADD__
+#pragma GCC push_options
+#pragma GCC target("cmpccxadd")
+#define __DISABLE_CMPCCXADD__
+#endif /* __CMPCCXADD__ */
+
+typedef enum {
+ _CMPCCX_O, /* Overflow. */
+ _CMPCCX_NO, /* No overflow. */
+ _CMPCCX_B, /* Below. */
+ _CMPCCX_NB, /* Not below. */
+ _CMPCCX_Z, /* Zero. */
+ _CMPCCX_NZ, /* Not zero. */
+ _CMPCCX_BE, /* Below or equal. */
+ _CMPCCX_NBE, /* Neither below nor equal. */
+ _CMPCCX_S, /* Sign. */
+ _CMPCCX_NS, /* No sign. */
+ _CMPCCX_P, /* Parity. */
+ _CMPCCX_NP, /* No parity. */
+ _CMPCCX_L, /* Less. */
+ _CMPCCX_NL, /* Not less. */
+ _CMPCCX_LE, /* Less or equal. */
+ _CMPCCX_NLE, /* Neither less nor equal. */
+} _CMPCCX_ENUM;
+
+#ifdef __OPTIMIZE__
+extern __inline int
+__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
+__cmpccxadd_epi32 (int *__A, int __B, int __C, const _CMPCCX_ENUM __D)
+{
+ return __builtin_ia32_cmpccxadd (__A, __B, __C, __D);
+}
+
+extern __inline long long
+__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
+__cmpccxadd_epi64 (long long *__A, long long __B, long long __C,
+ const _CMPCCX_ENUM __D)
+{
+ return __builtin_ia32_cmpccxadd64 (__A, __B, __C, __D);
+}
+#else
+#define __cmpccxadd_epi32(A,B,C,D) \
+ __builtin_ia32_cmpccxadd ((int *) (A), (int) (B), (int) (C), \
+ (_CMPCCX_ENUM) (D))
+#define __cmpccxadd_epi64(A,B,C,D) \
+ __builtin_ia32_cmpccxadd64 ((long long *) (A), (long long) (B), \
+ (long long) (C), (_CMPCCX_ENUM) (D))
+#endif
+
+#ifdef __DISABLE_CMPCCXADD__
+#undef __DISABLE_CMPCCXADD__
+#pragma GCC pop_options
+#endif /* __DISABLE_CMPCCXADD__ */
+
+#endif
+
+#endif /* _CMPCCXADDINTRIN_H_INCLUDED */
diff --git a/gcc/config/i386/cpuid.h b/gcc/config/i386/cpuid.h
index 18bbc0c..19c0d03 100644
--- a/gcc/config/i386/cpuid.h
+++ b/gcc/config/i386/cpuid.h
@@ -27,6 +27,7 @@
/* %eax */
#define bit_AVXVNNI (1 << 4)
#define bit_AVX512BF16 (1 << 5)
+#define bit_CMPCCXADD (1 << 7)
#define bit_HRESET (1 << 22)
#define bit_AVXIFMA (1 << 23)
diff --git a/gcc/config/i386/i386-builtin-types.def b/gcc/config/i386/i386-builtin-types.def
index abbb50b..2af6614 100644
--- a/gcc/config/i386/i386-builtin-types.def
+++ b/gcc/config/i386/i386-builtin-types.def
@@ -1407,3 +1407,7 @@ DEF_FUNCTION_TYPE (V4SF, PCV8HF)
DEF_FUNCTION_TYPE (V8SF, PCV16HF)
DEF_FUNCTION_TYPE (V4SF, PCV8BF)
DEF_FUNCTION_TYPE (V8SF, PCV16BF)
+
+# CMPccXADD builtins
+DEF_FUNCTION_TYPE (INT, PINT, INT, INT, INT)
+DEF_FUNCTION_TYPE (LONGLONG, PLONGLONG, LONGLONG, LONGLONG, INT)
diff --git a/gcc/config/i386/i386-builtin.def b/gcc/config/i386/i386-builtin.def
index 9345b8c..c272c39 100644
--- a/gcc/config/i386/i386-builtin.def
+++ b/gcc/config/i386/i386-builtin.def
@@ -288,6 +288,10 @@ BDESC (0, OPTION_MASK_ISA2_AVXNECONVERT, CODE_FOR_vcvtneobf162ps_v16bf, "__built
BDESC (0, OPTION_MASK_ISA2_AVXNECONVERT, CODE_FOR_vcvtneoph2ps_v8hf, "__builtin_ia32_vcvtneoph2ps128", IX86_BUILTIN_VCVTNEOPH2PS128, UNKNOWN, (int) V4SF_FTYPE_PCV8HF)
BDESC (0, OPTION_MASK_ISA2_AVXNECONVERT, CODE_FOR_vcvtneoph2ps_v16hf, "__builtin_ia32_vcvtneoph2ps256", IX86_BUILTIN_VCVTNEOPH2PS256, UNKNOWN, (int) V8SF_FTYPE_PCV16HF)
+/* CMPCCXADD */
+BDESC (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_CMPCCXADD, CODE_FOR_cmpccxadd_si, "__builtin_ia32_cmpccxadd", IX86_BUILTIN_CMPCCXADD, UNKNOWN, (int) INT_FTYPE_PINT_INT_INT_INT)
+BDESC (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_CMPCCXADD, CODE_FOR_cmpccxadd_di, "__builtin_ia32_cmpccxadd64", IX86_BUILTIN_CMPCCXADD64, UNKNOWN, (int) LONGLONG_FTYPE_PLONGLONG_LONGLONG_LONGLONG_INT)
+
/* AVX512BW */
BDESC (OPTION_MASK_ISA_AVX512BW, 0, CODE_FOR_avx512bw_loadv32hi_mask, "__builtin_ia32_loaddquhi512_mask", IX86_BUILTIN_LOADDQUHI512_MASK, UNKNOWN, (int) V32HI_FTYPE_PCSHORT_V32HI_USI)
BDESC (OPTION_MASK_ISA_AVX512BW, 0, CODE_FOR_avx512bw_loadv64qi_mask, "__builtin_ia32_loaddquqi512_mask", IX86_BUILTIN_LOADDQUQI512_MASK, UNKNOWN, (int) V64QI_FTYPE_PCCHAR_V64QI_UDI)
diff --git a/gcc/config/i386/i386-c.cc b/gcc/config/i386/i386-c.cc
index fa195e7..818cfd7 100644
--- a/gcc/config/i386/i386-c.cc
+++ b/gcc/config/i386/i386-c.cc
@@ -646,6 +646,8 @@ ix86_target_macros_internal (HOST_WIDE_INT isa_flag,
def_or_undef (parse_in, "__AVXVNNIINT8__");
if (isa_flag2 & OPTION_MASK_ISA2_AVXNECONVERT)
def_or_undef (parse_in, "__AVXNECONVERT__");
+ if (isa_flag2 & OPTION_MASK_ISA2_CMPCCXADD)
+ def_or_undef (parse_in, "__CMPCCXADD__");
if (TARGET_IAMCU)
{
def_or_undef (parse_in, "__iamcu");
diff --git a/gcc/config/i386/i386-expand.cc b/gcc/config/i386/i386-expand.cc
index 7d17bfe..a37fde3 100644
--- a/gcc/config/i386/i386-expand.cc
+++ b/gcc/config/i386/i386-expand.cc
@@ -11860,8 +11860,9 @@ ix86_expand_special_args_builtin (const struct builtin_description *d,
tree arg;
rtx pat, op;
unsigned int i, nargs, arg_adjust, memory;
+ unsigned int constant = 100;
bool aligned_mem = false;
- rtx xops[3];
+ rtx xops[4];
enum insn_code icode = d->icode;
const struct insn_data_d *insn_p = &insn_data[icode];
machine_mode tmode = insn_p->operand[0].mode;
@@ -12152,6 +12153,13 @@ ix86_expand_special_args_builtin (const struct builtin_description *d,
klass = load;
memory = 0;
break;
+ case INT_FTYPE_PINT_INT_INT_INT:
+ case LONGLONG_FTYPE_PLONGLONG_LONGLONG_LONGLONG_INT:
+ nargs = 4;
+ klass = load;
+ memory = 0;
+ constant = 3;
+ break;
default:
gcc_unreachable ();
}
@@ -12217,6 +12225,15 @@ ix86_expand_special_args_builtin (const struct builtin_description *d,
if (MEM_ALIGN (op) < align)
set_mem_align (op, align);
}
+ else if (i == constant)
+ {
+ /* This must be the constant. */
+ if (!insn_p->operand[nargs].predicate(op, SImode))
+ {
+ error ("the fourth argument must be one of enum %qs", "_CMPCCX_ENUM");
+ return const0_rtx;
+ }
+ }
else
{
/* This must be register. */
@@ -12258,6 +12275,9 @@ ix86_expand_special_args_builtin (const struct builtin_description *d,
case 3:
pat = GEN_FCN (icode) (target, xops[0], xops[1], xops[2]);
break;
+ case 4:
+ pat = GEN_FCN (icode) (target, xops[0], xops[1], xops[2], xops[3]);
+ break;
default:
gcc_unreachable ();
}
diff --git a/gcc/config/i386/i386-isa.def b/gcc/config/i386/i386-isa.def
index 4ea3f96..7ffc73b 100644
--- a/gcc/config/i386/i386-isa.def
+++ b/gcc/config/i386/i386-isa.def
@@ -112,3 +112,4 @@ DEF_PTA(AVX512FP16)
DEF_PTA(AVXIFMA)
DEF_PTA(AVXVNNIINT8)
DEF_PTA(AVXNECONVERT)
+DEF_PTA(CMPCCXADD)
diff --git a/gcc/config/i386/i386-options.cc b/gcc/config/i386/i386-options.cc
index ef9c888..38e3fd6 100644
--- a/gcc/config/i386/i386-options.cc
+++ b/gcc/config/i386/i386-options.cc
@@ -230,7 +230,8 @@ static struct ix86_target_opts isa2_opts[] =
{ "-mavx512fp16", OPTION_MASK_ISA2_AVX512FP16 },
{ "-mavxifma", OPTION_MASK_ISA2_AVXIFMA },
{ "-mavxvnniint8", OPTION_MASK_ISA2_AVXVNNIINT8 },
- { "-mavxneconvert", OPTION_MASK_ISA2_AVXNECONVERT }
+ { "-mavxneconvert", OPTION_MASK_ISA2_AVXNECONVERT },
+ { "-mcmpccxadd", OPTION_MASK_ISA2_CMPCCXADD }
};
static struct ix86_target_opts isa_opts[] =
{
@@ -1080,6 +1081,7 @@ ix86_valid_target_attribute_inner_p (tree fndecl, tree args, char *p_strings[],
IX86_ATTR_ISA ("avxifma", OPT_mavxifma),
IX86_ATTR_ISA ("avxvnniint8", OPT_mavxvnniint8),
IX86_ATTR_ISA ("avxneconvert", OPT_mavxneconvert),
+ IX86_ATTR_ISA ("cmpccxadd", OPT_mcmpccxadd),
/* enum options */
IX86_ATTR_ENUM ("fpmath=", OPT_mfpmath_),
diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt
index 6e07b89..c4a3bdc 100644
--- a/gcc/config/i386/i386.opt
+++ b/gcc/config/i386/i386.opt
@@ -1229,3 +1229,8 @@ mavxneconvert
Target Mask(ISA2_AVXNECONVERT) Var(ix86_isa_flags2) Save
Support MMX, SSE, SSE2, SSE3, SSSE3, SSE4.1, SSE4.2, AVX, AVX2, and
AVXNECONVERT build-in functions and code generation.
+
+mcmpccxadd
+Target Mask(ISA2_CMPCCXADD) Var(ix86_isa_flags2) Save
+Support MMX, SSE, SSE2, SSE3, SSSE3, SSE4.1, SSE4.2, AVX, AVX2, and
+CMPCCXADD build-in functions and code generation.
diff --git a/gcc/config/i386/sync.md b/gcc/config/i386/sync.md
index 92634d5..ff168b0 100644
--- a/gcc/config/i386/sync.md
+++ b/gcc/config/i386/sync.md
@@ -37,6 +37,9 @@
UNSPECV_CMPXCHG
UNSPECV_XCHG
UNSPECV_LOCK
+
+ ;; For CMPccXADD support
+ UNSPECV_CMPCCXADD
])
(define_expand "sse2_lfence"
@@ -1061,3 +1064,28 @@
(any_logic:SWI (match_dup 0) (match_dup 1)))]
""
"lock{%;} %K2<logic>{<imodesuffix>}\t{%1, %0|%0, %1}")
+
+;; CMPCCXADD
+
+(define_insn "cmpccxadd_<mode>"
+ [(set (match_operand:SWI48x 0 "register_operand" "=r")
+ (unspec_volatile:SWI48x
+ [(match_operand:SWI48x 1 "memory_operand" "+m")
+ (match_operand:SWI48x 2 "register_operand" "0")
+ (match_operand:SWI48x 3 "register_operand" "r")
+ (match_operand:SI 4 "const_0_to_15_operand" "n")]
+ UNSPECV_CMPCCXADD))
+ (set (match_dup 1)
+ (unspec_volatile:SWI48x [(const_int 0)] UNSPECV_CMPCCXADD))
+ (clobber (reg:CC FLAGS_REG))]
+ "TARGET_CMPCCXADD && TARGET_64BIT"
+{
+ char buf[128];
+ const char *ops = "cmp%sxadd\t{%%3, %%0, %%1|%%1, %%0, %%3}";
+ char const *cc[16] = {"o" ,"no", "b", "nb", "z", "nz", "be", "nbe",
+ "s", "ns", "p", "np", "l", "nl", "le", "nle"};
+
+ snprintf (buf, sizeof (buf), ops, cc[INTVAL (operands[4])]);
+ output_asm_insn (buf, operands);
+ return "";
+})
diff --git a/gcc/config/i386/x86gprintrin.h b/gcc/config/i386/x86gprintrin.h
index e0be01d..a84fbe9 100644
--- a/gcc/config/i386/x86gprintrin.h
+++ b/gcc/config/i386/x86gprintrin.h
@@ -52,6 +52,8 @@
#include <clzerointrin.h>
+#include <cmpccxaddintrin.h>
+
#include <enqcmdintrin.h>
#include <fxsrintrin.h>