我有一个下面的最小示例,其中我的主函数调用两个不同的函数function1()
和function2()
。他们俩都希望在一个表上工作,该表需要在function1()
的第一次运行中生成。在我的实际程序中,该表要大得多,这就是为什么我不希望它在程序存储器中作为全局变量硬编码,而是在代码的第一轮中进行计算。我声明了该表为静态表,以便在离开函数时保留分配的值。我不确定tblPtr
是否也需要static
。为什么我在这里得到SEGFAULT?
#include <stdio.h>
static void genTbl(unsigned int encodeTbl[][2])
{
int nn,mm;
for (nn=0; nn < 3;nn++){
for (mm=0; mm < 2; mm++){
encodeTbl[nn][mm] = nn+mm; //some example
}
}
}
unsigned int **tblPtr; //pointer to table
static unsigned int function1()
{
static int t1=0;
static unsigned int tbl[3][2];
if(t1==0){ //only gen table in first round
t1++;
genTbl(tbl);
tblPtr = &tbl; //assign pointer
t1++;
}
return (tbl[2][2]);
}
static unsigned int function2()
{
//also wants to work with tbl
return (tblPtr[2][2]); //SEGFAULT
}
int main()
{
int cnt=0;
while(cnt<5){
int f1 = function1();
printf("function1 return: %d\n", f1);
int f2 = function2();
printf("function1 return: %d\n", f2);
cnt++;
}
}
答案 0 :(得分:2)
在您的function1()
中,您已经调用了undefined behaviour。
您已经定义了类似于static unsigned int tbl[3][2];
的数组,因此有效访问权限将为tbl[i][j];
,其中0<i<3
和0<j<2
。因此,在代码中
return (tbl[2][2]);
正在超出范围使用内存,它是off-by-one。您在function2()
中也遇到了同样的问题。
也就是说,声明
tblPtr = &tbl;
是无效的,并且是违反约束的条件。任何启用了适当警告的编译器都会警告您有关该语句的信息。您需要将tblPtr
的类型更改为指向2个int
数组的指针,例如
unsigned int (*tblPtr)[2];
然后分配将有效。
答案 1 :(得分:0)
使用以下命令将tblPtr声明为用户定义的类型
typedef unsigned int myType[3][2];
myType **tblPtr; //pointer to table
使用此方法,可以将其显式声明为指向无符号int的二维数组的指针。
然后将static unsigned int tbl[3][2]
放在函数1之外