应用程序读取磁盘的数据流程
-
应用程序请求文件读取: 用户态的应用程序发起文件读取请求,通常是通过标准的文件操作函数(例如,在Linux中是 read(),在Windows中是 ReadFile())
-
系统调用: 操作系统内核接收到应用程序的读取请求,这将触发一个系统调用(system call)。系统调用是用户态和内核态之间的通信机制,用于执行操作系统内核中的特定功能
-
内核态处理: 操作系统内核根据请求打开相应的文件,确定要读取的数据位置等,并准备好数据进行读取。这一过程通常发生在内核态
-
磁盘读取: 操作系统内核通过设备驱动程序或文件系统模块与硬盘或存储设备进行通信,以从磁盘中读取请求的数据块
-
数据加载到内核缓冲区: 读取的数据通常会被加载到内核缓冲区(kernel buffer)中,这是内核维护的一块内存区域
-
数据复制到用户态缓冲区: 一旦数据被加载到内核缓冲区中,内核将执行一个额外的操作,将数据从内核缓冲区复制到用户态缓冲区(user buffer),这是应用程序所拥有的内存区域
-
系统调用返回: 当数据成功复制到用户态缓冲区后,系统调用返回到用户态,通知应用程序已经完成读取操作
-
应用程序使用数据: 应用程序处理从磁盘读取的数据
调用read()函数读取硬盘数据到用户空间:
- 调用read()函数,用户态进程发起系统调用,请求读取硬盘数据到用户空间,通过软中断或陷阱机制,CPU由用户态切换到内核态
- 内核分配一块内核缓冲区PageCache,CPU向DMA控制器发起请求
- DMA控制器被触发,将硬盘数据拷贝到内核缓冲区PageCache
- DMA控制器向CPU发起请求,CPU将内核缓冲区PageCache的数据拷贝到用户空间的缓冲区
- read函数结束后,内核将CPU由内核态切换到用户态,继续执行被中断的用户态进程
调用write()函数将用户空间数据写入到网卡中
- 调用write()函数,用户态进程发起系统调用,请求将用户空间数据写入网卡,CPU由用户态切换到内核态
- 内核分配一块内核缓冲区PageCache,CPU将用户空间的数据拷贝到Socket缓冲区,CPU向DMA控制器发起请求
- DMA控制器被触发,DMA控制器将Socket缓冲区的数据拷贝的网卡中
- 最好,DMA控制器发出数据写完信号,write结束,CPU由内核态切换到用户态
进程中有页表数据结构指向用户空间和内核空间,使用户态和内核态访问内存空间不同
(待改)