IO多路复用------poll系统调用

poll系统调用和selct类似,也是在指定时间内轮询一定数量的文件描述符,以测试其中是否有就绪者。

poll 的原型如下:

 int poll(struct pollfd *fds,nfds_ t nfds,int timeout);

struct pollfd
{
   int fd; //要监控的描述符
   short events; //对应fd描述符要监控的事件POLLIN-可读、 POLLOUT-可写
   short revents;//fd描述符在监控调用返回后实际就绪的事件
}
fds:监控的描述符集合
nfds:监控的描述符或者说事件数量,决定了从fds地址处拷贝多少数据到内核进行监控
timeout:超时等待时间-单位毫秒; -1表示阻塞, 0表示非阻塞
返回值:成功返回实际就绪的事件个数;超时返回0;出错返回-1

操作流程

1.定义描述符的事件结构体或者结构体数组,将需要监控的描述符以及事件信息填充到节点中
        示例: struct polfd fds[10]; fds[0].fd = 0; fds[0].events = POLLIN;
2.发起监控调用,将有效节点数据拷贝到内核进行监控,超时或者有描述符就绪则调用返回.
        监控调用返回前操作: poll会将 监控的结构体节点的revents成员设置为实际就绪的事件
3.监控调用返回后,程序中遍历结构体数组,通过revents成员确定描述符就绪了什么事件,进而进行对应操作


优缺点分析

优点:
       
poll采用事件结构体的方式对描述符进行监控,相较于select简化了操作流程
        poll所能监控的描述符数量没有最大上限限制
缺点:
       
poll每次监控都还是需要将监控数据从用户态拷贝到内核态进行
        pol监控原理与select相同也是在内核中多次遍历处理,导致性能会随着描述符的增多而下降
        poll无法直接获取就绪的描述符进行操作,需要遍历监控事件结构体数组通过每个元素的成员变量revents确定描述符就绪了什么事件
        poll不支持跨平台,只能类unix操作系统下使用

使用poll对标准写操作描述符进行监控 

#include <unistd.h>
#include <poll.h>
#include <stdio.h>

int main()
{
    struct pollfd fds[10];
    fds[0].fd = 0;
    fds[0].events = POLLIN;

    while (1)
    {
        int ret = poll(fds, 1, 3000);
        if (ret < 0)
        {
            perror("poll");
            return -1;
        }
        if (ret == 0)
        {
            printf("time out\n");
            continue;
        }
        for (int i = 0; i < 10; ++i)
        {
            //读事件
            if (fds[i].revents == POLLIN)
            {
                char buf[1024] = {0};
                read(fds[0].fd, buf, 1023);
                printf("%s\n");
            }
            else if(fds[i].revents == POLLOUT)
            {
                //...写事件
            }
        }
    }
    return 0;
}


   

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值