前言
这篇文章我们要学习权限,那学之前我们先来做一件事情。 在前面的学习中我们基本都是用root用户登录的,那这节的内容可能会用到普通用户登录,所以先来带大家了解一下如何创建一个普通用户。 其实很简单:
我现在是root用户登录,然后我们来创建一个普通用户 怎么创建呢——adduser 用户名
(用户名是我们自己起的)
然后,我们看到在/home下面就有创建好的这个用户了。 那然后做什么呢? 我们来给它设置一个密码: passwd 用户名
注意:Linux输入密码的时候不会回显。 输入两遍,就设置好了。 如果后续你想删除某个普通用户——userdel -r 用户名
1. Linux权限的概念
首先我们来了解一下权限的概念:
相信如果不谈Linux,只提权限的话,大家应该都不陌生,毕竟在在我们的日常生活中,权限无处不在。 比如:我们在爱奇艺、优酷这些软件上看视频,有些内容是会员才能看的,你没充VIP,就不让你看
还有比如说QQ空间,我们如果访问陌生人的空间,可能会遇到这样的提示
所以我们可以这样理解,权限是限制人的。
但是不能仅这么理解:
如果我现在想在腾讯视频里写代码,可以做成吗? 是不是也不能做,因为腾讯视频根本就不具备这个功能。 换句话说,我们访问的对象可能天然的就不具备某些“属性”。
所以我们可以这样理解:
权限就是:一件事情是否允许被谁“做” 权限=人+事物属性
那我们下面就从这两个方面来讨论一下Linux中的权限,先来说一下“人”——即Linux上的用户。
Linux下有两种用户:超级用户(root)和 普通用户:
超级用户root:可以在linux系统下做任何事情,几乎不受限制。root用户只有一个。 普通用户:在linux下做有限的事情,普通用户可以有多个。
那这是关于人的,那上面所说的事物对应到Linux中又是什么呢?
那这里所说的事物通常在Linux指的就是文件,当然不仅仅指文件,现阶段我们主要先来谈文件。 那事物属性当然就对应到文件的属性了。 那在Linux中,文件可以拥有的属性有:可读、可写、可执行。
简单了解了权限的概念,那接下来我们就来学习一下Linux的权限管理。
2. Linux权限管理
2.1 文件类型
我现在所在的目录下,有这些文件和目录:
那ll给我们显示了这么多信息,接下来我们就来分析一下这些信息都表示的是什么? 那其实里面有些信息我们还是有些了解的,最右边的,那就是文件名或者目录名嘛。 紧挨着的,就是文件创建或者最近修改的一个时间。 在往左,就是文件或目录的大小了嘛。
这几个我们差不多还知道它代表什么。 但是剩下的那几个,我们好像就不太清楚它们是啥了。
不着急,我们接下来都会慢慢介绍。
对于最左边的这一块:
我们看到有10列,现在我们先来讨论第一列是什么东西。 🆗,那第一列的这个字符其实表示的是文件类型 那我们就要知道: Linux不用文件后缀区分文件类型,而是用文件属性中第一列的第一个字符来标识文件类型。
那Linux中的文件都有哪些类型呢?那也就对应了第一个字符有哪几种呢?
-:普通文件(指不包含有文件系统信息的结构信息的文件,是用户所接触到的文件,比如常见的.exe,.c,.txt,归档文件等在Linux中统称为普通文件) d:目录(文件夹) (ps:前两个是最常见的) l:软链接(类似Windows的快捷方式)文件 b:块设备文件(例如硬盘、光驱等) p:管道文件 c:字符设备文件(例如屏幕等串口设备) s:套接字文件
那认识了文件类型之后,我们来思考一个问题,上面说了Linux不以文件后缀区分文件类型,那今后我们在Linux中该如何去看待文件后缀这个东西呢?
那想告诉大家的是,今后我们自己创建文件的时候照样可以加对应的后缀,想用就用,因为这个是给我们自己看的,给人看的。 在Linux中我们可以将后缀看成文件名的一部分。
但是呢,大家可能就会对这种现象产生疑问:
现在在我当前这个目录下有一个.c文件,里面有一段C语言代码
并且它编译生成的可执行文件也是可以正常运行的:
那我们上面说了,Linux不用文件后缀区分文件类型,那我就可以这样做:
我给a.out改名,改成a.txt,那它不会改变类型,还是可执行文件,还可以正常执行,没毛病。
那我现在在这样搞:
我现在把test.c 改成test.txt,里面还是这段代码,然后那我们再用gcc编译它:
哦豁,怎么回事,我们看到报错说文件格式不能被识别。
你不是说Linux不以文件名区分文件类型嘛,那这里为啥一改后缀就不行了呢?
🆗,大家仔细听了,我们上面说的是Linux不以文件后缀区分文件类型,那这里的Linux指的是操作系统,也就是说操作系统不以文件后缀区分文件类型。 但是我们刚才做了一件什么事情——gcc test.txt
Linux操作系统不以文件后缀区分类型(Windows是以文件后缀区分类型的),并不代表gcc(Linux中的C编译器)或者其它的一些软件或命令不以文件后缀区分文件类型啊。
2.2 Linux用户分类及切换
用户分类
那Linux用户的分类其实我们上面已经提过了,分为root用户和普通用户
超级用户root:可以在linux系统下做任何事情,几乎不受限制。root用户只有一个。 普通用户:在linux下做有限的事情,普通用户可以有多个。
普通用户—>root
那不同的用户之间如何进行切换呢?
🆗,我们刚开始的时候带着大家创建了一个普通用户,我现在就登陆了我的普通用户:
那我现在想切换到root,怎么做呢? 这里用到的命令叫做:su
这时它让我们输密码,输什么秘密呢? 输入root的密码,注意不会回显
此时,我就成功切换到root了。
然后如果我们想退出登录可是敲ctrl+d或者exit就可以退出刚才的登录,又回到普通用户。 那这里要给大家看一个东西,我们待会会用到:
现在我是普通用户,处在这个目录下。 我现在再用su切换到root:
这里我们得出: su(或su root)可以从普通用户切换到root用户,仅仅是一个用户身份的切换,用户所处的路径不发生改变。
那除了su,还有另外一个从普通用户切换到root的方法:
就是su -
也切换过来了,但是大家有发现什么不同吗? 🆗,我们发现用户也切换成root了,而且多了一条信息提示,显示了一下上次登录的时间,并且所处的路径发生了变化,变成了root的家目录/root。 所以,su -
其实是重新登录root,登录后默认所在路径在家目录下。
root—>普通用户
要从root用户切换到普通用户user,则使用 su user
普通用户之间的切换
普通用户之间相切换又该怎么做呢?
我这里现在有两个普通用户,我现在登录的是yhq,那现在我想切换到ymm,怎么做? 直接su 用户名
然后它让我输密码,那肯定是输ymm这个用户的秘密,可是我不知道,那怎么办呢?
我现在是一个普通用户,没有人家的密码,我就登录不了。 但是,权限是用来约束普通人的,我们是普通用户,我切换不了,那我可以变成root用户再切换啊!
现在我们变成root了,此时我再来切换成ymm用户
一句指令就搞定了,密码都不用输。 所以从目前看来,root是不受约束的,想干嘛就干嘛。
单条指令的提权
我们上面说了普通用户在Linux下能做的事情是有限的,可能会受到很多限制:
比如,我现在是普通用户yhq,当前目录下有一个文件:
由于某些原因,我现在没有查看该文件的权限,但是我很想看里面的内容,我当然可以切换成root查看,但是我们嫌这样做麻烦,有什么简单的办法吗?
此时我就可以选择对单条指令进行提权:
怎么做呢? 原指令不变,只需在前面加上sudo
就行了,这就是对单条指令进行提权:
根据提示,现在需要输我自己的密码。 但是呢,目前我们可能还用不了sudo这个命令,可能会报这样的错:
那我们后面会解决这个问题,现在大家先不用管,你可以直接切换成root去查看。
那上面的内容呢,可以认为是对具体用户的讨论,那下面我们再来讨论一个问题叫做用户角色的划分。
2.3 用户角色划分/文件访问者的分类(人)
那在Linux中还对用户角色进行了划分,或者说对文件访问者的一个分类:
那都分为了哪几类呢? 文件和文件目录的拥有者:u—User 文件和文件目录的所属组:g—Group 其它用户(及不是这个文件的拥有者):o—Others
那然后我们再来分析这张图:
这里面每一列都代表什么我们还没有分析完。 那我们刚才提到的文件访问者的几种分类在这里都对应哪一列呢? 🆗 ,图中的第三列其实就对应文件的拥有者,第四列就对应文件的所属组
那other在哪呢? 🆗,Linux其实不不记录other,other可能有很多个,除了拥有者和所属组之外的都是other。
然后我们再来讨论一个问题,相信文件的拥有者和other大家都很容易理解,那还有一个文件所属组,这个概念该怎么理解呢?为什么要有文件所属组呢?
🆗,下面通过一个例子带大家理解一下。 假设现在有一个公司,它比较穷,只有一台Linux机器,所有人都在这台机器上开发。另外呢,该公司允许不同的工作小组做同一件工作。 那假设现在有两个小组A组和B组,它们在开发同一款产品,现在有两个人,张三在A 组,李四在B组。 公司在Linux上创建了两个目录,A_code,B_code,分别让A,B两组存放自己的代码。
很快呢,张三就写好了一份代码test.c
,然后张三的组长看到了,就给张三说,把你的代码给我看看,我看你写的怎么样。 那我们假设此时Linux中没有所属组的概念,只有文件的拥有者和other。 然后A组长就去访问张三写的test.c,但是由于张三才是test.c的拥有者,A组长是other,所以看不了。 于是就去问张三,你这个代码我看不了啊,没有权限。 张三说,不好意思啊,我没有给other开权限,我现在开一下。 然后组长就可以看了。 但是呢,不仅A组长可以看了,B组的李四包括其它人也是other,所以B组的人也可以看了。 那这里就涉及到了权限安全的问题。 我只是想让我的组长看,但是现在其它组的人也可以看,那这不合理。 所以,Linux就顺理成章的引入了所属组的概念。 那有了所属组之后,张三就可以把自己的代码只开组内的权限,这样跟张三一组的人就都可以看了,但是其它组还是other,没有权限,就查看不了。
那我们继续:
上面呢我们讲到了Linux的用户分类,有root和普通用户,然后呢刚才又提到用户角色的划分,什么拥有者、所属组和other。
那上面提到的用户和刚才说的这些不同的角色有什么关系呢?
🆗,那这其实就是一个人和角色的关系。 比如我们在学校是学生,在家里是儿子或女儿,以后到了公司又是员工。 即人要扮演不同的角色。 那在Linux中也是这样,用户在不同情况下也可能是不同的角色。
2.4 文件类型和访问权限(事物属性)
a. 文件类型
首先文件类型其实我们上面已经介绍过了:
-:普通文件(指不包含有文件系统信息的结构信息的文件,是用户所接触到的文件,比如常见的.exe,.c,.txt,归档文件等在Linux中统称为普通文件) d:目录(文件夹) (ps:前两个是最常见的) l:软链接(类似Windows的快捷方式)文件 b:块设备文件(例如硬盘、光驱等) p:管道文件 c:字符设备文件(例如屏幕等串口设备) s:套接字文件
然后再来看这个:
我们来看第一列这一堆东西,首先第一个字符我们上面解释过了它表示文件类型,那剩下的9个字符代表什么呢?
那剩下的这9个呢,我们可以从前往后三个一组把他们划分为三组
那划分为三组,它们又分别代表什么呢?
它们是这样的一个对应关系。
那说到这里,就不得不提一下文件文件的基本权限了
b. 基本权限
Linux中文件的基本权限都有哪些呢?
读(r/4):Read对文件而言,具有读取文件内容的权限;对目录来说,具有浏览该目录信息的权限 写(w/2):Write对文件而言,具有修改文件内容的权限;对目录来说具有删除移动目录内文件的权限 执行(x/1):execute对文件而言,具有执行文件的权限;对目录来说,具有进入目录的权限 “—”表示不具有该项权限(三个字符的位置是确定的rwx,那个位置为_
就代表没有该权限)
那对于Linux中的一个文件,我们该如何去描述它的权限呢?
来看,当前我是普通用户登录,该目录下有这样几个文件。 拿test.c这个文件来说,怎么去描述它的权限呢? 我们上面说了,权限等于人+事物属性。
🆗,对于它的拥有者来说,权限是rw-
,即可读可写,所属组的权限也是可读可写rw-
,other的权限只有可读r--
。 另外,它的拥有者是yhq这个用户,所属组也是yhq。 那当前我就是yhq:
所以我就是拥有者和所属组,那其它的用户就是other。 所以呢? 我们未来描述一个文件的权限的时候,一定是描述它的拥有者、所属组、other分别有什么权限,它的拥有者和所属组都是谁。 这才是对一个文件权限的一个完整描述。
那然后我们再来看这个图:
现在除了第二列,其它列代表的含义我们都给大家解释了,拿第二列的数字表示什么呢? 那关于这个问题,我们现在还没法具体解释,后面再说。 大家可以先了解一下
2.5 文件访问权限的相关设置方法
上面我们学习了文件的访问权限,那现在有一个问题,我们如何去修改的权限呢?
那我们说了权限=人+事物属性。 那对应Linux中就是用户+文件属性。 所以,我们要修改权限,那要么修改用户,要么修改文件属性。 接下来我们就从这两个方面来讲解。
那我们先从文件的属性下手:
这里我们以tmp.txt为例,我当前登录的用户就是该文件的拥有者,所以我是可以修改文件的权限的,一般来说只有文件的拥有者和root才可以修改文件的权限。
那如何修改呢?
这里我们用到的命令叫做chmod
具体怎么做呢? 格式:chmod [参数] 权限 文件名 -R : 对目前目录下的所有文件与子目录进行相同的权限变更(即以递归的方式逐个变更) 比如对于tmp.txt文件,我现在想给拥有者增加r
即读的权限
我们看到就添加好了。 然后,给所属组添加写的权限
给other添加可执行权限
当然一次也可以添加多个权限:
比如给拥有者添加写和执行权限:
其它也是一样
那上面是添加权限,删除权限呢?
很简单,用-
就行了
当然,同时给不同角色修改权限也是可以的,用逗号隔开:
给所有人都去掉所有权限:
此外,如果我们想给所有人做同样的修改,可以这样:
还可以用=:
2.6 文件权限值的表示方法
上面我们讲到文件的三种权限读、写、执行的表示可以用三个字符r\w\x表示,那这种表示方法我们把它叫做字符表示法:
那除此之外呢,其实还有另外一种表示方法——8进制数值表示法:
什么意思呢?对于表示权限的9个字符来说,它们的情况无非就两种,要么是字母,要么是-
。
比如我们以test.c这个文件为例。 对于这九个字符来说,如果是字母,我们就认识是1,如果是-,就认为是0。 那么此时权限也可以这样表示:
那这就是文件权限的八进制表示法:
所以,我们修改文件权限,就也可以这样做:
我现在想给tmp.txt去掉所有权限,那就是:
我再想添加所有权限:
再来
这是文件权限的两种表示方法及修改方法。
2.7 有无权限的区别
那上面讲了那么多,改来改去也挺方便,那有权限和没权限到底会发生什么,有什么区别呢?
我们来看一下:
我现在把tmp.txt的所有权限都取消掉。 该文件的拥有者是yhq,而我现在就是yhq
那我们现在想查看tmp.txt的内容:
但是我们发现不行,被拒绝了,因为我虽然是拥有者,但我没有任何权限。 那看不了,我写入内容可以吗?
也不行。 权限是用来约束普通人的,而yhq就是一个普通用户,所以我们没有权限就操作不了。
那怎么办呢?怎么样可以查看呢?
那我就可以切换成root去查看:
那tmp.txt的拥有者是yhq,所以root是tmp.txt的other。 那other也没有权限啊。 但是,我root可以不用管这么多
我是other,但我照样查看。因为权限是约束普通人的,可管不了我root。 我不仅可以读,我还可以写:
2.8 更改文件拥有者
上面我们说了,修改权限,要么修改用户,要么修改文件属性,那修改文件属性我们上面讲过了,那怎么修改用户呢?
我们来演示一下:
我当前登录的是普通用户yhq,文件tmp.txt的拥有者就是我,那我现在想把它的拥有者改成root,怎么做呢? 我们要用到一个命令叫做chown
功能:修改文件的拥有者 格式:chown [参数] 用户名 文件名 -R : 处理指定目录以及其子目录下的所有文件 那我就可以这样做:chown root tmp.txt
但是我们发现这样不行。 怎么回事啊,我是这个文件的拥有者,为什么我不能修改啊。
那我问大家一个问题:你想把自己的一个东西给别人,要不要征得别人的允许?
当然是需要的。 但是在Linux中,我们好像没法去问另一个用户同不同意啊。 那既然这样,我就强制给你。 那强制的话,谁有这个能力啊,当然是root。
就可以了,当然后面我们可以用sudo的话用sudo也可以,不用切换,直接单条指令提权。
2.9 更改文件所属组
那上面是更改拥有者,那想更改所属组怎么做?
用另一个命令叫做chgrp
功能:修改文件或目录的所属组 格式:chgrp [参数] 用户组名 文件名 常用选项:-R 递归修改指定目录下的所有文件和子目录的所属组
就好了
那我想同时更改拥有者和所属组呢?
2.10 file指令
接下来我们再来认识一个指令——file
那file的作用是什么呢?
我们指令学过一个命令ls-l(ll)
,可以用来查看文件或目录的一些信息,这个指令相信大家已经很熟悉了:
然后通过这里第一列里面的第一个字符我们可以辨别该文件的类型。
那我这里要学的file指令,它可以更清晰的显示一个文件的类型:
功能说明:辨识文件类型。 语法:file [选项] 文件或目录… 常用选项: -c 详细显示指令执行过程,便于排错或分析程序执行的情形。 -z 尝试去解读压缩文件的内容。 演示一下:
2.11 目录的权限
那在上面我们学了文件的权限,相信对于文件来说,读写和执行,这些权限大家应该都比较容易理解,那目录的权限又该如何理解呢?
可执行权限x
首先我们来思考一个问题:对于一个目录来说,如果我们想进入这个目录,需要有什么权限呢?
不知道没关系。我们来测试一下。
当前这个路径下有一个目录dir,我目前登录的这个用户yhq就是它的拥有者,我拥有rwx所有的权限,所以我当前肯定是可以随意进出这个目录的:
但是我现在想知道进入目录依靠的是哪个权限。 那我们可以依次去取消对应的权限,看取消哪个之后不能再进入目录 首先我们把r
权限取消掉:
我发现还可以正常进入,所以r目录不是进入目录所需要的。 那w呢?
也不是。 那就剩x了,所以是x吗?
是的,就是r权限。我们把rw都加上,但是没有x,就还是进不去。
只有把x加上,才可以进入:
那我们得出结论:如果目录没有可执行权限(x),则无法cd到目录中。
可读权限r
那x权限决定是否能进入目录,那r
呢?
我们再来测试一下: 这次我们这么搞,把r权限去掉,看不能进行什么操作。
我们发现去掉r后,不能ls查看目录内容了。 那可以创建文件吗?
可以创建文件,因为我有写w
权限。
可写权限w
那w权限呢?
我现在把r加上,w去掉。 然后我们来测试
我发现不能在目录中创建文件和删除文件了。
这就是关于目录权限的理解,总结一下:
可执行权限x
: 如果目录没有可执行权限, 则无法cd到目录中 可读权限r
: 如果目录没有可读权限, 则无法用ls等命令查看目录中的文件内容 可写权限w
: 如果目录没有可写权限, 则无法在目录中创建文件, 也无法在目录中删除文件
2.12 默认权限
接下来我们再来认识一个概念叫做默认权限
当前目录下有这么几个文件,现在我来新建一个文件
我们看到普通文件(不包括可执行文件)new.c被创建出来自带的默认权限是664。 那我们再来创建一个目录
我们看到新创建的目录new_dir的默认权限是775。
那么现在问题就来了,为什么普通文件的默认权限是664,目录的默认权限是775呢?
首先呢要给大家说一下这里664和775只是在我当前所用的机器上(我用的是云服务器,centos7.6)是这个结果,可能在不同的操作系统上这个默认权限是不一样的。
权限掩码——umask
那下面我们就来分析一下默认权限为什么是这个值?
这里给大家引入一些概念: 首先有一个起始权限的概念,起始权限就是系统设定的。 普通文件(不包括可执行文件)的起始权限是666(没有x),目录文件的起始权限是777(rwx)。 那我们创建出来文件所看到的默认权限是怎么得到的呢? 🆗,Linux系统为了更好的控制权限,会提供一个默认的权限掩码,我们称之为umask
(在起始权限中,去掉在umask中出现出现的权限,不能影响其它任何权限)。
那这里掩码这个概念,大家如果没学过网络的话,可能不是很了解,那这里通过一个例子简单介绍一下:
比如,这里现在有这样一个二进制序列1011 1010
,那我现在想拿到它的后四位,有什么办法呢? 我可以拿他去按位与(&
)上0000 1111
就得到0000 1010
。 那这里我们用0000 1111
去提取原始数据(一个特定的二进制序列)中的特定区域,那这里用到的这个二进制序列0000 1111
我们就可以把他称之为“掩码”,这个东西就比较类似于掩码。
那下面,我们就来认识一下,在Linux中,系统默认是有自己的一个权限掩码的:
我们通过umaks
这条指令既可以获取这个权限掩码
那这个权限掩码我们可以认为是一个8进制数字(以0开头)。 那八进制002转换为二进制就是000 000 010
而我们的起始权限也是一个八进制数字嘛,这样它们正好可以一一对应。
那有了起始权限,有了权限掩码,如何得到我们的看到的文件的默认权限呢?
我们来分析一下: 我们现在知道普通文件的起始权限是666,二进制就是110 110 110
权限掩码是是000 000 010
那文件的默认权限是怎么得到的呢? 🆗,最终权限 = 起始权限 & (~umask)
是不是这样呢,我们来验证一下:
对于普通文件来说,我们上面看到默认权限是664。 那普通文件的起始权限是666—>110 110 110
权限掩码000 000 010
,~(按位取反)之后是111 111 101
两者进行&结果是:
110 110 100
,转换为八进制就是664 那目录呢? 目录默认权限是775—>111 111 110
目录起始权限是777—>111 111 111
权限掩码取反是111 111 101
起始权限 & (~umask)结果是:
111 111 101
,转换为八进制就是775
修改权限掩码
另外呢,起始权限掩码我们是可以修改的:
umask 权限值
那通过上面的认识,我想大家都应该明白,如果权限掩码改变了,那么文件和目录的默认权限必然也要发生变化。
那接下来大家就计算一下,我将权限掩码改成0007,此时文件和目录的默认权限是什么?
权限掩码0007—>000 000 111
取反为:111 111 000
文件的起始权限666—>110 110 110
此时普通文件的默认权限:起始权限 & (~umask)为110 110 000
—>660 目录的起始权限为777—>111 111 111
此时目录的默认权限为:111 111 000
—>770 🆗,我们来看一下是不是:
是的,没问题。