Socket套接字编程(I/O复用 select)

本文介绍了如何使用select函数进行Socket套接字编程,包括对TCP客户端和服务器端代码的修改,以及如何将多进程并发服务器端改写为单进程多连接池的select模型。重点讲解了select在监视读写文件描述符和异常集合时的作用,以及参数timeval的使用。同时,展示了在连接池中管理连接状态的变化过程。
摘要由CSDN通过智能技术生成

select函数

/* According to POSIX.1-2001 */
#include <sys/select.h>
/* According to earlier standards */
#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>
int select(int nfds, fd_set *readfds, fd_set *writefds,fd_set *exceptfds, struct timeval *timeout);
void FD_CLR(int fd, fd_set *set);//测试某个描述符是否在集合内
int  FD_ISSET(int fd, fd_set *set);//从集合内把一个描述符移除
void FD_SET(int fd, fd_set *set);//把一个描述符加入集合
void FD_ZERO(fd_set *set);//清空描述符集合

监视readfds查看读文件描述符集合会不会被堵塞(即使end-of-file,也是可读的)。

监视writefds查看写文件描述符集合会不会被堵塞。

监视exceptfd异常文件描述符集合是否出现了异常。主要用来读取OOB数据,异常并不是指出错。

注意当一个套接口出错时,它会变得既可读又可写。

如果有了状态改变,会将其他fd清零,只有那些发生改变了的fd保持置位,以用来指示set中的哪一个改变了状态。

参数n是所有set里所有fd里,具有最大值的那个fd的值加1

struct timeval 
{long    tv_sec;  /* seconds */
 long    tv_usec; /* microseconds */
};

timeval是从调用开始到select返回前,会经历的最大等待时间。

当timeval为 NULL时,会无限等待,直到被信号打断时返回1, errno 设置成 EINTR。

当timeval.tv_sec 为0并且 timeval.tv_usec为0,不等待立即返回。

当timeval.tv_sec非0 或者timeval.tv_usec非 0,等待特定时间长度, 超时返回0。



#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <signal.h>
#include <sys/wait.h>
#include <stdlib.h>
#include <stdio.h>
#include <errno.h>
#include <string.h>
int main(void)
{
    fd_set rfds;
    struct timeval tv;
    FD_ZERO(&rfds);
    FD_SET(0,&rfds);
    tv.tv_sec=10;
    tv.tv_usec=0;
    int ret=select(1,&rfds,NULL,NULL,&tv);
    if(ret==-1)
        printf("error!\n");
    else if(ret)
    {
        if(FD_ISSET(0,&rfds))
            printf("fd0 data is avilable!\n");
    }
    else
        printf("no data coming in 2 sec!\n");
    return 0;
}

用select对TCP客户端代码进行修改

#include<stdio.h>
#include<unistd.h>
#include<stdlib.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<sys/select.h>
#include<netinet/in.h>
#include<arpa/inet.h>
#include<string.h>
#include<signal.h>
#include <errno.h>
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值