stat() giving wrong directory size in c

2020-04-11 13:34发布

问题:

I need to find the size of a file or a directory whatever given in the commandline using stat(). It works fine for the files (both relative and absolute paths) but when I give a directory, it always returns the size as 512 or 1024.

If I print the files in the directory it goes as follows :

 Name : .
 Name : ..
 Name : new
 Name : new.c

but only the new and new.c files are actually in there. For this, the size is returned as 512 even if I place more files in the directory. Here s my code fragment:

if (stat(request.data,&st)>=0){
        request.msgType = (short)0xfe21;
        printf("\n Size : %ld\n",st.st_size);
        sprintf(reply.data,"%ld",st.st_size);
        reply.dataLen = strlen(reply.data);
    }
    else{
        perror("\n Stat()");
    }
}

Where did I go wrong???

here is my request, reply structure:

 struct message{
        unsigned short msgType;
        unsigned int offset;
        unsigned int serverDelay;
        unsigned int dataLen;
        char data[100];
    };
struct message request,reply;

I run it in gcc compiler in unix os.

回答1:

stat() on a directory doesn't return the sum of the file sizes in it. The size field represents how much space it taken by the directory entry instead, and it varies depending on a few factors. If you want to know how much space is taken by all files below a specific directory, then you have to recurse down the tree, adding up the space taken by all files. This is how tools like du work.



回答2:

Yes. opendir() + loop on readdir()/stat() will give you the file/directory sizes which you can sum to get a total. If you have sub-directories you will also have to loop on those and the files within them.

To use du you could use the system() function. This only returns a result code to the calling program so you could save the results to a file and then read the file. The code would be something like,

system("du -sb dirname > du_res_file");

Then you can read the file du_res_file (assuming it has been created successfully) to get your answer. This would give the size of the directory + sub-directories + files in one go.



回答3:

Im sorry, I missed it the first time, stat only gives the size of files, not directories:

These functions return information about a file. No permissions are required on the file itself, but-in the case of stat() and lstat() - execute (search) permission is required on all of the directories in path that lead to the file.

The st_size field gives the size of the file (if it is a regular file or a symbolic link) in bytes. The size of a symbolic link is the length of the pathname it contains, without a terminating null byte.

look at the man page on fstat/stat