2013-02-13 51 views
0

我做了嘗試創建一個目錄的功能,然後寫一個簡單的文件:書面文件和的mkdir比賽條件c

buffer = "Hello world!"; 
string url = "a/b/c/d/"; 
string tmp = ""; 
string done = ""; 
while((tmp = GetBaseDir(url)).compare("")!=0){ 
    done+=tmp; 
    mkdir(done.c_str(), 0777); 
} // GetBaseDir returns "a/", and changes url to "b/c/d/" 
ofstream file; 
file.open((url+"file.txt").c_str(),ios::trunc); 
file << buffer; 
file.close(); 

正如你所看到的,它只是嘗試,如果有故障它只是繼續前進。

我讀過'打開'將失敗,如果另一個進程打開具有寫入權限的同一文件。但是,這是真的嗎?
如果我同時運行此代碼的多個實例,mkdir和寫操作會發生什麼?

+1

[你有什麼試過](http://whathaveyoutried.com/)? – wallyk 2013-02-13 23:41:33

+0

編輯: 我還沒有試圖重現那種競爭條件。我想知道mkdir是否可靠執行,或者我必須使用互斥鎖來保護它。以及在C++中的寫入操作。 當我搜索這個問題,而不是找到相關的東西,我發現更多的問題或信息關於如何使用mkdir http://linux.die.net/man/3/mkdir,而不是如何工作。文檔頁面沒有提到競爭條件。 我發現寫入操作的競爭條件也沒有幫助。他們提到了不同例子的競爭條件,但我已經知道了。 – 2013-02-14 00:17:52

+0

我發現我可以使用打開的選項來保護文件O_WRONLY | O_CREAT | O_EXCL。但是,我不確定這是否足夠,或者我必須使用互斥鎖來確保正常工作。 – 2013-02-14 00:20:03

回答

0

當該目錄已經存在時,手冊頁註釋mkdir失敗。它返回-1而不是0.如果你忽略它,那麼只要a/b/c/d實際上是目錄,你的代碼通常工作正常。一個競爭過程可以將它們創建爲別的東西,從而導致錯誤。目前尚不清楚爲什麼使用0777模式,因爲使用0700甚至0770以及特殊組會更好。如果您確定它們始終是目錄,則代碼的每個實例都將確保dir路徑存在,並且唯一的爭用將在創建該文件時發生。

NAME 
    mkdir -- make a directory file 
SYNOPSIS 
    #include <sys/stat.h> 
    int mkdir(const char *path, mode_t mode); 
RETURN VALUES 
    A 0 return value indicates success. A -1 return value indicates an 
    error, and an error code is stored in errno. 
ERRORS 
    Mkdir() will fail and no directory will be created if: 
    ... 
    [EEXIST]   The named file exists.