在他的评论中,Roger Dahl链接了以下帖子:
直接将PTX程序传递给CUDA驱动程序。该帖子讨论了两个函数的使用,即
cuModuleLoad
和
cuModuleLoadDataEx
。前者用于从文件加载PTX代码并将其传递给
nvcc
编译器驱动程序。后者避免了I/O并使得可以将PTX代码作为C字符串传递给驱动程序。在任一情况下,您都需要已经拥有PTX代码,无论是作为CUDA内核编译的结果(要加载或复制并粘贴到C字符串中)还是手写源代码。
但是如果您必须根据CUDA内核实时创建PTX代码会发生什么?按照
CUDA表达式模板中的方法,您可以定义一个包含CUDA内核的字符串。
ss << "extern \"C\" __global__ void kernel( ";
ss << def_line.str() << ", unsigned int vector_size, unsigned int number_of_used_threads ) { \n";
ss << "\tint idx = blockDim.x * blockIdx.x + threadIdx.x; \n";
ss << "\tfor(unsigned int i = 0; i < ";
ss << "(vector_size + number_of_used_threads - 1) / number_of_used_threads; ++i) {\n";
ss << "\t\tif(idx < vector_size) { \n";
ss << "\t\t\t" << eval_line.str() << "\n";
ss << "\t\t\tidx += number_of_used_threads;\n";
ss << "\t\t}\n";
ss << "\t}\n";
ss << "}\n\n\n\n";
然后使用系统调用将其编译为。
int nvcc_exit_status = system(
(std::string(NVCC) + " -ptx " + NVCC_FLAGS + " " + kernel_filename
+ " -o " + kernel_comp_filename).c_str()
);
if (nvcc_exit_status) {
std::cerr << "ERROR: nvcc exits with status code: " << nvcc_exit_status << std::endl;
exit(1);
}
最后使用cuModuleLoad
和cuModuleGetFunction
从文件中加载PTX代码,并将其传递给编译器驱动程序,例如:
result = cuModuleLoad(&cuModule, kernel_comp_filename.c_str());
assert(result == CUDA_SUCCESS);
result = cuModuleGetFunction(&cuFunction, cuModule, "kernel");
assert(result == CUDA_SUCCESS);
当然,表达式模板与这个问题无关,我只是引用了我在回答中所报道的思想来源。