我是OpenCL的新手,正在阅读OpenCL in Action一书。有一个简单的问题,我不理解它:如何将值传递给内核并从内核返回它们。
首先,我们是否应该始终通过地址将参数传递给内核?
然后,我在下面有两个简单的内核示例。在第一个中,虽然输出是指针作为函数参数,但在内核体中我们从未使用*输出。在另一个内核中,* s1和* s2用作函数参数,我们实际上将值赋给* s1和* s2而不是s1和s2。任何人都可以告诉我为什么在第一个内核中将值赋给输出(而不是*输出),而在第二个内核中,我们将值赋给* s1和* s2(而不是s1和s2)。
我查看了很多资源,找到了传递和返回内核之间值的一般方法,我找不到任何一般规则。
以下是内核:
__kernel void id_check(__global float *output) {
/* Access work-item/work-group information */
size_t global_id_0 = get_global_id(0);
size_t global_id_1 = get_global_id(1);
size_t global_size_0 = get_global_size(0);
size_t offset_0 = get_global_offset(0);
size_t offset_1 = get_global_offset(1);
size_t local_id_0 = get_local_id(0);
size_t local_id_1 = get_local_id(1);
/* Determine array index */
int index_0 = global_id_0 - offset_0;
int index_1 = global_id_1 - offset_1;
int index = index_1 * global_size_0 + index_0;
/* Set float data */
float f = global_id_0 * 10.0f + global_id_1 * 1.0f;
f += local_id_0 * 0.1f + local_id_1 * 0.01f;
output[index] = f;
}
__kernel void select_test(__global float4 *s1,
__global uchar2 *s2) {
/* Execute select */
int4 mask1 = (int4)(-1, 0, -1, 0);
float4 input1 = (float4)(0.25f, 0.5f, 0.75f, 1.0f);
float4 input2 = (float4)(1.25f, 1.5f, 1.75f, 2.0f);
*s1 = select(input1, input2, mask1);
/* Execute bitselect */
uchar2 mask2 = (uchar2)(0xAA, 0x55);
uchar2 input3 = (uchar2)(0x0F, 0x0F);
uchar2 input4 = (uchar2)(0x33, 0x33);
*s2 = bitselect(input3, input4, mask2);
}
答案 0 :(得分:2)
您的问题不在于OpenCL,而在于C语言本身。请阅读一本关于C语言如何工作的书。你问的问题是一个非常基本的问题。
当你有一个指针(输出,s1,s2)时,你可以通过多种方式访问它。 output
引用指针(地址),*output
引用第一个元素(或指针指向的单个元素)的值,output[i]
引用i
元素值。
*output
和output[0]
相同,以及*(output+1)
和output[1]
。