Changeset 10528 in vbox
- Timestamp:
- Jul 11, 2008 2:27:01 PM (16 years ago)
- Location:
- trunk
- Files:
-
- 14 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/include/iprt/system.h
r9935 r10528 34 34 #include <iprt/types.h> 35 35 36 #define IPRT_USAGE_MULTIPLIER UINT64_C(1000000000)37 38 /**39 * This structure holds both computed and raw values of overall CPU load counters.40 *41 * @todo r=bird: What does these values mean?42 *43 * Also, I no longer use 'u32', 'u16', 'u8', 'u64', etc unless this information44 * is really important for the user. So, unless there is a better prefix just45 * stick to 'u' here.46 *47 * The name of the struct should include the prefix or a shortened48 * version of it: RTSYSCPUUSAGESTATS49 *50 * Also, I'd sugest calling it RTSYSCPULOADSTATS, replacing 'usage' with 'load',51 * no particular reason, other than that it is easier to read in the (silly)52 * condensed form we use for typedefs here.53 *54 * Finally, I'm wondering how portable this is. I'd like to see what APIs are55 * available on the important systems (Windows, Solaris, Linux) and compare56 * the kind of info they return. This should be done in the defect *before*57 * any of the above, please.58 */59 typedef struct RTSYSCPUUSAGESTATS60 {61 uint32_t u32User;62 uint32_t u32System;63 uint32_t u32Idle;64 /* Internal raw counter values. */65 uint32_t u32RawUser;66 uint32_t u32RawNice;67 uint32_t u32RawSystem;68 uint32_t u32RawIdle;69 } RTCPUUSAGESTATS;70 typedef RTCPUUSAGESTATS *PRTCPUUSAGESTATS;71 72 /* This structure holds both computed and raw values of per-VM CPU load counters. */73 typedef struct74 {75 uint32_t u32User;76 uint32_t u32System;77 /* Internal raw counter values. */78 uint64_t u64RawTotal;79 uint32_t u32RawProcUser;80 uint32_t u32RawProcSystem;81 } RTPROCCPUUSAGESTATS;82 typedef RTPROCCPUUSAGESTATS *PRTPROCCPUUSAGESTATS;83 84 36 85 37 __BEGIN_DECLS … … 108 60 RTDECL(uint64_t) RTSystemProcessorGetActiveMask(void); 109 61 110 /**111 * Gets the current figures of overall system processor usage.112 *113 * @remarks To get meaningful stats this function has to be114 * called twice with a bit of delay between calls. This115 * is due to the fact that at least two samples of116 * system usage stats are needed to calculate the load.117 *118 * @returns IPRT status code.119 * @param pStats Pointer to the structure that contains the120 * results. Note that this structure is121 * modified with each call to this function and122 * is used to provide both in and out values.123 * @todo r=bird: Change to RTSystemGetCpuLoadStats.124 */125 RTDECL(int) RTSystemProcessorGetUsageStats(PRTCPUUSAGESTATS pStats);126 127 /**128 * Gets the current processor usage for a partucilar process.129 *130 * @remarks To get meaningful stats this function has to be131 * called twice with a bit of delay between calls. This132 * is due to the fact that at least two samples of133 * system usage stats are needed to calculate the load.134 *135 * @returns IPRT status code.136 * @param pid VM process id.137 * @param pStats Pointer to the structure that contains the138 * results. Note that this structure is139 * modified with each call to this function and140 * is used to provide both in and out values.141 *142 * @todo Perharps this function should be moved somewhere143 * else.144 * @todo r=bird: Yes is should, iprt/proc.h. RTProcGetCpuLoadStats.145 */146 RTDECL(int) RTProcessGetProcessorUsageStats(RTPROCESS pid, PRTPROCCPUUSAGESTATS pStats);147 148 62 /** @} */ 149 63 -
trunk/src/VBox/Main/HostImpl.cpp
r10444 r10528 171 171 172 172 #ifdef VBOX_WITH_RESOURCE_USAGE_API 173 /* Start resource usage sampler */ 174 { 175 int vrc = RTTimerCreate (&mUsageSampler, VBOX_USAGE_SAMPLER_INTERVAL, 176 UsageSamplerCallback, this); 177 AssertMsgRC (vrc, ("Failed to create resource usage sampling " 178 "timer (%Rra)\n", vrc)); 179 if (RT_FAILURE (vrc)) 180 return E_FAIL; 181 } 173 registerMetrics(parent->getCollector()); 182 174 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 183 175 … … 195 187 196 188 AssertReturn (isReady(), (void) 0); 189 190 #ifdef VBOX_WITH_RESOURCE_USAGE_API 191 unregisterMetrics(mParent->getCollector()); 192 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 197 193 198 194 #ifdef VBOX_WITH_USB … … 211 207 mUSBDeviceFilters.clear(); 212 208 #endif 213 214 #ifdef VBOX_WITH_RESOURCE_USAGE_API215 /* Destroy resource usage sampler */216 {217 int vrc = RTTimerDestroy (mUsageSampler);218 AssertMsgRC (vrc, ("Failed to destroy resource usage "219 "sampling timer (%Rra)\n", vrc));220 }221 #endif /* VBOX_WITH_RESOURCE_USAGE_API */222 209 223 210 setReady (FALSE); … … 1110 1097 return E_NOTIMPL; 1111 1098 #endif 1112 }1113 1114 STDMETHODIMP Host::GetProcessorUsage (ULONG *aUser, ULONG *aSystem, ULONG *aIdle)1115 {1116 #ifdef VBOX_WITH_RESOURCE_USAGE_API1117 if (aUser == NULL || aSystem == NULL || aIdle == NULL)1118 return E_POINTER;1119 1120 *aUser = mCpuStats.u32User;1121 *aSystem = mCpuStats.u32System;1122 *aIdle = mCpuStats.u32Idle;1123 1124 return S_OK;1125 #else /* !VBOX_WITH_RESOURCE_USAGE_API */1126 return E_NOTIMPL;1127 #endif /* !VBOX_WITH_RESOURCE_USAGE_API */1128 1099 } 1129 1100 … … 2722 2693 2723 2694 #ifdef VBOX_WITH_RESOURCE_USAGE_API 2724 2725 /* static */ 2726 void Host::UsageSamplerCallback (PRTTIMER pTimer, void *pvUser, uint64_t iTick) 2727 { 2728 AssertReturnVoid (pvUser != NULL); 2729 static_cast <Host *> (pvUser)->usageSamplerCallback(); 2730 } 2731 2732 void Host::usageSamplerCallback() 2733 { 2734 int vrc = RTSystemProcessorGetUsageStats (&mCpuStats); 2735 AssertMsgRC (vrc, ("Failed to get CPU stats (%Rra)\n", vrc)); 2736 2737 // LogFlowThisFunc (("user=%u%% system=%u%% &mCpuStats=%p\n", 2738 // mCpuStats.u32User / 10000000, 2739 // mCpuStats.u32System / 10000000, &mCpuStats); 2740 // LogFlowThisFunc (("user=%.2f system=%.2f idle=%.2f\n", mCpuStats.u32User/10000000., 2741 // mCpuStats.u32System/10000000., mCpuStats.u32Idle/10000000.); 2742 } 2743 2695 void Host::registerMetrics(PerformanceCollector *collector) 2696 { 2697 pm::MetricFactory *metricFactory = collector->getMetricFactory(); 2698 // Create sub metrics 2699 pm::SubMetric *cpuLoadUser = new pm::SubMetric("CPU/Load/User"); 2700 pm::SubMetric *cpuLoadKernel = new pm::SubMetric("CPU/Load/Kernel"); 2701 pm::SubMetric *cpuLoadIdle = new pm::SubMetric("CPU/Load/Idle"); 2702 // Create and register base metrics 2703 IUnknown *objptr; 2704 ComObjPtr<Host> tmp = this; 2705 tmp.queryInterfaceTo(&objptr); 2706 pm::BaseMetric *cpuLoad = 2707 metricFactory->createHostCpuLoad(objptr, cpuLoadUser, cpuLoadKernel, cpuLoadIdle); 2708 collector->registerBaseMetric(cpuLoad); 2709 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, 0)); 2710 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, new pm::AggregateAvg())); 2711 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, new pm::AggregateMin())); 2712 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, new pm::AggregateMax())); 2713 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, 0)); 2714 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, new pm::AggregateAvg())); 2715 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, new pm::AggregateMin())); 2716 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, new pm::AggregateMax())); 2717 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadIdle, 0)); 2718 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadIdle, new pm::AggregateAvg())); 2719 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadIdle, new pm::AggregateMin())); 2720 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadIdle, new pm::AggregateMax())); 2721 }; 2722 2723 void Host::unregisterMetrics(PerformanceCollector *collector) 2724 { 2725 collector->unregisterMetricsFor(this); 2726 collector->unregisterBaseMetricsFor(this); 2727 }; 2744 2728 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 2745 2729 -
trunk/src/VBox/Main/MachineImpl.cpp
r10420 r10528 147 147 mSession.mPid = NIL_RTPROCESS; 148 148 mSession.mState = SessionState_Closed; 149 150 #ifdef VBOX_WITH_RESOURCE_USAGE_API151 mUsageSampler = NULL;152 #endif /* VBOX_WITH_RESOURCE_USAGE_API */153 149 } 154 150 … … 501 497 } 502 498 503 #ifdef VBOX_WITH_RESOURCE_USAGE_API504 /* Start resource usage sampler */505 {506 vrc = RTTimerCreate (&mData->mUsageSampler, VBOX_USAGE_SAMPLER_INTERVAL,507 Machine::UsageSamplerCallback, this);508 AssertMsgRC (vrc, ("Failed to create resource usage "509 "sampling timer(%Rra)\n", vrc));510 if (RT_FAILURE (vrc))511 rc = E_FAIL;512 }513 #endif /* VBOX_WITH_RESOURCE_USAGE_API */514 515 499 LogFlowThisFunc (("mName='%ls', mRegistered=%RTbool, mAccessible=%RTbool " 516 500 "rc=%08X\n", … … 636 620 */ 637 621 AutoMultiWriteLock2 alock (mParent, this); 638 639 #ifdef VBOX_WITH_RESOURCE_USAGE_API640 /* Destroy resource usage sampler */641 {642 int vrc = RTTimerDestroy (mData->mUsageSampler);643 AssertMsgRC (vrc, ("Failed to destroy resource usage "644 "sampling timer (%Rra)\n", vrc));645 }646 #endif /* VBOX_WITH_RESOURCE_USAGE_API */647 622 648 623 if (!mData->mSession.mMachine.isNull()) … … 2814 2789 } 2815 2790 2816 STDMETHODIMP Machine::GetProcessorUsage (ULONG *aUser, ULONG *aSystem)2817 {2818 #ifdef VBOX_WITH_RESOURCE_USAGE_API2819 if (aUser == NULL || aSystem == NULL)2820 return E_POINTER;2821 2822 // LogFlowThisFunc (("user=%u%% system=%u%% &mData->mCpuStats=%p\n",2823 // mData->mCpuStats.u32User / 10000000,2824 // mData->mCpuStats.u32System / 10000000, &mData->mCpuStats));2825 2826 *aUser = mData->mCpuStats.u32User;2827 *aSystem = mData->mCpuStats.u32System;2828 return S_OK;2829 #else /* !VBOX_WITH_RESOURCE_USAGE_API */2830 return E_NOTIMPL;2831 #endif /* !VBOX_WITH_RESOURCE_USAGE_API */2832 }2833 2834 2791 2835 2792 // public methods for internal purposes … … 7320 7277 7321 7278 #ifdef VBOX_WITH_RESOURCE_USAGE_API 7322 7323 /* static */ 7324 void Machine::UsageSamplerCallback (PRTTIMER pTimer, void *pvUser, uint64_t iTick) 7325 { 7326 AssertReturnVoid (pvUser != NULL);7327 static_cast <Machine *> (pvUser)->usageSamplerCallback();7328 } 7329 7330 void Machine::usageSamplerCallback() 7331 { 7332 // LogFlowThisFunc (("mData->mSession.mPid = %u &mData->mCpuStats = %p)\n", 7333 // mData->mSession.mPid, &m_CpuStats)); 7334 if (mData->mSession.mPid != NIL_RTPROCESS)7335 {7336 int vrc = RTProcessGetProcessorUsageStats (mData->mSession.mPid, 7337 &mData->mCpuStats);7338 AssertMsgRC (vrc, ("Failed to get CPU stats (%Rra)\n", vrc));7339 }7340 else7341 {7342 mData->mCpuStats.u32User = 0;7343 mData->mCpuStats.u32System = 0;7344 }7345 // LogFlowThisFunc (("user=%u%% system=%u%% &mData->mCpuStats=%p\n", 7346 // mData->mCpuStats.u32User / 10000000, 7347 // mData->mCpuStats.u32System / 10000000, &mData->mCpuStats)); 7348 // LogFlowThisFunc (("user=%.2f system=%.2f\n", 7349 // mData->mCpuStats.u32User/10000000., mData->mCpuStats.u32System/10000000.));7350 } 7351 7279 void Machine::registerMetrics(PerformanceCollector *collector) 7280 { 7281 pm::MetricFactory *metricFactory = collector->getMetricFactory(); 7282 // Create sub metrics 7283 pm::SubMetric *cpuLoadUser = new pm::SubMetric("CPU/Load/User"); 7284 pm::SubMetric *cpuLoadKernel = new pm::SubMetric("CPU/Load/Kernel"); 7285 // Create and register base metrics 7286 IUnknown *objptr; 7287 7288 ComObjPtr<Machine> tmp = this; 7289 tmp.queryInterfaceTo(&objptr); 7290 pm::BaseMetric *cpuLoad = 7291 metricFactory->createMachineCpuLoad(objptr, mData->mSession.mPid, cpuLoadUser, cpuLoadKernel); 7292 collector->registerBaseMetric(cpuLoad); 7293 7294 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, 0)); 7295 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, new pm::AggregateAvg())); 7296 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, new pm::AggregateMin())); 7297 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadUser, new pm::AggregateMax())); 7298 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, 0)); 7299 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, new pm::AggregateAvg())); 7300 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, new pm::AggregateMin())); 7301 collector->registerMetric(new pm::Metric(cpuLoad, cpuLoadKernel, new pm::AggregateMax())); 7302 }; 7303 7304 void Machine::unregisterMetrics(PerformanceCollector *collector) 7305 { 7306 collector->unregisterMetricsFor(this); 7307 collector->unregisterBaseMetricsFor(this); 7308 }; 7352 7309 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 7310 7353 7311 7354 7312 ///////////////////////////////////////////////////////////////////////////// … … 10406 10364 return S_OK; 10407 10365 } 10366 10367 -
trunk/src/VBox/Main/Makefile.kmk
r10268 r10528 259 259 VBoxSVC_SOURCES.solaris += solaris/USBProxyServiceSolaris.cpp 260 260 VBoxSVC_SOURCES.win += win/USBProxyServiceWindows.cpp 261 endif 262 263 ifdef VBOX_WITH_RESOURCE_USAGE_API 264 VBoxSVC_SOURCES += \ 265 PerformanceImpl.cpp \ 266 Performance.cpp 261 267 endif 262 268 -
trunk/src/VBox/Main/VirtualBoxImpl.cpp
r10400 r10528 228 228 Key global = tree.rootKey().key ("Global"); 229 229 230 #ifdef VBOX_WITH_RESOURCE_USAGE_API 231 /* create the performance collector object BEFORE host */ 232 unconst (mData.mPerformanceCollector).createObject(); 233 rc = mData.mPerformanceCollector->init (); 234 ComAssertComRCThrowRC (rc); 235 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 236 230 237 /* create the host object early, machines will need it */ 231 238 unconst (mData.mHost).createObject(); … … 376 383 } 377 384 385 #ifdef VBOX_WITH_RESOURCE_USAGE_API 386 if (mData.mPerformanceCollector) 387 { 388 mData.mPerformanceCollector->uninit(); 389 unconst (mData.mPerformanceCollector).setNull(); 390 } 391 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 392 378 393 /* 379 394 * Uninit all other children still referenced by clients … … 571 586 return S_OK; 572 587 } 588 589 STDMETHODIMP 590 VirtualBox::COMGETTER(PerformanceCollector) (IPerformanceCollector **aPerformanceCollector) 591 { 592 #ifdef VBOX_WITH_RESOURCE_USAGE_API 593 if (!aPerformanceCollector) 594 return E_POINTER; 595 596 AutoCaller autoCaller (this); 597 CheckComRCReturnRC (autoCaller.rc()); 598 599 mData.mPerformanceCollector.queryInterfaceTo (aPerformanceCollector); 600 601 return S_OK; 602 #else /* !VBOX_WITH_RESOURCE_USAGE_API */ 603 return E_NOTIMPL; 604 #endif /* !VBOX_WITH_RESOURCE_USAGE_API */ 605 } 606 573 607 574 608 /** -
trunk/src/VBox/Main/idl/VirtualBox.xidl
r10399 r10528 885 885 <interface 886 886 name="IVirtualBox" extends="$dispatched" 887 uuid=" 2d3b9ea7-25f5-4f07-a8e1-7dd7e0dcf667"887 uuid="557a07bc-e6ae-4520-a361-4a8493199137" 888 888 wsmap="managed" 889 889 > … … 1055 1055 implemented and therefore this collection is always empty. 1056 1056 </note> 1057 </desc> 1058 </attribute> 1059 <attribute name="performanceCollector" type="IPerformanceCollector" readonly="yes"> 1060 <desc> 1061 The only instance of IPerformanceCollector. 1057 1062 </desc> 1058 1063 </attribute> … … 3530 3535 </method> 3531 3536 3532 <method name="getProcessorUsage">3533 <desc>3534 Returns the current processor usage by this virtual machine measured3535 over all cores of all processors in the host system.3536 3537 The values returned for each parameter are in range from <tt>0</tt> (the3538 machine is powered off or does not load the CPUs at all) to3539 <tt>1 000 000 000</tt> (all cores of all CPUs are fully in use by this3540 machine).3541 </desc>3542 <param name="user" type="unsigned long" dir="out">3543 <desc>3544 Pecentage of processor time spent executing in user mode.3545 </desc>3546 </param>3547 <param name="system" type="unsigned long" dir="out">3548 <desc>3549 Pecentage of processor time spent executing in kernel mode.3550 </desc>3551 </param>3552 </method>3553 3554 3537 </interface> 3555 3538 … … 5053 5036 </method> 5054 5037 5055 <method name="getProcessorUsage">5056 <desc>5057 Returns the processor usage by the whole host system measured over all5058 cores of all processors of the host machine.5059 5060 The values returned for each parameter are in range from <tt>0</tt> (the5061 machine is powered off or doesn't load the CPUs at all) to5062 <tt>1 000 000 000</tt> (all cores of all CPUs are fully loaded by this5063 machine).5064 5065 <note>5066 The maximum value is 1000000000 which means that all cores of all CPUs5067 are completely used.5068 </note>5069 </desc>5070 <param name="user" type="unsigned long" dir="out">5071 <desc>5072 Pecentage of processor time spent executing in user mode.5073 </desc>5074 </param>5075 <param name="system" type="unsigned long" dir="out">5076 <desc>5077 Pecentage of processor time spent executing in kernel mode.5078 </desc>5079 </param>5080 <param name="idle" type="unsigned long" dir="out">5081 <desc>5082 Pecentage of processor time spent doing nothing.5083 </desc>5084 </param>5085 </method>5086 5038 </interface> 5087 5039 … … 10122 10074 </if> 10123 10075 10076 <interface 10077 name="IPerformanceMetric" extends="$unknown" 10078 uuid="50831d4c-ed55-4221-836c-87b487d3b44a" wsmap="managed" 10079 > 10080 <desc>Holds metrics parameters.</desc> 10081 10082 <attribute name="metricName" type="wstring" readonly="yes"> 10083 <desc> 10084 Name of the metric. 10085 </desc> 10086 </attribute> 10087 10088 <attribute name="object" type="$unknown" readonly="yes"> 10089 <desc> 10090 The object this metric belongs to. 10091 </desc> 10092 </attribute> 10093 10094 <attribute name="period" type="unsigned long" readonly="yes"> 10095 <desc> 10096 The time interval between samples, measured in seconds. 10097 </desc> 10098 </attribute> 10099 10100 <attribute name="count" type="unsigned long" readonly="yes"> 10101 <desc> 10102 The number of recent samples retained by the collector. Older samples 10103 are discarded. 10104 </desc> 10105 </attribute> 10106 10107 <attribute name="unit" type="wstring" readonly="yes"> 10108 <desc> 10109 The unit of measurement. 10110 </desc> 10111 </attribute> 10112 10113 <attribute name="minimumValue" type="long" readonly="yes"> 10114 <desc> 10115 The minimum possible value of this metric. 10116 </desc> 10117 </attribute> 10118 10119 <attribute name="maximumValue" type="long" readonly="yes"> 10120 <desc> 10121 The maximum possible value of this metric. 10122 </desc> 10123 </attribute> 10124 </interface> 10125 10126 <interface 10127 name="IPerformanceCollector" extends="$unknown" 10128 uuid="dcd37e5a-3964-43d1-be30-0f3c7234e347" 10129 wsmap="managed" 10130 > 10131 <desc> 10132 This object collects and stores performace metrics data. Performance 10133 metrics are associated with objects like IHost and IMachine. Each object 10134 has a distict set of performance metrics. It can be obtained with 10135 <link to="IPerformanceCollector::getMetrics"/>. 10136 </desc> 10137 10138 <attribute name="metricNames" type="wstring" readonly="yes" safearray="yes"> 10139 <desc> 10140 An array of unique names of metrics regardless of objects they are 10141 associated with. 10142 </desc> 10143 </attribute> 10144 10145 <method name="getMetrics"> 10146 <desc> 10147 Returns parameters (characteristics?) of specified metrics for a set of 10148 objects. 10149 <note> 10150 Null metrics array means all metrics. Null object array means all 10151 existing objects. 10152 </note> 10153 </desc> 10154 <param name="metricNames" type="wstring" dir="in" safearray="yes"/> 10155 <param name="objects" type="$unknown" dir="in" safearray="yes"/> 10156 <param name="metrics" type="IPerformanceMetric" dir="return" safearray="yes"/> 10157 </method> 10158 10159 <method name="setupMetrics"> 10160 <desc> 10161 Sets parameters of specified metrics for a set of objects. 10162 <note> 10163 Null metrics array means all metrics. Null object array means all 10164 existing objects. 10165 </note> 10166 </desc> 10167 <param name="metricNames" type="wstring" dir="in" safearray="yes"/> 10168 <param name="objects" type="$unknown" dir="in" safearray="yes"/> 10169 <param name="period" type="unsigned long" dir="in"/> 10170 <param name="count" type="unsigned long" dir="in"/> 10171 </method> 10172 10173 <method name="enableMetrics"> 10174 <desc> 10175 Turn on collection of specified metrics. 10176 <note> 10177 Null metrics array means all metrics. Null object array means all 10178 existing objects. 10179 </note> 10180 </desc> 10181 <param name="metricNames" type="wstring" dir="in" safearray="yes"/> 10182 <param name="objects" type="$unknown" dir="in" safearray="yes"/> 10183 </method> 10184 10185 <method name="disableMetrics"> 10186 <desc> 10187 Turn off collection of specified metrics. 10188 <note> 10189 Null metrics array means all metrics. Null object array means all 10190 existing objects. 10191 </note> 10192 </desc> 10193 <param name="metricNames" type="wstring" dir="in" safearray="yes"/> 10194 <param name="objects" type="$unknown" dir="in" safearray="yes"/> 10195 </method> 10196 10197 <method name="queryMetricsData"> 10198 <desc> 10199 Queries collected metrics data for a set of objects. 10200 <note> 10201 Null metrics array means all applicable metrics. Null object array 10202 means all existing objects. The @a returnData parameter is a 10203 flattened array of arrays. Each start and length of a sub-array is 10204 indicated by @a returnDataIndices and @a returnDataLengths. The 10205 rationale behind this API style is that it doesn't require objects 10206 to be returned, and thus eliminates all but the unavoidable IPC. 10207 </note> 10208 </desc> 10209 <param name="metricNames" type="wstring" dir="in" safearray="yes"/> 10210 <param name="objects" type="$unknown" dir="in" safearray="yes"/> 10211 <param name="returnMetricNames" type="wstring" dir="out" safearray="yes"/> 10212 <param name="returnObjects" type="$unknown" dir="out" safearray="yes"/> 10213 <param name="returnDataIndices" type="unsigned long" dir="out" safearray="yes"/> 10214 <param name="returnDataLengths" type="unsigned long" dir="out" safearray="yes"/> 10215 <param name="returnData" type="long" dir="return" safearray="yes"/> 10216 </method> 10217 10218 </interface> 10219 10124 10220 <module name="VBoxSVC" context="LocalServer"> 10125 10221 <class name="VirtualBox" uuid="B1A7A4F2-47B9-4A1E-82B2-07CCD5323C3F" -
trunk/src/VBox/Main/include/HostImpl.h
r10423 r10528 36 36 # include "win/svchlp.h" 37 37 #endif 38 39 #ifdef VBOX_WITH_RESOURCE_USAGE_API40 #include "iprt/timer.h"41 #include "iprt/system.h"42 43 /* Each second we obtain new CPU load stats. */44 #define VBOX_USAGE_SAMPLER_INTERVAL 100045 #endif /* VBOX_WITH_RESOURCE_USAGE_API */46 47 38 48 39 class VirtualBox; … … 110 101 STDMETHOD(RemoveUSBDeviceFilter) (ULONG aPosition, IHostUSBDeviceFilter **aFilter); 111 102 112 STDMETHOD(GetProcessorUsage) (ULONG *aUser, ULONG *aSystem, ULONG *aIdle);113 114 103 // public methods only for internal purposes 115 104 … … 171 160 172 161 #ifdef VBOX_WITH_RESOURCE_USAGE_API 173 /** Static timer callback. */ 174 static void UsageSamplerCallback (PRTTIMER pTimer, void *pvUser, uint64_t iTick); 175 /** Member timer callback. */ 176 void usageSamplerCallback(); 162 void registerMetrics(PerformanceCollector *collector); 163 void unregisterMetrics(PerformanceCollector *collector); 177 164 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 178 165 … … 186 173 #endif /* VBOX_WITH_USB */ 187 174 188 #ifdef VBOX_WITH_RESOURCE_USAGE_API189 /** Pointer to the usage sampling timer. */190 PRTTIMER mUsageSampler;191 /** Structure to hold processor usage stats. */192 RTCPUUSAGESTATS mCpuStats;193 #endif /* VBOX_WITH_RESOURCE_USAGE_API */194 175 }; 195 176 -
trunk/src/VBox/Main/include/MachineImpl.h
r10000 r10528 39 39 #include "BIOSSettingsImpl.h" 40 40 #include "SATAControllerImpl.h" 41 #ifdef VBOX_WITH_RESOURCE_USAGE_API 42 #include "PerformanceImpl.h" 43 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 41 44 42 45 // generated header … … 48 51 #include <iprt/thread.h> 49 52 #include <iprt/time.h> 50 #ifdef VBOX_WITH_RESOURCE_USAGE_API51 #include <iprt/system.h>52 #include <iprt/timer.h>53 #endif /* VBOX_WITH_RESOURCE_USAGE_API */54 53 55 54 #include <list> … … 169 168 ComObjPtr <Snapshot> mCurrentSnapshot; 170 169 171 #ifdef VBOX_WITH_RESOURCE_USAGE_API172 /** Pointer to the usage sampling timer. */173 PRTTIMER mUsageSampler;174 /** Structure to hold processor usage stats. */175 RTPROCCPUUSAGESTATS mCpuStats;176 #endif /* VBOX_WITH_RESOURCE_USAGE_API */177 170 }; 178 171 … … 530 523 STDMETHOD(SetGuestProperty) (INPTR BSTR aKey, INPTR BSTR aValue); 531 524 532 STDMETHOD(GetProcessorUsage) (ULONG *user, ULONG *system);533 534 525 // public methods only for internal purposes 535 526 … … 721 712 722 713 #ifdef VBOX_WITH_RESOURCE_USAGE_API 723 /** Static timer callback. */ 724 static void UsageSamplerCallback (PRTTIMER pTimer, void *pvUser, uint64_t iTick); 725 /** Member timer callback. */ 726 void usageSamplerCallback(); 714 void registerMetrics(PerformanceCollector *collector); 715 void unregisterMetrics(PerformanceCollector *collector); 727 716 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 728 717 -
trunk/src/VBox/Main/include/VirtualBoxImpl.h
r10333 r10528 36 36 # include "win/resource.h" 37 37 #endif 38 39 #ifdef VBOX_WITH_RESOURCE_USAGE_API 40 #include "PerformanceImpl.h" 41 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 42 38 43 39 44 class Machine; … … 127 132 STDMETHOD(COMGETTER(GuestOSTypes)) (IGuestOSTypeCollection **aGuestOSTypes); 128 133 STDMETHOD(COMGETTER(SharedFolders)) (ISharedFolderCollection **aSharedFolders); 134 STDMETHOD(COMGETTER(PerformanceCollector)) (IPerformanceCollector **aPerformanceCollector); 129 135 130 136 /* IVirtualBox methods */ … … 345 351 static const wchar_t *getComponentName() { return L"VirtualBox"; } 346 352 353 #ifdef VBOX_WITH_RESOURCE_USAGE_API 354 PerformanceCollector *getCollector() { return mData.mPerformanceCollector; }; 355 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 356 347 357 private: 348 358 … … 414 424 const ComObjPtr <Host> mHost; 415 425 const ComObjPtr <SystemProperties> mSystemProperties; 426 #ifdef VBOX_WITH_RESOURCE_USAGE_API 427 const ComObjPtr <PerformanceCollector> mPerformanceCollector; 428 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 416 429 417 430 CfgFile mCfgFile; -
trunk/src/VBox/Main/testcase/tstAPI.cpp
r9911 r10528 920 920 921 921 #if 1 922 for (int i = 0; i < 10; i++) 923 { 922 { 923 Bstr metricNames[] = { L"CPU/User:avg,CPU/System:avg,CPU/Idle:avg" }; 924 com::SafeArray<BSTR> metrics(1); 925 metricNames[0].detachTo(&metrics[0]); 926 924 927 ComPtr <IHost> host; 925 928 CHECK_RC_BREAK (virtualBox->COMGETTER(Host) (host.asOutParam())); 929 ComPtr <IPerformanceCollector> collector; 930 CHECK_RC( virtualBox->COMGETTER(PerformanceCollector)(collector.asOutParam()) ); 931 932 com::SafeIfaceArray<IUnknown> objects(1); 933 host.queryInterfaceTo(&objects[0]); 934 collector->SetupMetrics(ComSafeArrayAsInParam(metrics), 935 ComSafeArrayAsInParam(objects), 1u, 10u); 936 RTThreadSleep(3000); /* Sleep 10 seconds. */ 937 /*com::SafeIfaceArray<IPerformanceData> result; 938 collector->QueryMetricsData(ComSafeArrayAsInParam(metrics), 939 ComSafeArrayAsInParam(objects), 940 ComSafeArrayAsOutParam(result)); 941 for (unsigned i = 0; i < result.size(); i++) 942 { 943 Bstr metricName; 944 result[i]->COMGETTER(MetricName) (metricName.asOutParam()); 945 com::SafeArray<LONG> values; 946 result[i]->COMGETTER(Values) (ComSafeArrayAsOutParam(values)); 947 printf("%ls", metricName.raw()); 948 for (unsigned j = 0; j < values.size(); j++) 949 { 950 printf(" %d\n", values[j]); 951 } 952 }*/ 953 } 954 #endif 955 #if 0 956 for (int i = 0; i < 10; i++) 957 { 926 958 ULONG user, system, idle; 927 959 host->GetProcessorUsage(&user, &system, &idle); 928 960 printf("user=%u system=%u idle=%u\n", user/10000000, system/10000000, idle/10000000); 929 RTThreadSleep(1000); 930 } 931 #endif 932 933 #if 1 961 } 962 #endif 963 964 #if 0 934 965 { 935 966 ComPtr <IMachine> machine; -
trunk/src/VBox/Main/xpcom/server.cpp
r9446 r10528 189 189 NS_DECL_CLASSINFO(SystemProperties) 190 190 NS_IMPL_THREADSAFE_ISUPPORTS1_CI(SystemProperties, ISystemProperties) 191 #ifdef VBOX_WITH_RESOURCE_USAGE_API 192 NS_DECL_CLASSINFO(PerformanceCollector) 193 NS_IMPL_THREADSAFE_ISUPPORTS1_CI(PerformanceCollector, IPerformanceCollector) 194 NS_DECL_CLASSINFO(PerformanceMetric) 195 NS_IMPL_THREADSAFE_ISUPPORTS1_CI(PerformanceMetric, IPerformanceMetric) 196 #endif /* VBOX_WITH_RESOURCE_USAGE_API */ 191 197 NS_DECL_CLASSINFO(BIOSSettings) 192 198 NS_IMPL_THREADSAFE_ISUPPORTS1_CI(BIOSSettings, IBIOSSettings) -
trunk/src/VBox/Runtime/r3/os2/system-os2.cpp
r9906 r10528 67 67 } 68 68 69 RTDECL(int) RTSystemProcessorGetUsageStats(PRTCPUUSAGESTATS pStats)70 {71 /* @todo Implement! */72 return VERR_NOT_IMPLEMENTED;73 }74 75 RTDECL(int) RTProcessGetProcessorUsageStats(RTPROCESS pid, PRTPROCCPUUSAGESTATS pStats)76 {77 /* @todo Implement! */78 return VERR_NOT_IMPLEMENTED;79 }80 -
trunk/src/VBox/Runtime/r3/posix/system-posix.cpp
r9935 r10528 92 92 } 93 93 94 /**95 * Gets the current figures of overall system processor usage.96 *97 * @remarks To get meaningful stats this function has to be98 * called twice with a bit of delay between calls. This99 * is due to the fact that at least two samples of100 * system usage stats are needed to calculate the load.101 *102 * @returns None.103 */104 RTDECL(int) RTSystemProcessorGetUsageStats(PRTCPUUSAGESTATS pStats)105 {106 /** @todo r=bird: This is Linux specific and doesn't belong here. Move this to r3/linux/RTSystemGetCpuLoadStats-linux.cpp. */107 int rc = VINF_SUCCESS;108 uint32_t u32UserNow, u32NiceNow, u32SystemNow, u32IdleNow;109 uint32_t u32UserDelta, u32SystemDelta, u32IdleDelta, u32BusyDelta, u32TotalDelta;110 FILE *f = fopen("/proc/stat", "r");111 112 if (f)113 {114 if (fscanf(f, "cpu %u %u %u %u", &u32UserNow, &u32NiceNow, &u32SystemNow, &u32IdleNow) == 4)115 {116 u32UserDelta = (u32UserNow - pStats->u32RawUser) + (u32NiceNow - pStats->u32RawNice);117 u32SystemDelta = u32SystemNow - pStats->u32RawSystem;118 u32IdleDelta = u32IdleNow - pStats->u32RawIdle;119 u32BusyDelta = u32UserDelta + u32SystemDelta;120 u32TotalDelta = u32BusyDelta + u32IdleDelta;121 pStats->u32User = (uint32_t)(IPRT_USAGE_MULTIPLIER * u32UserDelta / u32TotalDelta);122 pStats->u32System = (uint32_t)(IPRT_USAGE_MULTIPLIER * u32SystemDelta / u32TotalDelta);123 pStats->u32Idle = (uint32_t)(IPRT_USAGE_MULTIPLIER * u32IdleDelta / u32TotalDelta);124 /* Update the base. */125 pStats->u32RawUser = u32UserNow;126 pStats->u32RawNice = u32NiceNow;127 pStats->u32RawSystem = u32SystemNow;128 pStats->u32RawIdle = u32IdleNow;129 }130 else131 rc = VERR_FILE_IO_ERROR;132 fclose(f);133 }134 else135 rc = VERR_ACCESS_DENIED;136 137 return rc;138 }139 140 /**141 * Gets the current processor usage for a partucilar process.142 *143 * @remarks To get meaningful stats this function has to be144 * called twice with a bit of delay between calls. This145 * is due to the fact that at least two samples of146 * system usage stats are needed to calculate the load.147 *148 * @returns None.149 */150 RTDECL(int) RTProcessGetProcessorUsageStats(RTPROCESS pid, PRTPROCCPUUSAGESTATS pStats)151 {152 int rc = VINF_SUCCESS;153 uint32_t u32UserNow, u32NiceNow, u32SystemNow, u32IdleNow;154 uint32_t u32UserDelta, u32SystemDelta;155 uint64_t u64TotalNow, u64TotalDelta;156 157 /** @todo r=bird: This is Linux specific and doesn't belong here. Move this to r3/linux/RTSystemGetCpuLoadStats-linux.cpp. */158 FILE *f = fopen("/proc/stat", "r");159 160 if (f)161 {162 if (fscanf(f, "cpu %u %u %u %u", &u32UserNow, &u32NiceNow, &u32SystemNow, &u32IdleNow) == 4) /** @todo 'uint32_t' is not necessarily the same as 'unsigned int'. */163 {164 char *pszName;165 pid_t pid2;166 char c;167 int iTmp;168 unsigned uTmp;169 unsigned long ulTmp, ulUserNow, ulSystemNow;170 char buf[80]; /* @todo: this should be tied to max allowed proc name. */171 172 u64TotalNow = (uint64_t)u32UserNow + u32NiceNow + u32SystemNow + u32IdleNow;173 fclose(f);174 RTStrAPrintf(&pszName, "/proc/%d/stat", pid);175 //printf("Opening %s...\n", pszName);176 f = fopen(pszName, "r");177 RTMemFree(pszName);178 179 if (f)180 {181 if (fscanf(f, "%d %s %c %d %d %d %d %d %u %lu %lu %lu %lu %lu %lu",182 &pid2, buf, &c, &iTmp, &iTmp, &iTmp, &iTmp, &iTmp, &uTmp,183 &ulTmp, &ulTmp, &ulTmp, &ulTmp, &ulUserNow, &ulSystemNow) == 15)184 {185 Assert((pid_t)pid == pid2);186 u32UserDelta = ulUserNow - pStats->u32RawProcUser;187 u32SystemDelta = ulSystemNow - pStats->u32RawProcSystem;188 u64TotalDelta = u64TotalNow - pStats->u64RawTotal;189 pStats->u32User = (uint32_t)(IPRT_USAGE_MULTIPLIER * u32UserDelta / u64TotalDelta);190 pStats->u32System = (uint32_t)(IPRT_USAGE_MULTIPLIER * u32SystemDelta / u64TotalDelta);191 // printf("%d: user=%u%% system=%u%% / raw user=%u raw system=%u total delta=%u\n", pid,192 // pStats->u32User / 10000000, pStats->u32System / 10000000,193 // pStats->u32RawProcUser, pStats->u32RawProcSystem, u64TotalDelta);194 /* Update the base. */195 pStats->u32RawProcUser = ulUserNow;196 pStats->u32RawProcSystem = ulSystemNow;197 pStats->u64RawTotal = u64TotalNow;198 // printf("%d: updated raw user=%u raw system=%u raw total=%u\n", pid,199 // pStats->u32RawProcUser, pStats->u32RawProcSystem, pStats->u64RawTotal);200 }201 else202 rc = VERR_FILE_IO_ERROR;203 }204 else205 rc = VERR_ACCESS_DENIED;206 }207 else208 rc = VERR_FILE_IO_ERROR;209 fclose(f);210 }211 else212 rc = VERR_ACCESS_DENIED;213 214 return rc;215 } -
trunk/src/VBox/Runtime/r3/win/system-win.cpp
r9906 r10528 62 62 } 63 63 64 RTDECL(int) RTSystemProcessorGetUsageStats(PRTCPUUSAGESTATS pStats)65 {66 /* @todo Implement! */67 return VERR_NOT_IMPLEMENTED;68 }69 70 RTDECL(int) RTProcessGetProcessorUsageStats(RTPROCESS pid, PRTPROCCPUUSAGESTATS pStats)71 {72 /* @todo Implement! */73 return VERR_NOT_IMPLEMENTED;74 }75
Note:
See TracChangeset
for help on using the changeset viewer.