1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143
|
Subject: [PATCH] unix: use libc-provided epoll_pwait wrapper
Bug-Debian: https://bugs.debian.org/841354
From: Luca Bruno <lucab@debian.org>
Date: Tue, 12 May 2015 22:04:35 +0200
Signed-off-by: Luca Bruno <lucab@debian.org>
We now use epoll_pwait() wrapper from libc, which takes care
of passing proper sigset_t size to kernel.
This is more portable, as some arch have a larger sigmask and
kernel explicitely checks size parameter to match sizeof(sigset_t).
Spotted as a uv_loop_configure regression on MIPS.
This fixes #335.
Many thanks to Tobias Leich who amended this
patch to fix #841354
---
src/unix/linux-core.c | 15 ++++++++-------
src/unix/linux-syscalls.c | 21 +++++++--------------
src/unix/linux-syscalls.h | 2 +-
3 files changed, 16 insertions(+), 22 deletions(-)
Index: libuv1/src/unix/linux-core.c
===================================================================
--- libuv1.orig/src/unix/linux-core.c 2016-05-29 19:25:29.000284791 +0200
+++ libuv1/src/unix/linux-core.c 2016-05-29 19:26:01.036605254 +0200
@@ -38,6 +38,7 @@
#include <sys/prctl.h>
#include <sys/sysinfo.h>
#include <unistd.h>
+#include <signal.h>
#include <fcntl.h>
#include <time.h>
@@ -186,8 +187,8 @@
QUEUE* q;
uv__io_t* w;
sigset_t sigset;
- uint64_t sigmask;
uint64_t base;
+ int is_sigmasked;
int have_signals;
int nevents;
int count;
@@ -236,11 +237,11 @@
w->events = w->pevents;
}
- sigmask = 0;
+ is_sigmasked = 0;
+ sigemptyset(&sigset);
if (loop->flags & UV_LOOP_BLOCK_SIGPROF) {
- sigemptyset(&sigset);
sigaddset(&sigset, SIGPROF);
- sigmask |= 1 << (SIGPROF - 1);
+ is_sigmasked = 1;
}
assert(timeout >= -1);
@@ -255,16 +256,16 @@
if (sizeof(int32_t) == sizeof(long) && timeout >= max_safe_timeout)
timeout = max_safe_timeout;
- if (sigmask != 0 && no_epoll_pwait != 0)
+ if (is_sigmasked != 0 && no_epoll_pwait != 0)
if (pthread_sigmask(SIG_BLOCK, &sigset, NULL))
abort();
- if (no_epoll_wait != 0 || (sigmask != 0 && no_epoll_pwait == 0)) {
+ if (no_epoll_wait != 0 || (is_sigmasked != 0 && no_epoll_pwait == 0)) {
nfds = uv__epoll_pwait(loop->backend_fd,
events,
ARRAY_SIZE(events),
timeout,
- sigmask);
+ &sigset);
if (nfds == -1 && errno == ENOSYS)
no_epoll_pwait = 1;
} else {
@@ -276,7 +277,7 @@
no_epoll_wait = 1;
}
- if (sigmask != 0 && no_epoll_pwait != 0)
+ if (is_sigmasked != 0 && no_epoll_pwait != 0)
if (pthread_sigmask(SIG_UNBLOCK, &sigset, NULL))
abort();
Index: libuv1/src/unix/linux-syscalls.c
===================================================================
--- libuv1.orig/src/unix/linux-syscalls.c 2016-05-29 19:25:29.000284791 +0200
+++ libuv1/src/unix/linux-syscalls.c 2016-05-29 19:25:29.000284791 +0200
@@ -22,6 +22,7 @@
#include "linux-syscalls.h"
#include <unistd.h>
#include <signal.h>
+#include <sys/epoll.h>
#include <sys/syscall.h>
#include <sys/types.h>
#include <errno.h>
@@ -334,21 +335,13 @@
struct uv__epoll_event* events,
int nevents,
int timeout,
- uint64_t sigmask) {
+ const sigset_t* sigmask) {
#if defined(__NR_epoll_pwait)
- int result;
- result = syscall(__NR_epoll_pwait,
- epfd,
- events,
- nevents,
- timeout,
- &sigmask,
- sizeof(sigmask));
-#if MSAN_ACTIVE
- if (result > 0)
- __msan_unpoison(events, sizeof(events[0]) * result);
-#endif
- return result;
+ return epoll_pwait(epfd,
+ (struct epoll_event *) events,
+ nevents,
+ timeout,
+ sigmask);
#else
return errno = ENOSYS, -1;
#endif
Index: libuv1/src/unix/linux-syscalls.h
===================================================================
--- libuv1.orig/src/unix/linux-syscalls.h 2016-05-29 19:25:29.000284791 +0200
+++ libuv1/src/unix/linux-syscalls.h 2016-05-29 19:25:29.000284791 +0200
@@ -124,7 +124,7 @@
struct uv__epoll_event* events,
int nevents,
int timeout,
- uint64_t sigmask);
+ const sigset_t* sigmask);
int uv__eventfd2(unsigned int count, int flags);
int uv__inotify_init(void);
int uv__inotify_init1(int flags);
|