2014-03-19 179 views
6

我一直想简单的文件用C处理,我想,以确保该文件可以访问尝试使用此FCLOSE()会导致段错误

#include<stdio.h> 

main() 
{ 
    CheckFile(); 
} 

int CheckFile() 
{ 
    int checkfile=0; 

    FILE *fp1; 
    fp1 = fopen("users.sav","r"); 

    if(fp1==NULL) 
    { 
     fopen("users.sav","w"); 
     fclose(fp1); 
    } 
    if(checkfile!=0)printf("\nERROR ACCESSING FILE!\nNow exiting program with exit code: %d\n",checkfile);exit(1); 
    return 0; 
} 

然后显示

Segmentation fault (core dumped) 

但它不会段错误,如果该文件已经存在(例如,当我手动创建它或当我第二次运行该程序)

请帮助。我需要在一周内完成我们的最终项目,并且我还没有获得文件和指针的悬念。

我使用 “GCC(Ubuntu的/ Linaro的4.8.1-10ubuntu9)4.8.1”

P.S

我知道,存在明显相似的问题,但请不要downvote这个。了解我已经开始编写几个月的代码,因此无法理解这些高级代码和内容。

PPS

我看到这个在其他问题

有在则fopen实际工作的原代码,在这种情况下,它会返回NULL和FCLOSE不会被定义的行为没有保证。

那么我该如何检查它是否工作?

+2

的检查是正确的,只是不'FCLOSE(FP1)''如果FP1 == NULL'但调用'FP1 = FOPEN(..., “W”);' –

+0

谢谢:) 的答案真的帮助我编码到目前为止进展顺利。 – user3437503

+0

可能重复[fclose()导致分段错误](http://stackoverflow.com/questions/1443164/fclose-causing-segmentation-fault) –

回答

1

fopen返回一个FILE指针。它将返回NULL并设置全局errno以指示错误。如果你想检查errno,你必须检查是否在你检查fopen是否返回NULL

if (fp1 == NULL) 
{ 
    printf("fopen failed, errno = %d\n", errno); 
} 

否则,你可能会从别的一个errno,不一定是你的fopen电话。还包括errno.h。您也不需要再次致电fopen("users.sav","w");。您不会重新分配指针,也不会再检查一次。

我看不出有什么理由在这里打电话fclose因为如果fopen返回NULL,没有什么可以关闭。这可能是您seg故障的原因。您正试图关闭一个空指针。 More information on fopen failures

对您的代码的另一种评论。如果您要从CheckFile返回int,那么失败时应该不是0。我会返回-1来指示一个错误。更好的是,你可以返回全球errno。另外,main应该是int main(),最后应该是return 0;。我并不特别在乎你的命名方案CheckFile。在C,check_file或驼峰驼checkFile会更好。

CheckFile中,您的一行if语句可以格式化,如果您在多行上格式化它,则工作得更加正确。它不会做你认为目前它的作用:

if(checkfile!=0) 
{ 
    printf("\nERROR ACCESSING FILE!\nNow exiting program with exit code: %d\n", checkfile); 
    exit(1); 
} 

此外,checkfile从未设置在你的代码的任何地方..不是零。因此,if语句中的代码将不会执行句点。

4

这很正常,当您在fp1为NULL时致电fclose(fp1)

BTW

fopen("users.sav","w"); 

是无用的,因为你不分配返回值到一个文件指针。这意味着users.sav文件将被打开进行写入,但是您将永远无法写入任何内容。

0

fclose手册页说 -

FCLOSE()的行为是不确定的,如果流参数为 非法指针,或者是已经传递到以前 调用FCLOSE的描述符() 。

错误出现在代码中的if块中。

if(fp1==NULL) 
{ 
    fopen("users.sav","w"); 
    fclose(fp1); // passing NULL to fclose invokes undefined behaviour 
} 
0

另一个不相关的问题:

此行可能不是你想要什么:

if(checkfile!=0)printf("\nERROR ACCESSING FILE!\nNow exiting program with exit code: %d\n",checkfile);exit(1); 

如果我们把它写得正确格式化错误就变得很明显:

if (checkfile != 0) 
    printf("\nERROR ACCESSING FILE!\nNow exiting program with exit code: %d\n",checkfile); 

exit(1); 
return 0 ; 

实际上,即使checkfile为零,我们也会得到exit(1)

你可能想这样的:

if (checkfile != 0) 
{ 
    printf("\nERROR ACCESSING FILE!\nNow exiting program with exit code: %d\n",checkfile); 
    exit(1); 
} 

return 0 ; 

结论:格式的代码正确和许多错误会突然看起来很明显。

+0

你可能应该把这个放到你的其他答案中,很好的抓住:) – Brian

+0

@GIJoe:呃,我不确定我是否应该这样做,因为这个问题与原始问题完全无关。 –

+0

我会..让你的答案更强。 – Brian