0

我有一个应用程序捕获(使用wireshark)数据包,我希望选择在我的表单上显示正在接收的数据包数量。

代码:

public class Tshark
{
    public int _interfaceNumber;
    public string _pcapPath;
    public int _packetsCount;
    public string _packet;
    public delegate void dlgPackProgress(int progress);
    public event dlgPackProgress evePacketProgress;

    public Tshark(int interfaceNumber, string pcapPath)
    {
        _interfaceNumber = interfaceNumber;
        _pcapPath = pcapPath;
    }

    public void startTheCapture()
    {
        Process _tsharkProcess1 = new Process();
        _tsharkProcess1.StartInfo.FileName = @"C:\Program Files\Wireshark\tshark.exe";
        _tsharkProcess1.StartInfo.Arguments = string.Format(" -i " + _interfaceNumber + " -V -x -w " + _pcapPath);
        //_tsharkProcess1.StartInfo.Arguments = string.Format(" -i " + _interfaceNumber + " -c " + int.MaxValue + " -w " + _pcapPath);
        _tsharkProcess1.OutputDataReceived += new DataReceivedEventHandler(process_OutputDataReceived);
        _tsharkProcess1.StartInfo.RedirectStandardOutput = true;
        _tsharkProcess1.StartInfo.UseShellExecute = false;
        _tsharkProcess1.StartInfo.CreateNoWindow = true;
        _tsharkProcess1.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
        _tsharkProcess1.Start();

        StreamReader myStreamReader = _tsharkProcess1.StandardOutput;

        while (!myStreamReader.EndOfStream)
        {
            _packet = myStreamReader.ReadLine();

            //if (_packet.StartsWith("Frame Number: "))
            //{
            //    string[] arr = _packet.Split(' ');
            //    _test = int.Parse(arr[2]);
            //    _packetsCount++;
            //}

            OnPacketProgress(_packetsCount++);
        }

        _tsharkProcess1.WaitForExit();
    }

    private void OnPacketProgress(int packet)
    {
        var handler = evePacketProgress;
        if (handler != null)
        {
            handler(packet);
        }
    }

    public void killProcess()
    {
        foreach (Process prc in System.Diagnostics.Process.GetProcessesByName("tshark"))
        {
            prc.Kill();
            prc.WaitForExit();
        }
    }

    private void process_OutputDataReceived(object sender, DataReceivedEventArgs arg)
    {
        string srt = arg.Data; //arg.Data contains the output data from the process...            
    }
}

这个类启动 Tshark 并从主窗体开始捕获我有这个 ProgressChanged,它对类属性进行采样,以便在我的窗体上显示数据包编号,问题是,例如,如果我的网络上有很高的速度(BitTorrent 下载)我的表格卡住了,也许我可以通过每隔几秒钟对类属性进行采样来解决这个问题?

private void bgWSniffer_ProgressChanged(object sender, ProgressChangedEventArgs e)
{
    tshark = e.UserState as Tshark;
    lbl.Text = tshark._packetsCount.ToString();
    lbl.Text = tshark._packet;
}

我知道有问题的行是 OnPacketProgress(_packetsCount++);

我开始捕获的开始按钮:

private void btnStartCapture_Click(object sender, EventArgs e)
{
    lblStatusSnifferTab2.Text = "Listening on ip address " + lblIpAddressSnifferTab2.Text;
    timerSniffer.Start();
    btnStartTabSniffer.Enabled = false;
    btnStopTabSniffer.Enabled = true;
    groupBoxSelectTabSniffer.Enabled = false;
    groupBoxOptionsSnifferTab.Enabled = false;
    groupBoxCaptureFilesTabSniffer.Enabled = false;
    groupBoxStopCaptureSnifferTab.Enabled = false;
    bgWorker = new BackgroundWorker();
    bgWorker.WorkerReportsProgress = true;
    bgWorker.ProgressChanged += new ProgressChangedEventHandler(bgWSniffer_ProgressChanged);
    bgWorker.DoWork += new DoWorkEventHandler(
        (s3, e3) =>
        {
            tshark = new Tshark(2, pcapFilePathSniffer);                    

            tshark.evePacketProgress += new Tshark.dlgPackProgress(
                (packet) =>
                {
                    bgWorker.ReportProgress(packet, tshark);
                });

            tshark.startTheCapture();
        });

    bgWorker.RunWorkerCompleted += new RunWorkerCompletedEventHandler(
        (s3, e3) =>
        {
            groupBoxSelectTabSniffer.Enabled = true;
            groupBoxCaptureFilesTabSniffer.Enabled = true;
        });

    bgWorker.RunWorkerAsync();
}
4

1 回答 1

1

一种解决方案是(使用毫秒,以便您可以进行精细控制,如果您想要的只是秒,您可以使用 TotalSeconds):

    DateTime lastUpdate = DateTime.MinValue;

    while (!myStreamReader.EndOfStream)
    {
        _packet = myStreamReader.ReadLine();

        //if (_packet.StartsWith("Frame Number: "))
        //{
        //    string[] arr = _packet.Split(' ');
        //    _test = int.Parse(arr[2]);
        //    _packetsCount++;
        //}

        // If more than one second
        if((DateTime.Now - lastUpdate).TotalMilliseconds > 1000)
        {
            lastUpdate = DateTime.Now;
            OnPacketProgress(_packetsCount++);
        }
    }

另外,我注意到的另一件事是,您在调用 OnPacketProgress 时使用后增量。这将传递 _packetsCount 的当前值,然后在 OnPacketProgress 返回后将其递增。你应该仔细检查这是否是你想要的。

于 2012-09-28T15:03:33.753 回答