C 无论我做什么,snprintf()都会给我一个分段错误
所以我搜索并查看了所有的snprintf()、sprintf()和segmentation错误线程,但仍然没有找到 基本上,似乎仅仅是snprintf()语句的存在就导致了我的代码出现分段错误。长话短说,是的,这是为了家庭作业……基本上,我必须填写缺失的代码,并且严格要求我不要触碰已经存在的代码。我的代码是这样的:C 无论我做什么,snprintf()都会给我一个分段错误,c,segmentation-fault,printf,C,Segmentation Fault,Printf,所以我搜索并查看了所有的snprintf()、sprintf()和segmentation错误线程,但仍然没有找到 基本上,似乎仅仅是snprintf()语句的存在就导致了我的代码出现分段错误。长话短说,是的,这是为了家庭作业……基本上,我必须填写缺失的代码,并且严格要求我不要触碰已经存在的代码。我的代码是这样的: struct dirent* dirEntryPtr; struct stat statBuffer; char *yourFileN
struct dirent* dirEntryPtr;
struct stat statBuffer;
char *yourFileName;
while((dirEntryPtr=readdir(dirPtr))!=NULL)
{
int yourFileSize;
memset(buffer,'\0',sizeof(buffer));
yourFileName=dirEntryPtr->d_name;
printf("Directory entry read...%s\n",yourFileName);
snprintf(buffer,MAX_LINE,"%s/%s",DIR_NAME,yourFileName);
printf("Printed directory entry to buffer...\n");
stat(buffer,&statBuffer);
yourFileSize=statBuffer.st_size;
printf("File size: %d\n",yourFileSize);
if(S_ISREG(statBuffer.st_mode))
{
printf("REGULAR!\n");
snprintf(buffer,MAX_LINE,"%30s (%5d)\n",yourFileName,yourFileSize);
printf("[%s] %30s (%5d)\n",(char *)statBuffer.st_mode,yourFileName,yourFileSize);
}
else
if(S_ISDIR(statBuffer.st_mode)){
printf("DIRECTORY!\n");
snprintf(buffer,MAX_LINE,"%30s (dir)\n",yourFileName);
printf("[%s] %30s (dir)\n",(char *)statBuffer.st_mode,yourFileName);}
else
{
printf("OTHER!!\n");
snprintf(buffer,MAX_LINE,"%30s (other)\n",yourFileName);
printf("[%s] [%s] %30s (other)\n",(char*) S_ISREG(statBuffer.st_mode),(char *)statBuffer.st_mode,yourFileName);
}
printf("Writing buffer \"%s\" to client...\n",buffer);
write(clientDescriptor,buffer,MAX_LINE);
free(buffer);
}
close(clientDescriptor);
exit(EXIT_SUCCESS);
所有printf()基本上都是用于调试的。(是的,我知道,使用GDB,但尽管经过多年的指导,我始终无法理解它是如何工作的!)
长话短说,当前目录中的文件一次读取一个。第一个文件通常是一个名为server.c的文件,它总是正确地标识为“常规”文件。然而,当snprintf()行出现时,分段错误就开始发挥作用。buffer是一个声明的字符串(代码的一部分我是不允许接触的,但指令是专门使用snprintf()将条目写入“buffer”——事实上,我使用的确切snprintf()命令是指令中给出的!),并设置为MAX_LINE bytes(80),它是在包含的外部头文件中定义的。我之前在那里有一个strnlen用于调试目的,以确认DIR_NAME是一个字符,而yourFileName,至少在server.c的情况下,是9——远没有接近80
我甚至尝试声明一个新变量,并通过snprintf()向它写入一个字节,但仍然出现了分段错误!我尝试了使用和不使用malloc()命令
我还应该找什么???我确实给我的教授发了电子邮件,但是说实话,我必须在今天提交这个(几天内还没有到期,但我要出城了),我只需要尽快给他一些提示……但是根据我对C的理解,这应该行得通。事实上,它昨天下午还在工作,但昨晚很晚的时候突然对我产生了影响(这是一个可能的原因:
printf("[%s] [%s] %30s (other)\n",
(char*) S_ISREG(statBuffer.st_mode),
(char *)statBuffer.st_mode,
yourFileName);
这指示printf()
:
- 将
的返回值视为指向以null结尾的字符串的指针,该字符串不是且将是S_ISREG()
或0
(基于从1
中拉出的以下内容):sys/stat.h
- 将
视为指向以空结尾的字符串的指针,而该字符串不是(假定st_模式
的类型是st_模式
)int
%d
作为格式说明符而不是%s
或s_ISREG()
的格式说明符,可以使用三元运算符并返回字符串文字:
printf("[%s] [%d] %30s (other)\n",
S_ISREG(statBuffer.st_mode) ? "regular file" : "not regular file",
statBuffer.st_mode,
yourFileName);
这是一个错误,几乎可以肯定是原因:
char buffer[MAX_LINE];
free(buffer);
仅传递给动态分配的free()
:
free函数导致ptr指向的空间被释放,即生成
可用于进一步分配。如果ptr是空指针,则不会发生任何操作。否则,如果
参数与calloc、malloc或realloc函数先前返回的指针不匹配,或者如果已通过调用free或realloc释放空间,
该行为未定义
这是一个可能的原因:
printf("[%s] [%s] %30s (other)\n",
(char*) S_ISREG(statBuffer.st_mode),
(char *)statBuffer.st_mode,
yourFileName);
这指示printf()
:
- 将
的返回值视为指向以null结尾的字符串的指针,该字符串不是且将是S_ISREG()
或0
(基于从1
中拉出的以下内容):sys/stat.h
- 将
视为指向以空结尾的字符串的指针,而该字符串不是(假定st_模式
的类型是st_模式
)int
%d
作为格式说明符而不是%s
或s_ISREG()
的格式说明符,可以使用三元运算符并返回字符串文字:
printf("[%s] [%d] %30s (other)\n",
S_ISREG(statBuffer.st_mode) ? "regular file" : "not regular file",
statBuffer.st_mode,
yourFileName);
这是一个错误,几乎可以肯定是原因:
char buffer[MAX_LINE];
free(buffer);
仅传递给动态分配的free()
:
free函数导致ptr指向的空间被释放,即生成
可用于进一步分配。如果ptr是空指针,则不会发生任何操作。否则,如果
参数与calloc、malloc或realloc函数先前返回的指针不匹配,或者如果已通过调用free或realloc释放空间,
该行为未定义
另一个bug:
write(clientDescriptor,buffer,MAX_LINE);
如果buffer
指向以NUL结尾的字符串,几乎肯定不是您想要的。这总是写入MAX\u LINE
字符,并且不会在NUL处停止。我建议fprintf
和朋友(put
,fputs
)输出字符串。另一个错误:
write(clientDescriptor,buffer,MAX_LINE);
如果
buffer
指向以NUL结尾的字符串,则几乎肯定不是您想要的。这总是写入MAX\u LINE
字符,并且不会在NUL处停止。我建议fprintf
和朋友(put
,fputs
)输出字符串。如果可以复制,请提供问题的详细信息。您的示例没有显示如何分配缓冲区(如果确实已分配)。目录名是什么?可能需要打印&DIR\u NAME:-)如果可以重现,请提供问题的详细信息。您的示例没有显示如何分配缓冲区(如果确实已分配)。目录名是什么?也许你需要打印&DIR_NAME:-)上面的printf也有一个错误的char*。在我看来,OP对第一个snprintf有问题。我猜可能是他的缓冲区分配不正确,或者目录名不能用作%s(类似于您的某些点)。@Scooter,是的。不过,希望OP在读了这篇文章后能够注意到这些。谢谢你的回复……不过,printf()是为debu准备的