VirtualBox

Changeset 56791 in vbox


Ignore:
Timestamp:
Jul 3, 2015 4:19:59 PM (10 years ago)
Author:
vboxsync
svn:sync-xref-src-repo-rev:
101441
Message:

VMM/GIM: Try passing identical TSC and NanoTS pairs to all VCPUs for KVM guests.

Location:
trunk/src/VBox/VMM
Files:
1 added
4 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/VMM/VMMAll/GIMAllKvm.cpp

    r55714 r56791  
    3535
    3636#include <iprt/asm-amd64-x86.h>
     37#include <iprt/time.h>
    3738
    3839
     
    226227            bool fEnable = RT_BOOL(uRawValue & MSR_GIM_KVM_SYSTEM_TIME_ENABLE_BIT);
    227228#ifndef IN_RING3
     229# ifdef IN_RING0
     230            gimR0KvmUpdateSystemTime(pVM, pVCpu);
     231# else
     232            Assert(pVM->cCpus == 1);
    228233            if (fEnable)
    229234            {
    230                 RTCCUINTREG fEFlags  = ASMIntDisableFlags();
    231                 pKvmCpu->uTsc        = TMCpuTickGetNoCheck(pVCpu);
    232                 pKvmCpu->uVirtNanoTS = TMVirtualGetNoCheck(pVM);
     235                RTCCUINTREG fEFlags = ASMIntDisableFlags();
     236                pKvmCpu->uTsc        = TMCpuTickGetNoCheck(pVCpu) | UINT64_C(1);
     237                pKvmCpu->uVirtNanoTS = TMVirtualGetNoCheck(pVM)   | UINT64_C(1);
    233238                ASMSetFlags(fEFlags);
    234239            }
     240# endif
    235241            return VINF_CPUM_R3_MSR_WRITE;
    236242#else
     
    251257                int rc2 = PGMPhysSimpleReadGCPhys(pVM, &SystemTime, pKvmCpu->GCPhysSystemTime, sizeof(GIMKVMSYSTEMTIME));
    252258                if (RT_SUCCESS(rc2))
    253                     fFlags = (SystemTime.fFlags & GIM_KVM_SYSTEM_TIME_FLAGS_GUEST_PAUSED);
     259                    pKvmCpu->fSystemTimeFlags = (SystemTime.fFlags & GIM_KVM_SYSTEM_TIME_FLAGS_GUEST_PAUSED);
    254260            }
    255261
     
    258264            pKvmCpu->GCPhysSystemTime      = MSR_GIM_KVM_SYSTEM_TIME_GUEST_GPA(uRawValue);
    259265            pKvmCpu->u32SystemTimeVersion += 2;
    260             int rc = gimR3KvmEnableSystemTime(pVM, pVCpu, pKvmCpu, fFlags);
     266            int rc = gimR3KvmEnableSystemTime(pVM, pVCpu);
    261267            if (RT_FAILURE(rc))
    262268            {
     
    282288                if (RT_SUCCESS(rc))
    283289                {
    284                     pKvm->u64WallClockMsr     = uRawValue;
     290                    pKvm->u64WallClockMsr = uRawValue;
    285291                    return VINF_SUCCESS;
    286292                }
  • trunk/src/VBox/VMM/VMMR0/GIMR0.cpp

    r54819 r56791  
    4343            return gimR0HvInitVM(pVM);
    4444
     45        case GIMPROVIDERID_KVM:
     46            return gimR0KvmInitVM(pVM);
     47
    4548        default:
    4649            break;
     
    6568        case GIMPROVIDERID_HYPERV:
    6669            return gimR0HvTermVM(pVM);
     70
     71        case GIMPROVIDERID_KVM:
     72            return gimR0KvmTermVM(pVM);
    6773
    6874        default:
  • trunk/src/VBox/VMM/VMMR3/GIMKvm.cpp

    r56693 r56791  
    358358        SSMR3GetGCPhys(pSSM, &pKvmCpu->GCPhysSystemTime);
    359359        SSMR3GetU32(pSSM, &pKvmCpu->u32SystemTimeVersion);
    360         rc = SSMR3GetU8(pSSM, &fSystemTimeFlags);
     360        rc = SSMR3GetU8(pSSM, &pKvmCpu->fSystemTimeFlags);
    361361        AssertRCReturn(rc, rc);
    362362
    363363        /* Enable the system-time struct. if necessary. */
     364        /** @todo update guest struct only if cTscTicksPerSecond doesn't match host
     365         *        anymore. */
    364366        if (MSR_GIM_KVM_SYSTEM_TIME_IS_ENABLED(pKvmCpu->u64SystemTimeMsr))
    365367        {
    366368            Assert(!TMVirtualIsTicking(pVM));       /* paranoia. */
    367369            Assert(!TMCpuTickIsTicking(pVCpu));
    368             rc = gimR3KvmEnableSystemTime(pVM, pVCpu, pKvmCpu, fSystemTimeFlags);
     370            rc = gimR3KvmEnableSystemTime(pVM, pVCpu);
    369371            AssertRCReturn(rc, rc);
    370372        }
     
    388390 * @param   pVM                Pointer to the VM.
    389391 * @param   pVCpu              Pointer to the VMCPU.
    390  * @param   pKvmCpu            Pointer to the GIMKVMCPU with all fields
    391  *                             populated by the caller.
    392  * @param   fFlags             The system-time struct. flags.
    393392 *
    394393 * @remarks Don't do any release assertions here, these can be triggered by
    395394 *          guest R0 code.
    396395 */
    397 VMMR3_INT_DECL(int) gimR3KvmEnableSystemTime(PVM pVM, PVMCPU pVCpu, PGIMKVMCPU pKvmCpu, uint8_t fFlags)
    398 {
     396VMMR3_INT_DECL(int) gimR3KvmEnableSystemTime(PVM pVM, PVMCPU pVCpu)
     397{
     398    PGIMKVM    pKvm    = &pVM->gim.s.u.Kvm;
     399    PGIMKVMCPU pKvmCpu = &pVCpu->gim.s.u.KvmCpu;
     400
    399401    /*
    400402     * Validate the mapping address first.
     
    407409    }
    408410
     411    /*
     412     * Construct the system-time struct.
     413     */
    409414    GIMKVMSYSTEMTIME SystemTime;
    410415    RT_ZERO(SystemTime);
     
    412417    SystemTime.u64NanoTS   = pKvmCpu->uVirtNanoTS;
    413418    SystemTime.u64Tsc      = pKvmCpu->uTsc;
    414     SystemTime.fFlags      = fFlags | GIM_KVM_SYSTEM_TIME_FLAGS_TSC_STABLE;
     419    SystemTime.fFlags      = pKvmCpu->fSystemTimeFlags | GIM_KVM_SYSTEM_TIME_FLAGS_TSC_STABLE;
    415420
    416421    /*
     
    424429     * time = ((tsc * SysTime.u32TscScale) >> 32) + SysTime.u64NanoTS
    425430     */
    426     PGIMKVM pKvm = &pVM->gim.s.u.Kvm;
    427431    uint64_t u64TscFreq   = pKvm->cTscTicksPerSecond;
    428432    SystemTime.i8TscShift = 0;
     
    440444    SystemTime.u32TscScale = ASMDivU64ByU32RetU32(RT_NS_1SEC_64 << 32, uTscFreqLo);
    441445
     446    /*
     447     * Update guest memory with the system-time struct.
     448     */
    442449    Assert(!(SystemTime.u32Version & UINT32_C(1)));
    443450    int rc = PGMPhysSimpleWriteGCPhys(pVM, pKvmCpu->GCPhysSystemTime, &SystemTime, sizeof(GIMKVMSYSTEMTIME));
  • trunk/src/VBox/VMM/include/GIMKvmInternal.h

    r56677 r56791  
    203203    /** The TSC frequency (in HZ) reported to the guest. */
    204204    uint64_t                    cTscTicksPerSecond;
     205    /** Ring-0 mutex. */
     206    RTSEMFASTMUTEX              hFastMtx;
    205207} GIMKVM;
    206208/** Pointer to per-VM GIM KVM instance data. */
     
    225227    /** The guest virtual time while enabling the system-time MSR. */
    226228    uint64_t                    uVirtNanoTS;
     229    /** The flags of the system-time struct. */
     230    uint8_t                     fSystemTimeFlags;
    227231} GIMKVMCPU;
    228232/** Pointer to per-VCPU GIM KVM instance data. */
     
    235239
    236240#ifdef IN_RING0
    237 #if 0
    238241VMMR0_INT_DECL(int)             gimR0KvmInitVM(PVM pVM);
    239242VMMR0_INT_DECL(int)             gimR0KvmTermVM(PVM pVM);
    240 VMMR0_INT_DECL(int)             gimR0KvmUpdateParavirtTsc(PVM pVM, uint64_t u64Offset);
    241 #endif
     243VMMR0_INT_DECL(int)             gimR0KvmUpdateSystemTime(PVM pVM, PVMCPU pVCpu);
    242244#endif /* IN_RING0 */
    243245
     
    252254
    253255VMMR3_INT_DECL(int)             gimR3KvmDisableSystemTime(PVM pVM);
    254 VMMR3_INT_DECL(int)             gimR3KvmEnableSystemTime(PVM pVM, PVMCPU pVCpu, PGIMKVMCPU pKvmCpu, uint8_t fFlags);
     256VMMR3_INT_DECL(int)             gimR3KvmEnableSystemTime(PVM pVM, PVMCPU pVCpu);
    255257VMMR3_INT_DECL(int)             gimR3KvmEnableWallClock(PVM pVM, RTGCPHYS GCPhysSysTime);
    256258#endif /* IN_RING3 */
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