TKeed tk_epoll_add函數詳解

tk_epoll_add函數定義於epoll.c:

int tk_epoll_add(int epoll_fd, int fd, tk_http_request_t* request, int events) {
	struct epoll_event event;
	event.data.ptr = (void*)request;//初始化事件地址,在webserver中是一個http請求
	event.events = events;//events傳入幾個宏的集合,表示epoll感興趣的事件
	int ret = epoll_ctl(epoll_fd, EPOLL_CTL_ADD, fd, &event);//註冊監聽描述符
	if (ret == -1)
		return -1;
}

該函數在main.c中的調用如下:

tk_epoll_add(epoll_fd, listen_fd, request, (EPOLLIN | EPOLLET));

功能:註冊監聽描述符
傳入的fd爲listen_fd,即註冊監聽描述符。
epoll_event結構體:

 typedef union epoll_data {
      void *ptr;
      int fd;
      __uint32_t u32;
      __uint64_t u64;
  } epoll_data_t;
  
  struct epoll_event {
     __uint32_t events; /* Epoll events */
    epoll_data_t data; /* User data variable */
};

event.events可以是以下幾個宏的集合:

EPOLLIN :表示對應的文件描述符可以讀(包括對端SOCKET正常關閉);

EPOLLOUT:表示對應的文件描述符可以寫;

EPOLLPRI:表示對應的文件描述符有緊急的數據可讀(這裏應該表示有帶外數據到來);

EPOLLERR:表示對應的文件描述符發生錯誤;

EPOLLHUP:表示對應的文件描述符被掛斷;

EPOLLET: 將EPOLL設爲邊緣觸發(Edge Triggered)模式,這是相對於水平觸發(Level Triggered)來說的;

EPOLLONESHOT:只監聽一次事件,當監聽完這次事件之後,如果還需要繼續監聽這個socket的話,需要再次把這個socket加入到EPOLL隊列裏。

因此,傳入本函數的第四個參數 EPOLLIN | EPOLLET 實際上做了兩件事:
1、該fd對應的文件描述符可以讀
2、將EPOLL設置爲ET模式

epoll_ctl函數:

int epoll_ctl(int epfd, int op, int fd, struct epoll_event *event);

epoll的事件註冊函數,它不同與select()是在監聽事件時告訴內核要監聽什麼類型的事件,而是在這裏先註冊要監聽的事件類型。第一個參數是epoll_create()的返回值,第二個參數表示動作,用三個宏來表示:

EPOLL_CTL_ADD:註冊新的fd到epfd中;

EPOLL_CTL_MOD:修改已經註冊的fd的監聽事件;

EPOLL_CTL_DEL:從epfd中刪除一個fd;

第三個參數是需要監聽的fd,第四個參數是告訴內核需要監聽什麼事件。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章