(2020.11.12 Wed)
路径和文件
文件和文件夹构成了一个文件系统(file system)。Linux文件系统是一个树状结构,整个文件系统有一个共同的起点,树状结构的顶端,也就是根目录(root)用/表示。
文件树的末端可能是文件,用于存储数据。树上的节点还可能是一个目录,提供从属关系。比如/home/pi/username/file.txt中的目录pi是home的子目录(child directory),home是pi的父目录(parent directory)。从pi往下,构成了一个由单一起点的子文件树。
找到一个文件,需要知道从根目录开始到该文件的所有目录名,沿途目录名构成了一个路径。file.txt的完整路径也就是绝对路径是/home/pi/username/file.txt。
目录directory
目录把文件组织起来,目录本身也是一种特殊的文件,可使用file命令获取文件类型。
$file /home/pi/username #查看该路径文件的类型
$/home/pi/username: directory #返回结果,directory文件
$file /home/pi/username/file.txt #作为对比,查看file.txt的文件类型
$/home/pi/username/file.txt: ASCII text #返回ASCII文本类型
目录文件中的内容以条目形式存在,包含以下条目:
.. 指向父目录
. 指向当前目录
比如打开当前文件夹下的文件file.txt和打开父目录下的文件1.txt
$cat ./file.txt #打开当前文件夹下的文件
$cat ../1.txt #打开父目录下的文件1.txt
一个目录文件中还有属于该目录文件的文件名,如/home/pi/username中有如下内容
../
./
file.txt
Linux系统运行时会维护一个名为工作目录(present working directory)的变量。用pwd指令确定当前目录,实际上就是Shell的工作目录。而所谓‘变换目录’,就是把一个新的目录存入该变量中。比如
$cd /home/pi
相当于把pwd变量中储存的值,变换为/home/pi。
硬链接Hard link
当文件目录中增加一个文件的条目时,就建立一个指向文件的硬链接(hard link)。有了硬链接,这个文件就纳入了文件系统中。一个文件允许出现在多个目录中,也就是有多个硬链接。文件拥有的硬链接数目,称为文件在整个系统中的链接数(link count)。该数字为 0时,说明孤立于文件系统之外,这样的文件会被Linux系统删除。一般情况下文件的链接数为1。删除硬链接的命令
$unlink file.txt #删除硬链接数目到0,等效于删除文件
给一个文件在新的目录下建立硬链接,则链接数超过1。用ln命令创建硬链接。
$ln file.txt /home/pi/xxx/another_file.txt #从当前文件夹复制到另一个文件夹,并更名
上面指令复制file.txt到另一个文件夹并更名,但实际上这两个文件是容一个文件,因此对其中任何一个文件的修改,也会出现在另一个文件中。
删除上面的another_file.txt可用unlink
$unlink another_file.txt
还可以通过找到another_file.txt的文件夹找到该文件,使用rm命令删除该文件。实际上,在Linux系统中rm和unlink命令的功能相同。
软链接Soft link
同一个文件的多个硬链接,会破坏树状的文件系统。Linux不鼓励手动创建硬链接。如有必要,可使用软链接(soft link),在多个目录下创建指向同一个文件的链接。
软链接不影响文件的链接数,它本质上是一个文件,类型为symbolic link。在该文件中,包含有链接指向的文件的绝对路径。当读写该文件时,Linux会根据软链接中的绝对路径把读写操作导向软链接所指向的文件。Linux的软链接就是Linux的快捷方式。创建软链接的指令是在ln加上-s选项
$ln -s file.txt /home/pi/file-link.txt #创建软链接
$file file-link.txt #查看软链接文件的类型
file-link.txt: symbolic link to '/home/pi/file.txt'
用文本编辑器比如nano编辑软链接文件file-link.txt,相关的读写操作也会反映在原文件file.txt中。与硬链接不同的是,软链接不影响文件的链接数,不会破坏文件系统的树状结构。
软链接本身是一个文件,但 很多时候 又会指代一个原始文件。这种双重身份有时带来困惑。用nano编辑软链接,该操作也会跟随连接指引,作用于原文件。如果用rm删除软链接,删除操作不会跟随软链接,原文件依然存在。一个命令是否跟随链接指引,由命令的程序 决定,在大多数情况下,对文件本身的操作,如读写数据和复制文件,会跟随指引。而对涉及文件所属目录的操作,如删除、移动等,则不会跟随指引。
文件操作
touch指令创建一个空的普通文件:
$touch empty.txt
目录操作
$mkdir good #创建目录good
$rmdir good #删除目录good
复制从某个目录开始的整个子文件树
$cp -r doc doc-copy #从doc开始的整个子文件树都将复制到/home/pi/doc-copy
$rm -r doc-copy #删除子文件树
移动文件的指令mv,整个操作过程只涉及两个目录文件。
$mv file.txt /home/pi/file1.txt #当前文件夹中的file.txt移动到/home/pi文件夹中成为file1.txt
文件搜索
find命令会递归的遍历文件系统,搜选出符合条件的文件。执行find命令时,还可以说明想要对目标文件进行的操作。命令的基本用法: find path ...[expression]
参数path是需要搜索的目标目录。如果有多个目标路径,可以将多个路径依次列出。expression是一个可选的表达式,说明要对目标文件进行的操作。表达式由主操作(primary)和运算(operand)组成。
例如,用find命令打印硬盘上所有文件后缀名为.c的文件。
$find / -name "*.c"
可用-not为筛选性操作取反。
$find . -not -name "*.c"
输出当前目录所有后缀名为.c文件的详细信息
$find . -name "*.c" -ls
相比之下,locate命令要比find命令精简很多,也能根据文件名来寻找文件。
$locate grep #查找名为grep的文件
$locate -i l*t #-i表示忽略大小写,找到所有l开头t结尾的文件
与find指令不同,locate查找文件不是实时的,这一点和实时遍历文件树的find命令不同。文件系统的信息提前存于一个数据库,locate命令在这个数据库中查找文件。可以用下面的命令来更新文件系统信息的数据库
$sudo updatedb
(2020.11.14 Sat)
/boot和树莓派启动
/boot下挂在了FAT32格式的启动分区,里面的文件用于树莓派的开机启动。
计算机常见的启动方式
接通电源,计算机自动从主板的BIOS上读取其中所存储的程序。BIOS知道连接在主板上的硬件。从默认存储设备中读取最开始512字节的数据,即所谓的MBR(master boot record)。用户可以通过BIOS配置,从其他数据存储设备中找到MBR。通过MBR,计算机知道从该存储设备的哪个分区来找引导加载程序。引导加载程序存储有操作系统的相关信息,比如操作系统名称、内核所在位置等。随后引导加载程序加载内核,操作系统开始工作。
树莓派的开机方式
有别于普通计算机。树莓派是一块集成电路板,无主板和BIOS。电路板上携带者启动程序。板载程序会挂载FAT32的启动分区,并运行其中的引导程序bootcode.bin。它负责下一阶段的启动工作,从SD卡找到GPU固件start.elf,将固件写入GPU。GPU在start.elf的指引下,会读取系统配置文件config.txt和内核配置文件cmdline.txt,并启动内核文件kernel.img。内核加载成功时,处理器开始工作,系统启动。
无论哪种开机方式,都可以看成小程序加载大程序,相继唤醒硬件。内核加载成功后,Linux系统开始工作,系统还会做一些准备工作,让系统更好用。
启动内核后系统都做了些什么
首先会预留运行所需的内存空间,然后通过驱动程序检测计算机硬件,以知道哪些可用。随后会启动init进程。至此,内核完成了启动阶段的工作。init进程会运行一系列初始脚本,用于准备操作系统。
- 设置计算机名称、时区等
- 检测存储器
- 挂载存储器
- 清空临时文件
- 设置网络
- 启动其他后台进程
这些做好之后,系统就准备好了,但无法登陆。init进程会给出登陆对话框/图形化登录界面。登陆后就是Shell或图形化的用户界面了。
应用程序相关
Linux中的应用程序都编译成二进制的可执行文件,位于名为bin的目录下,在根目录下。该文件夹下有系统运行必须的应用程序
1 | 2 | 3 | 4 | 5 | 6 |
---|---|---|---|---|---|
bash | cat | chmod | cp | date | echo |
expr | kill | ln | ls | mkdir | mv |
pwd | rm | rmdir | sleep | test | unlink |
根目录/sbin下保存了系统启动、修复和恢复所需的应用程序
1 | 2 | 3 | 4 | 5 |
---|---|---|---|---|
fdisk | hwclock | ifconfig | reboot | shutdown |
/usr下的/usr/bin目录存放了次要一些的应用程序,比/bin的程序多的多,通过apt-get安装的程序大多安在这里,比如文本编辑,编译器,数据库等。
1 | 2 | 3 | 4 | 5 | 6 |
---|---|---|---|---|---|
cut | diff | free | gcc | head | locate |
man | make | nano | nice | sftp | ssh |
tail | uniq | vi | wc | which | who |
/usr/sbin下也存放了次要的维护程序,比如cron。另外/usr/local/bin和/usr/local/sbin保存了用户自己手动编写或手动编译安装的应用程序。
二进制文件的dependency文件分布于/lib, /usr/lib, /usr/local/lib中。/usr/include和/usr/local/include包含有头文件。
/etc与配置
/etc保存配置文件,可影响系统和应用程序的行为。其中关键的操作系统配置文件如下表
路径 | 功能 |
---|---|
/etc/default/locale | 本地设置, e.g., 语言、字符编码 |
/etc/default/keyboard | 键盘设置 |
/etc/localtime | 时间和时区配置 |
/etc/modules | 可加载模块配置 |
操作系统启动时的init进程及inti调用的脚本也在/etc下
路径 | 功能 |
---|---|
/etc/init.d/ | 初始化相关文件 |
/etc/rc.local | 初始化脚本 |
/etc保存着用户和用户组的相关信息,增加或删除用户的操作,实际上是修改这些文件。
路径 | 功能 |
---|---|
/etc/passwd | 用户密码 |
/etc/group |
/etc不仅保存了操作系统级别的配置文件,还包括了应用程序的配置文件,这些配置文件是全局的,对所有用户有效。
路径 | 功能 |
---|---|
/etc/motion/motion.conf | Motion的配置文件 |
/etc/apt/sources.list | apt-get软件源配置 |
/etc/wpa_supplicationt/wpa_supplication.conf | Wi-Fi设置 |
应用程序也有自己的初始化脚本
路径 | 功能 |
---|---|
/etc/bashrc | ...初始化设置 |
/etc/nanorc | Nano初始化设置 |
/etc/virc | Vi初始化设置 |
系统信息和设备
内核直接管理的硬件信息可以在/proc下查询,这是一个虚拟文件系统,直接对应了内存上的内核空间,给用户提供了一个查询内核信息的简易窗口。/proc/cpuinfo保存CPU信息,/proc/meminfo保存内存使用信息。/proc下的文件大多是只读的。内核还保存着进程信息,这些原本在内核空间的信息也以文件的形式呈现在/proc目录下。
/dev目录保存着设备文件信息,每个文件对应一个设备。我们可以用与文件操作的形式与设备进行交流。通过读写/dev/ttyAMA0来与UART接口通信。Linux设备有主编号(major number)和副编号(minor number),主编号说明了设备的类型,在/dev中对应一个名字,比如ttyAMA,副编号是后面跟的0,即该类型下编号为0的设备。通过man指令看设备的主编号
$man 4 ttyAMA
/mnt文件夹用于挂载额外的文件系统,比如网络硬盘、光驱和额外的硬盘灯。/media用于挂载可插播设备,U盘等。
其他
/root是root用户目录,该目录文件的拥有者和拥有组都是root,其他用户的目录都位于/home下。
/var保存系统中动态增长的数据,比如/var/log下的系统日志和应用程序日志。每个应用程序也会产生动态增长的数据,比如邮件系统,邮件相关文字图片都随着用户使用而增长,因此电子邮件常常归档保存/var下。缓存数占据的空间经常浮动变化,因此保存在/var下。
/tmp含有一些临时数据需要保存的,随意修改该文件夹下的文件可能造成应用程序的崩溃,幸好/tmp下的文件会自动清空,因此不需要维护此文件夹。Raspbian系统会在开机后清空该文件夹,而不同Linux系统会在不同时间清空。该文件夹经常位于额外的存储器中,因临时文件的增长难以预料。
Reference
1 Vamei,周昕梓著,树莓派开始,玩转Linux,中国工信出版社,电子工业出版社,2018