Some parameters, struct and return values about epoll

#include <sys/epoll.h>

int epoll_create(int size);

int epoll_create1(int flags);

--When you program on linux kernel version higher than 2.6.8, you should ignore the parameter "size", you should give the paramater bigger than 0 sitll. The parameter is the file descriptor and can do dynamically allocation. So you should just give a bigger than 0 parameter to be compatible for lower version of linux kernel.

--in epoll_create1(), if the "flags" is 0, it is equal to epoll_create() except for the obsolete size abandonment. "flags" can be EPOLL_CLOEXEC, check O_CLOEXEC to understand EPOLL_CLOEXEC.

--return values: Nonnegative number (actually it's fd) for success, -1 for failure and please check error codes.

 

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

--There is 3 kinds of op values:

1)  EPOLL_CTL_ADD means register fd(file descriptor) into epfd and associate event with fd.

2)  EPOLL_CTL_MOD means modify the relationship between fd and event.

3)  EPOLL_CTL_DEL means the deletion of fd in epfd, event can be ignored and it can be NULL.

--As for struct 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 */

};

--The paramater events has forwads events:

EPOLLIN: while the fd it assciates can do read() operates

EPOLLOUT: write() operates

EPOLLRDHUP: (since linux 2.6.17)when socket close, or half close write part(when you use Edge-Triggered, this identification is good for test codes to check closing).

EPOLLPRI: when read() can do urgent data

EPOLLERR: while the file which it associate has something wrong, epoll_wait() will always wait this event, it is not a identification which must be set

EPOLLHUP: means hang up. epoll_wait() will always wait for this event, it is not a identification which must be set. When socket read data from somewhere(pipping or socket), this event is just identifying this is the end of reading(EOF). Any valid data is compeletely read, after that, it will return 0 for any read operation (EOF).

EPOLLET: set the file descriptor to Edge-Trigger, the default is Level-Triggered

EPOLLONESHOT: (since linux 2.6.17) set file descriptor to once mode. It means, it will be one time for epoll_wait() to catch  the event, after that you must call epoll_ctl() again to set it again.

return values: 0 for success, -1 for failuer and errno:

EBADF - epfd or fd is invalid

EEXIST - op is EPOLL_CTL_ADD, but the fd you want to register is already registered

EINVAL - epdf is not a epoll descriptor, or epfd is equal to fd, or op parameter illegal

ENOENT - op is POLL_CTL_MOD or POLL_CTL_DEL, but fd hasn't been registered into epoll.

ENOMEM - not enuf cache

EPERM - the objective fd doesn't support epoll

 

int epoll_wait(int epfd, struct epoll_event *events, int maxevents, int timeout);

int pepoll_wait(int epfd, struct epoll_event *events, int maxevents, int timeout, const sigset_t *sigmask);

--epoll_wait()is called for waiting for events in epfd, events point to stack area of events which caller can use. maxevents tell kernel the number of events and must larger than 0. time out is to formulate the blocking time(millisecond) of epoll_wait() and block until forward conditions:

1)  a fd trigger a event

2)  is interrupt by a signal handle function or timeout

if(timeout == -1)  forever waiting(block)

if(timeout == 0) return even if no events

--As for epoll_pwait()

ready = epoll_pwait(epfd, &events, maxevents, timeout, &sigmask);

at interior it is equal to:

pthread_sigmask(SIG_SETMASK, &sigmask, &origmask);

ready = epoll_wait(epfd, &events, maxevents, timeout);

pthread_sigmask(SIG_SETMASK, &origmask, NULL);

--Thus if &sigmask is NULL, it is equal to epoll_wait()

return values:

>0: numbers of ready IO events

=0: timeout

-1: failure and please check the error code:

EBADF - epfd is a invalid fd

EFAULT - no access authority of cache which pointer events point to

EINRE - this calling is interrupted by signal.

EINVAL - epfd is not an epoll descriptor, or maxevents <= 0

 

------OFFICIAL DEMO------

#define MAX_EVENTS 10

struct epoll_event ev, events[MAX_EVENTS];

int listen_sock, conn_sock, nfds, epollfd;

/* Code to set up listening socket, 'listen_sock', * (socket(), bind(), listen()) omitted */

epollfd = epoll_create1( 0 );

if ( epollfd == -1 ) {

    perror( "epoll_create1" );

    exit( EXIT_FAILURE );

}

ev.events = EPOLLIN;

ev.data.fd = listen_sock;

if ( epoll_ctl( epollfd, EPOLL_CTL_ADD, listen_sock, &ev ) == -1 ) {

    perror( "epoll_ctl: listen_sock" );

    exit( EXIT_FAILURE );

}

for (;; ) {

    nfds = epoll_wait( epollfd, events, MAX_EVENTS, -1 );

    if ( nfds == -1 ) {

        perror( "epoll_wait" );

        exit( EXIT_FAILURE );

    }

    for ( n = 0; n < nfds; ++n ) {

        if ( events[n].data.fd == listen_sock ) {

            conn_sock = accept( listen_sock, (struct sockaddr *) &local, &addrlen );

            if ( conn_sock == -1 ) {

                perror( "accept" );

                exit( EXIT_FAILURE );

            }

            setnonblocking( conn_sock );

            ev.events = EPOLLIN | EPOLLET;

            ev.data.fd = conn_sock;

            if ( epoll_ctl( epollfd, EPOLL_CTL_ADD, conn_sock, &ev ) == -1 ) {

                perror( "epoll_ctl: conn_sock" );

                exit( EXIT_FAILURE );

            }

        } else {

            do_use_fd( events[n].data.fd );

        }

    }

}


 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值