1、文件系统的基本概念
Linux文件系统中一切皆文件,文件包含一般文件(有时候也简称文件)和目录
它们都由inode节点和block节点集组成
1)针对一般文件
存在一个inode节点和一个block节点集(多个block节点)
一个inode节点中包含了文件大小,userId,groupId,读取执行权限配置等信息,具体见下图。
block节点集中的每个block节点中包含了该一般文件的具体数据内容
2)针对目录
存在一个inode节点和一个block节点集(多个block节点)
一个inode节点中包含了目录大小,userId,groupId,读取执行权限配置等信息,具体见上图。
block节点集中的每个block节点中包含了很多条记录,每条记录的形式是:
FileName表示该目录下的一般文件或者目录的名字,InodeID表示相应于名字的一般文件或者目录的Inode节点ID
如下图。
2、一般文件权限 1)读权限
指是否能够读取对应block节点中的内容
比如现在有一个一般文件a.txt,它的权限是"400",当前登录用户就是该一般文件的Owner
那么用vi打开该一般文件,就会在状态栏中看到如下图的提示信息
2)执行权限
指是否能够执行对应block节点中的内容
比如现在有一个一般文件a.txt,它的权限是"100"
那么用"ll a.txt"查看该一般文件,就会得到如下图的结果[呈现绿颜色,右上角有*号,表示该一般文件是可执行文件]
3)写权限
指是否能够修改对应block节点中的内容
比如现在有一个一般文件a.txt,它的权限是"200",当前登录用户就是该一般文件的Owner
那么执行"echo 'hello world!'>a.txt"命令,就能够把"hello world!"字符串写入a.txt文件中
3、目录权限
1)读权限
指是否能够读取对应block节点中的条目,但是不会去加载对应InodeID的数据信息,因而只能得到FileName信息
比如现在有一个authority目录,其下有一个a.txt一般文件,authority目录的权限是"400",当前登录用户就是目录的Owner
执行"ls authority",可以发现只能看到a.txt一般文件的名字,而不能看到该一般文件的权限信息[即没有去加载该一般文件的inode数据],如下图所示
2)执行权限
指是否能够读取对应block节点中的条目中的Inode节点的信息,并对其进行修改,即是否能够读取目录下一般文件和目录的"大小,userId,groupId,读取执行权限配置"等信息,并修改这些信息
能够读取inode节点信息的例子1:
如果将authority目录的权限改为属主可读可执行,即"chmod 500 authority",此时再执行"ls authority",就可以得到与"1)读权限"不一样的结果
此时已经将inode节点的信息读取出来,就有了权限,时间等信息
能够读取inode节点信息的例子2:
比如现在有一个authority目录,其下有一个a.txt一般文件,authority目录的权限是"100",当前登录用户就是目录的Owner,当前登录用户对a.txt具有rw(读写)权限
执行"echo 'hello world'>authority/a.txt",可以发现成功修改a.txt一般文件的内容
因为能够读取inode节点的信息,就能获取权限信息进行判断,然后发现当前用户能够对该一般文件进行rw操作,然后根据读取到的inode节点信息获取该一般文件的block节点集,进行文件内容修改
3)写权限 指是否能够增加,删除,修改block节点中的条目,即是否允许在该目录下增加文件,删除文件和进行文件重命名[注意:文件包括一般文件和目录]
由于增加文件,删除文件和进行文件重命名,都要使用到inode[比如增加文件需要修改inode上的时间属性,删除文件需要修改inode的硬链接计数,重命名通过先建立新的硬链接,再删除原有的硬链接来实现,因而也需要修改inode上的硬链接计数],因此需要拥有执行权限,写权限才能正常运作
比如现在有一个authority目录,其下有一个a.txt一般文件,authority目录的权限是"300",当前登录用户就是目录的Owner,
执行"touch authority/b.txt",就能在authority目录下创建一个b.txt一般文件
执行"rm authority/b.txt",就能将authority目录下的b.txt一般文件删除
执行"mv authority/a.txt authority/c.txt",就能将authority目录下的a.txt一般文件重命名为c.txt,如下图所示
4、进程权限 如何判定某个进程对文件的读取,写入和执行权限[注意:文件包括一般文件和目录]
首先介绍下进程的有效用户和有效用户组的概念,某个进程运行的时候,是以某个身份组合运行的[4][5],一般确定有效用户和有效用户组的方式是
有效用户:实际用户
有效用户组:实际用户组
实际用户:执行进程的用户
实际用户组:实际用户的primary group 比如说当前登录用户是dsl,它的primary group是dsl
那么执行kill命令,实际用户就是dsl,实际用户组是dsl,有效用户是dsl,有效用户组是dsl
那么执行sudo kill命令,实际用户就是root,实际用户组是root,有效用户是root,有效用户组是root[root的primary group是root]
判定某个进程对文件的读取,写入和执行权限,就只需要判定进程的身份组合对该文件的读取,写入和执行权限就可以了
我们经常使用的cd,ls等命令,在执行的时候也会创建相应的进程,我们经常会遇到"cd不了某个目录,ls不了某个目录下的文件"的情况,究其原因就是因为cd进程和ls进程的身份组合对这些目录缺少相关权限造成的
关于进程权限可参考另外一篇文章《进程的用户和用户组》
5、特殊权限
1)SUID
i、一般文件上设置SUID
当一个设置了SUID位的可执行文件被执行时,该文件将以文件所有者的身份运行,如果所有者是root,那么将以root的身份来执行该文件,即最后得到的进程的有效用户是root,在这种情况下效果与sudo执行一个文件一致[不过两者的Real UserId和Real GroupId并不一致,前者的是,这里以dsl代表进程创建用户,dsl是dsl用户的primary group,后者的是]
可通过以下代码来进行测试[6]
#include
#include
int main(int argc, char** argv) {
printf("%d", geteuid());
return 0;
}
> gcc -o setuid-test setuid-test.c
> ./setuid-test
备注:基于安全策略,在linux中,只能对二进制文件设置SUID,而不能对包括脚本文件在内的其他可执行文件设置SUID
ii、目录上设置SUID
The SUID permission set on a directory is ignored on UNIX and Linux systems.[7]
2)SGIT
i、一般文件上设置SGIT
当在一个可执行文件上设置了SGIT之后,那么文件执行创建得到的进程的有效用户组是该一般文件的所属组
可以用以下代码来测试有效用户组
#include
#include
int main(int argc,char** argv)
{
printf("%d\n",getegid());
return 0;
}
ii、目录上设置SGIT
当在一个目录A上设置了SGIT之后,在该目录下创建的的一般文件和目录的所属组跟A的所属组一致
3)sticky-bit
i、一般文件上设置sticky-bit
When set, it instructed theoperating systemto retain thetext segmentof the program inswap spaceafter theprocessexited. This speeds up subsequent executions by allowing the kernel to make a single operation of moving the program from swap to real memory.
ii、目录上设置sticky-bit
当在一个目录A上设置了sticky-bit之后,在该目录下创建的一般文件和目录具有这样的一个特殊性质: 只有它们(一般文件和目录)的属主和root用户有权删除它们,其他任何用户即便拥有对A目录的rwx权限,也不可以删除它们
最典型的例子是:
tmp目录是所有用户共有的临时文件夹,所有用户都拥有读写权限,这就必然出现一个问题,A用户在/tmp里创建了文件a.file,此时B用户看了不爽,在/tmp里把它给删了(因为拥有读写权限),那肯定是不行的。实际上是不会发生这种情况的,因为有特殊权限sticky-bit权限,正如drwxrwxrwt中的最后一个t
参考文献
[1]http://en.wikipedia.org/wiki/Inode
[2]http://superuser.com/questions/520107/how-are-directory-structures-stored-in-unix-filesystem
[3]http://www.cyberciti.biz/faq/how-linux-file-permissions-work/
[4]http://haifux.org/lectures/84-sil/users-processes-files-and-permissions/users-perms-lec.html
[5]http://stackoverflow.com/questions/6305416/how-does-a-process-in-linux-decides-privileges-allotted-to-it
[6]http://unix.stackexchange.com/questions/364/allow-setuid-on-shell-scripts
[7]http://en.wikipedia.org/wiki/Setuid#setuid_and_setgid_on_directories
[8]http://en.wikipedia.org/wiki/Sticky_bit