poll和ppoll學習筆記

2021-10-10 10:14:12 字數 4332 閱讀 4253

poll/ppoll其實是同select/pselect類似的,用於同步多路i/o復用。poll/ppoll同select/pselect的最大區別在於poll/ppoll沒有最大連線數限制,因為poll/ppoll使用的用於儲存fd的集合是根據實際fd的數量動態分配的。此外,poll/ppoll監聽的事件型別更加的豐富/細緻些。

/* data structure describing a polling request.  */

struct pollfd

;

結構成員說明

fd:將要通過poll監聽的fd;

events:輸入引數,通過poll監聽fd的事件;

revents:輸出引數,poll監聽獲取到fd上實際發生的事件。

事件型別說明

pollin:in/out。在events中設定,表示在fd上監聽讀事件;在revents中設定,表示fd上發生了讀事件。

pollpri:in/out。在events中設定,表示在fd上監聽緊急資料讀事件;在revents中設定,表示fd上發生了緊急資料讀事件。緊急資料讀事件包括:

pollout:in/out。在events中設定,表示在fd上監聽寫事件;在revents中設定,表示fd上發生了寫事件。

pollrdhup:in/out。在events中設定,表示在fd上監聽讀掛起事件;在revents中設定,表示fd上發生了讀掛起事件。讀掛起事件是指在如tcp這樣的流式socket上發生的連線對端已經關閉了連線,而本段還沒關閉,使得該連線處於半連線狀態。處於該狀態下的fd是不允許寫操作,而允許讀操作。該事件是從linux核心版本2.6.17起才支援的。

pollerr:out。只會出現在revents中,表示fd上發生了錯誤。

pollhup:out。連線對端處於掛起狀態。

pollnval:out。無效的請求資料,通常是由於fd是無效的造成。

pollrdnorm:in/out。需在編譯時定義了巨集_xopen_source時才可以用。作用同pollin相同。

pollrdband:in/out。需在編譯時定義了巨集_xopen_source時才可以用。在events中設定,表示在fd上監聽具有優先順序頻帶資料的讀事件;在revents中設定,表示fd上發生了具有優先順序頻帶資料的讀事件。該事件通常linux上是無用的。

pollwrnorm:in/out。需在編譯時定義了巨集_xopen_source時才可以用。作用同pollout相同。

pollwrband:in/out。需在編譯時定義了巨集_xopen_source時才可以用。在events中設定,表示在fd上監聽優先資料的可寫入事件;在revents中設定,表示fd上發生了允許優先資料事件。

struct timespec 

;

#include

int

poll

(struct pollfd *fds, nfds_t nfds,

int timeout)

;

功能和select相同,同時監聽多個fd上的指定事件。直到乙個或多個fd上有乙個或多個事件發生時,或超時時才返回。

引數說明

fds:指向struct pollfd結構陣列的指標。陣列的每個struct pollfd結構體物件標識乙個fd及其相關事件。

nfds:表示fds陣列中的陣列成員個數,即一次poll操作監聽的fd的數量。

timeout:超時時間,單位毫秒。

返回值說明

成功返回大於等於0,返回大於0表示三個fd集合中觸發事件的fd的總個數,等於0表示等待超時;錯誤返回-1,錯誤碼從errno中獲取。

錯誤碼說明

efault:fds的記憶體位址錯誤,該位址不包含系統分配給程序的記憶體位址範圍內。

eintr:在事件監聽過程中被訊號中斷了。

einval:nfds的數量超過了系統限制(rlimit_notfile)。

enomem:記憶體不足錯誤,導致沒有記憶體用於poll內部使用。

#define _gnu_source

#include

要使用ppoll,需地定義巨集_gnu_source。

int

ppoll

(struct pollfd *fds, nfds_t nfds,

const

struct timespec *timeout_ts,

const sigset_t *sigmask)

;

ppoll功能同poll相似。

引數說明

fds:指向struct pollfd結構陣列的指標。陣列的每個struct pollfd結構體物件標識乙個fd及其相關事件。

nfds:表示fds陣列中的陣列成員個數,即一次poll操作監聽的fd的數量。

timeout_ts:超時時間,struct timespec結構形式,精度到納秒,實際在底層實現時精度只到了毫秒。

sigmask:指向乙個設定了訊號掩碼資訊的結構。如果不為null,則ppoll先將當前的訊號掩碼替換成sigmask指向的訊號掩碼,再執行poll,最後再替換會原來的訊號掩碼。

返回值說明

成功返回大於等於0,返回大於0表示三個fd集合中觸發事件的fd的總個數,等於0表示等待超時;錯誤返回-1,錯誤碼從errno中獲取。

錯誤碼說明

efault:fds的記憶體位址錯誤,該位址不包含系統分配給程序的記憶體位址範圍內。

eintr:在事件監聽過程中被訊號中斷了。

einval:nfds的數量超過了系統限制(rlimit_notfile)。

enomem:記憶體不足錯誤,導致沒有記憶體用於poll內部使用。

poll的timeout使用的是int型別,單位為毫秒,所以精度為毫秒;ppoll的timeout使用的是struct timespec,精度為納秒。

ppoll帶有sigmask引數,poll不帶sigmask引數。

#include

#include

#include

#include

#include

#include

intmain

(void)if

(fds[1]

.revents & pollout)

}else

printf

("no data within five seconds.\n");

free

(fds)

;exit

(exit_success)

;}

#include

#include

#include

#include

#include

#include

intmain

(void)if

(fds[1]

.revents & pollout)

}else

printf

("no data within five seconds.\n");

free

(fds)

;exit

(exit_success)

;}

poll 函式學習筆記 適合小白理解

在工作中遇到了poll 函式,決定來了解一下,參考 unix環境高階程式設計 我的理解是 poll 函式有乙個監聽池,我們把要監聽的檔案描述符以及我們對該描述符感興趣的條件 讀,寫等等 放進池子裡,然後就等poll 幫我們監聽,等poll 正常返回時,就是有描述符發生了變化,我們通過遍歷找到這個變化...

select和poll的用法

select 函式的作用 系統呼叫select和poll的後端實現,用這兩個系統呼叫來查詢裝置是否可讀寫,或是否處於某種狀態。如果poll為空,則驅動裝置會被認為即可讀又可寫,返回值是乙個狀態掩碼 如何使用select 函式?select 函式的介面主要是建立在一種叫 fd set 型別的基礎上。它...

poll 和select 使用總結

poll poll函式和select函式功能十分相似,函式宣告 int poll struct pollfd fds,nfds t nfds,int timeout 引數說明 fds 是乙個struct pollfd結構型別的陣列 用於存放需要檢測其狀態的socket描述符 每當 呼叫這個函式之後,...