Soft dirty tracking fixes
Subsystems (6)
cover Soft dirty tracking fixes
Hi! Here is a couple of fixes for soft dirty pages tracking. While first two patches are adressing issues, the last one is rather a cleanup which I've been asked to implement long ago, but I'm not sure if anyone picked it up.
Please take a look, thanks!
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
PATCH 1/3 mm: migration -- Do not loose soft dirty bit if page is in migration state
If page migration is turne on in the config and the page is migrating, we may loose soft dirty bit. If fork and mprotect if called on migrating pages (once migration is complete) pages do not obtain soft dirty bit in correspond pte entries. Fix it adding appropriate test on swap entries.
--- mm/memory.c | 2 ++ mm/migrate.c | 2 ++ mm/mprotect.c | 7 +++++-- 3 files changed, 9 insertions(+), 2 deletions(-)
mm/memory.c +2 -0
@@ -837,6 +837,8 @@ copy_one_pte(struct mm_struct *dst_mm, s*/ make_migration_entry_read (&entry); pte =swp_entry_to_pte (entry); +if (pte_swp_soft_dirty (*src_pte)) + pte =pte_swp_mksoft_dirty (pte);set_pte_at (src_mm, addr, src_pte, pte); } }
mm/migrate.c +2 -0
@@ -161,6 +161,8 @@ static int remove_migration_pte(struct pget_page (new); pte =pte_mkold (mk_pte (new, vma->vm_page_prot)); +if (pte_swp_soft_dirty (*ptep)) + pte =pte_mksoft_dirty (pte);if (is_write_migration_entry (entry)) pte =pte_mkwrite (pte);#ifdef CONFIG_HUGETLB_PAGE
mm/mprotect.c +5 -2
@@ -94,13 +94,16 @@ static unsigned long change_pte_range(stswp_entry_t entry =pte_to_swp_entry (oldpte);if (is_write_migration_entry (entry)) { +pte_t newpte;/* * A protection check is difficult so * just be safe and disable write */ make_migration_entry_read (&entry); -set_pte_at (mm, addr, pte, -swp_entry_to_pte (entry)); + newpte =swp_entry_to_pte (entry); +if (pte_swp_soft_dirty (oldpte)) + newpte =pte_swp_mksoft_dirty (newpte); +set_pte_at (mm, addr, pte, newpte); } pages++; }
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
PATCH 3/3 mm: Unify pte_to_pgoff and pgoff_to_pte helpers
In reply to Cyrill GorcunovUse unified pte_bitop helper to manipulate bits in pte/pgoff bitfield, and convert pte_to_pgoff/pgoff_to_pte to inlines.
--- arch/x86/include/asm/pgtable-2level.h | 100 ++++++++++++++++++++-------------- 1 file changed, 59 insertions(+), 41 deletions(-)
arch/x86/include/asm/pgtable-2level.h +59 -41
@@ -55,6 +55,13 @@ static inline pmd_t native_pmdp_get_and_#define native_pmdp_get_and_clear (xp) native_local_pmdp_get_and_clear(xp)#endif +/* Bit manipulation helper on pte/pgoff entry */ +static inline unsigned long pte_bitop (unsigned long value,unsigned int rightshift, +unsigned long mask,unsigned int leftshift) +{ +return ((value >> rightshift) & mask) << leftshift; +} +#ifdef CONFIG_MEM_SOFT_DIRTY /*
@@ -71,31 +78,34 @@ static inline pmd_t native_pmdp_get_and_#define PTE_FILE_BITS2 (PTE_FILE_SHIFT3 - PTE_FILE_SHIFT2 - 1)#define PTE_FILE_BITS3 (PTE_FILE_SHIFT4 - PTE_FILE_SHIFT3 - 1) -#define pte_to_pgoff (pte) \ - ((((pte).pte_low >> (PTE_FILE_SHIFT1)) \ - & ((1U << PTE_FILE_BITS1) - 1))) \ - + ((((pte).pte_low >> (PTE_FILE_SHIFT2)) \ - & ((1U << PTE_FILE_BITS2) - 1)) \ - << (PTE_FILE_BITS1)) \ - + ((((pte).pte_low >> (PTE_FILE_SHIFT3)) \ - & ((1U << PTE_FILE_BITS3) - 1)) \ - << (PTE_FILE_BITS1 + PTE_FILE_BITS2)) \ - + ((((pte).pte_low >> (PTE_FILE_SHIFT4))) \ - << (PTE_FILE_BITS1 + PTE_FILE_BITS2 + PTE_FILE_BITS3)) - -#define pgoff_to_pte (off) \ - ((pte_t) { .pte_low = \ - ((((off)) & ((1U << PTE_FILE_BITS1) - 1)) << PTE_FILE_SHIFT1) \ - + ((((off) >> PTE_FILE_BITS1) \ - & ((1U << PTE_FILE_BITS2) - 1)) \ - << PTE_FILE_SHIFT2) \ - + ((((off) >> (PTE_FILE_BITS1 + PTE_FILE_BITS2)) \ - & ((1U << PTE_FILE_BITS3) - 1)) \ - << PTE_FILE_SHIFT3) \ - + ((((off) >> \ - (PTE_FILE_BITS1 + PTE_FILE_BITS2 + PTE_FILE_BITS3))) \ - << PTE_FILE_SHIFT4) \ - + _PAGE_FILE }) +#define PTE_FILE_MASK1 ((1U << PTE_FILE_BITS1) - 1) +#define PTE_FILE_MASK2 ((1U << PTE_FILE_BITS2) - 1) +#define PTE_FILE_MASK3 ((1U << PTE_FILE_BITS3) - 1) + +#define PTE_FILE_LSHIFT2 (PTE_FILE_BITS1) +#define PTE_FILE_LSHIFT3 (PTE_FILE_BITS1 + PTE_FILE_BITS2) +#define PTE_FILE_LSHIFT4 (PTE_FILE_BITS1 + PTE_FILE_BITS2 + PTE_FILE_BITS3) + +static __always_inline pgoff_t pte_to_pgoff(pte_t pte) +{ +return (pgoff_t) + (pte_bitop (pte.pte_low,PTE_FILE_SHIFT1 ,PTE_FILE_MASK1 ,0 ) + +pte_bitop (pte.pte_low,PTE_FILE_SHIFT2 ,PTE_FILE_MASK2 ,PTE_FILE_LSHIFT2 ) + +pte_bitop (pte.pte_low,PTE_FILE_SHIFT3 ,PTE_FILE_MASK3 ,PTE_FILE_LSHIFT3 ) + +pte_bitop (pte.pte_low,PTE_FILE_SHIFT4 ,-1UL ,PTE_FILE_LSHIFT4 )); +} + +static __always_inline pte_t pgoff_to_pte(pgoff_t off) +{ +return (pte_t ){ + .pte_low = +pte_bitop (off,0 ,PTE_FILE_MASK1 ,PTE_FILE_SHIFT1 ) + +pte_bitop (off,PTE_FILE_LSHIFT2 ,PTE_FILE_MASK2 ,PTE_FILE_SHIFT2 ) + +pte_bitop (off,PTE_FILE_LSHIFT3 ,PTE_FILE_MASK3 ,PTE_FILE_SHIFT3 ) + +pte_bitop (off,PTE_FILE_LSHIFT4 ,-1UL ,PTE_FILE_SHIFT4 ) + + _PAGE_FILE, + }; +}#else /* CONFIG_MEM_SOFT_DIRTY */
@@ -115,22 +125,30 @@ static inline pmd_t native_pmdp_get_and_#define PTE_FILE_BITS1 (PTE_FILE_SHIFT2 - PTE_FILE_SHIFT1 - 1)#define PTE_FILE_BITS2 (PTE_FILE_SHIFT3 - PTE_FILE_SHIFT2 - 1) -#define pte_to_pgoff (pte) \ - ((((pte).pte_low >> PTE_FILE_SHIFT1) \ - & ((1U << PTE_FILE_BITS1) - 1)) \ - + ((((pte).pte_low >> PTE_FILE_SHIFT2) \ - & ((1U << PTE_FILE_BITS2) - 1)) << PTE_FILE_BITS1) \ - + (((pte).pte_low >> PTE_FILE_SHIFT3) \ - << (PTE_FILE_BITS1 + PTE_FILE_BITS2))) - -#define pgoff_to_pte (off) \ - ((pte_t) { .pte_low = \ - (((off) & ((1U << PTE_FILE_BITS1) - 1)) << PTE_FILE_SHIFT1) \ - + ((((off) >> PTE_FILE_BITS1) & ((1U << PTE_FILE_BITS2) - 1)) \ - << PTE_FILE_SHIFT2) \ - + (((off) >> (PTE_FILE_BITS1 + PTE_FILE_BITS2)) \ - << PTE_FILE_SHIFT3) \ - + _PAGE_FILE }) +#define PTE_FILE_MASK1 ((1U << PTE_FILE_BITS1) - 1) +#define PTE_FILE_MASK2 ((1U << PTE_FILE_BITS2) - 1) + +#define PTE_FILE_LSHIFT2 (PTE_FILE_BITS1) +#define PTE_FILE_LSHIFT3 (PTE_FILE_BITS1 + PTE_FILE_BITS2) + +static __always_inline pgoff_t pte_to_pgoff(pte_t pte) +{ +return (pgoff_t) + (pte_bitop (pte.pte_low,PTE_FILE_SHIFT1 ,PTE_FILE_MASK1 ,0 ) + +pte_bitop (pte.pte_low,PTE_FILE_SHIFT2 ,PTE_FILE_MASK2 ,PTE_FILE_LSHIFT2 ) + +pte_bitop (pte.pte_low,PTE_FILE_SHIFT3 ,-1UL ,PTE_FILE_LSHIFT3 )); +} + +static __always_inline pte_t pgoff_to_pte(pgoff_t off) +{ +return (pte_t ){ + .pte_low = +pte_bitop (off,0 ,PTE_FILE_MASK1 ,PTE_FILE_SHIFT1 ) + +pte_bitop (off,PTE_FILE_LSHIFT2 ,PTE_FILE_MASK2 ,PTE_FILE_SHIFT2 ) + +pte_bitop (off,PTE_FILE_LSHIFT3 ,-1UL ,PTE_FILE_SHIFT3 ) + + _PAGE_FILE, + }; +}#endif /* CONFIG_MEM_SOFT_DIRTY */
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
PATCH 2/3 mm: pagemap -- Inspect _PAGE_SOFT_DIRTY only on present pages
In reply to Cyrill GorcunovIn case if a page we are inspecting is laying in swap we may occasionally report it as having soft dirty bit (even if it is clean). pte_soft_dirty helper should be called on present pte only.
--- fs/proc/task_mmu.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
fs/proc/task_mmu.c +3 -1
@@ -941,6 +941,8 @@ static void pte_to_pagemap_entry(pagemap frame =pte_pfn (pte); flags =PM_PRESENT ; page =vm_normal_page (vma, addr, pte); +if (pte_soft_dirty (pte)) + flags2 |= __PM_SOFT_DIRTY; }else if (is_swap_pte (pte)) {swp_entry_t entry;if (pte_swp_soft_dirty (pte))
@@ -960,7 +962,7 @@ static void pte_to_pagemap_entry(pagemapif (page && !PageAnon (page)) flags |=PM_FILE ; -if ((vma->vm_flags &VM_SOFTDIRTY ) ||pte_soft_dirty (pte)) +if ((vma->vm_flags &VM_SOFTDIRTY )) flags2 |= __PM_SOFT_DIRTY; *pme =make_pme (PM_PFRAME (frame) |PM_STATUS2 (pm->v2, flags2) | flags);
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
Re: [patch 1/3] [PATCH] mm: migration -- Do not loose soft dirty bit if page is in migration state
In reply to Cyrill GorcunovQuoted 28 lines · Cyrill Gorcunov
If page migration is turne on in the config and the page is migrating, we may loose soft dirty bit. If fork and mprotect if called on migrating pages (once migration is complete) pages do not obtain soft dirty bit in correspond pte entries. Fix it adding appropriate test on swap entries.
Signed-off-by Cyrill Gorcunov <[email protected]>Cc Pavel Emelyanov <[email protected]>Cc Andy Lutomirski <[email protected]>Cc Andrew Morton <[email protected]>Cc Matt Mackall <[email protected]>Cc Xiao Guangrong <[email protected]>Cc Marcelo Tosatti <[email protected]>Cc KOSAKI Motohiro <[email protected]>Cc Stephen Rothwell <[email protected]>Cc Peter Zijlstra <[email protected]>Cc "Aneesh Kumar K.V" <[email protected]>--- mm/memory.c | 2 ++ mm/migrate.c | 2 ++ mm/mprotect.c | 7 +++++-- 3 files changed, 9 insertions(+), 2 deletions(-)Index:
linux-2.6.git/mm/memory.c
===================================================================
mm/memory.c copy_one_pte(struct mm_struct *dst_mm, s · line 844
Quoted 8 lines
mm/memory.c +2
-0@@ -837,6 +837,8 @@ copy_one_pte(struct mm_struct *dst_mm, s*/ make_migration_entry_read (&entry); pte =swp_entry_to_pte (entry); +if (pte_swp_soft_dirty (*src_pte)) + pte =pte_swp_mksoft_dirty (pte);set_pte_at (src_mm, addr, src_pte, pte); } }
When we convert pte to swap_entry, we convert soft-dirty bit in pte_to_swp_entry(). So I think that it's better to convert it back in swp_entry_to_pte() when we do swap_entry-to-pte conversion.
Thanks,
Naoya Horiguchi
Quoted 38 lines
Index:
linux-2.6.git/mm/migrate.c
===================================================================mm/migrate.c +2
-0@@ -161,6 +161,8 @@ static int remove_migration_pte(struct pget_page (new); pte =pte_mkold (mk_pte (new, vma->vm_page_prot)); +if (pte_swp_soft_dirty (*ptep)) + pte =pte_mksoft_dirty (pte);if (is_write_migration_entry (entry)) pte =pte_mkwrite (pte);#ifdef CONFIG_HUGETLB_PAGE Index:
linux-2.6.git/mm/mprotect.c
===================================================================mm/mprotect.c +5
-3@@ -94,13 +94,16 @@ static unsigned long change_pte_range(stswp_entry_t entry =pte_to_swp_entry (oldpte);if (is_write_migration_entry (entry)) { +pte_t newpte;/* * A protection check is difficult so * just be safe and disable write */ make_migration_entry_read (&entry); -set_pte_at (mm, addr, pte, -swp_entry_to_pte (entry)); + newpte =swp_entry_to_pte (entry); +if (pte_swp_soft_dirty (oldpte)) + newpte =pte_swp_mksoft_dirty (newpte); +set_pte_at (mm, addr, pte, newpte); } pages++; } --
Quoted 5 lines
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
Re: [patch 2/3] [PATCH] mm: pagemap -- Inspect _PAGE_SOFT_DIRTY only on present pages
In reply to Cyrill GorcunovQuoted 5 lines · Cyrill Gorcunov
In case if a page we are inspecting is laying in swap we may occasionally report it as having soft dirty bit (even if it is clean).
pte_soft_dirtyhelper should be called on present pte only.
Quoted 11 lines
Signed-off-by Cyrill Gorcunov <[email protected]>Cc Pavel Emelyanov <[email protected]>Cc Andy Lutomirski <[email protected]>Cc Andrew Morton <[email protected]>Cc Matt Mackall <[email protected]>Cc Xiao Guangrong <[email protected]>Cc Marcelo Tosatti <[email protected]>Cc KOSAKI Motohiro <[email protected]>Cc Stephen Rothwell <[email protected]>Cc Peter Zijlstra <[email protected]>Cc "Aneesh Kumar K.V" <[email protected]>
Looks nice to me.
Quoted 28 lines
--- fs/proc/task_mmu.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)Index:
linux-2.6.git/fs/proc/task_mmu.c
===================================================================fs/proc/task_mmu.c +3
-2@@ -941,6 +941,8 @@ static void pte_to_pagemap_entry(pagemap frame =pte_pfn (pte); flags =PM_PRESENT ; page =vm_normal_page (vma, addr, pte); +if (pte_soft_dirty (pte)) + flags2 |= __PM_SOFT_DIRTY; }else if (is_swap_pte (pte)) {swp_entry_t entry;if (pte_swp_soft_dirty (pte))@@ -960,7 +962,7 @@ static void pte_to_pagemap_entry(pagemapif (page && !PageAnon (page)) flags |=PM_FILE ; -if ((vma->vm_flags &VM_SOFTDIRTY ) ||pte_soft_dirty (pte)) +if ((vma->vm_flags &VM_SOFTDIRTY )) flags2 |= __PM_SOFT_DIRTY; *pme =make_pme (PM_PFRAME (frame) |PM_STATUS2 (pm->v2, flags2) | flags); --
Quoted 5 lines
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
Re: [patch 1/3] [PATCH] mm: migration -- Do not loose soft dirty bit if page is in migration state
In reply to Naoya HoriguchiQuoted 9 lines · Naoya Horiguchi
Quoted 9 lines
Index:
linux-2.6.git/mm/memory.c
===================================================================mm/memory.c +1
-0@@ -837,6 +837,8 @@ copy_one_pte(struct mm_struct *dst_mm, s*/ make_migration_entry_read (&entry); pte =swp_entry_to_pte (entry); +if (pte_swp_soft_dirty (*src_pte))
Quoted 8 lines
mm/memory.c copy_one_pte(struct mm_struct *dst_mm, s · line 844
Quoted 4 lines
mm/memory.c +1
-0+ pte =pte_swp_mksoft_dirty (pte);set_pte_at (src_mm, addr, src_pte, pte); } }When we convert pte to
swap_entry, we convert soft-dirty bit inpte_to_swp_entry(). So I think that it's better to convert it back inswp_entry_to_pte()when we do swap_entry-to-pte conversion.
No, soft dirty bit lays _only_ inside pte entry in memory, iow swp_entry_t never has this bit, thus to be able to find soft dirty status in swp_entry_to_pte you need to extend this function and pass pte entry itself as an argument, which eventually will bring more massive patch and will be a way more confusing I think.
Or I misunderstood you?
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
Re: [patch 1/3] [PATCH] mm: migration -- Do not loose soft dirty bit if page is in migration state
Quoted 19 lines · Cyrill Gorcunov
Quoted 9 lines · Naoya Horiguchi
Quoted 9 lines
Index:
linux-2.6.git/mm/memory.c
===================================================================mm/memory.c +1
-0@@ -837,6 +837,8 @@ copy_one_pte(struct mm_struct *dst_mm, s*/ make_migration_entry_read (&entry); pte =swp_entry_to_pte (entry); +if (pte_swp_soft_dirty (*src_pte))Quoted 8 lines
mm/memory.c copy_one_pte(struct mm_struct *dst_mm, s · line 844
Quoted 4 lines
mm/memory.c +1
-0+ pte =pte_swp_mksoft_dirty (pte);set_pte_at (src_mm, addr, src_pte, pte); } }When we convert pte to
swap_entry, we convert soft-dirty bit inpte_to_swp_entry(). So I think that it's better to convert it back inswp_entry_to_pte()when we do swap_entry-to-pte conversion.
Quoted 5 lines
No, soft dirty bit lays _only_ inside pte entry in memory, iow
swp_entry_tnever has this bit, thus to be able to find soft dirty status inswp_entry_to_pteyou need to extend this function and pass pte entry itself as an argument, which eventually will bring more massive patch and will be a way more confusing I think.
OK, you're right. Thanks for explanation.
Quoted 1 line
Or I misunderstood you?
No, I misread the code, sorry.
Naoya
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
Andrew Morton
maintainerQuoted 5 lines · On Tue, 08 Oct 2013 13:00:19 +0400 Cyrill Gorcunov <[email protected]> wrote:
Hi! Here is a couple of fixes for soft dirty pages tracking. While first two patches are adressing issues, the last one is rather a cleanup which I've been asked to implement long ago, but I'm not sure if anyone picked it up.
Do you consider the problems which patches 1 and 2 address to be sufficiently serious to justify backporting into -stable?
I already have patch 3, as arch-x86-mnify-pte_to_pgoff-and-pgoff_to_pte-helpers.patch (with s/m/u). I've queued it for transmission to the x86 guys.
--
To unsubscribe, send a message with 'unsubscribe linux-mm' in the body to [email protected]. For more info on Linux MM,
see: http://www.linux-mm.org/ .
Don't email: <a href=mailto:"[email protected]"> [email protected] </a>
Quoted 3 lines · Andrew Morton
Do you consider the problems which patches 1 and 2 address to be sufficiently serious to justify backporting into -stable?
Good question! Yeah, since dirty bit traking is in 3.11 already, it would be great to merge these two patches into -stable. Should I resend them with stable team CC'ed?
Andrew Morton
maintainerQuoted 7 lines · On Wed, 9 Oct 2013 00:02:24 +0400 Cyrill Gorcunov <[email protected]> wrote:
Quoted 3 lines · Andrew Morton
Do you consider the problems which patches 1 and 2 address to be sufficiently serious to justify backporting into -stable?
Good question! Yeah, since dirty bit traking is in 3.11 already, it would be great to merge these two patches into -stable.
OK.
Quoted 1 line
Should I resend them with stable team CC'ed?
Nope, I added cc:stable to the changelogs so they should receive consideration by Greg automatically.