The OpenD Programming Language

1 // DerelictCL - a Derelict based dynamic binding for OpenCL
2 // written in the D programming language
3 //
4 // Copyright: MeinMein 2013-2014.
5 // License:   Boost License 1.0
6 //            (See accompanying file LICENSE_1_0.txt or copy at
7 //             http://www.boost.org/LICENSE_1_0.txt)
8 // Authors:   Gerbrand Kamphuis (meinmein.com),
9 //            Marvin Meeng (meinmein.com).
10 module derelict.opencl.cl;
11 
12 public
13 {
14     import derelict.util.exception;
15 
16     import derelict.opencl.types;
17     import derelict.opencl.constants;
18     import derelict.opencl.functions;
19 
20     import derelict.opencl.cl_ext;
21     import derelict.opencl.cl_egl;
22     import derelict.opencl.cl_gl;
23     import derelict.opencl.cl_gl_ext;
24     import derelict.opencl.cl_d3d10;
25     import derelict.opencl.cl_d3d11;
26     import derelict.opencl.cl_dx9_media_sharing;
27 }
28 
29 private
30 {
31     import std.algorithm;
32     import std.conv;
33 
34     import derelict.util.loader;
35     import derelict.util.system;
36 
37     static if(Derelict_OS_Windows)
38     {
39         enum libNames = "opencl.dll";
40     }
41     else static if(Derelict_OS_Mac)
42     {
43         enum libNames = "../Frameworks/OpenCL.framework/OpenCL, /Library/Frameworks/OpenCL.framework/OpenCL, /System/Library/Frameworks/OpenCL.framework/OpenCL";
44     }
45     else static if(Derelict_OS_Posix)
46     {
47         enum libNames = "libOpenCL.so.1,libOpenCL.so";
48     }
49     else
50         static assert(0, "Need to implement OpenCL libNames for this operating system.");
51 }
52 
53 class DerelictCLLoader : SharedLibLoader
54 {
55     public
56     {
57         CLVersion loadedVersion() @property
58         {
59             return _loadedVersion;
60         }
61 
62         CLVersion reload(CLVersion clVer)
63         {
64             // CLVersion depends on chosen platform & device.
65             // Here we assume this is handled by the developer.
66 
67             // (Alternatively, a CLContext could be passed as argument,
68             // and then the lowest found CLVersion in its devices could be used.)
69 
70             if(clVer <= CLVersion.CL10)
71             {
72                 // OpenCL 1.0 Deprecated in 1.1
73                 bindFunc(cast(void**)&clSetCommandQueueProperty, "clSetCommandQueueProperty");
74             }
75 
76             if(clVer >= CLVersion.CL11)
77             {
78                 // OpenCL 1.1
79                 bindFunc(cast(void**)&clCreateSubBuffer, "clCreateSubBuffer");
80                 bindFunc(cast(void**)&clSetMemObjectDestructorCallback, "clSetMemObjectDestructorCallback");
81                 bindFunc(cast(void**)&clCreateUserEvent, "clCreateUserEvent");
82                 bindFunc(cast(void**)&clSetUserEventStatus, "clSetUserEventStatus");
83                 bindFunc(cast(void**)&clSetEventCallback, "clSetEventCallback");
84                 bindFunc(cast(void**)&clEnqueueReadBufferRect, "clEnqueueReadBufferRect");
85                 bindFunc(cast(void**)&clEnqueueWriteBufferRect, "clEnqueueWriteBufferRect");
86                 bindFunc(cast(void**)&clEnqueueCopyBufferRect, "clEnqueueCopyBufferRect");
87             }
88 
89             if(clVer <= CLVersion.CL11)
90             {
91                 // OpenCL 1.1 Deprecated in 1.2
92                 bindFunc(cast(void**)&clCreateImage2D, "clCreateImage2D");
93                 bindFunc(cast(void**)&clCreateImage3D, "clCreateImage3D");
94                 bindFunc(cast(void**)&clEnqueueMarker, "clEnqueueMarker");
95                 bindFunc(cast(void**)&clEnqueueWaitForEvents, "clEnqueueWaitForEvents");
96                 bindFunc(cast(void**)&clEnqueueBarrier, "clEnqueueBarrier");
97                 bindFunc(cast(void**)&clUnloadCompiler, "clUnloadCompiler");
98                 bindFunc(cast(void**)&clGetExtensionFunctionAddress, "clGetExtensionFunctionAddress");
99             }
100 
101             if(clVer >= CLVersion.CL12)
102             {
103                 // OpenCL 1.2
104                 bindFunc(cast(void**)&clCreateSubDevices, "clCreateSubDevices");
105                 bindFunc(cast(void**)&clRetainDevice, "clRetainDevice");
106                 bindFunc(cast(void**)&clReleaseDevice, "clReleaseDevice");
107                 bindFunc(cast(void**)&clCreateImage, "clCreateImage");
108                 bindFunc(cast(void**)&clCreateProgramWithBuiltInKernels, "clCreateProgramWithBuiltInKernels");
109                 bindFunc(cast(void**)&clCompileProgram, "clCompileProgram");
110                 bindFunc(cast(void**)&clLinkProgram, "clLinkProgram");
111                 bindFunc(cast(void**)&clUnloadPlatformCompiler, "clUnloadPlatformCompiler");
112                 bindFunc(cast(void**)&clGetKernelArgInfo, "clGetKernelArgInfo");
113                 bindFunc(cast(void**)&clEnqueueFillBuffer, "clEnqueueFillBuffer");
114                 bindFunc(cast(void**)&clEnqueueFillImage, "clEnqueueFillImage");
115                 bindFunc(cast(void**)&clEnqueueMigrateMemObjects, "clEnqueueMigrateMemObjects");
116                 bindFunc(cast(void**)&clEnqueueMarkerWithWaitList, "clEnqueueMarkerWithWaitList");
117                 bindFunc(cast(void**)&clEnqueueBarrierWithWaitList, "clEnqueueBarrierWithWaitList");
118                 bindFunc(cast(void**)&clGetExtensionFunctionAddressForPlatform, "clGetExtensionFunctionAddressForPlatform");
119             }
120 
121 			if(clVer >= CLVersion.CL20)
122             {
123                 bindFunc(cast(void**)&clCreateCommandQueueWithProperties, "clCreateCommandQueueWithProperties");
124                 bindFunc(cast(void**)&clCreatePipe, "clCreatePipe");
125                 bindFunc(cast(void**)&clGetPipeInfo, "clGetPipeInfo");
126                 bindFunc(cast(void**)&clSVMAlloc, "clSVMAlloc");
127                 bindFunc(cast(void**)&clSVMFree, "clSVMFree");
128                 bindFunc(cast(void**)&clCreateSamplerWithProperties, "clCreateSamplerWithProperties");
129                 bindFunc(cast(void**)&clSetKernelArgSVMPointer, "clSetKernelArgSVMPointer");
130                 bindFunc(cast(void**)&clSetKernelExecInfo, "clSetKernelExecInfo");
131                 bindFunc(cast(void**)&clEnqueueSVMFree, "clEnqueueSVMFree");
132                 bindFunc(cast(void**)&clEnqueueSVMMemcpy, "clEnqueueSVMMemcpy");
133                 bindFunc(cast(void**)&clEnqueueSVMMemFill, "clEnqueueSVMMemFill");
134                 bindFunc(cast(void**)&clEnqueueSVMMap, "clEnqueueSVMMap");
135                 bindFunc(cast(void**)&clEnqueueSVMUnmap, "clEnqueueSVMUnmap");
136             }
137 
138             if(clVer >= CLVersion.CL21)
139             {
140 			    bindFunc(cast(void**)&clSetDefaultDeviceCommandQueue, "clSetDefaultDeviceCommandQueue");
141 			    bindFunc(cast(void**)&clGetDeviceAndHostTimer, "clGetDeviceAndHostTimer");
142 			    bindFunc(cast(void**)&clGetHostTimer, "clGetHostTimer");
143 			    bindFunc(cast(void**)&clCreateProgramWithIL, "clCreateProgramWithIL");
144 			    bindFunc(cast(void**)&clCloneKernel, "clCloneKernel");
145 			    bindFunc(cast(void**)&clGetKernelSubGroupInfo, "clGetKernelSubGroupInfo");
146             }
147 
148             if(clVer >= CLVersion.CL22)
149             {
150                 bindFunc(cast(void**)&clSetProgramReleaseCallback, "clSetProgramReleaseCallback");
151                 bindFunc(cast(void**)&clSetProgramSpecializationConstant, "clSetProgramSpecializationConstant");
152             }
153 
154             derelict.opencl.cl_ext.reload(&bindFunc, clVer);
155             derelict.opencl.cl_gl_ext.reload(&bindFunc, clVer);
156             derelict.opencl.cl_gl.reload(&bindFunc, clVer);
157             
158             if(Derelict_OS_Windows)
159             {
160                 derelict.opencl.cl_d3d10.reload(&bindFunc, clVer);
161                 derelict.opencl.cl_d3d11.reload(&bindFunc, clVer);
162                 derelict.opencl.cl_dx9_media_sharing.reload(&bindFunc, clVer);
163             }
164 
165             _loadedVersion = clVer;
166             return clVer;
167         }
168 
169         // Load official extensions
170         // In OpenCL 1.2 this is cl_platform dependent
171         void loadEXT(cl_platform_id platform = null)
172         {
173             if(_loadedVersion >= CLVersion.CL12 && platform is null)
174                 throw new DerelictException(`OpenCL 1.2 requires a cl_platform_id to load official extension functions`);
175 
176             derelict.opencl.cl_ext.loadEXT(_loadedVersion, platform);
177             derelict.opencl.cl_egl.loadEXT(_loadedVersion, platform);
178             derelict.opencl.cl_gl_ext.loadEXT(_loadedVersion, platform);
179             derelict.opencl.cl_gl.loadEXT(_loadedVersion, platform);
180             
181             if(Derelict_OS_Windows)
182             {
183                 derelict.opencl.cl_d3d10.loadEXT(_loadedVersion, platform);
184                 derelict.opencl.cl_d3d11.loadEXT(_loadedVersion, platform);
185                 derelict.opencl.cl_dx9_media_sharing.loadEXT(_loadedVersion, platform);
186             }
187         }
188     }
189 
190     protected
191     {
192         this()
193         {
194             super(libNames);
195         }
196 
197         override void loadSymbols()
198         {
199             // OpenCL 1.0
200             bindFunc(cast(void**)&clGetPlatformIDs, "clGetPlatformIDs");
201             bindFunc(cast(void**)&clGetPlatformInfo, "clGetPlatformInfo");
202             bindFunc(cast(void**)&clGetDeviceIDs, "clGetDeviceIDs");
203             bindFunc(cast(void**)&clGetDeviceInfo, "clGetDeviceInfo");
204             bindFunc(cast(void**)&clCreateContext, "clCreateContext");
205             bindFunc(cast(void**)&clCreateContextFromType, "clCreateContextFromType");
206             bindFunc(cast(void**)&clRetainContext, "clRetainContext");
207             bindFunc(cast(void**)&clReleaseContext, "clReleaseContext");
208             bindFunc(cast(void**)&clGetContextInfo, "clGetContextInfo");
209             bindFunc(cast(void**)&clCreateCommandQueue, "clCreateCommandQueue");
210             bindFunc(cast(void**)&clRetainCommandQueue, "clRetainCommandQueue");
211             bindFunc(cast(void**)&clReleaseCommandQueue, "clReleaseCommandQueue");
212             bindFunc(cast(void**)&clGetCommandQueueInfo, "clGetCommandQueueInfo");
213             bindFunc(cast(void**)&clCreateBuffer, "clCreateBuffer");
214             bindFunc(cast(void**)&clRetainMemObject, "clRetainMemObject");
215             bindFunc(cast(void**)&clReleaseMemObject, "clReleaseMemObject");
216             bindFunc(cast(void**)&clGetSupportedImageFormats, "clGetSupportedImageFormats");
217             bindFunc(cast(void**)&clGetMemObjectInfo, "clGetMemObjectInfo");
218             bindFunc(cast(void**)&clGetImageInfo, "clGetImageInfo");
219             bindFunc(cast(void**)&clCreateSampler, "clCreateSampler");
220             bindFunc(cast(void**)&clRetainSampler, "clRetainSampler");
221             bindFunc(cast(void**)&clReleaseSampler, "clReleaseSampler");
222             bindFunc(cast(void**)&clGetSamplerInfo, "clGetSamplerInfo");
223             bindFunc(cast(void**)&clCreateProgramWithSource, "clCreateProgramWithSource");
224             bindFunc(cast(void**)&clCreateProgramWithBinary, "clCreateProgramWithBinary");
225             bindFunc(cast(void**)&clRetainProgram, "clRetainProgram");
226             bindFunc(cast(void**)&clReleaseProgram, "clReleaseProgram");
227             bindFunc(cast(void**)&clBuildProgram, "clBuildProgram");
228             bindFunc(cast(void**)&clGetProgramInfo, "clGetProgramInfo");
229             bindFunc(cast(void**)&clGetProgramBuildInfo, "clGetProgramBuildInfo");
230             bindFunc(cast(void**)&clCreateKernel, "clCreateKernel");
231             bindFunc(cast(void**)&clCreateKernelsInProgram, "clCreateKernelsInProgram");
232             bindFunc(cast(void**)&clRetainKernel, "clRetainKernel");
233             bindFunc(cast(void**)&clReleaseKernel, "clReleaseKernel");
234             bindFunc(cast(void**)&clSetKernelArg, "clSetKernelArg");
235             bindFunc(cast(void**)&clGetKernelInfo, "clGetKernelInfo");
236             bindFunc(cast(void**)&clGetKernelWorkGroupInfo, "clGetKernelWorkGroupInfo");
237             bindFunc(cast(void**)&clWaitForEvents, "clWaitForEvents");
238             bindFunc(cast(void**)&clGetEventInfo, "clGetEventInfo");
239             bindFunc(cast(void**)&clRetainEvent, "clRetainEvent");
240             bindFunc(cast(void**)&clReleaseEvent, "clReleaseEvent");
241             bindFunc(cast(void**)&clGetEventProfilingInfo, "clGetEventProfilingInfo");
242             bindFunc(cast(void**)&clFlush, "clFlush");
243             bindFunc(cast(void**)&clFinish, "clFinish");
244             bindFunc(cast(void**)&clEnqueueReadBuffer, "clEnqueueReadBuffer");
245             bindFunc(cast(void**)&clEnqueueWriteBuffer, "clEnqueueWriteBuffer");
246             bindFunc(cast(void**)&clEnqueueCopyBuffer, "clEnqueueCopyBuffer");
247             bindFunc(cast(void**)&clEnqueueReadImage, "clEnqueueReadImage");
248             bindFunc(cast(void**)&clEnqueueWriteImage, "clEnqueueWriteImage");
249             bindFunc(cast(void**)&clEnqueueCopyImage, "clEnqueueCopyImage");
250             bindFunc(cast(void**)&clEnqueueCopyImageToBuffer, "clEnqueueCopyImageToBuffer");
251             bindFunc(cast(void**)&clEnqueueCopyBufferToImage, "clEnqueueCopyBufferToImage");
252             bindFunc(cast(void**)&clEnqueueMapBuffer, "clEnqueueMapBuffer");
253             bindFunc(cast(void**)&clEnqueueMapImage, "clEnqueueMapImage");
254             bindFunc(cast(void**)&clEnqueueUnmapMemObject, "clEnqueueUnmapMemObject");
255             bindFunc(cast(void**)&clEnqueueNDRangeKernel, "clEnqueueNDRangeKernel");
256             bindFunc(cast(void**)&clEnqueueTask, "clEnqueueTask");
257             bindFunc(cast(void**)&clEnqueueNativeKernel, "clEnqueueNativeKernel");
258 
259             derelict.opencl.cl_ext.loadSymbols(&bindFunc);
260             derelict.opencl.cl_gl_ext.loadSymbols(&bindFunc);
261             derelict.opencl.cl_gl.loadSymbols(&bindFunc);
262 
263             if(Derelict_OS_Windows)
264             {
265                 derelict.opencl.cl_d3d10.loadSymbols(&bindFunc);
266                 derelict.opencl.cl_d3d11.loadSymbols(&bindFunc);
267                 derelict.opencl.cl_dx9_media_sharing.loadSymbols(&bindFunc);
268             }
269 
270             _loadedVersion = CLVersion.CL10;
271         }
272     }
273 
274     private
275     {
276         CLVersion _loadedVersion;
277     }
278 }
279 
280 __gshared DerelictCLLoader DerelictCL;
281 
282 shared static this()
283 {
284     DerelictCL = new DerelictCLLoader;
285 }