summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/cl_driver.h3
-rw-r--r--libclapi/cl_kernel.c32
2 files changed, 34 insertions, 1 deletions
diff --git a/include/cl_driver.h b/include/cl_driver.h
index fe0021c5..c71a1532 100644
--- a/include/cl_driver.h
+++ b/include/cl_driver.h
@@ -48,7 +48,8 @@ typedef struct _cl_driver {
cl_int (*release_program)(cl_program program, const cl_device_id device);
cl_int (*get_program_kernel_names)(cl_program program, const cl_device_id device, char *names,
cl_uint name_sz, cl_uint* ret_sz, cl_uint* ker_num);
-
+ cl_int (*create_kernel)(cl_kernel kernel, const cl_device_id device);
+ cl_int (*release_kernel)(cl_kernel kernel, const cl_device_id device);
diff --git a/libclapi/cl_kernel.c b/libclapi/cl_kernel.c
index e03bd29d..91083219 100644
--- a/libclapi/cl_kernel.c
+++ b/libclapi/cl_kernel.c
@@ -26,6 +26,7 @@
#include "cl_kernel.h"
#include "cl_program.h"
#include "cl_context.h"
+#include "cl_device_id.h"
static void cl_argument_release(cl_argument arg)
{
@@ -97,10 +98,19 @@ LOCAL void cl_retain_kernel(cl_kernel k)
LOCAL void cl_release_kernel(cl_kernel k)
{
+ cl_uint i;
+
assert(k);
if (atomic_dec(&k->ref_n) > 1)
return;
+ for (i = 0; i < k->program->ctx->device_num; i++) {
+ if (k->program->valid[i] == 0) // We do not build for that device.
+ continue;
+
+ k->program->ctx->devices[i]->driver->release_kernel(k, k->program->ctx->devices[i]);
+ }
+
cl_kernel_delete(k);
}
@@ -108,6 +118,8 @@ LOCAL cl_kernel cl_create_kernel(cl_program p, char* kernel_name, cl_int* errcod
{
cl_kernel k = NULL;
cl_int err = CL_SUCCESS;
+ cl_uint created = 0;
+ cl_uint i;
k = cl_kernel_new(p, kernel_name);
if (UNLIKELY(k == NULL)) {
@@ -115,11 +127,31 @@ LOCAL cl_kernel cl_create_kernel(cl_program p, char* kernel_name, cl_int* errcod
goto error;
}
+ for (i = 0; i < p->ctx->device_num; i++) {
+ if (p->valid[i] == 0) // We do not build for that device.
+ continue;
+
+ err = p->ctx->devices[i]->driver->create_kernel(k, p->ctx->devices[i]);
+ if (err != CL_SUCCESS)
+ break;
+
+ created = i;
+ }
+
if (errcode_ret)
*errcode_ret = err;
return k;
error:
+ if (created) {
+ for (i = 0; i < created; i++) {
+ if (p->valid[i] == 0) // We do not build for that device.
+ continue;
+
+ p->ctx->devices[i]->driver->release_kernel(k, p->ctx->devices[i]);
+ }
+ }
+
if (k)
cl_kernel_delete(k);
if (errcode_ret)