第2章 Linux命令
Linux命令基本格式#
命令提示符#
登录系统后,第一眼看到的内容是:
[root@localhost ~]#
这就是 Linux 系统的命令提示符。那么,这个提示符的含义是什么呢?
- []:这是提示符的分隔符号,没有特殊含义。
- root:显示的是当前的登录用户,笔者现在使用的是 root 用户登录。
- @:分隔符号,没有特殊含义。
- localhost:当前系统的简写主机名(完整主机名是 localhost.localdomain)。
- ~:代表用户当前所在的目录,此例中用户当前所在的目录是家目录。
- #:命令提示符,Linux 用这个符号标识登录的用户权限等级。如果是超级用户,提示符就是 #;如果是普通用户,提示符就是 $。
家目录是什么? Linux 系统是纯字符界面,用户登录后,要有一个初始登录的位置,这个初始登录位置就称为用户的家:
- 超级用户的家目录:/root/。
- 普通用户的家目录:/home/用户名/。
用户在自己的家目录中拥有完整权限,所以我们也建议操作实验可以放在家目录中进行。我们切换一下用户所在目录,看看有什么效果。
[root@localhost ~]# cd /usr/local/
[root@localhost local]#
仔细看,如果切换用户所在目录,那么命令提示符中的会变成用户当前所在目录的最后一个目录(不显示完整的所在目录 /usr/ local/,只显示最后一个目录 local)。
命令的基本格式#
接下来看看 Linux 命令的基本格式:
[root@localhost ~]# 命令[选项][参数]
命令格式中的 [] 代表可选项,也就是有些命令可以不写选项或参数,也能执行。那么,我们就用 Linux 中最常见的 ls 命令来解释一下命令的格式。如果按照命令的分类,那么 ls 命令应该属于目录操作命令。
[root@localhost ~]# ls
anaconda-ks.cfg install.log install.log.syslog
1) 选项的作用#
ls 命令之后不加选项和参数也能执行,不过只能执行最基本的功能,即显示当前目录下的文件名。那么加入一个选项,会出现什么结果?
[root@localhost ~]# Is -l
总用量44
-rw-------.1 root root 1207 1 月 14 18:18 anaconda-ks.cfg
-rw-r--r--.1 root root 24772 1 月 14 18:17 install.log
-rw-r--r--.1 root root 7690 1 月 14 18:17 install.log.syslog
如果加一个"-l"选项,则可以看到显示的内容明显增多了。"-l"是长格式(long list)的意思,也就是显示文件的详细信息。至于"-l"选项的具体含义,我们稍后再详细讲解。可以看到选项的作用是调整命令功能。如果没有选项,那么命令只能执行最基本的功能;而一旦有选项,则可以显示更加丰富的数据。
Linux 的选项又分为短格式选项(-l)和长格式选项(--all)。短格式选项是英文的简写,用一个减号调用,例如:
[root@localhost ~]# ls -l
而长格式选项是英文完整单词,一般用两个减号调用,例如:
[root@localhost ~]# ls --all
一般情况下,短格式选项是长格式选项的缩写,也就是一个短格式选项会有对应的长格式选项。当然也有例外,比如 ls 命令的短格式选项 -l 就没有对应的长格式选项。所以具体的命令选项可以通过后面我们要学习的帮助命令来进行査询。
2) 参数的作用#
参数是命令的操作对象,一般文件、目录、用户和进程等可以作为参数被命令操作。例如:
[root@localhost ~]# ls -l anaconda-ks.cfg
-rw-------.1 root root 1207 1 月 14 18:18 anaconda-ks.cfg
但是为什么一开始 ls 命令可以省略参数?那是因为有默认参数。命令一般都需要加入参数,用于指定命令操作的对象是谁。如果可以省略参数,则一般都有默认参数。例如:
[root@localhost ~]# ls
anaconda-ks.cfg install.log install.log.syslog
这个 ls 命令后面没有指定参数,默认参数是当前所在位置,所以会显示当前目录下的文件名。
总结一下:命令的选项用于调整命令功能,而命令的参数是这个命令的操作对象。
linux ls命令 #
ls 是最常见的目录操作命令,主要作用是显示目录下的内容。这个命令的基本信息如下:
- 命令名称:ls。
- 英文原意:list。
- 所在路径:/bin/ls。
- 执行权限:所有用户。
- 功能描述:显示目录下的内容。
对命令的基本信息进行说明:英文原意有助于理解和记忆命令;执行权限是命令只能被超级用户执行,还是可以被所有用户执行;功能描述指的是这个命令的基本作用。
本节主要讲解基本命令,基本信息有助于大家记忆,本章所有命令都会加入命令的基本信息。在后续章节中,大家要学会通过帮助命令、搜索命令来自己査询这些信息,所以不再浪费篇幅来写了。
命令格式#
[root@localhost ~]#ls [选项][文件名或目录名]
选项:
- -a:显示所有文件;
- --color=when:支持颜色输出,when 的值默认是 always(总显示颜色),也可以是 never(从不显示颜色)和 auto(自动);
- -d:显示目录信息,而不是目录下的文件;
- -h:人性化显示,按照我们习惯的单位显示文件大小;
- -i:显示文件的 i 节点号;
- -l:长格式显示;
学习命令,主要学习的是命令选项,但是每个命令的选项非常多,比如 ls 命令就支持五六十个选项,我们不可能讲解每个选项,也没必要讲解每个选项,本章只能讲解最为常用的选项,即可满足我们曰常操作使用。
常见用法#
【例 1】"-a"选项#
-a 选项中的 a 是 all 的意思,也就是显示隐藏文件。例如:
[root@localhost ~]# ls
anaconda-ks.cfg install.log install.log.syslog
[root@localhost ~]# Is -a
.anaconda-ks.cfg .bash_logout .bashrc install.log .mysql_history .viminfo ...bash_history .bash_profile .cshrc install.log.syslog .tcshrc
可以看到,加入"-a"选项后,显示出来的文件明显变多了。而多出来的这些文件都有一个共同的特性,就是以"."开头。在 Linux 中以"."开头的文件是隐藏文件,只有通过"-a"选项才能査看。
说到隐藏文件的査看方式,曾经有读者问我:"为什么在 Linux 中査看隐藏文件这么简单?这样的话隐藏文件还有什么意义?"其实,他理解错了隐藏文件的含义。
隐藏文件不是为了把文件藏起来不让其他用户找到,而是为了告诉用户这些文件都是重要的系统文件,如非必要,不要乱动!所以,不论是 Linux 还是 Windows 都可以非常简单地査看隐藏文件,只是在 Windows 中绝大多数的病毒和木马都会把自己变成隐藏文件,给用户带来了错觉,以为隐藏文件是为了不让用户发现。
【例 2】"-l"选项#
[root@localhost ~]# ls -l
总用量44
-rw-------.1 root root 1207 1 月 14 18:18 anaconda-ks.cfg
-rw-r-r--.1 root root 24772 1 月 14 18:17 install.log
-rw-r-r--.1 root root 7690 1 月 14 18:17 install.log.syslog
#权限 引用计数 所有者 所属组 大小 文件修改时间 文件名
我们已经知道"-l"选项用于显示文件的详细信息,那么"-l"选项显示的这 7 列分别是什么含义?
- 第一列:权限,具体权限的含义将在后续章节中讲解。
- 第二列:引用计数,文件的引用计数代表该文件的硬链接个数,而目录的引用计数代表该目录有多少个一级子目录。
- 第三列:所有者,也就是这个文件属于哪个用户。默认所有者是文件的建立用户
- 第四列:所属组,默认所属组是文件建立用户的有效组,一般情况下就是建立用户的所在组。
- 第五列:大小,默认单位是字节。
- 第六列:文件修改时间,文件状态修改时间或文件数据修改时间都会更改这个时间,注意这个时间不是文件的创建时间。
- 第七列:文件名。
【例 3】"-d"选项#
如果我们想査看某个目录的详细信息,例如:
[root@localhost ~]# ls -l /root/
总用量44
-rw-------.1 root root 1207 1 月 14 18:18 anaconda-ks.cfg
-rw-r-r--.1 root root 24772 1 月 14 18:17 install.log
-rw-r-r--.1 root root 7690 1 月 14 18:17 install.log.syslog
这个命令会显示目录下的内容,而不会显示这个目录本身的详细信息。如果想显示目录本身的信息,就必须加入"-d"选项。
[root@localhost ~]# ls -ld /root/
dr-xr-x---.2 root root 4096 1 月 20 12:30 /root/
【例 4】"-h"选项#
"ls-l"显示的文件大小是字节,但是我们更加习惯的是千字节用 KB 显示,兆字节用 MB 显示,而"-h"选项就是按照人们习惯的单位显示文件大小的,例如:
[root@localhost ~]# ls -lh
总用量44K
-rw-------.1 root root1.2K 1 月 14 18:18 anaconda-ks.cfg
-rw-r-r--.1 root root25K 1 月 14 18:17 install.log
-rw-r-r--.1 root root7.6K 1 月 14 18:17 install.log.syslog
【例 5】"-i"选项#
每个文件都有一个被称作 inode(i 节点)的隐藏属性,可以看成系统搜索这个文件的 ID,而"-i"选项就是用来査看文件的 inode 号的,例如:
[root@localhost ~]# ls -i
262418 anaconda-ks.cfg 262147 install.log 262148 install.log.syslog
从理论上来说,每个文件的 inode 号都是不一样的,当然也有例外(如硬链接),这些例外情况我们会在本章的链接小节中进行讲解。
Linux cd命令#
cd 是切换所在目录的命令,这个命令的基本信息如下。
- 命令名称:cd。
- 英文原意:change directory。
- 所在路径:Shell 内置命令。
- 执行权限:所有用户。
- 功能描述:切换所在目录。
Linux 的命令按照来源方式分为两种:Shell 内置命令和外部命令。所谓 Shell 内置命令,就是 Shell 自带的命令,这些命令是没有执行文件的;而外部命令就是由程序员单独开发的,是命令,所以会有命令的执行文件。Linux 中的绝大多数命令是外部命令,而 cd 命令是一个典型的 Shell 内置命令,所以 cd 命令没有执行文件所在路径。
命令格式#
[root@localhost ~]#cd [目录名]
cd 命令是非常简单的命令,仅有的两个选项 -P 和 -L 的作用非常有限,很少使用:
- -P(大写)是指如果切换的目录是软链接目录,则进入其原始的物理目录,而不是进入软链接目录;
- -L(大写)是指如果切换的目录是软链接目录,则直接进入软链接目录。
常见用法#
【例 1】基本用法
cd 命令切换目录只需在命令后加目录名称即可。例如:
[root@localhost ~]# cd /usr/local/src/
[root@localhost src]#
#进入/usr/local/src/ 目录
通过命令提示符,我们可以确定当前所在目录已经切换。
【例 2】简化用法
cd 命令可以识别一些特殊符号,用于决速切换所在目录,这些符号如表 1 所示。
特殊符号 | 作 用 |
---|---|
~ | 代表用户的家目录 |
- | 代表上次所在目录 |
. | 代表当前目录 |
.. | 代表上级目录 |
这些简化用法以加快命令切换,我们来试试。
[root@localhost src]# cd ~
[root@localhost ~]#
"cd~"命令可以快速回到用户的家目录,cd 命令直接按回车键也是快速切换到家目录。
[root@localhost~]#cd /etc/
[root@localhost etc]#cd
[root@localhost ~]#
# 直接使用 cd 命令,也回到了家目录。
再试试"cd-"命令。
[root@localhost ~]# cd/usr/local/src/
#进入/usr/local/src/目录
[root@localhost src]# cd -/root
[root@localhost ~]#
#"cd-"命令回到进入 src 目录之前的家目录
[root@localhost ~]# cd-
/usr/local/src
[root@localhost src]#
#再执行一遍"cd-"命令,又回到了 /usr/local/src/ 目录。
再来试试"."和".."。
[root@localhost ~]# cd /usr/local/src/
#进入测试目录
[root@localhost src]# cd..
#进入上级目录
[root@localhost local]# pwd
/usr/local
#pwd是査看当前所在目录的命令,可以看到我们进入了上级目 /usr/local/
[root@localhost local]# cd.
#进入当前目录
[root@localhost local]# pwd
/usr/local
#这个命令不会有目录的改变,只是告诉大家"."代表当前目录。
绝对路径和相对路径#
cd 命令本身不难,但有两个非常重要的概念,就是绝对路径和相对路径。初学者由于对字符界面不熟悉,所以有大量的错误都是因为对这两个路径没有搞明白,比如进错了目录、打开不了文件、打开的文件和系统文件不一致等。所以我们先来区分一下这两个路径。
首先,我们先要弄明白什么是绝对、什么又是相对。其实我们一直说现实生活中没有绝对的事情,没有绝对的大,也没有绝对的小;没有绝对的快,也没有绝对的慢。这只是由于参照物的不同或认知的局限,导致会暂时认为某些东西可能是绝对的、不能改变的。比如目前我们认为光速是最快的速度,我们不能突破光速的限制。但也有可能随着技术的进步,我们会突破这一限制。
但在 Linux 的路径中是有绝对路径的,那是因为 Linux 有最高目录,也就是根目录。如果路径是从根目录开始,一级一级指定的,那使用的就是绝对路径。例如:
[root@localhost ~]# cd /usr/local/src/
[root@localhost src]# cd /etc/rc.d/init.d/
这些切换目录的方法使用的就是绝对路径。所谓相对路径,就是只从当前所在目录开始,切换目录。例如:
[root@localhost /]# cd etc/
#当前所在路径是/目录,而/目录下有etc目录,所以可以切换
[root@localhost etc]# cd etc/
-bash:cd:etc/:没有那个文件或目录
#而同样的命令,由于当前所在目录改变了,所以就算是同一个命令也会报错,除非在/etc/目录中还有一个etc目录
所以,虽然绝对路径输入更加烦琐,但是更准确,报错的可能性也更小。对初学者而言,笔者还是建议大家使用绝对路径。本教程为了使命令更容易理解,也会尽量使用绝对路径。
再举个例子,假设我当前在 root 用户的家目录中。
[root@localhost ~]#
那么,该如何使用相对路径进入 /usr/local/src/ 目录中呢?
[root@localhost ~]# cd ../usr/local/src/
从我当前所在路径算起,加入".."代表进入上一级目录,而上—级目录是根目录,而根目录中有 usr 目录,就会一级一级地进入 src 目录了。
Linux mkdir命令#
mkdir 是创建目录的命令,其基本信息如下:
- 命令名称:mkdir。
- 英文原意:make directories。
- 所在路径:/bin/mkdir。
- 执行权限:所有用户。
- 功能描述:创建空目录。
命令格式#
[root@localhost -]# mkdir [选项]目录名
选项:
- -p: 递归建立所需目录
mkdir 也是一个非常简单的命令,其主要作用就是新建一个空目录。
常见用法#
【例 1】建立目录。
[root@localhost ~]#mkdir cangls
[root@localhost ~]#ls
anaconda-ks.cfg cangls install.log install.log.syslog
我们建立一个名为 cangls 的目录,通过 ls 命令可以査看到这个目录已经建立。注意,我们在建立目录的时候使用的是相对路径,所以这个目录被建立到当前目录下。
【例 2】递归建立目录。
如果想建立一串空目录,可以吗?
[root@localhost ~]# mkdir lm/movie/jp/cangls
mkdir:无法创建目录"lm/movie/jp/cangls":没有那个文件或目录
笔者想建立一个保存电影的目录,结果这条命令报错,没有正确执行。这是因为这 4 个目录都是不存在的,mkdir 默认只能在已经存在的目录中建立新目录。
如果需要建立一系列的新目录,则需要加入"-p"选项,递归建立才可以。例如:
[root@localhost ~]# mkdir -p lm/movie/jp/cangls
[root@localhost ~]# ls
anaconda-ks.cfg cangls install.log install.log.syslog lm
[root@localhost ~]# ls lm/
movie
#这里只査看一级子目录,其实后续的jp目录、cangls目录都已经建立
所谓的递归建立,就是一级一级地建立目录。
Linux rmdir命令#
既然有建立目录的命令,就一定会有刪除目录的命令 rmdir,其基本信息如下:
- 命令名称:rmdir。
- 英文原意:remove empty directories。
- 所在路径:/bin/rmdir。
- 执行权限:所有用户。
- 功能描述:删除空目录。
命令格式#
[root@localhost -]# rmdir [选项]目录名
选项:
- -p: 递归刪除目录
常见用法#
[root@localhost ~]#rmdir cangls
就这么简单,命令后面加目录名称即可。既然可以递归建立目录,当然也可以递归删除目录。例如:
[root@localhost ~]# rmdir -p lm/movie/jp/cangls/
但 rmdir 命令的作用十分有限,因为只能刪除空目录,所以一旦目录中有内容,就会报错。例如:
[root@localhost # mkdir test
#建立测试目录
[root@localhost ~]# touch test/boduo
[root@localhost ~]# touch test/longze
#在测试目录中建立两个文件
[root@localhost ~]# rmdir test/
rmdir:删除"test/"失败:目录非空
这个命令比较"笨",所以我们不太常用。后续我们不论删除的是文件还是目录,都会使用 rm 命令(后续章节会讲)。
Linux touch命令#
touch 的意思是触摸,如果文件不存在,则会建立空文件;如果文件已经存在,则会修改文件的时间戳(访问时间、数据修改时间、状态修改时间都会改变)。
千万不要把 touch 命令当成新建文件的命令,牢牢记住这是触摸的意思。这个命令的基本信息如下:
- 命令名称:touch。
- 英文原意:change file timestamps。
- 所在路径:/bin/touch。
- 执行权限:所有用户。
- 功能描述:修改文件的时间戳。
命令格式#
[root@localhost -]# touch [选项]文件名或目录名
选项:
- -a:只修改文件的访问时间(Access Time)
- -c:如果文件不存在,则不建立新文件
- -d:把文件的时间改为指定的时间
- -m:只修改文件的数据修改时间(Modify Time)
Linux 中的每个文件都有三个时间,分别是访问时间(Access Time)、数据修改时间(Modify Time)和状态修改时间(Change Time)。这三个时间可以通过 stat 命令来进行査看。
不过,touch 命令只能手工指定只修改访问时间,或是只修改数据修改时间,而不能指定只修改状态修改时间。因为不论是修改访问时间,还是修改文件的数据时间,对文件来讲,状态都会发生改变,即状态修改时间会随之改变。我们稍后讲 stat 命令时再具体举例。
注意,在Linux中,文件没有创建时间。
常见用法#
[root@localhost ~]#touch bols
#建立名为 bols 的空文件
如果文件不存在,则会建立文件。
[root@localhost ~]#touch bols
[root@localhost ~]#touch bols
#而如果文件已经存在,则也不会报错,只是会修改文件的访问时间
Linux stat命令#
在 Linux 中,文件有访问时间、数据修改时间、状态修改时间这三个时间,而没有创建时间。stat 是査看文件详细信息的命令,而且可以看到文件的这三个时间,其基本信息如下。
- 命令名称:stat。
- 英文原意:display file or file system status。
- 所在路径:/usr/bin/stat。
- 执行权限:所有用户。
- 功能描述:显示文件或文件系统的详细信息。
命令格式#
[root@localhost ~]# stat [选项]文件名或目录名
选项:
- -f:査看文件所在的文件系统信息,而不是査看文件的信息。
常见用法#
【例 1】査看文件的详细信息。
[root@localhost ~]# stat anaconda-ks.cfg
File: "anaconda-ks.cfg"
#文件名
Size: 1170 Blocks: 8 IO Block: 4096 普通文件
#文件大小 占用的block数 块大小 文件类型
Device: 803h/2051d Inode: 130834 Links: 1
#i节点号 链接数
Access: (0600/-rw-------) Uid: ( 0/ root) Gid: ( 0/ root)
#权限 所有者 所属组
Access: 2016-05-06 23:31:41.396893415 +0800
#访问时间
Modify: 2016-05-06 23:31:41.396893415 +0800
#数据修改时间
Change: 2016-05-06 23:31:41.411006937 +0800
#状态修改时间
【例 2】 査看文件系统信息。
如果使用"-f"选项,就不再是査看指定文件的信息,而是査看这个文件所在文件系统的信息,例如:
[root@localhost ~]#stat -f anaconda-ks.cfg
File: "anaconda-ks.cfg"
ID: c05ad05e0e3b0580 Namelen: 255 Type: ext2/ext3
Block size: 4096 Fundamental block size: 4096
Blocks: Total: 5045314 Free: 4356956 Available: 4100662 Inodes: Total: 1283632 Free: 1192731
【例 3】三种时间的含义。
査看系统当前时间,如下:
[root@localhost ~]# date
2016年05月07日星期六01:40:49 CST
再査看 bds 文件的三种时间,可以看到,和当前时间是有差别的,如下:
[root@localhost ~]# stat bols
File: "bols"
Size: 0 Blocks: 0 IO Block: 4096 普通空文件
Device: 803h/2051d Inode: 130829 Links: 1
Access: (0644/-rw-r--r--) Uid: ( 0/ root) Gid: ( 0/ root)
Access: 2016-05-07 00:10:23.794319970 +0800
Modify: 2016-05-07 00:10:23.794319970 +0800
Change: 2016-05-07 00:10:23.794319970 +0800
#这些时间都是最后一次修改文件的时间,并不是当前时间
而如果用 cat 命令读取一下这个文件,就会发现文件的访问时间 (Access Time) 变成了 cat 命令的执行时间,如下:
[root@localhost ~]# cat bols
[root@localhost ~]# stat bols
File: "bols"
Size: 0 Blocks: 0 I0 Block: 4096 普通空文
Device: 803h/2051d Inode: 130829 Links: 1
Access: (0644/-rw-r--r--) Uid: ( 0/ root) Gid:(0/ root)
Access: 2016-05-07 01:41:08.202924900 +0800
#只有访问时间变为了cat命令的执行时间,其他两个时间没有改
Modify: 2016-05-07 00:10:23.794319970 +0800
Change: 2016-05-07 00:10:23.794319970 +0800
而如果用 echo 命令向文件中写入点数据,那么文件的数据修改时间(Modify Time)就会发生改变。但是文件数据改变了,系统会认为文件的状态也会改变,所以状态修改时间(Change Time)也会随之改变,如下:
[root@localhost ~]# echo 9527> bols
[root@localhost ~]# stat bols
File: "bols"
Size: 6 Blocks: 8 I0 Block: 4096 普通文件
Device: 803h/2051d Inode: 130829 Links: 1
Access: (0644/-rw-r--r--) Uid: ( 0/ root) Gid: ( 0/ root)
Access: 2016-05-07 01:41:08.202924900 +0800
#这个时间还是上次修改时间
Modify: 2016-05-07 01:42:42.459614017 +0800
Change: 2016-05-07 01:42:42.459614017 +0800 #而这两个时间变为了 echo 命令的执行时间
而如果只修改文件的状态(比如改变文件的所有者),而不修改文件的数据,则只会更改状态修改时间(ChangeTime),如下:
[root@localhost ~]# chown nobody bols
[root@localhost ~]# stat bols
File: "bols"
Size: 6 Blocks: 8 10 Block: 4096 普通文件
Device: 803h/2051d Inode: 130829 Links: 1
Access: (0644/-rw-r-r-) Uid: ( 502/ nobody) Gid: ( 0/root)
Access: 2016-05-07 01:41:08.202924900 +0800
Modify: 2016-05-07 01:42:42.459614017 +0800
# 前两个时间还是之前修改的时间
Change: 2016-05-07 01:43:09.676860399 +0800
#而状态修改时间变为了chown命令的执行时间
而如果用 touch 命令再次触摸这个文件,则这个文件的三个时间 都会改变。touch 命令的作用就是这样的,大家记住即可。如下:
[root@localhost ~]# touch bols
[root@localhost ~]# stat bols
File: "bols"
Size: 6 Blocks: 8 10 Block: 4096 普通文件
Device: 803h/2051d Inode: 130829 Links: 1
Access: (0644/-rw-r--r--) Uid: ( 502/ nobody) Gid: ( 0/root)
Access: 2016-05-07 01:54:14.466809236 +0800
Modify: 2016-05-07 01:54:14.466809236 +0800
Change: 2016-05-07 01:54:14.466809236 +0800
#三个时间都会变为touch命令的执行时间
Linux cat命令#
cat 命令用来査看文件内容。关于这个命令,有人以为写 cat 命令的人非常喜欢猫,所以写了一个命令就命名为猫(cat)。直到有一天,笔者无意中査询 cat 命令的帮助,才发现这个命令是 concatenate(连接、连续)的简写,和猫没有一点关系。
cat 命令的基本信息如下。
- 命令名称:cat。
- 英文原意:concatenate files and print on the standard output。
- 所在路径:/bin/cat。
- 执行权限:所有用户。
- 功能描述:连接文件并打印输出到标准输出。
命令格式#
[root@localhost ~]# cat [选项]文件名
选项:
- -A:相当于 -vET 选项的整合,用于列出所有隐藏符号;
- -E:列出每行结尾的回车符 $;
- -n:显示行号;
- -T:把 Tab 键 ^I 显示出来;
- -V:列出特殊字符;
常见用法#
cat 命令用于査看文件内容,不论文件内容有多少,都会一次性显示。如果文件非常大,那么文件开头的内容就看不到了。不过 Linux 可以使用PgUp+上箭头
组合键向上翻页,但是这种翻页是有极限的,如果文件足够长,那么还是无法看全文件的内容。
所以,cat 命令适合査看不太大的文件。当然,在 Linux 中是可以使用其他的命令或方法来査看大文件的,我们以后再来学习。cat 命令本身非常简单,我们可以直接査看文件的内容。例如:
[root@localhost ~]# cat anaconda-ks.cfg
# Kickstart file automatically generated by anaconda.
#version=DEVEL
install
cdrom
lang zh一CN.UTF-8
…省略部分内容...
而如果使用"-n"选项,则会显示行号。例如:
[root@localhost ~]# cat -n anaconda-ks.cfg
1 # Kickstart file automatically generated by anaconda.
2
3
4 #version=DEVEL
5 install
6 cdrom
…省略部分内容...
如果使用"-A"选项,则相当于使用了"-vET"选项,可以査看文本中的所有隐藏符号,包括回车符 ($)、Tab 键 (^I) 等。例如:
[root@localhost ~]# cat -A anaconda-ks.cfg
# Kickstart file automatically generated by anaconda.$
$
$
#version=DEVEL$
install$
cdrom$
…省略部分内容…
Linux more命令#
如果文件过大,则 cat 命令会有心无力,这时 more 命令的作用更加明显。
more 是分屏显示文件的命令,其基本信息如下。
- 命令名称:more。
- 英文原意:file perusal filter for crt viewin。
- 所在路径:/bin/more。
- 执行权限:所有用户。
- 功能描述:分屏显示文件内容。
命令格式#
[root@localhost ~]# more 文件名
more 命令比较简单,一般不用什么选项,命令会打开一个交互界面,可以识别一些交互命令。常用的交互命令如下。
- 空格键:向下翻页。
- b:向上翻页。
- 回车键:向下滚动一行。
- / 字符串:搜索指定的字符串。
- q:退出。
常见用法#
[root@localhost ~]# more anaconda-ks.cfg
# Kickstart file automatically generated by anaconda.
#version=DEVEL
install
cdrom
…省略部分内容…
--More--(69%)
#在这里执行交互命令即可
Linux head命令#
head 是用来显示文件开头的命令,其基本信息如下。
- 命令名称:head。
- 英文原意:output the first part of files。
- 所在路径:/usr/bin/head。
- 执行权限:所有用户。
- 功能描述:显示文件开头的内容。
命令格式#
[root@localhost ~]# head [选项]文件名
选项:
- -n 行数: 从文件头开始,显示指定行数;
- -v:显示文件名;
常见用法#
[root@localhost ~]# head anaconda-ks.cfg
head 命令默认显示文件的开头 10 行内容。如果想显示指定的行数,则只需使用"-n"选项即可,例如:
[root@localhost ~]# head -n 20 anaconda-ks.cfg
这是显示文件的开头 20 行内容,也可以直接写"-行数",例如:
[root@localhost ~]# head -20 anaconda-ks.cfg
Linux tail命令#
既然有显示文件开头的命令,就会有显示文件结尾的命令——tail 命令。
tail 命令的基本信息如下:
- 命令名称:tail。
- 英文原意:output the last part of files。
- 所在路径:/usr/bin/tail。
- 执行权限:所有用户。
- 功能描述:显示文件结尾的内容。
命令格式#
[root@localhost ~]#tail [选项] 文件名
选项:
- -n 行数:从文條尾开始,显示指定行数
- -f:监听文件的新増内容
常见用法#
【例 1】基本用法。
[root@localhost ~]# tail anaconda-ks.cfg
tail 命令和 head 命令的格式基本一致,默认会显示文件的后 10 行。如果想显示指定的行数,则只需使用"-n"选项即可,例如:
[root@localhost ~]# tail -n 20 anaconda-ks.cfg
也可直接写"-行数",例如:
[root@localhost ~]# tail -20 anaconda-ks.cfg
【例 2】 监听文件的新増内容。
tail 命令有一种比较有趣的用法,可以使用"-f"选项来监听文件的新増内容,例如:
[root@localhost ~]#tail -f anaconda-ks.cfg
@server-platform
@server-policy
pax
oddjob
sgpio
certmonger
pam_krb5
krb5-workstation
perl-DBD-SQLite
%end
#光标不会退出文件,而会一直监听在文件的结尾处
这条命令会显示文件的最后 10 行内容,而且光标不会退出命令,而会一直监听文件的结尾处,等待显示新増内容。这时如果向文件中追加一些数据(需要开启一个新终端),那么结果如下:
[root@localhost ~]# echo 2222222222 >> anaconda-ks.cfg
[root@localhost ~]# echo 3333333333 >> anaconda-ks.cfg
#在新终端中通过echo命令向文件中追加数据
在原始的正在监听的终端中,会看到如下信息:
[root@localhost ~]# tail -f anaconda-ks.cfg @server-platforin
@server-policy
pax
oddjob
sgpio
certmonger
pam_krb5
krb5-workstation
perl-DBD-SQLite
%end2222222222
33333333333
#在文件的结尾处监听到了新増数据
Linux ln命令#
如果要想说清楚 ln 命令,则必须先解释下 ext 文件系统是如何工作的。我们在前面讲解了分区的格式化就是写入文件系统,而我们的 Linux 目前使用的是 ext4 文件系统。如果用一张示意图来描述 ext4 文件系统,则可以参考图 1。

图 1 ext4 文件系统示意图
ext4 文件系统会把分区主要分为两大部分(暂时不提超级块):小部分用于保存文件的 inode (i 节点)信息;剩余的大部分用于保存 block 信息。
inode 的默认大小为 128 Byte,用来记录文件的权限(r、w、x)、文件的所有者和属组、文件的大小、文件的状态改变时间(ctime)、文件的最近一次读取时间(atime)、文件的最近一次修改时间(mtime)、文件的数据真正保存的 block 编号。每个文件需要占用一个 inode。大家如果仔细查看,就会发现 inode 中是不记录文件名的,那是因为文件名记录在文件所在目录的 block 中。
block 的大小可以是 1KB、2KB、4KB,默认为 4KB。block 用于实际的数据存储,如果一个 block 放不下数据,则可以占用多个 block。例如,有一个 10KB 的文件需要存储,则会占用 3 个 block,虽然最后一个 block 不能占满,但也不能再放入其他文件的数据。这 3 个 block 有可能是连续的,也有可能是分散的。
ln命令格式#
了解了 ext 文件系统的概念,我们来看看 ln 命令的基本信息。
- 命令名称:ln。
- 英文原意:make links between file0
- 所在路径:/bin/ln。
- 执行权限:所有用户。
- 功能描述:在文件之间建立链接。
ln 命令的基本格式如下:
[root@localhost ~]# ln [选项] 源文件 目标文件
选项:
- -s:建立软链接文件。如果不加"-s"选项,则建立硬链接文件;
- -f:强制。如果目标文件已经存在,则删除目标文件后再建立链接文件;
如果创建硬链接:
[root@localhost ~]# touch cangls
[root@localhost ~]# ln /root/cangls /tmp/
#建立硬链接文件,目标文件没有写文件名,会和原名一致
#也就是 /root/cangls 和 /tmp/cangls 是硬链接文件
如果创建软链接:
[root@localhost ~]# touch bols
[root@localhost ~]# In /root/bols /tmp/
#建立软链接文件
这里需要注意,软链接文件的源文件必须写成绝对路径,而不能写成相对路径(硬链接没有这样的要求);否则软链接文件会报错。这是初学者非常容易犯的错误。
建立硬链接和软链接非常简单,那这两种链接有什么区别?它们都有什么作用?这才是链接文件最不容易理解的地方,我们分别来讲讲。
硬链接#
我们再来建立一个硬链接文件,然后看看这两个文件的特点。
[root@localhost ~]# touch test
#建立源文件
[root@localhost ~]# ln /root/test /tmp/test-hard
#给源文件建立硬链接文件 /tmp/test-hard
[root@localhost ~]# ll -i /root/test /tmp/test-hard
262147 -rw-r--r-- 2 root root 0 6月 19 10:06 /root/test
hard
262147 -rw-r--r-- 2 root root 0 6月 19 10:06 /tmp/test-hard
#查看两个文件的详细信息,可以发现这两个文件的 inode 号是一样的,"ll"等同于"ls -l"。
这里有一件很奇怪的事情,我们之前在讲 inode 号的时候说过,每个文件的 inode 号都应该是不一样的。inode 号就相当于文件 ID,我们在查找文件的时候,要先查找 inode 号,才能读取到文件的内容。
但是这里源文件和硬链接文件的 inode 号居然是一样的,那我们在查找文件的时候,到底找到的是哪一个文件呢?我们来画一张示意图,如图 2 所示。

图 2 硬链接示意图
在 inode 信息中,是不会记录文件名称的,而是把文件名记录在上级目录的 block 中。也就是说,目录的 block 中记录的是这个目录下所有一级子文件和子目录的文件名及 inode 的对应;而文件的 block 中记录的才是文件实际的数据。
当我们查找一个文件,比如 /root/test 时,要经过以下步骤:
- 首先找到根目录的 inode(根目录的 inode 是系统已知的,inode 号是 2),然后判断用户是否有权限访问根目录的 block。
- 如果有权限,则可以在根目录的 block 中访问到 /root 的文件名及对应的 inode 号。
- 通过 /root/ 目录的 inode 号,可以查找到 /root/ 目录的 inode 信息,接着判断用户是否有权限访问 /root/ 目录的 block。
- 如果有权限,则可以从 /root/ 目录的 block 中读取到 test 文件的文件名及对应的 inode 号。
- 通过 test 文件的 inode 号,就可以找到 test 文件的 inode 信息,接着判断用户是否有权限访问 test 文件的 block。
- 如果有权限,则可以读取 block 中的数据,这样就完成了 /root/test 文件的读取与访问。
按照这个步骤,在给源文件 /root/test 建立了硬链接文件 /tmp/test-hard 之后,在 /root/ 目录和 /tmp/ 目录的 block 中就会建立 test 和 test-hard 的信息,这个信息主要就是文件名和对应的 inode 号。但是我们会发现 test 和 test-hard 的 inode 信息居然是一样的,那么,我们无论访问哪个文件,最终都会访问 inode 号是 262147 的文件信息。
这就是硬链接的原理。硬链接的特点如下:
- 不论是修改源文件(test 文件),还是修改硬链接文件(test-hard 文件),另一个文件中的数据都会发生改变。
- 不论是删除源文件,还是删除硬链接文件,只要还有一个文件存在,这个文件(inode 号是 262147 的文件)都可以被访问。
- 硬链接不会建立新的 inode 信息,也不会更改 inode 的总数。
- 硬链接不能跨文件系统(分区)建立,因为在不同的文件系统中,inode 号是重新计算的。
- 硬链接不能链接目录,因为如果给目录建立硬链接,那么不仅目录本身需要重新建立,目录下所有的子文件,包括子目录中的所有子文件都需要建立硬链接,这对当前的 Linux 来讲过于复杂。
硬链接的限制比较多,既不能跨文件系统,也不能链接目录,而且源文件和硬链接文件之间除 inode 号是一样的之外,没有其他明显的特征。这些特征都使得硬链接并不常用,大家有所了解就好。
我们通过实验来测试一下。
[root@localhost ~]# echo 1111 >>/root/test
#向源文件中写入数据
[root@localhost ~]# cat /root/test
1111
[root@localhost ~]# cat /tmp/test-hard
1111
#源文件和硬链接文件都会发生改变
[root@localhost ~]# echo 2222 >> /tmp/test-hard
#向硬链接文件中写入数据
[root@localhost ~]# cat /root/test
1111
2222
[root@localhost ~】# cat /tmp/test-hard
1111
2222
#源文件和硬链接文件也都会发生改变
[root@localhost ~]# rm -rf/root/test
#删除源文件
[root@localhost ~]# cat /tmp/test-hard
1111 2222
#硬链接文件依然可常读取
软链接#
软链接也称作符号链接,相比硬链接来讲,软链接就要常用多了。我们先建立一个软链接,再来看看软链接的特点。
[root@localhost ~]# touch check
#建立源文件
[root@localhost ~]# ln -s /root/check /tmp/check-soft
#建立软链接文件
[root@localhost ~]# ll -id /root/check /tmp/check-soft
262154 -rw-r--r-- 1 root root 0 6月 19 11:30 /root/check
917507 lrwxrwxrwx 1 root root 11 6月 19 11:31 /tmp/ check-soft -> /root/check
#软链接和源文件的 inode 号不一致,软链接通过 -> 明显地标识出源文件的位置
#在软链接的权限位 lrwxrwxrwx 中,l 就代表软链接文件
再强调一下,软链接的源文件必须写绝对路径,否则建立的软链接文件就会报错,无法正常使用。
软链接的标志非常明显,首先,权限位中"l"表示这是一个软链接文件;其次,在文件的后面通过 "->" 显示出源文件的完整名字。所以软链接比硬链接的标志要明显得多,而且软链接也不像硬链接的限制那样多,比如软链接可以链接目录,也可以跨分区来建立软链接。
软链接完全可以当作 Windows 的快捷方式来对待,它的特点和快捷方式一样,我们更推荐大家使用软链接,而不是硬链接。
大家在学习软链接的时候会有一些疑问:Windows 的快捷方式是由于源文件放置的位置过深,不容易找到,建立一个快捷方式放在桌面,方便查找,那 Linux 的软链接的作用是什么呢?
笔者个人觉得,软链接主要是为了照顾管理员的使用习惯。比如,有些系统的自启动文件 /etc/rc.local 放置在 /etc/ 目录中,而有些系统却将其放置在 /etc/rc.d/rc.local 中,那么干脆对这两个文件建立软链接,不论你习惯操作哪一个文件,结果都是一样的。
如果你比较细心,则应该已经发现软链接和源文件的 inode 号是不一致的,我们也画一张示意图来看看软链接的原理,如图 3 所示。

图 3 软链接示意图
软链接和硬链接在原理上最主要的不同在于:硬链接不会建立自己的 inode 索引和 block(数据块),而是直接指向源文件的 inode 信息和 block,所以硬链接和源文件的 inode 号是一致的;而软链接会真正建立自己的 inode 索引和 block,所以软链接和源文件的 inode 号是不一致的,而且在软链接的 block 中,写的不是真正的数据,而仅仅是源文件的文件名及 inode 号。
我们来看看访问软链接的步骤和访问硬链接的步骤有什么不同。
- 首先找到根目录的 inode 索引信息,然后判断用户是否有权限访问根目录的 block。
- 如果有权限访问根目录的 block,就会在 block 中查找到 /tmp/ 目录的 inode 号。
- 接着访问 /tmp/ 目录的 inode 信息,判断用户是否有权限访问 /tmp/ 目录的 block。
- 如果有权限,就会在 block 中读取到软链接文件 check-soft 的 inode 号。因为软链接文件会真正建立自己的 inode 索引和 block,所以软链接文件和源文件的 inode 号是不一样的。
- 通过软链接文件的 inode 号,找到了 check-soft 文件 inode 信息,判断用户是否有权限访问 block。
- 如果有权限,就会发现 check-soft 文件的 block 中没有实际数据,仅有源文件 check 的 inode 号。
- 接着通过源文件的 inode 号,访问到源文件 check 的 inode 信息,判断用户是否有权限访问 block。
- 如果有权限,就会在 check 文件的 block 中读取到真正的数据,从而完成数据访问。
通过这个过程,我们就可以总结出软链接的特点(软链接的特点和 Windows 中的快捷方式完全一致)。
- 不论是修改源文件(check),还是修改硬链接文件(check-soft),另一个文件中的数据都会发生改变。
- 删除软链接文件,源文件不受影响。而删除原文件,软链接文件将找不到实际的数据,从而显示文件不存在。
- 软链接会新建自己的 inode 信息和 block,只是在 block 中不存储实际文件数据,而存储的是源文件的文件名及 inode 号。
- 软链接可以链接目录。
- 软链接可以跨分区。
我们测试一下软链接的特性。
[root@localhost ~]# echo 111>>/root/check
#修改源文件
[root@localhost ~]# cat /root/check
111
[root@localhost ~]# cat /tmp/check-soft
111
#不论是源文件还是软链接文件,数据都发生改变
[root@localhost ~]# echo 2222 >>/tmp/check-soft
#修改软链接文件
[root@localhost ~]# cat /tmp/check-soft
111
2222
[root@localhost ~]# cat /root/check
111
2222
#不论是源文件还是软链接文件,数据也都会发生改变
[root@localhost ~]# rm -rf/root/check
#删除源文件
[root@localhost ~]# cat /tmp/check-soft
cat: /tmp/check-soft:没有那个文件或目录
#软链接无法正常使用
软链接是可以链接目录的,例如:
[root@localhost ~]# mkdir test
#建立源目录
[root@localhost ~]# ln -s /root/test/ /tmp/
[root@localhost ~]# ll -d /tmp/test
lrwxrwxrwx 1 root root 11 6月 19 12:43 /tmp/test->/root/test/
#软链接可以链接目录
Linux rm命令#
rm 是强大的删除命令,不仅可以删除文件,也可以删除目录。这个命令的基本信息如下。
- 命令名称:rm
- 英文原意:remove files or directories。
- 所在路径:/bin/rm。
- 执行权限:所有用户。
- 功能描述:删除文件或目录。
命令格式#
[root@localhost ~]# rm[选项] 文件或目录
选项:
- -f:强制删除(force)
- -i:交互删除,在删除之前会询问用户
- -r:递归删除,可以删除目录(recursive)
常见用法#
【例 1】基本用法。
rm 命令如果任何选项都不加,则默认执行的是"rm -i 文件名",也就是在删除一个文件之前会先询问是否删除。例如:
[root@localhost ~]# touch cangls
[root@localhost ~]# rm cangls
rm:是否删除普通空文件"cangls"?y
#删除前会询问是否删除
【例 2】 删除目录。
如果需要删除目录,则需要使用"-r"选项。例如:
[root@localhost ~]# mkdir -p /test/lm/movie/jp/
#递归建立测试目录
[root@localhost ~]# rm /test/
rm:无法删除"/test/": 是一个目录
#如果不加"-r"选项,则会报错
[root@localhost ~]# rm -r /test/
rm:是否进入目录"/test"?y
rm:是否进入目录"/test/lm/movie"?y
rm:是否删除目录"/test/lm/movie/jp"?y
rm:是否删除目录"/test/lm/movie"?y
rm:是否删除目录"/test/lm"?y
rm:是否删除目录"/test"?y
#会分别询问是否进入子目录、是否删除子目录
大家会发现,如果每级目录和每个文件都需要确认,那么在实际使用中简直是灾难!
【例 3】强制删除。
如果要删除的目录中有 1 万个子目录或子文件,那么普通的 rm 删除最少需要确认 1 万次。所以,在真正删除文件的时候,我们会选择强制删除。例如:
[root@localhost ~]# mkdir -p /test/lm/movie/jp/
#重新建立测试目录
[root@localhost ~]# rm -rf/test/
#强制删除,一了百了
加入了强制功能之后,删除就会变得很简单,但是需要注意,数据强制删除之后无法恢复,除非依赖第三方的数据恢复工具,如 extundelete 等。但要注意,数据恢复很难恢复完整的数据,一般能恢复 70%~80% 就很难得了。所以,与其把宝压在数据恢复上,不如养成良好的操作习惯。
虽然"-rf"选项是用来删除目录的,但是删除文件也不会报错。所以,为了使用方便,一般不论是删除文件还是删除目录,都会直接使用"-rf"选项。
Linux cp命令#
cp 是用于复制的命令,其基本信息如下:
- 命令名称:cp;
- 英文原意:copy files and directories;
- 所在路径:/bin/cp;
- 执行权限:所有用户;
- 功能描述:复制文件和目录;
命令格式#
[root@localhost ~]# cp [选项] 源文件 目标文件
选项:
- -a:相当于 -d、-p、-r 选项的集合,这几个选项我们一一介绍;
- -d:如果源文件为软链接(对硬链接无效),则复制出的目标文件也为软链接;
- -i:询问,如果目标文件已经存在,则会询问是否覆盖;
- -l:把目标文件建立为源文件的硬链接文件,而不是复制源文件;
- -s:把目标文件建立为源文件的软链接文件,而不是复制源文件;
- -p:复制后目标文件保留源文件的属性(包括所有者、所属组、权限和时间);
- -r:递归复制,用于复制目录;
常见用法#
【例 1】基本用法。
cp 命令既可以复制文件,也可以复制目录。我们先来看看如何复制文件,例如:
[root@localhost ~]# touch cangls
#建立源文件
[root@localhost ~]# cp cangls /tmp/
#把源文件不改名复制到 /tmp/ 目录下
如果需要改名复制,则命令如下:
[root@localhost ~]# cp cangls /tmp/bols
#改名复制
如果复制的目标位置已经存在同名的文件,则会提示是否覆盖,因为 cp 命令默认执行的是“cp -i”的别名,例如:
[root@localhost ~]# cp cangls /tmp/
cp:是否覆盖"/tmp/cangls"?y
#目标位置有同名文件,所以会提示是否覆盖
接下来我们看看如何复制目录,其实复制目录只需使用“-r”选项即可,例如:
[root@localhost ~]# mkdir movie
#建立测试目录
[root@localhost ~]# cp -r /root/movie/ /tmp/
#目录原名复制
【例 2】复制软链接属性
如果源文件不是一个普通文件,而是一个软链接文件,那么是否可以复制软链接的属性呢?我们试试:
[root@localhost ~]# ln -s /root/cangls /tmp/cangls_slink
#建立一个测试软链接文件/tmp/cangls_slink
[root@localhost ~]# ll /tmp/cangls_slink
lrwxrwxrwx 1 root root 12 6 月 14 05:53 /tmp/cangls_slink -> /root/cangls
#源文件本身就是一个软链接文件
[root@localhost ~]# cp /tmp/cangls_slink /tmp/cangls_t1
#复制软链接文件,但是不加"-d"选项
[root@localhost ~]# cp -d /tmp/cangls_slink /tmp/cangls_t2
#复制软链接文件,加入"-d"选项
[root@localhost ~]# ll /tmp/cangls_t1 /tmp/cangls_t2
-rw-r--r-- 1 root root 0 6月 14 05:56 /tmp/cangls_t1
#会发现不加"-d"选项,实际复制的是软链接的源文件,而不是软链接文件
lrwxrwxrwx 1 root root 12 6 月 14 05:56/tmp/ cangls_t2-> /root/cangls
#而如果加入了"-d"选项,则会复制软链接文件
这个例子说明:如果在复制软链接文件时不使用"-d"选项,则 cp 命令复制的是源文件,而不是软链接文件;只有加入了"-d"选项,才会复制软链接文件。请大家注意,"-d"选项对硬链接是无效的。
【例 3】保留源文件属性复制
我们发现,在执行复制命令后,目标文件的时间会变成复制命令的执行时间,而不是源文件的时间。例如:
[root@localhost ~]# cp /var/lib/mlocate/mlocate.db /tmp/
[root@localhost ~]# ll /var/lib/mlocate/mlocate.db
-rw-r-----1 root slocate2328027 6月 14 02:08/var/lib/mlocate/mlocate.db
#注意源文件的时间和所属组
[root@localhost ~]#ll /tmp/mlocate.db
-rw-r----- 1 root root2328027 6 月 14 06:05/tmp/mlocate.db
#由于复制命令由root用户执行,所以目标文件的所属组为了root,而且时间也变成了复制命令的执行时间
而当我们执行备份、曰志备份的时候,这些文件的时间可能是一个重要的参数,这就需执行"-p"选项了。这个选项会保留源文件的属性,包括所有者、所属组和时间。例如:
[root@localhost ~]# cp -p /var/lib/mlocate/mlocate.db /tmp/mlocate.db_2
#使用"-p"选项
[root@localhost ~]# ll /var/lib/mlocate/mlocate.db /tmp/mlocate.db_2
-rw-r----- root slocate 2328027 6月 14 02:08 /tmp/mlocate.db_2
-rw-r----- root slocate 2328027 6月 14 02:08 /var/lib/mlocate/mlocate.db
#源文件和目标文件的所有属性都一致,包括时间
我们之前讲过,"-a"选项相当于"-d、-p、-r"选项,这几个选项我们已经分别讲过了。所以,当我们使用"-a"选项时,目标文件和源文件的所有属性都一致,包街原文件的所有者,所属组、时间和软链接性。使用"-a" 选项来取代"-d、-p、-r"选项更加方便。
【例 4】 "-l"和"-s"选项
我们如果使用"-l"选项,则目标文件会被建立为源文件的硬链接;而如果使用了 "-s"选项,则目标文件会被建立为源文件的软链接。
这两个选项和"-d"选项是不同的,"d"选项要求源文件必须是软链接,目标文件才会复制为软链接;而"-l"和"-s"选项的源文件只需是普通文件,目标文件就可以直接复制为硬链接和软链接。例如:
[root@localhost ~]# touch bols
#建立测试文件
[root@localhost ~]# ll -i bols
262154-rw-r--r-- 1 root root 0 6月 14 06:26 bols
#源文件只是一个普通文件,而不是软链接文件
[root@localhost ~]# cp -l /root/bols /tmp/bols_h
[root@localhost ~]# cp -s /root/bols /tmp/bols_s
#使用"-l" 和"-s"选项复制
[root@localhost ~]# ll -i /tmp/bols_h /tmp/bols_s
262154-rw-r--r-- 2root root 0 6 月 14 06:26/tmp/bols_h
#目标文件 /tmp/bols_h 为源文件的硬链接文件
932113 lrwxrwxrwx 1 root root 10 6 月 14 06:27/tmp/bols_s -> /root/bols
#目标文件 /tmp/bols_s 为源文件的软链接文件
Linux mv命令#
mv 是用来剪切的命令,其基本信息如下。
- 命令名称:mv。
- 英文原意:move(rename)files。
- 所在路径:/bin/mv。
- 执行权限:所有用户。
- 功能描述:移动文件或改名。
命令格式#
[root@localhost ~]# mv 【选项】 源文件 目标文件
选项:
- -f:强制覆盖,如果目标文件已经存在,则不询问,直接强制覆盖;
- -i:交互移动,如果目标文件已经存在,则询问用户是否覆盖(默认选项);
- -n:如果目标文件已经存在,则不会覆盖移动,而且不询问用户;
- -v:显示详细信息;
常见用法#
【例 1】移动文件或目录。
[root@localhost ~]# mv cangls /tmp/
#移动之后,源文件会被删除,类似剪切
[root@localhost ~]# mkdir movie
[root@localhost ~]# mv movie/ /tmp/
#也可以移动目录。和 rm、cp 不同的是,mv 移动目录不需要加入"-r"选项
如果移动的目标位置已经存在同名的文件,则同样会提示是否覆盖,因为 mv 命令默认执行的也是"mv -i"的别名,例如:
[root@localhost ~]# touch cangls
#重新建立文件
[root@localhost ~]# mv cangls /tmp/
mv:县否覆盖"tmp/cangls"?y
#由于 /tmp/ 目录下已经存在 cangls 文件,所以会提示是否覆盖,需要手工输入 y 覆盖移动
【例 2】强制移动。
之前说过,如果目标目录下已经存在同名文件,则会提示是否覆盖,需要手工确认。这时如果移动的同名文件较多,则需要一个一个文件进行确认,很不方便。
如果我们确认需要覆盖已经存在的同名文件,则可以使用"-f"选项进行强制移动,这就不再需要用户手工确认了。例如:
[root@localhost ~]# touch cangls
#重新建立文件
[root@localhost ~]# mv -f cangls /tmp/
#就算 /tmp/ 目录下已经存在同名的文件,由于"-f"选项的作用,所以会强制覆盖
【例 3】不覆盖移动。
既然可以强制覆盖移动,那也有可能需要不覆盖的移动。如果需要移动几百个同名文件,但是不想覆盖,这时就需要"-n"选项的帮助了。例如:
[root@localhost ~]# ls /tmp*ls
/tmp/bols /tmp/cangls
#在/tmp/目录下已经存在bols、cangls文件了
[root@localhost ~]# mv -vn bols cangls lmls /tmp/
"lmls"->"/tmp/lmls"
#再向 /tmp/ 目录中移动同名文件,如果使用了 "-n"选项,则可以看到只移动了 lmls,而同名的 bols 和 cangls 并没有移动("-v"选项用于显示移动过程)
【例 4】改名。
如果源文件和目标文件在同一目录中,那就是改名。例如:
[root@localhost ~]# mv bols lmls
#把 bols 改名为 lmls
目录也可以按照同样的方法改名。
【例 5】显示移动过程。
如果我们想要知道在移动过程中到底有哪些文件进行了移动,则可以使用"-v"选项来査看详细的移动信息。例如:
[root@localhost ~]# touch testl.txt test2.txt test3.txt
#建立三个测试文件
[root@localhost ~]# mv -v *.txt/tmp/
"test1.txt" -> "/tmp/test1.txt"
"test2.txt" -> "/tmp/test2.txt"
"test3.txt" -> "/tmp/test3.txt"
#加入"-v"选项,可以看到有哪些文件进行了移动
Linux文件权限#
我们发现,初学者并不是不能理解权限命令,而是不能理解为什么需要设定不同的权限。所有的人都直接使用管理员身份,不可以吗?
这是由于绝大多数用户使用的是个人计算机,而使用个人计算机的用户一般都是被信任的用户(如家人、朋友等)。在这种情况下,大家都可以使用管理员身份直接登录。又因为管理员拥有最大权限,所以给我们带来了错觉,以为在计算机中不需要分配权限等级,不需要使用不同的账户。
但是在服务器上就不是这种情况了,在服务器上运行的数据越重要(如游戏数据),价值越高(如电子商城数据、银行数据),那么对权限的设定就要越详细,用户的分级也要越明确。所以,在服务器上,绝对不是所有的用户都使用 root 身份登录,而要根据不同的工作需要和职位需要,合理分配用户等级和权限等级。
文件的所有者、所属组和其他人#
前面讲 ls 命令的 -l 选项时,简单解释过所有者和所属组,例如:
[root@localhost ~]# ls -linstall.log
-rw-r--r--.1 root root 24772 1月 14 18:17 install.log
命令的第三列 root 用户就是文件的所有者,第四列 root 组就是文件的所属组。而且我们也介绍过,文件的所有者就是这个文件的建立者,而系统中绝大多数系统文件都是由 root 建立的,所以大多数系统文件的所有者都是 root。
接下来我们解释一下所属组,首先讲解一下用户组的概念。用户组就是一组用户的集合,类似于大学里的各种社团。那为什么要把用户放入一个用户组中呢?
当然是为了方便管理。大家想想,如果我有 100 位用户,而这 100 位用户对同一个文件的权限是一致的,那我是一位用户一位用户地分配权限方便,还是把 100 位用户加入一个用户组中,然后给这个用户组分配权限方便呢?不言而喻,一定是给一个用户组分配权限更加方便。
综上所述,给一个文件区分所有者、所属组和其他人,就是为了分配权限方便。就像笔者买了一台电脑,那我当然是这台电脑的所有者,可以把我的读者加入一个用户组,其他不认识的路人当然就是其他人了。分配完了用户身份,就可以分配权限了,所有者当然对这台电脑拥有所有的权限,而位于所属组中的这些学生可以借用我的电脑,而其他人则完全不能碰我的电脑。
Linux权限位#
前面讲解 ls 命令时,我们已经知道长格式显示的第一列就是文件的权限,例如:
[root@localhost ~]# ls -linstall.log
-rw-r--r--.1 root root 24772 1月 14 18:17 install.log
第一列的权限位如果不计算最后的"."(这个点的含义我们在后面解释),则共有 10 位,这 10位权限位的含义如图4-4所示。

图 1 权限位的含义
第 1 位代表文件类型。Linux 不像 Windows 使用扩展名表示文件类型,而是使用权限位的第 1 位表示文件类型。虽然 Linux 文件的种类不像 Windows 中那么多,但是分类也不少,详细情况可以使用"info ls"命令查看。笔者在这里只讲一些常见的文件类型。
- -"-":普通文件。
- -"b":块设备文件。这是一种特殊设备文件,存储设备都是这种文件,如分区文件 /dev/sda1 就是这种文件。
- -"c":字符设备文件。这也是特殊设备文件,输入设备一般都是这种文件,如鼠标、键盘等。
- -"d":目录文件。Linux 中一切皆文件,所以目录也是文件的一种。
- -"l":软链接文件。
- -"p":管道符文件。这是一种非常少见的特殊设备文件。
- -"s":套接字文件。这也是一种特殊设备文件,一些服务支持 Socket 访问,就会产生这样的文件。
第 2~4 位代表文件所有者的权限。
- -r:代表 read,是读取权限。
- -w:代表 write,是写权限。
- -x:代表 execute,是执行权限。
如果有字母,则代表拥有对应的权限;如果是"-",则代表没有对应的权限。
第 5~7 位代表文件所属组的权限,同样拥有"rwx"权限。
第 8~10 位代表其他人的权限,同样拥有"rwx"权限。
这就是文件基本权限的含义,那我们看看下面这个文件的权限是什么。
[root@localhost ~]#ls -linstall.log
-rw-r--r--.1 root root 24772 1月 14 18:17 install.log
这个文件的所有者,也就是 root 拥户,拥有读和写权限;所属组中的用户,也就是 root 组中除 root 用户以外的其他用户,拥有只读权限;而其他人拥有只读权限。
最后,我们再看看权限位的这个"."的作用。这个点是在 CentOS 6 以上的系统中才出现的,在以前的系统中是没有的。刚开始,笔者也饱受这个点的困扰,在各种资料中都查不到这个点的说明。直到无意中查询了 "info ls" 命令,才明白这个点的含义:如果在文件的权限位中含有".",则表示这个文件受 SELinux 的安全规则管理。
这个示例说明,任何资料都不如 Linux 自带的帮助文档准确和详细。所以,如果以后出现了不能解释的内容,则记得先查看 Linux 自带的帮助文档。
Linux chmod命令#
chmod 是修改权限的命令,其基本信息如下:
命令名称:chmod。
英文原意:change file mode bits。
所在路径:/bin/chmod。
执行权限:所有用户。
功能描述:修改文件的权限模式。
命令格式#
[root@localhost ~]# chmod [选项] 权限模式 文件名
选项#
- -R:递归设置权限,也就是给子目录中的所有文件设定权限
权限模式#
chmod 命令的权限模式的格式是"[ugoa] [[+-=] [perms]]",也就是"[用户身份][[赋予方式][权限]]"的格式,我们来解释一下。
用户身份:
- -u:代表所有者(user)。
- -g:代表所属组(group)。
- -o:代也人(other)。
- -a:代表全部身份(all)。
赋予方式:
- -+:加入权限。
- --:减去权限。
- -=:设置权限。
权限:
- -r:读取权限(read)。
- -w:写权限(write)。
- -x:执行权限(execute)。
这里我们只讲解基本权限,至于特殊权限(如 suid 、sgid 和 sbit 等),我们会在后续章节详细讲解。
下面举几个例子。
【例 1】用"+"加入权限。
[root@localhost ~]# touch lmls
#建立测试文件
[root@localhost ~]# ll lmls
-rw-r--r--1 root root 0 6月 15 02:48 lmls
#这个文件的默认权限是"所有者:读、写权限;所属组:只读权限;其他人:只读权限"
[root@localhost ~]# chmod u+x lmls
#给所有者加入执行权限
[root@localhost ~]# ll lmls-rwxr--r-- 1 root root 0 6月 15 02:48 lmls
#权限生效
【例 2】给多个身份同时加入权限。
[root@localhost ~]# chmod g+w,o+w lmls #给所属组和其他人同时加入写权限
[root@localhost ~]# ll lmls
-rwxrw-rw-1 root root 0 6月 15 02:48 lmls
#权限生效
【例 3】用"-"减去权限。
[root@localhost ~]# chmod u-x, g-w, o-w lmls
#给所有者减去执行权限,给所属组和其他人都减去写权限,也就是恢复默认权限
[root@localhost ~]#ll lmls
-rw-r--r-- 1 root root 0 6月 15 02:48 lmls
【例 4】用"="设置权限。
大家有没有发现,用"+-"赋予权限是比较麻烦的,需要先确定原始权限是什么,然后在原始权限的基础上加减权限。有没有简单一点的方法呢?可以使用"="来设定权限,例如:
[root@localhost ~]# chmod u=rwx, g=rw, o=rw lmls
#所有者赋予权限"rwx",给所属组和其他人赋予权限"rw"
[root@localhost ~]# ll lmls
-rwxrw-rw-1 root root 0 6月 15 02:48 lmls
使用"="赋予权限,确实不用在原始权限的基础行加减了,但是依然要写很长一条命令,笔者依然觉的不够简单,还可以使用数组权限的方式来赋予权限。
数字权限#
数字权限的赋予方式是最简单的,但是不如之前的字母权限好记、直观。
我们来看看这些数字权限的含义,
- 4:代表"r"权限。
- 2:代表"w"权限。
- 1:代表"x"权限。
举个例子:
[root@localhost ~]# chmod 755 lmls
#给文件赋予"755权限"
[root@localhost ~]#ll lmls
-rwxr-xr-x 1 root root 0 6月15 02:48 lmls
解释一下"755权限":
- 第一个数字"7":代表所有者的权限是"4+2+1",也就是读、写和执行权限。
- 第二个数字"5":代表所属组的权限是"4+1",也就是读和执行权限。
- 第三个数字"5":代表其他人的权限是"4+1",也就是读和执行权限。
数字权限的赋予方式更加简单,但是需要用户对这几个数字更加熟悉。其实常用权限也并不多,只有如下几个:
- 644:这是文件的基本权限,代表所有者拥有读、写权限,而所属组和其他人拥有只读权限。
- 755:这是文件的执行权限和目录的基本权限,代表所有者拥有读、写和执行权限,而所属组和其他人拥有读和执行权限。
- 777:这是最大权限。在实际的生产服务器中,要尽力避免给文件或目录赋予这样的权限,这会造成一定的安全隐患。
我们很少会使用"457"这样的权限,因为这样的权限是不合理的,怎么可能文件的所有者的权限还没有其他人的权限大呢?所以,除非是实验需要,否则一般情况下所有者的权限要大于所属组和其他人的权限。
Linux读写执行权限#
我们已经知道了权限的赋予方式,但是这些读、写、执行权限到底是什么含义呢?有些人可能会说:"你也太小瞧我们了,读、写、执行的含义这么明显,我们还能不知道吗?"其实,这些权限的含义不像表面上这么明显,下面我们就来讲讲这些权限到底是什么含义。
首先,读、写、执行权限对文件和目录的作用是不同的。
权限对文件的作用#
- -读(r):对文件有读(r)权限,代表可以读取文件中的数据。如果把权限对应到命令上,那么一旦对文件有读(r)权限,就可以对文件执行 cat、more、less、head、tail 等文件查看命令。
- -写(w):对文件有写(w)权限,代表可以修改文件中的数据。如果把权限对应到命令上,那么一旦对文件有写(w)权限,就可以对文件执行 vim、echo 等修改文件数据的命令。注意,对文件有写权限,是不能删除文件本身的,只能修改文件中的数据。如果要想删除文件,则需要对文件的上级目录拥有写权限。
- -执行(x):对文件有执行(x)权限,代表文件拥有了执行权限,可以运行。在 Linux 中,只要文件有执行(x)权限,这个文件就是执行文件了。只是这个文件到底能不能正确执行,不仅需要执行(x)权限,还要看文件中的代码是不是正确的语言代码。对文件来说,执行(x)权限是最高权限。
权限对目录的作用#
- -读(r):对目录有读 (r)权限,代表可以查看目录下的内容,也就是可以查看目录下有哪些子文件和子目录。如果把权限对应到命令上,那么一旦对目录拥有了读(r)权限,就可以在目录下执行 ls 命令,查看目录下的内容了。
- -写(w):对目录有写(r)权限,代表可以修改目录下的数据,也就是可以在目录中新建、删除、复制、剪切子文件或子目录。如果把权限对应到命令上,那么一旦对目录拥有了写(w)权限,就可以在目录下执行 touch、rm、cp、mv 命令。对目录来说,写(w)权限是最高权限。
- -执行(x):目录是不能运行的,那么对目录拥有执行(x)权限,代表可以进入目录。如果把权限对应到命令上,那么一旦对目录拥有了执行(x)权限,就可以对目录执行 cd 命令,进入目录。
注意事项#
初学权限的时候,可能对两种情况最不能理解,我们一个一个来看。
1) 为什么对文件有写权限,却不能删除文件?
这需要通过分区的格式化来讲解。我们之前讲过,分区的格式化可以理解为给分区打入隔断,这样才可以存储数据。
在 Linux 的 ext 文件系统中,格式化可以理解为把分区分成两大部分:
- 一部分占用空间较小,用于保存 inode(i 节点)信息;
- 绝大部分格式化为 block(数据块),用于保存文件中的实际数据。
在 Linux 中,默认 inode 的大小为 128 Byte,用于记录文件的权限(r、w、x)、文件的所有者和属组、文件的大小、文件的状态改变时间(ctime)、文件的最近一次读取时间(atime)、文件的最近一次修改时间(mtime)、文件中的数据真正保存的 block 编号。每个文件需要占用一个 inode。
仔细观察,在 inode 中并没有记录文件的文件名。那是因为文件名是记录在文件上级目录的 block 中的。我们画一张示意图看看,假设有这样一个文件 /test/cangls,如图 1 所示。

图 1 inode示意图
我们可以看到,在 /test/ 目录的 block 中会记录这个目录下所有的一级子文件或一级子目录的文件名及其对应的 inode 好。也就是说,系统读取 cangls 文件的过程是这样的:
- 通过 /test/ 目录的 inode 信息,找到 /test/ 目录的 block。
- 在 /test/ 目录的 block 中,查看到 cangls 文件的 inode 号。
- 通过 cangls 文件的 inode 号,找到了 cangls 文件的 inode 信息。
- 确定是否有权限访问 cangls 文件的内容。
- 通过 inode 信息中 block 的位置,找到 cangls 文件实际的 block。
- 读取 block 数据,从而读取出 cangls 文件的内容。
既然如此,那么 /test/ 目录的文件名放在哪里呢?当然放在 / 目录的 block 中了,而/目录的 inode 号(/ 目录的 inode 号是 2)是系统已知的。也就是说,在系统中读取任意一个文件,都要先通过 / 目录的 inode 信息找到 / 目录的 block,再查看 / 目录的 block,从而可以确定一级目录的 inode 信息。然后一级一级地查找到最终文件的 block 信息,从而读取数据。
总结:因为文件名保留在上级目录的 block 中,所以对文件拥有写权限,是不能删除文件本身的,只能删除文件中的数据(也就是文件 block 中的内容)。要想删除文件名,需要对文件所在目录拥有写权限。
2) 目录的可用权限。#
对目录来讲,如果只赋予只读(r)权限,则是不可以使用的。大家想想,要想读取目录下的文件,你怎么也要进入目录才可以吧?而进入目录,对目录来讲,需要执行(x)权限的支持。
目录的可用权限其实只有以下几个。
- 0:任何权都不赋予。
- 5:基本的目录浏览和进入权限。
- 7:完全权限。
示例#
我们做权限的实验,是不能使用 root 用户测试的。由于 root 用户是超级用户,就算没有任何权限,root 用户依然可执行全部操作。
所以我们只能使用普通用户来验证权限,而目前普通用户又不能修改文件权限(不是普通用户不能修改文件权限,而是只有文件的所有者才能修改文件权限,我们当前没有讲修改所有者的命令,从而导致普通用户不能修改文件权限)。在实验中,笔者会用 root 用户来修改文件权限,而用普通用户 user 来验证权限,请大家注意用户身份的变化。
实验思路:由 root 用户把测试目录和测试文件的权限改为最小(0),然后逐步放大权限,用普通用户来验证每个权限可以执行那些命令。
创建普通用户 user 的简单步骤:第一步,添加用户执行命令"useradd user";第二步,设置用户密码 "passwd user",输入两次密码确认。
#步骤一:由root身份建立测试文件
[root@localhost ~]# cd /home/user/
#进入普通用户的家目录中建立测试目录和文件,因为普通用户无法进入root的家目录中
[root@localhost user]# mkdir test
[root@localhost user]# touch test/cangls
#建立测试目录和文件
[root@localhost user]# chmod 750 test/
#修改test目录的权限为750
#由于没有修改所有者和所属组,所以user用户会匹配其他人权限
#为了实验效果,只把他人的权限改为0,而所有者和所属组权限不修改
[root@localhost user]# chmod 640 test/cangls
#修改cangls文件的权限为640
#步骤二:由user用户测试权限(执行命令"su-user"切换用户)
[user@localhost ~]$ ll
总用量 4
drwxr-x—-- 2 root root 4096 6月 15 13:19 test
#思考:为什么user对test目录没有权限,却能看到 test目录?
[user@localhost ~]$ ls test/
ls:无法打开目录test/:权限不够
[user@localhost ~]$ cd test/
-bash: cd: test/:权限不够
#由于user用户对test目录没有权限(0),所以既不能查看目录下的内容,也不能进入目录
#步骤三:由root用户给test目录赋予读(r)权限
[root@localhost user]# chmod 754 test
[root@localhost user]# ll test/
总用量0
-rw-r----- 1 root root 0 6月 15 13:19 cangls
#注意,这是测试实验,只读(r)权限对目录无法正常使用
#步骤四:由user用户测试,读(r)权限虽然可以看到目录下的内容,但是不能正常使用
[user@localhost ~]$ ls test/
ls:无法访问test/cangls:权限不够
cangls
#ls查看目录下的内容,虽然看到了文件名,但依然报错"权限不够"
[user@localhost ~]$ ll test/
ls:无法访问test/cangls:权限不够
总用量0
-????????? ???? ? cangls
#ll查看目录下的内容,会发现由于权限不足,所以只能看到文件名,其他信息都是"?",代表不能正常查看
[user@localhost ~]$ cd test/
-bash: cd: test/:权限不够
#当然也不能进入目录
#所以,只读(r)权限对目录来说是无法正常使用的权限
#步骤五:由root用户给test目录赋予读(r)和执行(x)权限
[root@localhost user]# chmod 755 test
[root@localhost user]# ll test/
总用量0
-rw-r—---- 1 root root 0 6月 15 13:19 cangls
#读(r)和执行(x)权限对目录来说才是可以正常使用的权限
#步骤六:由user用户测试
[user@localhost ~]$ ll test/
总用量0
-rw-r—---- 1 root root 0 6月 15 13:19 cangls
#可以正常查看目录下的内容
[user@localhost ~]$ cd test/
[user@localhost test]$
#可以进入目录了
#步骤七:我们开始测试文件权限,由user用户测试
[user@localhost test]$ cat cangls
cat: cangls:权限不够
#user用户没有读(r)权限,所以不能查看文件的内容
[user@localhost test]$ echo 22222 >> cangls
-bash: cangls:权限不够
#user用户没有写(w)权限,所以不能写入数据
#步骤八:由root用户给cangls文件赋予读(r)权限
[root@localhost user]# chmod 644 test/cangls
#步骤九:由user用户测试,可以读取cangls文件的内容
[user@localhost test]$ cat cangls
[user@localhost test]$
#虽然文件为空,但是不再报错
[user@localhost test]$ echo 22222 >> cangls
-bash: cangls:权限不够
#由于没有写权限,所以依然不能向文件中写入数据
#步骤十:由root用户给cangls文件赋予写(w)权限
[root@localhost user]# chmod 646 test/cangls
#这只是实验,才会出现其他人权限高于所属组权限的情况,实际情境不会这样
#步骤十一:由user用户测试,可以对cangls文件写入数据
[user@localhost test]$ echo 22222 >> cangls
[user@localhost test]$ rm -rf cangls
rm:无法删除"cangls":权限不够
#可以对cangls文件写入数据,但是不能删除这个文件本身
#步骤十二:由root用户给test目录赋予写(w)权限
[root@localhost user]# chmod 757 test/
[root@localhost user]# ll
总用量4
drwxr-xrwx 2 root root 4096 6月 15 13:19 test
#其他用户赋予7权限,非常不安全,在生产环境下严格禁用
#步骤十三:由user用户测试,可以删除cangls文件,并且可以新建、复制和剪切
[user@localhost test]$ rm -rf cangls
#可以删除
[user@localhost test]$ touch bols
#可以新建bols文件
[user@localhost test]$ mv bols Imls
#可以把bols文件改名为lmls
这个实验并不复杂,但是由于需要在两个用户身份之间切换,所以代码确实比较长。这个实验可以充分说明每个权限可以执行哪些命令,可以帮助我们更好地理解权限的含义。
Linux chown命令#
chown 是修改文件和目录的所有者和所属组的命令,其基本信息如下。
- 命令名称:chown。
- 文原意:change file owner and group。
- 所在路径:/bin/chown。
- 执行权限:所有用户。
- 功能描述:修改文件和目录的所有者和所属组。
命令格式#
[root@localhost ~]# chown [选项] 所有者:所属组文件或目录
选项:
- -R: 递归设置权限,也就是给子目录中的所有文件设置权限
常见用法#
【例 1】修改文件的所有者。
之所以需要修改文件的所有者,是因为赋予权限的需要。当普通用户需要对某个文件拥有最高权限的时候,是不能把其他人的权限修改为最高权限的,也就是不能出现 777 的权限,这是非常不安全的做法。
合理的做法是修改文件的所有者,这样既能让普通用户拥有最高权限,又不影响其他普通用户。我们来看例子:
[root@localhost ~]# touch laowang
#由root用户创建laowang文件
[root@localhost ~]# ll laowang
-rw-r--r-- 1root root 0 6月 16 05:12 laowang
#文件的所有者是root,普通用户user对这个文件拥有只读权限
[root@localhost ~]# chown user laowang
#修改文件的所有者
[root@localhost ~]# ll laowang
-rw-r--r-- 1 userroot 0 6月 16 05:12 laowang
#所有者变成了user用户,这时user用户对这个文件就拥有了读、写权限
【例 2】修改文件的所属组。
chown 命令不仅可以修改文件的所有者,也可以修改文件的所属组。例如:
[root@localhost ~]# chown user:user laowang
# ":"之前是文件的所有者,之后是所属组。这里的":"也可以使用"."代替
[root@localhost ~]# ll laowang
-rw-r--r-- 1 user user 0 6月 16 05:12 laowang
修改所属组,也是为了调整文件的权限。只是我们目前还没有学习如何把用户加入用户组中,如果可以把用户加入同一个组当中,然后直接调整所属组的权限,那当然要比用户赋予权限要简单方便。
Linux 中用户组的建立与 Windows 中是不同的。在 Windows 中,新建的用户都属于 users 这个组,而不会建立更多的新组。但是在 Linux 中,每个用户建立之后,都会建立和用户名同名的用户组,作为这个用户的初始组,user 用户组是自动建立的。
【例 3】普通用户修改权限。
笔者在讲权限作用的时候强调过,并不是只有 root 用户才可以修改文件的权限,而是超级用户可以修改任何文件的权限,普通用户只能修改自己文件的权限。也就是说,只有普通用户是这个文件的所有者,才可以修改文件的权限。我们试试:
[root@localhost ~]# cd /home/user/
#进入user用户的家目录
[root@localhost user]# touch test
#由root用户新建文件test
[root@localhost user]# ll test
-rw-r--r--1 root root 0 6月 16 05:37 test
#文件所有者和所属组都是root用户
[root@localhost user]# su- user
#切换为user用户
[user@localhost ~]$ chmod 755 test
chmod:更改"test"的权限:不允许的操作 #user用户不能修改test文件的权限
[user@localhost ~]$ exit
#退回到root身份
[root@localhost user]# chown user test
#由root用户把test文件的所有者改为user用户
[root@localhost user]# su- user
#切换为user用户
[user@localhost ~]$ chmod 755 test
#user用户由于是test文件的所有者,所以可以修改文件的权限
[user@localhost ~]$ ll test
-rwxr-xr-x 1 user root 0 6月 16 05:37 test
#查看权限
通过这个实验,我们可以确定,如果普通用户是这个文件的所有者,就可以修改文件的权限。
Linux chgrp命令#
chgrp 是修改文件和目录的所属组的命令,其基本信息如下:
- 命令名称:chgrp。
- 英文原意:change group ownership。
- 所在路径:/bin/chgrp。
- 执行权限:所有用户。
- 功能描述:修改文件和目录的所属组。
chgrp 命令比较简单,就是修改文件和目录的所属组。我们来试试:
[root@localhost ~]# touch test2
#建立测试文件
[root@localhost ~]# chgrp user test2
#修改test2文件的所属组为user用户组
[root@localhost ~]# ll test2
-rw-r--r-- 1 root user0 6月 16 05:54 test2
#修改生效
Linux umask默认权限#
umask 默认权限是 Linux 权限的一种,主要用于让 Linux 中的新建文件和目录拥有默认权限。Linux 是一个比较安全的操作系统,而安全的基础就是权限,所以,在 Linux 中所有的文件和目录都要有基本的权限,新建的文件和目录当然也要有默认的权限。
在 Linux 中,通过 umask 默认权限来给所有新建立的文件和目录赋予初始权限,这一点和 Windows 不太一样,Windows 是通过继承上级目录的权限来给文件和目录赋予初始权限的。
査看系统的 umask 权限:
[root@localhost ~]# umask
0022
#用八制数值显示umask权限
[root@localhost ~]# umask -S
u=rwx, g=rx, o=rx
#用字母表示文件和目录的初始权限
使用"-S"选项,会直接用字母来表示文件和目录的初始权限。我们査看数值的 umask 权限,看到的是 4 位数字"0022",其中第一个数字"0"代表的是文件的特殊权限(SetUID、SetGID、Sticky BIT),特殊权限我们放在后续章节来详细讲解,现在先不讨论。也就是后 3 位数字"022"才是真正的 umask 默认权限。
umask默认权限的计算方法#
在学习 umask 默认权限的计算方法之前,我们需要先了解一下新建文件和目录的默认最大权限。
- 对文件来讲,新建文件的默认最大权限是 666,没有执行(x)权限。这是因为执行权限对文件来讲比较危险,不能在新建文件的时候默认赋予,而必须通过用户手工赋予。
- 对目录来讲,新建目录的默认最大权限是 777。这是因为对目录而言,执行(x)权限仅仅代表进入目录,所以即使建立新文件时直接默认赋予,也没有什么危险。
接下来我们学习如何计算 umask 默认权限。按照官方的标准算法,umask 默认权限需要使用二进制进行逻辑与和逻辑非联合运算才可以得到正确的新建文件和目录的默认权限。这种方法既不好计算,也不好理解,笔者并不推荐。
我们在这里还是按照权限字母来讲解 umask 权限的计算方法。我们就按照默认的 umask 值是 022 来分别计算一下新建文件和目录的默认权限吧。
- 文件的默认权限最大只能是 666,换算成字母就是"-rw-rw-rw-";而 umask 的值是 022,也换算成字母就是"-----w--w-"。把两个字母权限相减,得到的就是新建文件的默认权限:(-rw-rw-rw-) - (-----w--w-)=(-rw-r--r--)。
- 目录的默认权限最大可以是 777,换算成字母就是"drwxrwxrwx";而 umask 的值是022,也换算成字母就是"d----w--w-"。也把两个字母权限相减,得到的就是新建目录的默认权限:(drwxrwxrwx) - (d----w--w-)=(drwx-r-xr-x)。
我们测试一下:
[root@localhost ~]# umask 0022
#默认umask的值是0022
[root@localhost ~]# touch laowang
[root@localhost ~]# mkdir fengjie
[root@localhost ~]# ll -d laowang fengjie/
drwxr-xr-x 2 root root 4096 6月 16 02:36 fengjie/ -rw-r--r-- 1 root root 0 6月 16 02:36 laowang
#新建立目录的默认权限是755,新建立文件的默认权限是644
注意,这里强调一下,umask 默认权限的计算是不能直接使用数字相减的。很多人会理解为,既然文件的默认权限最大是"666",umask 的值是"022",而新建文件的值刚好是"644",那是不是就是直接使用"666-644"呢?
这是不对的,如果 umask 的值是"033"呢?按照数值相减,就会得到"633"的值。但是我们强调过文件是不能在新建立时就拥有执行(x)权限的,而权限"3"是包含执行(x)权限的。我们测试一 下:
[root@localhost ~]# umask 033
#修改umask的值为033
[root@localhost ~]# touch xuejie
#建立测试文件xuejie
[root@localhost ~]# ll xuejie
-rw-r--r-- 1 root root 0 6月 16 02:46 xuejie
#xuejie文件的默认权限依然是644
由这个例子我们可以知道,umask 默认权限一定不是使用权限数字相减得到的,而是通过二进制逻辑与和逻辑非联合运算得到的。最简单的办法还是使用权限字母来计算。
文件的默认权限最大只能是 666,换算成字母就是"-rw-rw-rw-";而 umask 的值是 033,也换算成字母就是"-----wx-wx"。把两个字母权限相减,得到的就是新建文件的默认权限:(-rw-rw-rw-)-(-----wx-wx)=(-rw-r--r--)。
umask 默认权限的修改方法#
umask 默认权限可以直接通过命令来进行修改,例如:
[root@localhost ~]# umask 002
[root@localhost ~]# umask 033
不过,通过命令进行的修改只能临时生效,一旦重启或重新登录就会失效。如果想让修改永久生效,则需要修改对应的环境变量配置文件 /etc/profile。例如:
[root@localhost ~]# vi /etc/profile
...省略部分内容...
if [ $UID -gt 199]&&[ "'id -gn'" = "'id -un'" ]; then umask 002
#如果UID大于199(普通用户),则使用此umask值
else
umask 022
#如果UID小于199(超级用户),则使用此umask值
fi
…省略部分内容…
这是一段 Shell 脚本,大家目前可能看不懂,但是没有关系,只需知道普通用户的 umask 值由 if 语句的第一段定义,而超级用户的 umask 值由 else 语句定义即可。 如果修改的是这个文件,则 umask 值是永久生效的。
我们学习了文件的基本权限和 umask 默认权限这两种权限,但是 Linux 的权限并不只有这两种,其他的权限内容我们会在后续章节中介绍,这里就不一一列举了。
Linux man命令#
Linux 自带的帮助命令是最准确、最可靠的资料。笔者不止一次发现通过其他途径搜索到的信息都不准确,甚至是错误的。所以,虽然 Linux 自带的帮助命令是英文的,但是我们要静下心来慢慢学习。
main 是最常见的帮助命令,也是 Linux 最主要的帮助命令,其基本信息如下。
- 命令名称:man。
- 英文原意:format and display the on-line manual pages。
- 所在路径:/usr/bin/man。
- 执行权限:所有用户。
- 功能描述:显示联机帮助手册。
命令格式#
[root@localhost ~]# man [选项]命令
选项:
- -f:査看命令拥有哪个级别的帮助
- -k: 査看和命令相关的所有帮助
man 命令比较简单,我们举个例子:
[root@localhost -]# man ls
#获取ls命令的帮助信息
这就是 man 命令的基本使用方法,非常简单。但是帮助命令的重点不是命令如何使用,而是帮助信息应该如何使用。这些信息较多,我们通过下面一小节来详细讲解。
man命令的使用方法#
还是查看 ls 命令的帮助,我们看看这个帮助信息的详细内容。
[root@localhost -]# man ls
该命令会输出以下信息:
虽然不同命令的 man 信息有一些区别,但是每个命令 man 信息的整体结构皆如演示这样。在帮助信息中,我们主要査看的就是命令的格式和选项的详细作用。
不过大家请主意,在 man 信息的最后,可以看到还有哪些命令可以查看到此命令的相关信息。这是非常重要的提示,不同的帮助信息记录的侧重点是不太一样的。所以,如果在 man 信息中找不到想要的内容,则可以尝试看其他相关帮助命令。
man命令的快捷键#
man 命令的快捷键可以参考表 1。
快捷键 | 作 用 |
---|---|
上箭头 | 向上移动一行 |
下箭头 | 向下移动一行 |
PgUp | 向上翻一页 |
PgDn | 向下翻一页 |
g | 移动到第一页 |
G | 移动到最后一页 |
q | 退出 |
/字符串 | 从当前页向下搜索字符串 |
?字符串 | 从当前页向上搜索字符串 |
n | 当搜索字符串时,可以使用n键找到下一个字符串 |
N | 当搜索字符串时,使用N键反向查询字符串。也就是说,如果使用“/字符串”方式搜索, 则N键表示向上搜索字符串;如果使用“?字符串”方式搜索,则N键表示向下搜索字符串 |
man命令的帮助级别#
不知道大家有没有注意到,在执行 man 命令时,命令的开头会有一个数字标识这个命令的帮助级别。例如:
[root@localhost -]# man ls
LS(1) User Commands LS(1)
#这里(1)就表示这是 ls 的 1 级别的帮助信息
这些命令的级别号代表什么含义呢?我们通过表 2 来说明。
级 别 | 作 用 |
---|---|
1 | 普通用户可以执行的系统命令和可执行文件的帮助 |
2 | 内核可以调用的函数和工具的帮助 |
3 | C语言函数的帮助 |
4 | 设备和特殊文件的帮助 |
5 | 配置文件的帮助 |
6 | 游戏的帮助(个人版的Linux中是有游戏的) |
7 | 杂项的帮助 |
8 | 超级用户可以执行的系统命令的帮助 |
9 | 内核的帮助 |
我们来试试,ls 命令的帮助级别是 1,我们已经看到了。那么我们找一个只有超级用户才能执行的命令,如 useradd 命令(添加用户的命令),来看看这个命令的帮助:
[root@localhost ~]# man useradd U
SERADD(8) System Management Commands USERADD(8)
#我们可以看到,默认useradd命令的帮助级别是8,因为这是只有超级用户才可以执行的命令
命令拥有哪个级别的帮助可以通过"-f"选项来进行査看。例如:
[root@localhost -]# man -f ls
ls(1) - list directory contents
#可以看到ls命令只拥有1级别的帮助
ls 是一个比较简单的 Linux 命令,所以只有 1 级别的帮助。我们再査看一下 passwd 命令(给用户设定密码的命令)的帮助:
[root@localhost ~]# man -f passwd
passwd (1) - update user's authentication tokens
#passwd命令的帮助
passwd (5) - password file
#passwd配置文件的帮助
passwd[sslpasswd] (1ssl) - compute password hashes
#这里是SSL的passwd的帮助,和passwd命令并没有太大关系
passwd 是一个比较复杂的命令,而旦这个命令有一个相对比较复杂的配置文件 /etc/passwd。所以系统既给出了 passwd 命令的帮助,也给出了 /etc/passwd 配置文件的帮助。大家可以使用如下命令查看:
[root@localhost ~]# man 1 passwd
#查看passwd命令的帮助
[root@localhost ~]# man 5 passwd
#查看/etc/passwd配件的帮助
至于 useradd 和 passwd 命令,我们会在后续章节中详细讲解,这里只是用这个例子说明 man 命令的不同帮助级别。
man 命令还有一个"-k"选项,它的作用是査看命令名中包含指定字符串的所有相关命令的帮助。例如:
[root@localhost ~]# man -k useradd
luseradd(1) - Add an user
useradd(8) - create a new user or update default new user information
useradd [adduser] (8) - create a new user or update default new user information
useradd_selinux (8) -Security Enhanced Linux Policy for the useradd processes
#这条命令会列出系统中所有包含useradd字符串的命令,所以才会找到一些包含"useradd"字符串,但是和我们要査找的useradd无关的命令。
如果我们使用"man-k ls"命令,则会发现输出内容会多出几页,那是因为很多命令中都包含"ls"这个关键字。这条命令适合你只记得命令的几个字符,用来査找相关命令的情况。
在系统中还有两个命令。
- whatis:这个命令的作用和 man -f 是一致的。
- apropos:这个命令的作用和 man -k 是一致的。
不过这两个命令和 man 基本一致,所以了解就好。不过 Linux 的命令很有意思,想知道这个命令是干什么的,可以执行 whatis 命令;想知道命令在哪里,可以执行 whereis 命令;想知道当前登录用户是谁,可以执行 whoami 命令。
如果执行以上两个命令报错,那是因为 whatis 数据库没有建立。只要手工执行以下命令,重新建立 whatis 数据库即可。
Linux info命令#
info 命令也可以获取命令的帮助。和 man 命令不同的是,info 命令的帮助信息是一套完整的资料,每个单独命令的帮助信息只是这套完整资料中的某一个小章节。大家可以把 info 帮助信息看成一部独立的电子书,所以每个命令的帮助信息都会和书籍一样,拥有章节编号。例如:
[root@localhost ~]# info ls
Next: dir invocation, Up: Directory listing
10.1 'ls': List directory contents
The 'ls' program lists information about files (of any type, including directories). Options and file arguments can be intermixed arbitrarily, as usual.
...省略部分内容...
可以看到,ls 命令的帮助只是整个 info 帮助信息中的第 10.1 节。在这个帮助信息中,如果标题的前面有"*"符号,则代表这是一个可以进入査看详细信息的子页面,只要按下回车键就可以进入。例如:
[root@localhost ~]# info ls
…省略部分内容...
Also see *note Common options::.
*Menu:
*Which files are listed::
*What information is listed::
*Sorting the output::
*Details about version sort::
*General output formatting::
*Formatting file timestamps::
*Formatting the file names::
…省略部分内容…
这是 ls 命令的 info 帮助信息中可以査看详细的子页面的标题。info 命令主要是靠快捷键来进行操作的,我们来看看常用的快捷键,如表 1 所示。
快捷键 | 作 用 |
---|---|
上箭头 | 向上移动一行 |
下箭头 | 向下移动一行 |
PgUp | 向上翻一页 |
PgDn | 向下翻一页 |
Tab | 在有"*"符号的节点间进行切换 |
回车 | 进入有"*"符号的子页面,査看详细帮助信息 |
u | 进入上一层信息(回车是进入下一层信息) |
n | 进入下一小节信息 |
P | 进入上一小节信息 |
? | 査看帮助信息 |
q | 退出info信息 |
这是常用的快捷键,其他快捷键可以使用"?"快捷键查看。
Linux help命令#
help 是非常简单的命令,而且不经常使用。因为 help 只能获取 Shell 内置命令的帮助,但在 Linux 中绝大多数命令是外部命令,所以 help 命令的作用非常有限。而且内置命令也可以使用 man 命令获取帮助。
help 命令的基本信息如下。
- 命令名称:help。
- 英文原意:help。
- 所在路径:Shell 内置命令。
- 执行权限:所有用户。
- 功能描述:显示 Shell 内置命令的帮助。
help 命令的格式非常简单:
[root@localhost ~]# help 内置命令
Linux 中有哪些命令是内置命令呢?我们可以随意使用 man 命令来査看一个内置命令的帮助,例如:
[root@localhost ~]# man help
BASH_BUILTINS(1)
BASH_BUILTINS(1)
NAME
bash,:,.,[, alias, bg, bind, break, builtin, caller, cd, command, compgen,complete, compopt, continue, declare, dirs, disown, echo, enable, eval, exec,exit, export,false, fc, fg, getopts, hash, help, history, jobs, kill, let, local, logout,mapfile, popd, printf, pushd, pwd, read, readonly, return, set, shift, shopt,source, suspend, test, times, trap, true, type, typeset, ulimit, umask,unalias, unset, wait - bash built-in commands, seebash(1)
...省略部分内容...
#这里列出的命令就是所有的Shell内置命令
可以发现,如果使用 man 命令去査看任意一个 Shell 内置命令,则会列出所有 Shell 内置命令的帮助。査看一个具体的 Shell 内置命令如 history 的帮助,可以执行 "help history"。
如果我们使用 help 命令査看外部命令的帮助,则会如何呢?
[root@localhost ~]# help ls
-bash: help: no help topics match 'ls'.Try 'help help' or 'man -k Is' or 'info ls'.
#这里会报错,报错信息是"help无法得到 ls 命令的帮助,请査看 help 帮助,或者用 man 和 info 来査看ls的帮助信息"
--help 选项#
绝大多数命令都可以使用"--help"选项来査看帮助,这也是一种获取帮助的方法。例如:
[root@localhost ~]# ls --help
这种方法非常简单,输出的帮助信息基本上是 man 命令的信息简要版。
Linux whereis命令#
Linux 拥有强大的搜索功能,但是强大带来的缺点是相对赚复杂。但是大家不用担心,搜索命令只是选项较多,不容易记忆而已,并不难理解。
在使用搜索命令的时候,大家还是需要注意,如果搜索的范围过大、搜索的内容过多,则会给系统造成巨大的压力,所以不要在服务器访问的高峰执行大范围的搜索命令。
whereis 命令#
whereis 是搜索系统命令的命令(像绕口令一样),也就是说,whereis 命令不能搜索普通文件,而只能搜索系统命令。whereis 命令的基本信息如下。
- 命令名称:whereis。
- 英文原意:locate the binary, source, and manual page files for a command。
- 所在路径:/usr/bin/whereis.
- 执行权限:所有用户。
- 功能描述:査找二进制命令、源文件和帮助文档的命令。
命令格式#
看英文原意,就能发现 whereis 命令不仅可以搜索二进制命令,还可以找到命令的帮助文档的位置。
[root@localhost ~]# whereis [选项] 命令
选项:
- -b: 只査找二制命令;
- -m: 只查找帮助文档;
常见用法#
whereis 命令的使用比较简单,我们来试试,例如:
[root@localhost ~]# whereis ls
ls: /bin/ls /usr/share/man/man1/ls.1.gz /usr/share/ man/man1p/ls.1p.gz
#既可以看到二进制命令的位置,也可以看到帮助文档的位置
但是,如果使用 whereis 命令査看普通文件,则无法査找到。例如:
[root@localhost ~]# touch cangls
[root@localhost ~]# whereis cangls
cangls:
#无法査找到普通文件的信息
如果需要査找普通文件的内容,则需要使用 find 命令,我们稍后会详细讲解 find 命令。
再看一下 whereis 命令的选项。如果我们只想査看二进制命令的位置,则可以使用"-b"选项;而如果我们只想査看帮助文档的位置,则可以使用"-m"选项。
[root@localhost ~]# whereis -b ls
ls: /bin/ls
#只查看二进制命令的位置
[root@localhost ~]# whereis -m ls
ls: /usr/share/man/man1/ls.1.gz /usr/share/man/ man1p/ls.1p.gz
#只査看帮助文档的位置
Linux which命令#
which 也是搜索系统命令的命令。和 whereis 命令的区别在于,whereis 命令可以在查找到二进制命令的同时,查找到帮助文档的位置;而 which 命令在查找到二进制命令的同时,如果这个命令有别名,则还可以找到别名命令。
which 命令的基本信息如下。
- 命令名称:which。
- 英文原意:shows the full path of(shell)commands。
- 所在路径:/usr/bin/which。
- 执行权限:所有用户。
- 功能描述:列出命令的所在路径。
which 命令非常简单,可用选项也不多,我们直接举个例子:
[root@localhost ~]# which ls
alias ls='ls --color=auto'
/bin/ls
#which 命令可以查找到命令的别名和命令所在位置
#alias 这段就是别名,别名就是小名,也就是说,当我们输入 ls 命令时,实际上执行的是 ls--color=auto
Linux locate命令#
whereis 和 which 命令都是只能搜索系统命令的命令,而 locate 命令才是可以按照文件名搜索普通文件的命令。
但是 locate 命令的局限也很明显,它只能按照文件名来搜索文件,而不能执行更复杂的搜索,比如按照权限、大小、修改时间等搜索文件。如果要按照复杂条件执行搜索,则只能求助于功能更加强大的 find 命令。locate 命令的优点鮮常明显,那就是搜索速度非常快,而且耗费系统资源非常小。这是因为 locate 命令不会直接搜索硬盘空间,而会先建立 locate 数据库,然后在数据库中按照文件名进行搜索,是快速的搜索命令。
locate 命令的基本信息如下。
- 命令名称:locate。
- 英文原意:find files by name。
- 所在路径:/usr/bin/locate。
- 执行权限:所有用户。
- 功能描述:按照文件名搜索文件。
命令格式#
locate 命令只能按照文件名来进行搜索,所以使用比较简单。
[root@localhost ~]# locate [选项] 文件名
选项:
- -i:忽略大小写
常见用法#
【例 1】基本用法。
搜索 Linux 的安装日志。
[root@localhost ~]# locate install.log
/root/install.log
/root/install.log.syslog
#搜索文件名叫install.log的文件
系统命令其实也是文件,也可以按照文件名来搜索系统命令。
[root@localhost ~]# locate mkdir
/bin/mkdir
/usr/bin/gnomevfs-mkdir
/usr/lib/perl5/auto/POSIX/mkdir.al
…省略部分内容...
#会搜索出所有含有mkdir字符串的文件名,当然也包含mkdir命令
【例 2】locate 命令的数据库。
我们在使用 locate 命令的时候,可能会发现一个问题:如果我们新建立一个文件,那么 locate 命令找不到这个文件。例如:
[root@localhost ~]# touch cangls
[root@localhost ~]# locate cangls
#新建立的文件,locate命令找不到
这是因为 locate 命令不会直接搜索硬盘空间,而会搜索 locate 数据库。这样做的好处是耗费系统资源小、搜索速度快;缺点是不是实时更新的,而要等用户退出登录或重启系统时,locate 数据库才会更新,所以我们无法查找到新建立的文件。
既然如此,locate 命令的数据库在哪里呢?
[root@localhost ~]#ll /var/lib/mlocate/mlocate.db
-rw-r----- 1 root slocate 2328027 6月 14 02:08/var/lib/ mlocate/mlocate.db
#这是 locate 命令实际搜索的数据库的位置
这个数据库是二进制文件,不能直接使用 Vim 等编辑器査看,而只能使用对应的 locate 命令进行搜索。如果我们不想退出登录或重启系统,则也可以通过 updatedb 命令来手工更新这个数据。例如:
[root@localhost ~]# locate cangls
#没有更新数据库时,找不到cangls文件
[root@localhost ~]# updatedb
#更新数据库[root@localhost ~]# locate cangls
/root/cangls
#新建立的文件已经可以搜索到了
locate配置文件#
我们再做一个实验,看看这是什么原因导致的。
[root@localhost ~]# touch /tmp/lmls
#在/tmp/目录下新建立一个文件
[root@localhost ~]# updatedb
#更新locat数据库
[root@localhost ~]# locate lmls
#依然查询不到lmls这个新建文件
新建立了 /tmp/lmls 文件,而且也执行了 updatedb 命令,却依然无法找到这个文件,这是什么原因?这就要来看看 located 配置文件 /etc/updatedb.conf了。
[root@localhost ~]#vi /etc/updatedb.conf
PRUNE_BIND_MOUNTS = "yes"
#开启搜索机制,也就是让这个配置文件生效
PRUNEFS = "9p afs anonjnodefs auto autofs bdev binfmt_misc cgroup cifs coda
configfs cpuset debugfs devpts ecryptfs exofe fuse fusectl gfs gfe2 hugetlbfs
inotifyfs iso9660 jffs2 lustre mqueue ncpfs nfe nfs4 nfsd pipefe proc ramfs rootfs
rpc_pipefs securityfs selinuxfs sfs sockfs sysfs tmpfs ubifs udf usbfs"
#在local执行搜索时,禁止搜索这些文件系统类型
PRUNENAMES = ".git.hg.svn"
#在locate执行搜索时,禁止搜索带有这些扩展名的文件
PRUNEPATHS = "/afs /media /net /sfs /tmp /udev /var/cache/ccache /var/spod/cups /var/spool/squid /var/tmp"
#在locat执行搜索时,禁止搜索这些系统目录
在 locate 执行搜索时,系统认为某些文件系统、某些文件类型和某些目录是没有搜索必要的,比如光盘、网盘、临时目录等,这些内容要么不在 Linux 系统中,是外来存储和网络存储,要么是系统的缓存和临时文件。刚好 /tmp/ 目录也在 locate 搜索的排除目录当中,所以在 /tmp/ 目录下新建的文件是无法被找到的。
Linux find命令#
find 是 Linux 中强大的搜索命令,不仅可以按照文件名搜索文件,还可以按照权限、大小、时间、inode 号等来搜索文件。但是 find 命令是直接在硬盘中进行搜索的,如果指定的搜索范围过大,find命令就会消耗较大的系统资源,导致服务器压力过大。所以,在使用 find 命令搜索时,不要指定过大的搜索范围。
find 命令的基本信息如下:
- 命令名称:find。
- 英文原意:search for files in a directory hierarchy.
- 所在路径:/bin/find。
- 执行权限:所有用户。
- 功能描述:在目录中查找文件。
命令格式#
[root@localhost ~]# find 搜索路径 [选项] 搜索内容
find 是比较特殊的命令,它有两个参数:
- 第一个参数用来指定搜索路径;
- 第二个参数用来指定搜索内容。
而且find命令的选项比较复杂,我们一个一个举例来看。
按照文件名搜索#
[root@localhost ~]#find 搜索路径 [选项] 搜索内容
选项:
- -name: 按照文件名搜索;
- -iname: 按照文件名搜索,不区分文件名大小;
- -inum: 按照 inode 号搜索;
这是 find 最常用的用法,我们来试试:
[root@localhost ~]# find /-name yum.conf
/etc/yum.conf
#在目录下査找文件名是yum.conf的文件
但是 find 命令有一个小特性,就是搜索的文件名必须和你的搜索内容一致才能找到。如果只包含搜索内容,则不会找到。我们做一个实验:
[root@localhost ~]# touch yum.conf.bak
#在/root/目录下建立一个文件yum.conf.bak
[root@localhost ~]# find /-name yum.conf
/etc/yum.conf
#搜索只能找到yum.conf文件,而不能找到 yum.conf.bak 文件
find 能够找到的是只有和搜索内容 yum.conf 一致的 /etc/yum.conf 文件,而 /root/yum.conf.bak 文件虽然含有搜索关键字,但是不会被找到。这种特性我们总结为:find 命令是完全匹配的,必须和搜索关键字一模一样才会列出。
Linux 中的文件名是区分大小写的,也就是说,搜索小写文件,是找不到大写文件的。如果想要大小通吃,就要使用 -iname 来搜索文件。
[root@localhost ~]# touch CANGLS
[root@localhost ~]# touch cangls
#建立大写和小写文件
[root@localhost ~]#find.-iname cangls
./CANGLS
./cangls
#使用-iname,大小写文件通吃
每个文件都有 inode 号,如果我们知道 inode 号,则也可以按照 inode 号来搜索文件。
[root@localhost ~]#ls -i install.log
262147 install.log
#如果知道文件名,则可以用"ls -i"来査找inode号
[root@localhost ~]# find.-inum 262147
./install.log
#如果知道inode号,则可以用find命令来査找文件
按照 inode 号搜索文件,也是区分硬链接文件的重要手段,因为硬链接文件的 inode 号是一致的。
[root@localhost ~]# ln /root/install.log /tmp/
#给install.log文件创建一个硬链接文件
[root@localhost ~]#ll -i /root/install.log /tmp/install.log
262147 -rw-r--r--.2 root root 24772 1 月 14 2014/root/
install.log
262147 -rw-r--r--.2 root root 24772 1 月 14 2014/tmp/
install.log
#可以看到这两个硬链接文件的inode号是一致的
[root@localhost ~]# find /-inum 262147
/root/install.log
/tmp/install.log
#如果硬链接不是我们自己建立的,则可以通过find命令搜索inode号,来确定硬链接文件
按照文件大小搜索#
[root@localhost ~]#find 搜索路径 [选项] 搜索内容
选项:
- -size[+-]大小:按照指定大小搜索文件
这里的"+"的意思是搜索比指定大小还要大的文件,"-" 的意思是搜索比指定大小还要小的文件。我们来试试:
[root@localhost ~]# ll -h install.log
-rw-r--r--.1 root root 25K 1月 14 2014 install.log #在当前目录下有一个大小是25KB的文件
[root@localhost ~]#
[root@localhost ~]# find.-size 25k
./install.log
#当前目录下,査找大小刚好是25KB的文件,可以找到
[root@localhost ~]# find .-size -25k
.
./.bashrc
./.viminfo
./.tcshrc
./.pearrc
./anaconda-ks.cfg
./test2
./.ssh
./.bash_history
./.lesshst
./.bash_profile
./yum.conf.bak
./.bashjogout
./install.log.syslog
./.cshrc
./cangls
#搜索小于25KB的文件,可以找到很多文件
[root@localhost ~]# find.-size +25k
#而当前目录下没有大于25KB的文件
其实 find 命令的 -size 选项是笔者个人觉得比较恶心的选项,为什么这样说?find 命令可以按照 KB 来搜索,应该也可以按照 MB 来搜索吧。
[root@localhost ~]# find.-size -25m
find:无效的-size类型"m"
#为什么会报错呢?其实是因为如果按照MB来搜索,则必须是大写的M
这就是纠结点,千字节必须是小写的"k",而兆字节必领是大写的"M"。有些人会说:"你别那么执着啊,你就不能不写单位,直接按照字节搜索啊?"很傻,很天真,不写单位,你们就以为会按照字节搜索吗?我们来试试:
[root@localhost ~]# ll anaconda-ks.cfg
-rw-------.1 root root 1207 1 月 14 2014 anaconda-ks.cfg
#anaconda-ks.cfg文件有1207字芳
[root@localhost ~]# find.-size 1207
#但用find查找1207,是什么也找不到的
也就是说,find 命令的默认单位不是字节。如果不写单位,那么 find 命令是按照 512 Byte 来进行査找的。 我们看看 find 命令的帮助。
[root@localhost ~]# man find
-size n[cwbkMG]
File uses n units of space. The following suffixes can be used:
'b' for 512-byte blocks (this is the default if no suffix is used)
#这是默认单位,如果单位为b或不写单位,则按照 512Byte搜索
'c' for bytes
#搜索单位是c,按照字节搜索
'w' for two-byte words
#搜索单位是w,按照双字节(中文)搜索
'k'for Kilobytes (units of 1024 bytes)
#按照KB单位搜索,必须是小写的k
'M' for Megabytes (units of 1048576 bytes)
#按照MB单位搜索,必须是大写的M
'G' for Gigabytes (units of 1073741824 bytes)
#按照GB单位搜索,必须是大写的G
也就是说,如果想要按照字节搜索,则需要加搜索单位"c"。我们来试试:
[root@localhost ~]# find.-size 1207c
./anaconda-ks.cfg
#使用搜索单位c,才会按照字节搜索
按照修改时间搜索#
Linux 中的文件有访问时间(atime)、数据修改时间(mtime)、状态修改时间(ctime)这三个时间,我们也可以按照时间来搜索文件。
[root@localhost ~]# find搜索路径 [选项] 搜索内容
选项:
- -atime [+-]时间: 按照文件访问时间搜索
- -mtime [+-]时间: 按照文改时间搜索
- -ctime [+-]时间: 按照文件修改时间搜索
这三个时间的区别我们在 stat 命令中已经解释过了,这里用 mtime 数据修改时间来举例,重点说说 "[+-]"时间的含义。
- -5:代表@内修改的文件。
- 5:代表前5~6天那一天修改的文件。
- +5:代表6天前修改的文件。
我们画一个时间轴,来解释一下,如图 1 所示。

图 1 find时间轴
每次笔者讲到这里,"-5"代表 5 天内修改的文件,而"+5"总有人说代表 5 天修改的文件。要是笔者能知道 5 天系统中能建立什么文件,早就去买彩票了,那是未卜先知啊!所以"-5"指的是 5 天内修改的文件,"5"指的是前 5~6 天那一天修改的文件,"+5"指的是 6 天前修改的文件。我们来试试:
[root@localhost ~]#find.-mtime -5
#查找5天内修改的文件
大家可以在系统中把几个选项都试试,就可以明白各选项之间的差别了。
find 不仅可以按照 atmie、mtime、ctime 来査找文件的时间,也可以按照 amin、mmin 和 cmin 来査找文件的时间,区别只是所有 time 选项的默认单位是天,而 min 选项的默认单位是分钟。
按照权限搜索#
在 find 中,也可以按照文件的权限来进行搜索。权限也支持 [+/-] 选项。我们先看一下命令格式。
[root@localhost ~]# find 搜索路径 [选项] 搜索内容
选项:
- -perm 权限模式:査找文件权限刚好等于"权限模式"的文件
- -perm -权限模式:査找文件权限全部包含"权限模式"的文件
- -perm +权限模式:査找文件权限包含"权限模式"的任意一个权限的文件
为了便于理解,我们要举几个例子。先建立几个测试文件。
[root@localhost ~]# mkdir test
[root@localhost ~]# cd test/
[root@localhost test]# touch testl
[root@localhost test]# touch test2
[root@localhost test]# touch test3
[root@localhost test]# touch test4
#建立测试目录,以及测试文件
[root@localhost test]# chmod 755 testl
[root@localhost test]# chmod 444 test2
[root@localhost test]# chmod 600 test3
[root@localhost test]# chmod 200 test4
#设定实验权限。因为是实验权限,所以看起来比较别扭
[root@localhost test]# ll
总用量0
-rwxr-xr-x 1 root root 0 6月 17 11:05 testl -r--r--r-- 1 root root 0 6月 17 11:05 test2
-rw------- 1 root root 0 6月 17 11:05 test3
-w------- 1 root root 0 6月 17 11:05 test4
#查看权限
【例 1】"-perm权限模式"。
这种搜索比较简单,代表査找的权限必须和指定的权限模式一模一样,才可以找到。
[root@localhost test]#find.-perm 444
./test2
[root@localhost test]#find.-perm 200
./test4
#按照指定权限搜索文件,文件的权限必须和搜索指定的权限一致,才能找到
【例 2】"-perm-权限模式"。
如果使用"-权限模式",是代表的是文件的权限必须全部包含搜索命令指定的权限模式,才可以找到。
[root@localhost test]#find .-perm -200
./test4 <-此文件权限为200
./test3 <-此文件权限为600
./testl <-此文件权限为755
#搜索文件的权限包含200的文件,不会找到test2文件,因为test2的权限为444,不包含200权限
因为 test4 的权限 200(-w-------)、test3 的权限 600(-rw-------)和 test1 的权限 755(-rwxr-xr-x) 都包含 200(--w-------) 权限,所以可以找到;而 test2 的权限是 444 (-r--r--r--),不包含 200 (--w-------)权限,所以找不到,再试试:
[root@localhost test]# find .-perm -444
.
./test2 <-此文件权限为444
./test1 <-此文件权限为755
#搜索文件的权限包含444的文件
上述搜索会找到 test1 和 test2,因为 test1 的权限 755 (-rwxr-xr-x)和 test2 的权限 444 (-r--r--r--)都完全包含 444 (-r--r--r--)权限,所以可以找到;而 test3 的权限 600 (-rw-------)和 test4 的权限 200 (-w-------)不完全包含 444 (-r--r--r--) 权限,所以找不到。也就是说,test3 和 test4 文件的所有者权限虽然包含 4 权限,但是所属组权限和其他人权限都是 0,不包含 4 权限,所以找不到,这也是完全包含的意义。
【例 3】"-perm+权限模式"
刚刚的"-perm-权限模式"是必须完全包含,才能找到;而"-perm+权限模式"是只要包含任意一个指定权限,就可以找到。我们来试试:
[root@localhost test]# find .-perm +444
./test4 <-此文件权限为200
./test3 <-此文件权限为600
./testl <-此文件权限为755
#搜索文件的权限包含200的文件,不会找到test2文件,因为test2的权限为444,不包含200权限。
因为 test4 的权限 200 (--w-------)、test3 的权限 600 (-rw-------)和 test1 的权限 755 (-rwxr-xr-x)都包含 200(--w-------)权限,所以可以找到;而 test2 的权限是 444 (-r--r--r--),不包含 200 (--w-------)权限,所以找不到。
按照所有者和所属组搜索#
[root@localhost ~]# find 搜索路径 [选项] 搜索内容
选项:
- -uid 用户 ID:按照用户 ID 査找所有者是指定 ID 的文件
- -gid 组 ID:按照用户组 ID 査找所属组是指定 ID 的文件
- -user 用户名:按照用户名査找所有者是指定用户的文件
- -group 组名:按照组名査找所属组是指定用户组的文件
- -nouser:査找没有所有者的文件
这组选项比较简单,就是按照文件的所有者和所属组来进行文件的査找。在 Linux 系统中,绝大多数文件都是使用 root 用户身份建立的,所以在默认情况下,绝大多数系统文件的所有者都是 root。例如:
[root@localhost ~]#find.-user root
#在当前目录中査找所有者是 root 的文件
由于当前目录是 root 的家目录,所有文件的所有者都是 root 用户,所以这条搜索命令会找到当前目录下所有的文件。
按照所有者和所属组搜索时,"-nouser"选项比较常用,主要用于査找垃圾文件。在 Linux 中,所有的文件都有所有者,只有一种情况例外,那就是外来文件。比如光盘和 U 盘中的文件如果是由 Windows 复制的,在 Linux 中査看就是没有所有者的文件;再比如手工源码包安装的文件,也有可能没有所有者。
除这种外来文件外,如果系统中发现了没有所有者的文件,一般是没有作用的垃圾文件(比如用户删除之后遗留的文件),这时需要用户手工处理。搜索没有所有者的文件,可以执行以下命令:
[root@localhost ~]# find/-nouser
按照文件类型搜索#
[root@localhost ~]# find 搜索路径 [选项] 搜索内容
选项:
- -type d:查找目录
- -type f:查找普通文件
- -type l:查找软链接文件
这个命令也很简单,主要按照文件类型进行搜索。在一些特殊情况下,比如需要把普通文件和目录文件区分开,比如需要把普通文件和目录文件区分开,使用这个选项就很方便。
[root@localhost ~]# find /etc -type d
#查找/etc/目录下有哪些子目录
逻辑运算符#
[root@localhost ~]#find 搜索路径 [选项] 搜索内容
选项:
- -a:and逻辑与
- -o:or逻辑或
- -not:not逻辑非
1) -a:and逻辑与#
find 命令也支持逻辑运算符选项,其中 -a 代表逻辑与运算,也就是 -a 的两个条件都成立,find 搜索的结果才成立。
举个例子:
[root@localhost ~]# find.-size +2k -a -type f
#在当前目录下搜索大于2KB,并且文件类型是普通文件的文件
在这个例子中,文件既要大于 2KB,又必须是普通文件,find 命令才可以找到。再举个例子:
[root@localhost ~]# find.-mtime -3 -a -perm 644
#在当前目录下搜索3天以内修改过,并且权限是644的文件
2) -o:or逻辑或#
-o 选项代表逻辑或运算,也就是 -o 的两个条件只要其中一个成立,find 命令就可以找到结果。例如:
[root@localhost ~]#find.-name cangls -o -name bols
./cangls
./bols
#在当前目录下搜索文件名要么是cangls的文件,要么是bols的文件
-o 选项的两个条件只要成立一个,find 命令就可以找到结果,所以这个命令既可以找到 cangls 文件,也可以找到 bols 文件。
3) -not:not逻辑非#
-not是逻辑非,也就是取反的意思。举个例子:
[root@localhost ~]# find.-not -name cangls
#在当前目录下搜索文件名不是cangls的文件
其他选项#
1) -exec选项
这里我们主要讲解两个选项"-exec"和"-ok",这两个选项的基本作用非常相似。我们先来看看 "exec"选项的格式。
[root@localhost ~]# find 搜索路径 [选项] 搜索内容 -exec 命令2{}\;
首先,请大家注意这里的"{}"和"\;"是标准格式,只要执行"-exec"选项,这两个符号必须完整输入。
其次,这个选项的作用其实是把 find 命令的结果交给由"-exec"调用的命令 2 来处理。"{}"就代表 find 命令的査找结果。
我们举个例子,刚刚在讲权限的时候,使用权限模式搜索只能看到文件名,例如:
[root@localhost test]#find.-perm 444
./test2
如果要看文件的具体权限,还要用"ll"命令査看。用"-exec"选项则可以一条命令搞定:
[root@localhost test]# find.-perm 444 -exec ls -l {}\;
-r--r--r-- 1 root root 0 6月 17 11:05 ./test2
#使用"-exec"选项,把find命令的结果直接交给"ls -l"命令处理
"-exec"选项的作用是把 find 命令的结果放入"{}"中,再由命令 2 直接处理。在这个例子中就是用"ls -l"命令直接处理,会使 find 命令更加方便。
2) -ok选项
"-ok"选项和"-exec"选项的作用基本一致,区别在于:"-exec"的命令会直接处理,而不询问;"-ok"的命令 2 在处理前会先询问用户是否这样处理,在得到确认命令后,才会执行。例如:
[root@localhost test]# find .-perm 444 -ok rm -rf{}\;
<rm…./test2>?y <-需要用户输入y,才会执行
#我们这次使用rm命令来删除find找到的结果,删除的动作最好确认一下
Linux zip命令#
#
".zip"是 Windows 中最常用的压缩格式,Linux 也可以正确识别".zip"格式,这可以方便地和 Windows 系统通用压缩文件。
".zip"格式文件的压缩命令就是 zip,其基本信息如下。
- 命令名称:zip。
- 英文原意:package and compress(archive)files。
- 所在路径:/usr/bin/zip。
- 执行权限:所有用户。
- 功能描述:压缩文件或目录。
命令格式#
[root@localhost ~]#zip [选项] 压缩包名 源文件或源目录
选项:
- -r:压缩目录
zip 压缩命令需要手工指定压缩之后的压缩包名,注意写清楚扩展名,以便解压缩时使用。举个例子:
[root@localhost ~]# zip ana.zip anaconda-ks.cfg
adding: anaconda-ks.cfg (deflated 37%)
#压缩
[root@localhost ~]# ll ana.zip
-rw-r--r-- 1 root root 935 6月 1716:00 ana.zip
#压缩文件生成
所有的压缩命令都可以同时压缩多个文件,例如:
[root@localhost ~]# zip test.zip install.log install.log.syslog
adding: install.log (deflated 72%)
adding: install.log.syslog (deflated 85%)
#同时压缩多个文件到test.zip压缩包中
[root@localhost ~]#ll test.zip
-rw-r--r-- 1 root root 8368 6月 1716:03 test.zip
#压缩文件生成
如果想要压缩目录,则需要使用"-r"选项,例如:
[root@localhost ~]# mkdir dir1
#建立测试目录
[root@localhost ~]# zip -r dir1.zip dir1
adding: dir1/(stored 0%)
#压缩目录
[root@localhost ~]# ls -dl dir1.zip
-rw-r--r-- 1 root root 160 6月 1716:22 dir1.zip
#压缩文件生成
Linux unzip命令#
".zip"是 Windows 中最常用的压缩格式,Linux 也可以正确识别".zip"格式,这可以方便地和 Windows 系统通用压缩文件。
".zip"格式的解压缩命令是 unzip,其基本信息如下:
- 命令名称:unzip。
- 英文原意:list, test and extract compressed files in a ZIP archive。
- 所在路径:/usr/bin/unzip.
- 执行权限:所有用户。
- 功能描述:列表、测试和提取压缩文件中的文件。
命令格式#
[root@localhost ~]# unzip [选项] 压缩包名
选项:
- -d: 指定解压缩位置
不论是文件压缩包,还是目录压缩包,都可以直接解压缩,例如:
[root@localhost ~]# unzip dir1.zip
Archive: dir1.zip
creating: dirl/
#解压缩
也可以手工指定解压缩位置,例如:
[root@localhost ~]# unzip -d /tmp/ ana.zip
Archive: ana.zip
inflating: /tmp/anaconda-ks.cfg
#把压缩包解压到指定位置
Linux gzip命令#
".gz"格式是 Linux 中最常用的压缩格式,使用 gzip 命令进行压缩,其基本信息如下:
- 命令名称:gzip。
- 英文原意:compress or expand files。
- 所在路径:/bin/gzip。
- 执行权限:所有用户。
- 功能描述:压缩文件或目录。
命令格式#
[root@localhost ~]# gzip [选项] 源文件
选项:
- -c:将压缩数据输出到标准输出中,可以用于保留源文件;
- -d:解压缩;
- -r:压缩目录;
- -v:显示压缩文件的信息;
- -数字:用于指定压缩等级,-1 压缩等级最低,压缩比最差;-9 压缩比最高。默认压缩比是 -6;
【例 1】基本压缩。
gzip 压缩命令非常简单,甚至不需要指定压缩之后的压缩包名,只需指定源文件名即可。我们来试试:
[root@localhost ~]# gzip install.log
#压缩instal.log 文件
[root@localhost ~]# ls
anaconda-ks.cfg install.log.gz install.log.syslog
#压缩文件生成,但是源文件也消失了
【例 2】保留源文件压缩。
在使用 gzip 命令压缩文件时,源文件会消失,从而生成压缩文件。这时有些人会有强迫症,就逼问笔者:能不能在压缩文件的时候,不让源文件消失?好吧,也是可以的,不过很别扭。
[root@localhost ~]# gzip -c anaconda-ks.cfg >anaconda-ks.cfg.gz
#使用-c选项,但是不让压缩数据输出到屏幕上,而是重定向到压缩文件中,#这样可以缩文件的同时不删除源文件
[root@localhost ~]# ls
anaconda-ks.cfg anaconda-ks.cfg.gz install.log.gz install.log.syslog
#可以看到压缩文件和源文件都存在
【例 3】 压缩目录。
我们可能会想当然地认为 gzip 命令可以压缩目录。 我们来试试:
[root@localhost ~]# mkdir test
[root@localhost ~]# touch test/test1
[root@localhost ~]# touch test/test2
[root@localhost ~]# touch test/test3 #建立测试目录,并在里面建立几个测试文件
[root@localhost ~]# gzip -r test/
#压缩目录,并没有报错
[root@localhost ~]# ls
anaconda-ks.cfg anaconda-ks.cfg.gz install.log.gz install.log.syslog test
#但是査看发现test目录依然存在,并没有变为压缩文件
[root@localhost ~]# ls test/
testl .gz test2.gz test3.gz
#原来gzip命令不会打包目录,而是把目录下所有的子文件分别压缩
在 Linux 中,打包和压缩是分开处理的。而 gzip 命令只会压缩,不能打包,所以才会出现没有打包目录,而只把目录下的文件进行压缩的情况。
Linux gunzip命令#
".gz"格式是 Linux 中最常用的压缩格式,如果要解压缩".gz"格式,那么使用"gzip-d压缩包"和"gunzip 压缩包"命令都可以。
我们先看看 gunzip 命令的基本信息。
- 命令名称:gunzip。
- 英文原意:compress or expand files。
- 所在路径:/bin/gunzip。
- 执行权限:所有用户。
- 功能描述:解压缩文件或目录。
常规用法就是直接解压缩文件,例如:
[root@localhost ~]# gunzip install.log.gz
如果要解压缩目录下的内容,则依然使用"-r"选项,例如:
[root@localhost ~]# gunzip -r test/
当然,"gunzip -r"依然只会解压缩目录下的文件,而不会解打包。要想解压缩".gz"格式,还可以使用 "gzip -d"命令,例如:
[root@localhost ~]# gzip -d anaconda-ks.cfg.gz
查看".gz"格式压缩的文本文件内容#
如果我们压缩的是一个纯文本文件,则可以直接使用 zcat 命令在不解压缩的情况下査看这个文本文件中的内容。例如:
[root@localhost ~]# zcat anaconda-ks.cfg.gz
Linux bzip2命令#
".bz2"格式是 Linux 的另一种压缩格式,从理论上来讲,".bz2"格式的算法更先进、压缩比更好;而 ".gz"格式相对来讲的时间更快。
".bz2"格式的压缩命令是 bzip2,我们来看看这个命令的基本信息。
- 命令名称:bzip2。
- 英文原意:a block-sorting file compressor。
- 所在路径:/usr/bin/bzip2。
- 执行权限:所有用户。
- 功能描述:.bz格式的压缩命令。
命令格式#
[root@localhost ~]# bzip2 [选项] 源文件
选项:
- -d:解压缩。
- -k:压缩时,保留源文件。
- -v:显示压缩的详细信息。
- -数字:这个参数和 gzip 命令的作用一样,用于指定压缩等级,-1 压缩等级最低,压缩比最差;-9 压缩比最高。
大家注意,gzip 只是不会打包目录,但是如果使用“-r”选项,则可以分别压缩目录下的每个文件;而 bzip2 命令则根本不支持压缩目录,也没有“-r”选项。
【例 1】基本压缩命令。
在压缩文件命令后面直接指定源文件即可,例如:
[root@localhost ~]# bzip2 anaconda-ks.cfg
#压缩成".bz2"格式
这个压缩命令依然会在压缩的同时删除源文件。
【例 2】压缩的同时保留源文件
bzip 命令可以直接使用"-k"选项来保留源文件,而不用像 gzip 命令一样使用输出重定向来保留源文件。例如:
[root@localhost ~]# bzip2 -k install.log.syslog
#压缩
[root@localhost ~]# ls
anaconda-ks.cfg.bz2 install.loginstalLlogsyslog install.logsyslogbz2
#压缩文件和源文件都存在
Linux bunzip命令#
".bz2"格式是 Linux 的另一种压缩格式,从理论上来讲,".bz2"格式的算法更先进、压缩比更好;而".gz"格式相对来讲的时间更快。
".bz2"格式可以使用"bzip2 -d 压缩包"命令来进行解压缩,也可以使用"bunzip2 压缩包"命令来进行解压缩。
先看看 bunzip2 命令的基本信息。
- 命令名称:bunzip2。
- 英文原意:a block-sorting file compressor。
- 所在路径:/usr/bin/bunzip2。
- 执行权限:所有用户。
- 功能描述:.bz2格式的解压缩命令。
命令格式#
[root@localhost ~]# bunzip2 [选项] 源文件
选项:
- -k:解压缩时,保留源文件
先试试使用 gunzip2 命令来进行解压缩,例如:
[root@localhost ~]# bunzip2 anaconda-ks.cfg.bz2
".bz2"格式也可以使用"bzip2 -d 压缩包"命令来进行解压缩,例如:
[root@localhost ~]# bzip2 -d install.log.syslog.bz2
査看".bz2"格式压缩的文本文件内容#
和".gz"格式一样,".bz2"格式压缩的纯文本文件也可以不解压缩直接査看,使用的命令是 bzcat。例如:
[root@localhost ~]# bzcat install.log.syslog.bz2
Linux tar命令#
".tar"格式的打包和解打包都使用 tar 命令,区别只是选项不同。我们先看看 tar 命令的基本信息。
- 命令名称:tar。
- 英文原意:tar。
- 所在路径:/bin/tar。
- 执行权限:所有用户。
- 功能描述:打包与解打包命令。
打包命令格式#
[root@localhost ~]#tar [选项] [-f 压缩包名] 源文件或目录
选项:
- -c:打包;
- -f:指定压缩包的文件名。压缩包的扩展名是用来给管理员识别格式的,所以一定要正确指定扩展名;
- -v:显示打包文件过程;
【例 1】基本使用。
我们先打包一个文件练练手。
[root@localhost ~]# tar -cvf anaconda-ks.cfg.tar anaconda-ks.cfg
#把anacondehks.cfg打包为 anacondehks.cfg.tar文件
选项"-cvf"一般是习惯用法,记住打包时需要指定打包之后的文件名,而且要用".tar"作为扩展名。那打包目录呢?我们也试试:
[root@localhost ~]# ll -d test/
drwxr-xr-x 2 root root 4096 6月 17 21:09 test/
#test是我们之前的测试目录
[root@localhost ~]# tar -cvf test.tar test/
test/
test/test3
test/test2
test/test1
#把目录打包为test.tar文件
tar命令也可以打包多个文件或目录,只要用空格分开即可。例如:
[root@localhost ~]# tar -cvf ana.tar anaconda-ks.cfg /tmp/
#把anaconda-ks.cfg文件和/tmp目录打包成ana.tar文件包
【例 2】打包压缩目录。
我们已经解释过了,压缩命令不能直接压缩目录,我们就先用 tar 命令把目录打成数据包,然后再用 gzip 命令或 bzip2 命令压缩。例如:
[root@localhost ~]#ll -d test test.tar
drwxr-xr-x 2 root root 4096 6月 17 21:09 test
-rw-r--r-- 1 root root 10240 6月 18 01:06 test.tar
#我们之前已经把test目录打包成test.tar文件
[root@localhost ~]# gzip test.tar
[root@localhost ~]# ll test.tar.gz
-rw-r--r-- 1 root root 176 6月 18 01:06 test.tar.gz
#gzip命令会把test.tar压缩成test.tar.gz
[root@localhost ~]# gzip -d test.tar.gz
#解压缩,把test.tar.gz解压缩为test.tar
[root@localhost ~]# bzip2 test.tar
[root@localhost ~]# ll test.tar.bz2
-rw-r--r-- 1 root root 164 6月 18 01:06 test.tar.bz2
#bzip2命令会把test.tar压缩为 test.tar.bz2格式
解打包命令格式#
".tar"格式的解打包也需要使用 tar 命令,但是选项不太一样。命令格式如下:
[root@localhost ~]#tar [选项] 压缩包
选项:
- -x:解打包;
- -f:指定压缩包的文件名;
- -v:显示打包文件过程;
- -t:测试,就是不解打包,只是査看包中有哪些文件;
- -C 目录:指定解打包位置;
其实解打包和打包相比,只是把打包选项"-cvf"更换为"-xvf"。我们来试试:
[root@localhost ~]# tar -xvf anaconda-ks.cfg. tar
#解打包到当前目录下
如果使用"-xvf"选项,则会把包中的文件解压到当前目录下。如果想要指定解压位置,则需要使用"-C(大写)"选项。例如:
[root@localhost ~]# tar -xvf test.tar -C /tmp
#把文件包test.tar解打包到/tmp/目录下
如果只想査看文件包中有哪些文件,则可以把解打包选项"-x"更换为测试选项"-t"。例如:
[root@localhost ~]# tar -tvf test.tar
drwxr-xr-x root/root 0 2016-06-17 21:09 test/
-rw-r-r- root/root 0 2016-06-17 17:51 test/test3
-rw-r-r- root/root 0 2016-06-17 17:51 test/test2
-rw-r-r- root/root 0 2016-06-17 17:51 test/test1
#会用长格式显示test.tar文件包中文件的详细信息
".tar.gz"和".tar.bz2" 格式#
你可能会觉得 Linux 实在太不智能了,一个打包压缩,居然还要先打包成".tar"格式,再压缩成".tar.gz"或".tar.bz2"格式。其实 tar 命令是可以同时打包压缩的,前面的讲解之所打包和压缩分开,是为了让大家了解在 Linux 中打包和压缩的不同。
使用 tar 命令直接打包压缩。命令格式如下:
[root@localhost ~]#tar [选项] 压缩包 源文件或目录
选项:
- -z:压缩和解压缩 ".tar.gz"格式
- -j:压缩和街压缩 ".tar.bz2"格式
【例 1】压缩与解压缩 ".tar.gz"格式。
我们先来看看如何压缩".tar.gz"格式:
[root@localhost ~]# tar -zcvf tmp.tar.gz /tmp/
#把/temp/目录直接打包压缩为".tar.gz"格式,通过"-z"来识别格式,"-cvf"和打包选项一致
解压缩也只是在解打包选项"-xvf"前面加了一个"-z"选项。
[root@localhost ~]# tar -zxvf tmp.tar.gz
#解压缩与解打包".tar.gz"格式
前面讲的选项"-C"用于指定解压位置、"-t"用于査看压缩包内容,在这里同样适用。
【例 2】压缩与解压缩".tar.bz2"格式。
和".tar.gz"格式唯一的不同就是"-zcvf"选项换成了 "-jcvf"。
[root@localhost ~]# tar -jcvf tmp.tar.bz2 /tmp/
#打包压缩为".tar.bz2"格式,注意压缩包文件名
[root@localhost ~]# tar -jxvf tmp.tar.bz2
#解压缩与解打包".tar.bz2"格式
把文件直接压缩成".tar.gz"和".tar.bz2"格式,才是 Linux 中最常用的压缩方式,这是大家一定要掌握的压缩和解压缩方法。
Linux sync命令#
当我们在计算机上保存数据的时候,其实是先在内存中保存一定时间,再写入硬盘。这其实是一种缓存机制,当在内存中保存的数据需要被读取的时候,从内存中读取要比从硬盘中读取快得多。
不过,这也会带来一些问题,如果数据还没有来得及保存到硬盘中,就发生了突然岩机(比如断电)的情况,数据就会丟失。
sync 命令的作用就是把内存中的数据强制向硬盘中保存。这个命令在常规关机的命令中其实会自动执行,但如果不放心,则应该在关机或重启之前手工执行几次,避免数据丟失。
sync 命令的信息如下:
- 命令名称:sync。
- 英文原意:flush file system buffers。
- 所在路径:/bin/sync。
- 执行权限:所有用户。
- 功能描述:刷新文件系统缓冲区。
sync 命令直接执行就可以了,不需要任何选项。
[root@localhost ~]# sync
记得关机或重启之前多执行几次 sync 命令,多一重保险总是好的。
Linux shutdown命令#
在早期的 Linux 系统中,应该尽量使用 shutdown 命令来进行关机和重启。因为在那时的 Linux 中,只有 shutdown 命令在关机或重启之前会正确地中止进程及服务,所以我们一直认为 shutdown 才是最安全的关机与重启命令。
而在现在的系统中,一些其他的命令(如 reboot)也会正确地中止进程及服务,但我们仍建议使用 shutdown 命令来进行关机和重启。
shutdown 命令的基本信息如下。
- 命令名称:shutdown。
- 英文原意:bring the system down。
- 所在路径:/sbin/shutdown。
- 执行权限:超级用户。
- 功能描述:关机和重启
命令格式#
[root@localhost ~]# shutdown [选项] 时间 [警告信息]
选项:
- -c:取消已经执行的 shutdown 命令;
- -h:关机;
- -r:重启;
【例 1】重启与定时重启。
先来看看如何使用 shutdown 命令进行重启:
[root@localhost ~]# shutdown -r now
#重启, now是现在重启的意思
[root@localhost ~]# shutdown -r 05:30
#指定时间重启,但会占用前台终端
[root@localhost ~]# shutdown -r 05:30 &
#把定义重启命令放入后台,&是后台的意思
[root@localhost ~]# shutdown -c
//取消定时重启
[root@localhost ~]# shutdown -r +10
#10分钟之后重启
【例 2】关机和定时关机。
[root@localhost ~]# shutdown -h now
#现在关机
[root@localhost ~]# shutdown -h 05:30
#指定时间关机
Linux关机和重启命令#
说到关机和重启,很多人认为,重要的服务器(比如银行的服务器、电信的服务器)如果重启了,则会造成大范围的灾难。笔者在这里解释一下。
首先,就算是银行或电信的服务器,也不是不需要维护,而是依靠备份服务器代替。其次,每个人的经验都是和自己的技术成长环境息息相关的。比如笔者是游戏运维出身,而游戏又是数据为王,所以一切操作的目的就是保证数据的可靠和安全。这时,有计划的重启远比意外岩机造成的损失要小得多,所以定义重启是游戏运维的重要手段。
shutdown命令#
在早期的 Linux 系统中,应该尽量使用 shutdown 命令来进行关机和重启。因为在那时的 Linux 中,只有 shutdown 命令在关机或重启之前会正确地中止进程及服务,所以我们一直认为 shutdown 才是最安全的关机与重启命令。
而在现在的系统中,一些其他的命令(如 reboot)也会正确地中止进程及服务,但我们仍建议使用 shutdown 命令来进行关机和重启。
shutdown 命令的基本信息如下。
- 命令名称:shutdown。
- 英文原意:bring the system down。
- 所在路径:/sbin/shutdown。
- 执行权限:超级用户。
- 功能描述:关机和重启
命令格式#
[root@localhost ~]# shutdown [选项] 时间 [警告信息]
选项:
- -c:取消已经执行的 shutdown 命令;
- -h:关机;
- -r:重启;
【例 1】重启与定时重启。
先来看看如何使用 shutdown 命令进行重启:
[root@localhost ~]# shutdown -r now
#重启, now是现在重启的意思
[root@localhost ~]# shutdown -r 05:30
#指定时间重启,但会占用前台终端
[root@localhost ~]# shutdown -r 05:30 &
#把定义重启命令放入后台,&是后台的意思
[root@localhost ~]# shutdown -c
//取消定时重启
[root@localhost ~]# shutdown -r +10
#10分钟之后重启
【例 2】关机和定时关机。
[root@localhost ~]# shutdown -h now
#现在关机
[root@localhost ~]# shutdown -h 05:30
#指定时间关机
reboot命令#
在现在的系统中,reboot 命令也是安全的,而且不需要加入过多的选项。
[root@localhost ~]# reboot
#重启
halt和poweroff命令#
这两个都是关机命令,直接执行即可。
[root@localhost ~】# halt
#关机
[root@localhost ~】# poweroff
#关机
init命令#
init 是修改 Linux 运行级别的命令,也可以用于关机和重启。
[root@localhost~]# init 0
#关机,也就是调用系统的 0 级别
[root@localhost ~】# init 6
#重启,也就是调用系统的 6 级别
Linux setup命令#
Linux 当然也需要配置 IP 地址才可以正常使用网络。其实 Linux 主要是通过修改网卡配置文件来永久修改 IP 地址的。setup 是一个简化命令,是 Red Hat 系列专有的命令,其他的 Linux 系列不一定有此命令。
setup 命令的基本信息如下。
- 命令名称:setup。
- 英文原意:A text mode system configuration tool。
- 所在路径:/usr/bin/setup。
- 执行权限:所有用户。
- 功能描述:系统配置工具。
setup 命令会开启一个图形化的配置工具,如图 1 所示。

图 1 配置工具界面
这是一个综合工具,既可以配置 IP 地址,也可以管理防火墙和系统服务。如果我们需要配置 IP 地址,则只要选择"网络配置"就会开始 IP 地址配置。
接写来就可以执行动作选择了。我们要配置 IP 地址,就选择"设备配置",如图 2 所示。

图 2 选择动作
在 CentOS 6.x 中,网卡的设备文件名用 eth0 来表示第一块网卡,如果有第二块网卡,则设备文件名会依次为 eth1。在这里,我们的 Linux 只有一块网卡,所以在选择设备时只需选择 eth0 网卡配置即可,如图 3 所示。

图 3 选择设备
接下来就会进入网络配置界面,如图 4 所示。这时如果在"使用 DHCP"选项上输入"*"号(空格输入),就会自动获取 IP 地址;取消"*"号,就会手工分配 IP 地址。

图 4 网络配置
输入正确的 IP 地址后,使用 Tab 键切换至"确定"按钮上,接下来一路保存退出,IP 地址就输入完成了。
但是,如果想让 IP 地址配置生效,则还需要重启网络服务。
[root@localhost ~]# service network restart
#重启网络服务
当然,重启网络服务有很多种方法,这里直接使用 service 命令进行网络服务重启。
手工开启网卡#
在 CentOS 5.x 以前的系统中,通过 setup 配置 IP 地址,重启后,IP 地址就可以配置成功。但如果是在 CentOS 6.x 中,那么重启后可能依然无法找到 eth0 网卡,而只能看到 lo(本地回环)网卡。例如:
[root@localhost ~]# ifconfig
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:16436 Metric:1
RX packets:12 errors:0 dropped:0 overruns:0 frame:0
TX packets:12 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0
RX bytes:840 (840.0 b) TX bytes:840 (840.0 b)
#只有lo网卡,没有eth0网卡
这是因为,在 CentOS 6.x 中,eth0 网卡是默认没有开启的,需要修改网卡配置文件手工开启。例如:
[root@localhost ~]# vi /etc/sysconfig/network-scripts/ ifcfg-eth0
ONBOOT=no
…省略部分内容...
#在网卡配置文件中,ONBOOT默认是no
手工把 ONBOOT 选项改为 yes,然后再重启网络服务(service network restart),就会发现 eth0 网卡启动了,IP 地址也可以正常使用了。
Linux ifconfig命令(5.7里面没有了)#
ifconfig 是 Linux 中査看和临时修改 IP 地址的命令,其基本信息如下:
- 命令名称:ifconfig。
- 英文原意:configure a network interface。
- 所在路径:/sbin/ifconfig。
- 执行权限:超级用户。
- 功能描述:配置网络接口。
查看IP地址信息#
ifconfig 命令最主要的作用就是査看 IP 地址的信息,直接输入ifconfig命令即可。
[root@localhost ~]# ifconfig
eth0 Link encap:Ethernet HWaddr 00:OC:29:C5:FB:AA #eth0网卡信息 网络类型为以太网 MAC地址
inet addr:192.168.44.3 Beast:192.168.44.255 Mask:255.255.255.0
#IP地址 广播地址 子网掩码
inet6 addr: fe80::20c:29ff:fec5:fbaa/64 Scope:Link #IPv6的地址(目前不生效)
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1 #网络参数 最大传输单元数据包转送次数
RX packets:881 errors:0 dropped:0 overruns:0 frame:0
#接收到的数据包惰况
TX packets:8S3 errors:0 dropped:0 overruns:0 carrier:0
#发送的数据包情况
collisions:0 txqueuelen:1000
#数据包碰撞 数据缓冲区长度
RX bytes:82229 (80.3 KiB) TX bytes:273463 (267.0 KiB)
#接收包的大小 发送包的大小
Interrupt:19 Base address:0x2000
#IRQ中街 内存地址
lo Link encap:Local Loopback
#本地回环网卡信息
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:16436 Metric:1
RX packets:12 errors:0 dropped:0 overruns:0 frame:0
TX packets:12 errors:0 dropped:0 overruns:0 carrier:0 collisions:0 txqueuelen:0
RX bytes:840 (840.0 b) TX bytes:840 (840.0 b)
ifconfig 命令主要用于査看 IP 地址、子网掩码和 MAC 地址这三类信息,其他信息我们有所了解即可。
lo 网卡是 Loopback 的缩写,也就是本地回环网卡,这个网卡的 IP 地址是 127.0.0.1。它只代表我们的网络协议正常,就算不插入网线也可以 ping 通,所以基本没有实际使用价值,大家了解一下即可。
临时配置 IP 地址#
ifconfig 命令除可以査看 IP 地址之外,还可以临时配置 IP 地址,但是一旦重启,IP 地址就会失效,所以我们还是应该使用 setup 命令进行 IP 地址配置。使用 ifconfig 命令临时配置 IP 地址的示例如下:
[root@localhost ~]#ifconfig eth0 192.168.44.3
#配置IP地址,不指定子网掩码就会使用标准子网掩码
[root@localhost ~]#ifconfig eth0 192.168.44.3 netmask 255.255.255.0
#配置IP地址,同时配置子网掩码
Linux ping命令#
ping 是常用的网络命令,主要通过 ICMP 协议进行网络探测,测试网络中主机的通信情况。
ping 命令的基本信息如下。
- 命令名称:ping。
- 英文原意:send ICMP ECHO_REQUEST to network hosts。
- 所在路径:/bin/ping。
- 执行权限:所有用户。
- 功能描述:向网络主机发送 ICMP 请求。
命令的基本格式如下:
[root@localhost ~]# ping [选项] IP
选项:
- -b: 后面加入广播地址,用于对整个网段进行探测;
- -c 次数: 用于指定 ping 的次数;
- -s 字节: 指定探测包的大小;
【例 1】 探测与指定主机通信。
[root@localhost ~]#ping 192.168.103.151
PING 192.168.103.151 (192.168.103.151) 56(84) bytes of data.
64 bytes from 192.168.103.151: icmp_seq=1 ttl=128 time=0.300 ms
64 bytes from 192.168.103.151: icmp_seq=2 ttl=128 time=0.481 ms
…省略部分内容...
#探测与指定主机是否通信
Linux是一个比较实在的操作系统,这个 ping 命令如果不使用"Ctrl+C"快捷键强行中止,就会一直 ping 下去,直到天荒地老……
【例 2】指定 ping 的次数。
既然 ping 这么"实在",如果不想一直 ping 下去,则可以使用"-c"选项指定 ping 的次数。例如:
[root@localhost ~]# ping -c 3 192.168.103.151
#只探测3次,就中止ping命令
【例 3】 探测网段中的可用主机。
在 ping 命令中,可以使用"-b"选项,后面加入广播地址,探测整个网段。我们可以使用这个选项知道整个网络中有多少主机是可以和我们通信的,而不用一个一个 IP 进行探测。例如:
[root@localhost ~]# ping -b -c 3 192.168.103.255
WARNING: pinging broadcast address
PING 192.168.103.255 (192.168.103.255) 56(84) bytes of data.
64 bytes from 192.168.103.199: icmp_seq=1 ttl=64 time=1.95ms
64 bytes from 192.168.103.168: icmp_seq=1 ttl=64 time=1.97ms(DUP!)
64 bytes from 192.168.103.252: icmp_seq=1 ttl=64 time=2.29ms(DUP!)
…省略部分内容...
#探测192.168.103.0/24网段中有多少可以通信的主机
linux netstat命令#
我们需要先简单了解一下端口的作用。在互联网中,如果 IP 地址是 IP 服务器在互联网中唯一的地址标识,那么大家可以想象一下:我有一台服务器,它有固定的公网 IP 地址,通过 IP 地址可以找到我的服务器。但是我的服务器中既启动了网页服务(Web 服务),又启动了文件传输服务(FTP 服务),那么你的客户端访问我的服务器,到底应该如何确定你访问的是哪一个服务呢?
端口就是用于网络通信的接口,是数据从传输层向上传递到应用层的数据通道。我们可以理解为每个常规服务都有默认的端口号,通过不同的端口号,我们就可以确定不同的服务。也就是说,客户端通过 IP 地址访问到我的服务器,如果数据包访问的是 80 端口,则访问的是 Web 服务;而如果数据包访问的是 21 端口,则访问的是 FTP 服务。
我们可以简单地理解为每个常规服务都有一个默认端口(默认端口可以修改),这个端口是所有人都知道的,客户端可以通过固定的端口访问指定的服务。而我们通过在服务器中查看已经开启的端口号,就可以判断服务器中开启了那些服务。
netstat 是网络状态查看命令,既可以查看到本机开启的端口,也可以查看有哪些客户端连接。netstat 命令的基本信息如下。
- 命令名称:netstat。
- 英文原意:Print network connections, routing tables, interface statistics, masquerade connections, and multicast memberships。
- 所在路径:/bin/netstat.
- 执行权限:所有用户。
- 功能描述:输出网络连接、路由表、接口统计、伪装连接和组播成员。
命令格式如下:
[root@localhost ~]# netstat [选项]
选项:
- -a:列出所有网络状态,包括 Socket 程序;
- -c秒数:指定每隔几秒刷新一次网络状态;
- -n:使用 IP 地址和端口号显示,不使用域名与服务名;
- -p:显示 PID 和程序名;
- -t:显示使用 TCP 协议端口的连接状况;
- -u:显示使用 UDP 协议端口的连接状况;
- -I:仅显示监听状态的连接;
- -r:显示路由表;
【例 1】查看本机开启的端口。
这是本机最常用的方式,使用选项"-tuln"。因为使用了"-I"选项,所以只能看到监听状态的连接,而不能看到已经连接状态的连接。例如:
[root@localhost ~]# netstat -tuln
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address Foreign Address State
tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN
tcp 0 0 0.0.0.0:11211 0.0.0.0:* LISTEN
tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN
tcp 0 0:::11211 :::* LISTEN
tcp 0 0 :::80 :::* LISTEN
tcp 0 0 :::22 :::* LISTEN
udp 0 0 0.0.0.0:11211 0.0.0.0:*
udp 0 0:::11211 :::*
#协议接收队列发送队列本机的 IP 地址及端口号 远程主机的 IP 地址及端口号 状态
这个命令的输出较多。
1) Proto:网络连接的协议,一般就是 TCP 协议或者 UDP 协议。
2) Recv-Q:表示接收到的数据,已经在本地的缓冲中,但是还没有被进程取走。
3) Send-Q:表示从本机发送,对方还没有收到的数据,依然在本地的缓冲中,不具备 ACK 标志的数据包。
4) Local Address:本机的 IP 地址和端口号。
5) ForeignAddress:远程主机的 IP 地址和端口号。
6) State:状态。常见的状态主要有以下几种。
- -LISTEN:监听状态,只有 TCP 协议需要监听,而 UDP 协议不需要监听。
- -ESTABLISHED:已经建立连接的状态。如果使用"-I"选项,则看不到已经建立连接的状态。
- -SYN_SENT:SYN 发起包,就是主动发起连接的数据包。
- -SYN_RECV:接收到主动连接的数据包。
- -FIN_WAIT1:正在中断的连接。
- -FIN_WAIT2:已经中断的连接,但是正在等待对方主机进行确认。
- -TIME_WAIT:连接已经中断,但是套接字依然在网络中等待结束。
- -CLOSED:套接字没有被使用。
在这些状态中,我们最常用的就是 LISTEN 和 ESTABLISHED 状态,一种代表正在监听,另一种代表已经连接。
【例 2】查看本机有哪些程序开启的端口。
如果使用"-p"选项,则可以查看到是哪个程序占用了端口,并且可以知道这个程序的 PID。例如:
[root@localhost ~]# netstat -tulnp
Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address Foreign Address State PID/Program name
tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN 2359/mysqld
tcp 0 0 0.0.0.0:11211 0.0.0.0:* LISTEN 1563/memcached
tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN 1490/sshd
tcp 0 0 :::11211 :::* LISTEN 1563/memcached
tcp 0 0 :::80 :::* LISTEN 21025/httpd
tcp 0 0 :::22 :::*
LISTEN 1490/sshd
udp 0 0 0.0.0.0:11211 0.0.0.0:* 1563/memcached
udp 0 0:::11211 :::* 1563/memcached
#比之前的命令多了一个"-p"选项,结果多了可以知道是哪个程序占用了端口
【例 3】 查看所有连接。
使用选项"-an"可以查看所有连接,包括监听状态的连接(LISTEN)、已经建立连接状态的连接(ESTABLISHED)、Socke 程序连接等。因为连接较多,所以输出的内容有很多。例如:
[root@localhost ~]# netstat -an
Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address Foreign Address State
tcp 0 0 0.0.0.0:3306 0.0.0.0:* LISTEN
tcp 0 0 0.0.0.0:11211 0.0.0.0:* LISTEN
tcp 0 0 117.79.130.170:80 78.46.174.55:58815 SYN_RECV
tcp 0 0 0.0.0.0:22 0.0.0.0:* LISTEN
tcp 0 0 117.79.130.170:22 124.205.129.99:10379 ESTABLISHED
tcp 0 0 117.79.130.170:22 124.205.129.99:11811 ESTABLISHED
...省略部分内容...
udp 0 0 0.0.0.0:11211 0.0.0.0:*
udp 0 0:::11211 :::*
Active UNIX domain sockets (servers and established)
Proto RefCnt Flags Type State I-Node Path
unix 2 [ACC] STREAM LISTENING 9761 @/var/run/hald/dbus-fr41WkQn1C
…省略部分内容...
从"Active UNIX domain sockets"开始,之后的内容就是 Socke 程序产生的连接,之前的内容都是网络服务产生的连接。我们可以在"-an"选项的输出中看到各种网络连接状态,而之前的"-tuln"选项则只能看到监听状态。
Linux write命令#
在服务器上,有时会有多个用户同时登录,一些必要的沟通就显得尤为重要。比如,我必须关闭某个服务,或者需要重启服务器,当然需要通知同时登录服务器的用户,这时就可以使用 write 命令。
write 命令的信息如下:
- 命令名称:write。
- 英文原意:send a message to another user。
- 所在路径:/usr/bin/write。
- 执行权限:所有用户。
- 功能描述:向其他用户发送信息。
write 命令的基本格式如下:
[root@localhost ~]# write 用户名 [终端号]
write 命令没有多余的选项,我们要向在某个终端登录的用户发送信息,就可以这样来执行命令:
[root@localhost ~]#write user1 pts/1
hello
I will be in 5 minutes to restart, please save your data
#向在pts/1 (远程终端1)登录的user1用户发送信息,使用"Ctrl+D"快捷键保存发送的数据
这时,user1 用户就可以收到你要在 5 分钟之后重启系统的信息了。
Linux mail命令#
mail 是 Linux 的邮件客户端命令,可以利用这个命令给其他用户发送邮件。
mail 命令的基本信息如下。
- 命令名称:mail。
- 英文原意:send and receive Internet mail。
- 所在路径:/bin/mail。
- 执行权限:所有用户。
- 功能描述:发送和接收电子邮件。
【例 1】发送邮件。
如果我们想要给其他用户发送邮件,则可以执行如下命令:
[root@localhost ~]# mail userl
Subject: hello <-邮件标题
Nice to meet you! <-邮件具体内容
. <-使用.来结束邮件输入
#发送邮件给user1用户
我们接收到的邮件都保存在"/var/spod/mail/用户名"中,每个用户都有一个以自己的用户名命名的邮箱。
【例 2】发送文件内容。
如果我们想把某个文件的内容发送给指定用户,则可执行如下命令:
[root@localhost ~]# mail -s "test mail" root </root/ anaconda-ks.cfg
#把/root/anaconda-ks.cfg文件的内容发送给root用户
选项:
-s: 指定邮件标题
我们在写脚本时,有时需要脚本自动发送一些信息给指定用户,把要发送的信息预先写到文件中,是一个非常不错的选择。
【例 3】查看已经接收的邮件。
我们可以直接在命令行中执行 mail 命令,进入 mail 的交互命令中,可以在这里査看已经接收到的邮件。例如:
[root@localhost ~]# mail
Heirloom Mail version 12.4 7/29/08.Type ?for help.
"/var/spool/mail/root": 1 message 1 new
>N 1 root Mon Dec 5 22:45 68/1777 "test mail"<-之前收到的由件
>N 2 root Mon Dec 5 23:08 18/602 "hello"
#未阅读编号发件人 时间 标题
&
<-等待用户输入命令
可以看到已经接收到的邮件列表,"N"代表未读邮件,如果是已经阅读过的邮件,则前面是不会有这个"N"的;之后的数字是邮件的编号,我们主要通过这个编号来进行邮件的操作。如餓们想要査看第1邮件,则只需输入邮件的编号"1"就可以了》
在交互命令中执行"?",可以查看这个交互界面支持的命令。例如:
&? <-输入命令
mail commands
type<message list> type messages
next goto and type next message
from<message list> give head lines of messages
headers print out active message headers
delete<message list> delete messages
undelete<message list> undelete messages
save<message list> folder append messages to folder and mark as saved
copy<message list> folder append messages to folder without marking them
write<message list> file append message texts to file, save attachments
preserve<message list> keep incoming messages in mailbox even if saved
Reply <message list> reply to message senders
reply<message list> reply to message senders and all recipients
mail addresses mail to specific recipients
file folder change to another folder
quit quit and apply changes to folder
xit quit and discard changes made to folder
! shell escape
cd<directory> chdir to directory or home if none given
list list names of all available commands
这些交互命令是可以简化输入的,比如"headers"命令,就可以直接输入"h",这是列出邮件标题列表的命令。我们解释一下常用的交互命令。
- headers:列出邮件标题列表,直接输入"h"命令即可。
- delete:删除指定邮件。比如想要删除第二封邮件,可以输入"d2"。
- save:保存邮件。可以把指定邮件保存成文件,如"s 2/tmp/test.mair。
- quit:退出,并把已经操作过的邮件进行保存。比如移除已删除邮件,保存已阅读邮脾。
- exit:退出,但是不保存任何操作。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· 10年+ .NET Coder 心语 ── 封装的思维:从隐藏、稳定开始理解其本质意义
· 地球OL攻略 —— 某应届生求职总结
· 提示词工程——AI应用必不可少的技术
· Open-Sora 2.0 重磅开源!
· 周边上新:园子的第一款马克杯温暖上架