summaryrefslogtreecommitdiffstats
path: root/src/io-epoll.c
diff options
context:
space:
mode:
authorTimo Teras <timo.teras@iki.fi>2009-11-25 15:11:20 +0200
committerTimo Teras <timo.teras@iki.fi>2009-11-25 15:11:20 +0200
commit2b19cc385163a43b1d559074a795a8aaab751185 (patch)
tree322473e3446153c1bbaac8d6d990734b09d15977 /src/io-epoll.c
parentfc1044daf51f32b9d85f8497e4e0bd5a3c1e7fe9 (diff)
downloadlibtf-2b19cc385163a43b1d559074a795a8aaab751185.tar.bz2
libtf-2b19cc385163a43b1d559074a795a8aaab751185.tar.xz
libtf: implement basic networking i/o
pretty much untested. also some slight changes to how scheduler is invoked.
Diffstat (limited to 'src/io-epoll.c')
-rw-r--r--src/io-epoll.c43
1 files changed, 25 insertions, 18 deletions
diff --git a/src/io-epoll.c b/src/io-epoll.c
index 56d0743..5e28de8 100644
--- a/src/io-epoll.c
+++ b/src/io-epoll.c
@@ -14,15 +14,12 @@
#include <fcntl.h>
#include <unistd.h>
#include <sys/epoll.h>
+#include <sys/socket.h>
#include <libtf/io.h>
#include <libtf/fiber.h>
-#define TF_FD_AUTOCLOSE 1
-#define TF_FD_RESTORE_BLOCKING 2
-#define TF_FD_STREAM_ORIENTED 4
-
-static int tf_fd_init(struct tf_fd *fd, int kfd, int flags)
+static int tf_fd_created(struct tf_fd *fd)
{
struct tf_poll_data *pd = &tf_get_scheduler()->poll_data;
struct epoll_event ev;
@@ -30,20 +27,28 @@ static int tf_fd_init(struct tf_fd *fd, int kfd, int flags)
ev.events = EPOLLIN | EPOLLOUT | EPOLLET;
ev.data.ptr = fd;
- r = epoll_ctl(pd->epoll_fd, EPOLL_CTL_ADD, kfd, &ev);
- if (r < 0) {
+ r = epoll_ctl(pd->epoll_fd, EPOLL_CTL_ADD, fd->fd, &ev);
+ if (unlikely(r < 0)) {
TF_BUG_ON(errno == EEXIST);
- return -errno;
+ r = -errno;
+ return r;
}
- fd->fd = kfd;
- fd->flags = flags;
- fd->waiting_fiber = NULL;
+ return 0;
+}
+static int tf_fd_destroyed(struct tf_fd *fd)
+{
+ struct tf_poll_data *pd = &tf_get_scheduler()->poll_data;
+
+ if (fd->flags & TF_FD_AUTOCLOSE)
+ return 0;
+
+ epoll_ctl(pd->epoll_fd, EPOLL_CTL_DEL, fd->fd, NULL);
return 0;
}
-static void tf_fd_wait(struct tf_fd *fd, int events)
+static void tf_fd_monitor(struct tf_fd *fd, int events)
{
struct tf_poll_data *pd = &tf_get_scheduler()->poll_data;
@@ -53,7 +58,7 @@ static void tf_fd_wait(struct tf_fd *fd, int events)
pd->num_waiters++;
}
-static void tf_fd_release(struct tf_fd *fd)
+static void tf_fd_unmonitor(struct tf_fd *fd)
{
struct tf_poll_data *pd = &tf_get_scheduler()->poll_data;
@@ -76,21 +81,23 @@ int tf_poll(tf_mtime_diff_t timeout)
struct tf_poll_data *pd = &tf_get_scheduler()->poll_data;
struct epoll_event events[64];
struct tf_fd *fd;
- int ret = (timeout == 0) ? TF_WAKEUP_TIMEOUT : TF_WAKEUP_FD;
- int r, i;
+ int r, i, ret;
if (timeout == 0 && pd->num_waiters == 0)
- return ret;
+ return TF_WAKEUP_TIMEOUT;
+ ret = TF_WAKEUP_TIMEOUT;
do {
r = epoll_wait(pd->epoll_fd, events, array_size(events), timeout);
+ if (r == 0)
+ break;
+
for (i = 0; i < r; i++) {
fd = (struct tf_fd *) events[i].data.ptr;
if (likely(fd->events & events[i].events))
tf_wakeup(fd->waiting_fiber, TF_WAKEUP_FD);
}
- if (timeout != 0)
- ret = TF_WAKEUP_FD;
+ ret = TF_WAKEUP_FD;
timeout = 0;
} while (unlikely(r == array_size(events)));