免费注册 查看新帖 |

Chinaunix

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

疑问: PCIe BAR 只有32bit, 怎么在64bit kernel上使用?? [复制链接]

论坛徽章:
0
11 [报告]
发表于 2010-09-01 17:26 |只看该作者
回复 10# gaoping561


    是有相等一说.
弹缓冲区或者IOMMU是必要的吗 ?

论坛徽章:
0
12 [报告]
发表于 2010-09-01 17:38 |只看该作者
本帖最后由 gaoping561 于 2010-09-01 17:46 编辑

回复 11# epegasus


我的内存有24G啊,DMA很可能访问4G以上了。

如果是对等映射,这样看来如果DMA操作4G以上物理内存,那dma_addr_t肯定是64位总线地址了,至少PCIE设备设计的时候,DMA寄存器要64bit。

google了一把,关于PCI的讨论集中在32bit DMA如何访问高4G内存的问题,一般都是回弹缓冲或者IOMMU

可是我关心的32bit BAR address register 怎么搞,是不需要关心还是也需要搞IOMMU才行?或者必须得把设备设计成64bit addressing

背景就是,现在有一个PCIE的设备,FPGA实现的,目前所有地址register只支持32bit addressing,怎么用在x86_64上。

论坛徽章:
0
13 [报告]
发表于 2010-09-01 17:57 |只看该作者
本帖最后由 epegasus 于 2010-09-01 17:59 编辑

回复 12# gaoping561


    回弹是这个意思.
你操作的内存在设备DMA可访问的范围外,比如4G以外
你要做DMA时就把数据拷贝到4G以下,然后传完了释放这个4G以下内存,
对于能访问4G以上的就直接DMA了.因为一般都是物理内存连续的.

IOMMU是改变地址映射,直接访问过去.
这些都是不必要的.只是有时候才需要.


>>目前所有地址register只支持32bit addressing,怎么用在x86_64上。
直接用就好了.内核自己能分辨32位的.并分配4G以下的MEM地址.回弹什么的内核自己回处理.

论坛徽章:
0
14 [报告]
发表于 2010-09-01 18:04 |只看该作者
回复 13# epegasus


    非常感谢!!!

论坛徽章:
0
15 [报告]
发表于 2010-09-02 22:40 |只看该作者
http://en.wikipedia.org/wiki/Conventional_PCI#Dual-cycle_address

For conventional PCI, use DCA can access memory in 64bit address range.

Dual-cycle address

To allow 64-bit addressing, a master will present the address over two consecutive cycles. First, it sends the low-order address bits with a special "dual-cycle address" command on the C/BE[3:0]#. On the following cycle, it sends the high-order address bits and the actual command. Dual-address cycles are forbidden if the high-order address bits are zero, so devices which do not support 64-bit addressing can simply not respond to dual cycle commands.

For PCI express, it can support 64bit single access or DCA, I think.

论坛徽章:
0
16 [报告]
发表于 2010-09-03 14:46 |只看该作者
本帖最后由 gaoping561 于 2010-09-03 14:58 编辑
  1. int
  2. pci_bus_alloc_resource(struct pci_bus *bus, struct resource *res,
  3.                 resource_size_t size, resource_size_t align,
  4.                 resource_size_t min, unsigned int type_mask,
  5.                 void (*alignf)(void *, struct resource *, resource_size_t,
  6.                                 resource_size_t),
  7.                 void *alignf_data)
  8. {
  9.         int i, ret = -ENOMEM;
  10.         resource_size_t max = -1;

  11.         type_mask |= IORESOURCE_IO | IORESOURCE_MEM;

  12.         /* don't allocate too high if the pref mem doesn't support 64bit*/
  13.         if (!(res->flags & IORESOURCE_MEM_64))
  14.                 max = PCIBIOS_MAX_MEM_32;
复制代码
找到resource分配的证据了,在2.6.31内核中,如果32bit的BAR,不会分配超过4G的resource,max=PCIBIOS_MAX_MEM_32=0xffffffff,但是在2.6.18中没有这个判断,max=-1=0xffffffffffffffff; 2.6.18中不支持intel的iommu, DMA靠swiotlb性能就打折扣了。所以可以说32bit的PCI设备在64bit的2.6.18也就是rhel5.3中使用都是危险的。

另外pci_mem_start = 0xaeedbabe,这个是怎么来的,在e820.c 这个文件中,这个文件又是个什么东西呢,哪位高人指点下。

最后还有一个问题要确认,MSI-X 中断里的address也只有32bit,这个MSI-X包会发给x86的中断控制器,这个中断控制器的地址不会大于4G吧?

论坛徽章:
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
17 [报告]
发表于 2010-09-03 16:33 |只看该作者
回复 16# gaoping561


    谢谢分享.我认为这个应该是一样的.
MSI不过是设备向主设备执行写.这个地址肯定是被主设备捕获,从而转换成一条中断消息.
LAPIC是位于前端总线.对于设备来说是不可见的.
通常来说主设备可访问的地址应该都是在4G以下.当然应该存在一个规范给它分配规定的物理地址空间.可能是BIOS一类的规范吧.

论坛徽章:
0
18 [报告]
发表于 2010-09-04 19:23 |只看该作者
本帖最后由 gaoping561 于 2010-09-04 19:28 编辑

在函数msi_compose_msg里:
  1.              if (irq_remapped(irq))
  2.                               {....}
  3.               else {
  4.                 if (x2apic_enabled())
  5.                         msg->address_hi = MSI_ADDR_BASE_HI |
  6.                                           MSI_ADDR_EXT_DEST_ID(dest);
  7.                 else
  8.                         msg->address_hi = MSI_ADDR_BASE_HI;

  9.                 msg->address_lo =
  10.                         MSI_ADDR_BASE_LO |
  11.                         ((apic->irq_dest_mode == 0) ?
  12.                                 MSI_ADDR_DEST_MODE_PHYSICAL:
  13.                                 MSI_ADDR_DEST_MODE_LOGICAL) |
  14.                         ((apic->irq_delivery_mode != dest_LowestPrio) ?
  15.                                 MSI_ADDR_REDIRECTION_CPU:
  16.                                 MSI_ADDR_REDIRECTION_LOWPRI) |
  17.                         MSI_ADDR_DEST_ID(dest);
  18.               }
复制代码
如果没有irq remap的话,同时x2apic enable, msg->address_hi 被赋值了, 那么MSI必须要支持64bit address; 这个irq remap什么时候用,什么时候打开?  这个x2apic又是干嘛的呢?

论坛徽章:
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
19 [报告]
发表于 2010-09-04 19:32 |只看该作者
回复 18# gaoping561


    这个怎么判断是必须开64呢?
MSI_ADDR_BASE_HI只是地址的高几位,并不代表64位啊

论坛徽章:
0
20 [报告]
发表于 2010-09-05 22:31 |只看该作者
找到resource分配的证据了,在2.6.31内核中,如果32bit的BAR,不会分配超过4G的 resource,max=PCIBIOS_MAX_MEM_32=0xffffffff,但是在2.6.18中没有这个判断,max=-1=0xffffffffffffffff; 2.6.18中不支持intel的iommu, DMA靠swiotlb性能就打折扣了。所以可以说32bit的PCI设备在64bit的2.6.18也就是rhel5.3中使用都是危险的。

另外pci_mem_start = 0xaeedbabe,这个是怎么来的,在e820.c 这个文件中,这个文件又是个什么东西呢,哪位高人指点下。

最后还有一个问题要确认,MSI-X 中断里的address也只有32bit,这个MSI-X包会发给x86的中断控制器,这个中断控制器的地址不会大于4G吧?



32位的BAR不可能分配到4GB以上的物理地址。
64为的BAR虽然理论上可以分配到4G以上,但一般x86的BIOS为了兼容性,也一般保证不分配。所以Solaris x86的代码对大于4G的分配都返回错误,从来不会引来任何问题。

PCI设备的内存布局一般是ACPI规范有规定的,自己看看吧。


MSI-X中断在x86上是写一个固定的LAPIC的地址,这个地址也在4G以下,这个可以看Intel的规范。
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

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

清除 Cookies - ChinaUnix - Archiver - WAP - TOP