getelementptr
有什么区别和 store
对比 load
和 insertvalue
将值存储到指向聚合类型的指针时?在某些情况下是首选吗?如果是这样,为什么?还是我完全走错了方向?
例子:
; A contrived example
%X = type {i32, i64}
define i32 @main(i32 %argc, i8** %argv) {
entry:
%sX.0 = alloca %X
; change the first value with GEP + store
%val1 = getelementptr %X, %X* %sX.0, i32 0, i32 0
store i32 42, i32* %val1
; change the second value with load + insertvalue
%sX.1 = load %X, %X* %sX.0
%sX.2 = insertvalue %X %sX.1, i64 42, 1
store %X %sX.2, %X* %sX.0 ; I suppose this could be considered less than ideal
; however in some cases it is nice to have the
; struct `load`ed
ret i32 0
}
有趣的是使用
llc -O=0 ...
它们都编译为相同的指令。以下是什么,这正是我所希望的。movl $42, -16(%rsp) # GEP + store
movq $42, -8(%rsp) # load + insertvalue
背景:
我正在阅读 LLVM Language Reference我正在阅读 insertvalue .引用文献指出
extractvalue
与 GEP 的指令相似性以及以下区别。The major differences to getelementptr indexing are:
Since the value being indexed is not a pointer, the first index is omitted and assumed to be zero.
At least one index must be specified.
Not only struct indices but also array indices must be in bounds.
StackOverflow 上的以下问题也提到了
getelementptr
的使用和 insertvalue
,但出于不同的原因。 LLVM insertvalue bad optimized?
最佳答案
在语义上,load
ing 及以后 store
整个对象更浪费。如果它是一个巨大的结构呢?如果它是一个结构数组呢? GEP 允许您访问内存中要加载/存储的确切位置,而无需加载/存储其他任何内容。
虽然在您的示例中将两种形式降低为相同的说明,但通常不能保证。
关于indexing - LLVM GEP 和存储 vs 加载和插入值 : Storing value to a pointer to an aggregate,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35234940/