public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
* [PATCH] Support Intel USER_MSR
@ 2023-10-10  7:46 Hu, Lin1
  2023-10-10  8:06 ` Hu, Lin1
  0 siblings, 1 reply; 3+ messages in thread
From: Hu, Lin1 @ 2023-10-10  7:46 UTC (permalink / raw)
  To: gcc-patches; +Cc: hongtao.liu, ubizjak

This patch aims to support Intel USER_MSR.

gcc/ChangeLog:

	* common/config/i386/cpuinfo.h (get_available_features):
	Detect USER_MSR.
	* common/config/i386/i386-common.cc (OPTION_MASK_ISA2_USER_MSR_SET): New.
	(OPTION_MASK_ISA2_USER_MSR_UNSET): Ditto.
	(ix86_handle_option): Handle -musermsr.
	* common/config/i386/i386-cpuinfo.h (enum processor_features):
	Add FEATURE_USER_MSR.
	* common/config/i386/i386-isas.h: Add ISA_NAME_TABLE_ENTRY for usermsr.
	* config.gcc: Add usermsrintrin.h
	* config/i386/cpuid.h (bit_USER_MSR): New.
	* config/i386/i386-builtin-types.def:
	Add DEF_FUNCTION_TYPE (VOID, UINT64, UINT64).
	* config/i386/i386-builtins.cc (ix86_init_mmx_sse_builtins):
	Add __builtin_urdmsr and __builtin_uwrmsr.
	* config/i386/i386-builtins.h (ix86_builtins):
	Add IX86_BUILTIN_URDMSR and IX86_BUILTIN_UWRMSR.
	* config/i386/i386-c.cc (ix86_target_macros_internal):
	Define __USER_MSR__.
	* config/i386/i386-expand.cc (ix86_expand_builtin):
	Handle new builtins.
	* config/i386/i386-isa.def (USER_MSR): Add DEF_PTA(USER_MSR).
	* config/i386/i386-options.cc (ix86_valid_target_attribute_inner_p):
	Handle usermsr.
	* config/i386/i386.md (urdmsr): New define_insn.
	(uwrmsr): Ditto.
	* config/i386/i386.opt: Add option -musermsr.
	* config/i386/x86gprintrin.h: Include usermsrintrin.h
	* doc/extend.texi: Document usermsr.
	* doc/invoke.texi: Document -musermsr.
	* doc/sourcebuild.texi: Document target usermsr.
	* config/i386/usermsrintrin.h: New file.

gcc/testsuite/ChangeLog:

	* gcc.target/i386/funcspec-56.inc: Add new target attribute.
	* gcc.target/i386/x86gprintrin-1.c: Add -musermsr for 64bit target.
	* gcc.target/i386/x86gprintrin-2.c: Ditto.
	* gcc.target/i386/x86gprintrin-3.c: Ditto.
	* gcc.target/i386/x86gprintrin-4.c: Add musermsr for 64bit target.
	* gcc.target/i386/x86gprintrin-5.c: Ditto
	* gcc.target/i386/usermsr-1.c: New test.
	* gcc.target/i386/usermsr-2.c: Ditto.
---
 gcc/common/config/i386/cpuinfo.h              |  2 +
 gcc/common/config/i386/i386-common.cc         | 15 +++++
 gcc/common/config/i386/i386-cpuinfo.h         |  1 +
 gcc/common/config/i386/i386-isas.h            |  1 +
 gcc/config.gcc                                |  3 +-
 gcc/config/i386/cpuid.h                       |  1 +
 gcc/config/i386/i386-builtin-types.def        |  3 +
 gcc/config/i386/i386-builtins.cc              |  8 +++
 gcc/config/i386/i386-builtins.h               |  2 +
 gcc/config/i386/i386-c.cc                     |  2 +
 gcc/config/i386/i386-expand.cc                | 35 +++++++++++
 gcc/config/i386/i386-isa.def                  |  1 +
 gcc/config/i386/i386-options.cc               |  4 +-
 gcc/config/i386/i386.md                       | 24 ++++++++
 gcc/config/i386/i386.opt                      |  4 ++
 gcc/config/i386/usermsrintrin.h               | 60 +++++++++++++++++++
 gcc/config/i386/x86gprintrin.h                |  2 +
 gcc/doc/extend.texi                           |  5 ++
 gcc/doc/invoke.texi                           |  6 +-
 gcc/doc/sourcebuild.texi                      |  3 +
 gcc/testsuite/gcc.target/i386/funcspec-56.inc |  2 +
 gcc/testsuite/gcc.target/i386/user_msr-1.c    | 20 +++++++
 gcc/testsuite/gcc.target/i386/user_msr-2.c    | 16 +++++
 .../gcc.target/i386/x86gprintrin-1.c          |  2 +-
 .../gcc.target/i386/x86gprintrin-2.c          |  6 +-
 .../gcc.target/i386/x86gprintrin-3.c          | 28 ++++++++-
 .../gcc.target/i386/x86gprintrin-4.c          | 32 +++++++++-
 .../gcc.target/i386/x86gprintrin-5.c          |  6 +-
 28 files changed, 286 insertions(+), 8 deletions(-)
 create mode 100644 gcc/config/i386/usermsrintrin.h
 create mode 100644 gcc/testsuite/gcc.target/i386/user_msr-1.c
 create mode 100644 gcc/testsuite/gcc.target/i386/user_msr-2.c

diff --git a/gcc/common/config/i386/cpuinfo.h b/gcc/common/config/i386/cpuinfo.h
index 141d3743316..0f86b44730b 100644
--- a/gcc/common/config/i386/cpuinfo.h
+++ b/gcc/common/config/i386/cpuinfo.h
@@ -838,6 +838,8 @@ get_available_features (struct __processor_model *cpu_model,
 	set_feature (FEATURE_IBT);
       if (edx & bit_UINTR)
 	set_feature (FEATURE_UINTR);
+      if (edx & bit_USER_MSR)
+	set_feature (FEATURE_USER_MSR);
       if (amx_usable)
 	{
 	  if (edx & bit_AMX_TILE)
diff --git a/gcc/common/config/i386/i386-common.cc b/gcc/common/config/i386/i386-common.cc
index 684b0451bb3..13e423deceb 100644
--- a/gcc/common/config/i386/i386-common.cc
+++ b/gcc/common/config/i386/i386-common.cc
@@ -125,6 +125,7 @@ along with GCC; see the file COPYING3.  If not see
 #define OPTION_MASK_ISA2_SM4_SET OPTION_MASK_ISA2_SM4
 #define OPTION_MASK_ISA2_APX_F_SET OPTION_MASK_ISA2_APX_F
 #define OPTION_MASK_ISA2_EVEX512_SET OPTION_MASK_ISA2_EVEX512
+#define OPTION_MASK_ISA2_USER_MSR_SET OPTION_MASK_ISA2_USER_MSR
 
 /* SSE4 includes both SSE4.1 and SSE4.2. -msse4 should be the same
    as -msse4.2.  */
@@ -313,6 +314,7 @@ along with GCC; see the file COPYING3.  If not see
 #define OPTION_MASK_ISA2_SM4_UNSET OPTION_MASK_ISA2_SM4
 #define OPTION_MASK_ISA2_APX_F_UNSET OPTION_MASK_ISA2_APX_F
 #define OPTION_MASK_ISA2_EVEX512_UNSET OPTION_MASK_ISA2_EVEX512
+#define OPTION_MASK_ISA2_USER_MSR_UNSET OPTION_MASK_ISA2_USER_MSR
 
 /* SSE4 includes both SSE4.1 and SSE4.2.  -mno-sse4 should the same
    as -mno-sse4.1. */
@@ -1373,6 +1375,19 @@ ix86_handle_option (struct gcc_options *opts,
 	}
       return true;
 
+    case OPT_musermsr:
+      if (value)
+	{
+	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA2_USER_MSR_SET;
+	  opts->x_ix86_isa_flags2_explicit |= OPTION_MASK_ISA2_USER_MSR_SET;
+	}
+      else
+	{
+	  opts->x_ix86_isa_flags2 &= ~OPTION_MASK_ISA2_USER_MSR_UNSET;
+	  opts->x_ix86_isa_flags2_explicit |= OPTION_MASK_ISA2_USER_MSR_UNSET;
+	}
+      return true;
+
     case OPT_mfma:
       if (value)
 	{
diff --git a/gcc/common/config/i386/i386-cpuinfo.h b/gcc/common/config/i386/i386-cpuinfo.h
index 8bf592191ab..47e9dcfb8f7 100644
--- a/gcc/common/config/i386/i386-cpuinfo.h
+++ b/gcc/common/config/i386/i386-cpuinfo.h
@@ -262,6 +262,7 @@ enum processor_features
   FEATURE_SHA512,
   FEATURE_SM4,
   FEATURE_APX_F,
+  FEATURE_USER_MSR,
   CPU_FEATURE_MAX
 };
 
diff --git a/gcc/common/config/i386/i386-isas.h b/gcc/common/config/i386/i386-isas.h
index 47e0cbd6f5b..6875924994d 100644
--- a/gcc/common/config/i386/i386-isas.h
+++ b/gcc/common/config/i386/i386-isas.h
@@ -192,4 +192,5 @@ ISA_NAMES_TABLE_START
   ISA_NAMES_TABLE_ENTRY("sha512", FEATURE_SHA512, P_NONE, "-msha512")
   ISA_NAMES_TABLE_ENTRY("sm4", FEATURE_SM4, P_NONE, "-msm4")
   ISA_NAMES_TABLE_ENTRY("apxf", FEATURE_APX_F, P_NONE, "-mapxf")
+  ISA_NAMES_TABLE_ENTRY("usermsr", FEATURE_USER_MSR, P_NONE, "-musermsr")
 ISA_NAMES_TABLE_END
diff --git a/gcc/config.gcc b/gcc/config.gcc
index cc37a9c768d..284f3d507ba 100644
--- a/gcc/config.gcc
+++ b/gcc/config.gcc
@@ -448,7 +448,8 @@ i[34567]86-*-* | x86_64-*-*)
 		       avxvnniint8intrin.h avxneconvertintrin.h
 		       cmpccxaddintrin.h amxfp16intrin.h prfchiintrin.h
 		       raointintrin.h amxcomplexintrin.h avxvnniint16intrin.h
-		       sm3intrin.h sha512intrin.h sm4intrin.h"
+		       sm3intrin.h sha512intrin.h sm4intrin.h
+		       usermsrintrin.h"
 	;;
 ia64-*-*)
 	extra_headers=ia64intrin.h
diff --git a/gcc/config/i386/cpuid.h b/gcc/config/i386/cpuid.h
index f3d3a2a1c22..75ef2718204 100644
--- a/gcc/config/i386/cpuid.h
+++ b/gcc/config/i386/cpuid.h
@@ -149,6 +149,7 @@
 #define bit_AVXNECONVERT	(1 << 5)
 #define bit_AVXVNNIINT16	(1 << 10)
 #define bit_PREFETCHI	(1 << 14)
+#define bit_USER_MSR	(1 << 15)
 #define bit_APX_F	(1 << 21)
 
 /* Extended State Enumeration Sub-leaf (%eax == 0xd, %ecx == 1) */
diff --git a/gcc/config/i386/i386-builtin-types.def b/gcc/config/i386/i386-builtin-types.def
index e9463120eea..183029f2c75 100644
--- a/gcc/config/i386/i386-builtin-types.def
+++ b/gcc/config/i386/i386-builtin-types.def
@@ -1422,3 +1422,6 @@ DEF_FUNCTION_TYPE (V4SI, V4SI, V4SI, V4SI, INT)
 
 # SHA512 builtins
 DEF_FUNCTION_TYPE (V4DI, V4DI, V4DI, V2DI)
+
+# USER_MSR builtins
+DEF_FUNCTION_TYPE (VOID, UINT64, UINT64)
diff --git a/gcc/config/i386/i386-builtins.cc b/gcc/config/i386/i386-builtins.cc
index 70538fbe17b..42fc3751676 100644
--- a/gcc/config/i386/i386-builtins.cc
+++ b/gcc/config/i386/i386-builtins.cc
@@ -1262,6 +1262,14 @@ ix86_init_mmx_sse_builtins (void)
 	       "__builtin_ia32_testui",
 	       UINT8_FTYPE_VOID, IX86_BUILTIN_TESTUI);
 
+  /* USER_MSR.  */
+  def_builtin (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_USER_MSR,
+	       "__builtin_ia32_urdmsr", UINT64_FTYPE_UINT64,
+	       IX86_BUILTIN_URDMSR);
+  def_builtin (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_USER_MSR,
+	       "__builtin_ia32_uwrmsr", VOID_FTYPE_UINT64_UINT64,
+	       IX86_BUILTIN_UWRMSR);
+
   /* CLDEMOTE.  */
   def_builtin (0, OPTION_MASK_ISA2_CLDEMOTE, "__builtin_ia32_cldemote",
 	       VOID_FTYPE_PCVOID, IX86_BUILTIN_CLDEMOTE);
diff --git a/gcc/config/i386/i386-builtins.h b/gcc/config/i386/i386-builtins.h
index c632482087c..40785b0aa34 100644
--- a/gcc/config/i386/i386-builtins.h
+++ b/gcc/config/i386/i386-builtins.h
@@ -39,6 +39,8 @@ enum ix86_builtins
   IX86_BUILTIN_MWAIT,
   IX86_BUILTIN_UMONITOR,
   IX86_BUILTIN_UMWAIT,
+  IX86_BUILTIN_URDMSR,
+  IX86_BUILTIN_UWRMSR,
   IX86_BUILTIN_TPAUSE,
   IX86_BUILTIN_TESTUI,
   IX86_BUILTIN_CLZERO,
diff --git a/gcc/config/i386/i386-c.cc b/gcc/config/i386/i386-c.cc
index 9c44bd7fb63..042ad8b9d9c 100644
--- a/gcc/config/i386/i386-c.cc
+++ b/gcc/config/i386/i386-c.cc
@@ -712,6 +712,8 @@ ix86_target_macros_internal (HOST_WIDE_INT isa_flag,
     def_or_undef (parse_in, "__SM4__");
   if (isa_flag2 & OPTION_MASK_ISA2_EVEX512)
     def_or_undef (parse_in, "__EVEX512__");
+  if (isa_flag2 & OPTION_MASK_ISA2_USER_MSR)
+    def_or_undef (parse_in, "__USER_MSR__");
   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 d5083494798..4ef85570d44 100644
--- a/gcc/config/i386/i386-expand.cc
+++ b/gcc/config/i386/i386-expand.cc
@@ -13471,6 +13471,41 @@ ix86_expand_builtin (tree exp, rtx target, rtx subtarget,
 	return 0;
       }
 
+    case IX86_BUILTIN_URDMSR:
+    case IX86_BUILTIN_UWRMSR:
+      {
+	arg0 = CALL_EXPR_ARG (exp, 0);
+	op0 = expand_normal (arg0);
+
+	if (CONST_INT_P (op0))
+	  {
+	    unsigned HOST_WIDE_INT val = UINTVAL (op0);
+	    if (val > 0xffffffff)
+	      op0 = force_reg (DImode, op0);
+	  }
+	else
+	  op0 = force_reg (DImode, op0);
+
+	if (fcode == IX86_BUILTIN_UWRMSR)
+	  {
+	    arg1 = CALL_EXPR_ARG (exp, 1);
+	    op1 = expand_normal (arg1);
+	    op1 = force_reg (DImode, op1);
+	    icode = CODE_FOR_uwrmsr;
+	    target = 0;
+	  }
+	else
+	  {
+	    if (target == 0)
+	      target = gen_reg_rtx (DImode);
+	    icode = CODE_FOR_urdmsr;
+	    op1 = op0;
+	    op0 = target;
+	  }
+	emit_insn (GEN_FCN (icode) (op0, op1));
+	return target;
+      }
+
     case IX86_BUILTIN_VEC_INIT_V2SI:
     case IX86_BUILTIN_VEC_INIT_V4HI:
     case IX86_BUILTIN_VEC_INIT_V8QI:
diff --git a/gcc/config/i386/i386-isa.def b/gcc/config/i386/i386-isa.def
index c581f343339..991df5e2ef0 100644
--- a/gcc/config/i386/i386-isa.def
+++ b/gcc/config/i386/i386-isa.def
@@ -122,3 +122,4 @@ DEF_PTA(SM3)
 DEF_PTA(SHA512)
 DEF_PTA(SM4)
 DEF_PTA(APX_F)
+DEF_PTA(USER_MSR)
diff --git a/gcc/config/i386/i386-options.cc b/gcc/config/i386/i386-options.cc
index 06af373ca57..9506c470147 100644
--- a/gcc/config/i386/i386-options.cc
+++ b/gcc/config/i386/i386-options.cc
@@ -251,7 +251,8 @@ static struct ix86_target_opts isa2_opts[] =
   { "-msm3",		OPTION_MASK_ISA2_SM3 },
   { "-msha512",		OPTION_MASK_ISA2_SHA512 },
   { "-msm4",            OPTION_MASK_ISA2_SM4 },
-  { "-mevex512",        OPTION_MASK_ISA2_EVEX512 }
+  { "-mevex512",        OPTION_MASK_ISA2_EVEX512 },
+  { "-musermsr",	OPTION_MASK_ISA2_USER_MSR }
 };
 static struct ix86_target_opts isa_opts[] =
 {
@@ -1114,6 +1115,7 @@ ix86_valid_target_attribute_inner_p (tree fndecl, tree args, char *p_strings[],
     IX86_ATTR_ISA ("sm4", OPT_msm4),
     IX86_ATTR_ISA ("apxf", OPT_mapxf),
     IX86_ATTR_ISA ("evex512", OPT_mevex512),
+    IX86_ATTR_ISA ("usermsr", OPT_musermsr),
 
     /* enum options */
     IX86_ATTR_ENUM ("fpmath=",	OPT_mfpmath_),
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md
index f390fb5692b..b8f60d1df4b 100644
--- a/gcc/config/i386/i386.md
+++ b/gcc/config/i386/i386.md
@@ -340,6 +340,10 @@
 
   ;; For PREFETCHI support
   UNSPECV_PREFETCHI
+
+  ;; For USER_MSR support
+  UNSPECV_URDMSR
+  UNSPECV_UWRMSR
 ])
 
 ;; Constants to represent rounding modes in the ROUND instruction
@@ -26601,6 +26605,26 @@
   DONE;
 })
 
+(define_insn "urdmsr"
+  [(set (match_operand:DI 0 "register_operand" "=r")
+    (unspec_volatile:DI
+      [(match_operand:DI 1 "x86_64_szext_nonmemory_operand" "reZ")]
+      UNSPECV_URDMSR))]
+  "TARGET_USER_MSR && TARGET_64BIT"
+  "urdmsr\t{%1, %0|%0, %1}"
+  [(set_attr "prefix" "vex")
+   (set_attr "type" "other")])
+
+(define_insn "uwrmsr"
+  [(unspec_volatile
+    [(match_operand:DI 0 "x86_64_szext_nonmemory_operand" "reZ")
+      (match_operand:DI 1 "register_operand" "r")]
+      UNSPECV_UWRMSR)]
+  "TARGET_USER_MSR && TARGET_64BIT"
+  "uwrmsr\t{%1, %0|%0, %1}"
+  [(set_attr "prefix" "vex")
+   (set_attr "type" "other")])
+
 (include "mmx.md")
 (include "sse.md")
 (include "sync.md")
diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt
index 05ba7f37244..b8382c48099 100644
--- a/gcc/config/i386/i386.opt
+++ b/gcc/config/i386/i386.opt
@@ -1344,3 +1344,7 @@ hook reg or mem constraint in inline asm to GPR16.
 mevex512
 Target Mask(ISA2_EVEX512) Var(ix86_isa_flags2) Save
 Support 512 bit vector built-in functions and code generation.
+
+musermsr
+Target Mask(ISA2_USER_MSR) Var(ix86_isa_flags2) Save
+Support USER_MSR built-in functions and code generation.
diff --git a/gcc/config/i386/usermsrintrin.h b/gcc/config/i386/usermsrintrin.h
new file mode 100644
index 00000000000..9e1dbdca112
--- /dev/null
+++ b/gcc/config/i386/usermsrintrin.h
@@ -0,0 +1,60 @@
+/* Copyright (C) 2022 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 _X86GPRINTRIN_H_INCLUDED
+#error "Never use <usermsrintrin.h> directly; include <x86gprintrin.h> instead."
+#endif
+
+#ifndef _USER_MSRINTRIN_H_INCLUDED
+#define _USER_MSRINTRIN_H_INCLUDED
+
+#ifdef __x86_64__
+
+#ifndef __USER_MSR__
+#pragma GCC push_options
+#pragma GCC target("usermsr")
+#define __DISABLE_USER_MSR__
+#endif /* __USER_MSR__ */
+
+extern __inline unsigned long long
+__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
+_urdmsr (unsigned long long __A)
+{
+  return (unsigned long long) __builtin_ia32_urdmsr (__A);
+}
+
+extern __inline void
+__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
+_uwrmsr (unsigned long long __A, unsigned long long __B)
+{
+  __builtin_ia32_uwrmsr (__A, __B);
+}
+
+#ifdef __DISABLE_USER_MSR__
+#undef __DISABLE_USER_MSR__
+#pragma GCC pop_options
+#endif /* __DISABLE_USER_MSR__ */
+
+#endif /* __x86_64__ */
+
+#endif /* _USER_MSRINTRIN_H_INCLUDED */
diff --git a/gcc/config/i386/x86gprintrin.h b/gcc/config/i386/x86gprintrin.h
index f41be3ffcde..11a8a963020 100644
--- a/gcc/config/i386/x86gprintrin.h
+++ b/gcc/config/i386/x86gprintrin.h
@@ -108,6 +108,8 @@
 
 #include <hresetintrin.h>
 
+#include <usermsrintrin.h>
+
 extern __inline void
 __attribute__((__gnu_inline__, __always_inline__, __artificial__))
 _wbinvd (void)
diff --git a/gcc/doc/extend.texi b/gcc/doc/extend.texi
index b82497f00e4..991c2db8eba 100644
--- a/gcc/doc/extend.texi
+++ b/gcc/doc/extend.texi
@@ -7210,6 +7210,11 @@ Enable/disable the generation of the SHA512 instructions.
 @itemx no-sm4
 Enable/disable the generation of the SM4 instructions.
 
+@cindex @code{target("umsr")} function attribute, x86
+@item umsr
+@itemx no-umsr
+Enable/disable the generation of the UMSR instructions.
+
 @cindex @code{target("cld")} function attribute, x86
 @item cld
 @itemx no-cld
diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi
index 7c5f81d9783..3edf41257f1 100644
--- a/gcc/doc/invoke.texi
+++ b/gcc/doc/invoke.texi
@@ -1444,6 +1444,7 @@ See RS/6000 and PowerPC Options.
 -mamx-tile  -mamx-int8  -mamx-bf16 -muintr -mhreset -mavxvnni
 -mavx512fp16 -mavxifma -mavxvnniint8 -mavxneconvert -mcmpccxadd -mamx-fp16
 -mprefetchi -mraoint -mamx-complex -mavxvnniint16 -msm3 -msha512 -msm4 -mapxf
+-mumsr
 -mcldemote  -mms-bitfields  -mno-align-stringops  -minline-all-stringops
 -minline-stringops-dynamically  -mstringop-strategy=@var{alg}
 -mkl -mwidekl
@@ -33830,6 +33831,9 @@ preferred alignment to @option{-mpreferred-stack-boundary=2}.
 @need 200
 @opindex mapxf
 @itemx -mapxf
+@need 200
+@opindex mumsr
+@itemx -mumsr
 These switches enable the use of instructions in the MMX, SSE,
 AVX512ER, AVX512CD, AVX512VL, AVX512BW, AVX512DQ, AVX512IFMA, AVX512VBMI, SHA,
 AES, PCLMUL, CLFLUSHOPT, CLWB, FSGSBASE, PTWRITE, RDRND, F16C, FMA, PCONFIG,
@@ -33840,7 +33844,7 @@ GFNI, VAES, WAITPKG, VPCLMULQDQ, AVX512BITALG, MOVDIRI, MOVDIR64B, AVX512BF16,
 ENQCMD, AVX512VPOPCNTDQ, AVX5124FMAPS, AVX512VNNI, AVX5124VNNIW, SERIALIZE,
 UINTR, HRESET, AMXTILE, AMXINT8, AMXBF16, KL, WIDEKL, AVXVNNI, AVX512-FP16,
 AVXIFMA, AVXVNNIINT8, AVXNECONVERT, CMPCCXADD, AMX-FP16, PREFETCHI, RAOINT,
-AMX-COMPLEX, AVXVNNIINT16, SM3, SHA512, SM4, APX_F or CLDEMOTE extended
+AMX-COMPLEX, AVXVNNIINT16, SM3, SHA512, SM4, APX_F, UMSR or CLDEMOTE extended
 instruction sets. Each has a corresponding @option{-mno-} option to disable
 use of these instructions.
 
diff --git a/gcc/doc/sourcebuild.texi b/gcc/doc/sourcebuild.texi
index 8bf701461ec..a859bcc53cc 100644
--- a/gcc/doc/sourcebuild.texi
+++ b/gcc/doc/sourcebuild.texi
@@ -2624,6 +2624,9 @@ Test environment appears to run executables on a simulator that
 accepts only @code{EM_SPARC} executables and chokes on @code{EM_SPARC32PLUS}
 or @code{EM_SPARCV9} executables.
 
+@item umsr
+Target supports the execution of @code{umsr} instructions.
+
 @item vect_cmdline_needed
 Target requires a command line argument to enable a SIMD instruction set.
 
diff --git a/gcc/testsuite/gcc.target/i386/funcspec-56.inc b/gcc/testsuite/gcc.target/i386/funcspec-56.inc
index ca558b3e828..e0470a60483 100644
--- a/gcc/testsuite/gcc.target/i386/funcspec-56.inc
+++ b/gcc/testsuite/gcc.target/i386/funcspec-56.inc
@@ -92,6 +92,7 @@ extern void test_avxvnniint16 (void)		__attribute__((__target__("avxvnniint16"))
 extern void test_sm3 (void)			__attribute__((__target__("sm3")));
 extern void test_sha512 (void)			__attribute__((__target__("sha512")));
 extern void test_sm4 (void)                     __attribute__((__target__("sm4")));
+extern void test_user_msr (void)		__attribute__((__target__("usermsr")));
 
 extern void test_no_sgx (void)			__attribute__((__target__("no-sgx")));
 extern void test_no_avx5124fmaps(void)		__attribute__((__target__("no-avx5124fmaps")));
@@ -185,6 +186,7 @@ extern void test_no_avxvnniint16 (void)		__attribute__((__target__("no-avxvnniin
 extern void test_no_sm3 (void)			__attribute__((__target__("no-sm3")));
 extern void test_no_sha512 (void)		__attribute__((__target__("no-sha512")));
 extern void test_no_sm4 (void)                  __attribute__((__target__("no-sm4")));
+extern void test_no_user_msr (void)		__attribute__((__target__("no-usermsr")));
 
 extern void test_arch_nocona (void)		__attribute__((__target__("arch=nocona")));
 extern void test_arch_core2 (void)		__attribute__((__target__("arch=core2")));
diff --git a/gcc/testsuite/gcc.target/i386/user_msr-1.c b/gcc/testsuite/gcc.target/i386/user_msr-1.c
new file mode 100644
index 00000000000..447852306df
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/user_msr-1.c
@@ -0,0 +1,20 @@
+/* { dg-do compile { target { ! ia32  }  }  } */
+/* { dg-options "-musermsr -O2"  } */
+/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\%r\[a-z\]x, \\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\\$121" 1  }  } */
+/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x, \\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x, \\\$121" 1  }  } */
+
+#include <x86gprintrin.h>
+
+volatile unsigned long long x;
+volatile unsigned long long y;
+
+void extern
+user_msr_test (void)
+{
+  x = _urdmsr(y);
+  x = _urdmsr(121);
+  _uwrmsr(y, x);
+  _uwrmsr(121, x);
+}
diff --git a/gcc/testsuite/gcc.target/i386/user_msr-2.c b/gcc/testsuite/gcc.target/i386/user_msr-2.c
new file mode 100644
index 00000000000..ab0e76f9088
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/user_msr-2.c
@@ -0,0 +1,16 @@
+/* { dg-do compile { target { ! ia32 } } } */
+/* { dg-options "-O2 -musermsr" } */
+/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\%r\[a-z\]x, \\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x, \\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "movabsq\[ \\t\]\\\$20018842566655, \\%r\[a-z\]x" 1  }  } */
+
+#include <x86gprintrin.h>
+
+volatile unsigned long long x;
+
+void extern
+user_msr_test (void)
+{
+  x = _urdmsr(0x1234ffffffffULL);
+  _uwrmsr(0x1234ffffffffULL, x);
+}
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
index 68da4db4f3c..b9479beef7c 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
@@ -1,7 +1,7 @@
 /* Test that <x86gprintrin.h> is usable with -O -std=c89 -pedantic-errors.  */
 /* { dg-do compile } */
 /* { dg-options "-O -std=c89 -pedantic-errors -march=x86-64 -madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
-/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
+/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
 
 #include <x86gprintrin.h>
 
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
index 737c2a26f98..ee167ebab90 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
@@ -1,7 +1,7 @@
 /* { dg-do compile } */
 /* { dg-options "-O2 -Werror-implicit-function-declaration -march=x86-64 -madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
 /* { dg-add-options bind_pic_locally } */
-/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
+/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
 
 /* Test that the intrinsics in <x86gprintrin.h> compile with optimization.
    All of them are defined as inline functions that reference the proper
@@ -32,4 +32,8 @@
 #define __builtin_ia32_cmpccxadd(A, B, C, D) __builtin_ia32_cmpccxadd(A, B, C, 1)
 #define __builtin_ia32_cmpccxadd64(A, B, C, D) __builtin_ia32_cmpccxadd64(A, B, C, 1)
 
+/* usermsrintrin.h */
+#define __builtin_ia32_urdmsr(A) __builtin_ia32_urdmsr(1)
+#define __builtin_ia32_uwrmsr(A, B) __builtin_ia32_uwrmsr(1, B)
+
 #include <x86gprintrin.h>
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
index 52690b1dfb5..a87039149f9 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
@@ -1,7 +1,7 @@
 /* { dg-do compile } */
 /* { dg-options "-O0 -Werror-implicit-function-declaration -march=x86-64 -madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
 /* { dg-add-options bind_pic_locally } */
-/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
+/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
 
 /* Test that the intrinsics in <x86gprintrin.h> compile without optimization.
    All of them are defined as inline functions that reference the proper
@@ -14,3 +14,29 @@
 #define __inline
 
 #include <x86gprintrin.h>
+
+#define _CONCAT(x,y) x ## y
+
+#define test_0(func, type, imm)		  \
+  type _CONCAT(_0,func) (int const I)	  \
+	    { return func (imm);  }
+
+#define test_1(func, type, op1_type)   \
+  type _CONCAT(_1,func) (op1_type A)    \
+	{ return func (A); }
+
+#define test_1r(func, type, op1_type, imm)	    \
+  type _CONCAT(_1r,func) (op1_type A, int const I)    \
+	{ return func (imm, A); }
+
+#define test_2(func, type, op1_type,  op2_type)	    \
+    type _CONCAT(_2,func) (op1_type A, op2_type B)    \
+      { return func (A, B);  }
+
+/* usermsrintrin.h */
+#ifdef __x86_64__
+test_0 (_urdmsr, unsigned long long, 1)
+test_1 (_urdmsr, unsigned long long, unsigned long long)
+test_1r (_uwrmsr, void, unsigned long long, 1)
+test_2 (_uwrmsr, void, unsigned long long, unsigned long long)
+#endif
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
index 94cfc583dc9..c3c79473020 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
@@ -13,9 +13,27 @@
 #define extern
 #define __inline
 
+#define _CONCAT(x,y) x ## y
+
+#define test_0(func, type, imm)		  \
+  type _CONCAT(_0,func) (int const I)	  \
+	    { return func (imm);  }
+
+#define test_1(func, type, op1_type)   \
+  type _CONCAT(_1,func) (op1_type A)    \
+	{ return func (A); }
+
+#define test_1r(func, type, op1_type, imm)	    \
+  type _CONCAT(_1r,func) (op1_type A, int const I)    \
+	{ return func (imm, A); }
+
+#define test_2(func, type, op1_type,  op2_type)	    \
+    type _CONCAT(_2,func) (op1_type A, op2_type B)    \
+      { return func (A, B);  }
+
 #ifndef DIFFERENT_PRAGMAS
 #ifdef __x86_64__
-#pragma GCC target ("adx,bmi,bmi2,cmpccxadd,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,prefetchi,raoint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,uintr,xsaveopt")
+#pragma GCC target ("adx,bmi,bmi2,cmpccxadd,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,prefetchi,raoint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,uintr,usermsr,xsaveopt")
 #else
 #pragma GCC target ("adx,bmi,bmi2,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,raoint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,xsaveopt")
 #endif
@@ -29,6 +47,18 @@
 
 /* x86intrin.h (LWP/BMI/BMI2/TBM/LZCNT). */
 #ifdef DIFFERENT_PRAGMAS
+#ifdef __x86_64__
+#pragma GCC target ("lwp,bmi,bmi2,tbm,lzcnt,usermsr")
+#else
 #pragma GCC target ("lwp,bmi,bmi2,tbm,lzcnt")
 #endif
+#endif
 #include <x86gprintrin.h>
+
+/* usermsrintrin.h */
+#ifdef __x86_64__
+test_0 (_urdmsr, unsigned long long, 1)
+test_1 (_urdmsr, unsigned long long, unsigned long long)
+test_1r (_uwrmsr, void, unsigned long long, 1)
+test_2 (_uwrmsr, void, unsigned long long, unsigned long long)
+#endif
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
index 95f3e0a003c..ef126ea76c2 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
@@ -31,8 +31,12 @@
 #define __builtin_ia32_cmpccxadd(A, B, C, D) __builtin_ia32_cmpccxadd(A, B, C, 1)
 #define __builtin_ia32_cmpccxadd64(A, B, C, D) __builtin_ia32_cmpccxadd64(A, B, C, 1)
 
+/* usermsrintrin.h */
+#define __builtin_ia32_urdmsr(A) __builtin_ia32_urdmsr(1)
+#define __builtin_ia32_uwrmsr(A, B) __builtin_ia32_uwrmsr(1, B)
+
 #ifdef __x86_64__
-#pragma GCC target ("adx,bmi,bmi2,clflushopt,clwb,clzero,cmpccxadd,enqcmd,fsgsbase,fxsr,hreset,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,prefetchi,raoint,rdpid,rdrnd,rdseed,tbm,rtm,serialize,sgx,tsxldtrk,uintr,xsavec,xsaveopt,xsaves,wbnoinvd")
+#pragma GCC target ("adx,bmi,bmi2,clflushopt,clwb,clzero,cmpccxadd,enqcmd,fsgsbase,fxsr,hreset,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,prefetchi,raoint,rdpid,rdrnd,rdseed,tbm,rtm,serialize,sgx,tsxldtrk,uintr,usermsr,xsavec,xsaveopt,xsaves,wbnoinvd")
 #else
 #pragma GCC target ("adx,bmi,bmi2,clflushopt,clwb,clzero,enqcmd,fsgsbase,fxsr,hreset,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,raoint,rdpid,rdrnd,rdseed,tbm,rtm,serialize,sgx,tsxldtrk,xsavec,xsaveopt,xsaves,wbnoinvd")
 #endif
-- 
2.31.1


^ permalink raw reply	[flat|nested] 3+ messages in thread

* RE: [PATCH] Support Intel USER_MSR
  2023-10-10  7:46 [PATCH] Support Intel USER_MSR Hu, Lin1
@ 2023-10-10  8:06 ` Hu, Lin1
  2023-10-12  1:47   ` Liu, Hongtao
  0 siblings, 1 reply; 3+ messages in thread
From: Hu, Lin1 @ 2023-10-10  8:06 UTC (permalink / raw)
  To: Hu, Lin1, gcc-patches; +Cc: Liu, Hongtao, ubizjak

There are some typos In /gcc/doc/extend.texi and /gcc/doc/invoke.texi. They should be USER_MSR, not UMSR. I have modified them in my branch.

-----Original Message-----
From: Hu, Lin1 <lin1.hu@intel.com> 
Sent: Tuesday, October 10, 2023 3:47 PM
To: gcc-patches@gcc.gnu.org
Cc: Liu, Hongtao <hongtao.liu@intel.com>; ubizjak@gmail.com
Subject: [PATCH] Support Intel USER_MSR

This patch aims to support Intel USER_MSR.

gcc/ChangeLog:

	* common/config/i386/cpuinfo.h (get_available_features):
	Detect USER_MSR.
	* common/config/i386/i386-common.cc (OPTION_MASK_ISA2_USER_MSR_SET): New.
	(OPTION_MASK_ISA2_USER_MSR_UNSET): Ditto.
	(ix86_handle_option): Handle -musermsr.
	* common/config/i386/i386-cpuinfo.h (enum processor_features):
	Add FEATURE_USER_MSR.
	* common/config/i386/i386-isas.h: Add ISA_NAME_TABLE_ENTRY for usermsr.
	* config.gcc: Add usermsrintrin.h
	* config/i386/cpuid.h (bit_USER_MSR): New.
	* config/i386/i386-builtin-types.def:
	Add DEF_FUNCTION_TYPE (VOID, UINT64, UINT64).
	* config/i386/i386-builtins.cc (ix86_init_mmx_sse_builtins):
	Add __builtin_urdmsr and __builtin_uwrmsr.
	* config/i386/i386-builtins.h (ix86_builtins):
	Add IX86_BUILTIN_URDMSR and IX86_BUILTIN_UWRMSR.
	* config/i386/i386-c.cc (ix86_target_macros_internal):
	Define __USER_MSR__.
	* config/i386/i386-expand.cc (ix86_expand_builtin):
	Handle new builtins.
	* config/i386/i386-isa.def (USER_MSR): Add DEF_PTA(USER_MSR).
	* config/i386/i386-options.cc (ix86_valid_target_attribute_inner_p):
	Handle usermsr.
	* config/i386/i386.md (urdmsr): New define_insn.
	(uwrmsr): Ditto.
	* config/i386/i386.opt: Add option -musermsr.
	* config/i386/x86gprintrin.h: Include usermsrintrin.h
	* doc/extend.texi: Document usermsr.
	* doc/invoke.texi: Document -musermsr.
	* doc/sourcebuild.texi: Document target usermsr.
	* config/i386/usermsrintrin.h: New file.

gcc/testsuite/ChangeLog:

	* gcc.target/i386/funcspec-56.inc: Add new target attribute.
	* gcc.target/i386/x86gprintrin-1.c: Add -musermsr for 64bit target.
	* gcc.target/i386/x86gprintrin-2.c: Ditto.
	* gcc.target/i386/x86gprintrin-3.c: Ditto.
	* gcc.target/i386/x86gprintrin-4.c: Add musermsr for 64bit target.
	* gcc.target/i386/x86gprintrin-5.c: Ditto
	* gcc.target/i386/usermsr-1.c: New test.
	* gcc.target/i386/usermsr-2.c: Ditto.
---
 gcc/common/config/i386/cpuinfo.h              |  2 +
 gcc/common/config/i386/i386-common.cc         | 15 +++++
 gcc/common/config/i386/i386-cpuinfo.h         |  1 +
 gcc/common/config/i386/i386-isas.h            |  1 +
 gcc/config.gcc                                |  3 +-
 gcc/config/i386/cpuid.h                       |  1 +
 gcc/config/i386/i386-builtin-types.def        |  3 +
 gcc/config/i386/i386-builtins.cc              |  8 +++
 gcc/config/i386/i386-builtins.h               |  2 +
 gcc/config/i386/i386-c.cc                     |  2 +
 gcc/config/i386/i386-expand.cc                | 35 +++++++++++
 gcc/config/i386/i386-isa.def                  |  1 +
 gcc/config/i386/i386-options.cc               |  4 +-
 gcc/config/i386/i386.md                       | 24 ++++++++
 gcc/config/i386/i386.opt                      |  4 ++
 gcc/config/i386/usermsrintrin.h               | 60 +++++++++++++++++++
 gcc/config/i386/x86gprintrin.h                |  2 +
 gcc/doc/extend.texi                           |  5 ++
 gcc/doc/invoke.texi                           |  6 +-
 gcc/doc/sourcebuild.texi                      |  3 +
 gcc/testsuite/gcc.target/i386/funcspec-56.inc |  2 +
 gcc/testsuite/gcc.target/i386/user_msr-1.c    | 20 +++++++
 gcc/testsuite/gcc.target/i386/user_msr-2.c    | 16 +++++
 .../gcc.target/i386/x86gprintrin-1.c          |  2 +-
 .../gcc.target/i386/x86gprintrin-2.c          |  6 +-
 .../gcc.target/i386/x86gprintrin-3.c          | 28 ++++++++-
 .../gcc.target/i386/x86gprintrin-4.c          | 32 +++++++++-
 .../gcc.target/i386/x86gprintrin-5.c          |  6 +-
 28 files changed, 286 insertions(+), 8 deletions(-)  create mode 100644 gcc/config/i386/usermsrintrin.h  create mode 100644 gcc/testsuite/gcc.target/i386/user_msr-1.c
 create mode 100644 gcc/testsuite/gcc.target/i386/user_msr-2.c

diff --git a/gcc/common/config/i386/cpuinfo.h b/gcc/common/config/i386/cpuinfo.h
index 141d3743316..0f86b44730b 100644
--- a/gcc/common/config/i386/cpuinfo.h
+++ b/gcc/common/config/i386/cpuinfo.h
@@ -838,6 +838,8 @@ get_available_features (struct __processor_model *cpu_model,
 	set_feature (FEATURE_IBT);
       if (edx & bit_UINTR)
 	set_feature (FEATURE_UINTR);
+      if (edx & bit_USER_MSR)
+	set_feature (FEATURE_USER_MSR);
       if (amx_usable)
 	{
 	  if (edx & bit_AMX_TILE)
diff --git a/gcc/common/config/i386/i386-common.cc b/gcc/common/config/i386/i386-common.cc
index 684b0451bb3..13e423deceb 100644
--- a/gcc/common/config/i386/i386-common.cc
+++ b/gcc/common/config/i386/i386-common.cc
@@ -125,6 +125,7 @@ along with GCC; see the file COPYING3.  If not see  #define OPTION_MASK_ISA2_SM4_SET OPTION_MASK_ISA2_SM4  #define OPTION_MASK_ISA2_APX_F_SET OPTION_MASK_ISA2_APX_F  #define OPTION_MASK_ISA2_EVEX512_SET OPTION_MASK_ISA2_EVEX512
+#define OPTION_MASK_ISA2_USER_MSR_SET OPTION_MASK_ISA2_USER_MSR
 
 /* SSE4 includes both SSE4.1 and SSE4.2. -msse4 should be the same
    as -msse4.2.  */
@@ -313,6 +314,7 @@ along with GCC; see the file COPYING3.  If not see  #define OPTION_MASK_ISA2_SM4_UNSET OPTION_MASK_ISA2_SM4  #define OPTION_MASK_ISA2_APX_F_UNSET OPTION_MASK_ISA2_APX_F  #define OPTION_MASK_ISA2_EVEX512_UNSET OPTION_MASK_ISA2_EVEX512
+#define OPTION_MASK_ISA2_USER_MSR_UNSET OPTION_MASK_ISA2_USER_MSR
 
 /* SSE4 includes both SSE4.1 and SSE4.2.  -mno-sse4 should the same
    as -mno-sse4.1. */
@@ -1373,6 +1375,19 @@ ix86_handle_option (struct gcc_options *opts,
 	}
       return true;
 
+    case OPT_musermsr:
+      if (value)
+	{
+	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA2_USER_MSR_SET;
+	  opts->x_ix86_isa_flags2_explicit |= OPTION_MASK_ISA2_USER_MSR_SET;
+	}
+      else
+	{
+	  opts->x_ix86_isa_flags2 &= ~OPTION_MASK_ISA2_USER_MSR_UNSET;
+	  opts->x_ix86_isa_flags2_explicit |= OPTION_MASK_ISA2_USER_MSR_UNSET;
+	}
+      return true;
+
     case OPT_mfma:
       if (value)
 	{
diff --git a/gcc/common/config/i386/i386-cpuinfo.h b/gcc/common/config/i386/i386-cpuinfo.h
index 8bf592191ab..47e9dcfb8f7 100644
--- a/gcc/common/config/i386/i386-cpuinfo.h
+++ b/gcc/common/config/i386/i386-cpuinfo.h
@@ -262,6 +262,7 @@ enum processor_features
   FEATURE_SHA512,
   FEATURE_SM4,
   FEATURE_APX_F,
+  FEATURE_USER_MSR,
   CPU_FEATURE_MAX
 };
 
diff --git a/gcc/common/config/i386/i386-isas.h b/gcc/common/config/i386/i386-isas.h
index 47e0cbd6f5b..6875924994d 100644
--- a/gcc/common/config/i386/i386-isas.h
+++ b/gcc/common/config/i386/i386-isas.h
@@ -192,4 +192,5 @@ ISA_NAMES_TABLE_START
   ISA_NAMES_TABLE_ENTRY("sha512", FEATURE_SHA512, P_NONE, "-msha512")
   ISA_NAMES_TABLE_ENTRY("sm4", FEATURE_SM4, P_NONE, "-msm4")
   ISA_NAMES_TABLE_ENTRY("apxf", FEATURE_APX_F, P_NONE, "-mapxf")
+  ISA_NAMES_TABLE_ENTRY("usermsr", FEATURE_USER_MSR, P_NONE, 
+ "-musermsr")
 ISA_NAMES_TABLE_END
diff --git a/gcc/config.gcc b/gcc/config.gcc index cc37a9c768d..284f3d507ba 100644
--- a/gcc/config.gcc
+++ b/gcc/config.gcc
@@ -448,7 +448,8 @@ i[34567]86-*-* | x86_64-*-*)
 		       avxvnniint8intrin.h avxneconvertintrin.h
 		       cmpccxaddintrin.h amxfp16intrin.h prfchiintrin.h
 		       raointintrin.h amxcomplexintrin.h avxvnniint16intrin.h
-		       sm3intrin.h sha512intrin.h sm4intrin.h"
+		       sm3intrin.h sha512intrin.h sm4intrin.h
+		       usermsrintrin.h"
 	;;
 ia64-*-*)
 	extra_headers=ia64intrin.h
diff --git a/gcc/config/i386/cpuid.h b/gcc/config/i386/cpuid.h index f3d3a2a1c22..75ef2718204 100644
--- a/gcc/config/i386/cpuid.h
+++ b/gcc/config/i386/cpuid.h
@@ -149,6 +149,7 @@
 #define bit_AVXNECONVERT	(1 << 5)
 #define bit_AVXVNNIINT16	(1 << 10)
 #define bit_PREFETCHI	(1 << 14)
+#define bit_USER_MSR	(1 << 15)
 #define bit_APX_F	(1 << 21)
 
 /* Extended State Enumeration Sub-leaf (%eax == 0xd, %ecx == 1) */ diff --git a/gcc/config/i386/i386-builtin-types.def b/gcc/config/i386/i386-builtin-types.def
index e9463120eea..183029f2c75 100644
--- a/gcc/config/i386/i386-builtin-types.def
+++ b/gcc/config/i386/i386-builtin-types.def
@@ -1422,3 +1422,6 @@ DEF_FUNCTION_TYPE (V4SI, V4SI, V4SI, V4SI, INT)
 
 # SHA512 builtins
 DEF_FUNCTION_TYPE (V4DI, V4DI, V4DI, V2DI)
+
+# USER_MSR builtins
+DEF_FUNCTION_TYPE (VOID, UINT64, UINT64)
diff --git a/gcc/config/i386/i386-builtins.cc b/gcc/config/i386/i386-builtins.cc
index 70538fbe17b..42fc3751676 100644
--- a/gcc/config/i386/i386-builtins.cc
+++ b/gcc/config/i386/i386-builtins.cc
@@ -1262,6 +1262,14 @@ ix86_init_mmx_sse_builtins (void)
 	       "__builtin_ia32_testui",
 	       UINT8_FTYPE_VOID, IX86_BUILTIN_TESTUI);
 
+  /* USER_MSR.  */
+  def_builtin (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_USER_MSR,
+	       "__builtin_ia32_urdmsr", UINT64_FTYPE_UINT64,
+	       IX86_BUILTIN_URDMSR);
+  def_builtin (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_USER_MSR,
+	       "__builtin_ia32_uwrmsr", VOID_FTYPE_UINT64_UINT64,
+	       IX86_BUILTIN_UWRMSR);
+
   /* CLDEMOTE.  */
   def_builtin (0, OPTION_MASK_ISA2_CLDEMOTE, "__builtin_ia32_cldemote",
 	       VOID_FTYPE_PCVOID, IX86_BUILTIN_CLDEMOTE); diff --git a/gcc/config/i386/i386-builtins.h b/gcc/config/i386/i386-builtins.h index c632482087c..40785b0aa34 100644
--- a/gcc/config/i386/i386-builtins.h
+++ b/gcc/config/i386/i386-builtins.h
@@ -39,6 +39,8 @@ enum ix86_builtins
   IX86_BUILTIN_MWAIT,
   IX86_BUILTIN_UMONITOR,
   IX86_BUILTIN_UMWAIT,
+  IX86_BUILTIN_URDMSR,
+  IX86_BUILTIN_UWRMSR,
   IX86_BUILTIN_TPAUSE,
   IX86_BUILTIN_TESTUI,
   IX86_BUILTIN_CLZERO,
diff --git a/gcc/config/i386/i386-c.cc b/gcc/config/i386/i386-c.cc index 9c44bd7fb63..042ad8b9d9c 100644
--- a/gcc/config/i386/i386-c.cc
+++ b/gcc/config/i386/i386-c.cc
@@ -712,6 +712,8 @@ ix86_target_macros_internal (HOST_WIDE_INT isa_flag,
     def_or_undef (parse_in, "__SM4__");
   if (isa_flag2 & OPTION_MASK_ISA2_EVEX512)
     def_or_undef (parse_in, "__EVEX512__");
+  if (isa_flag2 & OPTION_MASK_ISA2_USER_MSR)
+    def_or_undef (parse_in, "__USER_MSR__");
   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 d5083494798..4ef85570d44 100644
--- a/gcc/config/i386/i386-expand.cc
+++ b/gcc/config/i386/i386-expand.cc
@@ -13471,6 +13471,41 @@ ix86_expand_builtin (tree exp, rtx target, rtx subtarget,
 	return 0;
       }
 
+    case IX86_BUILTIN_URDMSR:
+    case IX86_BUILTIN_UWRMSR:
+      {
+	arg0 = CALL_EXPR_ARG (exp, 0);
+	op0 = expand_normal (arg0);
+
+	if (CONST_INT_P (op0))
+	  {
+	    unsigned HOST_WIDE_INT val = UINTVAL (op0);
+	    if (val > 0xffffffff)
+	      op0 = force_reg (DImode, op0);
+	  }
+	else
+	  op0 = force_reg (DImode, op0);
+
+	if (fcode == IX86_BUILTIN_UWRMSR)
+	  {
+	    arg1 = CALL_EXPR_ARG (exp, 1);
+	    op1 = expand_normal (arg1);
+	    op1 = force_reg (DImode, op1);
+	    icode = CODE_FOR_uwrmsr;
+	    target = 0;
+	  }
+	else
+	  {
+	    if (target == 0)
+	      target = gen_reg_rtx (DImode);
+	    icode = CODE_FOR_urdmsr;
+	    op1 = op0;
+	    op0 = target;
+	  }
+	emit_insn (GEN_FCN (icode) (op0, op1));
+	return target;
+      }
+
     case IX86_BUILTIN_VEC_INIT_V2SI:
     case IX86_BUILTIN_VEC_INIT_V4HI:
     case IX86_BUILTIN_VEC_INIT_V8QI:
diff --git a/gcc/config/i386/i386-isa.def b/gcc/config/i386/i386-isa.def index c581f343339..991df5e2ef0 100644
--- a/gcc/config/i386/i386-isa.def
+++ b/gcc/config/i386/i386-isa.def
@@ -122,3 +122,4 @@ DEF_PTA(SM3)
 DEF_PTA(SHA512)
 DEF_PTA(SM4)
 DEF_PTA(APX_F)
+DEF_PTA(USER_MSR)
diff --git a/gcc/config/i386/i386-options.cc b/gcc/config/i386/i386-options.cc index 06af373ca57..9506c470147 100644
--- a/gcc/config/i386/i386-options.cc
+++ b/gcc/config/i386/i386-options.cc
@@ -251,7 +251,8 @@ static struct ix86_target_opts isa2_opts[] =
   { "-msm3",		OPTION_MASK_ISA2_SM3 },
   { "-msha512",		OPTION_MASK_ISA2_SHA512 },
   { "-msm4",            OPTION_MASK_ISA2_SM4 },
-  { "-mevex512",        OPTION_MASK_ISA2_EVEX512 }
+  { "-mevex512",        OPTION_MASK_ISA2_EVEX512 },
+  { "-musermsr",	OPTION_MASK_ISA2_USER_MSR }
 };
 static struct ix86_target_opts isa_opts[] =  { @@ -1114,6 +1115,7 @@ ix86_valid_target_attribute_inner_p (tree fndecl, tree args, char *p_strings[],
     IX86_ATTR_ISA ("sm4", OPT_msm4),
     IX86_ATTR_ISA ("apxf", OPT_mapxf),
     IX86_ATTR_ISA ("evex512", OPT_mevex512),
+    IX86_ATTR_ISA ("usermsr", OPT_musermsr),
 
     /* enum options */
     IX86_ATTR_ENUM ("fpmath=",	OPT_mfpmath_),
diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index f390fb5692b..b8f60d1df4b 100644
--- a/gcc/config/i386/i386.md
+++ b/gcc/config/i386/i386.md
@@ -340,6 +340,10 @@
 
   ;; For PREFETCHI support
   UNSPECV_PREFETCHI
+
+  ;; For USER_MSR support
+  UNSPECV_URDMSR
+  UNSPECV_UWRMSR
 ])
 
 ;; Constants to represent rounding modes in the ROUND instruction @@ -26601,6 +26605,26 @@
   DONE;
 })
 
+(define_insn "urdmsr"
+  [(set (match_operand:DI 0 "register_operand" "=r")
+    (unspec_volatile:DI
+      [(match_operand:DI 1 "x86_64_szext_nonmemory_operand" "reZ")]
+      UNSPECV_URDMSR))]
+  "TARGET_USER_MSR && TARGET_64BIT"
+  "urdmsr\t{%1, %0|%0, %1}"
+  [(set_attr "prefix" "vex")
+   (set_attr "type" "other")])
+
+(define_insn "uwrmsr"
+  [(unspec_volatile
+    [(match_operand:DI 0 "x86_64_szext_nonmemory_operand" "reZ")
+      (match_operand:DI 1 "register_operand" "r")]
+      UNSPECV_UWRMSR)]
+  "TARGET_USER_MSR && TARGET_64BIT"
+  "uwrmsr\t{%1, %0|%0, %1}"
+  [(set_attr "prefix" "vex")
+   (set_attr "type" "other")])
+
 (include "mmx.md")
 (include "sse.md")
 (include "sync.md")
diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt index 05ba7f37244..b8382c48099 100644
--- a/gcc/config/i386/i386.opt
+++ b/gcc/config/i386/i386.opt
@@ -1344,3 +1344,7 @@ hook reg or mem constraint in inline asm to GPR16.
 mevex512
 Target Mask(ISA2_EVEX512) Var(ix86_isa_flags2) Save  Support 512 bit vector built-in functions and code generation.
+
+musermsr
+Target Mask(ISA2_USER_MSR) Var(ix86_isa_flags2) Save Support USER_MSR 
+built-in functions and code generation.
diff --git a/gcc/config/i386/usermsrintrin.h b/gcc/config/i386/usermsrintrin.h new file mode 100644 index 00000000000..9e1dbdca112
--- /dev/null
+++ b/gcc/config/i386/usermsrintrin.h
@@ -0,0 +1,60 @@
+/* Copyright (C) 2022 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 _X86GPRINTRIN_H_INCLUDED
+#error "Never use <usermsrintrin.h> directly; include <x86gprintrin.h> instead."
+#endif
+
+#ifndef _USER_MSRINTRIN_H_INCLUDED
+#define _USER_MSRINTRIN_H_INCLUDED
+
+#ifdef __x86_64__
+
+#ifndef __USER_MSR__
+#pragma GCC push_options
+#pragma GCC target("usermsr")
+#define __DISABLE_USER_MSR__
+#endif /* __USER_MSR__ */
+
+extern __inline unsigned long long
+__attribute__ ((__gnu_inline__, __always_inline__, __artificial__)) 
+_urdmsr (unsigned long long __A) {
+  return (unsigned long long) __builtin_ia32_urdmsr (__A); }
+
+extern __inline void
+__attribute__ ((__gnu_inline__, __always_inline__, __artificial__)) 
+_uwrmsr (unsigned long long __A, unsigned long long __B) {
+  __builtin_ia32_uwrmsr (__A, __B);
+}
+
+#ifdef __DISABLE_USER_MSR__
+#undef __DISABLE_USER_MSR__
+#pragma GCC pop_options
+#endif /* __DISABLE_USER_MSR__ */
+
+#endif /* __x86_64__ */
+
+#endif /* _USER_MSRINTRIN_H_INCLUDED */
diff --git a/gcc/config/i386/x86gprintrin.h b/gcc/config/i386/x86gprintrin.h index f41be3ffcde..11a8a963020 100644
--- a/gcc/config/i386/x86gprintrin.h
+++ b/gcc/config/i386/x86gprintrin.h
@@ -108,6 +108,8 @@
 
 #include <hresetintrin.h>
 
+#include <usermsrintrin.h>
+
 extern __inline void
 __attribute__((__gnu_inline__, __always_inline__, __artificial__))  _wbinvd (void) diff --git a/gcc/doc/extend.texi b/gcc/doc/extend.texi index b82497f00e4..991c2db8eba 100644
--- a/gcc/doc/extend.texi
+++ b/gcc/doc/extend.texi
@@ -7210,6 +7210,11 @@ Enable/disable the generation of the SHA512 instructions.
 @itemx no-sm4
 Enable/disable the generation of the SM4 instructions.
 
+@cindex @code{target("umsr")} function attribute, x86 @item umsr @itemx 
+no-umsr Enable/disable the generation of the UMSR instructions.
+
 @cindex @code{target("cld")} function attribute, x86  @item cld  @itemx no-cld diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index 7c5f81d9783..3edf41257f1 100644
--- a/gcc/doc/invoke.texi
+++ b/gcc/doc/invoke.texi
@@ -1444,6 +1444,7 @@ See RS/6000 and PowerPC Options.
 -mamx-tile  -mamx-int8  -mamx-bf16 -muintr -mhreset -mavxvnni
 -mavx512fp16 -mavxifma -mavxvnniint8 -mavxneconvert -mcmpccxadd -mamx-fp16  -mprefetchi -mraoint -mamx-complex -mavxvnniint16 -msm3 -msha512 -msm4 -mapxf
+-mumsr
 -mcldemote  -mms-bitfields  -mno-align-stringops  -minline-all-stringops  -minline-stringops-dynamically  -mstringop-strategy=@var{alg}  -mkl -mwidekl @@ -33830,6 +33831,9 @@ preferred alignment to @option{-mpreferred-stack-boundary=2}.
 @need 200
 @opindex mapxf
 @itemx -mapxf
+@need 200
+@opindex mumsr
+@itemx -mumsr
 These switches enable the use of instructions in the MMX, SSE,  AVX512ER, AVX512CD, AVX512VL, AVX512BW, AVX512DQ, AVX512IFMA, AVX512VBMI, SHA,  AES, PCLMUL, CLFLUSHOPT, CLWB, FSGSBASE, PTWRITE, RDRND, F16C, FMA, PCONFIG, @@ -33840,7 +33844,7 @@ GFNI, VAES, WAITPKG, VPCLMULQDQ, AVX512BITALG, MOVDIRI, MOVDIR64B, AVX512BF16,  ENQCMD, AVX512VPOPCNTDQ, AVX5124FMAPS, AVX512VNNI, AVX5124VNNIW, SERIALIZE,  UINTR, HRESET, AMXTILE, AMXINT8, AMXBF16, KL, WIDEKL, AVXVNNI, AVX512-FP16,  AVXIFMA, AVXVNNIINT8, AVXNECONVERT, CMPCCXADD, AMX-FP16, PREFETCHI, RAOINT, -AMX-COMPLEX, AVXVNNIINT16, SM3, SHA512, SM4, APX_F or CLDEMOTE extended
+AMX-COMPLEX, AVXVNNIINT16, SM3, SHA512, SM4, APX_F, UMSR or CLDEMOTE 
+extended
 instruction sets. Each has a corresponding @option{-mno-} option to disable  use of these instructions.
 
diff --git a/gcc/doc/sourcebuild.texi b/gcc/doc/sourcebuild.texi index 8bf701461ec..a859bcc53cc 100644
--- a/gcc/doc/sourcebuild.texi
+++ b/gcc/doc/sourcebuild.texi
@@ -2624,6 +2624,9 @@ Test environment appears to run executables on a simulator that  accepts only @code{EM_SPARC} executables and chokes on @code{EM_SPARC32PLUS}  or @code{EM_SPARCV9} executables.
 
+@item umsr
+Target supports the execution of @code{umsr} instructions.
+
 @item vect_cmdline_needed
 Target requires a command line argument to enable a SIMD instruction set.
 
diff --git a/gcc/testsuite/gcc.target/i386/funcspec-56.inc b/gcc/testsuite/gcc.target/i386/funcspec-56.inc
index ca558b3e828..e0470a60483 100644
--- a/gcc/testsuite/gcc.target/i386/funcspec-56.inc
+++ b/gcc/testsuite/gcc.target/i386/funcspec-56.inc
@@ -92,6 +92,7 @@ extern void test_avxvnniint16 (void)		__attribute__((__target__("avxvnniint16"))
 extern void test_sm3 (void)			__attribute__((__target__("sm3")));
 extern void test_sha512 (void)			__attribute__((__target__("sha512")));
 extern void test_sm4 (void)                     __attribute__((__target__("sm4")));
+extern void test_user_msr (void)		__attribute__((__target__("usermsr")));
 
 extern void test_no_sgx (void)			__attribute__((__target__("no-sgx")));
 extern void test_no_avx5124fmaps(void)		__attribute__((__target__("no-avx5124fmaps")));
@@ -185,6 +186,7 @@ extern void test_no_avxvnniint16 (void)		__attribute__((__target__("no-avxvnniin
 extern void test_no_sm3 (void)			__attribute__((__target__("no-sm3")));
 extern void test_no_sha512 (void)		__attribute__((__target__("no-sha512")));
 extern void test_no_sm4 (void)                  __attribute__((__target__("no-sm4")));
+extern void test_no_user_msr (void)		__attribute__((__target__("no-usermsr")));
 
 extern void test_arch_nocona (void)		__attribute__((__target__("arch=nocona")));
 extern void test_arch_core2 (void)		__attribute__((__target__("arch=core2")));
diff --git a/gcc/testsuite/gcc.target/i386/user_msr-1.c b/gcc/testsuite/gcc.target/i386/user_msr-1.c
new file mode 100644
index 00000000000..447852306df
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/user_msr-1.c
@@ -0,0 +1,20 @@
+/* { dg-do compile { target { ! ia32  }  }  } */
+/* { dg-options "-musermsr -O2"  } */
+/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\%r\[a-z\]x, 
+\\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\\$121" 1  }  } */
+/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x, 
+\\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x, 
+\\\$121" 1  }  } */
+
+#include <x86gprintrin.h>
+
+volatile unsigned long long x;
+volatile unsigned long long y;
+
+void extern
+user_msr_test (void)
+{
+  x = _urdmsr(y);
+  x = _urdmsr(121);
+  _uwrmsr(y, x);
+  _uwrmsr(121, x);
+}
diff --git a/gcc/testsuite/gcc.target/i386/user_msr-2.c b/gcc/testsuite/gcc.target/i386/user_msr-2.c
new file mode 100644
index 00000000000..ab0e76f9088
--- /dev/null
+++ b/gcc/testsuite/gcc.target/i386/user_msr-2.c
@@ -0,0 +1,16 @@
+/* { dg-do compile { target { ! ia32 } } } */
+/* { dg-options "-O2 -musermsr" } */
+/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\%r\[a-z\]x, 
+\\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x, 
+\\%r\[a-z\]x" 1  }  } */
+/* { dg-final { scan-assembler-times "movabsq\[ 
+\\t\]\\\$20018842566655, \\%r\[a-z\]x" 1  }  } */
+
+#include <x86gprintrin.h>
+
+volatile unsigned long long x;
+
+void extern
+user_msr_test (void)
+{
+  x = _urdmsr(0x1234ffffffffULL);
+  _uwrmsr(0x1234ffffffffULL, x);
+}
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
index 68da4db4f3c..b9479beef7c 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
@@ -1,7 +1,7 @@
 /* Test that <x86gprintrin.h> is usable with -O -std=c89 -pedantic-errors.  */
 /* { dg-do compile } */
 /* { dg-options "-O -std=c89 -pedantic-errors -march=x86-64 -madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
-/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
+/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr" 
+{ target { ! ia32 } } }  */
 
 #include <x86gprintrin.h>
 
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
index 737c2a26f98..ee167ebab90 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
@@ -1,7 +1,7 @@
 /* { dg-do compile } */
 /* { dg-options "-O2 -Werror-implicit-function-declaration -march=x86-64 -madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
 /* { dg-add-options bind_pic_locally } */
-/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
+/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr" 
+{ target { ! ia32 } } }  */
 
 /* Test that the intrinsics in <x86gprintrin.h> compile with optimization.
    All of them are defined as inline functions that reference the proper @@ -32,4 +32,8 @@  #define __builtin_ia32_cmpccxadd(A, B, C, D) __builtin_ia32_cmpccxadd(A, B, C, 1)  #define __builtin_ia32_cmpccxadd64(A, B, C, D) __builtin_ia32_cmpccxadd64(A, B, C, 1)
 
+/* usermsrintrin.h */
+#define __builtin_ia32_urdmsr(A) __builtin_ia32_urdmsr(1) #define 
+__builtin_ia32_uwrmsr(A, B) __builtin_ia32_uwrmsr(1, B)
+
 #include <x86gprintrin.h>
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
index 52690b1dfb5..a87039149f9 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
@@ -1,7 +1,7 @@
 /* { dg-do compile } */
 /* { dg-options "-O0 -Werror-implicit-function-declaration -march=x86-64 -madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
 /* { dg-add-options bind_pic_locally } */
-/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { ! ia32 } } }  */
+/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr" 
+{ target { ! ia32 } } }  */
 
 /* Test that the intrinsics in <x86gprintrin.h> compile without optimization.
    All of them are defined as inline functions that reference the proper @@ -14,3 +14,29 @@  #define __inline
 
 #include <x86gprintrin.h>
+
+#define _CONCAT(x,y) x ## y
+
+#define test_0(func, type, imm)		  \
+  type _CONCAT(_0,func) (int const I)	  \
+	    { return func (imm);  }
+
+#define test_1(func, type, op1_type)   \
+  type _CONCAT(_1,func) (op1_type A)    \
+	{ return func (A); }
+
+#define test_1r(func, type, op1_type, imm)	    \
+  type _CONCAT(_1r,func) (op1_type A, int const I)    \
+	{ return func (imm, A); }
+
+#define test_2(func, type, op1_type,  op2_type)	    \
+    type _CONCAT(_2,func) (op1_type A, op2_type B)    \
+      { return func (A, B);  }
+
+/* usermsrintrin.h */
+#ifdef __x86_64__
+test_0 (_urdmsr, unsigned long long, 1)
+test_1 (_urdmsr, unsigned long long, unsigned long long) test_1r 
+(_uwrmsr, void, unsigned long long, 1)
+test_2 (_uwrmsr, void, unsigned long long, unsigned long long) #endif
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
index 94cfc583dc9..c3c79473020 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
@@ -13,9 +13,27 @@
 #define extern
 #define __inline
 
+#define _CONCAT(x,y) x ## y
+
+#define test_0(func, type, imm)		  \
+  type _CONCAT(_0,func) (int const I)	  \
+	    { return func (imm);  }
+
+#define test_1(func, type, op1_type)   \
+  type _CONCAT(_1,func) (op1_type A)    \
+	{ return func (A); }
+
+#define test_1r(func, type, op1_type, imm)	    \
+  type _CONCAT(_1r,func) (op1_type A, int const I)    \
+	{ return func (imm, A); }
+
+#define test_2(func, type, op1_type,  op2_type)	    \
+    type _CONCAT(_2,func) (op1_type A, op2_type B)    \
+      { return func (A, B);  }
+
 #ifndef DIFFERENT_PRAGMAS
 #ifdef __x86_64__
-#pragma GCC target ("adx,bmi,bmi2,cmpccxadd,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,prefetchi,raoint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,uintr,xsaveopt")
+#pragma GCC target 
+("adx,bmi,bmi2,cmpccxadd,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,prefetch
+i,raoint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,uintr,usermsr,xsaveopt
+")
 #else
 #pragma GCC target ("adx,bmi,bmi2,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,raoint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,xsaveopt")
 #endif
@@ -29,6 +47,18 @@
 
 /* x86intrin.h (LWP/BMI/BMI2/TBM/LZCNT). */  #ifdef DIFFERENT_PRAGMAS
+#ifdef __x86_64__
+#pragma GCC target ("lwp,bmi,bmi2,tbm,lzcnt,usermsr")
+#else
 #pragma GCC target ("lwp,bmi,bmi2,tbm,lzcnt")  #endif
+#endif
 #include <x86gprintrin.h>
+
+/* usermsrintrin.h */
+#ifdef __x86_64__
+test_0 (_urdmsr, unsigned long long, 1)
+test_1 (_urdmsr, unsigned long long, unsigned long long) test_1r 
+(_uwrmsr, void, unsigned long long, 1)
+test_2 (_uwrmsr, void, unsigned long long, unsigned long long) #endif
diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c b/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
index 95f3e0a003c..ef126ea76c2 100644
--- a/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
+++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
@@ -31,8 +31,12 @@
 #define __builtin_ia32_cmpccxadd(A, B, C, D) __builtin_ia32_cmpccxadd(A, B, C, 1)  #define __builtin_ia32_cmpccxadd64(A, B, C, D) __builtin_ia32_cmpccxadd64(A, B, C, 1)
 
+/* usermsrintrin.h */
+#define __builtin_ia32_urdmsr(A) __builtin_ia32_urdmsr(1) #define 
+__builtin_ia32_uwrmsr(A, B) __builtin_ia32_uwrmsr(1, B)
+
 #ifdef __x86_64__
-#pragma GCC target ("adx,bmi,bmi2,clflushopt,clwb,clzero,cmpccxadd,enqcmd,fsgsbase,fxsr,hreset,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,prefetchi,raoint,rdpid,rdrnd,rdseed,tbm,rtm,serialize,sgx,tsxldtrk,uintr,xsavec,xsaveopt,xsaves,wbnoinvd")
+#pragma GCC target 
+("adx,bmi,bmi2,clflushopt,clwb,clzero,cmpccxadd,enqcmd,fsgsbase,fxsr,hr
+eset,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,prefetchi,raoint,rdpid,rdrnd,r
+dseed,tbm,rtm,serialize,sgx,tsxldtrk,uintr,usermsr,xsavec,xsaveopt,xsav
+es,wbnoinvd")
 #else
 #pragma GCC target ("adx,bmi,bmi2,clflushopt,clwb,clzero,enqcmd,fsgsbase,fxsr,hreset,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,raoint,rdpid,rdrnd,rdseed,tbm,rtm,serialize,sgx,tsxldtrk,xsavec,xsaveopt,xsaves,wbnoinvd")
 #endif
--
2.31.1


^ permalink raw reply	[flat|nested] 3+ messages in thread

* RE: [PATCH] Support Intel USER_MSR
  2023-10-10  8:06 ` Hu, Lin1
@ 2023-10-12  1:47   ` Liu, Hongtao
  0 siblings, 0 replies; 3+ messages in thread
From: Liu, Hongtao @ 2023-10-12  1:47 UTC (permalink / raw)
  To: Hu, Lin1, gcc-patches; +Cc: ubizjak



> -----Original Message-----
> From: Hu, Lin1 <lin1.hu@intel.com>
> Sent: Tuesday, October 10, 2023 4:06 PM
> To: Hu, Lin1 <lin1.hu@intel.com>; gcc-patches@gcc.gnu.org
> Cc: Liu, Hongtao <hongtao.liu@intel.com>; ubizjak@gmail.com
> Subject: RE: [PATCH] Support Intel USER_MSR
> 
> There are some typos In /gcc/doc/extend.texi and /gcc/doc/invoke.texi. They
> should be USER_MSR, not UMSR. I have modified them in my branch.
> 
> -----Original Message-----
> From: Hu, Lin1 <lin1.hu@intel.com>
> Sent: Tuesday, October 10, 2023 3:47 PM
> To: gcc-patches@gcc.gnu.org
> Cc: Liu, Hongtao <hongtao.liu@intel.com>; ubizjak@gmail.com
> Subject: [PATCH] Support Intel USER_MSR
> 
> This patch aims to support Intel USER_MSR.
Ok.
> 
> gcc/ChangeLog:
> 
> 	* common/config/i386/cpuinfo.h (get_available_features):
> 	Detect USER_MSR.
> 	* common/config/i386/i386-common.cc
> (OPTION_MASK_ISA2_USER_MSR_SET): New.
> 	(OPTION_MASK_ISA2_USER_MSR_UNSET): Ditto.
> 	(ix86_handle_option): Handle -musermsr.
> 	* common/config/i386/i386-cpuinfo.h (enum processor_features):
> 	Add FEATURE_USER_MSR.
> 	* common/config/i386/i386-isas.h: Add ISA_NAME_TABLE_ENTRY
> for usermsr.
> 	* config.gcc: Add usermsrintrin.h
> 	* config/i386/cpuid.h (bit_USER_MSR): New.
> 	* config/i386/i386-builtin-types.def:
> 	Add DEF_FUNCTION_TYPE (VOID, UINT64, UINT64).
> 	* config/i386/i386-builtins.cc (ix86_init_mmx_sse_builtins):
> 	Add __builtin_urdmsr and __builtin_uwrmsr.
> 	* config/i386/i386-builtins.h (ix86_builtins):
> 	Add IX86_BUILTIN_URDMSR and IX86_BUILTIN_UWRMSR.
> 	* config/i386/i386-c.cc (ix86_target_macros_internal):
> 	Define __USER_MSR__.
> 	* config/i386/i386-expand.cc (ix86_expand_builtin):
> 	Handle new builtins.
> 	* config/i386/i386-isa.def (USER_MSR): Add DEF_PTA(USER_MSR).
> 	* config/i386/i386-options.cc (ix86_valid_target_attribute_inner_p):
> 	Handle usermsr.
> 	* config/i386/i386.md (urdmsr): New define_insn.
> 	(uwrmsr): Ditto.
> 	* config/i386/i386.opt: Add option -musermsr.
> 	* config/i386/x86gprintrin.h: Include usermsrintrin.h
> 	* doc/extend.texi: Document usermsr.
> 	* doc/invoke.texi: Document -musermsr.
> 	* doc/sourcebuild.texi: Document target usermsr.
> 	* config/i386/usermsrintrin.h: New file.
> 
> gcc/testsuite/ChangeLog:
> 
> 	* gcc.target/i386/funcspec-56.inc: Add new target attribute.
> 	* gcc.target/i386/x86gprintrin-1.c: Add -musermsr for 64bit target.
> 	* gcc.target/i386/x86gprintrin-2.c: Ditto.
> 	* gcc.target/i386/x86gprintrin-3.c: Ditto.
> 	* gcc.target/i386/x86gprintrin-4.c: Add musermsr for 64bit target.
> 	* gcc.target/i386/x86gprintrin-5.c: Ditto
> 	* gcc.target/i386/usermsr-1.c: New test.
> 	* gcc.target/i386/usermsr-2.c: Ditto.
> ---
>  gcc/common/config/i386/cpuinfo.h              |  2 +
>  gcc/common/config/i386/i386-common.cc         | 15 +++++
>  gcc/common/config/i386/i386-cpuinfo.h         |  1 +
>  gcc/common/config/i386/i386-isas.h            |  1 +
>  gcc/config.gcc                                |  3 +-
>  gcc/config/i386/cpuid.h                       |  1 +
>  gcc/config/i386/i386-builtin-types.def        |  3 +
>  gcc/config/i386/i386-builtins.cc              |  8 +++
>  gcc/config/i386/i386-builtins.h               |  2 +
>  gcc/config/i386/i386-c.cc                     |  2 +
>  gcc/config/i386/i386-expand.cc                | 35 +++++++++++
>  gcc/config/i386/i386-isa.def                  |  1 +
>  gcc/config/i386/i386-options.cc               |  4 +-
>  gcc/config/i386/i386.md                       | 24 ++++++++
>  gcc/config/i386/i386.opt                      |  4 ++
>  gcc/config/i386/usermsrintrin.h               | 60 +++++++++++++++++++
>  gcc/config/i386/x86gprintrin.h                |  2 +
>  gcc/doc/extend.texi                           |  5 ++
>  gcc/doc/invoke.texi                           |  6 +-
>  gcc/doc/sourcebuild.texi                      |  3 +
>  gcc/testsuite/gcc.target/i386/funcspec-56.inc |  2 +
>  gcc/testsuite/gcc.target/i386/user_msr-1.c    | 20 +++++++
>  gcc/testsuite/gcc.target/i386/user_msr-2.c    | 16 +++++
>  .../gcc.target/i386/x86gprintrin-1.c          |  2 +-
>  .../gcc.target/i386/x86gprintrin-2.c          |  6 +-
>  .../gcc.target/i386/x86gprintrin-3.c          | 28 ++++++++-
>  .../gcc.target/i386/x86gprintrin-4.c          | 32 +++++++++-
>  .../gcc.target/i386/x86gprintrin-5.c          |  6 +-
>  28 files changed, 286 insertions(+), 8 deletions(-)  create mode 100644
> gcc/config/i386/usermsrintrin.h  create mode 100644
> gcc/testsuite/gcc.target/i386/user_msr-1.c
>  create mode 100644 gcc/testsuite/gcc.target/i386/user_msr-2.c
> 
> diff --git a/gcc/common/config/i386/cpuinfo.h
> b/gcc/common/config/i386/cpuinfo.h
> index 141d3743316..0f86b44730b 100644
> --- a/gcc/common/config/i386/cpuinfo.h
> +++ b/gcc/common/config/i386/cpuinfo.h
> @@ -838,6 +838,8 @@ get_available_features (struct __processor_model
> *cpu_model,
>  	set_feature (FEATURE_IBT);
>        if (edx & bit_UINTR)
>  	set_feature (FEATURE_UINTR);
> +      if (edx & bit_USER_MSR)
> +	set_feature (FEATURE_USER_MSR);
>        if (amx_usable)
>  	{
>  	  if (edx & bit_AMX_TILE)
> diff --git a/gcc/common/config/i386/i386-common.cc
> b/gcc/common/config/i386/i386-common.cc
> index 684b0451bb3..13e423deceb 100644
> --- a/gcc/common/config/i386/i386-common.cc
> +++ b/gcc/common/config/i386/i386-common.cc
> @@ -125,6 +125,7 @@ along with GCC; see the file COPYING3.  If not see
> #define OPTION_MASK_ISA2_SM4_SET OPTION_MASK_ISA2_SM4  #define
> OPTION_MASK_ISA2_APX_F_SET OPTION_MASK_ISA2_APX_F  #define
> OPTION_MASK_ISA2_EVEX512_SET OPTION_MASK_ISA2_EVEX512
> +#define OPTION_MASK_ISA2_USER_MSR_SET
> OPTION_MASK_ISA2_USER_MSR
> 
>  /* SSE4 includes both SSE4.1 and SSE4.2. -msse4 should be the same
>     as -msse4.2.  */
> @@ -313,6 +314,7 @@ along with GCC; see the file COPYING3.  If not see
> #define OPTION_MASK_ISA2_SM4_UNSET OPTION_MASK_ISA2_SM4
> #define OPTION_MASK_ISA2_APX_F_UNSET OPTION_MASK_ISA2_APX_F
> #define OPTION_MASK_ISA2_EVEX512_UNSET
> OPTION_MASK_ISA2_EVEX512
> +#define OPTION_MASK_ISA2_USER_MSR_UNSET
> OPTION_MASK_ISA2_USER_MSR
> 
>  /* SSE4 includes both SSE4.1 and SSE4.2.  -mno-sse4 should the same
>     as -mno-sse4.1. */
> @@ -1373,6 +1375,19 @@ ix86_handle_option (struct gcc_options *opts,
>  	}
>        return true;
> 
> +    case OPT_musermsr:
> +      if (value)
> +	{
> +	  opts->x_ix86_isa_flags2 |= OPTION_MASK_ISA2_USER_MSR_SET;
> +	  opts->x_ix86_isa_flags2_explicit |=
> OPTION_MASK_ISA2_USER_MSR_SET;
> +	}
> +      else
> +	{
> +	  opts->x_ix86_isa_flags2 &=
> ~OPTION_MASK_ISA2_USER_MSR_UNSET;
> +	  opts->x_ix86_isa_flags2_explicit |=
> OPTION_MASK_ISA2_USER_MSR_UNSET;
> +	}
> +      return true;
> +
>      case OPT_mfma:
>        if (value)
>  	{
> diff --git a/gcc/common/config/i386/i386-cpuinfo.h
> b/gcc/common/config/i386/i386-cpuinfo.h
> index 8bf592191ab..47e9dcfb8f7 100644
> --- a/gcc/common/config/i386/i386-cpuinfo.h
> +++ b/gcc/common/config/i386/i386-cpuinfo.h
> @@ -262,6 +262,7 @@ enum processor_features
>    FEATURE_SHA512,
>    FEATURE_SM4,
>    FEATURE_APX_F,
> +  FEATURE_USER_MSR,
>    CPU_FEATURE_MAX
>  };
> 
> diff --git a/gcc/common/config/i386/i386-isas.h
> b/gcc/common/config/i386/i386-isas.h
> index 47e0cbd6f5b..6875924994d 100644
> --- a/gcc/common/config/i386/i386-isas.h
> +++ b/gcc/common/config/i386/i386-isas.h
> @@ -192,4 +192,5 @@ ISA_NAMES_TABLE_START
>    ISA_NAMES_TABLE_ENTRY("sha512", FEATURE_SHA512, P_NONE, "-
> msha512")
>    ISA_NAMES_TABLE_ENTRY("sm4", FEATURE_SM4, P_NONE, "-msm4")
>    ISA_NAMES_TABLE_ENTRY("apxf", FEATURE_APX_F, P_NONE, "-mapxf")
> +  ISA_NAMES_TABLE_ENTRY("usermsr", FEATURE_USER_MSR, P_NONE,
> + "-musermsr")
>  ISA_NAMES_TABLE_END
> diff --git a/gcc/config.gcc b/gcc/config.gcc index cc37a9c768d..284f3d507ba
> 100644
> --- a/gcc/config.gcc
> +++ b/gcc/config.gcc
> @@ -448,7 +448,8 @@ i[34567]86-*-* | x86_64-*-*)
>  		       avxvnniint8intrin.h avxneconvertintrin.h
>  		       cmpccxaddintrin.h amxfp16intrin.h prfchiintrin.h
>  		       raointintrin.h amxcomplexintrin.h avxvnniint16intrin.h
> -		       sm3intrin.h sha512intrin.h sm4intrin.h"
> +		       sm3intrin.h sha512intrin.h sm4intrin.h
> +		       usermsrintrin.h"
>  	;;
>  ia64-*-*)
>  	extra_headers=ia64intrin.h
> diff --git a/gcc/config/i386/cpuid.h b/gcc/config/i386/cpuid.h index
> f3d3a2a1c22..75ef2718204 100644
> --- a/gcc/config/i386/cpuid.h
> +++ b/gcc/config/i386/cpuid.h
> @@ -149,6 +149,7 @@
>  #define bit_AVXNECONVERT	(1 << 5)
>  #define bit_AVXVNNIINT16	(1 << 10)
>  #define bit_PREFETCHI	(1 << 14)
> +#define bit_USER_MSR	(1 << 15)
>  #define bit_APX_F	(1 << 21)
> 
>  /* Extended State Enumeration Sub-leaf (%eax == 0xd, %ecx == 1) */ diff --git
> a/gcc/config/i386/i386-builtin-types.def b/gcc/config/i386/i386-builtin-
> types.def
> index e9463120eea..183029f2c75 100644
> --- a/gcc/config/i386/i386-builtin-types.def
> +++ b/gcc/config/i386/i386-builtin-types.def
> @@ -1422,3 +1422,6 @@ DEF_FUNCTION_TYPE (V4SI, V4SI, V4SI, V4SI, INT)
> 
>  # SHA512 builtins
>  DEF_FUNCTION_TYPE (V4DI, V4DI, V4DI, V2DI)
> +
> +# USER_MSR builtins
> +DEF_FUNCTION_TYPE (VOID, UINT64, UINT64)
> diff --git a/gcc/config/i386/i386-builtins.cc b/gcc/config/i386/i386-builtins.cc
> index 70538fbe17b..42fc3751676 100644
> --- a/gcc/config/i386/i386-builtins.cc
> +++ b/gcc/config/i386/i386-builtins.cc
> @@ -1262,6 +1262,14 @@ ix86_init_mmx_sse_builtins (void)
>  	       "__builtin_ia32_testui",
>  	       UINT8_FTYPE_VOID, IX86_BUILTIN_TESTUI);
> 
> +  /* USER_MSR.  */
> +  def_builtin (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_USER_MSR,
> +	       "__builtin_ia32_urdmsr", UINT64_FTYPE_UINT64,
> +	       IX86_BUILTIN_URDMSR);
> +  def_builtin (OPTION_MASK_ISA_64BIT, OPTION_MASK_ISA2_USER_MSR,
> +	       "__builtin_ia32_uwrmsr", VOID_FTYPE_UINT64_UINT64,
> +	       IX86_BUILTIN_UWRMSR);
> +
>    /* CLDEMOTE.  */
>    def_builtin (0, OPTION_MASK_ISA2_CLDEMOTE, "__builtin_ia32_cldemote",
>  	       VOID_FTYPE_PCVOID, IX86_BUILTIN_CLDEMOTE); diff --git
> a/gcc/config/i386/i386-builtins.h b/gcc/config/i386/i386-builtins.h index
> c632482087c..40785b0aa34 100644
> --- a/gcc/config/i386/i386-builtins.h
> +++ b/gcc/config/i386/i386-builtins.h
> @@ -39,6 +39,8 @@ enum ix86_builtins
>    IX86_BUILTIN_MWAIT,
>    IX86_BUILTIN_UMONITOR,
>    IX86_BUILTIN_UMWAIT,
> +  IX86_BUILTIN_URDMSR,
> +  IX86_BUILTIN_UWRMSR,
>    IX86_BUILTIN_TPAUSE,
>    IX86_BUILTIN_TESTUI,
>    IX86_BUILTIN_CLZERO,
> diff --git a/gcc/config/i386/i386-c.cc b/gcc/config/i386/i386-c.cc index
> 9c44bd7fb63..042ad8b9d9c 100644
> --- a/gcc/config/i386/i386-c.cc
> +++ b/gcc/config/i386/i386-c.cc
> @@ -712,6 +712,8 @@ ix86_target_macros_internal (HOST_WIDE_INT
> isa_flag,
>      def_or_undef (parse_in, "__SM4__");
>    if (isa_flag2 & OPTION_MASK_ISA2_EVEX512)
>      def_or_undef (parse_in, "__EVEX512__");
> +  if (isa_flag2 & OPTION_MASK_ISA2_USER_MSR)
> +    def_or_undef (parse_in, "__USER_MSR__");
>    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
> d5083494798..4ef85570d44 100644
> --- a/gcc/config/i386/i386-expand.cc
> +++ b/gcc/config/i386/i386-expand.cc
> @@ -13471,6 +13471,41 @@ ix86_expand_builtin (tree exp, rtx target, rtx
> subtarget,
>  	return 0;
>        }
> 
> +    case IX86_BUILTIN_URDMSR:
> +    case IX86_BUILTIN_UWRMSR:
> +      {
> +	arg0 = CALL_EXPR_ARG (exp, 0);
> +	op0 = expand_normal (arg0);
> +
> +	if (CONST_INT_P (op0))
> +	  {
> +	    unsigned HOST_WIDE_INT val = UINTVAL (op0);
> +	    if (val > 0xffffffff)
> +	      op0 = force_reg (DImode, op0);
> +	  }
> +	else
> +	  op0 = force_reg (DImode, op0);
> +
> +	if (fcode == IX86_BUILTIN_UWRMSR)
> +	  {
> +	    arg1 = CALL_EXPR_ARG (exp, 1);
> +	    op1 = expand_normal (arg1);
> +	    op1 = force_reg (DImode, op1);
> +	    icode = CODE_FOR_uwrmsr;
> +	    target = 0;
> +	  }
> +	else
> +	  {
> +	    if (target == 0)
> +	      target = gen_reg_rtx (DImode);
> +	    icode = CODE_FOR_urdmsr;
> +	    op1 = op0;
> +	    op0 = target;
> +	  }
> +	emit_insn (GEN_FCN (icode) (op0, op1));
> +	return target;
> +      }
> +
>      case IX86_BUILTIN_VEC_INIT_V2SI:
>      case IX86_BUILTIN_VEC_INIT_V4HI:
>      case IX86_BUILTIN_VEC_INIT_V8QI:
> diff --git a/gcc/config/i386/i386-isa.def b/gcc/config/i386/i386-isa.def index
> c581f343339..991df5e2ef0 100644
> --- a/gcc/config/i386/i386-isa.def
> +++ b/gcc/config/i386/i386-isa.def
> @@ -122,3 +122,4 @@ DEF_PTA(SM3)
>  DEF_PTA(SHA512)
>  DEF_PTA(SM4)
>  DEF_PTA(APX_F)
> +DEF_PTA(USER_MSR)
> diff --git a/gcc/config/i386/i386-options.cc b/gcc/config/i386/i386-
> options.cc index 06af373ca57..9506c470147 100644
> --- a/gcc/config/i386/i386-options.cc
> +++ b/gcc/config/i386/i386-options.cc
> @@ -251,7 +251,8 @@ static struct ix86_target_opts isa2_opts[] =
>    { "-msm3",		OPTION_MASK_ISA2_SM3 },
>    { "-msha512",		OPTION_MASK_ISA2_SHA512 },
>    { "-msm4",            OPTION_MASK_ISA2_SM4 },
> -  { "-mevex512",        OPTION_MASK_ISA2_EVEX512 }
> +  { "-mevex512",        OPTION_MASK_ISA2_EVEX512 },
> +  { "-musermsr",	OPTION_MASK_ISA2_USER_MSR }
>  };
>  static struct ix86_target_opts isa_opts[] =  { @@ -1114,6 +1115,7 @@
> ix86_valid_target_attribute_inner_p (tree fndecl, tree args, char *p_strings[],
>      IX86_ATTR_ISA ("sm4", OPT_msm4),
>      IX86_ATTR_ISA ("apxf", OPT_mapxf),
>      IX86_ATTR_ISA ("evex512", OPT_mevex512),
> +    IX86_ATTR_ISA ("usermsr", OPT_musermsr),
> 
>      /* enum options */
>      IX86_ATTR_ENUM ("fpmath=",	OPT_mfpmath_),
> diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index
> f390fb5692b..b8f60d1df4b 100644
> --- a/gcc/config/i386/i386.md
> +++ b/gcc/config/i386/i386.md
> @@ -340,6 +340,10 @@
> 
>    ;; For PREFETCHI support
>    UNSPECV_PREFETCHI
> +
> +  ;; For USER_MSR support
> +  UNSPECV_URDMSR
> +  UNSPECV_UWRMSR
>  ])
> 
>  ;; Constants to represent rounding modes in the ROUND instruction @@ -
> 26601,6 +26605,26 @@
>    DONE;
>  })
> 
> +(define_insn "urdmsr"
> +  [(set (match_operand:DI 0 "register_operand" "=r")
> +    (unspec_volatile:DI
> +      [(match_operand:DI 1 "x86_64_szext_nonmemory_operand" "reZ")]
> +      UNSPECV_URDMSR))]
> +  "TARGET_USER_MSR && TARGET_64BIT"
> +  "urdmsr\t{%1, %0|%0, %1}"
> +  [(set_attr "prefix" "vex")
> +   (set_attr "type" "other")])
> +
> +(define_insn "uwrmsr"
> +  [(unspec_volatile
> +    [(match_operand:DI 0 "x86_64_szext_nonmemory_operand" "reZ")
> +      (match_operand:DI 1 "register_operand" "r")]
> +      UNSPECV_UWRMSR)]
> +  "TARGET_USER_MSR && TARGET_64BIT"
> +  "uwrmsr\t{%1, %0|%0, %1}"
> +  [(set_attr "prefix" "vex")
> +   (set_attr "type" "other")])
> +
>  (include "mmx.md")
>  (include "sse.md")
>  (include "sync.md")
> diff --git a/gcc/config/i386/i386.opt b/gcc/config/i386/i386.opt index
> 05ba7f37244..b8382c48099 100644
> --- a/gcc/config/i386/i386.opt
> +++ b/gcc/config/i386/i386.opt
> @@ -1344,3 +1344,7 @@ hook reg or mem constraint in inline asm to
> GPR16.
>  mevex512
>  Target Mask(ISA2_EVEX512) Var(ix86_isa_flags2) Save  Support 512 bit
> vector built-in functions and code generation.
> +
> +musermsr
> +Target Mask(ISA2_USER_MSR) Var(ix86_isa_flags2) Save Support USER_MSR
> +built-in functions and code generation.
> diff --git a/gcc/config/i386/usermsrintrin.h
> b/gcc/config/i386/usermsrintrin.h new file mode 100644 index
> 00000000000..9e1dbdca112
> --- /dev/null
> +++ b/gcc/config/i386/usermsrintrin.h
> @@ -0,0 +1,60 @@
> +/* Copyright (C) 2022 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 _X86GPRINTRIN_H_INCLUDED
> +#error "Never use <usermsrintrin.h> directly; include <x86gprintrin.h>
> instead."
> +#endif
> +
> +#ifndef _USER_MSRINTRIN_H_INCLUDED
> +#define _USER_MSRINTRIN_H_INCLUDED
> +
> +#ifdef __x86_64__
> +
> +#ifndef __USER_MSR__
> +#pragma GCC push_options
> +#pragma GCC target("usermsr")
> +#define __DISABLE_USER_MSR__
> +#endif /* __USER_MSR__ */
> +
> +extern __inline unsigned long long
> +__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
> +_urdmsr (unsigned long long __A) {
> +  return (unsigned long long) __builtin_ia32_urdmsr (__A); }
> +
> +extern __inline void
> +__attribute__ ((__gnu_inline__, __always_inline__, __artificial__))
> +_uwrmsr (unsigned long long __A, unsigned long long __B) {
> +  __builtin_ia32_uwrmsr (__A, __B);
> +}
> +
> +#ifdef __DISABLE_USER_MSR__
> +#undef __DISABLE_USER_MSR__
> +#pragma GCC pop_options
> +#endif /* __DISABLE_USER_MSR__ */
> +
> +#endif /* __x86_64__ */
> +
> +#endif /* _USER_MSRINTRIN_H_INCLUDED */
> diff --git a/gcc/config/i386/x86gprintrin.h b/gcc/config/i386/x86gprintrin.h
> index f41be3ffcde..11a8a963020 100644
> --- a/gcc/config/i386/x86gprintrin.h
> +++ b/gcc/config/i386/x86gprintrin.h
> @@ -108,6 +108,8 @@
> 
>  #include <hresetintrin.h>
> 
> +#include <usermsrintrin.h>
> +
>  extern __inline void
>  __attribute__((__gnu_inline__, __always_inline__, __artificial__))  _wbinvd
> (void) diff --git a/gcc/doc/extend.texi b/gcc/doc/extend.texi index
> b82497f00e4..991c2db8eba 100644
> --- a/gcc/doc/extend.texi
> +++ b/gcc/doc/extend.texi
> @@ -7210,6 +7210,11 @@ Enable/disable the generation of the SHA512
> instructions.
>  @itemx no-sm4
>  Enable/disable the generation of the SM4 instructions.
> 
> +@cindex @code{target("umsr")} function attribute, x86 @item umsr @itemx
> +no-umsr Enable/disable the generation of the UMSR instructions.
> +
>  @cindex @code{target("cld")} function attribute, x86  @item cld  @itemx no-
> cld diff --git a/gcc/doc/invoke.texi b/gcc/doc/invoke.texi index
> 7c5f81d9783..3edf41257f1 100644
> --- a/gcc/doc/invoke.texi
> +++ b/gcc/doc/invoke.texi
> @@ -1444,6 +1444,7 @@ See RS/6000 and PowerPC Options.
>  -mamx-tile  -mamx-int8  -mamx-bf16 -muintr -mhreset -mavxvnni
>  -mavx512fp16 -mavxifma -mavxvnniint8 -mavxneconvert -mcmpccxadd -
> mamx-fp16  -mprefetchi -mraoint -mamx-complex -mavxvnniint16 -msm3 -
> msha512 -msm4 -mapxf
> +-mumsr
>  -mcldemote  -mms-bitfields  -mno-align-stringops  -minline-all-stringops  -
> minline-stringops-dynamically  -mstringop-strategy=@var{alg}  -mkl -mwidekl
> @@ -33830,6 +33831,9 @@ preferred alignment to @option{-mpreferred-
> stack-boundary=2}.
>  @need 200
>  @opindex mapxf
>  @itemx -mapxf
> +@need 200
> +@opindex mumsr
> +@itemx -mumsr
>  These switches enable the use of instructions in the MMX, SSE,  AVX512ER,
> AVX512CD, AVX512VL, AVX512BW, AVX512DQ, AVX512IFMA,
> AVX512VBMI, SHA,  AES, PCLMUL, CLFLUSHOPT, CLWB, FSGSBASE, PTWRITE,
> RDRND, F16C, FMA, PCONFIG, @@ -33840,7 +33844,7 @@ GFNI, VAES,
> WAITPKG, VPCLMULQDQ, AVX512BITALG, MOVDIRI, MOVDIR64B,
> AVX512BF16,  ENQCMD, AVX512VPOPCNTDQ, AVX5124FMAPS,
> AVX512VNNI, AVX5124VNNIW, SERIALIZE,  UINTR, HRESET, AMXTILE,
> AMXINT8, AMXBF16, KL, WIDEKL, AVXVNNI, AVX512-FP16,  AVXIFMA,
> AVXVNNIINT8, AVXNECONVERT, CMPCCXADD, AMX-FP16, PREFETCHI,
> RAOINT, -AMX-COMPLEX, AVXVNNIINT16, SM3, SHA512, SM4, APX_F or
> CLDEMOTE extended
> +AMX-COMPLEX, AVXVNNIINT16, SM3, SHA512, SM4, APX_F, UMSR or
> CLDEMOTE
> +extended
>  instruction sets. Each has a corresponding @option{-mno-} option to disable
> use of these instructions.
> 
> diff --git a/gcc/doc/sourcebuild.texi b/gcc/doc/sourcebuild.texi index
> 8bf701461ec..a859bcc53cc 100644
> --- a/gcc/doc/sourcebuild.texi
> +++ b/gcc/doc/sourcebuild.texi
> @@ -2624,6 +2624,9 @@ Test environment appears to run executables on a
> simulator that  accepts only @code{EM_SPARC} executables and chokes on
> @code{EM_SPARC32PLUS}  or @code{EM_SPARCV9} executables.
> 
> +@item umsr
> +Target supports the execution of @code{umsr} instructions.
> +
>  @item vect_cmdline_needed
>  Target requires a command line argument to enable a SIMD instruction set.
> 
> diff --git a/gcc/testsuite/gcc.target/i386/funcspec-56.inc
> b/gcc/testsuite/gcc.target/i386/funcspec-56.inc
> index ca558b3e828..e0470a60483 100644
> --- a/gcc/testsuite/gcc.target/i386/funcspec-56.inc
> +++ b/gcc/testsuite/gcc.target/i386/funcspec-56.inc
> @@ -92,6 +92,7 @@ extern void test_avxvnniint16 (void)
> 	__attribute__((__target__("avxvnniint16"))
>  extern void test_sm3 (void)
> 	__attribute__((__target__("sm3")));
>  extern void test_sha512 (void)
> 	__attribute__((__target__("sha512")));
>  extern void test_sm4 (void)                     __attribute__((__target__("sm4")));
> +extern void test_user_msr (void)
> 	__attribute__((__target__("usermsr")));
> 
>  extern void test_no_sgx (void)
> 	__attribute__((__target__("no-sgx")));
>  extern void test_no_avx5124fmaps(void)
> 	__attribute__((__target__("no-avx5124fmaps")));
> @@ -185,6 +186,7 @@ extern void test_no_avxvnniint16 (void)
> 	__attribute__((__target__("no-avxvnniin
>  extern void test_no_sm3 (void)
> 	__attribute__((__target__("no-sm3")));
>  extern void test_no_sha512 (void)
> 	__attribute__((__target__("no-sha512")));
>  extern void test_no_sm4 (void)                  __attribute__((__target__("no-
> sm4")));
> +extern void test_no_user_msr (void)
> 	__attribute__((__target__("no-usermsr")));
> 
>  extern void test_arch_nocona (void)
> 	__attribute__((__target__("arch=nocona")));
>  extern void test_arch_core2 (void)
> 	__attribute__((__target__("arch=core2")));
> diff --git a/gcc/testsuite/gcc.target/i386/user_msr-1.c
> b/gcc/testsuite/gcc.target/i386/user_msr-1.c
> new file mode 100644
> index 00000000000..447852306df
> --- /dev/null
> +++ b/gcc/testsuite/gcc.target/i386/user_msr-1.c
> @@ -0,0 +1,20 @@
> +/* { dg-do compile { target { ! ia32  }  }  } */
> +/* { dg-options "-musermsr -O2"  } */
> +/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\%r\[a-z\]x,
> +\\%r\[a-z\]x" 1  }  } */
> +/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\\$121" 1  }  } */
> +/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x,
> +\\%r\[a-z\]x" 1  }  } */
> +/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x,
> +\\\$121" 1  }  } */
> +
> +#include <x86gprintrin.h>
> +
> +volatile unsigned long long x;
> +volatile unsigned long long y;
> +
> +void extern
> +user_msr_test (void)
> +{
> +  x = _urdmsr(y);
> +  x = _urdmsr(121);
> +  _uwrmsr(y, x);
> +  _uwrmsr(121, x);
> +}
> diff --git a/gcc/testsuite/gcc.target/i386/user_msr-2.c
> b/gcc/testsuite/gcc.target/i386/user_msr-2.c
> new file mode 100644
> index 00000000000..ab0e76f9088
> --- /dev/null
> +++ b/gcc/testsuite/gcc.target/i386/user_msr-2.c
> @@ -0,0 +1,16 @@
> +/* { dg-do compile { target { ! ia32 } } } */
> +/* { dg-options "-O2 -musermsr" } */
> +/* { dg-final { scan-assembler-times "urdmsr\[ \\t\]\\%r\[a-z\]x,
> +\\%r\[a-z\]x" 1  }  } */
> +/* { dg-final { scan-assembler-times "uwrmsr\[ \\t\]\\%r\[a-z\]x,
> +\\%r\[a-z\]x" 1  }  } */
> +/* { dg-final { scan-assembler-times "movabsq\[
> +\\t\]\\\$20018842566655, \\%r\[a-z\]x" 1  }  } */
> +
> +#include <x86gprintrin.h>
> +
> +volatile unsigned long long x;
> +
> +void extern
> +user_msr_test (void)
> +{
> +  x = _urdmsr(0x1234ffffffffULL);
> +  _uwrmsr(0x1234ffffffffULL, x);
> +}
> diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
> b/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
> index 68da4db4f3c..b9479beef7c 100644
> --- a/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
> +++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-1.c
> @@ -1,7 +1,7 @@
>  /* Test that <x86gprintrin.h> is usable with -O -std=c89 -pedantic-errors.  */
>  /* { dg-do compile } */
>  /* { dg-options "-O -std=c89 -pedantic-errors -march=x86-64 -madx -mbmi -
> mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -mfsgsbase -
> mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -mpopcnt -
> mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -msgx -mshstk
> -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -mxsaveopt -
> mxsaves -mraoint -mno-sse -mno-mmx" } */
> -/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { !
> ia32 } } }  */
> +/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr"
> +{ target { ! ia32 } } }  */
> 
>  #include <x86gprintrin.h>
> 
> diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
> b/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
> index 737c2a26f98..ee167ebab90 100644
> --- a/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
> +++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-2.c
> @@ -1,7 +1,7 @@
>  /* { dg-do compile } */
>  /* { dg-options "-O2 -Werror-implicit-function-declaration -march=x86-64 -
> madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -
> mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -
> mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -
> msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -
> mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
>  /* { dg-add-options bind_pic_locally } */
> -/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { !
> ia32 } } }  */
> +/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr"
> +{ target { ! ia32 } } }  */
> 
>  /* Test that the intrinsics in <x86gprintrin.h> compile with optimization.
>     All of them are defined as inline functions that reference the proper @@ -
> 32,4 +32,8 @@  #define __builtin_ia32_cmpccxadd(A, B, C, D)
> __builtin_ia32_cmpccxadd(A, B, C, 1)  #define __builtin_ia32_cmpccxadd64(A,
> B, C, D) __builtin_ia32_cmpccxadd64(A, B, C, 1)
> 
> +/* usermsrintrin.h */
> +#define __builtin_ia32_urdmsr(A) __builtin_ia32_urdmsr(1) #define
> +__builtin_ia32_uwrmsr(A, B) __builtin_ia32_uwrmsr(1, B)
> +
>  #include <x86gprintrin.h>
> diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
> b/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
> index 52690b1dfb5..a87039149f9 100644
> --- a/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
> +++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-3.c
> @@ -1,7 +1,7 @@
>  /* { dg-do compile } */
>  /* { dg-options "-O0 -Werror-implicit-function-declaration -march=x86-64 -
> madx -mbmi -mbmi2 -mcldemote -mclflushopt -mclwb -mclzero -menqcmd -
> mfsgsbase -mfxsr -mhreset -mlzcnt -mlwp -mmovdiri -mmwaitx -mpconfig -
> mpopcnt -mpku -mptwrite -mrdpid -mrdrnd -mrdseed -mrtm -mserialize -
> msgx -mshstk -mtbm -mtsxldtrk -mwaitpkg -mwbnoinvd -mxsave -mxsavec -
> mxsaveopt -mxsaves -mraoint -mno-sse -mno-mmx" } */
>  /* { dg-add-options bind_pic_locally } */
> -/* { dg-additional-options "-mcmpccxadd -mprefetchi -muintr" { target { !
> ia32 } } }  */
> +/* { dg-additional-options "-musermsr -mcmpccxadd -mprefetchi -muintr"
> +{ target { ! ia32 } } }  */
> 
>  /* Test that the intrinsics in <x86gprintrin.h> compile without optimization.
>     All of them are defined as inline functions that reference the proper @@ -
> 14,3 +14,29 @@  #define __inline
> 
>  #include <x86gprintrin.h>
> +
> +#define _CONCAT(x,y) x ## y
> +
> +#define test_0(func, type, imm)		  \
> +  type _CONCAT(_0,func) (int const I)	  \
> +	    { return func (imm);  }
> +
> +#define test_1(func, type, op1_type)   \
> +  type _CONCAT(_1,func) (op1_type A)    \
> +	{ return func (A); }
> +
> +#define test_1r(func, type, op1_type, imm)	    \
> +  type _CONCAT(_1r,func) (op1_type A, int const I)    \
> +	{ return func (imm, A); }
> +
> +#define test_2(func, type, op1_type,  op2_type)	    \
> +    type _CONCAT(_2,func) (op1_type A, op2_type B)    \
> +      { return func (A, B);  }
> +
> +/* usermsrintrin.h */
> +#ifdef __x86_64__
> +test_0 (_urdmsr, unsigned long long, 1)
> +test_1 (_urdmsr, unsigned long long, unsigned long long) test_1r
> +(_uwrmsr, void, unsigned long long, 1)
> +test_2 (_uwrmsr, void, unsigned long long, unsigned long long) #endif
> diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
> b/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
> index 94cfc583dc9..c3c79473020 100644
> --- a/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
> +++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-4.c
> @@ -13,9 +13,27 @@
>  #define extern
>  #define __inline
> 
> +#define _CONCAT(x,y) x ## y
> +
> +#define test_0(func, type, imm)		  \
> +  type _CONCAT(_0,func) (int const I)	  \
> +	    { return func (imm);  }
> +
> +#define test_1(func, type, op1_type)   \
> +  type _CONCAT(_1,func) (op1_type A)    \
> +	{ return func (A); }
> +
> +#define test_1r(func, type, op1_type, imm)	    \
> +  type _CONCAT(_1r,func) (op1_type A, int const I)    \
> +	{ return func (imm, A); }
> +
> +#define test_2(func, type, op1_type,  op2_type)	    \
> +    type _CONCAT(_2,func) (op1_type A, op2_type B)    \
> +      { return func (A, B);  }
> +
>  #ifndef DIFFERENT_PRAGMAS
>  #ifdef __x86_64__
> -#pragma GCC target
> ("adx,bmi,bmi2,cmpccxadd,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,prefetchi,ra
> oint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,uintr,xsaveopt")
> +#pragma GCC target
> +("adx,bmi,bmi2,cmpccxadd,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,prefetch
> +i,raoint,rdrnd,rdseed,tbm,rtm,serialize,tsxldtrk,uintr,usermsr,xsaveopt
> +")
>  #else
>  #pragma GCC target
> ("adx,bmi,bmi2,fsgsbase,fxsr,hreset,lwp,lzcnt,popcnt,raoint,rdrnd,rdseed,tb
> m,rtm,serialize,tsxldtrk,xsaveopt")
>  #endif
> @@ -29,6 +47,18 @@
> 
>  /* x86intrin.h (LWP/BMI/BMI2/TBM/LZCNT). */  #ifdef DIFFERENT_PRAGMAS
> +#ifdef __x86_64__
> +#pragma GCC target ("lwp,bmi,bmi2,tbm,lzcnt,usermsr")
> +#else
>  #pragma GCC target ("lwp,bmi,bmi2,tbm,lzcnt")  #endif
> +#endif
>  #include <x86gprintrin.h>
> +
> +/* usermsrintrin.h */
> +#ifdef __x86_64__
> +test_0 (_urdmsr, unsigned long long, 1)
> +test_1 (_urdmsr, unsigned long long, unsigned long long) test_1r
> +(_uwrmsr, void, unsigned long long, 1)
> +test_2 (_uwrmsr, void, unsigned long long, unsigned long long) #endif
> diff --git a/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
> b/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
> index 95f3e0a003c..ef126ea76c2 100644
> --- a/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
> +++ b/gcc/testsuite/gcc.target/i386/x86gprintrin-5.c
> @@ -31,8 +31,12 @@
>  #define __builtin_ia32_cmpccxadd(A, B, C, D) __builtin_ia32_cmpccxadd(A, B,
> C, 1)  #define __builtin_ia32_cmpccxadd64(A, B, C, D)
> __builtin_ia32_cmpccxadd64(A, B, C, 1)
> 
> +/* usermsrintrin.h */
> +#define __builtin_ia32_urdmsr(A) __builtin_ia32_urdmsr(1) #define
> +__builtin_ia32_uwrmsr(A, B) __builtin_ia32_uwrmsr(1, B)
> +
>  #ifdef __x86_64__
> -#pragma GCC target
> ("adx,bmi,bmi2,clflushopt,clwb,clzero,cmpccxadd,enqcmd,fsgsbase,fxsr,hrese
> t,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,prefetchi,raoint,rdpid,rdrnd,rdseed,tb
> m,rtm,serialize,sgx,tsxldtrk,uintr,xsavec,xsaveopt,xsaves,wbnoinvd")
> +#pragma GCC target
> +("adx,bmi,bmi2,clflushopt,clwb,clzero,cmpccxadd,enqcmd,fsgsbase,fxsr,hr
> +eset,lwp,lzcnt,mwaitx,pconfig,pku,popcnt,prefetchi,raoint,rdpid,rdrnd,r
> +dseed,tbm,rtm,serialize,sgx,tsxldtrk,uintr,usermsr,xsavec,xsaveopt,xsav
> +es,wbnoinvd")
>  #else
>  #pragma GCC target
> ("adx,bmi,bmi2,clflushopt,clwb,clzero,enqcmd,fsgsbase,fxsr,hreset,lwp,lzcnt,
> mwaitx,pconfig,pku,popcnt,raoint,rdpid,rdrnd,rdseed,tbm,rtm,serialize,sgx,ts
> xldtrk,xsavec,xsaveopt,xsaves,wbnoinvd")
>  #endif
> --
> 2.31.1


^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2023-10-12  1:47 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-10-10  7:46 [PATCH] Support Intel USER_MSR Hu, Lin1
2023-10-10  8:06 ` Hu, Lin1
2023-10-12  1:47   ` Liu, Hongtao

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).