(转)DotNet中的Socket编程(C#)
Socket基础介绍
.Net Framework中的网络编程结构
抛开ISO/OSI模型的7层构架,单从TCP/IP模型上的逻辑层面上看,.Net类可以视为包含3个层次:请求/响应层、应用协议层、传输层。 WebReqeust和WebResponse 代表了请求/响应层,支持Http、Tcp和Udp的类组成了应用协议层。而Socket类处于传输层,位于这个结构的最底层,当其上面的应用协议层和请求/响应层不能满足应用程序的特殊需要时,就需要使用这一层进行Socket套接字编程。
而在.Net中,System.Net.Sockets命名空间为需要严密控制网络访问的开发人员提供了Windows Sockets(Winsock)接口的托管实现。System.Net命名空间中的所有其他网络访问类都建立在该套接字Socket实现之上,如TCPClient、TCPListener 和UDPClient类封装有关创建到Internet的TCP和UDP连接的详细信息;NetworkStream类则提供用于网络访问的基础数据流等,常见的许多Internet服务都可以见到Socket的踪影,如Telnet、Http、Email等,这些服务尽管通讯协议Protocol的定义不同,但是其基础的传输都是采用的Socket。
.Net中Socket编程的必备基础
.NET框架的Socket类是Winsock32 API提供的套接字服务的托管代码版本。其中为实现网络编程提供了大量的方法。如果熟悉Winsock API函数,那么用Socket类编写网络程序会非常容易,当然,如果不曾接触过,也不会太困难。主要为Socket类的几个方法:
1、创建一个Socket实例
Socket s = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
2、建立远程连接
2、建立远程连接
Socket.Connect(EndPoint remoteEP)(有重载方法)
3、从数据中的指示位置开始将数据发送到连接的 Socket
Socket.Send(byte[], int, SocketFlags); (有重载方法)
Socket.Send(byte[], int, SocketFlags); (有重载方法)
4、将数据发送到特定终结点
Socket.SendTo(byte[], EndPoint); (有重载方法)
Socket.SendTo(byte[], EndPoint); (有重载方法)
5、将数据从连接的 Socket 接收到接收缓冲区的特定位置
Socket.Receive(byte[],int,SocketFlags);
Socket.Receive(byte[],int,SocketFlags);
6、接收数据缓冲区中特定位置的数据并存储终结点
Socket.ReceiveFrom(byte[], int, SocketFlags, ref EndPoint);
Socket.ReceiveFrom(byte[], int, SocketFlags, ref EndPoint);
7、使 Socket 与一个本地终结点相关联
Socket.Bind( EndPoint localEP );
Socket.Bind( EndPoint localEP );
8、将 Socket 置于侦听状态
Socket.Listen( int backlog );
Socket.Listen( int backlog );
9、创建新的 Socket 以处理传入的连接请求
Socket.Accept();
Socket.Accept();
10、禁用某 Socket 上的发送和接收
Socket.Shutdown( SocketShutdown how );
Socket.Shutdown( SocketShutdown how );
11、强制 Socket 连接关闭
Socket.Close();
Socket.Close();
用到IPEndPoint类的时候就不可避免地涉及到计算机IP地址,.Net中有两种类可以得到IP地址实例:
一是通过IPAddress类:IPAddress 类包含计算机在 IP 网络上的地址。其Parse方法可将 IP 地址字符串转换为 IPAddress 实例。下面的语句创建一个 IPAddress 实例:IPAddress myIP = IPAddress.Parse("192.168.1.2");
二是通过Dns 类:向使用 TCP/IP Internet 服务的应用程序提供域名服务。其Resolve方法查询DNS服务器以将用户友好的域名(如"host.contoso.com")映射到数字形式的 Internet 地址(如 192.168.1.1)。Resolve方法 返回一个 IPHostEnty实例,该实例包含所请求名称的地址和别名的列表。大多数情况下,可以使用AddressList数组中返回的第一个地址。下面的代码获取一个IPAddress实例,该实例包含服务器host.contoso.com的 IP 地址。
IPHostEntry ipHostInfo = Dns.Resolve("host.contoso.com");
IPAddress ipAddress = ipHostInfo.AddressList[0];
也可以使用GetHostName方法得到IPHostEntry实例:
IPHosntEntry hostInfo=Dns.GetHostByName("host.contoso.com")
Socket类工作原理
首先必须创建一个Socket,一旦创建Socket,在客户端,将可以通过Connect方法连接到指定的服务器,并通过Send/SendTo方法向远程服务器发送数据,而后可以通过Receive/ReceiveFrom从服务端接收数据;而在服务器端,你需要使用Bind方法绑定所指定的接口使Socket与一个本地终结点相联,并通过Listen方法侦听该接口上的请求,当侦听到用户端的连接时,调用Accept完成连接的操作,创建新的Socket以处理传入的连接请求。使用完Socket后,记住使用Shutdown方法禁用Socket,并使用Close方法关闭Socket。
另外,很多时候Socket编程视情况不同需要在客户端和服务器端分别予以实现,在客户端编制应用程序向服务端指定端口发送请求,同时编制服务端应用程序处理该请求,这个过程在上面的阐述中已经提及;当然,并非所有的Socket编程都需要你严格编写这两端程序;视应用情况不同,你可以在客户端构造出请求字符串,服务器相应端口捕获这个请求,交由其公用服务程序进行处理。以下事例语句中的字符串就向远程主机提出页面请求:
string Get = "GET / HTTP/1.1rnHost: " + server + "rnConnection: Closernrn";
远程主机指定端口接受到这一请求后,就可利用其公用服务程序进行处理而不需要另行编制服务器端应用程序。
用C#描述的Socket编程实例
下面的程序段完整地实现了Web页面下载功能。用户只需在窗体上输入远程主机名(Dns主机名或以点分隔的四部分表示法格式的 IP 地址)和预保存的本地文件名,并利用专门提供Http服务的80端口,就可以获取远程主机页面并保存在本地机指定文件中。如果保存格式是.htm格式,你就可以在Internet浏览器中打开该页面。适当添加代码,甚至可以实现一个简单的浏览器程序。源代码如下:
public void
}