VirtualBox

Changeset 72469 in vbox for trunk/src/VBox/VMM/VMMR3


Ignore:
Timestamp:
Jun 7, 2018 11:35:23 AM (7 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
122954
Message:

GIM,IEM: Correctly hook up hypercalls thru IEM. bugref:9044

  • IEM: Pass opcode and instruction length to GIM so it can do patching.
  • GIM: Introduced GIMHypercallEx API for receiving hypercalls with instruction opcode+length. Hooking this into the exiting #UD code paths.
  • GIM: Move the VMMPatchHypercall API into GIM and corrected the name to GIMQueryHypercallOpcodeBytes.
  • GIM/KVM: Use GIMQueryHypercallOpcodeBytes to decide which instruction is native and cache the opcode bytes for patching.
  • GIM/KVM: Check the VMCALL instruction encoding length rather than assuming its always 3 bytes when patching.
Location:
trunk/src/VBox/VMM/VMMR3
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMR3/GIMHv.cpp

    r72462 r72469  
    15211521     * Patch the hypercall-page.
    15221522     */
    1523     size_t cbWritten = 0;
    1524     int rc = VMMPatchHypercall(pVM, pvHypercallPage, PAGE_SIZE, &cbWritten);
     1523    size_t cbHypercall = 0;
     1524    int rc = GIMQueryHypercallOpcodeBytes(pVM, pvHypercallPage, PAGE_SIZE, &cbHypercall, NULL /*puDisOpcode*/);
    15251525    if (   RT_SUCCESS(rc)
    1526         && cbWritten < PAGE_SIZE)
    1527     {
    1528         uint8_t *pbLast = (uint8_t *)pvHypercallPage + cbWritten;
     1526        && cbHypercall < PAGE_SIZE)
     1527    {
     1528        uint8_t *pbLast = (uint8_t *)pvHypercallPage + cbHypercall;
    15291529        *pbLast = 0xc3;  /* RET */
    15301530
     
    15431543        if (rc == VINF_SUCCESS)
    15441544            rc = VERR_GIM_OPERATION_FAILED;
    1545         LogRel(("GIM: HyperV: VMMPatchHypercall failed. rc=%Rrc cbWritten=%u\n", rc, cbWritten));
     1545        LogRel(("GIM: HyperV: VMMPatchHypercall failed. rc=%Rrc cbHypercall=%u\n", rc, cbHypercall));
    15461546    }
    15471547
  • trunk/src/VBox/VMM/VMMR3/GIMKvm.cpp

    r72462 r72469  
    158158    /*
    159159     * Setup hypercall and #UD handling.
     160     * Note! We always need to trap VMCALL/VMMCALL hypercall using #UDs for raw-mode VMs.
    160161     */
    161162    for (VMCPUID i = 0; i < pVM->cCpus; i++)
    162163        EMSetHypercallInstructionsEnabled(&pVM->aCpus[i], true);
    163164
    164     if (ASMIsAmdCpu())
    165     {
    166         pKvm->fTrapXcptUD   = true;
    167         pKvm->uOpCodeNative = OP_VMMCALL;
    168     }
    169     else
    170     {
    171         Assert(ASMIsIntelCpu() || ASMIsViaCentaurCpu());
    172         pKvm->fTrapXcptUD   = false;
    173         pKvm->uOpCodeNative = OP_VMCALL;
    174     }
    175 
    176     /* We always need to trap VMCALL/VMMCALL hypercall using #UDs for raw-mode VMs. */
    177     if (VM_IS_RAW_MODE_ENABLED(pVM))
    178         pKvm->fTrapXcptUD = true;
     165    size_t cbHypercall = 0;
     166    rc = GIMQueryHypercallOpcodeBytes(pVM, pKvm->abOpcodeNative, sizeof(pKvm->abOpcodeNative), &cbHypercall, &pKvm->uOpcodeNative);
     167    AssertLogRelRCReturn(rc, rc);
     168    AssertLogRelReturn(cbHypercall == sizeof(pKvm->abOpcodeNative), VERR_GIM_IPE_1);
     169    pKvm->fTrapXcptUD = pKvm->uOpcodeNative != OP_VMCALL || VM_IS_RAW_MODE_ENABLED(pVM);
    179170
    180171    return VINF_SUCCESS;
Note: See TracChangeset for help on using the changeset viewer.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette