<
  • 主题:
  • + -
  • 清除背景
  • 禁用背景

Linux文件系统与文件类型

字数:11104 写于:2021-12-29
最新更新:2021-12-29 阅读本文预计花费您32分钟

文件与目录类型

常见的文件类型

  1. 普通文件:最为常见的文件类型,包括纯文本文件(ASCII),二进制文件(binary),数据文件(data)等
  2. 目录:即文件夹,用于包含更多目录和文件
  3. 块设备文件:将硬盘、光盘等存储设备以文件形式供用户操作
  4. 字符设备文件:将串行端口的接口设备,如键盘、鼠标等以文件形式供用户操作
  5. 套接字文件:又称为数据接口文件,用于网络数据连接
  6. 管道文件:用于进程间的通讯
  7. 链接文件:分为硬链接和软链接,用于通过快捷方式或引用快速访问另一个文件或目录

Linux目录

指令集
  • /bin   Binaries的缩写,存放普通用户可使用的系统命令,如:ls
  • /sbin Super user Binary的缩写,存放只有系统管理员才能使用的系统命令,如:shutdown、reboot
  • /usr/bin 存放安装软件后,普通用户可以使用的软件命令,如:c++、make、wget等
  • /usr/sbin 存放系统管理员用户安装使用的高级管理程序和系统服务程序,如:httpd、netconfig、tcpd等
系统文件
  • /etc Etcetera(其他)的缩写,这个目录用来存放所有系统管理所需要的配置文件和子目录
  • /var 存放一些经常被修改、扩充的文件,如各种日志文件
  • /boot 存放引导启动Linux时使用的核心文件,如镜像文件等
  • /sys  Linux2.6内核新增的文件系统sysfs,sysfs文件系统集成了3种文件系统的信息:针对进程信息的proc文件系统、针对设备的devfs文件系统以及针对伪终端的devpts文件系统
  • /lib 存放系统所需要的动态链接库(如C++库),相当于windows的dll文件
  • /dev Device的缩写, 将Linux主机的硬件以文件形式存储并提供访问,相当于Windows的设备管理器
  • /usr/src 内核源代码、说明文档等默认放置目录
  • /opt 默认为空,常用于安装额外软件,通常为第三方软件
  • /proc Processes(进程)的缩写,虚拟的目录,用于管理内存空间,是系统内存的映射,我们可以直接访问这个目录来获取系统信息。这个目录的内容不在硬盘上而是在内存里
  • /selinux 全称为security-enhanced linux,该目录是 Redhat/CentOS 所特有的目录,是Redhat/CentOS的安全子系统
  • /srv service缩写,存放一些服务启动后需要提取的数据
用户
  • /root 系统管理员的账号主目录
  • /home 存放普通用户的相关文件,Linux会在home目录下为每一个用户生成一个以用户账号命名的目录
  • /usr Unix Software Resource(共享资源)的缩写,放置用户的应用程序和文件,类似于windows下的program files目录
  • /usr/local 软件安装目录,一般通过源码编译安装方式安装的软件都会存放于该目录下
  • /usr/include 放置如c/c++等程序语言的头文件(header)与包含档(include)
  • /usr/lib 放置各应用软件的函式库、目标文件等,如果使用的是X86_64的Linux系统,则可能会生成/usr/lib64文件夹
外部文件
  • /media 挂载U盘、光驱等设备的目录,类似于windows的其他设备
  • /mnt 让用户挂载其他的文件系统,如将Windows上的某个目录挂载在/mnt下,可用于共享文件等

临时文件

  • /lost+found 一般情况下为空目录,用于存放系统非法关机或者发生意外错误后,fsck(磁盘修复)过程修复的部分文件
  • /tmp 用于存放临时文件
  • /run 一个临时文件系统,存放存储系统启动以来的信息。当系统重启时,这个目录下的文件应该被删掉或清除。

链接文件

链接文件是Linux文件系统的一个优势。当需要在系统上维护同一文件的两份或多份副本时,除了保存多份单独的物理文件副本之外(复制文件),还可以采用保存一份物理文件副本和多个虚拟副本的方法(链接文件),这种虚拟的副本就称为链接。Linux文件系统有两种链接文件:

  • 软链接:也称为符号链接或软连接,相当于文件的快捷方式。为了方便跨分区指向,软链接文件拥有独立的inode号,是一个单独的文件,但文件本身只包含指向原文件或原目录的路径,而不包含实际的文件内容,所有对软链接的读取、执行等操作都是基于原文件。当原文件删除,软链接文件也将失效,因此可视为软链接只是一个指向原文件的指针
  • 硬链接:是一个被创建出来的独立虚拟文件,其中包含了原文件的信息及位置。但是硬链接文件和原文件本质上是同一个文件,inode号相同,删除原文件并不会造成硬链接文件的失效,也不会造成文件内容丢失,因为此时仍然还存在一个可以访问文件存储区域的通道(硬链接文件)

二者区别:

  • 生成的软链接权限都为 rwxrwxrwx,实际权限取决于原文件权限
  • 硬链接文件 inode 节点与原文件相同,软链接不同
  • 硬链接指向不能跨分区,软链接可以
  • 不能给目录生成硬链接,软链接可以

inode(索引节点):是Linux文件系统中的一个概念,用于存储文件的元数据信息。每个文件在文件系统中都有一个对应的inode,它包含了文件的具体信息,如文件类型、文件大小、权限信息、所有者、访问时间、修改时间、链接数等。在Linux文件系统中,文件内容被存储于数据块中,而inode存储了文件的元数据信息和指向文件数据块的指针。当用户创建一个文件时,系统会分配一个inode给这个文件,并记录文件的元数据信息。每个inode都有一个唯一的索引号,即文件或目录的inode编号,它是一个用于标识的唯一数字,这个数字由内核分配给文件系统中的每一个对象。要查看文件或目录的inode编号,可以使用ls -i命令,文件系统可以通过该索引号来找到对应的inode和文件。硬链接文件和源文件共享相同的inode,即它们指向同一个文件的元数据信息,因此在inode中会有一个链接计数器,记录有多少个目录项指向这个inode,这样系统可以正确处理不同目录下的链接关系。

对于硬链接,硬链接和原始文件本质上是同一个文件,它们共享相同的inode。当用户创建一个硬链接时,实际上是在创建一个指向相同inode的新目录项,使得该文件在文件系统中有多个名称。因此,删除源文件时,不会影响到已经创建的硬链接文件,因为这其实只是减少了一个指向该inode的目录项,而硬链接文件依然指向这个inode,因此硬链接文件会继续存在。只有当所有指向该inode的目录项都被删除后,文件系统才会释放该inode及其对应的数据块,这时硬链接文件也会被删除。

对于软链接(Symbolic Link),它是一个特殊的文件,用于指向另一个文件的路径。和硬链接不同,软链接创建了一个新的inode来存储软链接文件的元数据信息。软链接和原始文件是两个独立的文件,它们可能位于不同的文件系统中。因此,软链接需要有自己的inode来存储自己的元数据信息,以确保其独立性。软链接的实现方式是通过存储目标文件的路径信息,而不是直接指向目标文件的inode。这样做的好处是可以在文件系统中创建指向不同文件系统的软链接,而硬链接只能在同一文件系统中有效。软链接文件的存储内容是指向另一个文件的路径,而不是具体的文件内容,因此即便源文件很大,软链接文件依旧可能很小。而所有通过vim等软件修改软链接内容,实际是在修改源文件的内容,所有对软链接的读取、执行等操作都会基于源文件,软链接只是一个指向源文件的指针,当源文件删除,软链接文件也将失效。

link创建硬链接

该命令只能创建硬链接
link 源文件 硬链接名

ln创建链接文件

ln 源文件 目标文件

  • 默认会创建硬链接,如果指定路径下已有与目标文件同名的文件,则返回错误,如果源文件不存在,则返回错误
  • -s 创建软链接,对于软链接,如果源文件不存在,依旧会创建软链接文件(悬空链接),指向一个不存在的文件。因此软链接支持先创建链接,后补源文件
  • -b 创建链接时如果已有同名文件,则备份该文件,参考通用的备份方案
  • -S “字符串”:指定备份文件的后缀名
  • -f 强制创建链接文件,有同名文件直接覆盖
  • -i 有同名文件时,询问用户是否覆盖
  • -v 打印每个创建链接的文件名
  • -L 当源文件是软链接文件时,创建的新链接指向该软链接所指向的文件,该选项会创建硬链接
  • -P 当源文件是软链接文件时,创建的新链接指向该软链接本身(默认)
  • -r 创建基于相对路径(默认为绝对路径)的软链接,这在目录结构整体发生移动时,链接仍然有效,该选项需要搭配-s选项
示例: # ln /etc/issue /tmp/issue.hard 为/etc/issue创建硬链接 # ln -s /etc/issue /tmp/issue.soft 为/etc/issue创建软链接

readlink查看软链接的源文件

readlink [选项] 文件名 查看软链接所指向的实际文件路径

  • 默认情况下,命令会直接输出符号链接文件本身所存储的源文件的文件路径,这个路径可能是绝对路径,也可能是相对路径,这取决于软链接创建时的选项
  • -f 输出符号链接所指向的文件或目录的绝对路径。如果符号链接指向另一个符号链接,则会继续解析直到找到最终的源文件或目录。即使路径中的某些目录或文件不存在(这些文件未来可能会由其他程序创建),也返回该路径而不报错
  • -e 输出符号链接所指向的文件或目录的绝对路径,这些路径必须是存在的,否则返回空并报错,该选项适用于要保证整个路径都真实存在的情况
  • -m 类似于-m选项,如果路径中的某个目录或文件不存在,命令会直接将其视为目录,然后返回完整的绝对路径
  • -n 输出的路径末尾不添加换行符,方便与其他命令结合使用
  • -s或-q 静默模式,禁止显示大多数错误消息(默认)
  • -v 输出错误消息

管道文件

管道(pipe)是一种在不同进程之间进行数据传输的通信机制,它允许一个进程写入数据,另一个进程按顺序读取数据,从而实现进程间的通信。管道中的数据是以”流”的形式进行传输,管道的使用能够有效地实现数据流的连接,使得用户能够将多个命令串联起来,形成一个复杂的命令执行流程。管道通信有以下特点:

  • 先进先出:先写入的数据会被先读取,遵循”First In, First Out”原则。
  • 双进程通信:管道允许两个进程之间进行数据传输,一个进程写入数据,另一个(或多个)进程读取数据,读与写可以同步进行
  • 流式数据:管道中的数据被存储于内存的内核缓冲区,数据是一次性传输的,被读取一次后就会消失,是一种流式数据
  • 阻塞行为:为了保证进程间数据传输的有序性和同步性,管道通过阻塞读写操作来协调数据的传输。进程在写入数据时,如果缓冲区已满,进程的写入操作会被阻塞,直到另一个进程从管道中读取数据,腾出缓冲区空间,写操作才会继续。类似的,读操作也会被阻塞,当进程从管道中读取数据时,如果缓冲区为空,进程的读操作会被阻塞,直到有数据写入。如果写入进程已经终止(写端关闭),且管道内的数据已被读完,则读操作会立即返回EOF(End Of File),表示管道结束。

匿名管道

匿名管道的创建完全基于内存,不会在文件系统中生成任何文件或路径,在创建时不分配名称,它只能在有关系的进程(如父子进程)间使用,而不能在任意进程之间通信。匿名管道的生命周期与创建它的进程相关,当创建这个管道的进程结束时,管道也会被关闭,匿名管道只能通过文件描述符来访问。

在C语言中,可以使用系统调用pipe()来创建匿名管道,在命令行中使用管道符|创建的也是匿名管道,此时shell会创建子shell,管道符两侧的命令都将在独立的子shell中并行执行,虽然子shell中运行的命令是独立的进程,但他们是在同一个父shell上下文中执行的,因此它们可以通过管道完成通信。

mkfifo创建命名管道(管道文件)

命名管道(named pipes)通常被直接称为FIFO(First In, First Out的缩写),它会被显式地创建在文件系统中,称为管道文件。管道文件是一种特殊的文件,它虽然在文件系统中拥有文件路径,但数据的存储位置依旧位于内存缓冲区,管道文件本身并不存储数据,管道文件可以通过以下命令创建:

mkfifo [选项] 文件名

  • -m 权限:为创建的管道文件指定权限,接收的参数支持权限的八进制值表示形式(如755),也支持符号模式(如:移除组的写权限g-w,默认为a=rw,即允许所有人读写,可以基于此权限进行删减)

mknod创建设备文件或管道文件

该命令用于让用户手动创建特殊文件,比如字符设备、块设备以及命名管道

mknod [选项] 文件名 文件类型 [参数]

  • -m 权限:为创建的管道文件指定权限,接收的参数支持权限的八进制值表示形式(如755),也支持符号模式(如:移除组的写权限g-w,默认为a=rw,即允许所有人读写,可以基于此权限进行删减)
  • 文件类型有:p(命名管道文件)、c(字符设备文件,如:键盘设备)、b(块设备文件,如:U盘设备)
1.创建一个命名管道文件 mknod newpipe p 2.创建块设备文件 mknod /dev/myblockdevice b 8 1 #8是主设备号,1是次设备号

临时文件

Linux系统提供了一个特殊的目录/tmp,用于存放临时文件。大多数Linux发行版会在系统在启动时自动删除tmp目录下的所有文件,或会周期性清理长期不访问的临时文件,且系统上的任何用户账户都有权限读写tmp目录中的文件,这为用户创建临时文件提供了便利,且不用担心清理工作

创建临时文件

mktemp [选项] [文件名模版.XXXXXX]
  • 使用该命令时,通常会指定一个文件名模板,文件名模板末尾必须包含至少3个(通常6个)X(必须为大写X),mktemp命令在创建该文件时会使用随机字符替换X,以保证临时文件的唯一性。默认情况下,如果文件名模板前未指定路径,命令会在当前目录中创建临时文件或目录,如果指定了路径,则前往指定路径下创建
  • 如果不指定文件名模板,命令将使用默认模板’tmp.XXXXXXXXXX’(10个随机字符),且默认会在/tmp目录下创建临时文件,而不管当前路径如何
  • -p 路径:在指定路径下创建临时文件或目录
  • -t 在 $TMPDIR 环境变量指定的目录中创建文件或目录。如果未设置 $TMPDIR,则在/tmp路径下生成临时文件或目录,返回完整路径名
  • -d 创建临时目录
  • -q 在无法创建临时文件或目录时不产生错误信息
  • -‌-suffix=”字符串”:为生成的文件添加指定后缀
1.在当前目录下创建临时文件 $ mktemp testing.XXXXXX test.Oa6cx4 2. 在tmp目录下创建临时文件,会返回完整路径 $ mktemp -t testing.XXXXXX /tmp/test.Nhy8Ym

临时文件的清理

Linux中的临时文件主要位于两个路径下:

  • /tmp:用于存放短期临时文件
  • /var/tmp:用于存放长期的临时文件,默认情况下,文件可能保留30天或更久

大多数现代Linux发行版使用systemd-tmpfiles来管理临时文件,部分系统可能使用cron定时任务来进行清理。systemd-tmpfiles的配置文件通常位于/usr/lib/tmpfiles.d/tmp.conf/etc/tmpfiles.d/路径下。如:配置文件 /usr/lib/tmpfiles.d/tmp.conf 中的内容可能如下:

# Clear tmp directories separately, to make them easier to override D /tmp 1777 root root 10d D /var/tmp 1777 root root 30d

该配置表示:

  • /tmp 目录中超过 10 天未被访问的文件会被清理
  • /var/tmp 目录中超过 30 天未被访问的文件会被清理

脚本中临时文件的使用

在脚本中创建临时文件时,使用touch、echo等命令创建临时文件有可能带来文件名冲突等问题,且所创建的文件容易受到符号链接攻击,使用mktemp命令创建临时文件是一种更安全的推荐方法

#!/bin/bash # 创建一个临时文件 tempfile=$(mktemp myfile.XXXXXX) ... # 脚本功能 ... # 在脚本退出时删除临时文件 trap "rm -rf $tempdir" EXIT

设备文件

设备挂载参考下文”文件系统挂载与卸载”,这里只介绍Linux内置有特殊用途的设备文件

数据

  • /dev/null 数据”黑洞”,所有写入该文件的数据都会被丢弃;读取该文件会立即返回EOF(文件结束),导致读取为空
  • /dev/zero 提供无限的空字符(\0),可用于初始化文件或内存
  • /dev/full 始终写满,写入返回 ENOSPC 错误,可用于测试磁盘写满场景

随机数生成

以下文件生成的是二进制数据,且包含不可打印字符,通过cat、head命令读取时会显示为乱码(因为终端尝试将其解释为文本字符),因此在使用时通常需转码使用

  • /dev/random 生成来自系统熵池的随机数,会被阻塞,适合对安全性要求极高的场景
  • /dev/urandom 一开始也会根据系统熵池生成随机数,当系统熵池不足时会开始使用算法生成的伪随机数,因此不会阻塞

二者的区别:/dev/random严格依赖系统熵池,系统熵池的数据来自硬件噪声、键盘/鼠标输入等,通过其生成的加密密钥安全性极高,但在虚拟机或嵌入式设备中,熵源可能较少,当系统熵池耗尽时会因熵不足而阻塞。/dev/urandom生成随机数通常更快,它一开始也会根据系统熵池生成随机数,当系统熵池不足时会开始降级为使用算法生成随机数,因此它不会因熵不足而阻塞。在现代Linux内核中,/dev/urandom已经被优化得安全性十足,能满足大部分使用场景,推荐优先使用。

1.从 /dev/urandom 读取16字节随机数据 head -c 16 /dev/urandom | base64 2.随机生成12位密码 < /dev/urandom tr -dc 'A-Za-z0-9!@#$%^&*()_' | head -c 12 或 head -c 30 /dev/urandom | tr -dc 'A-Za-z0-9!@#$%^&*()_' | head -c 12; echo

帮助文件 (manual)

1. 查看完整帮助man

man [命令或配置文件]

  • 查看配置文件的帮助时,直接写文件名,不能加上文件路径,使用文件路径会直接显示文件内容而不是该配置文件的使用说明

man命令返回的手册页一般包括以下信息,但不一定包括所有节,信息通过分页程序显示,分页程序可以通过PageUpPageDown或空格上下翻页,也可以通过上下方向键逐行滚动,或者使用回车键逐行向下查看,查看完毕后可以通过q键退出

内容
Name 显示命令名和一段简短的描述
Synopsis 命令的语法
Confi guration 命令配置信息
Description 命令的一般性描述
Options 命令选项描述
Exit Status 命令的退出状态指示
Return Value 命令的返回值
Errors 命令的错误消息
Environment 描述所使用的环境变量
Files 命令用到的文件
Versions 命令的版本信息
Conforming To 命名所遵从的标准
Notes 其他有帮助的资料
Bugs 提供提交bug的途径
Example 展示命令的用法
Authors 命令开发人员的信息
Copyright 命令源代码的版权状况
See Also 与该命令类型的其他命令

对于命令,man 有多个不同类型的帮助文档,并使用数字区分这些区域(通常为1-9),可以使用 whereis 命令查看该命令在man目录下有几种类型,如果有多个类型,可以使用man [值] [命令]来查看对应帮助。如:1为通常为解释该命令如何使用,5通常为命令对应的说明文档如何阅读。即:使用man 命令man 1 命令为查看命令的帮助,man 5 命令为查看命令说明文档的帮助(具体区域号视命令而定),以下为不同类型内容所包含的内容

区域号 所含内容
1 用户命令和可执行程序的帮助手册
2 系统调用和内核函数的帮助手册
3 C库函数的帮助手册
4 设备文件和特殊文件的帮助手册
5 配置文件的格式和约定的帮助手册
6 游戏的帮助手册
7 杂项(如宏包、约定等)的帮助手册
8 系统管理员手册和管理命令的帮助手册
9 内核例程的帮助手册

2. 查看简短帮助

  • what 命令 只显示命令帮助文档中NAME部分的内容
  • apropos 配置文件 简短查看配置文件作用

3. 查看命令的选项

只查看命令的可选参数选项,不需要查看命令完整帮助信息

命令 --help

4. 查看shell内置命令

有些命令是bash(shell)内置命令而不是Linux的命令,使用上述命令查看不到帮助,可以使用

help 命令

文件系统

介绍

简介

与Windows不同,Linux在路径中不使用驱动器盘符。Windows将物理磁盘驱动器分为盘符(如C盘、D盘),每个盘都会有自己的目录结构,并通过诸如C:\Users\ Administrator \Documents等方式访问文件。

Linux则采用了一种不同的方式,Linux内核采用虚拟文件系统(Virtual File System,VFS),内核将所有安装在PC上的存储设备的文件纳入单个目录结构中,这个目录被称为虚拟目录(virtual directory)。Linux虚拟目录结构只包含一个称为根(root)目录的基础目录。根目录下的目录和文件会按照访问它们的目录路径一一列出,并使用正斜线 /(windows使用反斜线\)来做路径划分。

Linux文件系统结构是从Unix文件结构演进过来的,并遵守文件系统层级标准(filesystem hierarchy standard,FHS),它确定了Linux系统中每个目录的用途和应该包含的内容,并保证不同Linux发行版之间的文件布局是一致的

Linux可用的文件系统

Linux内核支持通过不同类型的文件系统从硬盘中读写数据。除了自有的诸多文件系统外,Linux还支持从其他操作系统(比如Windows)采用的文件系统中读写数据,但内核必须在编译时加入对所有可能用到的文件系统的支持,以下为Linux系统用来读写数据的标准文件系统

文件系统 说明
ext Linux扩展文件系统,最早的Linux文件系统
ext2 第二代扩展文件系统,在ext的基础上提供了更多的功能
ext3 第三代扩展文件系统,支持日志功能
ext4 第四代扩展文件系统(Fourth Extended File System),支持高级日志功能,目前Linux主流的文件系统
tmpfs 一种临时文件系统,常见于类Unix操作系统,使用内存(RAM)作为文件存储区,适合需要高速读写和不需要持久存储的数据情况
devtmpfs 临时设备文件系统,常见于类Unix操作系统,该文件系统会在内存中创建一个区域,用于管理/dev目录下的设备文件,方便动态管理硬盘、网络接口、终端等物理设备,可以简化设备管理,提高系统启动速度
FAT16 用于微软的ms-dos操作系统,Windows最初是作为MS-DOS的一个图形用户界面(GUI)扩展而开发的,但随着技术的进步,Windows操作系统逐渐发展成一个独立的操作系统,从Windows NT 4.0 开始,Windows不再依赖于MS-DOS
VFAT FAT32的扩展版本,在FAT32的基础上加入了长文件名支持功能,名称上实际仍称为FAT32。FAT32是windows98等旧版本windows的主要文件系统,现在广泛用于相机SD卡、U盘等,最大支持的单个文件大小为4GB,最大分区大小为2TB
NTFS 全称为New Technology File System,目前windows主要使用的高级文件系统,广泛用于windows7、10,支持数据加密,文件权限控制,日志记录与恢复等功能,最大支持的单个文件大小为16TB(取决于分区大小),分区大小可达到256TB或更高
hpfs OS/2高性能文件系统
jfs IBM日志文件系统
iso9660 标准CD-ROM文件系统,主要用于CD
minix MINIX文件系统
ncp Netware文件系统
nfs 网络文件系统
proc 访问系统信息
ReiserFS 高级Linux文件系统,能提供更好的性能和硬盘恢复功能
smb 支持网络访问的Samba SMB文件系统
sysv 较早期的Unix文件系统
ufs BSD文件系统
umsdos 建立在msdos上的类Unix文件系统
XFS 高性能64位日志文件系统

文件系统的架构

Linux 文件系统采用了层次化的设计,通常分为以下几层:

  • 虚拟文件系统(Virtual File System,VFS):虚拟文件系统是操作系统内核的一部分,它为不同类型的文件系统提供了统一的接口,屏蔽了底层文件系统的差异性,使Linux能够同时挂载各种文件系统
  • 实际文件系统(File System Implementation Layer):该层实现了具体的文件系统,如 ext4、XFS、Btrfs、FAT32 等,每种文件系统都有其独特的数据结构和实现方式,但它们都通过 VFS 提供一致的接口,向上层应用程序隐藏具体细节
  • 存储设备层(Storage Device Layer):该层包括实际的存储设备(如 HDD、SSD、USB 闪存盘等)及其驱动程序,管理设备的物理 I/O 操作。文件系统将逻辑数据映射到这些物理设备上,通过块设备接口(如 /dev/sda)来访问硬盘的块(block)数据
简单预览: +--------------------+ | 应用程序层 | <---- 用户通过命令或程序操作文件 +--------------------+ | 系统调用层 | <---- 系统调用(如 `open`、`read`、`write`) +--------------------+ | 虚拟文件系统 (VFS)| +--------------------+ | 实际文件系统层 | <---- ext4, XFS, Btrfs, FAT32, NFS 等 +--------------------+ | 存储设备层 | <---- 硬盘、SSD、USB 驱动器 +--------------------+

Linux文件系统都有以下几个重要组成部分:

  • 超级块(Superblock):超级块包含了文件系统的元数据,比如文件系统的大小、块大小、inode 数量、已用和可用的 inode 及数据块等信息。超级块是文件系统的控制信息,通常被加载到内存中,用于文件系统的管理和访问。
  • 索引节点(Inode):Inode是每个文件或目录的描述符,每个文件都有唯一的inode标识符,在文件系统中,文件通过inode号来唯一标识,inode包含文件的元数据,如:
    • 文件类型(普通文件、目录、符号链接等)
    • 文件大小
    • 所有者(用户 ID 和组 ID)
    • 访问权限(读、写、执行)
    • 时间戳(创建时间、修改时间、访问时间)
    • 指向数据块的指针
  • 数据块(Data Block):数据块是文件的实际内容存储区域。每个数据块大小通常为4KB,文件系统通过 inode 中的指针(direct 和 indirect pointers)来定位文件的数据块
  • 目录(Directory):目录是一种特殊类型的文件,它包含了其他文件或子目录的列表。每个目录项包含文件名和对应的inode号。当用户查找一个文件时,系统会先根据目录文件中的inode号找到对应的 inode,再通过inode中的指针找到数据块。
  • 日志(Journaling):大多数现代Linux文件系统(如 ext3、ext4、XFS)都使用日志机制来提高数据可靠性。日志记录文件系统中所有的元数据变化操作,确保在系统崩溃或突然断电时,可以通过重播日志恢复文件系统的完整性。

文件系统的工作流程

  • 文件查找: 当用户要访问某个文件时(如 /home/user/file.txt),系统会按照以下步骤进行查找:
    1. 从根目录 / 开始,找到 home 目录的 inode。
    2. 根据 home 目录 inode 中的数据块指针,找到 user 目录的 inode。
    3. 最终找到 file.txt 的 inode,然后通过该 inode 访问文件的数据块。
  • 文件读操作: 当文件被读取时(例如使用 cat 命令),系统会:
    1. 根据目录结构找到文件的 inode。
    2. 读取 inode 中指向的数据块指针。
    3. 从数据块中读取文件内容,并将其返回给用户。
  • 文件写操作: 当文件被修改或创建时(例如使用 echo 命令),系统会:
    1. 为新文件分配一个 inode,设置文件的元数据(所有者、权限等)。
    2. 分配新的数据块,并写入文件内容。
    3. 更新 inode 中的指针,使其指向新的数据块。
    4. 更新文件系统的超级块信息(例如可用 inode 和数据块数量)。
  • 元数据更新和日志记录:为了防止数据丢失,文件系统通常会先将元数据更新写入到日志区域中,然后再进行实际操作。这种机制被称为 “Write Ahead Logging”。在日志写入成功后,再进行实际的文件写操作,确保在系统故障时能够快速恢复文件系统。

文件的时间戳

在 Linux 系统中,文件的时间戳主要包括以下三种类型:

  • 访问时间(Access Time,atime):文件上次被读取的时间,使用cat、less、head等命令读取文件内容,或通过bash script.sh执行脚本文件,都会更新atime。但认情况下,为了提升性能,大多数 Linux 文件系统(如 ext4)会使用relatime挂载选项,这意味着只有在 atime 比 mtime 或 ctime 旧时,atime 才会更新。因此,某些文件访问操作不会立即反映到atime中
  • 修改时间(Modification Time,mtime):文件内容上次被修改的时间,通过echo、vim、nano和重定向符修改文件内容都会更新mtime
  • 更改时间(Change Time,ctime):文件的元数据(如权限、所有者、文件名等文件属性)上次被更改的时间,通过chmod、chown、chattr修改文件属性,使用mv命令移动、重命名文件都会更新ctime,使用vim,nano修改文件时,编辑器可能会创建临时文件,并使用新文件覆盖原文件,也会更新ctime
  • 创建时间(Birth Time或Creation Time,btime):表示文件首次被创建时的时间,这是一个教新引入的时间戳,因此,一些传统的文件系统不支持该时间戳,一些新的文件系统(如 ext4)也默认不保存创建时间,需要特定文件系统(如 btrfs)或内核版本支持才可以查看

命令

df查看文件系统空间使用情况

GNU提示:df命令仅安装在拥有挂载表的系统上,因此跨平台可移植脚本不应该依赖该命令

df [参数] [挂载点]

  • 默认情况下,命令会输出所有当前已挂载文件系统的信息
  • -a  显示所有文件系统信息,包括特殊文件系统,这些文件系统通常无法直接访问,因此默认不显示
  • -h  将磁盘大小单位换算为KB、MB等单位,以1024作为基数进行换算
  • -H  等价于-‌-si选项,换算单位为K、M等单位,以1000作为基数进行换算
  • -m  以MB为单位显示容量
  • -k  以KB为单位显示容量,默认值
  • -T  显示文件系统类型
  • -i  列出 inode 使用情况信息,而不是块使用情况
  • -l  只列出本地文件系统,默认情况下还会列出远程文件系统
  • -‌-output=项目:只列出指定项目,指定多个项目可以用逗号分隔(如-‌-output=source,target),接收的参数有:source(挂载来源,通常是设备)、target(挂载点)、fstype(文件系统类型)、itotal(inode总数)、iused(已用inode数量)、iavail(可用inode数量)、ipcent(iused除以 itotal的百分比)、size(块总数)、used(已使用的块数)、avail(可用的块数)、pcent(used除以size)、file(文件名,需要在命令行指定)
  • -t 文件系统:只显示某个文件系统的信息,可以指定多个-t选项
df命令会输出以下信息: 1.文件系统名或挂载源 2.能容纳多少个1024字节大小的块 3.已用了多少个1024字节大小的块 4.还有多少个1024字节大小的块可用 5.已用空间所占的比例 6.设备挂载到了哪个挂载点上(挂载点) 如: Filesystem 1K-blocks Used Available Use% Mounted on devtmpfs 234280 0 234280 0% /dev tmpfs 246136 0 246136 0% /dev/shm tmpfs 246136 29192 216944 12% /run tmpfs 246136 0 246136 0% /sys/fs/cgroup /dev/vda1 9778432 3429132 5808684 38% / tmpfs 49228 0 49228 0% /run/user/0
df命令会统计包括一些磁盘碎片在内的空间,而该类空间是被程序占用后释放的碎片空间,需要Linux整理后才能使用,因此df命令统计结果也往往比du命令统计结果大,但更能正确反映系统可用的空间大小

du显示目录或文件大小

通过df命令发现磁盘空间快满时,可以通过du命令查看是哪些文件占用了较大的存储空间

du [参数] [目录或文件名]…

  • 默认情况下,命令会显示当前目录中每个子目录的磁盘块占用数量,并在最后一行输出当前目录总占用数量,该行为会递归进行,即会打印子目录的后代子目录信息,它会以磁盘块为单位来表明每个文件或目录占用了多大存储空间
  • -a 打印每个子目录以及子文件的大小
  • -h 将文件大小单位换算为K、M等单位
  • -k 以K为单位打印占用空间
  • -m 以M为单位打印占用空间
  • -c 在处理完所有文件后,打印总计
  • -s 只统计总大小,不列出子目录和文件
  • -d 值depth:只从当前目录向下统计depth层(文件的层次结构),当前目录为第0层
  • -‌-inodes 列出inode的使用情况,而不是块使用情况
  • -L 显示链接指向的文件或目录的所占用空间大小,而不是链接文件本身
  • -t 值:如果给定的值为正数,则只打印大于等于该值的目录或文件信息,如果值为负数,则只打印小于等于该值的目录或文件,这里的值可以使用kB、k、KiB等单位
  • -‌-time:打印文件或目录的上一次内容修改时间mtime
  • -‌-time=ctime:打印文件或目录上一次属性修改时间ctime
  • -‌-time=atime:打印文件或目录上一次访问时间atime
  • -‌-exclude=正则pattern:递归统计时,跳过与pattern匹配的子目录或文件,如du -‌-exclude=’*.o’ 排除以.o结尾的文件
  • -X 文件名:从该文件中获取需要排除的文件或目录,每一行表示一个或一类文件,可以使用正则表达式,如果文件名为-,表示从标准输入获取
ls命令只统计目录下一级子文件和子目录文件信息大小,而不统计子目录下属文件大小,du命令更能准确统计出子文件、子目录和子目录所含文件的数据大小

文件系统修复

fsck [参数] 分区设备名

  • -a  不显示用户提示,自动修复文件系统
  • -y  功能同-a,部分文件系统仅支持-y

文件系统的挂载与卸载

Linux文件系统将所有的磁盘都并入一个虚拟目录下。在使用新的存储媒体之前(如载入U盘等),需要把它映射到虚拟目录下的某个位置,方便通过虚拟目录直接操作文件和设备,这个步骤称为挂载(mounting)

/etc/fstab文件

/etc/fstab(File System Table)文件用来存储文件系统的静态信息,包括可以挂载的文件系统、挂载点路径、文件系统类型以及它们的挂载选项(如读写权限、是否需要自动挂载等),fsck、mount、umount、swapon、swapoff等命令都会读取该文件作为配置来源

/etc/fstab 文件每行定义一个挂载项,字段直接使用空格或制表符分隔,可以使用#注释行,每行挂载项的语法格式为:
挂载源 挂载点路径 文件系统类型 挂载选项 dump备份 fsck检查顺序

  • 挂载源是指要挂载的设备、远程文件系统、要启用的虚拟内存交换空间等,该参数可以上述挂载源的文件名,或者远程地址(url:路径形式),也可以UUID(如UUID=3a9f…形式),标签名(如LABEL=DATA),这些标签或uuid可以在mkswap(创建虚拟内存交换文件)、fatlabel时指定
  • 挂载点为在文件系统中的挂载路径和文件名,如果文件名包含空格,可以使用\040(空格)和\011(制表符)转义。对于交换空间swap,挂载点应该指定为none
  • 文件系统类型参考”Linux可用的文件系统”,swap表示用于交换空间的文件系统
  • 挂载选项用来控制挂载后文件系统的行为,可以是以下值:
    • defaults 使用内核和文件系统的默认值
    • 控制读写权限,如:ro(只读)、rw(可读写,默认)
    • noauto:表示mount -a(挂载所有配置的文件系统)或swapon -a(启用所有配置的虚拟内存交换空间)时排除该挂载源
    • noatime:不更新文件访问时间atime以提升性能
    • user:允许用户挂载
    • owner:允许所有者挂载
    • sw:表示这是一个交换文件swap
    • nofail:如果此设备不存在,不要输出错误
  • dump备份用来指定是否需要被dump工具备份,0表示不备份,1表示备份
  • fsck检查顺序用来指定启动时文件系统检查顺序,0表示不检查,1表示当前为根分区优先检查(因此对于根文件系统应该指定为1),2表示这是其他分区按顺序检查
根目录与虚拟内存挂载示例: UUID=aecbeedf-6eeb-40f6-b185-03030fc62888 / ext4 defaults 0 1 /swapfile none swap sw 0 0

查询挂载信息

mount显示已经挂载的设备

  • -l显示卷标
mount命令提供如下四部分信息: 1.媒体的设备文件名 2.媒体挂载到虚拟目录的挂载点 3.文件系统类型 4.已挂载媒体的访问状态 如:/dev/vda1 on / type ext4 (rw,relatime,data=ordered) /dev/vda1为设备文件名,该设备挂载在根目录下 /,文件系统为ext4,其余为该设备的访问状态

自动挂载

系统启动时,会根据文件/etc/fstab中指定的信息自动挂载部分文件系统,也可以根据该文件手动执行该过程

mount -a根据配置文件 /etc/fstab 自动挂载

  • -a 挂载所有未挂载的文件系统
  • -aF 会同时挂载所有文件系统
  • -aO 可以在/etc/fstab中为某个文件系统指定特定的挂载选项,并应用这些选项

手动挂载

mount [-t 文件系统] [-L 卷标名] [-o 特殊选项] 设备文件名 挂载点

  • -t 文件系统:挂载指定文件系统,如 ext4、iso9660
  • -L 卷标名:自定义卷标的名字
  • -f 模拟挂载设备,但并不真的挂载
  • -s 忽略该文件系统不支持的挂载选项
  • -r 将设备挂载为只读的
  • -w 将设备挂载为可读写的(默认参数)
  • -v 详细模式,详细说明挂在设备的每一步
  • -n 挂载设备,但不注册到/etc/mtab已挂载设备文件中
  • -s 忽略该文件系统不支持的挂载选项
  • -o 特殊选项:指定挂载的额外选项,以下是几个常用的选项:
参数 说明
ro 以只读方式挂载
rw 以可读写方式挂载
user/nouser 是否允许普通用户挂载文件系统,默认为不允许
check=none 挂载文件系统时不进行完整性校验
loop 挂载一个文件
atime/noatime 访问分区文件时是否更新文件访问时间
exec/noexec 是否允许文件系统中的可执行程序可以运行,默认为exec允许
remount 重挂载已经挂载的文件系统,一般用于修改特殊权限后重挂载
示例: # mount -o remount,noexec /home/ 禁止 /home/分区中的所有可执行程序执行,包括root用户

硬件设备文件名

通过文件名可以判断该设备文件对应的设备,以下说常用的设备文件名

硬件 设备文件名
IDE硬盘 /dev/hd[a-d]
SCSI/SATA/USB硬盘 /dev/sd[a-p]
光驱 /dev/cdrom 或 /dev/sr0
软盘 /dev/fd[0-1]
打印机(25针) /dev/lp[0-2]
打印机(USB) /dev/usb/lp[0-15]
鼠标 /dev/mouse

挂载光盘

为方便文件查找,一般将光盘挂载于根目录下的 /media ,U盘挂载于/mnt目录下,iso9660为光盘默认文件系统,因此-t iso9660 可以省略

mount -t iso9660 /dev/cdrom /media

挂载U盘

  1. fdisk -l查看U盘设备文件名

  2. mount -t  文件系统  /dev/U盘设备文件名  /mnt

linux默认不支持NTFS文件系统(大部分移动硬盘设备使用NTFS文件系统),但可以通过插件提供支持

卸载设备

注意,如果有任何程序正在使用设备上的文件,系统就不允许卸载,而是会提示 device is busy,注意命令不是un开头,没有n
umount 设备文件名或挂载点目录名卸载设备

如果在卸载设备时,系统提示设备繁忙,无法卸载设备,通常是有进程还在访问该设备或使用该设备上的文件。这时可用lsof命令获得使用它的进程信息,然后在应用中停止使用该设备或停止该进程。如:lsof /path/to/device/node,或者lsof /path/to/mount/point

上一篇:Linux用户与权限管理
下一篇:Linux文件操作
z z z z z