VirtualBox

Changeset 87130 in vbox for trunk/src


Ignore:
Timestamp:
Dec 27, 2020 7:32:53 PM (4 years ago)
Author:
vboxsync
Message:

VMM: More owner handling code for bugref:9837

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

Legend:

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

    r86751 r87130  
    2121*********************************************************************************************************************************/
    2222#define LOG_GROUP LOG_GROUP_DBGF
     23#define VMCPU_INCL_CPUM_GST_CTX
    2324#include <VBox/vmm/dbgf.h>
     25#include <VBox/vmm/iem.h>
     26#include <VBox/vmm/pgm.h>
    2427#include <VBox/vmm/selm.h>
    2528#include <VBox/log.h>
     
    117120
    118121
     122# ifdef IN_RING0
     123/**
     124 * Returns the internal breakpoint owner state for the given handle.
     125 *
     126 * @returns Pointer to the internal ring-0 breakpoint owner state or NULL if the handle is invalid.
     127 * @param   pVM                 The cross context VM structure.
     128 * @param   hBpOwner            The breakpoint owner handle to resolve.
     129 */
     130DECLINLINE(PCDBGFBPOWNERINTR0) dbgfR0BpOwnerGetByHnd(PVMCC pVM, DBGFBPOWNER hBpOwner)
     131{
     132    if (hBpOwner == NIL_DBGFBPOWNER)
     133        return NULL;
     134
     135    AssertReturn(hBpOwner < DBGF_BP_OWNER_COUNT_MAX, NULL);
     136
     137    PCDBGFBPOWNERINTR0 pBpOwnerR0 = &pVM->dbgfr0.s.paBpOwnersR0[hBpOwner];
     138    AssertReturn(pBpOwnerR0->cRefs > 1, NULL);
     139
     140    return pBpOwnerR0;
     141}
     142# endif
     143
     144
    119145/**
    120146 * Executes the actions associated with the given breakpoint.
     
    137163{
    138164    uint64_t cHits = ASMAtomicIncU64(&pBp->Pub.cHits);
    139     pVCpu->dbgf.s.hBpActive = hBp;
    140 
    141     /** @todo Owner handling. */
    142     RT_NOREF(pVM, pRegFrame);
    143 #ifdef IN_RING0
    144     RT_NOREF(pBpR0);
    145 #endif
    146 
     165
     166    RT_NOREF(pRegFrame);
    147167    LogFlow(("dbgfBpHit: hit breakpoint %u at %04x:%RGv cHits=0x%RX64\n",
    148168             hBp, pRegFrame->cs.Sel, pRegFrame->rip, cHits));
    149     return VINF_EM_DBG_BREAKPOINT;
     169
     170    int rc = VINF_EM_DBG_BREAKPOINT;
     171# ifdef IN_RING0
     172    PCDBGFBPOWNERINTR0 pBpOwnerR0 = dbgfR0BpOwnerGetByHnd(pVM,
     173                                                            pBpR0->fInUse
     174                                                          ? pBpR0->hOwner
     175                                                          : NIL_DBGFBPOWNER);
     176    if (pBpOwnerR0)
     177    {
     178        VBOXSTRICTRC rcStrict = pBpOwnerR0->pfnBpHitR0(pVM, pVCpu->idCpu, pBpR0->pvUserR0, hBp, &pBp->Pub);
     179        if (rcStrict == VINF_SUCCESS)
     180        {
     181            uint8_t abInstr[DBGF_BP_INSN_MAX];
     182            RTGCPTR const GCPtrInstr = pVCpu->cpum.GstCtx.rip + pVCpu->cpum.GstCtx.cs.u64Base;
     183            rc = PGMPhysSimpleReadGCPtr(pVCpu, &abInstr[0], GCPtrInstr, sizeof(abInstr));
     184            AssertRC(rc);
     185            if (RT_SUCCESS(rc))
     186            {
     187                /* Replace the int3 with the original instruction byte. */
     188                abInstr[0] = pBp->Pub.u.Int3.bOrg;
     189                rcStrict = IEMExecOneWithPrefetchedByPC(pVCpu, CPUMCTX2CORE(&pVCpu->cpum.GstCtx), GCPtrInstr, &abInstr[0], sizeof(abInstr));
     190                rc = VBOXSTRICTRC_VAL(rcStrict);
     191            }
     192        }
     193        else if (   rcStrict == VINF_DBGF_BP_HALT
     194                 || rcStrict == VINF_DBGF_R3_BP_OWNER_DEFER)
     195        {
     196            pVCpu->dbgf.s.hBpActive = hBp;
     197            if (rcStrict == VINF_DBGF_R3_BP_OWNER_DEFER)
     198                pVCpu->dbgf.s.fBpInvokeOwnerCallback = true;
     199            else
     200                pVCpu->dbgf.s.fBpInvokeOwnerCallback = false;
     201        }
     202        else /* Guru meditation. */
     203            rc = VERR_DBGF_BP_OWNER_CALLBACK_WRONG_STATUS;
     204    }
     205    else
     206    {
     207        pVCpu->dbgf.s.fBpInvokeOwnerCallback = true; /* Need to check this for ring-3 only owners. */
     208        pVCpu->dbgf.s.hBpActive              = hBp;
     209    }
     210# else
     211    RT_NOREF(pVM);
     212    pVCpu->dbgf.s.fBpInvokeOwnerCallback = true;
     213    pVCpu->dbgf.s.hBpActive = hBp;
     214# endif
     215
     216    return rc;
    150217}
    151218
  • trunk/src/VBox/VMM/VMMR3/DBGFR3Bp.cpp

    r87107 r87130  
    142142*********************************************************************************************************************************/
    143143#define LOG_GROUP LOG_GROUP_DBGF
     144#define VMCPU_INCL_CPUM_GST_CTX
    144145#include <VBox/vmm/dbgf.h>
    145146#include <VBox/vmm/selm.h>
     
    23262327}
    23272328
     2329
     2330/**
     2331 * Called whenever a breakpoint event needs to be serviced in ring-3 to decide what to do.
     2332 *
     2333 * @returns VBox status code.
     2334 * @param   pVM         The cross context VM structure.
     2335 * @param   pVCpu       The vCPU the breakpoint event happened on.
     2336 *
     2337 * @thread EMT
     2338 */
     2339VMMR3_INT_DECL(int) DBGFR3BpHit(PVM pVM, PVMCPU pVCpu)
     2340{
     2341    /* Send it straight into the debugger?. */
     2342    if (pVCpu->dbgf.s.fBpInvokeOwnerCallback)
     2343    {
     2344        DBGFBP hBp = pVCpu->dbgf.s.hBpActive;
     2345        PDBGFBPINT pBp = dbgfR3BpGetByHnd(pVM->pUVM, pVCpu->dbgf.s.hBpActive);
     2346        AssertReturn(pBp, VERR_DBGF_BP_IPE_9);
     2347
     2348        /* Resolve owner (can be NIL_DBGFBPOWNER) and invoke callback if there is one. */
     2349        PCDBGFBPOWNERINT pBpOwner = dbgfR3BpOwnerGetByHnd(pVM->pUVM, pBp->Pub.hOwner);
     2350        if (pBpOwner)
     2351        {
     2352            VBOXSTRICTRC rcStrict = pBpOwner->pfnBpHitR3(pVM, pVCpu->idCpu, pBp->pvUserR3, hBp, &pBp->Pub);
     2353            if (rcStrict == VINF_SUCCESS)
     2354            {
     2355                uint8_t abInstr[DBGF_BP_INSN_MAX];
     2356                RTGCPTR const GCPtrInstr = pVCpu->cpum.GstCtx.rip + pVCpu->cpum.GstCtx.cs.u64Base;
     2357                int rc = PGMPhysSimpleReadGCPtr(pVCpu, &abInstr[0], GCPtrInstr, sizeof(abInstr));
     2358                AssertRC(rc);
     2359                if (RT_SUCCESS(rc))
     2360                {
     2361                    /* Replace the int3 with the original instruction byte. */
     2362                    abInstr[0] = pBp->Pub.u.Int3.bOrg;
     2363                    rcStrict = IEMExecOneWithPrefetchedByPC(pVCpu, CPUMCTX2CORE(&pVCpu->cpum.GstCtx), GCPtrInstr, &abInstr[0], sizeof(abInstr));
     2364                    return VBOXSTRICTRC_VAL(rcStrict);
     2365                }
     2366            }
     2367            else if (rcStrict != VINF_DBGF_BP_HALT) /* Guru meditation. */
     2368                return VERR_DBGF_BP_OWNER_CALLBACK_WRONG_STATUS;
     2369            /* else: Halt in the debugger. */
     2370        }
     2371    }
     2372
     2373    return DBGFR3EventBreakpoint(pVM, DBGFEVENT_BREAKPOINT);
     2374}
     2375
  • trunk/src/VBox/VMM/VMMR3/EM.cpp

    r87040 r87130  
    839839
    840840            case VINF_EM_DBG_BREAKPOINT:
     841#ifdef VBOX_WITH_LOTS_OF_DBGF_BPS
     842                rc = DBGFR3BpHit(pVM, pVCpu);
     843#else
    841844                rc = DBGFR3EventBreakpoint(pVM, DBGFEVENT_BREAKPOINT);
     845#endif
    842846                break;
    843847
  • trunk/src/VBox/VMM/include/DBGFInternal.h

    r87107 r87130  
    6868/** Number of chunks required to support all breakpoints. */
    6969#define DBGF_BP_CHUNK_COUNT                 (DBGF_BP_COUNT_MAX / DBGF_BP_COUNT_PER_CHUNK)
     70/** Maximum number of instruction bytes when executing breakpointed instructions. */
     71#define DBGF_BP_INSN_MAX                    16
    7072/** @} */
    7173
     
    12631265     * @todo drop this in favor of aEvents!  */
    12641266    DBGFBP                  hBpActive;
     1267    /** Flag whether the to invoke any owner handlers in ring-3 before dropping into the debugger. */
     1268    bool                    fBpInvokeOwnerCallback;
    12651269#endif
    12661270    /** Set if we're singlestepping in raw mode.
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