加载中...

本篇要回答的问题:外置存储与内存最大的区别是什么?为什么外存的管理必然走向"自描述的数据格式"——也就是文件系统

上一讲讲了系统调用与编程接口(07 讲讲内存管理)。内存是为 CPU 计算服务的临时存储,而外置存储是持久存储,目的是存资料。正因为持久、要长期自查,外存管理的诉求与内存截然不同。

外存的分类

外置存储设备种类不可穷尽,但变的主要是"质量"(能耗、成本、性能)而非"功能",对 OS 来说管理方式高度一致。按功能特性分三类:

类型 代表 写特征 典型场景
顺序读写型 磁带 顺序读写 归档/数据备份(日常少见,略过)
随机只读型 光盘 单次完整写入、多次读取 资料分发与归档(软件、电影、音乐等)
随机读写型 软盘/硬盘/U 盘/SSD 随机读写 最常见,PC/手机/手表/汽车随处可见

外存的数据格式

关键判断:外存是持久存储,所以写到外存的数据必须是**"自描述"的某种数据格式**——能随时查看以前写了什么、什么时候写的。直接基于物理地址读写行不通(几个月后自己都忘了写哪了)。这就是文件系统的来源。

文件系统把存储组织成一棵树

节点 角色
根目录 树根,必是目录
目录 中间节点,可含子目录或文件
文件 叶节点,保存资料

每个节点都有名字、创建/最后编辑/最后访问时间等信息,有些还提供操作日志——帮我们记住"有什么内容、以前做过什么"。

文件系统的实现

接口高度一致,但实现很多。与架构关联不大,本质是数据结构与算法问题,且是基于外存(而非内存)的数据结构,二者很不同。

随机只读型存储(光盘)常见文件系统

随机读写型存储(硬盘)常见文件系统

设备类型 数据格式取向 设计要点
随机只读型(光盘) 读优化 批量一次写完,元数据与文件数据紧凑,文件不必支持分块
随机读写型(硬盘) 通用 多基于**日志(journal)**改善防灾难能力,B/B+ 树组织元数据

FAT(如 FAT32)是个古老的例外:把目录当作特殊文件,依次列出子节点元信息。结构简单,但目录树深/子节点多时性能大幅下降。

设备使用三步曲

步骤 操作 含义
1 分区 把一个存储设备模拟成多个设备(可省略,整盘作一个分区)
2 格式化 生成文件系统初始状态:标记分区格式 + 生成根目录
3 挂载(mount) 接入 OS 文件系统名字空间,之后即可读写/增删改

外存的使用接口

层次 目录相关 文件相关
命令行工具 ls, mkdir, mv, cp, rmdir cat, vi, mv, cp, rm
系统调用(最原始) —— ——
Go 封装 os.Mkdir, os.Rename, os.Remove os.Open/Create/OpenFile, os.Rename, os.Remove

关键判断:UNIX 曾想用"文件"统一抽象所有输入输出设备(stdin/stdout 代表键盘/显示器,“一切皆文件”)。但事实证明 UNIX 错了——输入输出设备太多样,图形界面时代到来后 stdin/stdout 这套就被颠覆了。

有了文件系统接口,进程便能互不影响地用外存。路径冲突有时反被故意利用做进程间通讯:例如"检查文件是否存在,不存在就创建它"在保证原子性时可用于进程间互斥(如保证软件只跑一个实例)。

虚拟内存的支持

外存还反过来支撑内存管理(07 讲的换出):

平台 换出载体
UNIX 系 专门的 swap 分区
Windows 具隐藏属性的 .swp 文件

缺页频繁时大量磁盘 IO 极占 CPU——计算机变慢且硬盘灯不停闪烁,基本可断定物理内存严重不足

总结

外存管理从架构角度比较简单,复杂性主要集中在文件系统的数据格式设计(数据结构与算法问题)。文件系统把外存组织成自描述的目录树,给了进程互不干扰使用外存的接口,同时也是进程间通讯与虚拟内存换出的天然基础设施。

先把"是什么"回答清楚

概念 一句话说明
外存 vs 内存 外存是持久存储(存资料),内存是临时存储(为计算服务)
文件系统 把外存组织成自描述的目录树(根目录/目录/文件)
journal 日志机制,改善断电/异常 unmount 的防灾难能力
分区/格式化/挂载 用设备的三步:切分→生成初始文件系统→接入名字空间
一切皆文件 UNIX 想统一抽象所有 IO 设备的口号,被证明过于理想
swap/.swp 外存中专用于虚拟内存换出的分区/文件

一句话速记

外存因"持久"而必须自描述,于是有了把存储组织成目录树的文件系统;其难点不在架构而在基于外存的数据结构(日志 + B/B+ 树),FAT 是反面教材。

几条值得记住的判断

  • 外存自描述是刚需,否则几个月后无人记得数据写在哪。
  • 文件系统设计是数据结构/算法问题,与架构关联不大。
  • "一切皆文件"是象牙塔理想,图形界面时代被颠覆。
  • 文件系统天然是进程间通讯的中间人(如原子"创建即互斥")。

思考题

UNIX 想用"文件"统一抽象所有输入输出设备,结果被证明过于理想。回到你的系统:你是否也曾试图用一个"大一统抽象"去覆盖差异巨大的子领域?什么情况下统一抽象是优雅,什么情况下它是过度理想化?

公告栏
这是我的个人知识库。
记录技术,也记录生活 —— 读过的、试过的、想明白的,都堆在这儿。
最新文章
网站资讯
文章数目 :
5
已运行时间 :
本站总字数 :
15.7k
本站访客数 :
本站总访问量 :
最后更新时间 :
全局知识图谱
当前页面 已访问 文章 标签
ESC 关闭 · 滚轮缩放 · 拖拽移动 · Ctrl+G 开关