1

我正在使用 LLVM 3.3 C++-API。我的代码使用ConstantArray::get, 和使用递归代码创建多维数组(最内层首先转换为 Constant*s 的向量,如上所述,然后用于初始化下一个最内层,依此类推)。

我试图通过说如果数组的元素类型满足ConstantDataArray::isElementTypeCompatible谓词来优化这一点,那么它应该使用ConstantDataArray::get.

这是一个更具体的例子来说明我的意思:

  1. 假设我要创建的数组将在 C++ 中这样声明:

    诠释 x[2][3] = {{1,2,3},{4,5,6}};

  2. 最内层(类型 int[3])是一个简单的数组类型,因此创建了两个 CDA。

  3. 下一个等级是两个 int[3] 的数组。它不是一个简单的类型,所以ConstantArray创建了一个正则。参数是ArrayRef<Constant*>包含两个 CDA 的。

在第 3 步,ConstantArray因为初始化程序没有完全正确的类型而抱怨。这是消息:

.../llvm-3.3.src/lib/IR/Constants.cpp:754:
static llvm::Constant* llvm::ConstantArray::get(llvm::ArrayType*,
llvm::ArrayRef<llvm::Constant*>):

Assertion `V[i]->getType() == Ty->getElementType()
&& "Wrong type in array element initializer"' failed.

我虽然ConstantDataArray是一个替代品ConstantArray是元素类型足够简单时的正确的理解方式是什么?

更新

这看起来像是我的代码中的一个错误(在 LLVM 之外)。 ConstantDataArray似乎确实是ConstantArray.

这是我用来演示问题的代码。它实际上在没有任何来自 LLVM 的投诉的情况下运行:

// int[2][3] = {{1,2,3},{4,5,6}};
IntegerType* i64 = IntegerType::get(mod->getContext(), 64);
Constant* one = ConstantInt::get(i64, 1);
Constant* two = ConstantInt::get(i64, 2);
Constant* three = ConstantInt::get(i64, 3);
Constant* four = ConstantInt::get(i64, 4);
Constant* five = ConstantInt::get(i64, 5);
Constant* six = ConstantInt::get(i64, 6);

ArrayType* int_3 = ArrayType::get(i64, 3);
ArrayType* int_2_3 = ArrayType::get(int_3, 2);
// Constant* array123 = ConstantArray::get(int_3, std::vector<Constant*>{one,two,three});
Constant* array123 = ConstantDataArray::get(mod->getContext(), std::vector<uint64_t>{1,2,3});
// Constant* array456 = ConstantArray::get(int_3, std::vector<Constant*>{four,five,six});
Constant* array456 = ConstantDataArray::get(mod->getContext(), std::vector<uint64_t>{4,5,6});
Constant* array = ConstantArray::get(int_2_3, std::vector<Constant*>{array123, array456});

如果有人感兴趣,断言源于我反转数组范围。 int[2][3]是一个由两个三个数组组成的数组。我正在重载operator[]构建一个数组类型 as i64[2][3],其中i64是一个包含 anIntegerType*和重载的对象operator[]。问题是这构建了一个由三个数组组成的数组,每组两个。

4

0 回答 0