Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]
Groups > linux.kernel > #1269373
| From | Ross Zwisler <ross.zwisler@linux.intel.com> |
|---|---|
| Newsgroups | linux.kernel |
| Subject | [PATCH v2 06/11] mm: add pgoff_mkclean() |
| Date | 2015-11-14 01:20 +0100 |
| Message-ID | <quwJs-4ZF-15@gated-at.bofh.it> (permalink) |
| References | <quwzM-4US-1@gated-at.bofh.it> |
| Organization | linux.* mail to news gateway |
Introduce pgoff_mkclean() which conceptually is similar to page_mkclean()
except it works in the absence of struct page and it can also be used to
clean PMDs. This is needed for DAX's dirty page handling.
pgoff_mkclean() doesn't return an error for a missing PTE/PMD when looping
through the VMAs because it's not a requirement that each of the
potentially many VMAs associated with a given struct address_space have a
mapping set up for our pgoff.
Signed-off-by: Ross Zwisler <ross.zwisler@linux.intel.com>
---
include/linux/rmap.h | 5 +++++
mm/rmap.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 56 insertions(+)
diff --git a/include/linux/rmap.h b/include/linux/rmap.h
index 29446ae..171a4ac 100644
--- a/include/linux/rmap.h
+++ b/include/linux/rmap.h
@@ -223,6 +223,11 @@ unsigned long page_address_in_vma(struct page *, struct vm_area_struct *);
int page_mkclean(struct page *);
/*
+ * Cleans and write protects the PTEs of shared mappings.
+ */
+void pgoff_mkclean(pgoff_t, struct address_space *);
+
+/*
* called in munlock()/munmap() path to check for other vmas holding
* the page mlocked.
*/
diff --git a/mm/rmap.c b/mm/rmap.c
index f5b5c1f..8114862 100644
--- a/mm/rmap.c
+++ b/mm/rmap.c
@@ -586,6 +586,16 @@ vma_address(struct page *page, struct vm_area_struct *vma)
return address;
}
+static inline unsigned long
+pgoff_address(pgoff_t pgoff, struct vm_area_struct *vma)
+{
+ unsigned long address;
+
+ address = vma->vm_start + ((pgoff - vma->vm_pgoff) << PAGE_SHIFT);
+ VM_BUG_ON_VMA(address < vma->vm_start || address >= vma->vm_end, vma);
+ return address;
+}
+
#ifdef CONFIG_ARCH_WANT_BATCHED_UNMAP_TLB_FLUSH
static void percpu_flush_tlb_batch_pages(void *data)
{
@@ -1040,6 +1050,47 @@ int page_mkclean(struct page *page)
}
EXPORT_SYMBOL_GPL(page_mkclean);
+void pgoff_mkclean(pgoff_t pgoff, struct address_space *mapping)
+{
+ struct vm_area_struct *vma;
+ int ret = 0;
+
+ i_mmap_lock_read(mapping);
+ vma_interval_tree_foreach(vma, &mapping->i_mmap, pgoff, pgoff) {
+ struct mm_struct *mm = vma->vm_mm;
+ pmd_t pmd, *pmdp = NULL;
+ pte_t pte, *ptep = NULL;
+ unsigned long address;
+ spinlock_t *ptl;
+
+ address = pgoff_address(pgoff, vma);
+
+ /* when this returns successfully ptl is locked */
+ ret = follow_pte_pmd(mm, address, &ptep, &pmdp, &ptl);
+ if (ret)
+ continue;
+
+ if (pmdp) {
+ flush_cache_page(vma, address, pmd_pfn(*pmdp));
+ pmd = pmdp_huge_clear_flush(vma, address, pmdp);
+ pmd = pmd_wrprotect(pmd);
+ pmd = pmd_mkclean(pmd);
+ set_pmd_at(mm, address, pmdp, pmd);
+ spin_unlock(ptl);
+ } else {
+ BUG_ON(!ptep);
+ flush_cache_page(vma, address, pte_pfn(*ptep));
+ pte = ptep_clear_flush(vma, address, ptep);
+ pte = pte_wrprotect(pte);
+ pte = pte_mkclean(pte);
+ set_pte_at(mm, address, ptep, pte);
+ pte_unmap_unlock(ptep, ptl);
+ }
+ }
+ i_mmap_unlock_read(mapping);
+}
+EXPORT_SYMBOL_GPL(pgoff_mkclean);
+
/**
* page_move_anon_rmap - move a page to our anon_vma
* @page: the page to move to our anon_vma
--
2.1.0
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Back to linux.kernel | Previous | Next — Previous in thread | Next in thread | Find similar | Unroll thread
[PATCH v2 00/11] DAX fsynx/msync support Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:10 +0100
[PATCH v2 09/11] ext2: add support for DAX fsync/msync Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:10 +0100
[PATCH v2 07/11] mm: add find_get_entries_tag() Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:10 +0100
[PATCH v2 10/11] ext4: add support for DAX fsync/msync Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:10 +0100
[PATCH v2 11/11] xfs: add support for DAX fsync/msync Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:10 +0100
[PATCH v2 05/11] mm: add follow_pte_pmd() Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:20 +0100
[PATCH v2 01/11] pmem: add wb_cache_pmem() to the PMEM API Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:20 +0100
[PATCH v2 08/11] dax: add support for fsync/sync Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:20 +0100
[PATCH v2 03/11] pmem: enable REQ_FUA/REQ_FLUSH handling Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:20 +0100
Re: [PATCH v2 03/11] pmem: enable REQ_FUA/REQ_FLUSH handling Dan Williams <dan.j.williams@intel.com> - 2015-11-14 01:30 +0100
Re: [PATCH v2 03/11] pmem: enable REQ_FUA/REQ_FLUSH handling Andreas Dilger <adilger@dilger.ca> - 2015-11-14 01:50 +0100
Re: [PATCH v2 03/11] pmem: enable REQ_FUA/REQ_FLUSH handling Dan Williams <dan.j.williams@intel.com> - 2015-11-14 03:40 +0100
[PATCH v2 06/11] mm: add pgoff_mkclean() Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:20 +0100
[PATCH v2 02/11] mm: add pmd_mkclean() Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:20 +0100
Re: [PATCH v2 02/11] mm: add pmd_mkclean() Dave Hansen <dave.hansen@intel.com> - 2015-11-14 02:10 +0100
[PATCH v2 04/11] dax: support dirty DAX entries in radix tree Ross Zwisler <ross.zwisler@linux.intel.com> - 2015-11-14 01:20 +0100
csiph-web