2013-06-10 26 views
12

Jak mogę uzyskać proces wysyłania/odbierania bajtów? preferowany sposób robi to za pomocą C#.Odzyskaj wykorzystanie sieci procesowej

Szukałem tego bardzo często i nie znalazłem żadnego prostego rozwiązania. Niektóre rozwiązania sugerowały instalację WinPCap na komputerze i pracę z tą biblioteką.

Tak jak ten gość zapytał: Need "Processes with Network Activity" functionality in managed code - Like resmon.exe does it Nie chcę, żeby narzut lib.

Czy istnieje proste rozwiązanie tego problemu? Właściwie chcę dokładnie te dane, które daje Monitor zasobów systemu Windows w zakładce "Procesy z aktywnością sieciową": enter image description here

W jaki sposób Monitor zasobów systemu Windows otrzymuje te informacje? Dowolny przykład?

Próbowano również użyć metody licznika wymienionej tutaj: Missing network sent/received , ale bez powodzenia - ponieważ nie każdy proces jest wyświetlany pod tym licznikiem. I znowu zastanawiam się, w jaki sposób Monitor zasobów otrzymuje tę informację, nawet bez użycia tego licznika ...

+1

Czy nie uważają Państwo odebrać w licznik wydajności? http://www.codeproject.com/Articles/8590/An-Introduction-To-Performance-Counters – Yogee

+0

Próbowałem pracować z wydajnością, ale bez powodzenia - nawet przeczytałem dodany link. –

+1

http://stackoverflow.com/questions/438240/monitor-a-processs-network-usage –

Odpowiedz

2

Można użyć PerformanceCounter. Przykładowy kod:

//Define 
string pn = "MyProcessName.exe"; 
var readOpSec = new PerformanceCounter("Process","IO Read Operations/sec", pn); 
var writeOpSec = new PerformanceCounter("Process","IO Write Operations/sec", pn); 
var dataOpSec = new PerformanceCounter("Process","IO Data Operations/sec", pn); 
var readBytesSec = new PerformanceCounter("Process","IO Read Bytes/sec", pn); 
var writeByteSec = new PerformanceCounter("Process","IO Write Bytes/sec", pn); 
var dataBytesSec = new PerformanceCounter("Process","IO Data Bytes/sec", pn); 

var counters = new List<PerformanceCounter> 
       { 
       readOpSec, 
       writeOpSec, 
       dataOpSec, 
       readBytesSec, 
       writeByteSec, 
       dataBytesSec 
       }; 

// get current value 
foreach (PerformanceCounter counter in counters) 
{ 
    float rawValue = counter.NextValue(); 

    // display the value 
} 

I to jest dostać liczników wydajności dla karty sieciowej. Zauważ, że nie jest proces specyficzny

string cn = "get connection string from WMI"; 

var networkBytesSent = new PerformanceCounter("Network Interface", "Bytes Sent/sec", cn); 
var networkBytesReceived = new PerformanceCounter("Network Interface", "Bytes Received/sec", cn); 
var networkBytesTotal = new PerformanceCounter("Network Interface", "Bytes Total/sec", cn); 

Counters.Add(networkBytesSent); 
Counters.Add(networkBytesReceived); 
Counters.Add(networkBytesTotal); 
+0

Ale chcę tylko aktywność sieci bez operacji we/wy urządzenia. "Operacje odczytu operacji na sekundę/s" - pokazuje szybkość incydentów na sekundę, podczas których proces wydał operacje odczytu/zapisu, zlicza wszystkie operacje we/wy generowane przez proces, w tym operacje wejścia/wyjścia pliku, sieci i urządzenia. " –

+0

Nie ma innej natywnej metody (chyba, że ​​korzystasz z bibliotek trzeciej strony), aby wykonać czystą kartę sieciową związaną z pojedynczym procesem. To, co zrobiłem, to monitorowanie procesu IO, a także IO karty sieciowej. Później jednak nie jest to specyficzne dla procesu - tzn. Gromadzi wszystkie liczniki IO niezależnie od procesu. Będę edytować kod, aby pokazać liczniki kart sieciowych. – oleksii

+1

Dziękuję za rozwiązanie, ale jest to jedno z rozwiązań, które już znalazłem i nie spełnia ono mojego celu - a mianowicie uzyskanie tylko użycia sieci procesowej. Szukam innego sposobu, na przykład Monitor zasobów systemu Windows pobiera te informacje ... –

2

Resource Monitor wykorzystuje ETW - na szczęście, Microsoft stworzył piękny nuget .net wrapper aby łatwiej korzystać.

napisałem coś takiego niedawno zgłosić powrotem sieć mój proces Io:

using System; 
using System.Diagnostics; 
using System.Threading.Tasks; 
using Microsoft.Diagnostics.Tracing.Parsers; 
using Microsoft.Diagnostics.Tracing.Session; 

namespace ProcessMonitoring 
{ 
    public sealed class NetworkPerformanceReporter : IDisposable 
    { 
     private DateTime m_EtwStartTime; 
     private TraceEventSession m_EtwSession; 

     private readonly Counters m_Counters = new Counters(); 

     private class Counters 
     { 
      public long Received; 
      public long Sent; 
     } 

     private NetworkPerformanceReporter() { } 

     public static NetworkPerformanceReporter Create() 
     { 
      var networkPerformancePresenter = new NetworkPerformanceReporter(); 
      networkPerformancePresenter.Initialise(); 
      return networkPerformancePresenter; 
     } 

     private void Initialise() 
     { 
      // Note that the ETW class blocks processing messages, so should be run on a different thread if you want the application to remain responsive. 
      Task.Run(() => StartEtwSession()); 
     } 

     private void StartEtwSession() 
     { 
      try 
      { 
       var processId = Process.GetCurrentProcess().Id; 
       ResetCounters(); 

       using (m_EtwSession = new TraceEventSession("MyKernelAndClrEventsSession")) 
       { 
        m_EtwSession.EnableKernelProvider(KernelTraceEventParser.Keywords.NetworkTCPIP); 

        m_EtwSession.Source.Kernel.TcpIpRecv += data => 
        { 
         if (data.ProcessID == processId) 
         { 
          lock (m_Counters) 
          { 
           m_Counters.Received += data.size; 
          } 
         } 
        }; 

        m_EtwSession.Source.Kernel.TcpIpSend += data => 
        { 
         if (data.ProcessID == processId) 
         { 
          lock (m_Counters) 
          { 
           m_Counters.Sent += data.size; 
          } 
         } 
        }; 

        m_EtwSession.Source.Process(); 
       } 
      } 
      catch 
      { 
       ResetCounters(); // Stop reporting figures 
       // Probably should log the exception 
      } 
     } 

     public NetworkPerformanceData GetNetworkPerformanceData() 
     { 
      var timeDifferenceInSeconds = (DateTime.Now - m_EtwStartTime).TotalSeconds; 

      NetworkPerformanceData networkData; 

      lock (m_Counters) 
      { 
       networkData = new NetworkPerformanceData 
       { 
        BytesReceived = Convert.ToInt64(m_Counters.Received/timeDifferenceInSeconds), 
        BytesSent = Convert.ToInt64(m_Counters.Sent/timeDifferenceInSeconds) 
       }; 

      } 

      // Reset the counters to get a fresh reading for next time this is called. 
      ResetCounters(); 

      return networkData; 
     } 

     private void ResetCounters() 
     { 
      lock (m_Counters) 
      { 
       m_Counters.Sent = 0; 
       m_Counters.Received = 0; 
      } 
      m_EtwStartTime = DateTime.Now; 
     } 

     public void Dispose() 
     { 
      m_EtwSession?.Dispose(); 
     } 
    } 

    public sealed class NetworkPerformanceData 
    { 
     public long BytesReceived { get; set; } 
     public long BytesSent { get; set; } 
    } 
} 
+0

Czy to musi być wykonane pod kontrolą administratora? Otrzymuję wyjątek 'System.UnauthorizedAccessException' z metody' EnableKernelProvider'. –

+0

Tak, potrzebne są uprawnienia administratora. – Kram