这篇博客主要是一个目的,即学习总结Linux文件系统的内容,参考《鸟哥的Linux私房菜》这本书,对Linux文件与目录相关知识及Linux磁盘与文件系统进行了学习。
【1】Linux文件与目录相关知识
改变文件属性与权限
chgrp:改变文件所属用户组
被改变的组名必须要在/etc/group文件内存在 chgrp users install.log
chown:改变文件所有者
被改变的账户名必须在/etc/passwd内存在 chown bin install.log
chmod:改变文件权限
文件权限对于一般文件与目录文件有何不同?
(1)权限对文件:
r:可读取文件内容
w:可编辑、新增或修改文件内容,但**不可删除该文件**
x:windows下判断文件是否有执行权限是根据**扩展名**,Linux下判断文件是否可执行根据**X**,与文件名无绝对关系
对于文件的r、w、x,主要针对文件内容,与文件名存在与否没有关系。
(2)权限对目录:
r:可读取目录结构列表
w:可更改目录结构列表
新建新的文件与目录
删除已经存在的文件与目录(不论该文件权限)
将已经存在的文件与目录重命名
转移改目录内文件、目录位置
x:能否切换到该目录
Linu目录配置标准 FHS
其主要目的是希望让用户可以了解到已安装软件通常放置于哪个目录下
根目录(/):越小越好
根目录下的目录:
因为根目录与开机有关,开机过程中仅有根目录会被挂载,其它分区是在开机完成之后才会持续进行挂载行为,因此,根目录下与开机过程有关的目录必须与根目录在同一分区!
- /etc:配置文件
- /bin:重要执行文件
- /dev:所需要的设备文件
- /lib:执行文件所需的函数库与内核所需的模块
- /sbin:重要的系统执行文件
/usr意义与内容
usr:不是user的缩写,usr是UNIX Soft Resource的缩写,即“UNIX操作系统软件资源”所放置的目录,而不是用户的数据。
/var意义与内容
如果说/usr在安装时就会占用较大硬盘容量,那么/var就是在系统运行后才会渐渐占用硬盘容量。/var主要针对常态性变动的文件,包括缓存(cache)、登录文件(logfile)以及某些软件运行所产生的文件。
几个常见的处理目录的命令
cd:切换目录
pwd:显示当前目录
mkdir:新建一个新的目录
rmdir:删除一个空的目录
rm -r:删除目录下所有内容
执行文件路径的变量:$PATH
ls的完整文件名:/bin/ls
但是为什么在任何地方都能执行ls?这是环境变量PATH的帮助。
PATH必须大写,PATH前加$表示后面接的是变量,所以会显示出目前的路径:
root@hyx-virtual-machine:/# echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games
将/root加入PATH:
root@hyx-virtual-machine:/# PATH="$PATH":/root
root@hyx-virtual-machine:/# echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/root
root@hyx-virtual-machine:/#
对文件的操作
cp:
复制文件:不加任何参数时,文件的某些属性/权限会改变,加上-a参数后,连同文件特性一起复制
创建连接文件:
hyx@hyx-virtual-machine:~$ cp -s 1.txt 1.txt_slink
hyx@hyx-virtual-machine:~$ cp -l 1.txt 1.txt_hlink
hyx@hyx-virtual-machine:~$ ls -l
总用量 160
-rw-rw-r-- 2 hyx hyx 0 11月 14 16:58 1.txt
-rw-rw-r-- 2 hyx hyx 0 11月 14 16:58 1.txt_hlink
lrwxrwxrwx 1 hyx hyx 5 12月 13 19:28 1.txt_slink -> 1.txt
对比两文件的新旧予以更新(-u)
复制整个目录(-r)
rm:移除文件或目录
-f:force
-i:互动模式
-r:递归删除
question:如何删除-aaa?
answer:rm ./-aaa
mv:移动文件与目录,或更名
这样就移动文件到目录中了
hyx@hyx-virtual-machine:~$ mkdir mvtest
hyx@hyx-virtual-machine:~$ mv 1.txt mvtest
这样就重命名了
hyx@hyx-virtual-machine:~$ mv mvtest mvtest1
查阅文件内容
cat -n:打印出行号
tac:从最后一行显示
nl:显示时,打印出行号
more:一页一页翻动,向下
less:不仅向下翻页,还可向上翻页
head:默认输出前10行,-n 20:输出20行
tail:默认从后显示10行
od [-t TYPE]:查看非纯文本文件内容
-t:
a 默认输出
c ASCII输出
d 十进制输出
f 浮点输出
o 八进制输出
x 十六进制输出
三个时间
文件默认权限umask
hyx@hyx-virtual-machine:~$ umask
0002 /*该默认值需要减掉的权限*/
hyx@hyx-virtual-machine:~$ umask -S
u=rwx,g=rwx,o=rx
- 一般文件创建时默认没有执行权限,即-rw-rw-rw
新建目录默认权限,drwxrwxrwx
root@hyx-virtual-machine:/home/hyx/hh# mkdir test1 root@hyx-virtual-machine:/home/hyx/hh# touch test2 root@hyx-virtual-machine:/home/hyx/hh# ll 总用量 12 drwxr-xr-x 3 root root 4096 12月 13 21:26 ./ drwxr-xr-x 21 hyx hyx 4096 12月 13 21:26 ../ drwxr-xr-x 2 root root 4096 12月 13 21:26 test1/ -rw-r--r-- 1 root root 0 12月 13 21:26 test2 root@hyx-virtual-machine:/home/hyx/hh#
查看文件类型file
touch的目的在于修改文件的时间参数,但也可以用来创建空文件
命令与文件的查询
which : 根据PATH这个环境变量所规范的路径去查询“执行文件”的文件名
?cd这个常用命令为什么找不到?
root@hyx-virtual-machine:/home/hyx/hh# which cd root@hyx-virtual-machine:/home/hyx/hh# 这是因为cd是bash内置的命令,但whic默认是查找PATH内所规范的目录,所以找不到。
【注意】
通常我们是先使用whereis或者locate来检查,如果真的找不到了,才用find来查找。为什么呢?因为Linux系统会将系统内的所有文件都记录在一个数据库文件里面,whereis和locate是利用数据库来查找数据,所以相当快速,而find是直接查找硬盘!
- whereis:寻找特定文件
对比whic和whereis:
root@hyx-virtual-machine:/home/hyx/hh# which ifconfig
/sbin/ifconfig /*只是寻找PATH路径中的*/
root@hyx-virtual-machine:/home/hyx/hh# whereis ifconfig
ifconfig: /sbin/ifconfig /usr/share/man/man8/ifconfig.8.gz
root@hyx-virtual-machine:/home/hyx/hh#
- locate:输入“文件部分名称”后就能得到结果
locate寻找的数据是由已创建数据库/var/lib/mlocate/里面数据查找的,数据库的创建默认是每天执行一次,所以当新建文件后查找该文件,locate会告诉你“找不到”!因为必须要更新数据库。直接输入“updatedb”即可!
- updatedb 根据/etc/updatedb.conf的设置去查找系统硬盘内的文件名,并更新/var/lib/mlocate内的数据库文件
- locate 依据/var/lib/mlocate内的数据库记载,做出用户输入的关键字文件名
root@hyx-virtual-machine:/home/hyx/hh# locate ifconf
/sbin/ifconfig
/usr/share/man/de/man8/ifconfig.8.gz
/usr/share/man/fr/man8/ifconfig.8.gz
/usr/share/man/man8/ifconfig.8.gz
/usr/share/man/pt_BR/man8/ifconfig.8.gz
/usr/src/linux-headers-3.19.0-25/tools/hv/hv_set_ifconfig.sh
- find
注意下面这个,0代表当前时间,所以,从现在开始到24小时前:
root@hyx-virtual-machine:/home/hyx/hh# find -mtime 0
.
./test2
./test1
【2】Linux磁盘与文件系统
正式了解这块内容前,先大致学习了下Linux磁盘分区的内容。
我们都知道,在Linux系统中,一切设备皆文件。怎么理解这句话呢?看下面这张表就明白了。
先要把IDE和STAT硬盘的文件名背下来!
Linux系统是安装在磁盘的,常见的磁盘接口有两种,分别是IDE和SATA接口。(目前主流的接口是SATA接口)
那么磁盘是怎么组成的?
磁盘主要由盘片、机械手臂、磁头、主轴马达组成,数据的写入是在盘片上面。盘片上又可细分出扇区与柱面两种单位。每个扇区是512字节,扇区组成一个圆就称为磁道,如果在多硬盘上面,所有盘片上面的同一个磁道可以组成一个柱面,柱面是我们对硬盘进行分区时的最小单位!
磁盘的第一个扇区尤其重要,记录了两个信息:
- 主引导分区(Master Boot Record,MBR):可以安装引导加载程序的地方,有446字节
- 分区表(partition table):记录整块硬盘分区状态,有64字节
MBR很重要,系统开机时会读取这个区块内容,这样系统才能知道你的程序放在哪里且该如何开机。
我们利用参考柱面号码的方式来对磁盘分区。分区表里面共分为四组记录区,每组记录着该区段的启始与结束的柱面号码。
参考下面的两个图:
假设上面的硬盘设备文件名是/dev/hda,那么这四个分区的名字是(重点是后面的数字)
P1:/dev/hda1
P2:/dev/hda2
P3:/dev/hda3
P4:/dev/hda4
这四个分区信息是主分区(primary)或扩展分区(extended)。
思考是不是一块硬盘只能分四个区呢?答案是否定的。我们可以用扩展分区来将一块硬盘分出来好多个区。扩展分区的目的是使用额外的扇区来记录分区信息,扩展分区本身不能被格式化。
参考下面的图来理解:
上述分区在Linux系统中的设备文件名如下:
P1:/dev/hda1
P2:/dev/hda2
L1:/dev/hda5
L2:/dev/hda6
L3:/dev/hda7
L4:/dev/hda8
L5:/dev/hda9
/dev/hda3和/dev/hda4去哪了?因为钱四个号码都保留给primary或extended,所以逻辑分区的设备号码就从5号开始了,这个很重要!
数据被存入到某个分区中,一个典型的Linux分区包含有下面各个部分:
我们据此来了解linux的文件系统特性。
文件系统特性
Linux的正规文件系统为Ext2。文件系统通常会将不同数据放在不同块。
- super block:记录此文件系统整体信息,包括inode/block总量、使用量、剩余量,及文件系统的格式与相关信息。
- inode:一个文件占用一个inode,记录文件的属性与此文件数据所在的block号码
- block:实际记录文件的内容,若文件太大,会占用多个block
下面是两种文件系统
(1)利用inode/block的索引式文件系统
文件属性与权限数据放在inode4,inode记录实际数据存放在2,7,13,15,操作系统能根据此顺序排列磁盘顺序,将4个block内容读出来。
(2)U盘的FAT格式的文件系统
没有inode的存在,它无法一下子读取四个block号码,每个block号码都记录在前一个block当中
Linux的目录树与文件系统
linux文件系统中,每个文件对应一个inode,系统通过inode中记录文件块信息去查找文件存放的block,并读取。我们在使用linux文件系统去读取文件时,使用的是文件名或目录名,并不直接使用inode,人们也不可能记住不同文件所对应的inode号。
那么问题来了,如何通过目录或文件名获得对应的inode?
目录和普通文件在存储上类似,系统也会分配唯一的inode号和至少一个block。只是inode记录该目录的相关权限与属性及可分配到的那块block号码;block记录的是在这个目录下的文件名及该文件名占用的inode号码数据。
linux中维护了一个目录树的结构,任何文件或目录的最上层根目录为:/
系统默认使用inode号(2)对应的block来存储根目录(/)中放置的子目录或文件名和它们对应的inode号。
用户通过文件名或目录读取相应磁盘块时,从根目录的inode 2 开始,查找对应子目录或文件名,找到后获取其inode号,再根据inode号读取磁盘块。依次向下进行。
举例来说,如果我想要读/etc/passwd下面的内容,系统如何读取?
重新认识软连接和硬连接
从前面我们可以知道:
每个文件都会占用一个inode,文件内容由inode的记录来指向,而文件名至于目录有关。多个文件名是可以对应到同一个inode的,hardlink由此而来。
下面是一个创建硬连接的例子:
root@hyx-virtual-machine:/# ln /etc/crontab .
root@hyx-virtual-machine:/# ll -i /etc/crontab ./crontab
655506 -rw-r--r-- 2 root root 722 2月 9 2013 ./crontab
655506 -rw-r--r-- 2 root root 722 2月 9 2013 /etc/crontab
root@hyx-virtual-machine:/#
上述分析:创建的硬连接与源文件指向同一inode号码,hardlink只是在目录下的block多写入一个关连数据而已,既不会增加inode也不会耗用block的数量。
hardlink的限制:
- 不能跨文件系统
- 不能连接到目录
下面是创建软连接的例子:
hyx@hyx-virtual-machine:/tmp$ touch abc
hyx@hyx-virtual-machine:/tmp$ ll -i abc
1054238 -rw-rw-r-- 1 hyx hyx 0 12月 14 21:14 abc
hyx@hyx-virtual-machine:/tmp$ ln -s abc def
hyx@hyx-virtual-machine:/tmp$ ll -i abc def
1054238 -rw-rw-r-- 1 hyx hyx 0 12月 14 21:14 abc
1054336 lrwxrwxrwx 1 hyx hyx 3 12月 14 21:14 def -> abc
hyx@hyx-virtual-machine:/tmp$
由结果,这两个文件指向不同的inode号码,也就是作为两个独立的文件存在,所以由symbolic link创建的文件会占用掉inode与block
挂载点的意义
每个文件系统都有独立的inode、block、super block等信息,这个文件系统要能够链接到目录树才能被我们使用。将文件系统与目录树结合的操作我们成为挂载。
具体来说,挂载就是利用一个目录当成进入点,将磁盘分区的数据放置在该目录下;也就是说,进入该目录就可以读取该分区。这个操作我们成为挂载,那个进入点的目录我们成为挂载点
参考图,假设我的硬盘分为两个区,partition1挂载到根目录,partition2挂载到/home目录。
可以通过判断inode来确认不同文件名是否是相同文件:
root@hyx-virtual-machine:/tmp# ls -ild / /. /..
2 drwxr-xr-x 23 root root 4096 12月 14 21:12 /
2 drwxr-xr-x 23 root root 4096 12月 14 21:12 /.
2 drwxr-xr-x 23 root root 4096 12月 14 21:12 /..
上面的信息挂载点都为/,因此三个文件(/ /. /..)均在一个文件系统内,这三个文件的inode号均为2,因此这三个文件名都指向同一个inode号码,当然这三个文件内容就一模一样。也就是说,根目录的上层就是它自己
学习体会
关于Linux文件系统的内容,整整看了一天的时间。主要参考的是《鸟哥的Linux私房菜》这本书,有一些模糊的地方,有一些没看到的地方,当然也有一些恍然大悟的地方,还是要继续努力!
参考资料
《鸟哥的Linux私房菜》