文件与目录管理

[TOC]

目录相关操作

. 代表此层目录
.. 代表上一层目录

  • 代表前一个工作目录
    ~ 代表“目前使用者身份”所在的主文件夹
    ~account 代表 account 这个使用者的主文件夹(account是个帐号名称)

pwd命令

1
2
3
4
5
6
7
8
9
10
11
#显示所在目录
root@study ~]# pwd [-P]
-P :显示出确实的路径,而非使用链接 (link) 路径。

[root@study mail]# ls -ld /var/mail
lrwxrwxrwx. 1 root root 10 May 4 17:51 /var/mail -> spool/mail
[root@study ~]# cd /var/mail
[root@study mail]# pwd
/var/mail <==列出目前的工作目录
[root@study mail]# pwd -P
/var/spool/mail

mkdir 创建目录

1
2
3
root@study ~]# mkdir [-p] 目录名
-p : 创建层级目录
mkdir -p /home/windus/test/linux

ls命令

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
	选项与参数:
-a :全部的文件,连同隐藏文件( 开头为 . 的文件) 一起列出来(常用)
-A :全部的文件,连同隐藏文件,但不包括 . 与 .. 这两个目录
-d :仅列出目录本身,而不是列出目录内的文件数据(常用)
-f :直接列出结果,而不进行排序 (ls 默认会以文件名排序!)
-F :根据文件、目录等信息,给予附加数据结构,例如:
*:代表可可执行文件; /:代表目录; =:代表 socket 文件; |:代表 FIFO 文件;
-h :将文件大小以人类较易读的方式(例如 GB, KB 等等)列出来;
-i :列出 inode 号码,inode 的意义下一章将会介绍;
-l :长数据串行出,包含文件的属性与权限等等数据;(常用)
字段说明:
1.文件属性:drwxr-xr-x
2.文件硬链接数量 3
3.所有者:user
4.所属用户组:group
5.文件大小:102 byte
6.修改时间:Mar11 22:56
7.文件名:Filename
-n :列出 UID 与 GID 而非使用者与群组的名称 (UID与GID会在帐号管理提到!)
-r :将排序结果反向输出,例如:原本文件名由小到大,反向则为由大到小;
-R :连同子目录内容一起列出来,等于该目录下的所有文件都会显示出来;
-S :以文件大小大小排序,而不是用文件名排序;
-t :依时间排序,而不是用文件名。
--color=never :不要依据文件特性给予颜色显示;
--color=always :显示颜色
--color=auto :让系统自行依据设置来判断是否给予颜色
--full-time :以完整时间模式 (包含年、月、日、时、分) 输出
--time={atime,ctime} :输出 access 时间或改变权限属性时间 (ctime)而非内容变更时间 (modification time)

cp命令

1
2
3
4
5
6
7
8
9
10
选项与参数:
-a :相当于 -dr --preserve=all 的意思,至于 dr 请参考下列说明;(常用)
-d :若来源文件为链接文件的属性(link file),则复制链接文件属性而非文件本身;
-i :若目标文件(destination)已经存在时,在覆盖时会先询问动作的进行(常用)
-l :进行硬式链接(hard link)的链接文件创建,而非复制文件本身;
-p :连同文件的属性(权限、用户、时间)一起复制过去,而非使用默认属性(备份常用);
-r :递回持续复制,用于目录的复制行为;(常用)
-s :复制成为符号链接文件 (symbolic link),亦即“捷径”文件;
-u :destination 比 source 旧才更新 destination,或 destination 不存在的情况下才复制。
--preserve=all :除了 -p 的权限相关参数外,还加入 SELinux 的属性, links, xattr 等也复制了。

rmdir命令

1
2
3
root@study ~]# rmdir [-p] 目录名称
选项与参数:
-p :连同“上层”“空的”目录也一起删除

rm命令

1.在指令前加上反斜线,可以忽略掉 alias 的指定选项喔!^[详见bash章节]
2.删除一个带有 - 开头的文件。(因为“-”是选项,所以系统误判了!

1
2
3
4
5
6
#错误
[root@study tmp]# rm -aaa-
rm: invalid option -- 'a‘
#正确 rm --help查找
[root@study tmp]# rm ./-aaa-
[root@study tmp]# rm -- -aaa-

mv命令

1
2
3
4
选项与参数:
-f :force 强制的意思,如果目标文件已经存在,不会询问而直接覆盖;
-i :若目标文件 (destination) 已经存在时,就会询问是否覆盖!
-u :若目标文件已经存在,且 source 比较新,才会更新 (update)

特殊用处:
1.文件更名(类似命令rename)
2.可同时移动多个文件到同一目录

rename命令

1
2
3
4
5
6
参数:
原字符串:将文件名需要替换的字符串;
目标字符串:将文件名中含有的原字符替换成目标字符串;
文件:指定要改变文件名的文件列表
#
[root@study tmp]# rename .htm .html *.htm

basename

获取文件/目录名

1
2
3
4
5
6
7
8
9
10
选项:
-a, --multiple support multiple arguments and treat each as a NAME
-s, --suffix=SUFFIX remove a trailing SUFFIX
-z, --zero separate output with NUL rather than newline

#例子
basename /usr/bin/sort -> "sort"
basename include/stdio.h .h -> "stdio"
basename -s .h include/stdio.h -> "stdio"
basename -a any/str1 any/str2 -> "str1" followed by "str2"

dirname

1
2
3
4
#例子
dirname /usr/bin/ -> "/usr"
dirname dir1/str dir2/str -> "dir1" followed by "dir2"
dirname stdio.h -> "."

文件内容审阅

cat命令

由第一行开始显示内容(与tac相反)

1
2
3
4
5
6
7
选项与参数:
-A :相当于 -vET 的整合选项,可列出一些特殊字符而不是空白而已;
-b :列出行号,仅针对非空白行做行号显示,空白行不标行号!
-E :将结尾的断行字符 $ 显示出来;
-n :打印出行号,连同空白行也会有行号,与 -b 的选项不同;
-T :将 [tab] 按键以 ^I 显示出来;
-v :列出一些看不出来的特殊字符

nl指令

添加行号打印,默认不打印空行行号.“其默认的结果与 cat -n 有点不太一样, nl 可以将行号做比较多的显示设计,包括位数与是否自动补齐 0 等等的功能呢。

1
2
3
4
5
6
7
8
9
10
11
12
nl [选项]... [文件]...
-b  :指定行号指定的方式,主要有两种:
-b a :表示不论是否为空行,也同样列出行号(类似 cat -n);
-b t :如果有空行,空的那一行不要列出行号(默认值);
-n  :列出行号表示的方法,主要有三种:
-n ln :行号在萤幕的最左方显示;
-n rn :行号在自己栏位的最右方显示,且不加 0 ;
-n rz :行号在自己栏位的最右方显示,且加 0 ;
-w  :行号栏位的占用的位数。(与-n ln 或 -n rz配合使用)
-p 在逻辑定界符处不重新开始计算。

$ nl -n ln -w 3 test.txt

可翻页检视 more / less

两者区别在于前者不能向前翻页(管线操作),后者可以向前翻页并支持更多其它操作

数据撷取

- head 撷取前面几行
- tail 取出后几行,默认10行  
***注意:当用-f |grep 选项时,默认会有缓存区不能及时显示可加--line-buffered***
1
2
3
例题:
假如我想要显示 /etc/man_db.conf 的第 11 到第 20 行呢?
head -n 20 /etc/man_db.conf | tail -n 10

非纯文本文件 od

1
2
3
4
5
6
7
8
选项或参数:
-t :后面可以接各种“类型 (TYPE)”的输出,例如:
a :利用默认的字符来输出;
c :使用 ASCII 字符来输出
d[size] :利用十进制(decimal)来输出数据,每个整数占用 size Bytes ;
f[size] :利用浮点数值(floating)来输出数据,每个数占用 size Bytes ;
o[size] :利用八进位(octal)来输出数据,每个整数占用 size Bytes ;
x[size] :利用十六进制(hexadecimal)来输出数据,每个整数占用 size Bytes ;

如果对纯文本文件使用这个指令,你甚至可以发现到 ASCII 与字符的对照表!
例题:想要立刻找到 password 这几个字的 ASCII 对照,该如何通过 od 来判断?
答:
echo password | od -t oCc

文件时间

  • modification time (mtime):
    当该文件的“内容数据”变更时,就会更新这个时间!内容数据指的是文件的内容,而不是文件的属性或权限喔!
  • status time (ctime):
    当该文件的“状态 (status)”改变时,就会更新这个时间,举例来说,像是权限与属性被更改了,都会更新这个时间啊。
  • access time (atime):
    当“该文件的内容被取用”时,就会更新这个读取时间 (access)。举例来说,我们使用 cat 去读取 /etc/man_db.conf , 就会更新该文件的 atime 了。

修改文件时间 touch命令

1
2
3
4
5
6
选项与参数:
-a :仅修订 access time;
-c :仅修改文件的时间,若该文件不存在则不创建新文件;
-d :后面可以接欲修订的日期而不用目前的日期,也可以使用 --date="日期或时间"
-m :仅修改 mtime ;
-t :后面可以接欲修订的时间而不用目前的时间,格式为[YYYYMMDDhhmm].

该命令也可用来新建文件

file命令

查看某个文件的基本数据类型,如:ASCII/data文件/binary文件等等信息,也可用来判断tar包文件是用哪种压缩功能打包的.

##文件与文件夹权限
在Linux传统的Ext2/Ext3/Ext4文件系统下,我们还可以设置其他的系统隐藏属性, 这部份可使用 chattr 来设置,而以 lsattr 来查看,最重要的属性就是可以设置其不可修改的特性!让连文件的拥有者都不能进行修改! 这个属性可是相当重要的,尤其是在安全机制上面 (security)!比较可惜的是,在 CentOS 7.x 当中利用 xfs 作为默认文件系统, 但是 xfs 就没有支持所有的 chattr 的参数了!仅有部份参数还有支持而已!

文件默认权限 umask

umask 的分数指的是“该默认值需要减掉的权限!

  • 若使用者创建为“文件”则默认“没有可执行( x )权限”,亦即只有 rw 这两个项目,也就是最大为 666 分,默认权限如下:-rw-rw-rw-

  • 若使用者创建为“目录”,则由于 x 与是否可以进入此目录有关,因此默认为所有权限均开放,亦即为 777 分,默认权限如下:drwxrwxrwx

1
2
3
4
5
[root@study ~]# umask
0022 <==与一般权限有关的是后面三个数字!
[root@study ~]# umask -S
u=rwx,g=rx,o=rx
[root@study ~]# umask 022 <==设置默认权限

文件隐藏属性 chattr

chattr指令只能在Ext2/Ext3/Ext4的 Linux 传统文件系统上面完整生效, 其他的文件系统可能就无法完整的支持这个指令了,例如 xfs 仅支持部份参数而已

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
[root@study ~]# chattr [+-=][ASacdistu] 文件或目录名称
选项与参数:
+ :增加某一个特殊参数,其他原本存在参数则不动。
- :移除某一个特殊参数,其他原本存在参数则不动。
= :设置一定,且仅有后面接的参数
A :当设置了 A 这个属性时,若你有存取此文件(或目录)时,他的存取时间 atime 将不会被修改,
可避免 I/O 较慢的机器过度的存取磁盘。(目前建议使用文件系统挂载参数处理这个项目)
S :一般文件是非同步写入磁盘的(原理请参考前一章sync的说明),如果加上 S 这个属性时,当你进行任何文件的修改,该更动会“同步”写入磁盘中。
a :当设置 a 之后,这个文件将只能增加数据,而不能删除也不能修改数据,只有root 才能设置这属性
c :这个属性设置之后,将会自动的将此文件“压缩”,在读取的时候将会自动解压缩,
但是在储存的时候,将会先进行压缩后再储存(看来对于大文件似乎蛮有用的!)
d :当 dump 程序被执行的时候,设置 d 属性将可使该文件(或目录)不会被 dump 备份
i :这个 i 可就很厉害了!他可以让一个文件“不能被删除、改名、设置链接也无法写入或新增数据!
对于系统安全性有相当大的助益!只有 root 能设置此属性
s :当文件设置了 s 属性时,如果这个文件被删除,他将会被完全的移除出这个硬盘空间,
所以如果误删了,完全无法救回来了喔!
u :与 s 相反的,当使用 u 来设置文件时,如果该文件被删除了,则数据内容其实还存在磁盘中,
可以使用来救援该文件喔!
注意1:属性设置常见的是 a 与 i 的设置值,而且很多设置值必须要身为 root 才能设置
注意2:xfs 文件系统仅支持 AadiS 而已

显示文件隐藏属性 lsattr

1
2
3
4
5
6
7
8
root@study ~]# lsattr [-adR] 文件或目录
选项与参数:
“-a :将隐藏文件的属性也秀出来;
-d :如果接的是目录,仅列出目录本身的属性而非目录内的文件名;
-R :连同子目录的数据也一并列出来!
[root@study tmp]# chattr +aiS attrtest
[root@study tmp]# lsattr attrtest
--S-ia---------- attrtest

文件特殊权限

Set UID -> SUID权限

1
2
[root@study ~]# ls -l /usr/bin/passwd
-rwsr-xr-x. 1 root root 27832 Jun 10 2014 /usr/bin/

注意:上面passwd指令,一般账号没有写入权限,为什么一般账号还能修改密码呢?
这就是USID的功能了(注意拥有者的“s”):
1、dmtsai 对于 /usr/bin/passwd 这个程序来说是具有 x 权限的,表示 dmtsai 能执行 passwd;
2、passwd 的拥有者是 root 这个帐号;
3、dmtsai 执行 passwd 的过程中,会“暂时”获得 root 的权限;
4、/etc/shadow 就可以被 dmtsai 所执行的 passwd 所修改。
如果一般用户用cat去读取/etc/shadow时,会提示权限不够,因为cat指令没有SUID权限。另外SUID只对二进制程序有用,不能用于shell脚本。

Set GID -> SGID权限

与SUID类似,当s标志在文件群组的x位置时,则称为SGID

1
2
3
[root@study ~]# ll /usr/bin/locate /var/lib/mlocate/mlocate.db
-rwx--s--x. 1 root slocate 40496 Jun 10 2014 /usr/bin/locate
-rw-r-----. 1 root slocate 2349055 Jun 15 03:44 /var/lib/mlocate/mlocate.db

使用 dmtsai 这个帐号去执行 locate 时,那 dmtsai 将会取得 slocate 群组的支持, 因此就能够去读取 mlocate.db 啦

除了 binary program 之外,事实上 SGID 也能够用在目录上,这也是非常常见的一种用途! 当一个目录设置了 SGID 的权限后,他将具有如下的功能:

  • 使用者若对于此目录具有 r 与 x 的权限时,该使用者能够进入此目录;
  • 使用者在此目录下的有效群组(effective group)将会变成该目录的群组;
  • 用途:若使用者在此目录下具有 w 的权限(可以新建文件),则使用者所创建的新文件,该新文件的群组与此目录的群组相同。

Sticky Bit -> SBIT权限

*目前这个权限仅针对目录有效,对于文件已经没有效果了。在others上的t标识

  • 当使用者对于此目录具有 w, x 权限,亦即具有写入的权限时;
  • 当使用者在该目录下创建文件或目录时,仅有自己与 root 才有权力删除该文件
    如:/tmp 本身的权限是“drwxrwxrwt”, 在这样的权限内容下,任何人都可以在 /tmp 内新增、修改文件,但仅有该文件/目录创建者与 root 能够删除自己的目录或文件。

SUID/SGID/SBIT 权限设置

SUID : 4 SGID : 2 SBIT : 1
在数字权限前面加上一个数字就表示几个特殊权限了.

假设要将一个文件权限改为“-rwsr-xr-x”时,由于 s 在使用者权限中,所以是 SUID ,因此, 在原先的 755 之前还要加上 4 ,也就是:“ chmod 4755 filename ”来设置!此外,还有大 S 与大 T 的产生喔!参考下面的范例啦!

1
2
[root@study tmp]# chmod 7666 test; ls -l test <==具有空的 SUID/SGID 权限
-rwSrwSrwT 1 root root 0 Jun 16 02:53 test

注意:上面大写SST,因为特殊权限要求必须有执行权限(上面是666),所以权限不能启作用为空权限

除了数字方法外,也可以通过符号来处理.其中 SUID 为 u+s ,而 SGID 为 g+s ,SBIT 则是 o+t

1
2
3
4
5
6
7
 #设置权限成为 -rws--x--x 的模样:
[root@study tmp]# chmod u=rwxs,go=x test; ls -l test
-rws--x--x 1 root root 0 Jun 16 02:53 test

#承上,加上 SGID 与 SBIT 在上述的文件权限中!
[root@study tmp]# chmod g+s,o+t test; ls -l test
-rws--s--t 1 root root 0 Jun 16 02:53 test

指令与文件的搜寻

指令文件名搜寻

which (寻找”可执行文件”)

默认查找PATH内所规范的目录第一个被找到的执行文件

1
2
3
4
5
6
选项参数:
-a 将所有由 PATH 目录中可以找到的指令均列出,而不止第一个被找到的指令名称

root@study ~]# which history
/usr/bin/which: no history in (/usr/local/sbin:/usr/local/bin:/sbin:/bin:
/usr/sbin:/usr/bin:/root/bin

因为history是bash内置命令所以不能用which查找,可以通过type命令查看。^[详见bash章节]

文件文件名搜寻

whereis (由一些特定的目录中寻找文件文件名)

1
2
3
4
5
6
7
[root@study ~]# whereis [-bmsu] 文件或目录名
选项与参数:
-l :可以列出 whereis 会去查询的几个主要目录而已
-b :只找 binary 格式的文件
-m :只找在说明文档 manual 路径下的文件
-s :只找 source 来源文件
-u :搜寻不在上述三个项目当中的其他特殊文件

locate / updatedb

locate寻找的数据是由/var/lib/mlocate里面的数据搜索到的,所以不用搜索硬盘,速度快。但由于数据库默认每天创建一次,所以新建的文件可能搜索不到,或者已删除文件还能搜索到

1
2
3
4
5
6
7
[root@study ~]# locate [-ir] keyword
选项与参数:
-i :忽略大小写的差异;
-c :不输出文件名,仅计算找到的文件数量
-l :仅输出几行的意思,例如输出五行则是 -l 5
-S :输出 locate 所使用的数据库文件的相关信息,包括该数据库纪录的文件/目录数量等
-r :后面可接正则表达式的显示方式

想要实时搜索就要手动更新数据库:updatedb
updatedb:根据 /etc/updatedb.conf 的设置去搜寻系统硬盘内的文件名,并更新 /var/lib/mlocate 内的数据库文件; locate:依据 /var/lib/mlocate 内的数据库记载,找出使用者输入的关键字文件名。
*因为 updatedb 会去搜寻硬盘,所以当你执行 updatedb 时,可能会等待数分钟的时间喔!

find

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
[root@study ~]# find [PATH] [option] [action]
选项与参数:
1. 与时间有关的选项:共有 -atime, -ctime 与 -mtime ,以 -mtime 说明
-mtime n :n 为数字,意义为在 n 天之前的“一天之内”被更动过内容的文件;
-mtime +n :列出在 n 天之前(不含 n 天本身)被更动过内容的文件文件名;
-mtime -n :列出在 n 天之内(含 n 天本身)被更动过内容的文件文件名。
-newer file :file 为一个存在的文件,列出比 file 还要新的文件文件名

2. 与使用者或群组名称有关的参数:
-uid n :n 为数字,这个数字是使用者的帐号 ID,亦即 UID ,这个 UID 是记录在/etc/passwd 里面与帐号名称对应的数字。这方面我们会在第四篇介绍。
-gid n :n 为数字,这个数字是群组名称的 ID,亦即 GID,这个 GID 记录在/etc/group
-user name :name 为使用者帐号名称喔!例如 dmtsai
-group name:name 为群组名称喔,例如 users
-nouser :寻找文件的拥有者不存在 /etc/passwd 的人!
-nogroup :寻找文件的拥有群组不存在于 /etc/group 的文件!
当你自行安装软件时,很可能该软件的属性当中并没有文件拥有者,
这是可能的!在这个时候,就可以使用 -nouser 与 -nogroup 搜寻。

3. 与文件权限及名称有关的参数:
-name filename :搜寻文件名称为 filename 的文件;
-size [+-]SIZE :搜寻比 SIZE 还要大(+)或小(-)的文件。这个 SIZE 的规格有:
c: 代表 Byte,
k: 代表 1024Bytes。
所以,要找比50KB还要大的文件,就是“ -size +50k”
-type TYPE :搜寻文件的类型为 TYPE 的,
类型主要有:
一般正规文件(f),
设备文件(b, c),
目录(d),
链接文件(l),
socket(s),
及 FIFO(p) 等属性。
-perm mode :搜寻文件权限“刚好等于” mode 的文件,这个 mode 为类似 chmod的属性值,举例来说, -rwsr-xr-x 的属性为 4755 !
-perm -mode :搜寻文件权限“必须要全部囊括 mode 的权“限”的文件。
-perm /mode : 任何权限位 mode 被设置了的文件。
举例:
[root@study ~]# find / -perm +7000
*所谓的 7000 就是 ---s--s--t ,那么只要含有 s 或 t 的就列出,所以当然要使用 /7000,
*使用 -7000 表示要同时含有 ---s--s--t 的所有三个权限。而只需要任意一个,就是 /7000 ~瞭乎?
(旧版是:-perm +7000已经被/7000替换)


4. 额外可进行的动作:
-exec command :command 为其他指令,-exec 后面可再接额外的指令来处理搜寻到的结果。
-print :将结果打印到屏幕上,这个动作是默认动作!
[root@study ~]# find / -name "passwd" -exec ls -l {} \;

-exec 后面不支持别名所以上面使用 ls -l
{} 代表的是“由find找到的内容”
由于find命令是硬盘搜索,所以速度会相对很慢