C/C++网络编程在windows将socket设置为非阻塞

文章介绍了在socket编程中如何设置套接字的阻塞和非阻塞模式,特别是在Windows和Linux系统下的差异。在Windows中使用ioctlsocket函数,而在Linux中使用fcntl函数。提供了一个名为SetBlock的函数示例,用于跨平台设置阻塞状态。此外,还展示了ioctlsocket函数的使用,包括设置非阻塞模式、获取缓冲区信息和控制Nagle算法等。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在 socket编程中,对于socket的读写默认都是阻塞的,但有的情况我们需要将其设置为非阻塞,比如做多路复用,或者通过select实现连接超时等功能,将socket设置为非阻塞,在windows和linux中的接口有所不同,在windows中使用ioctlsocket函数,在linux中使用 fcntl函数,下面我们做一个跨平台设置阻塞的函数SetBlock。

bool SetBlock(int sock,bool isblock)
{
	int re = 0;
//通过宏区分windows和linux,如果是windows64位程序判断 _WIN64宏
#ifdef WIN32
	unsigned long ul = 0;
	if(!isblock) ul = 1;
	re = ioctlsocket(sock, FIONBIO, (unsigned long*)&ul);
#else
	//先取到现有描述符属性,保证本次更改不变动原有属性
	int flags = fcntl(sock, F_GETFL, 0);
	if (flags < 0) {
		return false;
	}
	if(isblock)
	{
		flags = flags & ~O_NONBLOCK;
	}
	else
	{
		flags = flags | O_NONBLOCK;
	}
	re = fcntl(sock, F_SETFL, flags);
#endif
	if (re != 0) return false;
	return true;
}
//设置非阻塞
static void setnonblocking(int sockfd) {
    unsigned long on = 1;  //此值为0,会将套接字设置为阻塞(默认的);为1设置为非阻塞
    if (0 != ioctlsocket(sockfd, FIONBIO, &on))
    {
        /* Handle failure. */
    }
}

ioctlsocket 函数使用方法

ioctlsocket 函数是用于控制一个套接字的 I/O 操作的函数,该函数是在 Windows 系统下使用的。它的原型如下:

cCopy codeint ioctlsocket(
  SOCKET s,
  long   cmd,
  u_long *argp
);

其中,s 是要控制的套接字,cmd 是要执行的操作,argp 是传递给操作的参数。ioctlsocket 函数返回操作的结果,如果返回值为 SOCKET_ERROR,则说明操作失败。

ioctlsocket 函数可以用来执行各种操作,比如:

  • 获取套接字的当前状态(FIONREADFIONBIO
  • 设置套接字的非阻塞模式(FIONBIO
  • 设置套接字的缓冲区大小(SO_RCVBUFSO_SNDBUF
  • 获取套接字的错误状态(SIO_GET_ERROR
  • 禁止或启用 Nagle 算法(TCP_NODELAY

下面是一些使用 ioctlsocket 函数的示例代码:

cCopy code// 获取套接字接收缓冲区中可读取的字节数
u_long bytesAvailable;
ioctlsocket(socket, FIONREAD, &bytesAvailable);

// 设置套接字为非阻塞模式
u_long nonBlocking = 1;
ioctlsocket(socket, FIONBIO, &nonBlocking);

// 设置套接字的接收缓冲区大小为 1024 字节
int bufferSize = 1024;
setsockopt(socket, SOL_SOCKET, SO_RCVBUF, (const char*)&bufferSize, sizeof(bufferSize));

// 获取套接字的错误状态
u_long socketError;
ioctlsocket(socket, SIO_GET_ERROR, &socketError);

// 禁用 Nagle 算法
u_long nagleOff = 1;
setsockopt(socket, IPPROTO_TCP, TCP_NODELAY, (const char*)&nagleOff, sizeof(nagleOff));

需要注意的是,ioctlsocket 函数的使用方法和参数取值会因具体操作而有所不同,具体操作和参数请参考相关的文档或 API 参考手册。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

机载软件与适航

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值