[PATCH 17/35] mm, dmemfs: support unmap_page_range() for dmemfs pmd

From: yulei . kernel
Date: Thu Oct 08 2020 - 03:55:34 EST


From: Yulei Zhang <yuleixzhang@xxxxxxxxxxx>

It is required by munmap() for dmemfs mapping.

Signed-off-by: Chen Zhuo <sagazchen@xxxxxxxxxxx>
Signed-off-by: Yulei Zhang <yuleixzhang@xxxxxxxxxxx>
---
mm/huge_memory.c | 2 ++
mm/memory.c | 8 +++++---
2 files changed, 7 insertions(+), 3 deletions(-)

diff --git a/mm/huge_memory.c b/mm/huge_memory.c
index 531493a0bc82..73af337b454e 100644
--- a/mm/huge_memory.c
+++ b/mm/huge_memory.c
@@ -1636,6 +1636,8 @@ int zap_huge_pmd(struct mmu_gather *tlb, struct vm_area_struct *vma,
spin_unlock(ptl);
if (is_huge_zero_pmd(orig_pmd))
tlb_remove_page_size(tlb, pmd_page(orig_pmd), HPAGE_PMD_SIZE);
+ } else if (pmd_special(orig_pmd)) {
+ spin_unlock(ptl);
} else if (is_huge_zero_pmd(orig_pmd)) {
zap_deposited_table(tlb->mm, pmd);
spin_unlock(ptl);
diff --git a/mm/memory.c b/mm/memory.c
index 469af373ae76..2d2c0f8a966b 100644
--- a/mm/memory.c
+++ b/mm/memory.c
@@ -1178,10 +1178,12 @@ static inline unsigned long zap_pmd_range(struct mmu_gather *tlb,
pmd = pmd_offset(pud, addr);
do {
next = pmd_addr_end(addr, end);
- if (is_swap_pmd(*pmd) || pmd_trans_huge(*pmd) || pmd_devmap(*pmd)) {
- if (next - addr != HPAGE_PMD_SIZE)
+ if (is_swap_pmd(*pmd) || pmd_trans_huge(*pmd) ||
+ pmd_devmap(*pmd) || pmd_special(*pmd)) {
+ if (next - addr != HPAGE_PMD_SIZE) {
+ VM_BUG_ON(pmd_special(*pmd));
__split_huge_pmd(vma, pmd, addr, false, NULL);
- else if (zap_huge_pmd(tlb, vma, pmd, addr))
+ } else if (zap_huge_pmd(tlb, vma, pmd, addr))
goto next;
/* fall through */
}
--
2.28.0