WSAEventSelect 模型
来源:互联网 发布:知乎举报是匿名的吗 编辑:程序博客网 时间:2024/05/05 06:17
Winsock提供了另一种有用的异步事件通知I/O模型——WSAEventSelect模型。这个模型与WSAAsyncSelect模型类似,允许应用程序在一个或者多个套接字上接收基于事件的网络通知。它与WSAAsyncSelect 模型类似是因为它也接收FD_XXX类型的网络事件,不过并不是依靠Windows的消息驱动机制,而是经由事件对象句柄通知。
//////////////////////////////////////////////////// WSAEventSelect#include "../common/initsock.h"#include <stdio.h>#include <iostream.h>#include <windows.h>CInitSock initSock;// 初始化Winsock库int main(){// 事件句柄和套接字句柄表WSAEVENTeventArray[WSA_MAXIMUM_WAIT_EVENTS];SOCKETsockArray[WSA_MAXIMUM_WAIT_EVENTS];int nEventTotal = 0;USHORT nPort = 4567;// 服务器监听端口// 创建监听套接字SOCKET sListen = ::socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);sockaddr_in sin;sin.sin_family = AF_INET;sin.sin_port = htons(nPort);sin.sin_addr.S_un.S_addr = INADDR_ANY;// 绑定端口if (::bind(sListen, (sockaddr *)&sin, sizeof(sin)) == SOCKET_ERROR) {printf("Failed bind() \n");return -1;}// 进入监听::listen(sListen, 5);// 创建事件对象,并关联到新的套接字WSAEVENT event = ::WSACreateEvent();// 将网络事件和事件对象关联起来;::WSAEventSelect(sListen, event, FD_ACCEPT|FD_CLOSE);// 添加到表中eventArray[nEventTotal] = event;sockArray[nEventTotal] = sListen;nEventTotal++;// 处理网络事件while (TRUE) {// 在所有事件对象上等待,下面函数会等待网络事件发生int nIndex = ::WSAWaitForMultipleEvents(nEventTotal, eventArray, FALSE, WSA_INFINITE, FALSE);// 对每个事件再次调用WSAWaitForMultipleEvents, 以便确定它们的状态;nIndex = nIndex - WSA_WAIT_EVENT_0;for(int i = nIndex; i <nEventTotal; i++){nIndex = ::WSAWaitForMultipleEvents(1, &eventArray[i], TRUE, 1000, FALSE);if (nIndex == WSA_WAIT_FAILED || nIndex == WSA_WAIT_TIMEOUT) {continue;}else{// 获取到来的通知消息,WSAEnumNetworkEvents函数会自动重置受信事件;// 找到与之对应的套接字,WSAEnumNetworkEvents查看发生了什么网络事件;WSANETWORKEVENTS event;::WSAEnumNetworkEvents(sockArray[i], eventArray[i], &event);if (event.lNetworkEvents & FD_ACCEPT)// 处理FD_ACCEPT通知消息{if (event.iErrorCode[FD_ACCEPT_BIT] == 0)// FD_ACCEPT未出错{if (nEventTotal > WSA_MAXIMUM_WAIT_EVENTS) {printf(" Too many connections");continue;}SOCKET sNew = ::accept(sockArray[i], NULL, NULL);WSAEVENT event = ::WSACreateEvent();::WSAEventSelect(sNew, event, FD_READ|FD_CLOSE|FD_WRITE);eventArray[nEventTotal] = event;sockArray[nEventTotal] = sNew;nEventTotal++;}}else if (event.lNetworkEvents & FD_READ)// 处理FD_READ通知消息{if (event.iErrorCode[FD_READ_BIT] == 0) {char szText[256];int nRecv = ::recv(sockArray[i], szText, strlen(szText), 0);if (nRecv > 0) {szText[nRecv] = '\0';printf("接受到数据:%s \n", szText);}}}else if (event.lNetworkEvents & FD_CLOSE)// 处理FD_CLOSE通知消息 {if (event.iErrorCode[FD_CLOSE_BIT] == 0) {::closesocket(sockArray[i]);for(int j = i; j < nEventTotal; j++)// 删除数组元素;{sockArray[j] = sockArray[j+1];}nEventTotal--;}}else if (event.lNetworkEvents & FD_WRITE)// 处理FD_WRITE通知消息 {}}}}return 0;}
0 0
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect模型
- WSAEventSelect 模型
- 重载、重写、隐藏
- 窗口 dialog 弹出时动画效果
- 入门createjs———EaselJS模块基本介绍
- Photoshop脚本 > 通过Grow命令扩展选区
- 容易混淆的概念
- WSAEventSelect 模型
- BestCoder Round #18 1004 &&hdu 5107 K-short Problem 线段树
- DELETE 与 TRUNCATE 有什么不同?
- win32 判断IP及子网掩码是否合法
- 高可用、开源的Redis缓存集群方案
- 第十三周项目4-数组的排序:冒泡排序
- Photoshop脚本 > 选取相似的颜色
- java date与long,String的互转以及date大小比较
- Photoshop脚本 > 移动当前选区的内容