3

是否无法在 main() 中定义结构。我尝试以下只是为了获得分段错误:

#include <stdio.h>
#include <unistd.h>
#include <strings.h>
#define TRUE 1


void main(int argc,char **argv)
{
struct test_struct
{

        char test_name[50];
        char summary_desc[200];
        char result[50];
};

struct suite_struct
{
        char suite_name[50];
        struct test_struct test[500];
        int test_count;
        int passed;
        int failed;
        int unresolved;
        int notrun;
}suite[500];

        int a,b;

        for (a=0;a<500;a++)
        {
                strcpy(suite[a].suite_name,"");
                for (b=0;b<500;b++)
                {
                        strcpy(suite[a].test[b].test_name,"");
                        strcpy(suite[a].test[b].summary_desc,"");
                        strcpy(suite[a].test[b].result,"");
                }
                suite[a].test_count=0;
                suite[a].passed=0;
                suite[a].failed=0;
                suite[a].unresolved=0;
                suite[a].notrun=0;
        }
}

但是,当我将结构定义放在外面时,它就起作用了:

#include <stdio.h>
#include <unistd.h>
#include <strings.h>
#define TRUE 1


struct test_struct 
{ 

        char test_name[50]; 
        char summary_desc[200]; 
        char result[50]; 
}; 

struct suite_struct 
{ 
        char suite_name[50]; 
        struct test_struct test[500]; 
        int test_count; 
        int passed; 
        int failed; 
        int unresolved; 
        int notrun; 
}suite[500]; 
void main(int argc,char **argv)
{

        int a,b;

        for (a=0;a<500;a++)
        {
                strcpy(suite[a].suite_name,"");
                for (b=0;b<500;b++)
                {
                        strcpy(suite[a].test[b].test_name,"");
                        strcpy(suite[a].test[b].summary_desc,"");
                        strcpy(suite[a].test[b].result,"");
                }
                suite[a].test_count=0;
                suite[a].passed=0;
                suite[a].failed=0;
                suite[a].unresolved=0;
                suite[a].notrun=0;
        }
}

不知道为什么会这样。为此,我正在使用 Solaris SunStudio 编译器。

4

5 回答 5

6

在第一个示例中,suite位于堆栈上,而在第二个示例中,它位于数据段上。

由于suite相当大(~75MB),段错误几乎肯定是由于您的程序耗尽了堆栈空间。

在大多数情况下,最好在堆上分配大型数据结构(使用malloc()等)。这也可以只分配您需要的空间量,而不是总是为 500 个元素分配空间。

于 2012-01-25T18:08:51.720 回答
3

在 main 中声明一个结构是可以的。但是在您的程序中,问题与您在 main 函数中创建该结构的 500 个对象有关。每个对象的大小约为 15 KB。因此,500 个对象需要大约 75 MB。试试printf("size: %lu\n", sizeof suite);

默认情况下,您没有那么多可用的堆栈。您可以使用命令找到可用的堆栈ulimit -s。它以 KB 为单位打印可用堆栈。

您可以使用该ulimit命令来增加堆栈。例如ulimit -s 100000

更好的方法是动态分配您需要使用的内存malloc()

于 2012-01-25T18:10:37.243 回答
1

在任何函数中定义 astruct并声明它的局部变量都是合法的,包括.structmain

但是代码在语法上可能是合法的并且在运行时崩溃(例如,因为它具有未定义的行为,根据 C 标准,或者因为它遇到了一些系统限制,比如调用堆栈的限制)。

于 2012-01-25T18:13:45.137 回答
1

您在 main 之外定义的结构是全局且未初始化的,因此它将进入 .bss 段并在执行开始时初始化为 0。您在 main 中定义的结构非常大,超过了最大堆栈大小(在 Linux 上约为 1-2MB,也可能在 Solaris 上)。由于 main 之外的一个不在堆栈上,因此它似乎在这种情况下有效,而在另一种情况下则无效。

于 2012-01-25T18:18:58.110 回答
1

除了关于堆栈空间、malloc 和未定义行为的答案。. .

当我试图编译你的代码时,我收到了 3 个警告。

test.c:7:6: warning: return type of ‘main’ is not ‘int’
test.c: In function ‘main’:
test.c:32:17: warning: implicit declaration of function ‘strcpy’
test.c:32:17: warning: incompatible implicit declaration of built-in function ‘strcpy’

为 main 返回一个 int,而不是 void。

int main(int argc,char **argv)

在 C 中,strcpy 的标头是 string.h,而不是 strings.h。

于 2012-01-25T18:19:28.533 回答