这是来自OpenCL教程。我有:
void* args[4] = {(void*)5, (void*)123, NULL, NULL};
cl_mem mem_list[2] = {mem_d1, mem_d2}; // mem_d1 and mem_d2 are cl_mem objects
void* args_mem_loc[2] = {&args[2], &args[3]};
status = clEnqueueNativeKernel(*queue, nativeKernel, args, 4, 2, mem_list, args_mem_loc, 0, NULL, NULL); // http://www.khronos.org/registry/cl/sdk/1.0/docs/man/xhtml/clEnqueueNativeKernel.html
我一直收到编译器错误(在status = clEnqueueNativeKernel(* queue ...它正在讨论的参数是args_mem_loc)的行上。
error C2664: 'clEnqueueNativeKernel' : cannot convert parameter 7 from 'void *[2]' to 'const void **'
args_mem_loc是一个指向void指针数组的void指针,它使用的所有变量都是在堆栈上创建的(对吗?我非常肯定)。那么为什么编译器认为它是无效的[2]?
答案 0 :(得分:3)
此:
void* args_mem_loc[2] = {&args[2], &args[3]};
隐式转换为:
void **
不可隐式转换为:
const void **
因为您可以将const void *
分配给void *
并打破常规正确性。
编译器说args_mem_loc
是void *[2]
,因为它就是这样。如果要传递可以隐式转换为const void **
的数组,请将args_mem_loc
声明为const void *arg_mem_loc[2]= {...};
。
顺便提一下,该函数的const void **
参数应为const void * const *
;在这种情况下,隐式转换将起作用。这表明该函数不会修改args_mem_loc
,因为通过该指针进行分配是非法的,因此允许隐式转换。
答案 1 :(得分:1)
当你有一个指向数组的指针时,例如void* args_mem_loc[2]
,这意味着你有一个指向指针数组的指针,而不是另一个指针本身。基本上,您需要使用以下内容将args_mem_loc
作为指针传递给指针:
&args_mem_loc[0]
或
&args_mem_loc[1]
然后你会有一个指针(来自void *)指向另一个指针(数组的每个插槽中的内容)。