diff --git a/src/sys/unix/selector/epoll.rs b/src/sys/unix/selector/epoll.rs index 7853ed6548..31812aa0fd 100644 --- a/src/sys/unix/selector/epoll.rs +++ b/src/sys/unix/selector/epoll.rs @@ -23,21 +23,18 @@ pub struct Selector { impl Selector { pub fn new() -> io::Result { - // According to libuv, `EPOLL_CLOEXEC` is not defined on Android API < - // 21. But `EPOLL_CLOEXEC` is an alias for `O_CLOEXEC` on that platform, - // so we use it instead. - #[cfg(target_os = "android")] - let flag = libc::O_CLOEXEC; - #[cfg(not(target_os = "android"))] - let flag = libc::EPOLL_CLOEXEC; - - syscall!(epoll_create1(flag)).map(|ep| Selector { - #[cfg(debug_assertions)] - id: NEXT_ID.fetch_add(1, Ordering::Relaxed), - ep, - #[cfg(debug_assertions)] - has_waker: AtomicBool::new(false), - }) + // Using epoll_create() followed by fcntl() instead of epoll_create1() with EPOLL_CLOEXEC + // flag for backwards compatibility. Android API < 21 does not have EPOLL_CLOEXEC constant + // defined and Android API 16 does not have epoll_create1() at all. + syscall!(epoll_create(1)) + .and_then(|ep| syscall!(fcntl(ep, libc::F_SETFD, libc::FD_CLOEXEC)).map(|_| ep)) + .map(|ep| Selector { + #[cfg(debug_assertions)] + id: NEXT_ID.fetch_add(1, Ordering::Relaxed), + ep, + #[cfg(debug_assertions)] + has_waker: AtomicBool::new(false), + }) } pub fn try_clone(&self) -> io::Result {