使用VC++的网络编程总结_第1页
使用VC++的网络编程总结_第2页
使用VC++的网络编程总结_第3页
使用VC++的网络编程总结_第4页
使用VC++的网络编程总结_第5页
已阅读5页,还剩39页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、使用VC+的网络编程总结1. 套接字编程原理11 Client/server 通信模型1 2 Windows Sockets 规范1.3套接字131套接字定义1.3.2分类13 3套接字的作用1.3 4端I I与地址13 5套接II属性2. 基本的 Windows Sockets API 编程21常用函数2.2 TCP实例2.3UDP实例14 Socket通信阻来的解决方法3. MFC卜的Socket编程的类3.1 CAsyiicSocket 类3.2CSocket 类3 3 Windows Sockets:带存档的套接字的匸作方式3.4流式套接字通信的操作顺序3 .5 使用 C Async

2、Socket 类3 6从套接字类派生3 7套接字通知3.8 个使用CSocket类的网络通信实例3 8 1服务器端应用程序计(ServerDemo)3 82客户端向用程序设计(项忖名称ChentDemo)4. 套接字的托管实现4.1 System:: Net:: Sockets 命名空间4 2实例:一个新邮件检查器5. 怎样实现服务器端多线程的socket功能?1. 鞍字编程原理一个完整的网间通信进程需耍由两个进程组成,并冃.只能用同一种高层协议。也就是说. 不可能通信的一端用TCP,而另一端用UDPC 一个完整的网络信碍耍一个五元组來标识: 协议、本地地址、本地端门号、远端地址、远端端门号。

3、1.1 Client/server 通信模型在客户/服务器模式中我们将请求服务的一方称为客户(client),将提供某种服务的一方 称为服务器(seiver)o-个服务程序通常在一个众所周知的地址监听对服务的请求,也就足说服务进程一1处 休眠状态,直到一个客户对这个服务的地址提出了连接请求。在这个时刻,服务程序被“惊 醍'并II为客户提供服务一客F的请求作出适为的反虽然旱广连接的服务是设计客户 机/服务器臧用程序时的标准,但有些服务也是可以通过无连接的接I I提供的。客户机/服务器的请求/响W过程示意图如卜所示。客户机请求进程通信设施服务器图1客户/服务器通信模型通过上面的分析,我们不

4、难理解-个一个完樂的网络臧用程序包括*戸端和服务器两个 部分。客户与服务器进程的作用是罪对称的,因此编码不同。服务进程-般是等待客户请求 而启动的,只耍系统运行,该服务进程一直存在,直到终止或强迫终止。1 2 Window s Sockets 规范Windows Sockets规范是90年代初Microsoft公诃联合其他儿家人公诃共同制定的套 在Windows卜的二进制加容网络编程接1丨规范。它以U C Berkeley人学BSD UNIX屮流行 的Socket接II为基础,主耍在苴上扩充了一纽针对Windows的扩展库换数,增加了符介 Windows消息骡动特件的网络书件异步选择机制,以使

5、程序员能够充分利用Windov/s消息 驱动机制进行编程。Windows Sockets的用途是将基础网络抽彖出來,这样,您不必对网络非常了解,并且 您的应用程序可在任何支持套接字的网络上运行。它为应用程序开发苕定义了一套简单统一 的API,并让各家网络软件供应商共同遵守。Windows Sockets规范从90年代初的1 0版本开始,经过不断的完善和发展,目前C经 仃了 Window s Sockets 2版本。值得注意的是,Microsoft的MFC库现在只支持Wnidow s Sockets 1 版本,不支持 Windows Sockets 2 版本。MFC提供了两个类用以封装Windo

6、w s S ockets API。一个是CAsync Socket类,它主耍 是提供给那些八仃一定网络编程经验,希里同时拥仃Socket API编程的乂活性和类库编程便 利性的开发者的。另一个是CSocket类,它由CAsyiicSocket类派生,它貝冇更高的抽彖化. 致力J:简化网络编程所需的操作。1.31.31套接字定义套接字是一个通信终结点,它是Sockets应用程序用來在网络上发送或接收数据包的对 象。套接字貝有类熨,与正在运行的进程相关联,并月.可以有名称。H前,套接字一般只与 使用网际协议组的同一“通信域”屮的其他套接字交换数据。使用套接字的应用程序间通信模 型如图2所示。应用8

7、»a 一直用震 材字A ”字B B奪接字1««913-2分类可用的套接字类舉有以卜两种:1.32.1 式套接字流式套接字提供没有记录边界的数据流,即字节流。字节流能确保以1E确的顺序无逍 复地被送达。農务客户机1 廉井初繪化簽于|并字1I户机的求、<> f1立愛播1揍受燒揍求1& 、,| ««*«H1*«*11 1 1 *»*«14nt*«VI关1关图3流式套接7 (仔连接通信)笛R1. 322数据报套接字支持而向记录的数据流.但不能确保能被送达,也无法确保按照发送顺“. 户

8、机.创建井初怡化W按壬并初摘化厨町1展务#发出如一|3 z<、fI費n量1 数揺报耆揍字(无)aiy序”指数据包按发送的顺序送达。rw:复"指一个特定的数据包只能获取一次。这两 种套接字都是双向的,是可以同时在两个方向上(全双工)进彳j通信的数据流。在某些网络协议下(如XNS),流可以面向记录,即作为记录流而非字节流。但在更常用的TCP/IP协议卜流为字节流。Windows Sockets提供与基础协议无关的抽象化级别。L33套接字的作用套接字的作用非常人,至少在下而三种通信上卜文中如此: 客户端/服务器模屯。 对等网络方案,如聊大W用程序。 通过让接收应川程序将消息解释为函数

9、调川來进彳j远程过程调用(RPC)o 1.3.4靖口与地址在网络上,一个套接字的标识主要借助于地址和端I I來描述。套接字的地址指该套接字所在计算机的网络地址,町以为域名或IP地址的形式。通常, 创建套接字时不必指明网络地址,只仃在拥仃多个网洛地址的机器时,才需要显式指定-个 网络地址。同一机器上可以运仃多个网络W用程序,毎个应用程序都勺白己的套接字用以进仃网 络通信,此时如果只有地址标讲套接字,则当一个通信包到达机器时将无法确定究竞是哪 个W用程序的套接字需耍接收此信息。由此增加了端11的概念,以协助区分同一机器上不同 应用程序的套接字。端II用r标识进程,同一机器上不同的网络应用程序各冇不

10、同的端II,这样,通过“网 络地址+端II号”的标识方法,便唯一标识了机器上的应用程序了。某些端II是专门为公共服务保留的(Ftp 21,http30),除非程斥是耍提供这些服务,否 则应尽量避免使用这些端【I。 般來说,端I 1 1024以前的端口号都是系统保留的或是作为 公共服务的,应尽量选择AT- 1024的端【1号,以避免冲突.13 5套接II属性套接I I有一系列的属性用标识套接I I的状态等信息,它们的属性如衣1所示。*1套接口层性选项类型含义缺省值SO ACCEPTCONBOOL套接II正在监听FALSESO BROADCASTBOOL套接II设置为可发送广播数据FALSESO

11、DEBUGBOOL允许DebugFALSESO DONTUNGERBOOL是否禁止SO LINGER选项TRUESO DONTROUTEBOOL路由被禁止FALSESO ERRORnt得到并且清除错误状态0SO KEEPALIVEBOOL活跃信息正在被发送FALSESOJJNGERstruct返回目前的lingo-信息l onoffSO OOBINUNEBOOL帯外数据正在普通数据流中被接收FALSESO RCVBUFint接收缓冲区大小与貝体实现冇关SO REUSEADDRBOOL该套接1 1捆绑的地址可否被他人使用FALSESO SNDBUFnt发送缓冲区大小与具体实现白关SO TYPEn

12、t套接口类型与接口类型有关TCP NODELAYBOOL禁止采用Nagle进行介并传送与几体实现仃关可以通过getsockoptO函数获取套接口的H性,也可以通过setsockoptO两数设置套接口 的D性.2. 基本的 Windows Sockets API 编程 需要在程序中添加下面的包含语句$ #inciude<winiock2.W> 便用伙卄编译时需潑加编译傩接依聯頊wt2-32.1ib库协议寻址在wmsock中,应用程亍;通过sockaddr_in结构来指定IP地址和服务端11信息 sockaddrjn nteiTietAddr,nt nPortID=5320,mteme

13、tAddr sin_faniily=AF_INET,internet sn_addi' s_addr=met_addr(“ 202 2024288”),/INADDR_ANYnteiTiet sn_p ort=htons(nPortID),ip地址不容易记忆,还提供了许多地址和幺称解析函数如gethostbyiiaine,getliostbyaddi-等。2.1常用函数1) WSAStartup 调用 wnidows Socket DLL函数原型mt WSAStartup(WORD wVei'sionRequested,/应用程J#要求的 sockets 版本LPWSADATA

14、lpWSAData 指向数据结构WSDATA的指针,得到windows Socket的fl体信息):WSDATA定义如卜: typedef struct WSAData WORDWORD#ifdef _WIN64uiisigned short unsigned short char FAR char char#elsecharcharunsigned short unsigned short char FAR #endifw Version,wHighVei'sion,lhfaxSockets,lhfaxUdpDg,lpVendorlnfo,szDescnption WSADES CR

15、IPTION_LEN+1 , szSystemS tatus WS AS Y S_STATUS_LEN+1,szDesci-iptionWSADES CRIPTION_LEN+1 , szSystemStatusWSAS YS_STATUS_LEN+1 iMaxSockets, lhfaxUdpDg,lpVendorlnfo, WSADATA, FAR * LPWSADATA,2) WSACleaiiup 结束対 Windows Sockets DLL 的调用 函数原粮:nt WSACleanup(void),3) socket 用 J:建 f. Sockets®函数原型:SOCKE

16、T socket(nt af,地址族,-般是 AF_INETint type , /socket 类熨.SOCK_STREAM 或 SOCK_DGRAMnt protocol 协议类型,通常取值0),4) closesocket关闭套接字换数原型:mt closesocket(SOCKET s 要关闭的套接字),5) bind将一个本地地址和一个SOCKET描述字连按起來函数原型:nt bnd(SOCKET s, /凄绑定的套接字const struct sockaddi* FAR* name, /扌旨向 SCCKADDR 纟占构的地址 int nainelen地址结构的 sizeof)T卬仲

17、SOCKADDR结构stivct sockaddrunsigned short sa_family,char sa_data4,struct sockaddr_mshort unsigned short struct in_addr charsni_fairiily> sm_port, sm_addr, sin_zero ./>6)listen 设定 socket为临听状态函数原型:nt listen(SOCKET s, 进行监听的socketnt b acklog咯八端以连接的请求个数),7) accept接受一个socket的连接请求,同时返冋一个新的socket,新的sock

18、et用来在服务 器与客户端Z间传递和接收信息。函数原型:SOCKET accept(SOCKET s, 处于监听状态的socketstruct sockaddi* FAR* addr, 将耍接受地址的 sockaddr 指针 nt FAR* addrlen 地址的长度),8) connect连接客户端的socket到指定的网络服务器。连接成功后,客户端用此socket与服 务器通信。函数原型:int connect(SOCKET s, /力$耍连接的 socketconst struct sockaddi* FAR* name, /H 标 socket 地址nt nainelen 地址结构 s

19、izeof);9) recv用J;接收已经建立连接的socket数据信息函数原型:nt recv(SOCKET s,char FAR* buf, 接收数据缓冲区nt len,燈冲区长度nt flags 冇 MSG_PEEK 和 MSG_OOB),返回值:接收到的字节数10) send对已经建立连接的socket发送数据信息函数原型:nt send(SOCKET s,chai'FAR* buf, 发送数据缓冲区nt len,虑冲区长度mt flags 有 MSG_PEEK 和 MSG_OOB),返回值:发送的字节数11) WSAAsyncSelect要求socket在仃事件发生时通知使用

20、着,木旳数将套接I 1设置成为|1; 阴塞方式。函数原型:mt WSAAsyncS elect(SOCKET s,HWND hWnd, 接收网络事件的窗I I句柄unsigned mt wMsg发送给窗I I的网络爭件消息 long Ev ent/网络消息);12) sendto向口标地址发送数据信息int sendto(SOCKET s,const char FAR buf,mt len,mt flags,const struct sockaddr FAR to,mt tolen);13) recvfrom接收H标地址传來的数据信息int recvfrom(IN SOCKET s.OUT c

21、har FAR buf,IN mt len,IN mt flags,OUT stnict sockaddr FAR from,IN OUT mt FAR * fromlen),2.2 TCP实例服务器端需耍建立两个套接字,一个用监听连接请求,另一个用來与请求连接的套接 字建立连接,实际的数据传送是通过后i个套接字。而客门端只需耍一个套接字即可。客户堆代码实例(命令行)服务阳代码实例(命令行)#mdude<stdio h>#uidude<winsock2 h>void mamOSOCKET sock.struct sockaddrin sa, int err,int se

22、rvport=5555,char buff256;int len, WSADATAws,II初始化Winsock if(WSASt artup (0x0101, &ws)!=0) (pnntf(BWSAStartupO faledin*);#indude<stdioh>#mdude<winsock2.h>void marnOSOCKET servsockclisock, struct sock?ddr_in sa, struct sockfddrjn diaddr;int servport=5555;char buff256> WSADATAws; int

23、 len.err,II初始化Winsock if(WSASt artup (0x0101, &ws)!=0) (pnntf(MWSAStartup0 failedin-); exit(-l);)创建套接字 sock=socket(AFJNETSOCK_STREAM,0)t/定义服务器地址结构mens et (血 & 0, siz eo f(s a)» sa sin_family=AF_INET, sa sin j) ort=htons (servp ort).sasin_addr s_addr=met_addr("202.202.42 SS-).II连接服务

24、器 err=connect(sock (const sockaddra)&sa.sizeof(sa)t"接收欢迎词memset (buf£0,sizeof(buff)» len=recv(socktbufisizeof(buff)>0)>pnntfC%snB,buff),关闭连接dosesocketCsock), WSACleanupO,)创建套接7printfCCreate Socket nM)» servsodc=socket(AFJNET,SOCK_STREAM.O),填充服务器地址结构meinset(&sa>0,

25、sizeof(sa)>sa sin_family=AF_INET,sa sinj)ort=htons(servp ort),sasin_addr s_addr=inet_addr(M202.202 42 88*),绑定套接了到服务器地址结构pnnt f( Binding.An");err=bind(servsock,(const sockaddr *)&sa.sizeof(sa), if(err!=0)fpmitfCstderr.11 Bind faded %dnWSAGetLastErrorO)t exit(-2),)监听套接字printf(" Listen

26、ing An").err=listen(servsock, 5)»if(erri=0)jnntf(std err,11 Listen failed %dn"»WS AG et Last Err orO). e»t(-3),)等待连接请求printf(" Watting Request n")tlen=sizeof(diaddr)tdisock=accept(servsock,(struct sockaddr 拿)&diaddi;&len). print f(" AcceptClient %s %dn

27、",inet_ntoa(cliaddr sm_addr),ntohs(cliaddr sin_ port);spnntf(buf£" Welcomeyou%smet_ntoa(di addr. sin_addr)»发送欢迎词send(disock,bi成 strlen(buff).O);关闭连接closesocket(disock)»closesock et(servsock);WSACleanupO;)W4*«TCPierver (阻塞式)在 stdafxh 文件中加入 #include<¥insock2. h>

28、;启动TCP server按钮事件处理void CTcpServerDlg: :OnBnClickedButtonl 0/ TODO:在此潦加控件通知处理程序代码if(ISASt artup(0x0101,4ws)!=0)m_editl=A,ISAStartup() failed!UpdateData(false);return;创建套接字servsock=socket(AF.INET, SOCK.STREAM,0);览充服务器地址结构servport=5555;Jiemset (&sa, 0, sizeof (sa);sa. sin_fajiily=AF_INET;sa sinj)o

29、rt=htons (servport),sa. sinaddr. s_addr=inet_addr ("202 202. 42. 88");绑定套接7到服务器地址结构err=bind(servsock, (const sockaddr *)&sa, sizeof(sa);if(err1=0)m_editl二"Bind failed! *;UpdateData(false)xreturn;监听套接字err=l is t en(s ervs ock, 5);if(err 1=0)(jn_editl="Listen failed!'Update

30、Data(false);return;*_edit 1. Set String (Vai t ing request.;UpdateData(false);this->Redra»Vindow ();/伽不H用此句,11在lfiSocket方式下宣体无法正1WW等待连接请求len=sizeof(cliaddr);clisock=accept(servsock, (struct sockaddr *)&cliaddr&len); meditl.Foraat("AcceptClient :%s:%dn", inet_ntoa(cliaddr si

31、n_addr),ntohs(cliaddr sin_port); UpdateData(false);/復送清農事件处理void CTcpServerDlg:OnBnClickedButton2()/ TODO:此添加控件通知处理程序代码sprintf (buff, 'Velcoae you %s*, inet_ntoa(cliaddr sin.addr);发送欢迎诃send(clisock, buff, strlen(buff), 0);/快閒连接事件处理void CTcpServerDlg:OnBnClickedButton3()/ TODO:在此添加控件通知处理程序代码关闭连接M

32、_edi11="Connection Closed!"UpdateData(false);closesocket(clisock);closesocket(servsock);VSACleanupO;2.3 UDP实例客户端实例服务器端实例#include<stdio. h> finclude<stdlib. h> #include<s tring h> #include<winsock2. h>define BUFSIZE 256linclude<stdio. h> #include<stdlib. h&g

33、t; #include<s tring. h> #include<winsock2. h>"define BUFSIZE 256void main(void)ivoid Main(void)/istruct sockaddr_in client, server;istruct sockaddrin client, server;SOCKET s;SOCKET s;int len, zero, n;int len, i, n;char buftBUFSIZE,char bufBUFSIZE;/WftftTlnfock/M6 化 TiDfOdtISADATA vs

34、aData;ISADATA wsaData;VSASt arttj (0x0202,4<saData);ISAStarti?) (0x0202, ivsaData);/«*»*/»*»*s=socket(AF.INET. SOCK.DGRAM, 0);s=socket(AF.INET. SOCK_DGRA儿 0);/测炖务MiOIMBeiiset (char*)Aclient, 0, sizeof (client);Beaset (char*)&server, 0, sizeof (server);client, sirvfaftily =

35、AF_INET,server.sin.family =AF_INET;client, sin.addr. s_addr=htonl (INADDR.ANY);server, sinaddr. s_addr=htonl (INADDR.ANY);client sinport =htons(0);server sinport =htons(5320);/W定.ocketxgl客户她/W 定bind® (struct sockaddr*)&client, sizeof (client);bind(s, (struct sockaddr*) A server, sizeof (ser

36、ver):/她化JK务址第构,确定要住的農务化客户*e»set(char*)4server. 0, sizeof(server);server sin_fa»ily =AF_INET;server, sinaddr s.addr=inet_addr (202. 202. 42. 88");server sin_port =htons(5320);/«户|从他圧受字符孰 发送到展务* 在从服务酗i/»收客户増发送来的字符轧 回送客户竭接收眸的字符串回畳1ers i zeof(cli ent);len=sizeof(server);while(n=

37、recvfrom(s, buf, BUFSIZE, 0, (structwhiled)isockaddr*)4client, 4 len) >0)ifgets (buf, BUFSIZE, stdin);tfor(i=0;i<n;i-H-)if (strnc*p(buf, "exit", 4)=0) break,bufi=toupper(bufi);send:o(s. buf, strlen(buf), 0, (structsendto(s, buf, n. 0, (struct sockaddr*)Aclient, len);sockaddr*)&se

38、rver, len);n=recvfrojn(s, buf, BUFSIZE-1, 0, (structsockaddr*)0, ftzero);bufn= 0'; 注童要潘加字符串信束标志fputs (buf, stdout);ijfputs("bye bye 1*, stdout);/ 伏閒.odret/朕团ocketclosesocket(s);closesocket(s);ISACleanupO;ISACleanupO;exit(0);exit(O);24 Socket通信阻塞的解决方法使用select模空(UNIX卜也适用)或WSASelect模型,在VC+中已经实

39、现了一个异 步Sockett通信类C Async Socket,故在这里就不再赘述。3MFC下的Socket编程的类MFC提供J'两个类用以支持套接字编程,它们是CAsyncSocket 和CSocket类。3.1 CAsyncSocket 类CAsyncSocket -对 地対装 Windows Socket API。CAsyncSocket 适介哪些对网络 通信细节很了解,但希壑利用冋调的便利通知网络爭件的程序员使用。如果想利用Windows Sockets方便地处理MFC W用程序中的多个网络协议,而乂不想放弃灵活性,町以考虎使用 C Async SocketcCAsyncSoc

40、ket类是MFC在方便性与灵活性屮的-种折衷方案。它提供了一个类用以保 留网络编程的灵活性,而方便性则由下面耍讲到的CSocket类來提供。3.2 CSocket 类CSocket类是CAsyncSocket类的派生类,它致力提供比CAsyncSocket类更宙j的抽線 性,使得网络编程变得简单方便。CSocket类支持流方式和数据报方式,但一般情况$用的 更多的是流方式的数据通信。在流方式的通信模式卜,CSocket类通常会与CArchwe类结合,以串行化的方式发送和接收数据,这使得网络编程变得像读写文件-样简单了。CArchrve类扮演的是一个数据缓冲区的角色,它通过CSocketFile

41、类与个套接字相联系。只耍建立了两者的联系,然后往“数据缓冲区”装入数据与取出数据就完成了。发送数据与接收数据的示意图如图5所示。C ArchiveCArchiveCSKkefk141CSickefite mt图5海方式下敷窘的*AB则发送和接收数据时,由图5町以看出只耍建工好套接字跟CArchive类对象的关联, 只需要对CArchrve对彖进行操作,从而可以利用此类对彖优良的串行化功能,十分方便地 实现发送和接收数据。3.3 Windows Sockets:带存档的套接字的工作方式本节解释如何组合CSocket对象CSocketFile对象和CArchive对象以简化通过Windows套接字

42、发送和接收数据。对套接字,存档并不附加到标准的CFile对彖(通常与磁盘文件关联),而是附加到 CSocketFile対象。CSockeffUe对象不是连接到磁盘文件,而是连接到CSocket对象。一个CArchive对象管理一个缓冲区。当存储(发送)存档的缓冲区已满时,关联的 CFile对象写出缓冲区的内容。刷新附加到套接字的存档缓冲区相当于发送消息。当加载(接 收)存档的缓冲区已满时,CFile対象停止读取直到该缓冲区再次可用。CSocketFile类从CFile派主但它并不支持CFile成员西数.如定位丙数Seek.GetLength. SetLength 等,锁定函 数 Lock Ra

43、nge 和 IftilockRange.或 GetPositian 函数:每个CSocketFile対象必须耍做的爭是,将字节序列写入或读入关联的CSocket对象,或 从此对象為出或或出字节序列。I人1为不涉及文件,Seek和GetPosition等操作没仃盘义。 CSodcetFile从CFUe派生,因此它通常会继承所仃这些成员函数。为防止发生这种情况, 在CSodcetFlle屮币力不受支持的CFile成员函数以引发CNotSupportedExceptionCSocketFile对象调用其CSocket对象的成员函数來发送或接收数据。 卜图显示了在通信的两端这些対彖Z间的关系。CArd

44、iive% CSocketFile 和 CSocketCArchiveYCSocketFile这看起來很复杂 1CQ的是使您不必亲门管理套接宁的细节。您创建套接7、文件和存档.然厉通过将数据插入存档或从存档提取数据,开始发送或接收数据。CArchive .CSocketFile和CSocket管理后台的细节。CSocket对彖实际是一个两状态对象:有时异步(通常状态)有时同步。处F异步状 态时,套接字可以从框架接收并步通知。然而,在操作(如接收或发送数据)过程中,套接 字变为同步的。这意味着在同步操作完成之前,套接字不会接收进一步的异步通知。由r套 接字切换模式,请执行类似卜面的操作:Chly

45、Socket OnReceive()ar » strf/.如果CSocket没冇实现为两状态対象,则在您处理前而通知的同时,冇可能接收到同 类事件的附加通知。例如,在处理OnReceive时,可能收到OnRecewe通知。在上面的代 码片段屮,从存档提取str可能导致递归。通过切换状态,CSocket用防止附加通知的方 浓防止递归。一般规则是通知内没有通知。3 4信林作砒在构造CSocketHle对彖ZlW,卜面的顺序対CAsyncSocket和CSocket都是准确的 (只冇少数几个参数不同)。从构造CSocketFile对象开始,顺序只适用/ CSocket.卜表 阐释了在客户端

46、和服务器之间设置通信的操作顺序。设务参和客户竭之间的通信服务器/ construct a socketCSocket sockSrvi;/ create tlie SOCKET sockSivr Create(nPort)尸/ start listening sockSi-vrListen(),/ construct a new, empty socketCSocket sockRecv,/ accept connectionsockSivr Acc ept( sockRecv ),5/ constiuct file objectCSocketFile File(&sockRecv),

47、/ construct an archiveCArchive arlnC&file,CArchive load),-或-CArchive arOut(CArchive store),或两者-客户靖/ construct a socketCSocket sockClient,/ create the SOCKETsockClient Create( ),2/ seek a connectionsockClient. Connect(strAddr, liPoit),3*4/ constixict file object CSocketFile file(&sockClient),

48、 / construct an archive CArchive arln(&file,CArchiveoad),-或-CArchive arOut(CArchive 二 store).或两者-/usethe archive topass data: arln » dw Value,-或-/usethe archive topass data: aiin » dw Value,-或arOut« dwValue,6arOut« dwVakie,61.这里的nPoit是端I号。2服务器必须始终折疋一个端II,以便客八端可以连接。Create调用仃时也

49、折疋地址。k客户端使用默认参数.这些参数耍求MFC使用任何可用端II。3.这里的nPon是端II号,strAddr是计算机地址或网际协议(IP)地址。4计算机地址川以采川儿种形式:"ftp.micros0仕com"、""。IP地址采用“以点 分隔的数字”形式,如“127 5467 32”。Connect函数查看地址是否为以点分隔的数字(但它 不确保该数字是网络上的冇效计算机)。如果不是,则Connect使用氏他某种形式的计算 机名称。5当在服务器端调用Accept时,传递对新套接字对彖的引用。必须首先构造该对彖,但 不对它调用Create注意,如果此套接

50、字对象超出范曲则连接关闭。MFC将新对彖连接 到SOCKET句柄。可以在堆栈上构造此套接字(如表中所示)或在堆上构造。6存档和套接字文件在超出范閘时将被关闭。套接字对象超出范閘或被删除时,对彖的析 构函数也对此套接字对象调用Close成员函数。有关K序的其他说明匕表中显示的调用顺序适用r流式套接字。数据文报套接字是无连接的,不需要 CAsyncSocket Connect. Listen 和 Accept 调用(但町自扌羊地使用 Cannect)。相反,如 果正在使用CAsyncSocket类,则数据文报套接7使川CAsyncSocket: SendTo和RecehreFrom成员函数。(如果

51、对数据文报套接字使用Connect.则使用Send和 Receive,)因为CArchive不适川/数据文报,如果套接字是数据文报,则不耍使用帯存档 的 CSocketCSocketFile并不支持CHle的所冇功能,CFUe成员(如Seek)对套接字通信没冇 意义,是不可用的。因此,某些默认MFC Serialize函数与CSocketFile不兼容。这対: CEditView 类更是如此。不要试图使用 CEditView:SerializeRaw通过附加到 CSocketFUe 对象的CArchtve対彖來序列化CEdttView数据,而应使用CEditVIew:Serialize (无出

52、 处)。SenalizeRaw换数预期文件对象H冇CSocketFile不支持的负数,如Seek3.5 使用 CAsyncSocket 类请注,电:,该类在罪常低的级别上封装Windows Sockets APIa您可能也会感觉到,I'IlL 直接编写通信程序耍比使用CSocket类的通用替换模型效果更好。“MFC参考”中对CAsyncSocket进行了描述。Visual C+也提供 门立J: Platform SDK中 的 Windows Sockets规范。真体细肖由您决定。Visual C+不提供CAsyncSocket的示例 应用程序。3.5.1创建和使用CAsyncSodce

53、t对象1)构造f CAiyncSocket对象并使用该对象创建基础SOCKET句柄 套接字的创建遵循两阶段构造的MFC模式。例如:CAsyncSocket sock,sock Create( ),/ Use the default parameters-或CAsyncSocket* pSocket = new CAsyncSocket, int nPort = 27,pSocket->Create( nPort, SOCK_DGRAM ),上面的第一个构造换数在堆栈上创建一个CAsyncSocket对象,第二个构造函数在堆 上创建CAsyncSocket上而的第一个Create调用使用默

54、认参数创建流式套接字,第二个 Creite调用创建人冇指定端I I和地址的数据文报套接字。(任一个Create版本都可以和任 一种构造方法一起使用。)Creite的参数仃: “端口”:短整型。对J:服务器套接字,必须指定端II。对客户端套接字,通常接受此参数的默认值,该 值允许 Windows Sockets选择端I。 套接字类型:SOCK STREAM (默认值)或SOCK DGAM, 套接字“地址”,如“ ftp microsofl conf或“ 128.56 22.8"。该地址为网络上的网际协议(IP)地址。很可能要始终依赖此参数的默认值。2)如果套接字是客户端,则便用CAsy

55、ncSocket Connect将此套接字对彖连接到服务器套 接字。或-如果套接字是服务器,则将套接字设趕为开始侦听(使用CAsyncSocket Listen)來自客户 端的连接尝试。接收到连接请求时,用CAsyncSocket Accept接受该请求。接受连接后,可以执行验证密码等任务。注童 Accept成员两数采用对新的空CSocket对象的引用作为它的参数。在调用 Accept Zflij,必须构造该対彖。如果此套接字对彖超出范田,则连接关闭。不要対这个新 套接字対象调用Create>有关示例,请参见文章 WindowsSockets:操作顺八';。3)通过调用CAsyn

56、cSocket刈象的封装 Wmdow s Sockets API隨数的成员皈数,与Jt他套 接字进行通信。请参见“MFC参考”中的 Windows Sockets规范和CAsyncSocket类。4)销毁 CAsyncSocket 对彖。如果在堆栈上创建了套接字对象,当包含两数超出范閘时将调用此対象的析构隨数。如 果使用new运郭符在堆上创建了套接7对彖,则您必须负贞使用delete运算符销毁此对 彖。析构两数在销毁対彖之前调用对象的Close成员函数。3.5J 您对 CAsyncS ocket 的责任创建CAsyncSocket类的对象后,该对象1寸装 Windows SOCKET句柄并提供对此旬 柄的操作。使用CAsyncSocket时,如果您直接使用API.则必须处理可能面对的所有问 题。例如:“阻塞”方案。发送和接收计算机之间的字节顺序差异。在Unicode和多字节字符集(MBCS)字符串之间转换。尽管存在这些问题,但如果应用程序石耍您能获得所有的杲活性和控制能力, CAsycnSocket类可能是正确的选择

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论