項目中要計算指定文件夾的大小。
百度查到這篇文章,https://my.oschina.net/Tsybius2014/blog/330628
方法可行,運行正確。html
拿到咱們的項目中,卻遇到一些問題:程序中一些讀文件的代碼,開始報異常,都不到文件。這些都是之前沒有遇到過的問題。
究竟是什麼狀況呢?排查了很久,終於發現使用該文章提供的計算文件夾大小的函數(暫且叫作GetDirectorySize),其中有改變當前目錄的代碼:多線程
chdir(dir);
咱們的項目是多線程的,一個線程調用GetDirectorySize,調用的過程當中改變了當前目錄,而此時另外一個線程使用相對路徑去讀文件,原來能讀到的,如今就讀不到了。特別提示chdir改變的是,當前進程(固然包括其下全部線程)的工做目錄!!!(具體能夠查看線程共享進程的那些資源?)函數
爲了去掉GetDirectorySize的反作用,我從新實現了該函數:spa
1 #include <stdio.h> 2 #include <sys/stat.h> 3 #include <sys/types.h> 4 #include <unistd.h> 5 #include <stdlib.h> 6 #include <dirent.h> 7 #include <string.h> 8 9 //計算某目錄所佔空間大小(包含自己的4096Byte) 10 long long int GetDirectorySize(char *dir) 11 { 12 DIR *dp; 13 struct dirent *entry; 14 struct stat statbuf; 15 long long int totalSize=0; 16 17 if ((dp = opendir(dir)) == NULL) 18 { 19 fprintf(stderr, "Cannot open dir: %s\n", dir); 20 return -1; //多是個文件,或者目錄不存在 21 } 22 23 //先加上自身目錄的大小 24 lstat(dir, &statbuf); 25 totalSize+=statbuf.st_size; 26 27 while ((entry = readdir(dp)) != NULL) 28 { 29 char subdir[256]; 30 sprintf(subdir, "%s/%s", dir, entry->d_name); 31 lstat(subdir, &statbuf); 32 33 if (S_ISDIR(statbuf.st_mode)) 34 { 35 if (strcmp(".", entry->d_name) == 0 || 36 strcmp("..", entry->d_name) == 0) 37 { 38 continue; 39 } 40 41 long long int subDirSize = GetDirectorySize(subdir); 42 totalSize+=subDirSize; 43 } 44 else 45 { 46 totalSize+=statbuf.st_size; 47 } 48 } 49 50 closedir(dp); 51 return totalSize; 52 } 53 54 int main(int argc, char* argv[]) 55 { 56 char* dir = argv[1]; 57 long long int totalSize = GetDirectorySize(dir); 58 printf("totalSize: %lld\n", totalSize); 59 60 return 0; 61 }