Мне нужно найти способ измерить процент использования ОЗУ и ЦП (как отображается в диспетчере задач, несмотря на его неточности) в существующей системе. Метод, который я выбрал до сих пор, заключался в использовании команд CMD и Powershell из C# для получения этой информации.
Ниже приведены команды, сохраненные в файле ps1, который я использую для сбора всех необходимых мне переменных:
$mem = cmd.exe /c 'wmic ComputerSystem get TotalPhysicalMemory && wmic OS get FreePhysicalMemory';
$loadpc = cmd.exe /c 'wmic cpu get loadpercentage';
$maxclock = cmd.exe /c 'wmic cpu get maxclockspeed';
$cpuperf = (Get-Counter -Counter '\Processor Information(_Total)\% Processor Performance').CounterSamples.CookedValue;
$mem,$loadpc,$maxclock,$cpuperf
Это возвращает общую установленную память, общую доступную свободную память, процент загрузки ЦП, базовую тактовую частоту и производительность ЦП. Я использую эти числа для расчета использования ОЗУ и ЦП.
Файл .ps1 сохраняется в пути UNC, и я запускаю его на удаленных ПК, используя следующий код:
private static List<double> GetResourceUsages(string hostname)
{
string output = (LaunchProcess("powershell.exe", "-command Invoke-Command -ComputerName " + hostname + " -FilePath '<path>\\GetResources.ps1'"));
output = RemoveSubstrings(new List<string>() { "TotalPhysicalMemory", "FreePhysicalMemory", "LoadPercentage", "-", "MaxClockSpeed", " " }, output);
List<string> list = output.Split("\r\n").ToList();
for (int i = 0; i < list.Count; i++)
{
if (list[i].Length == 0)
{
list.RemoveAt(i);
i--;
}
}
long.TryParse(list[0], out long MaxRAM);
long.TryParse(list[1], out long AvailableRAM);
double RAMUsage = (double)100 - ((double)AvailableRAM / (((double)MaxRAM) / 1024) * (double)100);
Double.TryParse(list[2], out double loadPC);
Double.TryParse(list[3], out double baseClock);
Double.TryParse(list[4], out double perfPC);
double CurrentCPUClock = (perfPC / 100) * baseClock;
double CPUUtilization = loadPC / ((baseClock / CurrentCPUClock) * 100) * 100;
return new List<double>() { RAMUsage, CPUUtilization };
}
Кажется, это работает хорошо. Это позволяет мне точно рассчитать использование ОЗУ, а использование ЦП соответствует Диспетчеру задач, однако это неточно.
Теперь проблема в том, что, поскольку скрипт ps1 выполняется удаленно, загрузка ЦП удаленного ПК резко возрастает: Диспетчер задач чтение процессора
Причина, по которой я не использую PerformanceCounter
, заключается в том, что для того, чтобы рассчитать процент использования ЦП, отображаемый в диспетчере задач, на основе того, что я узнал, мне нужно немного повозиться с числами, некоторые из которых включают в себя получение Производительность процессора. Мне не удалось найти способ получить это число с помощью PerformanceCounter.
В любом случае, этот метод в настоящее время слишком сильно влияет на производительность, чтобы быть жизнеспособным. Есть ли другой способ измерить производительность ЦП, отображаемую в диспетчере задач, или я ограничен WMI?
Клептус, абсолютно верно! Файл ps сохраняется в папке, доступ к которой есть только у определенной учетной записи, и приложение может использоваться только под этой учетной записью - никакая другая учетная запись в домене или вне не имеет к нему доступа. Спасибо за указание на это, я должен был включить это!
С самого начала большое количество вычислительной мощности и мощности ввода-вывода будет потрачено на создание и уничтожение интерпретаторов команд, а также на загрузку, запуск и выгрузку wmic
снова и снова.
Вы можете тривиально выполнить всю свою логику в одном процессе либо с помощью одного скрипта PS (который поддерживает запросы WMI из коробки, и вы, похоже, все равно его используете), либо написав свой собственный исполняемый файл, который выполняет запросы и сбор данных.
Кроме того, существуют гораздо лучшие способы отправки и получения данных между компьютерами, чем создание удаленных процессов и анализ их текстовых выходных данных, таких как конвейеры или сокеты. Сокет UDP на много порядков эффективнее того, что вы там настроили.
Вы можете использовать PerformanceCounter для запроса необходимой информации (хотя иногда это может быть немного сложно).
Я думаю, что это чище, чем запуск скрипта power-shell и т. д.
Код, выполняющий эту выборку ресурсов, может выполняться в отдельном exe-файле и взаимодействовать с вашим основным через сокеты tcp/ip.
Вы упомянули, что не использовали PerformanceCounter
, потому что «мне нужно немного повозиться с числами».
Задача с PerformanceCounter
состоит в том, чтобы найти название нужной категории и счетчика (а иногда и имя экземпляра).
Следующий код демонстрирует загрузку ЦП (%) и доступную оперативную память (в МБ). Есть еще много счетчиков. Если вы запустите приложение Windows «Монитор производительности», вы сможете легко увидеть доступные счетчики (их много).
Я использовал следующее:
ЦП: категория: «Информация о процессоре», счетчик: «% использования процессора», экземпляр: _ «Всего».
ОЗУ: категория: "Память", счетчик: "Доступно МБ".
В моей системе он сообщает значения, соответствующие диспетчеру задач.
using System;
using System.Diagnostics;
using System.Threading;
public class Program
{
public static void Main(String[] args)
{
var cpuCounter = new PerformanceCounter("Processor Information", "% Processor Utility", "_Total");
var ramCounter = new PerformanceCounter("Memory", "Available MBytes");
while (true)
{
Thread.Sleep(1000);
double cpuSample = cpuCounter.NextValue();
double ramSample = ramCounter.NextValue();
Console.WriteLine("CPU utilization (%):" + cpuSample + ", Available RAM (MB): " + ramSample);
}
}
}
Это работает очень хорошо! Спасибо вам за это! Раньше, когда я пытался использовать PerformanceCounters, я всегда получал ошибку «Сетевой путь не найден», которую я не мог решить после нескольких часов поиска в Google, и после попытки вашего кода я получил ту же ошибку, но 1 Google теперь поиск нашел решение этой проблемы... Служба удаленного реестра должна быть включена и запущена. Еще раз спасибо!
С точки зрения безопасности вы должны быть очень осторожны с этим
.ps
расположением / разрешениями файла, иначе вы можете заразить свою сеть. Представьте, что кто-то меняет файл.ps
на злой... Это может быть весело.