#include #include #include #include #include #include #include "pevent.h" #include "log.h" void event_init(event_ctx **ctx) { assert(ctx); if (!*ctx) *ctx = (event_ctx *) malloc(sizeof(**ctx)); assert(*ctx); memset(*ctx, 0, sizeof(**ctx)); (*ctx)->epoll_fd = -1; } int event_setup(event_ctx *ctx) { assert(ctx); if (ctx->epoll_fd < 0) ctx->epoll_fd = epoll_create1(0); return ctx->epoll_fd < 0; } int event_add_sock(event_ctx *ctx, psocket *sock) { int s; struct epoll_event ev = {0,{0}}; assert(ctx && sock); ev.data.fd = sock->fd; ev.events = EPOLLIN | EPOLLET; s = epoll_ctl(ctx->epoll_fd, EPOLL_CTL_ADD, sock->fd, &ev); if (s) return 1; return 0; } int event_add_fd(event_ctx *ctx, int fd) { int s; struct epoll_event ev = {0,{0}}; assert(ctx); ev.data.fd = fd; ev.events = EPOLLIN | EPOLLET; s = epoll_ctl(ctx->epoll_fd, EPOLL_CTL_ADD, fd, &ev); if (s) return 1; return 0; } int event_loop(event_ctx *ctx, on_event_cb on_event, void *user_data) { int n, i; sigset_t eset; assert(ctx && on_event); sigemptyset(&eset); ctx->active = 1; while (ctx->active) { n = epoll_pwait(ctx->epoll_fd, ctx->events, POTD_MAXEVENTS, -1, &eset); if (n < 0) break; for (i = 0; i < n; ++i) { if ((ctx->events[i].events & EPOLLERR) || (ctx->events[i].events & EPOLLHUP) || (!(ctx->events[i].events & EPOLLIN))) { E_STRERR("Event epoll for descriptor %d", ctx->events[i].data.fd); close(ctx->events[i].data.fd); continue; } else { if (on_event(ctx->events[i].data.fd, user_data)) continue; W2("Event callback failed: [fd: %d , npoll: %d]", ctx->events[i].data.fd, n); } } } return ctx->active == 0; }