SCM Repository
Annotation of /branches/vis12-cl/src/lib/cl-target/ocl-image.c
Parent Directory
|
Revision Log
Revision 3349 - (view) (download) (as text)
1 : | jhr | 3118 | /*! \file ocl-image.c |
2 : | * | ||
3 : | * \author John Reppy | ||
4 : | * | ||
5 : | * Support for loading | ||
6 : | */ | ||
7 : | |||
8 : | /* | ||
9 : | jhr | 3349 | * This code is part of the Diderot Project (http://diderot-language.cs.uchicago.edu) |
10 : | * | ||
11 : | * COPYRIGHT (c) 2015 The University of Chicago | ||
12 : | jhr | 3118 | * All rights reserved. |
13 : | */ | ||
14 : | |||
15 : | #ifndef DIDEROT_TARGET_CL | ||
16 : | # define DIDEROT_TARGET_CL | ||
17 : | #endif | ||
18 : | |||
19 : | jhr | 3120 | #include "Diderot/diderot.h" |
20 : | jhr | 3118 | #include "Diderot/shadow-types.h" |
21 : | |||
22 : | // Report an OpenCL error | ||
23 : | STATIC_INLINE void ReportOCLError (OCLWorldPrefix_t *wrld, cl_int sts, const char *msg) | ||
24 : | { | ||
25 : | biffMsgAddf (wrld->errors, "%s: %s", msg, Diderot_OCLErrorString(sts)); | ||
26 : | } | ||
27 : | |||
28 : | // Check the return status of a CL API call. If there is an error, add a message to | ||
29 : | // the biff buffer and return true, otherwise return false. | ||
30 : | STATIC_INLINE bool CheckOCLStatus (OCLWorldPrefix_t *wrld, cl_int sts, const char *msg) | ||
31 : | { | ||
32 : | if (sts != CL_SUCCESS) { | ||
33 : | ReportOCLError (wrld, sts, msg); | ||
34 : | return true; | ||
35 : | } | ||
36 : | else | ||
37 : | return false; | ||
38 : | } | ||
39 : | |||
40 : | //! load a 1D image into a GPU-side global. | ||
41 : | //! \param wrld the world | ||
42 : | //! \param globals the GPU-side memory object that holds the program globals | ||
43 : | //! \param img the name of the image nrrd file | ||
44 : | //! \param initKern the kernel that initializes the GPU-side global image in question | ||
45 : | //! \param obj the GPU-side memory object that is allocated to hold the image data. | ||
46 : | //! \return true if there are any errors | ||
47 : | // | ||
48 : | bool Diderot_LoadGPUImage1D (OCLWorldPrefix_t *wrld, cl_mem globals, const char *imgName, cl_kernel initKern, cl_mem *objOut) | ||
49 : | { | ||
50 : | Diderot_image1D_t *img; | ||
51 : | Shadow_image1D_t shadow; | ||
52 : | cl_int sts; | ||
53 : | |||
54 : | if (Diderot_LoadImage1D((WorldPrefix_t *)wrld, imgName, &img)) { | ||
55 : | return true; | ||
56 : | } | ||
57 : | |||
58 : | // initialize the shadow object | ||
59 : | shadow.size[0] = img->size[0]; | ||
60 : | shadow.s = img->s; | ||
61 : | shadow.t = img->t; | ||
62 : | |||
63 : | // allocate and initialize GPU-side image object | ||
64 : | jhr | 3135 | cl_mem imgObj = clCreateBuffer(wrld->context, CL_MEM_READ_ONLY|CL_MEM_COPY_HOST_PTR, sizeof(shadow), &shadow, &sts); |
65 : | jhr | 3118 | if (CheckOCLStatus (wrld, sts, "error allocating GPU memory for image")) { |
66 : | Diderot_FreeImage1D((WorldPrefix_t *)wrld, img); | ||
67 : | return true; | ||
68 : | } | ||
69 : | |||
70 : | // allocate and initialize GPU-side image data | ||
71 : | jhr | 3135 | cl_mem dataObj = clCreateBuffer(wrld->context, CL_MEM_READ_ONLY|CL_MEM_COPY_HOST_PTR, img->dataSzb, img->data, &sts); |
72 : | jhr | 3118 | if (CheckOCLStatus (wrld, sts, "error allocating GPU memory for image data")) { |
73 : | Diderot_FreeImage1D((WorldPrefix_t *)wrld, img); | ||
74 : | clReleaseMemObject(imgObj); | ||
75 : | return true; | ||
76 : | } | ||
77 : | |||
78 : | /* invoke the initialization kernel. s*/ | ||
79 : | if (((sts = clSetKernelArg (initKern, 0, sizeof(cl_mem), &globals)) != CL_SUCCESS) | ||
80 : | || ((sts = clSetKernelArg (initKern, 1, sizeof(cl_mem), &imgObj)) != CL_SUCCESS) | ||
81 : | jhr | 3159 | || ((sts = clSetKernelArg (initKern, 2, sizeof(cl_mem), &dataObj)) != CL_SUCCESS) |
82 : | || ((sts = clEnqueueTask (wrld->cmdQ, initKern, 0, NULL, NULL)) != CL_SUCCESS)) | ||
83 : | jhr | 3118 | { |
84 : | ReportOCLError (wrld, sts, "error enqueuing image initialization kernel"); | ||
85 : | Diderot_FreeImage1D((WorldPrefix_t *)wrld, img); | ||
86 : | clReleaseMemObject(imgObj); | ||
87 : | clReleaseMemObject(dataObj); | ||
88 : | return true; | ||
89 : | } | ||
90 : | |||
91 : | // free CPU-side data | ||
92 : | Diderot_FreeImage1D((WorldPrefix_t *)wrld, img); | ||
93 : | |||
94 : | // free GPU-side shadow object | ||
95 : | if (clReleaseMemObject(imgObj) != CL_SUCCESS) { | ||
96 : | ReportOCLError (wrld, sts, "error freeing output kernel"); | ||
97 : | clReleaseMemObject(dataObj); | ||
98 : | return true; | ||
99 : | } | ||
100 : | |||
101 : | // return data object for future release | ||
102 : | *objOut = dataObj; | ||
103 : | |||
104 : | return false; | ||
105 : | |||
106 : | } // Diderot_LoadGPUImage1D | ||
107 : | |||
108 : | //! load a 2D image into a GPU-side global. | ||
109 : | //! \param wrld the world | ||
110 : | //! \param globals the GPU-side memory object that holds the program globals | ||
111 : | //! \param img the name of the image nrrd file | ||
112 : | //! \param initKern the kernel that initializes the GPU-side global image in question | ||
113 : | //! \param obj the GPU-side memory object that is allocated to hold the image data. | ||
114 : | //! \return true if there are any errors | ||
115 : | // | ||
116 : | bool Diderot_LoadGPUImage2D (OCLWorldPrefix_t *wrld, cl_mem globals, const char *imgName, cl_kernel initKern, cl_mem *objOut) | ||
117 : | { | ||
118 : | Diderot_image2D_t *img; | ||
119 : | Shadow_image2D_t shadow; | ||
120 : | cl_int sts; | ||
121 : | |||
122 : | if (Diderot_LoadImage2D((WorldPrefix_t *)wrld, imgName, &img)) { | ||
123 : | return true; | ||
124 : | } | ||
125 : | |||
126 : | // initialize the shadow object | ||
127 : | for (int i = 0; i < 2; i++) { | ||
128 : | shadow.size[i] = img->size[i]; | ||
129 : | ShadowVec2 (&(shadow.w2i[i]), img->w2i[i].v); | ||
130 : | ShadowVec2 (&(shadow.w2iT[i]), img->w2iT[i].v); | ||
131 : | } | ||
132 : | ShadowVec2 (&shadow.tVec, img->tVec); | ||
133 : | |||
134 : | // allocate and initialize GPU-side image object | ||
135 : | jhr | 3135 | cl_mem imgObj = clCreateBuffer(wrld->context, CL_MEM_READ_ONLY|CL_MEM_COPY_HOST_PTR, sizeof(shadow), &shadow, &sts); |
136 : | jhr | 3118 | if (CheckOCLStatus (wrld, sts, "error allocating GPU memory for image")) { |
137 : | Diderot_FreeImage2D((WorldPrefix_t *)wrld, img); | ||
138 : | return true; | ||
139 : | } | ||
140 : | |||
141 : | // allocate and initialize GPU-side image data | ||
142 : | jhr | 3135 | cl_mem dataObj = clCreateBuffer(wrld->context, CL_MEM_READ_ONLY|CL_MEM_COPY_HOST_PTR, img->dataSzb, img->data, &sts); |
143 : | jhr | 3118 | if (CheckOCLStatus (wrld, sts, "error allocating GPU memory for image data")) { |
144 : | Diderot_FreeImage2D((WorldPrefix_t *)wrld, img); | ||
145 : | clReleaseMemObject(imgObj); | ||
146 : | return true; | ||
147 : | } | ||
148 : | |||
149 : | /* invoke the initialization kernel. s*/ | ||
150 : | if (((sts = clSetKernelArg (initKern, 0, sizeof(cl_mem), &globals)) != CL_SUCCESS) | ||
151 : | || ((sts = clSetKernelArg (initKern, 1, sizeof(cl_mem), &imgObj)) != CL_SUCCESS) | ||
152 : | jhr | 3159 | || ((sts = clSetKernelArg (initKern, 2, sizeof(cl_mem), &dataObj)) != CL_SUCCESS) |
153 : | || ((sts = clEnqueueTask (wrld->cmdQ, initKern, 0, NULL, NULL)) != CL_SUCCESS)) | ||
154 : | jhr | 3118 | { |
155 : | ReportOCLError (wrld, sts, "error enqueuing image initialization kernel"); | ||
156 : | Diderot_FreeImage2D((WorldPrefix_t *)wrld, img); | ||
157 : | clReleaseMemObject(imgObj); | ||
158 : | clReleaseMemObject(dataObj); | ||
159 : | return true; | ||
160 : | } | ||
161 : | |||
162 : | // free CPU-side data | ||
163 : | Diderot_FreeImage2D((WorldPrefix_t *)wrld, img); | ||
164 : | |||
165 : | // free GPU-side shadow object | ||
166 : | if (clReleaseMemObject(imgObj) != CL_SUCCESS) { | ||
167 : | ReportOCLError (wrld, sts, "error freeing output kernel"); | ||
168 : | clReleaseMemObject(dataObj); | ||
169 : | return true; | ||
170 : | } | ||
171 : | |||
172 : | // return data object for future release | ||
173 : | *objOut = dataObj; | ||
174 : | |||
175 : | return false; | ||
176 : | |||
177 : | } // Diderot_LoadGPUImage2D | ||
178 : | |||
179 : | //! load a 3D image into a GPU-side global. | ||
180 : | //! \param wrld the world | ||
181 : | //! \param globals the GPU-side memory object that holds the program globals | ||
182 : | //! \param img the name of the image nrrd file | ||
183 : | //! \param initKern the kernel that initializes the GPU-side global image in question | ||
184 : | //! \param obj the GPU-side memory object that is allocated to hold the image data. | ||
185 : | //! \return true if there are any errors | ||
186 : | // | ||
187 : | bool Diderot_LoadGPUImage3D (OCLWorldPrefix_t *wrld, cl_mem globals, const char *imgName, cl_kernel initKern, cl_mem *objOut) | ||
188 : | { | ||
189 : | Diderot_image3D_t *img; | ||
190 : | Shadow_image3D_t shadow; | ||
191 : | cl_int sts; | ||
192 : | |||
193 : | if (Diderot_LoadImage3D((WorldPrefix_t *)wrld, imgName, &img)) { | ||
194 : | return true; | ||
195 : | } | ||
196 : | |||
197 : | // initialize the shadow object | ||
198 : | for (int i = 0; i < 3; i++) { | ||
199 : | shadow.size[i] = img->size[i]; | ||
200 : | ShadowVec3 (&(shadow.w2i[i]), img->w2i[i].v); | ||
201 : | ShadowVec3 (&(shadow.w2iT[i]), img->w2iT[i].v); | ||
202 : | } | ||
203 : | ShadowVec3 (&shadow.tVec, img->tVec); | ||
204 : | |||
205 : | // allocate and initialize GPU-side image object | ||
206 : | jhr | 3135 | cl_mem imgObj = clCreateBuffer(wrld->context, CL_MEM_READ_ONLY|CL_MEM_COPY_HOST_PTR, sizeof(shadow), &shadow, &sts); |
207 : | jhr | 3118 | if (CheckOCLStatus (wrld, sts, "error allocating GPU memory for image")) { |
208 : | Diderot_FreeImage3D((WorldPrefix_t *)wrld, img); | ||
209 : | return true; | ||
210 : | } | ||
211 : | |||
212 : | // allocate and initialize GPU-side image data | ||
213 : | jhr | 3135 | cl_mem dataObj = clCreateBuffer(wrld->context, CL_MEM_READ_ONLY|CL_MEM_COPY_HOST_PTR, img->dataSzb, img->data, &sts); |
214 : | jhr | 3118 | if (CheckOCLStatus (wrld, sts, "error allocating GPU memory for image data")) { |
215 : | Diderot_FreeImage3D((WorldPrefix_t *)wrld, img); | ||
216 : | clReleaseMemObject(imgObj); | ||
217 : | return true; | ||
218 : | } | ||
219 : | |||
220 : | /* invoke the initialization kernel. s*/ | ||
221 : | if (((sts = clSetKernelArg (initKern, 0, sizeof(cl_mem), &globals)) != CL_SUCCESS) | ||
222 : | || ((sts = clSetKernelArg (initKern, 1, sizeof(cl_mem), &imgObj)) != CL_SUCCESS) | ||
223 : | jhr | 3159 | || ((sts = clSetKernelArg (initKern, 2, sizeof(cl_mem), &dataObj)) != CL_SUCCESS) |
224 : | || ((sts = clEnqueueTask (wrld->cmdQ, initKern, 0, NULL, NULL)) != CL_SUCCESS)) | ||
225 : | jhr | 3118 | { |
226 : | ReportOCLError (wrld, sts, "error enqueuing image initialization kernel"); | ||
227 : | Diderot_FreeImage3D((WorldPrefix_t *)wrld, img); | ||
228 : | clReleaseMemObject(imgObj); | ||
229 : | clReleaseMemObject(dataObj); | ||
230 : | return true; | ||
231 : | } | ||
232 : | |||
233 : | // free CPU-side data | ||
234 : | Diderot_FreeImage3D((WorldPrefix_t *)wrld, img); | ||
235 : | |||
236 : | // free GPU-side shadow object | ||
237 : | if (clReleaseMemObject(imgObj) != CL_SUCCESS) { | ||
238 : | ReportOCLError (wrld, sts, "error freeing output kernel"); | ||
239 : | clReleaseMemObject(dataObj); | ||
240 : | return true; | ||
241 : | } | ||
242 : | |||
243 : | // return data object for future release | ||
244 : | *objOut = dataObj; | ||
245 : | |||
246 : | return false; | ||
247 : | |||
248 : | } // Diderot_LoadGPUImage3D |
root@smlnj-gforge.cs.uchicago.edu | ViewVC Help |
Powered by ViewVC 1.0.0 |