xref: /aosp_15_r20/external/angle/src/libANGLE/renderer/cl/CLProgramCL.cpp (revision 8975f5c5ed3d1c378011245431ada316dfb6f244)
1 //
2 // Copyright 2021 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 // CLProgramCL.cpp: Implements the class methods for CLProgramCL.
7 
8 #include "libANGLE/renderer/cl/CLProgramCL.h"
9 
10 #include "libANGLE/renderer/cl/CLDeviceCL.h"
11 #include "libANGLE/renderer/cl/CLKernelCL.h"
12 
13 #include "libANGLE/CLDevice.h"
14 #include "libANGLE/CLProgram.h"
15 #include "libANGLE/cl_utils.h"
16 
17 namespace rx
18 {
19 
CLProgramCL(const cl::Program & program,cl_program native)20 CLProgramCL::CLProgramCL(const cl::Program &program, cl_program native)
21     : CLProgramImpl(program), mNative(native)
22 {}
23 
~CLProgramCL()24 CLProgramCL::~CLProgramCL()
25 {
26     if (mNative->getDispatch().clReleaseProgram(mNative) != CL_SUCCESS)
27     {
28         ERR() << "Error while releasing CL program";
29     }
30 }
31 
build(const cl::DevicePtrs & devices,const char * options,cl::Program * notify)32 angle::Result CLProgramCL::build(const cl::DevicePtrs &devices,
33                                  const char *options,
34                                  cl::Program *notify)
35 {
36     std::vector<cl_device_id> nativeDevices;
37     for (const cl::DevicePtr &device : devices)
38     {
39         nativeDevices.emplace_back(device->getImpl<CLDeviceCL>().getNative());
40     }
41     const cl_uint numDevices = static_cast<cl_uint>(nativeDevices.size());
42     const cl_device_id *const nativeDevicesPtr =
43         !nativeDevices.empty() ? nativeDevices.data() : nullptr;
44     const cl::ProgramCB callback = notify != nullptr ? Callback : nullptr;
45     ANGLE_CL_TRY(mNative->getDispatch().clBuildProgram(mNative, numDevices, nativeDevicesPtr,
46                                                        options, callback, notify));
47     return angle::Result::Continue;
48 }
49 
compile(const cl::DevicePtrs & devices,const char * options,const cl::ProgramPtrs & inputHeaders,const char ** headerIncludeNames,cl::Program * notify)50 angle::Result CLProgramCL::compile(const cl::DevicePtrs &devices,
51                                    const char *options,
52                                    const cl::ProgramPtrs &inputHeaders,
53                                    const char **headerIncludeNames,
54                                    cl::Program *notify)
55 {
56     std::vector<cl_device_id> nativeDevices;
57     for (const cl::DevicePtr &device : devices)
58     {
59         nativeDevices.emplace_back(device->getImpl<CLDeviceCL>().getNative());
60     }
61     const cl_uint numDevices = static_cast<cl_uint>(nativeDevices.size());
62     const cl_device_id *const nativeDevicesPtr =
63         !nativeDevices.empty() ? nativeDevices.data() : nullptr;
64 
65     std::vector<cl_program> nativePrograms;
66     for (const cl::ProgramPtr &program : inputHeaders)
67     {
68         nativePrograms.emplace_back(program->getImpl<CLProgramCL>().getNative());
69     }
70     const cl_uint numInputHeaders = static_cast<cl_uint>(nativePrograms.size());
71     const cl_program *const inputHeadersPtr =
72         !nativePrograms.empty() ? nativePrograms.data() : nullptr;
73 
74     const cl::ProgramCB callback = notify != nullptr ? Callback : nullptr;
75     ANGLE_CL_TRY(mNative->getDispatch().clCompileProgram(mNative, numDevices, nativeDevicesPtr,
76                                                          options, numInputHeaders, inputHeadersPtr,
77                                                          headerIncludeNames, callback, notify));
78     return angle::Result::Continue;
79 }
80 
getInfo(cl::ProgramInfo name,size_t valueSize,void * value,size_t * valueSizeRet) const81 angle::Result CLProgramCL::getInfo(cl::ProgramInfo name,
82                                    size_t valueSize,
83                                    void *value,
84                                    size_t *valueSizeRet) const
85 {
86     ANGLE_CL_TRY(mNative->getDispatch().clGetProgramInfo(mNative, cl::ToCLenum(name), valueSize,
87                                                          value, valueSizeRet));
88     return angle::Result::Continue;
89 }
90 
getBuildInfo(const cl::Device & device,cl::ProgramBuildInfo name,size_t valueSize,void * value,size_t * valueSizeRet) const91 angle::Result CLProgramCL::getBuildInfo(const cl::Device &device,
92                                         cl::ProgramBuildInfo name,
93                                         size_t valueSize,
94                                         void *value,
95                                         size_t *valueSizeRet) const
96 {
97     ANGLE_CL_TRY(mNative->getDispatch().clGetProgramBuildInfo(
98         mNative, device.getImpl<CLDeviceCL>().getNative(), cl::ToCLenum(name), valueSize, value,
99         valueSizeRet));
100     return angle::Result::Continue;
101 }
102 
createKernel(const cl::Kernel & kernel,const char * name,CLKernelImpl::Ptr * kernelOut)103 angle::Result CLProgramCL::createKernel(const cl::Kernel &kernel,
104                                         const char *name,
105                                         CLKernelImpl::Ptr *kernelOut)
106 {
107     cl_int errorCode = CL_SUCCESS;
108 
109     const cl_kernel nativeKernel = mNative->getDispatch().clCreateKernel(mNative, name, &errorCode);
110     ANGLE_CL_TRY(errorCode);
111 
112     *kernelOut =
113         CLKernelImpl::Ptr(nativeKernel != nullptr ? new CLKernelCL(kernel, nativeKernel) : nullptr);
114     return angle::Result::Continue;
115 }
116 
createKernels(cl_uint numKernels,CLKernelImpl::CreateFuncs & createFuncs,cl_uint * numKernelsRet)117 angle::Result CLProgramCL::createKernels(cl_uint numKernels,
118                                          CLKernelImpl::CreateFuncs &createFuncs,
119                                          cl_uint *numKernelsRet)
120 {
121     if (numKernels == 0u)
122     {
123         ANGLE_CL_TRY(
124             mNative->getDispatch().clCreateKernelsInProgram(mNative, 0u, nullptr, numKernelsRet));
125     }
126 
127     std::vector<cl_kernel> nativeKernels(numKernels, nullptr);
128     ANGLE_CL_TRY(mNative->getDispatch().clCreateKernelsInProgram(
129         mNative, numKernels, nativeKernels.data(), numKernelsRet));
130     for (cl_kernel nativeKernel : nativeKernels)
131     {
132         createFuncs.emplace_back([nativeKernel](const cl::Kernel &kernel) {
133             return CLKernelImpl::Ptr(new CLKernelCL(kernel, nativeKernel));
134         });
135     }
136     return angle::Result::Continue;
137 }
138 
Callback(cl_program program,void * userData)139 void CLProgramCL::Callback(cl_program program, void *userData)
140 {
141     static_cast<cl::Program *>(userData)->callback();
142 }
143 
144 }  // namespace rx
145