]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
s390/uv: Convert uv_convert_owned_from_secure() to uv_convert_from_secure_(folio...
authorDavid Hildenbrand <david@redhat.com>
Wed, 8 May 2024 18:29:53 +0000 (20:29 +0200)
committerAlexander Gordeev <agordeev@linux.ibm.com>
Wed, 5 Jun 2024 15:17:25 +0000 (17:17 +0200)
Let's do the same as we did for uv_destroy_(folio|pte)() and
have the following variants:

(1) uv_convert_from_secure(): "low level" helper that operates on paddr
and does not mess with folios.

(2) uv_convert_from_secure_folio(): Consumes a folio to which we hold a
reference.

(3) uv_convert_from_secure_pte(): Consumes a PTE that holds a reference
through the mapping.

Unfortunately we need uv_convert_from_secure_pte(), because pfn_folio()
and friends are not available in pgtable.h.

Reviewed-by: Claudio Imbrenda <imbrenda@linux.ibm.com>
Signed-off-by: David Hildenbrand <david@redhat.com>
Link: https://lore.kernel.org/r/20240508182955.358628-9-david@redhat.com
Signed-off-by: Heiko Carstens <hca@linux.ibm.com>
Signed-off-by: Alexander Gordeev <agordeev@linux.ibm.com>
arch/s390/include/asm/pgtable.h
arch/s390/include/asm/uv.h
arch/s390/kernel/uv.c

index e9eaa4281d94d24261e66bd4684bb24c7ddc29bc..0fd5a9c7e90147fe7e514da00ffce40e55f72b8c 100644 (file)
@@ -1167,7 +1167,7 @@ static inline pte_t ptep_get_and_clear(struct mm_struct *mm,
        res = ptep_xchg_lazy(mm, addr, ptep, __pte(_PAGE_INVALID));
        /* At this point the reference through the mapping is still present */
        if (mm_is_protected(mm) && pte_present(res))
-               uv_convert_owned_from_secure(pte_val(res) & PAGE_MASK);
+               uv_convert_from_secure_pte(res);
        return res;
 }
 
@@ -1185,7 +1185,7 @@ static inline pte_t ptep_clear_flush(struct vm_area_struct *vma,
        res = ptep_xchg_direct(vma->vm_mm, addr, ptep, __pte(_PAGE_INVALID));
        /* At this point the reference through the mapping is still present */
        if (mm_is_protected(vma->vm_mm) && pte_present(res))
-               uv_convert_owned_from_secure(pte_val(res) & PAGE_MASK);
+               uv_convert_from_secure_pte(res);
        return res;
 }
 
@@ -1224,7 +1224,7 @@ static inline pte_t ptep_get_and_clear_full(struct mm_struct *mm,
         * if this is not a mm teardown, the slower export is used as
         * fallback instead.
         */
-       uv_convert_owned_from_secure(pte_val(res) & PAGE_MASK);
+       uv_convert_from_secure_pte(res);
        return res;
 }
 
index a1bef30066efe944019e0d4bb3bfdffa8aab54b3..0679445cac0be8ea9f76e35588d720192b3c77f0 100644 (file)
@@ -485,7 +485,7 @@ int gmap_make_secure(struct gmap *gmap, unsigned long gaddr, void *uvcb);
 int gmap_destroy_page(struct gmap *gmap, unsigned long gaddr);
 int uv_destroy_folio(struct folio *folio);
 int uv_destroy_pte(pte_t pte);
-int uv_convert_owned_from_secure(unsigned long paddr);
+int uv_convert_from_secure_pte(pte_t pte);
 int gmap_convert_to_secure(struct gmap *gmap, unsigned long gaddr);
 
 void setup_uv(void);
@@ -508,7 +508,7 @@ static inline int uv_destroy_pte(pte_t pte)
        return 0;
 }
 
-static inline int uv_convert_owned_from_secure(unsigned long paddr)
+static inline int uv_convert_from_secure_pte(pte_t pte)
 {
        return 0;
 }
index 61c1ce51c883dbd49f74f7cb27fb25ea0b427da7..b456066d72da96b1658a12dcd5409b506c44e31d 100644 (file)
@@ -178,11 +178,10 @@ static int uv_convert_from_secure(unsigned long paddr)
 }
 
 /*
- * The caller must already hold a reference to the page
+ * The caller must already hold a reference to the folio.
  */
-int uv_convert_owned_from_secure(unsigned long paddr)
+static int uv_convert_from_secure_folio(struct folio *folio)
 {
-       struct folio *folio = phys_to_folio(paddr);
        int rc;
 
        /* See gmap_make_secure(): large folios cannot be secure */
@@ -190,13 +189,22 @@ int uv_convert_owned_from_secure(unsigned long paddr)
                return 0;
 
        folio_get(folio);
-       rc = uv_convert_from_secure(paddr);
+       rc = uv_convert_from_secure(folio_to_phys(folio));
        if (!rc)
                clear_bit(PG_arch_1, &folio->flags);
        folio_put(folio);
        return rc;
 }
 
+/*
+ * The present PTE still indirectly holds a folio reference through the mapping.
+ */
+int uv_convert_from_secure_pte(pte_t pte)
+{
+       VM_WARN_ON(!pte_present(pte));
+       return uv_convert_from_secure_folio(pfn_folio(pte_pfn(pte)));
+}
+
 /*
  * Calculate the expected ref_count for a folio that would otherwise have no
  * further pins. This was cribbed from similar functions in other places in
@@ -481,7 +489,7 @@ int gmap_destroy_page(struct gmap *gmap, unsigned long gaddr)
         * we instead try to export the page.
         */
        if (rc)
-               rc = uv_convert_owned_from_secure(page_to_phys(page));
+               rc = uv_convert_from_secure_folio(folio);
        folio_put(folio);
 out:
        mmap_read_unlock(gmap->mm);