[英]Segmentation fault checking strcmp
我正在编写一个函数next_node
,该函数在目录中查找下一个文件。 节点将目录和文件名作为输入。
如果bname
之后没有其他文件或它是"."
我希望它返回NULL
"."
或".."
。 它仅在strcmp
的if
语句中运行时才给我segmentation fault (core dumped)
。
您能解释这个问题或提供解决方案吗?
码:
#include <stdio.h>
#include <dirent.h> // DIR opendir() closedir() struct dirent readdir()
#include <string.h> // strcmp()
char *next_node(char *dname, char *bname) {
if (!strcmp(dname, bname)) {
// dname same as bname
return NULL;
}
DIR *dirp = opendir(dname);
struct dirent *direntp;
while (((direntp = readdir(dirp)) != NULL) && (strcmp(direntp->d_name, bname))) {
}
if ((direntp = readdir(dirp)) != NULL) {
// if d_name is "." or ".." return NULL
if ((strcmp(direntp->d_name, ".")) || (strcmp(direntp->d_name, ".."))) {
return NULL;
}
// it can reach here with no problem
closedir(dirp);
return direntp->d_name;
} else {
closedir(dirp);
return NULL;
}
}
int main() {
char *dname = ".";
char *bname = "test.c";
char *result = next_node(dname, bname);
printf("%s\n", result);
return 0;
}
你有五个错误。
1:
DIR *dirp = opendir(dname);
您无需检查此opendir
成功。
2:
struct dirent *direntp;
while (((direntp = readdir(dirp)) != NULL) && (strcmp(direntp->d_name, bname))) {
}
if ((direntp = readdir(dirp)) != NULL) {
在这里,即使上一个循环由于readdir
返回NULL
终止,您也可以调用readdir
。 你要:
if ((direntp != NULL) && ((direntp = readdir(dirp)) != NULL)) {
3:
if ((strcmp(direntp->d_name, ".")) || (strcmp(direntp->d_name, ".."))){
将整数转换为布尔值等效于询问其是否不为零。 strcmp
函数在匹配时返回零。 因此,询问是否不为零就是询问其是否不匹配。 但是,一切都不是“。”的匹配项。 还是不匹配“ ..”! 你要:
if ((!strcmp(direntp->d_name, ".")) || (!strcmp(direntp->d_name, ".."))){
4:
// it can reach here with no problem
closedir(dirp);
return direntp->d_name;
您刚刚将指针返回到您关闭的目录中,从而使指针无效。 您需要确定返回的指针的寿命是多少,并可能分配一些内存以返回。
也许:
char *ret = strdup (dirent->d_name);
closedir(dirp);
return ret;
请注意,调用者完成处理后需要free
返回的字符串。
5:
char *result = next_node(dname, bname);
printf("%s\n", result);
如果result
为NULL
则将失败。 尝试:
char *result = next_node(dname, bname);
printf("%s\n", (result == NULL) ? "NULL" : result);
(代表OP张贴) 。
更新:问题是在main中打印NULL。 在Linux中,将NULL打印只会产生段错误,而在Windows中则不会。
strcmp返回0如果它们之间没有区别,请尝试以下操作
if (strcmp(dname, bname)) {
return NULL;
}
编辑:另外,我不确定您的问题是我正在Windows上使用gcc编译此文件,还是没有任何问题。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.