我正在尝试开始使用 LLVM,以便为我的代码添加即时编译,但发现很难找到有关如何在 LLVM 中执行我想要的操作的引用资料,尽管已经检查了 Kaleidoscopy 教程、语言引用手册、程序员手册和 doxygen 文档。还有比这些更多的 LLVM C++ API 引用吗?
现在提出具体问题。我分配了一个包含两个元素的数组对象(我假设对应于 C++ 中的 double[2]
):
const llvm::Type* double_t = llvm::Type::getDoubleTy(llvm::getGlobalContext());
const llvm::Type* array_t = llvm::ArrayType::get(double_t,2)
在代码的后面,我创建了一个函数,其中该数组是参数之一。然后,在我的函数中,我提取数组中的第一个元素并将其返回给用户:
llvm::Function::arg_iterator AI = jit_function_->arg_begin();
llvm::Value *x = AI;
llvm::Value *x0 = Builder.CreateExtractValue(x,0);
Builder.CreateRet(x0);
代码运行良好,但当我尝试运行它时,它不起作用。例如:
typedef double (*GenType)(double[2]);
GenType FP = GenType(intptr_t(TheExecutionEngine->getPointerToFunction(jit_function_)));
double y[2] = {10,20};
double r = FP(y);
printf("r = %g\n", r);
返回值只是无意义的,我看不出我做错了什么。如果我将数组中的值(10 和 20)作为标量参数传递给函数,它就可以正常工作。
最佳答案
我想我能够回答我自己的问题。对于问题的第一部分,对 LLVM 的一个很好的引用(除了上面提到的之外)是用纯 C 编写你想要的内容并使用 Clang 编译它并查看 LLVM 输出:clang -S -发出 llvm test.c -o -
.
const llvm::Type* array_t = llvm::ArrayType::get(double_t,2);
到
const llvm::Type* array_t = llvm::PointerType::getUnqual(llvm::ArrayType::get(double_t,2));
并通过更改添加额外的取消引用
llvm::Value *x0 = Builder.CreateExtractValue(x,0);
到
llvm::Value *x0 = Builder.CreateExtractValue(Builder.CreateLoad(x),0);
关于llvm - 访问 LLVM 数组中的元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9637803/