Print this page
8634 epoll fails to wake on certain edge-triggered conditions
8635 epoll should not emit POLLNVAL
8636 recursive epoll should emit EPOLLRDNORM
Reviewed by: Jerry Jelinek <jerry.jelinek@joyent.com>
Reviewed by: Robert Mustacchi <rm@joyent.com>
Reviewed by: Toomas Soome <tsoome@me.com>
Reviewed by: Igor Kozhukhov <igor@dilos.org>
*** 23,33 ****
/*
* Copyright (c) 1989, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright 2011 Nexenta Systems, Inc. All rights reserved.
! * Copyright 2015 Joyent, Inc.
*/
/*
* Generic vnode operations.
*/
--- 23,33 ----
/*
* Copyright (c) 1989, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright 2011 Nexenta Systems, Inc. All rights reserved.
! * Copyright 2017 Joyent, Inc.
*/
/*
* Generic vnode operations.
*/
*** 414,423 ****
--- 414,434 ----
/* ARGSUSED */
int
fs_poll(vnode_t *vp, short events, int anyyet, short *reventsp,
struct pollhead **phpp, caller_context_t *ct)
{
+ /*
+ * Reject all attempts for edge-triggered polling. These should only
+ * occur when regular files are added to a /dev/poll handle which is in
+ * epoll mode. The Linux epoll does not allow epoll-ing on regular
+ * files at all, so rejecting EPOLLET requests is congruent with those
+ * expectations.
+ */
+ if (events & POLLET) {
+ return (EPERM);
+ }
+
*reventsp = 0;
if (events & POLLIN)
*reventsp |= POLLIN;
if (events & POLLRDNORM)
*reventsp |= POLLRDNORM;
*** 425,435 ****
*reventsp |= POLLRDBAND;
if (events & POLLOUT)
*reventsp |= POLLOUT;
if (events & POLLWRBAND)
*reventsp |= POLLWRBAND;
! *phpp = !anyyet && !*reventsp ? &fs_pollhd : (struct pollhead *)NULL;
return (0);
}
/*
* POSIX pathconf() support.
--- 436,454 ----
*reventsp |= POLLRDBAND;
if (events & POLLOUT)
*reventsp |= POLLOUT;
if (events & POLLWRBAND)
*reventsp |= POLLWRBAND;
! /*
! * Emitting a pollhead without the intention of issuing pollwakeup()
! * calls against it is a recipe for trouble. It's only acceptable in
! * this case since the above logic matches practically all useful
! * events.
! */
! if (*reventsp == 0 && !anyyet) {
! *phpp = &fs_pollhd;
! }
return (0);
}
/*
* POSIX pathconf() support.