1
0
mirror of https://github.com/tmate-io/tmate-ssh-server.git synced 2020-11-18 19:53:51 -08:00

Support -c for new-session, based on code from J Raynor.

This commit is contained in:
nicm 2013-10-10 12:07:36 +00:00
parent fc54bfe6b0
commit b822d24b15
5 changed files with 67 additions and 49 deletions

View File

@ -35,7 +35,6 @@ const struct cmd_entry cmd_new_window_entry = {
CMD_TARGET_WINDOW_USAGE " [command]", CMD_TARGET_WINDOW_USAGE " [command]",
0, 0,
NULL, NULL,
NULL,
cmd_new_window_exec cmd_new_window_exec
}; };
@ -103,7 +102,7 @@ cmd_new_window_exec(struct cmd *self, struct cmd_q *cmdq)
cmd = options_get_string(&s->options, "default-command"); cmd = options_get_string(&s->options, "default-command");
else else
cmd = args->argv[0]; cmd = args->argv[0];
cwd = cmd_get_default_path(cmdq, args_get(args, 'c')); cwd = cmdq_default_path(cmdq, args_get(args, 'c'));
if (idx == -1) if (idx == -1)
idx = -1 - options_get_number(&s->options, "base-index"); idx = -1 - options_get_number(&s->options, "base-index");

View File

@ -35,7 +35,7 @@ cmdq_new(struct client *c)
cmdq->dead = 0; cmdq->dead = 0;
cmdq->client = c; cmdq->client = c;
cmdq->client_exit = 0; cmdq->client_exit = -1;
TAILQ_INIT(&cmdq->queue); TAILQ_INIT(&cmdq->queue);
cmdq->item = NULL; cmdq->item = NULL;
@ -259,7 +259,7 @@ cmdq_continue(struct cmd_q *cmdq)
} while (cmdq->item != NULL); } while (cmdq->item != NULL);
empty: empty:
if (cmdq->client_exit) if (cmdq->client_exit > 0)
cmdq->client->flags |= CLIENT_EXIT; cmdq->client->flags |= CLIENT_EXIT;
if (cmdq->emptyfn != NULL) if (cmdq->emptyfn != NULL)
cmdq->emptyfn(cmdq); /* may free cmdq */ cmdq->emptyfn(cmdq); /* may free cmdq */
@ -283,3 +283,27 @@ cmdq_flush(struct cmd_q *cmdq)
} }
cmdq->item = NULL; cmdq->item = NULL;
} }
/* Get default path using command queue. */
const char *
cmdq_default_path(struct cmd_q *cmdq, const char *cwd)
{
struct client *c = cmdq->client;
struct session *s;
const char *current;
if ((s = cmd_current_session(cmdq, 0)) == NULL)
return (NULL);
if (cwd == NULL)
cwd = options_get_string(&s->options, "default-path");
if (c != NULL && c->session == NULL && c->cwd != NULL)
current = c->cwd;
else if (s->curw != NULL)
current = get_proc_cwd(s->curw->window->active->fd);
else
current = NULL;
return (cmd_default_path(s->cwd, current, cwd));
}

View File

@ -38,7 +38,6 @@ const struct cmd_entry cmd_split_window_entry = {
CMD_TARGET_PANE_USAGE " [command]", CMD_TARGET_PANE_USAGE " [command]",
0, 0,
cmd_split_window_key_binding, cmd_split_window_key_binding,
NULL,
cmd_split_window_exec cmd_split_window_exec
}; };
@ -84,7 +83,7 @@ cmd_split_window_exec(struct cmd *self, struct cmd_q *cmdq)
cmd = options_get_string(&s->options, "default-command"); cmd = options_get_string(&s->options, "default-command");
else else
cmd = args->argv[0]; cmd = args->argv[0];
cwd = cmd_get_default_path(cmdq, args_get(args, 'c')); cwd = cmdq_default_path(cmdq, args_get(args, 'c'));
type = LAYOUT_TOPBOTTOM; type = LAYOUT_TOPBOTTOM;
if (args_has(args, 'h')) if (args_has(args, 'h'))

61
cmd.c
View File

@ -255,8 +255,6 @@ cmd_parse(int argc, char **argv, const char *file, u_int line, char **cause)
goto usage; goto usage;
if (entry->args_upper != -1 && args->argc > entry->args_upper) if (entry->args_upper != -1 && args->argc > entry->args_upper)
goto usage; goto usage;
if (entry->check != NULL && entry->check(args) != 0)
goto usage;
cmd = xcalloc(1, sizeof *cmd); cmd = xcalloc(1, sizeof *cmd);
cmd->entry = entry; cmd->entry = entry;
@ -1281,68 +1279,55 @@ cmd_template_replace(const char *template, const char *s, int idx)
} }
/* /*
* Return the default path for a new pane, using the given path or the * Return the default path for a new pane. Several special values are accepted:
* default-path option if it is NULL. Several special values are accepted: the * the empty string or relative path for the current working directory,
* empty string or relative path for the current pane's working directory, ~ * ~ for the user's home, - for the base working directory, . for the server
* for the user's home, - for the session working directory, . for the tmux * working directory.
* server's working directory. The default on failure is the session's working
* directory.
*/ */
const char * const char *
cmd_get_default_path(struct cmd_q *cmdq, const char *cwd) cmd_default_path(const char *base, const char *current, const char *in)
{ {
struct client *c = cmdq->client;
struct session *s;
struct environ_entry *envent;
const char *root; const char *root;
struct environ_entry *envent;
char tmp[MAXPATHLEN]; char tmp[MAXPATHLEN];
struct passwd *pw; struct passwd *pw;
int n; int n;
size_t skip; size_t skip;
static char path[MAXPATHLEN]; static char path[MAXPATHLEN];
if ((s = cmd_current_session(cmdq, 0)) == NULL)
return (NULL);
if (cwd == NULL)
cwd = options_get_string(&s->options, "default-path");
skip = 1; skip = 1;
if (strcmp(cwd, "$HOME") == 0 || strncmp(cwd, "$HOME/", 6) == 0) { if (strcmp(in, "$HOME") == 0 || strncmp(in, "$HOME/", 6) == 0) {
/* User's home directory - $HOME. */ /* User's home directory - $HOME. */
skip = 5; skip = 5;
goto find_home; goto find_home;
} else if (cwd[0] == '~' && (cwd[1] == '\0' || cwd[1] == '/')) { } else if (in[0] == '~' && (in[1] == '\0' || in[1] == '/')) {
/* User's home directory - ~. */ /* User's home directory - ~. */
goto find_home; goto find_home;
} else if (cwd[0] == '-' && (cwd[1] == '\0' || cwd[1] == '/')) { } else if (in[0] == '-' && (in[1] == '\0' || in[1] == '/')) {
/* Session working directory. */ /* Base working directory. */
root = s->cwd; root = base;
goto complete_path; goto complete_path;
} else if (cwd[0] == '.' && (cwd[1] == '\0' || cwd[1] == '/')) { } else if (in[0] == '.' && (in[1] == '\0' || in[1] == '/')) {
/* Server working directory. */ /* Server working directory. */
if (getcwd(tmp, sizeof tmp) != NULL) { if (getcwd(tmp, sizeof tmp) != NULL) {
root = tmp; root = tmp;
goto complete_path; goto complete_path;
} }
return (s->cwd); return ("/");
} else if (*cwd == '/') { } else if (*in == '/') {
/* Absolute path. */ /* Absolute path. */
return (cwd); return (in);
} else { } else {
/* Empty or relative path. */ /* Empty or relative path. */
if (c != NULL && c->session == NULL && c->cwd != NULL) if (current != NULL)
root = c->cwd; root = current;
else if (s->curw != NULL)
root = get_proc_cwd(s->curw->window->active->fd);
else else
return (s->cwd); return (base);
skip = 0; skip = 0;
if (root != NULL) goto complete_path;
goto complete_path;
} }
return (s->cwd); return (base);
find_home: find_home:
envent = environ_find(&global_environ, "HOME"); envent = environ_find(&global_environ, "HOME");
@ -1351,15 +1336,15 @@ find_home:
else if ((pw = getpwuid(getuid())) != NULL) else if ((pw = getpwuid(getuid())) != NULL)
root = pw->pw_dir; root = pw->pw_dir;
else else
return (s->cwd); return (base);
complete_path: complete_path:
if (root[skip] == '\0') { if (root[skip] == '\0') {
strlcpy(path, root, sizeof path); strlcpy(path, root, sizeof path);
return (path); return (path);
} }
n = snprintf(path, sizeof path, "%s/%s", root, cwd + skip); n = snprintf(path, sizeof path, "%s/%s", root, in + skip);
if (n > 0 && (size_t)n < sizeof path) if (n > 0 && (size_t)n < sizeof path)
return (path); return (path);
return (s->cwd); return (base);
} }

21
tmux.1
View File

@ -99,7 +99,9 @@ Force
.Nm .Nm
to assume the terminal supports 256 colours. to assume the terminal supports 256 colours.
.It Fl C .It Fl C
Start in control mode. Start in control mode (see the
.Sx CONTROL MODE
section).
Given twice Given twice
.Xo ( Fl CC ) Xc .Xo ( Fl CC ) Xc
disables echo. disables echo.
@ -622,9 +624,10 @@ If it does exist, exit with 0.
Kill the Kill the
.Nm .Nm
server and clients and destroy all sessions. server and clients and destroy all sessions.
.It Ic kill-session .It Xo Ic kill-session
.Op Fl a .Op Fl a
.Op Fl t Ar target-session .Op Fl t Ar target-session
.Xc
Destroy the given session, closing any windows linked to it and no other Destroy the given session, closing any windows linked to it and no other
sessions, and detaching all clients attached to it. sessions, and detaching all clients attached to it.
If If
@ -669,6 +672,7 @@ Lock all clients attached to
.Ar target-session . .Ar target-session .
.It Xo Ic new-session .It Xo Ic new-session
.Op Fl AdDP .Op Fl AdDP
.Op Fl c Ar start-directory
.Op Fl F Ar format .Op Fl F Ar format
.Op Fl n Ar window-name .Op Fl n Ar window-name
.Op Fl s Ar session-name .Op Fl s Ar session-name
@ -2708,8 +2712,8 @@ The default is on.
Control automatic window renaming. Control automatic window renaming.
When this setting is enabled, When this setting is enabled,
.Nm .Nm
will attempt - on supported platforms - to rename the window to reflect the will rename the window automatically using the format specified by
command currently running in it. .Ic automatic-rename-format .
This flag is automatically disabled for an individual window when a name This flag is automatically disabled for an individual window when a name
is specified at creation with is specified at creation with
.Ic new-window .Ic new-window
@ -2723,6 +2727,13 @@ It may be switched off globally with:
set-window-option -g automatic-rename off set-window-option -g automatic-rename off
.Ed .Ed
.Pp .Pp
.It Ic automatic-rename-format Ar format
The format (see
.Sx FORMATS )
used when the
.Ic automatic-rename
option is enabled.
.Pp
.It Ic c0-change-interval Ar interval .It Ic c0-change-interval Ar interval
.It Ic c0-change-trigger Ar trigger .It Ic c0-change-trigger Ar trigger
These two options configure a simple form of rate limiting for a pane. These two options configure a simple form of rate limiting for a pane.
@ -3570,7 +3581,7 @@ If the command doesn't return success, the exit status is also displayed.
.D1 (alias: Ic info ) .D1 (alias: Ic info )
Show server information and terminal details. Show server information and terminal details.
.It Xo Ic wait-for .It Xo Ic wait-for
.Fl LSU .Op Fl L | S | U
.Ar channel .Ar channel
.Xc .Xc
.D1 (alias: Ic wait ) .D1 (alias: Ic wait )