IOCP原理

// 完成端口.cpp : 定义控制台应用程序的入口点。
//

#include "stdafx.h"
#include "Winsock2.h"
#pragma comment(lib,"WS2_32.lib")


//完成键的结构体
typedef struct _COMPLETIONKEY
{
	SOCKET sock;
	int    ErrorCode;
}COMPLETIONKEY,*PCOMPLETIONKEY;

//自定义OverLapped结构体
typedef struct _MYOVERLAPPED
{
	WSAOVERLAPPED  stcOvlapped;
	WSABUF      WsaBuf;
	char        OverBuf[1024];
	int         nOperType;
}MYOVERLAPPED,*PMYOVERLAPPED;


DWORD ThreadProc(LPVOID prama)
{
	HANDLE hPort    = (HANDLE)prama;
	DWORD  dwSize   = 0;
	PCOMPLETIONKEY pCompletionKey = NULL;
	PMYOVERLAPPED   pOverLapped    = NULL;
	BOOL   bResult = FALSE;
	while (true)
	{
		bResult = GetQueuedCompletionStatus(
			hPort,
			&dwSize,
			(PULONG_PTR)&pCompletionKey,
			(LPOVERLAPPED*)&pOverLapped,
			-1);
		if (bResult == FALSE)
		{
			//处理错误
		}
		if (pCompletionKey->ErrorCode == -1)
		{
			PMYOVERLAPPED pOverlapped = new MYOVERLAPPED;
			memset(pOverlapped,0,sizeof(MYOVERLAPPED));
			//投递一个退出通知
			PostQueuedCompletionStatus(hPort,0,
				(ULONG_PTR)pCompletionKey,
				(LPOVERLAPPED)pOverlapped);
			ExitThread(0);

		}
		if (pOverLapped != NULL)
		{
			if (pOverLapped->nOperType == 1)
			{
				printf("%s",pOverLapped->OverBuf);

				//消耗掉了之前的接受操作,
				//再投递一个接收数据的操作
				DWORD  dwSize = 0;
				WSABUF  WsaBuf;
				WsaBuf.buf = pOverLapped->OverBuf;
				WsaBuf.len = 1024;
				WSARecv(
					pCompletionKey->sock,
					&WsaBuf,
					1,
					&dwSize,
					0,(LPWSAOVERLAPPED)pOverLapped,NULL);
			}
		}
		
	}
}

void Init()
{
	WSADATA stcWsaData = {0};
	WSAStartup(MAKEWORD(2,2),&stcWsaData);
}

SOCKET InitTcp()
{
	SOCKET sock = WSASocket(AF_INET,SOCK_STREAM,0,NULL,0,
		WSA_FLAG_OVERLAPPED);
	if (sock == INVALID_SOCKET)
	{
		return INVALID_SOCKET;
	}
	sockaddr_in BindAddr;
	BindAddr.sin_family = AF_INET;
	BindAddr.sin_port   = htons(1234);
	BindAddr.sin_addr.S_un.S_addr = 
		inet_addr("192.168.199.119");
	if (SOCKET_ERROR ==	bind(
		sock,(sockaddr*)&BindAddr,
		sizeof(sockaddr_in)))
	{
		return INVALID_SOCKET;
	}
	if (SOCKET_ERROR == listen(sock,4))
	{
		closesocket(sock);
		return INVALID_SOCKET;
	}
	return sock;
}





int _tmain(int argc, _TCHAR* argv[])
{
	//1 初始化Socket和完成端口
	Init();
	SOCKET sock  = InitTcp();
	HANDLE hPort = CreateIoCompletionPort(
		INVALID_HANDLE_VALUE,
		0,
		0,
		4
		);
	//2 获取CPU核心数量,并开启工作线程
	SYSTEM_INFO  stcSystemInfo = {0};
	GetSystemInfo(&stcSystemInfo);
	for (DWORD i =0;i<stcSystemInfo.dwNumberOfProcessors*2;i++)
	{
		CreateThread(0,0,(LPTHREAD_START_ROUTINE)ThreadProc,
			(LPVOID)hPort,0,0);
	}
	while (TRUE)
	{
		sockaddr_in ClientAddr;
		int nAddrSize = sizeof(sockaddr_in);
		SOCKET Clientsock = accept(
			sock,
			(sockaddr*)&ClientAddr,
			&nAddrSize);
		//将客户端Socket和完成端口绑定
		PCOMPLETIONKEY pClientComKey= new COMPLETIONKEY;
		pClientComKey->sock = Clientsock;
		CreateIoCompletionPort((HANDLE)Clientsock,hPort,
			(ULONG_PTR)pClientComKey,0);

		DWORD  dwSize = 0;
		DWORD  dwRubbish = 0;
		PMYOVERLAPPED pOverlapped = new MYOVERLAPPED;
		//将OverLapped结构初始化为0
		memset(pOverlapped,0,sizeof(MYOVERLAPPED));

		pOverlapped->nOperType = 1;
		pOverlapped->WsaBuf.buf = pOverlapped->OverBuf;
		pOverlapped->WsaBuf.len = 1024;
		//投递一个接收操作,并不能真正的获取到数据
		WSARecv(
			pClientComKey->sock,
			&(pOverlapped->WsaBuf),
			1,
			&dwSize,
			&dwRubbish,(LPWSAOVERLAPPED)pOverlapped,NULL);
	}
	return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
注:更多资料请根据压缩文件中的《更多资料.txt》文件的介绍免费获取 =====★★★★史上最全的IOCP资料大全★★★★============== 目的:研究和分享基于IOCP通讯模型的服务器端及即时通讯客户端相关技术 语言:Delphi\C++ 欢迎给位朋友加入 -------------------------前言------------------------ 最近在编写即时通讯工具,于是便参考和搜罗了网上大量的文章和源码, 对IOCP涉及的相关技术进行了广泛和深入的研究。 IOCP涉及的关键知识点有很多很多,这方面的文章也非常多, 但是很多讲述的都是某方面的,为了帮大家甄选资料,我决定分享给大家。 以下是我搜集的部分IOCP相关的资料目录,有需要的请加我QQ和QQ群,无偿分享: --------------------------IOCP部分相关知识点------------------ 线程池,Socket连接池、数据库连接池、内存池及内存管理 防DDos攻击、防只连接不发送消息及Setsockopt相关设置 WSAENOBUFS及0缓冲的WSARecive投递 优雅的链接关闭方法及shutdown、TIME_WAIT 及注册表设置:TcpNumConnections/MaxUserPort 多核多线程、生产消费者模型、读写者模型、多线程无锁环形队列及LockFreeList概念 Socket重用、端口重用 心跳、粘包、乱序 ------------------------我收集的文章及源码的部分目录---------------------- ------------------------供大家搜索资料时参考----------------------------------
### 回答1: IOCP(输入输出完成端口)是一种高效的异步通信模型,UDP是一种面向无连接的传输协议,C是一种编程语言。所以"IOCP UDP C demo"可以理解为使用IOCP和C语言实现的UDP通信示例。 在这个示例中,我们可以使用C语言编写一个简单的程序,通过UDP协议进行数据的传输。首先,我们需要创建一个UDP套接字,通过该套接字与远程主机进行通信。接收方需要创建一个IOCP对象,并将套接字绑定在该IOCP对象上,以便异步地接收数据。 发送方可以使用sendto函数将数据发送给接收方。数据可以是任意类型的,例如文字、图片或者音频等。发送方只需要将数据写入套接字,并指定接收方的IP地址和端口号。 接收方在接收到数据时,会触发IOCP的回调函数,我们可以在回调函数中对数据进行处理。可以根据需要对数据进行解析或者存储等操作。 在整个过程中,IOCP实现了异步的数据传输,可以同时处理多个连接,提高了系统的性能。 总结来说,IOC UDP C demo是一个使用IOCP和C语言实现的UDP通信示例程序,可以通过该示例了解IOCP的异步通信模型和C语言的编程技巧,以及UDP协议在网络通信中的应用。 ### 回答2: IOCP(Input/Output Completion Port)是一种高效的 I/O 处理机制,UDP(User Datagram Protocol)是一种无连接的传输协议,C 是一种编程语言,在下面的回答中,我将简要介绍 IOCp UDP C demo 的相关内容。 IOCp UDP C demo 是一个基于 IOCP 模型开发的 UDP 网络通信的示例程序,使用 C 语言编写。该示例程序主要用于展示如何使用 IOCP 来实现高性能的 UDP 网络通信。 在该示例程序中,首先会创建一个 IOCP 对象,并将其与一个 UDP 套接字绑定。然后,程序会创建多个工作者线程,每个线程都会调用 GetQueuedCompletionStatus 函数来等待 I/O 完成的通知。 当有 I/O 操作完成时,工作者线程会收到通知,并通过相关的数据结构获取完成的信息,比如接收到的数据、发送是否成功等。然后,线程根据具体的业务需求进行相应的处理,比如解析接收到的数据、发送响应等。 IOCP 可以实现高并发的网络通信,因为它使用了事件驱动的模型,可以同时处理多个 I/O 请求。而 UDP 是无连接的,没有连接的建立和断开的开销,适合实时性要求较高的应用场景,比如游戏中的实时通信。 通过这个示例程序,可以更好地了解 IOCP 模型的基本原理和使用方法,以及如何使用 UDP 进行高性能的网络通信。同时,可以根据自身需求进行改进和扩展,实现更复杂的网络应用。 总之,IOCp UDP C demo 是一个基于 IOCP 模型开发的 UDP 网络通信的示例程序,通过该示例程序可以学习和理解 IOCP 模型和 UDP 网络通信的相关知识。 ### 回答3: IOC(Input/Output Completion Ports)是一种高效的异步输入输出模型,UDP(User Datagram Protocol)是一种无连接的传输协议,而C Demo则指的是使用C语言编写的演示程序。 IOC和UDP可以结合使用,通过IOC监听网络IO事件,实现高吞吐量的UDP数据传输。在C Demo中,我们可以使用Windows平台提供的IOCP机制,在C语言中编写代码来演示如何使用IOC和UDP。 在C Demo中,首先需要创建一个套接字,用于监听和发送UDP数据包。然后,创建一个IOCP对象,用于管理套接字的异步IO操作。接下来,将套接字与IOCP对象关联起来,以便在IO事件发生时能够收到通知。 在程序运行时,我们可以使用多个线程来同时处理多个UDP连接。每个线程都会从IOCP对象中获取完成的IO事件,并根据不同的事件类型进行相应的处理。例如,当有数据包到达时,可以直接从套接字中读取数据并进行处理;当需要发送数据包时,可以将数据包写入套接字并发送。 通过使用IOC和UDP,我们可以实现高效的网络数据传输,同时充分利用系统资源,提高程序的性能和响应速度。C Demo可以帮助我们理解和学习如何使用IOC和UDP编写高性能的网络应用程序。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值