From: Janosch Frank <frankja@linux.vnet.ibm.com>
To: kvm@vger.kernel.org
Cc: schwidefsky@de.ibm.com, borntraeger@de.ibm.com, david@redhat.com,
dominik.dingel@gmail.com, linux-s390@vger.kernel.org
Subject: [RFC/PATCH v3 07/16] s390/mm: Make gmap_read_table EDAT1 compatible
Date: Fri, 9 Feb 2018 10:34:15 +0100 [thread overview]
Message-ID: <1518168864-147803-8-git-send-email-frankja@linux.vnet.ibm.com> (raw)
In-Reply-To: <1518168864-147803-1-git-send-email-frankja@linux.vnet.ibm.com>
For the VSIE we shadow the GMAP/DAT tables that a guest N builds for
its N + 1 guest. This means we read the GMAP from the memory of guest
N and use the retrieved information to build a shadow version from it
which is actually used to run the guest.
gmap_read_table is used to retrieve the data from the guest's address
space. Unfortunately it currently has no support for reading from huge
guests, so let's add that.
gmap_read_table has to tell us to which guest DAT level it traveled to
get the information we requested. With this information we can start
shadowing without searching for the pmd or pte a second time.
Signed-off-by: Janosch Frank <frankja@linux.vnet.ibm.com>
---
arch/s390/include/asm/gmap.h | 2 +-
arch/s390/kvm/gaccess.c | 17 ++++++++++-------
arch/s390/mm/gmap.c | 34 ++++++++++++++++++++++++----------
3 files changed, 35 insertions(+), 18 deletions(-)
diff --git a/arch/s390/include/asm/gmap.h b/arch/s390/include/asm/gmap.h
index 26a31c3..e7592e1 100644
--- a/arch/s390/include/asm/gmap.h
+++ b/arch/s390/include/asm/gmap.h
@@ -128,7 +128,7 @@ void gmap_discard(struct gmap *, unsigned long from, unsigned long to);
void __gmap_zap(struct gmap *, unsigned long gaddr);
void gmap_unlink(struct mm_struct *, unsigned long *table, unsigned long vmaddr);
-int gmap_read_table(struct gmap *gmap, unsigned long gaddr, unsigned long *val);
+int gmap_read_table(struct gmap *gmap, unsigned long gaddr, unsigned long *val, int *fc);
struct gmap *gmap_shadow(struct gmap *parent, unsigned long asce,
int edat_level);
diff --git a/arch/s390/kvm/gaccess.c b/arch/s390/kvm/gaccess.c
index c24bfa7..f9c5cc0 100644
--- a/arch/s390/kvm/gaccess.c
+++ b/arch/s390/kvm/gaccess.c
@@ -987,7 +987,7 @@ static int kvm_s390_shadow_tables(struct gmap *sg, unsigned long saddr,
union asce asce;
union vaddress vaddr;
unsigned long ptr;
- int rc;
+ int rc, fc = 0;
*fake = 0;
*dat_protection = 0;
@@ -1034,7 +1034,8 @@ static int kvm_s390_shadow_tables(struct gmap *sg, unsigned long saddr,
rfte.val = ptr;
goto shadow_r2t;
}
- rc = gmap_read_table(parent, ptr + vaddr.rfx * 8, &rfte.val);
+ rc = gmap_read_table(parent, ptr + vaddr.rfx * 8, &rfte.val,
+ &fc);
if (rc)
return rc;
if (rfte.i)
@@ -1060,7 +1061,8 @@ static int kvm_s390_shadow_tables(struct gmap *sg, unsigned long saddr,
rste.val = ptr;
goto shadow_r3t;
}
- rc = gmap_read_table(parent, ptr + vaddr.rsx * 8, &rste.val);
+ rc = gmap_read_table(parent, ptr + vaddr.rsx * 8, &rste.val,
+ &fc);
if (rc)
return rc;
if (rste.i)
@@ -1087,7 +1089,8 @@ static int kvm_s390_shadow_tables(struct gmap *sg, unsigned long saddr,
rtte.val = ptr;
goto shadow_sgt;
}
- rc = gmap_read_table(parent, ptr + vaddr.rtx * 8, &rtte.val);
+ rc = gmap_read_table(parent, ptr + vaddr.rtx * 8, &rtte.val,
+ &fc);
if (rc)
return rc;
if (rtte.i)
@@ -1123,7 +1126,7 @@ static int kvm_s390_shadow_tables(struct gmap *sg, unsigned long saddr,
ste.val = ptr;
goto shadow_pgt;
}
- rc = gmap_read_table(parent, ptr + vaddr.sx * 8, &ste.val);
+ rc = gmap_read_table(parent, ptr + vaddr.sx * 8, &ste.val, &fc);
if (rc)
return rc;
if (ste.i)
@@ -1170,7 +1173,7 @@ int kvm_s390_shadow_fault(struct kvm_vcpu *vcpu, struct gmap *sg,
union vaddress vaddr;
union page_table_entry pte;
unsigned long pgt;
- int dat_protection, fake;
+ int dat_protection, fake, fc;
int rc;
down_read(&sg->mm->mmap_sem);
@@ -1192,7 +1195,7 @@ int kvm_s390_shadow_fault(struct kvm_vcpu *vcpu, struct gmap *sg,
goto shadow_page;
}
if (!rc)
- rc = gmap_read_table(sg->parent, pgt + vaddr.px * 8, &pte.val);
+ rc = gmap_read_table(sg->parent, pgt + vaddr.px * 8, &pte.val, &fc);
if (!rc && pte.i)
rc = PGM_PAGE_TRANSLATION;
if (!rc && pte.z)
diff --git a/arch/s390/mm/gmap.c b/arch/s390/mm/gmap.c
index 4dafa1e..5699770 100644
--- a/arch/s390/mm/gmap.c
+++ b/arch/s390/mm/gmap.c
@@ -1254,27 +1254,41 @@ EXPORT_SYMBOL_GPL(gmap_mprotect_notify);
*
* Called with gmap->mm->mmap_sem in read.
*/
-int gmap_read_table(struct gmap *gmap, unsigned long gaddr, unsigned long *val)
+int gmap_read_table(struct gmap *gmap, unsigned long gaddr, unsigned long *val,
+ int *fc)
{
unsigned long address, vmaddr;
spinlock_t *ptl;
+ pmd_t *pmdp;
pte_t *ptep, pte;
int rc;
while (1) {
rc = -EAGAIN;
- ptep = gmap_pte_op_walk(gmap, gaddr, &ptl);
- if (ptep) {
- pte = *ptep;
- if (pte_present(pte) && (pte_val(pte) & _PAGE_READ)) {
- address = pte_val(pte) & PAGE_MASK;
- address += gaddr & ~PAGE_MASK;
+ pmdp = gmap_pmd_op_walk(gmap, gaddr);
+ if (pmdp && !(pmd_val(*pmdp) & _SEGMENT_ENTRY_INVALID)) {
+ if (!pmd_large(*pmdp)) {
+ ptep = pte_alloc_map_lock(gmap->mm, pmdp, gaddr, &ptl);
+ if (ptep) {
+ pte = *ptep;
+ if (pte_present(pte) && (pte_val(pte) & _PAGE_READ)) {
+ address = pte_val(pte) & PAGE_MASK;
+ address += gaddr & ~PAGE_MASK;
+ *val = *(unsigned long *) address;
+ pte_val(*ptep) |= _PAGE_YOUNG;
+ /* Do *NOT* clear the _PAGE_INVALID bit! */
+ rc = 0;
+ }
+ gmap_pte_op_end(ptl);
+ }
+ } else {
+ address = pmd_val(*pmdp) & HPAGE_MASK;
+ address += gaddr & ~HPAGE_MASK;
*val = *(unsigned long *) address;
- pte_val(*ptep) |= _PAGE_YOUNG;
- /* Do *NOT* clear the _PAGE_INVALID bit! */
+ *fc = 1;
rc = 0;
}
- gmap_pte_op_end(ptl);
+ gmap_pmd_op_end(gmap, pmdp);
}
if (!rc)
break;
--
2.7.4
next prev parent reply other threads:[~2018-02-09 9:34 UTC|newest]
Thread overview: 49+ messages / expand[flat|nested] mbox.gz Atom feed top
2018-02-09 9:34 [RFC/PATCH v3 00/16] KVM/s390: Hugetlbfs enablement Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 01/16] s390/mm: make gmap_protect_range more modular Janosch Frank
2018-02-13 14:07 ` David Hildenbrand
2018-02-09 9:34 ` [RFC/PATCH v3 02/16] s390/mm: Abstract gmap notify bit setting Janosch Frank
2018-02-13 14:10 ` David Hildenbrand
2018-02-13 14:31 ` Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 03/16] s390/mm: Introduce gmap_pmdp_xchg Janosch Frank
2018-02-13 14:16 ` David Hildenbrand
2018-02-13 14:39 ` Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 04/16] s390/mm: add gmap PMD invalidation notification Janosch Frank
2018-02-13 14:36 ` David Hildenbrand
2018-02-13 14:54 ` Janosch Frank
2018-02-13 14:59 ` David Hildenbrand
2018-02-13 15:33 ` Janosch Frank
2018-02-14 10:42 ` David Hildenbrand
2018-02-14 11:19 ` Janosch Frank
2018-02-14 14:18 ` David Hildenbrand
2018-02-14 14:55 ` Janosch Frank
2018-02-14 15:15 ` David Hildenbrand
2018-02-14 15:24 ` Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 05/16] s390/mm: Add gmap pmd invalidation and clearing Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 06/16] s390/mm: Add huge page dirty sync support Janosch Frank
2018-02-09 9:34 ` Janosch Frank [this message]
2018-02-09 9:34 ` [RFC/PATCH v3 08/16] s390/mm: Make protect_rmap EDAT1 compatible Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 09/16] s390/mm: Add shadow segment code Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 10/16] s390/mm: Add VSIE reverse fake case Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 11/16] s390/mm: Enable gmap huge pmd support Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 12/16] s390/mm: clear huge page storage keys on enable_skey Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 13/16] s390/mm: Add huge pmd storage key handling Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 14/16] s390/mm: hugetlb pages within a gmap can not be freed Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 15/16] KVM: s390: Add KVM HPAGE capability Janosch Frank
2018-02-09 9:34 ` [RFC/PATCH v3 16/16] s390/mm: Add gmap lock classes Janosch Frank
2018-02-14 14:30 ` [RFC/PATCH v3 00/16] KVM/s390: Hugetlbfs enablement David Hildenbrand
2018-02-14 15:01 ` Janosch Frank
2018-02-14 15:07 ` David Hildenbrand
2018-02-14 15:33 ` Janosch Frank
2018-02-14 15:48 ` Christian Borntraeger
2018-02-14 15:57 ` David Hildenbrand
2018-02-14 15:56 ` David Hildenbrand
2018-02-15 15:43 ` [PATCH 0/3] Hpage capability rework Janosch Frank
2018-02-15 15:43 ` [PATCH 1/3] KVM: s390: Refactor host cmma and pfmfi interpretation controls Janosch Frank
2018-02-15 16:08 ` David Hildenbrand
2018-02-15 16:42 ` Janosch Frank
2018-02-16 9:46 ` David Hildenbrand
2018-02-15 15:43 ` [PATCH 2/3] KVM: s390: Add storage key facility interpretation control Janosch Frank
2018-02-15 16:09 ` David Hildenbrand
2018-02-15 20:27 ` Farhan Ali
2018-02-15 15:43 ` [PATCH 3/3] s390/mm: Enable gmap huge pmd support Janosch Frank
2018-02-15 16:10 ` David Hildenbrand
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=1518168864-147803-8-git-send-email-frankja@linux.vnet.ibm.com \
--to=frankja@linux.vnet.ibm.com \
--cc=borntraeger@de.ibm.com \
--cc=david@redhat.com \
--cc=dominik.dingel@gmail.com \
--cc=kvm@vger.kernel.org \
--cc=linux-s390@vger.kernel.org \
--cc=schwidefsky@de.ibm.com \
/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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).