`
- 浏览:
1028937 次
-
x86 vt-d在linux中的应用
在新公司已近两年,所学甚多甚杂,已经不能用一篇水文来记录里面的点点滴滴,这是我一直没有写一篇总结的原因.现在想想随兴所至一些更好。
翻看前文,发现还差一篇风河hypervisor硬件虚拟化的文章,懒得写了,浪费时间.看过xen的代码后觉得hypervisor就是只小麻雀.以后有精力了写写xen里面对x86硬件虚拟化技术的利用,那将是一个大篇幅.今天介绍下linux里对x86硬件虚拟化技术的利用,算是个引子.xen里面用到硬件虚拟化那是理所当然,有意思的是linux也用到了里面的东西,vt-d,sr-iov.它当然不会用vt-x,这里不讲kvm,它本身就把linux变成了虚拟机而不是一个纯内核了.同样我不会写代码分析的细节,那是很无聊的事,只写我认为有意思的东西.
vt-d里主要有两个新技术,int remapping和dma remapping.
int remap在服务器配置中经常见到,如果系统中cpu超过255个或有apic_id>255的时候,intr是必须打开的,因为ioxapic系统即使在物理目标模式也只支持8bit的cpu_id,没有办法把中断分发给所有的cpu.而打开intr后,虽然ioapic中索引是16bit,但是irte中可以有32bit的物理地址或逻辑地址,最大能有2的32次个cpu.当然也有一些老系统只支持intr的xapic模式,也就是不能和x2apic配合,那和不打开也就没什么分别了,只在中断迁移时能保证不丢中断.intr关闭时,ioapic或msi/msix中触发中断后转换成内存写消息向上传到北桥,被识别为中断后自动分发给相应的cpu,中间还会经过cpu的仲裁与选择,识别是通过特殊地址信息fee来识别的.linux中已经基本有完善的支持了,只是缺msi这块,msi目前只支持单个中断,倒不是无法实现,只是代码要有大的改动,申请一段连续的vector和irq号都是比较困难的。msix比较不错,没有32个vector限制,而且每个vector和irq都不需要连续,缺点是会占用一些mem空间。另外打开msi中断后记得关闭legacy
int。如果打开intr的话,rte或msix msg中要填的是一个索引,不是关于这个irq的所有信息,比如触发模式,目标模式,目标地址,vector等。这个index会去索引内存中一个irte的表,找到后取出其中的信息转发给apic。有意思的是这里面的信息就是irq的所有信息。当然那个表未必是一个,要看这个系统是不是只有一个pci段,或者说是不是只有一个drhd单元。另外irte是有缓存的,修改irte后要有指令清除irte缓存.
所谓dmar就是给设备一个地址空间映射,设备对内存的访问要通过一个页表结构转换成真正的访存地址.也就是说设备地址就是个设备虚拟地址,真正的访存地址是设备物理地址。这个页表结构和cpu的页表结构还有vmx的ept相似,可以有大页,还有地址映射的缓存即所谓iotlb,等同于cpu的tlb,但是在北桥里.有的系统为了优化,在设备中也提供了device-iotlb,这些对软件是透明的,只有特殊的刷新指令序列能改变它们.dmar在一些特殊场合有用,比如32bit pci设备要dma数据到4G以上地址,dmar可以提供这种映射,让高端地址在pci设备中映射为32bit的范围之内.关闭dmar的话只能用软件模拟了,即bounce-buffer.
整个iommu功能是在acpi表结构中提供的,目前有4种子表,drhd,rmrr,atsr,rhsa。其中drhd是最本文最关键的一个表,它枚举了每个dma重映射单元及属于它的下属设备,每个drhd有指针指向一个reg集合,里面会有irte表基址和dmar root entry,root entry数组,256项,指向context entry数组,context entry指向顶级页表。整个结构是由sid索引的,sid通常是bus,dev,fn,对pci桥下的设备,是桥的sid,也就是说所有pci桥下的设备都只能处于同一个域,具体在xen中的话只能直接分配桥下所有的设备给同一个domain。hpet和ioapic这两个特殊设备的sid是通过device
scope得到的。rmrr指定保留内存,目前只在usb和显卡中用到,要注意不要将页表中含有这些保留内存的映射。否则会导致系统panic。atsr是关于device-iotlb,rhsa指定drhd单元的node亲和性,可用于各种表项内存分配的优化。写来写去,又虎头蛇尾了,但还是那句老话,随兴就好。
分享到:
Global site tag (gtag.js) - Google Analytics
相关推荐
qt-sdk-linux-x86-opensource-2010.05.1
libsigar-amd64-linux.so以及libsigar-x86-linux.so应用于Linux 32位操作系统
docker-compose-Linux-x86-64
qt-creator-linux-x86-opensource-1.3.0
Miniconda3-latest-Linux-x86_64 miniconda安装包Miniconda3-latest-Linux-x86_64 miniconda安装包Miniconda3-latest-Linux-x86_64 miniconda安装包Miniconda3-latest-Linux-x86_64 miniconda安装包Miniconda3-...
qt-creator-linux-x86_64-opensource-2.6.1.bin
docker-compose-linux-x86_64-v2.4.1.zip
codelldb-x86_64-linux.vsix 下载,用于vscode 的LLDB 插件,用来debug调试 vscode,包括cpp、go、rust、c等语言
qt-eclipse-integration-linux.x86-1.4.0.tar.gz
qt-sdk-linux-x86-opensource-2009.03.bin.part4 ||QT开发SDK
gcc-arm-8.3交叉编译工具链,可用于linux系统中程序的交叉编译,版本较高适用于QT。不用去下载了
qt-eclipse-integration-linux.x86-gcc3.3-1.4.0.tar.gz
mysql-router-2.1.4-linux-glibc2.12-x86-64bit.tar.gz
qt-creator-linux-x86-opensource-2.6.1 应用程序 linux 32位
mysql-8.2.0-linux-glibc2.17-x86_64.tar.xz 适用于Generic Linux (Architecture Independent)
获取Linux系统监控信息必备的文件 libsigar-amd64-linux.so和libsigar-x86-linux.so
kibana-5.5.1-linux-x86_64.tar.gz;kibana-5.5.1-linux-x86_64.tar.gz;kibana-5.5.1-linux-x86_64.tar.gz;kibana-5.5.1-linux-x86_64.tar.gz;kibana-5.5.1-linux-x86_64.tar.gz;kibana-5.5.1-linux-x86_64.tar.gz;...
mysql-connector-c++-1.1.7-linux-glibc2.5-x86-64bit.rpm 安装只需: rpm -ivh mysql-connector-c++-1.1.7-linux-glibc2.5-x86-64bit.rpm 即可
cmake-3.16.0-Linux-x86_64.tar.gz; cmake-3.16.0-Linux-x86_64.tar.gz;