C语言 分段错误 - strcat
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/13901209/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Segmentation fault- strcat
提问by Mahesh Bansod
This is my code:
这是我的代码:
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
void main(int arge, char *argv[])
{
FILE *f1;
char ch,*fn="~/lyrics/";
strcat(fn,argv[1]);
strcat(fn,".txt");
if( (f1 = fopen(fn,"r"))==NULL )
{
printf("\nWrong filename\n%s not found",argv[1]);
return;
}
while((ch=getw(f1))!=EOF)
{
printf("%c",ch);
}
}
I compiled it using gcc -g -o file file.cand the compiler gave no error messages. But when I run it I get the error message:
我使用编译它gcc -g -o file file.c并且编译器没有给出错误消息。但是当我运行它时,我收到错误消息:
Segmentation fault (core dumped)
Bad permissions for mapped region at address 0x8048659 at 0x402C36B: strcat
(in /usr/lib/valgrind/vgpreload_memcheck-x86-linux.so) by 0x80484D6: main (lyrics.c:9)
Can anyone please help me?
谁能帮帮我吗?
回答by Goz
You don't have enough space in fn. By strcat'ing on to it you overwrite the end of its stack allocation and into the stack .. hence the segmentation fault.
您在 fn 中没有足够的空间。通过对它进行 strcat'ing,您可以覆盖其堆栈分配的末尾并进入堆栈……因此出现分段错误。
You could try the following instead:
您可以尝试以下方法:
char fn[255];
strcpy( fn, "~/lyrics/" );
strcat( fn, argv[1] );
strcat( fn, ".txt" );
You just have to be sure that the whole path and filename can fit into 255 characters.
您只需要确保整个路径和文件名可以容纳 255 个字符。
Alternatively you could do this:
或者你可以这样做:
char* fn = NULL;
int argvLen = strlen( argv[1] );
fn = malloc( 9 + argvLen + 4 + 1 ); // Add 1 for null terminator.
strcpy( fn, "~/lyrics/" );
strcat( fn, argv[1] );
strcat( fn, ".txt" );
And you have definitely allocated enough space for the string. Just don't forget to free it when you have finished with it!
而且您肯定为字符串分配了足够的空间。完成后不要忘记释放它!
回答by md5
char *fn = "~/lyrics/";
Because fncould point on a string in read-only memory, you should declare fnas pointer to const char.
因为fn可以指向只读内存中的字符串,所以应该声明fn为指向const char.
const char *fn = "~/lyrics/";
Then you can see there are some errors. Here is a better solution:
然后你可以看到有一些错误。这是一个更好的解决方案:
char fn[MAX_SIZE] = "~/lyrics/";
Here MAX_SIZEshall be the sum of the size of "~/lyrics/", the maximum length of argv[1]and the length of ".txt".
此处MAX_SIZE应为 的大小"~/lyrics/"、最大长度argv[1]和 的长度之和".txt"。
回答by alk
This approach is not portable.
这种方法不可移植。
If using glibcyou also might call asprintf()which just allocates as much memory as you need.
如果使用,glibc您也可以调用asprintf()which 只分配您需要的内存。
#include <stdio.h>
...
char * pFn = NULL;
if (-1 == asprintf(&pFn, "~/lyrics/%s.txt", argv+1);
{
perror("asprintf()");
}
else
{
... /* use pFn */
}
free(pFn);
...

