How to get the indices in an getelementptr Value?

Hi, all

I am a LLVM user. I want to get every element in the next instruction:

%0 = load i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 2), align 4, !dbg !85, !clap !86

Now I can only get value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 2)” through “getOperand(0)”,
but I can not get “%struct.Args* @globalArg”, “i64 0”, and “i32 2” in this instruction.

I know I can get the indices of getelementptr instructions through “getOperand()”, but now in the previous example,
I want to get the indices from a getlementptr value. How should I do? Thank you in advance.

Hi Qiuping,

I guess you need to use getPointerOperand to access the pointer operand (@globalArg in your example) and idx_begin/idx_end iterators to access indexes. You can find a short description of these functions in documentation [1], or look at examples of their uses in the code, e.g. in lib/Transforms/InstCombine/*.cpp.

[1] http://llvm.org/doxygen/classllvm_1_1GetElementPtrInst.html

Best regards,
Michael

Hi Michael,

Thank you very much.

But idx_begin/idx_end iterators can only be used through a getelementptr instruction, right? However, I think value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 2)” itself is not a getelementptr instruction, so? Or could you tell me how can I get a getelementptr instruction first from this value?

Hi Qiuping,

If I'm reading the IR correctly, what you have is a
GetElementPtrConstantExpr [1]. It subclasses from llvm::Constant.

Thanks,
-- Sanjoy

[1]: http://llvm.org/docs/doxygen/html/classllvm_1_1GetElementPtrConstantExpr.html

Hi Qiuping,

If I'm reading the IR correctly, what you have is a
GetElementPtrConstantExpr [1]. It subclasses from llvm::Constant.

If you want the same code to handle GetElementPtrConstantExpr *and*
GetElementPtrInst, you can use GEPOperator.

Thank you very much for your useful information. As you say, it is a subclass llvm::ConstantExpr.

Now I cast value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 2)” to its subclass llvm::Constant and then subclass llvm::ConstantExpr, and then I can access its indices through

for (unsigned i=0; igetNumOperands(); ++i)
v = constExpr->getOperand(i);

However, I have another question. The invoking of getNumOperands() on value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 2)” returns 3, but it returns 1 on value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 0)”, and furthermore, through value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 2)” is subclass llvm::Constant, but it is not subclass llvm::ConstantExpr, why?

Hi David Majnemer,

I found I can cast value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 2)” to class GEPOperator, but failed on value “i32* getelementptr inbounds (%struct.Args* @globalArg, i64 0, i32 0)”. As my previous email described, I found that the later value is a class llvm::Constant but not a subclass llvm::ConstantExpr. I find it is very strange.

I find the root of my problem. I mistakenly invoking stripPointerCasts() before casting. Now I can access these elements by casting the related value to subclass llvm::constantExpr or GEPOperator. Thank you all.