重明鸟软件知识平台
@网络编程:IOCP(1)
完成端口(IOCP)是WINDOWS平台上特有的一种技术。要使用IOCP技术,就要用到微软的WSA(windows socket api)。

进行网络编程的套接口(socket)有UNIX套接口、伯克利套接口、WSA。其中使用最多的是伯克利套接口,因为他可在UNIX、WINDOWS、OS/2等计算机上使用。WSA套接口比伯克利套接口多了WSA三个字母。

伯克利套接口:socket()、recv()、send()等。
WSA套接口:WSASocket()、WSARecv()、WSASend()等。

WSA2.0还增加了很多新的功能函数。IOCP要在WSA2.0以上才能实现,所以我们要检查我们的系统是否支持WSA2.0(现在大部份都支持)。 IOCP的过程是,建立一个线程池(通常是有几个处理核心就创建几个线程。然后等待I/O操作提出,每一个链接进来的SOCKET分配一个线程去处理,处理完释放线程)。因为他是等待系统I/O操作的提出,而不是主动去轮询端口,所以他比传统方法更有效率。另外I/O的速度比CPU慢,而在IOCP里,数据是否传送到了由I/O提出,CPU只管处理数据问题,而不用轮询I/O端口,所以CPU的使用更高效。 还有一点,IOCP一般用TCP链接服务器,当然他也可以做UDP。为什么用IOCP做UDP少呢。我觉得理由很简单,因为UDP比较适合局域网内使用,IOCP是处理大规模链接用的,比如上千人的连网游戏,而且需要同时管理几百、上千个套接字时才使用。而在局域网里很少出现这种情况。所以,我觉得ICOP还是适合TCP链接。
IOCP经常用到的函数:
//创建一个完成端口
HANDLE CreateIoCompletionProt(
HANDLE FileHandle, //socket接口
HANDLE ExistingCompletionPort, //指定一个现有的IOCP
DWORD CompletionKey, //指定要与某个特定套接字关联在一起的数据。
DWORD NumberOfConcurrentThreads //一个IOCP上能同时执行几个线程,通常是0,
让系统根据核心数情况来定。
)
   
//获取完成端口队列的状态。
BOOL GetQueuedCompletionStatus(
HANDLE CompletionPort, //一个等待的完成端口。
LPDWORD lpNumberOfBytesTransferred, // I/O操作后实际接收或发送的字节数。
LPDWORD lpCompletionkey, //CreateioCompletionProt中的completionkey。
LPOVERLAPPED* lpOVerlapped, //接收完成的I/o操作的重叠结果。
DWORD dwMilliseconds //调用者喜欢等待一个数据包在IOCP上出现的时间
//设为INFINTE,则无休止等待。
)
   
//向完成端口线程发出指示“立即结束并退出”
BOOL PostQueuedCompletionStatus(
HANDLE CompletionPort, //想退出的完成端口
DWORD dwNumbetOfBytesTransferred,
DWORD dwCompletionKey,
LPOVERLAPPED lpOverlapped
)
后面三个参数的解释跟GetQueuedCompletionStatus是一样的。
   
//接收活动SOCKET
SOCKET WSAAPI WSAAccept (
SOCKET s, //监听一个套接口。
struct sockaddr FAR * addr, //通讯地址族
int FAR * addrlen, //通讯地址族长度
LPCONDITIONPROC lpfnCondition, //用户提供的条件函数的进程实例地址。
//该函数根据参数传入的调用者信息作出接受或拒绝的决定
DWORD dwCallbackData //作为条件函数参数返回给应用程序的回调数据。
)
   
//向套接字发送数据
int WSAAPI WSASend (
SOCKET s, //发送目的套接字
LPWSABUF lpBuffers, //发送数据缓冲区,这是个指针数组。存多组缓冲区
DWORD dwBufferCount, // lpBuffers包含缓冲区数
LPDWORD lpNumberOfBytesSent, //已发送字节数
int iFlags, //标志位
LPWSAOVERLAPPED lpOverlapped, //WSAOVERLAPPED结构的指针
LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine
//发送操作完成后调用的完成例程的指针
)
//返回已发送字节数
   
//向套接字接送数据
int WSARecv(
SOCKET s, //接收数据的套接字
LPWSABUF lpBuffers, // 接收缓冲区
DWORD dwBufferCount, // lpBuffers中WSABUF结构的数量
LPDWORD lpNumberOfBytesRecvd, // 如果接收操作立即完成,
//这里会返回函数调用所接收到的字节数
LPDWORD lpFlags, // 通常设置为0
LPWSAOVERLAPPED lpOverlapped, // “绑定”的重叠结构
LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine
// 完成例程中将会用到的参数,我们这里设置为 NULL
)
//返回WSA_IO_PENDING表示成功

在给系统分配完成端口时最好先用GetSystemInfo()函数查询一下系统有几个处理器。然后根据处理器情况为每个处理器创建工作线程。这样可发挥处理器的最大效率。
GetSystemInfo()用法:
SYSTEM_INFO SystemInfo;
GetSystemInfo(&SystemInfo);
int numCore = SystemInfo.dwNumberOfProcessors;
@站内查找
@栏目文章
【基础教程】TKinter(5):Label控件
【基础教程】TKinter(4):Messagebox控件
【基础教程】TKinter(3):Button控件
【基础教程】TKinter(2):控件及其属性
【基础教程】TKinter(1):第一个tkinter程序
【基础教程】Python守护进程创建
【基础教程】PyGame(13):三维环境设置
【基础教程】C/C++指针函数和回调函数
【基础教程】C/C++多进程编程(3)
【基础教程】C/C++多进程编程(2)
【基础教程】C/C++多进程编程(1)
【基础教程】C/C++多线程编程(2)
【基础教程】C/C++多线程编程(1)
【基础教程】C/C++动态库编程
【基础教程】C/C++静态库编程
【基础教程】photoshop图片混合公式
【基础教程】PyGame(12):旋转和缩放
【基础教程】PyGame(11):Surface操作
【基础教程】网络编程:Epoll(2)
【基础教程】网络编程:Epoll(1)
【基础教程】网络编程:IOCP(3)
【基础教程】网络编程:IOCP(2)
【基础教程】网络编程:IOCP(1)
【基础教程】网络编程:UDP
【基础教程】网络编程:TCP
【基础教程】Ubuntu安装Hadoop(4)
【基础教程】Ubuntu安装Hadoop(3)
【基础教程】Ubuntu安装Hadoop(2)
【基础教程】Ubuntu安装Hadoop(1)
【基础教程】Hadoop技术原理
【基础教程】Hadoop基本命令
【基础教程】Hadoop是什么东西
【基础教程】排序算法介绍
【基础教程】PyGame(10):声音控制
【基础教程】PyGame(9):鼠标事件(2)
【基础教程】PyGame(8):鼠标事件(1)
【基础教程】PyGame(7):键盘事件(2)
【基础教程】PyGame(6):键盘事件(1)
【基础教程】PyGame(5):显示图片
【基础教程】PyGame(4):显示文字
【基础教程】PyGame(3):图元绘制
【基础教程】PyGame(2):游戏框架
【基础教程】PyGame(1):开发环境搭建
【基础教程】Python(10):类定义
【基础教程】Python(9):自定义模块
【基础教程】Python(8):输入输出控制
【基础教程】Python(7):函数定义
【基础教程】Python(6):中断语句
【基础教程】Python(5):判断语句
【基础教程】Python(4):循环语句
【基础教程】Python(3):变量与运算符
【基础教程】Python(2):Hello
【基础教程】Python(1):介绍与安装
Copyright @ 2011-2018 by szc  桂ICP备11003301号-1  桂公网安备45040302000027号  Email:szcsoft@qq.com