内核中的Opencl循环

内核中的Opencl循环,opencl,reduction,Opencl,Reduction,在代码块中有我的内核函数。它基本上计算出哪个点距离所有簇最远,结果保存在长度[3](点的id)中,并输出[0]到所属簇的距离。while片段做一个简单的求和归约。我知道这不是最好的方法,但我需要理解为什么一个集群的代码工作正常,而两个或更多集群返回错误的值 __kernel void computeDistances(__global t_cluster *points,__global t_cluster *clusters, __global float *output,__glob

在代码块中有我的内核函数。它基本上计算出哪个点距离所有簇最远,结果保存在长度[3](点的id)中,并输出[0]到所属簇的距离。while片段做一个简单的求和归约。我知道这不是最好的方法,但我需要理解为什么一个集群的代码工作正常,而两个或更多集群返回错误的值

__kernel void computeDistances(__global t_cluster *points,__global t_cluster *clusters,     __global float *output,__global t_cluster *support,__global short *lengths)
{
    int threadId = get_global_id(0);
    float bestVal = 0;
    int counter, offset;

    short idPoint, idCluster;
    for(idPoint = 0; idPoint < lengths[0]; idPoint++)
    {

        for(idCluster = 0; idCluster < lengths[2]; idCluster++)
        {     
            support[0].attributes[threadId] = pow( (points[idPoint].attributes[threadId] - clusters[idCluster].attributes[threadId]) , 2 );

            counter = SIZE;
            offset = 1;

            while(counter != 1)
            {
                counter = counter / 2 + (counter % 2);

                barrier(CLK_GLOBAL_MEM_FENCE);

                if(threadId % (2*offset) == 0)
                    if(threadId + offset < lengths[1])
                        support[0].attributes[threadId] = support[0].attributes[threadId] + support[0].attributes[threadId+offset];

                offset = offset * 2 ;
             }

             barrier(CLK_GLOBAL_MEM_FENCE);

            if(support[0].attributes[threadId] > bestVal)
                bestVal = support[0].attributes[threadId];

    }

    barrier(CLK_GLOBAL_MEM_FENCE);

    if(threadId == 0 && bestVal > output[threadId])
    {
        output[0] = bestVal;
        lengths[3] = idPoint;
    }
}
\u内核无效计算距离(\u全局t簇*点、\u全局t簇*簇、\u全局浮点*输出、\u全局t簇*支持、\u全局短*长度)
{
int-threadId=get\u-global\u-id(0);
float bestVal=0;
整数计数器,偏移量;
短idPoint,idCluster;
对于(idPoint=0;idPoint<长度[0];idPoint++)
{
对于(idCluster=0;idClusterbestVal)
bestVal=支持[0]。属性[threadId];
}
屏障(CLK_GLOBAL_MEM_围栏);
如果(threadId==0&&bestVal>output[threadId])
{
输出[0]=bestVal;
长度[3]=idPoint;
}
}

}

您使用的屏障不能用于跨多个计算核心(工作组)进行同步

屏障同步仅在同一逻辑工作组内工作。看看能不能更好地理解我指的是什么

增加集群大小也会增加正在使用的工作项的数量,这可能会使用多个工作组,这就是您遇到此问题的原因


编辑:可能值得指出的是,不能跨工作组使用同步原语。

Ok这就是解决方案。非常感谢。