这是在学《Windows网络编程(第二版)》第六章时制作的一个例子
由于书中没有给出简洁的例子,本人在学这里时就费了很多时间。
现在把完成的代码贴出来,供大家参考。
本程序在VS2003编译器编译运行。在6.0下可能需要稍加修改。
DWORD WINAPI ServerThread(LPVOID lpParam)
{
HANDLE CompletionPort = (HANDLE)lpParam;
DWORD bytes;
LPPER_HANDLE_DATA perHandleData = NULL; //单句柄数据
LPPER_IO_DATA perIoData; //单IO数据
DWORD Flags;
int ret;
DWORD RecvBytes;
//进入循环的等待重叠操作的完成
while(true)
{
bytes = -1;
ret=GetQueuedCompletionStatus(
CompletionPort, //原先的完成端口句柄
&bytes, //重叠操作完成的字节数
(LPDWORD)&perHandleData, //原先和完成端口句柄关联起来的单句柄数据
(LPOVERLAPPED*)&perIoData, //用于接收已完成的IO操作的重叠结构
INFINITE); //在完成端口上等待的时间 INFINITE 为无限等待
//先检查在套接字上是否发生错误
//当发生错误时关闭套接字同时释放掉所有的内存.
int i = 0;
if(bytes == 0 && (perIoData->operatorType == RECV ||
perIoData->operatorType == SEND))
{
closesocket(perHandleData->socket);
GlobalFree(perHandleData);
GlobalFree(perIoData);
cout<<"closesocket and globalfree perhandledata periodata!"<<endl;
continue;
}
//这是AcceptEx函数处理完成,在下面处理
if(perIoData->operatorType == ACCEPT) //处理连接操作
{
//使用GetAcceptExSockaddrs函数 获得具体的各个地址参数.
if(setsockopt( perIoData->client, SOL_SOCKET, SO_UPDATE_ACCEPT_CONTEXT,
( char* )&(perHandleData->socket ), sizeof( perHandleData->socket ) )==SOCKET_ERROR)
cout<<"setsockopt..."<<endl;
perHandleData->socket = perIoData->client;
//memcpy(&(perHandleData->clientAddr),raddr,sizeof(raddr));
//将新的客户套接字与完成端口连接
CreateIoCompletionPort((HANDLE)perHandleData->socket,
CompletionPort,(ULONG_PTR)perHandleData,0);
memset(&(perIoData->overlapped),0,sizeof(OVERLAPPED));
perIoData->operatorType = RECV; //将状态设置成接收
//设置WSABUF结构
perIoData->buffer.buf = perIoData->dataBuffer;
perIoData->buffer.len = perIoData->dataLength = DATA_LENGTH;
cout<<"wait for data arrive(Accept)..."<<endl;
Flags = 0;
if(WSARecv(perHandleData->socket,&(perIoData->buffer),1,
&RecvBytes,&Flags,&(perIoData->overlapped),NULL)==SOCKET_ERROR)
if(WSAGetLastError()==WSA_IO_PENDING)
cout<<"WSARecv Pending..."<<endl;
continue;
}
if(perIoData->operatorType == RECV)
cout<<perIoData->buffer.buf<<endl; //将接收到的数据显示出来
Flags = 0;
perIoData->operatorType = RECV; //设置成接受数据类型
ZeroMemory(&(perIoData->overlapped),sizeof(OVERLAPPED));
//重新投递一个新的接收请求
cout<<" wait for data arrive..."<<endl;
WSARecv(perHandleData->socket,&(perIoData->buffer),1,
&RecvBytes,&Flags,&(perIoData->overlapped),NULL);
}
return 0;
}
在前面有贴出了一个简单的客户端例子,可以结合起来调试,很方便的。
欢迎同道同志来信讨论 chang841018@yahoo.com.cn
正文
IOCP配合AcceptEx的例子(2)2006-07-02 14:36:00
【评论】 【打印】 【字体:大 中 小】 本文链接:http://blog.pfan.cn/marks/16317.html
阅读(10089) | 评论(2)
版权声明:编程爱好者网站为此博客服务提供商,如本文牵涉到版权问题,编程爱好者网站不承担相关责任,如有版权问题请直接与本文作者联系解决。谢谢!
评论