类似kafka的文件存储机制
零拷贝是什么呢?操作系统层面的加速文件读写的操作机制,提升io性能
说实话这篇没说什么(嘘~~),几句话可以精简,欢迎大家来评论区总结😄
基础知识
晚上没有eat food,就先基础知识垫巴一口
话说CPU这么尊贵的东西不是任何人、任何事可以随便调动起来的,咱们操作系统为了能和CPU产生关系,可谓是废寝忘食、费尽心机,首先他先划分出内核态、用户态:划清界限 站好队才好下手,抹黑一把抓,往往费力不讨好
- 内核态:kernel mode/ring 0,这就是传说中No零的存在,拥有最尊贵的权限------出现就直接秒杀全场:对于cpu可以为所欲为:执行任何指令,对于内存地址如履平地想去哪就去那,任意访问所有的内存地址,直接和老大哥------硬件打交道(读写IO、控制中断控制器、管理页表)这也太厉害了吧🤩🤩🤩
- 用户态:user mode/ring 3,直接掉三档,只能执行一些无伤大雅的命令(非特权指令),轻如鸿毛,此生见不到硬件大哥一面!关键的系统资源------闻都闻不着(物理内存、设备寄存器、中断向量表),当然态生如此也是不容易🥺🥺,没有他们打地基也不会有上面的高楼平地起
磁盘、网卡、显卡等设备的寄存器映射到物理内存,就是说他们有内部通道可以串门唠嗑,但是这些物理地址没有给用户态开后门:堵死死的,用户态进程的虚拟地址中看不见,就是看见了也没有钥匙不能访问。
咱这也能理解,如果谁都能读写硬盘控制器,这万一谁来了给个格式化,直接over 辛辛苦苦全都白干;就算没这么过分,万一像小朋友一样 玩心重、玩一样随意关闭中断,这系统直接死锁,前面千万、几亿的订单,这也不是闹着玩呢;再说了如果能读取其他进程的内存,直接把人银行卡密码拿过来,这世界可就好玩了。所以咱们的应用程序是不能直接操作硬件的,是吧,需要内核空间进行操作转换;
- 操作系统通过系统调用system call提高标准化硬件访问接口:用户程序读文件------read------内核验证参数合法性、切换到内核态、操作磁盘驱动、返回结果;这样咱们用户也不需要关系底层硬件细节,避免了重复实现驱动逻辑,咱也不会需要学需要long long time是不是
- 用户进程运行在独立虚拟地址空间,内核管理者来协调cpu、内存、io资源分配,这样才能不偏心,站在全局者角度,尽可能根据用户进程的需要分配,每个进程也是互不影响,专心当牛马
如果用户程序需要访问硬件、系统资源,有三种上访通道:通过
1、软件中断(int 0x80)
2、快速系统调用指令x86-64syscall/sysret
3、陷入trap机制:cpu自动保存上下文,跳转到内核预设的入口
此时cpu切换到内核态,内核执行对应服务例程sys_read等,验证参数、执行操作、返回结果,切回用户态,恢复用户程序执行,当然这个过程很复杂,这里就不说了(隐约可以感觉到cpu在暗渡船仓hh,大概这个意思,所以有大量读写的时候cpu的占用率特别高,就容易卡)
大家也能感受到上面的流程太繁琐,比较慢,所以聪明的人类想出来例外的情况,让用户态"间接"高效访问硬件?不过下面都依赖内核的明确授权,并非"绕过"内核
- 内存映射io:mmap 显卡帧缓冲区、DPDK 网卡驱动,通过内核授权将设备内存映射到用户空间(但仍需内核初始化和权限检查)
- UIO(Userspace I/O) 或 VFIO:Linux 中允许用户态驱动在严格限制下访问硬件
- eBPF:在内核沙箱中运行用户提供的代码,用于网络、追踪等场景
| 概念 | 说明 |
|---|---|
| 用户态 | 应用程序运行的受限环境,不能执行特权指令,不能直接访问硬件 |
| 内核态 | 操作系统核心运行的高权限环境,可完全控制硬件和系统资源 |
| 切换机制 | 通过系统调用、中断、异常等触发,由 CPU 硬件支持 |
| 设计目的 | 安全、稳定、隔离、抽象、资源管理 |
| "无法直接操作硬件" | 指不能执行特权指令、不能访问受保护的物理地址或设备寄存器 |
当然这上面漏掉了DMA,之前也提到过,不详细,今天再来写一下
DMA:direct memory access直接内存访问
没有dma这个宝贝之前,数据传输的流程比较那个什么:
cpu请求读取设备------设备准备好一个字节/字------cpu通过i/o逐个读取数据,写入内存------重复
cpu被大量io占用,没有办法做其他事情,用户态内核态来回切换,系统性能严重受限
所以dma就是来解决这一问题:让专门的控制器来搬运数据,cpu只需要说自己需要什么,关注收到了什么。
那么让咱们看看接下来事情是否变得有趣:
- 应用程序读取***
- 内核驱动配置dma控制器:源地址(设备寄存器/缓冲区) 目标地址(内存中缓冲区)传输多少字节,传输方向(内存-设备,设备-内存)
- 启动DMa传输:设备和dma开始干活啦
- dma控制器接管总线:从设备读取数据,写入内存指定位置,一点不需要cpu关心
- 传完,dma控制器触发中断,cpu接收到通知应用程序数据已经ok了,下来米西吧
反推咱们dma的特点:
dma能做这么些重要的操作,能肯定不能是外人指示的,那得是内核驱动程序挑起来的
毕竟需要物理内存地址:多么珍稀和宝贵的财富;那用户态哪有这么金贵的东西,都是些虚拟骗自己玩的东西
还需要配置硬件寄存器,那要不怎么从设备中读取数据呢,是不是;这个就需要后台足够硬,得是特权才能有这种权利
而且得锁住内存吧,那正哐次哐次干活正带劲呢,内存乱了,这谁能有心情干活,毕竟不是人人能当牛做马
所以综上dma很重要,很重要,很重要
太多了写不完,就这打住 重新开一篇吧,新的一篇也能有点流 哈哈开玩笑,主要是太长了就是老太太洗脚布了,毕竟是三脚猫的功夫,撑不起来什么长的篇幅