diff mbox series

x86/HVM: update repeat count upon nested lin->phys failure

Message ID 793580d3-3fd8-4715-8a34-bf9965dd5938@suse.com (mailing list archive)
State New
Headers show
Series x86/HVM: update repeat count upon nested lin->phys failure | expand

Commit Message

Jan Beulich April 16, 2025, 1:44 p.m. UTC
For the X86EMUL_EXCEPTION case the repeat count must be correctly
propagated back. Since for the recursive invocation we use a local
helper variable, its value needs copying to the caller's one.

While there also correct the off-by-1 range in the comment ahead of the
function (strictly speaking for the "DF set" case we'd need to put
another, different range there as well).

Fixes: 53f87c03b4ea ("x86emul: generalize exception handling for rep_* hooks")
Reported-by: Manuel Andreas <manuel.andreas@tum.de>
Signed-off-by: Jan Beulich <jbeulich@suse.com>

Comments

Andrew Cooper April 16, 2025, 3:48 p.m. UTC | #1
On 16/04/2025 2:44 pm, Jan Beulich wrote:
> For the X86EMUL_EXCEPTION case the repeat count must be correctly
> propagated back. Since for the recursive invocation we use a local
> helper variable, its value needs copying to the caller's one.
>
> While there also correct the off-by-1 range in the comment ahead of the
> function (strictly speaking for the "DF set" case we'd need to put
> another, different range there as well).
>
> Fixes: 53f87c03b4ea ("x86emul: generalize exception handling for rep_* hooks")
> Reported-by: Manuel Andreas <manuel.andreas@tum.de>
> Signed-off-by: Jan Beulich <jbeulich@suse.com>

Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>

I really do hate everything about how *reps is handled in the emulator,
but this will have to do in the short term.
diff mbox series

Patch

--- a/xen/arch/x86/hvm/emulate.c
+++ b/xen/arch/x86/hvm/emulate.c
@@ -825,7 +825,7 @@  static void hvmemul_unmap_linear_addr(
 
 /*
  * Convert addr from linear to physical form, valid over the range
- * [addr, addr + *reps * bytes_per_rep]. *reps is adjusted according to
+ * [addr, addr + *reps * bytes_per_rep). *reps is adjusted according to
  * the valid computed range. It is always >0 when X86EMUL_OKAY is returned.
  * @pfec indicates the access checks to be performed during page-table walks.
  */
@@ -865,7 +865,10 @@  static int hvmemul_linear_to_phys(
         int rc = hvmemul_linear_to_phys(
             addr, &_paddr, bytes_per_rep, &one_rep, pfec, hvmemul_ctxt);
         if ( rc != X86EMUL_OKAY )
+        {
+            *reps = one_rep;
             return rc;
+        }
         pfn = _paddr >> PAGE_SHIFT;
     }
     else if ( (pfn = paging_gva_to_gfn(curr, addr, &pfec)) == gfn_x(INVALID_GFN) )