免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
楼主: 冬瓜头
打印 上一主题 下一主题

[硬件及驱动] 关于PCIE、主桥、BAR、驱动、MMU、IOMMU、地址翻译 [复制链接]

论坛徽章:
7
丑牛
日期:2013-10-18 14:43:21技术图书徽章
日期:2013-11-03 09:58:03辰龙
日期:2014-01-15 22:57:50午马
日期:2014-09-15 07:04:39丑牛
日期:2014-10-16 14:25:222015年亚洲杯之伊朗
日期:2015-03-16 10:24:352015亚冠之城南
日期:2015-05-31 09:52:32
11 [报告]
发表于 2013-12-24 14:00 |只看该作者
PCI概念讲清楚的最好是王齐的《pci-e 体系结构导读》

论坛徽章:
2
2015年迎新春徽章
日期:2015-03-04 09:49:45IT运维版块每日发帖之星
日期:2016-07-29 06:20:00
12 [报告]
发表于 2013-12-24 14:55 |只看该作者
smalloc 发表于 2013-12-24 14:00
PCI概念讲清楚的最好是王齐的《pci-e 体系结构导读》


是的,这些问题就是阅后的总结,很多细节问题没有串起来,所以理解不透彻。

论坛徽章:
17
水瓶座
日期:2013-08-29 12:09:27白羊座
日期:2014-08-07 12:36:42丑牛
日期:2014-07-24 12:44:41寅虎
日期:2014-04-16 16:15:33寅虎
日期:2014-03-12 09:28:43摩羯座
日期:2014-03-06 13:22:04技术图书徽章
日期:2014-03-06 11:34:50天蝎座
日期:2014-01-09 11:31:44寅虎
日期:2013-12-27 17:01:44双子座
日期:2013-12-27 12:32:29双子座
日期:2013-12-25 09:03:33丑牛
日期:2013-12-24 16:18:44
13 [报告]
发表于 2013-12-24 19:43 |只看该作者
回复 10# 冬瓜头

Linux的pci总线枚举代码里面没看到对bar进行配置过!

论坛徽章:
2
CU十二周年纪念徽章
日期:2013-10-24 15:41:34处女座
日期:2013-12-27 22:22:41
14 [报告]
发表于 2013-12-24 23:14 |只看该作者
asuka2001 发表于 2013-12-24 08:59
回复 4# 冬瓜头

可以,之所以需要os设置bar,是因为CPU域的物理地址空间有限,而且不能产生冲突。


扯远了。配置PCI BAR就是一个在PCI域分配地址段的过程,跟CPU域没什么关系。动态配置地址是PCI总线的优点之一。

论坛徽章:
2
CU十二周年纪念徽章
日期:2013-10-24 15:41:34处女座
日期:2013-12-27 22:22:41
15 [报告]
发表于 2013-12-24 23:24 |只看该作者
asuka2001 发表于 2013-12-24 13:11
回复 7# 冬瓜头

额抱歉,这里说错了,真正设置bar的不是os而是bios。os做pci总线枚举时已经是直接利用b ...


如果内核决定相信固件,那么就直接用BAR里读出来的值,不然自己会重新分配。这涉及到计算每个设备BAR的大小,而且必需知道一个域上有可供分配的PCI域地址资源有哪些,包括可分配的IO地址段,可分配的不可缓存的地址段,可分配的可以缓存的地址段。这些都由平台提供代码,记录在root bridge相关结构体中。

不过我怀疑这些分配资源的代码到底有没有经过充分测试。在我们的平台上开启64 bit MMIO后,发现这些代码bug连连。

论坛徽章:
2
CU十二周年纪念徽章
日期:2013-10-24 15:41:34处女座
日期:2013-12-27 22:22:41
16 [报告]
发表于 2013-12-24 23:36 |只看该作者
bensenq 发表于 2013-12-23 19:20
顶,这个问答形式不错,逻辑性、顺序性也很强。

11. IOMMU就是转门给设备用的MMU。CPU透过MMU来看Memory ...


两者的视角不同。MMU是隔离进程的地址空间,IOMMU是隔离设备簇的DMA地址空间。

论坛徽章:
2
CU十二周年纪念徽章
日期:2013-10-24 15:41:34处女座
日期:2013-12-27 22:22:41
17 [报告]
发表于 2013-12-25 00:10 |只看该作者
冬瓜头 发表于 2013-12-24 11:57
请问这个把PCIE空间映射到主存空间的过程,是否在内核代码里有体现?或者说因为x86是简单的相等关系,所 ...


功能上是由host bridge实现的。这里涉及到两个问题:

1.哪些地址会被host bridge接收?即CPU域上的地址分配情况是怎么的。
2.这段地址会被转换到哪一段PCI地址?即CPU域地址到PCI域地址的转换。

第一个问题与体系相关太大。一般来说这是可以通过写寄存器配置的,但这个配置是又往往是静态的,即每一款产品,哪些部件占哪些物理地址已经规划好了。如果需要做配置,固件会完成这个工作。就PCI而言,host bridge可能会得到一段内存为作为32-bit PCI地址窗口,另一段内存作为64-bit PCI地址窗口。

第二个问题是通过配置host bridge解决的。通过来说,host bridge会提供一个简单的转换机制,比加一个偏移量,来完成两个域间的地址转换。简单相等当然是最方便的了,但有时候从设计上来讲就不能如此。例如服务器端的PowerPC,分给host bridge的物理地址段全在4G以上,那么32位PCI窗口无论如何也不能简单相等了,这就必需把4G以上的CPU地址转换为4G以下的PCI地址。64位窗口就无所谓了。事实上,服务器端PowerPC的64-bit窗口就是简单映射。

Linux也是以此建模,在host bridge相关结构体里,记录了一个域上有效的PCI地址及其与CPU域地址的偏移量。只有在CPU域开了窗口的PCI地址才是可以使用的,平台代码必需呈上这个信息。有了有效PCI地址段与offset,就可以用pcibios_resource_to_bus及pcibios_bus_to_resource在CPU域和PCI域转来转去了。

论坛徽章:
2
CU十二周年纪念徽章
日期:2013-10-24 15:41:34处女座
日期:2013-12-27 22:22:41
18 [报告]
发表于 2013-12-25 00:47 |只看该作者
回复 1# 冬瓜头


> PCIE设备DMA的时候不是必须发出PCIE总线物理地址么,如果它发出的驱动告诉它的主存虚拟地址,怎么解?

无解。真发生这种情况就是驱动的bug。驱动告诉设备的地址必然是一个PCI域的地址。如果两个域简单相等,那么这个地址是就是一个CPU域的物理地址。不然,必需于"在PCI域中开了窗口的物理内存"中分配DMA用的内存,有任何简单地址转换,如offset什么的,也必需apply之后才告诉设备。

如果有IOMMU,则可以分配任何物理内存,同时在设备所属DMA域中分配一段地址,然后在IOMMU中编程将两者结合起来,告诉设备的是后一个地址。

> 11. 那好,设备通过DMA控制器把要访问的虚拟地址发送给北桥DMA控制器,北桥DMA控制器是要通过MMU翻译成物理地址么?
> 答:理论上应该是这样,但是据说有个叫做IOMMU的东西,专门负责DMA时候的地址翻译。但是这里我也不明白,IOMMU会把虚拟地址翻译成物理地址么?为何不用MMU,单独搞一个IOMMU?

不经过MMU。DMA来的时候根本不知道是哪个进程在运行,进而更不可能用这个进程的内在映射关系了。

>12. 那好,PCIE设备是不是只能访问主机端主存在BAR里定义的地址段?
>答:之前看过一些文章说不管是CPU访问外设地址还是外设访问主存地址,都是限制在BAR里的地址段的,都不能越界访问。但是现实中好像根本不是这么回事。外设DMA主存的时候可以访问任意地址空间,有4GB可用,那么一定是虚拟空间了,我之前也理解外设访问主存也必须限制在BAR规定的地址段内,可能被深深误导了。但是既然SGL里通告的是虚拟地址,那么为何DMA不是用MMU来映射回物理地址呢?非要再搞个IOMMU为何呢?

这里完全混乱了。BAR记录的是设备在PCI域分得的地址,物理内存想要被DMA,也得在PCI域得到一块地址。实际上CPU读MMIO和设备读物理内存用的可能是相同的PCIe事务,设备甚至可以这种事务,不经CPU而直接读另一个设备内存空间。总之,出现在PCI总线上的,定然是PCI域上的地址。如果没有人使用这段地址,会有相应的出错回应。

设备访问内存时,出现在PCI总线上的,仍然是PCI域地址。这与CPU访问设备MMIO时基本类似,但方向是反的,bridge是否接收数据的依据也不同。如果没有其它设备回答这个读请求,这个请求最终会来到host bridge。而host bridge可以通过配置决定自己要接受哪一段PCI地址。比如,可以将host bridge配置为接受0~2G的PCI地址,如果某个对2G以上的读请求到达host bridge,说明没有其它设备拥有这段地址,但host bridge也不会接受它,于是整个过程就失败了。如果这个地址在host bridge配置里记录的PCI地址段之内,host bridge就会将这个PCI的事务转换为CPU native总线事务去读物理内存,其中可能会涉及到地址转换,比如加个offset什么的。这可以认为是host bridge自带的超简陋的IOMMU。如果有货真价实的IOMMU存在,则按IOMMU的规则转化这个地址。


>13. 那好,请告诉我既然有“PCIE域总线地址”,那么PCIE插槽针脚上,地址线连接在哪里?
>答:PCIE总线使用数据针脚复用地址和数据信号,分周期,先地址,后数据。但是,也请明白的告诉我,传送64位地址的话,一个时钟周期传完,起码要64根导线,PCIE插槽上如果是4个Lane的,没有64线吧,那是不是要分多个周期传送了。

PCI可以分两个周期传,PCIe的地址写在报文里。

>15. 哦。那请告诉我书上说“BAR内存放的是PCIE总线域的地址而不是存储器域的地址”,我也要疯了,内核初始化PCIE的时候,不是把其分配的存储器域的基地址写入到BAR内么?怎么就不是存储器域的地址了呢?难道“正统”做法应该是写入PCIE总线域地址,然后再由PCIE主桥进行翻译?
>答:哎?尼玛,你可能还真说对了。的确“正统”的做法,就是为每个PCIE设备分配各自的PCIE域的总线基地址并保证不冲突,然后为每个PCIE域的基地址映射存储器域的基地址,然后记录在PCIE初始化那个树结构里,并且把这个地址翻译表保存在北桥。。。

你哪里看到向BAR里写存储域地址了?如果是内核分配BAR空间,它必需知道可供分配的PCI地址段,写入BAR的是PCI域地址。

>16. 哦?尼玛太好了。那么请解释一下书上说的“PCIE设备在DMA的时候也只能使用PCIE总线地址,而且不能访问未被映射的地址空间”。
>答:晕了。这完全颠覆了我的认知。PCIE设备应该是可以完全DMA主存的虚拟地址空间,但是如果BAR里如果只分配了1MB地址,按照“书”上说的,它和寻址4GB虚拟空间? “书”中的描述为何不能啰嗦和通俗一些呢?愁死了。

未映射的地址空间是指"在PCI地址空间内没有窗口的物理内存"。举个例子,32位PCI一共有4G可用地址,各个设备的BAR要从这4G中分配地址,物理内存也要从这4G中分配地址,设备的BAR和物理内存在PCI域中可以认为是平等关系。例如,高2G PCI地址可以供PCI设备的BAR使用,低2G的PCI地址作为物理内存在PCI域中的窗口。如果PCI设备随便DMA,说不定就读到其它设备MMIO空间去了。

论坛徽章:
17
水瓶座
日期:2013-08-29 12:09:27白羊座
日期:2014-08-07 12:36:42丑牛
日期:2014-07-24 12:44:41寅虎
日期:2014-04-16 16:15:33寅虎
日期:2014-03-12 09:28:43摩羯座
日期:2014-03-06 13:22:04技术图书徽章
日期:2014-03-06 11:34:50天蝎座
日期:2014-01-09 11:31:44寅虎
日期:2013-12-27 17:01:44双子座
日期:2013-12-27 12:32:29双子座
日期:2013-12-25 09:03:33丑牛
日期:2013-12-24 16:18:44
19 [报告]
发表于 2013-12-25 09:02 |只看该作者
回复 14# tempname2

但是因为x86是1:1的映射,你虽然是配置pci域地址,但是同样也是直接就将其映射到了cpu域。

相信bios也是因为这个考虑而没有直接将pci域地址从0开始分配,而是从高位往下分配不是吗?

论坛徽章:
17
水瓶座
日期:2013-08-29 12:09:27白羊座
日期:2014-08-07 12:36:42丑牛
日期:2014-07-24 12:44:41寅虎
日期:2014-04-16 16:15:33寅虎
日期:2014-03-12 09:28:43摩羯座
日期:2014-03-06 13:22:04技术图书徽章
日期:2014-03-06 11:34:50天蝎座
日期:2014-01-09 11:31:44寅虎
日期:2013-12-27 17:01:44双子座
日期:2013-12-27 12:32:29双子座
日期:2013-12-25 09:03:33丑牛
日期:2013-12-24 16:18:44
20 [报告]
发表于 2013-12-25 09:26 |只看该作者
本帖最后由 asuka2001 于 2013-12-25 09:30 编辑

回复 18# tempname2

"在PCI域中开了窗口的物理内存"


看到过有说ppc上的pci设备可以不允许访问所有的物理内存的,由inbound,outbound寄存器决定。请教下是不是真的?

如果是这样的话,写驱动时岂不是还不能随意分配dma buffer,还是说ppc上的dma_map_page会对这种情况作处理,使用bounce buffer?
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP