views:

367

answers:

2

Hello,

Do you know why a lot of file are not listed by this program, even if they are "regular"?

#include <stdio.h>
#include <sys/types.h>
#include <sys/param.h>
#include <sys/stat.h>
#include <dirent.h>

int main(void) {
  DIR *dh = opendir("./"); // directory handle
  struct dirent *file; // a 'directory entity' AKA file    
  struct stat info; // info about the file.
  while (file = readdir(dh)) {
    stat(file->d_name, &info);
    printf("note: file->d_name => %s\n", file->d_name);
    printf("note: info.st_mode => %i\n", info.st_mode);
    if (S_ISREG(info.st_mode))
      printf("REGULAR FILE FOUND! %s\n", file->d_name);
  }
  closedir(dh);

  return 0;
}

After executed this program, I get this:

note: file->d_name => .
note: info.st_mode => 16877
note: file->d_name => ..
note: info.st_mode => 16832
note: file->d_name => .DS_Store
note: info.st_mode => 16832
note: file->d_name => ef efeff
note: info.st_mode => 16832
note: file->d_name => ffffff
note: info.st_mode => 16832
note: file->d_name => ffffff - copie
note: info.st_mode => 16832
note: file->d_name => folder
note: info.st_mode => 16832
note: file->d_name => printiie.tt
note: info.st_mode => 16832
note: file->d_name => test.c
note: info.st_mode => 33188
REGULAR FILE FOUND! test.c
note: file->d_name => z
note: info.st_mode => 33188
REGULAR FILE FOUND! z

As you can see, the program see only 2 files. But every files are regulars, and there is only one folder...

Here is a copy past of the shell command: $ ls -lai

total 64
2421444 drwxr-xr-x  10 denis  staff   340 27 oct 22:19 .
2416789 drwxr-xr-x@ 28 denis  staff   952 27 oct 22:20 ..
2423204 -rw-r--r--@  1 denis  staff  6148 27 oct 21:41 .DS_Store
2423206 -rwxr-xr-x@  1 denis  staff   895 27 oct 19:57 ef efeff
2423183 -rwxr-xr-x@  1 denis  staff   895 27 oct 19:57 ffffff
2423216 -rwxr-xr-x@  1 denis  staff   895 27 oct 19:57 ffffff - copie
2423436 drwxr-xr-x   2 denis  staff    68 27 oct 21:57 folder
2423180 -rw-r--r--@  1 denis  staff    38 27 oct 21:32 printiie.tt
2423682 -rw-r--r--@  1 denis  staff   895 27 oct 19:57 test.c
2423208 -rwxr-xr-x@  1 denis  staff    34 27 oct 21:39 z

Actually I just would like to list the name of each file, but without directories. I work on Mac OS X, but I don't think this could be the reason of the problem.

Thanks for any help.

+3  A: 

It looks like the stat function is failing for some of the files, so the info struct isn't being updated and still has the data in it from "..". Replace that line with:

if (stat(file->d_name, &info))
{
    printf("error: stat(%s): %s\n", file->d_name, strerror(errno));
    continue;
}

..and you'll see why.

caf
Thanks! I get this message for unlisted files: error: stat(printiie.tt): No such file or directory For the moment I don't understand why, because those files exist...
Denis
It looks to me like the directory you're examining with `opendir` isn't the same as the current working directory that `stat` is looking at. What happens with `opendir(".")` instead?
caf
after some tests, I get this: note: file->d_name => .note: info.st_mode => 16877note: file->d_name => ..note: info.st_mode => 16832It is strange because after deleting .DS_Store, the program detect 0 file.
Denis
A: 

I once had to list every yml file in directory including subdirectories. It was on Win XP: system("dir C:\Path\To\File\*.yml /B /S >> list.txt"); and then I would parse list.txt to get all of the them. One line was one file. Easy, but not portable. Also that was some time ago - now I would maybe try boost.

EDIT: I can't comment, so I'm editing this answer. It's not about the code, but:

Actually I just would like to list the name of each file, but without directories.

If he took the same approach as me, he would have his problem solved.

Yelonek
-1: this is not an answer to the question about the code.
Andrew Y