#include
#include
#include
#include using namespace std;#pragma comment(lib, "ws2_32.lib") //socket动态链接库
#pragma comment(lib, "kernel32.lib") //IOCP动态链接库//重叠IO用到的结构体,记录IO数据const int DataBufferSize = 2* 1024;
typedef struct s1
{OVERLAPPED overlapped;WSABUF databuff;char cBuffer[DataBufferSize];int BufferLen;int OperationType;}PER_IO_DATA, *LPPER_IO_DATA;//记录每个连接的socket信息
typedef struct
{SOCKET socket;SOCKADDR_STORAGE clientAddr;
}PER_HANDLE_DATA, * LPPER_HANDLE_DATA;//定义全局变量
const int nDefaultPort = 6000;
vector g_vClientGroup;//记录客户端的容器HANDLE hMutex = CreateMutex(NULL, FALSE, NULL);DWORD WINAPI ServerWorkThread(LPVOID CompletionPortID);
DWORD WINAPI ServerSendThread(LPVOID lpParam);int main()
{WORD wVersionRequested &#61; MAKEWORD(2,2);//请求版本为2.2的WINSOCKET库WSADATA wsaData; //接收windows socket的结构信息DWORD err &#61; WSAStartup(wVersionRequested, &wsaData);if(0 !&#61; err){cout<<"Request Windows Socket Library Error!"<socket &#61; acceptSocket;memcpy(&lpPer_Handle_Data->clientAddr, &sockaddr_client, nsocketaddr_client);g_vClientGroup.push_back(lpPer_Handle_Data);//将接收套接字和完成端口关联CreateIoCompletionPort((HANDLE)(lpPer_Handle_Data->socket), completionPort, (DWORD)lpPer_Handle_Data, 0);LPPER_IO_DATA perIoData &#61; NULL;memset(perIoData, 0, sizeof(struct s1));//perIoData &#61; (LPPER_IO_DATA)GlobalAlloc(GPTR, sizeof(PER_IO_DATA));//perIoData &#61; new PER_IO_DATA;//ZeroMemory(&(perIoData->overlapped), sizeof(OVERLAPPED));perIoData->databuff.len &#61; 1024;perIoData->databuff.buf &#61; perIoData->cBuffer;perIoData->OperationType &#61; 0; //readDWORD RecvBytes;DWORD Flags &#61; 0;WSARecv(lpPer_Handle_Data->socket, &(perIoData->databuff), 1, &RecvBytes, &Flags, &(perIoData->overlapped), NULL);}return 0;
}//开始服务器工作线程函数
DWORD WINAPI ServerWorkThread(LPVOID IpParam)
{HANDLE CompletionPort &#61; (HANDLE)IpParam;DWORD BytesTransferred;LPOVERLAPPED IpOverlapped;LPPER_HANDLE_DATA PerHandleData &#61; NULL;LPPER_IO_DATA lpPerIoData &#61; NULL;DWORD RecvBytes;DWORD Flags &#61; 0;BOOL bRet &#61; false;while(true){bRet &#61; GetQueuedCompletionStatus(CompletionPort, &BytesTransferred, (PULONG_PTR)&PerHandleData, (LPOVERLAPPED *)&IpOverlapped, INFINITE);if(bRet &#61;&#61; 0){cout<<"GetQueuedCompletionStatus Error:"<socket);GlobalFree(PerHandleData);GlobalFree(lpPerIoData);continue;}//开始数据处理&#xff0c;接收来至客户端的数据WaitForSingleObject(hMutex, INFINITE);cout<<"A Client says:"<databuff.buf<overlapped), sizeof(OVERLAPPED)); //清空内存lpPerIoData->databuff.len &#61; 1024;lpPerIoData->databuff.buf &#61; lpPerIoData->cBuffer;lpPerIoData->OperationType &#61; 0;WSARecv(PerHandleData->socket, &(lpPerIoData->databuff), 1, &RecvBytes, &Flags, &(lpPerIoData->overlapped), NULL);}return 0;
}DWORD WINAPI ServerSendThread(LPVOID IpParam)
{while(true){char talk[200]&#61;{0x00};gets(talk);int len;for(len&#61;0; talk[len] !&#61; &#39;\0&#39;; &#43;&#43;len){}talk[len]&#61;&#39;\n&#39;;talk[&#43;&#43;len] &#61; &#39;\0&#39;;cout<<"I Say :";cout<socket, talk, 200, 0);}ReleaseMutex(hMutex);}return 0;
}