2014-12-05 19 views
1

我想使用我的struct vm_area_struct *的頁面錯誤處理程序將物理頁面映射到用戶空間。如何使用頁面錯誤處理程序來映射頁面?

這是我如何着手:

  • 我在全球分配模塊初始化期間使用alloc_page(GFP_USER)頁面(我嘗試過各種GFP)。
  • 我創建了一個struct vm_area_struct,設置了自定義的頁面錯誤處理程序,並將vma附加到current->mm

當發生頁面錯誤:

  • 我設置vmf->page到我以前分配的頁面,返回0

其結果是,在vma每個虛擬頁面應該被映射到頁面錯誤後的同一個物理頁面。

但這裏是我發現:

  • 當我寫從我的內核模塊的頁面,它反映了我的用戶空間程序。
  • 當我從我的用戶空間寫入頁面時,我沒有從我的內核模塊中看到它。
  • 當我在我的內核模塊中使用get_user_pages來獲取頁面(而不是使用我的全局變量)時,我得到與全局頁面變量不同的物理地址。我使用page_to_phys(page)打印地址。寫入此頁面反映在我的用戶空間程序中。

所有這些都是在頁面錯誤處理程序中完成的。

這個好奇的行爲如何解釋?

要從內核空間訪問頁面,我使用kmap_atomickunmap_atomic

回答

1

這是由於寫入時複製機制。 運行頁面錯誤處理程序後,您在vmf->page中返回的頁面將被複制到新分配的頁面。這就是爲什麼你的用戶空間變化不會反映在你的內核模塊中。 您嘗試在內核中讀取的頁面不是真正映射到用戶空間進程中的頁面。

您可以參考mm/memory.c中的do_cow_fault函數。