目录
一、磁盘
1. 机械磁盘组成
2. 磁盘逻辑结构
3. 磁盘分区
4. 分区与文件系统
二、文件系统
1. 目录树
2. Ext2文件系统(inode)
3. inode与目录树的关系
4. 文件系统操作命令
三、Linux文件权限
1. linux文件属性
2. 目录与文件的权限意义
3. 改变文件属性与权限
4. 文件与目录管理常用命令
一个传统的机械硬盘结构如下图:
机械硬盘主要由磁盘盘片、磁头、主轴与传动轴等组成,数据就存放在磁盘盘片中。大家见过老式的留声机吗?留声机上使用的唱片和我们的磁盘盘片非常相似,只不过留声机只有一个磁头,而硬盘是上下双磁头,盘片在两个磁头中间高速旋转,类似下图:
硬盘的盘片一般用铝合金材料做基片,高速硬盘也可能用玻璃做基片。硬盘的每一个盘片都有两个盘面(Side),即上、下盘面,一般每个盘面都会利 用,都可以存储数据,成为有效盘片,也有极个别的硬盘盘面数为单数。硬盘的盘片组在2~14片不等,通常有2~3个盘片。
硬盘在逻辑上被划分为磁道、柱面以及扇区。
2.1 磁道
磁盘在格式化时被划分成许多同心圆,这些同心圆轨迹叫做磁道(Track)。磁道从外向内从0开始顺序编号。硬盘的每一个盘面有300~1 024个磁道,新式大容量硬盘每面的磁道数更多。磁道是“看”不见的,只是盘面上以特殊形式磁化了的一些磁化区,在磁盘格式化时就已规划完毕。
2.2 柱面
所有盘面上的同一磁道构成一个圆柱,通常称做柱面(Cylinder),每个圆柱上的磁头由上而下从“0”开始编号。数据的读/写按柱面进行,即磁 头读/写数据时首先在同一柱面内从“0”磁头开始进行操作,依次向下在同一柱面的不同盘面即磁头上进行操作,只在同一柱面所有的磁头全部读/写完毕后磁头才转移到下一柱面,因为选取磁头只需通过电子切换即可,而选取柱面则必须通过机械切换。电子切换相当快,比在机械上磁头向邻近磁道移动快得多,所以,数据 的读/写按柱面进行,而不按盘面进行。也就是说,一个磁道写满数据后,就在同一柱面的下一个盘面来写,一个柱面写满后,才移到下一个扇区开始写数据。读数 据也按照这种方式进行,这样就提高了硬盘的读/写效率(这也是为什么硬盘顺序读写比随机读写高效的原因)。
2.3 扇区
从圆心向外画直线,可以将磁道划分为若干个弧段,每个磁上一个弧段被称之为一个扇区,用以存储数据。每个扇区可以存放512个字节的数据,磁盘驱动器在向磁盘读取和写入数据时,要以扇区为单位。若干个扇区就组成整个盘片,硬盘的读写以扇区为基本单位。
硬盘容量 = 磁头数(盘面数 x 2) x 柱面数 x 扇区数 x 512bytes(每个扇区的大小)
磁盘的第一个扇区主要记录了两个重要的信息,分别是:
3.1 分区表
在分区表所在的64bytes容量中,总共分为4组记录区,每组记录区记录了该区段的启动与结束的柱面编号。逻辑结构如下图所示:
其实所谓的“分区”只是针对那个64bytes的分区表进行设置而已。
磁盘使用扩展分区的例子如下图所示:
3.2 开机流程与主引导分区(MBR)
CMOS是记录各项硬件参数且嵌入在主板上面的存储器,BIOS则是写入到主板上的一个软件程序。这个BIOS就是在开机的时候计算机系统会去主动执行的第一个程序了。BIOS会依据用户的设置去取得能够开机的硬盘,并且到该硬盘里面去读取第一个扇区的MBR位置。MBR这个仅有446bytes的硬盘容量里面会放置最基本的引导加载程序。
这个引导加载程序的目的是在加载内核文件,由于引导加载程序是操作系统在安装的时候所提供的,所以它会识别硬盘内的文件系统格式,因此就能够读取内核文件,然后就是内核文件的工作。
磁盘在分区完成之后,要使得操作系统能够识别文件系统,就需要进行格式化,把分区格式化成某一个操作系统能够识别的文件系统。格式化后常见的磁盘格式有:FAT(FAT16)、FAT32、NTFS、ext2、ext3等。
linux内所有数据都是以文件形态来呈现的,以目录树的形式逻辑组织文件,以路径“/”开头。在物理上使用基于索引表结构(ext2, ext3等)的分区格式来存放数据。默认情况下,linux所有文件内容均存储于根路径所在的磁盘分区,如果要使用多个分区或磁盘,需要使用磁盘挂载(mount)。
整个Linux系统最重要的地方就是在于目录树架构,所谓的目录树架构就是以根目录为主, 然后向下呈现分支状的目录结构的一种档案架构。我们可以先通过下面这幅图来直观的认识一下Linux的目录结构。
linux的一些主要目录简介:
linux文件系统会将文件本身属性与文件内容分开存放,将文件权限(rwx)与文件属性(所有者,群组,时间参数等)放置到inode中,至于实际数据则放置到data block块中。另外,还有一个超级块会记录文件系统的整体信息,包括inode与block的总量、使用量、剩余量等。
每个inode 与block 都有编号,三者的意义可以简略说明如下:
读取文件时,先找到文件所在的inode,然后读取inode中的内容,得到文件内容的block编号列表,然后根据block编号去访问实际的block内容,流程如下图所示:
如果将所有的inode与block放置在一起是很不明智的决定,因为inode与block的数量太大时,不容易管理。因此Ext2文件系统在格式化的时候基本区分为多个块组(block group)的,每个块组都有自己独立的inode/block/superblock系统。在整体规划中,文件系统最前面有一个启动扇区(boot sector),这个启动扇区可以安装引导装载程序,这样就不用覆盖整块硬盘唯一的MBR,从而实现在一块硬盘上安装多个操作系统。整体结构如下图所示:
2.1 inode
inode 的数量与大小也是在格式化时就已经固定了,每个inode 大小均固定为128 bytes (新的ext4 与xfs 可设定到256 bytes),每个文件都仅会占用一个inode 而已,系统读取文件时需要先找到inode,并分析inode 所记录的权限与使用者是否符合,若符合才能够开始实际读取 block 的内容。inode记录的文件数据主要有以下内容:
2.2 data block (数据块)
data block是用来放置文件内容的地方,在Ext2文件系统中所支持的block大小有1K, 2K及4K三种而已。在格式化时block的大小就固定了,且每个block都有编号,以方便inode的记录。不过要注意的是,由于block大小的差异,会导致该文件系统能够支持的最大磁盘容量与最大单一档案容量并不相同。因为block大小而产生的Ext2档案系统限制如下:
Block 大小 | 1KB | 2KB | 4KB |
---|---|---|---|
最大单一文件限制 | 16GB | 256GB | 2TB |
最大档案系统总容量 | 2TB | 8TB | 16TB |
除此之外,还有一些基本限制如下:
3.1 目录
在linux下的ext2文件系统新建一个目录时,ext2会至少分配一个inode与至少一块block给该目录。其中,inode记录该目录的相关权限和属性,并记录分配到的那块block号码,而block则是记录在这个目录下的所有文件的文件名与该文件名占用的inode号码数据。
3.2 文件
在linux下的ext2文件系统新建一个普通文件时,ext2会分配一个inode以及相应数量的block给该文件。需要注意的是,文件名本身没有存放在inode中,而是在其所在目录的block当中。
3.3 目录树读取
目录树是由根目录开始读起,因此系统通过挂载的信息可以找到挂载点的inode号码(通常一个文件系统的inode号码会由2号开始),此时就能够得到根目录的inode内容,并依据该inode读取根目录的block内的文件名数据,再一层一层地往下读到正确的文件名。
例如,要读取文件/var/log/messages的流程如下:
1. 查看整体磁盘使用量:df -h
[root@demo211 ~]# df -h
文件系统 容量 已用 可用 已用% 挂载点
/dev/vda1 200G 40G 161G 20% /
devtmpfs 32G 0 32G 0% /dev
tmpfs 32G 0 32G 0% /dev/shm
tmpfs 32G 159M 32G 1% /run
tmpfs 32G 0 32G 0% /sys/fs/cgroup
2. 查看目录的磁盘使用量:du -sh /xxx
[root@demo211 ~]# du -sh /opt/
22G /opt/
3. 创建类似于Windows的快捷方式的符号连接(Symbolic link):ln -s xxx xxx
[root@demo211 ~]# ln -s /usr/lib/hive/bin/hplsql /usr/bin/
[root@demo211 ~]# ls -l /usr/bin/hplsql
lrwxrwxrwx. 1 root root 24 7月 6 10:44 /usr/bin/hplsql -> /usr/lib/hive/bin/hplsql
4. 列出所有磁盘设备:fdisk -l
[root@demo211 ~]# fdisk -l
磁盘 /dev/vda:214.7 GB, 214748364800 字节,419430400 个扇区
Units = 扇区 of 1 * 512 = 512 bytes
扇区大小(逻辑/物理):512 字节 / 512 字节
I/O 大小(最小/最佳):512 字节 / 512 字节
磁盘标签类型:dos
磁盘标识符:0x000b74bd
设备 Boot Start End Blocks Id System
/dev/vda1 * 2048 419430366 209714159+ 83 Linux
磁盘 /dev/vdb:1099.5 GB, 1099511627776 字节,2147483648 个扇区
Units = 扇区 of 1 * 512 = 512 bytes
扇区大小(逻辑/物理):512 字节 / 512 字节
I/O 大小(最小/最佳):512 字节 / 512 字节
5. 对磁盘进行分区:fdisk 磁盘名称
[root@demo211 ~]# fdisk /dev/vdb
欢迎使用 fdisk (util-linux 2.23.2)。
更改将停留在内存中,直到您决定将更改写入磁盘。
使用写入命令前请三思。
Device does not contain a recognized partition table
使用磁盘标识符 0x6f757e35 创建新的 DOS 磁盘标签。
命令(输入 m 获取帮助):
6. 对磁盘分区进行文件系统的格式化:mkfs [-t 文件系统格式] 分区名称
[root@demo211 ~]# mkfs -t ext3 /dev/vda1
7. 将磁盘分区挂载到某个目录:mount 分区名 目录名
[root@demo211 ~]# mount /dev/vdb1 /mydata
8. 取消磁盘挂载:umount 目录名
[root@demo211 ~]# umount /mydata
Linux支持多用户,多任务环境,使用权限管理来限制用户访问目录和文件。Linux一般将文件可存取访问的身份分为3个类别:
Linux文件属性是指包含文件名,文件大小,创建时间以及文件权限等属性。使用ls -al 命令可以查看当前目录下的所有文件的属性,如下图所示:
[root@demo67 opt]# ls -al
总用量 723200
drwxr-xr-x. 6 root root 270 6月 28 19:01 .
dr-xr-xr-x. 17 root root 224 6月 14 2018 ..
-rw-r--r--. 1 root root 53311084 6月 28 2020 cluster-manager-1.0.0+c0001-b0073.noarch.rpm
drwx--x--x. 4 root root 28 6月 5 15:37 containerd
-rwxr-xr-x. 1 root root 261 6月 4 10:42 deploy_cluster.sh
上面命令的显示结果一共包含了7列,每一列对应的含义如下:
第二栏表示有多少个文件名连结到此节点(i-node)
第三栏表示这个文件(或目录)的owner
第四栏表示这个文件的所属group
第五栏为这个文件的容量大小,默认单位为bytes
第六栏为这个文件的创建日期或者是最近的修改日期
第七栏为这个文件的文件名
2.1 权限对文件的重要性
文件是实际含有数据的地方,包括一般文本文件、数据库内容文件、二进制可执行文件(binary program)等等。 因此,权限对于文件来说,他的意义是这样的:
2.2 权限对目录的意义
目录主要的内容在记录文件名列表。针对目录时,他的意义是这样的:
有以下几个常用命令可以修改文件的权限,onwer,以及group:
chgrp : 改变文件所属群组
chown : 改变文件拥有者
chmod : 改变文件的权限, SUID, SGID, SBIT等等的特性
4.1 常见的处理目录的命令:
4.2 文件内容查阅
1) 直接全部显示文件内容可以使用以下命令:
2) 当文件太大,需要分页查看内容时,可以使用以下命令:
3)如果只想展示文件的头部或者尾部的部分内容,可以使用以下命令:
4.3 命令与文件的查询
我们经常在linux要查找某个文件,但不知道放在哪里了,可以使用下面的一些命令来搜索:
1) which命令的作用是,在PATH变量指定的路径中,搜索某个系统命令的位置,并且返回第一个搜索结果。也就是说,使用which命令,就可以看到某个系统命令是否存在,以及执行的到底是哪一个位置的命令。
2) whereis命令只能用于程序文件的搜索,而且只搜索二进制文件(参数-b)、man说明文件(参数-m)和源代码文件(参数-s)。如果省略参数,则返回所有信息
wangzhe@wangzhe-pc:~/Downloads$ whereis whoami
whoami: /usr/bin/whoami /usr/share/man/man1/whoami.1.gz
3) locate命令其实是“find -name”的另一种写法,但是要比后者快得多,原因在于它不搜索具体目录,而是搜索一个数据库(/var/lib/locatedb),这个数据库中含有本地所有文件信息。Linux系统自动创建这个数据库,并且每天自动更新一次,所以使用locate命令查不到最新变动过的文件。为了避免这种情况,可以在使用locate之前,先使用updatedb命令,手动更新数据库。
locate /etc/sh:搜索etc目录下所有以sh开头的文件。
4) find是最常见和最强大的查找命令,你可以用它找到任何你想找的文件。
find的使用格式如下:
$ find <指定目录> <指定条件> <指定动作>
- <指定目录>: 所要搜索的目录及其所有子目录。默认为当前目录。
- <指定条件>: 所要搜索的文件的特征。
- <指定动作>: 对搜索结果进行特定的处理。
如果什么参数也不加,find默认搜索当前目录及其子目录,并且不过滤任何结果(也就是返回所有文件),将它们全都显示在屏幕上。
find的使用实例:
$ find . -name "my*"
搜索当前目录(含子目录,以下同)中,所有文件名以my开头的文件。
$ find . -name "my*" -ls
搜索当前目录中,所有文件名以my开头的文件,并显示它们的详细信息。
$ find . -type f -mmin -10
搜索当前目录中,所有过去10分钟中更新过的普通文件。