chiark
/
gitweb
/
~ianmdlvl
/
elogind.git
/ blobdiff
commit
grep
author
committer
pickaxe
?
search:
re
summary
|
shortlog
|
log
|
commit
|
commitdiff
|
tree
raw
|
inline
| side by side
sd-event: EPOLLONESHOT only disables event reporting after an event. The fd is still...
[elogind.git]
/
src
/
libsystemd-bus
/
sd-event.c
diff --git
a/src/libsystemd-bus/sd-event.c
b/src/libsystemd-bus/sd-event.c
index 3599d90eb41b683d253f28e1cb6e4c4d9b265716..b3a6c5b08ae845aed532723c60aec8590ce8b1c9 100644
(file)
--- a/
src/libsystemd-bus/sd-event.c
+++ b/
src/libsystemd-bus/sd-event.c
@@
-1384,8
+1384,20
@@
static int event_arm_timer(
assert_se(next);
a = prioq_peek(earliest);
assert_se(next);
a = prioq_peek(earliest);
- if (!a || a->enabled == SD_EVENT_OFF)
+ if (!a || a->enabled == SD_EVENT_OFF) {
+
+ if (*next == (usec_t) -1)
+ return 0;
+
+ /* disarm */
+ r = timerfd_settime(timer_fd, TFD_TIMER_ABSTIME, &its, NULL);
+ if (r < 0)
+ return r;
+
+ *next = (usec_t) -1;
+
return 0;
return 0;
+ }
b = prioq_peek(latest);
assert_se(b && b->enabled != SD_EVENT_OFF);
b = prioq_peek(latest);
assert_se(b && b->enabled != SD_EVENT_OFF);
@@
-1418,24
+1430,17
@@
static int process_io(sd_event *e, sd_event_source *s, uint32_t events) {
s->io.revents = events;
s->io.revents = events;
- /*
- If this is a oneshot event source, then we added it to the
- epoll with EPOLLONESHOT, hence we know it's not registered
- anymore. We can save a syscall here...
- */
-
- if (s->enabled == SD_EVENT_ONESHOT)
- s->io.registered = false;
-
return source_set_pending(s, true);
}
return source_set_pending(s, true);
}
-static int flush_timer(sd_event *e, int fd, uint32_t events) {
+static int flush_timer(sd_event *e, int fd, uint32_t events
, usec_t *next
) {
uint64_t x;
ssize_t ss;
assert(e);
assert(fd >= 0);
uint64_t x;
ssize_t ss;
assert(e);
assert(fd >= 0);
+ assert(next);
+
assert_return(events == EPOLLIN, -EIO);
ss = read(fd, &x, sizeof(x));
assert_return(events == EPOLLIN, -EIO);
ss = read(fd, &x, sizeof(x));
@@
-1449,6
+1454,8
@@
static int flush_timer(sd_event *e, int fd, uint32_t events) {
if (ss != sizeof(x))
return -EIO;
if (ss != sizeof(x))
return -EIO;
+ *next = (usec_t) -1;
+
return 0;
}
return 0;
}
@@
-1578,7
+1585,7
@@
static int process_signal(sd_event *e, uint32_t events) {
}
static int source_dispatch(sd_event_source *s) {
}
static int source_dispatch(sd_event_source *s) {
- int r;
+ int r
= 0
;
assert(s);
assert(s->pending || s->type == SOURCE_QUIT);
assert(s);
assert(s->pending || s->type == SOURCE_QUIT);
@@
-1732,7
+1739,7
@@
int sd_event_run(sd_event *e, uint64_t timeout) {
m = epoll_wait(e->epoll_fd, ev_queue, EPOLL_QUEUE_MAX,
timeout == (uint64_t) -1 ? -1 : (int) ((timeout + USEC_PER_MSEC - 1) / USEC_PER_MSEC));
if (m < 0) {
m = epoll_wait(e->epoll_fd, ev_queue, EPOLL_QUEUE_MAX,
timeout == (uint64_t) -1 ? -1 : (int) ((timeout + USEC_PER_MSEC - 1) / USEC_PER_MSEC));
if (m < 0) {
- r =
m
;
+ r =
errno == EAGAIN || errno == EINTR ? 0 : -errno
;
goto finish;
}
goto finish;
}
@@
-1741,9
+1748,9
@@
int sd_event_run(sd_event *e, uint64_t timeout) {
for (i = 0; i < m; i++) {
if (ev_queue[i].data.ptr == INT_TO_PTR(SOURCE_MONOTONIC))
for (i = 0; i < m; i++) {
if (ev_queue[i].data.ptr == INT_TO_PTR(SOURCE_MONOTONIC))
- r = flush_timer(e, e->monotonic_fd, ev_queue[i].events);
+ r = flush_timer(e, e->monotonic_fd, ev_queue[i].events
, &e->monotonic_next
);
else if (ev_queue[i].data.ptr == INT_TO_PTR(SOURCE_REALTIME))
else if (ev_queue[i].data.ptr == INT_TO_PTR(SOURCE_REALTIME))
- r = flush_timer(e, e->realtime_fd, ev_queue[i].events);
+ r = flush_timer(e, e->realtime_fd, ev_queue[i].events
, &e->realtime_next
);
else if (ev_queue[i].data.ptr == INT_TO_PTR(SOURCE_SIGNAL))
r = process_signal(e, ev_queue[i].events);
else
else if (ev_queue[i].data.ptr == INT_TO_PTR(SOURCE_SIGNAL))
r = process_signal(e, ev_queue[i].events);
else