2017-08-04 88 views
1

我正在寫一個實用程序來遞歸掃描目錄樹並記錄文件名和大小的樹結構。 (儘可能快)如何獲得給定名稱和父目錄句柄或inode的文件大小?

也許我已經把自己編碼到了一個角落。我可以用readdir(3)獲取目錄的內容,並分別處理常規文件和目錄。

我看不到如何獲得除openat(), fstat(), close()調用以外的常規文件的文件大小。

有沒有辦法在我處理目錄條目時更直接地獲取文件大小?也許從inode號碼?

我期待這會存在:statat(int parentDirFD, const char * filename)因爲我只有文件名,而不是文件路徑。

我的內核似乎沒有O_PATH支持。

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

DIR* p_dir = ...; 

int dir_fd = dirfd(p_dir); 


size_t get_file_size(const char * filename_only, int dir_fd, DIR* pdir) 
{ 
    //// this just strikes me as overly expensive: 
    int fd = openat(dir_fd, filename_only, O_RDONLY); 
    struct stat sb; 
    fstat(fd, &sb); 
    size_t file_size = sb.st_size; 
    close(fd); 
    ////// 

    return file_size; 
} 
+3

,你希望被調用的函數'statat'實際上是所謂的'fstatat'。它需要一個額外的標誌參數來確定它是否在符號鏈接的情況下具有類似lstat的行爲。 [POSIX spec](http://pubs.opengroup.org/onlinepubs/9699919799/functions/fstatat.html)[Linux man page](http://man7.org/linux/man-pages/man2/fstatat.2 .html) –

+0

哦,我的天哪。它是!我想我在查看我的goto web手冊頁[fstat](https://linux.die.net/man/2/fstat)時忽略了它。 – NoahR

回答

0

有一次,Wumpus Q. Wumbley在評論中給出了答案,結果證明這很容易。 fstatat()

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

DIR* p_dir = ...; 

int dir_fd = dirfd(p_dir); 


size_t get_file_size(const char * filename_only, int dir_fd) 
{ 
    struct stat sb; 
    int fstatat_flags = 0; //| AT_SYMLINK_NOFOLLOW 
    int stat_res = fstatat(dir_fd, filename_only, &sb, fstatat_flags); 
    size_t file_size = sb.st_size; 

    return file_size; 
} 
+0

出於好奇,你有沒有發現你的系統在'fstatat'(和'openat' +'fdopendir'我猜想)和傳遞完整路徑名之間有任何性能差異?幾年前,我做了一些修補工作,希望能夠削減一些週期,並回想起結果有些不知所措。 – doynax

相關問題