新建一個文件或目錄,它的默認權限是什么?如果要修改一個用戶創建的文件和目錄的默認權限該如何做?本文將介紹相關的內容。說明:本文的演示環境為 ubuntu 16.04。
文件的默認權限
為了查看用戶創建的文件和目錄的默認權限,我們用一個普通的用戶創建文件 myfile 和目錄 mydir 並查看它們的默認權限:
目錄的權限為 775,文件的權限為 664。對比之下發現目錄比文件多了執行的權限。這是因為執行權限對於目錄來說是非常重要的,有了目錄的執行權限才能夠進入目錄中進行文件操作。
默認情況下對於目錄來說最大的權限是 777,對於文件來說最大的權限一般為 666(只有可以執行的文件才添加可執行權限)。所以我們創建的文件和目錄的共同特點是從最大權限中減去了 2,也就是其他用戶的寫權限。而這個被減去的值就是我們常說的 umask。umask 還是 bash 的一個內置命令,默認輸出當前用戶的 umask 值:
注意,umask 顯示的值為從默認的最大權限中減去的值。上圖中的第一個 0 表示 8 進制,這里我們可以暫時忽略它。
系統的默認策略(Ubuntu16.04)
系統在用戶登錄時通過 login 程序調用 pam_umask 模塊設置用戶默認的 umask。從 login 程序的配置文件 /etc/login.defs 中我們可以找到 umask 相關的配置:
# UMASK is the default umask value for pam_umask and is used by # useradd and newusers to set the mode of the new home directories. # 022 is the "historical" value in Debian for UMASK # 027, or even 077, could be considered better for privacy # There is no One True Answer here : each sysadmin must make up his/her # mind. # # If USERGROUPS_ENAB is set to "yes", that will modify this UMASK default value # for private user groups, i. e. the uid is the same as gid, and username is # the same as the primary group name: for these, the user permissions will be # used as group permissions, e. g. 022 will become 002. # # Prefix these values with "0" to get octal, "0x" to get hexadecimal. # UMASK 022 …….. # Enable setting of the umask group bits to be the same as owner bits # (examples: 022 -> 002, 077 -> 007) for non-root users, if the uid is # the same as gid, and username is the same as the primary group name. # # If set to yes, userdel will remove the user´s group if it contains no # more members, and useradd will create by default a group with the name # of the user. # USERGROUPS_ENAB yes
乍一看上面的配置信息,用戶的默認 umask 應該是 022 才對啊。仔細地閱讀相關的說明信息發現,當 USERGROUPS_ENAB 被設置為 yes 時(默認值),對於 uid 和 gid 相同且用戶名和主組名相同的用戶,系統會把其 umask 改為 002。所以我們看到用戶 nick 的 umask 為 002。
由於 root 用戶的特殊性,它默認的 umask 與其它用戶是不同的,其值為 022:
umask 命令
umask 是 bash 的一個內置命令,用來顯示或設置新建文件/目錄的權限掩碼(umask)。前面我們以數字的方式輸出了用戶默認的 umask 值,這次我們以符號的方式進行輸出:
$ umask -S
以符號輸出的就是用戶創建目錄時的默認權限,算一下,其實就是 775。
為了改變用戶創建的文件/目錄的默認值,我們可以改變 umask 的默認值。
設置 umask 值
最簡單的方式就是為 umask 命令指定一個數字:
$ umask 026
026 的含義為:去掉 group 中的寫權限,去掉 other 中的讀寫權限。
這時創建的文件權限為 640,目錄權限為 751。注意,修改 umask 后只有新建的文件和目錄受影響,已經存在的文件和目錄的權限不會被影響。
以符號的方式設置 umask 值
比如下面的命令:
$ umask u=, g=w, o=rwx
上面的命令表示從 group 中去掉寫權限,從 other 中去掉讀寫執行的權限。
注意:"=" 號在 umask 命令和 chmod 命令中的作用恰恰相反。在 chmod 命令中,利用它來設置指定的權限,而其余權限則被刪除。但是在 umask 命令中,將在原有權限的基礎上刪除指定的權限。
在 ~/.bashrc 文件中為用戶設置默認的 umask
如果讓用戶每次登陸后都執行 umask 命令修改默認的 umask 值是不科學的,我們可以在用戶的 ~/.bashrc 文件中執行 umask 命令,這樣用戶登錄后 umask 的值自動就變成了設置的值。把下面的命令添加到 ~/.bashrc 文件的最后一行:
umask 026
保存后重新登錄一次,然后查看 umask 的值:
文件和目錄的創建
下面通過 strace 來跟蹤文件和目錄創建的過程,看看 mask 是如何影響它們的創建操作的。
創建一個文件
$ umask 077; strace -eopen touch testfile 2>&1 | tail -2; ls -l testfile
上圖中 open 函數使用 666 權限創建文件,但是由於設置了 umask 為 077,所以內核在創建文件時移除了 group 和 other 的 rwx 權限,最終創建的文件權限為 600。
創建一個目錄
$ umask 022; strace -emkdir mkdir testdir; ls -ld testdir
上圖中 mkdir 函數使用 777 權限創建目錄,但是由於設置了 umask 為 022,內核最終創建的目錄權限為 755。
umask 與 ACL
如果一個目錄沒有被設置 default ACL,那么將由 umask 決定新文件的 ACL 權限。這種情況其實就是我們常見的沒有 ACL 權限時的情況。比如我們設置 umask 為 026,那么創建的文件和目錄的權限就是由它決定的。
如果一個目錄被設置了 default ACL,那么將會由文件創建函數的 mode 參數和目錄的 default ACL 共通決定新文件的 ACL 權限,此時 umask 被忽略。還以 umask 026 為例,我們創建一個目錄 dir2 並設置 default ACL 權限:
$ setfacl -m d:u:tester:rwx dir2
然后在 dir2 目錄中創建文件 testfile:
這次 testfile 的權限已經不受 umask 的影響了!
總結
umask 是一個看似簡單實則影響重大的命令,根據實際需求設置好 umask 不僅能夠保護系統的安全,還會讓操作變得輕松(少一些 Permission denied)。