Im trying to implement a performance monitoring tool, I want to monitor basic things such as Memory and CPU.
I am attempting to do so by using Performance Counters as I believe this is what Task Manager is using behind the scenes too. I have no idea how Task Manager is able to do this however as to me it seems to take a VERY long time to retrieve process data using this method:
class Program
{
static void Main(string[] args)
{
while (true)
{
var pcs = Process.GetProcesses()
.Select(p => new PerformanceCounter("Process", "Working Set - Private", p.ProcessName));
var sw = Stopwatch.StartNew();
foreach (var pc in pcs)
pc.NextValue();
Console.WriteLine($"Time taken to read {pcs.Count()} performance counters: {sw.ElapsedMilliseconds}ms");
Thread.Sleep(1000);
}
}
}
Has anyone got any suggestions on how to do this or how even Task Manager or Process Explorer is able to do this?
he used calls to
ZwQuerySystemInformation
,ZwQueryInformationProcess
,ZwQueryInformationThread
.. Task Manager maintain database of active processes and periodically update this info by callingZwQuerySystemInformation(SystemProcessInformation,)
- so got array ofSYSTEM_PROCESS_INFORMATION
on exit. add new entries if found new process, yet not inDB
, remove entries for died processes, update info for livedSYSTEM_PROCESS_INFORMATION
already containing a lot information of process. additional information can be get by open process and callZwQueryInformationProcess
with appropriate info classif you want implement a performance monitoring tool, without "quantum effect" (when the measurement affects the state itself) you need use this ntdll api. for definitions look at http://processhacker.sourceforge.net/doc/ntexapi_8h_source.html despite this is undocumented, existing functions and structures not changed how minimum from win2000 (so ~17 years) - new version of windows add a lot new info classes, some fields which was spare/unused in old version - can become used, but old(legacy) not changed