[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"$f6dNlDUUTW_gMqrjL4Fqe6axj4ecyRrj_bMA5cwyVBGw":3},{"item":4,"related":44},{"id":5,"type":6,"title":7,"slug":8,"summary":9,"body":10,"coverUrl":11,"productScreenshots":12,"productLinks":13,"authorName":14,"authorUrl":15,"authorSubject":16,"category":17,"tags":22,"sourceLabel":35,"sourceName":36,"sourceUrl":37,"status":38,"seoTitle":7,"seoDescription":9,"canonicalUrl":35,"isFeatured":39,"sno":40,"sortOrder":41,"publishedAt":42,"updatedAt":43,"createdAt":43},"0152f765-818c-413a-b4f6-546b2825348b","article","mmap：文件什么时候会变成程序地址空间里的一扇窗？","mmap-memory-mapped-files","mmap 将文件映射进进程虚拟地址空间，程序像访问内存一样按页访问文件，同时把缺页装载、缓存与回收交给操作系统。","文件通常被理解为磁盘上的一串字节，程序要读它，往往先调用 read 把内容复制到用户态缓冲区。mmap（memory mapping，内存映射）提供了另一种视角：把文件的一段内容映射到进程的虚拟地址空间，让程序像访问内存一样访问文件。\n\n可以把文件想成仓库，把进程地址空间想成一张城市地图。mmap 不是把整个仓库立刻搬到城市，而是在地图上预留一块“对应区域”。程序第一次触碰某一页时，操作系统再通过缺页机制把相应文件页装入内存，并建立虚拟地址到物理页的映射。没访问的部分可以继续留在磁盘上。\n\n这种方式很适合随机访问大型文件、共享内存、加载动态库和构建文件缓存。多个进程还可以映射同一文件的页面，让操作系统在物理内存层面复用缓存。对程序来说，索引结构可以直接用指针或偏移访问，避免显式地管理每次 read 的缓冲区。\n\n代价是，文件访问的延迟被隐藏到页面错误里，第一次触碰某页可能触发磁盘 I\u002FO；映射区域也可能因为内存压力被换出。文件被截断后继续访问映射区会导致异常，多个进程写同一映射还涉及可见性、同步和持久化边界。mmap 也不等于永久驻留内存，更不保证每一次访问都比 read 快。\n\n理解 mmap 的关键是区分虚拟地址和物理数据：程序拿到的是一个地址视图，操作系统负责在背后按页装载、缓存和回收。它把文件系统与虚拟内存连接起来，使文件、共享内存和进程地址空间可以用同一种访问模型协作。\n\n映射还分为共享和私有等不同语义。共享映射可以让写入对其他映射者可见，并最终通过同步机制落回文件；私有映射则常借助写时复制，让进程拥有自己的修改。选择哪一种，取决于应用要的是跨进程通信、文件持久化，还是高效读取，而不能只看 API 名字里有“memory”。\n\n资料来源：[Linux mmap(2) 手册](https:\u002F\u002Fwww.man7.org\u002Flinux\u002Fman-pages\u002Fman2\u002Fmmap.2.html)","\u002Fuploads\u002F2026-09-26\u002F26595a9e-4618-469f-9a6d-5159a54f4ba1.jpg",[],[],"Foundit","https:\u002F\u002Ffoundit.cn","foundit-ai-editorial",{"id":18,"name":19,"slug":20,"description":21},"6179d3b6-dc34-4483-9ded-3cd9f1b37a47","科普","abbreviation","介绍各领域新兴概念",[23,27,31],{"id":24,"name":25,"slug":26},"144abe77-0dc6-4f66-a176-20bddb1c0bfa","编程","coding",{"id":28,"name":29,"slug":30},"7c76bfc2-f80f-4ee0-a95d-27bd8708b434","技术","slug",{"id":32,"name":33,"slug":34},"a202d639-99a6-488a-a712-4d4c6ffd7e15","开发","dev",null,"Linux mmap(2) 手册","https:\u002F\u002Fwww.man7.org\u002Flinux\u002Fman-pages\u002Fman2\u002Fmmap.2.html","published",false,47,0,"2026-09-27T00:00:00.000Z","2026-09-26T16:26:00.127Z",[45,54,62],{"id":46,"type":6,"title":47,"slug":48,"summary":49,"coverUrl":50,"authorName":14,"sno":51,"publishedAt":52,"createdAt":53},"4ce57934-2b23-41a1-800e-bb2d8ab36684","Wasm Component Model：不同语言写的模块怎样用同一套接口协作？","wasm-component-model-wit-interfaces","WebAssembly Component Model 用有类型的接口描述组件如何交换数据与调用功能，WIT 则帮助表达这些接口。本文用模块化电器说明跨语言组合的意义，也指出它不代表程序脱离运行时就能在任何环境原样运行。","\u002Fuploads\u002F2026-10-17\u002F0eb1c88d-dc1f-486d-8194-54f72dd215ec.jpg",45,"2026-10-17T00:00:00.000Z","2026-10-17T03:08:52.474Z",{"id":55,"type":6,"title":56,"slug":57,"summary":58,"coverUrl":59,"authorName":14,"sno":51,"publishedAt":60,"createdAt":61},"07fe8e6e-82b0-46cc-9015-c6d027564430","pidfd：进程号会被重用，怎样才能稳定指向一个进程？","linux-pidfd-stable-process-reference","Linux pidfd 用文件描述符稳定引用一个进程，避免退出后的 PID 被重用而误操作新进程。本文介绍它的等待、信号用途和版本边界。","\u002Fuploads\u002F2026-10-06\u002F699e59f8-693f-47cb-87b1-c51764d1a679.jpg","2026-10-06T00:00:00.000Z","2026-10-06T07:51:27.054Z",{"id":63,"type":6,"title":64,"slug":65,"summary":66,"coverUrl":67,"authorName":14,"sno":51,"publishedAt":42,"createdAt":68},"15988123-6303-4ab1-ba01-dcc41f36329f","Futex：Linux 的锁为什么大多数时候根本不需要进内核？","futex-fast-userspace-locking","Futex 把无竞争时的锁操作留在用户态，只有真正需要睡眠和唤醒时才进入内核，是 Linux 高性能锁的关键低层构件。","\u002Fuploads\u002F2026-09-26\u002F90e98cc8-e57b-4dea-afc7-2afe7550d483.jpg","2026-09-26T16:25:54.119Z"]