diff options
author | Timothy J Fontaine <tjfontaine@gmail.com> | 2014-03-10 17:01:21 -0700 |
---|---|---|
committer | Timothy J Fontaine <tjfontaine@gmail.com> | 2014-03-10 17:01:21 -0700 |
commit | e92d35d80be6e193cb547e94c6fbf3654542dbaa (patch) | |
tree | bede6f090b8cca1397728634b03b31cfa7a4334c /deps/uv/src/unix/tty.c | |
parent | b444392a98e66b49dfee8c7e36c59d4e7c6ea1ac (diff) | |
download | android-node-v8-e92d35d80be6e193cb547e94c6fbf3654542dbaa.tar.gz android-node-v8-e92d35d80be6e193cb547e94c6fbf3654542dbaa.tar.bz2 android-node-v8-e92d35d80be6e193cb547e94c6fbf3654542dbaa.zip |
uv: Upgrade to v0.11.22
Diffstat (limited to 'deps/uv/src/unix/tty.c')
-rw-r--r-- | deps/uv/src/unix/tty.c | 65 |
1 files changed, 50 insertions, 15 deletions
diff --git a/deps/uv/src/unix/tty.c b/deps/uv/src/unix/tty.c index ca9459dd0d..c7ed101a75 100644 --- a/deps/uv/src/unix/tty.c +++ b/deps/uv/src/unix/tty.c @@ -35,26 +35,61 @@ static uv_spinlock_t termios_spinlock = UV_SPINLOCK_INITIALIZER; int uv_tty_init(uv_loop_t* loop, uv_tty_t* tty, int fd, int readable) { - uv__stream_init(loop, (uv_stream_t*)tty, UV_TTY); + int flags; + int newfd; + int r; + + newfd = -1; + + uv__stream_init(loop, (uv_stream_t*) tty, UV_TTY); + + /* Reopen the file descriptor when it refers to a tty. This lets us put the + * tty in non-blocking mode without affecting other processes that share it + * with us. + * + * Example: `node | cat` - if we put our fd 0 in non-blocking mode, it also + * affects fd 1 of `cat` because both file descriptors refer to the same + * struct file in the kernel. When we reopen our fd 0, it points to a + * different struct file, hence changing its properties doesn't affect + * other processes. + */ + if (isatty(fd)) { + newfd = uv__open_cloexec("/dev/tty", O_RDWR); + + if (newfd == -1) + return -errno; -#if defined(__APPLE__) - { - int err = uv__stream_try_select((uv_stream_t*) tty, &fd); - if (err) - return err; + r = uv__dup2_cloexec(newfd, fd); + if (r < 0 && r != -EINVAL) { + /* EINVAL means newfd == fd which could conceivably happen if another + * thread called close(fd) between our calls to isatty() and open(). + * That's a rather unlikely event but let's handle it anyway. + */ + uv__close(newfd); + return r; + } + + fd = newfd; } -#endif /* defined(__APPLE__) */ - - if (readable) { - uv__nonblock(fd, 1); - uv__stream_open((uv_stream_t*)tty, fd, UV_STREAM_READABLE); - } else { - /* Note: writable tty we set to blocking mode. */ - uv__stream_open((uv_stream_t*)tty, fd, UV_STREAM_WRITABLE); - tty->flags |= UV_STREAM_BLOCKING; + +#if defined(__APPLE__) + r = uv__stream_try_select((uv_stream_t*) tty, &fd); + if (r) { + if (newfd != -1) + uv__close(newfd); + return r; } +#endif + if (readable) + flags = UV_STREAM_READABLE; + else + flags = UV_STREAM_WRITABLE; + + uv__nonblock(fd, 1); + uv__stream_open((uv_stream_t*) tty, fd, flags); tty->mode = 0; + return 0; } |