mirror of https://github.com/tmux/tmux.git
Don't attempt to open() the tty path, rely on the client sending its stdin fd
with imsg and fatal if it doesn't, then set the FD_CLOEXEC flag in tty_init instead of tty_open to prevent them leaking into child processes if any are created between the two calls. This bumps the protocol version, so the tmux server should be killed before upgrading.pull/1/head
parent
0a9005678d
commit
64caf59e84
11
client.c
11
client.c
|
@ -45,7 +45,7 @@ client_init(char *path, struct client_ctx *cctx, int cmdflags, int flags)
|
|||
struct winsize ws;
|
||||
size_t size;
|
||||
int fd, fd2, mode;
|
||||
char *name, *term;
|
||||
char *term;
|
||||
char rpathbuf[MAXPATHLEN];
|
||||
|
||||
if (realpath(path, rpathbuf) == NULL)
|
||||
|
@ -113,13 +113,8 @@ server_started:
|
|||
*data.term = '\0';
|
||||
}
|
||||
|
||||
*data.tty = '\0';
|
||||
if ((name = ttyname(STDIN_FILENO)) == NULL)
|
||||
fatal("ttyname failed");
|
||||
if (strlcpy(data.tty, name, sizeof data.tty) >= sizeof data.tty)
|
||||
fatalx("ttyname failed");
|
||||
|
||||
fd2 = dup(STDIN_FILENO);
|
||||
if ((fd2 = dup(STDIN_FILENO)) == -1)
|
||||
fatal("dup failed");
|
||||
imsg_compose(&cctx->ibuf, MSG_IDENTIFY,
|
||||
PROTOCOL_VERSION, -1, fd2, &data, sizeof data);
|
||||
}
|
||||
|
|
19
server-msg.c
19
server-msg.c
|
@ -74,6 +74,8 @@ server_msg_dispatch(struct client *c)
|
|||
case MSG_IDENTIFY:
|
||||
if (datalen != sizeof identifydata)
|
||||
fatalx("bad MSG_IDENTIFY size");
|
||||
if (imsg.fd == -1)
|
||||
fatalx("MSG_IDENTIFY missing fd");
|
||||
memcpy(&identifydata, imsg.data, sizeof identifydata);
|
||||
|
||||
server_msg_identify(c, &identifydata, imsg.fd);
|
||||
|
@ -243,21 +245,13 @@ error:
|
|||
void
|
||||
server_msg_identify(struct client *c, struct msg_identify_data *data, int fd)
|
||||
{
|
||||
c->tty.sx = data->sx;
|
||||
if (c->tty.sx == 0)
|
||||
c->tty.sx = 80;
|
||||
c->tty.sy = data->sy;
|
||||
if (c->tty.sy == 0)
|
||||
c->tty.sy = 24;
|
||||
|
||||
c->cwd = NULL;
|
||||
data->cwd[(sizeof data->cwd) - 1] = '\0';
|
||||
if (*data->cwd != '\0')
|
||||
c->cwd = xstrdup(data->cwd);
|
||||
|
||||
data->tty[(sizeof data->tty) - 1] = '\0';
|
||||
data->term[(sizeof data->term) - 1] = '\0';
|
||||
tty_init(&c->tty, fd, data->tty, data->term);
|
||||
tty_init(&c->tty, fd, data->term);
|
||||
if (data->flags & IDENTIFY_UTF8)
|
||||
c->tty.flags |= TTY_UTF8;
|
||||
if (data->flags & IDENTIFY_256COLOURS)
|
||||
|
@ -267,6 +261,13 @@ server_msg_identify(struct client *c, struct msg_identify_data *data, int fd)
|
|||
if (data->flags & IDENTIFY_HASDEFAULTS)
|
||||
c->tty.term_flags |= TERM_HASDEFAULTS;
|
||||
|
||||
c->tty.sx = data->sx;
|
||||
if (c->tty.sx == 0)
|
||||
c->tty.sx = 80;
|
||||
c->tty.sy = data->sy;
|
||||
if (c->tty.sy == 0)
|
||||
c->tty.sy = 24;
|
||||
|
||||
c->flags |= CLIENT_TERMINAL;
|
||||
}
|
||||
|
||||
|
|
6
tmux.h
6
tmux.h
|
@ -19,7 +19,7 @@
|
|||
#ifndef TMUX_H
|
||||
#define TMUX_H
|
||||
|
||||
#define PROTOCOL_VERSION 1
|
||||
#define PROTOCOL_VERSION 2
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/time.h>
|
||||
|
@ -328,8 +328,6 @@ struct msg_command_data {
|
|||
};
|
||||
|
||||
struct msg_identify_data {
|
||||
char tty[TTY_NAME_MAX];
|
||||
|
||||
char cwd[MAXPATHLEN];
|
||||
|
||||
char term[TERMINAL_LENGTH];
|
||||
|
@ -1200,7 +1198,7 @@ void tty_putcode2(struct tty *, enum tty_code_code, int, int);
|
|||
void tty_puts(struct tty *, const char *);
|
||||
void tty_putc(struct tty *, u_char);
|
||||
void tty_pututf8(struct tty *, const struct grid_utf8 *);
|
||||
void tty_init(struct tty *, int, char *, char *);
|
||||
void tty_init(struct tty *, int, char *);
|
||||
void tty_start_tty(struct tty *);
|
||||
void tty_stop_tty(struct tty *);
|
||||
void tty_detect_utf8(struct tty *);
|
||||
|
|
46
tty.c
46
tty.c
|
@ -44,16 +44,31 @@ void tty_cell(struct tty *,
|
|||
const struct grid_cell *, const struct grid_utf8 *);
|
||||
|
||||
void
|
||||
tty_init(struct tty *tty, int fd, char *path, char *term)
|
||||
tty_init(struct tty *tty, int fd, char *term)
|
||||
{
|
||||
tty->path = xstrdup(path);
|
||||
tty->fd = fd;
|
||||
int mode;
|
||||
char *path;
|
||||
|
||||
memset(tty, 0, sizeof *tty);
|
||||
tty->log_fd = -1;
|
||||
|
||||
if (term == NULL || *term == '\0')
|
||||
tty->termname = xstrdup("unknown");
|
||||
else
|
||||
tty->termname = xstrdup(term);
|
||||
|
||||
if ((mode = fcntl(fd, F_GETFL)) == -1)
|
||||
fatal("fcntl failed");
|
||||
if (fcntl(fd, F_SETFL, mode|O_NONBLOCK) == -1)
|
||||
fatal("fcntl failed");
|
||||
if (fcntl(fd, F_SETFD, FD_CLOEXEC) == -1)
|
||||
fatal("fcntl failed");
|
||||
tty->fd = fd;
|
||||
|
||||
if ((path = ttyname(fd)) == NULL)
|
||||
fatalx("ttyname failed");
|
||||
tty->path = xstrdup(path);
|
||||
|
||||
tty->flags = 0;
|
||||
tty->term_flags = 0;
|
||||
}
|
||||
|
@ -61,27 +76,14 @@ tty_init(struct tty *tty, int fd, char *path, char *term)
|
|||
int
|
||||
tty_open(struct tty *tty, const char *overrides, char **cause)
|
||||
{
|
||||
int mode;
|
||||
int fd;
|
||||
|
||||
if (tty->fd == -1) {
|
||||
tty->fd = open(tty->path, O_RDWR|O_NONBLOCK);
|
||||
if (tty->fd == -1) {
|
||||
xasprintf(cause, "%s: %s", tty->path, strerror(errno));
|
||||
return (-1);
|
||||
if (debug_level > 3) {
|
||||
fd = open("tmux.out", O_WRONLY|O_CREAT|O_TRUNC, 0644);
|
||||
if (fd != -1 && fcntl(fd, F_SETFD, FD_CLOEXEC) == -1)
|
||||
fatal("fcntl failed");
|
||||
tty->log_fd = fd;
|
||||
}
|
||||
}
|
||||
|
||||
if ((mode = fcntl(tty->fd, F_GETFL)) == -1)
|
||||
fatal("fcntl failed");
|
||||
if (fcntl(tty->fd, F_SETFL, mode|O_NONBLOCK) == -1)
|
||||
fatal("fcntl failed");
|
||||
if (fcntl(tty->fd, F_SETFD, FD_CLOEXEC) == -1)
|
||||
fatal("fcntl failed");
|
||||
|
||||
if (debug_level > 3)
|
||||
tty->log_fd = open("tmux.out", O_WRONLY|O_CREAT|O_TRUNC, 0644);
|
||||
else
|
||||
tty->log_fd = -1;
|
||||
|
||||
tty->term = tty_term_find(tty->termname, tty->fd, overrides, cause);
|
||||
if (tty->term == NULL) {
|
||||
|
|
Loading…
Reference in New Issue