2012-04-08 3 views
2

Так что я продолжаю запутываться в странные ошибки, когда я называю свои ядра; заявленный максимальный размер рабочей группы ядра равен единице, а размер рабочей группы моего устройства (мой Macbook) явно выше. Какие возможные причины могут возникнуть для ядер, ограничивающих код одной рабочей группой? Вот один из моих ядер:Ограничение на размер рабочей группы ядра OpenCL

__kernel 
void termination_kernel(const int Elements, 
        __global float* c_I, 
        __global float* c_Ihat, 
        __global float* c_rI, 
        __local float* s_a) 
{ 
    const int bdim = 128; 
    int n = get_global_id(0); 
    const int tx = get_local_id(0); // thread index in thread-block (0-indexed) 
    const int bx = get_group_id(0); // block index (0-indexed) 
    const int gx = get_num_groups(0); 

    // is thread in range for the addition 
    float d = 0.f; 
    while(n < Elements){ 
    d += pow(c_I[n] - c_Ihat[n], 2); 
    n += gx * bdim; 
    } 

    // assume bx power of 2 
    int alive = bdim/2; 
    s_a[tx] = d; 
    barrier(CLK_LOCAL_MEM_FENCE); 

    while(alive > 1){ 
    if(tx < alive) 
     s_a[tx] += s_a[tx + alive]; 
    alive /= 2; 
    barrier(CLK_LOCAL_MEM_FENCE); 
    } 

    if(tx == 0) 
    c_rI[bx] = s_a[0] + s_a[1]; 
} 

и ошибка Возвращается

OpenCL Error (via pfn_notify): [CL_INVALID_WORK_GROUP_SIZE] : OpenCL Error : clEnqueueNDRangeKernel  
failed: total work group size (128) is greater than the device can support (1) 
OpenCL Error: 'clEnqueueNDRangeKernel(queue, kernel_N, dim, NULL, global_N, local_N, 0, NULL, NULL)' 

Я знаю, что он говорит, что ограничение на устройстве, но отладка показывает, что

CL_DEVICE_MAX_WORK_GROUP_SIZE = 1024 

и

CL_KERNEL_WORK_GROUP_SIZE = 1 

Ядро против вызывается

char *KernelSource_T = readSource("Includes/termination_kernel.cl"); 
    cl_program program_T = clCreateProgramWithSource(context, 1, (const char **) &KernelSource_T, NULL, &err); 
    clBuildProgram(program_T, 1, &device, flags, NULL, NULL); 
    cl_kernel kernel_T = clCreateKernel(program_T, "termination_kernel", &err); 

Я бы включил функцию вызова, но я не уверен, что это актуально; моя интуиция заключается в том, что это что-то в коде ядра, которое вынуждает ограничение. Есть идеи? Заранее спасибо за помощь!

+0

Вы должны показать остальную часть исходного кода - Enqueue и SetArgs команды. –

+0

На каком оборудовании вы используете код? – virtuallinux

ответ

0

Надеемся, что количество локальной памяти avilable меньше для этого размера рабочей группы. Можете ли вы показать аргументы? , Вы можете попытаться уменьшить размер рабочей группы, начиная с 2,4,8,16,32,64,128, так что убедитесь, что ее мощность равна 2.

0

CL_KERNEL_WORK_GROUP_SIZE сообщает, насколько велика максимальный размер рабочей группы для этого конкретное ядро. Время выполнения OpenCL определяет это путем проверки кода ядра. CL_KERNEL_WORK_GROUP_SIZE будет числом, меньшим или равным CL_DEVICE_MAX_WORK_GROUP_SIZE.

2

Apple OpenCL не поддерживает рабочие группы, большие, чем [1, 1, 1] на процессоре. Я понятия не имею, почему, но так было, по крайней мере, до OSX 10.9.2. Тем не менее, большие рабочие группы отлично подходят для GPU.

+0

Это вещь OSX. В Linux большие размеры рабочих групп хороши при работе на процессоре. В linux один и тот же cl-код в 3,5 раза быстрее для меня. Является ли OSX OpenCL просто сломанным для процессора? – Bram

0

Прошло время с answer of Tomi, и кажется, что Apple стала немного более гибкой в ​​этом аспекте. В моей OS X 10.12.3 (все еще OpenCL 1.2) в первом измерении можно использовать до CL_DEVICE_MAX_WORK_GROUP_SIZE.

Согласно спецификации, также можно получить максимальное количество рабочих групп для каждого измерения через CL_DEVICE_MAX_WORK_ITEM_SIZES согласно documentation

Смежные вопросы