poll学习笔记

来源:互联网 发布:淘宝网页点击没反应 编辑:程序博客网 时间:2024/05/01 03:32

poll函数

  poll函数起源于SVR3,最初局限于流设备。SVR4取消了这种限制,允许poll工作在任何描述字上。poll提供的功能与select类似,不过在处理流设备时,它能够提供额外的信息。

#include <poll.h>int pollresult = poll(struct pollfd *fdarray, unsigned long nfds, int timeout);
第一个参数fdarray是指向一个结构数组第一个元素的指针。每个数组元素都是一个pollfd结构:

struct pollfd{  int fd;              //descriptor to check  short events;    //events of interest on fd  short revents;   //events that occurred on fd};

结构数组中的 events 成员指定要测试的条件,而返回的结果则在保存在 revents。常用条件及含意说明如下:

poll函数可用的测试值

常量说明POLLIN普通或优先级带数据可读POLLRDNORM普通数据可读POLLRDBAND优先级带数据可读POLLPRI高优先级数据可读POLLOUT普通数据可写POLLWRNORM普通数据可写POLLWRBAND优先级带数据可写POLLERR发生错误POLLHUP发生挂起POLLNVAL描述字不是一个打开的文件

注意:后三个只能作为描述字的返回结果存储在revents中,而不能作为测试条件用于events中。

第二个参数nfds是用来指定数组fdarray的长度。

最后一个参数timeout是指定poll函数返回前等待多长时间。它的取值如下:

timeout值说明-1永远等待0立即返回,不阻塞进程>0等待指定数目的毫秒数

返回的结果pollresult 

 -1poll函数调用失败 0在timeout内,数组fdarray中没有任何文件描述符准备好读、写或出错,poll函数正常超时返回。 >0数组fdarray中准备好读、写或出错状态的那些文件描述符的总数量



之后根据  fdarray[0].revents & POLLIN来判断是哪个发生了变化,之后直接read就可以了。

例子

#include <stdio.h>#include <poll.h>#include <linux/inotify.h>#include <string.h>#define OPEN_MAX 3#define PATH_MAX 3#define READ_MAX 1000int main(int argc,char *argv[]){  char *path = "/root/test/poll_test";  char *paths[PATH_MAX] = {    "/dev/input/event0",    "/dev/input/event2"   };   struct pollfd client[OPEN_MAX];   char read_buf[READ_MAX];   struct inotify_event *event;   char *event_buf[512];    printf("poll_test ...\n");   int fd = inotify_init();   if(fd != -1){     int wd = inotify_add_watch(fd,path,IN_DELETE | IN_CREATE);     client[0].fd = fd;     client[0].events = POLLIN;     printf("open inotify\n");   }else{     printf("error:inotify can't open.\n");     return -1;   }   int i;   for(i = 1;i<OPEN_MAX; i++){    fd = open(paths[i-1],O_RDWR);    if(fd != -1){      client[i].fd = fd;      client[i].events = POLLIN;      printf("open %s\n",paths[i-1]);    }else{      printf("error:%s can't open.\n",paths[i]);      return -1;    }   }           printf("ok. start loop.\n");   int pollresult = 0;   while(1){      if(pollresult == -1){        printf("error.\n");        return -1;      }else if(pollresult == 0){      }else{        if(client[0].revents & POLLIN){ //判断           size_t len = read(client[0].fd,event_buf,512);           event = (struct inotify_event *)(event_buf);           if(event->mask & IN_CREATE){              printf("notify:add %s \n",event->name);           }else{              printf("notify:delete %s \n",event->name);           }        }        for(i = 1;i<OPEN_MAX;i++){           if(client[i].revents & POLLIN){ //判断              int readsize = read(client[i].fd,read_buf,READ_MAX);              printf("read:%s\n",read_buf);           }        }       }      printf("polling...\n");        pollresult = poll(client,OPEN_MAX,-1); //轮询   } }