xref: /freebsd/contrib/llvm-project/clang/lib/Sema/OpenCLBuiltins.td (revision dc318a4ffabcbfa23bb56a33403aad36e6de30af)
1//==--- OpenCLBuiltins.td - OpenCL builtin declarations -------------------===//
2//
3//                     The LLVM Compiler Infrastructure
4//
5// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
6// See https://llvm.org/LICENSE.txt for license information.
7// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
8//
9//===----------------------------------------------------------------------===//
10//
11// This file contains TableGen definitions for OpenCL builtin function
12// declarations.  In case of an unresolved function name in OpenCL, Clang will
13// check for a function described in this file when -fdeclare-opencl-builtins
14// is specified.
15//
16//===----------------------------------------------------------------------===//
17
18//===----------------------------------------------------------------------===//
19//              Definitions of miscellaneous basic entities.
20//===----------------------------------------------------------------------===//
21// Versions of OpenCL
22class Version<int _Version> {
23  int ID = _Version;
24}
25def CLAll : Version<  0>;
26def CL10  : Version<100>;
27def CL11  : Version<110>;
28def CL12  : Version<120>;
29def CL20  : Version<200>;
30
31// Address spaces
32// Pointer types need to be assigned an address space.
33class AddressSpace<string _AS> {
34  string Name = _AS;
35}
36def DefaultAS    : AddressSpace<"clang::LangAS::Default">;
37def PrivateAS    : AddressSpace<"clang::LangAS::opencl_private">;
38def GlobalAS     : AddressSpace<"clang::LangAS::opencl_global">;
39def ConstantAS   : AddressSpace<"clang::LangAS::opencl_constant">;
40def LocalAS      : AddressSpace<"clang::LangAS::opencl_local">;
41def GenericAS    : AddressSpace<"clang::LangAS::opencl_generic">;
42
43// OpenCL language extension.
44class AbstractExtension<string _Ext> {
45  // One or more OpenCL extensions, space separated.  Each extension must be
46  // a valid extension name for the opencl extension pragma.
47  string ExtName = _Ext;
48}
49
50// Extension associated to a builtin function.
51class FunctionExtension<string _Ext> : AbstractExtension<_Ext>;
52
53// FunctionExtension definitions.
54def FuncExtNone                          : FunctionExtension<"">;
55def FuncExtKhrSubgroups                  : FunctionExtension<"cl_khr_subgroups">;
56def FuncExtKhrGlobalInt32BaseAtomics     : FunctionExtension<"cl_khr_global_int32_base_atomics">;
57def FuncExtKhrGlobalInt32ExtendedAtomics : FunctionExtension<"cl_khr_global_int32_extended_atomics">;
58def FuncExtKhrLocalInt32BaseAtomics      : FunctionExtension<"cl_khr_local_int32_base_atomics">;
59def FuncExtKhrLocalInt32ExtendedAtomics  : FunctionExtension<"cl_khr_local_int32_extended_atomics">;
60def FuncExtKhrInt64BaseAtomics           : FunctionExtension<"cl_khr_int64_base_atomics">;
61def FuncExtKhrInt64ExtendedAtomics       : FunctionExtension<"cl_khr_int64_extended_atomics">;
62def FuncExtKhrMipmapImage                : FunctionExtension<"cl_khr_mipmap_image">;
63def FuncExtKhrMipmapImageWrites          : FunctionExtension<"cl_khr_mipmap_image_writes">;
64def FuncExtKhrGlMsaaSharing              : FunctionExtension<"cl_khr_gl_msaa_sharing">;
65
66// Multiple extensions
67def FuncExtKhrMipmapWritesAndWrite3d     : FunctionExtension<"cl_khr_mipmap_image_writes cl_khr_3d_image_writes">;
68
69// Arm extensions.
70def ArmIntegerDotProductInt8                   : FunctionExtension<"cl_arm_integer_dot_product_int8">;
71def ArmIntegerDotProductAccumulateInt8         : FunctionExtension<"cl_arm_integer_dot_product_accumulate_int8">;
72def ArmIntegerDotProductAccumulateInt16        : FunctionExtension<"cl_arm_integer_dot_product_accumulate_int16">;
73def ArmIntegerDotProductAccumulateSaturateInt8 : FunctionExtension<"cl_arm_integer_dot_product_accumulate_saturate_int8">;
74
75// Qualified Type.  These map to ASTContext::QualType.
76class QualType<string _Name, bit _IsAbstract=0> {
77  // Name of the field or function in a clang::ASTContext
78  // E.g. Name="IntTy" for the int type, and "getIntPtrType()" for an intptr_t
79  string Name = _Name;
80  // Some QualTypes in this file represent an abstract type for which there is
81  // no corresponding AST QualType, e.g. a GenType or an `image2d_t` type
82  // without access qualifiers.
83  bit IsAbstract = _IsAbstract;
84}
85
86// List of integers.
87class IntList<string _Name, list<int> _List> {
88  string Name = _Name;
89  list<int> List = _List;
90}
91
92//===----------------------------------------------------------------------===//
93//                      OpenCL C classes for types
94//===----------------------------------------------------------------------===//
95// OpenCL C basic data types (int, float, image2d_t, ...).
96// Its child classes can represent concrete types (e.g. VectorType) or
97// abstract types (e.g. GenType).
98class Type<string _Name, QualType _QTName> {
99  // Name of the Type.
100  string Name = _Name;
101  // QualType associated with this type.
102  QualType QTName = _QTName;
103  // Size of the vector (if applicable).
104  int VecWidth = 1;
105  // Is a pointer.
106  bit IsPointer = 0;
107  // "const" qualifier.
108  bit IsConst = 0;
109  // "volatile" qualifier.
110  bit IsVolatile = 0;
111  // Access qualifier. Must be one of ("RO", "WO", "RW").
112  string AccessQualifier = "";
113  // Address space.
114  string AddrSpace = DefaultAS.Name;
115}
116
117// OpenCL vector types (e.g. int2, int3, int16, float8, ...).
118class VectorType<Type _Ty, int _VecWidth> : Type<_Ty.Name, _Ty.QTName> {
119  let VecWidth = _VecWidth;
120  let AccessQualifier = "";
121  // Inherited fields
122  let IsPointer = _Ty.IsPointer;
123  let IsConst = _Ty.IsConst;
124  let IsVolatile = _Ty.IsVolatile;
125  let AddrSpace = _Ty.AddrSpace;
126}
127
128// OpenCL pointer types (e.g. int*, float*, ...).
129class PointerType<Type _Ty, AddressSpace _AS = DefaultAS> :
130    Type<_Ty.Name, _Ty.QTName> {
131  let AddrSpace = _AS.Name;
132  // Inherited fields
133  let VecWidth = _Ty.VecWidth;
134  let IsPointer = 1;
135  let IsConst = _Ty.IsConst;
136  let IsVolatile = _Ty.IsVolatile;
137  let AccessQualifier = _Ty.AccessQualifier;
138}
139
140// OpenCL const types (e.g. const int).
141class ConstType<Type _Ty> : Type<_Ty.Name, _Ty.QTName> {
142  let IsConst = 1;
143  // Inherited fields
144  let VecWidth = _Ty.VecWidth;
145  let IsPointer = _Ty.IsPointer;
146  let IsVolatile = _Ty.IsVolatile;
147  let AccessQualifier = _Ty.AccessQualifier;
148  let AddrSpace = _Ty.AddrSpace;
149}
150
151// OpenCL volatile types (e.g. volatile int).
152class VolatileType<Type _Ty> : Type<_Ty.Name, _Ty.QTName> {
153  let IsVolatile = 1;
154  // Inherited fields
155  let VecWidth = _Ty.VecWidth;
156  let IsPointer = _Ty.IsPointer;
157  let IsConst = _Ty.IsConst;
158  let AccessQualifier = _Ty.AccessQualifier;
159  let AddrSpace = _Ty.AddrSpace;
160}
161
162// OpenCL image types (e.g. image2d).
163class ImageType<Type _Ty, string _AccessQualifier> :
164    Type<_Ty.Name, QualType<_Ty.QTName.Name#_AccessQualifier#"Ty", 0>> {
165  let VecWidth = 0;
166  let AccessQualifier = _AccessQualifier;
167  // Inherited fields
168  let IsPointer = _Ty.IsPointer;
169  let IsConst = _Ty.IsConst;
170  let IsVolatile = _Ty.IsVolatile;
171  let AddrSpace = _Ty.AddrSpace;
172}
173
174// List of Types.
175class TypeList<list<Type> _Type> {
176  list<Type> List = _Type;
177}
178
179// A GenericType is an abstract type that defines a set of types as a
180// combination of Types and vector sizes.
181//
182// For example, if TypeList = <int, float> and VectorList = <1, 2, 4>, then it
183// represents <int, int2, int4, float, float2, float4>.
184//
185// Some rules apply when using multiple GenericType arguments in a declaration:
186//   1. The number of vector sizes must be equal or 1 for all gentypes in a
187//      declaration.
188//   2. The number of Types must be equal or 1 for all gentypes in a
189//      declaration.
190//   3. Generic types are combined by iterating over all generic types at once.
191//      For example, for the following GenericTypes
192//        GenT1 = GenericType<half, [1, 2]> and
193//        GenT2 = GenericType<float, int, [1, 2]>
194//      A declaration f(GenT1, GenT2) results in the combinations
195//        f(half, float), f(half2, float2), f(half, int), f(half2, int2) .
196//   4. "sgentype" from the OpenCL specification is supported by specifying
197//      a single vector size.
198//      For example, for the following GenericTypes
199//        GenT = GenericType<half, int, [1, 2]> and
200//        SGenT = GenericType<half, int, [1]>
201//      A declaration f(GenT, SGenT) results in the combinations
202//        f(half, half), f(half2, half), f(int, int), f(int2, int) .
203class GenericType<string _Ty, TypeList _TypeList, IntList _VectorList> :
204    Type<_Ty, QualType<"null", 1>> {
205  // Possible element types of the generic type.
206  TypeList TypeList = _TypeList;
207  // Possible vector sizes of the types in the TypeList.
208  IntList VectorList = _VectorList;
209  // The VecWidth field is ignored for GenericTypes. Use VectorList instead.
210  let VecWidth = 0;
211}
212
213// Builtin function attributes.
214def Attr {
215  list<bit> None = [0, 0, 0];
216  list<bit> Pure = [1, 0, 0];
217  list<bit> Const = [0, 1, 0];
218  list<bit> Convergent = [0, 0, 1];
219}
220
221//===----------------------------------------------------------------------===//
222//                      OpenCL C class for builtin functions
223//===----------------------------------------------------------------------===//
224class Builtin<string _Name, list<Type> _Signature, list<bit> _Attributes = Attr.None> {
225  // Name of the builtin function
226  string Name = _Name;
227  // List of types used by the function. The first one is the return type and
228  // the following are the arguments. The list must have at least one element
229  // (the return type).
230  list<Type> Signature = _Signature;
231  // Function attribute __attribute__((pure))
232  bit IsPure = _Attributes[0];
233  // Function attribute __attribute__((const))
234  bit IsConst = _Attributes[1];
235  // Function attribute __attribute__((convergent))
236  bit IsConv = _Attributes[2];
237  // OpenCL extensions to which the function belongs.
238  FunctionExtension Extension = FuncExtNone;
239  // Version of OpenCL from which the function is available (e.g.: CL10).
240  // MinVersion is inclusive.
241  Version MinVersion = CL10;
242  // Version of OpenCL from which the function is not supported anymore.
243  // MaxVersion is exclusive.
244  // CLAll makes the function available for all versions.
245  Version MaxVersion = CLAll;
246}
247
248//===----------------------------------------------------------------------===//
249//                 Definitions of OpenCL C types
250//===----------------------------------------------------------------------===//
251
252// OpenCL v1.0/1.2/2.0 s6.1.1: Built-in Scalar Data Types.
253def Bool      : Type<"bool",      QualType<"BoolTy">>;
254def Char      : Type<"char",      QualType<"CharTy">>;
255def UChar     : Type<"uchar",     QualType<"UnsignedCharTy">>;
256def Short     : Type<"short",     QualType<"ShortTy">>;
257def UShort    : Type<"ushort",    QualType<"UnsignedShortTy">>;
258def Int       : Type<"int",       QualType<"IntTy">>;
259def UInt      : Type<"uint",      QualType<"UnsignedIntTy">>;
260def Long      : Type<"long",      QualType<"LongTy">>;
261def ULong     : Type<"ulong",     QualType<"UnsignedLongTy">>;
262def Float     : Type<"float",     QualType<"FloatTy">>;
263def Double    : Type<"double",    QualType<"DoubleTy">>;
264def Half      : Type<"half",      QualType<"HalfTy">>;
265def Size      : Type<"size_t",    QualType<"getSizeType()">>;
266def PtrDiff   : Type<"ptrdiff_t", QualType<"getPointerDiffType()">>;
267def IntPtr    : Type<"intptr_t",  QualType<"getIntPtrType()">>;
268def UIntPtr   : Type<"uintptr_t", QualType<"getUIntPtrType()">>;
269def Void      : Type<"void",      QualType<"VoidTy">>;
270
271// OpenCL v1.0/1.2/2.0 s6.1.2: Built-in Vector Data Types.
272// Built-in vector data types are created by TableGen's OpenCLBuiltinEmitter.
273
274// OpenCL v1.0/1.2/2.0 s6.1.3: Other Built-in Data Types.
275// The image definitions are "abstract".  They should not be used without
276// specifying an access qualifier (RO/WO/RW).
277def Image1d               : Type<"image1d_t", QualType<"OCLImage1d", 1>>;
278def Image2d               : Type<"image2d_t", QualType<"OCLImage2d", 1>>;
279def Image3d               : Type<"image3d_t", QualType<"OCLImage3d", 1>>;
280def Image1dArray          : Type<"image1d_array_t", QualType<"OCLImage1dArray", 1>>;
281def Image1dBuffer         : Type<"image1d_buffer_t", QualType<"OCLImage1dBuffer", 1>>;
282def Image2dArray          : Type<"image2d_array_t", QualType<"OCLImage2dArray", 1>>;
283def Image2dDepth          : Type<"image2d_depth_t", QualType<"OCLImage2dDepth", 1>>;
284def Image2dArrayDepth     : Type<"image2d_array_depth_t", QualType<"OCLImage2dArrayDepth", 1>>;
285def Image2dMsaa           : Type<"image2d_msaa_t", QualType<"OCLImage2dMSAA", 1>>;
286def Image2dArrayMsaa      : Type<"image2d_array_msaa_t", QualType<"OCLImage2dArrayMSAA", 1>>;
287def Image2dMsaaDepth      : Type<"image2d_msaa_depth_t", QualType<"OCLImage2dMSAADepth", 1>>;
288def Image2dArrayMsaaDepth : Type<"image2d_array_msaa_depth_t", QualType<"OCLImage2dArrayMSAADepth", 1>>;
289
290def Sampler               : Type<"sampler_t", QualType<"OCLSamplerTy">>;
291def ClkEvent              : Type<"clk_event_t", QualType<"OCLClkEventTy">>;
292def Event                 : Type<"event_t", QualType<"OCLEventTy">>;
293def Queue                 : Type<"queue_t", QualType<"OCLQueueTy">>;
294def ReserveId             : Type<"reserve_id_t", QualType<"OCLReserveIDTy">>;
295
296// OpenCL v2.0 s6.13.11: Atomic integer and floating-point types.
297def AtomicInt             : Type<"atomic_int", QualType<"getAtomicType(Context.IntTy)">>;
298def AtomicUInt            : Type<"atomic_uint", QualType<"getAtomicType(Context.UnsignedIntTy)">>;
299def AtomicLong            : Type<"atomic_long", QualType<"getAtomicType(Context.LongTy)">>;
300def AtomicULong           : Type<"atomic_ulong", QualType<"getAtomicType(Context.UnsignedLongTy)">>;
301def AtomicFloat           : Type<"atomic_float", QualType<"getAtomicType(Context.FloatTy)">>;
302def AtomicDouble          : Type<"atomic_double", QualType<"getAtomicType(Context.DoubleTy)">>;
303def AtomicIntPtr          : Type<"atomic_intptr_t", QualType<"getAtomicType(Context.getIntPtrType())">>;
304def AtomicUIntPtr         : Type<"atomic_uintptr_t", QualType<"getAtomicType(Context.getUIntPtrType())">>;
305def AtomicSize            : Type<"atomic_size_t", QualType<"getAtomicType(Context.getSizeType())">>;
306def AtomicPtrDiff         : Type<"atomic_ptrdiff_t", QualType<"getAtomicType(Context.getPointerDiffType())">>;
307
308//===----------------------------------------------------------------------===//
309//                 Definitions of OpenCL gentype variants
310//===----------------------------------------------------------------------===//
311// The OpenCL specification often uses "gentype" in builtin function
312// declarations to indicate that a builtin function is available with various
313// argument and return types.  The types represented by "gentype" vary between
314// different parts of the specification.  The following definitions capture
315// the different type lists for gentypes in different parts of the
316// specification.
317
318// Vector width lists.
319def VecAndScalar: IntList<"VecAndScalar", [1, 2, 3, 4, 8, 16]>;
320def VecNoScalar : IntList<"VecNoScalar", [2, 3, 4, 8, 16]>;
321def Vec1        : IntList<"Vec1", [1]>;
322def Vec2        : IntList<"Vec2", [2]>;
323def Vec4        : IntList<"Vec4", [4]>;
324def Vec8        : IntList<"Vec8", [8]>;
325def Vec16       : IntList<"Vec16", [16]>;
326def Vec1234     : IntList<"Vec1234", [1, 2, 3, 4]>;
327
328// Type lists.
329def TLAll           : TypeList<[Char,  UChar, Short,  UShort, Int,  UInt, Long,  ULong, Float, Double, Half]>;
330def TLAllUnsigned   : TypeList<[UChar, UChar, UShort, UShort, UInt, UInt, ULong, ULong, UInt,  ULong,  UShort]>;
331def TLFloat         : TypeList<[Float, Double, Half]>;
332def TLSignedInts    : TypeList<[Char, Short, Int, Long]>;
333def TLUnsignedInts  : TypeList<[UChar, UShort, UInt, ULong]>;
334
335def TLIntLongFloats : TypeList<[Int, UInt, Long, ULong, Float, Double, Half]>;
336
337// All unsigned integer types twice, to facilitate unsigned return types for e.g.
338// uchar abs(char) and
339// uchar abs(uchar).
340def TLAllUIntsTwice : TypeList<[UChar, UChar, UShort, UShort, UInt, UInt, ULong, ULong]>;
341
342def TLAllInts       : TypeList<[Char, UChar, Short, UShort, Int, UInt, Long, ULong]>;
343
344// GenType definitions for multiple base types (e.g. all floating point types,
345// or all integer types).
346// All types
347def AGenTypeN              : GenericType<"AGenTypeN", TLAll, VecAndScalar>;
348def AGenTypeNNoScalar      : GenericType<"AGenTypeNNoScalar", TLAll, VecNoScalar>;
349// All integer
350def AIGenType1             : GenericType<"AIGenType1", TLAllInts, Vec1>;
351def AIGenTypeN             : GenericType<"AIGenTypeN", TLAllInts, VecAndScalar>;
352def AIGenTypeNNoScalar     : GenericType<"AIGenTypeNNoScalar", TLAllInts, VecNoScalar>;
353// All integer to unsigned
354def AI2UGenTypeN           : GenericType<"AI2UGenTypeN", TLAllUIntsTwice, VecAndScalar>;
355// Signed integer
356def SGenTypeN              : GenericType<"SGenTypeN", TLSignedInts, VecAndScalar>;
357// Unsigned integer
358def UGenTypeN              : GenericType<"UGenTypeN", TLUnsignedInts, VecAndScalar>;
359// Float
360def FGenTypeN              : GenericType<"FGenTypeN", TLFloat, VecAndScalar>;
361// (u)int, (u)long, and all floats
362def IntLongFloatGenType1   : GenericType<"IntLongFloatGenType1", TLIntLongFloats, Vec1>;
363
364// GenType definitions for every single base type (e.g. fp32 only).
365// Names are like: GenTypeFloatVecAndScalar.
366foreach Type = [Char, UChar, Short, UShort,
367                Int, UInt, Long, ULong,
368                Float, Double, Half] in {
369  foreach VecSizes = [VecAndScalar, VecNoScalar] in {
370    def "GenType" # Type # VecSizes :
371              GenericType<"GenType" # Type # VecSizes,
372                          TypeList<[Type]>, VecSizes>;
373  }
374}
375
376// GenType definitions for vec1234.
377foreach Type = [Float, Double, Half] in {
378  def "GenType" # Type # Vec1234 :
379              GenericType<"GenType" # Type # Vec1234,
380                          TypeList<[Type]>, Vec1234>;
381}
382
383
384//===----------------------------------------------------------------------===//
385//                 Definitions of OpenCL builtin functions
386//===----------------------------------------------------------------------===//
387//--------------------------------------------------------------------
388// OpenCL v1.1/1.2/2.0 s6.2.3 - Explicit conversions.
389// OpenCL v2.0 Extensions s5.1.1 and s6.1.1 - Conversions.
390
391// Generate the convert_* builtins functions.
392foreach RType = [Float, Double, Half, Char, UChar, Short,
393                 UShort, Int, UInt, Long, ULong] in {
394  foreach IType = [Float, Double, Half, Char, UChar, Short,
395                   UShort, Int, UInt, Long, ULong] in {
396    // Conversions to integer type have a sat and non-sat variant.
397    foreach sat = !cond(!eq(RType.Name, "float") : [""],
398                        !eq(RType.Name, "double") : [""],
399                        !eq(RType.Name, "half") : [""],
400                        1 : ["", "_sat"]) in {
401      foreach rnd = ["", "_rte", "_rtn", "_rtp", "_rtz"] in {
402        def : Builtin<"convert_" # RType.Name # sat # rnd, [RType, IType],
403                      Attr.Const>;
404        foreach v = [2, 3, 4, 8, 16] in {
405          def : Builtin<"convert_" # RType.Name # v # sat # rnd,
406                        [VectorType<RType, v>, VectorType<IType, v>],
407                        Attr.Const>;
408        }
409      }
410    }
411  }
412}
413
414//--------------------------------------------------------------------
415// OpenCL v1.1 s6.11.1, v1.2 s6.12.1, v2.0 s6.13.1 - Work-item Functions
416// --- Table 7 ---
417def : Builtin<"get_work_dim", [UInt], Attr.Const>;
418foreach name = ["get_global_size", "get_global_id", "get_local_size",
419                "get_local_id", "get_num_groups", "get_group_id",
420                "get_global_offset"] in {
421  def : Builtin<name, [Size, UInt], Attr.Const>;
422}
423
424let MinVersion = CL20 in {
425  def : Builtin<"get_enqueued_local_size", [Size, UInt]>;
426  foreach name = ["get_global_linear_id", "get_local_linear_id"] in {
427    def : Builtin<name, [Size]>;
428  }
429}
430
431
432//--------------------------------------------------------------------
433// OpenCL v1.1 s6.11.2, v1.2 s6.12.2, v2.0 s6.13.2 - Math functions
434// OpenCL Extension v2.0 s5.1.2 and s6.1.2 - Math Functions
435// --- Table 8 ---
436// --- 1 argument ---
437foreach name = ["acos", "acosh", "acospi",
438                "asin", "asinh", "asinpi",
439                "atan", "atanh", "atanpi",
440                "cbrt", "ceil",
441                "cos", "cosh", "cospi",
442                "erfc", "erf",
443                "exp", "exp2", "exp10", "expm1",
444                "fabs", "floor",
445                "log", "log2", "log10", "log1p", "logb",
446                "rint", "round", "rsqrt",
447                "sin", "sinh", "sinpi",
448                "sqrt",
449                "tan", "tanh", "tanpi",
450                "tgamma", "trunc",
451                "lgamma"] in {
452    def : Builtin<name, [FGenTypeN, FGenTypeN], Attr.Const>;
453}
454foreach name = ["nan"] in {
455  def : Builtin<name, [GenTypeFloatVecAndScalar, GenTypeUIntVecAndScalar], Attr.Const>;
456  def : Builtin<name, [GenTypeDoubleVecAndScalar, GenTypeULongVecAndScalar], Attr.Const>;
457  def : Builtin<name, [GenTypeHalfVecAndScalar, GenTypeUShortVecAndScalar], Attr.Const>;
458}
459
460// --- 2 arguments ---
461foreach name = ["atan2", "atan2pi", "copysign", "fdim", "fmod", "hypot",
462                "maxmag", "minmag", "nextafter", "pow", "powr",
463                "remainder"] in {
464  def : Builtin<name, [FGenTypeN, FGenTypeN, FGenTypeN], Attr.Const>;
465}
466foreach name = ["fmax", "fmin"] in {
467  def : Builtin<name, [FGenTypeN, FGenTypeN, FGenTypeN], Attr.Const>;
468  def : Builtin<name, [GenTypeFloatVecNoScalar, GenTypeFloatVecNoScalar, Float], Attr.Const>;
469  def : Builtin<name, [GenTypeDoubleVecNoScalar, GenTypeDoubleVecNoScalar, Double], Attr.Const>;
470  def : Builtin<name, [GenTypeHalfVecNoScalar, GenTypeHalfVecNoScalar, Half], Attr.Const>;
471}
472foreach name = ["ilogb"] in {
473  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeFloatVecAndScalar], Attr.Const>;
474  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeDoubleVecAndScalar], Attr.Const>;
475  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeHalfVecAndScalar], Attr.Const>;
476}
477foreach name = ["ldexp"] in {
478  def : Builtin<name, [GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
479  def : Builtin<name, [GenTypeFloatVecNoScalar, GenTypeFloatVecNoScalar, Int], Attr.Const>;
480  def : Builtin<name, [GenTypeDoubleVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
481  def : Builtin<name, [GenTypeDoubleVecNoScalar, GenTypeDoubleVecNoScalar, Int], Attr.Const>;
482  def : Builtin<name, [GenTypeHalfVecAndScalar, GenTypeHalfVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
483  def : Builtin<name, [GenTypeHalfVecNoScalar, GenTypeHalfVecNoScalar, Int], Attr.Const>;
484}
485foreach name = ["pown", "rootn"] in {
486  def : Builtin<name, [GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
487  def : Builtin<name, [GenTypeDoubleVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
488  def : Builtin<name, [GenTypeHalfVecAndScalar, GenTypeHalfVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
489}
490
491// --- 3 arguments ---
492foreach name = ["fma", "mad"] in {
493  def : Builtin<name, [FGenTypeN, FGenTypeN, FGenTypeN, FGenTypeN], Attr.Const>;
494}
495
496// --- Version dependent ---
497let MaxVersion = CL20 in {
498  foreach AS = [GlobalAS, LocalAS, PrivateAS] in {
499    foreach name = ["fract", "modf", "sincos"] in {
500      def : Builtin<name, [FGenTypeN, FGenTypeN, PointerType<FGenTypeN, AS>]>;
501    }
502    foreach name = ["frexp", "lgamma_r"] in {
503      foreach Type = [GenTypeFloatVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeHalfVecAndScalar] in {
504        def : Builtin<name, [Type, Type, PointerType<GenTypeIntVecAndScalar, AS>]>;
505      }
506    }
507    foreach name = ["remquo"] in {
508      foreach Type = [GenTypeFloatVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeHalfVecAndScalar] in {
509        def : Builtin<name, [Type, Type, Type, PointerType<GenTypeIntVecAndScalar, AS>]>;
510      }
511    }
512  }
513}
514let MinVersion = CL20 in {
515  foreach name = ["fract", "modf", "sincos"] in {
516    def : Builtin<name, [FGenTypeN, FGenTypeN, PointerType<FGenTypeN, GenericAS>]>;
517  }
518  foreach name = ["frexp", "lgamma_r"] in {
519    foreach Type = [GenTypeFloatVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeHalfVecAndScalar] in {
520      def : Builtin<name, [Type, Type, PointerType<GenTypeIntVecAndScalar, GenericAS>]>;
521    }  }
522  foreach name = ["remquo"] in {
523    foreach Type = [GenTypeFloatVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeHalfVecAndScalar] in {
524      def : Builtin<name, [Type, Type, Type, PointerType<GenTypeIntVecAndScalar, GenericAS>]>;
525    }
526  }
527}
528
529// --- Table 9 ---
530foreach name = ["half_cos",
531                "half_exp", "half_exp2", "half_exp10",
532                "half_log", "half_log2", "half_log10",
533                "half_recip", "half_rsqrt",
534                "half_sin", "half_sqrt", "half_tan",
535                "native_cos",
536                "native_exp", "native_exp2", "native_exp10",
537                "native_log", "native_log2", "native_log10",
538                "native_recip", "native_rsqrt",
539                "native_sin", "native_sqrt", "native_tan"] in {
540  def : Builtin<name, [GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar], Attr.Const>;
541}
542foreach name = ["half_divide", "half_powr",
543                "native_divide", "native_powr"] in {
544  def : Builtin<name, [GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar], Attr.Const>;
545}
546
547//--------------------------------------------------------------------
548// OpenCL v1.1 s6.11.3, v1.2 s6.12.3, v2.0 s6.13.3 - Integer Functions
549// --- Table 10 ---
550// --- 1 argument ---
551foreach name = ["abs"] in {
552  def : Builtin<name, [AI2UGenTypeN, AIGenTypeN], Attr.Const>;
553}
554foreach name = ["clz", "popcount"] in {
555  def : Builtin<name, [AIGenTypeN, AIGenTypeN], Attr.Const>;
556}
557let MinVersion = CL20 in {
558  foreach name = ["ctz"] in {
559    def : Builtin<name, [AIGenTypeN, AIGenTypeN]>;
560  }
561}
562
563// --- 2 arguments ---
564foreach name = ["abs_diff"] in {
565  def : Builtin<name, [AI2UGenTypeN, AIGenTypeN, AIGenTypeN], Attr.Const>;
566}
567foreach name = ["add_sat", "hadd", "rhadd", "mul_hi", "rotate", "sub_sat"] in {
568  def : Builtin<name, [AIGenTypeN, AIGenTypeN, AIGenTypeN], Attr.Const>;
569}
570foreach name = ["max", "min"] in {
571  def : Builtin<name, [AIGenTypeN, AIGenTypeN, AIGenTypeN], Attr.Const>;
572  def : Builtin<name, [AIGenTypeNNoScalar, AIGenTypeNNoScalar, AIGenType1], Attr.Const>;
573}
574foreach name = ["upsample"] in {
575  def : Builtin<name, [GenTypeShortVecAndScalar, GenTypeCharVecAndScalar, GenTypeUCharVecAndScalar], Attr.Const>;
576  def : Builtin<name, [GenTypeUShortVecAndScalar, GenTypeUCharVecAndScalar, GenTypeUCharVecAndScalar], Attr.Const>;
577  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeShortVecAndScalar, GenTypeUShortVecAndScalar], Attr.Const>;
578  def : Builtin<name, [GenTypeUIntVecAndScalar, GenTypeUShortVecAndScalar, GenTypeUShortVecAndScalar], Attr.Const>;
579  def : Builtin<name, [GenTypeLongVecAndScalar, GenTypeIntVecAndScalar, GenTypeUIntVecAndScalar], Attr.Const>;
580  def : Builtin<name, [GenTypeULongVecAndScalar, GenTypeUIntVecAndScalar, GenTypeUIntVecAndScalar], Attr.Const>;
581}
582
583// --- 3 arguments ---
584foreach name = ["clamp"] in {
585  def : Builtin<name, [AIGenTypeN, AIGenTypeN, AIGenTypeN, AIGenTypeN], Attr.Const>;
586  def : Builtin<name, [AIGenTypeNNoScalar, AIGenTypeNNoScalar, AIGenType1, AIGenType1], Attr.Const>;
587}
588foreach name = ["mad_hi", "mad_sat"] in {
589  def : Builtin<name, [AIGenTypeN, AIGenTypeN, AIGenTypeN, AIGenTypeN], Attr.Const>;
590}
591
592// --- Table 11 ---
593foreach name = ["mad24"] in {
594  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeIntVecAndScalar, GenTypeIntVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
595  def : Builtin<name, [GenTypeUIntVecAndScalar, GenTypeUIntVecAndScalar, GenTypeUIntVecAndScalar, GenTypeUIntVecAndScalar], Attr.Const>;
596}
597foreach name = ["mul24"] in {
598  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeIntVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
599  def : Builtin<name, [GenTypeUIntVecAndScalar, GenTypeUIntVecAndScalar, GenTypeUIntVecAndScalar], Attr.Const>;
600}
601
602//--------------------------------------------------------------------
603// OpenCL v1.1 s6.11.4, v1.2 s6.12.4, v2.0 s6.13.4 - Common Functions
604// OpenCL Extension v2.0 s5.1.3 and s6.1.3 - Common Functions
605// --- Table 12 ---
606// --- 1 argument ---
607foreach name = ["degrees", "radians", "sign"] in {
608  def : Builtin<name, [FGenTypeN, FGenTypeN], Attr.Const>;
609}
610
611// --- 2 arguments ---
612foreach name = ["max", "min"] in {
613  def : Builtin<name, [FGenTypeN, FGenTypeN, FGenTypeN], Attr.Const>;
614  def : Builtin<name, [GenTypeFloatVecNoScalar, GenTypeFloatVecNoScalar, Float], Attr.Const>;
615  def : Builtin<name, [GenTypeDoubleVecNoScalar, GenTypeDoubleVecNoScalar, Double], Attr.Const>;
616  def : Builtin<name, [GenTypeHalfVecNoScalar, GenTypeHalfVecNoScalar, Half], Attr.Const>;
617}
618foreach name = ["step"] in {
619  def : Builtin<name, [FGenTypeN, FGenTypeN, FGenTypeN], Attr.Const>;
620  def : Builtin<name, [GenTypeFloatVecNoScalar, Float, GenTypeFloatVecNoScalar], Attr.Const>;
621  def : Builtin<name, [GenTypeDoubleVecNoScalar, Double, GenTypeDoubleVecNoScalar], Attr.Const>;
622  def : Builtin<name, [GenTypeHalfVecNoScalar, Half, GenTypeHalfVecNoScalar], Attr.Const>;
623}
624
625// --- 3 arguments ---
626foreach name = ["clamp", "mix"] in {
627  def : Builtin<name, [FGenTypeN, FGenTypeN, FGenTypeN, FGenTypeN], Attr.Const>;
628  def : Builtin<name, [GenTypeFloatVecNoScalar, GenTypeFloatVecNoScalar, Float, Float], Attr.Const>;
629  def : Builtin<name, [GenTypeDoubleVecNoScalar, GenTypeDoubleVecNoScalar, Double, Double], Attr.Const>;
630  def : Builtin<name, [GenTypeHalfVecNoScalar, GenTypeHalfVecNoScalar, Half, Half], Attr.Const>;
631}
632foreach name = ["smoothstep"] in {
633  def : Builtin<name, [FGenTypeN, FGenTypeN, FGenTypeN, FGenTypeN], Attr.Const>;
634  def : Builtin<name, [GenTypeFloatVecNoScalar, Float, Float, GenTypeFloatVecNoScalar], Attr.Const>;
635  def : Builtin<name, [GenTypeDoubleVecNoScalar, Double, Double, GenTypeDoubleVecNoScalar], Attr.Const>;
636  def : Builtin<name, [GenTypeHalfVecNoScalar, Half, Half, GenTypeHalfVecNoScalar], Attr.Const>;
637}
638
639
640//--------------------------------------------------------------------
641// OpenCL v1.1 s6.11.5, v1.2 s6.12.5, v2.0 s6.13.5 - Geometric Functions
642// OpenCL Extension v2.0 s5.1.4 and s6.1.4 - Geometric Functions
643// --- Table 13 ---
644// --- 1 argument ---
645foreach name = ["length"] in {
646  def : Builtin<name, [Float, GenTypeFloatVec1234], Attr.Const>;
647  def : Builtin<name, [Double, GenTypeDoubleVec1234], Attr.Const>;
648  def : Builtin<name, [Half, GenTypeHalfVec1234], Attr.Const>;
649}
650foreach name = ["normalize"] in {
651  def : Builtin<name, [GenTypeFloatVec1234, GenTypeFloatVec1234], Attr.Const>;
652  def : Builtin<name, [GenTypeDoubleVec1234, GenTypeDoubleVec1234], Attr.Const>;
653  def : Builtin<name, [GenTypeHalfVec1234, GenTypeHalfVec1234], Attr.Const>;
654}
655foreach name = ["fast_length"] in {
656  def : Builtin<name, [Float, GenTypeFloatVec1234], Attr.Const>;
657}
658foreach name = ["fast_normalize"] in {
659  def : Builtin<name, [GenTypeFloatVec1234, GenTypeFloatVec1234], Attr.Const>;
660}
661
662// --- 2 arguments ---
663foreach name = ["cross"] in {
664  foreach VSize = [3, 4] in {
665    def : Builtin<name, [VectorType<Float, VSize>, VectorType<Float, VSize>, VectorType<Float, VSize>], Attr.Const>;
666    def : Builtin<name, [VectorType<Double, VSize>, VectorType<Double, VSize>, VectorType<Double, VSize>], Attr.Const>;
667    def : Builtin<name, [VectorType<Half, VSize>, VectorType<Half, VSize>, VectorType<Half, VSize>], Attr.Const>;
668  }
669}
670foreach name = ["dot", "distance"] in {
671  def : Builtin<name, [Float, GenTypeFloatVec1234, GenTypeFloatVec1234], Attr.Const>;
672  def : Builtin<name, [Double, GenTypeDoubleVec1234, GenTypeDoubleVec1234], Attr.Const>;
673  def : Builtin<name, [Half, GenTypeHalfVec1234, GenTypeHalfVec1234], Attr.Const>;
674}
675foreach name = ["fast_distance"] in {
676  def : Builtin<name, [Float, GenTypeFloatVec1234, GenTypeFloatVec1234], Attr.Const>;
677}
678
679
680//--------------------------------------------------------------------
681// OpenCL v1.1 s6.11.6, v1.2 s6.12.6, v2.0 s6.13.6 - Relational Functions
682// OpenCL Extension v2.0 s5.1.5 and s6.1.5 - Relational Functions
683// --- Table 14 ---
684// --- 1 argument ---
685foreach name = ["isfinite", "isinf", "isnan", "isnormal", "signbit"] in {
686  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeFloatVecAndScalar], Attr.Const>;
687  def : Builtin<name, [Int, Double], Attr.Const>;
688  def : Builtin<name, [GenTypeLongVecNoScalar, GenTypeDoubleVecNoScalar], Attr.Const>;
689  def : Builtin<name, [Int, Half], Attr.Const>;
690  def : Builtin<name, [GenTypeShortVecNoScalar, GenTypeHalfVecNoScalar], Attr.Const>;
691}
692foreach name = ["any", "all"] in {
693  def : Builtin<name, [Int, SGenTypeN], Attr.Const>;
694}
695
696// --- 2 arguments ---
697foreach name = ["isequal", "isnotequal", "isgreater", "isgreaterequal",
698                "isless", "islessequal", "islessgreater", "isordered",
699                "isunordered"] in {
700  def : Builtin<name, [GenTypeIntVecAndScalar, GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar], Attr.Const>;
701  def : Builtin<name, [Int, Double, Double], Attr.Const>;
702  def : Builtin<name, [GenTypeLongVecNoScalar, GenTypeDoubleVecNoScalar, GenTypeDoubleVecNoScalar], Attr.Const>;
703  def : Builtin<name, [Int, Half, Half], Attr.Const>;
704  def : Builtin<name, [GenTypeShortVecNoScalar, GenTypeHalfVecNoScalar, GenTypeHalfVecNoScalar], Attr.Const>;
705}
706
707// --- 3 arguments ---
708foreach name = ["bitselect"] in {
709  def : Builtin<name, [AGenTypeN, AGenTypeN, AGenTypeN, AGenTypeN], Attr.Const>;
710}
711foreach name = ["select"] in {
712  def : Builtin<name, [SGenTypeN, SGenTypeN, SGenTypeN, SGenTypeN], Attr.Const>;
713  def : Builtin<name, [SGenTypeN, SGenTypeN, SGenTypeN, UGenTypeN], Attr.Const>;
714  def : Builtin<name, [UGenTypeN, UGenTypeN, UGenTypeN, UGenTypeN], Attr.Const>;
715  def : Builtin<name, [UGenTypeN, UGenTypeN, UGenTypeN, SGenTypeN], Attr.Const>;
716  def : Builtin<name, [GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar, GenTypeIntVecAndScalar], Attr.Const>;
717  def : Builtin<name, [GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar, GenTypeFloatVecAndScalar, GenTypeUIntVecAndScalar], Attr.Const>;
718  def : Builtin<name, [GenTypeDoubleVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeLongVecAndScalar], Attr.Const>;
719  def : Builtin<name, [GenTypeDoubleVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeDoubleVecAndScalar, GenTypeULongVecAndScalar], Attr.Const>;
720  def : Builtin<name, [GenTypeHalfVecAndScalar, GenTypeHalfVecAndScalar, GenTypeHalfVecAndScalar, GenTypeShortVecAndScalar], Attr.Const>;
721  def : Builtin<name, [GenTypeHalfVecAndScalar, GenTypeHalfVecAndScalar, GenTypeHalfVecAndScalar, GenTypeUShortVecAndScalar], Attr.Const>;
722}
723
724
725//--------------------------------------------------------------------
726// OpenCL v1.1 s6.11.7, v1.2 s6.12.7, v2.0 s6.13.7 - Vector Data Load and Store Functions
727// OpenCL Extension v1.1 s9.3.6 and s9.6.6, v1.2 s9.5.6, v2.0 s5.1.6 and s6.1.6 - Vector Data Load and Store Functions
728// --- Table 15 ---
729// Variants for OpenCL versions below 2.0, using pointers to the global, local
730// and private address spaces.
731let MaxVersion = CL20 in {
732  foreach AS = [GlobalAS, LocalAS, PrivateAS] in {
733    foreach VSize = [2, 3, 4, 8, 16] in {
734      foreach name = ["vload" # VSize] in {
735        def : Builtin<name, [VectorType<Char, VSize>, Size, PointerType<ConstType<Char>, AS>]>;
736        def : Builtin<name, [VectorType<UChar, VSize>, Size, PointerType<ConstType<UChar>, AS>]>;
737        def : Builtin<name, [VectorType<Short, VSize>, Size, PointerType<ConstType<Short>, AS>]>;
738        def : Builtin<name, [VectorType<UShort, VSize>, Size, PointerType<ConstType<UShort>, AS>]>;
739        def : Builtin<name, [VectorType<Int, VSize>, Size, PointerType<ConstType<Int>, AS>]>;
740        def : Builtin<name, [VectorType<UInt, VSize>, Size, PointerType<ConstType<UInt>, AS>]>;
741        def : Builtin<name, [VectorType<Long, VSize>, Size, PointerType<ConstType<Long>, AS>]>;
742        def : Builtin<name, [VectorType<ULong, VSize>, Size, PointerType<ConstType<ULong>, AS>]>;
743        def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Float>, AS>]>;
744        def : Builtin<name, [VectorType<Double, VSize>, Size, PointerType<ConstType<Double>, AS>]>;
745        def : Builtin<name, [VectorType<Half, VSize>, Size, PointerType<ConstType<Half>, AS>]>;
746      }
747      foreach name = ["vstore" # VSize] in {
748        def : Builtin<name, [Void, VectorType<Char, VSize>, Size, PointerType<Char, AS>]>;
749        def : Builtin<name, [Void, VectorType<UChar, VSize>, Size, PointerType<UChar, AS>]>;
750        def : Builtin<name, [Void, VectorType<Short, VSize>, Size, PointerType<Short, AS>]>;
751        def : Builtin<name, [Void, VectorType<UShort, VSize>, Size, PointerType<UShort, AS>]>;
752        def : Builtin<name, [Void, VectorType<Int, VSize>, Size, PointerType<Int, AS>]>;
753        def : Builtin<name, [Void, VectorType<UInt, VSize>, Size, PointerType<UInt, AS>]>;
754        def : Builtin<name, [Void, VectorType<Long, VSize>, Size, PointerType<Long, AS>]>;
755        def : Builtin<name, [Void, VectorType<ULong, VSize>, Size, PointerType<ULong, AS>]>;
756        def : Builtin<name, [Void, VectorType<Float, VSize>, Size, PointerType<Float, AS>]>;
757        def : Builtin<name, [Void, VectorType<Double, VSize>, Size, PointerType<Double, AS>]>;
758        def : Builtin<name, [Void, VectorType<Half, VSize>, Size, PointerType<Half, AS>]>;
759      }
760      foreach name = ["vloada_half" # VSize] in {
761        def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Half>, AS>]>;
762      }
763      foreach rnd = ["", "_rte", "_rtz", "_rtp", "_rtn"] in {
764        foreach name = ["vstorea_half" # VSize # rnd] in {
765          def : Builtin<name, [Void, VectorType<Float, VSize>, Size, PointerType<Half, AS>]>;
766          def : Builtin<name, [Void, VectorType<Double, VSize>, Size, PointerType<Half, AS>]>;
767        }
768      }
769    }
770  }
771}
772// Variants for OpenCL versions above 2.0, using pointers to the generic
773// address space.
774let MinVersion = CL20 in {
775  foreach VSize = [2, 3, 4, 8, 16] in {
776    foreach name = ["vload" # VSize] in {
777      def : Builtin<name, [VectorType<Char, VSize>, Size, PointerType<ConstType<Char>, GenericAS>]>;
778      def : Builtin<name, [VectorType<UChar, VSize>, Size, PointerType<ConstType<UChar>, GenericAS>]>;
779      def : Builtin<name, [VectorType<Short, VSize>, Size, PointerType<ConstType<Short>, GenericAS>]>;
780      def : Builtin<name, [VectorType<UShort, VSize>, Size, PointerType<ConstType<UShort>, GenericAS>]>;
781      def : Builtin<name, [VectorType<Int, VSize>, Size, PointerType<ConstType<Int>, GenericAS>]>;
782      def : Builtin<name, [VectorType<UInt, VSize>, Size, PointerType<ConstType<UInt>, GenericAS>]>;
783      def : Builtin<name, [VectorType<Long, VSize>, Size, PointerType<ConstType<Long>, GenericAS>]>;
784      def : Builtin<name, [VectorType<ULong, VSize>, Size, PointerType<ConstType<ULong>, GenericAS>]>;
785      def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Float>, GenericAS>]>;
786      def : Builtin<name, [VectorType<Double, VSize>, Size, PointerType<ConstType<Double>, GenericAS>]>;
787      def : Builtin<name, [VectorType<Half, VSize>, Size, PointerType<ConstType<Half>, GenericAS>]>;
788    }
789    foreach name = ["vstore" # VSize] in {
790      def : Builtin<name, [Void, VectorType<Char, VSize>, Size, PointerType<Char, GenericAS>]>;
791      def : Builtin<name, [Void, VectorType<UChar, VSize>, Size, PointerType<UChar, GenericAS>]>;
792      def : Builtin<name, [Void, VectorType<Short, VSize>, Size, PointerType<Short, GenericAS>]>;
793      def : Builtin<name, [Void, VectorType<UShort, VSize>, Size, PointerType<UShort, GenericAS>]>;
794      def : Builtin<name, [Void, VectorType<Int, VSize>, Size, PointerType<Int, GenericAS>]>;
795      def : Builtin<name, [Void, VectorType<UInt, VSize>, Size, PointerType<UInt, GenericAS>]>;
796      def : Builtin<name, [Void, VectorType<Long, VSize>, Size, PointerType<Long, GenericAS>]>;
797      def : Builtin<name, [Void, VectorType<ULong, VSize>, Size, PointerType<ULong, GenericAS>]>;
798      def : Builtin<name, [Void, VectorType<Float, VSize>, Size, PointerType<Float, GenericAS>]>;
799      def : Builtin<name, [Void, VectorType<Double, VSize>, Size, PointerType<Double, GenericAS>]>;
800      def : Builtin<name, [Void, VectorType<Half, VSize>, Size, PointerType<Half, GenericAS>]>;
801    }
802    foreach name = ["vloada_half" # VSize] in {
803      def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Half>, GenericAS>]>;
804    }
805    foreach rnd = ["", "_rte", "_rtz", "_rtp", "_rtn"] in {
806      foreach name = ["vstorea_half" # VSize # rnd] in {
807        def : Builtin<name, [Void, VectorType<Float, VSize>, Size, PointerType<Half, GenericAS>]>;
808        def : Builtin<name, [Void, VectorType<Double, VSize>, Size, PointerType<Half, GenericAS>]>;
809      }
810    }
811  }
812}
813// Variants using pointers to the constant address space.
814foreach VSize = [2, 3, 4, 8, 16] in {
815  foreach name = ["vload" # VSize] in {
816    def : Builtin<name, [VectorType<Char, VSize>, Size, PointerType<ConstType<Char>, ConstantAS>]>;
817    def : Builtin<name, [VectorType<UChar, VSize>, Size, PointerType<ConstType<UChar>, ConstantAS>]>;
818    def : Builtin<name, [VectorType<Short, VSize>, Size, PointerType<ConstType<Short>, ConstantAS>]>;
819    def : Builtin<name, [VectorType<UShort, VSize>, Size, PointerType<ConstType<UShort>, ConstantAS>]>;
820    def : Builtin<name, [VectorType<Int, VSize>, Size, PointerType<ConstType<Int>, ConstantAS>]>;
821    def : Builtin<name, [VectorType<UInt, VSize>, Size, PointerType<ConstType<UInt>, ConstantAS>]>;
822    def : Builtin<name, [VectorType<Long, VSize>, Size, PointerType<ConstType<Long>, ConstantAS>]>;
823    def : Builtin<name, [VectorType<ULong, VSize>, Size, PointerType<ConstType<ULong>, ConstantAS>]>;
824    def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Float>, ConstantAS>]>;
825    def : Builtin<name, [VectorType<Double, VSize>, Size, PointerType<ConstType<Double>, ConstantAS>]>;
826    def : Builtin<name, [VectorType<Half, VSize>, Size, PointerType<ConstType<Half>, ConstantAS>]>;
827  }
828  foreach name = ["vloada_half" # VSize] in {
829    def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Half>, ConstantAS>]>;
830  }
831}
832let MaxVersion = CL20 in {
833  foreach AS = [GlobalAS, LocalAS, PrivateAS] in {
834    def : Builtin<"vload_half", [Float, Size, PointerType<ConstType<Half>, AS>]>;
835    def : Builtin<"vloada_half", [Float, Size, PointerType<ConstType<Half>, AS>]>;
836    foreach VSize = [2, 3, 4, 8, 16] in {
837      foreach name = ["vload_half" # VSize] in {
838        def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Half>, AS>]>;
839      }
840    }
841    foreach rnd = ["", "_rte", "_rtz", "_rtp", "_rtn"] in {
842      foreach name = ["vstore_half" # rnd, "vstorea_half" # rnd] in {
843        def : Builtin<name, [Void, Float, Size, PointerType<Half, AS>]>;
844        def : Builtin<name, [Void, Double, Size, PointerType<Half, AS>]>;
845      }
846      foreach VSize = [2, 3, 4, 8, 16] in {
847        foreach name = ["vstore_half" # VSize # rnd] in {
848          def : Builtin<name, [Void, VectorType<Float, VSize>, Size, PointerType<Half, AS>]>;
849          def : Builtin<name, [Void, VectorType<Double, VSize>, Size, PointerType<Half, AS>]>;
850        }
851      }
852    }
853  }
854}
855let MinVersion = CL20 in {
856  foreach AS = [GenericAS] in {
857    def : Builtin<"vload_half", [Float, Size, PointerType<ConstType<Half>, AS>]>;
858    def : Builtin<"vloada_half", [Float, Size, PointerType<ConstType<Half>, AS>]>;
859    foreach VSize = [2, 3, 4, 8, 16] in {
860      foreach name = ["vload_half" # VSize] in {
861        def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Half>, AS>]>;
862      }
863    }
864    foreach rnd = ["", "_rte", "_rtz", "_rtp", "_rtn"] in {
865      foreach name = ["vstore_half" # rnd, "vstorea_half" # rnd] in {
866        def : Builtin<name, [Void, Float, Size, PointerType<Half, AS>]>;
867        def : Builtin<name, [Void, Double, Size, PointerType<Half, AS>]>;
868      }
869      foreach VSize = [2, 3, 4, 8, 16] in {
870        foreach name = ["vstore_half" # VSize # rnd] in {
871          def : Builtin<name, [Void, VectorType<Float, VSize>, Size, PointerType<Half, AS>]>;
872          def : Builtin<name, [Void, VectorType<Double, VSize>, Size, PointerType<Half, AS>]>;
873        }
874      }
875    }
876  }
877}
878
879foreach AS = [ConstantAS] in {
880  def : Builtin<"vload_half", [Float, Size, PointerType<ConstType<Half>, AS>]>;
881  def : Builtin<"vloada_half", [Float, Size, PointerType<ConstType<Half>, AS>]>;
882  foreach VSize = [2, 3, 4, 8, 16] in {
883    foreach name = ["vload_half" # VSize] in {
884      def : Builtin<name, [VectorType<Float, VSize>, Size, PointerType<ConstType<Half>, AS>]>;
885    }
886  }
887}
888
889//--------------------------------------------------------------------
890// OpenCL v1.1 s6.11.10, v1.2 s6.12.10, v2.0 s6.13.10: Async Copies from Global to Local Memory, Local to Global Memory, and Prefetch
891// OpenCL Extension v2.0 s5.1.7 and s6.1.7: Async Copies from Global to Local Memory, Local to Global Memory, and Prefetch
892// --- Table 18 ---
893foreach name = ["async_work_group_copy"] in {
894  def : Builtin<name, [Event, PointerType<AGenTypeN, LocalAS>, PointerType<ConstType<AGenTypeN>, GlobalAS>, Size, Event]>;
895  def : Builtin<name, [Event, PointerType<AGenTypeN, GlobalAS>, PointerType<ConstType<AGenTypeN>, LocalAS>, Size, Event]>;
896}
897foreach name = ["async_work_group_strided_copy"] in {
898  def : Builtin<name, [Event, PointerType<AGenTypeN, LocalAS>, PointerType<ConstType<AGenTypeN>, GlobalAS>, Size, Size, Event]>;
899  def : Builtin<name, [Event, PointerType<AGenTypeN, GlobalAS>, PointerType<ConstType<AGenTypeN>, LocalAS>, Size, Size, Event]>;
900}
901foreach name = ["wait_group_events"] in {
902  def : Builtin<name, [Void, Int, PointerType<Event, GenericAS>]>;
903}
904foreach name = ["prefetch"] in {
905  def : Builtin<name, [Void, PointerType<ConstType<AGenTypeN>, GlobalAS>, Size]>;
906}
907
908//--------------------------------------------------------------------
909// OpenCL v2.0 s6.13.11 - Atomics Functions.
910// Functions that use memory_order and cl_mem_fence_flags enums are not
911// declared here as the TableGen backend does not handle enums.
912
913// OpenCL v1.0 s9.5, s9.6, s9.7 - Atomic Functions for 32-bit integers
914// --- Table 9.1 ---
915let Extension = FuncExtKhrGlobalInt32BaseAtomics in {
916  foreach Type = [Int, UInt] in {
917    foreach name = ["atom_add", "atom_sub", "atom_xchg"] in {
918      def : Builtin<name, [Type, PointerType<VolatileType<Type>, GlobalAS>, Type]>;
919    }
920    foreach name = ["atom_inc", "atom_dec"] in {
921      def : Builtin<name, [Type, PointerType<VolatileType<Type>, GlobalAS>]>;
922    }
923    foreach name = ["atom_cmpxchg"] in {
924      def : Builtin<name, [Type, PointerType<VolatileType<Type>, GlobalAS>, Type, Type]>;
925    }
926  }
927}
928// --- Table 9.3 ---
929let Extension = FuncExtKhrLocalInt32BaseAtomics in {
930  foreach Type = [Int, UInt] in {
931    foreach name = ["atom_add", "atom_sub", "atom_xchg"] in {
932      def : Builtin<name, [Type, PointerType<VolatileType<Type>, LocalAS>, Type]>;
933    }
934    foreach name = ["atom_inc", "atom_dec"] in {
935      def : Builtin<name, [Type, PointerType<VolatileType<Type>, LocalAS>]>;
936    }
937    foreach name = ["atom_cmpxchg"] in {
938      def : Builtin<name, [Type, PointerType<VolatileType<Type>, LocalAS>, Type, Type]>;
939    }
940  }
941}
942// --- Table 9.5 ---
943let Extension = FuncExtKhrInt64BaseAtomics in {
944  foreach AS = [GlobalAS, LocalAS] in {
945    foreach Type = [Long, ULong] in {
946      foreach name = ["atom_add", "atom_sub", "atom_xchg"] in {
947        def : Builtin<name, [Type, PointerType<VolatileType<Type>, AS>, Type]>;
948      }
949      foreach name = ["atom_inc", "atom_dec"] in {
950        def : Builtin<name, [Type, PointerType<VolatileType<Type>, AS>]>;
951      }
952      foreach name = ["atom_cmpxchg"] in {
953        def : Builtin<name, [Type, PointerType<VolatileType<Type>, AS>, Type, Type]>;
954      }
955    }
956  }
957}
958// --- Table 9.2 ---
959let Extension = FuncExtKhrGlobalInt32ExtendedAtomics in {
960  foreach Type = [Int, UInt] in {
961    foreach name = ["atom_min", "atom_max", "atom_and",
962                    "atom_or", "atom_xor"] in {
963      def : Builtin<name, [Type, PointerType<VolatileType<Type>, GlobalAS>, Type]>;
964    }
965  }
966}
967// --- Table 9.4 ---
968let Extension = FuncExtKhrLocalInt32ExtendedAtomics in {
969  foreach Type = [Int, UInt] in {
970    foreach name = ["atom_min", "atom_max", "atom_and",
971                    "atom_or", "atom_xor"] in {
972      def : Builtin<name, [Type, PointerType<VolatileType<Type>, LocalAS>, Type]>;
973    }
974  }
975}
976// --- Table 9.6 ---
977let Extension = FuncExtKhrInt64ExtendedAtomics in {
978  foreach AS = [GlobalAS, LocalAS] in {
979    foreach Type = [Long, ULong] in {
980      foreach name = ["atom_min", "atom_max", "atom_and",
981                      "atom_or", "atom_xor"] in {
982        def : Builtin<name, [Type, PointerType<VolatileType<Type>, AS>, Type]>;
983      }
984    }
985  }
986}
987// OpenCL v1.1 s6.11.1, v1.2 s6.12.11 - Atomic Functions
988foreach AS = [GlobalAS, LocalAS] in {
989  foreach Type = [Int, UInt] in {
990    foreach name = ["atomic_add", "atomic_sub", "atomic_xchg",
991                    "atomic_min", "atomic_max", "atomic_and",
992                    "atomic_or", "atomic_xor"] in {
993      def : Builtin<name, [Type, PointerType<VolatileType<Type>, AS>, Type]>;
994    }
995    foreach name = ["atomic_inc", "atomic_dec"] in {
996      def : Builtin<name, [Type, PointerType<VolatileType<Type>, AS>]>;
997    }
998    foreach name = ["atomic_cmpxchg"] in {
999      def : Builtin<name, [Type, PointerType<VolatileType<Type>, AS>, Type, Type]>;
1000    }
1001  }
1002}
1003// OpenCL v2.0 s6.13.11 - Atomic Functions.
1004let MinVersion = CL20 in {
1005  foreach TypePair = [[AtomicInt, Int], [AtomicUInt, UInt],
1006                      [AtomicLong, Long], [AtomicULong, ULong],
1007                      [AtomicFloat, Float], [AtomicDouble, Double]] in {
1008    def : Builtin<"atomic_init",
1009        [Void, PointerType<VolatileType<TypePair[0]>, GenericAS>, TypePair[1]]>;
1010    def : Builtin<"atomic_store",
1011        [Void, PointerType<VolatileType<TypePair[0]>, GenericAS>, TypePair[1]]>;
1012    def : Builtin<"atomic_load",
1013        [TypePair[1], PointerType<VolatileType<TypePair[0]>, GenericAS>]>;
1014    def : Builtin<"atomic_exchange",
1015        [TypePair[1], PointerType<VolatileType<TypePair[0]>, GenericAS>, TypePair[1]]>;
1016    foreach Variant = ["weak", "strong"] in {
1017      def : Builtin<"atomic_compare_exchange_" # Variant,
1018          [Bool, PointerType<VolatileType<TypePair[0]>, GenericAS>,
1019           PointerType<TypePair[1], GenericAS>, TypePair[1]]>;
1020    }
1021  }
1022
1023  foreach TypePair = [[AtomicInt, Int, Int], [AtomicUInt, UInt, UInt],
1024                      [AtomicLong, Long, Long], [AtomicULong, ULong, ULong],
1025                      [AtomicIntPtr, IntPtr, PtrDiff],
1026                      [AtomicUIntPtr, UIntPtr, PtrDiff]] in {
1027    foreach ModOp = ["add", "sub"] in {
1028      def : Builtin<"atomic_fetch_" # ModOp,
1029          [TypePair[1], PointerType<VolatileType<TypePair[0]>, GenericAS>, TypePair[2]]>;
1030    }
1031  }
1032  foreach TypePair = [[AtomicInt, Int, Int], [AtomicUInt, UInt, UInt],
1033                      [AtomicLong, Long, Long], [AtomicULong, ULong, ULong],
1034                      [AtomicIntPtr, IntPtr, IntPtr],
1035                      [AtomicUIntPtr, UIntPtr, UIntPtr]] in {
1036    foreach ModOp = ["or", "xor", "and", "min", "max"] in {
1037      def : Builtin<"atomic_fetch_" # ModOp,
1038          [TypePair[1], PointerType<VolatileType<TypePair[0]>, GenericAS>, TypePair[2]]>;
1039    }
1040  }
1041}
1042
1043//--------------------------------------------------------------------
1044// OpenCL v1.1 s6.11.12, v1.2 s6.12.12, v2.0 s6.13.12 - Miscellaneous Vector Functions
1045// --- Table 19 ---
1046foreach VSize1 = [Vec2, Vec4, Vec8, Vec16] in {
1047  foreach VSize2 = [Vec2, Vec4, Vec8, Vec16] in {
1048    def : Builtin<"shuffle", [GenericType<"TLAll" # VSize1.Name, TLAll, VSize1>,
1049                              GenericType<"TLAll" # VSize2.Name, TLAll, VSize2>,
1050                              GenericType<"TLAllUnsigned" # VSize1.Name, TLAllUnsigned, VSize1>],
1051                  Attr.Const>;
1052  }
1053}
1054foreach VSize1 = [Vec2, Vec4, Vec8, Vec16] in {
1055  foreach VSize2 = [Vec2, Vec4, Vec8, Vec16] in {
1056    def : Builtin<"shuffle2", [GenericType<"TLAll" # VSize1.Name, TLAll, VSize1>,
1057                               GenericType<"TLAll" # VSize2.Name, TLAll, VSize2>,
1058                               GenericType<"TLAll" # VSize2.Name, TLAll, VSize2>,
1059                               GenericType<"TLAllUnsigned" # VSize1.Name, TLAllUnsigned, VSize1>],
1060                  Attr.Const>;
1061  }
1062}
1063
1064//--------------------------------------------------------------------
1065// OpenCL v1.1 s6.11.3, v1.2 s6.12.14, v2.0 s6.13.14: Image Read and Write Functions
1066// OpenCL Extension v2.0 s5.1.8 and s6.1.8: Image Read and Write Functions
1067// --- Table 22: Image Read Functions with Samplers ---
1068foreach imgTy = [Image1d] in {
1069  foreach coordTy = [Int, Float] in {
1070    def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, "RO">, Sampler, coordTy], Attr.Pure>;
1071    def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, "RO">, Sampler, coordTy], Attr.Pure>;
1072    def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, "RO">, Sampler, coordTy], Attr.Pure>;
1073  }
1074}
1075foreach imgTy = [Image2d, Image1dArray] in {
1076  foreach coordTy = [Int, Float] in {
1077    def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, "RO">, Sampler, VectorType<coordTy, 2>], Attr.Pure>;
1078    def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, "RO">, Sampler, VectorType<coordTy, 2>], Attr.Pure>;
1079    def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, "RO">, Sampler, VectorType<coordTy, 2>], Attr.Pure>;
1080  }
1081}
1082foreach imgTy = [Image3d, Image2dArray] in {
1083  foreach coordTy = [Int, Float] in {
1084    def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, "RO">, Sampler, VectorType<coordTy, 4>], Attr.Pure>;
1085    def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, "RO">, Sampler, VectorType<coordTy, 4>], Attr.Pure>;
1086    def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, "RO">, Sampler, VectorType<coordTy, 4>], Attr.Pure>;
1087  }
1088}
1089foreach coordTy = [Int, Float] in {
1090  def : Builtin<"read_imagef", [Float, ImageType<Image2dDepth, "RO">, Sampler, VectorType<coordTy, 2>], Attr.Pure>;
1091  def : Builtin<"read_imagef", [Float, ImageType<Image2dArrayDepth, "RO">, Sampler, VectorType<coordTy, 4>], Attr.Pure>;
1092}
1093
1094// --- Table 23: Sampler-less Read Functions ---
1095foreach aQual = ["RO", "RW"] in {
1096  foreach imgTy = [Image2d, Image1dArray] in {
1097    def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, aQual>, VectorType<Int, 2>], Attr.Pure>;
1098    def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, aQual>, VectorType<Int, 2>], Attr.Pure>;
1099    def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, aQual>, VectorType<Int, 2>], Attr.Pure>;
1100  }
1101  foreach imgTy = [Image3d, Image2dArray] in {
1102    def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, aQual>, VectorType<Int, 4>], Attr.Pure>;
1103    def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, aQual>, VectorType<Int, 4>], Attr.Pure>;
1104    def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, aQual>, VectorType<Int, 4>], Attr.Pure>;
1105  }
1106  foreach imgTy = [Image1d, Image1dBuffer] in {
1107    def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, aQual>, Int], Attr.Pure>;
1108    def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, aQual>, Int], Attr.Pure>;
1109    def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Int], Attr.Pure>;
1110  }
1111  def : Builtin<"read_imagef", [Float, ImageType<Image2dDepth, aQual>, VectorType<Int, 2>], Attr.Pure>;
1112  def : Builtin<"read_imagef", [Float, ImageType<Image2dArrayDepth, aQual>, VectorType<Int, 4>], Attr.Pure>;
1113}
1114
1115// --- Table 24: Image Write Functions ---
1116foreach aQual = ["WO", "RW"] in {
1117  foreach imgTy = [Image2d] in {
1118    def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, VectorType<Float, 4>]>;
1119    def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, VectorType<Int, 4>]>;
1120    def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, VectorType<UInt, 4>]>;
1121  }
1122  foreach imgTy = [Image2dArray] in {
1123    def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, VectorType<Float, 4>]>;
1124    def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, VectorType<Int, 4>]>;
1125    def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, VectorType<UInt, 4>]>;
1126  }
1127  foreach imgTy = [Image1d, Image1dBuffer] in {
1128    def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, Int, VectorType<Float, 4>]>;
1129    def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, Int, VectorType<Int, 4>]>;
1130    def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, Int, VectorType<UInt, 4>]>;
1131  }
1132  foreach imgTy = [Image1dArray] in {
1133    def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, VectorType<Float, 4>]>;
1134    def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, VectorType<Int, 4>]>;
1135    def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, VectorType<UInt, 4>]>;
1136  }
1137  foreach imgTy = [Image3d] in {
1138    def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, VectorType<Float, 4>]>;
1139    def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, VectorType<Int, 4>]>;
1140    def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, VectorType<UInt, 4>]>;
1141  }
1142  def : Builtin<"write_imagef", [Void, ImageType<Image2dDepth, aQual>, VectorType<Int, 2>, Float]>;
1143  def : Builtin<"write_imagef", [Void, ImageType<Image2dArrayDepth, aQual>, VectorType<Int, 4>, Float]>;
1144}
1145
1146// --- Table 25: Image Query Functions ---
1147foreach aQual = ["RO", "WO", "RW"] in {
1148  foreach imgTy = [Image1d, Image1dBuffer, Image2d, Image3d,
1149                   Image1dArray, Image2dArray, Image2dDepth,
1150                   Image2dArrayDepth] in {
1151    foreach name = ["get_image_width", "get_image_channel_data_type",
1152                    "get_image_channel_order"] in {
1153      def : Builtin<name, [Int, ImageType<imgTy, aQual>]>;
1154    }
1155  }
1156  foreach imgTy = [Image2d, Image3d, Image2dArray, Image2dDepth,
1157                   Image2dArrayDepth] in {
1158    def : Builtin<"get_image_height", [Int, ImageType<imgTy, aQual>]>;
1159  }
1160  def : Builtin<"get_image_depth", [Int, ImageType<Image3d, aQual>]>;
1161  foreach imgTy = [Image2d, Image2dArray, Image2dDepth,
1162                   Image2dArrayDepth] in {
1163    def : Builtin<"get_image_dim", [VectorType<Int, 2>, ImageType<imgTy, aQual>]>;
1164  }
1165  def : Builtin<"get_image_dim", [VectorType<Int, 4>, ImageType<Image3d, aQual>]>;
1166  foreach imgTy = [Image1dArray, Image2dArray, Image2dArrayDepth] in {
1167    def : Builtin<"get_image_array_size", [Size, ImageType<imgTy, aQual>]>;
1168  }
1169}
1170
1171// OpenCL extension v2.0 s5.1.9: Built-in Image Read Functions
1172// --- Table 8 ---
1173foreach aQual = ["RO"] in {
1174  foreach name = ["read_imageh"] in {
1175    foreach coordTy = [Int, Float] in {
1176      foreach imgTy = [Image2d, Image1dArray] in {
1177        def : Builtin<name, [VectorType<Half, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<coordTy, 2>], Attr.Pure>;
1178      }
1179      foreach imgTy = [Image3d, Image2dArray] in {
1180        def : Builtin<name, [VectorType<Half, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<coordTy, 4>], Attr.Pure>;
1181      }
1182      foreach imgTy = [Image1d] in {
1183        def : Builtin<name, [VectorType<Half, 4>, ImageType<imgTy, aQual>, Sampler, coordTy], Attr.Pure>;
1184      }
1185    }
1186  }
1187}
1188// OpenCL extension v2.0 s5.1.10: Built-in Image Sampler-less Read Functions
1189// --- Table 9 ---
1190foreach aQual = ["RO", "RW"] in {
1191  foreach name = ["read_imageh"] in {
1192    foreach imgTy = [Image2d, Image1dArray] in {
1193      def : Builtin<name, [VectorType<Half, 4>, ImageType<imgTy, aQual>, VectorType<Int, 2>], Attr.Pure>;
1194    }
1195    foreach imgTy = [Image3d, Image2dArray] in {
1196      def : Builtin<name, [VectorType<Half, 4>, ImageType<imgTy, aQual>, VectorType<Int, 4>], Attr.Pure>;
1197    }
1198    foreach imgTy = [Image1d, Image1dBuffer] in {
1199      def : Builtin<name, [VectorType<Half, 4>, ImageType<imgTy, aQual>, Int], Attr.Pure>;
1200    }
1201  }
1202}
1203// OpenCL extension v2.0 s5.1.11: Built-in Image Write Functions
1204// --- Table 10 ---
1205foreach aQual = ["WO", "RW"] in {
1206  foreach name = ["write_imageh"] in {
1207    def : Builtin<name, [Void, ImageType<Image2d, aQual>, VectorType<Int, 2>, VectorType<Half, 4>]>;
1208    def : Builtin<name, [Void, ImageType<Image2dArray, aQual>, VectorType<Int, 4>, VectorType<Half, 4>]>;
1209    def : Builtin<name, [Void, ImageType<Image1d, aQual>, Int, VectorType<Half, 4>]>;
1210    def : Builtin<name, [Void, ImageType<Image1dBuffer, aQual>, Int, VectorType<Half, 4>]>;
1211    def : Builtin<name, [Void, ImageType<Image1dArray, aQual>, VectorType<Int, 2>, VectorType<Half, 4>]>;
1212    def : Builtin<name, [Void, ImageType<Image3d, aQual>, VectorType<Int, 4>, VectorType<Half, 4>]>;
1213  }
1214}
1215
1216
1217//--------------------------------------------------------------------
1218// OpenCL v2.0 s6.13.15 - Work-group Functions
1219// --- Table 26 ---
1220let MinVersion = CL20 in {
1221  foreach name = ["work_group_all", "work_group_any"] in {
1222    def : Builtin<name, [Int, Int], Attr.Convergent>;
1223  }
1224  foreach name = ["work_group_broadcast"] in {
1225    def : Builtin<name, [IntLongFloatGenType1, IntLongFloatGenType1, Size], Attr.Convergent>;
1226    def : Builtin<name, [IntLongFloatGenType1, IntLongFloatGenType1, Size, Size], Attr.Convergent>;
1227    def : Builtin<name, [IntLongFloatGenType1, IntLongFloatGenType1, Size, Size, Size], Attr.Convergent>;
1228  }
1229  foreach op = ["add", "min", "max"] in {
1230    foreach name = ["work_group_reduce_", "work_group_scan_exclusive_",
1231                    "work_group_scan_inclusive_"] in {
1232      def : Builtin<name # op, [IntLongFloatGenType1, IntLongFloatGenType1], Attr.Convergent>;
1233    }
1234  }
1235}
1236
1237
1238//--------------------------------------------------------------------
1239// OpenCL2.0 : 6.13.16 : Pipe Functions
1240// --- Table 27 ---
1241// Defined in Builtins.def
1242
1243// --- Table 28 ---
1244// Builtins taking pipe arguments are defined in Builtins.def
1245def : Builtin<"is_valid_reserve_id", [Bool, ReserveId]>;
1246
1247// --- Table 29 ---
1248// Defined in Builtins.def
1249
1250
1251//--------------------------------------------------------------------
1252// OpenCL2.0 : 6.13.17 : Enqueuing Kernels
1253// --- Table 30 ---
1254// Defined in Builtins.def
1255
1256// --- Table 32 ---
1257// Defined in Builtins.def
1258
1259// --- Table 33 ---
1260def : Builtin<"enqueue_marker",
1261    [Int, Queue, UInt, PointerType<ConstType<ClkEvent>, GenericAS>, PointerType<ClkEvent, GenericAS>]>;
1262
1263// --- Table 34 ---
1264def : Builtin<"retain_event", [Void, ClkEvent]>;
1265def : Builtin<"release_event", [Void, ClkEvent]>;
1266def : Builtin<"create_user_event", [ClkEvent]>;
1267def : Builtin<"is_valid_event", [Bool, ClkEvent]>;
1268def : Builtin<"set_user_event_status", [Void, ClkEvent, Int]>;
1269// TODO: capture_event_profiling_info
1270
1271// --- Table 35 ---
1272def : Builtin<"get_default_queue", [Queue]>;
1273// TODO: ndrange functions
1274
1275
1276//--------------------------------------------------------------------
1277// End of the builtin functions defined in the OpenCL C specification.
1278// Builtin functions defined in the OpenCL C Extension are below.
1279//--------------------------------------------------------------------
1280
1281
1282// OpenCL Extension v2.0 s9.18 - Mipmaps
1283let Extension = FuncExtKhrMipmapImage in {
1284  // Added to section 6.13.14.2.
1285  foreach aQual = ["RO"] in {
1286    foreach imgTy = [Image2d] in {
1287      foreach name = ["read_imagef"] in {
1288        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float], Attr.Pure>;
1289        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1290      }
1291      foreach name = ["read_imagei"] in {
1292        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float], Attr.Pure>;
1293        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1294      }
1295      foreach name = ["read_imageui"] in {
1296        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float], Attr.Pure>;
1297        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1298      }
1299    }
1300    foreach imgTy = [Image2dDepth] in {
1301      foreach name = ["read_imagef"] in {
1302        def : Builtin<name, [Float, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float], Attr.Pure>;
1303        def : Builtin<name, [Float, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1304      }
1305    }
1306    foreach imgTy = [Image1d] in {
1307      foreach name = ["read_imagef"] in {
1308        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, Float, Float], Attr.Pure>;
1309        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, Float, Float, Float], Attr.Pure>;
1310      }
1311      foreach name = ["read_imagei"] in {
1312        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, Float, Float], Attr.Pure>;
1313        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, Float, Float, Float], Attr.Pure>;
1314      }
1315      foreach name = ["read_imageui"] in {
1316        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, Float, Float], Attr.Pure>;
1317        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, Float, Float, Float], Attr.Pure>;
1318      }
1319    }
1320    foreach imgTy = [Image3d] in {
1321      foreach name = ["read_imagef"] in {
1322        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, VectorType<Float, 4>, VectorType<Float, 4>], Attr.Pure>;
1323        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, Float], Attr.Pure>;
1324      }
1325      foreach name = ["read_imagei"] in {
1326        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, VectorType<Float, 4>, VectorType<Float, 4>], Attr.Pure>;
1327        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, Float], Attr.Pure>;
1328      }
1329      foreach name = ["read_imageui"] in {
1330        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, VectorType<Float, 4>, VectorType<Float, 4>], Attr.Pure>;
1331        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, Float], Attr.Pure>;
1332      }
1333    }
1334    foreach imgTy = [Image1dArray] in {
1335      foreach name = ["read_imagef"] in {
1336        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float], Attr.Pure>;
1337        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float, Float], Attr.Pure>;
1338      }
1339      foreach name = ["read_imagei"] in {
1340        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float], Attr.Pure>;
1341        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float, Float], Attr.Pure>;
1342      }
1343      foreach name = ["read_imageui"] in {
1344        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float], Attr.Pure>;
1345        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 2>, Float, Float], Attr.Pure>;
1346      }
1347    }
1348    foreach imgTy = [Image2dArray] in {
1349      foreach name = ["read_imagef"] in {
1350        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, Float], Attr.Pure>;
1351        def : Builtin<name, [VectorType<Float, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1352      }
1353      foreach name = ["read_imagei"] in {
1354        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, Float], Attr.Pure>;
1355        def : Builtin<name, [VectorType<Int, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1356      }
1357      foreach name = ["read_imageui"] in {
1358        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, Float], Attr.Pure>;
1359        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1360      }
1361    }
1362    foreach imgTy = [Image2dArrayDepth] in {
1363      foreach name = ["read_imagef"] in {
1364        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, Float], Attr.Pure>;
1365        def : Builtin<name, [VectorType<UInt, 4>, ImageType<imgTy, aQual>, Sampler, VectorType<Float, 4>, VectorType<Float, 2>, VectorType<Float, 2>], Attr.Pure>;
1366      }
1367    }
1368  }
1369  // Added to section 6.13.14.5
1370  foreach aQual = ["RO", "WO", "RW"] in {
1371    foreach imgTy = [Image1d, Image2d, Image3d, Image1dArray, Image2dArray, Image2dDepth, Image2dArrayDepth] in {
1372      def : Builtin<"get_image_num_mip_levels", [Int, ImageType<imgTy, aQual>]>;
1373    }
1374  }
1375}
1376
1377// Write functions are enabled using a separate extension.
1378let Extension = FuncExtKhrMipmapImageWrites in {
1379  // Added to section 6.13.14.4.
1380  foreach aQual = ["WO"] in {
1381    foreach imgTy = [Image2d] in {
1382      def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int, VectorType<Float, 4>]>;
1383      def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int, VectorType<Int, 4>]>;
1384      def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int, VectorType<UInt, 4>]>;
1385    }
1386    def : Builtin<"write_imagef", [Void, ImageType<Image2dDepth, aQual>, VectorType<Int, 2>, Int, Float]>;
1387    foreach imgTy = [Image1d] in {
1388      def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, Int, Int, VectorType<Float, 4>]>;
1389      def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, Int, Int, VectorType<Int, 4>]>;
1390      def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, Int, Int, VectorType<UInt, 4>]>;
1391    }
1392    foreach imgTy = [Image1dArray] in {
1393      def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int, VectorType<Float, 4>]>;
1394      def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int, VectorType<Int, 4>]>;
1395      def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int, VectorType<UInt, 4>]>;
1396    }
1397    foreach imgTy = [Image2dArray] in {
1398      def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int, VectorType<Float, 4>]>;
1399      def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int, VectorType<Int, 4>]>;
1400      def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int, VectorType<UInt, 4>]>;
1401    }
1402    def : Builtin<"write_imagef", [Void, ImageType<Image2dArrayDepth, aQual>, VectorType<Int, 4>, Int, Float]>;
1403    let Extension = FuncExtKhrMipmapWritesAndWrite3d in {
1404      foreach imgTy = [Image3d] in {
1405        def : Builtin<"write_imagef", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int, VectorType<Float, 4>]>;
1406        def : Builtin<"write_imagei", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int, VectorType<Int, 4>]>;
1407        def : Builtin<"write_imageui", [Void, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int, VectorType<UInt, 4>]>;
1408      }
1409    }
1410  }
1411}
1412
1413//--------------------------------------------------------------------
1414// OpenCL Extension v2.0 s18.3 - Creating OpenCL Memory Objects from OpenGL MSAA Textures
1415let Extension = FuncExtKhrGlMsaaSharing in {
1416  // --- Table 6.13.14.3 ---
1417  foreach aQual = ["RO", "RW"] in {
1418    foreach imgTy = [Image2dMsaa] in {
1419      def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int], Attr.Pure>;
1420      def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int], Attr.Pure>;
1421      def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, aQual>, VectorType<Int, 2>, Int], Attr.Pure>;
1422    }
1423    foreach imgTy = [Image2dArrayMsaa] in {
1424      def : Builtin<"read_imagef", [VectorType<Float, 4>, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int], Attr.Pure>;
1425      def : Builtin<"read_imagei", [VectorType<Int, 4>, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int], Attr.Pure>;
1426      def : Builtin<"read_imageui", [VectorType<UInt, 4>, ImageType<imgTy, aQual>, VectorType<Int, 4>, Int], Attr.Pure>;
1427    }
1428    foreach name = ["read_imagef"] in {
1429      def : Builtin<name, [Float, ImageType<Image2dMsaaDepth, aQual>, VectorType<Int, 2>, Int], Attr.Pure>;
1430      def : Builtin<name, [Float, ImageType<Image2dArrayMsaaDepth, aQual>, VectorType<Int, 4>, Int], Attr.Pure>;
1431    }
1432  }
1433
1434  // --- Table 6.13.14.5 ---
1435  foreach aQual = ["RO", "WO", "RW"] in {
1436    foreach imgTy = [Image2dMsaa, Image2dArrayMsaa, Image2dMsaaDepth, Image2dArrayMsaaDepth] in {
1437      foreach name = ["get_image_width", "get_image_height",
1438                      "get_image_channel_data_type", "get_image_channel_order",
1439                      "get_image_num_samples"] in {
1440        def : Builtin<name, [Int, ImageType<imgTy, aQual>], Attr.Const>;
1441      }
1442      def : Builtin<"get_image_dim", [VectorType<Int, 2>, ImageType<imgTy, aQual>], Attr.Const>;
1443    }
1444    foreach imgTy = [Image2dArrayMsaa, Image2dArrayMsaaDepth] in {
1445      def : Builtin<"get_image_array_size", [Size, ImageType<imgTy, aQual>], Attr.Const>;
1446    }
1447  }
1448}
1449
1450//--------------------------------------------------------------------
1451// OpenCL Extension v2.0 s28 - Subgroups
1452// --- Table 28.2.1 ---
1453let Extension = FuncExtKhrSubgroups in {
1454  foreach name = ["get_sub_group_size", "get_max_sub_group_size",
1455                  "get_num_sub_groups", "get_sub_group_id",
1456                  "get_sub_group_local_id"] in {
1457    def : Builtin<name, [UInt]>;
1458  }
1459  let MinVersion = CL20 in {
1460    foreach name = ["get_enqueued_num_sub_groups"] in {
1461      def : Builtin<name, [UInt]>;
1462    }
1463  }
1464}
1465
1466// --- Table 28.2.2 ---
1467// TODO: sub_group_barrier
1468
1469// --- Table 28.2.4 ---
1470let Extension = FuncExtKhrSubgroups in {
1471  foreach name = ["sub_group_all", "sub_group_any"] in {
1472    def : Builtin<name, [Int, Int], Attr.Convergent>;
1473  }
1474  foreach name = ["sub_group_broadcast"] in {
1475    def : Builtin<name, [IntLongFloatGenType1, IntLongFloatGenType1, UInt], Attr.Convergent>;
1476  }
1477  foreach name = ["sub_group_reduce_", "sub_group_scan_exclusive_",
1478                  "sub_group_scan_inclusive_"] in {
1479    foreach op = ["add", "min", "max"] in {
1480      def : Builtin<name # op, [IntLongFloatGenType1, IntLongFloatGenType1], Attr.Convergent>;
1481    }
1482  }
1483}
1484
1485//--------------------------------------------------------------------
1486// Arm extensions.
1487let Extension = ArmIntegerDotProductInt8 in {
1488  foreach name = ["arm_dot"] in {
1489    def : Builtin<name, [UInt, VectorType<UChar, 4>, VectorType<UChar, 4>]>;
1490    def : Builtin<name, [Int, VectorType<Char, 4>, VectorType<Char, 4>]>;
1491  }
1492}
1493let Extension = ArmIntegerDotProductAccumulateInt8 in {
1494  foreach name = ["arm_dot_acc"] in {
1495    def : Builtin<name, [UInt, VectorType<UChar, 4>, VectorType<UChar, 4>, UInt]>;
1496    def : Builtin<name, [Int, VectorType<Char, 4>, VectorType<Char, 4>, Int]>;
1497  }
1498}
1499let Extension = ArmIntegerDotProductAccumulateInt16 in {
1500  foreach name = ["arm_dot_acc"] in {
1501    def : Builtin<name, [UInt, VectorType<UShort, 2>, VectorType<UShort, 2>, UInt]>;
1502    def : Builtin<name, [Int, VectorType<Short, 2>, VectorType<Short, 2>, Int]>;
1503  }
1504}
1505let Extension = ArmIntegerDotProductAccumulateSaturateInt8 in {
1506  foreach name = ["arm_dot_acc_sat"] in {
1507    def : Builtin<name, [UInt, VectorType<UChar, 4>, VectorType<UChar, 4>, UInt]>;
1508    def : Builtin<name, [Int, VectorType<Char, 4>, VectorType<Char, 4>, Int]>;
1509  }
1510}
1511