Skip to content

树形目录结构

bash
/
├── bin -> usr/bin          			# 二进制可执行文件(软链接到/usr/bin)
├── boot                    			# 内核文件与启动引导文件
├── dev                     			# 设备文件(如磁盘、终端等)
├── etc                     			# 系统全局配置文件
|   ├── hosts							# 主机名映射文件
   ├── sysconfig/network-scripts/		# 系统网卡配置文件所在路径
   └── systemd/system/					# 系统systemd服务文件存储.service
├── home                    			# 普通用户家目录的宿主目录(每个用户独立子目录))
├── lib -> usr/lib          			# 基础共享库(软链接到/usr/lib)
├── media                   			# 可移动设备挂载点(如U盘、光盘)
├── mnt                     			# 临时手动挂载目录
├── opt                     			# 第三方软件安装目录
├── proc                    			# 内核与进程的虚拟文件系统(临时存放内存的目录)
├── root                    			# root用户的家目录
├── run                     			# 运行时数据(如PID文件)
├── sbin -> usr/sbin        			# 管理员用户的二进制命令,系统管理命令(软链接到/usr/sbin)
├── srv                     			# 服务相关数据(如Web、FTP数据)
├── sys                     			# 系统硬件信息的虚拟文件系统
├── tmp                     			# 临时文件(所有用户可写)
├── usr                     			# 用户程序与资源(二级层级结构)
   ├── bin                				# 用户命令
   ├── lib                				# 库文件
   ├── local              				# 本地安装的软件
|   |   ├── bin/                 		# 用户可执行文件(如 nginx、python3)
|   |   ├── lib/                 		# 库文件
|   |   ├── include/             		# 头文件(C/C++开发)
|   |   ├── share/               		# 文档、数据等
|   |   └── src/                 		# 可选:存放源码
   ├── sbin               				# 系统管理命令
   └── share              				# 架构无关数据(如文档、字体)
└── var                     			# 可变文件和临时文件(日志;缓存;临时存储)
    ├── log                				# 系统日志
    ├── cache              				# 应用程序缓存
    └── lib                				# 程序状态数据

/opt和/usr/local/关键区别

特性/opt/usr/local
用途第三方独立软件包本地编译/手动安装的软件
结构每个软件独占子目录仿照 /usr 的层级结构
管理方式由软件供应商提供通常由管理员手动编译安装
典型内容商业软件、预编译二进制开源软件、自定义程序
卸载便利性直接删除对应目录即可需手动清理分散的文件

如何选择

  • 使用 /opt
    • 软件是独立的、预编译的,且希望所有文件集中存放(如 /opt/myapp/bin)。
    • 软件由供应商提供安装脚本(如 ./install.sh)。
  • 使用 /usr/local
    • 从源码编译安装,且需要集成到系统路径(如 /usr/local/bin 已在 $PATH 中)。
    • 软件需要标准的 Unix 文件布局(如 binlib 分离)。

注意事项

PATH 环境变量

/usr/local/bin 通常默认在 $PATH 中,而 /opt/<package>/bin 可能需要手动添加。

bash
export PATH="/opt/myapp/bin:$PATH"

权限管理

/opt/usr/local 通常需要 root 权限写入,但软件运行时可用普通用户权限。

冲突避免

避免将同一个软件同时安装在 /opt/usr/local 中。

/dev特殊设备文件说明

  • /dev/null
    • 写入的数据会被丢弃,读取时返回 EOF(文件结束)。常用于屏蔽命令输出。
    • 示例:command > /dev/null 2>&1
  • /dev/zero
    • 提供无限的空字符(\0),常用于初始化文件或内存。
    • 示例:dd if=/dev/zero of=testfile bs=1M count=100
  • /dev/random/dev/urandom
    • 生成随机数据:/dev/random 阻塞直到收集足够熵,/dev/urandom 非阻塞但安全性稍低。
    • 示例:生成随机密码:head -c 16 /dev/urandom | base64
  • /dev/stdin/dev/stdout/dev/stderr
    • 分别对应标准输入、输出、错误流,常用于重定向。
  • /dev/tty
    • 表示当前终端设备,可用于强制输出到终端(如脚本中交互提示)。
  • /dev/loopX
    • 虚拟设备,用于挂载镜像文件(如 ISO)到文件系统。
  • /dev/sdX/dev/nvmeXnY
    • 物理磁盘设备(如 /dev/sda 为第一块 SATA 硬盘)。

/etc关键配置文件解析

  • /etc/inittab:系统初始化配置文件
  • /etc/passwd:用户账户信息(不含密码,密码在 /etc/shadow 中)。
  • /etc/shadow:存储用户加密密码,仅 root 可读。
  • /etc/group:用户组定义信息。
  • /etc/fstab:定义开机自动挂载的分区和设备。
  • /etc/hosts:本地主机名与 IP 映射,可绕过 DNS 解析。
  • /etc/resolv.conf:DNS 服务器配置。
  • /etc/ssh/sshd_config:SSH 服务端配置(如端口、密钥登录等)。
  • /etc/crontab/etc/cron.d/:系统级定时任务配置。
  • /etc/sudoers:定义用户 sudo 权限(需用 visudo 编辑)。
  • /etc/os-release:系统发行版信息(如版本号、名称)。
  • /etc/null:黑洞文件
  • /etc/zero:零时文件
  • /etc/profile:全局环境变量文件
  • /etc/securetty:登录终端配置文件
  • /etc/systemd/system/:系统systemd服务文件.service存储
  • /etc/sysconfig/network-scripts/:网卡文件存储目录

/var可变文件和临时文件

  • /var/spool/cron/<应户名>:定时任务存放位置
  • /var/spool/mail/<用户名>:系统邮件的保存位置
  • /var/spool/postfix/maildrop/:系统邮件产生的小文件保存位置(邮件服务postfix关闭时产生)

/var用户程序与资源

  • /usr/bin:存放非基础系统命令(与/bin的区别是不包含启动/修复必需命令)
  • /usr/sbin:系统管理员专用命令
  • /usr/lib:程序库文件存储
  • /usr/include:开发头文件
  • /usr/share:项目文档手册存储
  • /usr/local:本地编译安装软件位置
  • /usr/src:内核源码和驱动开发文件

Linux日志体系详解

  • /var/log/syslog/var/log/messages
    • 系统全局日志(取决于发行版)。
  • /var/log/auth.log
    • 认证相关日志(如 SSH 登录记录)。
  • /var/log/kern.log
    • 内核日志(硬件、驱动问题排查)。
  • /var/log/apt//var/log/dnf.log
    • 包管理器日志(安装/更新记录)。

运行时和内核文件

  • /proc/ 目录
    • 虚拟文件系统,实时反映内核和进程状态:
      • /proc/cpuinfo:CPU 信息。
      • /proc/meminfo:内存使用情况。
      • /proc/net/:网络状态(如 /proc/net/tcp)。
  • /sys/ 目录
    • 另一个虚拟文件系统,管理设备、驱动和内核参数。

inode 与 block

文件储存在硬盘上,硬盘的最小储存单位叫“扇区”(sector),每个扇区储存 512 字节。 操作系统读取硬盘的时候,不会一个个扇区的读取,这样效率太低,而是一次性连续读 取多个扇区,即一次性读取一个“块”(block)。这种由多个扇区组成的“块”,是文件存取 的最小单位。“块”的大小,最常见的是4KB,即连续八个 sector 组成一个 block。 文件数据存储在“块”中,那么还必须找到一个地方存储文件的元信息,比如文件的创 建者、文件的创建时间,文件的大小等等。这种储存文件元信息的区域叫做inode,中文译 名为“索引节点”,也叫 i 节点。

NOTE

一个文件必须占用一个 inode,但至少占用一个block

inode文件源信息

索引节点(inode)是文件系统的元数据仓库,每个文件/目录对应唯一inode。

文件的字节数、拥有者的 UID、GID、文件的读写执行权限、时间戳等,但不包含文件 名。文件名是储存在目录的目录项中。

c
struct inode {
  uid_t owner;        // 所属用户
  gid_t group;        // 所属组
  mode_t permissions; // 权限模式
  loff_t size;        // 文件大小
  time_t atime;       // 访问时间
  time_t mtime;       // 修改时间  
  time_t ctime;       // 状态变更时间
  blkcnt_t blocks;    // 占用块数
  // 12个直接指针 + 3级间接指针
}

查看文件的 inode

bash
[root@localhost ~]# stat 1.txt 
  文件:1.txt
  大小:0         	块:0          IO 块大小:4096   普通空文件
设备:253,0	Inode: 131079      硬链接:1
权限:(0644/-rw-r--r--)  Uid: (    0/    root)   Gid: (    0/    root)
上下文:unconfined_u:object_r:admin_home_t:s0
访问时间:2025-05-10 10:21:51.309179685 +0800
修改时间:2025-05-10 10:21:51.309179685 +0800
变更时间:2025-05-10 10:21:51.309179685 +0800
创建时间:2025-05-10 10:21:51.309179685 +0800

Atime、Mtime、Ctime 详解

英文别称中文翻译何时修改查看命令
AccessAtime (访问时间)文件被读取或写入时ls -lu
ModifyMtime (修改时间)文件内容被写入或修改时ls -l
ChangeCtime (改变时间)修改文件名、写入内容、更改权限、创建硬链接时ls -lc
  1. Atime 更新场景
    • 使用 cat 查看文件
    • 程序读取文件内容
    • grep 搜索文件
  2. Mtime 更新场景
    • vim 保存文件
    • echo >> 追加内容
    • 文件被截断 (truncate)
  3. Ctime 更新场景
    • chmod 修改权限
    • chown 修改所有者
    • mv 重命名文件
    • 创建硬链接

修改时间戳

在Linux中,可以使用 touch 命令来修改文件的时间戳。 touch 命令可以同时修改文件的访问时间(atime)、修改时间(mtime)和状态改变时间(ctime)。

以下是一些常用的 touch 命令选项:

  • -a : 只修改访问时间
  • -m : 只修改修改时间
  • -t : 指定具体的时间戳,格式为 [[CC]YY]MMDDhhmm[.ss]
bash
# 修改访问时间和修改时间
touch -t 200003101030.00 text.txt
# 只修改访问时间
touch -a -t 200103101030.00 text.txt
# 只修改修改时间
touch -m -t 200203101030.00 text.txt

目录文件的结构

每个 inode 都有一个号码,操作系统用 inode 号码来识别不同的文件 Linux 系统内部不使用文件名,而使用 inode 号码来识别文件。对于系统来说,文件名 只是 inode 号码便于识别的别称。

black

block是基本存储单位

存储规则

  • 默认块大小:4KB(可通过dumpe2fs查看)

  • 大文件分配策略:

    mermaid
    graph LR
    直接块-->|≤48KB|12个直接指针
    间接块-->|≤4MB|一级间接指针
    双间接块-->|≤4GB|二级间接指针
    三间接块-->|≤4TB|三级间接指针

    ​ inode 一般为 128 字节或 256 字节,每个 inode 中都记录着文件所在的 block 号, 每条记录着block 号的信息占用 4 字节。inode 中关于 block 号的记录一共包含有 12 个 直接、1 个间接、1 个双间接和 1 个三间接。

12 个直接连接

共占用 48 字节磁盘空间,包含着 12 个直接指向 block号的信息,若此文件系统默认的 block 大小为 4KB,则仅仅可以指向 12*4=48KB 大小的文件内容,然而我们的文件若较大时,则需要使用到更多的 block,肯定要多于 12 个 block,进而 有间接、双间接和三间接。

一个间接

inode 中所记录这 4 字节的内容,所指向一个 block,这个 block 中存放的不是真是的文件内容,而是真实文件所存放位置的 block 号信息,若每个 block大小为 4KB,那么可以存放 1024个 block 号信息,1 个间接可以存放的文件大小为:1024*4=4096KB 。

双间接

可以存放更大的文件内容,即在间接的基础上再进行间接,若此时 block 大小为默认的4KB,则 1 个双间接可以存放的文件内容大小为:102410244=4096MB。

三间接

即在双间接的基础上在进行间接,若此时 block 大小为默认的 4KB,则 1 个 三间接可以存放的文件内容大小为:102410241024*4=4096GB。也就是说,在一个 block 大小默认为 4KB 的文件系统中,一个文件最大存储可以达 到 48KB+4096KB+4096MB+4096GB,约为 4100G

查看文件的 inode 号码

bash
ls -i 文件名
stat 文件名
mermaid
graph TD
    subgraph 左侧
        A[文件名]
        B[元信息]
        C[数据]
    end
    subgraph 右侧
        D[目录项]
        E[inode]
        F[block]
    end
    A --> D
    B --> E
    C --> F

对应关系

  • 文件名 ↔ 目录项(存储文件名到inode的映射)
  • 元信息 ↔ inode(存储权限/时间戳等)
  • 数据 ↔ block(实际存储文件内容)

查看文件系统的 inode 与 block

bash
# 文件系统已挂载时查询,查询 inode 总数与已用数量
df -i 设备名
# 需要 ext4 系统类型(文件系统无需挂载)
dumpe2fs -h 设备名
# 需要 ext4 系统类型(文件系统无需挂载)
tune2fs -l 设备名

设置文件系统inode和block大小

bash
mkfs.ext4 -N inode -b 块大小(单位字节) 设备名

解决 inode 耗尽导致的

  • 删除不使用的文件
  • 将文件备份,重新格式化此文件系统,指定较多的 inode 个数

Linux删除文件本质

在Linux系统中,删除文件的本质并非立即擦除磁盘数据,而是没有目录项(硬链接)指向该inode没有进程正在打开该文件,此时系统才会释放inode编号并且标记数据块为可重用。

核心概念

  • Inode(索引节点):存储文件的元数据(如权限、大小、数据块位置等),但不包含文件名或内容。
  • 硬链接(i_nlink):记录指向该文件的目录项数量。当i_nlink=0且无进程引用时,文件才会被真正删除。
  • 进程引用(i_count):若文件被进程打开(如tail -f),即使i_nlink=0,数据仍保留至进程关闭。

删除流程

  • 步骤1:执行rm命令后,系统减少文件的i_nlink值。若i_nlink>0(存在其他硬链接),仅删除当前目录项。
  • 步骤2:检查i_count值。若i_count>0(文件被进程占用),延迟释放数据块和Inode。
  • 步骤3:当i_nlink=0且i_count=0时,系统标记Inode和数据块为可重用,空间被回收

恢复可能性

  • 若文件刚被删除且磁盘未被覆盖,可通过工具扫描残留数据块恢复
  • 若文件仍被进程占用(i_count>0),可通过lsof查找进程并恢复文件

Linux 文件系统链接

在 Linux 中,链接(Link)分为**硬链接(Hard Link)符号链接(Symbolic Link,又称软链接)**两种类型。它们的主要区别在于存储方式、跨文件系统支持以及删除原文件的影响。

硬链接

特点

  • 直接指向 inode,与原始文件共享相同的 inode 和数据块。
  • 不能跨文件系统(因为 inode 只在同一个文件系统内有效)。
  • 删除原文件不影响硬链接(只有当所有硬链接都被删除时,数据才会真正释放)。
  • 目录不能创建硬链接(防止循环引用问题)。

目录特殊性:

  • 每个目录至少包含2个硬链接:
    • 目录自身的链接(.
    • 父目录的链接(..
  • 每增加一个子目录,父目录链接数+1
  • 目录硬链接只统计下一级子目录的数,不统计文件和子子级以下的目录数

创建硬链接

bash
ln 源文件 硬链接名

示例

bash
echo "Hello" > original.txt
ln original.txt hardlink.txt
ls -li  # 查看 inode(硬链接和原文件相同)

符号链接(软链接)

特点

  • 存储的是目标文件的路径,而不是 inode。
  • 可以跨文件系统(因为只是路径引用)。
  • 删除原文件后,软链接失效(变成“悬空链接”)。
  • 可以链接目录

创建软链接

bash
ln -s 源文件 软链接名

示例

bash
echo "World" > target.txt
ln -s target.txt symlink.txt
ls -l

硬链接 vs 软链接

特性硬链接软链接
存储方式直接指向 inode存储目标路径
跨文件系统❌ 不支持✅ 支持
删除原文件仍然可用失效
链接目录❌ 不允许✅ 允许
inode 相同✅ 是❌ 否
文件大小与原文件相同仅存储路径长度

分析日志文件

日志文件的作用

日志文件是用于记录 Linux 系统中各种运行信息的文件,相当于 Linux 主机的“日记”。 不同的日志文件记载了不同类型的信息,如 Linux 内核消息、用户登录事件、程序错误等。 日志文件对于诊断和解决系统中的问题很有帮助,因为在 Linux 系统中运行的程序通常 会把系统消息和错误消息写入相应的日志文件,这样系统一旦出现问题就会“有据可查”。 此外,当主机遭受攻击时,日志文件还可以帮助寻找攻击者留下的痕迹。

日志分类

内核及系统日志

在 6 以上的系统版本中,这种日志数据由系统服务 rsyslog 统一管理,根据其主配置文件/etc/rsyslog.conf中的设置决定将内核消息及各种系统程序消息记录到什么位置。

/etc/rsyslog.conf :

  • “.”:比后面等级要高(包含该等级)的都记录。例如:“*.info”
  • “.=”:只记录该等级。例如:“.=debug”
  • “!”:除了该等级都记录。例如:“!info”
  • “-”:当有记录信息需要记录时,先存到缓存中,到一定大小时一次性写入,以减少对磁盘读写性能
  • 的占用。例如:“-/var/log/maillog”

用户日志

用于记录 Linux 系统用户登录及退出系统的相关信息,包括用户名、登录的终端、登录 时间、来源主机、正在使用的进程操作等

程序日志

有些应用程序会选择由自己独立管理一份日志文件,而不是交给 rsyslog 服务管理,用 于记录本程序运行过程中的各种事件信息。

日志文件的位置

Linux 系统本身和大部分服务器程序的日志文件默认放在/var/log/下。一部分程序共用 一个日志文件,一部分程序使用单个日志文件。而有些大型服务器程序日志由于日志文件不 止一个,所以会在/var/log/目录中建立相应的子目录来存放日志文件,这样既保证了日志文 件目录的结构清晰,又可以快速定位日志文件。 有相当一部分日志只有 root 用户才有权限读取,这保证了相关日志信息的安全性。

常见的日志文件及查看方式

日志文件存放内容查看命令
/var/log/messages内核消息及应用程序的公共日志(启动、I/O错误、网络错误、程序故障等)cattail -f
/var/log/croncrond 周期性计划任务的执行记录catless
/var/log/dmesg系统引导过程中的内核消息(硬件检测、驱动加载等)catdmesg
/var/log/maillog邮件服务(Postfix/Sendmail)的收发记录catgrep "error"
/var/log/lastlog每个用户最近的登录事件lastlog
/var/log/secure用户认证相关事件(SSH登录、sudo使用、密码失败等)catgrep "Failed"
/var/log/wtmp用户登录、注销及系统启动/关机记录(二进制格式)lastwhow
/var/log/btmp失败的登录尝试记录(二进制格式)lastb

日志消息级别

级别英文表示中文翻译意义
0EMERG紧急系统不可用(如内核崩溃、硬件故障)
1ALERT警告必须立即采取行动(如关键服务崩溃、磁盘满)
2CRIT严重严重错误(如数据损坏、系统组件失效)
3ERR错误常规错误(如服务启动失败、网络连接中断)
4WARNING提醒潜在问题(如高内存使用率、配置文件权限不当)
5NOTICE注意正常但需关注的事件(如用户登录、计划任务执行)
6INFO信息一般运行信息(如服务启动完成、定时备份成功)
7DEBUG调试开发/调试信息(如变量值、详细执行流程)
8none不记录(用于关闭日志输出)

日志文件分析

内核及系统消息日志

存放位置

  • /var/log/messages(通用系统日志)
  • /var/log/syslog(Debian/Ubuntu)
  • /var/log/kern.log(内核专用日志)

内容解析

字段说明
时间标签日志生成的日期和时间(如 Jan 1 12:00:00
主机名生成日志的计算机名称(如 hostname
子系统名产生日志的应用程序或服务(如 kernelsshdnginx
消息内容具体事件描述(如 "Failed to mount /dev/sdb1: Invalid filesystem"

常用命令

bash
cat /var/log/messages | grep -i error      # 过滤错误日志
tail -f /var/log/syslog                    # 实时监控日志
journalctl -p err --since "2024-01-01"     # 按优先级过滤(systemd 系统)

用户登录日志

存放位置

日志文件记录内容
/var/log/wtmp用户登录、注销及系统启停记录(二进制格式)
/var/log/btmp失败的登录尝试(如暴力破解)
/var/log/lastlog所有用户最近一次登录信息

查询命令

命令功能示例
users显示当前登录的用户名(每会话一行)users
who显示当前登录用户的详细信息(终端、IP、登录时间)who -a
w显示当前用户及运行的进程w
last查询成功登录记录(按时间倒序)last -n 5 -i(显示最近5次登录的IP)
lastlog显示所有用户最近一次登录时间lastlog -u root(仅查看root用户)
lastb列出失败的登录尝试(用于排查入侵)lastb -a(显示IP地址)

选项说明

  • -a:显示登录来源主机名/IP
  • -d:将IP解析为主机名
  • -R:隐藏主机名/IP
  • -n [数字]:限制显示条目数

应用程序日志

存放位置

  • 通常位于 /var/log/[服务名]/ 目录下(如 /var/log/nginx//var/log/mysql/
  • 源码安装的服务可能自定义路径(如 Apache 默认在 /usr/local/apache2/logs/

示例:Apache 日志分析

bash
# 查看访问日志(实时监控)
tail -f /var/log/apache2/access.log

# 统计访问量最高的IP(前10)
awk '{print $1}' /var/log/apache2/access.log | sort | uniq -c | sort -nr | head -10

# 过滤错误日志
grep -i "500" /var/log/apache2/error.log

日志分析注意事项

可疑现象排查

  • 异常登录
    • 非工作时间登录(如凌晨3点的root登录)
    • 陌生IP地址登录(对比历史记录)
  • 频繁失败登录
    • 同一IP多次尝试失败(lastb 检查)
  • 权限滥用
    • 非管理员用户使用 sudogrep "sudo:" /var/log/auth.log
  • 服务异常重启
    • 检查 /var/log/cron 或服务日志中的非计划重启记录

日志保护措施

bash
# 防止日志被篡改(仅允许追加)
sudo chattr +a /var/log/messages

# 递归保护目录(如 /var/log/nginx/)
sudo chattr -R +a /var/log/nginx/

注意chattr +a 后,需用 rmecho "" > file 会报错,必须通过 logrotate 清理。echo "" >> file追加不报错