2012-07-17 75 views
3

我一直在檢查和戰鬥這個程序沒有成功很長一段時間,希望你能幫助我。使用readdir_r閱讀目錄

這個想法是讀取存儲在c_Localpath中的目錄,並將讀取的目錄複製到c_namesLocal以返回它們。

我在執行中做錯了什麼?該程序打破了strcpy,我不知道爲什麼。

DIR* ptr_dir = opendir(c_Localpath); 

char** c_namesLocal = calloc(1, 256); 

    size_t numElements = 0; 
    int returnCode =0; 
    struct dirent ptr_PrevDirEntry; 
    struct dirent* ptr_DirEntry = NULL; 
    returnCode = readdir_r(ptr_dir, &ptr_PrevDirEntry, 
      &ptr_DirEntry); 

    while ((returnCode ==0) && (ptr_DirEntry != NULL)) { 
     char* name = c_namesLocal[numElements]; 
     strcpy(name, ptr_DirEntry->d_name); 
     ptr_PrevDirEntry = *ptr_DirEntry; 
     returnCode = readdir_r(ptr_dir, &ptr_PrevDirEntry, 
       &ptr_DirEntry); 
     numElements++; 
     c_namesLocal = realloc(c_namesLocal, 256 * numElements); 
    } 

回答

0

這是一個零指示字例外,c_namesLocal實際上指向256 /的sizeof(字符*)的char *指針全部由釋放calloc設置爲空,所以c_namesLocal[numElements] == 0的序列。您必須爲每個條目分配內存。

+0

非常感謝您的回答,但我沒有完全得到它,我應該如何分配,否則比realloc? – 2012-07-17 22:17:11

0

在此代碼:

char* name = c_namesLocal[numElements]; 
strcpy(name, ptr_DirEntry->d_name); 

name開始爲NULL。您初始化了指針的一個向量,但單指針本身仍然指向NULL。你應該分配內存d_name:當你的realloc指針的矢量

if (NULL == (c_namesLocal[numElements] = strdup(ptr_DirEntry->d_name))) 
{ 
    // signal out of memory and return 
} 

而同樣的檢查:

// You no longer need '*name' 
c_namesLocal[numElements] = strdup(ptr_DirEntry->d_name); 

然後,它會謹慎地添加檢查。

5

對不起,2年後回覆。但我想幫助那些想知道答案的人。 我一直在執行readdir_r,因此我修改了您的代碼以使其工作。我不能說整個代碼都可以工作,但可以確定的是,您可以在您提到的指定目錄中獲得下一個文件條目。因此,您可以將這些條目保存到其他變量中,並可以做任何您想要的操作。

請參閱下文。

DIR* ptr_dir = opendir(c_Localpath); 
size_t numElements = 0; 
int returnCode =0; 
struct dirent *ptr_PrevDirEntry = NULL; 
struct dirent *ptr_DirEntry = NULL; 
int len_entry; 
char *c_namesLocal = NULL; 

len_entry = offsetof(struct dirent, d_name) + fpathconf(dirfd(ptr_dir), _PC_NAME_MAX) + 1; 
ptr_PrevDirEntry = malloc(len_entry); 

if(!ptr_PrevDirEntry) 
     exit(0); 

for(;;){ 
     readdir_r(ptr_dir, ptr_PrevDirEntry, &ptr_DirEntry); 
     if(!ptr_DirEntry) 
      break; 
     else 
     { 
       if((strcmp(ptr_DirEntry->d_name, ".") != 0) && (strcmp(ptr_DirEntry->d_name, "..") != 0)) // skip "." and ".." file listings 
       { 
        //Perform copying or do whatever you want with the file entry read from the dir "c_Localpath" 
        //Increase numElements to 1 and keep on increasing by 1 on every iteration 
        numElements++; 
        //realloc everytime you find next entry 
        c_namesLocal = realloc(c_namesLocal, 256 * numElements); 
        //copy the next file name in the c_namesLocal[0], c_namesLocal[1] and so on. 
        strcpy(c_namesLocal[numElements - 1], ptr_DirEntry->d_name); 
       } 
     } 
} 

//free "ptr_PrevDirEntry" before returning and take care of "c_namesLocal" as well. 

上面的代碼是不言自明的。我希望它能幫助你。歡呼:)

+0

'if(strlen(ptr_DirEntry)> 2)'會比這個跳過更多。 – 2014-12-24 13:55:46

+0

修改代碼。感謝您指出。 :) – Rohit 2014-12-26 05:13:31

+0

我想在Visual Studio中使用readdir_r函數。你有什麼想法,我該怎麼做? – 2016-07-20 11:12:01