OpenCL输出缓冲区

OpenCL输出缓冲区,opencl,Opencl,我正在努力学习OpenCL的基础知识 我认为这是内核中的代码: out[ 1 & ((a+b)==(b+a)) ] = (char)1; 将产生与以下相同的结果: out[ 1 ] = (char)1; 有人能告诉我为什么它会产生不同的结果吗 以下是我的内核的完整源代码: #pragma OPENCL EXTENSION cl_khr_byte_addressable_store : enable __kernel void hello(__global char * out) {

我正在努力学习OpenCL的基础知识

我认为这是内核中的代码:

out[ 1 & ((a+b)==(b+a)) ] = (char)1;
将产生与以下相同的结果:

out[ 1 ] = (char)1;
有人能告诉我为什么它会产生不同的结果吗

以下是我的内核的完整源代码:

#pragma OPENCL EXTENSION cl_khr_byte_addressable_store : enable
__kernel void hello(__global char * out)
{
    size_t tid = get_global_id(0);
    int a = tid & 0xff;
    int b = (tid >> 8) & 0xff;
    out[ 1 & ((a+b)==(b+a)) ] = (char)1;
}
如果我将最后一条语句替换为“out[1]=(char)1;”,则不会写入“out[0]”。但是上面的内核会将“1”写入out[0]

<>编辑:这是我的C++代码:

#include <utility>
#define __NO_STD_VECTOR // Use cl::vector instead of STL version
#include <CL/cl.hpp>

#include <cstdio>
#include <cstdlib>
#include <fstream>
#include <iostream>
#include <string>
#include <iterator>

inline void checkErr(cl_int err, const char * name)
{
    if (err != CL_SUCCESS) {
        std::cerr << "ERROR: " << name
                 << " (" << err << ")" << std::endl;
        std::exit(EXIT_FAILURE);
    }
}

int main()
{
    cl_int err;

    cl::vector< cl::Platform > platformList;
    cl::Platform::get(&platformList);
    checkErr(platformList.size()!=0 ? CL_SUCCESS : -1, "cl::Platform::get");
    std::cerr << "Platform number is: " << platformList.size() << std::endl;

    std::string platformVendor;
    platformList[0].getInfo((cl_platform_info)CL_PLATFORM_VENDOR, &platformVendor);
    std::cerr << "Platform is by: " << platformVendor << "\n";
    cl_context_properties cprops[3] = 
        {CL_CONTEXT_PLATFORM, (cl_context_properties)(platformList[0])(), 0};

    cl::Context context(
       CL_DEVICE_TYPE_GPU, 
       cprops,
       NULL,
       NULL,
       &err);
    checkErr(err, "Conext::Context()"); 


    unsigned char outH[2] = {0};
    cl::Buffer outCL(
        context,
        CL_MEM_WRITE_ONLY | CL_MEM_USE_HOST_PTR,
        sizeof(outH),
        outH,
        &err);
    checkErr(err, "Buffer::Buffer()");


    cl::vector<cl::Device> devices;
    devices = context.getInfo<CL_CONTEXT_DEVICES>();
    checkErr(
        devices.size() > 0 ? CL_SUCCESS : -1, "devices.size() > 0");


    std::ifstream file("condition1.cl");
    checkErr(file.is_open() ? CL_SUCCESS:-1, "condition1.cl");
    const std::string prog(std::istreambuf_iterator<char>(file), (std::istreambuf_iterator<char>()));

    cl::Program::Sources source(1, std::make_pair(prog.c_str(), prog.length()+1));
    cl::Program program(context, source);
    err = program.build(devices,""); 
    checkErr(err, "Program::build()"); 


    cl::Kernel kernel(program, "hello", &err);
    checkErr(err, "Kernel::Kernel()");

    err = kernel.setArg(0, outCL);
    checkErr(err, "Kernel::setArg()");


    cl::CommandQueue queue(context, devices[0], 0, &err);
    checkErr(err, "CommandQueue::CommandQueue()");


    cl::Event event;
    err = queue.enqueueNDRangeKernel(
        kernel, 
        cl::NullRange,
        cl::NDRange(65536),
         cl::NDRange(1, 1), 
        NULL, 
        &event);
    checkErr(err, "ComamndQueue::enqueueNDRangeKernel()");

    event.wait();    
    err = queue.enqueueReadBuffer(
        outCL,
        CL_TRUE,
        0,
        sizeof(outH),
        outH);
    checkErr(err, "ComamndQueue::enqueueReadBuffer()");

    for (int i = 0; i < sizeof(outH); i++)
        std::cout << (int)outH[i] << " ";

    std::string str;
    std::getline(std::cin, str);

    return EXIT_SUCCESS;
}
#包括
#定义_NO_STD_VECTOR//使用cl::VECTOR而不是STL版本
#包括
#包括
#包括
#包括
#包括
#包括
#包括
内联无效校验错误(cl_int err,常量字符*名称)
{
如果(错误!=CL_成功){

我现在能看到的唯一可能的解释是,隐式地将一个大小指定给一个int可能是未定义的行为,尽管我觉得不太可能。你是想在索引中使用按位AND吗?你只使用一个工作单元,对吗?谢谢。是的,我想这可能是因为未定义的行为。我不明白UR“您是否打算使用一个按位和索引”?因为我看到它,我使用它,它看起来正确。我不知道什么是“工作单元”,所以我添加了C++代码。我的意思是,因为= =操作符返回什么被认为是布尔,所以使用& &(逻辑和)似乎更有意义。运算符。但这是一个相当复杂的内核,所以我想这并不重要。我明天早上会再看一次,我必须睡一会儿——希望到时候有人能解开这个谜。啊,谢谢。我还试着写“out[(a+b)=(b+a))?1:0]=(char)1;”但是我得到了同样的结果。为什么在内核调用中使用Cl::NDRange(65536)?有什么特殊的原因吗?(我更熟悉原始C绑定,而不是C++的,但是我认为这是全局工作大小参数)
char result = 0;
for (int a = 0; a < 2; a++) {
    for (int b = 0; b < 2; b++) {
        if ((a+b) != (b+a))
            result |= (1 << (a+2*b));
    }
}
char result = 0;
int a = 1;
/*for (int a = 0; a < 2; a++)*/ {
    for (int b = 0; b < 2; b++) {
        if ((a+b) != (b+a))
            result |= (1 << (a+2*b));
    }
}