All of lore.kernel.org
 help / color / mirror / Atom feed
From: Christophe Leroy <christophe.leroy@csgroup.eu>
To: Rick Edgecombe <rick.p.edgecombe@intel.com>,
	"x86@kernel.org" <x86@kernel.org>,
	"H . Peter Anvin" <hpa@zytor.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Ingo Molnar <mingo@redhat.com>,
	"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"linux-doc@vger.kernel.org" <linux-doc@vger.kernel.org>,
	"linux-mm@kvack.org" <linux-mm@kvack.org>,
	"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
	"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
	Arnd Bergmann <arnd@arndb.de>, Andy Lutomirski <luto@kernel.org>,
	Balbir Singh <bsingharora@gmail.com>,
	Borislav Petkov <bp@alien8.de>,
	Cyrill Gorcunov <gorcunov@gmail.com>,
	Dave Hansen <dave.hansen@linux.intel.com>,
	Eugene Syromiatnikov <esyr@redhat.com>,
	Florian Weimer <fweimer@redhat.com>,
	"H . J . Lu" <hjl.tools@gmail.com>, Jann Horn <jannh@google.com>,
	Jonathan Corbet <corbet@lwn.net>,
	Kees Cook <keescook@chromium.org>,
	Mike Kravetz <mike.kravetz@oracle.com>,
	Nadav Amit <nadav.amit@gmail.com>,
	Oleg Nesterov <oleg@redhat.com>, Pavel Machek <pavel@ucw.cz>,
	Peter Zijlstra <peterz@infradead.org>,
	Randy Dunlap <rdunlap@infradead.org>,
	Weijiang Yang <weijiang.yang@intel.com>,
	"Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>,
	John Allen <john.allen@amd.com>,
	"kcc@google.com" <kcc@google.com>,
	"eranian@google.com" <eranian@google.com>,
	"rppt@kernel.org" <rppt@kernel.org>,
	"jamorris@linux.microsoft.com" <jamorris@linux.microsoft.com>,
	"dethoma@microsoft.com" <dethoma@microsoft.com>,
	"akpm@linux-foundation.org" <akpm@linux-foundation.org>,
	"Andrew.Cooper3@citrix.com" <Andrew.Cooper3@citrix.com>,
	"christina.schimpe@intel.com" <christina.schimpe@intel.com>,
	"david@redhat.com" <david@redhat.com>,
	"debug@rivosinc.com" <debug@rivosinc.com>
Cc: "linux-alpha@vger.kernel.org" <linux-alpha@vger.kernel.org>,
	"linux-snps-arc@lists.infradead.org"
	<linux-snps-arc@lists.infradead.org>,
	"linux-arm-kernel@lists.infradead.org"
	<linux-arm-kernel@lists.infradead.org>,
	"linux-csky@vger.kernel.org" <linux-csky@vger.kernel.org>,
	"linux-hexagon@vger.kernel.org" <linux-hexagon@vger.kernel.org>,
	"linux-ia64@vger.kernel.org" <linux-ia64@vger.kernel.org>,
	"loongarch@lists.linux.dev" <loongarch@lists.linux.dev>,
	"linux-m68k@lists.linux-m68k.org"
	<linux-m68k@lists.linux-m68k.org>,
	Michal Simek <monstr@monstr.eu>,
	Dinh Nguyen <dinguyen@kernel.org>,
	"linux-mips@vger.kernel.org" <linux-mips@vger.kernel.org>,
	"linux-openrisc@vger.kernel.org" <linux-openrisc@vger.kernel.org>,
	"linux-parisc@vger.kernel.org" <linux-parisc@vger.kernel.org>,
	"linuxppc-dev@lists.ozlabs.org" <linuxppc-dev@lists.ozlabs.org>,
	"linux-riscv@lists.infradead.org"
	<linux-riscv@lists.infradead.org>,
	"linux-s390@vger.kernel.org" <linux-s390@vger.kernel.org>,
	"linux-sh@vger.kernel.org" <linux-sh@vger.kernel.org>,
	"sparclinux@vger.kernel.org" <sparclinux@vger.kernel.org>,
	"linux-um@lists.infradead.org" <linux-um@lists.infradead.org>,
	"xen-devel@lists.xenproject.org" <xen-devel@lists.xenproject.org>
Subject: Re: [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA
Date: Wed, 1 Mar 2023 07:03:23 +0000	[thread overview]
Message-ID: <1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu> (raw)
In-Reply-To: <20230227222957.24501-14-rick.p.edgecombe@intel.com>



Le 27/02/2023 à 23:29, Rick Edgecombe a écrit :
> The x86 Control-flow Enforcement Technology (CET) feature includes a new
> type of memory called shadow stack. This shadow stack memory has some
> unusual properties, which requires some core mm changes to function
> properly.
> 
> One of these unusual properties is that shadow stack memory is writable,
> but only in limited ways. These limits are applied via a specific PTE
> bit combination. Nevertheless, the memory is writable, and core mm code
> will need to apply the writable permissions in the typical paths that
> call pte_mkwrite().
> 
> In addition to VM_WRITE, the shadow stack VMA's will have a flag denoting
> that they are special shadow stack flavor of writable memory. So make
> pte_mkwrite() take a VMA, so that the x86 implementation of it can know to
> create regular writable memory or shadow stack memory.
> 
> Apply the same changes for pmd_mkwrite() and huge_pte_mkwrite().

I'm not sure it is a good idea to add a second argument to 
pte_mkwrite(). All pte_mkxxxx() only take a pte and nothing else.

I think you should do the same as commit d9ed9faac283 ("mm: add new 
arch_make_huge_pte() method for tile support")

Christophe

> 
> No functional change.
> 
> Cc: linux-doc@vger.kernel.org
> Cc: linux-kernel@vger.kernel.org
> Cc: linux-alpha@vger.kernel.org
> Cc: linux-snps-arc@lists.infradead.org
> Cc: linux-arm-kernel@lists.infradead.org
> Cc: linux-csky@vger.kernel.org
> Cc: linux-hexagon@vger.kernel.org
> Cc: linux-ia64@vger.kernel.org
> Cc: loongarch@lists.linux.dev
> Cc: linux-m68k@lists.linux-m68k.org
> Cc: Michal Simek <monstr@monstr.eu>
> Cc: Dinh Nguyen <dinguyen@kernel.org>
> Cc: linux-mips@vger.kernel.org
> Cc: linux-openrisc@vger.kernel.org
> Cc: linux-parisc@vger.kernel.org
> Cc: linuxppc-dev@lists.ozlabs.org
> Cc: linux-riscv@lists.infradead.org
> Cc: linux-s390@vger.kernel.org
> Cc: linux-sh@vger.kernel.org
> Cc: sparclinux@vger.kernel.org
> Cc: linux-um@lists.infradead.org
> Cc: xen-devel@lists.xenproject.org
> Cc: linux-arch@vger.kernel.org
> Cc: linux-mm@kvack.org
> Tested-by: Pengfei Xu <pengfei.xu@intel.com>
> Tested-by: John Allen <john.allen@amd.com>
> Tested-by: Kees Cook <keescook@chromium.org>
> Acked-by: Mike Rapoport (IBM) <rppt@kernel.org>
> Acked-by: Michael Ellerman <mpe@ellerman.id.au>
> Acked-by: David Hildenbrand <david@redhat.com>
> Reviewed-by: Kees Cook <keescook@chromium.org>
> Suggested-by: David Hildenbrand <david@redhat.com>
> Signed-off-by: Rick Edgecombe <rick.p.edgecombe@intel.com>
> 
> ---
> Hi Non-x86 Arch’s,
> 
> x86 has a feature that allows for the creation of a special type of
> writable memory (shadow stack) that is only writable in limited specific
> ways. Previously, changes were proposed to core MM code to teach it to
> decide when to create normally writable memory or the special shadow stack
> writable memory, but David Hildenbrand suggested[0] to change
> pXX_mkwrite() to take a VMA, so awareness of shadow stack memory can be
> moved into x86 code.
> 
> Since pXX_mkwrite() is defined in every arch, it requires some tree-wide
> changes. So that is why you are seeing some patches out of a big x86
> series pop up in your arch mailing list. There is no functional change.
> After this refactor, the shadow stack series goes on to use the arch
> helpers to push shadow stack memory details inside arch/x86.
> 
> Testing was just 0-day build testing.
> 
> Hopefully that is enough context. Thanks!
> 
> [0] https://lore.kernel.org/lkml/0e29a2d0-08d8-bcd6-ff26-4bea0e4037b0@redhat.com/#t
> 
> v6:
>   - New patch
> ---
>   Documentation/mm/arch_pgtable_helpers.rst    |  9 ++++++---
>   arch/alpha/include/asm/pgtable.h             |  6 +++++-
>   arch/arc/include/asm/hugepage.h              |  2 +-
>   arch/arc/include/asm/pgtable-bits-arcv2.h    |  7 ++++++-
>   arch/arm/include/asm/pgtable-3level.h        |  7 ++++++-
>   arch/arm/include/asm/pgtable.h               |  2 +-
>   arch/arm64/include/asm/pgtable.h             |  4 ++--
>   arch/csky/include/asm/pgtable.h              |  2 +-
>   arch/hexagon/include/asm/pgtable.h           |  2 +-
>   arch/ia64/include/asm/pgtable.h              |  2 +-
>   arch/loongarch/include/asm/pgtable.h         |  4 ++--
>   arch/m68k/include/asm/mcf_pgtable.h          |  2 +-
>   arch/m68k/include/asm/motorola_pgtable.h     |  6 +++++-
>   arch/m68k/include/asm/sun3_pgtable.h         |  6 +++++-
>   arch/microblaze/include/asm/pgtable.h        |  2 +-
>   arch/mips/include/asm/pgtable.h              |  6 +++---
>   arch/nios2/include/asm/pgtable.h             |  2 +-
>   arch/openrisc/include/asm/pgtable.h          |  2 +-
>   arch/parisc/include/asm/pgtable.h            |  6 +++++-
>   arch/powerpc/include/asm/book3s/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/book3s/64/pgtable.h |  4 ++--
>   arch/powerpc/include/asm/nohash/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/nohash/32/pte-8xx.h |  2 +-
>   arch/powerpc/include/asm/nohash/64/pgtable.h |  2 +-
>   arch/riscv/include/asm/pgtable.h             |  6 +++---
>   arch/s390/include/asm/hugetlb.h              |  4 ++--
>   arch/s390/include/asm/pgtable.h              |  4 ++--
>   arch/sh/include/asm/pgtable_32.h             | 10 ++++++++--
>   arch/sparc/include/asm/pgtable_32.h          |  2 +-
>   arch/sparc/include/asm/pgtable_64.h          |  6 +++---
>   arch/um/include/asm/pgtable.h                |  2 +-
>   arch/x86/include/asm/pgtable.h               |  6 ++++--
>   arch/xtensa/include/asm/pgtable.h            |  2 +-
>   include/asm-generic/hugetlb.h                |  4 ++--
>   include/linux/mm.h                           |  2 +-
>   mm/debug_vm_pgtable.c                        | 16 ++++++++--------
>   mm/huge_memory.c                             |  6 +++---
>   mm/hugetlb.c                                 |  4 ++--
>   mm/memory.c                                  |  4 ++--
>   mm/migrate_device.c                          |  2 +-
>   mm/mprotect.c                                |  2 +-
>   mm/userfaultfd.c                             |  2 +-
>   42 files changed, 106 insertions(+), 69 deletions(-)
> 
> diff --git a/Documentation/mm/arch_pgtable_helpers.rst b/Documentation/mm/arch_pgtable_helpers.rst
> index 30d9a09f01f4..78ac3ff2fe1d 100644
> --- a/Documentation/mm/arch_pgtable_helpers.rst
> +++ b/Documentation/mm/arch_pgtable_helpers.rst
> @@ -46,7 +46,8 @@ PTE Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pte_mkclean               | Creates a clean PTE                              |
>   +---------------------------+--------------------------------------------------+
> -| pte_mkwrite               | Creates a writable PTE                           |
> +| pte_mkwrite               | Creates a writable PTE of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pte_wrprotect             | Creates a write protected PTE                    |
>   +---------------------------+--------------------------------------------------+
> @@ -118,7 +119,8 @@ PMD Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pmd_mkclean               | Creates a clean PMD                              |
>   +---------------------------+--------------------------------------------------+
> -| pmd_mkwrite               | Creates a writable PMD                           |
> +| pmd_mkwrite               | Creates a writable PMD of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pmd_wrprotect             | Creates a write protected PMD                    |
>   +---------------------------+--------------------------------------------------+
> @@ -222,7 +224,8 @@ HugeTLB Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_mkdirty          | Creates a dirty HugeTLB                          |
>   +---------------------------+--------------------------------------------------+
> -| huge_pte_mkwrite          | Creates a writable HugeTLB                       |
> +| huge_pte_mkwrite          | Creates a writable HugeTLB of the type specified |
> +|                           | by the VMA.                                      |
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_wrprotect        | Creates a write protected HugeTLB                |
>   +---------------------------+--------------------------------------------------+
> diff --git a/arch/alpha/include/asm/pgtable.h b/arch/alpha/include/asm/pgtable.h
> index ba43cb841d19..fb5d207c2a89 100644
> --- a/arch/alpha/include/asm/pgtable.h
> +++ b/arch/alpha/include/asm/pgtable.h
> @@ -256,9 +256,13 @@ extern inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   extern inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~(__DIRTY_BITS); return pte; }
>   extern inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~(__ACCESS_BITS); return pte; }
> -extern inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= __DIRTY_BITS; return pte; }
>   extern inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= __ACCESS_BITS; return pte; }
> +extern inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_FOW;
> +	return pte;
> +}
>   
>   /*
>    * The smp_rmb() in the following functions are required to order the load of
> diff --git a/arch/arc/include/asm/hugepage.h b/arch/arc/include/asm/hugepage.h
> index 5001b796fb8d..223a96967188 100644
> --- a/arch/arc/include/asm/hugepage.h
> +++ b/arch/arc/include/asm/hugepage.h
> @@ -21,7 +21,7 @@ static inline pmd_t pte_pmd(pte_t pte)
>   }
>   
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/arc/include/asm/pgtable-bits-arcv2.h b/arch/arc/include/asm/pgtable-bits-arcv2.h
> index 6e9f8ca6d6a1..a5b8bc955015 100644
> --- a/arch/arc/include/asm/pgtable-bits-arcv2.h
> +++ b/arch/arc/include/asm/pgtable-bits-arcv2.h
> @@ -87,7 +87,6 @@
>   
>   PTE_BIT_FUNC(mknotpresent,     &= ~(_PAGE_PRESENT));
>   PTE_BIT_FUNC(wrprotect,	&= ~(_PAGE_WRITE));
> -PTE_BIT_FUNC(mkwrite,	|= (_PAGE_WRITE));
>   PTE_BIT_FUNC(mkclean,	&= ~(_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkdirty,	|= (_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkold,	&= ~(_PAGE_ACCESSED));
> @@ -95,6 +94,12 @@ PTE_BIT_FUNC(mkyoung,	|= (_PAGE_ACCESSED));
>   PTE_BIT_FUNC(mkspecial,	|= (_PAGE_SPECIAL));
>   PTE_BIT_FUNC(mkhuge,	|= (_PAGE_HW_SZ));
>   
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= (_PAGE_WRITE);
> +	return pte;
> +}
> +
>   static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
>   {
>   	return __pte((pte_val(pte) & _PAGE_CHG_MASK) | pgprot_val(newprot));
> diff --git a/arch/arm/include/asm/pgtable-3level.h b/arch/arm/include/asm/pgtable-3level.h
> index 106049791500..df071a807610 100644
> --- a/arch/arm/include/asm/pgtable-3level.h
> +++ b/arch/arm/include/asm/pgtable-3level.h
> @@ -202,11 +202,16 @@ static inline pmd_t pmd_##fn(pmd_t pmd) { pmd_val(pmd) op; return pmd; }
>   
>   PMD_BIT_FUNC(wrprotect,	|= L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkold,	&= ~PMD_SECT_AF);
> -PMD_BIT_FUNC(mkwrite,   &= ~L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkdirty,   |= L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkclean,   &= ~L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkyoung,   |= PMD_SECT_AF);
>   
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
> +{
> +	pmd_val(pmd) |= L_PMD_SECT_RDONLY;
> +	return pmd;
> +}
> +
>   #define pmd_mkhuge(pmd)		(__pmd(pmd_val(pmd) & ~PMD_TABLE_BIT))
>   
>   #define pmd_pfn(pmd)		(((pmd_val(pmd) & PMD_MASK) & PHYS_MASK) >> PAGE_SHIFT)
> diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
> index a58ccbb406ad..39ad1ae1308d 100644
> --- a/arch/arm/include/asm/pgtable.h
> +++ b/arch/arm/include/asm/pgtable.h
> @@ -227,7 +227,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   	return set_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return clear_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
> diff --git a/arch/arm64/include/asm/pgtable.h b/arch/arm64/include/asm/pgtable.h
> index cccf8885792e..913bf370f74a 100644
> --- a/arch/arm64/include/asm/pgtable.h
> +++ b/arch/arm64/include/asm/pgtable.h
> @@ -187,7 +187,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -492,7 +492,7 @@ static inline int pmd_trans_huge(pmd_t pmd)
>   #define pmd_cont(pmd)		pte_cont(pmd_pte(pmd))
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/csky/include/asm/pgtable.h b/arch/csky/include/asm/pgtable.h
> index d4042495febc..c2f92c991e37 100644
> --- a/arch/csky/include/asm/pgtable.h
> +++ b/arch/csky/include/asm/pgtable.h
> @@ -176,7 +176,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> diff --git a/arch/hexagon/include/asm/pgtable.h b/arch/hexagon/include/asm/pgtable.h
> index 59393613d086..14ab9c789c0e 100644
> --- a/arch/hexagon/include/asm/pgtable.h
> +++ b/arch/hexagon/include/asm/pgtable.h
> @@ -300,7 +300,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   }
>   
>   /* pte_mkwrite - mark page as writable */
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/ia64/include/asm/pgtable.h b/arch/ia64/include/asm/pgtable.h
> index 21c97e31a28a..f879dd626da6 100644
> --- a/arch/ia64/include/asm/pgtable.h
> +++ b/arch/ia64/include/asm/pgtable.h
> @@ -268,7 +268,7 @@ ia64_phys_addr_valid (unsigned long addr)
>    * access rights:
>    */
>   #define pte_wrprotect(pte)	(__pte(pte_val(pte) & ~_PAGE_AR_RW))
> -#define pte_mkwrite(pte)	(__pte(pte_val(pte) | _PAGE_AR_RW))
> +#define pte_mkwrite(pte, vma)	(__pte(pte_val(pte) | _PAGE_AR_RW))
>   #define pte_mkold(pte)		(__pte(pte_val(pte) & ~_PAGE_A))
>   #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_A))
>   #define pte_mkclean(pte)	(__pte(pte_val(pte) & ~_PAGE_D))
> diff --git a/arch/loongarch/include/asm/pgtable.h b/arch/loongarch/include/asm/pgtable.h
> index d28fb9dbec59..ebf645f40298 100644
> --- a/arch/loongarch/include/asm/pgtable.h
> +++ b/arch/loongarch/include/asm/pgtable.h
> @@ -390,7 +390,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -490,7 +490,7 @@ static inline int pmd_write(pmd_t pmd)
>   	return !!(pmd_val(pmd) & _PAGE_WRITE);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/m68k/include/asm/mcf_pgtable.h b/arch/m68k/include/asm/mcf_pgtable.h
> index 13741c1245e1..37d77e055016 100644
> --- a/arch/m68k/include/asm/mcf_pgtable.h
> +++ b/arch/m68k/include/asm/mcf_pgtable.h
> @@ -211,7 +211,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= CF_PAGE_WRITABLE;
>   	return pte;
> diff --git a/arch/m68k/include/asm/motorola_pgtable.h b/arch/m68k/include/asm/motorola_pgtable.h
> index ec0dc19ab834..c4e8eb76286d 100644
> --- a/arch/m68k/include/asm/motorola_pgtable.h
> +++ b/arch/m68k/include/asm/motorola_pgtable.h
> @@ -155,7 +155,6 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~_PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)
> @@ -168,6 +167,11 @@ static inline pte_t pte_mkcache(pte_t pte)
>   	pte_val(pte) = (pte_val(pte) & _CACHEMASK040) | m68k_supervisor_cachemode;
>   	return pte;
>   }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_RONLY;
> +	return pte;
> +}
>   
>   #define swapper_pg_dir kernel_pg_dir
>   extern pgd_t kernel_pg_dir[128];
> diff --git a/arch/m68k/include/asm/sun3_pgtable.h b/arch/m68k/include/asm/sun3_pgtable.h
> index e582b0484a55..2a06bea51a1e 100644
> --- a/arch/m68k/include/asm/sun3_pgtable.h
> +++ b/arch/m68k/include/asm/sun3_pgtable.h
> @@ -143,10 +143,14 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & SUN3_PAGE_ACCESS
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_NOCACHE; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= SUN3_PAGE_WRITEABLE;
> +	return pte;
> +}
>   // use this version when caches work...
>   //static inline pte_t pte_mkcache(pte_t pte)	{ pte_val(pte) &= SUN3_PAGE_NOCACHE; return pte; }
>   // until then, use:
> diff --git a/arch/microblaze/include/asm/pgtable.h b/arch/microblaze/include/asm/pgtable.h
> index d1b8272abcd9..5b83e82f8d7e 100644
> --- a/arch/microblaze/include/asm/pgtable.h
> +++ b/arch/microblaze/include/asm/pgtable.h
> @@ -266,7 +266,7 @@ static inline pte_t pte_mkread(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER; return pte; }
>   static inline pte_t pte_mkexec(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER | _PAGE_EXEC; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte) \
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma) \
>   	{ pte_val(pte) |= _PAGE_RW; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
> diff --git a/arch/mips/include/asm/pgtable.h b/arch/mips/include/asm/pgtable.h
> index 791389bf3c12..06efd567144a 100644
> --- a/arch/mips/include/asm/pgtable.h
> +++ b/arch/mips/include/asm/pgtable.h
> @@ -309,7 +309,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte.pte_low |= _PAGE_WRITE;
>   	if (pte.pte_low & _PAGE_MODIFIED) {
> @@ -364,7 +364,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -626,7 +626,7 @@ static inline pmd_t pmd_wrprotect(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/nios2/include/asm/pgtable.h b/arch/nios2/include/asm/pgtable.h
> index 0f5c2564e9f5..edd458518e0e 100644
> --- a/arch/nios2/include/asm/pgtable.h
> +++ b/arch/nios2/include/asm/pgtable.h
> @@ -129,7 +129,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/openrisc/include/asm/pgtable.h b/arch/openrisc/include/asm/pgtable.h
> index 3eb9b9555d0d..fd40aec189d1 100644
> --- a/arch/openrisc/include/asm/pgtable.h
> +++ b/arch/openrisc/include/asm/pgtable.h
> @@ -250,7 +250,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/parisc/include/asm/pgtable.h b/arch/parisc/include/asm/pgtable.h
> index e2950f5db7c9..89f62137e67f 100644
> --- a/arch/parisc/include/asm/pgtable.h
> +++ b/arch/parisc/include/asm/pgtable.h
> @@ -331,8 +331,12 @@ static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; retu
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~_PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= _PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkspecial(pte_t pte)	{ pte_val(pte) |= _PAGE_SPECIAL; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= _PAGE_WRITE;
> +	return pte;
> +}
>   
>   /*
>    * Huge pte definitions.
> diff --git a/arch/powerpc/include/asm/book3s/32/pgtable.h b/arch/powerpc/include/asm/book3s/32/pgtable.h
> index 7bf1fe7297c6..10d9a1d2aca9 100644
> --- a/arch/powerpc/include/asm/book3s/32/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/32/pgtable.h
> @@ -498,7 +498,7 @@ static inline pte_t pte_mkpte(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h
> index 4acc9690f599..be0636522d36 100644
> --- a/arch/powerpc/include/asm/book3s/64/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/64/pgtable.h
> @@ -600,7 +600,7 @@ static inline pte_t pte_mkexec(pte_t pte)
>   	return __pte_raw(pte_raw(pte) | cpu_to_be64(_PAGE_EXEC));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	/*
>   	 * write implies read, hence set both
> @@ -1071,7 +1071,7 @@ static inline pte_t *pmdp_ptep(pmd_t *pmd)
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   
>   #ifdef CONFIG_HAVE_ARCH_SOFT_DIRTY
>   #define pmd_soft_dirty(pmd)    pte_soft_dirty(pmd_pte(pmd))
> diff --git a/arch/powerpc/include/asm/nohash/32/pgtable.h b/arch/powerpc/include/asm/nohash/32/pgtable.h
> index fec56d965f00..7bfbcb9ba55b 100644
> --- a/arch/powerpc/include/asm/nohash/32/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/32/pgtable.h
> @@ -171,7 +171,7 @@ void unmap_kernel_page(unsigned long va);
>   	do { pte_update(mm, addr, ptep, ~0, 0, 0); } while (0)
>   
>   #ifndef pte_mkwrite
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/32/pte-8xx.h b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> index 1a89ebdc3acc..f32450eb270a 100644
> --- a/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> +++ b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> @@ -101,7 +101,7 @@ static inline int pte_write(pte_t pte)
>   
>   #define pte_write pte_write
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) & ~_PAGE_RO);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/64/pgtable.h b/arch/powerpc/include/asm/nohash/64/pgtable.h
> index 287e25864ffa..589009555877 100644
> --- a/arch/powerpc/include/asm/nohash/64/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/64/pgtable.h
> @@ -85,7 +85,7 @@
>   #ifndef __ASSEMBLY__
>   /* pte_clear moved to later in this file */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
> index d8d8de0ded99..fed1b81fbe07 100644
> --- a/arch/riscv/include/asm/pgtable.h
> +++ b/arch/riscv/include/asm/pgtable.h
> @@ -338,7 +338,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   
>   /* static inline pte_t pte_mkread(pte_t pte) */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_WRITE);
>   }
> @@ -624,9 +624,9 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pte_pmd(pte_mkyoung(pmd_pte(pmd)));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
> -	return pte_pmd(pte_mkwrite(pmd_pte(pmd)));
> +	return pte_pmd(pte_mkwrite(pmd_pte(pmd), vma));
>   }
>   
>   static inline pmd_t pmd_wrprotect(pmd_t pmd)
> diff --git a/arch/s390/include/asm/hugetlb.h b/arch/s390/include/asm/hugetlb.h
> index ccdbccfde148..558f7eef9c4d 100644
> --- a/arch/s390/include/asm/hugetlb.h
> +++ b/arch/s390/include/asm/hugetlb.h
> @@ -102,9 +102,9 @@ static inline int huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   static inline pte_t huge_pte_mkdirty(pte_t pte)
> diff --git a/arch/s390/include/asm/pgtable.h b/arch/s390/include/asm/pgtable.h
> index deeb918cae1d..8f2c743da0eb 100644
> --- a/arch/s390/include/asm/pgtable.h
> +++ b/arch/s390/include/asm/pgtable.h
> @@ -1013,7 +1013,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -1499,7 +1499,7 @@ static inline pmd_t pmd_mkwrite_kernel(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_mkwrite_kernel(pmd);
>   }
> diff --git a/arch/sh/include/asm/pgtable_32.h b/arch/sh/include/asm/pgtable_32.h
> index 21952b094650..9f2dcb9eafc8 100644
> --- a/arch/sh/include/asm/pgtable_32.h
> +++ b/arch/sh/include/asm/pgtable_32.h
> @@ -351,6 +351,12 @@ static inline void set_pte(pte_t *ptep, pte_t pte)
>   
>   #define PTE_BIT_FUNC(h,fn,op) \
>   static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
> +#define PTE_BIT_FUNC_VMA(h,fn,op) \
> +static inline pte_t pte_##fn(pte_t pte, struct vm_area_struct *vma) \
> +{ \
> +	pte.pte_##h op; \
> +	return pte; \
> +}
>   
>   #ifdef CONFIG_X2TLB
>   /*
> @@ -359,11 +365,11 @@ static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
>    * kernel permissions), we attempt to couple them a bit more sanely here.
>    */
>   PTE_BIT_FUNC(high, wrprotect, &= ~(_PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE));
> -PTE_BIT_FUNC(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
> +PTE_BIT_FUNC_VMA(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
>   PTE_BIT_FUNC(high, mkhuge, |= _PAGE_SZHUGE);
>   #else
>   PTE_BIT_FUNC(low, wrprotect, &= ~_PAGE_RW);
> -PTE_BIT_FUNC(low, mkwrite, |= _PAGE_RW);
> +PTE_BIT_FUNC_VMA(low, mkwrite, |= _PAGE_RW);
>   PTE_BIT_FUNC(low, mkhuge, |= _PAGE_SZHUGE);
>   #endif
>   
> diff --git a/arch/sparc/include/asm/pgtable_32.h b/arch/sparc/include/asm/pgtable_32.h
> index d4330e3c57a6..3e8836179456 100644
> --- a/arch/sparc/include/asm/pgtable_32.h
> +++ b/arch/sparc/include/asm/pgtable_32.h
> @@ -241,7 +241,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return __pte(pte_val(pte) & ~SRMMU_REF);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | SRMMU_WRITE);
>   }
> diff --git a/arch/sparc/include/asm/pgtable_64.h b/arch/sparc/include/asm/pgtable_64.h
> index 2dc8d4641734..c5cd5c03f557 100644
> --- a/arch/sparc/include/asm/pgtable_64.h
> +++ b/arch/sparc/include/asm/pgtable_64.h
> @@ -466,7 +466,7 @@ static inline pte_t pte_mkclean(pte_t pte)
>   	return __pte(val);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	unsigned long val = pte_val(pte), mask;
>   
> @@ -756,11 +756,11 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return __pmd(pte_val(pte));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pte_t pte = __pte(pmd_val(pmd));
>   
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, vma);
>   
>   	return __pmd(pte_val(pte));
>   }
> diff --git a/arch/um/include/asm/pgtable.h b/arch/um/include/asm/pgtable.h
> index a70d1618eb35..963479c133b7 100644
> --- a/arch/um/include/asm/pgtable.h
> +++ b/arch/um/include/asm/pgtable.h
> @@ -207,7 +207,7 @@ static inline pte_t pte_mkyoung(pte_t pte)
>   	return(pte);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (unlikely(pte_get_bits(pte,  _PAGE_RW)))
>   		return pte;
> diff --git a/arch/x86/include/asm/pgtable.h b/arch/x86/include/asm/pgtable.h
> index 3607f2572f9e..66c514808276 100644
> --- a/arch/x86/include/asm/pgtable.h
> +++ b/arch/x86/include/asm/pgtable.h
> @@ -369,7 +369,9 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte_set_flags(pte, _PAGE_RW);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +struct vm_area_struct;
> +
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -470,7 +472,7 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pmd_set_flags(pmd, _PAGE_ACCESSED);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_set_flags(pmd, _PAGE_RW);
>   }
> diff --git a/arch/xtensa/include/asm/pgtable.h b/arch/xtensa/include/asm/pgtable.h
> index fc7a14884c6c..d72632d9c53c 100644
> --- a/arch/xtensa/include/asm/pgtable.h
> +++ b/arch/xtensa/include/asm/pgtable.h
> @@ -262,7 +262,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   	{ pte_val(pte) |= _PAGE_WRITABLE; return pte; }
>   
>   #define pgprot_noncached(prot) \
> diff --git a/include/asm-generic/hugetlb.h b/include/asm-generic/hugetlb.h
> index d7f6335d3999..e86c830728de 100644
> --- a/include/asm-generic/hugetlb.h
> +++ b/include/asm-generic/hugetlb.h
> @@ -20,9 +20,9 @@ static inline unsigned long huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   #ifndef __HAVE_ARCH_HUGE_PTE_WRPROTECT
> diff --git a/include/linux/mm.h b/include/linux/mm.h
> index 1f79667824eb..af652444fbba 100644
> --- a/include/linux/mm.h
> +++ b/include/linux/mm.h
> @@ -1163,7 +1163,7 @@ void free_compound_page(struct page *page);
>   static inline pte_t maybe_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	return pte;
>   }
>   
> diff --git a/mm/debug_vm_pgtable.c b/mm/debug_vm_pgtable.c
> index af59cc7bd307..7bc5592900bc 100644
> --- a/mm/debug_vm_pgtable.c
> +++ b/mm/debug_vm_pgtable.c
> @@ -109,10 +109,10 @@ static void __init pte_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pte_same(pte, pte));
>   	WARN_ON(!pte_young(pte_mkyoung(pte_mkold(pte))));
>   	WARN_ON(!pte_dirty(pte_mkdirty(pte_mkclean(pte))));
> -	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte))));
> +	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte), args->vma)));
>   	WARN_ON(pte_young(pte_mkold(pte_mkyoung(pte))));
>   	WARN_ON(pte_dirty(pte_mkclean(pte_mkdirty(pte))));
> -	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte))));
> +	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte, args->vma))));
>   	WARN_ON(pte_dirty(pte_wrprotect(pte_mkclean(pte))));
>   	WARN_ON(!pte_dirty(pte_wrprotect(pte_mkdirty(pte))));
>   }
> @@ -153,7 +153,7 @@ static void __init pte_advanced_tests(struct pgtable_debug_args *args)
>   	pte = pte_mkclean(pte);
>   	set_pte_at(args->mm, args->vaddr, args->ptep, pte);
>   	flush_dcache_page(page);
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, args->vma);
>   	pte = pte_mkdirty(pte);
>   	ptep_set_access_flags(args->vma, args->vaddr, args->ptep, pte, 1);
>   	pte = ptep_get(args->ptep);
> @@ -199,10 +199,10 @@ static void __init pmd_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pmd_same(pmd, pmd));
>   	WARN_ON(!pmd_young(pmd_mkyoung(pmd_mkold(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_mkdirty(pmd_mkclean(pmd))));
> -	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd))));
> +	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd), args->vma)));
>   	WARN_ON(pmd_young(pmd_mkold(pmd_mkyoung(pmd))));
>   	WARN_ON(pmd_dirty(pmd_mkclean(pmd_mkdirty(pmd))));
> -	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd))));
> +	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd, args->vma))));
>   	WARN_ON(pmd_dirty(pmd_wrprotect(pmd_mkclean(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_wrprotect(pmd_mkdirty(pmd))));
>   	/*
> @@ -253,7 +253,7 @@ static void __init pmd_advanced_tests(struct pgtable_debug_args *args)
>   	pmd = pmd_mkclean(pmd);
>   	set_pmd_at(args->mm, vaddr, args->pmdp, pmd);
>   	flush_dcache_page(page);
> -	pmd = pmd_mkwrite(pmd);
> +	pmd = pmd_mkwrite(pmd, args->vma);
>   	pmd = pmd_mkdirty(pmd);
>   	pmdp_set_access_flags(args->vma, vaddr, args->pmdp, pmd, 1);
>   	pmd = READ_ONCE(*args->pmdp);
> @@ -928,8 +928,8 @@ static void __init hugetlb_basic_tests(struct pgtable_debug_args *args)
>   	pte = mk_huge_pte(page, args->page_prot);
>   
>   	WARN_ON(!huge_pte_dirty(huge_pte_mkdirty(pte)));
> -	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte))));
> -	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte))));
> +	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte), args->vma)));
> +	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte, args->vma))));
>   
>   #ifdef CONFIG_ARCH_WANT_GENERAL_HUGETLB
>   	pte = pfn_pte(args->fixed_pmd_pfn, args->page_prot);
> diff --git a/mm/huge_memory.c b/mm/huge_memory.c
> index 4fc43859e59a..aaf815838144 100644
> --- a/mm/huge_memory.c
> +++ b/mm/huge_memory.c
> @@ -555,7 +555,7 @@ __setup("transparent_hugepage=", setup_transparent_hugepage);
>   pmd_t maybe_pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	return pmd;
>   }
>   
> @@ -1580,7 +1580,7 @@ vm_fault_t do_huge_pmd_numa_page(struct vm_fault *vmf)
>   	pmd = pmd_modify(oldpmd, vma->vm_page_prot);
>   	pmd = pmd_mkyoung(pmd);
>   	if (writable)
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	set_pmd_at(vma->vm_mm, haddr, vmf->pmd, pmd);
>   	update_mmu_cache_pmd(vma, vmf->address, vmf->pmd);
>   	spin_unlock(vmf->ptl);
> @@ -1926,7 +1926,7 @@ int change_huge_pmd(struct mmu_gather *tlb, struct vm_area_struct *vma,
>   	/* See change_pte_range(). */
>   	if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) && !pmd_write(entry) &&
>   	    can_change_pmd_writable(vma, addr, entry))
> -		entry = pmd_mkwrite(entry);
> +		entry = pmd_mkwrite(entry, vma);
>   
>   	ret = HPAGE_PMD_NR;
>   	set_pmd_at(mm, addr, pmd, entry);
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 07abcb6eb203..6af471bdcff8 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -4900,7 +4900,7 @@ static pte_t make_huge_pte(struct vm_area_struct *vma, struct page *page,
>   
>   	if (writable) {
>   		entry = huge_pte_mkwrite(huge_pte_mkdirty(mk_huge_pte(page,
> -					 vma->vm_page_prot)));
> +					 vma->vm_page_prot)), vma);
>   	} else {
>   		entry = huge_pte_wrprotect(mk_huge_pte(page,
>   					   vma->vm_page_prot));
> @@ -4916,7 +4916,7 @@ static void set_huge_ptep_writable(struct vm_area_struct *vma,
>   {
>   	pte_t entry;
>   
> -	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)));
> +	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)), vma);
>   	if (huge_ptep_set_access_flags(vma, address, ptep, entry, 1))
>   		update_mmu_cache(vma, address, ptep);
>   }
> diff --git a/mm/memory.c b/mm/memory.c
> index f456f3b5049c..d0972d2d6f36 100644
> --- a/mm/memory.c
> +++ b/mm/memory.c
> @@ -4067,7 +4067,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
>   	entry = mk_pte(&folio->page, vma->vm_page_prot);
>   	entry = pte_sw_mkyoung(entry);
>   	if (vma->vm_flags & VM_WRITE)
> -		entry = pte_mkwrite(pte_mkdirty(entry));
> +		entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   
>   	vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, vmf->address,
>   			&vmf->ptl);
> @@ -4755,7 +4755,7 @@ static vm_fault_t do_numa_page(struct vm_fault *vmf)
>   	pte = pte_modify(old_pte, vma->vm_page_prot);
>   	pte = pte_mkyoung(pte);
>   	if (writable)
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	ptep_modify_prot_commit(vma, vmf->address, vmf->pte, old_pte, pte);
>   	update_mmu_cache(vma, vmf->address, vmf->pte);
>   	pte_unmap_unlock(vmf->pte, vmf->ptl);
> diff --git a/mm/migrate_device.c b/mm/migrate_device.c
> index d30c9de60b0d..df3f5e9d5f76 100644
> --- a/mm/migrate_device.c
> +++ b/mm/migrate_device.c
> @@ -646,7 +646,7 @@ static void migrate_vma_insert_page(struct migrate_vma *migrate,
>   		}
>   		entry = mk_pte(page, vma->vm_page_prot);
>   		if (vma->vm_flags & VM_WRITE)
> -			entry = pte_mkwrite(pte_mkdirty(entry));
> +			entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   	}
>   
>   	ptep = pte_offset_map_lock(mm, pmdp, addr, &ptl);
> diff --git a/mm/mprotect.c b/mm/mprotect.c
> index 1d4843c97c2a..381163a41e88 100644
> --- a/mm/mprotect.c
> +++ b/mm/mprotect.c
> @@ -198,7 +198,7 @@ static long change_pte_range(struct mmu_gather *tlb,
>   			if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) &&
>   			    !pte_write(ptent) &&
>   			    can_change_pte_writable(vma, addr, ptent))
> -				ptent = pte_mkwrite(ptent);
> +				ptent = pte_mkwrite(ptent, vma);
>   
>   			ptep_modify_prot_commit(vma, addr, pte, oldpte, ptent);
>   			if (pte_needs_flush(oldpte, ptent))
> diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
> index 53c3d916ff66..3db6f87c0aca 100644
> --- a/mm/userfaultfd.c
> +++ b/mm/userfaultfd.c
> @@ -75,7 +75,7 @@ int mfill_atomic_install_pte(struct mm_struct *dst_mm, pmd_t *dst_pmd,
>   	if (page_in_cache && !vm_shared)
>   		writable = false;
>   	if (writable)
> -		_dst_pte = pte_mkwrite(_dst_pte);
> +		_dst_pte = pte_mkwrite(_dst_pte, dst_vma);
>   	if (wp_copy)
>   		_dst_pte = pte_mkuffd_wp(_dst_pte);
>   

WARNING: multiple messages have this Message-ID (diff)
From: Christophe Leroy <christophe.leroy@csgroup.eu>
To: Rick Edgecombe <rick.p.edgecombe@intel.com>,
	"x86@kernel.org" <x86@kernel.org>,
	"H . Peter Anvin" <hpa@zytor.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Ingo Molnar <mingo@redhat.com>,
	"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"linux-doc@vger.kernel.org" <linux-doc@vger.kernel.org>,
	"linux-mm@kvack.org" <linux-mm@kvack.org>,
	"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
	"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
	Arnd Bergmann <arnd@arndb.de>, Andy Lutomirski <luto@kernel.org>,
	Balbir Singh <bsingharora@gmail.com>,
	Borislav Petkov <bp@alien8.de>,
	Cyrill Gorcunov <gorcunov@gmail.com>,
	Dave Hansen <dave.hansen@linux.intel.com>,
	Eugene Syromiatnikov <esyr@redhat.com>,
	Florian Weimer <fweimer@redhat.com>,
	"H . J . Lu" <hjl.tools@gmail.com>, Jann Horn <jannh@google.com>,
	Jonathan Corbet <corbet@lwn.net>,
	Kees Cook <keescook@chromium.org>,
	Mike Kravetz <mike.kravetz@oracle.com>,
	Nadav Amit <nadav.amit@gmail.com>,
	Oleg Nesterov <oleg@redhat.com>, Pavel Machek <pavel@ucw.cz>,
	Peter Zijlstra <peterz@infradead.org>,
	Randy Dunlap <rdunlap@infradead.org>,
	Weijiang Yang <weijiang.yang@intel.com>,
	"Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>,
	John Allen <john.allen@amd.com>,
	"kcc@google.com" <kcc@google.com>,
	"eranian@google.com" <eranian@google.com>,
	"rppt@kernel.org" <rppt@kernel.org>,
	"jamorris@linux.microsoft.com" <jamorris@linux.microsoft.com>,
	"dethoma@microsoft.com" <dethoma@microsoft.com>,
	"akpm@linux-foundation.org" <akpm@linux-foundation.org>,
	"Andrew.Cooper3@citrix.com" <Andrew.Cooper3@citrix.com>,
	"christina.schimpe@intel.com" <christina.schimpe@intel.com>,
	"david@redhat.com" <david@redhat.com>,
	"debug@rivosinc.com" <debug@rivosinc.com>
Cc: "linux-alpha@vger.kernel.org" <linux-alpha@vger.kernel.org>,
	"linux-snps-arc@lists.infradead.org"
	<linux-snps-arc@lists.infradead.org>,
	"linux-arm-kernel@lists.infradead.org"
	<linux-arm-kernel@lists.infradead.org>,
	"linux-csky@vger.kernel.org" <linux-csky@vger.kernel.org>,
	"linux-hexagon@vger.kernel.org" <linux-hexagon@vger.kernel.org>,
	"linux-ia64@vger.kernel.org" <linux-ia64@vger.kernel.org>,
	"loongarch@lists.linux.dev" <loongarch@lists.linux.dev>,
	"linux-m68k@lists.linux-m68k.org"
	<linux-m68k@lists.linux-m68k.org>,
	Michal Simek <monstr@monstr.eu>,
	Dinh Nguyen <dinguyen@kernel.org>,
	"linux-mips@vger.kernel.org" <linux-mips@vger.kernel.org>,
	"linux-openrisc@vger.kernel.org" <linux-openrisc@vger.kernel.org>,
	"linux-parisc@vger.kernel.org" <linux-parisc@vger.kernel.org>,
	"linuxppc-dev@lists.ozlabs.org" <linuxppc-dev@lists.ozlabs.org>,
	"linux-riscv@lists.infradead.org"
	<linux-riscv@lists.infradead.org>,
	"linux-s390@vger.kernel.org" <linux-s390@vger.kernel.org>,
	"linux-sh@vger.kernel.org" <linux-sh@vger.kernel.org>,
	"sparclinux@vger.kernel.org" <sparclinux@vger.kernel.org>,
	"linux-um@lists.infradead.org" <linux-um@lists.infradead.org>,
	"xen-devel@lists.xenproject.org" <xen-devel@lists.xenproject.org>
Subject: Re: [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA
Date: Wed, 1 Mar 2023 07:03:23 +0000	[thread overview]
Message-ID: <1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu> (raw)
In-Reply-To: <20230227222957.24501-14-rick.p.edgecombe@intel.com>



Le 27/02/2023 à 23:29, Rick Edgecombe a écrit :
> The x86 Control-flow Enforcement Technology (CET) feature includes a new
> type of memory called shadow stack. This shadow stack memory has some
> unusual properties, which requires some core mm changes to function
> properly.
> 
> One of these unusual properties is that shadow stack memory is writable,
> but only in limited ways. These limits are applied via a specific PTE
> bit combination. Nevertheless, the memory is writable, and core mm code
> will need to apply the writable permissions in the typical paths that
> call pte_mkwrite().
> 
> In addition to VM_WRITE, the shadow stack VMA's will have a flag denoting
> that they are special shadow stack flavor of writable memory. So make
> pte_mkwrite() take a VMA, so that the x86 implementation of it can know to
> create regular writable memory or shadow stack memory.
> 
> Apply the same changes for pmd_mkwrite() and huge_pte_mkwrite().

I'm not sure it is a good idea to add a second argument to 
pte_mkwrite(). All pte_mkxxxx() only take a pte and nothing else.

I think you should do the same as commit d9ed9faac283 ("mm: add new 
arch_make_huge_pte() method for tile support")

Christophe

> 
> No functional change.
> 
> Cc: linux-doc@vger.kernel.org
> Cc: linux-kernel@vger.kernel.org
> Cc: linux-alpha@vger.kernel.org
> Cc: linux-snps-arc@lists.infradead.org
> Cc: linux-arm-kernel@lists.infradead.org
> Cc: linux-csky@vger.kernel.org
> Cc: linux-hexagon@vger.kernel.org
> Cc: linux-ia64@vger.kernel.org
> Cc: loongarch@lists.linux.dev
> Cc: linux-m68k@lists.linux-m68k.org
> Cc: Michal Simek <monstr@monstr.eu>
> Cc: Dinh Nguyen <dinguyen@kernel.org>
> Cc: linux-mips@vger.kernel.org
> Cc: linux-openrisc@vger.kernel.org
> Cc: linux-parisc@vger.kernel.org
> Cc: linuxppc-dev@lists.ozlabs.org
> Cc: linux-riscv@lists.infradead.org
> Cc: linux-s390@vger.kernel.org
> Cc: linux-sh@vger.kernel.org
> Cc: sparclinux@vger.kernel.org
> Cc: linux-um@lists.infradead.org
> Cc: xen-devel@lists.xenproject.org
> Cc: linux-arch@vger.kernel.org
> Cc: linux-mm@kvack.org
> Tested-by: Pengfei Xu <pengfei.xu@intel.com>
> Tested-by: John Allen <john.allen@amd.com>
> Tested-by: Kees Cook <keescook@chromium.org>
> Acked-by: Mike Rapoport (IBM) <rppt@kernel.org>
> Acked-by: Michael Ellerman <mpe@ellerman.id.au>
> Acked-by: David Hildenbrand <david@redhat.com>
> Reviewed-by: Kees Cook <keescook@chromium.org>
> Suggested-by: David Hildenbrand <david@redhat.com>
> Signed-off-by: Rick Edgecombe <rick.p.edgecombe@intel.com>
> 
> ---
> Hi Non-x86 Arch’s,
> 
> x86 has a feature that allows for the creation of a special type of
> writable memory (shadow stack) that is only writable in limited specific
> ways. Previously, changes were proposed to core MM code to teach it to
> decide when to create normally writable memory or the special shadow stack
> writable memory, but David Hildenbrand suggested[0] to change
> pXX_mkwrite() to take a VMA, so awareness of shadow stack memory can be
> moved into x86 code.
> 
> Since pXX_mkwrite() is defined in every arch, it requires some tree-wide
> changes. So that is why you are seeing some patches out of a big x86
> series pop up in your arch mailing list. There is no functional change.
> After this refactor, the shadow stack series goes on to use the arch
> helpers to push shadow stack memory details inside arch/x86.
> 
> Testing was just 0-day build testing.
> 
> Hopefully that is enough context. Thanks!
> 
> [0] https://lore.kernel.org/lkml/0e29a2d0-08d8-bcd6-ff26-4bea0e4037b0@redhat.com/#t
> 
> v6:
>   - New patch
> ---
>   Documentation/mm/arch_pgtable_helpers.rst    |  9 ++++++---
>   arch/alpha/include/asm/pgtable.h             |  6 +++++-
>   arch/arc/include/asm/hugepage.h              |  2 +-
>   arch/arc/include/asm/pgtable-bits-arcv2.h    |  7 ++++++-
>   arch/arm/include/asm/pgtable-3level.h        |  7 ++++++-
>   arch/arm/include/asm/pgtable.h               |  2 +-
>   arch/arm64/include/asm/pgtable.h             |  4 ++--
>   arch/csky/include/asm/pgtable.h              |  2 +-
>   arch/hexagon/include/asm/pgtable.h           |  2 +-
>   arch/ia64/include/asm/pgtable.h              |  2 +-
>   arch/loongarch/include/asm/pgtable.h         |  4 ++--
>   arch/m68k/include/asm/mcf_pgtable.h          |  2 +-
>   arch/m68k/include/asm/motorola_pgtable.h     |  6 +++++-
>   arch/m68k/include/asm/sun3_pgtable.h         |  6 +++++-
>   arch/microblaze/include/asm/pgtable.h        |  2 +-
>   arch/mips/include/asm/pgtable.h              |  6 +++---
>   arch/nios2/include/asm/pgtable.h             |  2 +-
>   arch/openrisc/include/asm/pgtable.h          |  2 +-
>   arch/parisc/include/asm/pgtable.h            |  6 +++++-
>   arch/powerpc/include/asm/book3s/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/book3s/64/pgtable.h |  4 ++--
>   arch/powerpc/include/asm/nohash/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/nohash/32/pte-8xx.h |  2 +-
>   arch/powerpc/include/asm/nohash/64/pgtable.h |  2 +-
>   arch/riscv/include/asm/pgtable.h             |  6 +++---
>   arch/s390/include/asm/hugetlb.h              |  4 ++--
>   arch/s390/include/asm/pgtable.h              |  4 ++--
>   arch/sh/include/asm/pgtable_32.h             | 10 ++++++++--
>   arch/sparc/include/asm/pgtable_32.h          |  2 +-
>   arch/sparc/include/asm/pgtable_64.h          |  6 +++---
>   arch/um/include/asm/pgtable.h                |  2 +-
>   arch/x86/include/asm/pgtable.h               |  6 ++++--
>   arch/xtensa/include/asm/pgtable.h            |  2 +-
>   include/asm-generic/hugetlb.h                |  4 ++--
>   include/linux/mm.h                           |  2 +-
>   mm/debug_vm_pgtable.c                        | 16 ++++++++--------
>   mm/huge_memory.c                             |  6 +++---
>   mm/hugetlb.c                                 |  4 ++--
>   mm/memory.c                                  |  4 ++--
>   mm/migrate_device.c                          |  2 +-
>   mm/mprotect.c                                |  2 +-
>   mm/userfaultfd.c                             |  2 +-
>   42 files changed, 106 insertions(+), 69 deletions(-)
> 
> diff --git a/Documentation/mm/arch_pgtable_helpers.rst b/Documentation/mm/arch_pgtable_helpers.rst
> index 30d9a09f01f4..78ac3ff2fe1d 100644
> --- a/Documentation/mm/arch_pgtable_helpers.rst
> +++ b/Documentation/mm/arch_pgtable_helpers.rst
> @@ -46,7 +46,8 @@ PTE Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pte_mkclean               | Creates a clean PTE                              |
>   +---------------------------+--------------------------------------------------+
> -| pte_mkwrite               | Creates a writable PTE                           |
> +| pte_mkwrite               | Creates a writable PTE of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pte_wrprotect             | Creates a write protected PTE                    |
>   +---------------------------+--------------------------------------------------+
> @@ -118,7 +119,8 @@ PMD Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pmd_mkclean               | Creates a clean PMD                              |
>   +---------------------------+--------------------------------------------------+
> -| pmd_mkwrite               | Creates a writable PMD                           |
> +| pmd_mkwrite               | Creates a writable PMD of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pmd_wrprotect             | Creates a write protected PMD                    |
>   +---------------------------+--------------------------------------------------+
> @@ -222,7 +224,8 @@ HugeTLB Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_mkdirty          | Creates a dirty HugeTLB                          |
>   +---------------------------+--------------------------------------------------+
> -| huge_pte_mkwrite          | Creates a writable HugeTLB                       |
> +| huge_pte_mkwrite          | Creates a writable HugeTLB of the type specified |
> +|                           | by the VMA.                                      |
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_wrprotect        | Creates a write protected HugeTLB                |
>   +---------------------------+--------------------------------------------------+
> diff --git a/arch/alpha/include/asm/pgtable.h b/arch/alpha/include/asm/pgtable.h
> index ba43cb841d19..fb5d207c2a89 100644
> --- a/arch/alpha/include/asm/pgtable.h
> +++ b/arch/alpha/include/asm/pgtable.h
> @@ -256,9 +256,13 @@ extern inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   extern inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~(__DIRTY_BITS); return pte; }
>   extern inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~(__ACCESS_BITS); return pte; }
> -extern inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= __DIRTY_BITS; return pte; }
>   extern inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= __ACCESS_BITS; return pte; }
> +extern inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_FOW;
> +	return pte;
> +}
>   
>   /*
>    * The smp_rmb() in the following functions are required to order the load of
> diff --git a/arch/arc/include/asm/hugepage.h b/arch/arc/include/asm/hugepage.h
> index 5001b796fb8d..223a96967188 100644
> --- a/arch/arc/include/asm/hugepage.h
> +++ b/arch/arc/include/asm/hugepage.h
> @@ -21,7 +21,7 @@ static inline pmd_t pte_pmd(pte_t pte)
>   }
>   
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/arc/include/asm/pgtable-bits-arcv2.h b/arch/arc/include/asm/pgtable-bits-arcv2.h
> index 6e9f8ca6d6a1..a5b8bc955015 100644
> --- a/arch/arc/include/asm/pgtable-bits-arcv2.h
> +++ b/arch/arc/include/asm/pgtable-bits-arcv2.h
> @@ -87,7 +87,6 @@
>   
>   PTE_BIT_FUNC(mknotpresent,     &= ~(_PAGE_PRESENT));
>   PTE_BIT_FUNC(wrprotect,	&= ~(_PAGE_WRITE));
> -PTE_BIT_FUNC(mkwrite,	|= (_PAGE_WRITE));
>   PTE_BIT_FUNC(mkclean,	&= ~(_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkdirty,	|= (_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkold,	&= ~(_PAGE_ACCESSED));
> @@ -95,6 +94,12 @@ PTE_BIT_FUNC(mkyoung,	|= (_PAGE_ACCESSED));
>   PTE_BIT_FUNC(mkspecial,	|= (_PAGE_SPECIAL));
>   PTE_BIT_FUNC(mkhuge,	|= (_PAGE_HW_SZ));
>   
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= (_PAGE_WRITE);
> +	return pte;
> +}
> +
>   static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
>   {
>   	return __pte((pte_val(pte) & _PAGE_CHG_MASK) | pgprot_val(newprot));
> diff --git a/arch/arm/include/asm/pgtable-3level.h b/arch/arm/include/asm/pgtable-3level.h
> index 106049791500..df071a807610 100644
> --- a/arch/arm/include/asm/pgtable-3level.h
> +++ b/arch/arm/include/asm/pgtable-3level.h
> @@ -202,11 +202,16 @@ static inline pmd_t pmd_##fn(pmd_t pmd) { pmd_val(pmd) op; return pmd; }
>   
>   PMD_BIT_FUNC(wrprotect,	|= L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkold,	&= ~PMD_SECT_AF);
> -PMD_BIT_FUNC(mkwrite,   &= ~L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkdirty,   |= L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkclean,   &= ~L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkyoung,   |= PMD_SECT_AF);
>   
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
> +{
> +	pmd_val(pmd) |= L_PMD_SECT_RDONLY;
> +	return pmd;
> +}
> +
>   #define pmd_mkhuge(pmd)		(__pmd(pmd_val(pmd) & ~PMD_TABLE_BIT))
>   
>   #define pmd_pfn(pmd)		(((pmd_val(pmd) & PMD_MASK) & PHYS_MASK) >> PAGE_SHIFT)
> diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
> index a58ccbb406ad..39ad1ae1308d 100644
> --- a/arch/arm/include/asm/pgtable.h
> +++ b/arch/arm/include/asm/pgtable.h
> @@ -227,7 +227,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   	return set_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return clear_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
> diff --git a/arch/arm64/include/asm/pgtable.h b/arch/arm64/include/asm/pgtable.h
> index cccf8885792e..913bf370f74a 100644
> --- a/arch/arm64/include/asm/pgtable.h
> +++ b/arch/arm64/include/asm/pgtable.h
> @@ -187,7 +187,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -492,7 +492,7 @@ static inline int pmd_trans_huge(pmd_t pmd)
>   #define pmd_cont(pmd)		pte_cont(pmd_pte(pmd))
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/csky/include/asm/pgtable.h b/arch/csky/include/asm/pgtable.h
> index d4042495febc..c2f92c991e37 100644
> --- a/arch/csky/include/asm/pgtable.h
> +++ b/arch/csky/include/asm/pgtable.h
> @@ -176,7 +176,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> diff --git a/arch/hexagon/include/asm/pgtable.h b/arch/hexagon/include/asm/pgtable.h
> index 59393613d086..14ab9c789c0e 100644
> --- a/arch/hexagon/include/asm/pgtable.h
> +++ b/arch/hexagon/include/asm/pgtable.h
> @@ -300,7 +300,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   }
>   
>   /* pte_mkwrite - mark page as writable */
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/ia64/include/asm/pgtable.h b/arch/ia64/include/asm/pgtable.h
> index 21c97e31a28a..f879dd626da6 100644
> --- a/arch/ia64/include/asm/pgtable.h
> +++ b/arch/ia64/include/asm/pgtable.h
> @@ -268,7 +268,7 @@ ia64_phys_addr_valid (unsigned long addr)
>    * access rights:
>    */
>   #define pte_wrprotect(pte)	(__pte(pte_val(pte) & ~_PAGE_AR_RW))
> -#define pte_mkwrite(pte)	(__pte(pte_val(pte) | _PAGE_AR_RW))
> +#define pte_mkwrite(pte, vma)	(__pte(pte_val(pte) | _PAGE_AR_RW))
>   #define pte_mkold(pte)		(__pte(pte_val(pte) & ~_PAGE_A))
>   #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_A))
>   #define pte_mkclean(pte)	(__pte(pte_val(pte) & ~_PAGE_D))
> diff --git a/arch/loongarch/include/asm/pgtable.h b/arch/loongarch/include/asm/pgtable.h
> index d28fb9dbec59..ebf645f40298 100644
> --- a/arch/loongarch/include/asm/pgtable.h
> +++ b/arch/loongarch/include/asm/pgtable.h
> @@ -390,7 +390,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -490,7 +490,7 @@ static inline int pmd_write(pmd_t pmd)
>   	return !!(pmd_val(pmd) & _PAGE_WRITE);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/m68k/include/asm/mcf_pgtable.h b/arch/m68k/include/asm/mcf_pgtable.h
> index 13741c1245e1..37d77e055016 100644
> --- a/arch/m68k/include/asm/mcf_pgtable.h
> +++ b/arch/m68k/include/asm/mcf_pgtable.h
> @@ -211,7 +211,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= CF_PAGE_WRITABLE;
>   	return pte;
> diff --git a/arch/m68k/include/asm/motorola_pgtable.h b/arch/m68k/include/asm/motorola_pgtable.h
> index ec0dc19ab834..c4e8eb76286d 100644
> --- a/arch/m68k/include/asm/motorola_pgtable.h
> +++ b/arch/m68k/include/asm/motorola_pgtable.h
> @@ -155,7 +155,6 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~_PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)
> @@ -168,6 +167,11 @@ static inline pte_t pte_mkcache(pte_t pte)
>   	pte_val(pte) = (pte_val(pte) & _CACHEMASK040) | m68k_supervisor_cachemode;
>   	return pte;
>   }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_RONLY;
> +	return pte;
> +}
>   
>   #define swapper_pg_dir kernel_pg_dir
>   extern pgd_t kernel_pg_dir[128];
> diff --git a/arch/m68k/include/asm/sun3_pgtable.h b/arch/m68k/include/asm/sun3_pgtable.h
> index e582b0484a55..2a06bea51a1e 100644
> --- a/arch/m68k/include/asm/sun3_pgtable.h
> +++ b/arch/m68k/include/asm/sun3_pgtable.h
> @@ -143,10 +143,14 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & SUN3_PAGE_ACCESS
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_NOCACHE; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= SUN3_PAGE_WRITEABLE;
> +	return pte;
> +}
>   // use this version when caches work...
>   //static inline pte_t pte_mkcache(pte_t pte)	{ pte_val(pte) &= SUN3_PAGE_NOCACHE; return pte; }
>   // until then, use:
> diff --git a/arch/microblaze/include/asm/pgtable.h b/arch/microblaze/include/asm/pgtable.h
> index d1b8272abcd9..5b83e82f8d7e 100644
> --- a/arch/microblaze/include/asm/pgtable.h
> +++ b/arch/microblaze/include/asm/pgtable.h
> @@ -266,7 +266,7 @@ static inline pte_t pte_mkread(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER; return pte; }
>   static inline pte_t pte_mkexec(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER | _PAGE_EXEC; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte) \
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma) \
>   	{ pte_val(pte) |= _PAGE_RW; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
> diff --git a/arch/mips/include/asm/pgtable.h b/arch/mips/include/asm/pgtable.h
> index 791389bf3c12..06efd567144a 100644
> --- a/arch/mips/include/asm/pgtable.h
> +++ b/arch/mips/include/asm/pgtable.h
> @@ -309,7 +309,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte.pte_low |= _PAGE_WRITE;
>   	if (pte.pte_low & _PAGE_MODIFIED) {
> @@ -364,7 +364,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -626,7 +626,7 @@ static inline pmd_t pmd_wrprotect(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/nios2/include/asm/pgtable.h b/arch/nios2/include/asm/pgtable.h
> index 0f5c2564e9f5..edd458518e0e 100644
> --- a/arch/nios2/include/asm/pgtable.h
> +++ b/arch/nios2/include/asm/pgtable.h
> @@ -129,7 +129,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/openrisc/include/asm/pgtable.h b/arch/openrisc/include/asm/pgtable.h
> index 3eb9b9555d0d..fd40aec189d1 100644
> --- a/arch/openrisc/include/asm/pgtable.h
> +++ b/arch/openrisc/include/asm/pgtable.h
> @@ -250,7 +250,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/parisc/include/asm/pgtable.h b/arch/parisc/include/asm/pgtable.h
> index e2950f5db7c9..89f62137e67f 100644
> --- a/arch/parisc/include/asm/pgtable.h
> +++ b/arch/parisc/include/asm/pgtable.h
> @@ -331,8 +331,12 @@ static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; retu
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~_PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= _PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkspecial(pte_t pte)	{ pte_val(pte) |= _PAGE_SPECIAL; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= _PAGE_WRITE;
> +	return pte;
> +}
>   
>   /*
>    * Huge pte definitions.
> diff --git a/arch/powerpc/include/asm/book3s/32/pgtable.h b/arch/powerpc/include/asm/book3s/32/pgtable.h
> index 7bf1fe7297c6..10d9a1d2aca9 100644
> --- a/arch/powerpc/include/asm/book3s/32/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/32/pgtable.h
> @@ -498,7 +498,7 @@ static inline pte_t pte_mkpte(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h
> index 4acc9690f599..be0636522d36 100644
> --- a/arch/powerpc/include/asm/book3s/64/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/64/pgtable.h
> @@ -600,7 +600,7 @@ static inline pte_t pte_mkexec(pte_t pte)
>   	return __pte_raw(pte_raw(pte) | cpu_to_be64(_PAGE_EXEC));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	/*
>   	 * write implies read, hence set both
> @@ -1071,7 +1071,7 @@ static inline pte_t *pmdp_ptep(pmd_t *pmd)
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   
>   #ifdef CONFIG_HAVE_ARCH_SOFT_DIRTY
>   #define pmd_soft_dirty(pmd)    pte_soft_dirty(pmd_pte(pmd))
> diff --git a/arch/powerpc/include/asm/nohash/32/pgtable.h b/arch/powerpc/include/asm/nohash/32/pgtable.h
> index fec56d965f00..7bfbcb9ba55b 100644
> --- a/arch/powerpc/include/asm/nohash/32/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/32/pgtable.h
> @@ -171,7 +171,7 @@ void unmap_kernel_page(unsigned long va);
>   	do { pte_update(mm, addr, ptep, ~0, 0, 0); } while (0)
>   
>   #ifndef pte_mkwrite
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/32/pte-8xx.h b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> index 1a89ebdc3acc..f32450eb270a 100644
> --- a/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> +++ b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> @@ -101,7 +101,7 @@ static inline int pte_write(pte_t pte)
>   
>   #define pte_write pte_write
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) & ~_PAGE_RO);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/64/pgtable.h b/arch/powerpc/include/asm/nohash/64/pgtable.h
> index 287e25864ffa..589009555877 100644
> --- a/arch/powerpc/include/asm/nohash/64/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/64/pgtable.h
> @@ -85,7 +85,7 @@
>   #ifndef __ASSEMBLY__
>   /* pte_clear moved to later in this file */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
> index d8d8de0ded99..fed1b81fbe07 100644
> --- a/arch/riscv/include/asm/pgtable.h
> +++ b/arch/riscv/include/asm/pgtable.h
> @@ -338,7 +338,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   
>   /* static inline pte_t pte_mkread(pte_t pte) */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_WRITE);
>   }
> @@ -624,9 +624,9 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pte_pmd(pte_mkyoung(pmd_pte(pmd)));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
> -	return pte_pmd(pte_mkwrite(pmd_pte(pmd)));
> +	return pte_pmd(pte_mkwrite(pmd_pte(pmd), vma));
>   }
>   
>   static inline pmd_t pmd_wrprotect(pmd_t pmd)
> diff --git a/arch/s390/include/asm/hugetlb.h b/arch/s390/include/asm/hugetlb.h
> index ccdbccfde148..558f7eef9c4d 100644
> --- a/arch/s390/include/asm/hugetlb.h
> +++ b/arch/s390/include/asm/hugetlb.h
> @@ -102,9 +102,9 @@ static inline int huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   static inline pte_t huge_pte_mkdirty(pte_t pte)
> diff --git a/arch/s390/include/asm/pgtable.h b/arch/s390/include/asm/pgtable.h
> index deeb918cae1d..8f2c743da0eb 100644
> --- a/arch/s390/include/asm/pgtable.h
> +++ b/arch/s390/include/asm/pgtable.h
> @@ -1013,7 +1013,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -1499,7 +1499,7 @@ static inline pmd_t pmd_mkwrite_kernel(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_mkwrite_kernel(pmd);
>   }
> diff --git a/arch/sh/include/asm/pgtable_32.h b/arch/sh/include/asm/pgtable_32.h
> index 21952b094650..9f2dcb9eafc8 100644
> --- a/arch/sh/include/asm/pgtable_32.h
> +++ b/arch/sh/include/asm/pgtable_32.h
> @@ -351,6 +351,12 @@ static inline void set_pte(pte_t *ptep, pte_t pte)
>   
>   #define PTE_BIT_FUNC(h,fn,op) \
>   static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
> +#define PTE_BIT_FUNC_VMA(h,fn,op) \
> +static inline pte_t pte_##fn(pte_t pte, struct vm_area_struct *vma) \
> +{ \
> +	pte.pte_##h op; \
> +	return pte; \
> +}
>   
>   #ifdef CONFIG_X2TLB
>   /*
> @@ -359,11 +365,11 @@ static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
>    * kernel permissions), we attempt to couple them a bit more sanely here.
>    */
>   PTE_BIT_FUNC(high, wrprotect, &= ~(_PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE));
> -PTE_BIT_FUNC(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
> +PTE_BIT_FUNC_VMA(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
>   PTE_BIT_FUNC(high, mkhuge, |= _PAGE_SZHUGE);
>   #else
>   PTE_BIT_FUNC(low, wrprotect, &= ~_PAGE_RW);
> -PTE_BIT_FUNC(low, mkwrite, |= _PAGE_RW);
> +PTE_BIT_FUNC_VMA(low, mkwrite, |= _PAGE_RW);
>   PTE_BIT_FUNC(low, mkhuge, |= _PAGE_SZHUGE);
>   #endif
>   
> diff --git a/arch/sparc/include/asm/pgtable_32.h b/arch/sparc/include/asm/pgtable_32.h
> index d4330e3c57a6..3e8836179456 100644
> --- a/arch/sparc/include/asm/pgtable_32.h
> +++ b/arch/sparc/include/asm/pgtable_32.h
> @@ -241,7 +241,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return __pte(pte_val(pte) & ~SRMMU_REF);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | SRMMU_WRITE);
>   }
> diff --git a/arch/sparc/include/asm/pgtable_64.h b/arch/sparc/include/asm/pgtable_64.h
> index 2dc8d4641734..c5cd5c03f557 100644
> --- a/arch/sparc/include/asm/pgtable_64.h
> +++ b/arch/sparc/include/asm/pgtable_64.h
> @@ -466,7 +466,7 @@ static inline pte_t pte_mkclean(pte_t pte)
>   	return __pte(val);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	unsigned long val = pte_val(pte), mask;
>   
> @@ -756,11 +756,11 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return __pmd(pte_val(pte));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pte_t pte = __pte(pmd_val(pmd));
>   
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, vma);
>   
>   	return __pmd(pte_val(pte));
>   }
> diff --git a/arch/um/include/asm/pgtable.h b/arch/um/include/asm/pgtable.h
> index a70d1618eb35..963479c133b7 100644
> --- a/arch/um/include/asm/pgtable.h
> +++ b/arch/um/include/asm/pgtable.h
> @@ -207,7 +207,7 @@ static inline pte_t pte_mkyoung(pte_t pte)
>   	return(pte);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (unlikely(pte_get_bits(pte,  _PAGE_RW)))
>   		return pte;
> diff --git a/arch/x86/include/asm/pgtable.h b/arch/x86/include/asm/pgtable.h
> index 3607f2572f9e..66c514808276 100644
> --- a/arch/x86/include/asm/pgtable.h
> +++ b/arch/x86/include/asm/pgtable.h
> @@ -369,7 +369,9 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte_set_flags(pte, _PAGE_RW);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +struct vm_area_struct;
> +
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -470,7 +472,7 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pmd_set_flags(pmd, _PAGE_ACCESSED);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_set_flags(pmd, _PAGE_RW);
>   }
> diff --git a/arch/xtensa/include/asm/pgtable.h b/arch/xtensa/include/asm/pgtable.h
> index fc7a14884c6c..d72632d9c53c 100644
> --- a/arch/xtensa/include/asm/pgtable.h
> +++ b/arch/xtensa/include/asm/pgtable.h
> @@ -262,7 +262,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   	{ pte_val(pte) |= _PAGE_WRITABLE; return pte; }
>   
>   #define pgprot_noncached(prot) \
> diff --git a/include/asm-generic/hugetlb.h b/include/asm-generic/hugetlb.h
> index d7f6335d3999..e86c830728de 100644
> --- a/include/asm-generic/hugetlb.h
> +++ b/include/asm-generic/hugetlb.h
> @@ -20,9 +20,9 @@ static inline unsigned long huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   #ifndef __HAVE_ARCH_HUGE_PTE_WRPROTECT
> diff --git a/include/linux/mm.h b/include/linux/mm.h
> index 1f79667824eb..af652444fbba 100644
> --- a/include/linux/mm.h
> +++ b/include/linux/mm.h
> @@ -1163,7 +1163,7 @@ void free_compound_page(struct page *page);
>   static inline pte_t maybe_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	return pte;
>   }
>   
> diff --git a/mm/debug_vm_pgtable.c b/mm/debug_vm_pgtable.c
> index af59cc7bd307..7bc5592900bc 100644
> --- a/mm/debug_vm_pgtable.c
> +++ b/mm/debug_vm_pgtable.c
> @@ -109,10 +109,10 @@ static void __init pte_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pte_same(pte, pte));
>   	WARN_ON(!pte_young(pte_mkyoung(pte_mkold(pte))));
>   	WARN_ON(!pte_dirty(pte_mkdirty(pte_mkclean(pte))));
> -	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte))));
> +	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte), args->vma)));
>   	WARN_ON(pte_young(pte_mkold(pte_mkyoung(pte))));
>   	WARN_ON(pte_dirty(pte_mkclean(pte_mkdirty(pte))));
> -	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte))));
> +	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte, args->vma))));
>   	WARN_ON(pte_dirty(pte_wrprotect(pte_mkclean(pte))));
>   	WARN_ON(!pte_dirty(pte_wrprotect(pte_mkdirty(pte))));
>   }
> @@ -153,7 +153,7 @@ static void __init pte_advanced_tests(struct pgtable_debug_args *args)
>   	pte = pte_mkclean(pte);
>   	set_pte_at(args->mm, args->vaddr, args->ptep, pte);
>   	flush_dcache_page(page);
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, args->vma);
>   	pte = pte_mkdirty(pte);
>   	ptep_set_access_flags(args->vma, args->vaddr, args->ptep, pte, 1);
>   	pte = ptep_get(args->ptep);
> @@ -199,10 +199,10 @@ static void __init pmd_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pmd_same(pmd, pmd));
>   	WARN_ON(!pmd_young(pmd_mkyoung(pmd_mkold(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_mkdirty(pmd_mkclean(pmd))));
> -	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd))));
> +	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd), args->vma)));
>   	WARN_ON(pmd_young(pmd_mkold(pmd_mkyoung(pmd))));
>   	WARN_ON(pmd_dirty(pmd_mkclean(pmd_mkdirty(pmd))));
> -	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd))));
> +	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd, args->vma))));
>   	WARN_ON(pmd_dirty(pmd_wrprotect(pmd_mkclean(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_wrprotect(pmd_mkdirty(pmd))));
>   	/*
> @@ -253,7 +253,7 @@ static void __init pmd_advanced_tests(struct pgtable_debug_args *args)
>   	pmd = pmd_mkclean(pmd);
>   	set_pmd_at(args->mm, vaddr, args->pmdp, pmd);
>   	flush_dcache_page(page);
> -	pmd = pmd_mkwrite(pmd);
> +	pmd = pmd_mkwrite(pmd, args->vma);
>   	pmd = pmd_mkdirty(pmd);
>   	pmdp_set_access_flags(args->vma, vaddr, args->pmdp, pmd, 1);
>   	pmd = READ_ONCE(*args->pmdp);
> @@ -928,8 +928,8 @@ static void __init hugetlb_basic_tests(struct pgtable_debug_args *args)
>   	pte = mk_huge_pte(page, args->page_prot);
>   
>   	WARN_ON(!huge_pte_dirty(huge_pte_mkdirty(pte)));
> -	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte))));
> -	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte))));
> +	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte), args->vma)));
> +	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte, args->vma))));
>   
>   #ifdef CONFIG_ARCH_WANT_GENERAL_HUGETLB
>   	pte = pfn_pte(args->fixed_pmd_pfn, args->page_prot);
> diff --git a/mm/huge_memory.c b/mm/huge_memory.c
> index 4fc43859e59a..aaf815838144 100644
> --- a/mm/huge_memory.c
> +++ b/mm/huge_memory.c
> @@ -555,7 +555,7 @@ __setup("transparent_hugepage=", setup_transparent_hugepage);
>   pmd_t maybe_pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	return pmd;
>   }
>   
> @@ -1580,7 +1580,7 @@ vm_fault_t do_huge_pmd_numa_page(struct vm_fault *vmf)
>   	pmd = pmd_modify(oldpmd, vma->vm_page_prot);
>   	pmd = pmd_mkyoung(pmd);
>   	if (writable)
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	set_pmd_at(vma->vm_mm, haddr, vmf->pmd, pmd);
>   	update_mmu_cache_pmd(vma, vmf->address, vmf->pmd);
>   	spin_unlock(vmf->ptl);
> @@ -1926,7 +1926,7 @@ int change_huge_pmd(struct mmu_gather *tlb, struct vm_area_struct *vma,
>   	/* See change_pte_range(). */
>   	if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) && !pmd_write(entry) &&
>   	    can_change_pmd_writable(vma, addr, entry))
> -		entry = pmd_mkwrite(entry);
> +		entry = pmd_mkwrite(entry, vma);
>   
>   	ret = HPAGE_PMD_NR;
>   	set_pmd_at(mm, addr, pmd, entry);
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 07abcb6eb203..6af471bdcff8 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -4900,7 +4900,7 @@ static pte_t make_huge_pte(struct vm_area_struct *vma, struct page *page,
>   
>   	if (writable) {
>   		entry = huge_pte_mkwrite(huge_pte_mkdirty(mk_huge_pte(page,
> -					 vma->vm_page_prot)));
> +					 vma->vm_page_prot)), vma);
>   	} else {
>   		entry = huge_pte_wrprotect(mk_huge_pte(page,
>   					   vma->vm_page_prot));
> @@ -4916,7 +4916,7 @@ static void set_huge_ptep_writable(struct vm_area_struct *vma,
>   {
>   	pte_t entry;
>   
> -	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)));
> +	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)), vma);
>   	if (huge_ptep_set_access_flags(vma, address, ptep, entry, 1))
>   		update_mmu_cache(vma, address, ptep);
>   }
> diff --git a/mm/memory.c b/mm/memory.c
> index f456f3b5049c..d0972d2d6f36 100644
> --- a/mm/memory.c
> +++ b/mm/memory.c
> @@ -4067,7 +4067,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
>   	entry = mk_pte(&folio->page, vma->vm_page_prot);
>   	entry = pte_sw_mkyoung(entry);
>   	if (vma->vm_flags & VM_WRITE)
> -		entry = pte_mkwrite(pte_mkdirty(entry));
> +		entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   
>   	vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, vmf->address,
>   			&vmf->ptl);
> @@ -4755,7 +4755,7 @@ static vm_fault_t do_numa_page(struct vm_fault *vmf)
>   	pte = pte_modify(old_pte, vma->vm_page_prot);
>   	pte = pte_mkyoung(pte);
>   	if (writable)
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	ptep_modify_prot_commit(vma, vmf->address, vmf->pte, old_pte, pte);
>   	update_mmu_cache(vma, vmf->address, vmf->pte);
>   	pte_unmap_unlock(vmf->pte, vmf->ptl);
> diff --git a/mm/migrate_device.c b/mm/migrate_device.c
> index d30c9de60b0d..df3f5e9d5f76 100644
> --- a/mm/migrate_device.c
> +++ b/mm/migrate_device.c
> @@ -646,7 +646,7 @@ static void migrate_vma_insert_page(struct migrate_vma *migrate,
>   		}
>   		entry = mk_pte(page, vma->vm_page_prot);
>   		if (vma->vm_flags & VM_WRITE)
> -			entry = pte_mkwrite(pte_mkdirty(entry));
> +			entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   	}
>   
>   	ptep = pte_offset_map_lock(mm, pmdp, addr, &ptl);
> diff --git a/mm/mprotect.c b/mm/mprotect.c
> index 1d4843c97c2a..381163a41e88 100644
> --- a/mm/mprotect.c
> +++ b/mm/mprotect.c
> @@ -198,7 +198,7 @@ static long change_pte_range(struct mmu_gather *tlb,
>   			if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) &&
>   			    !pte_write(ptent) &&
>   			    can_change_pte_writable(vma, addr, ptent))
> -				ptent = pte_mkwrite(ptent);
> +				ptent = pte_mkwrite(ptent, vma);
>   
>   			ptep_modify_prot_commit(vma, addr, pte, oldpte, ptent);
>   			if (pte_needs_flush(oldpte, ptent))
> diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
> index 53c3d916ff66..3db6f87c0aca 100644
> --- a/mm/userfaultfd.c
> +++ b/mm/userfaultfd.c
> @@ -75,7 +75,7 @@ int mfill_atomic_install_pte(struct mm_struct *dst_mm, pmd_t *dst_pmd,
>   	if (page_in_cache && !vm_shared)
>   		writable = false;
>   	if (writable)
> -		_dst_pte = pte_mkwrite(_dst_pte);
> +		_dst_pte = pte_mkwrite(_dst_pte, dst_vma);
>   	if (wp_copy)
>   		_dst_pte = pte_mkuffd_wp(_dst_pte);
>   
_______________________________________________
linux-riscv mailing list
linux-riscv@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-riscv

WARNING: multiple messages have this Message-ID (diff)
From: Christophe Leroy <christophe.leroy@csgroup.eu>
To: Rick Edgecombe <rick.p.edgecombe@intel.com>,
	"x86@kernel.org" <x86@kernel.org>,
	"H . Peter Anvin" <hpa@zytor.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Ingo Molnar <mingo@redhat.com>,
	"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"linux-doc@vger.kernel.org" <linux-doc@vger.kernel.org>,
	"linux-mm@kvack.org" <linux-mm@kvack.org>,
	"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
	"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
	Arnd Bergmann <arnd@arndb.de>, Andy Lutomirski <luto@kernel.org>,
	Balbir Singh <bsingharora@gmail.com>,
	Borislav Petkov <bp@alien8.de>,
	Cyrill Gorcunov <gorcunov@gmail.com>,
	Dave Hansen <dave.hansen@linux.intel.com>,
	Eugene Syromiatnikov <esyr@redhat.com>,
	Florian Weimer <fweimer@redhat.com>,
	"H . J . Lu" <hjl.tools@gmail.com>, Jann Horn <jannh@google.com>,
	Jonathan Corbet <corbet@lwn.net>,
	Kees Cook <keescook@chromium.org>,
	Mike Kravetz <mike.kravetz@oracle.com>,
	Nadav Amit <nadav.amit@gmail.com>,
	Oleg Nesterov <oleg@redhat.com>, Pavel Machek <pavel@ucw.cz>,
	Peter Zijlstra <peterz@infradead.org>,
	Randy Dunlap <rdunlap@infradead.org>,
	Weijiang Yang <weijiang.yang@intel.com>,
	"Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>,
	John Allen <john.allen@amd.com>,
	"kcc@google.com" <kcc@google.com>,
	"eranian@google.com" <eranian@google.com>,
	"rppt@kernel.org" <rppt@kernel.org>,
	"jamorris@linux.microsoft.com" <jamorris@linux.microsoft.com>,
	"dethoma@microsoft.com" <dethoma@microsoft.com>,
	"akpm@linux-foundation.org" <akpm@linux-foundation.org>,
	"Andrew.Cooper3@citrix.com" <Andrew.Cooper3@citrix.com>,
	"christina.schimpe@intel.com" <christina.schimpe@intel.com>,
	"david@redhat.com" <david@redhat.com>,
	"debug@rivosinc.com" <debug@rivosinc.com>
Cc: "linux-alpha@vger.kernel.org" <linux-alpha@vger.kernel.org>,
	"linux-snps-arc@lists.infradead.org"
	<linux-snps-arc@lists.infradead.org>,
	"linux-arm-kernel@lists.infradead.org"
	<linux-arm-kernel@lists.infradead.org>,
	"linux-csky@vger.kernel.org" <linux-csky@vger.kernel.org>,
	"linux-hexagon@vger.kernel.org" <linux-hexagon@vger.kernel.org>,
	"linux-ia64@vger.kernel.org" <linux-ia64@vger.kernel.org>,
	"loongarch@lists.linux.dev" <loongarch@lists.linux.dev>,
	"linux-m68k@lists.linux-m68k.org"
	<linux-m68k@lists.linux-m68k.org>,
	Michal Simek <monstr@monstr.eu>,
	Dinh Nguyen <dinguyen@kernel.org>,
	"linux-mips@vger.kernel.org" <linux-mips@vger.kernel.org>,
	"linux-openrisc@vger.kernel.org" <linux-openrisc@vger.kernel.org>,
	"linux-parisc@vger.kernel.org" <linux-parisc@vger.kernel.org>,
	"linuxppc-dev@lists.ozlabs.org" <linuxppc-dev@lists.ozlabs.org>,
	"linux-riscv@lists.infradead.org"
	<linux-riscv@lists.infradead.org>,
	"linux-s390@vger.kernel.org" <linux-s390@vger.kernel.org>,
	"linux-sh@vger.kernel.org" <linux-sh@vger.kernel.org>,
	"sparclinux@vger.kernel.org" <sparclinux@vger.kernel.org>,
	"linux-um@lists.infradead.org" <linux-um@lists.infradead.org>,
	"xen-devel@lists.xenproject.org" <xen-devel@lists.xenproject.org>
Subject: Re: [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA
Date: Wed, 1 Mar 2023 07:03:23 +0000	[thread overview]
Message-ID: <1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu> (raw)
In-Reply-To: <20230227222957.24501-14-rick.p.edgecombe@intel.com>



Le 27/02/2023 à 23:29, Rick Edgecombe a écrit :
> The x86 Control-flow Enforcement Technology (CET) feature includes a new
> type of memory called shadow stack. This shadow stack memory has some
> unusual properties, which requires some core mm changes to function
> properly.
> 
> One of these unusual properties is that shadow stack memory is writable,
> but only in limited ways. These limits are applied via a specific PTE
> bit combination. Nevertheless, the memory is writable, and core mm code
> will need to apply the writable permissions in the typical paths that
> call pte_mkwrite().
> 
> In addition to VM_WRITE, the shadow stack VMA's will have a flag denoting
> that they are special shadow stack flavor of writable memory. So make
> pte_mkwrite() take a VMA, so that the x86 implementation of it can know to
> create regular writable memory or shadow stack memory.
> 
> Apply the same changes for pmd_mkwrite() and huge_pte_mkwrite().

I'm not sure it is a good idea to add a second argument to 
pte_mkwrite(). All pte_mkxxxx() only take a pte and nothing else.

I think you should do the same as commit d9ed9faac283 ("mm: add new 
arch_make_huge_pte() method for tile support")

Christophe

> 
> No functional change.
> 
> Cc: linux-doc@vger.kernel.org
> Cc: linux-kernel@vger.kernel.org
> Cc: linux-alpha@vger.kernel.org
> Cc: linux-snps-arc@lists.infradead.org
> Cc: linux-arm-kernel@lists.infradead.org
> Cc: linux-csky@vger.kernel.org
> Cc: linux-hexagon@vger.kernel.org
> Cc: linux-ia64@vger.kernel.org
> Cc: loongarch@lists.linux.dev
> Cc: linux-m68k@lists.linux-m68k.org
> Cc: Michal Simek <monstr@monstr.eu>
> Cc: Dinh Nguyen <dinguyen@kernel.org>
> Cc: linux-mips@vger.kernel.org
> Cc: linux-openrisc@vger.kernel.org
> Cc: linux-parisc@vger.kernel.org
> Cc: linuxppc-dev@lists.ozlabs.org
> Cc: linux-riscv@lists.infradead.org
> Cc: linux-s390@vger.kernel.org
> Cc: linux-sh@vger.kernel.org
> Cc: sparclinux@vger.kernel.org
> Cc: linux-um@lists.infradead.org
> Cc: xen-devel@lists.xenproject.org
> Cc: linux-arch@vger.kernel.org
> Cc: linux-mm@kvack.org
> Tested-by: Pengfei Xu <pengfei.xu@intel.com>
> Tested-by: John Allen <john.allen@amd.com>
> Tested-by: Kees Cook <keescook@chromium.org>
> Acked-by: Mike Rapoport (IBM) <rppt@kernel.org>
> Acked-by: Michael Ellerman <mpe@ellerman.id.au>
> Acked-by: David Hildenbrand <david@redhat.com>
> Reviewed-by: Kees Cook <keescook@chromium.org>
> Suggested-by: David Hildenbrand <david@redhat.com>
> Signed-off-by: Rick Edgecombe <rick.p.edgecombe@intel.com>
> 
> ---
> Hi Non-x86 Arch’s,
> 
> x86 has a feature that allows for the creation of a special type of
> writable memory (shadow stack) that is only writable in limited specific
> ways. Previously, changes were proposed to core MM code to teach it to
> decide when to create normally writable memory or the special shadow stack
> writable memory, but David Hildenbrand suggested[0] to change
> pXX_mkwrite() to take a VMA, so awareness of shadow stack memory can be
> moved into x86 code.
> 
> Since pXX_mkwrite() is defined in every arch, it requires some tree-wide
> changes. So that is why you are seeing some patches out of a big x86
> series pop up in your arch mailing list. There is no functional change.
> After this refactor, the shadow stack series goes on to use the arch
> helpers to push shadow stack memory details inside arch/x86.
> 
> Testing was just 0-day build testing.
> 
> Hopefully that is enough context. Thanks!
> 
> [0] https://lore.kernel.org/lkml/0e29a2d0-08d8-bcd6-ff26-4bea0e4037b0@redhat.com/#t
> 
> v6:
>   - New patch
> ---
>   Documentation/mm/arch_pgtable_helpers.rst    |  9 ++++++---
>   arch/alpha/include/asm/pgtable.h             |  6 +++++-
>   arch/arc/include/asm/hugepage.h              |  2 +-
>   arch/arc/include/asm/pgtable-bits-arcv2.h    |  7 ++++++-
>   arch/arm/include/asm/pgtable-3level.h        |  7 ++++++-
>   arch/arm/include/asm/pgtable.h               |  2 +-
>   arch/arm64/include/asm/pgtable.h             |  4 ++--
>   arch/csky/include/asm/pgtable.h              |  2 +-
>   arch/hexagon/include/asm/pgtable.h           |  2 +-
>   arch/ia64/include/asm/pgtable.h              |  2 +-
>   arch/loongarch/include/asm/pgtable.h         |  4 ++--
>   arch/m68k/include/asm/mcf_pgtable.h          |  2 +-
>   arch/m68k/include/asm/motorola_pgtable.h     |  6 +++++-
>   arch/m68k/include/asm/sun3_pgtable.h         |  6 +++++-
>   arch/microblaze/include/asm/pgtable.h        |  2 +-
>   arch/mips/include/asm/pgtable.h              |  6 +++---
>   arch/nios2/include/asm/pgtable.h             |  2 +-
>   arch/openrisc/include/asm/pgtable.h          |  2 +-
>   arch/parisc/include/asm/pgtable.h            |  6 +++++-
>   arch/powerpc/include/asm/book3s/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/book3s/64/pgtable.h |  4 ++--
>   arch/powerpc/include/asm/nohash/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/nohash/32/pte-8xx.h |  2 +-
>   arch/powerpc/include/asm/nohash/64/pgtable.h |  2 +-
>   arch/riscv/include/asm/pgtable.h             |  6 +++---
>   arch/s390/include/asm/hugetlb.h              |  4 ++--
>   arch/s390/include/asm/pgtable.h              |  4 ++--
>   arch/sh/include/asm/pgtable_32.h             | 10 ++++++++--
>   arch/sparc/include/asm/pgtable_32.h          |  2 +-
>   arch/sparc/include/asm/pgtable_64.h          |  6 +++---
>   arch/um/include/asm/pgtable.h                |  2 +-
>   arch/x86/include/asm/pgtable.h               |  6 ++++--
>   arch/xtensa/include/asm/pgtable.h            |  2 +-
>   include/asm-generic/hugetlb.h                |  4 ++--
>   include/linux/mm.h                           |  2 +-
>   mm/debug_vm_pgtable.c                        | 16 ++++++++--------
>   mm/huge_memory.c                             |  6 +++---
>   mm/hugetlb.c                                 |  4 ++--
>   mm/memory.c                                  |  4 ++--
>   mm/migrate_device.c                          |  2 +-
>   mm/mprotect.c                                |  2 +-
>   mm/userfaultfd.c                             |  2 +-
>   42 files changed, 106 insertions(+), 69 deletions(-)
> 
> diff --git a/Documentation/mm/arch_pgtable_helpers.rst b/Documentation/mm/arch_pgtable_helpers.rst
> index 30d9a09f01f4..78ac3ff2fe1d 100644
> --- a/Documentation/mm/arch_pgtable_helpers.rst
> +++ b/Documentation/mm/arch_pgtable_helpers.rst
> @@ -46,7 +46,8 @@ PTE Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pte_mkclean               | Creates a clean PTE                              |
>   +---------------------------+--------------------------------------------------+
> -| pte_mkwrite               | Creates a writable PTE                           |
> +| pte_mkwrite               | Creates a writable PTE of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pte_wrprotect             | Creates a write protected PTE                    |
>   +---------------------------+--------------------------------------------------+
> @@ -118,7 +119,8 @@ PMD Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pmd_mkclean               | Creates a clean PMD                              |
>   +---------------------------+--------------------------------------------------+
> -| pmd_mkwrite               | Creates a writable PMD                           |
> +| pmd_mkwrite               | Creates a writable PMD of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pmd_wrprotect             | Creates a write protected PMD                    |
>   +---------------------------+--------------------------------------------------+
> @@ -222,7 +224,8 @@ HugeTLB Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_mkdirty          | Creates a dirty HugeTLB                          |
>   +---------------------------+--------------------------------------------------+
> -| huge_pte_mkwrite          | Creates a writable HugeTLB                       |
> +| huge_pte_mkwrite          | Creates a writable HugeTLB of the type specified |
> +|                           | by the VMA.                                      |
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_wrprotect        | Creates a write protected HugeTLB                |
>   +---------------------------+--------------------------------------------------+
> diff --git a/arch/alpha/include/asm/pgtable.h b/arch/alpha/include/asm/pgtable.h
> index ba43cb841d19..fb5d207c2a89 100644
> --- a/arch/alpha/include/asm/pgtable.h
> +++ b/arch/alpha/include/asm/pgtable.h
> @@ -256,9 +256,13 @@ extern inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   extern inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~(__DIRTY_BITS); return pte; }
>   extern inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~(__ACCESS_BITS); return pte; }
> -extern inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= __DIRTY_BITS; return pte; }
>   extern inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= __ACCESS_BITS; return pte; }
> +extern inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_FOW;
> +	return pte;
> +}
>   
>   /*
>    * The smp_rmb() in the following functions are required to order the load of
> diff --git a/arch/arc/include/asm/hugepage.h b/arch/arc/include/asm/hugepage.h
> index 5001b796fb8d..223a96967188 100644
> --- a/arch/arc/include/asm/hugepage.h
> +++ b/arch/arc/include/asm/hugepage.h
> @@ -21,7 +21,7 @@ static inline pmd_t pte_pmd(pte_t pte)
>   }
>   
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/arc/include/asm/pgtable-bits-arcv2.h b/arch/arc/include/asm/pgtable-bits-arcv2.h
> index 6e9f8ca6d6a1..a5b8bc955015 100644
> --- a/arch/arc/include/asm/pgtable-bits-arcv2.h
> +++ b/arch/arc/include/asm/pgtable-bits-arcv2.h
> @@ -87,7 +87,6 @@
>   
>   PTE_BIT_FUNC(mknotpresent,     &= ~(_PAGE_PRESENT));
>   PTE_BIT_FUNC(wrprotect,	&= ~(_PAGE_WRITE));
> -PTE_BIT_FUNC(mkwrite,	|= (_PAGE_WRITE));
>   PTE_BIT_FUNC(mkclean,	&= ~(_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkdirty,	|= (_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkold,	&= ~(_PAGE_ACCESSED));
> @@ -95,6 +94,12 @@ PTE_BIT_FUNC(mkyoung,	|= (_PAGE_ACCESSED));
>   PTE_BIT_FUNC(mkspecial,	|= (_PAGE_SPECIAL));
>   PTE_BIT_FUNC(mkhuge,	|= (_PAGE_HW_SZ));
>   
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= (_PAGE_WRITE);
> +	return pte;
> +}
> +
>   static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
>   {
>   	return __pte((pte_val(pte) & _PAGE_CHG_MASK) | pgprot_val(newprot));
> diff --git a/arch/arm/include/asm/pgtable-3level.h b/arch/arm/include/asm/pgtable-3level.h
> index 106049791500..df071a807610 100644
> --- a/arch/arm/include/asm/pgtable-3level.h
> +++ b/arch/arm/include/asm/pgtable-3level.h
> @@ -202,11 +202,16 @@ static inline pmd_t pmd_##fn(pmd_t pmd) { pmd_val(pmd) op; return pmd; }
>   
>   PMD_BIT_FUNC(wrprotect,	|= L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkold,	&= ~PMD_SECT_AF);
> -PMD_BIT_FUNC(mkwrite,   &= ~L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkdirty,   |= L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkclean,   &= ~L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkyoung,   |= PMD_SECT_AF);
>   
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
> +{
> +	pmd_val(pmd) |= L_PMD_SECT_RDONLY;
> +	return pmd;
> +}
> +
>   #define pmd_mkhuge(pmd)		(__pmd(pmd_val(pmd) & ~PMD_TABLE_BIT))
>   
>   #define pmd_pfn(pmd)		(((pmd_val(pmd) & PMD_MASK) & PHYS_MASK) >> PAGE_SHIFT)
> diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
> index a58ccbb406ad..39ad1ae1308d 100644
> --- a/arch/arm/include/asm/pgtable.h
> +++ b/arch/arm/include/asm/pgtable.h
> @@ -227,7 +227,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   	return set_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return clear_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
> diff --git a/arch/arm64/include/asm/pgtable.h b/arch/arm64/include/asm/pgtable.h
> index cccf8885792e..913bf370f74a 100644
> --- a/arch/arm64/include/asm/pgtable.h
> +++ b/arch/arm64/include/asm/pgtable.h
> @@ -187,7 +187,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -492,7 +492,7 @@ static inline int pmd_trans_huge(pmd_t pmd)
>   #define pmd_cont(pmd)		pte_cont(pmd_pte(pmd))
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/csky/include/asm/pgtable.h b/arch/csky/include/asm/pgtable.h
> index d4042495febc..c2f92c991e37 100644
> --- a/arch/csky/include/asm/pgtable.h
> +++ b/arch/csky/include/asm/pgtable.h
> @@ -176,7 +176,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> diff --git a/arch/hexagon/include/asm/pgtable.h b/arch/hexagon/include/asm/pgtable.h
> index 59393613d086..14ab9c789c0e 100644
> --- a/arch/hexagon/include/asm/pgtable.h
> +++ b/arch/hexagon/include/asm/pgtable.h
> @@ -300,7 +300,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   }
>   
>   /* pte_mkwrite - mark page as writable */
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/ia64/include/asm/pgtable.h b/arch/ia64/include/asm/pgtable.h
> index 21c97e31a28a..f879dd626da6 100644
> --- a/arch/ia64/include/asm/pgtable.h
> +++ b/arch/ia64/include/asm/pgtable.h
> @@ -268,7 +268,7 @@ ia64_phys_addr_valid (unsigned long addr)
>    * access rights:
>    */
>   #define pte_wrprotect(pte)	(__pte(pte_val(pte) & ~_PAGE_AR_RW))
> -#define pte_mkwrite(pte)	(__pte(pte_val(pte) | _PAGE_AR_RW))
> +#define pte_mkwrite(pte, vma)	(__pte(pte_val(pte) | _PAGE_AR_RW))
>   #define pte_mkold(pte)		(__pte(pte_val(pte) & ~_PAGE_A))
>   #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_A))
>   #define pte_mkclean(pte)	(__pte(pte_val(pte) & ~_PAGE_D))
> diff --git a/arch/loongarch/include/asm/pgtable.h b/arch/loongarch/include/asm/pgtable.h
> index d28fb9dbec59..ebf645f40298 100644
> --- a/arch/loongarch/include/asm/pgtable.h
> +++ b/arch/loongarch/include/asm/pgtable.h
> @@ -390,7 +390,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -490,7 +490,7 @@ static inline int pmd_write(pmd_t pmd)
>   	return !!(pmd_val(pmd) & _PAGE_WRITE);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/m68k/include/asm/mcf_pgtable.h b/arch/m68k/include/asm/mcf_pgtable.h
> index 13741c1245e1..37d77e055016 100644
> --- a/arch/m68k/include/asm/mcf_pgtable.h
> +++ b/arch/m68k/include/asm/mcf_pgtable.h
> @@ -211,7 +211,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= CF_PAGE_WRITABLE;
>   	return pte;
> diff --git a/arch/m68k/include/asm/motorola_pgtable.h b/arch/m68k/include/asm/motorola_pgtable.h
> index ec0dc19ab834..c4e8eb76286d 100644
> --- a/arch/m68k/include/asm/motorola_pgtable.h
> +++ b/arch/m68k/include/asm/motorola_pgtable.h
> @@ -155,7 +155,6 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~_PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)
> @@ -168,6 +167,11 @@ static inline pte_t pte_mkcache(pte_t pte)
>   	pte_val(pte) = (pte_val(pte) & _CACHEMASK040) | m68k_supervisor_cachemode;
>   	return pte;
>   }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_RONLY;
> +	return pte;
> +}
>   
>   #define swapper_pg_dir kernel_pg_dir
>   extern pgd_t kernel_pg_dir[128];
> diff --git a/arch/m68k/include/asm/sun3_pgtable.h b/arch/m68k/include/asm/sun3_pgtable.h
> index e582b0484a55..2a06bea51a1e 100644
> --- a/arch/m68k/include/asm/sun3_pgtable.h
> +++ b/arch/m68k/include/asm/sun3_pgtable.h
> @@ -143,10 +143,14 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & SUN3_PAGE_ACCESS
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_NOCACHE; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= SUN3_PAGE_WRITEABLE;
> +	return pte;
> +}
>   // use this version when caches work...
>   //static inline pte_t pte_mkcache(pte_t pte)	{ pte_val(pte) &= SUN3_PAGE_NOCACHE; return pte; }
>   // until then, use:
> diff --git a/arch/microblaze/include/asm/pgtable.h b/arch/microblaze/include/asm/pgtable.h
> index d1b8272abcd9..5b83e82f8d7e 100644
> --- a/arch/microblaze/include/asm/pgtable.h
> +++ b/arch/microblaze/include/asm/pgtable.h
> @@ -266,7 +266,7 @@ static inline pte_t pte_mkread(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER; return pte; }
>   static inline pte_t pte_mkexec(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER | _PAGE_EXEC; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte) \
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma) \
>   	{ pte_val(pte) |= _PAGE_RW; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
> diff --git a/arch/mips/include/asm/pgtable.h b/arch/mips/include/asm/pgtable.h
> index 791389bf3c12..06efd567144a 100644
> --- a/arch/mips/include/asm/pgtable.h
> +++ b/arch/mips/include/asm/pgtable.h
> @@ -309,7 +309,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte.pte_low |= _PAGE_WRITE;
>   	if (pte.pte_low & _PAGE_MODIFIED) {
> @@ -364,7 +364,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -626,7 +626,7 @@ static inline pmd_t pmd_wrprotect(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/nios2/include/asm/pgtable.h b/arch/nios2/include/asm/pgtable.h
> index 0f5c2564e9f5..edd458518e0e 100644
> --- a/arch/nios2/include/asm/pgtable.h
> +++ b/arch/nios2/include/asm/pgtable.h
> @@ -129,7 +129,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/openrisc/include/asm/pgtable.h b/arch/openrisc/include/asm/pgtable.h
> index 3eb9b9555d0d..fd40aec189d1 100644
> --- a/arch/openrisc/include/asm/pgtable.h
> +++ b/arch/openrisc/include/asm/pgtable.h
> @@ -250,7 +250,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/parisc/include/asm/pgtable.h b/arch/parisc/include/asm/pgtable.h
> index e2950f5db7c9..89f62137e67f 100644
> --- a/arch/parisc/include/asm/pgtable.h
> +++ b/arch/parisc/include/asm/pgtable.h
> @@ -331,8 +331,12 @@ static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; retu
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~_PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= _PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkspecial(pte_t pte)	{ pte_val(pte) |= _PAGE_SPECIAL; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= _PAGE_WRITE;
> +	return pte;
> +}
>   
>   /*
>    * Huge pte definitions.
> diff --git a/arch/powerpc/include/asm/book3s/32/pgtable.h b/arch/powerpc/include/asm/book3s/32/pgtable.h
> index 7bf1fe7297c6..10d9a1d2aca9 100644
> --- a/arch/powerpc/include/asm/book3s/32/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/32/pgtable.h
> @@ -498,7 +498,7 @@ static inline pte_t pte_mkpte(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h
> index 4acc9690f599..be0636522d36 100644
> --- a/arch/powerpc/include/asm/book3s/64/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/64/pgtable.h
> @@ -600,7 +600,7 @@ static inline pte_t pte_mkexec(pte_t pte)
>   	return __pte_raw(pte_raw(pte) | cpu_to_be64(_PAGE_EXEC));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	/*
>   	 * write implies read, hence set both
> @@ -1071,7 +1071,7 @@ static inline pte_t *pmdp_ptep(pmd_t *pmd)
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   
>   #ifdef CONFIG_HAVE_ARCH_SOFT_DIRTY
>   #define pmd_soft_dirty(pmd)    pte_soft_dirty(pmd_pte(pmd))
> diff --git a/arch/powerpc/include/asm/nohash/32/pgtable.h b/arch/powerpc/include/asm/nohash/32/pgtable.h
> index fec56d965f00..7bfbcb9ba55b 100644
> --- a/arch/powerpc/include/asm/nohash/32/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/32/pgtable.h
> @@ -171,7 +171,7 @@ void unmap_kernel_page(unsigned long va);
>   	do { pte_update(mm, addr, ptep, ~0, 0, 0); } while (0)
>   
>   #ifndef pte_mkwrite
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/32/pte-8xx.h b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> index 1a89ebdc3acc..f32450eb270a 100644
> --- a/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> +++ b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> @@ -101,7 +101,7 @@ static inline int pte_write(pte_t pte)
>   
>   #define pte_write pte_write
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) & ~_PAGE_RO);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/64/pgtable.h b/arch/powerpc/include/asm/nohash/64/pgtable.h
> index 287e25864ffa..589009555877 100644
> --- a/arch/powerpc/include/asm/nohash/64/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/64/pgtable.h
> @@ -85,7 +85,7 @@
>   #ifndef __ASSEMBLY__
>   /* pte_clear moved to later in this file */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
> index d8d8de0ded99..fed1b81fbe07 100644
> --- a/arch/riscv/include/asm/pgtable.h
> +++ b/arch/riscv/include/asm/pgtable.h
> @@ -338,7 +338,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   
>   /* static inline pte_t pte_mkread(pte_t pte) */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_WRITE);
>   }
> @@ -624,9 +624,9 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pte_pmd(pte_mkyoung(pmd_pte(pmd)));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
> -	return pte_pmd(pte_mkwrite(pmd_pte(pmd)));
> +	return pte_pmd(pte_mkwrite(pmd_pte(pmd), vma));
>   }
>   
>   static inline pmd_t pmd_wrprotect(pmd_t pmd)
> diff --git a/arch/s390/include/asm/hugetlb.h b/arch/s390/include/asm/hugetlb.h
> index ccdbccfde148..558f7eef9c4d 100644
> --- a/arch/s390/include/asm/hugetlb.h
> +++ b/arch/s390/include/asm/hugetlb.h
> @@ -102,9 +102,9 @@ static inline int huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   static inline pte_t huge_pte_mkdirty(pte_t pte)
> diff --git a/arch/s390/include/asm/pgtable.h b/arch/s390/include/asm/pgtable.h
> index deeb918cae1d..8f2c743da0eb 100644
> --- a/arch/s390/include/asm/pgtable.h
> +++ b/arch/s390/include/asm/pgtable.h
> @@ -1013,7 +1013,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -1499,7 +1499,7 @@ static inline pmd_t pmd_mkwrite_kernel(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_mkwrite_kernel(pmd);
>   }
> diff --git a/arch/sh/include/asm/pgtable_32.h b/arch/sh/include/asm/pgtable_32.h
> index 21952b094650..9f2dcb9eafc8 100644
> --- a/arch/sh/include/asm/pgtable_32.h
> +++ b/arch/sh/include/asm/pgtable_32.h
> @@ -351,6 +351,12 @@ static inline void set_pte(pte_t *ptep, pte_t pte)
>   
>   #define PTE_BIT_FUNC(h,fn,op) \
>   static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
> +#define PTE_BIT_FUNC_VMA(h,fn,op) \
> +static inline pte_t pte_##fn(pte_t pte, struct vm_area_struct *vma) \
> +{ \
> +	pte.pte_##h op; \
> +	return pte; \
> +}
>   
>   #ifdef CONFIG_X2TLB
>   /*
> @@ -359,11 +365,11 @@ static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
>    * kernel permissions), we attempt to couple them a bit more sanely here.
>    */
>   PTE_BIT_FUNC(high, wrprotect, &= ~(_PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE));
> -PTE_BIT_FUNC(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
> +PTE_BIT_FUNC_VMA(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
>   PTE_BIT_FUNC(high, mkhuge, |= _PAGE_SZHUGE);
>   #else
>   PTE_BIT_FUNC(low, wrprotect, &= ~_PAGE_RW);
> -PTE_BIT_FUNC(low, mkwrite, |= _PAGE_RW);
> +PTE_BIT_FUNC_VMA(low, mkwrite, |= _PAGE_RW);
>   PTE_BIT_FUNC(low, mkhuge, |= _PAGE_SZHUGE);
>   #endif
>   
> diff --git a/arch/sparc/include/asm/pgtable_32.h b/arch/sparc/include/asm/pgtable_32.h
> index d4330e3c57a6..3e8836179456 100644
> --- a/arch/sparc/include/asm/pgtable_32.h
> +++ b/arch/sparc/include/asm/pgtable_32.h
> @@ -241,7 +241,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return __pte(pte_val(pte) & ~SRMMU_REF);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | SRMMU_WRITE);
>   }
> diff --git a/arch/sparc/include/asm/pgtable_64.h b/arch/sparc/include/asm/pgtable_64.h
> index 2dc8d4641734..c5cd5c03f557 100644
> --- a/arch/sparc/include/asm/pgtable_64.h
> +++ b/arch/sparc/include/asm/pgtable_64.h
> @@ -466,7 +466,7 @@ static inline pte_t pte_mkclean(pte_t pte)
>   	return __pte(val);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	unsigned long val = pte_val(pte), mask;
>   
> @@ -756,11 +756,11 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return __pmd(pte_val(pte));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pte_t pte = __pte(pmd_val(pmd));
>   
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, vma);
>   
>   	return __pmd(pte_val(pte));
>   }
> diff --git a/arch/um/include/asm/pgtable.h b/arch/um/include/asm/pgtable.h
> index a70d1618eb35..963479c133b7 100644
> --- a/arch/um/include/asm/pgtable.h
> +++ b/arch/um/include/asm/pgtable.h
> @@ -207,7 +207,7 @@ static inline pte_t pte_mkyoung(pte_t pte)
>   	return(pte);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (unlikely(pte_get_bits(pte,  _PAGE_RW)))
>   		return pte;
> diff --git a/arch/x86/include/asm/pgtable.h b/arch/x86/include/asm/pgtable.h
> index 3607f2572f9e..66c514808276 100644
> --- a/arch/x86/include/asm/pgtable.h
> +++ b/arch/x86/include/asm/pgtable.h
> @@ -369,7 +369,9 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte_set_flags(pte, _PAGE_RW);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +struct vm_area_struct;
> +
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -470,7 +472,7 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pmd_set_flags(pmd, _PAGE_ACCESSED);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_set_flags(pmd, _PAGE_RW);
>   }
> diff --git a/arch/xtensa/include/asm/pgtable.h b/arch/xtensa/include/asm/pgtable.h
> index fc7a14884c6c..d72632d9c53c 100644
> --- a/arch/xtensa/include/asm/pgtable.h
> +++ b/arch/xtensa/include/asm/pgtable.h
> @@ -262,7 +262,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   	{ pte_val(pte) |= _PAGE_WRITABLE; return pte; }
>   
>   #define pgprot_noncached(prot) \
> diff --git a/include/asm-generic/hugetlb.h b/include/asm-generic/hugetlb.h
> index d7f6335d3999..e86c830728de 100644
> --- a/include/asm-generic/hugetlb.h
> +++ b/include/asm-generic/hugetlb.h
> @@ -20,9 +20,9 @@ static inline unsigned long huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   #ifndef __HAVE_ARCH_HUGE_PTE_WRPROTECT
> diff --git a/include/linux/mm.h b/include/linux/mm.h
> index 1f79667824eb..af652444fbba 100644
> --- a/include/linux/mm.h
> +++ b/include/linux/mm.h
> @@ -1163,7 +1163,7 @@ void free_compound_page(struct page *page);
>   static inline pte_t maybe_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	return pte;
>   }
>   
> diff --git a/mm/debug_vm_pgtable.c b/mm/debug_vm_pgtable.c
> index af59cc7bd307..7bc5592900bc 100644
> --- a/mm/debug_vm_pgtable.c
> +++ b/mm/debug_vm_pgtable.c
> @@ -109,10 +109,10 @@ static void __init pte_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pte_same(pte, pte));
>   	WARN_ON(!pte_young(pte_mkyoung(pte_mkold(pte))));
>   	WARN_ON(!pte_dirty(pte_mkdirty(pte_mkclean(pte))));
> -	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte))));
> +	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte), args->vma)));
>   	WARN_ON(pte_young(pte_mkold(pte_mkyoung(pte))));
>   	WARN_ON(pte_dirty(pte_mkclean(pte_mkdirty(pte))));
> -	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte))));
> +	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte, args->vma))));
>   	WARN_ON(pte_dirty(pte_wrprotect(pte_mkclean(pte))));
>   	WARN_ON(!pte_dirty(pte_wrprotect(pte_mkdirty(pte))));
>   }
> @@ -153,7 +153,7 @@ static void __init pte_advanced_tests(struct pgtable_debug_args *args)
>   	pte = pte_mkclean(pte);
>   	set_pte_at(args->mm, args->vaddr, args->ptep, pte);
>   	flush_dcache_page(page);
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, args->vma);
>   	pte = pte_mkdirty(pte);
>   	ptep_set_access_flags(args->vma, args->vaddr, args->ptep, pte, 1);
>   	pte = ptep_get(args->ptep);
> @@ -199,10 +199,10 @@ static void __init pmd_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pmd_same(pmd, pmd));
>   	WARN_ON(!pmd_young(pmd_mkyoung(pmd_mkold(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_mkdirty(pmd_mkclean(pmd))));
> -	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd))));
> +	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd), args->vma)));
>   	WARN_ON(pmd_young(pmd_mkold(pmd_mkyoung(pmd))));
>   	WARN_ON(pmd_dirty(pmd_mkclean(pmd_mkdirty(pmd))));
> -	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd))));
> +	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd, args->vma))));
>   	WARN_ON(pmd_dirty(pmd_wrprotect(pmd_mkclean(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_wrprotect(pmd_mkdirty(pmd))));
>   	/*
> @@ -253,7 +253,7 @@ static void __init pmd_advanced_tests(struct pgtable_debug_args *args)
>   	pmd = pmd_mkclean(pmd);
>   	set_pmd_at(args->mm, vaddr, args->pmdp, pmd);
>   	flush_dcache_page(page);
> -	pmd = pmd_mkwrite(pmd);
> +	pmd = pmd_mkwrite(pmd, args->vma);
>   	pmd = pmd_mkdirty(pmd);
>   	pmdp_set_access_flags(args->vma, vaddr, args->pmdp, pmd, 1);
>   	pmd = READ_ONCE(*args->pmdp);
> @@ -928,8 +928,8 @@ static void __init hugetlb_basic_tests(struct pgtable_debug_args *args)
>   	pte = mk_huge_pte(page, args->page_prot);
>   
>   	WARN_ON(!huge_pte_dirty(huge_pte_mkdirty(pte)));
> -	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte))));
> -	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte))));
> +	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte), args->vma)));
> +	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte, args->vma))));
>   
>   #ifdef CONFIG_ARCH_WANT_GENERAL_HUGETLB
>   	pte = pfn_pte(args->fixed_pmd_pfn, args->page_prot);
> diff --git a/mm/huge_memory.c b/mm/huge_memory.c
> index 4fc43859e59a..aaf815838144 100644
> --- a/mm/huge_memory.c
> +++ b/mm/huge_memory.c
> @@ -555,7 +555,7 @@ __setup("transparent_hugepage=", setup_transparent_hugepage);
>   pmd_t maybe_pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	return pmd;
>   }
>   
> @@ -1580,7 +1580,7 @@ vm_fault_t do_huge_pmd_numa_page(struct vm_fault *vmf)
>   	pmd = pmd_modify(oldpmd, vma->vm_page_prot);
>   	pmd = pmd_mkyoung(pmd);
>   	if (writable)
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	set_pmd_at(vma->vm_mm, haddr, vmf->pmd, pmd);
>   	update_mmu_cache_pmd(vma, vmf->address, vmf->pmd);
>   	spin_unlock(vmf->ptl);
> @@ -1926,7 +1926,7 @@ int change_huge_pmd(struct mmu_gather *tlb, struct vm_area_struct *vma,
>   	/* See change_pte_range(). */
>   	if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) && !pmd_write(entry) &&
>   	    can_change_pmd_writable(vma, addr, entry))
> -		entry = pmd_mkwrite(entry);
> +		entry = pmd_mkwrite(entry, vma);
>   
>   	ret = HPAGE_PMD_NR;
>   	set_pmd_at(mm, addr, pmd, entry);
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 07abcb6eb203..6af471bdcff8 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -4900,7 +4900,7 @@ static pte_t make_huge_pte(struct vm_area_struct *vma, struct page *page,
>   
>   	if (writable) {
>   		entry = huge_pte_mkwrite(huge_pte_mkdirty(mk_huge_pte(page,
> -					 vma->vm_page_prot)));
> +					 vma->vm_page_prot)), vma);
>   	} else {
>   		entry = huge_pte_wrprotect(mk_huge_pte(page,
>   					   vma->vm_page_prot));
> @@ -4916,7 +4916,7 @@ static void set_huge_ptep_writable(struct vm_area_struct *vma,
>   {
>   	pte_t entry;
>   
> -	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)));
> +	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)), vma);
>   	if (huge_ptep_set_access_flags(vma, address, ptep, entry, 1))
>   		update_mmu_cache(vma, address, ptep);
>   }
> diff --git a/mm/memory.c b/mm/memory.c
> index f456f3b5049c..d0972d2d6f36 100644
> --- a/mm/memory.c
> +++ b/mm/memory.c
> @@ -4067,7 +4067,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
>   	entry = mk_pte(&folio->page, vma->vm_page_prot);
>   	entry = pte_sw_mkyoung(entry);
>   	if (vma->vm_flags & VM_WRITE)
> -		entry = pte_mkwrite(pte_mkdirty(entry));
> +		entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   
>   	vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, vmf->address,
>   			&vmf->ptl);
> @@ -4755,7 +4755,7 @@ static vm_fault_t do_numa_page(struct vm_fault *vmf)
>   	pte = pte_modify(old_pte, vma->vm_page_prot);
>   	pte = pte_mkyoung(pte);
>   	if (writable)
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	ptep_modify_prot_commit(vma, vmf->address, vmf->pte, old_pte, pte);
>   	update_mmu_cache(vma, vmf->address, vmf->pte);
>   	pte_unmap_unlock(vmf->pte, vmf->ptl);
> diff --git a/mm/migrate_device.c b/mm/migrate_device.c
> index d30c9de60b0d..df3f5e9d5f76 100644
> --- a/mm/migrate_device.c
> +++ b/mm/migrate_device.c
> @@ -646,7 +646,7 @@ static void migrate_vma_insert_page(struct migrate_vma *migrate,
>   		}
>   		entry = mk_pte(page, vma->vm_page_prot);
>   		if (vma->vm_flags & VM_WRITE)
> -			entry = pte_mkwrite(pte_mkdirty(entry));
> +			entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   	}
>   
>   	ptep = pte_offset_map_lock(mm, pmdp, addr, &ptl);
> diff --git a/mm/mprotect.c b/mm/mprotect.c
> index 1d4843c97c2a..381163a41e88 100644
> --- a/mm/mprotect.c
> +++ b/mm/mprotect.c
> @@ -198,7 +198,7 @@ static long change_pte_range(struct mmu_gather *tlb,
>   			if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) &&
>   			    !pte_write(ptent) &&
>   			    can_change_pte_writable(vma, addr, ptent))
> -				ptent = pte_mkwrite(ptent);
> +				ptent = pte_mkwrite(ptent, vma);
>   
>   			ptep_modify_prot_commit(vma, addr, pte, oldpte, ptent);
>   			if (pte_needs_flush(oldpte, ptent))
> diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
> index 53c3d916ff66..3db6f87c0aca 100644
> --- a/mm/userfaultfd.c
> +++ b/mm/userfaultfd.c
> @@ -75,7 +75,7 @@ int mfill_atomic_install_pte(struct mm_struct *dst_mm, pmd_t *dst_pmd,
>   	if (page_in_cache && !vm_shared)
>   		writable = false;
>   	if (writable)
> -		_dst_pte = pte_mkwrite(_dst_pte);
> +		_dst_pte = pte_mkwrite(_dst_pte, dst_vma);
>   	if (wp_copy)
>   		_dst_pte = pte_mkuffd_wp(_dst_pte);
>   
_______________________________________________
linux-snps-arc mailing list
linux-snps-arc@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-snps-arc

WARNING: multiple messages have this Message-ID (diff)
From: Christophe Leroy <christophe.leroy@csgroup.eu>
To: Rick Edgecombe <rick.p.edgecombe@intel.com>,
	"x86@kernel.org" <x86@kernel.org>,
	"H . Peter Anvin" <hpa@zytor.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Ingo Molnar <mingo@redhat.com>,
	"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"linux-doc@vger.kernel.org" <linux-doc@vger.kernel.org>,
	"linux-mm@kvack.org" <linux-mm@kvack.org>,
	"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
	"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
	Arnd Bergmann <arnd@arndb.de>, Andy Lutomirski <luto@kernel.org>,
	Balbir Singh <bsingharora@gmail.com>,
	Borislav Petkov <bp@alien8.de>,
	Cyrill Gorcunov <gorcunov@gmail.com>,
	Dave Hansen <dave.hansen@linux.intel.com>,
	Eugene Syromiatnikov <esyr@redhat.com>,
	Florian Weimer <fweimer@redhat.com>,
	"H . J . Lu" <hjl.tools@gmail.com>, Jann Horn <jannh@google.com>,
	Jonathan Corbet <corbet@lwn.net>,
	Kees Cook <keescook@chromium.org>,
	Mike Kravetz <mike.kravetz@oracle.com>,
	Nadav Amit <nadav.amit@gmail.com>,
	Oleg Nesterov <oleg@redhat.com>, Pavel Machek <pavel@ucw.cz>,
	Peter Zijlstra <peterz@infradead.org>,
	Randy Dunlap <rdunlap@infradead.org>,
	Weijiang Yang <weijiang.yang@intel.com>,
	"Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>,
	John Allen <john.allen@amd.com>,
	"kcc@google.com" <kcc@google.com>,
	"eranian@google.com" <eranian@google.com>,
	"rppt@kernel.org" <rppt@kernel.org>,
	"jamorris@linux.microsoft.com" <jamorris@linux.microsoft.com>,
	"dethoma@microsoft.com" <dethoma@microsoft.com>,
	"akpm@linux-foundation.org" <akpm@linux-foundation.org>,
	"Andrew.Cooper3@citrix.com" <Andrew.Cooper3@citrix.com>,
	"christina.schimpe@intel.com" <christina.schimpe@intel.com>,
	"david@redhat.com" <david@redhat.com>,
	"debug@rivosinc.com" <debug@rivosinc.com>
Cc: "linux-alpha@vger.kernel.org" <linux-alpha@vger.kernel.org>,
	"linux-snps-arc@lists.infradead.org"
	<linux-snps-arc@lists.infradead.org>,
	"linux-arm-kernel@lists.infradead.org"
	<linux-arm-kernel@lists.infradead.org>,
	"linux-csky@vger.kernel.org" <linux-csky@vger.kernel.org>,
	"linux-hexagon@vger.kernel.org" <linux-hexagon@vger.kernel.org>,
	"linux-ia64@vger.kernel.org" <linux-ia64@vger.kernel.org>,
	"loongarch@lists.linux.dev" <loongarch@lists.linux.dev>,
	"linux-m68k@lists.linux-m68k.org"
	<linux-m68k@lists.linux-m68k.org>,
	Michal Simek <monstr@monstr.eu>,
	Dinh Nguyen <dinguyen@kernel.org>,
	"linux-mips@vger.kernel.org" <linux-mips@vger.kernel.org>,
	"linux-openrisc@vger.kernel.org" <linux-openrisc@vger.kernel.org>,
	"linux-parisc@vger.kernel.org" <linux-parisc@vger.kernel.org>,
	"linuxppc-dev@lists.ozlabs.org" <linuxppc-dev@lists.ozlabs.org>,
	"linux-riscv@lists.infradead.org"
	<linux-riscv@lists.infradead.org>,
	"linux-s390@vger.kernel.org" <linux-s390@vger.kernel.org>,
	"linux-sh@vger.kernel.org" <linux-sh@vger.kernel.org>,
	"sparclinux@vger.kernel.org" <sparclinux@vger.kernel.org>,
	"linux-um@lists.infradead.org" <linux-um@lists.infradead.org>,
	"xen-devel@lists.xenproject.org" <xen-devel@lists.xenproject.org>
Subject: Re: [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA
Date: Wed, 1 Mar 2023 07:03:23 +0000	[thread overview]
Message-ID: <1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu> (raw)
In-Reply-To: <20230227222957.24501-14-rick.p.edgecombe@intel.com>



Le 27/02/2023 à 23:29, Rick Edgecombe a écrit :
> The x86 Control-flow Enforcement Technology (CET) feature includes a new
> type of memory called shadow stack. This shadow stack memory has some
> unusual properties, which requires some core mm changes to function
> properly.
> 
> One of these unusual properties is that shadow stack memory is writable,
> but only in limited ways. These limits are applied via a specific PTE
> bit combination. Nevertheless, the memory is writable, and core mm code
> will need to apply the writable permissions in the typical paths that
> call pte_mkwrite().
> 
> In addition to VM_WRITE, the shadow stack VMA's will have a flag denoting
> that they are special shadow stack flavor of writable memory. So make
> pte_mkwrite() take a VMA, so that the x86 implementation of it can know to
> create regular writable memory or shadow stack memory.
> 
> Apply the same changes for pmd_mkwrite() and huge_pte_mkwrite().

I'm not sure it is a good idea to add a second argument to 
pte_mkwrite(). All pte_mkxxxx() only take a pte and nothing else.

I think you should do the same as commit d9ed9faac283 ("mm: add new 
arch_make_huge_pte() method for tile support")

Christophe

> 
> No functional change.
> 
> Cc: linux-doc@vger.kernel.org
> Cc: linux-kernel@vger.kernel.org
> Cc: linux-alpha@vger.kernel.org
> Cc: linux-snps-arc@lists.infradead.org
> Cc: linux-arm-kernel@lists.infradead.org
> Cc: linux-csky@vger.kernel.org
> Cc: linux-hexagon@vger.kernel.org
> Cc: linux-ia64@vger.kernel.org
> Cc: loongarch@lists.linux.dev
> Cc: linux-m68k@lists.linux-m68k.org
> Cc: Michal Simek <monstr@monstr.eu>
> Cc: Dinh Nguyen <dinguyen@kernel.org>
> Cc: linux-mips@vger.kernel.org
> Cc: linux-openrisc@vger.kernel.org
> Cc: linux-parisc@vger.kernel.org
> Cc: linuxppc-dev@lists.ozlabs.org
> Cc: linux-riscv@lists.infradead.org
> Cc: linux-s390@vger.kernel.org
> Cc: linux-sh@vger.kernel.org
> Cc: sparclinux@vger.kernel.org
> Cc: linux-um@lists.infradead.org
> Cc: xen-devel@lists.xenproject.org
> Cc: linux-arch@vger.kernel.org
> Cc: linux-mm@kvack.org
> Tested-by: Pengfei Xu <pengfei.xu@intel.com>
> Tested-by: John Allen <john.allen@amd.com>
> Tested-by: Kees Cook <keescook@chromium.org>
> Acked-by: Mike Rapoport (IBM) <rppt@kernel.org>
> Acked-by: Michael Ellerman <mpe@ellerman.id.au>
> Acked-by: David Hildenbrand <david@redhat.com>
> Reviewed-by: Kees Cook <keescook@chromium.org>
> Suggested-by: David Hildenbrand <david@redhat.com>
> Signed-off-by: Rick Edgecombe <rick.p.edgecombe@intel.com>
> 
> ---
> Hi Non-x86 Arch’s,
> 
> x86 has a feature that allows for the creation of a special type of
> writable memory (shadow stack) that is only writable in limited specific
> ways. Previously, changes were proposed to core MM code to teach it to
> decide when to create normally writable memory or the special shadow stack
> writable memory, but David Hildenbrand suggested[0] to change
> pXX_mkwrite() to take a VMA, so awareness of shadow stack memory can be
> moved into x86 code.
> 
> Since pXX_mkwrite() is defined in every arch, it requires some tree-wide
> changes. So that is why you are seeing some patches out of a big x86
> series pop up in your arch mailing list. There is no functional change.
> After this refactor, the shadow stack series goes on to use the arch
> helpers to push shadow stack memory details inside arch/x86.
> 
> Testing was just 0-day build testing.
> 
> Hopefully that is enough context. Thanks!
> 
> [0] https://lore.kernel.org/lkml/0e29a2d0-08d8-bcd6-ff26-4bea0e4037b0@redhat.com/#t
> 
> v6:
>   - New patch
> ---
>   Documentation/mm/arch_pgtable_helpers.rst    |  9 ++++++---
>   arch/alpha/include/asm/pgtable.h             |  6 +++++-
>   arch/arc/include/asm/hugepage.h              |  2 +-
>   arch/arc/include/asm/pgtable-bits-arcv2.h    |  7 ++++++-
>   arch/arm/include/asm/pgtable-3level.h        |  7 ++++++-
>   arch/arm/include/asm/pgtable.h               |  2 +-
>   arch/arm64/include/asm/pgtable.h             |  4 ++--
>   arch/csky/include/asm/pgtable.h              |  2 +-
>   arch/hexagon/include/asm/pgtable.h           |  2 +-
>   arch/ia64/include/asm/pgtable.h              |  2 +-
>   arch/loongarch/include/asm/pgtable.h         |  4 ++--
>   arch/m68k/include/asm/mcf_pgtable.h          |  2 +-
>   arch/m68k/include/asm/motorola_pgtable.h     |  6 +++++-
>   arch/m68k/include/asm/sun3_pgtable.h         |  6 +++++-
>   arch/microblaze/include/asm/pgtable.h        |  2 +-
>   arch/mips/include/asm/pgtable.h              |  6 +++---
>   arch/nios2/include/asm/pgtable.h             |  2 +-
>   arch/openrisc/include/asm/pgtable.h          |  2 +-
>   arch/parisc/include/asm/pgtable.h            |  6 +++++-
>   arch/powerpc/include/asm/book3s/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/book3s/64/pgtable.h |  4 ++--
>   arch/powerpc/include/asm/nohash/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/nohash/32/pte-8xx.h |  2 +-
>   arch/powerpc/include/asm/nohash/64/pgtable.h |  2 +-
>   arch/riscv/include/asm/pgtable.h             |  6 +++---
>   arch/s390/include/asm/hugetlb.h              |  4 ++--
>   arch/s390/include/asm/pgtable.h              |  4 ++--
>   arch/sh/include/asm/pgtable_32.h             | 10 ++++++++--
>   arch/sparc/include/asm/pgtable_32.h          |  2 +-
>   arch/sparc/include/asm/pgtable_64.h          |  6 +++---
>   arch/um/include/asm/pgtable.h                |  2 +-
>   arch/x86/include/asm/pgtable.h               |  6 ++++--
>   arch/xtensa/include/asm/pgtable.h            |  2 +-
>   include/asm-generic/hugetlb.h                |  4 ++--
>   include/linux/mm.h                           |  2 +-
>   mm/debug_vm_pgtable.c                        | 16 ++++++++--------
>   mm/huge_memory.c                             |  6 +++---
>   mm/hugetlb.c                                 |  4 ++--
>   mm/memory.c                                  |  4 ++--
>   mm/migrate_device.c                          |  2 +-
>   mm/mprotect.c                                |  2 +-
>   mm/userfaultfd.c                             |  2 +-
>   42 files changed, 106 insertions(+), 69 deletions(-)
> 
> diff --git a/Documentation/mm/arch_pgtable_helpers.rst b/Documentation/mm/arch_pgtable_helpers.rst
> index 30d9a09f01f4..78ac3ff2fe1d 100644
> --- a/Documentation/mm/arch_pgtable_helpers.rst
> +++ b/Documentation/mm/arch_pgtable_helpers.rst
> @@ -46,7 +46,8 @@ PTE Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pte_mkclean               | Creates a clean PTE                              |
>   +---------------------------+--------------------------------------------------+
> -| pte_mkwrite               | Creates a writable PTE                           |
> +| pte_mkwrite               | Creates a writable PTE of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pte_wrprotect             | Creates a write protected PTE                    |
>   +---------------------------+--------------------------------------------------+
> @@ -118,7 +119,8 @@ PMD Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pmd_mkclean               | Creates a clean PMD                              |
>   +---------------------------+--------------------------------------------------+
> -| pmd_mkwrite               | Creates a writable PMD                           |
> +| pmd_mkwrite               | Creates a writable PMD of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pmd_wrprotect             | Creates a write protected PMD                    |
>   +---------------------------+--------------------------------------------------+
> @@ -222,7 +224,8 @@ HugeTLB Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_mkdirty          | Creates a dirty HugeTLB                          |
>   +---------------------------+--------------------------------------------------+
> -| huge_pte_mkwrite          | Creates a writable HugeTLB                       |
> +| huge_pte_mkwrite          | Creates a writable HugeTLB of the type specified |
> +|                           | by the VMA.                                      |
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_wrprotect        | Creates a write protected HugeTLB                |
>   +---------------------------+--------------------------------------------------+
> diff --git a/arch/alpha/include/asm/pgtable.h b/arch/alpha/include/asm/pgtable.h
> index ba43cb841d19..fb5d207c2a89 100644
> --- a/arch/alpha/include/asm/pgtable.h
> +++ b/arch/alpha/include/asm/pgtable.h
> @@ -256,9 +256,13 @@ extern inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   extern inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~(__DIRTY_BITS); return pte; }
>   extern inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~(__ACCESS_BITS); return pte; }
> -extern inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= __DIRTY_BITS; return pte; }
>   extern inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= __ACCESS_BITS; return pte; }
> +extern inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_FOW;
> +	return pte;
> +}
>   
>   /*
>    * The smp_rmb() in the following functions are required to order the load of
> diff --git a/arch/arc/include/asm/hugepage.h b/arch/arc/include/asm/hugepage.h
> index 5001b796fb8d..223a96967188 100644
> --- a/arch/arc/include/asm/hugepage.h
> +++ b/arch/arc/include/asm/hugepage.h
> @@ -21,7 +21,7 @@ static inline pmd_t pte_pmd(pte_t pte)
>   }
>   
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/arc/include/asm/pgtable-bits-arcv2.h b/arch/arc/include/asm/pgtable-bits-arcv2.h
> index 6e9f8ca6d6a1..a5b8bc955015 100644
> --- a/arch/arc/include/asm/pgtable-bits-arcv2.h
> +++ b/arch/arc/include/asm/pgtable-bits-arcv2.h
> @@ -87,7 +87,6 @@
>   
>   PTE_BIT_FUNC(mknotpresent,     &= ~(_PAGE_PRESENT));
>   PTE_BIT_FUNC(wrprotect,	&= ~(_PAGE_WRITE));
> -PTE_BIT_FUNC(mkwrite,	|= (_PAGE_WRITE));
>   PTE_BIT_FUNC(mkclean,	&= ~(_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkdirty,	|= (_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkold,	&= ~(_PAGE_ACCESSED));
> @@ -95,6 +94,12 @@ PTE_BIT_FUNC(mkyoung,	|= (_PAGE_ACCESSED));
>   PTE_BIT_FUNC(mkspecial,	|= (_PAGE_SPECIAL));
>   PTE_BIT_FUNC(mkhuge,	|= (_PAGE_HW_SZ));
>   
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= (_PAGE_WRITE);
> +	return pte;
> +}
> +
>   static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
>   {
>   	return __pte((pte_val(pte) & _PAGE_CHG_MASK) | pgprot_val(newprot));
> diff --git a/arch/arm/include/asm/pgtable-3level.h b/arch/arm/include/asm/pgtable-3level.h
> index 106049791500..df071a807610 100644
> --- a/arch/arm/include/asm/pgtable-3level.h
> +++ b/arch/arm/include/asm/pgtable-3level.h
> @@ -202,11 +202,16 @@ static inline pmd_t pmd_##fn(pmd_t pmd) { pmd_val(pmd) op; return pmd; }
>   
>   PMD_BIT_FUNC(wrprotect,	|= L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkold,	&= ~PMD_SECT_AF);
> -PMD_BIT_FUNC(mkwrite,   &= ~L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkdirty,   |= L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkclean,   &= ~L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkyoung,   |= PMD_SECT_AF);
>   
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
> +{
> +	pmd_val(pmd) |= L_PMD_SECT_RDONLY;
> +	return pmd;
> +}
> +
>   #define pmd_mkhuge(pmd)		(__pmd(pmd_val(pmd) & ~PMD_TABLE_BIT))
>   
>   #define pmd_pfn(pmd)		(((pmd_val(pmd) & PMD_MASK) & PHYS_MASK) >> PAGE_SHIFT)
> diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
> index a58ccbb406ad..39ad1ae1308d 100644
> --- a/arch/arm/include/asm/pgtable.h
> +++ b/arch/arm/include/asm/pgtable.h
> @@ -227,7 +227,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   	return set_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return clear_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
> diff --git a/arch/arm64/include/asm/pgtable.h b/arch/arm64/include/asm/pgtable.h
> index cccf8885792e..913bf370f74a 100644
> --- a/arch/arm64/include/asm/pgtable.h
> +++ b/arch/arm64/include/asm/pgtable.h
> @@ -187,7 +187,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -492,7 +492,7 @@ static inline int pmd_trans_huge(pmd_t pmd)
>   #define pmd_cont(pmd)		pte_cont(pmd_pte(pmd))
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/csky/include/asm/pgtable.h b/arch/csky/include/asm/pgtable.h
> index d4042495febc..c2f92c991e37 100644
> --- a/arch/csky/include/asm/pgtable.h
> +++ b/arch/csky/include/asm/pgtable.h
> @@ -176,7 +176,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> diff --git a/arch/hexagon/include/asm/pgtable.h b/arch/hexagon/include/asm/pgtable.h
> index 59393613d086..14ab9c789c0e 100644
> --- a/arch/hexagon/include/asm/pgtable.h
> +++ b/arch/hexagon/include/asm/pgtable.h
> @@ -300,7 +300,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   }
>   
>   /* pte_mkwrite - mark page as writable */
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/ia64/include/asm/pgtable.h b/arch/ia64/include/asm/pgtable.h
> index 21c97e31a28a..f879dd626da6 100644
> --- a/arch/ia64/include/asm/pgtable.h
> +++ b/arch/ia64/include/asm/pgtable.h
> @@ -268,7 +268,7 @@ ia64_phys_addr_valid (unsigned long addr)
>    * access rights:
>    */
>   #define pte_wrprotect(pte)	(__pte(pte_val(pte) & ~_PAGE_AR_RW))
> -#define pte_mkwrite(pte)	(__pte(pte_val(pte) | _PAGE_AR_RW))
> +#define pte_mkwrite(pte, vma)	(__pte(pte_val(pte) | _PAGE_AR_RW))
>   #define pte_mkold(pte)		(__pte(pte_val(pte) & ~_PAGE_A))
>   #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_A))
>   #define pte_mkclean(pte)	(__pte(pte_val(pte) & ~_PAGE_D))
> diff --git a/arch/loongarch/include/asm/pgtable.h b/arch/loongarch/include/asm/pgtable.h
> index d28fb9dbec59..ebf645f40298 100644
> --- a/arch/loongarch/include/asm/pgtable.h
> +++ b/arch/loongarch/include/asm/pgtable.h
> @@ -390,7 +390,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -490,7 +490,7 @@ static inline int pmd_write(pmd_t pmd)
>   	return !!(pmd_val(pmd) & _PAGE_WRITE);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/m68k/include/asm/mcf_pgtable.h b/arch/m68k/include/asm/mcf_pgtable.h
> index 13741c1245e1..37d77e055016 100644
> --- a/arch/m68k/include/asm/mcf_pgtable.h
> +++ b/arch/m68k/include/asm/mcf_pgtable.h
> @@ -211,7 +211,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= CF_PAGE_WRITABLE;
>   	return pte;
> diff --git a/arch/m68k/include/asm/motorola_pgtable.h b/arch/m68k/include/asm/motorola_pgtable.h
> index ec0dc19ab834..c4e8eb76286d 100644
> --- a/arch/m68k/include/asm/motorola_pgtable.h
> +++ b/arch/m68k/include/asm/motorola_pgtable.h
> @@ -155,7 +155,6 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~_PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)
> @@ -168,6 +167,11 @@ static inline pte_t pte_mkcache(pte_t pte)
>   	pte_val(pte) = (pte_val(pte) & _CACHEMASK040) | m68k_supervisor_cachemode;
>   	return pte;
>   }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_RONLY;
> +	return pte;
> +}
>   
>   #define swapper_pg_dir kernel_pg_dir
>   extern pgd_t kernel_pg_dir[128];
> diff --git a/arch/m68k/include/asm/sun3_pgtable.h b/arch/m68k/include/asm/sun3_pgtable.h
> index e582b0484a55..2a06bea51a1e 100644
> --- a/arch/m68k/include/asm/sun3_pgtable.h
> +++ b/arch/m68k/include/asm/sun3_pgtable.h
> @@ -143,10 +143,14 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & SUN3_PAGE_ACCESS
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_NOCACHE; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= SUN3_PAGE_WRITEABLE;
> +	return pte;
> +}
>   // use this version when caches work...
>   //static inline pte_t pte_mkcache(pte_t pte)	{ pte_val(pte) &= SUN3_PAGE_NOCACHE; return pte; }
>   // until then, use:
> diff --git a/arch/microblaze/include/asm/pgtable.h b/arch/microblaze/include/asm/pgtable.h
> index d1b8272abcd9..5b83e82f8d7e 100644
> --- a/arch/microblaze/include/asm/pgtable.h
> +++ b/arch/microblaze/include/asm/pgtable.h
> @@ -266,7 +266,7 @@ static inline pte_t pte_mkread(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER; return pte; }
>   static inline pte_t pte_mkexec(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER | _PAGE_EXEC; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte) \
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma) \
>   	{ pte_val(pte) |= _PAGE_RW; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
> diff --git a/arch/mips/include/asm/pgtable.h b/arch/mips/include/asm/pgtable.h
> index 791389bf3c12..06efd567144a 100644
> --- a/arch/mips/include/asm/pgtable.h
> +++ b/arch/mips/include/asm/pgtable.h
> @@ -309,7 +309,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte.pte_low |= _PAGE_WRITE;
>   	if (pte.pte_low & _PAGE_MODIFIED) {
> @@ -364,7 +364,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -626,7 +626,7 @@ static inline pmd_t pmd_wrprotect(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/nios2/include/asm/pgtable.h b/arch/nios2/include/asm/pgtable.h
> index 0f5c2564e9f5..edd458518e0e 100644
> --- a/arch/nios2/include/asm/pgtable.h
> +++ b/arch/nios2/include/asm/pgtable.h
> @@ -129,7 +129,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/openrisc/include/asm/pgtable.h b/arch/openrisc/include/asm/pgtable.h
> index 3eb9b9555d0d..fd40aec189d1 100644
> --- a/arch/openrisc/include/asm/pgtable.h
> +++ b/arch/openrisc/include/asm/pgtable.h
> @@ -250,7 +250,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/parisc/include/asm/pgtable.h b/arch/parisc/include/asm/pgtable.h
> index e2950f5db7c9..89f62137e67f 100644
> --- a/arch/parisc/include/asm/pgtable.h
> +++ b/arch/parisc/include/asm/pgtable.h
> @@ -331,8 +331,12 @@ static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; retu
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~_PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= _PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkspecial(pte_t pte)	{ pte_val(pte) |= _PAGE_SPECIAL; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= _PAGE_WRITE;
> +	return pte;
> +}
>   
>   /*
>    * Huge pte definitions.
> diff --git a/arch/powerpc/include/asm/book3s/32/pgtable.h b/arch/powerpc/include/asm/book3s/32/pgtable.h
> index 7bf1fe7297c6..10d9a1d2aca9 100644
> --- a/arch/powerpc/include/asm/book3s/32/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/32/pgtable.h
> @@ -498,7 +498,7 @@ static inline pte_t pte_mkpte(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h
> index 4acc9690f599..be0636522d36 100644
> --- a/arch/powerpc/include/asm/book3s/64/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/64/pgtable.h
> @@ -600,7 +600,7 @@ static inline pte_t pte_mkexec(pte_t pte)
>   	return __pte_raw(pte_raw(pte) | cpu_to_be64(_PAGE_EXEC));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	/*
>   	 * write implies read, hence set both
> @@ -1071,7 +1071,7 @@ static inline pte_t *pmdp_ptep(pmd_t *pmd)
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   
>   #ifdef CONFIG_HAVE_ARCH_SOFT_DIRTY
>   #define pmd_soft_dirty(pmd)    pte_soft_dirty(pmd_pte(pmd))
> diff --git a/arch/powerpc/include/asm/nohash/32/pgtable.h b/arch/powerpc/include/asm/nohash/32/pgtable.h
> index fec56d965f00..7bfbcb9ba55b 100644
> --- a/arch/powerpc/include/asm/nohash/32/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/32/pgtable.h
> @@ -171,7 +171,7 @@ void unmap_kernel_page(unsigned long va);
>   	do { pte_update(mm, addr, ptep, ~0, 0, 0); } while (0)
>   
>   #ifndef pte_mkwrite
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/32/pte-8xx.h b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> index 1a89ebdc3acc..f32450eb270a 100644
> --- a/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> +++ b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> @@ -101,7 +101,7 @@ static inline int pte_write(pte_t pte)
>   
>   #define pte_write pte_write
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) & ~_PAGE_RO);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/64/pgtable.h b/arch/powerpc/include/asm/nohash/64/pgtable.h
> index 287e25864ffa..589009555877 100644
> --- a/arch/powerpc/include/asm/nohash/64/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/64/pgtable.h
> @@ -85,7 +85,7 @@
>   #ifndef __ASSEMBLY__
>   /* pte_clear moved to later in this file */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
> index d8d8de0ded99..fed1b81fbe07 100644
> --- a/arch/riscv/include/asm/pgtable.h
> +++ b/arch/riscv/include/asm/pgtable.h
> @@ -338,7 +338,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   
>   /* static inline pte_t pte_mkread(pte_t pte) */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_WRITE);
>   }
> @@ -624,9 +624,9 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pte_pmd(pte_mkyoung(pmd_pte(pmd)));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
> -	return pte_pmd(pte_mkwrite(pmd_pte(pmd)));
> +	return pte_pmd(pte_mkwrite(pmd_pte(pmd), vma));
>   }
>   
>   static inline pmd_t pmd_wrprotect(pmd_t pmd)
> diff --git a/arch/s390/include/asm/hugetlb.h b/arch/s390/include/asm/hugetlb.h
> index ccdbccfde148..558f7eef9c4d 100644
> --- a/arch/s390/include/asm/hugetlb.h
> +++ b/arch/s390/include/asm/hugetlb.h
> @@ -102,9 +102,9 @@ static inline int huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   static inline pte_t huge_pte_mkdirty(pte_t pte)
> diff --git a/arch/s390/include/asm/pgtable.h b/arch/s390/include/asm/pgtable.h
> index deeb918cae1d..8f2c743da0eb 100644
> --- a/arch/s390/include/asm/pgtable.h
> +++ b/arch/s390/include/asm/pgtable.h
> @@ -1013,7 +1013,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -1499,7 +1499,7 @@ static inline pmd_t pmd_mkwrite_kernel(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_mkwrite_kernel(pmd);
>   }
> diff --git a/arch/sh/include/asm/pgtable_32.h b/arch/sh/include/asm/pgtable_32.h
> index 21952b094650..9f2dcb9eafc8 100644
> --- a/arch/sh/include/asm/pgtable_32.h
> +++ b/arch/sh/include/asm/pgtable_32.h
> @@ -351,6 +351,12 @@ static inline void set_pte(pte_t *ptep, pte_t pte)
>   
>   #define PTE_BIT_FUNC(h,fn,op) \
>   static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
> +#define PTE_BIT_FUNC_VMA(h,fn,op) \
> +static inline pte_t pte_##fn(pte_t pte, struct vm_area_struct *vma) \
> +{ \
> +	pte.pte_##h op; \
> +	return pte; \
> +}
>   
>   #ifdef CONFIG_X2TLB
>   /*
> @@ -359,11 +365,11 @@ static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
>    * kernel permissions), we attempt to couple them a bit more sanely here.
>    */
>   PTE_BIT_FUNC(high, wrprotect, &= ~(_PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE));
> -PTE_BIT_FUNC(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
> +PTE_BIT_FUNC_VMA(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
>   PTE_BIT_FUNC(high, mkhuge, |= _PAGE_SZHUGE);
>   #else
>   PTE_BIT_FUNC(low, wrprotect, &= ~_PAGE_RW);
> -PTE_BIT_FUNC(low, mkwrite, |= _PAGE_RW);
> +PTE_BIT_FUNC_VMA(low, mkwrite, |= _PAGE_RW);
>   PTE_BIT_FUNC(low, mkhuge, |= _PAGE_SZHUGE);
>   #endif
>   
> diff --git a/arch/sparc/include/asm/pgtable_32.h b/arch/sparc/include/asm/pgtable_32.h
> index d4330e3c57a6..3e8836179456 100644
> --- a/arch/sparc/include/asm/pgtable_32.h
> +++ b/arch/sparc/include/asm/pgtable_32.h
> @@ -241,7 +241,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return __pte(pte_val(pte) & ~SRMMU_REF);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | SRMMU_WRITE);
>   }
> diff --git a/arch/sparc/include/asm/pgtable_64.h b/arch/sparc/include/asm/pgtable_64.h
> index 2dc8d4641734..c5cd5c03f557 100644
> --- a/arch/sparc/include/asm/pgtable_64.h
> +++ b/arch/sparc/include/asm/pgtable_64.h
> @@ -466,7 +466,7 @@ static inline pte_t pte_mkclean(pte_t pte)
>   	return __pte(val);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	unsigned long val = pte_val(pte), mask;
>   
> @@ -756,11 +756,11 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return __pmd(pte_val(pte));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pte_t pte = __pte(pmd_val(pmd));
>   
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, vma);
>   
>   	return __pmd(pte_val(pte));
>   }
> diff --git a/arch/um/include/asm/pgtable.h b/arch/um/include/asm/pgtable.h
> index a70d1618eb35..963479c133b7 100644
> --- a/arch/um/include/asm/pgtable.h
> +++ b/arch/um/include/asm/pgtable.h
> @@ -207,7 +207,7 @@ static inline pte_t pte_mkyoung(pte_t pte)
>   	return(pte);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (unlikely(pte_get_bits(pte,  _PAGE_RW)))
>   		return pte;
> diff --git a/arch/x86/include/asm/pgtable.h b/arch/x86/include/asm/pgtable.h
> index 3607f2572f9e..66c514808276 100644
> --- a/arch/x86/include/asm/pgtable.h
> +++ b/arch/x86/include/asm/pgtable.h
> @@ -369,7 +369,9 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte_set_flags(pte, _PAGE_RW);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +struct vm_area_struct;
> +
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -470,7 +472,7 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pmd_set_flags(pmd, _PAGE_ACCESSED);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_set_flags(pmd, _PAGE_RW);
>   }
> diff --git a/arch/xtensa/include/asm/pgtable.h b/arch/xtensa/include/asm/pgtable.h
> index fc7a14884c6c..d72632d9c53c 100644
> --- a/arch/xtensa/include/asm/pgtable.h
> +++ b/arch/xtensa/include/asm/pgtable.h
> @@ -262,7 +262,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   	{ pte_val(pte) |= _PAGE_WRITABLE; return pte; }
>   
>   #define pgprot_noncached(prot) \
> diff --git a/include/asm-generic/hugetlb.h b/include/asm-generic/hugetlb.h
> index d7f6335d3999..e86c830728de 100644
> --- a/include/asm-generic/hugetlb.h
> +++ b/include/asm-generic/hugetlb.h
> @@ -20,9 +20,9 @@ static inline unsigned long huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   #ifndef __HAVE_ARCH_HUGE_PTE_WRPROTECT
> diff --git a/include/linux/mm.h b/include/linux/mm.h
> index 1f79667824eb..af652444fbba 100644
> --- a/include/linux/mm.h
> +++ b/include/linux/mm.h
> @@ -1163,7 +1163,7 @@ void free_compound_page(struct page *page);
>   static inline pte_t maybe_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	return pte;
>   }
>   
> diff --git a/mm/debug_vm_pgtable.c b/mm/debug_vm_pgtable.c
> index af59cc7bd307..7bc5592900bc 100644
> --- a/mm/debug_vm_pgtable.c
> +++ b/mm/debug_vm_pgtable.c
> @@ -109,10 +109,10 @@ static void __init pte_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pte_same(pte, pte));
>   	WARN_ON(!pte_young(pte_mkyoung(pte_mkold(pte))));
>   	WARN_ON(!pte_dirty(pte_mkdirty(pte_mkclean(pte))));
> -	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte))));
> +	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte), args->vma)));
>   	WARN_ON(pte_young(pte_mkold(pte_mkyoung(pte))));
>   	WARN_ON(pte_dirty(pte_mkclean(pte_mkdirty(pte))));
> -	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte))));
> +	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte, args->vma))));
>   	WARN_ON(pte_dirty(pte_wrprotect(pte_mkclean(pte))));
>   	WARN_ON(!pte_dirty(pte_wrprotect(pte_mkdirty(pte))));
>   }
> @@ -153,7 +153,7 @@ static void __init pte_advanced_tests(struct pgtable_debug_args *args)
>   	pte = pte_mkclean(pte);
>   	set_pte_at(args->mm, args->vaddr, args->ptep, pte);
>   	flush_dcache_page(page);
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, args->vma);
>   	pte = pte_mkdirty(pte);
>   	ptep_set_access_flags(args->vma, args->vaddr, args->ptep, pte, 1);
>   	pte = ptep_get(args->ptep);
> @@ -199,10 +199,10 @@ static void __init pmd_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pmd_same(pmd, pmd));
>   	WARN_ON(!pmd_young(pmd_mkyoung(pmd_mkold(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_mkdirty(pmd_mkclean(pmd))));
> -	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd))));
> +	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd), args->vma)));
>   	WARN_ON(pmd_young(pmd_mkold(pmd_mkyoung(pmd))));
>   	WARN_ON(pmd_dirty(pmd_mkclean(pmd_mkdirty(pmd))));
> -	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd))));
> +	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd, args->vma))));
>   	WARN_ON(pmd_dirty(pmd_wrprotect(pmd_mkclean(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_wrprotect(pmd_mkdirty(pmd))));
>   	/*
> @@ -253,7 +253,7 @@ static void __init pmd_advanced_tests(struct pgtable_debug_args *args)
>   	pmd = pmd_mkclean(pmd);
>   	set_pmd_at(args->mm, vaddr, args->pmdp, pmd);
>   	flush_dcache_page(page);
> -	pmd = pmd_mkwrite(pmd);
> +	pmd = pmd_mkwrite(pmd, args->vma);
>   	pmd = pmd_mkdirty(pmd);
>   	pmdp_set_access_flags(args->vma, vaddr, args->pmdp, pmd, 1);
>   	pmd = READ_ONCE(*args->pmdp);
> @@ -928,8 +928,8 @@ static void __init hugetlb_basic_tests(struct pgtable_debug_args *args)
>   	pte = mk_huge_pte(page, args->page_prot);
>   
>   	WARN_ON(!huge_pte_dirty(huge_pte_mkdirty(pte)));
> -	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte))));
> -	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte))));
> +	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte), args->vma)));
> +	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte, args->vma))));
>   
>   #ifdef CONFIG_ARCH_WANT_GENERAL_HUGETLB
>   	pte = pfn_pte(args->fixed_pmd_pfn, args->page_prot);
> diff --git a/mm/huge_memory.c b/mm/huge_memory.c
> index 4fc43859e59a..aaf815838144 100644
> --- a/mm/huge_memory.c
> +++ b/mm/huge_memory.c
> @@ -555,7 +555,7 @@ __setup("transparent_hugepage=", setup_transparent_hugepage);
>   pmd_t maybe_pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	return pmd;
>   }
>   
> @@ -1580,7 +1580,7 @@ vm_fault_t do_huge_pmd_numa_page(struct vm_fault *vmf)
>   	pmd = pmd_modify(oldpmd, vma->vm_page_prot);
>   	pmd = pmd_mkyoung(pmd);
>   	if (writable)
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	set_pmd_at(vma->vm_mm, haddr, vmf->pmd, pmd);
>   	update_mmu_cache_pmd(vma, vmf->address, vmf->pmd);
>   	spin_unlock(vmf->ptl);
> @@ -1926,7 +1926,7 @@ int change_huge_pmd(struct mmu_gather *tlb, struct vm_area_struct *vma,
>   	/* See change_pte_range(). */
>   	if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) && !pmd_write(entry) &&
>   	    can_change_pmd_writable(vma, addr, entry))
> -		entry = pmd_mkwrite(entry);
> +		entry = pmd_mkwrite(entry, vma);
>   
>   	ret = HPAGE_PMD_NR;
>   	set_pmd_at(mm, addr, pmd, entry);
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 07abcb6eb203..6af471bdcff8 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -4900,7 +4900,7 @@ static pte_t make_huge_pte(struct vm_area_struct *vma, struct page *page,
>   
>   	if (writable) {
>   		entry = huge_pte_mkwrite(huge_pte_mkdirty(mk_huge_pte(page,
> -					 vma->vm_page_prot)));
> +					 vma->vm_page_prot)), vma);
>   	} else {
>   		entry = huge_pte_wrprotect(mk_huge_pte(page,
>   					   vma->vm_page_prot));
> @@ -4916,7 +4916,7 @@ static void set_huge_ptep_writable(struct vm_area_struct *vma,
>   {
>   	pte_t entry;
>   
> -	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)));
> +	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)), vma);
>   	if (huge_ptep_set_access_flags(vma, address, ptep, entry, 1))
>   		update_mmu_cache(vma, address, ptep);
>   }
> diff --git a/mm/memory.c b/mm/memory.c
> index f456f3b5049c..d0972d2d6f36 100644
> --- a/mm/memory.c
> +++ b/mm/memory.c
> @@ -4067,7 +4067,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
>   	entry = mk_pte(&folio->page, vma->vm_page_prot);
>   	entry = pte_sw_mkyoung(entry);
>   	if (vma->vm_flags & VM_WRITE)
> -		entry = pte_mkwrite(pte_mkdirty(entry));
> +		entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   
>   	vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, vmf->address,
>   			&vmf->ptl);
> @@ -4755,7 +4755,7 @@ static vm_fault_t do_numa_page(struct vm_fault *vmf)
>   	pte = pte_modify(old_pte, vma->vm_page_prot);
>   	pte = pte_mkyoung(pte);
>   	if (writable)
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	ptep_modify_prot_commit(vma, vmf->address, vmf->pte, old_pte, pte);
>   	update_mmu_cache(vma, vmf->address, vmf->pte);
>   	pte_unmap_unlock(vmf->pte, vmf->ptl);
> diff --git a/mm/migrate_device.c b/mm/migrate_device.c
> index d30c9de60b0d..df3f5e9d5f76 100644
> --- a/mm/migrate_device.c
> +++ b/mm/migrate_device.c
> @@ -646,7 +646,7 @@ static void migrate_vma_insert_page(struct migrate_vma *migrate,
>   		}
>   		entry = mk_pte(page, vma->vm_page_prot);
>   		if (vma->vm_flags & VM_WRITE)
> -			entry = pte_mkwrite(pte_mkdirty(entry));
> +			entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   	}
>   
>   	ptep = pte_offset_map_lock(mm, pmdp, addr, &ptl);
> diff --git a/mm/mprotect.c b/mm/mprotect.c
> index 1d4843c97c2a..381163a41e88 100644
> --- a/mm/mprotect.c
> +++ b/mm/mprotect.c
> @@ -198,7 +198,7 @@ static long change_pte_range(struct mmu_gather *tlb,
>   			if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) &&
>   			    !pte_write(ptent) &&
>   			    can_change_pte_writable(vma, addr, ptent))
> -				ptent = pte_mkwrite(ptent);
> +				ptent = pte_mkwrite(ptent, vma);
>   
>   			ptep_modify_prot_commit(vma, addr, pte, oldpte, ptent);
>   			if (pte_needs_flush(oldpte, ptent))
> diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
> index 53c3d916ff66..3db6f87c0aca 100644
> --- a/mm/userfaultfd.c
> +++ b/mm/userfaultfd.c
> @@ -75,7 +75,7 @@ int mfill_atomic_install_pte(struct mm_struct *dst_mm, pmd_t *dst_pmd,
>   	if (page_in_cache && !vm_shared)
>   		writable = false;
>   	if (writable)
> -		_dst_pte = pte_mkwrite(_dst_pte);
> +		_dst_pte = pte_mkwrite(_dst_pte, dst_vma);
>   	if (wp_copy)
>   		_dst_pte = pte_mkuffd_wp(_dst_pte);
>   
_______________________________________________
linux-um mailing list
linux-um@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/linux-um

WARNING: multiple messages have this Message-ID (diff)
From: Christophe Leroy <christophe.leroy@csgroup.eu>
To: Rick Edgecombe <rick.p.edgecombe@intel.com>,
	"x86@kernel.org" <x86@kernel.org>,
	"H . Peter Anvin" <hpa@zytor.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Ingo Molnar <mingo@redhat.com>,
	"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"linux-doc@vger.kernel.org" <linux-doc@vger.kernel.org>,
	"linux-mm@kvack.org" <linux-mm@kvack.org>,
	"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
	"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
	Arnd Bergmann <arnd@arndb.de>, Andy Lutomirski <luto@kernel.org>,
	Balbir Singh <bsingharora@gmail.com>,
	Borislav Petkov <bp@alien8.de>,
	Cyrill Gorcunov <gorcunov@gmail.com>,
	Dave Hansen <dave.hansen@linux.intel.com>,
	Eugene Syromiatnikov <esyr@redhat.com>,
	Florian Weimer <fweimer@redhat.com>,
	"H . J . Lu" <hjl.tools@gmail.com>, Jann Horn <jannh@google.com>,
	Jonathan Corbet <corbet@lwn.net>,
	Kees Cook <keescook@chromium.org>,
	Mike Kravetz <mike.kravetz@oracle.com>,
	Nadav Amit <nadav.amit@gmail.com>,
	Oleg Nesterov <oleg@redhat.com>, Pavel Machek <pavel@ucw.cz>,
	Peter Zijlstra <peterz@infradead.org>,
	Randy Dunlap <rdunlap@infradead.org>,
	Weijiang Yang <weijiang.yang@intel.com>,
	"Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>,
	John Allen <john.allen@amd.com>,
	"kcc@google.com" <kcc@google.com>,
	"eranian@google.com" <eranian@google.com>,
	"rppt@kernel.org" <rppt@kernel.org>,
	"jamorris@linux.microsoft.com" <jamorris@linux.microsoft.com>,
	"dethoma@microsoft.com" <dethoma@microsoft.com>,
	"akpm@linux-foundation.org" <akpm@linux-foundation.org>,
	"Andrew.Cooper3@citrix.com" <Andrew.Cooper3@citrix.com>,
	"christina.schimpe@intel.com" <christina.schimpe@intel.com>,
	"david@redhat.com" <david@redhat.com>,
	"debug@rivosinc.com" <debug@rivosinc.com>
Cc: "linux-s390@vger.kernel.org" <linux-s390@vger.kernel.org>,
	Michal Simek <monstr@monstr.eu>,
	"linux-ia64@vger.kernel.org" <linux-ia64@vger.kernel.org>,
	"linux-parisc@vger.kernel.org" <linux-parisc@vger.kernel.org>,
	"linux-openrisc@vger.kernel.org" <linux-openrisc@vger.kernel.org>,
	"linux-hexagon@vger.kernel.org" <linux-hexagon@vger.kernel.org>,
	"linux-sh@vger.kernel.org" <linux-sh@vger.kernel.org>,
	"linux-um@lists.infradead.org" <linux-um@lists.infradead.org>,
	"linux-mips@vger.kernel.org" <linux-mips@vger.kernel.org>,
	"linux-csky@vger.kernel.org" <linux-csky@vger.kernel.org>,
	Dinh Nguyen <dinguyen@kernel.org>,
	"linux-m68k@lists.linux-m68k.org"
	<linux-m68k@lists.linux-m68k.org>,
	"loongarch@lists.linux.dev" <loongarch@lists.linux.dev>,
	"linux-alpha@vger.kernel.org" <linux-alpha@vger.kernel.org>,
	"sparclinux@vger.kernel.org" <sparclinux@vger.kernel.org>,
	"xen-devel@lists.xenproject.org" <xen-devel@lists.xenproject.org>,
	"linux-riscv@lists.infradead.org" <linux-riscv@lists.infradead.o
	rg>,
	"linux-snps-arc@lists.infradead.org"
	<linux-snps-arc@lists.infradead.org>,
	"linuxppc-dev@lists.ozlabs.org" <linuxppc-dev@lists.ozlabs.org>,
	"linux-arm-kernel@lists.infradead.org"
	<linux-arm-kernel@lists.infradead.org>
Subject: Re: [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA
Date: Wed, 1 Mar 2023 07:03:23 +0000	[thread overview]
Message-ID: <1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu> (raw)
In-Reply-To: <20230227222957.24501-14-rick.p.edgecombe@intel.com>



Le 27/02/2023 à 23:29, Rick Edgecombe a écrit :
> The x86 Control-flow Enforcement Technology (CET) feature includes a new
> type of memory called shadow stack. This shadow stack memory has some
> unusual properties, which requires some core mm changes to function
> properly.
> 
> One of these unusual properties is that shadow stack memory is writable,
> but only in limited ways. These limits are applied via a specific PTE
> bit combination. Nevertheless, the memory is writable, and core mm code
> will need to apply the writable permissions in the typical paths that
> call pte_mkwrite().
> 
> In addition to VM_WRITE, the shadow stack VMA's will have a flag denoting
> that they are special shadow stack flavor of writable memory. So make
> pte_mkwrite() take a VMA, so that the x86 implementation of it can know to
> create regular writable memory or shadow stack memory.
> 
> Apply the same changes for pmd_mkwrite() and huge_pte_mkwrite().

I'm not sure it is a good idea to add a second argument to 
pte_mkwrite(). All pte_mkxxxx() only take a pte and nothing else.

I think you should do the same as commit d9ed9faac283 ("mm: add new 
arch_make_huge_pte() method for tile support")

Christophe

> 
> No functional change.
> 
> Cc: linux-doc@vger.kernel.org
> Cc: linux-kernel@vger.kernel.org
> Cc: linux-alpha@vger.kernel.org
> Cc: linux-snps-arc@lists.infradead.org
> Cc: linux-arm-kernel@lists.infradead.org
> Cc: linux-csky@vger.kernel.org
> Cc: linux-hexagon@vger.kernel.org
> Cc: linux-ia64@vger.kernel.org
> Cc: loongarch@lists.linux.dev
> Cc: linux-m68k@lists.linux-m68k.org
> Cc: Michal Simek <monstr@monstr.eu>
> Cc: Dinh Nguyen <dinguyen@kernel.org>
> Cc: linux-mips@vger.kernel.org
> Cc: linux-openrisc@vger.kernel.org
> Cc: linux-parisc@vger.kernel.org
> Cc: linuxppc-dev@lists.ozlabs.org
> Cc: linux-riscv@lists.infradead.org
> Cc: linux-s390@vger.kernel.org
> Cc: linux-sh@vger.kernel.org
> Cc: sparclinux@vger.kernel.org
> Cc: linux-um@lists.infradead.org
> Cc: xen-devel@lists.xenproject.org
> Cc: linux-arch@vger.kernel.org
> Cc: linux-mm@kvack.org
> Tested-by: Pengfei Xu <pengfei.xu@intel.com>
> Tested-by: John Allen <john.allen@amd.com>
> Tested-by: Kees Cook <keescook@chromium.org>
> Acked-by: Mike Rapoport (IBM) <rppt@kernel.org>
> Acked-by: Michael Ellerman <mpe@ellerman.id.au>
> Acked-by: David Hildenbrand <david@redhat.com>
> Reviewed-by: Kees Cook <keescook@chromium.org>
> Suggested-by: David Hildenbrand <david@redhat.com>
> Signed-off-by: Rick Edgecombe <rick.p.edgecombe@intel.com>
> 
> ---
> Hi Non-x86 Arch’s,
> 
> x86 has a feature that allows for the creation of a special type of
> writable memory (shadow stack) that is only writable in limited specific
> ways. Previously, changes were proposed to core MM code to teach it to
> decide when to create normally writable memory or the special shadow stack
> writable memory, but David Hildenbrand suggested[0] to change
> pXX_mkwrite() to take a VMA, so awareness of shadow stack memory can be
> moved into x86 code.
> 
> Since pXX_mkwrite() is defined in every arch, it requires some tree-wide
> changes. So that is why you are seeing some patches out of a big x86
> series pop up in your arch mailing list. There is no functional change.
> After this refactor, the shadow stack series goes on to use the arch
> helpers to push shadow stack memory details inside arch/x86.
> 
> Testing was just 0-day build testing.
> 
> Hopefully that is enough context. Thanks!
> 
> [0] https://lore.kernel.org/lkml/0e29a2d0-08d8-bcd6-ff26-4bea0e4037b0@redhat.com/#t
> 
> v6:
>   - New patch
> ---
>   Documentation/mm/arch_pgtable_helpers.rst    |  9 ++++++---
>   arch/alpha/include/asm/pgtable.h             |  6 +++++-
>   arch/arc/include/asm/hugepage.h              |  2 +-
>   arch/arc/include/asm/pgtable-bits-arcv2.h    |  7 ++++++-
>   arch/arm/include/asm/pgtable-3level.h        |  7 ++++++-
>   arch/arm/include/asm/pgtable.h               |  2 +-
>   arch/arm64/include/asm/pgtable.h             |  4 ++--
>   arch/csky/include/asm/pgtable.h              |  2 +-
>   arch/hexagon/include/asm/pgtable.h           |  2 +-
>   arch/ia64/include/asm/pgtable.h              |  2 +-
>   arch/loongarch/include/asm/pgtable.h         |  4 ++--
>   arch/m68k/include/asm/mcf_pgtable.h          |  2 +-
>   arch/m68k/include/asm/motorola_pgtable.h     |  6 +++++-
>   arch/m68k/include/asm/sun3_pgtable.h         |  6 +++++-
>   arch/microblaze/include/asm/pgtable.h        |  2 +-
>   arch/mips/include/asm/pgtable.h              |  6 +++---
>   arch/nios2/include/asm/pgtable.h             |  2 +-
>   arch/openrisc/include/asm/pgtable.h          |  2 +-
>   arch/parisc/include/asm/pgtable.h            |  6 +++++-
>   arch/powerpc/include/asm/book3s/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/book3s/64/pgtable.h |  4 ++--
>   arch/powerpc/include/asm/nohash/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/nohash/32/pte-8xx.h |  2 +-
>   arch/powerpc/include/asm/nohash/64/pgtable.h |  2 +-
>   arch/riscv/include/asm/pgtable.h             |  6 +++---
>   arch/s390/include/asm/hugetlb.h              |  4 ++--
>   arch/s390/include/asm/pgtable.h              |  4 ++--
>   arch/sh/include/asm/pgtable_32.h             | 10 ++++++++--
>   arch/sparc/include/asm/pgtable_32.h          |  2 +-
>   arch/sparc/include/asm/pgtable_64.h          |  6 +++---
>   arch/um/include/asm/pgtable.h                |  2 +-
>   arch/x86/include/asm/pgtable.h               |  6 ++++--
>   arch/xtensa/include/asm/pgtable.h            |  2 +-
>   include/asm-generic/hugetlb.h                |  4 ++--
>   include/linux/mm.h                           |  2 +-
>   mm/debug_vm_pgtable.c                        | 16 ++++++++--------
>   mm/huge_memory.c                             |  6 +++---
>   mm/hugetlb.c                                 |  4 ++--
>   mm/memory.c                                  |  4 ++--
>   mm/migrate_device.c                          |  2 +-
>   mm/mprotect.c                                |  2 +-
>   mm/userfaultfd.c                             |  2 +-
>   42 files changed, 106 insertions(+), 69 deletions(-)
> 
> diff --git a/Documentation/mm/arch_pgtable_helpers.rst b/Documentation/mm/arch_pgtable_helpers.rst
> index 30d9a09f01f4..78ac3ff2fe1d 100644
> --- a/Documentation/mm/arch_pgtable_helpers.rst
> +++ b/Documentation/mm/arch_pgtable_helpers.rst
> @@ -46,7 +46,8 @@ PTE Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pte_mkclean               | Creates a clean PTE                              |
>   +---------------------------+--------------------------------------------------+
> -| pte_mkwrite               | Creates a writable PTE                           |
> +| pte_mkwrite               | Creates a writable PTE of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pte_wrprotect             | Creates a write protected PTE                    |
>   +---------------------------+--------------------------------------------------+
> @@ -118,7 +119,8 @@ PMD Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pmd_mkclean               | Creates a clean PMD                              |
>   +---------------------------+--------------------------------------------------+
> -| pmd_mkwrite               | Creates a writable PMD                           |
> +| pmd_mkwrite               | Creates a writable PMD of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pmd_wrprotect             | Creates a write protected PMD                    |
>   +---------------------------+--------------------------------------------------+
> @@ -222,7 +224,8 @@ HugeTLB Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_mkdirty          | Creates a dirty HugeTLB                          |
>   +---------------------------+--------------------------------------------------+
> -| huge_pte_mkwrite          | Creates a writable HugeTLB                       |
> +| huge_pte_mkwrite          | Creates a writable HugeTLB of the type specified |
> +|                           | by the VMA.                                      |
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_wrprotect        | Creates a write protected HugeTLB                |
>   +---------------------------+--------------------------------------------------+
> diff --git a/arch/alpha/include/asm/pgtable.h b/arch/alpha/include/asm/pgtable.h
> index ba43cb841d19..fb5d207c2a89 100644
> --- a/arch/alpha/include/asm/pgtable.h
> +++ b/arch/alpha/include/asm/pgtable.h
> @@ -256,9 +256,13 @@ extern inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   extern inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~(__DIRTY_BITS); return pte; }
>   extern inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~(__ACCESS_BITS); return pte; }
> -extern inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= __DIRTY_BITS; return pte; }
>   extern inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= __ACCESS_BITS; return pte; }
> +extern inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_FOW;
> +	return pte;
> +}
>   
>   /*
>    * The smp_rmb() in the following functions are required to order the load of
> diff --git a/arch/arc/include/asm/hugepage.h b/arch/arc/include/asm/hugepage.h
> index 5001b796fb8d..223a96967188 100644
> --- a/arch/arc/include/asm/hugepage.h
> +++ b/arch/arc/include/asm/hugepage.h
> @@ -21,7 +21,7 @@ static inline pmd_t pte_pmd(pte_t pte)
>   }
>   
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/arc/include/asm/pgtable-bits-arcv2.h b/arch/arc/include/asm/pgtable-bits-arcv2.h
> index 6e9f8ca6d6a1..a5b8bc955015 100644
> --- a/arch/arc/include/asm/pgtable-bits-arcv2.h
> +++ b/arch/arc/include/asm/pgtable-bits-arcv2.h
> @@ -87,7 +87,6 @@
>   
>   PTE_BIT_FUNC(mknotpresent,     &= ~(_PAGE_PRESENT));
>   PTE_BIT_FUNC(wrprotect,	&= ~(_PAGE_WRITE));
> -PTE_BIT_FUNC(mkwrite,	|= (_PAGE_WRITE));
>   PTE_BIT_FUNC(mkclean,	&= ~(_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkdirty,	|= (_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkold,	&= ~(_PAGE_ACCESSED));
> @@ -95,6 +94,12 @@ PTE_BIT_FUNC(mkyoung,	|= (_PAGE_ACCESSED));
>   PTE_BIT_FUNC(mkspecial,	|= (_PAGE_SPECIAL));
>   PTE_BIT_FUNC(mkhuge,	|= (_PAGE_HW_SZ));
>   
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= (_PAGE_WRITE);
> +	return pte;
> +}
> +
>   static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
>   {
>   	return __pte((pte_val(pte) & _PAGE_CHG_MASK) | pgprot_val(newprot));
> diff --git a/arch/arm/include/asm/pgtable-3level.h b/arch/arm/include/asm/pgtable-3level.h
> index 106049791500..df071a807610 100644
> --- a/arch/arm/include/asm/pgtable-3level.h
> +++ b/arch/arm/include/asm/pgtable-3level.h
> @@ -202,11 +202,16 @@ static inline pmd_t pmd_##fn(pmd_t pmd) { pmd_val(pmd) op; return pmd; }
>   
>   PMD_BIT_FUNC(wrprotect,	|= L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkold,	&= ~PMD_SECT_AF);
> -PMD_BIT_FUNC(mkwrite,   &= ~L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkdirty,   |= L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkclean,   &= ~L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkyoung,   |= PMD_SECT_AF);
>   
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
> +{
> +	pmd_val(pmd) |= L_PMD_SECT_RDONLY;
> +	return pmd;
> +}
> +
>   #define pmd_mkhuge(pmd)		(__pmd(pmd_val(pmd) & ~PMD_TABLE_BIT))
>   
>   #define pmd_pfn(pmd)		(((pmd_val(pmd) & PMD_MASK) & PHYS_MASK) >> PAGE_SHIFT)
> diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
> index a58ccbb406ad..39ad1ae1308d 100644
> --- a/arch/arm/include/asm/pgtable.h
> +++ b/arch/arm/include/asm/pgtable.h
> @@ -227,7 +227,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   	return set_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return clear_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
> diff --git a/arch/arm64/include/asm/pgtable.h b/arch/arm64/include/asm/pgtable.h
> index cccf8885792e..913bf370f74a 100644
> --- a/arch/arm64/include/asm/pgtable.h
> +++ b/arch/arm64/include/asm/pgtable.h
> @@ -187,7 +187,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -492,7 +492,7 @@ static inline int pmd_trans_huge(pmd_t pmd)
>   #define pmd_cont(pmd)		pte_cont(pmd_pte(pmd))
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/csky/include/asm/pgtable.h b/arch/csky/include/asm/pgtable.h
> index d4042495febc..c2f92c991e37 100644
> --- a/arch/csky/include/asm/pgtable.h
> +++ b/arch/csky/include/asm/pgtable.h
> @@ -176,7 +176,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> diff --git a/arch/hexagon/include/asm/pgtable.h b/arch/hexagon/include/asm/pgtable.h
> index 59393613d086..14ab9c789c0e 100644
> --- a/arch/hexagon/include/asm/pgtable.h
> +++ b/arch/hexagon/include/asm/pgtable.h
> @@ -300,7 +300,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   }
>   
>   /* pte_mkwrite - mark page as writable */
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/ia64/include/asm/pgtable.h b/arch/ia64/include/asm/pgtable.h
> index 21c97e31a28a..f879dd626da6 100644
> --- a/arch/ia64/include/asm/pgtable.h
> +++ b/arch/ia64/include/asm/pgtable.h
> @@ -268,7 +268,7 @@ ia64_phys_addr_valid (unsigned long addr)
>    * access rights:
>    */
>   #define pte_wrprotect(pte)	(__pte(pte_val(pte) & ~_PAGE_AR_RW))
> -#define pte_mkwrite(pte)	(__pte(pte_val(pte) | _PAGE_AR_RW))
> +#define pte_mkwrite(pte, vma)	(__pte(pte_val(pte) | _PAGE_AR_RW))
>   #define pte_mkold(pte)		(__pte(pte_val(pte) & ~_PAGE_A))
>   #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_A))
>   #define pte_mkclean(pte)	(__pte(pte_val(pte) & ~_PAGE_D))
> diff --git a/arch/loongarch/include/asm/pgtable.h b/arch/loongarch/include/asm/pgtable.h
> index d28fb9dbec59..ebf645f40298 100644
> --- a/arch/loongarch/include/asm/pgtable.h
> +++ b/arch/loongarch/include/asm/pgtable.h
> @@ -390,7 +390,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -490,7 +490,7 @@ static inline int pmd_write(pmd_t pmd)
>   	return !!(pmd_val(pmd) & _PAGE_WRITE);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/m68k/include/asm/mcf_pgtable.h b/arch/m68k/include/asm/mcf_pgtable.h
> index 13741c1245e1..37d77e055016 100644
> --- a/arch/m68k/include/asm/mcf_pgtable.h
> +++ b/arch/m68k/include/asm/mcf_pgtable.h
> @@ -211,7 +211,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= CF_PAGE_WRITABLE;
>   	return pte;
> diff --git a/arch/m68k/include/asm/motorola_pgtable.h b/arch/m68k/include/asm/motorola_pgtable.h
> index ec0dc19ab834..c4e8eb76286d 100644
> --- a/arch/m68k/include/asm/motorola_pgtable.h
> +++ b/arch/m68k/include/asm/motorola_pgtable.h
> @@ -155,7 +155,6 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~_PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)
> @@ -168,6 +167,11 @@ static inline pte_t pte_mkcache(pte_t pte)
>   	pte_val(pte) = (pte_val(pte) & _CACHEMASK040) | m68k_supervisor_cachemode;
>   	return pte;
>   }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_RONLY;
> +	return pte;
> +}
>   
>   #define swapper_pg_dir kernel_pg_dir
>   extern pgd_t kernel_pg_dir[128];
> diff --git a/arch/m68k/include/asm/sun3_pgtable.h b/arch/m68k/include/asm/sun3_pgtable.h
> index e582b0484a55..2a06bea51a1e 100644
> --- a/arch/m68k/include/asm/sun3_pgtable.h
> +++ b/arch/m68k/include/asm/sun3_pgtable.h
> @@ -143,10 +143,14 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & SUN3_PAGE_ACCESS
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_NOCACHE; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= SUN3_PAGE_WRITEABLE;
> +	return pte;
> +}
>   // use this version when caches work...
>   //static inline pte_t pte_mkcache(pte_t pte)	{ pte_val(pte) &= SUN3_PAGE_NOCACHE; return pte; }
>   // until then, use:
> diff --git a/arch/microblaze/include/asm/pgtable.h b/arch/microblaze/include/asm/pgtable.h
> index d1b8272abcd9..5b83e82f8d7e 100644
> --- a/arch/microblaze/include/asm/pgtable.h
> +++ b/arch/microblaze/include/asm/pgtable.h
> @@ -266,7 +266,7 @@ static inline pte_t pte_mkread(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER; return pte; }
>   static inline pte_t pte_mkexec(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER | _PAGE_EXEC; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte) \
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma) \
>   	{ pte_val(pte) |= _PAGE_RW; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
> diff --git a/arch/mips/include/asm/pgtable.h b/arch/mips/include/asm/pgtable.h
> index 791389bf3c12..06efd567144a 100644
> --- a/arch/mips/include/asm/pgtable.h
> +++ b/arch/mips/include/asm/pgtable.h
> @@ -309,7 +309,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte.pte_low |= _PAGE_WRITE;
>   	if (pte.pte_low & _PAGE_MODIFIED) {
> @@ -364,7 +364,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -626,7 +626,7 @@ static inline pmd_t pmd_wrprotect(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/nios2/include/asm/pgtable.h b/arch/nios2/include/asm/pgtable.h
> index 0f5c2564e9f5..edd458518e0e 100644
> --- a/arch/nios2/include/asm/pgtable.h
> +++ b/arch/nios2/include/asm/pgtable.h
> @@ -129,7 +129,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/openrisc/include/asm/pgtable.h b/arch/openrisc/include/asm/pgtable.h
> index 3eb9b9555d0d..fd40aec189d1 100644
> --- a/arch/openrisc/include/asm/pgtable.h
> +++ b/arch/openrisc/include/asm/pgtable.h
> @@ -250,7 +250,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/parisc/include/asm/pgtable.h b/arch/parisc/include/asm/pgtable.h
> index e2950f5db7c9..89f62137e67f 100644
> --- a/arch/parisc/include/asm/pgtable.h
> +++ b/arch/parisc/include/asm/pgtable.h
> @@ -331,8 +331,12 @@ static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; retu
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~_PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= _PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkspecial(pte_t pte)	{ pte_val(pte) |= _PAGE_SPECIAL; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= _PAGE_WRITE;
> +	return pte;
> +}
>   
>   /*
>    * Huge pte definitions.
> diff --git a/arch/powerpc/include/asm/book3s/32/pgtable.h b/arch/powerpc/include/asm/book3s/32/pgtable.h
> index 7bf1fe7297c6..10d9a1d2aca9 100644
> --- a/arch/powerpc/include/asm/book3s/32/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/32/pgtable.h
> @@ -498,7 +498,7 @@ static inline pte_t pte_mkpte(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h
> index 4acc9690f599..be0636522d36 100644
> --- a/arch/powerpc/include/asm/book3s/64/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/64/pgtable.h
> @@ -600,7 +600,7 @@ static inline pte_t pte_mkexec(pte_t pte)
>   	return __pte_raw(pte_raw(pte) | cpu_to_be64(_PAGE_EXEC));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	/*
>   	 * write implies read, hence set both
> @@ -1071,7 +1071,7 @@ static inline pte_t *pmdp_ptep(pmd_t *pmd)
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   
>   #ifdef CONFIG_HAVE_ARCH_SOFT_DIRTY
>   #define pmd_soft_dirty(pmd)    pte_soft_dirty(pmd_pte(pmd))
> diff --git a/arch/powerpc/include/asm/nohash/32/pgtable.h b/arch/powerpc/include/asm/nohash/32/pgtable.h
> index fec56d965f00..7bfbcb9ba55b 100644
> --- a/arch/powerpc/include/asm/nohash/32/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/32/pgtable.h
> @@ -171,7 +171,7 @@ void unmap_kernel_page(unsigned long va);
>   	do { pte_update(mm, addr, ptep, ~0, 0, 0); } while (0)
>   
>   #ifndef pte_mkwrite
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/32/pte-8xx.h b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> index 1a89ebdc3acc..f32450eb270a 100644
> --- a/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> +++ b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> @@ -101,7 +101,7 @@ static inline int pte_write(pte_t pte)
>   
>   #define pte_write pte_write
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) & ~_PAGE_RO);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/64/pgtable.h b/arch/powerpc/include/asm/nohash/64/pgtable.h
> index 287e25864ffa..589009555877 100644
> --- a/arch/powerpc/include/asm/nohash/64/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/64/pgtable.h
> @@ -85,7 +85,7 @@
>   #ifndef __ASSEMBLY__
>   /* pte_clear moved to later in this file */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
> index d8d8de0ded99..fed1b81fbe07 100644
> --- a/arch/riscv/include/asm/pgtable.h
> +++ b/arch/riscv/include/asm/pgtable.h
> @@ -338,7 +338,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   
>   /* static inline pte_t pte_mkread(pte_t pte) */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_WRITE);
>   }
> @@ -624,9 +624,9 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pte_pmd(pte_mkyoung(pmd_pte(pmd)));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
> -	return pte_pmd(pte_mkwrite(pmd_pte(pmd)));
> +	return pte_pmd(pte_mkwrite(pmd_pte(pmd), vma));
>   }
>   
>   static inline pmd_t pmd_wrprotect(pmd_t pmd)
> diff --git a/arch/s390/include/asm/hugetlb.h b/arch/s390/include/asm/hugetlb.h
> index ccdbccfde148..558f7eef9c4d 100644
> --- a/arch/s390/include/asm/hugetlb.h
> +++ b/arch/s390/include/asm/hugetlb.h
> @@ -102,9 +102,9 @@ static inline int huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   static inline pte_t huge_pte_mkdirty(pte_t pte)
> diff --git a/arch/s390/include/asm/pgtable.h b/arch/s390/include/asm/pgtable.h
> index deeb918cae1d..8f2c743da0eb 100644
> --- a/arch/s390/include/asm/pgtable.h
> +++ b/arch/s390/include/asm/pgtable.h
> @@ -1013,7 +1013,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -1499,7 +1499,7 @@ static inline pmd_t pmd_mkwrite_kernel(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_mkwrite_kernel(pmd);
>   }
> diff --git a/arch/sh/include/asm/pgtable_32.h b/arch/sh/include/asm/pgtable_32.h
> index 21952b094650..9f2dcb9eafc8 100644
> --- a/arch/sh/include/asm/pgtable_32.h
> +++ b/arch/sh/include/asm/pgtable_32.h
> @@ -351,6 +351,12 @@ static inline void set_pte(pte_t *ptep, pte_t pte)
>   
>   #define PTE_BIT_FUNC(h,fn,op) \
>   static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
> +#define PTE_BIT_FUNC_VMA(h,fn,op) \
> +static inline pte_t pte_##fn(pte_t pte, struct vm_area_struct *vma) \
> +{ \
> +	pte.pte_##h op; \
> +	return pte; \
> +}
>   
>   #ifdef CONFIG_X2TLB
>   /*
> @@ -359,11 +365,11 @@ static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
>    * kernel permissions), we attempt to couple them a bit more sanely here.
>    */
>   PTE_BIT_FUNC(high, wrprotect, &= ~(_PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE));
> -PTE_BIT_FUNC(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
> +PTE_BIT_FUNC_VMA(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
>   PTE_BIT_FUNC(high, mkhuge, |= _PAGE_SZHUGE);
>   #else
>   PTE_BIT_FUNC(low, wrprotect, &= ~_PAGE_RW);
> -PTE_BIT_FUNC(low, mkwrite, |= _PAGE_RW);
> +PTE_BIT_FUNC_VMA(low, mkwrite, |= _PAGE_RW);
>   PTE_BIT_FUNC(low, mkhuge, |= _PAGE_SZHUGE);
>   #endif
>   
> diff --git a/arch/sparc/include/asm/pgtable_32.h b/arch/sparc/include/asm/pgtable_32.h
> index d4330e3c57a6..3e8836179456 100644
> --- a/arch/sparc/include/asm/pgtable_32.h
> +++ b/arch/sparc/include/asm/pgtable_32.h
> @@ -241,7 +241,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return __pte(pte_val(pte) & ~SRMMU_REF);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | SRMMU_WRITE);
>   }
> diff --git a/arch/sparc/include/asm/pgtable_64.h b/arch/sparc/include/asm/pgtable_64.h
> index 2dc8d4641734..c5cd5c03f557 100644
> --- a/arch/sparc/include/asm/pgtable_64.h
> +++ b/arch/sparc/include/asm/pgtable_64.h
> @@ -466,7 +466,7 @@ static inline pte_t pte_mkclean(pte_t pte)
>   	return __pte(val);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	unsigned long val = pte_val(pte), mask;
>   
> @@ -756,11 +756,11 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return __pmd(pte_val(pte));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pte_t pte = __pte(pmd_val(pmd));
>   
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, vma);
>   
>   	return __pmd(pte_val(pte));
>   }
> diff --git a/arch/um/include/asm/pgtable.h b/arch/um/include/asm/pgtable.h
> index a70d1618eb35..963479c133b7 100644
> --- a/arch/um/include/asm/pgtable.h
> +++ b/arch/um/include/asm/pgtable.h
> @@ -207,7 +207,7 @@ static inline pte_t pte_mkyoung(pte_t pte)
>   	return(pte);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (unlikely(pte_get_bits(pte,  _PAGE_RW)))
>   		return pte;
> diff --git a/arch/x86/include/asm/pgtable.h b/arch/x86/include/asm/pgtable.h
> index 3607f2572f9e..66c514808276 100644
> --- a/arch/x86/include/asm/pgtable.h
> +++ b/arch/x86/include/asm/pgtable.h
> @@ -369,7 +369,9 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte_set_flags(pte, _PAGE_RW);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +struct vm_area_struct;
> +
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -470,7 +472,7 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pmd_set_flags(pmd, _PAGE_ACCESSED);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_set_flags(pmd, _PAGE_RW);
>   }
> diff --git a/arch/xtensa/include/asm/pgtable.h b/arch/xtensa/include/asm/pgtable.h
> index fc7a14884c6c..d72632d9c53c 100644
> --- a/arch/xtensa/include/asm/pgtable.h
> +++ b/arch/xtensa/include/asm/pgtable.h
> @@ -262,7 +262,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   	{ pte_val(pte) |= _PAGE_WRITABLE; return pte; }
>   
>   #define pgprot_noncached(prot) \
> diff --git a/include/asm-generic/hugetlb.h b/include/asm-generic/hugetlb.h
> index d7f6335d3999..e86c830728de 100644
> --- a/include/asm-generic/hugetlb.h
> +++ b/include/asm-generic/hugetlb.h
> @@ -20,9 +20,9 @@ static inline unsigned long huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   #ifndef __HAVE_ARCH_HUGE_PTE_WRPROTECT
> diff --git a/include/linux/mm.h b/include/linux/mm.h
> index 1f79667824eb..af652444fbba 100644
> --- a/include/linux/mm.h
> +++ b/include/linux/mm.h
> @@ -1163,7 +1163,7 @@ void free_compound_page(struct page *page);
>   static inline pte_t maybe_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	return pte;
>   }
>   
> diff --git a/mm/debug_vm_pgtable.c b/mm/debug_vm_pgtable.c
> index af59cc7bd307..7bc5592900bc 100644
> --- a/mm/debug_vm_pgtable.c
> +++ b/mm/debug_vm_pgtable.c
> @@ -109,10 +109,10 @@ static void __init pte_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pte_same(pte, pte));
>   	WARN_ON(!pte_young(pte_mkyoung(pte_mkold(pte))));
>   	WARN_ON(!pte_dirty(pte_mkdirty(pte_mkclean(pte))));
> -	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte))));
> +	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte), args->vma)));
>   	WARN_ON(pte_young(pte_mkold(pte_mkyoung(pte))));
>   	WARN_ON(pte_dirty(pte_mkclean(pte_mkdirty(pte))));
> -	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte))));
> +	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte, args->vma))));
>   	WARN_ON(pte_dirty(pte_wrprotect(pte_mkclean(pte))));
>   	WARN_ON(!pte_dirty(pte_wrprotect(pte_mkdirty(pte))));
>   }
> @@ -153,7 +153,7 @@ static void __init pte_advanced_tests(struct pgtable_debug_args *args)
>   	pte = pte_mkclean(pte);
>   	set_pte_at(args->mm, args->vaddr, args->ptep, pte);
>   	flush_dcache_page(page);
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, args->vma);
>   	pte = pte_mkdirty(pte);
>   	ptep_set_access_flags(args->vma, args->vaddr, args->ptep, pte, 1);
>   	pte = ptep_get(args->ptep);
> @@ -199,10 +199,10 @@ static void __init pmd_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pmd_same(pmd, pmd));
>   	WARN_ON(!pmd_young(pmd_mkyoung(pmd_mkold(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_mkdirty(pmd_mkclean(pmd))));
> -	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd))));
> +	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd), args->vma)));
>   	WARN_ON(pmd_young(pmd_mkold(pmd_mkyoung(pmd))));
>   	WARN_ON(pmd_dirty(pmd_mkclean(pmd_mkdirty(pmd))));
> -	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd))));
> +	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd, args->vma))));
>   	WARN_ON(pmd_dirty(pmd_wrprotect(pmd_mkclean(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_wrprotect(pmd_mkdirty(pmd))));
>   	/*
> @@ -253,7 +253,7 @@ static void __init pmd_advanced_tests(struct pgtable_debug_args *args)
>   	pmd = pmd_mkclean(pmd);
>   	set_pmd_at(args->mm, vaddr, args->pmdp, pmd);
>   	flush_dcache_page(page);
> -	pmd = pmd_mkwrite(pmd);
> +	pmd = pmd_mkwrite(pmd, args->vma);
>   	pmd = pmd_mkdirty(pmd);
>   	pmdp_set_access_flags(args->vma, vaddr, args->pmdp, pmd, 1);
>   	pmd = READ_ONCE(*args->pmdp);
> @@ -928,8 +928,8 @@ static void __init hugetlb_basic_tests(struct pgtable_debug_args *args)
>   	pte = mk_huge_pte(page, args->page_prot);
>   
>   	WARN_ON(!huge_pte_dirty(huge_pte_mkdirty(pte)));
> -	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte))));
> -	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte))));
> +	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte), args->vma)));
> +	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte, args->vma))));
>   
>   #ifdef CONFIG_ARCH_WANT_GENERAL_HUGETLB
>   	pte = pfn_pte(args->fixed_pmd_pfn, args->page_prot);
> diff --git a/mm/huge_memory.c b/mm/huge_memory.c
> index 4fc43859e59a..aaf815838144 100644
> --- a/mm/huge_memory.c
> +++ b/mm/huge_memory.c
> @@ -555,7 +555,7 @@ __setup("transparent_hugepage=", setup_transparent_hugepage);
>   pmd_t maybe_pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	return pmd;
>   }
>   
> @@ -1580,7 +1580,7 @@ vm_fault_t do_huge_pmd_numa_page(struct vm_fault *vmf)
>   	pmd = pmd_modify(oldpmd, vma->vm_page_prot);
>   	pmd = pmd_mkyoung(pmd);
>   	if (writable)
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	set_pmd_at(vma->vm_mm, haddr, vmf->pmd, pmd);
>   	update_mmu_cache_pmd(vma, vmf->address, vmf->pmd);
>   	spin_unlock(vmf->ptl);
> @@ -1926,7 +1926,7 @@ int change_huge_pmd(struct mmu_gather *tlb, struct vm_area_struct *vma,
>   	/* See change_pte_range(). */
>   	if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) && !pmd_write(entry) &&
>   	    can_change_pmd_writable(vma, addr, entry))
> -		entry = pmd_mkwrite(entry);
> +		entry = pmd_mkwrite(entry, vma);
>   
>   	ret = HPAGE_PMD_NR;
>   	set_pmd_at(mm, addr, pmd, entry);
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 07abcb6eb203..6af471bdcff8 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -4900,7 +4900,7 @@ static pte_t make_huge_pte(struct vm_area_struct *vma, struct page *page,
>   
>   	if (writable) {
>   		entry = huge_pte_mkwrite(huge_pte_mkdirty(mk_huge_pte(page,
> -					 vma->vm_page_prot)));
> +					 vma->vm_page_prot)), vma);
>   	} else {
>   		entry = huge_pte_wrprotect(mk_huge_pte(page,
>   					   vma->vm_page_prot));
> @@ -4916,7 +4916,7 @@ static void set_huge_ptep_writable(struct vm_area_struct *vma,
>   {
>   	pte_t entry;
>   
> -	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)));
> +	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)), vma);
>   	if (huge_ptep_set_access_flags(vma, address, ptep, entry, 1))
>   		update_mmu_cache(vma, address, ptep);
>   }
> diff --git a/mm/memory.c b/mm/memory.c
> index f456f3b5049c..d0972d2d6f36 100644
> --- a/mm/memory.c
> +++ b/mm/memory.c
> @@ -4067,7 +4067,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
>   	entry = mk_pte(&folio->page, vma->vm_page_prot);
>   	entry = pte_sw_mkyoung(entry);
>   	if (vma->vm_flags & VM_WRITE)
> -		entry = pte_mkwrite(pte_mkdirty(entry));
> +		entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   
>   	vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, vmf->address,
>   			&vmf->ptl);
> @@ -4755,7 +4755,7 @@ static vm_fault_t do_numa_page(struct vm_fault *vmf)
>   	pte = pte_modify(old_pte, vma->vm_page_prot);
>   	pte = pte_mkyoung(pte);
>   	if (writable)
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	ptep_modify_prot_commit(vma, vmf->address, vmf->pte, old_pte, pte);
>   	update_mmu_cache(vma, vmf->address, vmf->pte);
>   	pte_unmap_unlock(vmf->pte, vmf->ptl);
> diff --git a/mm/migrate_device.c b/mm/migrate_device.c
> index d30c9de60b0d..df3f5e9d5f76 100644
> --- a/mm/migrate_device.c
> +++ b/mm/migrate_device.c
> @@ -646,7 +646,7 @@ static void migrate_vma_insert_page(struct migrate_vma *migrate,
>   		}
>   		entry = mk_pte(page, vma->vm_page_prot);
>   		if (vma->vm_flags & VM_WRITE)
> -			entry = pte_mkwrite(pte_mkdirty(entry));
> +			entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   	}
>   
>   	ptep = pte_offset_map_lock(mm, pmdp, addr, &ptl);
> diff --git a/mm/mprotect.c b/mm/mprotect.c
> index 1d4843c97c2a..381163a41e88 100644
> --- a/mm/mprotect.c
> +++ b/mm/mprotect.c
> @@ -198,7 +198,7 @@ static long change_pte_range(struct mmu_gather *tlb,
>   			if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) &&
>   			    !pte_write(ptent) &&
>   			    can_change_pte_writable(vma, addr, ptent))
> -				ptent = pte_mkwrite(ptent);
> +				ptent = pte_mkwrite(ptent, vma);
>   
>   			ptep_modify_prot_commit(vma, addr, pte, oldpte, ptent);
>   			if (pte_needs_flush(oldpte, ptent))
> diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
> index 53c3d916ff66..3db6f87c0aca 100644
> --- a/mm/userfaultfd.c
> +++ b/mm/userfaultfd.c
> @@ -75,7 +75,7 @@ int mfill_atomic_install_pte(struct mm_struct *dst_mm, pmd_t *dst_pmd,
>   	if (page_in_cache && !vm_shared)
>   		writable = false;
>   	if (writable)
> -		_dst_pte = pte_mkwrite(_dst_pte);
> +		_dst_pte = pte_mkwrite(_dst_pte, dst_vma);
>   	if (wp_copy)
>   		_dst_pte = pte_mkuffd_wp(_dst_pte);
>   

WARNING: multiple messages have this Message-ID (diff)
From: Christophe Leroy <christophe.leroy@csgroup.eu>
To: Rick Edgecombe <rick.p.edgecombe@intel.com>,
	"x86@kernel.org" <x86@kernel.org>,
	"H . Peter Anvin" <hpa@zytor.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Ingo Molnar <mingo@redhat.com>,
	"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"linux-doc@vger.kernel.org" <linux-doc@vger.kernel.org>,
	"linux-mm@kvack.org" <linux-mm@kvack.org>,
	"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
	"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
	Arnd Bergmann <arnd@arndb.de>, Andy Lutomirski <luto@kernel.org>,
	Balbir Singh <bsingharora@gmail.com>,
	Borislav Petkov <bp@alien8.de>,
	Cyrill Gorcunov <gorcunov@gmail.com>,
	Dave Hansen <dave.hansen@linux.intel.com>,
	Eugene Syromiatnikov <esyr@redhat.com>,
	Florian Weimer <fweimer@redhat.com>,
	"H . J . Lu" <hjl.tools@gmail.com>, Jann Horn <jannh@google.com>,
	Jonathan Corbet <corbet@lwn.net>,
	Kees Cook <keescook@chromium.org>,
	Mike Kravetz <mike.kravetz@oracle.com>,
	Nadav Amit <nadav.amit@gmail.com>,
	Oleg Nesterov <oleg@redhat.com>, Pavel Machek <pavel@ucw.cz>,
	Peter Zijlstra <peterz@infradead.org>,
	Randy Dunlap <rdunlap@infradead.org>,
	Weijiang Yang <weijiang.yang@intel.com>,
	"Kirill A . Shutemov" <kirill.shutemov@linux.intel.com>,
	John Allen <john.allen@amd.com>,
	"kcc@google.com" <kcc@google.com>,
	"eranian@google.com" <eranian@google.com>,
	"rppt@kernel.org" <rppt@kernel.org>,
	"jamorris@linux.microsoft.com" <jamorris@linux.microsoft.com>,
	"dethoma@microsoft.com" <dethoma@microsoft.com>,
	"akpm@linux-foundation.org" <akpm@linux-foundation.org>,
	"Andrew.Cooper3@citrix.com" <Andrew.Cooper3@citrix.com>,
	"christina.schimpe@intel.com" <christina.schimpe@intel.com>,
	"david@redhat.com" <david@redhat.com>,
	"debug@rivosinc.com" <debug@rivosinc.com>
Cc: "linux-alpha@vger.kernel.org" <linux-alpha@vger.kernel.org>,
	"linux-snps-arc@lists.infradead.org"
	<linux-snps-arc@lists.infradead.org>,
	"linux-arm-kernel@lists.infradead.org"
	<linux-arm-kernel@lists.infradead.org>,
	"linux-csky@vger.kernel.org" <linux-csky@vger.kernel.org>,
	"linux-hexagon@vger.kernel.org" <linux-hexagon@vger.kernel.org>,
	"linux-ia64@vger.kernel.org" <linux-ia64@vger.kernel.org>,
	"loongarch@lists.linux.dev" <loongarch@lists.linux.dev>,
	"linux-m68k@lists.linux-m68k.org"
	<linux-m68k@lists.linux-m68k.org>,
	Michal Simek <monstr@monstr.eu>,
	Dinh Nguyen <dinguyen@kernel.org>,
	"linux-mips@vger.kernel.org" <linux-mips@vger.kernel.org>,
	"linux-openrisc@vger.kernel.org" <linux-openrisc@vger.kernel.org>,
	"linux-parisc@vger.kernel.org" <linux-parisc@vger.kernel.org>,
	"linuxppc-dev@lists.ozlabs.org" <linuxppc-dev@lists.ozlabs.org>,
	"linux-riscv@lists.infradead.org"
	<linux-riscv@lists.infradead.org>,
	"linux-s390@vger.kernel.org" <linux-s390@vger.kernel.org>,
	"linux-sh@vger.kernel.org" <linux-sh@vger.kernel.org>,
	"sparclinux@vger.kernel.org" <sparclinux@vger.kernel.org>,
	"linux-um@lists.infradead.org" <linux-um@lists.infradead.org>,
	"xen-devel@lists.xenproject.org" <xen-devel@lists.xenproject.org>
Subject: Re: [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA
Date: Wed, 01 Mar 2023 07:03:23 +0000	[thread overview]
Message-ID: <1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu> (raw)
In-Reply-To: <20230227222957.24501-14-rick.p.edgecombe@intel.com>

DQoNCkxlIDI3LzAyLzIwMjMgw6AgMjM6MjksIFJpY2sgRWRnZWNvbWJlIGEgw6ljcml0wqA6DQo+
IFRoZSB4ODYgQ29udHJvbC1mbG93IEVuZm9yY2VtZW50IFRlY2hub2xvZ3kgKENFVCkgZmVhdHVy
ZSBpbmNsdWRlcyBhIG5ldw0KPiB0eXBlIG9mIG1lbW9yeSBjYWxsZWQgc2hhZG93IHN0YWNrLiBU
aGlzIHNoYWRvdyBzdGFjayBtZW1vcnkgaGFzIHNvbWUNCj4gdW51c3VhbCBwcm9wZXJ0aWVzLCB3
aGljaCByZXF1aXJlcyBzb21lIGNvcmUgbW0gY2hhbmdlcyB0byBmdW5jdGlvbg0KPiBwcm9wZXJs
eS4NCj4gDQo+IE9uZSBvZiB0aGVzZSB1bnVzdWFsIHByb3BlcnRpZXMgaXMgdGhhdCBzaGFkb3cg
c3RhY2sgbWVtb3J5IGlzIHdyaXRhYmxlLA0KPiBidXQgb25seSBpbiBsaW1pdGVkIHdheXMuIFRo
ZXNlIGxpbWl0cyBhcmUgYXBwbGllZCB2aWEgYSBzcGVjaWZpYyBQVEUNCj4gYml0IGNvbWJpbmF0
aW9uLiBOZXZlcnRoZWxlc3MsIHRoZSBtZW1vcnkgaXMgd3JpdGFibGUsIGFuZCBjb3JlIG1tIGNv
ZGUNCj4gd2lsbCBuZWVkIHRvIGFwcGx5IHRoZSB3cml0YWJsZSBwZXJtaXNzaW9ucyBpbiB0aGUg
dHlwaWNhbCBwYXRocyB0aGF0DQo+IGNhbGwgcHRlX21rd3JpdGUoKS4NCj4gDQo+IEluIGFkZGl0
aW9uIHRvIFZNX1dSSVRFLCB0aGUgc2hhZG93IHN0YWNrIFZNQSdzIHdpbGwgaGF2ZSBhIGZsYWcg
ZGVub3RpbmcNCj4gdGhhdCB0aGV5IGFyZSBzcGVjaWFsIHNoYWRvdyBzdGFjayBmbGF2b3Igb2Yg
d3JpdGFibGUgbWVtb3J5LiBTbyBtYWtlDQo+IHB0ZV9ta3dyaXRlKCkgdGFrZSBhIFZNQSwgc28g
dGhhdCB0aGUgeDg2IGltcGxlbWVudGF0aW9uIG9mIGl0IGNhbiBrbm93IHRvDQo+IGNyZWF0ZSBy
ZWd1bGFyIHdyaXRhYmxlIG1lbW9yeSBvciBzaGFkb3cgc3RhY2sgbWVtb3J5Lg0KPiANCj4gQXBw
bHkgdGhlIHNhbWUgY2hhbmdlcyBmb3IgcG1kX21rd3JpdGUoKSBhbmQgaHVnZV9wdGVfbWt3cml0
ZSgpLg0KDQpJJ20gbm90IHN1cmUgaXQgaXMgYSBnb29kIGlkZWEgdG8gYWRkIGEgc2Vjb25kIGFy
Z3VtZW50IHRvIA0KcHRlX21rd3JpdGUoKS4gQWxsIHB0ZV9ta3h4eHgoKSBvbmx5IHRha2UgYSBw
dGUgYW5kIG5vdGhpbmcgZWxzZS4NCg0KSSB0aGluayB5b3Ugc2hvdWxkIGRvIHRoZSBzYW1lIGFz
IGNvbW1pdCBkOWVkOWZhYWMyODMgKCJtbTogYWRkIG5ldyANCmFyY2hfbWFrZV9odWdlX3B0ZSgp
IG1ldGhvZCBmb3IgdGlsZSBzdXBwb3J0IikNCg0KQ2hyaXN0b3BoZQ0KDQo+IA0KPiBObyBmdW5j
dGlvbmFsIGNoYW5nZS4NCj4gDQo+IENjOiBsaW51eC1kb2NAdmdlci5rZXJuZWwub3JnDQo+IENj
OiBsaW51eC1rZXJuZWxAdmdlci5rZXJuZWwub3JnDQo+IENjOiBsaW51eC1hbHBoYUB2Z2VyLmtl
cm5lbC5vcmcNCj4gQ2M6IGxpbnV4LXNucHMtYXJjQGxpc3RzLmluZnJhZGVhZC5vcmcNCj4gQ2M6
IGxpbnV4LWFybS1rZXJuZWxAbGlzdHMuaW5mcmFkZWFkLm9yZw0KPiBDYzogbGludXgtY3NreUB2
Z2VyLmtlcm5lbC5vcmcNCj4gQ2M6IGxpbnV4LWhleGFnb25Admdlci5rZXJuZWwub3JnDQo+IENj
OiBsaW51eC1pYTY0QHZnZXIua2VybmVsLm9yZw0KPiBDYzogbG9vbmdhcmNoQGxpc3RzLmxpbnV4
LmRldg0KPiBDYzogbGludXgtbTY4a0BsaXN0cy5saW51eC1tNjhrLm9yZw0KPiBDYzogTWljaGFs
IFNpbWVrIDxtb25zdHJAbW9uc3RyLmV1Pg0KPiBDYzogRGluaCBOZ3V5ZW4gPGRpbmd1eWVuQGtl
cm5lbC5vcmc+DQo+IENjOiBsaW51eC1taXBzQHZnZXIua2VybmVsLm9yZw0KPiBDYzogbGludXgt
b3BlbnJpc2NAdmdlci5rZXJuZWwub3JnDQo+IENjOiBsaW51eC1wYXJpc2NAdmdlci5rZXJuZWwu
b3JnDQo+IENjOiBsaW51eHBwYy1kZXZAbGlzdHMub3psYWJzLm9yZw0KPiBDYzogbGludXgtcmlz
Y3ZAbGlzdHMuaW5mcmFkZWFkLm9yZw0KPiBDYzogbGludXgtczM5MEB2Z2VyLmtlcm5lbC5vcmcN
Cj4gQ2M6IGxpbnV4LXNoQHZnZXIua2VybmVsLm9yZw0KPiBDYzogc3BhcmNsaW51eEB2Z2VyLmtl
cm5lbC5vcmcNCj4gQ2M6IGxpbnV4LXVtQGxpc3RzLmluZnJhZGVhZC5vcmcNCj4gQ2M6IHhlbi1k
ZXZlbEBsaXN0cy54ZW5wcm9qZWN0Lm9yZw0KPiBDYzogbGludXgtYXJjaEB2Z2VyLmtlcm5lbC5v
cmcNCj4gQ2M6IGxpbnV4LW1tQGt2YWNrLm9yZw0KPiBUZXN0ZWQtYnk6IFBlbmdmZWkgWHUgPHBl
bmdmZWkueHVAaW50ZWwuY29tPg0KPiBUZXN0ZWQtYnk6IEpvaG4gQWxsZW4gPGpvaG4uYWxsZW5A
YW1kLmNvbT4NCj4gVGVzdGVkLWJ5OiBLZWVzIENvb2sgPGtlZXNjb29rQGNocm9taXVtLm9yZz4N
Cj4gQWNrZWQtYnk6IE1pa2UgUmFwb3BvcnQgKElCTSkgPHJwcHRAa2VybmVsLm9yZz4NCj4gQWNr
ZWQtYnk6IE1pY2hhZWwgRWxsZXJtYW4gPG1wZUBlbGxlcm1hbi5pZC5hdT4NCj4gQWNrZWQtYnk6
IERhdmlkIEhpbGRlbmJyYW5kIDxkYXZpZEByZWRoYXQuY29tPg0KPiBSZXZpZXdlZC1ieTogS2Vl
cyBDb29rIDxrZWVzY29va0BjaHJvbWl1bS5vcmc+DQo+IFN1Z2dlc3RlZC1ieTogRGF2aWQgSGls
ZGVuYnJhbmQgPGRhdmlkQHJlZGhhdC5jb20+DQo+IFNpZ25lZC1vZmYtYnk6IFJpY2sgRWRnZWNv
bWJlIDxyaWNrLnAuZWRnZWNvbWJlQGludGVsLmNvbT4NCj4gDQo+IC0tLQ0KPiBIaSBOb24teDg2
IEFyY2jigJlzLA0KPiANCj4geDg2IGhhcyBhIGZlYXR1cmUgdGhhdCBhbGxvd3MgZm9yIHRoZSBj
cmVhdGlvbiBvZiBhIHNwZWNpYWwgdHlwZSBvZg0KPiB3cml0YWJsZSBtZW1vcnkgKHNoYWRvdyBz
dGFjaykgdGhhdCBpcyBvbmx5IHdyaXRhYmxlIGluIGxpbWl0ZWQgc3BlY2lmaWMNCj4gd2F5cy4g
UHJldmlvdXNseSwgY2hhbmdlcyB3ZXJlIHByb3Bvc2VkIHRvIGNvcmUgTU0gY29kZSB0byB0ZWFj
aCBpdCB0bw0KPiBkZWNpZGUgd2hlbiB0byBjcmVhdGUgbm9ybWFsbHkgd3JpdGFibGUgbWVtb3J5
IG9yIHRoZSBzcGVjaWFsIHNoYWRvdyBzdGFjaw0KPiB3cml0YWJsZSBtZW1vcnksIGJ1dCBEYXZp
ZCBIaWxkZW5icmFuZCBzdWdnZXN0ZWRbMF0gdG8gY2hhbmdlDQo+IHBYWF9ta3dyaXRlKCkgdG8g
dGFrZSBhIFZNQSwgc28gYXdhcmVuZXNzIG9mIHNoYWRvdyBzdGFjayBtZW1vcnkgY2FuIGJlDQo+
IG1vdmVkIGludG8geDg2IGNvZGUuDQo+IA0KPiBTaW5jZSBwWFhfbWt3cml0ZSgpIGlzIGRlZmlu
ZWQgaW4gZXZlcnkgYXJjaCwgaXQgcmVxdWlyZXMgc29tZSB0cmVlLXdpZGUNCj4gY2hhbmdlcy4g
U28gdGhhdCBpcyB3aHkgeW91IGFyZSBzZWVpbmcgc29tZSBwYXRjaGVzIG91dCBvZiBhIGJpZyB4
ODYNCj4gc2VyaWVzIHBvcCB1cCBpbiB5b3VyIGFyY2ggbWFpbGluZyBsaXN0LiBUaGVyZSBpcyBu
byBmdW5jdGlvbmFsIGNoYW5nZS4NCj4gQWZ0ZXIgdGhpcyByZWZhY3RvciwgdGhlIHNoYWRvdyBz
dGFjayBzZXJpZXMgZ29lcyBvbiB0byB1c2UgdGhlIGFyY2gNCj4gaGVscGVycyB0byBwdXNoIHNo
YWRvdyBzdGFjayBtZW1vcnkgZGV0YWlscyBpbnNpZGUgYXJjaC94ODYuDQo+IA0KPiBUZXN0aW5n
IHdhcyBqdXN0IDAtZGF5IGJ1aWxkIHRlc3RpbmcuDQo+IA0KPiBIb3BlZnVsbHkgdGhhdCBpcyBl
bm91Z2ggY29udGV4dC4gVGhhbmtzIQ0KPiANCj4gWzBdIGh0dHBzOi8vbG9yZS5rZXJuZWwub3Jn
L2xrbWwvMGUyOWEyZDAtMDhkOC1iY2Q2LWZmMjYtNGJlYTBlNDAzN2IwQHJlZGhhdC5jb20vI3QN
Cj4gDQo+IHY2Og0KPiAgIC0gTmV3IHBhdGNoDQo+IC0tLQ0KPiAgIERvY3VtZW50YXRpb24vbW0v
YXJjaF9wZ3RhYmxlX2hlbHBlcnMucnN0ICAgIHwgIDkgKysrKysrLS0tDQo+ICAgYXJjaC9hbHBo
YS9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggICAgICAgICAgICAgfCAgNiArKysrKy0NCj4gICBhcmNo
L2FyYy9pbmNsdWRlL2FzbS9odWdlcGFnZS5oICAgICAgICAgICAgICB8ICAyICstDQo+ICAgYXJj
aC9hcmMvaW5jbHVkZS9hc20vcGd0YWJsZS1iaXRzLWFyY3YyLmggICAgfCAgNyArKysrKystDQo+
ICAgYXJjaC9hcm0vaW5jbHVkZS9hc20vcGd0YWJsZS0zbGV2ZWwuaCAgICAgICAgfCAgNyArKysr
KystDQo+ICAgYXJjaC9hcm0vaW5jbHVkZS9hc20vcGd0YWJsZS5oICAgICAgICAgICAgICAgfCAg
MiArLQ0KPiAgIGFyY2gvYXJtNjQvaW5jbHVkZS9hc20vcGd0YWJsZS5oICAgICAgICAgICAgIHwg
IDQgKystLQ0KPiAgIGFyY2gvY3NreS9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggICAgICAgICAgICAg
IHwgIDIgKy0NCj4gICBhcmNoL2hleGFnb24vaW5jbHVkZS9hc20vcGd0YWJsZS5oICAgICAgICAg
ICB8ICAyICstDQo+ICAgYXJjaC9pYTY0L2luY2x1ZGUvYXNtL3BndGFibGUuaCAgICAgICAgICAg
ICAgfCAgMiArLQ0KPiAgIGFyY2gvbG9vbmdhcmNoL2luY2x1ZGUvYXNtL3BndGFibGUuaCAgICAg
ICAgIHwgIDQgKystLQ0KPiAgIGFyY2gvbTY4ay9pbmNsdWRlL2FzbS9tY2ZfcGd0YWJsZS5oICAg
ICAgICAgIHwgIDIgKy0NCj4gICBhcmNoL202OGsvaW5jbHVkZS9hc20vbW90b3JvbGFfcGd0YWJs
ZS5oICAgICB8ICA2ICsrKysrLQ0KPiAgIGFyY2gvbTY4ay9pbmNsdWRlL2FzbS9zdW4zX3BndGFi
bGUuaCAgICAgICAgIHwgIDYgKysrKystDQo+ICAgYXJjaC9taWNyb2JsYXplL2luY2x1ZGUvYXNt
L3BndGFibGUuaCAgICAgICAgfCAgMiArLQ0KPiAgIGFyY2gvbWlwcy9pbmNsdWRlL2FzbS9wZ3Rh
YmxlLmggICAgICAgICAgICAgIHwgIDYgKysrLS0tDQo+ICAgYXJjaC9uaW9zMi9pbmNsdWRlL2Fz
bS9wZ3RhYmxlLmggICAgICAgICAgICAgfCAgMiArLQ0KPiAgIGFyY2gvb3BlbnJpc2MvaW5jbHVk
ZS9hc20vcGd0YWJsZS5oICAgICAgICAgIHwgIDIgKy0NCj4gICBhcmNoL3BhcmlzYy9pbmNsdWRl
L2FzbS9wZ3RhYmxlLmggICAgICAgICAgICB8ICA2ICsrKysrLQ0KPiAgIGFyY2gvcG93ZXJwYy9p
bmNsdWRlL2FzbS9ib29rM3MvMzIvcGd0YWJsZS5oIHwgIDIgKy0NCj4gICBhcmNoL3Bvd2VycGMv
aW5jbHVkZS9hc20vYm9vazNzLzY0L3BndGFibGUuaCB8ICA0ICsrLS0NCj4gICBhcmNoL3Bvd2Vy
cGMvaW5jbHVkZS9hc20vbm9oYXNoLzMyL3BndGFibGUuaCB8ICAyICstDQo+ICAgYXJjaC9wb3dl
cnBjL2luY2x1ZGUvYXNtL25vaGFzaC8zMi9wdGUtOHh4LmggfCAgMiArLQ0KPiAgIGFyY2gvcG93
ZXJwYy9pbmNsdWRlL2FzbS9ub2hhc2gvNjQvcGd0YWJsZS5oIHwgIDIgKy0NCj4gICBhcmNoL3Jp
c2N2L2luY2x1ZGUvYXNtL3BndGFibGUuaCAgICAgICAgICAgICB8ICA2ICsrKy0tLQ0KPiAgIGFy
Y2gvczM5MC9pbmNsdWRlL2FzbS9odWdldGxiLmggICAgICAgICAgICAgIHwgIDQgKystLQ0KPiAg
IGFyY2gvczM5MC9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggICAgICAgICAgICAgIHwgIDQgKystLQ0K
PiAgIGFyY2gvc2gvaW5jbHVkZS9hc20vcGd0YWJsZV8zMi5oICAgICAgICAgICAgIHwgMTAgKysr
KysrKystLQ0KPiAgIGFyY2gvc3BhcmMvaW5jbHVkZS9hc20vcGd0YWJsZV8zMi5oICAgICAgICAg
IHwgIDIgKy0NCj4gICBhcmNoL3NwYXJjL2luY2x1ZGUvYXNtL3BndGFibGVfNjQuaCAgICAgICAg
ICB8ICA2ICsrKy0tLQ0KPiAgIGFyY2gvdW0vaW5jbHVkZS9hc20vcGd0YWJsZS5oICAgICAgICAg
ICAgICAgIHwgIDIgKy0NCj4gICBhcmNoL3g4Ni9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggICAgICAg
ICAgICAgICB8ICA2ICsrKystLQ0KPiAgIGFyY2gveHRlbnNhL2luY2x1ZGUvYXNtL3BndGFibGUu
aCAgICAgICAgICAgIHwgIDIgKy0NCj4gICBpbmNsdWRlL2FzbS1nZW5lcmljL2h1Z2V0bGIuaCAg
ICAgICAgICAgICAgICB8ICA0ICsrLS0NCj4gICBpbmNsdWRlL2xpbnV4L21tLmggICAgICAgICAg
ICAgICAgICAgICAgICAgICB8ICAyICstDQo+ICAgbW0vZGVidWdfdm1fcGd0YWJsZS5jICAgICAg
ICAgICAgICAgICAgICAgICAgfCAxNiArKysrKysrKy0tLS0tLS0tDQo+ICAgbW0vaHVnZV9tZW1v
cnkuYyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfCAgNiArKystLS0NCj4gICBtbS9odWdl
dGxiLmMgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB8ICA0ICsrLS0NCj4gICBtbS9t
ZW1vcnkuYyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICB8ICA0ICsrLS0NCj4gICBt
bS9taWdyYXRlX2RldmljZS5jICAgICAgICAgICAgICAgICAgICAgICAgICB8ICAyICstDQo+ICAg
bW0vbXByb3RlY3QuYyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfCAgMiArLQ0KPiAg
IG1tL3VzZXJmYXVsdGZkLmMgICAgICAgICAgICAgICAgICAgICAgICAgICAgIHwgIDIgKy0NCj4g
ICA0MiBmaWxlcyBjaGFuZ2VkLCAxMDYgaW5zZXJ0aW9ucygrKSwgNjkgZGVsZXRpb25zKC0pDQo+
IA0KPiBkaWZmIC0tZ2l0IGEvRG9jdW1lbnRhdGlvbi9tbS9hcmNoX3BndGFibGVfaGVscGVycy5y
c3QgYi9Eb2N1bWVudGF0aW9uL21tL2FyY2hfcGd0YWJsZV9oZWxwZXJzLnJzdA0KPiBpbmRleCAz
MGQ5YTA5ZjAxZjQuLjc4YWMzZmYyZmUxZCAxMDA2NDQNCj4gLS0tIGEvRG9jdW1lbnRhdGlvbi9t
bS9hcmNoX3BndGFibGVfaGVscGVycy5yc3QNCj4gKysrIGIvRG9jdW1lbnRhdGlvbi9tbS9hcmNo
X3BndGFibGVfaGVscGVycy5yc3QNCj4gQEAgLTQ2LDcgKzQ2LDggQEAgUFRFIFBhZ2UgVGFibGUg
SGVscGVycw0KPiAgICstLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rDQo+ICAgfCBwdGVfbWtjbGVhbiAg
ICAgICAgICAgICAgIHwgQ3JlYXRlcyBhIGNsZWFuIFBURSAgICAgICAgICAgICAgICAgICAgICAg
ICAgICAgIHwNCj4gICArLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKw0KPiAtfCBwdGVfbWt3cml0ZSAg
ICAgICAgICAgICAgIHwgQ3JlYXRlcyBhIHdyaXRhYmxlIFBURSAgICAgICAgICAgICAgICAgICAg
ICAgICAgIHwNCj4gK3wgcHRlX21rd3JpdGUgICAgICAgICAgICAgICB8IENyZWF0ZXMgYSB3cml0
YWJsZSBQVEUgb2YgdGhlIHR5cGUgc3BlY2lmaWVkIGJ5ICB8DQo+ICt8ICAgICAgICAgICAgICAg
ICAgICAgICAgICAgfCB0aGUgVk1BLiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAg
ICAgICAgfA0KPiAgICstLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rDQo+ICAgfCBwdGVfd3Jwcm90ZWN0
ICAgICAgICAgICAgIHwgQ3JlYXRlcyBhIHdyaXRlIHByb3RlY3RlZCBQVEUgICAgICAgICAgICAg
ICAgICAgIHwNCj4gICArLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKw0KPiBAQCAtMTE4LDcgKzExOSw4
IEBAIFBNRCBQYWdlIFRhYmxlIEhlbHBlcnMNCj4gICArLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKw0K
PiAgIHwgcG1kX21rY2xlYW4gICAgICAgICAgICAgICB8IENyZWF0ZXMgYSBjbGVhbiBQTUQgICAg
ICAgICAgICAgICAgICAgICAgICAgICAgICB8DQo+ICAgKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tLSstLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSsN
Cj4gLXwgcG1kX21rd3JpdGUgICAgICAgICAgICAgICB8IENyZWF0ZXMgYSB3cml0YWJsZSBQTUQg
ICAgICAgICAgICAgICAgICAgICAgICAgICB8DQo+ICt8IHBtZF9ta3dyaXRlICAgICAgICAgICAg
ICAgfCBDcmVhdGVzIGEgd3JpdGFibGUgUE1EIG9mIHRoZSB0eXBlIHNwZWNpZmllZCBieSAgfA0K
PiArfCAgICAgICAgICAgICAgICAgICAgICAgICAgIHwgdGhlIFZNQS4gICAgICAgICAgICAgICAg
ICAgICAgICAgICAgICAgICAgICAgICAgIHwNCj4gICArLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKw0K
PiAgIHwgcG1kX3dycHJvdGVjdCAgICAgICAgICAgICB8IENyZWF0ZXMgYSB3cml0ZSBwcm90ZWN0
ZWQgUE1EICAgICAgICAgICAgICAgICAgICB8DQo+ICAgKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tLSstLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLSsN
Cj4gQEAgLTIyMiw3ICsyMjQsOCBAQCBIdWdlVExCIFBhZ2UgVGFibGUgSGVscGVycw0KPiAgICst
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0rDQo+ICAgfCBodWdlX3B0ZV9ta2RpcnR5ICAgICAgICAgIHwg
Q3JlYXRlcyBhIGRpcnR5IEh1Z2VUTEIgICAgICAgICAgICAgICAgICAgICAgICAgIHwNCj4gICAr
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0tKw0KPiAtfCBodWdlX3B0ZV9ta3dyaXRlICAgICAgICAgIHwg
Q3JlYXRlcyBhIHdyaXRhYmxlIEh1Z2VUTEIgICAgICAgICAgICAgICAgICAgICAgIHwNCj4gK3wg
aHVnZV9wdGVfbWt3cml0ZSAgICAgICAgICB8IENyZWF0ZXMgYSB3cml0YWJsZSBIdWdlVExCIG9m
IHRoZSB0eXBlIHNwZWNpZmllZCB8DQo+ICt8ICAgICAgICAgICAgICAgICAgICAgICAgICAgfCBi
eSB0aGUgVk1BLiAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgfA0KPiAgICst
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0rLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0rDQo+ICAgfCBodWdlX3B0ZV93cnByb3RlY3QgICAgICAgIHwg
Q3JlYXRlcyBhIHdyaXRlIHByb3RlY3RlZCBIdWdlVExCICAgICAgICAgICAgICAgIHwNCj4gICAr
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tKy0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0tKw0KPiBkaWZmIC0tZ2l0IGEvYXJjaC9hbHBoYS9pbmNsdWRl
L2FzbS9wZ3RhYmxlLmggYi9hcmNoL2FscGhhL2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBpbmRl
eCBiYTQzY2I4NDFkMTkuLmZiNWQyMDdjMmE4OSAxMDA2NDQNCj4gLS0tIGEvYXJjaC9hbHBoYS9p
bmNsdWRlL2FzbS9wZ3RhYmxlLmgNCj4gKysrIGIvYXJjaC9hbHBoYS9pbmNsdWRlL2FzbS9wZ3Rh
YmxlLmgNCj4gQEAgLTI1Niw5ICsyNTYsMTMgQEAgZXh0ZXJuIGlubGluZSBpbnQgcHRlX3lvdW5n
KHB0ZV90IHB0ZSkJCXsgcmV0dXJuIHB0ZV92YWwocHRlKSAmIF9QQUdFX0FDQ0VTU0VEOw0KPiAg
IGV4dGVybiBpbmxpbmUgcHRlX3QgcHRlX3dycHJvdGVjdChwdGVfdCBwdGUpCXsgcHRlX3ZhbChw
dGUpIHw9IF9QQUdFX0ZPVzsgcmV0dXJuIHB0ZTsgfQ0KPiAgIGV4dGVybiBpbmxpbmUgcHRlX3Qg
cHRlX21rY2xlYW4ocHRlX3QgcHRlKQl7IHB0ZV92YWwocHRlKSAmPSB+KF9fRElSVFlfQklUUyk7
IHJldHVybiBwdGU7IH0NCj4gICBleHRlcm4gaW5saW5lIHB0ZV90IHB0ZV9ta29sZChwdGVfdCBw
dGUpCXsgcHRlX3ZhbChwdGUpICY9IH4oX19BQ0NFU1NfQklUUyk7IHJldHVybiBwdGU7IH0NCj4g
LWV4dGVybiBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlKQl7IHB0ZV92YWwocHRl
KSAmPSB+X1BBR0VfRk9XOyByZXR1cm4gcHRlOyB9DQo+ICAgZXh0ZXJuIGlubGluZSBwdGVfdCBw
dGVfbWtkaXJ0eShwdGVfdCBwdGUpCXsgcHRlX3ZhbChwdGUpIHw9IF9fRElSVFlfQklUUzsgcmV0
dXJuIHB0ZTsgfQ0KPiAgIGV4dGVybiBpbmxpbmUgcHRlX3QgcHRlX21reW91bmcocHRlX3QgcHRl
KQl7IHB0ZV92YWwocHRlKSB8PSBfX0FDQ0VTU19CSVRTOyByZXR1cm4gcHRlOyB9DQo+ICtleHRl
cm4gaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3Ry
dWN0ICp2bWEpDQo+ICt7DQo+ICsJcHRlX3ZhbChwdGUpICY9IH5fUEFHRV9GT1c7DQo+ICsJcmV0
dXJuIHB0ZTsNCj4gK30NCj4gICANCj4gICAvKg0KPiAgICAqIFRoZSBzbXBfcm1iKCkgaW4gdGhl
IGZvbGxvd2luZyBmdW5jdGlvbnMgYXJlIHJlcXVpcmVkIHRvIG9yZGVyIHRoZSBsb2FkIG9mDQo+
IGRpZmYgLS1naXQgYS9hcmNoL2FyYy9pbmNsdWRlL2FzbS9odWdlcGFnZS5oIGIvYXJjaC9hcmMv
aW5jbHVkZS9hc20vaHVnZXBhZ2UuaA0KPiBpbmRleCA1MDAxYjc5NmZiOGQuLjIyM2E5Njk2NzE4
OCAxMDA2NDQNCj4gLS0tIGEvYXJjaC9hcmMvaW5jbHVkZS9hc20vaHVnZXBhZ2UuaA0KPiArKysg
Yi9hcmNoL2FyYy9pbmNsdWRlL2FzbS9odWdlcGFnZS5oDQo+IEBAIC0yMSw3ICsyMSw3IEBAIHN0
YXRpYyBpbmxpbmUgcG1kX3QgcHRlX3BtZChwdGVfdCBwdGUpDQo+ICAgfQ0KPiAgIA0KPiAgICNk
ZWZpbmUgcG1kX3dycHJvdGVjdChwbWQpCXB0ZV9wbWQocHRlX3dycHJvdGVjdChwbWRfcHRlKHBt
ZCkpKQ0KPiAtI2RlZmluZSBwbWRfbWt3cml0ZShwbWQpCXB0ZV9wbWQocHRlX21rd3JpdGUocG1k
X3B0ZShwbWQpKSkNCj4gKyNkZWZpbmUgcG1kX21rd3JpdGUocG1kLCB2bWEpCXB0ZV9wbWQocHRl
X21rd3JpdGUocG1kX3B0ZShwbWQpLCAodm1hKSkpDQo+ICAgI2RlZmluZSBwbWRfbWtkaXJ0eShw
bWQpCXB0ZV9wbWQocHRlX21rZGlydHkocG1kX3B0ZShwbWQpKSkNCj4gICAjZGVmaW5lIHBtZF9t
a29sZChwbWQpCQlwdGVfcG1kKHB0ZV9ta29sZChwbWRfcHRlKHBtZCkpKQ0KPiAgICNkZWZpbmUg
cG1kX21reW91bmcocG1kKQlwdGVfcG1kKHB0ZV9ta3lvdW5nKHBtZF9wdGUocG1kKSkpDQo+IGRp
ZmYgLS1naXQgYS9hcmNoL2FyYy9pbmNsdWRlL2FzbS9wZ3RhYmxlLWJpdHMtYXJjdjIuaCBiL2Fy
Y2gvYXJjL2luY2x1ZGUvYXNtL3BndGFibGUtYml0cy1hcmN2Mi5oDQo+IGluZGV4IDZlOWY4Y2E2
ZDZhMS4uYTViOGJjOTU1MDE1IDEwMDY0NA0KPiAtLS0gYS9hcmNoL2FyYy9pbmNsdWRlL2FzbS9w
Z3RhYmxlLWJpdHMtYXJjdjIuaA0KPiArKysgYi9hcmNoL2FyYy9pbmNsdWRlL2FzbS9wZ3RhYmxl
LWJpdHMtYXJjdjIuaA0KPiBAQCAtODcsNyArODcsNiBAQA0KPiAgIA0KPiAgIFBURV9CSVRfRlVO
Qyhta25vdHByZXNlbnQsICAgICAmPSB+KF9QQUdFX1BSRVNFTlQpKTsNCj4gICBQVEVfQklUX0ZV
TkMod3Jwcm90ZWN0LAkmPSB+KF9QQUdFX1dSSVRFKSk7DQo+IC1QVEVfQklUX0ZVTkMobWt3cml0
ZSwJfD0gKF9QQUdFX1dSSVRFKSk7DQo+ICAgUFRFX0JJVF9GVU5DKG1rY2xlYW4sCSY9IH4oX1BB
R0VfRElSVFkpKTsNCj4gICBQVEVfQklUX0ZVTkMobWtkaXJ0eSwJfD0gKF9QQUdFX0RJUlRZKSk7
DQo+ICAgUFRFX0JJVF9GVU5DKG1rb2xkLAkmPSB+KF9QQUdFX0FDQ0VTU0VEKSk7DQo+IEBAIC05
NSw2ICs5NCwxMiBAQCBQVEVfQklUX0ZVTkMobWt5b3VuZywJfD0gKF9QQUdFX0FDQ0VTU0VEKSk7
DQo+ICAgUFRFX0JJVF9GVU5DKG1rc3BlY2lhbCwJfD0gKF9QQUdFX1NQRUNJQUwpKTsNCj4gICBQ
VEVfQklUX0ZVTkMobWtodWdlLAl8PSAoX1BBR0VfSFdfU1opKTsNCj4gICANCj4gK3N0YXRpYyBp
bmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlLCBzdHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3Qg
KnZtYSkNCj4gK3sNCj4gKwlwdGVfdmFsKHB0ZSkgfD0gKF9QQUdFX1dSSVRFKTsNCj4gKwlyZXR1
cm4gcHRlOw0KPiArfQ0KPiArDQo+ICAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbW9kaWZ5KHB0
ZV90IHB0ZSwgcGdwcm90X3QgbmV3cHJvdCkNCj4gICB7DQo+ICAgCXJldHVybiBfX3B0ZSgocHRl
X3ZhbChwdGUpICYgX1BBR0VfQ0hHX01BU0spIHwgcGdwcm90X3ZhbChuZXdwcm90KSk7DQo+IGRp
ZmYgLS1naXQgYS9hcmNoL2FybS9pbmNsdWRlL2FzbS9wZ3RhYmxlLTNsZXZlbC5oIGIvYXJjaC9h
cm0vaW5jbHVkZS9hc20vcGd0YWJsZS0zbGV2ZWwuaA0KPiBpbmRleCAxMDYwNDk3OTE1MDAuLmRm
MDcxYTgwNzYxMCAxMDA2NDQNCj4gLS0tIGEvYXJjaC9hcm0vaW5jbHVkZS9hc20vcGd0YWJsZS0z
bGV2ZWwuaA0KPiArKysgYi9hcmNoL2FybS9pbmNsdWRlL2FzbS9wZ3RhYmxlLTNsZXZlbC5oDQo+
IEBAIC0yMDIsMTEgKzIwMiwxNiBAQCBzdGF0aWMgaW5saW5lIHBtZF90IHBtZF8jI2ZuKHBtZF90
IHBtZCkgeyBwbWRfdmFsKHBtZCkgb3A7IHJldHVybiBwbWQ7IH0NCj4gICANCj4gICBQTURfQklU
X0ZVTkMod3Jwcm90ZWN0LAl8PSBMX1BNRF9TRUNUX1JET05MWSk7DQo+ICAgUE1EX0JJVF9GVU5D
KG1rb2xkLAkmPSB+UE1EX1NFQ1RfQUYpOw0KPiAtUE1EX0JJVF9GVU5DKG1rd3JpdGUsICAgJj0g
fkxfUE1EX1NFQ1RfUkRPTkxZKTsNCj4gICBQTURfQklUX0ZVTkMobWtkaXJ0eSwgICB8PSBMX1BN
RF9TRUNUX0RJUlRZKTsNCj4gICBQTURfQklUX0ZVTkMobWtjbGVhbiwgICAmPSB+TF9QTURfU0VD
VF9ESVJUWSk7DQo+ICAgUE1EX0JJVF9GVU5DKG1reW91bmcsICAgfD0gUE1EX1NFQ1RfQUYpOw0K
PiAgIA0KPiArc3RhdGljIGlubGluZSBwbWRfdCBwbWRfbWt3cml0ZShwbWRfdCBwbWQsIHN0cnVj
dCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiArew0KPiArCXBtZF92YWwocG1kKSB8PSBMX1BNRF9T
RUNUX1JET05MWTsNCj4gKwlyZXR1cm4gcG1kOw0KPiArfQ0KPiArDQo+ICAgI2RlZmluZSBwbWRf
bWtodWdlKHBtZCkJCShfX3BtZChwbWRfdmFsKHBtZCkgJiB+UE1EX1RBQkxFX0JJVCkpDQo+ICAg
DQo+ICAgI2RlZmluZSBwbWRfcGZuKHBtZCkJCSgoKHBtZF92YWwocG1kKSAmIFBNRF9NQVNLKSAm
IFBIWVNfTUFTSykgPj4gUEFHRV9TSElGVCkNCj4gZGlmZiAtLWdpdCBhL2FyY2gvYXJtL2luY2x1
ZGUvYXNtL3BndGFibGUuaCBiL2FyY2gvYXJtL2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBpbmRl
eCBhNThjY2JiNDA2YWQuLjM5YWQxYWUxMzA4ZCAxMDA2NDQNCj4gLS0tIGEvYXJjaC9hcm0vaW5j
bHVkZS9hc20vcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvYXJtL2luY2x1ZGUvYXNtL3BndGFibGUu
aA0KPiBAQCAtMjI3LDcgKzIyNyw3IEBAIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX3dycHJvdGVj
dChwdGVfdCBwdGUpDQo+ICAgCXJldHVybiBzZXRfcHRlX2JpdChwdGUsIF9fcGdwcm90KExfUFRF
X1JET05MWSkpOw0KPiAgIH0NCj4gICANCj4gLXN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3Jp
dGUocHRlX3QgcHRlKQ0KPiArc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBw
dGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4gICAJcmV0dXJuIGNsZWFy
X3B0ZV9iaXQocHRlLCBfX3BncHJvdChMX1BURV9SRE9OTFkpKTsNCj4gICB9DQo+IGRpZmYgLS1n
aXQgYS9hcmNoL2FybTY0L2luY2x1ZGUvYXNtL3BndGFibGUuaCBiL2FyY2gvYXJtNjQvaW5jbHVk
ZS9hc20vcGd0YWJsZS5oDQo+IGluZGV4IGNjY2Y4ODg1NzkyZS4uOTEzYmYzNzBmNzRhIDEwMDY0
NA0KPiAtLS0gYS9hcmNoL2FybTY0L2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiArKysgYi9hcmNo
L2FybTY0L2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBAQCAtMTg3LDcgKzE4Nyw3IEBAIHN0YXRp
YyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGVfa2VybmVsKHB0ZV90IHB0ZSkNCj4gICAJcmV0dXJu
IHB0ZTsNCj4gICB9DQo+ICAgDQo+IC1zdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0
ZV90IHB0ZSkNCj4gK3N0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlLCBz
dHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3QgKnZtYSkNCj4gICB7DQo+ICAgCXJldHVybiBwdGVfbWt3cml0
ZV9rZXJuZWwocHRlKTsNCj4gICB9DQo+IEBAIC00OTIsNyArNDkyLDcgQEAgc3RhdGljIGlubGlu
ZSBpbnQgcG1kX3RyYW5zX2h1Z2UocG1kX3QgcG1kKQ0KPiAgICNkZWZpbmUgcG1kX2NvbnQocG1k
KQkJcHRlX2NvbnQocG1kX3B0ZShwbWQpKQ0KPiAgICNkZWZpbmUgcG1kX3dycHJvdGVjdChwbWQp
CXB0ZV9wbWQocHRlX3dycHJvdGVjdChwbWRfcHRlKHBtZCkpKQ0KPiAgICNkZWZpbmUgcG1kX21r
b2xkKHBtZCkJCXB0ZV9wbWQocHRlX21rb2xkKHBtZF9wdGUocG1kKSkpDQo+IC0jZGVmaW5lIHBt
ZF9ta3dyaXRlKHBtZCkJcHRlX3BtZChwdGVfbWt3cml0ZShwbWRfcHRlKHBtZCkpKQ0KPiArI2Rl
ZmluZSBwbWRfbWt3cml0ZShwbWQsIHZtYSkJcHRlX3BtZChwdGVfbWt3cml0ZShwbWRfcHRlKHBt
ZCksICh2bWEpKSkNCj4gICAjZGVmaW5lIHBtZF9ta2NsZWFuKHBtZCkJcHRlX3BtZChwdGVfbWtj
bGVhbihwbWRfcHRlKHBtZCkpKQ0KPiAgICNkZWZpbmUgcG1kX21rZGlydHkocG1kKQlwdGVfcG1k
KHB0ZV9ta2RpcnR5KHBtZF9wdGUocG1kKSkpDQo+ICAgI2RlZmluZSBwbWRfbWt5b3VuZyhwbWQp
CXB0ZV9wbWQocHRlX21reW91bmcocG1kX3B0ZShwbWQpKSkNCj4gZGlmZiAtLWdpdCBhL2FyY2gv
Y3NreS9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggYi9hcmNoL2Nza3kvaW5jbHVkZS9hc20vcGd0YWJs
ZS5oDQo+IGluZGV4IGQ0MDQyNDk1ZmViYy4uYzJmOTJjOTkxZTM3IDEwMDY0NA0KPiAtLS0gYS9h
cmNoL2Nza3kvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvY3NreS9pbmNsdWRl
L2FzbS9wZ3RhYmxlLmgNCj4gQEAgLTE3Niw3ICsxNzYsNyBAQCBzdGF0aWMgaW5saW5lIHB0ZV90
IHB0ZV9ta29sZChwdGVfdCBwdGUpDQo+ICAgCXJldHVybiBwdGU7DQo+ICAgfQ0KPiAgIA0KPiAt
c3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUpDQo+ICtzdGF0aWMgaW5s
aW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2
bWEpDQo+ICAgew0KPiAgIAlwdGVfdmFsKHB0ZSkgfD0gX1BBR0VfV1JJVEU7DQo+ICAgCWlmIChw
dGVfdmFsKHB0ZSkgJiBfUEFHRV9NT0RJRklFRCkNCj4gZGlmZiAtLWdpdCBhL2FyY2gvaGV4YWdv
bi9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggYi9hcmNoL2hleGFnb24vaW5jbHVkZS9hc20vcGd0YWJs
ZS5oDQo+IGluZGV4IDU5MzkzNjEzZDA4Ni4uMTRhYjljNzg5YzBlIDEwMDY0NA0KPiAtLS0gYS9h
cmNoL2hleGFnb24vaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvaGV4YWdvbi9p
bmNsdWRlL2FzbS9wZ3RhYmxlLmgNCj4gQEAgLTMwMCw3ICszMDAsNyBAQCBzdGF0aWMgaW5saW5l
IHB0ZV90IHB0ZV93cnByb3RlY3QocHRlX3QgcHRlKQ0KPiAgIH0NCj4gICANCj4gICAvKiBwdGVf
bWt3cml0ZSAtIG1hcmsgcGFnZSBhcyB3cml0YWJsZSAqLw0KPiAtc3RhdGljIGlubGluZSBwdGVf
dCBwdGVfbWt3cml0ZShwdGVfdCBwdGUpDQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dy
aXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgew0KPiAgIAlw
dGVfdmFsKHB0ZSkgfD0gX1BBR0VfV1JJVEU7DQo+ICAgCXJldHVybiBwdGU7DQo+IGRpZmYgLS1n
aXQgYS9hcmNoL2lhNjQvaW5jbHVkZS9hc20vcGd0YWJsZS5oIGIvYXJjaC9pYTY0L2luY2x1ZGUv
YXNtL3BndGFibGUuaA0KPiBpbmRleCAyMWM5N2UzMWEyOGEuLmY4NzlkZDYyNmRhNiAxMDA2NDQN
Cj4gLS0tIGEvYXJjaC9pYTY0L2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiArKysgYi9hcmNoL2lh
NjQvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+IEBAIC0yNjgsNyArMjY4LDcgQEAgaWE2NF9waHlz
X2FkZHJfdmFsaWQgKHVuc2lnbmVkIGxvbmcgYWRkcikNCj4gICAgKiBhY2Nlc3MgcmlnaHRzOg0K
PiAgICAqLw0KPiAgICNkZWZpbmUgcHRlX3dycHJvdGVjdChwdGUpCShfX3B0ZShwdGVfdmFsKHB0
ZSkgJiB+X1BBR0VfQVJfUlcpKQ0KPiAtI2RlZmluZSBwdGVfbWt3cml0ZShwdGUpCShfX3B0ZShw
dGVfdmFsKHB0ZSkgfCBfUEFHRV9BUl9SVykpDQo+ICsjZGVmaW5lIHB0ZV9ta3dyaXRlKHB0ZSwg
dm1hKQkoX19wdGUocHRlX3ZhbChwdGUpIHwgX1BBR0VfQVJfUlcpKQ0KPiAgICNkZWZpbmUgcHRl
X21rb2xkKHB0ZSkJCShfX3B0ZShwdGVfdmFsKHB0ZSkgJiB+X1BBR0VfQSkpDQo+ICAgI2RlZmlu
ZSBwdGVfbWt5b3VuZyhwdGUpCShfX3B0ZShwdGVfdmFsKHB0ZSkgfCBfUEFHRV9BKSkNCj4gICAj
ZGVmaW5lIHB0ZV9ta2NsZWFuKHB0ZSkJKF9fcHRlKHB0ZV92YWwocHRlKSAmIH5fUEFHRV9EKSkN
Cj4gZGlmZiAtLWdpdCBhL2FyY2gvbG9vbmdhcmNoL2luY2x1ZGUvYXNtL3BndGFibGUuaCBiL2Fy
Y2gvbG9vbmdhcmNoL2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBpbmRleCBkMjhmYjlkYmVjNTku
LmViZjY0NWY0MDI5OCAxMDA2NDQNCj4gLS0tIGEvYXJjaC9sb29uZ2FyY2gvaW5jbHVkZS9hc20v
cGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvbG9vbmdhcmNoL2luY2x1ZGUvYXNtL3BndGFibGUuaA0K
PiBAQCAtMzkwLDcgKzM5MCw3IEBAIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rZGlydHkocHRl
X3QgcHRlKQ0KPiAgIAlyZXR1cm4gcHRlOw0KPiAgIH0NCj4gICANCj4gLXN0YXRpYyBpbmxpbmUg
cHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RhdGljIGlubGluZSBwdGVfdCBwdGVf
bWt3cml0ZShwdGVfdCBwdGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4g
ICAJcHRlX3ZhbChwdGUpIHw9IF9QQUdFX1dSSVRFOw0KPiAgIAlpZiAocHRlX3ZhbChwdGUpICYg
X1BBR0VfTU9ESUZJRUQpDQo+IEBAIC00OTAsNyArNDkwLDcgQEAgc3RhdGljIGlubGluZSBpbnQg
cG1kX3dyaXRlKHBtZF90IHBtZCkNCj4gICAJcmV0dXJuICEhKHBtZF92YWwocG1kKSAmIF9QQUdF
X1dSSVRFKTsNCj4gICB9DQo+ICAgDQo+IC1zdGF0aWMgaW5saW5lIHBtZF90IHBtZF9ta3dyaXRl
KHBtZF90IHBtZCkNCj4gK3N0YXRpYyBpbmxpbmUgcG1kX3QgcG1kX21rd3JpdGUocG1kX3QgcG1k
LCBzdHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3QgKnZtYSkNCj4gICB7DQo+ICAgCXBtZF92YWwocG1kKSB8
PSBfUEFHRV9XUklURTsNCj4gICAJaWYgKHBtZF92YWwocG1kKSAmIF9QQUdFX01PRElGSUVEKQ0K
PiBkaWZmIC0tZ2l0IGEvYXJjaC9tNjhrL2luY2x1ZGUvYXNtL21jZl9wZ3RhYmxlLmggYi9hcmNo
L202OGsvaW5jbHVkZS9hc20vbWNmX3BndGFibGUuaA0KPiBpbmRleCAxMzc0MWMxMjQ1ZTEuLjM3
ZDc3ZTA1NTAxNiAxMDA2NDQNCj4gLS0tIGEvYXJjaC9tNjhrL2luY2x1ZGUvYXNtL21jZl9wZ3Rh
YmxlLmgNCj4gKysrIGIvYXJjaC9tNjhrL2luY2x1ZGUvYXNtL21jZl9wZ3RhYmxlLmgNCj4gQEAg
LTIxMSw3ICsyMTEsNyBAQCBzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta29sZChwdGVfdCBwdGUp
DQo+ICAgCXJldHVybiBwdGU7DQo+ICAgfQ0KPiAgIA0KPiAtc3RhdGljIGlubGluZSBwdGVfdCBw
dGVfbWt3cml0ZShwdGVfdCBwdGUpDQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRl
KHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgew0KPiAgIAlwdGVf
dmFsKHB0ZSkgfD0gQ0ZfUEFHRV9XUklUQUJMRTsNCj4gICAJcmV0dXJuIHB0ZTsNCj4gZGlmZiAt
LWdpdCBhL2FyY2gvbTY4ay9pbmNsdWRlL2FzbS9tb3Rvcm9sYV9wZ3RhYmxlLmggYi9hcmNoL202
OGsvaW5jbHVkZS9hc20vbW90b3JvbGFfcGd0YWJsZS5oDQo+IGluZGV4IGVjMGRjMTlhYjgzNC4u
YzRlOGViNzYyODZkIDEwMDY0NA0KPiAtLS0gYS9hcmNoL202OGsvaW5jbHVkZS9hc20vbW90b3Jv
bGFfcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvbTY4ay9pbmNsdWRlL2FzbS9tb3Rvcm9sYV9wZ3Rh
YmxlLmgNCj4gQEAgLTE1NSw3ICsxNTUsNiBAQCBzdGF0aWMgaW5saW5lIGludCBwdGVfeW91bmco
cHRlX3QgcHRlKQkJeyByZXR1cm4gcHRlX3ZhbChwdGUpICYgX1BBR0VfQUNDRVNTRUQ7DQo+ICAg
c3RhdGljIGlubGluZSBwdGVfdCBwdGVfd3Jwcm90ZWN0KHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0
ZSkgfD0gX1BBR0VfUk9OTFk7IHJldHVybiBwdGU7IH0NCj4gICBzdGF0aWMgaW5saW5lIHB0ZV90
IHB0ZV9ta2NsZWFuKHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgJj0gfl9QQUdFX0RJUlRZOyBy
ZXR1cm4gcHRlOyB9DQo+ICAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWtvbGQocHRlX3QgcHRl
KQl7IHB0ZV92YWwocHRlKSAmPSB+X1BBR0VfQUNDRVNTRUQ7IHJldHVybiBwdGU7IH0NCj4gLXN0
YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlKQl7IHB0ZV92YWwocHRlKSAm
PSB+X1BBR0VfUk9OTFk7IHJldHVybiBwdGU7IH0NCj4gICBzdGF0aWMgaW5saW5lIHB0ZV90IHB0
ZV9ta2RpcnR5KHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgfD0gX1BBR0VfRElSVFk7IHJldHVy
biBwdGU7IH0NCj4gICBzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3lvdW5nKHB0ZV90IHB0ZSkJ
eyBwdGVfdmFsKHB0ZSkgfD0gX1BBR0VfQUNDRVNTRUQ7IHJldHVybiBwdGU7IH0NCj4gICBzdGF0
aWMgaW5saW5lIHB0ZV90IHB0ZV9ta25vY2FjaGUocHRlX3QgcHRlKQ0KPiBAQCAtMTY4LDYgKzE2
NywxMSBAQCBzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta2NhY2hlKHB0ZV90IHB0ZSkNCj4gICAJ
cHRlX3ZhbChwdGUpID0gKHB0ZV92YWwocHRlKSAmIF9DQUNIRU1BU0swNDApIHwgbTY4a19zdXBl
cnZpc29yX2NhY2hlbW9kZTsNCj4gICAJcmV0dXJuIHB0ZTsNCj4gICB9DQo+ICtzdGF0aWMgaW5s
aW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2
bWEpDQo+ICt7DQo+ICsJcHRlX3ZhbChwdGUpICY9IH5fUEFHRV9ST05MWTsNCj4gKwlyZXR1cm4g
cHRlOw0KPiArfQ0KPiAgIA0KPiAgICNkZWZpbmUgc3dhcHBlcl9wZ19kaXIga2VybmVsX3BnX2Rp
cg0KPiAgIGV4dGVybiBwZ2RfdCBrZXJuZWxfcGdfZGlyWzEyOF07DQo+IGRpZmYgLS1naXQgYS9h
cmNoL202OGsvaW5jbHVkZS9hc20vc3VuM19wZ3RhYmxlLmggYi9hcmNoL202OGsvaW5jbHVkZS9h
c20vc3VuM19wZ3RhYmxlLmgNCj4gaW5kZXggZTU4MmIwNDg0YTU1Li4yYTA2YmVhNTFhMWUgMTAw
NjQ0DQo+IC0tLSBhL2FyY2gvbTY4ay9pbmNsdWRlL2FzbS9zdW4zX3BndGFibGUuaA0KPiArKysg
Yi9hcmNoL202OGsvaW5jbHVkZS9hc20vc3VuM19wZ3RhYmxlLmgNCj4gQEAgLTE0MywxMCArMTQz
LDE0IEBAIHN0YXRpYyBpbmxpbmUgaW50IHB0ZV95b3VuZyhwdGVfdCBwdGUpCQl7IHJldHVybiBw
dGVfdmFsKHB0ZSkgJiBTVU4zX1BBR0VfQUNDRVNTDQo+ICAgc3RhdGljIGlubGluZSBwdGVfdCBw
dGVfd3Jwcm90ZWN0KHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgJj0gflNVTjNfUEFHRV9XUklU
RUFCTEU7IHJldHVybiBwdGU7IH0NCj4gICBzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta2NsZWFu
KHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgJj0gflNVTjNfUEFHRV9NT0RJRklFRDsgcmV0dXJu
IHB0ZTsgfQ0KPiAgIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rb2xkKHB0ZV90IHB0ZSkJeyBw
dGVfdmFsKHB0ZSkgJj0gflNVTjNfUEFHRV9BQ0NFU1NFRDsgcmV0dXJuIHB0ZTsgfQ0KPiAtc3Rh
dGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUpCXsgcHRlX3ZhbChwdGUpIHw9
IFNVTjNfUEFHRV9XUklURUFCTEU7IHJldHVybiBwdGU7IH0NCj4gICBzdGF0aWMgaW5saW5lIHB0
ZV90IHB0ZV9ta2RpcnR5KHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgfD0gU1VOM19QQUdFX01P
RElGSUVEOyByZXR1cm4gcHRlOyB9DQo+ICAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt5b3Vu
ZyhwdGVfdCBwdGUpCXsgcHRlX3ZhbChwdGUpIHw9IFNVTjNfUEFHRV9BQ0NFU1NFRDsgcmV0dXJu
IHB0ZTsgfQ0KPiAgIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rbm9jYWNoZShwdGVfdCBwdGUp
CXsgcHRlX3ZhbChwdGUpIHw9IFNVTjNfUEFHRV9OT0NBQ0hFOyByZXR1cm4gcHRlOyB9DQo+ICtz
dGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFf
c3RydWN0ICp2bWEpDQo+ICt7DQo+ICsJcHRlX3ZhbChwdGUpIHw9IFNVTjNfUEFHRV9XUklURUFC
TEU7DQo+ICsJcmV0dXJuIHB0ZTsNCj4gK30NCj4gICAvLyB1c2UgdGhpcyB2ZXJzaW9uIHdoZW4g
Y2FjaGVzIHdvcmsuLi4NCj4gICAvL3N0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rY2FjaGUocHRl
X3QgcHRlKQl7IHB0ZV92YWwocHRlKSAmPSBTVU4zX1BBR0VfTk9DQUNIRTsgcmV0dXJuIHB0ZTsg
fQ0KPiAgIC8vIHVudGlsIHRoZW4sIHVzZToNCj4gZGlmZiAtLWdpdCBhL2FyY2gvbWljcm9ibGF6
ZS9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggYi9hcmNoL21pY3JvYmxhemUvaW5jbHVkZS9hc20vcGd0
YWJsZS5oDQo+IGluZGV4IGQxYjgyNzJhYmNkOS4uNWI4M2U4MmY4ZDdlIDEwMDY0NA0KPiAtLS0g
YS9hcmNoL21pY3JvYmxhemUvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvbWlj
cm9ibGF6ZS9pbmNsdWRlL2FzbS9wZ3RhYmxlLmgNCj4gQEAgLTI2Niw3ICsyNjYsNyBAQCBzdGF0
aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3JlYWQocHRlX3QgcHRlKSBcDQo+ICAgCXsgcHRlX3ZhbChw
dGUpIHw9IF9QQUdFX1VTRVI7IHJldHVybiBwdGU7IH0NCj4gICBzdGF0aWMgaW5saW5lIHB0ZV90
IHB0ZV9ta2V4ZWMocHRlX3QgcHRlKSBcDQo+ICAgCXsgcHRlX3ZhbChwdGUpIHw9IF9QQUdFX1VT
RVIgfCBfUEFHRV9FWEVDOyByZXR1cm4gcHRlOyB9DQo+IC1zdGF0aWMgaW5saW5lIHB0ZV90IHB0
ZV9ta3dyaXRlKHB0ZV90IHB0ZSkgXA0KPiArc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0
ZShwdGVfdCBwdGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKSBcDQo+ICAgCXsgcHRlX3Zh
bChwdGUpIHw9IF9QQUdFX1JXOyByZXR1cm4gcHRlOyB9DQo+ICAgc3RhdGljIGlubGluZSBwdGVf
dCBwdGVfbWtkaXJ0eShwdGVfdCBwdGUpIFwNCj4gICAJeyBwdGVfdmFsKHB0ZSkgfD0gX1BBR0Vf
RElSVFk7IHJldHVybiBwdGU7IH0NCj4gZGlmZiAtLWdpdCBhL2FyY2gvbWlwcy9pbmNsdWRlL2Fz
bS9wZ3RhYmxlLmggYi9hcmNoL21pcHMvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+IGluZGV4IDc5
MTM4OWJmM2MxMi4uMDZlZmQ1NjcxNDRhIDEwMDY0NA0KPiAtLS0gYS9hcmNoL21pcHMvaW5jbHVk
ZS9hc20vcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvbWlwcy9pbmNsdWRlL2FzbS9wZ3RhYmxlLmgN
Cj4gQEAgLTMwOSw3ICszMDksNyBAQCBzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta29sZChwdGVf
dCBwdGUpDQo+ICAgCXJldHVybiBwdGU7DQo+ICAgfQ0KPiAgIA0KPiAtc3RhdGljIGlubGluZSBw
dGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUpDQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9t
a3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgew0KPiAg
IAlwdGUucHRlX2xvdyB8PSBfUEFHRV9XUklURTsNCj4gICAJaWYgKHB0ZS5wdGVfbG93ICYgX1BB
R0VfTU9ESUZJRUQpIHsNCj4gQEAgLTM2NCw3ICszNjQsNyBAQCBzdGF0aWMgaW5saW5lIHB0ZV90
IHB0ZV9ta29sZChwdGVfdCBwdGUpDQo+ICAgCXJldHVybiBwdGU7DQo+ICAgfQ0KPiAgIA0KPiAt
c3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUpDQo+ICtzdGF0aWMgaW5s
aW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2
bWEpDQo+ICAgew0KPiAgIAlwdGVfdmFsKHB0ZSkgfD0gX1BBR0VfV1JJVEU7DQo+ICAgCWlmIChw
dGVfdmFsKHB0ZSkgJiBfUEFHRV9NT0RJRklFRCkNCj4gQEAgLTYyNiw3ICs2MjYsNyBAQCBzdGF0
aWMgaW5saW5lIHBtZF90IHBtZF93cnByb3RlY3QocG1kX3QgcG1kKQ0KPiAgIAlyZXR1cm4gcG1k
Ow0KPiAgIH0NCj4gICANCj4gLXN0YXRpYyBpbmxpbmUgcG1kX3QgcG1kX21rd3JpdGUocG1kX3Qg
cG1kKQ0KPiArc3RhdGljIGlubGluZSBwbWRfdCBwbWRfbWt3cml0ZShwbWRfdCBwbWQsIHN0cnVj
dCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4gICAJcG1kX3ZhbChwbWQpIHw9IF9QQUdF
X1dSSVRFOw0KPiAgIAlpZiAocG1kX3ZhbChwbWQpICYgX1BBR0VfTU9ESUZJRUQpDQo+IGRpZmYg
LS1naXQgYS9hcmNoL25pb3MyL2luY2x1ZGUvYXNtL3BndGFibGUuaCBiL2FyY2gvbmlvczIvaW5j
bHVkZS9hc20vcGd0YWJsZS5oDQo+IGluZGV4IDBmNWMyNTY0ZTlmNS4uZWRkNDU4NTE4ZTBlIDEw
MDY0NA0KPiAtLS0gYS9hcmNoL25pb3MyL2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiArKysgYi9h
cmNoL25pb3MyL2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBAQCAtMTI5LDcgKzEyOSw3IEBAIHN0
YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rb2xkKHB0ZV90IHB0ZSkNCj4gICAJcmV0dXJuIHB0ZTsN
Cj4gICB9DQo+ICAgDQo+IC1zdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0
ZSkNCj4gK3N0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlLCBzdHJ1Y3Qg
dm1fYXJlYV9zdHJ1Y3QgKnZtYSkNCj4gICB7DQo+ICAgCXB0ZV92YWwocHRlKSB8PSBfUEFHRV9X
UklURTsNCj4gICAJcmV0dXJuIHB0ZTsNCj4gZGlmZiAtLWdpdCBhL2FyY2gvb3BlbnJpc2MvaW5j
bHVkZS9hc20vcGd0YWJsZS5oIGIvYXJjaC9vcGVucmlzYy9pbmNsdWRlL2FzbS9wZ3RhYmxlLmgN
Cj4gaW5kZXggM2ViOWI5NTU1ZDBkLi5mZDQwYWVjMTg5ZDEgMTAwNjQ0DQo+IC0tLSBhL2FyY2gv
b3BlbnJpc2MvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvb3BlbnJpc2MvaW5j
bHVkZS9hc20vcGd0YWJsZS5oDQo+IEBAIC0yNTAsNyArMjUwLDcgQEAgc3RhdGljIGlubGluZSBw
dGVfdCBwdGVfbWtvbGQocHRlX3QgcHRlKQ0KPiAgIAlyZXR1cm4gcHRlOw0KPiAgIH0NCj4gICAN
Cj4gLXN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RhdGlj
IGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVj
dCAqdm1hKQ0KPiAgIHsNCj4gICAJcHRlX3ZhbChwdGUpIHw9IF9QQUdFX1dSSVRFOw0KPiAgIAly
ZXR1cm4gcHRlOw0KPiBkaWZmIC0tZ2l0IGEvYXJjaC9wYXJpc2MvaW5jbHVkZS9hc20vcGd0YWJs
ZS5oIGIvYXJjaC9wYXJpc2MvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+IGluZGV4IGUyOTUwZjVk
YjdjOS4uODlmNjIxMzdlNjdmIDEwMDY0NA0KPiAtLS0gYS9hcmNoL3BhcmlzYy9pbmNsdWRlL2Fz
bS9wZ3RhYmxlLmgNCj4gKysrIGIvYXJjaC9wYXJpc2MvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+
IEBAIC0zMzEsOCArMzMxLDEyIEBAIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rb2xkKHB0ZV90
IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgJj0gfl9QQUdFX0FDQ0VTU0VEOyByZXR1DQo+ICAgc3RhdGlj
IGlubGluZSBwdGVfdCBwdGVfd3Jwcm90ZWN0KHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgJj0g
fl9QQUdFX1dSSVRFOyByZXR1cm4gcHRlOyB9DQo+ICAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVf
bWtkaXJ0eShwdGVfdCBwdGUpCXsgcHRlX3ZhbChwdGUpIHw9IF9QQUdFX0RJUlRZOyByZXR1cm4g
cHRlOyB9DQo+ICAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt5b3VuZyhwdGVfdCBwdGUpCXsg
cHRlX3ZhbChwdGUpIHw9IF9QQUdFX0FDQ0VTU0VEOyByZXR1cm4gcHRlOyB9DQo+IC1zdGF0aWMg
aW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSkJeyBwdGVfdmFsKHB0ZSkgfD0gX1BB
R0VfV1JJVEU7IHJldHVybiBwdGU7IH0NCj4gICBzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3Nw
ZWNpYWwocHRlX3QgcHRlKQl7IHB0ZV92YWwocHRlKSB8PSBfUEFHRV9TUEVDSUFMOyByZXR1cm4g
cHRlOyB9DQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3Ry
dWN0IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICt7DQo+ICsJcHRlX3ZhbChwdGUpIHw9IF9QQUdF
X1dSSVRFOw0KPiArCXJldHVybiBwdGU7DQo+ICt9DQo+ICAgDQo+ICAgLyoNCj4gICAgKiBIdWdl
IHB0ZSBkZWZpbml0aW9ucy4NCj4gZGlmZiAtLWdpdCBhL2FyY2gvcG93ZXJwYy9pbmNsdWRlL2Fz
bS9ib29rM3MvMzIvcGd0YWJsZS5oIGIvYXJjaC9wb3dlcnBjL2luY2x1ZGUvYXNtL2Jvb2szcy8z
Mi9wZ3RhYmxlLmgNCj4gaW5kZXggN2JmMWZlNzI5N2M2Li4xMGQ5YTFkMmFjYTkgMTAwNjQ0DQo+
IC0tLSBhL2FyY2gvcG93ZXJwYy9pbmNsdWRlL2FzbS9ib29rM3MvMzIvcGd0YWJsZS5oDQo+ICsr
KyBiL2FyY2gvcG93ZXJwYy9pbmNsdWRlL2FzbS9ib29rM3MvMzIvcGd0YWJsZS5oDQo+IEBAIC00
OTgsNyArNDk4LDcgQEAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWtwdGUocHRlX3QgcHRlKQ0K
PiAgIAlyZXR1cm4gcHRlOw0KPiAgIH0NCj4gICANCj4gLXN0YXRpYyBpbmxpbmUgcHRlX3QgcHRl
X21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShw
dGVfdCBwdGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4gICAJcmV0dXJu
IF9fcHRlKHB0ZV92YWwocHRlKSB8IF9QQUdFX1JXKTsNCj4gICB9DQo+IGRpZmYgLS1naXQgYS9h
cmNoL3Bvd2VycGMvaW5jbHVkZS9hc20vYm9vazNzLzY0L3BndGFibGUuaCBiL2FyY2gvcG93ZXJw
Yy9pbmNsdWRlL2FzbS9ib29rM3MvNjQvcGd0YWJsZS5oDQo+IGluZGV4IDRhY2M5NjkwZjU5OS4u
YmUwNjM2NTIyZDM2IDEwMDY0NA0KPiAtLS0gYS9hcmNoL3Bvd2VycGMvaW5jbHVkZS9hc20vYm9v
azNzLzY0L3BndGFibGUuaA0KPiArKysgYi9hcmNoL3Bvd2VycGMvaW5jbHVkZS9hc20vYm9vazNz
LzY0L3BndGFibGUuaA0KPiBAQCAtNjAwLDcgKzYwMCw3IEBAIHN0YXRpYyBpbmxpbmUgcHRlX3Qg
cHRlX21rZXhlYyhwdGVfdCBwdGUpDQo+ICAgCXJldHVybiBfX3B0ZV9yYXcocHRlX3JhdyhwdGUp
IHwgY3B1X3RvX2JlNjQoX1BBR0VfRVhFQykpOw0KPiAgIH0NCj4gICANCj4gLXN0YXRpYyBpbmxp
bmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RhdGljIGlubGluZSBwdGVfdCBw
dGVfbWt3cml0ZShwdGVfdCBwdGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsN
Cj4gICAJLyoNCj4gICAJICogd3JpdGUgaW1wbGllcyByZWFkLCBoZW5jZSBzZXQgYm90aA0KPiBA
QCAtMTA3MSw3ICsxMDcxLDcgQEAgc3RhdGljIGlubGluZSBwdGVfdCAqcG1kcF9wdGVwKHBtZF90
ICpwbWQpDQo+ICAgI2RlZmluZSBwbWRfbWtkaXJ0eShwbWQpCXB0ZV9wbWQocHRlX21rZGlydHko
cG1kX3B0ZShwbWQpKSkNCj4gICAjZGVmaW5lIHBtZF9ta2NsZWFuKHBtZCkJcHRlX3BtZChwdGVf
bWtjbGVhbihwbWRfcHRlKHBtZCkpKQ0KPiAgICNkZWZpbmUgcG1kX21reW91bmcocG1kKQlwdGVf
cG1kKHB0ZV9ta3lvdW5nKHBtZF9wdGUocG1kKSkpDQo+IC0jZGVmaW5lIHBtZF9ta3dyaXRlKHBt
ZCkJcHRlX3BtZChwdGVfbWt3cml0ZShwbWRfcHRlKHBtZCkpKQ0KPiArI2RlZmluZSBwbWRfbWt3
cml0ZShwbWQsIHZtYSkJcHRlX3BtZChwdGVfbWt3cml0ZShwbWRfcHRlKHBtZCksICh2bWEpKSkN
Cj4gICANCj4gICAjaWZkZWYgQ09ORklHX0hBVkVfQVJDSF9TT0ZUX0RJUlRZDQo+ICAgI2RlZmlu
ZSBwbWRfc29mdF9kaXJ0eShwbWQpICAgIHB0ZV9zb2Z0X2RpcnR5KHBtZF9wdGUocG1kKSkNCj4g
ZGlmZiAtLWdpdCBhL2FyY2gvcG93ZXJwYy9pbmNsdWRlL2FzbS9ub2hhc2gvMzIvcGd0YWJsZS5o
IGIvYXJjaC9wb3dlcnBjL2luY2x1ZGUvYXNtL25vaGFzaC8zMi9wZ3RhYmxlLmgNCj4gaW5kZXgg
ZmVjNTZkOTY1ZjAwLi43YmZiY2I5YmE1NWIgMTAwNjQ0DQo+IC0tLSBhL2FyY2gvcG93ZXJwYy9p
bmNsdWRlL2FzbS9ub2hhc2gvMzIvcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvcG93ZXJwYy9pbmNs
dWRlL2FzbS9ub2hhc2gvMzIvcGd0YWJsZS5oDQo+IEBAIC0xNzEsNyArMTcxLDcgQEAgdm9pZCB1
bm1hcF9rZXJuZWxfcGFnZSh1bnNpZ25lZCBsb25nIHZhKTsNCj4gICAJZG8geyBwdGVfdXBkYXRl
KG1tLCBhZGRyLCBwdGVwLCB+MCwgMCwgMCk7IH0gd2hpbGUgKDApDQo+ICAgDQo+ICAgI2lmbmRl
ZiBwdGVfbWt3cml0ZQ0KPiAtc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBw
dGUpDQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0
IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgew0KPiAgIAlyZXR1cm4gX19wdGUocHRlX3ZhbChw
dGUpIHwgX1BBR0VfUlcpOw0KPiAgIH0NCj4gZGlmZiAtLWdpdCBhL2FyY2gvcG93ZXJwYy9pbmNs
dWRlL2FzbS9ub2hhc2gvMzIvcHRlLTh4eC5oIGIvYXJjaC9wb3dlcnBjL2luY2x1ZGUvYXNtL25v
aGFzaC8zMi9wdGUtOHh4LmgNCj4gaW5kZXggMWE4OWViZGMzYWNjLi5mMzI0NTBlYjI3MGEgMTAw
NjQ0DQo+IC0tLSBhL2FyY2gvcG93ZXJwYy9pbmNsdWRlL2FzbS9ub2hhc2gvMzIvcHRlLTh4eC5o
DQo+ICsrKyBiL2FyY2gvcG93ZXJwYy9pbmNsdWRlL2FzbS9ub2hhc2gvMzIvcHRlLTh4eC5oDQo+
IEBAIC0xMDEsNyArMTAxLDcgQEAgc3RhdGljIGlubGluZSBpbnQgcHRlX3dyaXRlKHB0ZV90IHB0
ZSkNCj4gICANCj4gICAjZGVmaW5lIHB0ZV93cml0ZSBwdGVfd3JpdGUNCj4gICANCj4gLXN0YXRp
YyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RhdGljIGlubGluZSBw
dGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0K
PiAgIHsNCj4gICAJcmV0dXJuIF9fcHRlKHB0ZV92YWwocHRlKSAmIH5fUEFHRV9STyk7DQo+ICAg
fQ0KPiBkaWZmIC0tZ2l0IGEvYXJjaC9wb3dlcnBjL2luY2x1ZGUvYXNtL25vaGFzaC82NC9wZ3Rh
YmxlLmggYi9hcmNoL3Bvd2VycGMvaW5jbHVkZS9hc20vbm9oYXNoLzY0L3BndGFibGUuaA0KPiBp
bmRleCAyODdlMjU4NjRmZmEuLjU4OTAwOTU1NTg3NyAxMDA2NDQNCj4gLS0tIGEvYXJjaC9wb3dl
cnBjL2luY2x1ZGUvYXNtL25vaGFzaC82NC9wZ3RhYmxlLmgNCj4gKysrIGIvYXJjaC9wb3dlcnBj
L2luY2x1ZGUvYXNtL25vaGFzaC82NC9wZ3RhYmxlLmgNCj4gQEAgLTg1LDcgKzg1LDcgQEANCj4g
ICAjaWZuZGVmIF9fQVNTRU1CTFlfXw0KPiAgIC8qIHB0ZV9jbGVhciBtb3ZlZCB0byBsYXRlciBp
biB0aGlzIGZpbGUgKi8NCj4gICANCj4gLXN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUo
cHRlX3QgcHRlKQ0KPiArc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUs
IHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4gICAJcmV0dXJuIF9fcHRlKHB0
ZV92YWwocHRlKSB8IF9QQUdFX1JXKTsNCj4gICB9DQo+IGRpZmYgLS1naXQgYS9hcmNoL3Jpc2N2
L2luY2x1ZGUvYXNtL3BndGFibGUuaCBiL2FyY2gvcmlzY3YvaW5jbHVkZS9hc20vcGd0YWJsZS5o
DQo+IGluZGV4IGQ4ZDhkZTBkZWQ5OS4uZmVkMWI4MWZiZTA3IDEwMDY0NA0KPiAtLS0gYS9hcmNo
L3Jpc2N2L2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiArKysgYi9hcmNoL3Jpc2N2L2luY2x1ZGUv
YXNtL3BndGFibGUuaA0KPiBAQCAtMzM4LDcgKzMzOCw3IEBAIHN0YXRpYyBpbmxpbmUgcHRlX3Qg
cHRlX3dycHJvdGVjdChwdGVfdCBwdGUpDQo+ICAgDQo+ICAgLyogc3RhdGljIGlubGluZSBwdGVf
dCBwdGVfbWtyZWFkKHB0ZV90IHB0ZSkgKi8NCj4gICANCj4gLXN0YXRpYyBpbmxpbmUgcHRlX3Qg
cHRlX21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0
ZShwdGVfdCBwdGUsIHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4gICAJcmV0
dXJuIF9fcHRlKHB0ZV92YWwocHRlKSB8IF9QQUdFX1dSSVRFKTsNCj4gICB9DQo+IEBAIC02MjQs
OSArNjI0LDkgQEAgc3RhdGljIGlubGluZSBwbWRfdCBwbWRfbWt5b3VuZyhwbWRfdCBwbWQpDQo+
ICAgCXJldHVybiBwdGVfcG1kKHB0ZV9ta3lvdW5nKHBtZF9wdGUocG1kKSkpOw0KPiAgIH0NCj4g
ICANCj4gLXN0YXRpYyBpbmxpbmUgcG1kX3QgcG1kX21rd3JpdGUocG1kX3QgcG1kKQ0KPiArc3Rh
dGljIGlubGluZSBwbWRfdCBwbWRfbWt3cml0ZShwbWRfdCBwbWQsIHN0cnVjdCB2bV9hcmVhX3N0
cnVjdCAqdm1hKQ0KPiAgIHsNCj4gLQlyZXR1cm4gcHRlX3BtZChwdGVfbWt3cml0ZShwbWRfcHRl
KHBtZCkpKTsNCj4gKwlyZXR1cm4gcHRlX3BtZChwdGVfbWt3cml0ZShwbWRfcHRlKHBtZCksIHZt
YSkpOw0KPiAgIH0NCj4gICANCj4gICBzdGF0aWMgaW5saW5lIHBtZF90IHBtZF93cnByb3RlY3Qo
cG1kX3QgcG1kKQ0KPiBkaWZmIC0tZ2l0IGEvYXJjaC9zMzkwL2luY2x1ZGUvYXNtL2h1Z2V0bGIu
aCBiL2FyY2gvczM5MC9pbmNsdWRlL2FzbS9odWdldGxiLmgNCj4gaW5kZXggY2NkYmNjZmRlMTQ4
Li41NThmN2VlZjljNGQgMTAwNjQ0DQo+IC0tLSBhL2FyY2gvczM5MC9pbmNsdWRlL2FzbS9odWdl
dGxiLmgNCj4gKysrIGIvYXJjaC9zMzkwL2luY2x1ZGUvYXNtL2h1Z2V0bGIuaA0KPiBAQCAtMTAy
LDkgKzEwMiw5IEBAIHN0YXRpYyBpbmxpbmUgaW50IGh1Z2VfcHRlX2RpcnR5KHB0ZV90IHB0ZSkN
Cj4gICAJcmV0dXJuIHB0ZV9kaXJ0eShwdGUpOw0KPiAgIH0NCj4gICANCj4gLXN0YXRpYyBpbmxp
bmUgcHRlX3QgaHVnZV9wdGVfbWt3cml0ZShwdGVfdCBwdGUpDQo+ICtzdGF0aWMgaW5saW5lIHB0
ZV90IGh1Z2VfcHRlX21rd3JpdGUocHRlX3QgcHRlLCBzdHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3QgKnZt
YSkNCj4gICB7DQo+IC0JcmV0dXJuIHB0ZV9ta3dyaXRlKHB0ZSk7DQo+ICsJcmV0dXJuIHB0ZV9t
a3dyaXRlKHB0ZSwgdm1hKTsNCj4gICB9DQo+ICAgDQo+ICAgc3RhdGljIGlubGluZSBwdGVfdCBo
dWdlX3B0ZV9ta2RpcnR5KHB0ZV90IHB0ZSkNCj4gZGlmZiAtLWdpdCBhL2FyY2gvczM5MC9pbmNs
dWRlL2FzbS9wZ3RhYmxlLmggYi9hcmNoL3MzOTAvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+IGlu
ZGV4IGRlZWI5MThjYWUxZC4uOGYyYzc0M2RhMGViIDEwMDY0NA0KPiAtLS0gYS9hcmNoL3MzOTAv
aW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+ICsrKyBiL2FyY2gvczM5MC9pbmNsdWRlL2FzbS9wZ3Rh
YmxlLmgNCj4gQEAgLTEwMTMsNyArMTAxMyw3IEBAIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21r
d3JpdGVfa2VybmVsKHB0ZV90IHB0ZSkNCj4gICAJcmV0dXJuIHB0ZTsNCj4gICB9DQo+ICAgDQo+
IC1zdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSkNCj4gK3N0YXRpYyBp
bmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlLCBzdHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3Qg
KnZtYSkNCj4gICB7DQo+ICAgCXJldHVybiBwdGVfbWt3cml0ZV9rZXJuZWwocHRlKTsNCj4gICB9
DQo+IEBAIC0xNDk5LDcgKzE0OTksNyBAQCBzdGF0aWMgaW5saW5lIHBtZF90IHBtZF9ta3dyaXRl
X2tlcm5lbChwbWRfdCBwbWQpDQo+ICAgCXJldHVybiBwbWQ7DQo+ICAgfQ0KPiAgIA0KPiAtc3Rh
dGljIGlubGluZSBwbWRfdCBwbWRfbWt3cml0ZShwbWRfdCBwbWQpDQo+ICtzdGF0aWMgaW5saW5l
IHBtZF90IHBtZF9ta3dyaXRlKHBtZF90IHBtZCwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEp
DQo+ICAgew0KPiAgIAlyZXR1cm4gcG1kX21rd3JpdGVfa2VybmVsKHBtZCk7DQo+ICAgfQ0KPiBk
aWZmIC0tZ2l0IGEvYXJjaC9zaC9pbmNsdWRlL2FzbS9wZ3RhYmxlXzMyLmggYi9hcmNoL3NoL2lu
Y2x1ZGUvYXNtL3BndGFibGVfMzIuaA0KPiBpbmRleCAyMTk1MmIwOTQ2NTAuLjlmMmRjYjllYWZj
OCAxMDA2NDQNCj4gLS0tIGEvYXJjaC9zaC9pbmNsdWRlL2FzbS9wZ3RhYmxlXzMyLmgNCj4gKysr
IGIvYXJjaC9zaC9pbmNsdWRlL2FzbS9wZ3RhYmxlXzMyLmgNCj4gQEAgLTM1MSw2ICszNTEsMTIg
QEAgc3RhdGljIGlubGluZSB2b2lkIHNldF9wdGUocHRlX3QgKnB0ZXAsIHB0ZV90IHB0ZSkNCj4g
ICANCj4gICAjZGVmaW5lIFBURV9CSVRfRlVOQyhoLGZuLG9wKSBcDQo+ICAgc3RhdGljIGlubGlu
ZSBwdGVfdCBwdGVfIyNmbihwdGVfdCBwdGUpIHsgcHRlLnB0ZV8jI2ggb3A7IHJldHVybiBwdGU7
IH0NCj4gKyNkZWZpbmUgUFRFX0JJVF9GVU5DX1ZNQShoLGZuLG9wKSBcDQo+ICtzdGF0aWMgaW5s
aW5lIHB0ZV90IHB0ZV8jI2ZuKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEp
IFwNCj4gK3sgXA0KPiArCXB0ZS5wdGVfIyNoIG9wOyBcDQo+ICsJcmV0dXJuIHB0ZTsgXA0KPiAr
fQ0KPiAgIA0KPiAgICNpZmRlZiBDT05GSUdfWDJUTEINCj4gICAvKg0KPiBAQCAtMzU5LDExICsz
NjUsMTEgQEAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVfIyNmbihwdGVfdCBwdGUpIHsgcHRlLnB0
ZV8jI2ggb3A7IHJldHVybiBwdGU7IH0NCj4gICAgKiBrZXJuZWwgcGVybWlzc2lvbnMpLCB3ZSBh
dHRlbXB0IHRvIGNvdXBsZSB0aGVtIGEgYml0IG1vcmUgc2FuZWx5IGhlcmUuDQo+ICAgICovDQo+
ICAgUFRFX0JJVF9GVU5DKGhpZ2gsIHdycHJvdGVjdCwgJj0gfihfUEFHRV9FWFRfVVNFUl9XUklU
RSB8IF9QQUdFX0VYVF9LRVJOX1dSSVRFKSk7DQo+IC1QVEVfQklUX0ZVTkMoaGlnaCwgbWt3cml0
ZSwgfD0gX1BBR0VfRVhUX1VTRVJfV1JJVEUgfCBfUEFHRV9FWFRfS0VSTl9XUklURSk7DQo+ICtQ
VEVfQklUX0ZVTkNfVk1BKGhpZ2gsIG1rd3JpdGUsIHw9IF9QQUdFX0VYVF9VU0VSX1dSSVRFIHwg
X1BBR0VfRVhUX0tFUk5fV1JJVEUpOw0KPiAgIFBURV9CSVRfRlVOQyhoaWdoLCBta2h1Z2UsIHw9
IF9QQUdFX1NaSFVHRSk7DQo+ICAgI2Vsc2UNCj4gICBQVEVfQklUX0ZVTkMobG93LCB3cnByb3Rl
Y3QsICY9IH5fUEFHRV9SVyk7DQo+IC1QVEVfQklUX0ZVTkMobG93LCBta3dyaXRlLCB8PSBfUEFH
RV9SVyk7DQo+ICtQVEVfQklUX0ZVTkNfVk1BKGxvdywgbWt3cml0ZSwgfD0gX1BBR0VfUlcpOw0K
PiAgIFBURV9CSVRfRlVOQyhsb3csIG1raHVnZSwgfD0gX1BBR0VfU1pIVUdFKTsNCj4gICAjZW5k
aWYNCj4gICANCj4gZGlmZiAtLWdpdCBhL2FyY2gvc3BhcmMvaW5jbHVkZS9hc20vcGd0YWJsZV8z
Mi5oIGIvYXJjaC9zcGFyYy9pbmNsdWRlL2FzbS9wZ3RhYmxlXzMyLmgNCj4gaW5kZXggZDQzMzBl
M2M1N2E2Li4zZTg4MzYxNzk0NTYgMTAwNjQ0DQo+IC0tLSBhL2FyY2gvc3BhcmMvaW5jbHVkZS9h
c20vcGd0YWJsZV8zMi5oDQo+ICsrKyBiL2FyY2gvc3BhcmMvaW5jbHVkZS9hc20vcGd0YWJsZV8z
Mi5oDQo+IEBAIC0yNDEsNyArMjQxLDcgQEAgc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWtvbGQo
cHRlX3QgcHRlKQ0KPiAgIAlyZXR1cm4gX19wdGUocHRlX3ZhbChwdGUpICYgflNSTU1VX1JFRik7
DQo+ICAgfQ0KPiAgIA0KPiAtc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBw
dGUpDQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0
IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgew0KPiAgIAlyZXR1cm4gX19wdGUocHRlX3ZhbChw
dGUpIHwgU1JNTVVfV1JJVEUpOw0KPiAgIH0NCj4gZGlmZiAtLWdpdCBhL2FyY2gvc3BhcmMvaW5j
bHVkZS9hc20vcGd0YWJsZV82NC5oIGIvYXJjaC9zcGFyYy9pbmNsdWRlL2FzbS9wZ3RhYmxlXzY0
LmgNCj4gaW5kZXggMmRjOGQ0NjQxNzM0Li5jNWNkNWMwM2Y1NTcgMTAwNjQ0DQo+IC0tLSBhL2Fy
Y2gvc3BhcmMvaW5jbHVkZS9hc20vcGd0YWJsZV82NC5oDQo+ICsrKyBiL2FyY2gvc3BhcmMvaW5j
bHVkZS9hc20vcGd0YWJsZV82NC5oDQo+IEBAIC00NjYsNyArNDY2LDcgQEAgc3RhdGljIGlubGlu
ZSBwdGVfdCBwdGVfbWtjbGVhbihwdGVfdCBwdGUpDQo+ICAgCXJldHVybiBfX3B0ZSh2YWwpOw0K
PiAgIH0NCj4gICANCj4gLXN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRl
KQ0KPiArc3RhdGljIGlubGluZSBwdGVfdCBwdGVfbWt3cml0ZShwdGVfdCBwdGUsIHN0cnVjdCB2
bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4gICAJdW5zaWduZWQgbG9uZyB2YWwgPSBwdGVf
dmFsKHB0ZSksIG1hc2s7DQo+ICAgDQo+IEBAIC03NTYsMTEgKzc1NiwxMSBAQCBzdGF0aWMgaW5s
aW5lIHBtZF90IHBtZF9ta3lvdW5nKHBtZF90IHBtZCkNCj4gICAJcmV0dXJuIF9fcG1kKHB0ZV92
YWwocHRlKSk7DQo+ICAgfQ0KPiAgIA0KPiAtc3RhdGljIGlubGluZSBwbWRfdCBwbWRfbWt3cml0
ZShwbWRfdCBwbWQpDQo+ICtzdGF0aWMgaW5saW5lIHBtZF90IHBtZF9ta3dyaXRlKHBtZF90IHBt
ZCwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgew0KPiAgIAlwdGVfdCBwdGUgPSBf
X3B0ZShwbWRfdmFsKHBtZCkpOw0KPiAgIA0KPiAtCXB0ZSA9IHB0ZV9ta3dyaXRlKHB0ZSk7DQo+
ICsJcHRlID0gcHRlX21rd3JpdGUocHRlLCB2bWEpOw0KPiAgIA0KPiAgIAlyZXR1cm4gX19wbWQo
cHRlX3ZhbChwdGUpKTsNCj4gICB9DQo+IGRpZmYgLS1naXQgYS9hcmNoL3VtL2luY2x1ZGUvYXNt
L3BndGFibGUuaCBiL2FyY2gvdW0vaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+IGluZGV4IGE3MGQx
NjE4ZWIzNS4uOTYzNDc5YzEzM2I3IDEwMDY0NA0KPiAtLS0gYS9hcmNoL3VtL2luY2x1ZGUvYXNt
L3BndGFibGUuaA0KPiArKysgYi9hcmNoL3VtL2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBAQCAt
MjA3LDcgKzIwNyw3IEBAIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21reW91bmcocHRlX3QgcHRl
KQ0KPiAgIAlyZXR1cm4ocHRlKTsNCj4gICB9DQo+ICAgDQo+IC1zdGF0aWMgaW5saW5lIHB0ZV90
IHB0ZV9ta3dyaXRlKHB0ZV90IHB0ZSkNCj4gK3N0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3Jp
dGUocHRlX3QgcHRlLCBzdHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3QgKnZtYSkNCj4gICB7DQo+ICAgCWlm
ICh1bmxpa2VseShwdGVfZ2V0X2JpdHMocHRlLCAgX1BBR0VfUlcpKSkNCj4gICAJCXJldHVybiBw
dGU7DQo+IGRpZmYgLS1naXQgYS9hcmNoL3g4Ni9pbmNsdWRlL2FzbS9wZ3RhYmxlLmggYi9hcmNo
L3g4Ni9pbmNsdWRlL2FzbS9wZ3RhYmxlLmgNCj4gaW5kZXggMzYwN2YyNTcyZjllLi42NmM1MTQ4
MDgyNzYgMTAwNjQ0DQo+IC0tLSBhL2FyY2gveDg2L2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiAr
KysgYi9hcmNoL3g4Ni9pbmNsdWRlL2FzbS9wZ3RhYmxlLmgNCj4gQEAgLTM2OSw3ICszNjksOSBA
QCBzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlX2tlcm5lbChwdGVfdCBwdGUpDQo+ICAg
CXJldHVybiBwdGVfc2V0X2ZsYWdzKHB0ZSwgX1BBR0VfUlcpOw0KPiAgIH0NCj4gICANCj4gLXN0
YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RydWN0IHZtX2Fy
ZWFfc3RydWN0Ow0KPiArDQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0ZV90
IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgew0KPiAgIAlyZXR1cm4gcHRl
X21rd3JpdGVfa2VybmVsKHB0ZSk7DQo+ICAgfQ0KPiBAQCAtNDcwLDcgKzQ3Miw3IEBAIHN0YXRp
YyBpbmxpbmUgcG1kX3QgcG1kX21reW91bmcocG1kX3QgcG1kKQ0KPiAgIAlyZXR1cm4gcG1kX3Nl
dF9mbGFncyhwbWQsIF9QQUdFX0FDQ0VTU0VEKTsNCj4gICB9DQo+ICAgDQo+IC1zdGF0aWMgaW5s
aW5lIHBtZF90IHBtZF9ta3dyaXRlKHBtZF90IHBtZCkNCj4gK3N0YXRpYyBpbmxpbmUgcG1kX3Qg
cG1kX21rd3JpdGUocG1kX3QgcG1kLCBzdHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3QgKnZtYSkNCj4gICB7
DQo+ICAgCXJldHVybiBwbWRfc2V0X2ZsYWdzKHBtZCwgX1BBR0VfUlcpOw0KPiAgIH0NCj4gZGlm
ZiAtLWdpdCBhL2FyY2gveHRlbnNhL2luY2x1ZGUvYXNtL3BndGFibGUuaCBiL2FyY2gveHRlbnNh
L2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBpbmRleCBmYzdhMTQ4ODRjNmMuLmQ3MjYzMmQ5YzUz
YyAxMDA2NDQNCj4gLS0tIGEvYXJjaC94dGVuc2EvaW5jbHVkZS9hc20vcGd0YWJsZS5oDQo+ICsr
KyBiL2FyY2gveHRlbnNhL2luY2x1ZGUvYXNtL3BndGFibGUuaA0KPiBAQCAtMjYyLDcgKzI2Miw3
IEBAIHN0YXRpYyBpbmxpbmUgcHRlX3QgcHRlX21rZGlydHkocHRlX3QgcHRlKQ0KPiAgIAl7IHB0
ZV92YWwocHRlKSB8PSBfUEFHRV9ESVJUWTsgcmV0dXJuIHB0ZTsgfQ0KPiAgIHN0YXRpYyBpbmxp
bmUgcHRlX3QgcHRlX21reW91bmcocHRlX3QgcHRlKQ0KPiAgIAl7IHB0ZV92YWwocHRlKSB8PSBf
UEFHRV9BQ0NFU1NFRDsgcmV0dXJuIHB0ZTsgfQ0KPiAtc3RhdGljIGlubGluZSBwdGVfdCBwdGVf
bWt3cml0ZShwdGVfdCBwdGUpDQo+ICtzdGF0aWMgaW5saW5lIHB0ZV90IHB0ZV9ta3dyaXRlKHB0
ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFfc3RydWN0ICp2bWEpDQo+ICAgCXsgcHRlX3ZhbChwdGUp
IHw9IF9QQUdFX1dSSVRBQkxFOyByZXR1cm4gcHRlOyB9DQo+ICAgDQo+ICAgI2RlZmluZSBwZ3By
b3Rfbm9uY2FjaGVkKHByb3QpIFwNCj4gZGlmZiAtLWdpdCBhL2luY2x1ZGUvYXNtLWdlbmVyaWMv
aHVnZXRsYi5oIGIvaW5jbHVkZS9hc20tZ2VuZXJpYy9odWdldGxiLmgNCj4gaW5kZXggZDdmNjMz
NWQzOTk5Li5lODZjODMwNzI4ZGUgMTAwNjQ0DQo+IC0tLSBhL2luY2x1ZGUvYXNtLWdlbmVyaWMv
aHVnZXRsYi5oDQo+ICsrKyBiL2luY2x1ZGUvYXNtLWdlbmVyaWMvaHVnZXRsYi5oDQo+IEBAIC0y
MCw5ICsyMCw5IEBAIHN0YXRpYyBpbmxpbmUgdW5zaWduZWQgbG9uZyBodWdlX3B0ZV9kaXJ0eShw
dGVfdCBwdGUpDQo+ICAgCXJldHVybiBwdGVfZGlydHkocHRlKTsNCj4gICB9DQo+ICAgDQo+IC1z
dGF0aWMgaW5saW5lIHB0ZV90IGh1Z2VfcHRlX21rd3JpdGUocHRlX3QgcHRlKQ0KPiArc3RhdGlj
IGlubGluZSBwdGVfdCBodWdlX3B0ZV9ta3dyaXRlKHB0ZV90IHB0ZSwgc3RydWN0IHZtX2FyZWFf
c3RydWN0ICp2bWEpDQo+ICAgew0KPiAtCXJldHVybiBwdGVfbWt3cml0ZShwdGUpOw0KPiArCXJl
dHVybiBwdGVfbWt3cml0ZShwdGUsIHZtYSk7DQo+ICAgfQ0KPiAgIA0KPiAgICNpZm5kZWYgX19I
QVZFX0FSQ0hfSFVHRV9QVEVfV1JQUk9URUNUDQo+IGRpZmYgLS1naXQgYS9pbmNsdWRlL2xpbnV4
L21tLmggYi9pbmNsdWRlL2xpbnV4L21tLmgNCj4gaW5kZXggMWY3OTY2NzgyNGViLi5hZjY1MjQ0
NGZiYmEgMTAwNjQ0DQo+IC0tLSBhL2luY2x1ZGUvbGludXgvbW0uaA0KPiArKysgYi9pbmNsdWRl
L2xpbnV4L21tLmgNCj4gQEAgLTExNjMsNyArMTE2Myw3IEBAIHZvaWQgZnJlZV9jb21wb3VuZF9w
YWdlKHN0cnVjdCBwYWdlICpwYWdlKTsNCj4gICBzdGF0aWMgaW5saW5lIHB0ZV90IG1heWJlX21r
d3JpdGUocHRlX3QgcHRlLCBzdHJ1Y3Qgdm1fYXJlYV9zdHJ1Y3QgKnZtYSkNCj4gICB7DQo+ICAg
CWlmIChsaWtlbHkodm1hLT52bV9mbGFncyAmIFZNX1dSSVRFKSkNCj4gLQkJcHRlID0gcHRlX21r
d3JpdGUocHRlKTsNCj4gKwkJcHRlID0gcHRlX21rd3JpdGUocHRlLCB2bWEpOw0KPiAgIAlyZXR1
cm4gcHRlOw0KPiAgIH0NCj4gICANCj4gZGlmZiAtLWdpdCBhL21tL2RlYnVnX3ZtX3BndGFibGUu
YyBiL21tL2RlYnVnX3ZtX3BndGFibGUuYw0KPiBpbmRleCBhZjU5Y2M3YmQzMDcuLjdiYzU1OTI5
MDBiYyAxMDA2NDQNCj4gLS0tIGEvbW0vZGVidWdfdm1fcGd0YWJsZS5jDQo+ICsrKyBiL21tL2Rl
YnVnX3ZtX3BndGFibGUuYw0KPiBAQCAtMTA5LDEwICsxMDksMTAgQEAgc3RhdGljIHZvaWQgX19p
bml0IHB0ZV9iYXNpY190ZXN0cyhzdHJ1Y3QgcGd0YWJsZV9kZWJ1Z19hcmdzICphcmdzLCBpbnQg
aWR4KQ0KPiAgIAlXQVJOX09OKCFwdGVfc2FtZShwdGUsIHB0ZSkpOw0KPiAgIAlXQVJOX09OKCFw
dGVfeW91bmcocHRlX21reW91bmcocHRlX21rb2xkKHB0ZSkpKSk7DQo+ICAgCVdBUk5fT04oIXB0
ZV9kaXJ0eShwdGVfbWtkaXJ0eShwdGVfbWtjbGVhbihwdGUpKSkpOw0KPiAtCVdBUk5fT04oIXB0
ZV93cml0ZShwdGVfbWt3cml0ZShwdGVfd3Jwcm90ZWN0KHB0ZSkpKSk7DQo+ICsJV0FSTl9PTigh
cHRlX3dyaXRlKHB0ZV9ta3dyaXRlKHB0ZV93cnByb3RlY3QocHRlKSwgYXJncy0+dm1hKSkpOw0K
PiAgIAlXQVJOX09OKHB0ZV95b3VuZyhwdGVfbWtvbGQocHRlX21reW91bmcocHRlKSkpKTsNCj4g
ICAJV0FSTl9PTihwdGVfZGlydHkocHRlX21rY2xlYW4ocHRlX21rZGlydHkocHRlKSkpKTsNCj4g
LQlXQVJOX09OKHB0ZV93cml0ZShwdGVfd3Jwcm90ZWN0KHB0ZV9ta3dyaXRlKHB0ZSkpKSk7DQo+
ICsJV0FSTl9PTihwdGVfd3JpdGUocHRlX3dycHJvdGVjdChwdGVfbWt3cml0ZShwdGUsIGFyZ3Mt
PnZtYSkpKSk7DQo+ICAgCVdBUk5fT04ocHRlX2RpcnR5KHB0ZV93cnByb3RlY3QocHRlX21rY2xl
YW4ocHRlKSkpKTsNCj4gICAJV0FSTl9PTighcHRlX2RpcnR5KHB0ZV93cnByb3RlY3QocHRlX21r
ZGlydHkocHRlKSkpKTsNCj4gICB9DQo+IEBAIC0xNTMsNyArMTUzLDcgQEAgc3RhdGljIHZvaWQg
X19pbml0IHB0ZV9hZHZhbmNlZF90ZXN0cyhzdHJ1Y3QgcGd0YWJsZV9kZWJ1Z19hcmdzICphcmdz
KQ0KPiAgIAlwdGUgPSBwdGVfbWtjbGVhbihwdGUpOw0KPiAgIAlzZXRfcHRlX2F0KGFyZ3MtPm1t
LCBhcmdzLT52YWRkciwgYXJncy0+cHRlcCwgcHRlKTsNCj4gICAJZmx1c2hfZGNhY2hlX3BhZ2Uo
cGFnZSk7DQo+IC0JcHRlID0gcHRlX21rd3JpdGUocHRlKTsNCj4gKwlwdGUgPSBwdGVfbWt3cml0
ZShwdGUsIGFyZ3MtPnZtYSk7DQo+ICAgCXB0ZSA9IHB0ZV9ta2RpcnR5KHB0ZSk7DQo+ICAgCXB0
ZXBfc2V0X2FjY2Vzc19mbGFncyhhcmdzLT52bWEsIGFyZ3MtPnZhZGRyLCBhcmdzLT5wdGVwLCBw
dGUsIDEpOw0KPiAgIAlwdGUgPSBwdGVwX2dldChhcmdzLT5wdGVwKTsNCj4gQEAgLTE5OSwxMCAr
MTk5LDEwIEBAIHN0YXRpYyB2b2lkIF9faW5pdCBwbWRfYmFzaWNfdGVzdHMoc3RydWN0IHBndGFi
bGVfZGVidWdfYXJncyAqYXJncywgaW50IGlkeCkNCj4gICAJV0FSTl9PTighcG1kX3NhbWUocG1k
LCBwbWQpKTsNCj4gICAJV0FSTl9PTighcG1kX3lvdW5nKHBtZF9ta3lvdW5nKHBtZF9ta29sZChw
bWQpKSkpOw0KPiAgIAlXQVJOX09OKCFwbWRfZGlydHkocG1kX21rZGlydHkocG1kX21rY2xlYW4o
cG1kKSkpKTsNCj4gLQlXQVJOX09OKCFwbWRfd3JpdGUocG1kX21rd3JpdGUocG1kX3dycHJvdGVj
dChwbWQpKSkpOw0KPiArCVdBUk5fT04oIXBtZF93cml0ZShwbWRfbWt3cml0ZShwbWRfd3Jwcm90
ZWN0KHBtZCksIGFyZ3MtPnZtYSkpKTsNCj4gICAJV0FSTl9PTihwbWRfeW91bmcocG1kX21rb2xk
KHBtZF9ta3lvdW5nKHBtZCkpKSk7DQo+ICAgCVdBUk5fT04ocG1kX2RpcnR5KHBtZF9ta2NsZWFu
KHBtZF9ta2RpcnR5KHBtZCkpKSk7DQo+IC0JV0FSTl9PTihwbWRfd3JpdGUocG1kX3dycHJvdGVj
dChwbWRfbWt3cml0ZShwbWQpKSkpOw0KPiArCVdBUk5fT04ocG1kX3dyaXRlKHBtZF93cnByb3Rl
Y3QocG1kX21rd3JpdGUocG1kLCBhcmdzLT52bWEpKSkpOw0KPiAgIAlXQVJOX09OKHBtZF9kaXJ0
eShwbWRfd3Jwcm90ZWN0KHBtZF9ta2NsZWFuKHBtZCkpKSk7DQo+ICAgCVdBUk5fT04oIXBtZF9k
aXJ0eShwbWRfd3Jwcm90ZWN0KHBtZF9ta2RpcnR5KHBtZCkpKSk7DQo+ICAgCS8qDQo+IEBAIC0y
NTMsNyArMjUzLDcgQEAgc3RhdGljIHZvaWQgX19pbml0IHBtZF9hZHZhbmNlZF90ZXN0cyhzdHJ1
Y3QgcGd0YWJsZV9kZWJ1Z19hcmdzICphcmdzKQ0KPiAgIAlwbWQgPSBwbWRfbWtjbGVhbihwbWQp
Ow0KPiAgIAlzZXRfcG1kX2F0KGFyZ3MtPm1tLCB2YWRkciwgYXJncy0+cG1kcCwgcG1kKTsNCj4g
ICAJZmx1c2hfZGNhY2hlX3BhZ2UocGFnZSk7DQo+IC0JcG1kID0gcG1kX21rd3JpdGUocG1kKTsN
Cj4gKwlwbWQgPSBwbWRfbWt3cml0ZShwbWQsIGFyZ3MtPnZtYSk7DQo+ICAgCXBtZCA9IHBtZF9t
a2RpcnR5KHBtZCk7DQo+ICAgCXBtZHBfc2V0X2FjY2Vzc19mbGFncyhhcmdzLT52bWEsIHZhZGRy
LCBhcmdzLT5wbWRwLCBwbWQsIDEpOw0KPiAgIAlwbWQgPSBSRUFEX09OQ0UoKmFyZ3MtPnBtZHAp
Ow0KPiBAQCAtOTI4LDggKzkyOCw4IEBAIHN0YXRpYyB2b2lkIF9faW5pdCBodWdldGxiX2Jhc2lj
X3Rlc3RzKHN0cnVjdCBwZ3RhYmxlX2RlYnVnX2FyZ3MgKmFyZ3MpDQo+ICAgCXB0ZSA9IG1rX2h1
Z2VfcHRlKHBhZ2UsIGFyZ3MtPnBhZ2VfcHJvdCk7DQo+ICAgDQo+ICAgCVdBUk5fT04oIWh1Z2Vf
cHRlX2RpcnR5KGh1Z2VfcHRlX21rZGlydHkocHRlKSkpOw0KPiAtCVdBUk5fT04oIWh1Z2VfcHRl
X3dyaXRlKGh1Z2VfcHRlX21rd3JpdGUoaHVnZV9wdGVfd3Jwcm90ZWN0KHB0ZSkpKSk7DQo+IC0J
V0FSTl9PTihodWdlX3B0ZV93cml0ZShodWdlX3B0ZV93cnByb3RlY3QoaHVnZV9wdGVfbWt3cml0
ZShwdGUpKSkpOw0KPiArCVdBUk5fT04oIWh1Z2VfcHRlX3dyaXRlKGh1Z2VfcHRlX21rd3JpdGUo
aHVnZV9wdGVfd3Jwcm90ZWN0KHB0ZSksIGFyZ3MtPnZtYSkpKTsNCj4gKwlXQVJOX09OKGh1Z2Vf
cHRlX3dyaXRlKGh1Z2VfcHRlX3dycHJvdGVjdChodWdlX3B0ZV9ta3dyaXRlKHB0ZSwgYXJncy0+
dm1hKSkpKTsNCj4gICANCj4gICAjaWZkZWYgQ09ORklHX0FSQ0hfV0FOVF9HRU5FUkFMX0hVR0VU
TEINCj4gICAJcHRlID0gcGZuX3B0ZShhcmdzLT5maXhlZF9wbWRfcGZuLCBhcmdzLT5wYWdlX3By
b3QpOw0KPiBkaWZmIC0tZ2l0IGEvbW0vaHVnZV9tZW1vcnkuYyBiL21tL2h1Z2VfbWVtb3J5LmMN
Cj4gaW5kZXggNGZjNDM4NTllNTlhLi5hYWY4MTU4MzgxNDQgMTAwNjQ0DQo+IC0tLSBhL21tL2h1
Z2VfbWVtb3J5LmMNCj4gKysrIGIvbW0vaHVnZV9tZW1vcnkuYw0KPiBAQCAtNTU1LDcgKzU1NSw3
IEBAIF9fc2V0dXAoInRyYW5zcGFyZW50X2h1Z2VwYWdlPSIsIHNldHVwX3RyYW5zcGFyZW50X2h1
Z2VwYWdlKTsNCj4gICBwbWRfdCBtYXliZV9wbWRfbWt3cml0ZShwbWRfdCBwbWQsIHN0cnVjdCB2
bV9hcmVhX3N0cnVjdCAqdm1hKQ0KPiAgIHsNCj4gICAJaWYgKGxpa2VseSh2bWEtPnZtX2ZsYWdz
ICYgVk1fV1JJVEUpKQ0KPiAtCQlwbWQgPSBwbWRfbWt3cml0ZShwbWQpOw0KPiArCQlwbWQgPSBw
bWRfbWt3cml0ZShwbWQsIHZtYSk7DQo+ICAgCXJldHVybiBwbWQ7DQo+ICAgfQ0KPiAgIA0KPiBA
QCAtMTU4MCw3ICsxNTgwLDcgQEAgdm1fZmF1bHRfdCBkb19odWdlX3BtZF9udW1hX3BhZ2Uoc3Ry
dWN0IHZtX2ZhdWx0ICp2bWYpDQo+ICAgCXBtZCA9IHBtZF9tb2RpZnkob2xkcG1kLCB2bWEtPnZt
X3BhZ2VfcHJvdCk7DQo+ICAgCXBtZCA9IHBtZF9ta3lvdW5nKHBtZCk7DQo+ICAgCWlmICh3cml0
YWJsZSkNCj4gLQkJcG1kID0gcG1kX21rd3JpdGUocG1kKTsNCj4gKwkJcG1kID0gcG1kX21rd3Jp
dGUocG1kLCB2bWEpOw0KPiAgIAlzZXRfcG1kX2F0KHZtYS0+dm1fbW0sIGhhZGRyLCB2bWYtPnBt
ZCwgcG1kKTsNCj4gICAJdXBkYXRlX21tdV9jYWNoZV9wbWQodm1hLCB2bWYtPmFkZHJlc3MsIHZt
Zi0+cG1kKTsNCj4gICAJc3Bpbl91bmxvY2sodm1mLT5wdGwpOw0KPiBAQCAtMTkyNiw3ICsxOTI2
LDcgQEAgaW50IGNoYW5nZV9odWdlX3BtZChzdHJ1Y3QgbW11X2dhdGhlciAqdGxiLCBzdHJ1Y3Qg
dm1fYXJlYV9zdHJ1Y3QgKnZtYSwNCj4gICAJLyogU2VlIGNoYW5nZV9wdGVfcmFuZ2UoKS4gKi8N
Cj4gICAJaWYgKChjcF9mbGFncyAmIE1NX0NQX1RSWV9DSEFOR0VfV1JJVEFCTEUpICYmICFwbWRf
d3JpdGUoZW50cnkpICYmDQo+ICAgCSAgICBjYW5fY2hhbmdlX3BtZF93cml0YWJsZSh2bWEsIGFk
ZHIsIGVudHJ5KSkNCj4gLQkJZW50cnkgPSBwbWRfbWt3cml0ZShlbnRyeSk7DQo+ICsJCWVudHJ5
ID0gcG1kX21rd3JpdGUoZW50cnksIHZtYSk7DQo+ICAgDQo+ICAgCXJldCA9IEhQQUdFX1BNRF9O
UjsNCj4gICAJc2V0X3BtZF9hdChtbSwgYWRkciwgcG1kLCBlbnRyeSk7DQo+IGRpZmYgLS1naXQg
YS9tbS9odWdldGxiLmMgYi9tbS9odWdldGxiLmMNCj4gaW5kZXggMDdhYmNiNmViMjAzLi42YWY0
NzFiZGNmZjggMTAwNjQ0DQo+IC0tLSBhL21tL2h1Z2V0bGIuYw0KPiArKysgYi9tbS9odWdldGxi
LmMNCj4gQEAgLTQ5MDAsNyArNDkwMCw3IEBAIHN0YXRpYyBwdGVfdCBtYWtlX2h1Z2VfcHRlKHN0
cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hLCBzdHJ1Y3QgcGFnZSAqcGFnZSwNCj4gICANCj4gICAJ
aWYgKHdyaXRhYmxlKSB7DQo+ICAgCQllbnRyeSA9IGh1Z2VfcHRlX21rd3JpdGUoaHVnZV9wdGVf
bWtkaXJ0eShta19odWdlX3B0ZShwYWdlLA0KPiAtCQkJCQkgdm1hLT52bV9wYWdlX3Byb3QpKSk7
DQo+ICsJCQkJCSB2bWEtPnZtX3BhZ2VfcHJvdCkpLCB2bWEpOw0KPiAgIAl9IGVsc2Ugew0KPiAg
IAkJZW50cnkgPSBodWdlX3B0ZV93cnByb3RlY3QobWtfaHVnZV9wdGUocGFnZSwNCj4gICAJCQkJ
CSAgIHZtYS0+dm1fcGFnZV9wcm90KSk7DQo+IEBAIC00OTE2LDcgKzQ5MTYsNyBAQCBzdGF0aWMg
dm9pZCBzZXRfaHVnZV9wdGVwX3dyaXRhYmxlKHN0cnVjdCB2bV9hcmVhX3N0cnVjdCAqdm1hLA0K
PiAgIHsNCj4gICAJcHRlX3QgZW50cnk7DQo+ICAgDQo+IC0JZW50cnkgPSBodWdlX3B0ZV9ta3dy
aXRlKGh1Z2VfcHRlX21rZGlydHkoaHVnZV9wdGVwX2dldChwdGVwKSkpOw0KPiArCWVudHJ5ID0g
aHVnZV9wdGVfbWt3cml0ZShodWdlX3B0ZV9ta2RpcnR5KGh1Z2VfcHRlcF9nZXQocHRlcCkpLCB2
bWEpOw0KPiAgIAlpZiAoaHVnZV9wdGVwX3NldF9hY2Nlc3NfZmxhZ3Modm1hLCBhZGRyZXNzLCBw
dGVwLCBlbnRyeSwgMSkpDQo+ICAgCQl1cGRhdGVfbW11X2NhY2hlKHZtYSwgYWRkcmVzcywgcHRl
cCk7DQo+ICAgfQ0KPiBkaWZmIC0tZ2l0IGEvbW0vbWVtb3J5LmMgYi9tbS9tZW1vcnkuYw0KPiBp
bmRleCBmNDU2ZjNiNTA0OWMuLmQwOTcyZDJkNmYzNiAxMDA2NDQNCj4gLS0tIGEvbW0vbWVtb3J5
LmMNCj4gKysrIGIvbW0vbWVtb3J5LmMNCj4gQEAgLTQwNjcsNyArNDA2Nyw3IEBAIHN0YXRpYyB2
bV9mYXVsdF90IGRvX2Fub255bW91c19wYWdlKHN0cnVjdCB2bV9mYXVsdCAqdm1mKQ0KPiAgIAll
bnRyeSA9IG1rX3B0ZSgmZm9saW8tPnBhZ2UsIHZtYS0+dm1fcGFnZV9wcm90KTsNCj4gICAJZW50
cnkgPSBwdGVfc3dfbWt5b3VuZyhlbnRyeSk7DQo+ICAgCWlmICh2bWEtPnZtX2ZsYWdzICYgVk1f
V1JJVEUpDQo+IC0JCWVudHJ5ID0gcHRlX21rd3JpdGUocHRlX21rZGlydHkoZW50cnkpKTsNCj4g
KwkJZW50cnkgPSBwdGVfbWt3cml0ZShwdGVfbWtkaXJ0eShlbnRyeSksIHZtYSk7DQo+ICAgDQo+
ICAgCXZtZi0+cHRlID0gcHRlX29mZnNldF9tYXBfbG9jayh2bWEtPnZtX21tLCB2bWYtPnBtZCwg
dm1mLT5hZGRyZXNzLA0KPiAgIAkJCSZ2bWYtPnB0bCk7DQo+IEBAIC00NzU1LDcgKzQ3NTUsNyBA
QCBzdGF0aWMgdm1fZmF1bHRfdCBkb19udW1hX3BhZ2Uoc3RydWN0IHZtX2ZhdWx0ICp2bWYpDQo+
ICAgCXB0ZSA9IHB0ZV9tb2RpZnkob2xkX3B0ZSwgdm1hLT52bV9wYWdlX3Byb3QpOw0KPiAgIAlw
dGUgPSBwdGVfbWt5b3VuZyhwdGUpOw0KPiAgIAlpZiAod3JpdGFibGUpDQo+IC0JCXB0ZSA9IHB0
ZV9ta3dyaXRlKHB0ZSk7DQo+ICsJCXB0ZSA9IHB0ZV9ta3dyaXRlKHB0ZSwgdm1hKTsNCj4gICAJ
cHRlcF9tb2RpZnlfcHJvdF9jb21taXQodm1hLCB2bWYtPmFkZHJlc3MsIHZtZi0+cHRlLCBvbGRf
cHRlLCBwdGUpOw0KPiAgIAl1cGRhdGVfbW11X2NhY2hlKHZtYSwgdm1mLT5hZGRyZXNzLCB2bWYt
PnB0ZSk7DQo+ICAgCXB0ZV91bm1hcF91bmxvY2sodm1mLT5wdGUsIHZtZi0+cHRsKTsNCj4gZGlm
ZiAtLWdpdCBhL21tL21pZ3JhdGVfZGV2aWNlLmMgYi9tbS9taWdyYXRlX2RldmljZS5jDQo+IGlu
ZGV4IGQzMGM5ZGU2MGIwZC4uZGYzZjVlOWQ1Zjc2IDEwMDY0NA0KPiAtLS0gYS9tbS9taWdyYXRl
X2RldmljZS5jDQo+ICsrKyBiL21tL21pZ3JhdGVfZGV2aWNlLmMNCj4gQEAgLTY0Niw3ICs2NDYs
NyBAQCBzdGF0aWMgdm9pZCBtaWdyYXRlX3ZtYV9pbnNlcnRfcGFnZShzdHJ1Y3QgbWlncmF0ZV92
bWEgKm1pZ3JhdGUsDQo+ICAgCQl9DQo+ICAgCQllbnRyeSA9IG1rX3B0ZShwYWdlLCB2bWEtPnZt
X3BhZ2VfcHJvdCk7DQo+ICAgCQlpZiAodm1hLT52bV9mbGFncyAmIFZNX1dSSVRFKQ0KPiAtCQkJ
ZW50cnkgPSBwdGVfbWt3cml0ZShwdGVfbWtkaXJ0eShlbnRyeSkpOw0KPiArCQkJZW50cnkgPSBw
dGVfbWt3cml0ZShwdGVfbWtkaXJ0eShlbnRyeSksIHZtYSk7DQo+ICAgCX0NCj4gICANCj4gICAJ
cHRlcCA9IHB0ZV9vZmZzZXRfbWFwX2xvY2sobW0sIHBtZHAsIGFkZHIsICZwdGwpOw0KPiBkaWZm
IC0tZ2l0IGEvbW0vbXByb3RlY3QuYyBiL21tL21wcm90ZWN0LmMNCj4gaW5kZXggMWQ0ODQzYzk3
YzJhLi4zODExNjNhNDFlODggMTAwNjQ0DQo+IC0tLSBhL21tL21wcm90ZWN0LmMNCj4gKysrIGIv
bW0vbXByb3RlY3QuYw0KPiBAQCAtMTk4LDcgKzE5OCw3IEBAIHN0YXRpYyBsb25nIGNoYW5nZV9w
dGVfcmFuZ2Uoc3RydWN0IG1tdV9nYXRoZXIgKnRsYiwNCj4gICAJCQlpZiAoKGNwX2ZsYWdzICYg
TU1fQ1BfVFJZX0NIQU5HRV9XUklUQUJMRSkgJiYNCj4gICAJCQkgICAgIXB0ZV93cml0ZShwdGVu
dCkgJiYNCj4gICAJCQkgICAgY2FuX2NoYW5nZV9wdGVfd3JpdGFibGUodm1hLCBhZGRyLCBwdGVu
dCkpDQo+IC0JCQkJcHRlbnQgPSBwdGVfbWt3cml0ZShwdGVudCk7DQo+ICsJCQkJcHRlbnQgPSBw
dGVfbWt3cml0ZShwdGVudCwgdm1hKTsNCj4gICANCj4gICAJCQlwdGVwX21vZGlmeV9wcm90X2Nv
bW1pdCh2bWEsIGFkZHIsIHB0ZSwgb2xkcHRlLCBwdGVudCk7DQo+ICAgCQkJaWYgKHB0ZV9uZWVk
c19mbHVzaChvbGRwdGUsIHB0ZW50KSkNCj4gZGlmZiAtLWdpdCBhL21tL3VzZXJmYXVsdGZkLmMg
Yi9tbS91c2VyZmF1bHRmZC5jDQo+IGluZGV4IDUzYzNkOTE2ZmY2Ni4uM2RiNmY4N2MwYWNhIDEw
MDY0NA0KPiAtLS0gYS9tbS91c2VyZmF1bHRmZC5jDQo+ICsrKyBiL21tL3VzZXJmYXVsdGZkLmMN
Cj4gQEAgLTc1LDcgKzc1LDcgQEAgaW50IG1maWxsX2F0b21pY19pbnN0YWxsX3B0ZShzdHJ1Y3Qg
bW1fc3RydWN0ICpkc3RfbW0sIHBtZF90ICpkc3RfcG1kLA0KPiAgIAlpZiAocGFnZV9pbl9jYWNo
ZSAmJiAhdm1fc2hhcmVkKQ0KPiAgIAkJd3JpdGFibGUgPSBmYWxzZTsNCj4gICAJaWYgKHdyaXRh
YmxlKQ0KPiAtCQlfZHN0X3B0ZSA9IHB0ZV9ta3dyaXRlKF9kc3RfcHRlKTsNCj4gKwkJX2RzdF9w
dGUgPSBwdGVfbWt3cml0ZShfZHN0X3B0ZSwgZHN0X3ZtYSk7DQo+ICAgCWlmICh3cF9jb3B5KQ0K
PiAgIAkJX2RzdF9wdGUgPSBwdGVfbWt1ZmZkX3dwKF9kc3RfcHRlKTsNCj4gICANCg=

WARNING: multiple messages have this Message-ID (diff)
From: Christophe Leroy <christophe.leroy@csgroup.eu>
To: Rick Edgecombe <rick.p.edgecombe@intel.com>,
	"x86@kernel.org" <x86@kernel.org>,
	"H . Peter Anvin" <hpa@zytor.com>,
	Thomas Gleixner <tglx@linutronix.de>,
	Ingo Molnar <mingo@redhat.com>,
	"linux-kernel@vger.kernel.org" <linux-kernel@vger.kernel.org>,
	"linux-doc@vger.kernel.org" <linux-doc@vger.kernel.org>,
	"linux-mm@kvack.org" <linux-mm@kvack.org>,
	"linux-arch@vger.kernel.org" <linux-arch@vger.kernel.org>,
	"linux-api@vger.kernel.org" <linux-api@vger.kernel.org>,
	Arnd Bergmann <arnd@arndb.de>, Andy Lutomirski <luto@kernel.org>,
	Balbir Singh <bsingharora@gmail.com>,
	Borislav Petkov <bp@alien8.de>,
	Cyrill Gorcunov <gorcunov@gmail.com>,
	Dave Hansen <dave.hansen@linux.intel.com>,
	Eugene Syromiatnikov <esyr@redhat.com>,
	Florian Weimer <fweimer@redhat.com>
Cc: "linux-alpha@vger.kernel.org" <linux-alpha@vger.kernel.org>,
	"linux-snps-arc@lists.infradead.org"
	<linux-snps-arc@lists.infradead.org>,
	"linux-arm-kernel@lists.infradead.org"
	<linux-arm-kernel@lists.infradead.org>,
	"linux-csky@vger.kernel.org" <linux-csky@vger.kernel.org>,
	"linux-hexagon@vger.kernel.org" <linux-hexagon@vger.kernel.org>,
	"linux-ia64@vger.kernel.org" <linux-ia64@vger.kernel.org>,
	"loongarch@lists.linux.dev" <loongarch@lists.linux.dev>,
	"linux-m68k@lists.linux-m68k.org"
	<linux-m68k@lists.linux-m68k.org>,
	Michal Simek <monstr@monstr.eu>,
	Dinh Nguyen <dinguyen@kernel.org>,
	"linux-mips@vger.kernel.org" <linux-mips@vger.kernel.org>,
	"linux-openrisc@vger.kernel.org" <linux-openrisc@vger.kernel.org>,
	"linux-parisc@vger.kernel.org" <linux-parisc@vger.kernel.org>
Subject: Re: [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA
Date: Wed, 1 Mar 2023 07:03:23 +0000	[thread overview]
Message-ID: <1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu> (raw)
In-Reply-To: <20230227222957.24501-14-rick.p.edgecombe@intel.com>



Le 27/02/2023 à 23:29, Rick Edgecombe a écrit :
> The x86 Control-flow Enforcement Technology (CET) feature includes a new
> type of memory called shadow stack. This shadow stack memory has some
> unusual properties, which requires some core mm changes to function
> properly.
> 
> One of these unusual properties is that shadow stack memory is writable,
> but only in limited ways. These limits are applied via a specific PTE
> bit combination. Nevertheless, the memory is writable, and core mm code
> will need to apply the writable permissions in the typical paths that
> call pte_mkwrite().
> 
> In addition to VM_WRITE, the shadow stack VMA's will have a flag denoting
> that they are special shadow stack flavor of writable memory. So make
> pte_mkwrite() take a VMA, so that the x86 implementation of it can know to
> create regular writable memory or shadow stack memory.
> 
> Apply the same changes for pmd_mkwrite() and huge_pte_mkwrite().

I'm not sure it is a good idea to add a second argument to 
pte_mkwrite(). All pte_mkxxxx() only take a pte and nothing else.

I think you should do the same as commit d9ed9faac283 ("mm: add new 
arch_make_huge_pte() method for tile support")

Christophe

> 
> No functional change.
> 
> Cc: linux-doc@vger.kernel.org
> Cc: linux-kernel@vger.kernel.org
> Cc: linux-alpha@vger.kernel.org
> Cc: linux-snps-arc@lists.infradead.org
> Cc: linux-arm-kernel@lists.infradead.org
> Cc: linux-csky@vger.kernel.org
> Cc: linux-hexagon@vger.kernel.org
> Cc: linux-ia64@vger.kernel.org
> Cc: loongarch@lists.linux.dev
> Cc: linux-m68k@lists.linux-m68k.org
> Cc: Michal Simek <monstr@monstr.eu>
> Cc: Dinh Nguyen <dinguyen@kernel.org>
> Cc: linux-mips@vger.kernel.org
> Cc: linux-openrisc@vger.kernel.org
> Cc: linux-parisc@vger.kernel.org
> Cc: linuxppc-dev@lists.ozlabs.org
> Cc: linux-riscv@lists.infradead.org
> Cc: linux-s390@vger.kernel.org
> Cc: linux-sh@vger.kernel.org
> Cc: sparclinux@vger.kernel.org
> Cc: linux-um@lists.infradead.org
> Cc: xen-devel@lists.xenproject.org
> Cc: linux-arch@vger.kernel.org
> Cc: linux-mm@kvack.org
> Tested-by: Pengfei Xu <pengfei.xu@intel.com>
> Tested-by: John Allen <john.allen@amd.com>
> Tested-by: Kees Cook <keescook@chromium.org>
> Acked-by: Mike Rapoport (IBM) <rppt@kernel.org>
> Acked-by: Michael Ellerman <mpe@ellerman.id.au>
> Acked-by: David Hildenbrand <david@redhat.com>
> Reviewed-by: Kees Cook <keescook@chromium.org>
> Suggested-by: David Hildenbrand <david@redhat.com>
> Signed-off-by: Rick Edgecombe <rick.p.edgecombe@intel.com>
> 
> ---
> Hi Non-x86 Arch’s,
> 
> x86 has a feature that allows for the creation of a special type of
> writable memory (shadow stack) that is only writable in limited specific
> ways. Previously, changes were proposed to core MM code to teach it to
> decide when to create normally writable memory or the special shadow stack
> writable memory, but David Hildenbrand suggested[0] to change
> pXX_mkwrite() to take a VMA, so awareness of shadow stack memory can be
> moved into x86 code.
> 
> Since pXX_mkwrite() is defined in every arch, it requires some tree-wide
> changes. So that is why you are seeing some patches out of a big x86
> series pop up in your arch mailing list. There is no functional change.
> After this refactor, the shadow stack series goes on to use the arch
> helpers to push shadow stack memory details inside arch/x86.
> 
> Testing was just 0-day build testing.
> 
> Hopefully that is enough context. Thanks!
> 
> [0] https://lore.kernel.org/lkml/0e29a2d0-08d8-bcd6-ff26-4bea0e4037b0@redhat.com/#t
> 
> v6:
>   - New patch
> ---
>   Documentation/mm/arch_pgtable_helpers.rst    |  9 ++++++---
>   arch/alpha/include/asm/pgtable.h             |  6 +++++-
>   arch/arc/include/asm/hugepage.h              |  2 +-
>   arch/arc/include/asm/pgtable-bits-arcv2.h    |  7 ++++++-
>   arch/arm/include/asm/pgtable-3level.h        |  7 ++++++-
>   arch/arm/include/asm/pgtable.h               |  2 +-
>   arch/arm64/include/asm/pgtable.h             |  4 ++--
>   arch/csky/include/asm/pgtable.h              |  2 +-
>   arch/hexagon/include/asm/pgtable.h           |  2 +-
>   arch/ia64/include/asm/pgtable.h              |  2 +-
>   arch/loongarch/include/asm/pgtable.h         |  4 ++--
>   arch/m68k/include/asm/mcf_pgtable.h          |  2 +-
>   arch/m68k/include/asm/motorola_pgtable.h     |  6 +++++-
>   arch/m68k/include/asm/sun3_pgtable.h         |  6 +++++-
>   arch/microblaze/include/asm/pgtable.h        |  2 +-
>   arch/mips/include/asm/pgtable.h              |  6 +++---
>   arch/nios2/include/asm/pgtable.h             |  2 +-
>   arch/openrisc/include/asm/pgtable.h          |  2 +-
>   arch/parisc/include/asm/pgtable.h            |  6 +++++-
>   arch/powerpc/include/asm/book3s/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/book3s/64/pgtable.h |  4 ++--
>   arch/powerpc/include/asm/nohash/32/pgtable.h |  2 +-
>   arch/powerpc/include/asm/nohash/32/pte-8xx.h |  2 +-
>   arch/powerpc/include/asm/nohash/64/pgtable.h |  2 +-
>   arch/riscv/include/asm/pgtable.h             |  6 +++---
>   arch/s390/include/asm/hugetlb.h              |  4 ++--
>   arch/s390/include/asm/pgtable.h              |  4 ++--
>   arch/sh/include/asm/pgtable_32.h             | 10 ++++++++--
>   arch/sparc/include/asm/pgtable_32.h          |  2 +-
>   arch/sparc/include/asm/pgtable_64.h          |  6 +++---
>   arch/um/include/asm/pgtable.h                |  2 +-
>   arch/x86/include/asm/pgtable.h               |  6 ++++--
>   arch/xtensa/include/asm/pgtable.h            |  2 +-
>   include/asm-generic/hugetlb.h                |  4 ++--
>   include/linux/mm.h                           |  2 +-
>   mm/debug_vm_pgtable.c                        | 16 ++++++++--------
>   mm/huge_memory.c                             |  6 +++---
>   mm/hugetlb.c                                 |  4 ++--
>   mm/memory.c                                  |  4 ++--
>   mm/migrate_device.c                          |  2 +-
>   mm/mprotect.c                                |  2 +-
>   mm/userfaultfd.c                             |  2 +-
>   42 files changed, 106 insertions(+), 69 deletions(-)
> 
> diff --git a/Documentation/mm/arch_pgtable_helpers.rst b/Documentation/mm/arch_pgtable_helpers.rst
> index 30d9a09f01f4..78ac3ff2fe1d 100644
> --- a/Documentation/mm/arch_pgtable_helpers.rst
> +++ b/Documentation/mm/arch_pgtable_helpers.rst
> @@ -46,7 +46,8 @@ PTE Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pte_mkclean               | Creates a clean PTE                              |
>   +---------------------------+--------------------------------------------------+
> -| pte_mkwrite               | Creates a writable PTE                           |
> +| pte_mkwrite               | Creates a writable PTE of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pte_wrprotect             | Creates a write protected PTE                    |
>   +---------------------------+--------------------------------------------------+
> @@ -118,7 +119,8 @@ PMD Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | pmd_mkclean               | Creates a clean PMD                              |
>   +---------------------------+--------------------------------------------------+
> -| pmd_mkwrite               | Creates a writable PMD                           |
> +| pmd_mkwrite               | Creates a writable PMD of the type specified by  |
> +|                           | the VMA.                                         |
>   +---------------------------+--------------------------------------------------+
>   | pmd_wrprotect             | Creates a write protected PMD                    |
>   +---------------------------+--------------------------------------------------+
> @@ -222,7 +224,8 @@ HugeTLB Page Table Helpers
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_mkdirty          | Creates a dirty HugeTLB                          |
>   +---------------------------+--------------------------------------------------+
> -| huge_pte_mkwrite          | Creates a writable HugeTLB                       |
> +| huge_pte_mkwrite          | Creates a writable HugeTLB of the type specified |
> +|                           | by the VMA.                                      |
>   +---------------------------+--------------------------------------------------+
>   | huge_pte_wrprotect        | Creates a write protected HugeTLB                |
>   +---------------------------+--------------------------------------------------+
> diff --git a/arch/alpha/include/asm/pgtable.h b/arch/alpha/include/asm/pgtable.h
> index ba43cb841d19..fb5d207c2a89 100644
> --- a/arch/alpha/include/asm/pgtable.h
> +++ b/arch/alpha/include/asm/pgtable.h
> @@ -256,9 +256,13 @@ extern inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   extern inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~(__DIRTY_BITS); return pte; }
>   extern inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~(__ACCESS_BITS); return pte; }
> -extern inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_FOW; return pte; }
>   extern inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= __DIRTY_BITS; return pte; }
>   extern inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= __ACCESS_BITS; return pte; }
> +extern inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_FOW;
> +	return pte;
> +}
>   
>   /*
>    * The smp_rmb() in the following functions are required to order the load of
> diff --git a/arch/arc/include/asm/hugepage.h b/arch/arc/include/asm/hugepage.h
> index 5001b796fb8d..223a96967188 100644
> --- a/arch/arc/include/asm/hugepage.h
> +++ b/arch/arc/include/asm/hugepage.h
> @@ -21,7 +21,7 @@ static inline pmd_t pte_pmd(pte_t pte)
>   }
>   
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/arc/include/asm/pgtable-bits-arcv2.h b/arch/arc/include/asm/pgtable-bits-arcv2.h
> index 6e9f8ca6d6a1..a5b8bc955015 100644
> --- a/arch/arc/include/asm/pgtable-bits-arcv2.h
> +++ b/arch/arc/include/asm/pgtable-bits-arcv2.h
> @@ -87,7 +87,6 @@
>   
>   PTE_BIT_FUNC(mknotpresent,     &= ~(_PAGE_PRESENT));
>   PTE_BIT_FUNC(wrprotect,	&= ~(_PAGE_WRITE));
> -PTE_BIT_FUNC(mkwrite,	|= (_PAGE_WRITE));
>   PTE_BIT_FUNC(mkclean,	&= ~(_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkdirty,	|= (_PAGE_DIRTY));
>   PTE_BIT_FUNC(mkold,	&= ~(_PAGE_ACCESSED));
> @@ -95,6 +94,12 @@ PTE_BIT_FUNC(mkyoung,	|= (_PAGE_ACCESSED));
>   PTE_BIT_FUNC(mkspecial,	|= (_PAGE_SPECIAL));
>   PTE_BIT_FUNC(mkhuge,	|= (_PAGE_HW_SZ));
>   
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= (_PAGE_WRITE);
> +	return pte;
> +}
> +
>   static inline pte_t pte_modify(pte_t pte, pgprot_t newprot)
>   {
>   	return __pte((pte_val(pte) & _PAGE_CHG_MASK) | pgprot_val(newprot));
> diff --git a/arch/arm/include/asm/pgtable-3level.h b/arch/arm/include/asm/pgtable-3level.h
> index 106049791500..df071a807610 100644
> --- a/arch/arm/include/asm/pgtable-3level.h
> +++ b/arch/arm/include/asm/pgtable-3level.h
> @@ -202,11 +202,16 @@ static inline pmd_t pmd_##fn(pmd_t pmd) { pmd_val(pmd) op; return pmd; }
>   
>   PMD_BIT_FUNC(wrprotect,	|= L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkold,	&= ~PMD_SECT_AF);
> -PMD_BIT_FUNC(mkwrite,   &= ~L_PMD_SECT_RDONLY);
>   PMD_BIT_FUNC(mkdirty,   |= L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkclean,   &= ~L_PMD_SECT_DIRTY);
>   PMD_BIT_FUNC(mkyoung,   |= PMD_SECT_AF);
>   
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
> +{
> +	pmd_val(pmd) |= L_PMD_SECT_RDONLY;
> +	return pmd;
> +}
> +
>   #define pmd_mkhuge(pmd)		(__pmd(pmd_val(pmd) & ~PMD_TABLE_BIT))
>   
>   #define pmd_pfn(pmd)		(((pmd_val(pmd) & PMD_MASK) & PHYS_MASK) >> PAGE_SHIFT)
> diff --git a/arch/arm/include/asm/pgtable.h b/arch/arm/include/asm/pgtable.h
> index a58ccbb406ad..39ad1ae1308d 100644
> --- a/arch/arm/include/asm/pgtable.h
> +++ b/arch/arm/include/asm/pgtable.h
> @@ -227,7 +227,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   	return set_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return clear_pte_bit(pte, __pgprot(L_PTE_RDONLY));
>   }
> diff --git a/arch/arm64/include/asm/pgtable.h b/arch/arm64/include/asm/pgtable.h
> index cccf8885792e..913bf370f74a 100644
> --- a/arch/arm64/include/asm/pgtable.h
> +++ b/arch/arm64/include/asm/pgtable.h
> @@ -187,7 +187,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -492,7 +492,7 @@ static inline int pmd_trans_huge(pmd_t pmd)
>   #define pmd_cont(pmd)		pte_cont(pmd_pte(pmd))
>   #define pmd_wrprotect(pmd)	pte_pmd(pte_wrprotect(pmd_pte(pmd)))
>   #define pmd_mkold(pmd)		pte_pmd(pte_mkold(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> diff --git a/arch/csky/include/asm/pgtable.h b/arch/csky/include/asm/pgtable.h
> index d4042495febc..c2f92c991e37 100644
> --- a/arch/csky/include/asm/pgtable.h
> +++ b/arch/csky/include/asm/pgtable.h
> @@ -176,7 +176,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> diff --git a/arch/hexagon/include/asm/pgtable.h b/arch/hexagon/include/asm/pgtable.h
> index 59393613d086..14ab9c789c0e 100644
> --- a/arch/hexagon/include/asm/pgtable.h
> +++ b/arch/hexagon/include/asm/pgtable.h
> @@ -300,7 +300,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   }
>   
>   /* pte_mkwrite - mark page as writable */
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/ia64/include/asm/pgtable.h b/arch/ia64/include/asm/pgtable.h
> index 21c97e31a28a..f879dd626da6 100644
> --- a/arch/ia64/include/asm/pgtable.h
> +++ b/arch/ia64/include/asm/pgtable.h
> @@ -268,7 +268,7 @@ ia64_phys_addr_valid (unsigned long addr)
>    * access rights:
>    */
>   #define pte_wrprotect(pte)	(__pte(pte_val(pte) & ~_PAGE_AR_RW))
> -#define pte_mkwrite(pte)	(__pte(pte_val(pte) | _PAGE_AR_RW))
> +#define pte_mkwrite(pte, vma)	(__pte(pte_val(pte) | _PAGE_AR_RW))
>   #define pte_mkold(pte)		(__pte(pte_val(pte) & ~_PAGE_A))
>   #define pte_mkyoung(pte)	(__pte(pte_val(pte) | _PAGE_A))
>   #define pte_mkclean(pte)	(__pte(pte_val(pte) & ~_PAGE_D))
> diff --git a/arch/loongarch/include/asm/pgtable.h b/arch/loongarch/include/asm/pgtable.h
> index d28fb9dbec59..ebf645f40298 100644
> --- a/arch/loongarch/include/asm/pgtable.h
> +++ b/arch/loongarch/include/asm/pgtable.h
> @@ -390,7 +390,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -490,7 +490,7 @@ static inline int pmd_write(pmd_t pmd)
>   	return !!(pmd_val(pmd) & _PAGE_WRITE);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/m68k/include/asm/mcf_pgtable.h b/arch/m68k/include/asm/mcf_pgtable.h
> index 13741c1245e1..37d77e055016 100644
> --- a/arch/m68k/include/asm/mcf_pgtable.h
> +++ b/arch/m68k/include/asm/mcf_pgtable.h
> @@ -211,7 +211,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= CF_PAGE_WRITABLE;
>   	return pte;
> diff --git a/arch/m68k/include/asm/motorola_pgtable.h b/arch/m68k/include/asm/motorola_pgtable.h
> index ec0dc19ab834..c4e8eb76286d 100644
> --- a/arch/m68k/include/asm/motorola_pgtable.h
> +++ b/arch/m68k/include/asm/motorola_pgtable.h
> @@ -155,7 +155,6 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & _PAGE_ACCESSED;
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) |= _PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~_PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) &= ~_PAGE_RONLY; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)
> @@ -168,6 +167,11 @@ static inline pte_t pte_mkcache(pte_t pte)
>   	pte_val(pte) = (pte_val(pte) & _CACHEMASK040) | m68k_supervisor_cachemode;
>   	return pte;
>   }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) &= ~_PAGE_RONLY;
> +	return pte;
> +}
>   
>   #define swapper_pg_dir kernel_pg_dir
>   extern pgd_t kernel_pg_dir[128];
> diff --git a/arch/m68k/include/asm/sun3_pgtable.h b/arch/m68k/include/asm/sun3_pgtable.h
> index e582b0484a55..2a06bea51a1e 100644
> --- a/arch/m68k/include/asm/sun3_pgtable.h
> +++ b/arch/m68k/include/asm/sun3_pgtable.h
> @@ -143,10 +143,14 @@ static inline int pte_young(pte_t pte)		{ return pte_val(pte) & SUN3_PAGE_ACCESS
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkclean(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~SUN3_PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_WRITEABLE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_MODIFIED; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_ACCESSED; return pte; }
>   static inline pte_t pte_mknocache(pte_t pte)	{ pte_val(pte) |= SUN3_PAGE_NOCACHE; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= SUN3_PAGE_WRITEABLE;
> +	return pte;
> +}
>   // use this version when caches work...
>   //static inline pte_t pte_mkcache(pte_t pte)	{ pte_val(pte) &= SUN3_PAGE_NOCACHE; return pte; }
>   // until then, use:
> diff --git a/arch/microblaze/include/asm/pgtable.h b/arch/microblaze/include/asm/pgtable.h
> index d1b8272abcd9..5b83e82f8d7e 100644
> --- a/arch/microblaze/include/asm/pgtable.h
> +++ b/arch/microblaze/include/asm/pgtable.h
> @@ -266,7 +266,7 @@ static inline pte_t pte_mkread(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER; return pte; }
>   static inline pte_t pte_mkexec(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_USER | _PAGE_EXEC; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte) \
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma) \
>   	{ pte_val(pte) |= _PAGE_RW; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte) \
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
> diff --git a/arch/mips/include/asm/pgtable.h b/arch/mips/include/asm/pgtable.h
> index 791389bf3c12..06efd567144a 100644
> --- a/arch/mips/include/asm/pgtable.h
> +++ b/arch/mips/include/asm/pgtable.h
> @@ -309,7 +309,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte.pte_low |= _PAGE_WRITE;
>   	if (pte.pte_low & _PAGE_MODIFIED) {
> @@ -364,7 +364,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	if (pte_val(pte) & _PAGE_MODIFIED)
> @@ -626,7 +626,7 @@ static inline pmd_t pmd_wrprotect(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pmd_val(pmd) |= _PAGE_WRITE;
>   	if (pmd_val(pmd) & _PAGE_MODIFIED)
> diff --git a/arch/nios2/include/asm/pgtable.h b/arch/nios2/include/asm/pgtable.h
> index 0f5c2564e9f5..edd458518e0e 100644
> --- a/arch/nios2/include/asm/pgtable.h
> +++ b/arch/nios2/include/asm/pgtable.h
> @@ -129,7 +129,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/openrisc/include/asm/pgtable.h b/arch/openrisc/include/asm/pgtable.h
> index 3eb9b9555d0d..fd40aec189d1 100644
> --- a/arch/openrisc/include/asm/pgtable.h
> +++ b/arch/openrisc/include/asm/pgtable.h
> @@ -250,7 +250,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	pte_val(pte) |= _PAGE_WRITE;
>   	return pte;
> diff --git a/arch/parisc/include/asm/pgtable.h b/arch/parisc/include/asm/pgtable.h
> index e2950f5db7c9..89f62137e67f 100644
> --- a/arch/parisc/include/asm/pgtable.h
> +++ b/arch/parisc/include/asm/pgtable.h
> @@ -331,8 +331,12 @@ static inline pte_t pte_mkold(pte_t pte)	{ pte_val(pte) &= ~_PAGE_ACCESSED; retu
>   static inline pte_t pte_wrprotect(pte_t pte)	{ pte_val(pte) &= ~_PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkdirty(pte_t pte)	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)	{ pte_val(pte) |= _PAGE_WRITE; return pte; }
>   static inline pte_t pte_mkspecial(pte_t pte)	{ pte_val(pte) |= _PAGE_SPECIAL; return pte; }
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
> +{
> +	pte_val(pte) |= _PAGE_WRITE;
> +	return pte;
> +}
>   
>   /*
>    * Huge pte definitions.
> diff --git a/arch/powerpc/include/asm/book3s/32/pgtable.h b/arch/powerpc/include/asm/book3s/32/pgtable.h
> index 7bf1fe7297c6..10d9a1d2aca9 100644
> --- a/arch/powerpc/include/asm/book3s/32/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/32/pgtable.h
> @@ -498,7 +498,7 @@ static inline pte_t pte_mkpte(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/book3s/64/pgtable.h b/arch/powerpc/include/asm/book3s/64/pgtable.h
> index 4acc9690f599..be0636522d36 100644
> --- a/arch/powerpc/include/asm/book3s/64/pgtable.h
> +++ b/arch/powerpc/include/asm/book3s/64/pgtable.h
> @@ -600,7 +600,7 @@ static inline pte_t pte_mkexec(pte_t pte)
>   	return __pte_raw(pte_raw(pte) | cpu_to_be64(_PAGE_EXEC));
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	/*
>   	 * write implies read, hence set both
> @@ -1071,7 +1071,7 @@ static inline pte_t *pmdp_ptep(pmd_t *pmd)
>   #define pmd_mkdirty(pmd)	pte_pmd(pte_mkdirty(pmd_pte(pmd)))
>   #define pmd_mkclean(pmd)	pte_pmd(pte_mkclean(pmd_pte(pmd)))
>   #define pmd_mkyoung(pmd)	pte_pmd(pte_mkyoung(pmd_pte(pmd)))
> -#define pmd_mkwrite(pmd)	pte_pmd(pte_mkwrite(pmd_pte(pmd)))
> +#define pmd_mkwrite(pmd, vma)	pte_pmd(pte_mkwrite(pmd_pte(pmd), (vma)))
>   
>   #ifdef CONFIG_HAVE_ARCH_SOFT_DIRTY
>   #define pmd_soft_dirty(pmd)    pte_soft_dirty(pmd_pte(pmd))
> diff --git a/arch/powerpc/include/asm/nohash/32/pgtable.h b/arch/powerpc/include/asm/nohash/32/pgtable.h
> index fec56d965f00..7bfbcb9ba55b 100644
> --- a/arch/powerpc/include/asm/nohash/32/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/32/pgtable.h
> @@ -171,7 +171,7 @@ void unmap_kernel_page(unsigned long va);
>   	do { pte_update(mm, addr, ptep, ~0, 0, 0); } while (0)
>   
>   #ifndef pte_mkwrite
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/32/pte-8xx.h b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> index 1a89ebdc3acc..f32450eb270a 100644
> --- a/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> +++ b/arch/powerpc/include/asm/nohash/32/pte-8xx.h
> @@ -101,7 +101,7 @@ static inline int pte_write(pte_t pte)
>   
>   #define pte_write pte_write
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) & ~_PAGE_RO);
>   }
> diff --git a/arch/powerpc/include/asm/nohash/64/pgtable.h b/arch/powerpc/include/asm/nohash/64/pgtable.h
> index 287e25864ffa..589009555877 100644
> --- a/arch/powerpc/include/asm/nohash/64/pgtable.h
> +++ b/arch/powerpc/include/asm/nohash/64/pgtable.h
> @@ -85,7 +85,7 @@
>   #ifndef __ASSEMBLY__
>   /* pte_clear moved to later in this file */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_RW);
>   }
> diff --git a/arch/riscv/include/asm/pgtable.h b/arch/riscv/include/asm/pgtable.h
> index d8d8de0ded99..fed1b81fbe07 100644
> --- a/arch/riscv/include/asm/pgtable.h
> +++ b/arch/riscv/include/asm/pgtable.h
> @@ -338,7 +338,7 @@ static inline pte_t pte_wrprotect(pte_t pte)
>   
>   /* static inline pte_t pte_mkread(pte_t pte) */
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | _PAGE_WRITE);
>   }
> @@ -624,9 +624,9 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pte_pmd(pte_mkyoung(pmd_pte(pmd)));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
> -	return pte_pmd(pte_mkwrite(pmd_pte(pmd)));
> +	return pte_pmd(pte_mkwrite(pmd_pte(pmd), vma));
>   }
>   
>   static inline pmd_t pmd_wrprotect(pmd_t pmd)
> diff --git a/arch/s390/include/asm/hugetlb.h b/arch/s390/include/asm/hugetlb.h
> index ccdbccfde148..558f7eef9c4d 100644
> --- a/arch/s390/include/asm/hugetlb.h
> +++ b/arch/s390/include/asm/hugetlb.h
> @@ -102,9 +102,9 @@ static inline int huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   static inline pte_t huge_pte_mkdirty(pte_t pte)
> diff --git a/arch/s390/include/asm/pgtable.h b/arch/s390/include/asm/pgtable.h
> index deeb918cae1d..8f2c743da0eb 100644
> --- a/arch/s390/include/asm/pgtable.h
> +++ b/arch/s390/include/asm/pgtable.h
> @@ -1013,7 +1013,7 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte;
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -1499,7 +1499,7 @@ static inline pmd_t pmd_mkwrite_kernel(pmd_t pmd)
>   	return pmd;
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_mkwrite_kernel(pmd);
>   }
> diff --git a/arch/sh/include/asm/pgtable_32.h b/arch/sh/include/asm/pgtable_32.h
> index 21952b094650..9f2dcb9eafc8 100644
> --- a/arch/sh/include/asm/pgtable_32.h
> +++ b/arch/sh/include/asm/pgtable_32.h
> @@ -351,6 +351,12 @@ static inline void set_pte(pte_t *ptep, pte_t pte)
>   
>   #define PTE_BIT_FUNC(h,fn,op) \
>   static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
> +#define PTE_BIT_FUNC_VMA(h,fn,op) \
> +static inline pte_t pte_##fn(pte_t pte, struct vm_area_struct *vma) \
> +{ \
> +	pte.pte_##h op; \
> +	return pte; \
> +}
>   
>   #ifdef CONFIG_X2TLB
>   /*
> @@ -359,11 +365,11 @@ static inline pte_t pte_##fn(pte_t pte) { pte.pte_##h op; return pte; }
>    * kernel permissions), we attempt to couple them a bit more sanely here.
>    */
>   PTE_BIT_FUNC(high, wrprotect, &= ~(_PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE));
> -PTE_BIT_FUNC(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
> +PTE_BIT_FUNC_VMA(high, mkwrite, |= _PAGE_EXT_USER_WRITE | _PAGE_EXT_KERN_WRITE);
>   PTE_BIT_FUNC(high, mkhuge, |= _PAGE_SZHUGE);
>   #else
>   PTE_BIT_FUNC(low, wrprotect, &= ~_PAGE_RW);
> -PTE_BIT_FUNC(low, mkwrite, |= _PAGE_RW);
> +PTE_BIT_FUNC_VMA(low, mkwrite, |= _PAGE_RW);
>   PTE_BIT_FUNC(low, mkhuge, |= _PAGE_SZHUGE);
>   #endif
>   
> diff --git a/arch/sparc/include/asm/pgtable_32.h b/arch/sparc/include/asm/pgtable_32.h
> index d4330e3c57a6..3e8836179456 100644
> --- a/arch/sparc/include/asm/pgtable_32.h
> +++ b/arch/sparc/include/asm/pgtable_32.h
> @@ -241,7 +241,7 @@ static inline pte_t pte_mkold(pte_t pte)
>   	return __pte(pte_val(pte) & ~SRMMU_REF);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return __pte(pte_val(pte) | SRMMU_WRITE);
>   }
> diff --git a/arch/sparc/include/asm/pgtable_64.h b/arch/sparc/include/asm/pgtable_64.h
> index 2dc8d4641734..c5cd5c03f557 100644
> --- a/arch/sparc/include/asm/pgtable_64.h
> +++ b/arch/sparc/include/asm/pgtable_64.h
> @@ -466,7 +466,7 @@ static inline pte_t pte_mkclean(pte_t pte)
>   	return __pte(val);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	unsigned long val = pte_val(pte), mask;
>   
> @@ -756,11 +756,11 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return __pmd(pte_val(pte));
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	pte_t pte = __pte(pmd_val(pmd));
>   
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, vma);
>   
>   	return __pmd(pte_val(pte));
>   }
> diff --git a/arch/um/include/asm/pgtable.h b/arch/um/include/asm/pgtable.h
> index a70d1618eb35..963479c133b7 100644
> --- a/arch/um/include/asm/pgtable.h
> +++ b/arch/um/include/asm/pgtable.h
> @@ -207,7 +207,7 @@ static inline pte_t pte_mkyoung(pte_t pte)
>   	return(pte);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (unlikely(pte_get_bits(pte,  _PAGE_RW)))
>   		return pte;
> diff --git a/arch/x86/include/asm/pgtable.h b/arch/x86/include/asm/pgtable.h
> index 3607f2572f9e..66c514808276 100644
> --- a/arch/x86/include/asm/pgtable.h
> +++ b/arch/x86/include/asm/pgtable.h
> @@ -369,7 +369,9 @@ static inline pte_t pte_mkwrite_kernel(pte_t pte)
>   	return pte_set_flags(pte, _PAGE_RW);
>   }
>   
> -static inline pte_t pte_mkwrite(pte_t pte)
> +struct vm_area_struct;
> +
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	return pte_mkwrite_kernel(pte);
>   }
> @@ -470,7 +472,7 @@ static inline pmd_t pmd_mkyoung(pmd_t pmd)
>   	return pmd_set_flags(pmd, _PAGE_ACCESSED);
>   }
>   
> -static inline pmd_t pmd_mkwrite(pmd_t pmd)
> +static inline pmd_t pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	return pmd_set_flags(pmd, _PAGE_RW);
>   }
> diff --git a/arch/xtensa/include/asm/pgtable.h b/arch/xtensa/include/asm/pgtable.h
> index fc7a14884c6c..d72632d9c53c 100644
> --- a/arch/xtensa/include/asm/pgtable.h
> +++ b/arch/xtensa/include/asm/pgtable.h
> @@ -262,7 +262,7 @@ static inline pte_t pte_mkdirty(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_DIRTY; return pte; }
>   static inline pte_t pte_mkyoung(pte_t pte)
>   	{ pte_val(pte) |= _PAGE_ACCESSED; return pte; }
> -static inline pte_t pte_mkwrite(pte_t pte)
> +static inline pte_t pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   	{ pte_val(pte) |= _PAGE_WRITABLE; return pte; }
>   
>   #define pgprot_noncached(prot) \
> diff --git a/include/asm-generic/hugetlb.h b/include/asm-generic/hugetlb.h
> index d7f6335d3999..e86c830728de 100644
> --- a/include/asm-generic/hugetlb.h
> +++ b/include/asm-generic/hugetlb.h
> @@ -20,9 +20,9 @@ static inline unsigned long huge_pte_dirty(pte_t pte)
>   	return pte_dirty(pte);
>   }
>   
> -static inline pte_t huge_pte_mkwrite(pte_t pte)
> +static inline pte_t huge_pte_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
> -	return pte_mkwrite(pte);
> +	return pte_mkwrite(pte, vma);
>   }
>   
>   #ifndef __HAVE_ARCH_HUGE_PTE_WRPROTECT
> diff --git a/include/linux/mm.h b/include/linux/mm.h
> index 1f79667824eb..af652444fbba 100644
> --- a/include/linux/mm.h
> +++ b/include/linux/mm.h
> @@ -1163,7 +1163,7 @@ void free_compound_page(struct page *page);
>   static inline pte_t maybe_mkwrite(pte_t pte, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	return pte;
>   }
>   
> diff --git a/mm/debug_vm_pgtable.c b/mm/debug_vm_pgtable.c
> index af59cc7bd307..7bc5592900bc 100644
> --- a/mm/debug_vm_pgtable.c
> +++ b/mm/debug_vm_pgtable.c
> @@ -109,10 +109,10 @@ static void __init pte_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pte_same(pte, pte));
>   	WARN_ON(!pte_young(pte_mkyoung(pte_mkold(pte))));
>   	WARN_ON(!pte_dirty(pte_mkdirty(pte_mkclean(pte))));
> -	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte))));
> +	WARN_ON(!pte_write(pte_mkwrite(pte_wrprotect(pte), args->vma)));
>   	WARN_ON(pte_young(pte_mkold(pte_mkyoung(pte))));
>   	WARN_ON(pte_dirty(pte_mkclean(pte_mkdirty(pte))));
> -	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte))));
> +	WARN_ON(pte_write(pte_wrprotect(pte_mkwrite(pte, args->vma))));
>   	WARN_ON(pte_dirty(pte_wrprotect(pte_mkclean(pte))));
>   	WARN_ON(!pte_dirty(pte_wrprotect(pte_mkdirty(pte))));
>   }
> @@ -153,7 +153,7 @@ static void __init pte_advanced_tests(struct pgtable_debug_args *args)
>   	pte = pte_mkclean(pte);
>   	set_pte_at(args->mm, args->vaddr, args->ptep, pte);
>   	flush_dcache_page(page);
> -	pte = pte_mkwrite(pte);
> +	pte = pte_mkwrite(pte, args->vma);
>   	pte = pte_mkdirty(pte);
>   	ptep_set_access_flags(args->vma, args->vaddr, args->ptep, pte, 1);
>   	pte = ptep_get(args->ptep);
> @@ -199,10 +199,10 @@ static void __init pmd_basic_tests(struct pgtable_debug_args *args, int idx)
>   	WARN_ON(!pmd_same(pmd, pmd));
>   	WARN_ON(!pmd_young(pmd_mkyoung(pmd_mkold(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_mkdirty(pmd_mkclean(pmd))));
> -	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd))));
> +	WARN_ON(!pmd_write(pmd_mkwrite(pmd_wrprotect(pmd), args->vma)));
>   	WARN_ON(pmd_young(pmd_mkold(pmd_mkyoung(pmd))));
>   	WARN_ON(pmd_dirty(pmd_mkclean(pmd_mkdirty(pmd))));
> -	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd))));
> +	WARN_ON(pmd_write(pmd_wrprotect(pmd_mkwrite(pmd, args->vma))));
>   	WARN_ON(pmd_dirty(pmd_wrprotect(pmd_mkclean(pmd))));
>   	WARN_ON(!pmd_dirty(pmd_wrprotect(pmd_mkdirty(pmd))));
>   	/*
> @@ -253,7 +253,7 @@ static void __init pmd_advanced_tests(struct pgtable_debug_args *args)
>   	pmd = pmd_mkclean(pmd);
>   	set_pmd_at(args->mm, vaddr, args->pmdp, pmd);
>   	flush_dcache_page(page);
> -	pmd = pmd_mkwrite(pmd);
> +	pmd = pmd_mkwrite(pmd, args->vma);
>   	pmd = pmd_mkdirty(pmd);
>   	pmdp_set_access_flags(args->vma, vaddr, args->pmdp, pmd, 1);
>   	pmd = READ_ONCE(*args->pmdp);
> @@ -928,8 +928,8 @@ static void __init hugetlb_basic_tests(struct pgtable_debug_args *args)
>   	pte = mk_huge_pte(page, args->page_prot);
>   
>   	WARN_ON(!huge_pte_dirty(huge_pte_mkdirty(pte)));
> -	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte))));
> -	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte))));
> +	WARN_ON(!huge_pte_write(huge_pte_mkwrite(huge_pte_wrprotect(pte), args->vma)));
> +	WARN_ON(huge_pte_write(huge_pte_wrprotect(huge_pte_mkwrite(pte, args->vma))));
>   
>   #ifdef CONFIG_ARCH_WANT_GENERAL_HUGETLB
>   	pte = pfn_pte(args->fixed_pmd_pfn, args->page_prot);
> diff --git a/mm/huge_memory.c b/mm/huge_memory.c
> index 4fc43859e59a..aaf815838144 100644
> --- a/mm/huge_memory.c
> +++ b/mm/huge_memory.c
> @@ -555,7 +555,7 @@ __setup("transparent_hugepage=", setup_transparent_hugepage);
>   pmd_t maybe_pmd_mkwrite(pmd_t pmd, struct vm_area_struct *vma)
>   {
>   	if (likely(vma->vm_flags & VM_WRITE))
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	return pmd;
>   }
>   
> @@ -1580,7 +1580,7 @@ vm_fault_t do_huge_pmd_numa_page(struct vm_fault *vmf)
>   	pmd = pmd_modify(oldpmd, vma->vm_page_prot);
>   	pmd = pmd_mkyoung(pmd);
>   	if (writable)
> -		pmd = pmd_mkwrite(pmd);
> +		pmd = pmd_mkwrite(pmd, vma);
>   	set_pmd_at(vma->vm_mm, haddr, vmf->pmd, pmd);
>   	update_mmu_cache_pmd(vma, vmf->address, vmf->pmd);
>   	spin_unlock(vmf->ptl);
> @@ -1926,7 +1926,7 @@ int change_huge_pmd(struct mmu_gather *tlb, struct vm_area_struct *vma,
>   	/* See change_pte_range(). */
>   	if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) && !pmd_write(entry) &&
>   	    can_change_pmd_writable(vma, addr, entry))
> -		entry = pmd_mkwrite(entry);
> +		entry = pmd_mkwrite(entry, vma);
>   
>   	ret = HPAGE_PMD_NR;
>   	set_pmd_at(mm, addr, pmd, entry);
> diff --git a/mm/hugetlb.c b/mm/hugetlb.c
> index 07abcb6eb203..6af471bdcff8 100644
> --- a/mm/hugetlb.c
> +++ b/mm/hugetlb.c
> @@ -4900,7 +4900,7 @@ static pte_t make_huge_pte(struct vm_area_struct *vma, struct page *page,
>   
>   	if (writable) {
>   		entry = huge_pte_mkwrite(huge_pte_mkdirty(mk_huge_pte(page,
> -					 vma->vm_page_prot)));
> +					 vma->vm_page_prot)), vma);
>   	} else {
>   		entry = huge_pte_wrprotect(mk_huge_pte(page,
>   					   vma->vm_page_prot));
> @@ -4916,7 +4916,7 @@ static void set_huge_ptep_writable(struct vm_area_struct *vma,
>   {
>   	pte_t entry;
>   
> -	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)));
> +	entry = huge_pte_mkwrite(huge_pte_mkdirty(huge_ptep_get(ptep)), vma);
>   	if (huge_ptep_set_access_flags(vma, address, ptep, entry, 1))
>   		update_mmu_cache(vma, address, ptep);
>   }
> diff --git a/mm/memory.c b/mm/memory.c
> index f456f3b5049c..d0972d2d6f36 100644
> --- a/mm/memory.c
> +++ b/mm/memory.c
> @@ -4067,7 +4067,7 @@ static vm_fault_t do_anonymous_page(struct vm_fault *vmf)
>   	entry = mk_pte(&folio->page, vma->vm_page_prot);
>   	entry = pte_sw_mkyoung(entry);
>   	if (vma->vm_flags & VM_WRITE)
> -		entry = pte_mkwrite(pte_mkdirty(entry));
> +		entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   
>   	vmf->pte = pte_offset_map_lock(vma->vm_mm, vmf->pmd, vmf->address,
>   			&vmf->ptl);
> @@ -4755,7 +4755,7 @@ static vm_fault_t do_numa_page(struct vm_fault *vmf)
>   	pte = pte_modify(old_pte, vma->vm_page_prot);
>   	pte = pte_mkyoung(pte);
>   	if (writable)
> -		pte = pte_mkwrite(pte);
> +		pte = pte_mkwrite(pte, vma);
>   	ptep_modify_prot_commit(vma, vmf->address, vmf->pte, old_pte, pte);
>   	update_mmu_cache(vma, vmf->address, vmf->pte);
>   	pte_unmap_unlock(vmf->pte, vmf->ptl);
> diff --git a/mm/migrate_device.c b/mm/migrate_device.c
> index d30c9de60b0d..df3f5e9d5f76 100644
> --- a/mm/migrate_device.c
> +++ b/mm/migrate_device.c
> @@ -646,7 +646,7 @@ static void migrate_vma_insert_page(struct migrate_vma *migrate,
>   		}
>   		entry = mk_pte(page, vma->vm_page_prot);
>   		if (vma->vm_flags & VM_WRITE)
> -			entry = pte_mkwrite(pte_mkdirty(entry));
> +			entry = pte_mkwrite(pte_mkdirty(entry), vma);
>   	}
>   
>   	ptep = pte_offset_map_lock(mm, pmdp, addr, &ptl);
> diff --git a/mm/mprotect.c b/mm/mprotect.c
> index 1d4843c97c2a..381163a41e88 100644
> --- a/mm/mprotect.c
> +++ b/mm/mprotect.c
> @@ -198,7 +198,7 @@ static long change_pte_range(struct mmu_gather *tlb,
>   			if ((cp_flags & MM_CP_TRY_CHANGE_WRITABLE) &&
>   			    !pte_write(ptent) &&
>   			    can_change_pte_writable(vma, addr, ptent))
> -				ptent = pte_mkwrite(ptent);
> +				ptent = pte_mkwrite(ptent, vma);
>   
>   			ptep_modify_prot_commit(vma, addr, pte, oldpte, ptent);
>   			if (pte_needs_flush(oldpte, ptent))
> diff --git a/mm/userfaultfd.c b/mm/userfaultfd.c
> index 53c3d916ff66..3db6f87c0aca 100644
> --- a/mm/userfaultfd.c
> +++ b/mm/userfaultfd.c
> @@ -75,7 +75,7 @@ int mfill_atomic_install_pte(struct mm_struct *dst_mm, pmd_t *dst_pmd,
>   	if (page_in_cache && !vm_shared)
>   		writable = false;
>   	if (writable)
> -		_dst_pte = pte_mkwrite(_dst_pte);
> +		_dst_pte = pte_mkwrite(_dst_pte, dst_vma);
>   	if (wp_copy)
>   		_dst_pte = pte_mkuffd_wp(_dst_pte);
>   

  reply	other threads:[~2023-03-01  7:03 UTC|newest]

Thread overview: 184+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2023-02-27 22:29 [PATCH v7 00/41] Shadow stacks for userspace Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 01/41] Documentation/x86: Add CET shadow stack description Rick Edgecombe
2023-03-01 14:21   ` Szabolcs Nagy
2023-03-01 14:38     ` Szabolcs Nagy
2023-03-01 18:07     ` Edgecombe, Rick P
2023-03-01 18:32       ` Edgecombe, Rick P
2023-03-02 16:34         ` szabolcs.nagy
2023-03-03 22:35           ` Edgecombe, Rick P
2023-03-06 16:20             ` szabolcs.nagy
2023-03-06 16:31               ` Florian Weimer
2023-03-06 18:08                 ` Edgecombe, Rick P
2023-03-07 13:03                   ` szabolcs.nagy
2023-03-07 14:00                     ` Florian Weimer
2023-03-07 16:14                       ` Szabolcs Nagy
2023-03-06 18:05               ` Edgecombe, Rick P
2023-03-06 20:31                 ` Liang, Kan
2023-03-02 16:14       ` szabolcs.nagy
2023-03-02 21:17         ` Edgecombe, Rick P
2023-03-03 16:30           ` szabolcs.nagy
2023-03-03 16:57             ` H.J. Lu
2023-03-03 17:39               ` szabolcs.nagy
2023-03-03 17:50                 ` H.J. Lu
2023-03-03 17:41             ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 02/41] x86/shstk: Add Kconfig option for shadow stack Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 03/41] x86/cpufeatures: Add CPU feature flags for shadow stacks Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 04/41] x86/cpufeatures: Enable CET CR4 bit for shadow stack Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 05/41] x86/fpu/xstate: Introduce CET MSR and XSAVES supervisor states Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 06/41] x86/fpu: Add helper for modifying xstate Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 07/41] x86: Move control protection handler to separate file Rick Edgecombe
2023-03-01 15:38   ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 08/41] x86/shstk: Add user control-protection fault handler Rick Edgecombe
2023-03-01 18:06   ` Borislav Petkov
2023-03-01 18:14     ` Edgecombe, Rick P
2023-03-01 18:37       ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 09/41] x86/mm: Remove _PAGE_DIRTY from kernel RO pages Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 10/41] x86/mm: Move pmd_write(), pud_write() up in the file Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 11/41] mm: Introduce pte_mkwrite_kernel() Rick Edgecombe
2023-02-27 22:29   ` Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 12/41] s390/mm: Introduce pmd_mkwrite_kernel() Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 13/41] mm: Make pte_mkwrite() take a VMA Rick Edgecombe
2023-02-27 22:29   ` Rick Edgecombe
2023-02-27 22:29   ` Rick Edgecombe
2023-02-27 22:29   ` Rick Edgecombe
2023-02-27 22:29   ` Rick Edgecombe
2023-02-27 22:29   ` Rick Edgecombe
2023-02-27 22:29   ` Rick Edgecombe
2023-03-01  7:03   ` Christophe Leroy [this message]
2023-03-01  7:03     ` Christophe Leroy
2023-03-01  7:03     ` Christophe Leroy
2023-03-01  7:03     ` Christophe Leroy
2023-03-01  7:03     ` Christophe Leroy
2023-03-01  7:03     ` Christophe Leroy
2023-03-01  7:03     ` Christophe Leroy
2023-03-01  8:16     ` David Hildenbrand
2023-03-01  8:16       ` David Hildenbrand
2023-03-01  8:16       ` David Hildenbrand
2023-03-01  8:16       ` David Hildenbrand
2023-03-01  8:16       ` David Hildenbrand
2023-03-01  8:16       ` David Hildenbrand
2023-03-01  8:16       ` David Hildenbrand
2023-03-02 12:19   ` Borislav Petkov
2023-03-02 12:19     ` Borislav Petkov
2023-03-02 12:19     ` Borislav Petkov
2023-03-02 12:19     ` Borislav Petkov
2023-03-02 12:19     ` Borislav Petkov
2023-03-02 12:19     ` Borislav Petkov
2023-03-02 12:19     ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 14/41] x86/mm: Introduce _PAGE_SAVED_DIRTY Rick Edgecombe
2023-03-02 12:48   ` Borislav Petkov
2023-03-02 17:01     ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 15/41] x86/mm: Update ptep/pmdp_set_wrprotect() for _PAGE_SAVED_DIRTY Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 16/41] x86/mm: Start actually marking _PAGE_SAVED_DIRTY Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 17/41] mm: Move VM_UFFD_MINOR_BIT from 37 to 38 Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 18/41] mm: Introduce VM_SHADOW_STACK for shadow stack memory Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 19/41] x86/mm: Check shadow stack page fault errors Rick Edgecombe
2023-03-03 14:00   ` Borislav Petkov
2023-03-03 14:39     ` Dave Hansen
2023-02-27 22:29 ` [PATCH v7 20/41] x86/mm: Teach pte_mkwrite() about stack memory Rick Edgecombe
2023-03-03 15:37   ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 21/41] mm: Add guard pages around a shadow stack Rick Edgecombe
2023-03-06  8:08   ` Borislav Petkov
2023-03-07  1:29     ` Edgecombe, Rick P
2023-03-07 10:32       ` Borislav Petkov
2023-03-07 10:44         ` David Hildenbrand
2023-03-08 22:48           ` Edgecombe, Rick P
2023-03-17 17:09   ` Deepak Gupta
2023-02-27 22:29 ` [PATCH v7 22/41] mm/mmap: Add shadow stack pages to memory accounting Rick Edgecombe
2023-03-06 13:01   ` Borislav Petkov
2023-03-06 18:11     ` Edgecombe, Rick P
2023-03-06 18:16       ` Borislav Petkov
2023-03-07 10:42   ` David Hildenbrand
2023-03-17 17:12   ` Deepak Gupta
2023-03-17 17:16     ` Dave Hansen
2023-03-17 17:28       ` Deepak Gupta
2023-03-17 17:42         ` Edgecombe, Rick P
2023-03-17 19:26           ` Deepak Gupta
2023-02-27 22:29 ` [PATCH v7 23/41] mm: Re-introduce vm_flags to do_mmap() Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 24/41] mm: Don't allow write GUPs to shadow stack memory Rick Edgecombe
2023-03-06 13:10   ` Borislav Petkov
2023-03-06 18:15     ` Andy Lutomirski
2023-03-06 18:33       ` Edgecombe, Rick P
2023-03-06 18:57         ` Andy Lutomirski
2023-03-07  1:47           ` Edgecombe, Rick P
2023-03-17 17:05   ` Deepak Gupta
2023-02-27 22:29 ` [PATCH v7 25/41] x86/mm: Introduce MAP_ABOVE4G Rick Edgecombe
2023-03-06 18:09   ` Borislav Petkov
2023-03-07  1:10     ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 26/41] mm: Warn on shadow stack memory in wrong vma Rick Edgecombe
2023-03-08  8:53   ` Borislav Petkov
2023-03-08 23:36     ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 27/41] x86/mm: Warn if create Write=0,Dirty=1 with raw prot Rick Edgecombe
2023-02-27 22:54   ` Kees Cook
2023-03-08  9:23   ` Borislav Petkov
2023-03-08 23:35     ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 28/41] x86: Introduce userspace API for shadow stack Rick Edgecombe
2023-03-08 10:27   ` Borislav Petkov
2023-03-08 23:32     ` Edgecombe, Rick P
2023-03-09 12:57       ` Borislav Petkov
2023-03-09 16:56         ` Edgecombe, Rick P
2023-03-09 23:51           ` Borislav Petkov
2023-03-10  1:13             ` Edgecombe, Rick P
2023-03-10  2:03               ` H.J. Lu
2023-03-10 20:00                 ` H.J. Lu
2023-03-10 20:27                   ` Edgecombe, Rick P
2023-03-10 20:43                     ` H.J. Lu
2023-03-10 21:01                       ` Edgecombe, Rick P
2023-03-10 11:40               ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 29/41] x86/shstk: Add user-mode shadow stack support Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 30/41] x86/shstk: Handle thread shadow stack Rick Edgecombe
2023-03-02 17:34   ` Szabolcs Nagy
2023-03-02 21:48     ` Edgecombe, Rick P
2023-03-08 15:26   ` Borislav Petkov
2023-03-08 20:03     ` Edgecombe, Rick P
2023-03-09 14:12       ` Borislav Petkov
2023-03-09 16:59         ` Edgecombe, Rick P
2023-03-09 17:04           ` Borislav Petkov
2023-03-09 20:29             ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 31/41] x86/shstk: Introduce routines modifying shstk Rick Edgecombe
2023-03-09 16:48   ` Borislav Petkov
2023-03-09 17:03     ` Edgecombe, Rick P
2023-03-09 17:22       ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 32/41] x86/shstk: Handle signals for shadow stack Rick Edgecombe
2023-03-09 17:02   ` Borislav Petkov
2023-03-09 17:16     ` Edgecombe, Rick P
2023-03-09 23:35       ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 33/41] x86/shstk: Introduce map_shadow_stack syscall Rick Edgecombe
2023-03-02 17:22   ` Szabolcs Nagy
2023-03-02 21:21     ` Edgecombe, Rick P
2023-03-09 18:55     ` Deepak Gupta
2023-03-09 19:39       ` Edgecombe, Rick P
2023-03-09 21:08         ` Deepak Gupta
2023-03-10  0:14           ` Edgecombe, Rick P
2023-03-10 21:00             ` Deepak Gupta
2023-03-10 21:43               ` Edgecombe, Rick P
2023-03-16 20:07                 ` Deepak Gupta
2023-03-14  7:19       ` Mike Rapoport
2023-03-16 19:30         ` Deepak Gupta
2023-03-20 11:35           ` Szabolcs Nagy
2023-03-10 16:11   ` Borislav Petkov
2023-03-10 17:12     ` Edgecombe, Rick P
2023-03-10 20:05       ` Borislav Petkov
2023-03-10 20:19         ` Edgecombe, Rick P
2023-03-10 20:26           ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 34/41] x86/shstk: Support WRSS for userspace Rick Edgecombe
2023-03-10 16:44   ` Borislav Petkov
2023-03-10 17:16     ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 35/41] x86: Expose thread features in /proc/$PID/status Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 36/41] x86/shstk: Wire in shadow stack interface Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 37/41] selftests/x86: Add shadow stack test Rick Edgecombe
2023-02-27 22:29 ` [PATCH v7 38/41] x86/fpu: Add helper for initing features Rick Edgecombe
2023-03-11 12:54   ` Borislav Petkov
2023-03-13  2:45     ` Edgecombe, Rick P
2023-03-13 11:03       ` Borislav Petkov
2023-03-13 16:10         ` Edgecombe, Rick P
2023-03-13 17:10           ` Borislav Petkov
2023-03-13 23:31             ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 39/41] x86: Add PTRACE interface for shadow stack Rick Edgecombe
2023-03-11 15:06   ` Borislav Petkov
2023-03-13  2:53     ` Edgecombe, Rick P
2023-02-27 22:29 ` [PATCH v7 40/41] x86/shstk: Add ARCH_SHSTK_UNLOCK Rick Edgecombe
2023-03-11 15:11   ` Borislav Petkov
2023-03-13  3:04     ` Edgecombe, Rick P
2023-03-13 11:05       ` Borislav Petkov
2023-02-27 22:29 ` [PATCH v7 41/41] x86/shstk: Add ARCH_SHSTK_STATUS Rick Edgecombe

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1f8b78b6-9f34-b646-68f2-eac62136b9f4@csgroup.eu \
    --to=christophe.leroy@csgroup.eu \
    --cc=Andrew.Cooper3@citrix.com \
    --cc=akpm@linux-foundation.org \
    --cc=arnd@arndb.de \
    --cc=bp@alien8.de \
    --cc=bsingharora@gmail.com \
    --cc=christina.schimpe@intel.com \
    --cc=corbet@lwn.net \
    --cc=dave.hansen@linux.intel.com \
    --cc=david@redhat.com \
    --cc=debug@rivosinc.com \
    --cc=dethoma@microsoft.com \
    --cc=dinguyen@kernel.org \
    --cc=eranian@google.com \
    --cc=esyr@redhat.com \
    --cc=fweimer@redhat.com \
    --cc=gorcunov@gmail.com \
    --cc=hjl.tools@gmail.com \
    --cc=hpa@zytor.com \
    --cc=jamorris@linux.microsoft.com \
    --cc=jannh@google.com \
    --cc=john.allen@amd.com \
    --cc=kcc@google.com \
    --cc=keescook@chromium.org \
    --cc=kirill.shutemov@linux.intel.com \
    --cc=linux-alpha@vger.kernel.org \
    --cc=linux-api@vger.kernel.org \
    --cc=linux-arch@vger.kernel.org \
    --cc=linux-arm-kernel@lists.infradead.org \
    --cc=linux-csky@vger.kernel.org \
    --cc=linux-doc@vger.kernel.org \
    --cc=linux-hexagon@vger.kernel.org \
    --cc=linux-ia64@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-m68k@lists.linux-m68k.org \
    --cc=linux-mips@vger.kernel.org \
    --cc=linux-mm@kvack.org \
    --cc=linux-openrisc@vger.kernel.org \
    --cc=linux-parisc@vger.kernel.org \
    --cc=linux-riscv@lists.infradead.org \
    --cc=linux-s390@vger.kernel.org \
    --cc=linux-sh@vger.kernel.org \
    --cc=linux-snps-arc@lists.infradead.org \
    --cc=linux-um@lists.infradead.org \
    --cc=linuxppc-dev@lists.ozlabs.org \
    --cc=loongarch@lists.linux.dev \
    --cc=luto@kernel.org \
    --cc=mike.kravetz@oracle.com \
    --cc=mingo@redhat.com \
    --cc=monstr@monstr.eu \
    --cc=nadav.amit@gmail.com \
    --cc=oleg@redhat.com \
    --cc=pavel@ucw.cz \
    --cc=peterz@infradead.org \
    --cc=rdunlap@infradead.org \
    --cc=rick.p.edgecombe@intel.com \
    --cc=rppt@kernel.org \
    --cc=sparclinux@vger.kernel.org \
    --cc=tglx@linutronix.de \
    --cc=weijiang.yang@intel.com \
    --cc=x86@kernel.org \
    --cc=xen-devel@lists.xenproject.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.