这是本科时候的一个课程设计,要求调用Log Parser的dll实现图形界面分析Network Monitor 的抓包文件,编程语言是c#。
Log Parser 是微软的一款日志分析工具,可以支持很多格式的输入输出,但只提供命令行界面。本文采用的是Log Parser 2.2,百度可以下载,安装到c盘不然可能会出现问题,本身也才2M不大。Log Parser提供一种类似与SQL语句的查询语言,对日志文件进行分析,输出想要的结果。下图是命令行模式下的操作,可以看到查询语句基本类似与SQL,说明文档里有非常详细的操作说明,支持格式说明以及COM调用说明。IP地址在WIN7下显示有问题:
图1:
在Log Parser的说明文档里有关于支持格式的各字段描述,可以方便使用者了解所分析文件的结构。本文将以network monitor的抓包文件.cap文件作为分析对象。
图2:
使用vs2010开发,建立一个c#窗体应用工程,
图3:
然后在解决方案浏览器右键引用,添加引用,然后选择浏览,浏览LogParser2.2的安装目录下的LogParser.dll,添加引用。
图4:
然后在窗体上添加一个Button控件,一个DataGridView空间和一个Chart空间
图5:
然后进行代码编写:
代码:
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Windows.Forms.DataVisualization.Charting; //新添加
namespace LogParserTest
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
//文件操作
OpenFileDialog file1 = new OpenFileDialog(); //定义新的文件打开位置控件
file1.Filter = "Netmon抓包文件|*.cap";
if (file1.ShowDialog() == DialogResult.OK)
{
string sql = @"SELECT Frame,FrameBytes,DateTime,SrcIP,SrcPort ,DstIP,DstPort,
FrameBytes,SrcMac,DstMac,IPVersion,TCPFlags,PayloadBytes FROM " + file1.FileName; //完整的查询语句
DataTable dt = OpenLog(sql);
//对表中载荷单位进行处理
for (int i = 0; i < dt.Rows.Count; i++)
{
double temppayloadbyte = double.Parse(dt.Rows[i]["有效载荷大小"].ToString());
double tempframebyte = int.Parse(dt.Rows[i]["帧大小"].ToString());
dt.Rows[i]["有效载荷大小"] = (temppayloadbyte / 1024).ToString("0.00") + "KB";
dt.Rows[i]["帧大小"] = (tempframebyte / 1024).ToString("0.00") + "KB";
}
//绑定数据源,实现表格显示
dataGridView1.DataSource = dt;
//计算流量实现流量统计
string TimeSql = @"SELECT QUANTIZE(DateTime, 1) AS Second, SUM(FrameBytes) AS FrameNum FROM "+ file1.FileName +" GROUP BY Second";
DataTable dt2 = TimeFromLog(TimeSql);
//将dt2中帧字节数转为KB
for (int i = 0; i < dt2.Rows.Count; i++)
{
//string CovStr = dt4.Rows[i]["流量"].ToString(); //获得美秒字节数
Int32 CovInt = Int32.Parse(dt2.Rows[i]["流量"].ToString());
CovInt /= 1024; //单位转为KB
dt2.Rows[i]["流量"] = CovInt.ToString();
}
// Set series chart type
chart1.Series[0].ChartType = SeriesChartType.Line;
// Show as 3D
chart1.ChartAreas[0].Area3DStyle.Enable3D = false;
// Draw as 3D Cylinder
//chart3.Series[0]["DrawingStyle"] = "Cylinder";
//chart1.BackColor = Color.Azure; //图表背景色
//chart1.Titles.Add("IP协议分布"); //图表标题
//设置图表的数据源
chart1.DataSource = dt2;
//设置图表Y轴对应项
chart1.Series[0].YValueMembers = "流量";
//Chart1.Series[1].YValueMembers = "Volume2";
//设置图表X轴对应项
chart1.Series[0].XValueMember = "时间";
chart1.Series[0].IsValueShownAsLabel = false; //是否显示数据
chart1.Series[0].IsVisibleInLegend = false; //是否显示数据说明
chart1.Series[0].MarkerStyle = MarkerStyle.Circle; //线条上的数据点标志类型
chart1.Series[0].MarkerSize = 0; //标志大小
chart1.ChartAreas[0].AxisX.LineColor = Color.Red; //X 轴颜色
chart1.ChartAreas[0].AxisY.LineColor = Color.Red; //Y 轴颜色
chart1.ChartAreas[0].AxisX.LineWidth = 2; //X 轴宽度
chart1.ChartAreas[0].AxisY.LineWidth = 2; //Y 轴宽度
chart1.ChartAreas[0].AxisY.Title = "流量 KB"; //Y 轴标题
chart1.ChartAreas[0].AxisX.Title = "时间"; //X 轴标题
chart1.ChartAreas[0].CursorX.IsUserEnabled = true;//启用x轴游标
chart1.ChartAreas[0].CursorX.IsUserSelectionEnabled = true;
chart1.ChartAreas[0].CursorY.IsUserEnabled = true;//启用y轴游标
chart1.ChartAreas[0].CursorY.IsUserSelectionEnabled = true;
//绑定数据
chart1.DataBind();
}
}
public DataTable OpenLog(string sql)
{
try
{
DataTable datat = new DataTable();
datat.Columns.Add("帧号", typeof(string));
datat.Columns.Add("时间", typeof(string));
datat.Columns.Add("源Mac", typeof(string));
datat.Columns.Add("源地址", typeof(string));
datat.Columns.Add("源端口", typeof(string));
datat.Columns.Add("目标地址", typeof(string));
datat.Columns.Add("目标Mac", typeof(string));
datat.Columns.Add("目标端口", typeof(string));
datat.Columns.Add("IP版本", typeof(string));
datat.Columns.Add("TCP Flags", typeof(string));
datat.Columns.Add("帧大小", typeof(string));
datat.Columns.Add("有效载荷大小", typeof(string));
// Instantiate the LogQuery object
MSUtil.ILogQuery oLogQuery = new MSUtil.LogQueryClass();
// Instantiate the Netmon Input Format object
MSUtil.ICOMNetMonInputContext oEvtInputFormat = new MSUtil.COMNetMonInputContextClass();
oEvtInputFormat.fMode = "TCPIP"; //这是netmon输入格式的模式之一,LogParser说明文档有详细介绍
oEvtInputFormat.binaryFormat = "ASC";
// Create the query
string query = sql;
// Execute the query
//object o=null;
MSUtil.ILogRecordset oRecordSet = oLogQuery.Execute(query, oEvtInputFormat); //oEvtInputFormat
while (!oRecordSet.atEnd())
{
var itemData = oRecordSet.getRecord();
DataRow dr = datat.NewRow();
dr["帧号"] = itemData.getValue("Frame").ToString();
dr["时间"] = itemData.getValue("DateTime").ToString();
dr["源端口"] = itemData.getValue("SrcPort").ToString();
dr["源Mac"] = itemData.getValue("SrcMAC").ToString();
dr["源地址"] = itemData.getValue("SrcIP").ToString();
dr["目标地址"] = itemData.getValue("DstIP").ToString();
dr["目标端口"] = itemData.getValue("DstPort").ToString();
dr["目标Mac"] = itemData.getValue("DstMAC").ToString();
dr["IP版本"] = itemData.getValue("IPVersion").ToString();
dr["TCP Flags"] = itemData.getValue("TCPFlags").ToString();
dr["帧大小"] = itemData.getValue("FrameBytes").ToString();
dr["有效载荷大小"] = itemData.getValue("PayloadBytes").ToString();
datat.Rows.Add(dr);
oRecordSet.moveNext();
}
// Close the recordset
oRecordSet.close();
return datat;
}
catch (System.Runtime.InteropServices.COMException exc)
{
MessageBox.Show("Unexpected error: " + exc.Message);
return null;
}
}
public DataTable TimeFromLog(string sql)
{
try
{
DataTable datat = new DataTable();
datat.Columns.Add("时间", typeof(string));
datat.Columns.Add("流量", typeof(string));
// Instantiate the LogQuery object
MSUtil.ILogQuery oLogQuery = new MSUtil.LogQueryClass();
// Instantiate the Netmon Input Format object
MSUtil.ICOMNetMonInputContext oEvtInputFormat = new MSUtil.COMNetMonInputContextClass();
oEvtInputFormat.fMode = "TCPIP";
oEvtInputFormat.binaryFormat = "ASC";
// Create the query
string query = sql;
// Execute the query
//object o=null;
MSUtil.ILogRecordset oRecordSet = oLogQuery.Execute(query, oEvtInputFormat); //oEvtInputFormat
while (!oRecordSet.atEnd())
{
var itemData = oRecordSet.getRecord();
DataRow dr = datat.NewRow();
dr["时间"] = itemData.getValue("Second").ToString();
dr["流量"] = itemData.getValue("FrameNum").ToString();
datat.Rows.Add(dr);
oRecordSet.moveNext();
}
// Close the recordset
oRecordSet.close();
return datat;
}
catch (System.Runtime.InteropServices.COMException exc)
{
MessageBox.Show("Unexpected error: " + exc.Message);
return null;
}
}
}
}
运行结果如下图。经验证,IP地址无论是命令行还是COM调用都无法在WIN7、win8、win10显示,XP显示正常。支持netmon3.2,3.3,3.4以及MMA的.cap文件,wireshark的文件未验证:
图6: