https://github.com/wenju-he created 
https://github.com/llvm/llvm-project/pull/204330

Following 6 OpenCL extensions are promoted to core features in 3.1: 
https://github.com/KhronosGroup/OpenCL-Docs/commit/9fff1a87a975
- cl_khr_extended_bit_ops
- cl_khr_integer_dot_product
- cl_khr_subgroup_extended_types
- cl_khr_subgroup_rotate
- cl_khr_subgroup_shuffle
- cl_khr_subgroup_shuffle_relative

Built-in functions in these extensions are available in OpenCL 3.1 without 
explicitly enabling them via `-cl-ext=+ext`.

Updated release notes for the change.

Assisted-by: Claude

>From f4aa82f80e00592bf7bf4d45e0cdde8f46b62f0e Mon Sep 17 00:00:00 2001
From: Wenju He <[email protected]>
Date: Wed, 17 Jun 2026 12:05:19 +0200
Subject: [PATCH] [Clang][OpenCL] Promote a few extensions to OpenCL 3.1 core

Following 6 OpenCL extensions are promoted to core features in 3.1:
https://github.com/KhronosGroup/OpenCL-Docs/commit/9fff1a87a975
- cl_khr_extended_bit_ops
- cl_khr_integer_dot_product
- cl_khr_subgroup_extended_types
- cl_khr_subgroup_rotate
- cl_khr_subgroup_shuffle
- cl_khr_subgroup_shuffle_relative

Built-in functions in these extensions are available in OpenCL 3.1
without explicitly enabling them via `-cl-ext=+ext`.

Updated release notes for the change.

Assisted-by: Claude
---
 clang/docs/ReleaseNotes.rst                   |  6 +++
 clang/lib/Headers/opencl-c.h                  | 32 +++++++-----
 clang/lib/Sema/OpenCLBuiltins.td              | 21 +++++---
 clang/lib/Sema/SemaLookup.cpp                 | 27 ++++++----
 clang/test/SemaOpenCL/extension-version.cl    |  2 +
 .../SemaOpenCL/fdeclare-opencl-builtins.cl    | 39 ++++++++++++++
 .../TableGen/ClangOpenCLBuiltinEmitter.cpp    | 52 ++++++++++++++-----
 7 files changed, 137 insertions(+), 42 deletions(-)

diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index 89909fe27cbb9..9c33970ac448d 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -825,6 +825,12 @@ OpenACC Specific Changes
 OpenCL Specific Changes
 -----------------------
 - Added support for OpenCL C 3.1 language version (``-cl-std=CL3.1``).
+- Extensions ``cl_khr_extended_bit_ops``, ``cl_khr_integer_dot_product``,
+  ``cl_khr_subgroup_extended_types``, ``cl_khr_subgroup_rotate``,
+  ``cl_khr_subgroup_shuffle``, and ``cl_khr_subgroup_shuffle_relative`` are
+  promoted to core features in OpenCL C 3.1. Built-in functions from these
+  extensions are available in OpenCL C 3.1 without explicitly enabling them via
+  ``-cl-ext=+ext``.
 
 Target Specific Changes
 -----------------------
diff --git a/clang/lib/Headers/opencl-c.h b/clang/lib/Headers/opencl-c.h
index 6d0bf7cb89974..fb84c5223361b 100644
--- a/clang/lib/Headers/opencl-c.h
+++ b/clang/lib/Headers/opencl-c.h
@@ -16439,7 +16439,8 @@ double  __ovld __conv 
sub_group_scan_inclusive_max(double);
 
 #endif // __opencl_subgroup_builtins
 
-#if defined(cl_khr_subgroup_extended_types)
+#if defined(cl_khr_subgroup_extended_types) ||                                 
\
+    (__OPENCL_C_VERSION__ >= CL_VERSION_3_1)
 char __ovld __conv sub_group_broadcast( char value, uint index );
 char2 __ovld __conv sub_group_broadcast( char2 value, uint index );
 char3 __ovld __conv sub_group_broadcast( char3 value, uint index );
@@ -16566,7 +16567,7 @@ double8 __ovld __conv sub_group_broadcast( double8 
value, uint index );
 double16 __ovld __conv sub_group_broadcast( double16 value, uint index );
 #endif  // cl_khr_fp64
 
-#endif  // cl_khr_subgroup_extended_types
+#endif // cl_khr_subgroup_extended_types || CL_VERSION_3_1
 
 #if defined(cl_khr_subgroup_non_uniform_vote)
 int     __ovld sub_group_elect(void);
@@ -16953,7 +16954,7 @@ double  __ovld 
sub_group_non_uniform_scan_exclusive_max( double value );
 
 #endif // cl_khr_subgroup_non_uniform_arithmetic
 
-#if defined(cl_khr_subgroup_shuffle)
+#if defined(cl_khr_subgroup_shuffle) || (__OPENCL_C_VERSION__ >= 
CL_VERSION_3_1)
 char    __ovld sub_group_shuffle( char value, uint index );
 uchar   __ovld sub_group_shuffle( uchar value, uint index );
 short   __ovld sub_group_shuffle( short value, uint index );
@@ -16984,9 +16985,10 @@ double  __ovld sub_group_shuffle( double value, uint 
index );
 double  __ovld sub_group_shuffle_xor( double value, uint mask );
 #endif // cl_khr_fp64
 
-#endif // cl_khr_subgroup_shuffle
+#endif // cl_khr_subgroup_shuffle || CL_VERSION_3_1
 
-#if defined(cl_khr_subgroup_shuffle_relative)
+#if defined(cl_khr_subgroup_shuffle_relative) ||                               
\
+    (__OPENCL_C_VERSION__ >= CL_VERSION_3_1)
 char    __ovld sub_group_shuffle_up( char value, uint delta );
 uchar   __ovld sub_group_shuffle_up( uchar value, uint delta );
 short   __ovld sub_group_shuffle_up( short value, uint delta );
@@ -17017,7 +17019,7 @@ double  __ovld sub_group_shuffle_up( double value, uint 
delta );
 double  __ovld sub_group_shuffle_down( double value, uint delta );
 #endif // cl_khr_fp64
 
-#endif // cl_khr_subgroup_shuffle_relative
+#endif // cl_khr_subgroup_shuffle_relative || CL_VERSION_3_1
 
 #if defined(cl_khr_subgroup_clustered_reduce)
 char    __ovld sub_group_clustered_reduce_add( char value, uint clustersize );
@@ -17107,7 +17109,7 @@ double  __ovld sub_group_clustered_reduce_max( double 
value, uint clustersize );
 
 #endif // cl_khr_subgroup_clustered_reduce
 
-#if defined(cl_khr_extended_bit_ops)
+#if defined(cl_khr_extended_bit_ops) || (__OPENCL_C_VERSION__ >= 
CL_VERSION_3_1)
 char __ovld __cnfn bitfield_insert(char, char, uint, uint);
 uchar __ovld __cnfn bitfield_insert(uchar, uchar, uint, uint);
 short __ovld __cnfn bitfield_insert(short, short, uint, uint);
@@ -17305,9 +17307,10 @@ int16 __ovld __cnfn bit_reverse(int16);
 uint16 __ovld __cnfn bit_reverse(uint16);
 long16 __ovld __cnfn bit_reverse(long16);
 ulong16 __ovld __cnfn bit_reverse(ulong16);
-#endif // cl_khr_extended_bit_ops
+#endif // cl_khr_extended_bit_ops || CL_VERSION_3_1
 
-#if defined(__opencl_c_integer_dot_product_input_4x8bit)
+#if defined(__opencl_c_integer_dot_product_input_4x8bit) ||                    
\
+    (__OPENCL_C_VERSION__ >= CL_VERSION_3_1)
 uint __ovld __cnfn dot(uchar4, uchar4);
 int __ovld __cnfn dot(char4, char4);
 int __ovld __cnfn dot(uchar4, char4);
@@ -17317,9 +17320,10 @@ uint __ovld __cnfn dot_acc_sat(uchar4, uchar4, uint);
 int __ovld __cnfn dot_acc_sat(char4, char4, int);
 int __ovld __cnfn dot_acc_sat(uchar4, char4, int);
 int __ovld __cnfn dot_acc_sat(char4, uchar4, int);
-#endif // __opencl_c_integer_dot_product_input_4x8bit
+#endif // __opencl_c_integer_dot_product_input_4x8bit || CL_VERSION_3_1
 
-#if defined(__opencl_c_integer_dot_product_input_4x8bit_packed)
+#if defined(__opencl_c_integer_dot_product_input_4x8bit_packed) ||             
\
+    (__OPENCL_C_VERSION__ >= CL_VERSION_3_1)
 uint __ovld __cnfn dot_4x8packed_uu_uint(uint, uint);
 int __ovld __cnfn dot_4x8packed_ss_int(uint, uint);
 int __ovld __cnfn dot_4x8packed_us_int(uint, uint);
@@ -17329,9 +17333,9 @@ uint __ovld __cnfn dot_acc_sat_4x8packed_uu_uint(uint, 
uint, uint);
 int __ovld __cnfn dot_acc_sat_4x8packed_ss_int(uint, uint, int);
 int __ovld __cnfn dot_acc_sat_4x8packed_us_int(uint, uint, int);
 int __ovld __cnfn dot_acc_sat_4x8packed_su_int(uint, uint, int);
-#endif // __opencl_c_integer_dot_product_input_4x8bit_packed
+#endif // __opencl_c_integer_dot_product_input_4x8bit_packed || CL_VERSION_3_1
 
-#if defined(cl_khr_subgroup_rotate)
+#if defined(cl_khr_subgroup_rotate) || (__OPENCL_C_VERSION__ >= CL_VERSION_3_1)
 char __ovld __conv sub_group_rotate(char, int);
 uchar __ovld __conv sub_group_rotate(uchar, int);
 short __ovld __conv sub_group_rotate(short, int);
@@ -17363,7 +17367,7 @@ double __ovld __conv sub_group_clustered_rotate(double, 
int, uint);
 #if defined(cl_khr_fp16)
 half __ovld __conv sub_group_clustered_rotate(half, int, uint);
 #endif // cl_khr_fp16
-#endif // cl_khr_subgroup_rotate
+#endif // cl_khr_subgroup_rotate || CL_VERSION_3_1
 
 #if defined(cl_khr_kernel_clock)
 #if defined(__opencl_c_kernel_clock_scope_device)
diff --git a/clang/lib/Sema/OpenCLBuiltins.td b/clang/lib/Sema/OpenCLBuiltins.td
index 761c9771b0891..273bcf2704bc1 100644
--- a/clang/lib/Sema/OpenCLBuiltins.td
+++ b/clang/lib/Sema/OpenCLBuiltins.td
@@ -27,6 +27,8 @@ def CL10  : Version<100>;
 def CL11  : Version<110>;
 def CL12  : Version<120>;
 def CL20  : Version<200>;
+def CL30  : Version<300>;
+def CL31  : Version<310>;
 
 // Address spaces
 // Pointer types need to be assigned an address space.
@@ -337,6 +339,11 @@ class Builtin<string _Name, list<Type> _Signature, 
list<bit> _Attributes = Attr.
   // MaxVersion is exclusive.
   // CLAll makes the function available for all versions.
   Version MaxVersion = CLAll;
+  // If the function belongs to an extension that was promoted to core in a 
later
+  // OpenCL version, set CoreMinVersion to that version so the function is also
+  // available without the extension macro from that version on.
+  // CLAll (the default) means no such promotion applies.
+  Version CoreMinVersion = CLAll;
 }
 
 
//===----------------------------------------------------------------------===//
@@ -1759,7 +1766,7 @@ let Extension = FuncExtKhrSubgroups in {
 // OpenCL Extension v3.0 s38 - Extended Subgroup Functions
 
 // Section 38.4.1 - cl_khr_subgroup_extended_types
-let Extension = FuncExtKhrSubgroupExtendedTypes in {
+let Extension = FuncExtKhrSubgroupExtendedTypes, CoreMinVersion = CL31 in {
   // For sub_group_broadcast, add scalar char, uchar, short, and ushort 
support,
   def : Builtin<"sub_group_broadcast", [CharShortGenType1, CharShortGenType1, 
UInt], Attr.Convergent>;
   // gentype may additionally be one of the supported built-in vector data 
types.
@@ -1815,13 +1822,13 @@ let Extension = FuncExtKhrSubgroupNonUniformArithmetic 
in {
 }
 
 // Section 38.8.1 - cl_khr_subgroup_shuffle
-let Extension = FuncExtKhrSubgroupShuffle in {
+let Extension = FuncExtKhrSubgroupShuffle, CoreMinVersion = CL31 in {
   def : Builtin<"sub_group_shuffle", [AGenType1, AGenType1, UInt]>;
   def : Builtin<"sub_group_shuffle_xor", [AGenType1, AGenType1, UInt]>;
 }
 
 // Section 38.9.1 - cl_khr_subgroup_shuffle_relative
-let Extension = FuncExtKhrSubgroupShuffleRelative in {
+let Extension = FuncExtKhrSubgroupShuffleRelative, CoreMinVersion = CL31 in {
   def : Builtin<"sub_group_shuffle_up", [AGenType1, AGenType1, UInt]>;
   def : Builtin<"sub_group_shuffle_down", [AGenType1, AGenType1, UInt]>;
 }
@@ -1840,7 +1847,7 @@ let Extension = FuncExtKhrSubgroupClusteredReduce in {
 }
 
 // Section 40.3.1 - cl_khr_extended_bit_ops
-let Extension = FuncExtKhrExtendedBitOps in {
+let Extension = FuncExtKhrExtendedBitOps, CoreMinVersion = CL31 in {
   def : Builtin<"bitfield_insert", [AIGenTypeN, AIGenTypeN, AIGenTypeN, UInt, 
UInt], Attr.Const>;
   def : Builtin<"bitfield_extract_signed", [SGenTypeN, SGenTypeN, UInt, UInt], 
Attr.Const>;
   def : Builtin<"bitfield_extract_signed", [SGenTypeN, UGenTypeN, UInt, UInt], 
Attr.Const>;
@@ -1850,7 +1857,7 @@ let Extension = FuncExtKhrExtendedBitOps in {
 }
 
 // Section 42.3 - cl_khr_integer_dot_product
-let Extension = 
FunctionExtension<"__opencl_c_integer_dot_product_input_4x8bit"> in {
+let Extension = 
FunctionExtension<"__opencl_c_integer_dot_product_input_4x8bit">, 
CoreMinVersion = CL31 in {
   def : Builtin<"dot", [UInt, VectorType<UChar, 4>, VectorType<UChar, 4>], 
Attr.Const>;
   def : Builtin<"dot", [Int, VectorType<Char, 4>, VectorType<Char, 4>], 
Attr.Const>;
   def : Builtin<"dot", [Int, VectorType<UChar, 4>, VectorType<Char, 4>], 
Attr.Const>;
@@ -1862,7 +1869,7 @@ let Extension = 
FunctionExtension<"__opencl_c_integer_dot_product_input_4x8bit">
   def : Builtin<"dot_acc_sat", [Int, VectorType<Char, 4>, VectorType<UChar, 
4>, Int], Attr.Const>;
 }
 
-let Extension = 
FunctionExtension<"__opencl_c_integer_dot_product_input_4x8bit_packed"> in {
+let Extension = 
FunctionExtension<"__opencl_c_integer_dot_product_input_4x8bit_packed">, 
CoreMinVersion = CL31 in {
   def : Builtin<"dot_4x8packed_uu_uint", [UInt, UInt, UInt], Attr.Const>;
   def : Builtin<"dot_4x8packed_ss_int", [Int, UInt, UInt], Attr.Const>;
   def : Builtin<"dot_4x8packed_us_int", [Int, UInt, UInt], Attr.Const>;
@@ -1875,7 +1882,7 @@ let Extension = 
FunctionExtension<"__opencl_c_integer_dot_product_input_4x8bit_p
 }
 
 // Section 48.3 - cl_khr_subgroup_rotate
-let Extension = FunctionExtension<"cl_khr_subgroup_rotate"> in {
+let Extension = FunctionExtension<"cl_khr_subgroup_rotate">, CoreMinVersion = 
CL31 in {
   def : Builtin<"sub_group_rotate", [AGenType1, AGenType1, Int], 
Attr.Convergent>;
   def : Builtin<"sub_group_clustered_rotate", [AGenType1, AGenType1, Int, 
UInt], Attr.Convergent>;
 }
diff --git a/clang/lib/Sema/SemaLookup.cpp b/clang/lib/Sema/SemaLookup.cpp
index 65b60964d1192..30996984e7a68 100644
--- a/clang/lib/Sema/SemaLookup.cpp
+++ b/clang/lib/Sema/SemaLookup.cpp
@@ -844,19 +844,28 @@ static void InsertOCLBuiltinDeclarationsFromTable(Sema 
&S, LookupResult &LR,
     // Ignore this builtin function if it carries an extension macro that is
     // not defined. This indicates that the extension is not supported by the
     // target, so the builtin function should not be available.
+    // Exception: if CoreVersions is set and the current OpenCL version is
+    // greater than or equal to the value, the builtin is available as core
+    // regardless of whether the extension macro is defined.
     StringRef Extensions = FunctionExtensionTable[OpenCLBuiltin.Extension];
     if (!Extensions.empty()) {
-      SmallVector<StringRef, 2> ExtVec;
-      Extensions.split(ExtVec, " ");
-      bool AllExtensionsDefined = true;
-      for (StringRef Ext : ExtVec) {
-        if (!S.getPreprocessor().isMacroDefined(Ext)) {
-          AllExtensionsDefined = false;
-          break;
+      bool AvailableAsCore =
+          OpenCLBuiltin.CoreVersions &&
+          isOpenCLVersionContainedInMask(Context.getLangOpts(),
+                                         OpenCLBuiltin.CoreVersions);
+      if (!AvailableAsCore) {
+        SmallVector<StringRef, 2> ExtVec;
+        Extensions.split(ExtVec, " ");
+        bool AllExtensionsDefined = true;
+        for (StringRef Ext : ExtVec) {
+          if (!S.getPreprocessor().isMacroDefined(Ext)) {
+            AllExtensionsDefined = false;
+            break;
+          }
         }
+        if (!AllExtensionsDefined)
+          continue;
       }
-      if (!AllExtensionsDefined)
-        continue;
     }
 
     SmallVector<QualType, 1> RetTypes;
diff --git a/clang/test/SemaOpenCL/extension-version.cl 
b/clang/test/SemaOpenCL/extension-version.cl
index a02dbb93a535d..ee53b345a7eb2 100644
--- a/clang/test/SemaOpenCL/extension-version.cl
+++ b/clang/test/SemaOpenCL/extension-version.cl
@@ -4,12 +4,14 @@
 // RUN: %clang_cc1 -x cl -cl-std=CL2.0 %s -verify -triple spir-unknown-unknown
 // RUN: %clang_cc1 -x cl -cl-std=clc++ %s -verify -triple spir-unknown-unknown
 // RUN: %clang_cc1 -x cl -cl-std=CL3.0 %s -verify -triple spir-unknown-unknown
+// RUN: %clang_cc1 -x cl -cl-std=CL3.1 %s -verify -triple spir-unknown-unknown
 // RUN: %clang_cc1 -x cl -cl-std=CL %s -verify -triple spir-unknown-unknown 
-Wpedantic-core-features -DTEST_CORE_FEATURES
 // RUN: %clang_cc1 -x cl -cl-std=CL1.1 %s -verify -triple spir-unknown-unknown 
-Wpedantic-core-features -DTEST_CORE_FEATURES
 // RUN: %clang_cc1 -x cl -cl-std=CL1.2 %s -verify -triple spir-unknown-unknown 
-Wpedantic-core-features -DTEST_CORE_FEATURES
 // RUN: %clang_cc1 -x cl -cl-std=CL2.0 %s -verify -triple spir-unknown-unknown 
-Wpedantic-core-features -DTEST_CORE_FEATURES
 // RUN: %clang_cc1 -x cl -cl-std=clc++ %s -verify -triple spir-unknown-unknown 
-Wpedantic-core-features -DTEST_CORE_FEATURES
 // RUN: %clang_cc1 -x cl -cl-std=CL3.0 %s -verify -triple spir-unknown-unknown 
-Wpedantic-core-features -DTEST_CORE_FEATURES
+// RUN: %clang_cc1 -x cl -cl-std=CL3.1 %s -verify -triple spir-unknown-unknown 
-Wpedantic-core-features -DTEST_CORE_FEATURES
 
 // Extensions in all versions
 #ifndef cl_clang_storage_class_specifiers
diff --git a/clang/test/SemaOpenCL/fdeclare-opencl-builtins.cl 
b/clang/test/SemaOpenCL/fdeclare-opencl-builtins.cl
index 1fb2579bdc483..0b0cca5dbe2de 100644
--- a/clang/test/SemaOpenCL/fdeclare-opencl-builtins.cl
+++ b/clang/test/SemaOpenCL/fdeclare-opencl-builtins.cl
@@ -5,11 +5,15 @@
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL2.0 -fdeclare-opencl-builtins -DNO_HEADER
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL2.0 -fdeclare-opencl-builtins -finclude-default-header
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL3.0 -fdeclare-opencl-builtins -finclude-default-header
+// RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL3.1 -fdeclare-opencl-builtins -finclude-default-header
+// RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL3.1 -fdeclare-opencl-builtins -DNO_HEADER
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CLC++ -fdeclare-opencl-builtins -DNO_HEADER
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CLC++ -fdeclare-opencl-builtins -finclude-default-header
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CLC++2021 -fdeclare-opencl-builtins 
-finclude-default-header
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL2.0 -fdeclare-opencl-builtins -finclude-default-header 
-cl-ext=-cl_khr_fp64 -DNO_FP64
 // RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL3.0 -fdeclare-opencl-builtins -finclude-default-header 
-DNO_ATOMSCOPE
+// RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL3.0 -fdeclare-opencl-builtins -finclude-default-header 
-DTEST_3_1_CORE_EXT -DNO_3_1_BUILTIN
+// RUN: %clang_cc1 %s -triple spir -verify -pedantic -Wconversion -Werror 
-fsyntax-only -cl-std=CL3.1 -fdeclare-opencl-builtins -finclude-default-header 
-DTEST_3_1_CORE_EXT
 
 // Test the -fdeclare-opencl-builtins option.  This is not a completeness
 // test, so it should not test for all builtins defined by OpenCL.  Instead
@@ -551,3 +555,38 @@ void test_extension_types(char2 c2) {
   // expected-note@-3 6 {{candidate function not viable: no known conversion 
from '__private char2' (vector of 2 'char' values) to 'half}}
 }
 #endif
+
+// Test builtins from extensions promoted to OpenCL 3.1 core.
+#ifdef TEST_3_1_CORE_EXT
+#undef cl_khr_extended_bit_ops
+#undef cl_khr_subgroup_rotate
+#undef cl_khr_subgroup_shuffle
+#undef cl_khr_subgroup_shuffle_relative
+#undef cl_khr_subgroup_extended_types
+#undef __opencl_c_integer_dot_product_input_4x8bit
+#undef __opencl_c_integer_dot_product_input_4x8bit_packed
+
+kernel void test_core_builtins(int i, char c, uchar4 uc4, char4 c4, uint u1) {
+  int x = bitfield_insert(i, i, 0u, 8u);      // cl_khr_extended_bit_ops
+  uint u2 = dot_acc_sat(uc4, uc4, u1);              // 
cl_khr_integer_dot_product (4x8bit)
+  u2 = dot_4x8packed_uu_uint(u1, u1);          // cl_khr_integer_dot_product 
(4x8bit_packed)
+  x = sub_group_broadcast((char2)c, 0u).x;    // cl_khr_subgroup_extended_types
+  x = sub_group_rotate(i, 1);                 // cl_khr_subgroup_rotate
+  x = sub_group_shuffle(i, 0u);               // cl_khr_subgroup_shuffle
+  x = sub_group_shuffle_xor(i, 1u);           // cl_khr_subgroup_shuffle
+  x = sub_group_shuffle_up(i, 1u);            // 
cl_khr_subgroup_shuffle_relative
+  x = sub_group_shuffle_down(i, 1u);          // 
cl_khr_subgroup_shuffle_relative
+#ifdef NO_3_1_BUILTIN
+// expected-error@-10{{use of undeclared identifier 'bitfield_insert'}}
+// expected-error@-10{{use of undeclared identifier 'dot_acc_sat'}}
+// expected-error@-10{{use of undeclared identifier 'dot_4x8packed_uu_uint'}}
+// expected-error@-10{{no matching function for call to 'sub_group_broadcast'}}
+// expected-note@-11 0+{{candidate function not viable}}
+// expected-error@-11{{use of undeclared identifier 'sub_group_rotate'}}
+// expected-error@-11{{use of undeclared identifier 'sub_group_shuffle'}}
+// expected-error@-11{{use of undeclared identifier 'sub_group_shuffle_xor'}}
+// expected-error@-11{{use of undeclared identifier 'sub_group_shuffle_up'}}
+// expected-error@-11{{use of undeclared identifier 'sub_group_shuffle_down'}}
+#endif
+}
+#endif // TEST_3_1_CORE_EXT
diff --git a/clang/utils/TableGen/ClangOpenCLBuiltinEmitter.cpp 
b/clang/utils/TableGen/ClangOpenCLBuiltinEmitter.cpp
index a666dd1ed795d..89feefa2b293a 100644
--- a/clang/utils/TableGen/ClangOpenCLBuiltinEmitter.cpp
+++ b/clang/utils/TableGen/ClangOpenCLBuiltinEmitter.cpp
@@ -446,6 +446,9 @@ struct OpenCLBuiltinStruct {
   const unsigned short Extension;
   // OpenCL versions in which this overload is available.
   const unsigned short Versions;
+  // OpenCL versions in which this overload is available as core
+  // (i.e. without requiring the extension macro). Zero means not promoted.
+  const unsigned short CoreVersions;
 };
 
 )";
@@ -632,6 +635,8 @@ void BuiltinNameEmitter::EmitBuiltinTable() {
           Overload.first->getValueAsDef("MinVersion")->getValueAsInt("ID");
       unsigned int MaxVersion =
           Overload.first->getValueAsDef("MaxVersion")->getValueAsInt("ID");
+      unsigned int CoreMinVersion =
+          Overload.first->getValueAsDef("CoreMinVersion")->getValueAsInt("ID");
 
       OS << "  { " << Overload.second << ", "
          << Overload.first->getValueAsListOfDefs("Signature").size() << ", "
@@ -639,7 +644,8 @@ void BuiltinNameEmitter::EmitBuiltinTable() {
          << (Overload.first->getValueAsBit("IsConst")) << ", "
          << (Overload.first->getValueAsBit("IsConv")) << ", "
          << FunctionExtensionIndex[ExtName] << ", "
-         << EncodeVersions(MinVersion, MaxVersion) << " },\n";
+         << EncodeVersions(MinVersion, MaxVersion) << ", "
+         << (CoreMinVersion ? EncodeVersions(CoreMinVersion, 0) : 0) << " 
},\n";
       Index++;
     }
   }
@@ -664,6 +670,8 @@ bool BuiltinNameEmitter::CanReuseSignature(
             Rec2->getValueAsDef("MinVersion")->getValueAsInt("ID") &&
         Rec->getValueAsDef("MaxVersion")->getValueAsInt("ID") ==
             Rec2->getValueAsDef("MaxVersion")->getValueAsInt("ID") &&
+        Rec->getValueAsDef("CoreMinVersion")->getValueAsInt("ID") ==
+            Rec2->getValueAsDef("CoreMinVersion")->getValueAsInt("ID") &&
         Rec->getValueAsDef("Extension")->getName() ==
             Rec2->getValueAsDef("Extension")->getName()) {
       return true;
@@ -1123,19 +1131,39 @@ OpenCLBuiltinFileEmitterBase::emitExtensionGuard(const 
Record *Builtin) {
   if (Extensions.empty())
     return "";
 
-  OS << "#if";
-
-  SmallVector<StringRef, 2> ExtVec;
-  Extensions.split(ExtVec, " ");
-  bool isFirst = true;
-  for (StringRef Ext : ExtVec) {
-    if (!isFirst) {
-      OS << " &&";
+  int CoreMinVersion =
+      Builtin->getValueAsDef("CoreMinVersion")->getValueAsInt("ID");
+
+  // If this extension was promoted to core, guard as:
+  //   #if defined(EXT) || __OPENCL_C_VERSION__ >= CORE_VERSION
+  // Otherwise guard as:
+  //   #if defined(EXT0) && defined(EXT1) && ...
+  if (CoreMinVersion) {
+    SmallVector<StringRef, 2> ExtVec;
+    Extensions.split(ExtVec, " ");
+    OS << "#if (";
+    bool isFirst = true;
+    for (StringRef Ext : ExtVec) {
+      if (!isFirst)
+        OS << " && ";
+      OS << "defined(" << Ext << ")";
+      isFirst = false;
     }
-    OS << " defined(" << Ext << ")";
-    isFirst = false;
+    OS << ") || (__OPENCL_C_VERSION__ >= CL_VERSION_" << (CoreMinVersion / 100)
+       << "_" << ((CoreMinVersion % 100) / 10) << ")\n";
+  } else {
+    OS << "#if";
+    SmallVector<StringRef, 2> ExtVec;
+    Extensions.split(ExtVec, " ");
+    bool isFirst = true;
+    for (StringRef Ext : ExtVec) {
+      if (!isFirst)
+        OS << " &&";
+      OS << " defined(" << Ext << ")";
+      isFirst = false;
+    }
+    OS << "\n";
   }
-  OS << "\n";
 
   return "#endif // Extension\n";
 }

_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to