Linux文件权限

Linux的安全性

Linux安全系统的核心是用户账户。每个能访问Linux系统的用户都会被分配一个唯一的用户账户

用户权限是通过创建用户时分配的用户ID(user ID,UID)来跟踪的

用户在登录系统时是使用登录名(login name)来代替UID登录

登录名是用户用来登录系统的最长8字符的字符串(字符可以是数字或字母),同时会关联一个对应的密码。

/etc/passwd文件

/etc/passwd来匹配登录名与对应的UID值。

[root@Wesuiliye ~]# cat /etc/passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin
sync:x:5:0:sync:/sbin:/bin/sync
shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown
halt:x:7:0:halt:/sbin:/sbin/halt
mail:x:8:12:mail:/var/spool/mail:/sbin/nologin
operator:x:11:0:operator:/root:/sbin/nologin
games:x:12:100:games:/usr/games:/sbin/nologin

root用户账户是Linux系统的管理员,为其固定分配的UID是0。

Linux系统会为各种各样的功能创建不同的用户账户,而这些账户并非真正的人类用户。我们称其为系统账户,它们是系统中运行的各种服务进程访问资源使用的特殊账户。所有运行在后台的服务都需要通过一个系统用户账户登录到Linux系统中。

1.为了安全。运行在Linux服务器后台的大多数服务是用自己的账户登录。

2.Linux为系统账户预留了500以下的UID。

/etc/passwd文件中包含的内容远不止用户的登录名和UID。该文件各个字段的含义如下。

·登录用户名
·用户密码
·用户账户的UID(数字形式)
·用户账户的组ID(数字形式)
·用户账户的文本描述(称为备注字段)
·用户$HOME目录的位置
·用户的默认shell

/etc/passwd文件中的密码字段都被设置为x,这可不是说所有的用户账户都使用相同的密码。只是在这个passwd这个文件看不到密码了

现在,绝大多数Linux系统将用户密码保存在单独的文件(称为shadow文件,位于/etc/shadow)中。只有特定的程序(比如登录程序)才能访问该文件。

/etc/shadow文件

/etc/shadow文件为系统中的每个用户账户都保存了一条记录。记录就像下面这样。

root:$6$VTKAlky5$h65nTRD:19418:0:99999:7:::

/etc/shadow文件中的每条记录共包含9个字段。

·登录名,对应于/etc/passwd文件中的登录名。
·加密后的密码。
·自上次修改密码后已经过去的天数(从1970年1月1日开始计算)。
·多少天后才能更改密码。
·多少天后必须更改密码。
·密码过期前提前多少天提醒用户更改密码。
·密码过期后多少天禁用用户账户。
·用户账户被禁用的日期(以从1970年1月1日到当时的天数表示)。
·预留给以后使用的字段。

添加新用户

用来向Linux系统添加新用户的主要工具是useradd。该命令可以一次性轻松创建新用户账户并设置用户的$HOME目录结构。

要想查看所使用的Linux发行版的系统默认值,可以使用加入了-D选项的useradd命令。如果不明确指明具体值,useradd命令所使用的默认值。

[root@Wesuiliye ~]# useradd -D
GROUP=100 #新用户会被添加到GID为100的公共组。
HOME=/home #新用户的主目录会位于/home/loginname。
INACTIVE=-1 #新用户账户密码在过期后不会被禁用。
EXPIRE= #新用户账户不设置过期日期。
SHELL=/bin/bash #新用户账户将bash shell作为默认shell。
SKEL=/etc/skel #系统会将/etc/skel目录的内容复制到用户的$HOME目录。
CREATE_MAIL_SPOOL=yes  #系统会为该用户账户在mail目录下创建一个用于接收邮件的文件。
[root@Wesuiliye ~]# 

useradd命令的默认值使用/etc/default/useradd文件设置。另外,进一步的安全设置在/etc/login.defs文件中定义。

useradd命令允许管理员创建默认的$HOME目录配置,然后将其作为创建新用户$HOME目录的模板。

[root@Wesuiliye ~]# ll -a /etc/skel/
total 32
drwxr-xr-x.   3 root root  4096 Mar  8 10:19 .
drwxr-xr-x. 150 root root 12288 Apr 28 18:24 ..
-rw-r--r--    1 root root    18 Nov 25  2021 .bash_logout
-rw-r--r--    1 root root   193 Nov 25  2021 .bash_profile
-rw-r--r--    1 root root   231 Nov 25  2021 .bashrc
drwxr-xr-x    4 root root  4096 Mar  8 10:19 .mozilla
[root@Wesuiliye ~]# 

1.系统会自动将这些默认文件复制到你创建的每个用户的$HOME目录。

2.对很多Linux发行版而言,useradd命令默认并不创建$HOME目录,但是-m命令行选项会使其创建$HOME目录。你可以在/etc/login.defs文件中更改该行为。

useradd命令行选项

useradd修改系统默认值

可以使用-D选项来修改系统默认的新用户设置。

[root@Wesuiliye ~]# useradd -D -s /bash/tsch
[root@Wesuiliye ~]# useradd -D
GROUP=100
HOME=/home
INACTIVE=-1
EXPIRE=
SHELL=/bash/tsch
SKEL=/etc/skel
CREATE_MAIL_SPOOL=yes
[root@Wesuiliye ~]# 

删除用户

在默认情况下,userdel命令只删除/etc/passwd和/etc/shadow文件中的用户信息,属于该账户的文件会被保留。

如果加入-r选项,则userdel会删除用户的$HOME目录以及邮件目录。然而,系统中仍可能存有已删除用户的其他文件。

[root@Wesuiliye ~]# userdel -r test
[root@Wesuiliye ~]# ls -al /home/test
ls: cannot access /home/test: No such file or directory
[root@Wesuiliye ~]# 

修改用户

usermod

·-l:修改用户账户的登录名。
·-L:锁定账户,禁止用户登录。
·-p:修改账户密码。
·-U:解除锁定,恢复用户登录。
·-g<群组>  修改用户所属的群组。
·-G<群组>  修改用户所属的附加群组。

·-L:选项尤为实用。该选项可以锁定账户,使用户无法登录,无须删除账户和用户数据。要恢复账户,只需使用-U选项即可。

passwd和chpasswd

passwd命令可以方便地修改用户密码:

[root@Wesuiliye ~]# passwd test 
Changing password for user test.
New password: 
Retype new password: 
passwd: all authentication tokens updated successfully.
[root@Wesuiliye ~]# 

如果只使用passwd命令,则修改的是你自己的密码。系统中的任何用户都能修改自己的密码,但只有root用户才有权限修改别人的密码。

-e选项可以强制用户下次登录时修改密码。你可以先给用户设置一个简单的密码,之后强制用户在下次登录时改成他们能记住的更复杂的密码。

如果需要为系统中的大量用户修改密码,那么chpasswd命令可以助你事半功倍。

echo test:Adjf31js1 | chpasswd 

chpasswd命令能从标准输入自动读取一系列以冒号分隔的登录名和密码对偶(login name and password pair),自动对密码加密,然后为用户账户设置密码。

也可以用重定向命令将包含username:password对偶的文件重定向给该命令。

chpasswd < users.txt

chsh、chfn和chage

chsh、chfn和chage用于修改特定的账户信息。

chsh命令可以快速修改默认的用户登录shell。使用时必须用shell的全路径名作为参数,不能只用shell名:

[root@Wesuiliye ~]# chsh -s /bin/csh test
Changing shell for test.
Shell changed.
[root@Wesuiliye ~]# 

finger命令可以非常方便地查看Linux系统的用户信息。

[root@Wesuiliye ~]# finger test
Login: test                             Name: 
Directory: /home/test                   Shell: /bin/csh
Last login Thu May 11 15:14 (CST) on pts/2
No mail.
No Plan.
[root@Wesuiliye ~]# 

如果使用chfn命令时不加任何选项,则会询问你要将哪些内容写入备注字段:

[root@Wesuiliye ~]# chfn test
Changing finger information for test.
Name []: for testing
Office []: 
Office Phone []: 
Home Phone []: 

Finger information changed.
[root@Wesuiliye ~]# finger test
Login: test                             Name: for testing
Directory: /home/test                   Shell: /bin/csh
Last login Thu May 11 15:14 (CST) on pts/2
No mail.
No Plan.
[root@Wesuiliye ~]# 

查看/etc/passwd文件中的记录,结果如下:

test:x:1002:1002:for testing:/home/test:/bin/csh

chage命令可用于帮助管理用户账户的有效期。

chage命令的日期值可以用下面两种方式中的任意一种表示。

·YYYY-MM-DD格式的日期

·代表从1970年1月1日起的天数

使用Linux组

每个组都有唯一的GID,和UID类似,该值在系统中是唯一的。除了GID,每个组还有一个唯一的组名。

/etc/group文件

[root@Wesuiliye ~]# cat /etc/group
root:x:0:
bin:x:1:
daemon:x:2:
sys:x:3:
adm:x:4:
tty:x:5:
disk:x:6:
lp:x:7:
mem:x:8:
kmem:x:9:

对于系统账户组,为其分配的GID值低于500,而普通用户组的GID则从500开始分配。

/etc/group文件有4个字段。

·组名
·组密码
·GID
·属于该组的用户列表

注意 用户账户列表多少有些误导人。你会发现列表中的一些组没有任何用户。这并不是说这些组没有成员。当一个用户在/etc/passwd文件中指定某个组作为主要组时,该用户不会作为该组成员再出现在/etc/group文件中。多年来被这个问题困扰的系统管理员可不止一两个。

创建新组

groupadd命令可用于创建新组:

[root@Wesuiliye ~]# groupadd shared 
[root@Wesuiliye ~]# tail /etc/group
stapsys:x:157:
stapdev:x:158:
slocate:x:21:
avahi:x:70:
www:x:1000:
docker:x:981:
wesuiliye:x:1001:
screen:x:84:
test:x:1002:
shared:x:1003:
[root@Wesuiliye ~]# 

在创建新组时,默认不为其分配任何用户。groupadd命令没有提供向组中添加用户的选项,但可以用usermod命令来解决:

[root@Wesuiliye ~]# usermod -G shared test
[root@Wesuiliye ~]# tail /etc/group
stapsys:x:157:
stapdev:x:158:
slocate:x:21:
avahi:x:70:
www:x:1000:
docker:x:981:
wesuiliye:x:1001:
screen:x:84:
test:x:1002:
shared:x:1003:test

1.注意 如果更改了已登录系统的用户所属的组,则该用户必须注销后重新登录,这样新的组关系才能生效。

2.警告 为用户分配组时要格外小心。如果使用了-g选项,则指定的组名会替换掉在/etc/passwd文件中为该用户分配的主要组。-G选项则会将该组加入该用户的属组列表,不会影响主要组。

修改组

groupmod命令可以修改已有组的GID(使用-g选项)或组名(使用-n选项):

[root@Wesuiliye ~]# usermod -G shared test
[root@Wesuiliye ~]# groupmod -g 1111 sharing
[root@Wesuiliye ~]# tail /etc/group 
stapsys:x:157:
stapdev:x:158:
slocate:x:21:
avahi:x:70:
www:x:1000:
docker:x:981:
wesuiliye:x:1001:
screen:x:84:
test:x:1002:
sharing:x:1111:test

修改组名时,GID和组成员保持不变,只有组名会改变。由于所有的安全权限均基于GID,因此可以随意改变组名,不会影响文件的安全性。

理解文件权限

使用文件权限符号

[root@Wesuiliye ~]# ls -l
total 20
-rw-r--r-- 1 root root    0 Apr 29 22:26 123
drwxr-xr-x 2 root root 4096 May  1 00:11 data
drwxr-xr-x 2 root root 4096 Apr 28 18:24 java
drwxr-xr-x 3 root root 4096 Apr 28 18:28 MCserver
drwxr-xr-x 3 root root 4096 Apr  9 09:55 New_dir
drwxr-xr-x 6 root root 4096 Apr 22 10:21 Nonebot

输出结果的第一个字段就是描述文件和目录权限的编码。

之后是3组三字符的编码。每一组定义了3种访问权限。

·r代表对象是可读的

·w代表对象是可写的

·x代表对象是可执行的

如果没有某种权限,则在该权限位会出现连字符。这3组权限分别对应对象的3个安全级别。

·对象的属主

·对象的属组

·系统其他用户

还有另一种表现形式,八进制

r = 4 = 100
w = 2 = 010
x = 1 = 001

例子:

drwxr-xr-x 2 root root 4096 May  1 00:11 data

所属用户root有 读 写 执行 权限

所属组root有 读 执行 权限

所属其他用户有 读 执行 权限

默认文件权限

umask命令用来设置新建文件和目录的默认权限:

[root@Wesuiliye wesuiliye]# umask 
0022
[root@Wesuiliye wesuiliye]# 

umask值只是个掩码,它会屏蔽掉不想授予该安全级别的权限。

要把umask值从对象的全权限值(full permission)中减掉。对文件而言,全权限值是666(所有用户都有读取和写入的权限);对目录而言,全权限值则是777(所有用户都有读取、写入和执行权限)。

[root@Wesuiliye data]# touch 123
[root@Wesuiliye data]# ll
total 0
-rw-r--r-- 1 root root 0 May 12 23:34 123

所以,在上面的例子中,文件一开始的权限是666,减去umask值022之后,剩下的文件权限就成了644。

umask值通常会被设置在/etc/profile启动文件中。可以使用umask命令指定其他的umask默认值:

[root@Wesuiliye data]# umask 055
[root@Wesuiliye data]# touch 3
[root@Wesuiliye data]# ll
total 0
-rw--w--w- 1 root root 0 May 12 23:42 3

umask值同样会作用在新创建的目录上:

[root@Wesuiliye data]# umask 066
[root@Wesuiliye data]# mkdir 123
[root@Wesuiliye data]# ll
total 4
drwx--x--x 2 root root 4096 May 12 23:43 123

更改安全设置

修改权限

chmod命令可以修改文件和目录的安全设置。

chmod options mode file

options为chmod命令提供了额外的增强特性。-R选项能够以递归方式修改文件和目录的权限。你可以使用通配符指定多个文件名,然后用单个命令批量修改权限。

mode参数允许使用八进制模式或符号模式来进行安全设置。

[root@Wesuiliye data]# ll
total 4
drwx--x--x 2 root root 4096 May 12 23:43 123
[root@Wesuiliye data]# chmod 000 123
[root@Wesuiliye data]# ll
total 4
d--------- 2 root root 4096 May 12 23:43 123

在符号模式下指定权限的格式:

[ugoa...][[+-=][rwxXstugo...]

第一组字符定义了权限作用的对象。

·u代表用户·g代表组·o代表其他用户·a代表上述所有

接下来的符号表示你是想在现有权限基础上

增加权限(+)、移除权限(-),还是设置权限(=)。

最后,第三个符号代表要设置的权限。

·r代表对象是可读的
·w代表对象是可写的
·x代表对象是可执行的
·X:仅当对象是目录或者已有执行权限时才赋予执行权限。
·s:在执行时设置SUID或SGID。
·t:设置粘滞位(sticky bit)。
·u:设置属主权限。
·g:设置属组权限。
·o:设置其他用户权限。

具体用法如下:

[root@Wesuiliye data]# chmod o+r 123
[root@Wesuiliye data]# ll
total 4
d------r-- 2 root root 4096 May 12 23:43 123

改变所属关系

Linux提供了两个命令:chownchgrp,前者可以修改文件的属主,后者可以修改文件的默认属组。

chown命令的格式如下:

 chown options owner[.group] file

chown命令使用了一些不同的options。

-R选项与通配符相配合可以递归地修改子目录和文件的所属关系。

-h选项可以修改文件的所有符号链接文件的所属关系。

注意 只有root用户能修改文件的属主。任何用户都可以修改文件的属组,但前提是该用户必须是原属组和新属组的成员。

可以使用登录名或UID来指定文件的新属主:

[root@Wesuiliye data]# chown test newfile 
[root@Wesuiliye data]# ll
total 0
-rw-r--r-- 1 test root    0 May 13 00:07 newfile

chown命令也支持同时修改文件的属主和属组:

[root@Wesuiliye data]# chown test.test newfile 
[root@Wesuiliye data]# ll
total 0
-rw-r--r-- 1 test test    0 May 13 00:07 newfile

# 对于修改成与用户登录名相同的组名,也可以使用下面的方法
[root@Wesuiliye data]# chown test. newfile 
[root@Wesuiliye data]# ll
total 0
-rw-r--r-- 1 test test    0 May 13 00:07 newfile

也可以只修改文件的默认属组:

[root@Wesuiliye data]# chown .root newfile 
[root@Wesuiliye data]# ll
total 0
-rw-r--r-- 1 test root    0 May 13 00:07 newfile

chgrp命令可以方便地修改文件或目录的默认属组:

[root@Wesuiliye data]# chgrp test newfile 
[root@Wesuiliye data]# ll
total 0
-rw-r--r-- 1 test test    0 May 13 00:07 newfile

共享文件

Linux为每个文件和目录存储了3个额外的信息位。

·SUID(set user ID):让普通用户临时拥有该文件的属主的执行权限,suid权限只能应用在二进制可执行文件(命令)上,而且suid权限只能设置在属主位置上。

suid权限使用s表示,增加权限u+s,移除权限u-s;
suid权限也可以使用数字形式表示,0表示去除suid权限,4表示添加suid权限,而且是在原权限的数字表达形式开头加0或4,如:0755移除suid权限,4755添加suid权限。

·SGID(set group ID):sgid权限一般应用在目录上,当一个目录拥有sgid权限时,任何用户在该目录下创建的文件的属组都会继承该目录的属组。

sgid权限也使用s表示,增加权限g+s,移除权限g-s;
sgid权限也可以使用数字形式表示,0表示去除sgid权限,2表示添加sgid权限,而且是在原权限的数字表达形式开头加0或2,如:0755移除sgid权限,2755添加sgid权限。

[root@Wesuiliye wesuiliye]# ll
total 4
drwxrwxr-x 2 wesuiliye wesuiliye 4096 May 13 17:10 newfile
[root@Wesuiliye wesuiliye]# touch newfile/file
[root@Wesuiliye wesuiliye]# ll newfile/file 
-rw-r--r-- 1 root root 0 May 13 17:11 newfile/file
[root@Wesuiliye wesuiliye]# chmod g+s newfile/
[root@Wesuiliye wesuiliye]# touch newfile/newfile   
[root@Wesuiliye wesuiliye]# ll newfile/newfile -d    
-rw-r--r-- 1 root wesuiliye 0 May 13 17:11 newfile/newfile # 可以看到所属组已经改变了
[root@Wesuiliye wesuiliye]# 
·粘滞位(sticky bit):sticky权限一般针对目录来设置,作用是只允该目录下的文件的创建者删除自己的创建的文件,不允许其他人删除文件。(root用户除外,因为root用户是超级管理员),而且sticky权限只能设置在other位置上。

sticky权限使用t表示,增加权限o+t,移除权限o-t;
sticky权限也可以使用数字形式表示,0表示去除权限,1表示添加权限,而且是在原权限的数字表达形式开头加0或1,如下:如:0755移除sticky权限,1755添加sticky权限。

[root@Wesuiliye wesuiliye]# mkdir newfile
[root@Wesuiliye wesuiliye]# chmod 777 newfile/
[root@Wesuiliye wesuiliye]# ll
total 4
drwxrwxrwx 2 root root 4096 May 13 17:15 newfile
[root@Wesuiliye wesuiliye]# touch newfile/file 
[root@Wesuiliye wesuiliye]# su wesuiliye
[wesuiliye@Wesuiliye ~]$ rm -f newfile/file 
[wesuiliye@Wesuiliye ~]$ ll newfile/
total 0
[wesuiliye@Wesuiliye ~]$  # 正常情况能删除

[root@Wesuiliye wesuiliye]# chmod o+t newfile/
[root@Wesuiliye wesuiliye]# ll
total 4
drwxrwxrwt 2 root root 4096 May 13 17:18 newfile
[root@Wesuiliye wesuiliye]# touch newfile/file 
[root@Wesuiliye wesuiliye]# su wesuiliye
[wesuiliye@Wesuiliye ~]$ ll
total 4
drwxrwxrwt 2 root root 4096 May 13 17:19 newfile
[wesuiliye@Wesuiliye ~]$ rm -f newfile/file 
rm: cannot remove ‘newfile/file’: Operation not permitted # 设置sticky权限后就不能删除了
[wesuiliye@Wesuiliye ~]$ 

访问控制列表

可以使用setfacl命令和getfacl命令在Linux中实现ACL特性。

getfacl命令能够查看分配给文件或目录的ACL:

[root@Wesuiliye ~]# getfacl 123
# file: 123
# owner: root
# group: root
user::rw-
group::r--
other::r--

[root@Wesuiliye ~]# 

setfacl命令可以为用户或组分配权限:

setfacl [options] rule filenames

setfacl命令允许使用-m选项修改分配给文件或目录的权限,或使用-x选项删除特定权限。可以使用下列3种格式定义规则:

u[ser]:uid:perms
g[roup]:gid:perms
o[ther]::perms

例子:

[root@Wesuiliye ~]# setfacl -m g:test:rw 123
[root@Wesuiliye ~]# ll 
total 0
-rw-rw-r--+ 1 root root    0 Apr 29 22:26 123

注意,setfacl命令不产生输出。在列出文件时,只显示标准的属主、属组和其他用户权限,但在权限列的末尾多了一个加号(+),指明该文件还应用了ACL。

[root@Wesuiliye ~]# getfacl 123
# file: 123
# owner: root
# group: root
user::rw-
group::r--
group:test:rw-
mask::rw-
other::r--

默认组(rich)对文件有读权限,sales组对文件有读写权限

要想删除权限,可以使用-x选项:

[root@Wesuiliye ~]# setfacl -x g:test 123
[root@Wesuiliye ~]# getfacl 123
# file: 123
# owner: root
# group: root
user::rw-
group::r--
mask::r--
other::r--

[root@Wesuiliye ~]# 

Linux也允许对目录设置默认ACL,在该目录中创建的文件会自动继承。

要想设置目录的默认ACL,可以在正常的规则定义前加上d:

[root@Wesuiliye data]# ll
total 4
drwxr-xr-x 2 root root 4096 May 13 23:24 newfile
[root@Wesuiliye data]# setfacl -m d:g:test:rw newfile/
[root@Wesuiliye data]# cd newfile/
[root@Wesuiliye newfile]# touch 123
[root@Wesuiliye newfile]# ll
total 0
-rw-rw-r--+ 1 root root 0 May 13 23:25 123
[root@Wesuiliye newfile]# getfacl 123
# file: 123
# owner: root
# group: root
user::rw-
group::r-x                      #effective:r--
group:test:rw-
mask::rw-
other::r--

[root@Wesuiliye newfile]#

/sales目录添加了sales组的读写权限。在该目录中创建的所有文件都会自动为sales组分配读写权限。

posted @ 2023-05-23 14:47  0x1e61  阅读(63)  评论(0编辑  收藏  举报