如何用rawsocket接收tcp数据包
我是个初学者,对网络编程比较感兴趣,我想用c#rawsocket方式监视进出网卡的tcp数据包,想了解tcp包里面的内容,请各位高手老师给个实现的思路和实现的方法。
------解决方案--------------------tcp数据包应该有头的,也就是说一个包的开始几个Byte应该把它所在的这个包的大小和起始终了都描述清楚. 如果没有这个头,包之间就很难分开了.    
 头的定义最简单的方法是: 最开始两个Byte定义为包开始的特征字,比如00,然后规定若干位,比如4表示整个包的长度.   
 通常的手法是把每次得到的byte[] 放到加到一个缓存里,比如一个List <byte> , 然后靠每个包的头把各个包拆出来.   
------解决方案--------------------//This file contains the RawSocket class.  The goal of this class is to have a generic packet 
 //sniffing kind of class that fires events when an incoming IP packet is received.  The event 
 //gives the user access to everything contained in the IP packet and hopefully makes creating 
 //your own packet sniffer quite easy.  The event args returned with the event give the user of 
 //the class access to things like the from and to IP address, ports, protocol, etc. and even the 
 //contents of the message in the form of a byte array.   
 /****************************************** 
  *  Fixed Some Problem 
  *  Modify By Red_angelX  
  *  Build 2007.4.24 
  *****************************************/     
 namespace QQFamilyAnalytics 
 { 
 	using System; 
 	using System.Net; 
 	using System.Net.Sockets; 
 	using System.Runtime.InteropServices; 
 	using System.Windows.Forms;  	 
 	[StructLayout(LayoutKind.Explicit)] 
 	public struct IPHeader 
 	{ 
 		[FieldOffset(0)] public byte    ip_verlen; //IP version and IP Header length Combined 
 		[FieldOffset(1)] public byte    ip_tos; //Type of Service 
 		[FieldOffset(2)] public ushort  ip_totallength; //Total Packet Length 
 		[FieldOffset(4)] public ushort  ip_id; //Unique ID 
 		[FieldOffset(6)] public ushort  ip_offset; //Flags and Offset 
 		[FieldOffset(8)] public byte    ip_ttl; //Time To Live 
 		[FieldOffset(9)] public byte    ip_protocol; //Protocol (TCP, UDP, ICMP, Etc.) 
 		[FieldOffset(10)] public ushort ip_checksum; //IP Header Checksum 
 		[FieldOffset(12)] public uint   ip_srcaddr; //Source IP Address 
 		[FieldOffset(16)] public uint   ip_destaddr; //Destination IP Address 
 	}   
 	public class RawSocket 
 	{ 
 		private bool error_occurred; 
 		public bool KeepRunning; 
 		private static int len_receive_buf; 
 		byte [] receive_buf_bytes; 
 		private Socket socket = null; 
         private static string localip;   
 		public RawSocket() 
 		{ 
 			error_occurred=false; 
 			len_receive_buf = 4096; 
 			receive_buf_bytes = new byte[len_receive_buf]; 
 		}  		 
 		public void CreateAndBindSocket(string IP) 
 		{ 
             localip = IP; 
 			socket = new Socket(AddressFamily.InterNetwork, SocketType.Raw, ProtocolType.IP); 
 			socket.Blocking = false; 
 			socket.Bind(new IPEndPoint(IPAddress.Parse(IP), 0));   
 			if (SetSocketOption()==false) error_occurred=true; 
 		}   
 		public void Shutdown() 
 		{ 
 			if(socket != null) 
 			{ 
 				socket.Shutdown(SocketShutdown.Both); 
 				socket.Close(); 
 			} 
 		}   
 		private bool SetSocketOption() 
 		{ 
 			bool ret_value = true; 
 			try 
 			{ 
 				socket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.HeaderIncluded, 1);       
 				byte []IN = new byte[4]{1, 0, 0, 0}; 
 				byte []OUT = new byte[4]; 
 				int SIO_RCVALL = unchecked((int)0x98000001); 
 				int ret_code = socket.IOControl(SIO_RCVALL, IN, OUT); 
 				ret_code = OUT[0] + OUT[1] + OUT[2] + OUT[3]; 
 				if(ret_code != 0) ret_value = false; 
 			} 
 			catch(SocketException) 
 			{ 
 				ret_value = false;