开启辅助访问 切换到窄版

打印 上一主题 下一主题

帮你精通Linux:透彻解析Linux的目录树结构

[复制链接]
作者:新天地1688 
版块:
嵌入式操作系统 linux 发布时间:2020-12-8 15:27:27
12190
楼主
跳转到指定楼层
| 只看该作者 回帖奖励 |倒序浏览 |阅读模式
伊甸园中有两棵树,一棵是生命树,另一棵是智慧树(知识书)。Linux系统的文件树目录,无疑是人类历史上结满最多果子,最多智慧的树。这是一棵神奇的树,根Root植于天上,枝叶Branch散于地下,一棵倒置的树。
我们先查看根目录下的24个子目录,进行初步筛选和分析。
$ sudo du -sh /* 2> /dev/null |sort -hr |nl 1 77G /home 2 11G /usr 3 3.3G /var 4 3.3G /root 5 1.2G /opt 6 563M /snap 7 202M /boot 8 12M /etc 9 1.5M /run 10 208K /tmp 11 16K /lost+found 12 8.0K /media 13 8.0K /dev 14 4.0K /srv 15 4.0K /mnt 16 4.0K /cdrom 17 0 /sys 18 0 /sbin 19 0 /proc 20 0 /libx32 21 0 /lib64 22 0 /lib32 23 0 /lib 24 0 /bin通过观察,我们合并同类项,并用排除法做初步筛选处理。

  • lib, lib32, lib64, libx32分别针对32位和64位的操作系统,功能相同,合并同类项,只留下/lib;
  • cdrom目录是历史遗留的古董遗迹,当今的计算机不再使用光盘,将其删掉;
  • lost+found 失物招领目录,用于存储当文件系统发生错误时的遗失片段,使用标准的ext2/ext3档案系统格式才会产生的一个目录,也将其排除;
  • snap目录是Ubuntu独有的包管理目录,也将其排除。
经过初步处理,我们将4个lib目录合并同类项成一个,排除掉另外三个目录;从24个目录中减去6个目录,剩下18个需要我们记住并认真研读。
$ tree -L 1 / |grep -v -e lib -e lost -e cd -e snap |nl -v 0 0 / 1 ├── bin -> usr/bin 2 ├── boot 3 ├── dev 4 ├── etc 5 ├── home 6 ├── lib -> usr/lib 7 ├── media 8 ├── mnt 9 ├── opt 10 ├── proc 11 ├── root 12 ├── run 13 ├── sbin -> usr/sbin 14 ├── srv 15 ├── sys 16 ├── tmp 17 ├── usr 18 └── var按照Linux的上电启动顺序,对上述18个目录作如下分类:
五类18个目录
分类的简要逻辑:
第一类,Linux从boot目录启动之后便开始boom宇宙大爆炸,所有生成的进程保存在/proc/目录下,而系统进程的变量数据写入/run/,最后系统的手伸向了外接设备,相关信息在/sys目录;
第二类动态程序是第一类中的活的进程的出处,按照权限和优先级分别为:sbin,bin,lib,opt;
第三类是第二类的后勤保障部队,设置运行程序的参数和监控其运行状态;
第四类静态文件与第二类的动态程序相呼应;
第五类设备是Linux系统触手的最末端。
第一类囊括四个子目录/boot, /proc, /run, /sys
1.0 /boot/
我们在前文详细阐述了BIOS/MBR模式启动过程,第一股电流流遍主板之后首先到达BIOS所在的芯片,BIOS硬盘自检完毕后将权限交给Grub,再由Grub加载linux内核。

Linux中一切皆为文件,上述启动过程并非只是想象的抽象,它们都有肉身的实体文件。
$ tree -L 1 -s -h /boot/boot├── config-5.3.0-42-generic├── efi├── grub├── initrd.img -> initrd.img-5.3.0-42-generic├── initrd.img-5.3.0-42-generic├── memtest86+.bin├── System.map-5.3.0-42-generic├── vmlinuz -> vmlinuz-5.3.0-42-generic├── vmlinuz-5.3.0-42-generic1.1 /boot/efi
上图中有文件 efi,可以将其简单理解为 BIOS 的升级版,全称为 Extensible Firmware Interface;深入查看其结构:
$ sudo tree -L 3 -s -h /boot/efi/boot/efi├── BOOTLOG└── EFI ├── APPLE │ └── CACHES ├── BOOT │ ├── BOOTX64.EFI │ ├── fbx64.efi │ └── mmx64.efi └── ubuntu ├── BOOTX64.CSV ├── grub.cfg ├── grubx64.efi ├── mmx64.efi └── shimx64.efi1.2 /boot/grub
$ sudo tree -L 1 -s -h /boot/grub/boot/grub├── fonts├── gfxblacklist.txt├── grub.cfg├── grubenv├── unicode.pf2└── x86_64-efi1.3 /boot/vmlinuz
加载的内核也是在/boot/目录下
$ sudo ls -lh /boot/vmlinuz-5.3.0-42-generic-rw------- 1 root root 11M Feb 28 13:40 /boot/vmlinuz-5.3.0-42-generic这个只有11M的文件就是如雷贯耳的Linux内核,操作系统最核心的部分竟然只有区区11M,忍不住要高声赞美。
我们可以double-check Linux内核的版本:
$ uname -r5.3.0-42-generic/boot小结:
Linux的启动过程的三个阶段: BIOS自检 —> Grub引导程序 —> 加载内核, 都在/boot/目录之下。而启动之后的过程犹如宇宙大爆炸。
2./proc/
proc是一个虚拟的神奇目录,它读取内存的数据。换言之,在Linux系统中,不仅磁盘,就算是内存,我们都可以伸手触摸到。
计算机boot起来,从init这个原点出发,开启了宇宙大爆炸的进程。子目录/proc/ 记录了爆炸过程中生成的所有星系的实时数据与状态。
每个进程都有一个独一无二的,以进程的ID命名的子目录。
以我当前正在使用的的进程Emacs编辑器为例:
该进程id为2750,我们可以从/proc目录中一睹其真容:

/proc/2750/cwd -> /home/spiritme 为指向当前工作目录
/proc/2750/exe -> /usr/bin/emacs-gtk 是指向emacs程序的软连接
/proc/2750/task 保存当前进程中所每一个现成的相关信息。
$ ls -l /proc/2750/tasktotal 0dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:23 2750dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:23 2760dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:23 2766dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:23 2773dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:23 2774dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:41 4299dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:41 4300dr-xr-xr-x 7 spiritme spiritme 0 Jun 10 18:23 7764当我们查看当下程序的树状依赖关系的时候,pstree正是从/proc/目录读取数据。
$ pstree -asp -U 2750systemd,1 splash└─emacs,2750 ├─{emacs},2760 ├─{emacs},2766 ├─{emacs},2773 ├─{emacs},2774 ├─{emacs},7764 ├─{emacs},4299 └─{emacs},4300结果中我们看到了emacs所运行的所有的线程的信息,就是从/proc/2750/task中读取的。 另外我们注意第一行 systemd,1 splash,从 systemd 这个一号程序 开始爆炸向外飞溅(splash)。
进程的信息之外,/proc/ 目录下还有其他有意思的内容:
$ ls /proc |grep infobuddyinfocpuinfomeminfopagetypeinfoslabinfovmallocinfozoneinfo从中,我们可查看cpu信息和内存信息:
$ cat /proc/cpuinfo |head # 查看CPU信息processor : 0vendor_id : GenuineIntelcpu family : 6model : 69model name : Intel(R) Core(TM) i5-4258U CPU @ 2.40GHzstepping : 1microcode : 0x25cpu MHz : 1297.982cache size : 3072 KBphysical id : 0$ cat /proc/meminfo |head # 查看内存信息MemTotal: 3936648 kBMemFree: 583552 kBMemAvailable: 801528 kBBuffers: 32172 kBCached: 929400 kBSwapCached: 34752 kBActive: 2116536 kBInactive: 914844 kBActive(anon): 1919756 kBInactive(anon): 722688 kB3./run/
/run 一个临时文件系统,存储系统启动以来,系统进程的变量数据,比如文件锁、进程ID或者套接字等等。既然是临时文件,系统重启之后,所有数据都会删除。
查看守护进程mysqld的信息:
$ ls -l /run/mysqldtotal 8srwxrwxrwx 1 mysql mysql 0 Jun 10 14:44 mysqld.sock-rw------- 1 mysql mysql 5 Jun 10 14:44 mysqld.sock.locksrwxrwxrwx 1 mysql mysql 0 Jun 10 14:44 mysqlx.sock-rw------- 1 mysql mysql 6 Jun 10 14:44 mysqlx.sock.lock预告一句第三类目录下的/var/run是指向该目录的软连接。
4./sys/
/sys/ 与 /proc/ 相同,是一个虚拟目录,包含连接到计算机的设备,驱动,以及某些内核功能。
$ tree -L 1 /sys/sys├── block├── bus├── class├── dev├── devices├── firmware├── fs├── hypervisor├── kernel├── module└── power第一类小结
计算机从 /boot 目录的 efi,grub,kernel 按顺序启动;启动后从/proc目录记录生成的程序的实时运行状态数据,而系统程序的变量数据存放在 /run中,此时Linux开始向外伸出手,通过驱动管理外部设备的数据写入 /sys目录。
计算机从/boot目录启动之后,/boot/proc记录了所有运行程序的状态与信息,那么程序是从哪里来的呢?他们主要来自于四个目录,分别是/sbin, /bin, /lib,/ lib和/opt
先用Tree命令查看:
$ tree -L 1 / |grep -e 'lib' -e 'bin'├── bin -> usr/bin├── lib -> usr/lib├── lib32 -> usr/lib32├── lib64 -> usr/lib64├── libx32 -> usr/libx32├── sbin -> usr/sbin观察输出结果,很容易发现根目录下的程序文件都是指向 /usr/ 的软连接
因此这一类中包括五大目录,分别为 /usr,/usr/sbin, /usr/bin, /usr/lib 和 /opt。
1./sbin --> /usr/sbin
sbin 顾名思义 superuser-binary。目录下的程序必须使用 sudo 获取 root
权限才能使用。目录下有磁盘格式化(mkfs)、磁盘分区(fdisk)和网络配置(ifconfig)等命令。
如果使用不当,会造成难以挽回的致命故障。
尤为关键的是,内核文件加载以后,系统开始运行的第一个程序(一号程序)就在该目录下,即 /sbin/init。
我们看到,如今绝大多数Linux版本的一号程序是 systemd。
2./bin --> /usr/bin
/bin/ 目录是最基础也是我们最熟悉的目录。Gnu/Coreutils和linux-utils的程序大部分都在这里。
$ tree -h /bin/ |grep -e mv$ -e rm$ -e touch -e echo -e find$ -e ^du -e tree$├── colrm├── echo├── find├── frm -> /etc/alternatives/frm├── ipcrm├── ippfind├── kcm-touchpad-list-devices├── lessecho├── lprm├── mkzftree├── mv├── pgmnorm -> pnmnorm├── pnmnorm├── ppmnorm -> pnmnorm├── pstree├── pstree.x11 -> pstree├── rm├── setterm├── smbtree├── testparm├── touch├── transform├── tree/bin 目录下的程序是全球开源项目的起点,即Richard Stallman开创的GNU项目。
3./lib -->/usr/lib
lib即libraries,目录中存储的是/bin和/sbin中二进制文件(应用程序)需要的库文件。他们之间是一一对应的关系。
$ tree -h -L 2 /bin/gcc /lib/gcc/bin/gcc /lib/gcc├── i686-linux-gnu│ └── 9└── x86_64-linux-gnu └── 9/4.opt/
opt即optional pacakages。用户自己安装的程序在该目录下。
比如我安装的百度网盘和google-chrome浏览器
$ tree -h /opt |grep -e google -e baidu├── baidunetdisk│ ├── baidunetdisk├── google│ │ └── google-chrome│ ├── google-chrome5./usr/include
最后介绍一个不直接在根目录下,但却极为重要的目录 /usr/include。C/C++头文件都在这里。
$ tree -h -L 1 --sort=size /usr/include | head -n 20/usr/include├── elf.h├── zlib.h├── linux├── uv.h├── expat.h├── unistd.h├── pthread.h├── stdlib.h├── tgmath.h├── wchar.h├── stdio.h├── netdb.h├── argp.h├── regex.h├── obstack.h├── langinfo.h├── string.h├── features.h小结
根目录下的动态程序仅仅是软连接,实际指向的是/usr目录。从重要性和权限的视角,我们依次介绍了 /sbin /bin 以及二者的支持库 /lib,接着介绍了存放第三方软件的 /opt目录,最后以 /usr/include这个存放C/C++头文件的目录收尾。
总计有 /usr /sbin /bin /lib /opt 五个根子目录外加/usr/include。
第三类目录是第二类动态程序目录的后勤保障部队。程序的运行不能如脱缰野马,也不能如断线的风筝,自顾自的运行,不受控制。就如维护一架机器的运转,我们需要时时调整参数,常常查看其运行状态和故障报告 。
该类有两个子目录:/etc和/var
1./etc/
etc 这三个字母代表的原初含义是 "et cetera",真让人看得一头雾水。好在当今,我们可以将其简单的理解为 'edit to config' 的缩写。换言之,我们在此目录下编辑和修改配置。
操作系统和应用程序的配置文件通常都统一存储在此处。
比如最著名的ssh的配置,数据库的配置,bash的配置,cron的配置,X11的配置等等
$ tree -h -L 1 /etc |grep -e ssh -e sql -e bash -e cron -e init -e X11 -e systemd├── anacrontab├── bash.bashrc├── bash_completion├── bash_completion.d├── cron.d├── cron.daily├── cron.hourly├── cron.monthly├── crontab├── cron.weekly├── cryptsetup-initramfs├── init├── init.d├── initramfs-tools├── mysql├── postgresql├── postgresql-common├── resolv.conf -> ../run/systemd/resolve/stub-resolv.conf├── ssh├── systemd├── X11我们扫一眼ssh的目录结构:
$ tree -h /etc/ssh/etc/ssh├── moduli├── ssh_config├── sshd_config├── ssh_host_ecdsa_key├── ssh_host_ecdsa_key.pub├── ssh_host_ed25519_key├── ssh_host_ed25519_key.pub├── ssh_host_rsa_key├── ssh_host_rsa_key.pub└── ssh_import_id再次强调/etc 这三个字母是 edit to config 的缩写。
2./var/
从/etc目录,我们调整机器的运行参数;而从 /var/ 目录我们实时掌握机器的运行状态报告。也就是说,此处存放程序的数据和日志。
$ tree -L 1 -h --sort=size /var/var├── backups├── cache├── crash├── lib├── local├── log├── mail├── metrics├── opt├── snap├── spool├── tmp├── lock -> /run/lock└── run -> /run上图中的最后一行,我们看到 run 指向了 /run 目录,程序的运行数据在逻辑上归类到此处。同时也看到了log,mail等记录运行状态的日志文件。
详细查看log的目录结构
$ tree -L 1 -h --sort=size /var/log |grep -v -e gz -e old -e 1$/var/log├── boot.log├── syslog├── wtmp├── mail.log├── kern.log├── lastlog├── bootstrap.log...├── private├── samba├── sysstat├── unattended-upgrades├── btmp├── gpu-manager.log├── apport.log├── alternatives.log├── gufw.log├── vbox-setup.log├── mail.err├── sddm.log├── ubuntu-advantage.log└── ufw.log当我们dmesg查看内核运行状况的时候,
dmesg -H就是从 kern.log 读取日志
$ tail /var/log/kern.logJun 10 17:01:44 alpha kernel: usb 2-3: device not accepting address 8, error -62Jun 10 17:01:44 alpha kernel: usb usb2-port3: attempt power cycleJun 10 17:01:50 alpha kernel: xhci_hcd 0000:00:14.0: Timeout while waiting for setup device commandJun 10 17:01:52 alpha kernel: IPv6: ADDRCONF(NETDEV_CHANGE): wlp3s0: link becomes readyJun 10 17:01:56 alpha kernel: xhci_hcd 0000:00:14.0: Timeout while waiting for setup device commandJun 10 17:01:56 alpha kernel: usb 2-3: device not accepting address 9, error -62Jun 10 17:02:01 alpha kernel: xhci_hcd 0000:00:14.0: Timeout while waiting for setup device commandJun 10 17:02:07 alpha kernel: xhci_hcd 0000:00:14.0: Timeout while waiting for setup device commandJun 10 17:02:07 alpha kernel: usb 2-3: device not accepting address 10, error -62Jun 10 17:02:07 alpha kernel: usb usb2-port3: unable to enumerate USB device/var/ 将会是我们日后工作打交道最多的目录。有种说法,程序员读log水平最能衡量其编程的水平。
小结
第三类中的两个目录 /etc/ 构建程序的运行环境,调整参数和配置;/var/ 监控程序的实时运行状态。
该分类与第二类动态程序遥相呼应,包含/root, /home, /tmp, /srv四个子目录。
1./root
/root为管理员的主目录,即root用户的Home目录。
$ sudo ls -al /roottotal 44drwx------ 7 root root 4096 Jan 29 08:16 .drwxr-xr-x 20 root root 4096 Nov 22 2019 ..drwxr-xr-x 26 root root 4096 Oct 20 2019 anaconda3-rw------- 1 root root 24 Jan 23 06:12 .bash_history-rw-r--r-- 1 root root 3557 Oct 20 2019 .bashrcdrwxr-xr-x 5 root root 4096 Jan 29 08:22 .cachedrwxr-xr-x 2 root root 4096 Oct 20 2019 .condadrwx------ 4 root root 4096 May 10 12:24 .configdrwx------ 3 root root 4096 Nov 13 2019 .local-rw------- 1 root root 842 Dec 4 2019 .mysql_history-rw-r--r-- 1 root root 148 Aug 28 2019 .profile2./home
/home 为用户的主目录,linux是多用户操作系统,因此每个用户都对应一个以其账户名命名的主目录。本目录我们最为熟知,不再赘述。
3./tmp
/tmp/ 目录用存储临时文件。这些文件关机重启后会自动删除。
比如当我们在ipython的交互界面中,键入it调出编辑器,就会自动生成一个python临时文件。
4./srv
/srv 即service,该目录存放一些服务器启动之后需要提取的数据。当linux作为服务器时,网站的HTML文件存放在 /srv/http(或 /srv/www);运行 FTP 服务器,相关文件放在 /srv/ftp。
小结
与第二类的动态程序相呼应,第四类的四个目录 /root,/home,/tmp,srv 归类为静态文件,用作存储数据与资料。
Device分类包含dev, media, mnt三个子目录。
1&2 /media 和 /mnt
/media 目录下为系统自动识别挂载的设备(比如优盘或者外接硬盘等),与之相对应的是 /mnt 目录下是用户手动挂载设备到该目录下面,作为临时挂载点。
当然这只是我们应当遵循的惯例。
3./dev/
dev即 device。这是一个神奇的目录,存放的是外接设备。在linux中,一切都是文件,因此访问文件的方式与访问设备的方式是相同的。
可以看到外接磁盘
$ ls -l /dev |grep sdbrw-rw---- 1 root disk 8, 0 Jun 10 05:22 sdabrw-rw---- 1 root disk 8, 1 Jun 10 05:22 sda1brw-rw---- 1 root disk 8, 2 Jun 10 05:22 sda2brw-rw---- 1 root disk 8, 16 Jun 10 05:22 sdbbrw-rw---- 1 root disk 8, 17 Jun 10 05:22 sdb1可以看到总线和CPU
$ ls -lh |grep -e bus -e cpudrwxr-xr-x 3 root root 60 Jun 10 05:21 busdrwxr-xr-x 2 root root 60 Jun 10 05:21 cpucrw------- 1 root root 10, 59 Jun 10 05:22 cpu_dma_latency可以看到系统的文件I/O接口
$ ls -l |grep stdlrwxrwxrwx 1 root root 15 Jun 10 05:21 stderr -> /proc/self/fd/2lrwxrwxrwx 1 root root 15 Jun 10 05:21 stdin -> /proc/self/fd/0lrwxrwxrwx 1 root root 15 Jun 10 05:21 stdout -> /proc/self/fd/1还可以看到终端(Terminal)等
$ ls -l |grep tty | headcrw--w---- 1 root tty 5, 1 Jun 10 05:22 consolecrw-rw-rw- 1 root tty 5, 2 Jun 10 11:27 ptmxcrw-rw-rw- 1 root tty 5, 0 Jun 10 05:22 ttycrw--w---- 1 root tty 4, 0 Jun 10 05:22 tty0crw--w---- 1 root tty 4, 1 Jun 10 05:22 tty1crw--w---- 1 root tty 4, 10 Jun 10 05:22 tty10crw--w---- 1 root tty 4, 11 Jun 10 05:22 tty11crw--w---- 1 root tty 4, 12 Jun 10 05:22 tty12crw--w---- 1 root tty 4, 13 Jun 10 05:22 tty13crw--w---- 1 root tty 4, 14 Jun 10 05:22 tty14同时,dev还有一些有意思的目录,比如 /dev/null /dev/random 等
$ ls -lh /dev |grep -e null -e random -e zerocrw-rw-rw- 1 root root 1, 3 Jun 10 14:44 nullcrw-rw-rw- 1 root root 1, 8 Jun 10 14:44 randomcrw-rw-rw- 1 root root 1, 9 Jun 10 14:44 urandomcrw-rw-rw- 1 root root 1, 5 Jun 10 14:44 zero本文的写作初衷一方面简要介绍Linux的树状目录结构,同时也颇具野心,希望你读罢此文,就能永久性记住Linux文件系统的一级目录的全部18个文件,不必再读第二遍。
我们按照Linux系统启动的顺序,分18个子目录为五类。
第一类,Linux从boot下启动读取EFI, Grub并加载内核,之后便开始boom宇宙大爆炸,所有生成的进程保存在/proc/目录下,而系统进程的变量数据写入/run/,最后系统的手伸向了外接设备,相关信息在/sys目录;
第二类动态程序是第一类中的活的进程的家乡,按照权限和优先级分别为:sbin,bin,lib,opt;
第三类是第二类的后勤保障部队,/etc 调整运行程序的参数和/var监控其运行状态;
第四类静态文件与第二类的动态程序相呼应;
第五类设备是Linux系统触手的最末端。
总结表格如下:

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?立即注册

回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

快速回复 返回顶部 返回列表