我目前正在研究LLVM编译器。在他们的语言参考(http://llvm.org/releases/3.7.0/docs/LangRef.html#getelementptr-instruction)中,他们给出了一些C代码作为getelementptr指令的示例。但我不明白这段代码是如何工作的。
struct RT {
char A;
int B[10][20];
char C;
};
struct ST {
int X;
double Y;
struct RT Z;
};
int *foo(struct ST *s) {
return &s[1].Z.B[5][13];
}
s[1]
在这做什么?
是否使用索引访问结构?
如何在这里获得元素Z?
答案 0 :(得分:0)
s
的类型为struct ST *
,指向struct ST
的指针。数组中的数组和指针大致相同(有一些警告)。因此s[1]
是struct ST
。
.Z
访问其中的元素Z
,即struct RT
。 .B
访问该结构中的元素B
,然后我们获取其中的[5][13]
元素,最后使用&
返回该元素的地址。
答案 1 :(得分:0)
是否使用索引访问结构?
没有。 struct ST *s
:s是一个指针,因此它可能指向ST
类型的某些元素数组。
s[1]
获取此类数组的第二个元素。 s[1]
相当于(*(s+1))
。
答案 2 :(得分:0)
由于我们有struct ST *s
,我们也知道s [1]的类型为struct ST
。它只是将s
视为指向struct-of-struct-S的第一个元素的指针。
答案 3 :(得分:0)
在这种情况下,任何指针struct ST *
都可以视为指向数组的指针。通过编写s[1]
,程序员假设foo
收到至少两个struct ST
个对象的数组。 (如果程序员错误的话,该程序有不确定的行为。)
因此,s[1]
访问S
指向的数组的第二个元素。该元素为struct ST
,因此.Z
访问其Z
字段,即struct RT
。 .B
到达struct RT
内的B
字段,这是一个二维数组,最后[5][13]
索引该数组中的特定整数。
在所有这些操作之后,&
运算符被评估,并检索该特定整数的地址,这是该函数的结果。
我不熟悉LLVM的中间表示,但getelementptr
听起来像是IR运算符的合理名称,它实现了一系列索引和字段访问并返回指针。