gpt4 book ai didi

c++ - 我想根据前一条指令的结果更改 GEP 的索引

转载 作者:行者123 更新时间:2023-11-30 01:34:12 24 4
gpt4 key购买 nike

我正在编写一个 LLVM IR pass,它在运行时更改 GetElementPtr 指令的索引操作数。

我成功地用常数整数替换了 GEP 索引。例如,下面的代码会将 GEP 指令的每个最后索引替换为 0。

// For each instruction in the function
for(inst_iterator I = inst_begin(F), E = inst_end(F); I != E; ++I){
// Find GEP instruction
if(auto *GI = dyn_cast<GetElementPtrInst>(&*I)){
GI->setOperand(GI->getNumIndices(), ConstantInt::get(Type::getInt32Ty(I->getContext()), 0));
}
}

结果IR是这样的

Original:  %7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, i32 0
Replace: %7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, i32 0
Original: %9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, i32 1
Replace: %9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, i32 0

问题是,当我尝试根据运行时指令的结果更改索引时,它失败了。
修改通行证:

for(inst_iterator I = inst_begin(F), E = inst_end(F); I != E; ++I){
// Find GEP instruction
if(auto *GI = dyn_cast<GetElementPtrInst>(&*I)){
IRBuilder<> Builder(I);
Instruction* X = Builder.CreateCall(...)
GI->setOperand(GI->getNumIndices(), X);
}
}

修改后的结果:

Original:  %7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, i32 0
Replace: %7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, void <badref>
Original: %9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, i32 1
Replace: %9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, void <badref>
GEP indexes must be integers
%7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, void <badref>
GEP indexes must be integers
%9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, void <badref>

我还尝试通过以下方式获取返回值的常量整数值 I->setOperand(I->getNumIndices(), ConstantInt::get(Type::getInt32Ty(I->getContext()), cast<ConstantInt>(X)->getZExtValue()));但也不起作用。

Original:  %7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, i32 0
Replace: %7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, i32 784505880
Original: %9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, i32 1
Replace: %9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, i32 784506264
Invalid indices for GEP pointer type!
%7 = getelementptr inbounds %struct.A, %struct.A* %6, i32 0, i32 784505880
Invalid indices for GEP pointer type!
%9 = getelementptr inbounds %struct.A, %struct.A* %8, i32 0, i32 784506264

我认为原因是无法通过运行结果来设置GEP索引。那我应该怎么做才能在运行时更改 GEP 的每个索引?我是否需要用一些地址添加和内存访问指令来替换 GEP 指令?

最佳答案

注意错误信息:GEP indexes must be integers。如果调用的是一个返回 int 的函数,那么它就可以工作。它并不总是有效 — 您可以调用 foo() 并使用结果来获取数组的第 foo() 个元素,但是当您检索结构字段时,您必须有一个常量。

在你的第二种情况下,你要求结构的第 784505880 个字段。那要么是一个错误,要么是一个非常宽的结构;)

关于c++ - 我想根据前一条指令的结果更改 GEP 的索引,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56791896/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com