我想使用ioremap_wc()
将设备内存(NIC)映射到内核空间内存区域。然后我想将内存区域从内核空间重新映射到用户空间,我可以使用2个函数:vm_insert_page()
和remap_pfn_range()
POSIX mmap(3)
通常使用第二个:remap_pfn_range()
vm_insert_page()
和remap_pfn_range()
之间的区别是什么?我何时需要使用vm_insert_page()
代替remap_pfn_range()
?
答案 0 :(得分:3)
vm_insert_page()
允许驱动程序插入已分配到用户vma中的各个页面。页面必须在内核中独立分配。它要求页面是为此目的而获得的零订单分配。它不会发出警告,也不需要设置PG_reserved。
传统上,这是使用remap_pfn_range()
完成的,它采用了任意页面保护参数。 vm_insert_page()
不允许这样做。您的vma保护必须正确设置,这意味着如果您想要一个共享的可写映射,您最好要求共享的可写映射!
remap_pfn_range()
用于将一组页面映射或重新映射到内存中。
答案 1 :(得分:2)
正如他们的名字所示vm_insert_page()
映射单页,而remap_pfn_range()
映射内核内存的连续块。检查原型和评论vm_insert_page,remap_pfn_range
例如,您可以使用vm_insert_page
来映射vmalloc
aree
do {
page = vmalloc_to_page(vaddr);
vm_insert_page(vma, uaddr, page);
vaddr += PAGE_SIZE;
} while(/* there is something to map */);
使用remap_pfn_range
是不可能的,因为它只映射了一个连续的内核内存块。
另一个区别是,使用remap_pfn_range
,您不仅可以映射RAM缓冲区,还可以映射其他范围。使用vm_inser_page
,您只能映射RAM缓冲区
来自Linus的explanation