hva_to_pfn_fast() currently just fails for faults where establishing writable mappings is forbidden, which is unnecessary. Instead, try getting the page without passing FOLL_WRITE. This allows the aforementioned faults to (potentially) be resolved without falling back to slow GUP. Suggested-by: James Houghton <jthoughton@xxxxxxxxxx> Signed-off-by: Anish Moorthy <amoorthy@xxxxxxxxxx> --- virt/kvm/kvm_main.c | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c index 88946d5d102b..725191333c4e 100644 --- a/virt/kvm/kvm_main.c +++ b/virt/kvm/kvm_main.c @@ -2811,7 +2811,7 @@ static inline int check_user_page_hwpoison(unsigned long addr) } /* - * The fast path to get the writable pfn which will be stored in @pfn, + * The fast path to get the pfn which will be stored in @pfn, * true indicates success, otherwise false is returned. It's also the * only part that runs if we can in atomic context. */ @@ -2825,10 +2825,9 @@ static bool hva_to_pfn_fast(unsigned long addr, bool write_fault, * or the caller allows to map a writable pfn for a read fault * request. */ - if (!(write_fault || writable)) - return false; + unsigned int gup_flags = (write_fault || writable) ? FOLL_WRITE : 0; - if (get_user_page_fast_only(addr, FOLL_WRITE, page)) { + if (get_user_page_fast_only(addr, gup_flags, page)) { *pfn = page_to_pfn(page[0]); if (writable) -- 2.42.0.869.gea05f2083d-goog