C方向扫描进入无限循环
}更新:为了完整起见,添加另一个观察:C方向扫描进入无限循环,c,C,}更新:为了完整起见,添加另一个观察: tmp处理也被破坏;它被分配为一个1字符的缓冲区,除了空字符串外,它永远不能保存任何有效的C字符串,因为字符串终止字符需要1个字符 删除tmp,直接与ent->d_name比较即可: int ScanDirectories(const char *dirname, struct images *imagesHeadPtr, struct filesToParse *filesHeadPtr) { // scan the directory and
tmp
处理也被破坏;它被分配为一个1字符的缓冲区,除了空字符串外,它永远不能保存任何有效的C字符串,因为字符串终止字符需要1个字符
删除tmp
,直接与ent->d_name
比较即可:
int ScanDirectories(const char *dirname, struct images *imagesHeadPtr, struct filesToParse *filesHeadPtr)
{
// scan the directory and store the entries in a buffer
DIR *dir;
struct dirent *ent;
int jpgs = 0, pngs = 0;
int totalFiles = 0;
int filesToScan = 0;
char name[256];
char *tmp = malloc(sizeof(char));
if((dir = opendir(dirname)) == NULL)
{
perror("Unable to open directory");
DisplayFolderNotFound();
return(0);
}
while((ent = readdir(dir)) != NULL)
{
strcpy(name, ent->d_name);
strncpy(tmp, name, 1);
if(strcmp(tmp, ".") == 0) //Not valid directories. These are dir's created by system and are hidden.
continue;
char dirCopy[strlen(dirname)+ strlen(name) + 1 /* for slash */ + 1 /*for null character*/];
strcpy(dirCopy, dirname);
strcat(dirCopy, "/");
strcat(dirCopy, name);
struct stat s;
if( stat(dirCopy, &s) == 0 )
{
if( s.st_mode & S_IFDIR )
{
// it's a directory
// printf("Directory [%s]\n", dirCopy);
ScanDirectories(dirCopy, imagesHeadPtr, filesHeadPtr); //Already inside a dir, recursively traverse it.
}
else if( s.st_mode & S_IFREG )
{
//it's a file
//printf("File [%s]\n", name);
++totalFiles;
}
else
{
//something else
}
}
else
{
//error
return(0);
}
int extensionLength = 0;
char *endP = name + strlen(name) - 1; //pointer to the last char of filename
char *temp = endP;
while (*temp != '.')
{
++extensionLength;
--temp;
}
char *extension = (char *)malloc(sizeof(char)*(extensionLength+1 /* for . */ + 1 /* for null char */));
strncpy(extension, name+strlen(name)-extensionLength-1, extensionLength+2);
if(strcmp(extension, ".abc")==0)
{
++pngs;
struct images *nextPtr = imagesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->fileName = (char *)malloc(sizeof(char)*(strlen(name)+1));
strcpy(nextPtr->fileName, name);
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->isUsed = 0;
nextPtr->fileSize = GetFileSize(dirCopy)/1000.0;
nextPtr->next = (struct images *)malloc(sizeof(struct images));
nextPtr = nextPtr->next;
nextPtr->fileName = NULL;
nextPtr->filePath = NULL;
nextPtr->isUsed = 0;
nextPtr->fileSize = 0;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".rst")==0)
{
++jpgs;
struct images *nextPtr = imagesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->fileName = (char *)malloc(sizeof(char)*(strlen(name)+1));
strcpy(nextPtr->fileName, name);
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->isUsed = 0;
nextPtr->fileSize = GetFileSize(dirCopy)/1000.0;
nextPtr->next = (struct images *)malloc(sizeof(struct images));
nextPtr = nextPtr->next;
nextPtr->fileName = NULL;
nextPtr->filePath = NULL;
nextPtr->isUsed = 0;
nextPtr->fileSize = 0;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".dig") == 0)
{
++filesToScan;
struct filesToParse *nextPtr = filesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->next = (struct filesToParse *)malloc(sizeof(struct filesToParse));
nextPtr = nextPtr->next;
nextPtr->filePath = NULL;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".x") == 0)
{
++filesToScan;
struct filesToParse *nextPtr = filesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->next = (struct filesToParse *)malloc(sizeof(struct filesToParse));
nextPtr = nextPtr->next;
nextPtr->filePath = NULL;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".cderf") == 0)
{
++filesToScan;
struct filesToParse *nextPtr = filesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->next = (struct filesToParse *)malloc(sizeof(struct filesToParse));
nextPtr = nextPtr->next;
nextPtr->filePath = NULL;
nextPtr->next = NULL;
}
free(extension); //because of this line, my code runs into infinite loop saying
//unable to open dir : too many files open. If I comment this out, my code works fine but the concepts of memory management say that I should be freeing it.
}
free(tmp);
if (closedir(dir) != 0)
perror("Unable to close directory");
return(1);
那么这个,
if(strcmp(ent->d_name, ".") == 0)
continue;
对于不包含句点的文件名,将非常糟糕
更明智的方法是寻找最后一个时期,并处理它不存在的情况:
char *endP = name + strlen(name) - 1; //pointer to the last char of filename
char *temp = endP;
while (*temp != '.')
{
++extensionLength;
--temp;
}
当然,如果文件名采用多字节编码,则在文件名上使用库函数(如
)是不安全的;您需要注意这一点。更新:为了完整起见,添加另一个观察:
tmp
处理也被破坏;它被分配为一个1字符的缓冲区,除了空字符串外,它永远不能保存任何有效的C字符串,因为字符串终止字符需要1个字符
删除tmp
,直接与ent->d_name
比较即可:
int ScanDirectories(const char *dirname, struct images *imagesHeadPtr, struct filesToParse *filesHeadPtr)
{
// scan the directory and store the entries in a buffer
DIR *dir;
struct dirent *ent;
int jpgs = 0, pngs = 0;
int totalFiles = 0;
int filesToScan = 0;
char name[256];
char *tmp = malloc(sizeof(char));
if((dir = opendir(dirname)) == NULL)
{
perror("Unable to open directory");
DisplayFolderNotFound();
return(0);
}
while((ent = readdir(dir)) != NULL)
{
strcpy(name, ent->d_name);
strncpy(tmp, name, 1);
if(strcmp(tmp, ".") == 0) //Not valid directories. These are dir's created by system and are hidden.
continue;
char dirCopy[strlen(dirname)+ strlen(name) + 1 /* for slash */ + 1 /*for null character*/];
strcpy(dirCopy, dirname);
strcat(dirCopy, "/");
strcat(dirCopy, name);
struct stat s;
if( stat(dirCopy, &s) == 0 )
{
if( s.st_mode & S_IFDIR )
{
// it's a directory
// printf("Directory [%s]\n", dirCopy);
ScanDirectories(dirCopy, imagesHeadPtr, filesHeadPtr); //Already inside a dir, recursively traverse it.
}
else if( s.st_mode & S_IFREG )
{
//it's a file
//printf("File [%s]\n", name);
++totalFiles;
}
else
{
//something else
}
}
else
{
//error
return(0);
}
int extensionLength = 0;
char *endP = name + strlen(name) - 1; //pointer to the last char of filename
char *temp = endP;
while (*temp != '.')
{
++extensionLength;
--temp;
}
char *extension = (char *)malloc(sizeof(char)*(extensionLength+1 /* for . */ + 1 /* for null char */));
strncpy(extension, name+strlen(name)-extensionLength-1, extensionLength+2);
if(strcmp(extension, ".abc")==0)
{
++pngs;
struct images *nextPtr = imagesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->fileName = (char *)malloc(sizeof(char)*(strlen(name)+1));
strcpy(nextPtr->fileName, name);
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->isUsed = 0;
nextPtr->fileSize = GetFileSize(dirCopy)/1000.0;
nextPtr->next = (struct images *)malloc(sizeof(struct images));
nextPtr = nextPtr->next;
nextPtr->fileName = NULL;
nextPtr->filePath = NULL;
nextPtr->isUsed = 0;
nextPtr->fileSize = 0;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".rst")==0)
{
++jpgs;
struct images *nextPtr = imagesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->fileName = (char *)malloc(sizeof(char)*(strlen(name)+1));
strcpy(nextPtr->fileName, name);
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->isUsed = 0;
nextPtr->fileSize = GetFileSize(dirCopy)/1000.0;
nextPtr->next = (struct images *)malloc(sizeof(struct images));
nextPtr = nextPtr->next;
nextPtr->fileName = NULL;
nextPtr->filePath = NULL;
nextPtr->isUsed = 0;
nextPtr->fileSize = 0;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".dig") == 0)
{
++filesToScan;
struct filesToParse *nextPtr = filesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->next = (struct filesToParse *)malloc(sizeof(struct filesToParse));
nextPtr = nextPtr->next;
nextPtr->filePath = NULL;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".x") == 0)
{
++filesToScan;
struct filesToParse *nextPtr = filesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->next = (struct filesToParse *)malloc(sizeof(struct filesToParse));
nextPtr = nextPtr->next;
nextPtr->filePath = NULL;
nextPtr->next = NULL;
}
else if(strcmp(extension, ".cderf") == 0)
{
++filesToScan;
struct filesToParse *nextPtr = filesHeadPtr;
while(nextPtr->next != NULL)
nextPtr = nextPtr ->next;
nextPtr->filePath = (char *)malloc(sizeof(char)*(strlen(dirCopy)+1));
strcpy(nextPtr->filePath, dirCopy);
nextPtr->next = (struct filesToParse *)malloc(sizeof(struct filesToParse));
nextPtr = nextPtr->next;
nextPtr->filePath = NULL;
nextPtr->next = NULL;
}
free(extension); //because of this line, my code runs into infinite loop saying
//unable to open dir : too many files open. If I comment this out, my code works fine but the concepts of memory management say that I should be freeing it.
}
free(tmp);
if (closedir(dir) != 0)
perror("Unable to close directory");
return(1);
那么这个,
if(strcmp(ent->d_name, ".") == 0)
continue;
对于不包含句点的文件名,将非常糟糕
更明智的方法是寻找最后一个时期,并处理它不存在的情况:
char *endP = name + strlen(name) - 1; //pointer to the last char of filename
char *temp = endP;
while (*temp != '.')
{
++extensionLength;
--temp;
}
当然,如果文件名采用多字节编码,则在文件名上使用库函数(如
)是不安全的;您需要注意这一点。C库函数strcmp()
在字符串不同或达到\0
(字符串末尾)时停止比较:
但是tmp字符串没有空终止符\0
。因此,比较生成无限循环
为tmp字符串保留2个字节,而不是1个:
if(strcmp(tmp, ".") == 0) //Not valid directories. These are dir's created by system and are hidden.
continue;
将终止符\0
添加到字符串:
char *tmp = malloc(2*sizeof(char));
当字符串不同或达到
\0
(字符串末尾)时,C库函数strcmp()
停止比较:
但是tmp字符串没有空终止符\0
。因此,比较生成无限循环
为tmp字符串保留2个字节,而不是1个:
if(strcmp(tmp, ".") == 0) //Not valid directories. These are dir's created by system and are hidden.
continue;
将终止符\0
添加到字符串:
char *tmp = malloc(2*sizeof(char));
我还没有阅读所有代码,但我可能在这里:
tmp[1]='\0';
通过使用此结构,您只需排除。(当前)目录。所以你没有排除。。(父)目录,它导致循环。除此之外,您还希望排除隐藏目录,所以最好使用以下构造:
if(strcmp(tmp, ".") == 0) //Not valid directories. These are dir's created by system and are hidden.
continue;
我还没有阅读所有代码,但我可能在这里:
tmp[1]='\0';
通过使用此结构,您只需排除。(当前)目录。所以你没有排除。。(父)目录,它导致循环。除此之外,您还希望排除隐藏目录,所以最好使用以下构造:
if(strcmp(tmp, ".") == 0) //Not valid directories. These are dir's created by system and are hidden.
continue;
在这种情况下,它应该是
const char*extension=strrchr(name,'.')
并且他应该删除malloc
和strncpy
。所有的文件名都包含“.”这个漏洞在哪里?char*tmp=malloc(sizeof(char));在while循环之外,最后被释放。我看不出我的内存管理哪里出了问题,但是如果你看到下一行strncpy(tmp,name,1);它只复制一个字符,从名称表示的地址开始,该地址与&name[0]相同。tmp的大小应为2字节,1字节用于“.”,1字节用于“\0”。不是吗?char*endP=name+strlen(name)-1//指向文件名char*temp=endP的最后一个字符的指针;而(*temp!='.'){++extensionLength;--temp;}这又是为什么会严重泄漏呢?在这种情况下,它应该是const char*extension=strrchr(name'.')
并且他应该删除malloc
和strncpy
。所有的文件名都包含“.”这个漏洞在哪里?char*tmp=malloc(sizeof(char));在while循环之外,最后被释放。我看不出我的内存管理哪里出了问题,但是如果你看到下一行strncpy(tmp,name,1);它只复制一个字符,从名称表示的地址开始,该地址与&name[0]相同。tmp的大小应为2字节,1字节用于“.”,1字节用于“\0”。不是吗?char*endP=name+strlen(name)-1//指向文件名char*temp=endP的最后一个字符的指针;while(*temp!='){++extensionLength;--temp;}为什么会严重泄漏?使用调试器并检查它在无限循环中的确切位置。使用调试器并检查它在无限循环中的确切位置。我看到那里应该有一个空终止符,但为什么我这样注释时它不会发生//免费(延长)接球不错。谢谢这修复了错误。哦,我喜欢C。那里也有一个问题。。。尝试在while
循环之外声明指针,因为您在每个iterarion中都这样做。迭代内部:extension=(char*)malloc(sizeof(char)*(extensionLength+nullCharLength))代码>在迭代之外:char*扩展代码>。如果文件没有扩展名怎么办?我看到应该有一个空终止符,但为什么我这样注释时不会出现这种情况//免费(延长)接球不错。谢谢这修复了错误。哦,我喜欢C。那里也有一个问题。。。尝试在while
循环之外声明指针,因为您在每个iterarion中都这样做。迭代内部:extension=(char*)malloc(sizeof(char)*(extensionLength+nullCharLength))代码>在迭代之外:char*扩展代码>。如果文件没有扩展名怎么办?