将特定虚拟地址映射到特定物理虚拟地址

时间:2013-03-21 09:21:17

标签: linux memory kernel memory-address

我正在编写一个Linux内核模块,需要将特定的物理地址映射到特定的虚拟地址,而我却找不到办法。

2 个答案:

答案 0 :(得分:2)

好的,这是我目前的解决方案。要将phys_addr映射到virt_addr,请使用以下代码:

page = pfn_to_page(virt_addr >> PAGE_SHIFT);
pte = get_locked_pte(&init_mm, phys_addr, &ptl);
set_pte_at(&init_mm, phys_addr, pte, mk_pte(page, VM_READ | VM_WRITE | VM_EXEC));
spin_unlock(ptl);
flush_tlb_all();

一些表达式:我使用pfn_to_page func来获取与我的virt_addr对应的页面结构。我得到了包含pte func的页表条目{get_locked_pte),该func需要与所需pte对应的物理地址和未初始化的自旋锁(ptl)。然后,我实际使用set_pte_at func和mk_pte宏映射页面,解锁自旋锁并刷新tlb缓存。

这个解决方案似乎运行得很好,但它不能在上下文切换后继续存在。

答案 1 :(得分:0)

您能告诉我们您使用的内核版本和CPU架构/类型吗?一般来说,如果要映射到的特定虚拟地址与内核虚拟地址(例如0xC0000000)不重叠,并且如果设备使用的物理地址与系统内存物理地址范围不重叠,则可以使用低级函数(如果没有,您可以使用汇编语言在内核启动期间直接设置MMU TLB条目)来设置MMU TLB条目,以在内核启动期间将特定地址映射到特定的虚拟地址。我可以提供一个基于2.6.10内核版本和飞思卡尔PowerPC CPU的示例,有一个函数io_block_mapping来做你想要的事情。