VirtualBox

Ignore:
Timestamp:
Apr 26, 2011 9:38:02 AM (14 years ago)
Author:
vboxsync
Message:

VBoxBallonCtrl: fix event queue processing, change update interval handling, use correct base metric, make everything static, eliminate redundant event semaphore, fix error logging, avoid cluttering the code with Utf8Str conversions.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/VBox/Frontends/VBoxBalloonCtrl/VBoxBalloonCtrl.cpp

    r36711 r36847  
    6262 * of a per-machine based one. */
    6363#define VBOX_BALLOONCTRL_GLOBAL_PERFCOL
    64 
    65 /** The semaphore we're blocking on. */
    66 static RTSEMEVENTMULTI g_BalloonControlEvent = NIL_RTSEMEVENTMULTI;
    6764
    6865/** The critical section for keep our stuff in sync. */
     
    120117};
    121118
    122 unsigned long g_ulTimeoutMS = 30 * 1000; /* Default is 30 seconds timeout. */
    123 unsigned long g_ulMemoryBalloonIncrementMB = 256;
    124 unsigned long g_ulMemoryBalloonDecrementMB = 128;
     119static unsigned long g_ulTimeoutMS = 30 * 1000; /* Default is 30 seconds timeout. */
     120static unsigned long g_ulMemoryBalloonIncrementMB = 256;
     121static unsigned long g_ulMemoryBalloonDecrementMB = 128;
    125122/** Global balloon limit is 0, so disabled. Can be overridden by a per-VM
    126123 *  "VBoxInternal/Guest/BalloonSizeMax" value. */
    127 unsigned long g_ulMemoryBalloonMaxMB = 0;
    128 unsigned long g_ulLowerMemoryLimitMB = 64;
     124static unsigned long g_ulMemoryBalloonMaxMB = 0;
     125static unsigned long g_ulLowerMemoryLimitMB = 64;
    129126
    130127/** Global objects. */
     
    152149typedef std::map<Bstr, VBOXBALLOONCTRL_MACHINE>::iterator mapVMIter;
    153150typedef std::map<Bstr, VBOXBALLOONCTRL_MACHINE>::const_iterator mapVMIterConst;
    154 mapVM g_mapVM;
     151static mapVM g_mapVM;
    155152
    156153/* Prototypes. */
    157154#define serviceLogVerbose(a) if (g_fVerbose) { serviceLog a; }
    158 void serviceLog(const char *pszFormat, ...);
    159 
    160 bool machineIsRunning(MachineState_T enmState);
    161 mapVMIter machineGetByUUID(const Bstr &strUUID);
    162 int machineAdd(const ComPtr<IMachine> &rptrMachine);
    163 int machineUpdate(const ComPtr<IMachine> &rptrMachine, MachineState_T enmState);
    164 int machineUpdate(mapVMIter it, MachineState_T enmState);
    165 void machineRemove(mapVMIter it);
    166 
    167 unsigned long balloonGetMaxSize(const ComPtr<IMachine> &rptrMachine);
    168 bool balloonIsRequired(mapVMIter it);
    169 int balloonUpdate(mapVMIterConst it);
    170 
    171 HRESULT balloonCtrlSetup();
    172 void balloonCtrlShutdown();
    173 
    174 HRESULT createGlobalObjects();
    175 void deleteGlobalObjects();
     155static void serviceLog(const char *pszFormat, ...);
     156
     157static bool machineIsRunning(MachineState_T enmState);
     158static mapVMIter machineGetByUUID(const Bstr &strUUID);
     159static int machineAdd(const ComPtr<IMachine> &rptrMachine);
     160static int machineUpdate(const ComPtr<IMachine> &rptrMachine, MachineState_T enmState);
     161static int machineUpdate(mapVMIter it, MachineState_T enmState);
     162static void machineRemove(mapVMIter it);
     163
     164static unsigned long balloonGetMaxSize(const ComPtr<IMachine> &rptrMachine);
     165static bool balloonIsRequired(mapVMIter it);
     166static int balloonUpdate(mapVMIterConst it);
     167
     168static HRESULT balloonCtrlSetup();
     169static void balloonCtrlShutdown();
     170
     171static HRESULT createGlobalObjects();
     172static void deleteGlobalObjects();
    176173
    177174#ifdef RT_OS_WINDOWS
     
    339336    ASMAtomicWriteBool(&g_fCanceled, true);
    340337
    341     if (g_BalloonControlEvent != NIL_RTSEMEVENTMULTI)
    342     {
    343         int rc = RTSemEventMultiSignal(g_BalloonControlEvent);
     338    if (!g_pEventQ)
     339    {
     340        int rc = g_pEventQ->interruptEventQueueProcessing();
    344341        if (RT_FAILURE(rc))
    345             serviceLog("Error: RTSemEventMultiSignal failed with rc=%Rrc\n");
     342            serviceLog("Error: interruptEventQueueProcessing failed with rc=%Rrc\n", rc);
    346343    }
    347344}
     
    370367}
    371368
    372 long getlBalloonDelta(unsigned long ulCurrentDesktopBalloonSize, unsigned long ulDesktopFreeMemory, unsigned long ulMaxBalloonSize)
     369static long getlBalloonDelta(unsigned long ulCurrentDesktopBalloonSize, unsigned long ulDesktopFreeMemory, unsigned long ulMaxBalloonSize)
    373370{
    374371    if (ulCurrentDesktopBalloonSize > ulMaxBalloonSize)
     
    411408 * @param   enmState        The VM's machine state to judge whether it's running or not.
    412409 */
    413 bool machineIsRunning(MachineState_T enmState)
     410static bool machineIsRunning(MachineState_T enmState)
    414411{
    415412    switch (enmState)
     
    430427}
    431428
    432 mapVMIter machineGetByUUID(const Bstr &strUUID)
     429static mapVMIter machineGetByUUID(const Bstr &strUUID)
    433430{
    434431    return g_mapVM.find(strUUID);
    435432}
    436433
    437 int machineAdd(const ComPtr<IMachine> &rptrMachine)
     434static int machineAdd(const ComPtr<IMachine> &rptrMachine)
    438435{
    439436    HRESULT rc;
     
    451448        com::SafeIfaceArray<IPerformanceMetric> metricAffected;
    452449
    453         Bstr strMetricNames(L"Guest/RAM*");
     450        Bstr strMetricNames(L"Guest/RAM/Usage");
    454451        strMetricNames.cloneTo(&metricNames[0]);
    455452
     
    481478        g_mapVM.insert(std::make_pair(strUUID, m));
    482479
    483         serviceLogVerbose(("Added machine \"%s\"\n", Utf8Str(strUUID).c_str()));
     480        serviceLogVerbose(("Added machine \"%ls\"\n", strUUID.raw()));
    484481
    485482    } while (0);
     
    488485}
    489486
    490 void machineRemove(mapVMIter it)
     487static void machineRemove(mapVMIter it)
    491488{
    492489    if (it != g_mapVM.end())
    493490    {
    494491        /* Must log before erasing the iterator because of the UUID ref! */
    495         serviceLogVerbose(("Removing machine \"%s\"\n", Utf8Str(it->first).c_str()));
     492        serviceLogVerbose(("Removing machine \"%ls\"\n", it->first.raw()));
    496493
    497494        /*
     
    502499}
    503500
    504 int machineUpdate(const ComPtr<IMachine> &rptrMachine, MachineState_T enmState)
     501static int machineUpdate(const ComPtr<IMachine> &rptrMachine, MachineState_T enmState)
    505502{
    506503    if (   !balloonGetMaxSize(rptrMachine)
     
    512509}
    513510
    514 int machineUpdate(mapVMIter it, MachineState_T enmState)
     511static int machineUpdate(mapVMIter it, MachineState_T enmState)
    515512{
    516513    Assert(it != g_mapVM.end());
     
    526523}
    527524
    528 int getMetric(mapVMIterConst it, const Bstr& strName, LONG *pulData)
     525static int getMetric(mapVMIterConst it, const Bstr& strName, LONG *pulData)
    529526{
    530527    AssertPtrReturn(pulData, VERR_INVALID_PARAMETER);
     
    595592 * @param   rptrMachine             Pointer to specified machine.
    596593 */
    597 unsigned long balloonGetMaxSize(const ComPtr<IMachine> &rptrMachine)
     594static unsigned long balloonGetMaxSize(const ComPtr<IMachine> &rptrMachine)
    598595{
    599596    /*
     
    637634 * @param   it          Iterator pointing to the VM to be processed.
    638635 */
    639 bool balloonIsRequired(mapVMIter it)
     636static bool balloonIsRequired(mapVMIter it)
    640637{
    641638    /* Only do ballooning if we have a maximum balloon size set. */
     
    652649 * @param   it          Iterator pointing to the VM to be processed.
    653650 */
    654 int balloonUpdate(mapVMIterConst it)
     651static int balloonUpdate(mapVMIterConst it)
    655652{
    656653    /*
     
    669666        {
    670667#ifdef DEBUG
    671             serviceLogVerbose(("%s: No metrics available yet!\n", Utf8Str(it->first).c_str()));
     668            serviceLogVerbose(("%ls: No metrics available yet!\n", it->first.raw()));
    672669#endif
    673670            return VINF_SUCCESS;
     
    677674        lBalloonCur /= 1024;
    678675
    679         serviceLogVerbose(("%s: Balloon: %ld, Free mem: %ld, Max ballon: %ld\n",
    680                            Utf8Str(it->first).c_str(),
     676        serviceLogVerbose(("%ls: Balloon: %ld, Free mem: %ld, Max ballon: %ld\n",
     677                           it->first.raw(),
    681678                           lBalloonCur, lMemFree, it->second.ulBalloonSizeMax));
    682679
     
    688685            Assert(lBalloonCur > 0);
    689686
    690             serviceLog("%s: %s balloon by %ld to %ld ...\n",
    691                        Utf8Str(it->first).c_str(),
     687            serviceLog("%ls: %s balloon by %ld to %ld ...\n",
     688                       it->first.raw(),
    692689                       lDelta > 0 ? "Inflating" : "Deflating", lDelta, lBalloonCur);
    693690
     
    708705                    CHECK_ERROR_BREAK(guest, COMSETTER(MemoryBalloonSize)(lBalloonCur));
    709706                else
    710                     serviceLog("Error: Unable to set new balloon size %ld for machine \"%s\", rc=%Rhrc",
    711                                lBalloonCur, Utf8Str(it->first).c_str(), rc);
     707                    serviceLog("Error: Unable to set new balloon size %ld for machine \"%ls\", rc=%Rhrc",
     708                               lBalloonCur, it->first.raw(), rc);
    712709            } while (0);
    713710
     
    717714    }
    718715    else
    719         serviceLog("Error: Unable to retrieve metrics for machine \"%s\", rc=%Rrc",
    720                    Utf8Str(it->first).c_str(), vrc);
     716        serviceLog("Error: Unable to retrieve metrics for machine \"%ls\", rc=%Rrc",
     717                   it->first.raw(), vrc);
    721718    return vrc;
    722719}
    723720
    724 void vmListDestroy()
     721static void vmListDestroy()
    725722{
    726723    serviceLogVerbose(("Destroying VM list ...\n"));
     
    746743}
    747744
    748 int vmListBuild()
     745static int vmListBuild()
    749746{
    750747    serviceLogVerbose(("Building VM list ...\n"));
     
    779776                    if (!fAccessible)
    780777                    {
    781                         serviceLogVerbose(("Machine \"%s\" is inaccessible, skipping\n",
    782                                            Utf8Str(strUUID).c_str()));
     778                        serviceLogVerbose(("Machine \"%ls\" is inaccessible, skipping\n",
     779                                           strUUID.raw()));
    783780                        continue;
    784781                    }
     
    788785
    789786                    if (g_fVerbose)
    790                         serviceLogVerbose(("Processing machine \"%s\" (state: %ld)\n",
    791                                            Utf8Str(strUUID).c_str(), machineState));
     787                        serviceLogVerbose(("Processing machine \"%ls\" (state: %ld)\n",
     788                                           strUUID.raw(), machineState));
    792789
    793790                    if (machineIsRunning(machineState))
     
    811808}
    812809
    813 int balloonCtrlCheck()
    814 {
     810static int balloonCtrlCheck()
     811{
     812    static uint64_t uLast = UINT64_MAX;
     813    uint64_t uNow = RTTimeProgramMilliTS() / g_ulTimeoutMS;
     814    if (uLast == uNow)
     815        return VINF_SUCCESS;
     816    uLast = uNow;
     817
    815818    int rc = RTCritSectEnter(&g_MapCritSect);
    816819    if (RT_SUCCESS(rc))
     
    838841}
    839842
    840 HRESULT balloonCtrlSetup()
     843static HRESULT balloonCtrlSetup()
    841844{
    842845    HRESULT rc = S_OK;
     
    868871}
    869872
    870 void balloonCtrlShutdown()
     873static void balloonCtrlShutdown()
    871874{
    872875    serviceLog("Shutting down ballooning ...\n");
     
    879882}
    880883
    881 RTEXITCODE balloonCtrlMain(HandlerArg *a)
     884static RTEXITCODE balloonCtrlMain(HandlerArg *a)
    882885{
    883886    HRESULT rc = S_OK;
     
    885888    do
    886889    {
     890        int vrc = VINF_SUCCESS;
     891
    887892        /* Initialize global weak references. */
    888893        g_pEventQ = com::EventQueue::getMainEventQueue();
    889894
    890895        RTCritSectInit(&g_MapCritSect);
    891 
    892         int vrc = RTSemEventMultiCreate(&g_BalloonControlEvent);
    893         AssertRCReturn(vrc, RTEXITCODE_FAILURE);
    894896
    895897        /*
     
    945947             * processes NULL events signalling event loop termination.
    946948             */
    947             g_pEventQ->processEventQueue(500);
     949            g_pEventQ->processEventQueue(g_ulTimeoutMS / 10);
    948950
    949951            if (g_fCanceled)
    950952            {
    951953                serviceLog("Signal caught, exiting ...\n");
    952                 break;
    953             }
    954 
    955             vrc = RTSemEventMultiWait(g_BalloonControlEvent, g_ulTimeoutMS);
    956             if (vrc != VERR_TIMEOUT && RT_FAILURE(vrc))
    957             {
    958                 serviceLog("Error: RTSemEventMultiWait failed; rc=%Rrc\n", vrc);
    959954                break;
    960955            }
     
    980975
    981976        RTCritSectDelete(&g_MapCritSect);
    982         RTSemEventMultiDestroy(g_BalloonControlEvent);
    983         g_BalloonControlEvent = NIL_RTSEMEVENTMULTI;
    984977
    985978        if (RT_FAILURE(vrc))
     
    991984}
    992985
    993 void serviceLog(const char *pszFormat, ...)
     986static void serviceLog(const char *pszFormat, ...)
    994987{
    995988    va_list args;
     
    1004997}
    1005998
    1006 void logHeaderFooter(PRTLOGGER pLoggerRelease, RTLOGPHASE enmPhase, PFNRTLOGPHASEMSG pfnLog)
     999static void logHeaderFooter(PRTLOGGER pLoggerRelease, RTLOGPHASE enmPhase, PFNRTLOGPHASEMSG pfnLog)
    10071000{
    10081001    /* Some introductory information. */
     
    10721065}
    10731066
    1074 void displayHelp()
     1067static void displayHelp()
    10751068{
    10761069    RTStrmPrintf(g_pStdErr, "\nUsage: VBoxBalloonCtrl [options]\n\nSupported options (default values in brackets):\n");
     
    11481141}
    11491142
    1150 void deleteGlobalObjects()
     1143static void deleteGlobalObjects()
    11511144{
    11521145    serviceLogVerbose(("Deleting local objects ...\n"));
     
    11611154 * @return  HRESULT
    11621155 */
    1163 HRESULT createGlobalObjects()
     1156static HRESULT createGlobalObjects()
    11641157{
    11651158    serviceLogVerbose(("Creating local objects ...\n"));
     
    12131206            case 'i': /* Interval. */
    12141207                g_ulTimeoutMS = ValueUnion.u32;
     1208                if (g_ulTimeoutMS < 500)
     1209                    g_ulTimeoutMS = 500;
    12151210                break;
    12161211
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