mirror of
https://github.com/xen-project/xen.git
synced 2026-10-29 10:40:03 +01:00
libxl: fd events: Break out libxl__fd_poll_recheck
Replaces two call sites where a rechecking poll() was open-coded. No functional change, other than to highly unusual error path diagnosis, and debug and error message output. Signed-off-by: Ian Jackson <Ian.Jackson@eu.citrix.com> CC: Jim Fehlig <jfehlig@suse.com> CC: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com> Tested-by: Jim Fehlig <jfehlig@suse.com> Acked-by: Ian Campbell <ian.campbell@citrix.com>
This commit is contained in:
1 parent
269ac7369d
commit
12f005c19d
2 files changed
+34
-33
No files matched your search
+30
-33
@@ -236,6 +236,29 @@ void libxl__ev_fd_deregister(libxl__gc *gc, libxl__ev_fd *ev)
|
||||
CTX_UNLOCK;
|
||||
}
|
||||
|
||||
short libxl__fd_poll_recheck(libxl__egc *egc, int fd, short events) {
|
||||
struct pollfd check;
|
||||
int r;
|
||||
|
||||
for (;;) {
|
||||
check.fd = fd;
|
||||
check.events = events;
|
||||
r = poll(&check, 1, 0);
|
||||
DBG("poll recheck fd=%d r=%d revents=%#x", fd, r, check.revents);
|
||||
if (!r)
|
||||
break;
|
||||
if (r==1)
|
||||
break;
|
||||
assert(r<0);
|
||||
if (errno != EINTR) {
|
||||
LIBXL__EVENT_DISASTER(egc, "failed poll to check for fd", errno, 0);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
assert(!!r == !!check.revents);
|
||||
return check.revents;
|
||||
}
|
||||
|
||||
/*
|
||||
* timeouts
|
||||
*/
|
||||
@@ -661,9 +684,8 @@ static void evtchn_fd_callback(libxl__egc *egc, libxl__ev_fd *ev,
|
||||
{
|
||||
EGC_GC;
|
||||
libxl__ev_evtchn *evev;
|
||||
int r, rc;
|
||||
int rc;
|
||||
evtchn_port_or_error_t port;
|
||||
struct pollfd recheck;
|
||||
|
||||
rc = evtchn_revents_check(egc, revents);
|
||||
if (rc) return;
|
||||
@@ -674,21 +696,10 @@ static void evtchn_fd_callback(libxl__egc *egc, libxl__ev_fd *ev,
|
||||
* held continuously since someone noticed the fd. Normally
|
||||
* this wouldn't be a problem but evtchn devices don't always
|
||||
* honour O_NONBLOCK (see xenctrl.h). */
|
||||
|
||||
recheck.fd = fd;
|
||||
recheck.events = POLLIN;
|
||||
recheck.revents = 0;
|
||||
r = poll(&recheck, 1, 0);
|
||||
DBG("ev_evtchn recheck r=%d revents=%#x", r, recheck.revents);
|
||||
if (r < 0) {
|
||||
LIBXL__EVENT_DISASTER(egc,
|
||||
"unexpected failure polling event channel fd for recheck",
|
||||
errno, 0);
|
||||
return;
|
||||
}
|
||||
if (r == 0)
|
||||
revents = libxl__fd_poll_recheck(egc,fd,POLLIN);
|
||||
if (!revents)
|
||||
break;
|
||||
rc = evtchn_revents_check(egc, recheck.revents);
|
||||
rc = evtchn_revents_check(egc, revents);
|
||||
if (rc) return;
|
||||
|
||||
/* OK, that's that workaround done. We can actually check for
|
||||
@@ -1239,24 +1250,10 @@ void libxl_osevent_occurred_fd(libxl_ctx *ctx, void *for_libxl,
|
||||
if (!ev) goto out;
|
||||
if (ev->fd != fd) goto out;
|
||||
|
||||
struct pollfd check;
|
||||
for (;;) {
|
||||
check.fd = fd;
|
||||
check.events = ev->events;
|
||||
int r = poll(&check, 1, 0);
|
||||
if (!r)
|
||||
goto out;
|
||||
if (r==1)
|
||||
break;
|
||||
assert(r<0);
|
||||
if (errno != EINTR) {
|
||||
LIBXL__EVENT_DISASTER(egc, "failed poll to check for fd", errno, 0);
|
||||
goto out;
|
||||
}
|
||||
}
|
||||
short current_revents = libxl__fd_poll_recheck(egc, ev->fd, ev->events);
|
||||
|
||||
if (check.revents)
|
||||
ev->func(egc, ev, fd, ev->events, check.revents);
|
||||
if (current_revents)
|
||||
ev->func(egc, ev, fd, ev->events, current_revents);
|
||||
|
||||
out:
|
||||
CTX_UNLOCK;
|
||||
|
||||
@@ -1587,6 +1587,10 @@ _hidden int libxl__device_from_disk(libxl__gc *gc, uint32_t domid,
|
||||
libxl_device_disk *disk,
|
||||
libxl__device *device);
|
||||
|
||||
/* Calls poll() again - useful to check whether a signaled condition
|
||||
* is still true. Cannot fail. Returns currently-true revents. */
|
||||
_hidden short libxl__fd_poll_recheck(libxl__egc *egc, int fd, short events);
|
||||
|
||||
_hidden char *libxl__uuid2string(libxl__gc *gc, const libxl_uuid uuid);
|
||||
|
||||
struct libxl__xen_console_reader {
|
||||
|
||||