VirtualBox

Changeset 93787 in vbox for trunk/src/VBox


Ignore:
Timestamp:
Feb 16, 2022 11:07:57 AM (3 years ago)
Author:
vboxsync
Message:

VMM/{NEM*,DBGF}: Make NEM respond to debug event changes and implement the logic for the darwin backend, bugref:9044

Location:
trunk/src/VBox/VMM
Files:
6 edited

Legend:

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

    r93115 r93787  
    7676#include <VBox/vmm/hm.h>
    7777#include <VBox/vmm/mm.h>
     78#include <VBox/vmm/nem.h>
    7879#include "DBGFInternal.h"
    7980#include <VBox/vmm/vm.h>
     
    19121913         * Inform HM about changes.
    19131914         */
    1914         if (cChanges > 0 && HMIsEnabled(pVM))
    1915         {
    1916             HMR3NotifyDebugEventChanged(pVM);
    1917             HMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     1915        if (cChanges > 0)
     1916        {
     1917            if (HMIsEnabled(pVM))
     1918            {
     1919                HMR3NotifyDebugEventChanged(pVM);
     1920                HMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     1921            }
     1922            else if (VM_IS_NEM_ENABLED(pVM))
     1923            {
     1924                NEMR3NotifyDebugEventChanged(pVM);
     1925                NEMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     1926            }
    19181927        }
    19191928    }
    19201929    else if (HMIsEnabled(pVM))
    19211930        HMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     1931    else if (VM_IS_NEM_ENABLED(pVM))
     1932        NEMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
    19221933
    19231934    return VINF_SUCCESS;
     
    21362147         * Inform HM about changes.
    21372148         */
    2138         if (fChanged && HMIsEnabled(pVM))
    2139         {
    2140             HMR3NotifyDebugEventChanged(pVM);
    2141             HMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     2149        if (fChanged)
     2150        {
     2151            if (HMIsEnabled(pVM))
     2152            {
     2153                HMR3NotifyDebugEventChanged(pVM);
     2154                HMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     2155            }
     2156            else if (VM_IS_NEM_ENABLED(pVM))
     2157            {
     2158                NEMR3NotifyDebugEventChanged(pVM);
     2159                NEMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     2160            }
    21422161        }
    21432162    }
    21442163    else if (HMIsEnabled(pVM))
    21452164        HMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
     2165    else if (VM_IS_NEM_ENABLED(pVM))
     2166        NEMR3NotifyDebugEventChangedPerCpu(pVM, pVCpu);
    21462167
    21472168    return VINF_SUCCESS;
  • trunk/src/VBox/VMM/VMMR3/NEMR3.cpp

    r93722 r93787  
    3131*********************************************************************************************************************************/
    3232#define LOG_GROUP LOG_GROUP_NEM
     33#include <VBox/vmm/dbgf.h>
    3334#include <VBox/vmm/nem.h>
    3435#include <VBox/vmm/gim.h>
     
    458459#endif
    459460
     461
     462/**
     463 * Notification callback from DBGF when interrupt breakpoints or generic debug
     464 * event settings changes.
     465 *
     466 * DBGF will call NEMR3NotifyDebugEventChangedPerCpu on each CPU afterwards, this
     467 * function is just updating the VM globals.
     468 *
     469 * @param   pVM         The VM cross context VM structure.
     470 * @thread  EMT(0)
     471 */
     472VMMR3_INT_DECL(void) NEMR3NotifyDebugEventChanged(PVM pVM)
     473{
     474    AssertLogRelReturnVoid(VM_IS_NEM_ENABLED(pVM));
     475
     476    /* Interrupts. */
     477    bool fUseDebugLoop = pVM->dbgf.ro.cSoftIntBreakpoints > 0
     478                      || pVM->dbgf.ro.cHardIntBreakpoints > 0;
     479
     480    /* CPU Exceptions. */
     481    for (DBGFEVENTTYPE enmEvent = DBGFEVENT_XCPT_FIRST;
     482         !fUseDebugLoop && enmEvent <= DBGFEVENT_XCPT_LAST;
     483         enmEvent = (DBGFEVENTTYPE)(enmEvent + 1))
     484        fUseDebugLoop = DBGF_IS_EVENT_ENABLED(pVM, enmEvent);
     485
     486    /* Common VM exits. */
     487    for (DBGFEVENTTYPE enmEvent = DBGFEVENT_EXIT_FIRST;
     488         !fUseDebugLoop && enmEvent <= DBGFEVENT_EXIT_LAST_COMMON;
     489         enmEvent = (DBGFEVENTTYPE)(enmEvent + 1))
     490        fUseDebugLoop = DBGF_IS_EVENT_ENABLED(pVM, enmEvent);
     491
     492    /* Done. */
     493    pVM->nem.s.fUseDebugLoop = nemR3NativeNotifyDebugEventChanged(pVM, fUseDebugLoop);
     494}
     495
     496
     497/**
     498 * Follow up notification callback to NEMR3NotifyDebugEventChanged for each CPU.
     499 *
     500 * NEM uses this to combine the decision made NEMR3NotifyDebugEventChanged with
     501 * per CPU settings.
     502 *
     503 * @param   pVM         The VM cross context VM structure.
     504 * @param   pVCpu       The cross context virtual CPU structure of the calling EMT.
     505 */
     506VMMR3_INT_DECL(void) NEMR3NotifyDebugEventChangedPerCpu(PVM pVM, PVMCPU pVCpu)
     507{
     508    AssertLogRelReturnVoid(VM_IS_NEM_ENABLED(pVM));
     509
     510    pVCpu->nem.s.fUseDebugLoop = nemR3NativeNotifyDebugEventChangedPerCpu(pVM, pVCpu,
     511                                                                          pVCpu->nem.s.fSingleInstruction | pVM->nem.s.fUseDebugLoop);
     512}
  • trunk/src/VBox/VMM/VMMR3/NEMR3Native-darwin.cpp

    r93785 r93787  
    36963696bool nemR3NativeSetSingleInstruction(PVM pVM, PVMCPU pVCpu, bool fEnable)
    36973697{
    3698     NOREF(pVM); NOREF(pVCpu); NOREF(fEnable);
    3699     return false;
     3698    VMCPU_ASSERT_EMT(pVCpu);
     3699    bool fOld = pVCpu->nem.s.fSingleInstruction;
     3700    pVCpu->nem.s.fSingleInstruction = fEnable;
     3701    pVCpu->nem.s.fUseDebugLoop = fEnable || pVM->nem.s.fUseDebugLoop;
     3702    return fOld;
    37003703}
    37013704
     
    37203723    if (hrc != HV_SUCCESS)
    37213724        LogRel(("NEM: hv_vcpu_interrupt(%u, 1) failed with %#x\n", pVCpu->nem.s.hVCpuId, hrc));
     3725}
     3726
     3727
     3728DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChanged(PVM pVM, bool fUseDebugLoop)
     3729{
     3730    for (DBGFEVENTTYPE enmEvent = DBGFEVENT_EXIT_VMX_FIRST;
     3731         !fUseDebugLoop && enmEvent <= DBGFEVENT_EXIT_VMX_LAST;
     3732         enmEvent = (DBGFEVENTTYPE)(enmEvent + 1))
     3733        fUseDebugLoop = DBGF_IS_EVENT_ENABLED(pVM, enmEvent);
     3734
     3735    return fUseDebugLoop;
     3736}
     3737
     3738
     3739DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChangedPerCpu(PVM pVM, PVMCPU pVCpu, bool fUseDebugLoop)
     3740{
     3741    RT_NOREF(pVM, pVCpu);
     3742    return fUseDebugLoop;
    37223743}
    37233744
  • trunk/src/VBox/VMM/VMMR3/NEMR3Native-linux.cpp

    r93115 r93787  
    19981998
    19991999
     2000DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChanged(PVM pVM, bool fUseDebugLoop);
     2001{
     2002    RT_NOREF(pVM, fUseDebugLoop);
     2003    return false;
     2004}
     2005
     2006
     2007DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChangedPerCpu(PVM pVM, PVMCPU pVCpu, bool fUseDebugLoop);
     2008{
     2009    RT_NOREF(pVM, pVCpu, fUseDebugLoop);
     2010    return false;
     2011}
     2012
     2013
    20002014/**
    20012015 * Deals with pending interrupt FFs prior to executing guest code.
  • trunk/src/VBox/VMM/VMMR3/NEMR3Native-win.cpp

    r93515 r93787  
    16911691    RT_NOREF_PV(hrc);
    16921692    RT_NOREF_PV(fFlags);
     1693}
     1694
     1695
     1696DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChanged(PVM pVM, bool fUseDebugLoop);
     1697{
     1698    RT_NOREF(pVM, fUseDebugLoop);
     1699    return false;
     1700}
     1701
     1702
     1703DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChangedPerCpu(PVM pVM, PVMCPU pVCpu, bool fUseDebugLoop);
     1704{
     1705    RT_NOREF(pVM, pVCpu, fUseDebugLoop);
     1706    return false;
    16931707}
    16941708
  • trunk/src/VBox/VMM/include/NEMInternal.h

    r93728 r93787  
    180180    /** Set if long mode guests are allowed. */
    181181    bool                        fAllow64BitGuests;
     182    /** Set when the debug facility has breakpoints/events enabled that requires
     183     *  us to use the debug execution loop. */
     184    bool                        fUseDebugLoop;
    182185
    183186#if defined(RT_OS_LINUX)
     
    327330    /** Whether \#GP needs to be intercept for mesa driver workaround. */
    328331    bool                        fTrapXcptGpForLovelyMesaDrv: 1;
     332    /** Whether we should use the debug loop because of single stepping or special
     333     *  debug breakpoints / events are armed. */
     334    bool                        fUseDebugLoop : 1;
     335    /** Whether we're executing a single instruction. */
     336    bool                        fSingleInstruction : 1;
    329337
    330338#if defined(RT_OS_LINUX)
     
    439447    /** @name State shared with the VT-x code.
    440448     * @{ */
    441     /** Whether we should use the debug loop because of single stepping or special
    442      *  debug breakpoints / events are armed. */
    443     bool                        fUseDebugLoop;
    444     /** Whether we're executing a single instruction. */
    445     bool                        fSingleInstruction;
    446 
    447     bool                        afAlignment0[2];
    448 
    449449    /** An additional error code used for some gurus. */
    450450    uint32_t                    u32HMError;
     
    590590bool            nemR3NativeSetSingleInstruction(PVM pVM, PVMCPU pVCpu, bool fEnable);
    591591void            nemR3NativeNotifyFF(PVM pVM, PVMCPU pVCpu, uint32_t fFlags);
     592
     593/**
     594 * Called by NEMR3NotifyDebugEventChanged() to let the native backend take the final decision
     595 * on whether to switch to the debug loop.
     596 *
     597 * @returns Final flag whether to switch to the debug loop.
     598 * @param   pVM             The VM cross context VM structure.
     599 * @param   fUseDebugLoop   The current value determined by NEMR3NotifyDebugEventChanged().
     600 * @thread  EMT(0)
     601 */
     602DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChanged(PVM pVM, bool fUseDebugLoop);
     603
     604
     605/**
     606 * Called by NEMR3NotifyDebugEventChangedPerCpu() to let the native backend take the final decision
     607 * on whether to switch to the debug loop.
     608 *
     609 * @returns Final flag whether to switch to the debug loop.
     610 * @param   pVM             The VM cross context VM structure.
     611 * @param   pVCpu           The cross context virtual CPU structure of the calling EMT.
     612 * @param   fUseDebugLoop   The current value determined by NEMR3NotifyDebugEventChangedPerCpu().
     613 */
     614DECLHIDDEN(bool) nemR3NativeNotifyDebugEventChangedPerCpu(PVM pVM, PVMCPU pVCpu, bool fUseDebugLoop);
    592615#endif
    593616
Note: See TracChangeset for help on using the changeset viewer.

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