VirtualBox

Changeset 90550 in vbox for trunk


Ignore:
Timestamp:
Aug 6, 2021 1:59:06 PM (4 years ago)
Author:
vboxsync
Message:

VMM/PGMCritSect: Added 'critsect' info item. bugref:6695

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

Legend:

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

    r90348 r90550  
    483483     * Initialize critical sections first.
    484484     */
    485     int rc = pdmR3CritSectBothInitStats(pVM);
     485    int rc = pdmR3CritSectBothInitStatsAndInfo(pVM);
    486486    if (RT_SUCCESS(rc))
    487487        rc = PDMR3CritSectInit(pVM, &pVM->pdm.s.CritSect, RT_SRC_POS, "PDM");
  • trunk/src/VBox/VMM/VMMR3/PDMCritSect.cpp

    r90534 r90550  
    2020*   Header Files                                                                                                                 *
    2121*********************************************************************************************************************************/
    22 #define LOG_GROUP LOG_GROUP_PDM_CRITSECT
     22#define LOG_GROUP LOG_GROUP_PDM//_CRITSECT
    2323#include "PDMInternal.h"
    2424#include <VBox/vmm/pdmcritsect.h>
     
    3333#include <iprt/asm.h>
    3434#include <iprt/assert.h>
     35#include <iprt/getopt.h>
    3536#include <iprt/lockvalidator.h>
    3637#include <iprt/string.h>
     
    4344static int pdmR3CritSectDeleteOne(PVM pVM, PUVM pUVM, PPDMCRITSECTINT pCritSect, PPDMCRITSECTINT pPrev, bool fFinal);
    4445static int pdmR3CritSectRwDeleteOne(PVM pVM, PUVM pUVM, PPDMCRITSECTRWINT pCritSect, PPDMCRITSECTRWINT pPrev, bool fFinal);
    45 
    46 
    47 
    48 /**
    49  * Register statistics related to the critical sections.
     46static FNDBGFINFOARGVINT pdmR3CritSectInfo;
     47
     48
     49
     50/**
     51 * Register statistics and info items related to the critical sections.
    5052 *
    5153 * @returns VBox status code.
    5254 * @param   pVM         The cross context VM structure.
    5355 */
    54 int pdmR3CritSectBothInitStats(PVM pVM)
    55 {
    56     RT_NOREF_PV(pVM);
     56int pdmR3CritSectBothInitStatsAndInfo(PVM pVM)
     57{
     58    /*
     59     * Statistics.
     60     */
    5761    STAM_REL_REG(pVM, &pVM->pdm.s.StatQueuedCritSectLeaves, STAMTYPE_COUNTER, "/PDM/CritSects/00-QueuedLeaves", STAMUNIT_OCCURENCES,
    5862                 "Number of times a critical section leave request needed to be queued for ring-3 execution.");
     
    6771    STAM_REL_REG(pVM, &pVM->pdm.s.StatCritSectNonInterruptibleWaits, STAMTYPE_COUNTER, "/PDM/CritSects/00-Non-interruptible-Waits-VINF_SUCCESS",
    6872                 STAMUNIT_OCCURENCES, "Number of non-interruptible waits for rcBusy=VINF_SUCCESS");
     73
     74    /*
     75     * Info items.
     76     */
     77    DBGFR3InfoRegisterInternalArgv(pVM, "critsect", "Show critical section: critsect [-v] [pattern[...]]", pdmR3CritSectInfo, 0);
     78
    6979    return VINF_SUCCESS;
    7080}
     
    163173                 * Initialize the structure (first bit is c&p from RTCritSectInitEx).
    164174                 */
    165                 Log(("pdmR3CritSectInitOne: %p - %s\n", pCritSect, pszName));
    166175                pCritSect->Core.u32Magic             = RTCRITSECT_MAGIC;
    167176                pCritSect->Core.fFlags               = 0;
     
    10691078}
    10701079
     1080
     1081/**
     1082 * Display matching critical sections.
     1083 */
     1084static void pdmR3CritSectInfoWorker(PUVM pUVM, const char *pszPatterns, PCDBGFINFOHLP pHlp, unsigned cVerbosity)
     1085{
     1086    size_t const cchPatterns = pszPatterns ? strlen(pszPatterns) : 0;
     1087    RTCritSectEnter(&pUVM->pdm.s.ListCritSect);
     1088
     1089    for (PPDMCRITSECTINT pCritSect = pUVM->pdm.s.pCritSects; pCritSect; pCritSect = pCritSect->pNext)
     1090        if (   !pszPatterns
     1091            || RTStrSimplePatternMultiMatch(pszPatterns, cchPatterns, pCritSect->pszName, RTSTR_MAX, NULL))
     1092        {
     1093            pHlp->pfnPrintf(pHlp, "%p: '%s'%s\n", pCritSect, pCritSect->pszName,
     1094                            pCritSect->fAutomaticDefaultCritsect ? " default" : "",
     1095                            pCritSect->fUsedByTimerOrSimilar ? " used-by-timer-or-similar" : "");
     1096
     1097            /*
     1098             * Get the volatile data:
     1099             */
     1100            RTNATIVETHREAD hOwner;
     1101            int32_t        cLockers;
     1102            int32_t        cNestings;
     1103            uint32_t       fFlags;
     1104            uint32_t       uMagic;
     1105            for (uint32_t iTry = 0; iTry < 16; iTry++)
     1106            {
     1107                hOwner    = pCritSect->Core.NativeThreadOwner;
     1108                cLockers  = pCritSect->Core.cLockers;
     1109                cNestings = pCritSect->Core.cNestings;
     1110                fFlags    = pCritSect->Core.fFlags;
     1111                uMagic    = pCritSect->Core.u32Magic;
     1112                if (   hOwner    == pCritSect->Core.NativeThreadOwner
     1113                    && cLockers  == pCritSect->Core.cLockers
     1114                    && cNestings == pCritSect->Core.cNestings
     1115                    && fFlags    == pCritSect->Core.fFlags
     1116                    && uMagic    == pCritSect->Core.u32Magic)
     1117                    break;
     1118            }
     1119
     1120            /*
     1121             * Check and resolve the magic to a string, print if not RTCRITSECT_MAGIC.
     1122             */
     1123            const char *pszMagic;
     1124            switch (uMagic)
     1125            {
     1126                case RTCRITSECT_MAGIC:                  pszMagic = NULL; break;
     1127                case ~RTCRITSECT_MAGIC:                 pszMagic = " deleted"; break;
     1128                case PDMCRITSECT_MAGIC_CORRUPTED:       pszMagic = " PDMCRITSECT_MAGIC_CORRUPTED!"; break;
     1129                case PDMCRITSECT_MAGIC_FAILED_ABORT:    pszMagic = " PDMCRITSECT_MAGIC_FAILED_ABORT!"; break;
     1130                default:                                pszMagic = " !unknown!"; break;
     1131            }
     1132            if (pszMagic || cVerbosity > 1)
     1133                pHlp->pfnPrintf(pHlp, "  uMagic=%#x%s\n", uMagic, pszMagic ? pszMagic : "");
     1134
     1135            /*
     1136             * If locked, print details
     1137             */
     1138            if (cLockers != -1 || cNestings != 1 || hOwner != NIL_RTNATIVETHREAD || cVerbosity > 1)
     1139            {
     1140                /* Translate the owner to a name if we have one and can. */
     1141                const char *pszOwner = NULL;
     1142                if (hOwner != NIL_RTNATIVETHREAD)
     1143                {
     1144                    RTTHREAD hOwnerThread = RTThreadFromNative(hOwner); /* Note! Does not return a reference (crazy). */
     1145                    if (hOwnerThread != NIL_RTTHREAD)
     1146                        pszOwner = RTThreadGetName(hOwnerThread);
     1147                }
     1148                else
     1149                    pszOwner = "<no-owner>";
     1150
     1151                pHlp->pfnPrintf(pHlp, "  cLockers=%d cNestings=%d hOwner=%p %s%s\n", cLockers, cNestings, hOwner,
     1152                                pszOwner ? pszOwner : "???", fFlags & PDMCRITSECT_FLAGS_PENDING_UNLOCK ? " pending-unlock" : "");
     1153            }
     1154        }
     1155    RTCritSectLeave(&pUVM->pdm.s.ListCritSect);
     1156}
     1157
     1158
     1159/**
     1160 * @callback_method_impl{FNDBGFINFOARGVINT, critsect}
     1161 */
     1162static DECLCALLBACK(void) pdmR3CritSectInfo(PVM pVM, PCDBGFINFOHLP pHlp, int cArgs, char **papszArgs)
     1163{
     1164    PUVM pUVM = pVM->pUVM;
     1165
     1166    /*
     1167     * Process arguments.
     1168     */
     1169    static const RTGETOPTDEF s_aOptions[] =
     1170    {
     1171        {   "--verbose", 'v', RTGETOPT_REQ_NOTHING },
     1172    };
     1173    RTGETOPTSTATE State;
     1174    int rc = RTGetOptInit(&State, cArgs, papszArgs, s_aOptions, RT_ELEMENTS(s_aOptions), 0, RTGETOPTINIT_FLAGS_NO_STD_OPTS);
     1175    AssertRC(rc);
     1176
     1177    unsigned cVerbosity = 1;
     1178    unsigned cProcessed = 0;
     1179
     1180    RTGETOPTUNION ValueUnion;
     1181    while ((rc = RTGetOpt(&State, &ValueUnion)) != 0)
     1182    {
     1183        switch (rc)
     1184        {
     1185            case 'v':
     1186                cVerbosity++;
     1187                break;
     1188
     1189            case VINF_GETOPT_NOT_OPTION:
     1190                pdmR3CritSectInfoWorker(pUVM, ValueUnion.psz, pHlp, cVerbosity);
     1191                cProcessed++;
     1192                break;
     1193
     1194            default:
     1195                pHlp->pfnGetOptError(pHlp, rc, &ValueUnion, &State);
     1196                return;
     1197        }
     1198    }
     1199
     1200    /*
     1201     * If we did nothing above, dump all.
     1202     */
     1203    if (!cProcessed)
     1204        pdmR3CritSectInfoWorker(pUVM, NULL, pHlp, cVerbosity);
     1205}
     1206
     1207
  • trunk/src/VBox/VMM/include/PDMInternal.h

    r90504 r90550  
    16221622bool        pdmR3IsValidName(const char *pszName);
    16231623
    1624 int         pdmR3CritSectBothInitStats(PVM pVM);
     1624int         pdmR3CritSectBothInitStatsAndInfo(PVM pVM);
    16251625int         pdmR3CritSectBothDeleteDevice(PVM pVM, PPDMDEVINS pDevIns);
    16261626int         pdmR3CritSectBothDeleteDriver(PVM pVM, PPDMDRVINS pDrvIns);
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