From: "Christoph Schlameuss" <schlameuss@linux.ibm.com>
To: "Claudio Imbrenda" <imbrenda@linux.ibm.com>, <kvm@vger.kernel.org>
Cc: <linux-s390@vger.kernel.org>, <frankja@linux.ibm.com>,
<borntraeger@de.ibm.com>, <david@redhat.com>,
<willy@infradead.org>, <hca@linux.ibm.com>, <svens@linux.ibm.com>,
<agordeev@linux.ibm.com>, <gor@linux.ibm.com>,
<nrb@linux.ibm.com>, <nsg@linux.ibm.com>
Subject: Re: [PATCH v1 03/13] KVM: s390: use __kvm_faultin_pfn()
Date: Tue, 14 Jan 2025 18:34:13 +0100 [thread overview]
Message-ID: <D71Z6BW4A19F.3OQIPSERFIUCH@linux.ibm.com> (raw)
In-Reply-To: <20250108181451.74383-4-imbrenda@linux.ibm.com>
On Wed Jan 8, 2025 at 7:14 PM CET, Claudio Imbrenda wrote:
> Refactor the existing page fault handling code to use __kvm_faultin_pfn().
>
> This possible now that memslots are always present.
>
> Signed-off-by: Claudio Imbrenda <imbrenda@linux.ibm.com>
> ---
> arch/s390/kvm/kvm-s390.c | 92 +++++++++++++++++++++++++++++++---------
> arch/s390/mm/gmap.c | 1 +
> 2 files changed, 73 insertions(+), 20 deletions(-)
With nits resolved:
Reviewed-by: Christoph Schlameuss <schlameuss@linux.ibm.com>
>
> diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c
> index 797b8503c162..8e4e7e45238b 100644
> --- a/arch/s390/kvm/kvm-s390.c
> +++ b/arch/s390/kvm/kvm-s390.c
> @@ -4794,11 +4794,66 @@ static void kvm_s390_assert_primary_as(struct kvm_vcpu *vcpu)
> current->thread.gmap_int_code, current->thread.gmap_teid.val);
> }
>
> +static int kvm_s390_handle_dat_fault(struct kvm_vcpu *vcpu, gfn_t gfn, gpa_t gaddr,
> + unsigned int flags)
> +{
> + struct kvm_memory_slot *slot;
> + unsigned int fault_flags;
> + bool writable, unlocked;
> + unsigned long vmaddr;
> + struct page *page;
> + kvm_pfn_t pfn;
> + int rc;
> +
> + slot = kvm_vcpu_gfn_to_memslot(vcpu, gfn);
> + if (!slot || slot->flags & KVM_MEMSLOT_INVALID)
> + return vcpu_post_run_addressing_exception(vcpu);
> +
> + fault_flags = flags & FOLL_WRITE ? FAULT_FLAG_WRITE : 0;
> + if (vcpu->arch.gmap->pfault_enabled)
> + flags |= FOLL_NOWAIT;
> + vmaddr = __gfn_to_hva_memslot(slot, gfn);
> +
> +try_again:
> + pfn = __kvm_faultin_pfn(slot, gfn, flags, &writable, &page);
> +
> + /* Access outside memory, inject addressing exception */
> + if (is_noslot_pfn(pfn))
> + return vcpu_post_run_addressing_exception(vcpu);
> + /* Signal pending: try again */
> + if (pfn == KVM_PFN_ERR_SIGPENDING)
> + return -EAGAIN;
> +
> + /* Needs I/O, try to setup async pfault (only possible with FOLL_NOWAIT) */
> + if (pfn == KVM_PFN_ERR_NEEDS_IO) {
> + trace_kvm_s390_major_guest_pfault(vcpu);
> + if (kvm_arch_setup_async_pf(vcpu))
> + return 0;
> + vcpu->stat.pfault_sync++;
> + /* Could not setup async pfault, try again synchronously */
> + flags &= ~FOLL_NOWAIT;
> + goto try_again;
> + }
> + /* Any other error */
> + if (is_error_pfn(pfn))
> + return -EFAULT;
> +
> + /* Success */
> + mmap_read_lock(vcpu->arch.gmap->mm);
> + /* Mark the userspace PTEs as young and/or dirty, to avoid page fault loops */
> + rc = fixup_user_fault(vcpu->arch.gmap->mm, vmaddr, fault_flags, &unlocked);
> + if (!rc)
> + rc = __gmap_link(vcpu->arch.gmap, gaddr, vmaddr);
> + kvm_release_faultin_page(vcpu->kvm, page, false, writable);
> + mmap_read_unlock(vcpu->arch.gmap->mm);
> + return rc;
> +}
> +
> static int vcpu_post_run_handle_fault(struct kvm_vcpu *vcpu)
> {
> + unsigned long gaddr, gaddr_tmp;
> unsigned int flags = 0;
> - unsigned long gaddr;
> - int rc = 0;
> + gfn_t gfn;
>
> gaddr = current->thread.gmap_teid.addr * PAGE_SIZE;
> if (kvm_s390_cur_gmap_fault_is_write())
> @@ -4850,29 +4905,26 @@ static int vcpu_post_run_handle_fault(struct kvm_vcpu *vcpu)
> case PGM_REGION_SECOND_TRANS:
> case PGM_REGION_THIRD_TRANS:
> kvm_s390_assert_primary_as(vcpu);
> - if (vcpu->arch.gmap->pfault_enabled) {
> - rc = gmap_fault(vcpu->arch.gmap, gaddr, flags | FAULT_FLAG_RETRY_NOWAIT);
> - if (rc == -EFAULT)
> - return vcpu_post_run_addressing_exception(vcpu);
> - if (rc == -EAGAIN) {
> - trace_kvm_s390_major_guest_pfault(vcpu);
> - if (kvm_arch_setup_async_pf(vcpu))
> - return 0;
> - vcpu->stat.pfault_sync++;
> - } else {
> - return rc;
> - }
> - }
> - rc = gmap_fault(vcpu->arch.gmap, gaddr, flags);
> - if (rc == -EFAULT) {
> - if (kvm_is_ucontrol(vcpu->kvm)) {
> +
> + gfn = gpa_to_gfn(gaddr);
> + if (kvm_is_ucontrol(vcpu->kvm)) {
> + /*
> + * This translates the per-vCPU guest address into a
> + * fake guest address, which can then be used with the
> + * fake memslots that are identity mapping userspace.
> + * This allows ucontrol VMs to use the normal fault
> + * resolution path, like normal VMs.
> + */
> + gaddr_tmp = gmap_translate(vcpu->arch.gmap, gaddr);
> + if (gaddr_tmp == -EFAULT) {
> vcpu->run->exit_reason = KVM_EXIT_S390_UCONTROL;
> vcpu->run->s390_ucontrol.trans_exc_code = gaddr;
> vcpu->run->s390_ucontrol.pgm_code = 0x10;
nit: s/0x10/PGM_SEGMENT_TRANSLATION/
> return -EREMOTE;
> }
> - return vcpu_post_run_addressing_exception(vcpu);
> + gfn = gpa_to_gfn(gaddr_tmp);
> }
> + return kvm_s390_handle_dat_fault(vcpu, gfn, gaddr, flags);
> break;
nit: Remove the break after the return here?
> default:
> KVM_BUG(1, vcpu->kvm, "Unexpected program interrupt 0x%x, TEID 0x%016lx",
> @@ -4880,7 +4932,7 @@ static int vcpu_post_run_handle_fault(struct kvm_vcpu *vcpu)
> send_sig(SIGSEGV, current, 0);
> break;
> }
> - return rc;
> + return 0;
> }
>
> static int vcpu_post_run(struct kvm_vcpu *vcpu, int exit_reason)
> diff --git a/arch/s390/mm/gmap.c b/arch/s390/mm/gmap.c
> index 16b8a36c56de..3aacef77c174 100644
> --- a/arch/s390/mm/gmap.c
> +++ b/arch/s390/mm/gmap.c
> @@ -605,6 +605,7 @@ int __gmap_link(struct gmap *gmap, unsigned long gaddr, unsigned long vmaddr)
> radix_tree_preload_end();
> return rc;
> }
> +EXPORT_SYMBOL(__gmap_link);
>
> /**
> * fixup_user_fault_nowait - manually resolve a user page fault without waiting
next prev parent reply other threads:[~2025-01-14 17:34 UTC|newest]
Thread overview: 39+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-01-08 18:14 [PATCH v1 00/13] KVM: s390: Stop using page->index and other things Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 01/13] KVM: s390: wrapper for KVM_BUG Claudio Imbrenda
2025-01-10 9:09 ` Christian Borntraeger
2025-01-10 13:13 ` Christoph Schlameuss
2025-01-08 18:14 ` [PATCH v1 02/13] KVM: s390: fake memslots for ucontrol VMs Claudio Imbrenda
2025-01-10 9:31 ` Christian Borntraeger
2025-01-10 11:47 ` Claudio Imbrenda
2025-01-10 16:22 ` Sean Christopherson
2025-01-10 17:02 ` Claudio Imbrenda
2025-01-10 17:34 ` Sean Christopherson
2025-01-10 17:43 ` Claudio Imbrenda
2025-01-10 15:40 ` Christoph Schlameuss
2025-01-10 16:18 ` Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 03/13] KVM: s390: use __kvm_faultin_pfn() Claudio Imbrenda
2025-01-14 17:34 ` Christoph Schlameuss [this message]
2025-01-14 17:56 ` Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 04/13] KVM: s390: move pv gmap functions into kvm Claudio Imbrenda
2025-01-09 17:42 ` kernel test robot
2025-01-15 12:48 ` Janosch Frank
2025-01-15 12:59 ` Claudio Imbrenda
2025-01-15 13:23 ` Janosch Frank
2025-01-08 18:14 ` [PATCH v1 05/13] KVM: s390: get rid of gmap_fault() Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 06/13] KVM: s390: get rid of gmap_translate() Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 07/13] KVM: s390: move some gmap shadowing functions away from mm/gmap.c Claudio Imbrenda
2025-01-15 8:56 ` Janosch Frank
2025-01-15 10:20 ` Claudio Imbrenda
2025-01-15 11:48 ` Janosch Frank
2025-01-08 18:14 ` [PATCH v1 08/13] KVM: s390: stop using page->index for non-shadow gmaps Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 09/13] KVM: s390: stop using lists to keep track of used dat tables Claudio Imbrenda
2025-01-15 9:01 ` Janosch Frank
2025-01-08 18:14 ` [PATCH v1 10/13] KVM: s390: move gmap_shadow_pgt_lookup() into kvm Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 11/13] KVM: s390: remove useless page->index usage Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 12/13] KVM: s390: move PGSTE softbits Claudio Imbrenda
2025-01-08 18:14 ` [PATCH v1 13/13] KVM: s390: remove the last user of page->index Claudio Imbrenda
2025-01-15 12:17 ` Janosch Frank
2025-01-15 12:23 ` Claudio Imbrenda
2025-01-20 9:43 ` David Hildenbrand
2025-01-20 10:28 ` Claudio Imbrenda
2025-01-20 10:34 ` 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=D71Z6BW4A19F.3OQIPSERFIUCH@linux.ibm.com \
--to=schlameuss@linux.ibm.com \
--cc=agordeev@linux.ibm.com \
--cc=borntraeger@de.ibm.com \
--cc=david@redhat.com \
--cc=frankja@linux.ibm.com \
--cc=gor@linux.ibm.com \
--cc=hca@linux.ibm.com \
--cc=imbrenda@linux.ibm.com \
--cc=kvm@vger.kernel.org \
--cc=linux-s390@vger.kernel.org \
--cc=nrb@linux.ibm.com \
--cc=nsg@linux.ibm.com \
--cc=svens@linux.ibm.com \
--cc=willy@infradead.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.