久久精品精选,精品九九视频,www久久只有这里有精品,亚洲熟女乱色综合一区
    分享

    select()函數以及FD_ZERO、FD_SET、FD_CLR、FD_ISSET

     ColonelLee 2015-01-07

    標簽: 

    描述符

     

    函數

     

    集合

     

    it

    分類: Linux

    轉載:select()函數以及FD_ZERO、FD_SET、FD_CLR、FD_ISSET

        從別人的博客中轉載過來了這一篇文章,經過重新編輯排版之后展現于此,做一個知識點保存與學習。

        select函數用于在非阻塞中,當一個套接字或一組套接字有信號時通知你,系統提供select函數來實現多路復用輸入/輸出模型,原型:
    int select(int maxfd,fd_set *rdset,fd_set *wrset,fd_set *exset,struct timeval *timeout);

       所在的頭文件為:#include <sys/time.h> 和#include <unistd.h>

       先對函數中的參數做一個簡單的介紹。參數maxfd是需要監視的最大的文件描述符值+1;rdset,wrset,exset分別對應于需要檢測的可讀文件描述符的集合,可寫文件描述符的集 合及異常文件描述符的集合。struct timeval結構用于描述一段時間長度,如果在這個時間內,需要監視的描述符沒有事件發生則函數返回,返回值為0。 
        在這些參數中有一個類似于結構體的東西,
    fd_set,這是什么的名字,我們先來看看這個所具有的含義吧。這是一組文件描述字(fd)的集合,它用一位來表示一個fd,等等,文件描述字,熟悉吧,之前都把這個當做一個文件的路徑保存的地方了,也就是當做是一個文件的標志哦,現不在做猜想了,看看下文是怎么介紹的吧。

        對于fd_set類型通過下面四個宏來操作:
        FD_ZERO(fd_set *fdset) 將指定的文件描述符集清空,在對文件描述符集合進行設置前,必須對其進行初始化,如果不清空,由于在系統分配內存空間后,通常并不作清空處理,所以結果是不可知的。
        FD_SET(fd_set *fdset) 用于在文件描述符集合中增加一個新的文件描述符。
        FD_CLR(fd_set *fdset) 用于在文件描述符集合中刪除一個文件描述符。
        FD_ISSET(int fd,fd_set *fdset) 用于測試指定的文件描述符是否在該集合中。

        過去。。。。。。好長一大段哦,為了保證大家的注意力,我決定將這一大段長長的對過去情況的介紹去掉,直接尋找正題,保持目標的關注度啊。現在,UNIX系統通常會在頭文件<sys/select.h>中定義常量FD_SETSIZE,它是數據類型fd_set的描述字數量,其值通常是1024,這樣就能表示<1024的fd。

        好了在研究了一番關于fd_set的信息之后,再回到對select函數的理解上來吧。

        功能:測試指定的fd可讀?可寫?有異常條件待處理?
        readset  用來檢查可讀性的一組文件描述字。
        writeset 用來檢查可寫性的一組文件描述字。
        exceptset用來檢查是否有異常條件出現的文件描述字。(注:不包括錯誤)
        timeout  用于描述一段時間長度,如果在這個時間內,需要監視的描述符沒有事件發生則函數返回,返回值為0。

        對于select函數的功能簡單的說就是對文件fd做一個測試。測試結果有三種可能:
        1.timeout=NULL(阻塞:select將一直被阻塞,直到某個文件描述符上發生了事件)
        2.timeout所指向的結構設為非零時間(等待固定時間:如果在指定的時間段里有事件發生或者時間耗盡,函數均返回)
        3.timeout所指向的結構,時間設為0(非阻塞:僅檢測描述符集合的狀態,然后立即返回,并不等待外部事件的發生)

     

        返回值:返回對應位仍然為1的fd的總數。注意啦:只有那些可讀,可寫以及有異常條件待處理的fd位仍然為1。否則為0哦。舉個例子,比如recv(), 在沒有數據到來調用它的時候,你的線程將被阻塞,如果數據一直不來,你的線程就要阻塞很久.這樣顯然不好。所以采用select來查看套節字是否可讀(也就是是否有數據讀了) 。
    步驟如下——
    socket s;
    .....
    fd_set set;
    while(1)
    {
    FD_ZERO(&set);//將你的套節字集合清空
    FD_SET(s, &set);//加入你感興趣的套節字到集合,這里是一個讀數據的套節字s
    select(0,&set,NULL,NULL,NULL);//檢查套節字是否可讀,
    //很多情況下就是是否有數據(注意,只是說很多情況)
    //這里select是否出錯沒有寫
    if(FD_ISSET(s, &set) //檢查s是否在這個集合里面,
    { //select將更新這個集合,把其中不可讀的套節字去掉
    //只保留符合條件的套節字在這個集合里面
    recv(s,...);
    }
    //do something here
    }

        理解select模型的關鍵在于理解fd_set,為說明方便,取fd_set長度為1字節,fd_set中的每一bit可以對應一個文件描述符fd。則1字節長的fd_set最大可以對應8個fd。
       (1)執行fd_set set; FD_ZERO(&set);則set用位表示是0000,0000。
       (2)若fd=5,執行FD_SET(fd,&set);后set變為0001,0000(第5位置為1)

       (3)若再加入fd=2,fd=1,則set變為0001,0011
       (4)執行select(6,&set,0,0,0)阻塞等待
       (5)若fd=1,fd=2上都發生可讀事件,則select返回,此時set變為0000,0011。注意:沒有事件發生的fd=5被清空。


    基于上面的討論,可以輕松得出select模型的特點:
       (1)可監控的文件描述符個數取決與sizeof(fd_set)的值。

       (2)可以有效突破select可監控的文件描述符上限。
       (3)將fd加入select監控集的同時,還要再使用一個數據結構array保存放到select監控集中的fd,一是用于再select 返回后,array作為源數據和fd_set進行FD_ISSET判斷。二是select返回后會把以前加入的但并無事件發生的fd清空,則每次開始 select前都要重新從array取得fd逐一加入(FD_ZERO最先),掃描array的同時取得fd最大值maxfd,用于select的第一個 參數。
       (4)可見select模型必須在select前循環array(加fd,取maxfd),select返回后循環array(FD_ISSET判斷是否有時間發生)。


    使用select函數的過程一般是:
        先調用宏FD_ZERO將指定的fd_set清零,然后調用宏FD_SET將需要測試的fd加入fd_set,接著調用函數select測試fd_set中的所有fd,最后用宏FD_ISSET檢查某個fd在函數select調用后,相應位是否仍然為1。

    以下是一個測試單個文件描述字可讀性的例子:
    int isready(int fd)
    {
    int rc;
    fd_set fds;
    struct tim tv;
    FD_ZERO(&fds);
    FD_SET(fd,&fds);
    tv.tv_sec = tv.tv_usec = 0;
    rc = select(fd+1, &fds, NULL, NULL, &tv);
    if (rc < 0) //error
    return -1;
    return FD_ISSET(fd,&fds) ? 1 : 0;
    }

      本站是提供個人知識管理的網絡存儲空間,所有內容均由用戶發布,不代表本站觀點。請注意甄別內容中的聯系方式、誘導購買等信息,謹防詐騙。如發現有害或侵權內容,請點擊一鍵舉報。
      轉藏 分享 獻花(0

      0條評論

      發表

      請遵守用戶 評論公約

      類似文章 更多

      主站蜘蛛池模板: 无码人妻斩一区二区三区| 免费无码一区无码东京热| 永久免费av网站可以直接看的 | 91中文字幕一区在线| 白嫩少妇无套内谢视频| 亚洲精品漫画一二三区| 欧美一本大道香蕉综合视频| 亚洲高清WWW色好看美女| 2020国产激情视频在线观看 | 综合偷自拍亚洲乱中文字幕 | 国产最新进精品视频| 久久人搡人人玩人妻精品首页| YY111111少妇影院| 肥臀浪妇太爽了快点再快点| 成年女人片免费视频播放A| 国产午夜成人无码免费看| 人妻少妇精品一区二区三区| 亚洲最大日韩精品一区| 激情 自拍 另类 亚洲| 中文字幕乱伦视频| 成人免费无码大片A毛片抽搐色欲 成人啪精品视频网站午夜 | 国产成人综合95精品视频 | 国产L精品国产亚洲区久久| 国产日产精品系列| 99久久er热在这里只有精品99| 亚洲人成网网址在线看| 香港日本三级亚洲三级| 亚洲精品一区二区美女| 国产免费看插插插视频| 亚洲国产成人AV在线电影播放| 亚洲中文在线精品国产| 亚洲爆乳精品无码AAA片| 亚洲AV综合色区无码二区偷拍| 国产农村妇女毛片精品久久| 人妻久久久一区二区三区| 久久无码人妻丰满熟妇区毛片 | 中文字幕有码高清日韩| 大陆精大陆国产国语精品| 国产亚洲精AA在线观看SEE| 久久99精品久久久久久9| 成人免费乱码大片a毛片|