在安全管理日益重要的今天,傳統的 Unix 文件系統的 UGO 權限管理方式已經沒法知足平常系統管理工做的須要。而 ACL 機制逐漸成爲主流的權限管理方式。本文主要介紹了在基於 Linux2.6 內核的發行版 Fedora Core 上進行的一些 ACL 基本功能的實驗。
ACL 簡介java
用戶權限管理始終是 Unix 系統管理中最重要的環節。你們對 Linux/Unix 的 UGO 權限管理方式必定不陌生,還有最經常使用的 chmod 命令。爲了實現一些比較複雜的權限管理,每每不得不建立不少的組,並加以詳細的記錄和區分(不少時候就是管理員的噩夢)。能夠針對某一個用戶對某一文件指定一個權限,恐怕管理員都期待的功能。好比對某一個特定的文件,用戶A能夠讀取,用戶B所在的組能夠修改,唯獨用戶B不能夠……。因而就有了IEEE POSIX 1003.1e這個ACL的標準。所謂ACL,就是Access Control List,一個文件/目錄的訪問控制列表,能夠針對任意指定的用戶/組分配RWX權限。如今主流的商業Unix系統都支持ACL。FreeBSD也提供了對ACL的支持。Linux在這個方面也不會落後,從2.6版內核開始支持ACL。node
準備工做安全
支持ACL須要內核和文件系統的支持。如今2.6內核配合EXT2/EXT3, JFS, XFS, ReiserFS等文件系統都是能夠支持ACL的。用本身工做用的物理分區體驗ACL,老是不明智的行爲。萬一誤操做致使分區的損壞,形成數據的丟失,損失就大了。做一個loop設備是個安全的替代方法。這樣不須要一個單獨的分區,也不須要很大的硬盤空間,大約有個幾百KB就足夠進行咱們的體驗了。OK,下面我使用Fedora Core 5和Ext3文件開始對Linux的ACL的體驗。bash
首先建立一個512KB的空白文件:ide
[root@FC3-vm opt]# dd if=/dev/zero of=/opt/testptn count=512
512+0 records in
512+0 records out
|
和一個loop設備聯繫在一塊兒:工具
[root@FC3-vm opt]# losetup /dev/loop0 /opt/testptn
|
建立一個EXT2的文件系統:oop
[root@FC3-vm opt]# mke2fs /dev/loop0
mke2fs 1.35 (28-Feb-2004)
max_blocks 262144, rsv_groups = 32, rsv_gdb = 0
Filesystem label=
OS type: Linux
Block size=1024 (log=0)
Fragment size=1024 (log=0)
32 inodes, 256 blocks
12 blocks (4.69%) reserved for the super user
First data block=1
1 block group
8192 blocks per group, 8192 fragments per group
32 inodes per group
Writing inode tables: done
Writing superblocks and filesystem accounting information: done
This filesystem will be automatically checked every 30 mounts or
180 days, whichever comes first. Use tune2fs -c or -i to override.
|
掛載新建的文件系統(注意mount選項裏的acl標誌,咱們靠它來通知內核咱們須要在這個文件系統中使用ACL):this
[root@FC3-vm opt]# mount -o rw,acl /dev/loop0 /mnt [root@FC3-vm opt]# cd /mnt [root@FC3-vm mnt]# ls lost+found |
如今我已經獲得了一個小型的文件系統。並且是支持ACL的。而且即便完全損壞也不會影響硬盤上其餘有價值的數據。能夠開始咱們的ACL體驗之旅了。spa
|
我首先新建一個文件做爲實施ACL的對象:
[root@FC3-vm mnt]# touch file1 [root@FC3-vm mnt]# ls -l file1 -rw-r--r-- 1 root root 7 Dec 11 00:28 file1 |
而後看一下這個文件缺省的ACL,這時這個文件除了一般的UGO的權限以外,並無ACL:
[root@FC3-vm mnt]# getfacl file1
# file: file1
# owner: root
# group: root
user::rw-
group::r--
other::r-
|
*注意:即便是不支持ACL的狀況下,getfacl仍然能返回一個這樣的結果。不過setfacl是不能工做的。
下面添加幾個用戶和組,一會我將使用ACL賦予他們不一樣的權限:
[root@FC3-vm mnt]# groupadd testg1 [root@FC3-vm mnt]# useradd testu1 [root@FC3-vm mnt]# useradd testu2 [root@FC3-vm mnt]# usermod -G testg1 testu1 |
如今咱們看看testu1能作什麼:
[root@FC3-vm mnt]# su testu1 [testu1@FC3-vm mnt]$ echo "testu1" >> file1 bash: file1: Permission denied |
失敗了。由於file1並不容許除了root之外的用戶寫。咱們如今就經過修改file1的ACL賦予testu1足夠的權限:
[root@FC3-vm mnt]# setfacl -m u:testu1:rw file1 [root@FC3-vm mnt]# su testu1 [testu1@FC3-vm mnt]$ echo "testu1" >> file1 [testu1@FC3-vm mnt]$ cat file1 testu1 |
修改爲功了,用戶testu1能夠對file1作讀寫操做了。咱們來看一下file1的ACL:
[testu1@FC3-vm mnt]$ getfacl file1
# file: file1
# owner: root
# group: root
user::rw-
user:testu1:rw-
group::r--
mask::rw-
other::r-
|
咱們ls看一下:
[root@FC3-vm mnt]# ls -l file1
-rw-rw-r--+ 1 root root 7 Dec 11 00:28 file1
|
能夠看到那個"+"了麼?就在一般咱們看到的權限位的旁邊。這個說明file1設置了ACL, 接下來咱們修改一下testu1的權限,同時給testg1這個組以讀的權限:
[root@FC3-vm mnt]# setfacl -m u:testu1:rwx,g:testg1:r file1 [root@FC3-vm mnt]# getfacl file1 # file: file1 # owner: root # group: root user::rw- user:testu1:rwx group::r-- group:testg1:r-- mask::rwx other::r- |
能夠看到設置後的權限,testu1已經有了執行的權限,而testg1這個組也得到了讀取文件內容的權限。也許有人已經注意到了兩個問題:首先,file1的組權限從r--變成了rw-。其次,mask是什麼?爲何也變化了呢?咱們先從mask提及。若是說acl的優先級高於UGO,那麼mask就是一個名副其實的最後一道防線。它決定了一個用戶/組可以獲得的最大的權限。這樣咱們在不破壞已有ACL的定義的基礎上,能夠臨時提升或是下降安全級別:
[root@FC3-vm mnt]# setfacl -m mask::r file1 [root@FC3-vm mnt]# getfacl file1 # file: file1 # owner: root # group: root user::rw- user:testu1:rwx #effective:r-- group::r-- group:testg1:r-- mask::r-- other::r-- [root@FC3-vm mnt]# ls -l file1 -rw-r--r--+ 1 root root 7 Dec 11 00:28 file1 |
在testu1對應的ACL項的後邊出現了effective的字樣,這是實際testu1獲得的權限。Mask只對其餘用戶和組的權限有影響,對owner和other的權限是沒有任何影響的。執行ls的結果也顯示UGO的設置也有了對應的變化。由於在使用了ACL的狀況下,group的權限顯示的就是當前的mask。一般咱們把mask設置成rwx,以不阻止任何的單個ACL項。
*須要注意的是,每次修改或添加某個用戶或組的ACL項的時候,mask都會隨之修改以使最新的修改可以真正生效。因此若是須要一個比較嚴格的mask的話,可能須要每次都從新設置一下mask。
|
咱們來看一下其餘的ACL操做。首先如何刪除已有的ACL項呢?
[root@FC3-vm mnt]# setfacl -x g:testg1 file1 [root@FC3-vm mnt]# getfacl file1 # file: file1 # owner: root # group: root user::rw- user:testu1:rwx group::r-- mask::rwx other::r-- |
咱們看到testg1的權限已經被去掉了。若是須要去掉全部的ACL能夠用-b選項。全部的ACL項都會被去掉。
[root@FC3-vm mnt]# setfacl -b file1 [root@FC3-vm mnt]# getfacl file1 # file: file1 # owner: root # group: root user::rw- group::r-- other::r-- |
咱們能夠用--set 設置一些新的ACL項,並把原有的ACL項所有都覆蓋掉。和-m不一樣,-m選項只是修改已有的配置或是新增長一些。--set選項會把原有的ACL項都刪除,用新的替代,須要注意的是必定要包含UGO的設置,不能象-m同樣只是添加ACL就能夠了。好比下邊這一段:
[root@FC3-vm mnt]# setfacl --set u::rw,u:testu1:rw,g::r,o::- file1 [root@FC3-vm mnt]# getfacl file1 # file: file1 # owner: root # group: root user::rw- user:testu1:rw- group::r-- mask::rw- other::--- |
o::-是另外一個須要注意的地方。其實完整的寫法是other::---,正如u::rw的完整寫法是user::rw-。一般咱們能夠把"-"省略,可是當權限位只包含"-"時,必須至少保留一個。若是寫成了o::,就會出現錯誤。
若是但願對目錄下的全部子目錄都設置一樣的ACL,可使用-R參數:
[root@FC3-vm mnt]# setfacl --set u::rw,u:testu1:rw,g::r,o::- dir1
|
若是但願能從一個文件來讀入ACL,並修改當前的文件的ACL,能夠用-M參數:
[root@FC3-vm mnt]# cat test.acl
user:testu1:rw-
user:testu2:rw-
group:testg1:r--
group:testg2:r--
mask::rw-
other::---
|
|
若是咱們但願在一個目錄中新建的文件和目錄都使用同一個預約的ACL,那麼咱們可使用默認(Default) ACL。在對一個目錄設置了默認的ACL之後,每一個在目錄中建立的文件都會自動繼承目錄的默認ACL做爲本身的ACL。用setfacl的-d選項就能夠作到這一點:
[root@FC3-vm mnt]# setfacl -d --set g:testg1:rwx dir1 [root@FC3-vm mnt]# getfacl dir1 # file: dir1 # owner: root # group: root user::rwx group::r-x other::r-x default:user::rwx default:group::r-x default:group:testg1:rwx default:mask::rwx default:other::r-x |
能夠看到默認ACL已經被設置了。創建一個文件試試:
[root@FC3-vm mnt]# touch dir1/file1 [root@FC3-vm mnt]# getfacl dir1/file1 # file: dir1/file1 # owner: root # group: root user::rw- group::r-x #effective:r-- group:testg1:rwx #effective:rw- mask::rw- other::r-- |
file1自動繼承了dir1對testg1設置的ACL。只是因爲mask的存在使得testg1只能得到rw-權限。
|
主要的文件操做命令cp和mv都支持ACL,只是cp命令須要加上-p 參數。可是tar等常見的備份工具是不會保留目錄和文件的ACL信息的。 若是但願備份和恢復帶有ACL的文件和目錄,那麼能夠先把ACL備份到一個文件裏。之後用--restore選項來回復這個文件中保存的ACL信息:
[root@FC3-vm mnt]# getfacl -R dir1 > dir1.acl [root@FC3-vm mnt]# ls -l dir1.acl total 16 -rw-r--r-- 1 root root 310 Dec 12 21:10 dir1.acl |
咱們用-b選項刪除全部的ACL數據,來模擬從備份中回覆的文件和目錄:
[root@FC3-vm mnt]# setfacl -R -b dir1 [root@FC3-vm mnt]# getfacl -R dir1 # file: dir1 # owner: root # group: root user::rwx group::r-x other::r-x # file: dir1/file1 # owner: root # group: root user::rw- group::r-- other::r-- |
如今咱們從dir1.acl中恢復被刪除的ACL信息:
[root@FC3-vm mnt]# setfacl --restore dir1.acl [root@FC3-vm mnt]# getfacl -R dir1 # file: dir1 # owner: root # group: root user::rwx group::r-x other::r-x default:user::rwx default:group::r-x default:group:testg1:rwx default:mask::rwx default:other::r-x # file: dir1/file1 # owner: root # group: root user::rw- group::r-x #effective:r-- group:testg1:rwx #effective:rw- mask::rw- other::r-- |
|
ACL 的引入使得大規模的複雜權限管理能夠很容易的在 Linux 上實現。對於 /home 這樣存放大量用戶文件的分區,能夠作到更有效的管理。可是咱們也看到在備份工具等方面的欠缺,好在 FC2 中已經開始包含了 star 這樣的支持 ACL 的備份工具,雖然仍是 alpha 版。
在單個文件的 ACL 條目的數量上,不一樣的文件系統有不一樣的限制。Ext2 和 Ext3 只能支持每一個文件 25 個 ACL 條目。ReiserFS 和 JFS 能夠支持超過 8,000 個條目。這個方面 Ext* 文件系統還須要增強。
不管多麼複雜的系統中,文件系統的權限管理都是最基礎的內容。而 Linux 對 ACL的支持,無疑是一把管理海量用戶系統的利器,對 Linux 在大規模的企業級應用中更方便的發揮更大的做用添了一把火。