2014-04-18 75 views
2

我需要創建一個與其他文件夾具有相同權限的新文件夾。 我的任務最終目標是完全複製一個目錄及其內容。 這是我的第一步,我似乎無法得到它的工作。如何創建一個與現有訪問權限相同的目錄?

我有如下:

struct stat srcstat; 
int srcstatus = stat(source, &srcstat); 
if (chdir(dest)) 
    if (mkdir(dest, srcstat.st_mode)){ 
     printf("error: could not create <dest>\n"); 
     exit(1); 
    } 

源與路徑我想使用其權限的文​​件夾,一個CString。 dest是一個c字符串,包含新文件夾的路徑。

與新老和文件夾的權限LS低於

drwxrwxrwx 2 kingacev CS-Majors 4096 Apr 18 17:03 test 
drwxr-xr-x 2 kingacev CS-Majors 4096 Apr 18 18:12 test3 

我首先想到的是,我不能在我試圖方式使用srcstat.st_mode。如果是這樣的話,有沒有一種同樣簡單的方法來做我想做的事情?如果不是,離我的標記有多遠?

回答

10

您正在運行的「umask」,每個進程設置犯規這掩蓋了文件和目錄的創建操作了權限位。

沒有安全的方法來禁用umask。你應該做的是創建一個模式爲零的目錄(即所有訪問被拒絕),然後使用chmod(系統調用,而不是相同名稱的shell命令)將權限調整爲你想要的。

你的程序片段有許多其他的錯誤。這是很難全面恢復,並很可能是一個安全漏洞,如果你把它,所以我就寫出來了詳細正確的代碼:

int 
make_directory_like(const char *to_create, 
        const char *prototype)   
{ 
    struct stat st; 
    if (lstat(prototype, &st)) { 
     fprintf(stderr, "lstat: %s: %s\n", prototype, strerror(errno)); 
     return -1; 
    } 
    if (!S_ISDIR(st.st_mode)) { 
     fprintf(stderr, "lstat: %s: %s\n", prototype, strerror(ENOTDIR)); 
     return -1; 
    } 
    /* create directory initially with no perms at all - this is the only 
     safe way to suppress the effects of the umask. */ 
    if (mkdir(to_create, 0000)) { 
     if (errno != EEXIST) { 
      fprintf(stderr, "mkdir: %s: %s\n", to_create, strerror(errno)); 
      return -1; 
     } else { 
      /* check whether the thing that exists is a directory */ 
      struct stat st2; 
      if (lstat(to_create, &st2)) { 
       fprintf(stderr, "lstat: %s: %s\n", to_create, strerror(errno)); 
       return -1; 
      } 
      if (!S_ISDIR(st2.st_mode)) { 
       fprintf(stderr, "mkdir: %s: %s\n", to_create, strerror(EEXIST)); 
       return -1; 
      } 
     } 
    } 
    if (chmod(to_create, st.st_mode & ~S_IFMT)) { 
     fprintf(stderr, "chmod: %s: %s\n", to_create, strerror(errno)); 
     return -1; 
    } 
    return 0; 
} 

練習你:

  1. 爲什麼這是抑制umask影響的唯一安全方法? (提示:線程,但這只是幾個原因之一)
  2. 爲什麼我用lstat而不是stat
  3. 爲什麼需要統計創建路徑如果mkdir失敗errno == EEXIST
  4. 爲什麼使用chdir這樣做不正確? (有兩個原因。)
  5. 爲什麼它安全繼續前進,並呼籲mkdir在創建路徑,當我們不知道是否已經有東西嗎?
  6. 爲什麼& ~S_IFMT必需的東西?
+0

我會看看你的其他問題,謝謝。 – d0m1n1c

+0

但我的老師明確說過要使用stat,爲什麼不應該我 – d0m1n1c

+0

我可以考慮不使用chdir的唯一原因是它可能會移動我的cwd,但是我使用我修復了我發佈的段之外的內容。 – d0m1n1c

0

您需要將umask設置爲零。請參閱http://man7.org/linux/man-pages/man2/umask.2.html

否則,一些位(通常爲022,就像您所看到的)將始終被清除。

umask(0); 
+0

工作。我很好奇,你知道爲什麼它默認爲022而不是0嗎? – d0m1n1c

+0

爲什麼downvote? –

+1

-1:在任何情況下都不是線程安全的;如果您忘記將其恢復到原始值,即使在單線程程序中也可能造成災難性後果。 – zwol

相關問題