2011-10-03 11 views
7

Hola, estoy tratando de crear un contador de rendimiento personalizado para usar en perfmon. El siguiente código funciona bastante bien, sin embargo tengo un problema ...contador de rendimiento personalizado en C#/perfmon

Con esta solución tengo un temporizador actualizando el valor del contador de rendimiento, sin embargo, me gustaría no tener que ejecutar este ejecutable para obtener los datos que necesito . Es decir, me gustaría simplemente poder instalar el contador como algo único y luego tener una consulta de perfmon para los datos (como lo hace con todos los contadores preinstalados).

¿Cómo puedo lograrlo?

using System; 
using System.Diagnostics; 
using System.Net.NetworkInformation; 

namespace PerfCounter 
{ 
class PerfCounter 
{ 
    private const String categoryName = "Custom category"; 
    private const String counterName = "Total bytes received"; 
    private const String categoryHelp = "A category for custom performance counters"; 
    private const String counterHelp = "Total bytes received on network interface"; 
    private const String lanName = "Local Area Connection"; // change this to match your network connection 
    private const int sampleRateInMillis = 1000; 
    private const int numberofSamples = 100; 

    private static NetworkInterface lan = null; 
    private static PerformanceCounter perfCounter; 

    static void Main(string[] args) 
    { 
     setupLAN(); 
     setupCategory(); 
     createCounters(); 
     updatePerfCounters(); 
    } 

    private static void setupCategory() 
    { 
     if (!PerformanceCounterCategory.Exists(categoryName)) 
     { 
      CounterCreationDataCollection counterCreationDataCollection = new CounterCreationDataCollection(); 
      CounterCreationData totalBytesReceived = new CounterCreationData(); 
      totalBytesReceived.CounterType = PerformanceCounterType.NumberOfItems64; 
      totalBytesReceived.CounterName = counterName; 
      counterCreationDataCollection.Add(totalBytesReceived); 
      PerformanceCounterCategory.Create(categoryName, categoryHelp, PerformanceCounterCategoryType.MultiInstance, counterCreationDataCollection); 
     } 
     else 
      Console.WriteLine("Category {0} exists", categoryName); 
    } 

    private static void createCounters() { 
     perfCounter = new PerformanceCounter(categoryName, counterName, false); 
     perfCounter.RawValue = getTotalBytesReceived(); 
    } 

    private static long getTotalBytesReceived() 
    { 
     return lan.GetIPv4Statistics().BytesReceived; 
    } 

    private static void setupLAN() 
    { 
     NetworkInterface[] interfaces = NetworkInterface.GetAllNetworkInterfaces(); 
     foreach (NetworkInterface networkInterface in interfaces) 
     { 
      if (networkInterface.Name.Equals(lanName)) 
       lan = networkInterface; 
     } 
    } 
    private static void updatePerfCounters() 
    { 
     for (int i = 0; i < numberofSamples; i++) 
     { 
      perfCounter.RawValue = getTotalBytesReceived(); 
      Console.WriteLine("perfCounter.RawValue = {0}", perfCounter.RawValue); 
      System.Threading.Thread.Sleep(sampleRateInMillis); 
     } 
    } 
} 

}

Respuesta

6

En Win32, contadores de rendimiento en el trabajo por tener PerfMon cargar una DLL que proporciona los valores de contador.

En .NET, este archivo DLL es un apéndice que utiliza la memoria compartida para comunicarse con un proceso .NET en ejecución. El proceso periódicamente envía nuevos valores al bloque de memoria compartida y el DLL los pone a disposición como contadores de rendimiento.

Así que, básicamente, probablemente tenga que implementar su DLL de contador de rendimiento en código nativo, porque los contadores de rendimiento de .NET suponen que hay un proceso en ejecución.

Cuestiones relacionadas