mirror of
				https://github.com/tmux/tmux.git
				synced 2025-10-26 12:27:15 +00:00 
			
		
		
		
	Clean up and simplify tmux command argument parsing.
Originally, tmux commands were parsed in the client process into a struct with the command data which was then serialised and sent to the server to be executed. The parsing was later moved into the server (an argv was sent from the client), but the parse step and intermediate struct was kept. This change removes that struct and the separate parse step. Argument parsing and printing is now common to all commands (in arguments.c) with each command left with just an optional check function (to validate the arguments at parse time), the exec function and a function to set up any key bindings (renamed from the old init function). This is overall more simple and consistent. There should be no changes to any commands behaviour or syntax although as this touches every command please watch for any unexpected changes.
This commit is contained in:
		
							
								
								
									
										4
									
								
								Makefile
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								Makefile
									
									
									
									
									
								
							| @@ -1,13 +1,13 @@ | |||||||
| # $OpenBSD$ | # $OpenBSD$ | ||||||
|  |  | ||||||
| PROG=	tmux | PROG=	tmux | ||||||
| SRCS=	attributes.c cfg.c client.c clock.c \ | SRCS=	arguments.c attributes.c cfg.c client.c clock.c \ | ||||||
| 	cmd-attach-session.c cmd-bind-key.c \ | 	cmd-attach-session.c cmd-bind-key.c \ | ||||||
| 	cmd-break-pane.c cmd-choose-session.c cmd-choose-window.c \ | 	cmd-break-pane.c cmd-choose-session.c cmd-choose-window.c \ | ||||||
| 	cmd-clear-history.c cmd-clock-mode.c cmd-command-prompt.c \ | 	cmd-clear-history.c cmd-clock-mode.c cmd-command-prompt.c \ | ||||||
| 	cmd-confirm-before.c cmd-copy-mode.c \ | 	cmd-confirm-before.c cmd-copy-mode.c \ | ||||||
| 	cmd-choose-buffer.c cmd-delete-buffer.c cmd-detach-client.c \ | 	cmd-choose-buffer.c cmd-delete-buffer.c cmd-detach-client.c \ | ||||||
| 	cmd-find-window.c cmd-generic.c cmd-has-session.c cmd-kill-pane.c \ | 	cmd-find-window.c cmd-has-session.c cmd-kill-pane.c \ | ||||||
| 	cmd-kill-server.c cmd-kill-session.c cmd-kill-window.c \ | 	cmd-kill-server.c cmd-kill-session.c cmd-kill-window.c \ | ||||||
| 	cmd-last-pane.c cmd-last-window.c cmd-link-window.c cmd-list-buffers.c \ | 	cmd-last-pane.c cmd-last-window.c cmd-link-window.c cmd-list-buffers.c \ | ||||||
| 	cmd-list-clients.c cmd-list-commands.c cmd-list-keys.c \ | 	cmd-list-clients.c cmd-list-commands.c cmd-list-keys.c \ | ||||||
|   | |||||||
							
								
								
									
										222
									
								
								arguments.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										222
									
								
								arguments.c
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,222 @@ | |||||||
|  | /* $OpenBSD$ */ | ||||||
|  |  | ||||||
|  | /* | ||||||
|  |  * Copyright (c) 2010 Nicholas Marriott <nicm@users.sourceforge.net> | ||||||
|  |  * | ||||||
|  |  * Permission to use, copy, modify, and distribute this software for any | ||||||
|  |  * purpose with or without fee is hereby granted, provided that the above | ||||||
|  |  * copyright notice and this permission notice appear in all copies. | ||||||
|  |  * | ||||||
|  |  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES | ||||||
|  |  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF | ||||||
|  |  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR | ||||||
|  |  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES | ||||||
|  |  * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER | ||||||
|  |  * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING | ||||||
|  |  * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. | ||||||
|  |  */ | ||||||
|  |  | ||||||
|  | #include <sys/types.h> | ||||||
|  |  | ||||||
|  | #include <bitstring.h> | ||||||
|  | #include <stdlib.h> | ||||||
|  | #include <string.h> | ||||||
|  |  | ||||||
|  | #include "tmux.h" | ||||||
|  |  | ||||||
|  | /* Create an arguments set with no flags. */ | ||||||
|  | struct args * | ||||||
|  | args_create(int argc, ...) | ||||||
|  | { | ||||||
|  | 	struct args	*args; | ||||||
|  | 	va_list		 ap; | ||||||
|  | 	int		 i; | ||||||
|  |  | ||||||
|  | 	args = xcalloc(1, sizeof *args); | ||||||
|  | 	if ((args->flags = bit_alloc(SCHAR_MAX)) == NULL) | ||||||
|  | 		fatal("bit_alloc failed"); | ||||||
|  |  | ||||||
|  | 	args->argc = argc; | ||||||
|  | 	if (argc == 0) | ||||||
|  | 		args->argv = NULL; | ||||||
|  | 	else | ||||||
|  | 		args->argv = xcalloc(argc, sizeof **args->argv); | ||||||
|  |  | ||||||
|  | 	va_start(ap, argc); | ||||||
|  | 	for (i = 0; i < argc; i++) | ||||||
|  | 		args->argv[i] = xstrdup(va_arg(ap, char *)); | ||||||
|  | 	va_end(ap); | ||||||
|  |  | ||||||
|  | 	return (args); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Parse an argv and argc into a new argument set. */ | ||||||
|  | struct args * | ||||||
|  | args_parse(const char *template, int argc, char **argv) | ||||||
|  | { | ||||||
|  | 	struct args	*args; | ||||||
|  | 	char		*ptr; | ||||||
|  | 	int		 opt; | ||||||
|  |  | ||||||
|  | 	args = xcalloc(1, sizeof *args); | ||||||
|  | 	if ((args->flags = bit_alloc(SCHAR_MAX)) == NULL) | ||||||
|  | 		fatal("bit_alloc failed"); | ||||||
|  |  | ||||||
|  | 	optreset = 1; | ||||||
|  | 	optind = 1; | ||||||
|  |  | ||||||
|  | 	while ((opt = getopt(argc, argv, template)) != -1) { | ||||||
|  | 		if (opt < 0 || opt >= SCHAR_MAX) | ||||||
|  | 			continue; | ||||||
|  | 		if (opt == '?' || (ptr = strchr(template, opt)) == NULL) { | ||||||
|  | 			xfree(args->flags); | ||||||
|  | 			xfree(args); | ||||||
|  | 			return (NULL); | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		bit_set(args->flags, opt); | ||||||
|  | 		if (ptr[1] == ':') { | ||||||
|  | 			if (args->values[opt] != NULL) | ||||||
|  | 				xfree(args->values[opt]); | ||||||
|  | 			args->values[opt] = xstrdup(optarg); | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	argc -= optind; | ||||||
|  | 	argv += optind; | ||||||
|  |  | ||||||
|  | 	args->argc = argc; | ||||||
|  | 	args->argv = cmd_copy_argv(argc, argv); | ||||||
|  |  | ||||||
|  | 	return (args); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Free an arguments set. */ | ||||||
|  | void | ||||||
|  | args_free(struct args *args) | ||||||
|  | { | ||||||
|  | 	u_int	i; | ||||||
|  |  | ||||||
|  | 	cmd_free_argv(args->argc, args->argv); | ||||||
|  |  | ||||||
|  | 	for (i = 0; i < SCHAR_MAX; i++) { | ||||||
|  | 		if (args->values[i] != NULL) | ||||||
|  | 			xfree(args->values[i]); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	xfree(args->flags); | ||||||
|  | 	xfree(args); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Print a set of arguments. */ | ||||||
|  | size_t | ||||||
|  | args_print(struct args *args, char *buf, size_t len) | ||||||
|  | { | ||||||
|  | 	size_t		 off; | ||||||
|  | 	int		 i; | ||||||
|  | 	const char	*quotes; | ||||||
|  |  | ||||||
|  | 	/* There must be at least one byte at the start. */ | ||||||
|  | 	if (len == 0) | ||||||
|  | 		return (0); | ||||||
|  | 	off = 0; | ||||||
|  |  | ||||||
|  | 	/* Process the flags first. */ | ||||||
|  | 	buf[off++] = '-'; | ||||||
|  | 	for (i = 0; i < SCHAR_MAX; i++) { | ||||||
|  | 		if (!bit_test(args->flags, i) || args->values[i] != NULL) | ||||||
|  | 			continue; | ||||||
|  |  | ||||||
|  | 		if (off == len - 1) { | ||||||
|  | 			buf[off] = '\0'; | ||||||
|  | 			return (len); | ||||||
|  | 		} | ||||||
|  | 		buf[off++] = i; | ||||||
|  | 		buf[off] = '\0'; | ||||||
|  | 	} | ||||||
|  | 	if (off == 1) | ||||||
|  | 		buf[--off] = '\0'; | ||||||
|  |  | ||||||
|  | 	/* Then the flags with arguments. */ | ||||||
|  | 	for (i = 0; i < SCHAR_MAX; i++) { | ||||||
|  | 		if (!bit_test(args->flags, i) || args->values[i] == NULL) | ||||||
|  | 			continue; | ||||||
|  |  | ||||||
|  | 		if (off >= len) { | ||||||
|  | 			/* snprintf will have zero terminated. */ | ||||||
|  | 			return (len); | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		if (strchr(args->values[i], ' ') != NULL) | ||||||
|  | 			quotes = "\""; | ||||||
|  | 		else | ||||||
|  | 			quotes = ""; | ||||||
|  | 		off += xsnprintf(buf + off, len - off, "%s-%c %s%s%s", | ||||||
|  | 		    off != 0 ? " " : "", i, quotes, args->values[i], quotes); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	/* And finally the argument vector. */ | ||||||
|  | 	for (i = 0; i < args->argc; i++) { | ||||||
|  | 		if (off >= len) { | ||||||
|  | 			/* snprintf will have zero terminated. */ | ||||||
|  | 			return (len); | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		if (strchr(args->argv[i], ' ') != NULL) | ||||||
|  | 			quotes = "\""; | ||||||
|  | 		else | ||||||
|  | 			quotes = ""; | ||||||
|  | 		off += xsnprintf(buf + off, len - off, "%s%s%s%s", | ||||||
|  | 		    off != 0 ? " " : "", quotes, args->argv[i], quotes); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	return (off); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Return if an argument is present. */ | ||||||
|  | int | ||||||
|  | args_has(struct args *args, u_char ch) | ||||||
|  | { | ||||||
|  | 	return (bit_test(args->flags, ch)); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Set argument value. */ | ||||||
|  | void | ||||||
|  | args_set(struct args *args, u_char ch, const char *value) | ||||||
|  | { | ||||||
|  | 	if (value != NULL) { | ||||||
|  | 		if (args->values[ch] != NULL) | ||||||
|  | 			xfree(args->values[ch]); | ||||||
|  | 		args->values[ch] = xstrdup(value); | ||||||
|  | 	} | ||||||
|  | 	bit_set(args->flags, ch); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Get argument value. Will be NULL if it isn't present. */ | ||||||
|  | const char * | ||||||
|  | args_get(struct args *args, u_char ch) | ||||||
|  | { | ||||||
|  | 	return (args->values[ch]); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | /* Convert an argument value to a number. */ | ||||||
|  | long long | ||||||
|  | args_strtonum(struct args *args, | ||||||
|  |     u_char ch, long long minval, long long maxval, char **cause) | ||||||
|  | { | ||||||
|  | 	const char	*errstr; | ||||||
|  | 	long long 	 ll; | ||||||
|  |  | ||||||
|  | 	if (!args_has(args, ch)) { | ||||||
|  | 		*cause = xstrdup("missing"); | ||||||
|  | 		return (0); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	ll = strtonum(args->values[ch], minval, maxval, &errstr); | ||||||
|  | 	if (errstr != NULL) { | ||||||
|  | 		*cause = xstrdup(errstr); | ||||||
|  | 		return (0); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	*cause = NULL; | ||||||
|  | 	return (ll); | ||||||
|  | } | ||||||
| @@ -28,37 +28,37 @@ int	cmd_attach_session_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_attach_session_entry = { | const struct cmd_entry cmd_attach_session_entry = { | ||||||
| 	"attach-session", "attach", | 	"attach-session", "attach", | ||||||
|  | 	"drt:", 0, 0, | ||||||
| 	"[-dr] " CMD_TARGET_SESSION_USAGE, | 	"[-dr] " CMD_TARGET_SESSION_USAGE, | ||||||
| 	CMD_CANTNEST|CMD_STARTSERVER|CMD_SENDENVIRON, "dr", | 	CMD_CANTNEST|CMD_STARTSERVER|CMD_SENDENVIRON, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_attach_session_exec, | 	cmd_attach_session_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_attach_session_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_attach_session_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
| 	struct client		*c; | 	struct client	*c; | ||||||
| 	const char		*update; | 	const char	*update; | ||||||
| 	char			*overrides, *cause; | 	char		*overrides, *cause; | ||||||
| 	u_int			 i; | 	u_int		 i; | ||||||
|  |  | ||||||
| 	if (RB_EMPTY(&sessions)) { | 	if (RB_EMPTY(&sessions)) { | ||||||
| 		ctx->error(ctx, "no sessions"); | 		ctx->error(ctx, "no sessions"); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) |  | ||||||
|  | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (ctx->cmdclient == NULL && ctx->curclient == NULL) | 	if (ctx->cmdclient == NULL && ctx->curclient == NULL) | ||||||
| 		return (0); | 		return (0); | ||||||
|  |  | ||||||
| 	if (ctx->cmdclient == NULL) { | 	if (ctx->cmdclient == NULL) { | ||||||
| 		if (cmd_check_flag(data->chflags, 'd')) { | 		if (args_has(self->args, 'd')) { | ||||||
| 			/* | 			/* | ||||||
| 			 * Can't use server_write_session in case attaching to | 			 * Can't use server_write_session in case attaching to | ||||||
| 			 * the same session as currently attached to. | 			 * the same session as currently attached to. | ||||||
| @@ -90,10 +90,10 @@ cmd_attach_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
|  |  | ||||||
| 		if (cmd_check_flag(data->chflags, 'r')) | 		if (args_has(self->args, 'r')) | ||||||
| 			ctx->cmdclient->flags |= CLIENT_READONLY; | 			ctx->cmdclient->flags |= CLIENT_READONLY; | ||||||
|  |  | ||||||
| 		if (cmd_check_flag(data->chflags, 'd')) | 		if (args_has(self->args, 'd')) | ||||||
| 			server_write_session(s, MSG_DETACH, NULL, 0); | 			server_write_session(s, MSG_DETACH, NULL, 0); | ||||||
|  |  | ||||||
| 		ctx->cmdclient->session = s; | 		ctx->cmdclient->session = s; | ||||||
|   | |||||||
							
								
								
									
										189
									
								
								cmd-bind-key.c
									
									
									
									
									
								
							
							
						
						
									
										189
									
								
								cmd-bind-key.c
									
									
									
									
									
								
							| @@ -26,136 +26,87 @@ | |||||||
|  * Bind a key to a command, this recurses through cmd_*. |  * Bind a key to a command, this recurses through cmd_*. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_bind_key_parse(struct cmd *, int, char **, char **); | int	cmd_bind_key_check(struct args *); | ||||||
| int	cmd_bind_key_exec(struct cmd *, struct cmd_ctx *); | int	cmd_bind_key_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_bind_key_free(struct cmd *); |  | ||||||
| size_t	cmd_bind_key_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| int	cmd_bind_key_table(struct cmd *, struct cmd_ctx *); | int	cmd_bind_key_table(struct cmd *, struct cmd_ctx *, int); | ||||||
|  |  | ||||||
| struct cmd_bind_key_data { |  | ||||||
| 	int		 key; |  | ||||||
| 	int		 can_repeat; |  | ||||||
| 	struct cmd_list	*cmdlist; |  | ||||||
|  |  | ||||||
| 	int		 command_key; |  | ||||||
| 	char		*tablename; |  | ||||||
| 	char 		*modecmd; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_bind_key_entry = { | const struct cmd_entry cmd_bind_key_entry = { | ||||||
| 	"bind-key", "bind", | 	"bind-key", "bind", | ||||||
|  | 	"cnrt:", 1, -1, | ||||||
| 	"[-cnr] [-t key-table] key command [arguments]", | 	"[-cnr] [-t key-table] key command [arguments]", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_bind_key_parse, | 	cmd_bind_key_check, | ||||||
| 	cmd_bind_key_exec, | 	cmd_bind_key_exec | ||||||
| 	cmd_bind_key_free, |  | ||||||
| 	cmd_bind_key_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_bind_key_parse(struct cmd *self, int argc, char **argv, char **cause) | cmd_bind_key_check(struct args *args) | ||||||
| { | { | ||||||
| 	struct cmd_bind_key_data	*data; | 	if (args_has(args, 't')) { | ||||||
| 	int				 opt, no_prefix = 0; | 		if (args->argc != 1) | ||||||
|  | 			return (-1); | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->can_repeat = 0; |  | ||||||
| 	data->cmdlist = NULL; |  | ||||||
| 	data->command_key = 0; |  | ||||||
| 	data->tablename = NULL; |  | ||||||
| 	data->modecmd = NULL; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "cnrt:")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'c': |  | ||||||
| 			data->command_key = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'n': |  | ||||||
| 			no_prefix = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'r': |  | ||||||
| 			data->can_repeat = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->tablename == NULL) |  | ||||||
| 				data->tablename = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc < 1) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	if ((data->key = key_string_lookup_string(argv[0])) == KEYC_NONE) { |  | ||||||
| 		xasprintf(cause, "unknown key: %s", argv[0]); |  | ||||||
| 		goto error; |  | ||||||
| 	} |  | ||||||
| 	if (!no_prefix) |  | ||||||
| 		data->key |= KEYC_PREFIX; |  | ||||||
|  |  | ||||||
| 	argc--; |  | ||||||
| 	argv++; |  | ||||||
| 	if (data->tablename != NULL) { |  | ||||||
| 		if (argc != 1) |  | ||||||
| 			goto usage; |  | ||||||
| 		data->modecmd = xstrdup(argv[0]); |  | ||||||
| 	} else { | 	} else { | ||||||
| 		if ((data->cmdlist = cmd_list_parse(argc, argv, cause)) == NULL) | 		if (args->argc < 2) | ||||||
| 			goto error; | 			return (-1); | ||||||
|  | 	} | ||||||
|  | 	return (0); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | int | ||||||
|  | cmd_bind_key_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
|  | { | ||||||
|  | 	struct args	*args = self->args; | ||||||
|  | 	char		*cause; | ||||||
|  | 	struct cmd_list	*cmdlist; | ||||||
|  | 	int		 key; | ||||||
|  |  | ||||||
|  | 	key = key_string_lookup_string(args->argv[0]); | ||||||
|  | 	if (key == KEYC_NONE) { | ||||||
|  | 		ctx->error(ctx, "unknown key: %s", args->argv[0]); | ||||||
|  | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	return (0); | 	if (args_has(args, 't')) | ||||||
|  | 		return (cmd_bind_key_table(self, ctx, key)); | ||||||
|  |  | ||||||
| usage: | 	cmdlist = cmd_list_parse(args->argc - 1, args->argv + 1, &cause); | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); | 	if (cmdlist == NULL) { | ||||||
|  | 		ctx->error(ctx, "%s", cause); | ||||||
| error: | 		xfree(cause); | ||||||
| 	self->entry->free(self); | 		return (-1); | ||||||
| 	return (-1); | 	} | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_bind_key_exec(struct cmd *self, unused struct cmd_ctx *ctx) |  | ||||||
| { |  | ||||||
| 	struct cmd_bind_key_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (0); |  | ||||||
| 	if (data->tablename != NULL) |  | ||||||
| 		return (cmd_bind_key_table(self, ctx)); |  | ||||||
|  |  | ||||||
| 	key_bindings_add(data->key, data->can_repeat, data->cmdlist); |  | ||||||
| 	data->cmdlist->references++; |  | ||||||
|  |  | ||||||
|  | 	if (!args_has(args, 'n')) | ||||||
|  | 	    key |= KEYC_PREFIX; | ||||||
|  | 	key_bindings_add(key, args_has(args, 'r'), cmdlist); | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_bind_key_table(struct cmd *self, struct cmd_ctx *ctx) | cmd_bind_key_table(struct cmd *self, struct cmd_ctx *ctx, int key) | ||||||
| { | { | ||||||
| 	struct cmd_bind_key_data	*data = self->data; | 	struct args			*args = self->args; | ||||||
|  | 	const char			*tablename; | ||||||
| 	const struct mode_key_table	*mtab; | 	const struct mode_key_table	*mtab; | ||||||
| 	struct mode_key_binding		*mbind, mtmp; | 	struct mode_key_binding		*mbind, mtmp; | ||||||
| 	enum mode_key_cmd		 cmd; | 	enum mode_key_cmd		 cmd; | ||||||
|  |  | ||||||
| 	if ((mtab = mode_key_findtable(data->tablename)) == NULL) { | 	tablename = args_get(args, 't'); | ||||||
| 		ctx->error(ctx, "unknown key table: %s", data->tablename); | 	if ((mtab = mode_key_findtable(tablename)) == NULL) { | ||||||
|  | 		ctx->error(ctx, "unknown key table: %s", tablename); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	cmd = mode_key_fromstring(mtab->cmdstr, data->modecmd); | 	cmd = mode_key_fromstring(mtab->cmdstr, args->argv[0]); | ||||||
| 	if (cmd == MODEKEY_NONE) { | 	if (cmd == MODEKEY_NONE) { | ||||||
| 		ctx->error(ctx, "unknown command: %s", data->modecmd); | 		ctx->error(ctx, "unknown command: %s", args->argv[0]); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	mtmp.key = data->key & ~KEYC_PREFIX; | 	mtmp.key = key; | ||||||
| 	mtmp.mode = data->command_key ? 1 : 0; | 	mtmp.mode = !!args_has(args, 'c'); | ||||||
| 	if ((mbind = SPLAY_FIND(mode_key_tree, mtab->tree, &mtmp)) != NULL) { | 	if ((mbind = SPLAY_FIND(mode_key_tree, mtab->tree, &mtmp)) != NULL) { | ||||||
| 		mbind->cmd = cmd; | 		mbind->cmd = cmd; | ||||||
| 		return (0); | 		return (0); | ||||||
| @@ -167,45 +118,3 @@ cmd_bind_key_table(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	SPLAY_INSERT(mode_key_tree, mtab->tree, mbind); | 	SPLAY_INSERT(mode_key_tree, mtab->tree, mbind); | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_bind_key_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_bind_key_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->cmdlist != NULL) |  | ||||||
| 		cmd_list_free(data->cmdlist); |  | ||||||
| 	if (data->tablename != NULL) |  | ||||||
| 		xfree(data->tablename); |  | ||||||
| 	if (data->modecmd != NULL) |  | ||||||
| 		xfree(data->modecmd); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_bind_key_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_bind_key_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
| 	const char			*skey; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
|  |  | ||||||
| 	if (off < len && data->command_key) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -c"); |  | ||||||
| 	if (off < len && !(data->key & KEYC_PREFIX)) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -n"); |  | ||||||
| 	if (off < len && data->can_repeat) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -r"); |  | ||||||
| 	if (off < len && data->tablename != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->tablename); |  | ||||||
| 	if (off < len) { |  | ||||||
| 		skey = key_string_lookup_key(data->key & ~KEYC_PREFIX); |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " %s ", skey); |  | ||||||
| 	} |  | ||||||
| 	if (off < len) |  | ||||||
| 		off += cmd_list_print(data->cmdlist, buf + off, len - off); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -30,19 +30,18 @@ int	cmd_break_pane_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_break_pane_entry = { | const struct cmd_entry cmd_break_pane_entry = { | ||||||
| 	"break-pane", "breakp", | 	"break-pane", "breakp", | ||||||
| 	CMD_TARGET_PANE_USAGE " [-d]", | 	"dt:", 0, 0, | ||||||
| 	0, "d", | 	"[-d] " CMD_TARGET_PANE_USAGE, | ||||||
| 	cmd_target_init, | 	0, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_break_pane_exec, | 	NULL, | ||||||
| 	cmd_target_free, | 	cmd_break_pane_exec | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_break_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_break_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	struct session		*s; | 	struct session		*s; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
| @@ -50,7 +49,7 @@ cmd_break_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	char			*cause; | 	char			*cause; | ||||||
| 	int			 base_idx; | 	int			 base_idx; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_pane(ctx, data->target, &s, &wp)) == NULL) | 	if ((wl = cmd_find_pane(ctx, args_get(args, 't'), &s, &wp)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (window_count_panes(wl->window) == 1) { | 	if (window_count_panes(wl->window) == 1) { | ||||||
| @@ -74,7 +73,7 @@ cmd_break_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	base_idx = options_get_number(&s->options, "base-index"); | 	base_idx = options_get_number(&s->options, "base-index"); | ||||||
| 	wl = session_attach(s, w, -1 - base_idx, &cause); /* can't fail */ | 	wl = session_attach(s, w, -1 - base_idx, &cause); /* can't fail */ | ||||||
| 	if (!cmd_check_flag(data->chflags, 'd')) | 	if (!args_has(self->args, 'd')) | ||||||
| 		session_select(s, wl->idx); | 		session_select(s, wl->idx); | ||||||
|  |  | ||||||
| 	server_redraw_session(s); | 	server_redraw_session(s); | ||||||
|   | |||||||
| @@ -27,93 +27,30 @@ | |||||||
|  * Write the entire contents of a pane to a buffer. |  * Write the entire contents of a pane to a buffer. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_capture_pane_parse(struct cmd *, int, char **, char **); |  | ||||||
| int	cmd_capture_pane_exec(struct cmd *, struct cmd_ctx *); | int	cmd_capture_pane_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_capture_pane_free(struct cmd *); |  | ||||||
| void	cmd_capture_pane_init(struct cmd *, int); |  | ||||||
| size_t	cmd_capture_pane_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_capture_pane_data { |  | ||||||
| 	char	*target; |  | ||||||
| 	int	 buffer; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_capture_pane_entry = { | const struct cmd_entry cmd_capture_pane_entry = { | ||||||
| 	"capture-pane", "capturep", | 	"capture-pane", "capturep", | ||||||
|  | 	"b:t:", 0, 0, | ||||||
| 	"[-b buffer-index] [-t target-pane]", | 	"[-b buffer-index] [-t target-pane]", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_capture_pane_init, | 	NULL, | ||||||
| 	cmd_capture_pane_parse, | 	NULL, | ||||||
| 	cmd_capture_pane_exec, | 	cmd_capture_pane_exec | ||||||
| 	cmd_capture_pane_free, |  | ||||||
| 	cmd_capture_pane_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_capture_pane_init(struct cmd *self, unused int arg) |  | ||||||
| { |  | ||||||
| 	struct cmd_capture_pane_data	*data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->buffer = -1; |  | ||||||
| 	data->target = NULL; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_capture_pane_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_capture_pane_data	*data; |  | ||||||
| 	const char			*errstr; |  | ||||||
| 	int				 n, opt; |  | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "b:t:")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'b': |  | ||||||
| 			if (data->buffer == -1) { |  | ||||||
| 				n = strtonum(optarg, 0, INT_MAX, &errstr); |  | ||||||
| 				if (errstr != NULL) { |  | ||||||
| 					xasprintf(cause, "buffer %s", errstr); |  | ||||||
| 					goto error; |  | ||||||
| 				} |  | ||||||
| 				data->buffer = n; |  | ||||||
| 			} |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| error: |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_capture_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_capture_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_capture_pane_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct window_pane		*wp; | 	struct window_pane	*wp; | ||||||
| 	char 				*buf, *line; | 	char 			*buf, *line, *cause; | ||||||
| 	struct screen			*s; | 	struct screen		*s; | ||||||
| 	u_int			 	 i, limit; | 	int			 buffer; | ||||||
| 	size_t         		 	 len, linelen; | 	u_int			 i, limit; | ||||||
|  | 	size_t         		 len, linelen; | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, NULL, &wp) == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	s = &wp->base; | 	s = &wp->base; | ||||||
|  |  | ||||||
| @@ -133,40 +70,24 @@ cmd_capture_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	limit = options_get_number(&global_options, "buffer-limit"); | 	limit = options_get_number(&global_options, "buffer-limit"); | ||||||
| 	if (data->buffer == -1) { |  | ||||||
|  | 	if (!args_has(args, 'b')) { | ||||||
| 		paste_add(&global_buffers, buf, len, limit); | 		paste_add(&global_buffers, buf, len, limit); | ||||||
| 		return (0); | 		return (0); | ||||||
| 	} | 	} | ||||||
| 	if (paste_replace(&global_buffers, data->buffer, buf, len) != 0) { |  | ||||||
| 		ctx->error(ctx, "no buffer %d", data->buffer); | 	buffer = args_strtonum(args, 'b', 0, INT_MAX, &cause); | ||||||
|  | 	if (cause != NULL) { | ||||||
|  | 		ctx->error(ctx, "buffer %s", cause); | ||||||
|  | 		xfree(cause); | ||||||
|  | 		return (-1); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if (paste_replace(&global_buffers, buffer, buf, len) != 0) { | ||||||
|  | 		ctx->error(ctx, "no buffer %d", buffer); | ||||||
| 		xfree(buf); | 		xfree(buf); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_capture_pane_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_capture_pane_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_capture_pane_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_capture_pane_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->buffer != -1) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -b %d", data->buffer); |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -t %s", data->target); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -33,24 +33,23 @@ void	cmd_choose_buffer_free(void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_choose_buffer_entry = { | const struct cmd_entry cmd_choose_buffer_entry = { | ||||||
| 	"choose-buffer", NULL, | 	"choose-buffer", NULL, | ||||||
|  | 	"t:", 0, 1, | ||||||
| 	CMD_TARGET_WINDOW_USAGE " [template]", | 	CMD_TARGET_WINDOW_USAGE " [template]", | ||||||
| 	CMD_ARG01, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_choose_buffer_exec, | 	cmd_choose_buffer_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_choose_buffer_data { | struct cmd_choose_buffer_data { | ||||||
| 	struct client	*client; | 	struct client   *client; | ||||||
| 	char   		*template; | 	char            *template; | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_choose_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_choose_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_choose_buffer_data	*cdata; | 	struct cmd_choose_buffer_data	*cdata; | ||||||
| 	struct winlink			*wl; | 	struct winlink			*wl; | ||||||
| 	struct paste_buffer		*pb; | 	struct paste_buffer		*pb; | ||||||
| @@ -62,7 +61,7 @@ cmd_choose_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (paste_get_top(&global_buffers) == NULL) | 	if (paste_get_top(&global_buffers) == NULL) | ||||||
| @@ -80,8 +79,8 @@ cmd_choose_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	cdata = xmalloc(sizeof *cdata); | 	cdata = xmalloc(sizeof *cdata); | ||||||
| 	if (data->arg != NULL) | 	if (args->argc != 0) | ||||||
| 		cdata->template = xstrdup(data->arg); | 		cdata->template = xstrdup(args->argv[0]); | ||||||
| 	else | 	else | ||||||
| 		cdata->template = xstrdup("paste-buffer -b '%%'"); | 		cdata->template = xstrdup("paste-buffer -b '%%'"); | ||||||
| 	cdata->client = ctx->curclient; | 	cdata->client = ctx->curclient; | ||||||
|   | |||||||
| @@ -33,13 +33,12 @@ void	cmd_choose_client_free(void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_choose_client_entry = { | const struct cmd_entry cmd_choose_client_entry = { | ||||||
| 	"choose-client", NULL, | 	"choose-client", NULL, | ||||||
|  | 	"t:", 0, 1, | ||||||
| 	CMD_TARGET_WINDOW_USAGE " [template]", | 	CMD_TARGET_WINDOW_USAGE " [template]", | ||||||
| 	CMD_ARG01, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_choose_client_exec, | 	cmd_choose_client_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_choose_client_data { | struct cmd_choose_client_data { | ||||||
| @@ -50,7 +49,7 @@ struct cmd_choose_client_data { | |||||||
| int | int | ||||||
| cmd_choose_client_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_choose_client_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_choose_client_data	*cdata; | 	struct cmd_choose_client_data	*cdata; | ||||||
| 	struct winlink			*wl; | 	struct winlink			*wl; | ||||||
| 	struct client			*c; | 	struct client			*c; | ||||||
| @@ -61,7 +60,7 @@ cmd_choose_client_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0) | 	if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0) | ||||||
| @@ -83,8 +82,8 @@ cmd_choose_client_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	cdata = xmalloc(sizeof *cdata); | 	cdata = xmalloc(sizeof *cdata); | ||||||
| 	if (data->arg != NULL) | 	if (args->argc != 0) | ||||||
| 		cdata->template = xstrdup(data->arg); | 		cdata->template = xstrdup(args->argv[0]); | ||||||
| 	else | 	else | ||||||
| 		cdata->template = xstrdup("detach-client -t '%%'"); | 		cdata->template = xstrdup("detach-client -t '%%'"); | ||||||
| 	cdata->client = ctx->curclient; | 	cdata->client = ctx->curclient; | ||||||
|   | |||||||
| @@ -33,13 +33,12 @@ void	cmd_choose_session_free(void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_choose_session_entry = { | const struct cmd_entry cmd_choose_session_entry = { | ||||||
| 	"choose-session", NULL, | 	"choose-session", NULL, | ||||||
|  | 	"t:", 0, 1, | ||||||
| 	CMD_TARGET_WINDOW_USAGE " [template]", | 	CMD_TARGET_WINDOW_USAGE " [template]", | ||||||
| 	CMD_ARG01, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_choose_session_exec, | 	cmd_choose_session_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_choose_session_data { | struct cmd_choose_session_data { | ||||||
| @@ -50,7 +49,7 @@ struct cmd_choose_session_data { | |||||||
| int | int | ||||||
| cmd_choose_session_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_choose_session_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_choose_session_data	*cdata; | 	struct cmd_choose_session_data	*cdata; | ||||||
| 	struct winlink			*wl; | 	struct winlink			*wl; | ||||||
| 	struct session			*s; | 	struct session			*s; | ||||||
| @@ -63,7 +62,7 @@ cmd_choose_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0) | 	if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0) | ||||||
| @@ -90,8 +89,8 @@ cmd_choose_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	cdata = xmalloc(sizeof *cdata); | 	cdata = xmalloc(sizeof *cdata); | ||||||
| 	if (data->arg != NULL) | 	if (args->argc != 0) | ||||||
| 		cdata->template = xstrdup(data->arg); | 		cdata->template = xstrdup(args->argv[0]); | ||||||
| 	else | 	else | ||||||
| 		cdata->template = xstrdup("switch-client -t '%%'"); | 		cdata->template = xstrdup("switch-client -t '%%'"); | ||||||
| 	cdata->client = ctx->curclient; | 	cdata->client = ctx->curclient; | ||||||
|   | |||||||
| @@ -33,13 +33,12 @@ void	cmd_choose_window_free(void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_choose_window_entry = { | const struct cmd_entry cmd_choose_window_entry = { | ||||||
| 	"choose-window", NULL, | 	"choose-window", NULL, | ||||||
|  | 	"t:", 0, 1, | ||||||
| 	CMD_TARGET_WINDOW_USAGE " [template]", | 	CMD_TARGET_WINDOW_USAGE " [template]", | ||||||
| 	CMD_ARG01, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_choose_window_exec, | 	cmd_choose_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_choose_window_data { | struct cmd_choose_window_data { | ||||||
| @@ -51,7 +50,7 @@ struct cmd_choose_window_data { | |||||||
| int | int | ||||||
| cmd_choose_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_choose_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_choose_window_data	*cdata; | 	struct cmd_choose_window_data	*cdata; | ||||||
| 	struct session			*s; | 	struct session			*s; | ||||||
| 	struct winlink			*wl, *wm; | 	struct winlink			*wl, *wm; | ||||||
| @@ -66,7 +65,7 @@ cmd_choose_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
| 	s = ctx->curclient->session; | 	s = ctx->curclient->session; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0) | 	if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0) | ||||||
| @@ -99,8 +98,8 @@ cmd_choose_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	cdata = xmalloc(sizeof *cdata); | 	cdata = xmalloc(sizeof *cdata); | ||||||
| 	if (data->arg != NULL) | 	if (args->argc != 0) | ||||||
| 		cdata->template = xstrdup(data->arg); | 		cdata->template = xstrdup(args->argv[0]); | ||||||
| 	else | 	else | ||||||
| 		cdata->template = xstrdup("select-window -t '%%'"); | 		cdata->template = xstrdup("select-window -t '%%'"); | ||||||
| 	cdata->session = s; | 	cdata->session = s; | ||||||
|   | |||||||
| @@ -28,23 +28,22 @@ int	cmd_clear_history_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_clear_history_entry = { | const struct cmd_entry cmd_clear_history_entry = { | ||||||
| 	"clear-history", "clearhist", | 	"clear-history", "clearhist", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_PANE_USAGE, | 	CMD_TARGET_PANE_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_clear_history_exec, | 	cmd_clear_history_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_clear_history_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_clear_history_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
| 	struct grid		*gd; | 	struct grid		*gd; | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, NULL, &wp) == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	gd = wp->base.grid; | 	gd = wp->base.grid; | ||||||
|  |  | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_clock_mode_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_clock_mode_entry = { | const struct cmd_entry cmd_clock_mode_entry = { | ||||||
| 	"clock-mode", NULL, | 	"clock-mode", NULL, | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_PANE_USAGE, | 	CMD_TARGET_PANE_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_clock_mode_exec, | 	cmd_clock_mode_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_clock_mode_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_clock_mode_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, NULL, &wp) == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	window_pane_set_mode(wp, &window_clock_mode); | 	window_pane_set_mode(wp, &window_clock_mode); | ||||||
|   | |||||||
| @@ -27,30 +27,21 @@ | |||||||
|  * Prompt for command in client. |  * Prompt for command in client. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	 cmd_command_prompt_init(struct cmd *, int); | void	cmd_command_prompt_key_binding(struct cmd *, int); | ||||||
| int	 cmd_command_prompt_parse(struct cmd *, int, char **, char **); | int	cmd_command_prompt_check(struct args *); | ||||||
| int	 cmd_command_prompt_exec(struct cmd *, struct cmd_ctx *); | int	cmd_command_prompt_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	 cmd_command_prompt_free(struct cmd *); |  | ||||||
| size_t	 cmd_command_prompt_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| int	 cmd_command_prompt_callback(void *, const char *); | int	cmd_command_prompt_callback(void *, const char *); | ||||||
| void	 cmd_command_prompt_cfree(void *); | void	cmd_command_prompt_free(void *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_command_prompt_entry = { | const struct cmd_entry cmd_command_prompt_entry = { | ||||||
| 	"command-prompt", NULL, | 	"command-prompt", NULL, | ||||||
|  | 	"p:t:", 0, 0, | ||||||
| 	CMD_TARGET_CLIENT_USAGE " [-p prompts] [template]", | 	CMD_TARGET_CLIENT_USAGE " [-p prompts] [template]", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_command_prompt_init, | 	cmd_command_prompt_key_binding, | ||||||
| 	cmd_command_prompt_parse, | 	NULL, | ||||||
| 	cmd_command_prompt_exec, | 	cmd_command_prompt_exec | ||||||
| 	cmd_command_prompt_free, |  | ||||||
| 	cmd_command_prompt_print |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| struct cmd_command_prompt_data { |  | ||||||
| 	char	*prompts; |  | ||||||
| 	char	*target; |  | ||||||
| 	char	*template; |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_command_prompt_cdata { | struct cmd_command_prompt_cdata { | ||||||
| @@ -62,82 +53,39 @@ struct cmd_command_prompt_cdata { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_command_prompt_init(struct cmd *self, int key) | cmd_command_prompt_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_command_prompt_data	*data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->prompts = NULL; |  | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->template = NULL; |  | ||||||
|  |  | ||||||
| 	switch (key) { | 	switch (key) { | ||||||
| 	case ',': | 	case ',': | ||||||
| 		data->template = xstrdup("rename-window '%%'"); | 		self->args = args_create(1, "rename-window '%%'"); | ||||||
| 		break; | 		break; | ||||||
| 	case '.': | 	case '.': | ||||||
| 		data->template = xstrdup("move-window -t '%%'"); | 		self->args = args_create(1, "move-window -t '%%'"); | ||||||
| 		break; | 		break; | ||||||
| 	case 'f': | 	case 'f': | ||||||
| 		data->template = xstrdup("find-window '%%'"); | 		self->args = args_create(1, "find-window '%%'"); | ||||||
| 		break; | 		break; | ||||||
| 	case '\'': | 	case '\'': | ||||||
| 		data->template = xstrdup("select-window -t ':%%'"); | 		self->args = args_create(1, "select-window -t ':%%'"); | ||||||
| 		data->prompts = xstrdup("index"); | 		args_set(self->args, 'p', "index"); | ||||||
|  | 		break; | ||||||
|  | 	default: | ||||||
|  | 		self->args = args_create(0); | ||||||
| 		break; | 		break; | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_command_prompt_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_command_prompt_data	*data; |  | ||||||
| 	int				 opt; |  | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "p:t:")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'p': |  | ||||||
| 			if (data->prompts == NULL) |  | ||||||
| 				data->prompts = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc != 0 && argc != 1) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	if (argc == 1) |  | ||||||
| 		data->template = xstrdup(argv[0]); |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_command_prompt_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_command_prompt_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_command_prompt_data	*data = self->data; | 	struct args			*args = self->args; | ||||||
|  | 	const char			*prompts; | ||||||
| 	struct cmd_command_prompt_cdata	*cdata; | 	struct cmd_command_prompt_cdata	*cdata; | ||||||
| 	struct client			*c; | 	struct client			*c; | ||||||
| 	char				*prompt, *ptr; | 	char				*prompt, *ptr; | ||||||
| 	size_t				 n; | 	size_t				 n; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (c->prompt_string != NULL) | 	if (c->prompt_string != NULL) | ||||||
| @@ -150,63 +98,33 @@ cmd_command_prompt_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	cdata->prompts = NULL; | 	cdata->prompts = NULL; | ||||||
| 	cdata->template = NULL; | 	cdata->template = NULL; | ||||||
|  |  | ||||||
| 	if (data->template != NULL) | 	if (args->argc != 0) | ||||||
| 		cdata->template = xstrdup(data->template); | 		cdata->template = xstrdup(args->argv[0]); | ||||||
| 	else | 	else | ||||||
| 		cdata->template = xstrdup("%1"); | 		cdata->template = xstrdup("%1"); | ||||||
| 	if (data->prompts != NULL) |  | ||||||
| 		cdata->prompts = xstrdup(data->prompts); | 	prompts = args_get(args, 'p'); | ||||||
| 	else if (data->template != NULL) { | 	if (prompts != NULL) | ||||||
| 		n = strcspn(data->template, " ,"); | 		cdata->prompts = xstrdup(prompts); | ||||||
| 		xasprintf(&cdata->prompts, "(%.*s) ", (int) n, data->template); | 	else if (args->argc != 0) { | ||||||
|  | 		n = strcspn(cdata->template, " ,"); | ||||||
|  | 		xasprintf(&cdata->prompts, "(%.*s) ", (int) n, cdata->template); | ||||||
| 	} else | 	} else | ||||||
| 		cdata->prompts = xstrdup(":"); | 		cdata->prompts = xstrdup(":"); | ||||||
|  |  | ||||||
| 	cdata->next_prompt = cdata->prompts; | 	cdata->next_prompt = cdata->prompts; | ||||||
| 	ptr = strsep(&cdata->next_prompt, ","); | 	ptr = strsep(&cdata->next_prompt, ","); | ||||||
| 	if (data->prompts == NULL) | 	if (prompts == NULL) | ||||||
| 		prompt = xstrdup(ptr); | 		prompt = xstrdup(ptr); | ||||||
| 	else | 	else | ||||||
| 		xasprintf(&prompt, "%s ", ptr); | 		xasprintf(&prompt, "%s ", ptr); | ||||||
| 	status_prompt_set(c, prompt, cmd_command_prompt_callback, | 	status_prompt_set(c, prompt, cmd_command_prompt_callback, | ||||||
| 	    cmd_command_prompt_cfree, cdata, 0); | 	    cmd_command_prompt_free, cdata, 0); | ||||||
| 	xfree(prompt); | 	xfree(prompt); | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_command_prompt_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_command_prompt_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->prompts != NULL) |  | ||||||
| 		xfree(data->prompts); |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	if (data->template != NULL) |  | ||||||
| 		xfree(data->template); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_command_prompt_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_command_prompt_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->prompts != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -p ", data->prompts); |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
| 	if (off < len && data->template != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->template); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_command_prompt_callback(void *data, const char *s) | cmd_command_prompt_callback(void *data, const char *s) | ||||||
| { | { | ||||||
| @@ -258,7 +176,7 @@ cmd_command_prompt_callback(void *data, const char *s) | |||||||
| } | } | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_command_prompt_cfree(void *data) | cmd_command_prompt_free(void *data) | ||||||
| { | { | ||||||
| 	struct cmd_command_prompt_cdata	*cdata = data; | 	struct cmd_command_prompt_cdata	*cdata = data; | ||||||
|  |  | ||||||
|   | |||||||
| @@ -25,21 +25,20 @@ | |||||||
|  * Asks for confirmation before executing a command. |  * Asks for confirmation before executing a command. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
|  | void	cmd_confirm_before_key_binding(struct cmd *, int); | ||||||
| int	cmd_confirm_before_exec(struct cmd *, struct cmd_ctx *); | int	cmd_confirm_before_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_confirm_before_init(struct cmd *, int); |  | ||||||
|  |  | ||||||
| int	cmd_confirm_before_callback(void *, const char *); | int	cmd_confirm_before_callback(void *, const char *); | ||||||
| void	cmd_confirm_before_free(void *); | void	cmd_confirm_before_free(void *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_confirm_before_entry = { | const struct cmd_entry cmd_confirm_before_entry = { | ||||||
| 	"confirm-before", "confirm", | 	"confirm-before", "confirm", | ||||||
|  | 	"t:", 1, 1, | ||||||
| 	CMD_TARGET_CLIENT_USAGE " command", | 	CMD_TARGET_CLIENT_USAGE " command", | ||||||
| 	CMD_ARG1, "", | 	0, | ||||||
| 	cmd_confirm_before_init, | 	cmd_confirm_before_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_confirm_before_exec, | 	cmd_confirm_before_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_confirm_before_data { | struct cmd_confirm_before_data { | ||||||
| @@ -48,19 +47,17 @@ struct cmd_confirm_before_data { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_confirm_before_init(struct cmd *self, int key) | cmd_confirm_before_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; |  | ||||||
|  |  | ||||||
| 	cmd_target_init(self, key); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	switch (key) { | 	switch (key) { | ||||||
| 	case '&': | 	case '&': | ||||||
| 		data->arg = xstrdup("kill-window"); | 		self->args = args_create(1, "kill-window"); | ||||||
| 		break; | 		break; | ||||||
| 	case 'x': | 	case 'x': | ||||||
| 		data->arg = xstrdup("kill-pane"); | 		self->args = args_create(1, "kill-pane"); | ||||||
|  | 		break; | ||||||
|  | 	default: | ||||||
|  | 		self->args = args_create(0); | ||||||
| 		break; | 		break; | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
| @@ -68,7 +65,7 @@ cmd_confirm_before_init(struct cmd *self, int key) | |||||||
| int | int | ||||||
| cmd_confirm_before_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_confirm_before_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_confirm_before_data	*cdata; | 	struct cmd_confirm_before_data	*cdata; | ||||||
| 	struct client			*c; | 	struct client			*c; | ||||||
| 	char				*buf, *cmd, *ptr; | 	char				*buf, *cmd, *ptr; | ||||||
| @@ -78,17 +75,17 @@ cmd_confirm_before_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	ptr = xstrdup(data->arg); | 	ptr = xstrdup(args->argv[0]); | ||||||
| 	if ((cmd = strtok(ptr, " \t")) == NULL) | 	if ((cmd = strtok(ptr, " \t")) == NULL) | ||||||
| 		cmd = ptr; | 		cmd = ptr; | ||||||
| 	xasprintf(&buf, "Confirm '%s'? (y/n) ", cmd); | 	xasprintf(&buf, "Confirm '%s'? (y/n) ", cmd); | ||||||
| 	xfree(ptr); | 	xfree(ptr); | ||||||
|  |  | ||||||
| 	cdata = xmalloc(sizeof *cdata); | 	cdata = xmalloc(sizeof *cdata); | ||||||
| 	cdata->cmd = xstrdup(data->arg); | 	cdata->cmd = xstrdup(args->argv[0]); | ||||||
| 	cdata->c = c; | 	cdata->c = c; | ||||||
| 	status_prompt_set(cdata->c, buf, | 	status_prompt_set(cdata->c, buf, | ||||||
| 	    cmd_confirm_before_callback, cmd_confirm_before_free, cdata, | 	    cmd_confirm_before_callback, cmd_confirm_before_free, cdata, | ||||||
|   | |||||||
| @@ -24,48 +24,40 @@ | |||||||
|  * Enter copy mode. |  * Enter copy mode. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_copy_mode_init(struct cmd *, int); | void	cmd_copy_mode_key_binding(struct cmd *, int); | ||||||
| int	cmd_copy_mode_exec(struct cmd *, struct cmd_ctx *); | int	cmd_copy_mode_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_copy_mode_entry = { | const struct cmd_entry cmd_copy_mode_entry = { | ||||||
| 	"copy-mode", NULL, | 	"copy-mode", NULL, | ||||||
|  | 	"t:u", 0, 0, | ||||||
| 	"[-u] " CMD_TARGET_PANE_USAGE, | 	"[-u] " CMD_TARGET_PANE_USAGE, | ||||||
| 	0, "u", | 	0, | ||||||
| 	cmd_copy_mode_init, | 	cmd_copy_mode_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_copy_mode_exec, | 	cmd_copy_mode_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_copy_mode_init(struct cmd *self, int key) | cmd_copy_mode_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	self->args = args_create(0); | ||||||
|  | 	if (key == KEYC_PPAGE) | ||||||
| 	cmd_target_init(self, key); | 		args_set(self->args, 'u', NULL); | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	switch (key) { |  | ||||||
| 	case KEYC_PPAGE: |  | ||||||
| 		cmd_set_flag(&data->chflags, 'u'); |  | ||||||
| 		break; |  | ||||||
| 	} |  | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_copy_mode_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_copy_mode_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, NULL, &wp) == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (window_pane_set_mode(wp, &window_copy_mode) != 0) | 	if (window_pane_set_mode(wp, &window_copy_mode) != 0) | ||||||
| 		return (0); | 		return (0); | ||||||
| 	window_copy_init_from_pane(wp); | 	window_copy_init_from_pane(wp); | ||||||
| 	if (wp->mode == &window_copy_mode && cmd_check_flag(data->chflags, 'u')) | 	if (wp->mode == &window_copy_mode && args_has(self->args, 'u')) | ||||||
| 		window_copy_pageup(wp); | 		window_copy_pageup(wp); | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
|   | |||||||
| @@ -30,24 +30,35 @@ int	cmd_delete_buffer_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_delete_buffer_entry = { | const struct cmd_entry cmd_delete_buffer_entry = { | ||||||
| 	"delete-buffer", "deleteb", | 	"delete-buffer", "deleteb", | ||||||
|  | 	"b:", 0, 0, | ||||||
| 	CMD_BUFFER_USAGE, | 	CMD_BUFFER_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_buffer_init, | 	NULL, | ||||||
| 	cmd_buffer_parse, | 	NULL, | ||||||
| 	cmd_delete_buffer_exec, | 	cmd_delete_buffer_exec | ||||||
| 	cmd_buffer_free, |  | ||||||
| 	cmd_buffer_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_delete_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_delete_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_buffer_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
|  | 	char		*cause; | ||||||
|  | 	int		 buffer; | ||||||
|  |  | ||||||
| 	if (data->buffer == -1) | 	if (!args_has(args, 'b')) { | ||||||
| 		paste_free_top(&global_buffers); | 		paste_free_top(&global_buffers); | ||||||
| 	else if (paste_free_index(&global_buffers, data->buffer) != 0) { | 		return (0); | ||||||
| 		ctx->error(ctx, "no buffer %d", data->buffer); | 	} | ||||||
|  |  | ||||||
|  | 	buffer = args_strtonum(args, 'b', 0, INT_MAX, &cause); | ||||||
|  | 	if (cause != NULL) { | ||||||
|  | 		ctx->error(ctx, "buffer %s", cause); | ||||||
|  | 		xfree(cause); | ||||||
|  | 		return (-1); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if (paste_free_index(&global_buffers, buffer) != 0) { | ||||||
|  | 		ctx->error(ctx, "no buffer %d", buffer); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_detach_client_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_detach_client_entry = { | const struct cmd_entry cmd_detach_client_entry = { | ||||||
| 	"detach-client", "detach", | 	"detach-client", "detach", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_CLIENT_USAGE, | 	CMD_TARGET_CLIENT_USAGE, | ||||||
| 	CMD_READONLY, "", | 	CMD_READONLY, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_detach_client_exec, | 	cmd_detach_client_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_detach_client_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_detach_client_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct client		*c; | 	struct client	*c; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	server_write_client(c, MSG_DETACH, NULL, 0); | 	server_write_client(c, MSG_DETACH, NULL, 0); | ||||||
|   | |||||||
| @@ -30,33 +30,32 @@ int	cmd_display_message_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_display_message_entry = { | const struct cmd_entry cmd_display_message_entry = { | ||||||
| 	"display-message", "display", | 	"display-message", "display", | ||||||
|  | 	"pt:", 0, 1, | ||||||
| 	"[-p] " CMD_TARGET_CLIENT_USAGE " [message]", | 	"[-p] " CMD_TARGET_CLIENT_USAGE " [message]", | ||||||
| 	CMD_ARG01, "p", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_display_message_exec, | 	cmd_display_message_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_display_message_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_display_message_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct client		*c; | 	struct client		*c; | ||||||
| 	const char		*template; | 	const char		*template; | ||||||
| 	char			*msg; | 	char			*msg; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (data->arg == NULL) | 	if (args->argc == 0) | ||||||
| 		template = "[#S] #I:#W, current pane #P - (%H:%M %d-%b-%y)"; | 		template = "[#S] #I:#W, current pane #P - (%H:%M %d-%b-%y)"; | ||||||
| 	else | 	else | ||||||
| 		template = data->arg; | 		template = args->argv[0]; | ||||||
|  |  | ||||||
| 	msg = status_replace(c, NULL, template, time(NULL), 0); | 	msg = status_replace(c, NULL, template, time(NULL), 0); | ||||||
| 	if (cmd_check_flag(data->chflags, 'p')) | 	if (args_has(self->args, 'p')) | ||||||
| 		ctx->print(ctx, "%s", msg); | 		ctx->print(ctx, "%s", msg); | ||||||
| 	else | 	else | ||||||
| 		status_message_set(c, "%s", msg); | 		status_message_set(c, "%s", msg); | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_display_panes_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_display_panes_entry = { | const struct cmd_entry cmd_display_panes_entry = { | ||||||
| 	"display-panes", "displayp", | 	"display-panes", "displayp", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_CLIENT_USAGE, | 	CMD_TARGET_CLIENT_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_display_panes_exec, | 	cmd_display_panes_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_display_panes_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_display_panes_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct client		*c; | 	struct client	*c; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	server_set_identify(c); | 	server_set_identify(c); | ||||||
|   | |||||||
| @@ -34,13 +34,12 @@ void	cmd_find_window_free(void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_find_window_entry = { | const struct cmd_entry cmd_find_window_entry = { | ||||||
| 	"find-window", "findw", | 	"find-window", "findw", | ||||||
|  | 	"t:", 1, 1, | ||||||
| 	CMD_TARGET_WINDOW_USAGE " match-string", | 	CMD_TARGET_WINDOW_USAGE " match-string", | ||||||
| 	CMD_ARG1, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_find_window_exec, | 	cmd_find_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_find_window_data { | struct cmd_find_window_data { | ||||||
| @@ -50,7 +49,7 @@ struct cmd_find_window_data { | |||||||
| int | int | ||||||
| cmd_find_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_find_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_find_window_data	*cdata; | 	struct cmd_find_window_data	*cdata; | ||||||
| 	struct session			*s; | 	struct session			*s; | ||||||
| 	struct winlink			*wl, *wm; | 	struct winlink			*wl, *wm; | ||||||
| @@ -58,7 +57,7 @@ cmd_find_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	struct window_pane		*wp; | 	struct window_pane		*wp; | ||||||
| 	ARRAY_DECL(, u_int)	 	 list_idx; | 	ARRAY_DECL(, u_int)	 	 list_idx; | ||||||
| 	ARRAY_DECL(, char *)	 	 list_ctx; | 	ARRAY_DECL(, char *)	 	 list_ctx; | ||||||
| 	char				*sres, *sctx, *searchstr; | 	char				*str, *sres, *sctx, *searchstr; | ||||||
| 	u_int				 i, line; | 	u_int				 i, line; | ||||||
|  |  | ||||||
| 	if (ctx->curclient == NULL) { | 	if (ctx->curclient == NULL) { | ||||||
| @@ -67,13 +66,15 @@ cmd_find_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
| 	s = ctx->curclient->session; | 	s = ctx->curclient->session; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
|  | 	str = args->argv[0]; | ||||||
|  |  | ||||||
| 	ARRAY_INIT(&list_idx); | 	ARRAY_INIT(&list_idx); | ||||||
| 	ARRAY_INIT(&list_ctx); | 	ARRAY_INIT(&list_ctx); | ||||||
|  |  | ||||||
| 	xasprintf(&searchstr, "*%s*", data->arg); | 	xasprintf(&searchstr, "*%s*", str); | ||||||
| 	RB_FOREACH(wm, winlinks, &s->windows) { | 	RB_FOREACH(wm, winlinks, &s->windows) { | ||||||
| 		i = 0; | 		i = 0; | ||||||
| 		TAILQ_FOREACH(wp, &wm->window->panes, entry) { | 		TAILQ_FOREACH(wp, &wm->window->panes, entry) { | ||||||
| @@ -82,7 +83,7 @@ cmd_find_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 			if (fnmatch(searchstr, wm->window->name, 0) == 0) | 			if (fnmatch(searchstr, wm->window->name, 0) == 0) | ||||||
| 				sctx = xstrdup(""); | 				sctx = xstrdup(""); | ||||||
| 			else { | 			else { | ||||||
| 				sres = window_pane_search(wp, data->arg, &line); | 				sres = window_pane_search(wp, str, &line); | ||||||
| 				if (sres == NULL && | 				if (sres == NULL && | ||||||
| 				    fnmatch(searchstr, wp->base.title, 0) != 0) | 				    fnmatch(searchstr, wp->base.title, 0) != 0) | ||||||
| 					continue; | 					continue; | ||||||
| @@ -106,7 +107,7 @@ cmd_find_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	xfree(searchstr); | 	xfree(searchstr); | ||||||
|  |  | ||||||
| 	if (ARRAY_LENGTH(&list_idx) == 0) { | 	if (ARRAY_LENGTH(&list_idx) == 0) { | ||||||
| 		ctx->error(ctx, "no windows matching: %s", data->arg); | 		ctx->error(ctx, "no windows matching: %s", str); | ||||||
| 		ARRAY_FREE(&list_idx); | 		ARRAY_FREE(&list_idx); | ||||||
| 		ARRAY_FREE(&list_ctx); | 		ARRAY_FREE(&list_ctx); | ||||||
| 		return (-1); | 		return (-1); | ||||||
|   | |||||||
							
								
								
									
										414
									
								
								cmd-generic.c
									
									
									
									
									
								
							
							
						
						
									
										414
									
								
								cmd-generic.c
									
									
									
									
									
								
							| @@ -1,414 +0,0 @@ | |||||||
| /* $OpenBSD$ */ |  | ||||||
|  |  | ||||||
| /* |  | ||||||
|  * Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net> |  | ||||||
|  * |  | ||||||
|  * Permission to use, copy, modify, and distribute this software for any |  | ||||||
|  * purpose with or without fee is hereby granted, provided that the above |  | ||||||
|  * copyright notice and this permission notice appear in all copies. |  | ||||||
|  * |  | ||||||
|  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES |  | ||||||
|  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF |  | ||||||
|  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR |  | ||||||
|  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES |  | ||||||
|  * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER |  | ||||||
|  * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING |  | ||||||
|  * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. |  | ||||||
|  */ |  | ||||||
|  |  | ||||||
| #include <sys/types.h> |  | ||||||
|  |  | ||||||
| #include <stdlib.h> |  | ||||||
| #include <string.h> |  | ||||||
|  |  | ||||||
| #include "tmux.h" |  | ||||||
|  |  | ||||||
| int	cmd_getopt(int, char **, const char *, const char *); |  | ||||||
| int	cmd_parse_flags(int, const char *, uint64_t *); |  | ||||||
| size_t	cmd_print_flags(char *, size_t, size_t, uint64_t); |  | ||||||
| int	cmd_fill_argument(int, char **, char **, int, char **); |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_prarg(char *buf, size_t len, const char *prefix, char *arg) |  | ||||||
| { |  | ||||||
| 	if (strchr(arg, ' ') != NULL) |  | ||||||
| 		return (xsnprintf(buf, len, "%s\"%s\"", prefix, arg)); |  | ||||||
| 	return (xsnprintf(buf, len, "%s%s", prefix, arg)); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* Append two flag strings together and call getopt. */ |  | ||||||
| int |  | ||||||
| cmd_getopt(int argc, char **argv, const char *flagstr, const char *chflagstr) |  | ||||||
| { |  | ||||||
| 	char	tmp[BUFSIZ]; |  | ||||||
|  |  | ||||||
| 	if (strlcpy(tmp, flagstr, sizeof tmp) >= sizeof tmp) |  | ||||||
| 		fatalx("strlcpy overflow"); |  | ||||||
| 	if (strlcat(tmp, chflagstr, sizeof tmp) >= sizeof tmp) |  | ||||||
| 		fatalx("strlcat overflow"); |  | ||||||
| 	return (getopt(argc, argv, tmp)); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* Return if flag character is set. */ |  | ||||||
| int |  | ||||||
| cmd_check_flag(uint64_t chflags, int flag) |  | ||||||
| { |  | ||||||
| 	if (flag >= 'A' && flag <= 'Z') |  | ||||||
| 		flag = 26 + flag - 'A'; |  | ||||||
| 	else if (flag >= 'a' && flag <= 'z') |  | ||||||
| 		flag = flag - 'a'; |  | ||||||
| 	else |  | ||||||
| 		return (0); |  | ||||||
| 	return ((chflags & (1ULL << flag)) != 0); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* Set flag character. */ |  | ||||||
| void |  | ||||||
| cmd_set_flag(uint64_t *chflags, int flag) |  | ||||||
| { |  | ||||||
| 	if (flag >= 'A' && flag <= 'Z') |  | ||||||
| 		flag = 26 + flag - 'A'; |  | ||||||
| 	else if (flag >= 'a' && flag <= 'z') |  | ||||||
| 		flag = flag - 'a'; |  | ||||||
| 	else |  | ||||||
| 		return; |  | ||||||
| 	(*chflags) |= (1ULL << flag); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* If this option is expected, set it in chflags, otherwise return -1. */ |  | ||||||
| int |  | ||||||
| cmd_parse_flags(int opt, const char *chflagstr, uint64_t *chflags) |  | ||||||
| { |  | ||||||
| 	if (strchr(chflagstr, opt) == NULL) |  | ||||||
| 		return (-1); |  | ||||||
| 	cmd_set_flag(chflags, opt); |  | ||||||
| 	return (0); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* Print the flags present in chflags. */ |  | ||||||
| size_t |  | ||||||
| cmd_print_flags(char *buf, size_t len, size_t off, uint64_t chflags) |  | ||||||
| { |  | ||||||
| 	u_char	ch; |  | ||||||
| 	size_t	boff = off; |  | ||||||
|  |  | ||||||
| 	if (chflags == 0) |  | ||||||
| 		return (0); |  | ||||||
| 	off += xsnprintf(buf + off, len - off, " -"); |  | ||||||
|  |  | ||||||
| 	for (ch = 0; ch < 26; ch++) { |  | ||||||
| 		if (cmd_check_flag(chflags, 'a' + ch)) |  | ||||||
| 			off += xsnprintf(buf + off, len - off, "%c", 'a' + ch); |  | ||||||
| 		if (cmd_check_flag(chflags, 'A' + ch)) |  | ||||||
| 			off += xsnprintf(buf + off, len - off, "%c", 'A' + ch); |  | ||||||
| 	} |  | ||||||
| 	return (off - boff); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_fill_argument(int flags, char **arg, char **arg2, int argc, char **argv) |  | ||||||
| { |  | ||||||
| 	*arg = NULL; |  | ||||||
| 	*arg2 = NULL; |  | ||||||
|  |  | ||||||
| 	if (flags & CMD_ARG1) { |  | ||||||
| 		if (argc != 1) |  | ||||||
| 			return (-1); |  | ||||||
| 		*arg = xstrdup(argv[0]); |  | ||||||
| 		return (0); |  | ||||||
| 	} |  | ||||||
|  |  | ||||||
| 	if (flags & CMD_ARG01) { |  | ||||||
| 		if (argc != 0 && argc != 1) |  | ||||||
| 			return (-1); |  | ||||||
| 		if (argc == 1) |  | ||||||
| 			*arg = xstrdup(argv[0]); |  | ||||||
| 		return (0); |  | ||||||
| 	} |  | ||||||
|  |  | ||||||
| 	if (flags & CMD_ARG2) { |  | ||||||
| 		if (argc != 2) |  | ||||||
| 			return (-1); |  | ||||||
| 		*arg = xstrdup(argv[0]); |  | ||||||
| 		*arg2 = xstrdup(argv[1]); |  | ||||||
| 		return (0); |  | ||||||
| 	} |  | ||||||
|  |  | ||||||
| 	if (flags & CMD_ARG12) { |  | ||||||
| 		if (argc != 1 && argc != 2) |  | ||||||
| 			return (-1); |  | ||||||
| 		*arg = xstrdup(argv[0]); |  | ||||||
| 		if (argc == 2) |  | ||||||
| 			*arg2 = xstrdup(argv[1]); |  | ||||||
| 		return (0); |  | ||||||
| 	} |  | ||||||
|  |  | ||||||
| 	if (argc != 0) |  | ||||||
| 		return (-1); |  | ||||||
| 	return (0); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_target_init(struct cmd *self, unused int key) |  | ||||||
| { |  | ||||||
| 	struct cmd_target_data	*data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->chflags = 0; |  | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->arg = NULL; |  | ||||||
| 	data->arg2 = NULL; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_target_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_target_data	*data; |  | ||||||
| 	const struct cmd_entry	*entry = self->entry; |  | ||||||
| 	int			 opt; |  | ||||||
|  |  | ||||||
| 	/* Don't use the entry version since it may be dependent on key. */ |  | ||||||
| 	cmd_target_init(self, 0); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = cmd_getopt(argc, argv, "t:", entry->chflags)) != -1) { |  | ||||||
| 		if (cmd_parse_flags(opt, entry->chflags, &data->chflags) == 0) |  | ||||||
| 			continue; |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
|  |  | ||||||
| 	if (cmd_fill_argument( |  | ||||||
| 	    self->entry->flags, &data->arg, &data->arg2, argc, argv) != 0) |  | ||||||
| 		goto usage; |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_target_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_target_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	if (data->arg != NULL) |  | ||||||
| 		xfree(data->arg); |  | ||||||
| 	if (data->arg2 != NULL) |  | ||||||
| 		xfree(data->arg2); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_target_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_target_data	*data = self->data; |  | ||||||
| 	size_t			 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	off += cmd_print_flags(buf, len, off, data->chflags); |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
| 	if (off < len && data->arg != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->arg); |  | ||||||
| 	if (off < len && data->arg2 != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->arg2); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_srcdst_init(struct cmd *self, unused int key) |  | ||||||
| { |  | ||||||
| 	struct cmd_srcdst_data	*data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->chflags = 0; |  | ||||||
| 	data->src = NULL; |  | ||||||
| 	data->dst = NULL; |  | ||||||
| 	data->arg = NULL; |  | ||||||
| 	data->arg2 = NULL; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_srcdst_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_srcdst_data	*data; |  | ||||||
| 	const struct cmd_entry	*entry = self->entry; |  | ||||||
| 	int			 opt; |  | ||||||
|  |  | ||||||
| 	cmd_srcdst_init(self, 0); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = cmd_getopt(argc, argv, "s:t:", entry->chflags)) != -1) { |  | ||||||
| 		if (cmd_parse_flags(opt, entry->chflags, &data->chflags) == 0) |  | ||||||
| 			continue; |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 's': |  | ||||||
| 			if (data->src == NULL) |  | ||||||
| 				data->src = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->dst == NULL) |  | ||||||
| 				data->dst = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
|  |  | ||||||
| 	if (cmd_fill_argument( |  | ||||||
| 	    self->entry->flags, &data->arg, &data->arg2, argc, argv) != 0) |  | ||||||
| 		goto usage; |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_srcdst_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_srcdst_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->src != NULL) |  | ||||||
| 		xfree(data->src); |  | ||||||
| 	if (data->dst != NULL) |  | ||||||
| 		xfree(data->dst); |  | ||||||
| 	if (data->arg != NULL) |  | ||||||
| 		xfree(data->arg); |  | ||||||
| 	if (data->arg2 != NULL) |  | ||||||
| 		xfree(data->arg2); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_srcdst_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_srcdst_data	*data = self->data; |  | ||||||
| 	size_t			 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	off += cmd_print_flags(buf, len, off, data->chflags); |  | ||||||
| 	if (off < len && data->src != NULL) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -s %s", data->src); |  | ||||||
| 	if (off < len && data->dst != NULL) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -t %s", data->dst); |  | ||||||
| 	if (off < len && data->arg != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->arg); |  | ||||||
| 	if (off < len && data->arg2 != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->arg2); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_buffer_init(struct cmd *self, unused int key) |  | ||||||
| { |  | ||||||
| 	struct cmd_buffer_data	*data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->chflags = 0; |  | ||||||
| 	data->buffer = -1; |  | ||||||
| 	data->arg = NULL; |  | ||||||
| 	data->arg2 = NULL; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_buffer_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_buffer_data	*data; |  | ||||||
| 	const struct cmd_entry	*entry = self->entry; |  | ||||||
| 	int			 opt, n; |  | ||||||
| 	const char		*errstr; |  | ||||||
|  |  | ||||||
| 	cmd_buffer_init(self, 0); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = cmd_getopt(argc, argv, "b:", entry->chflags)) != -1) { |  | ||||||
| 		if (cmd_parse_flags(opt, entry->chflags, &data->chflags) == 0) |  | ||||||
| 			continue; |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'b': |  | ||||||
| 			if (data->buffer == -1) { |  | ||||||
| 				n = strtonum(optarg, 0, INT_MAX, &errstr); |  | ||||||
| 				if (errstr != NULL) { |  | ||||||
| 					xasprintf(cause, "buffer %s", errstr); |  | ||||||
| 					goto error; |  | ||||||
| 				} |  | ||||||
| 				data->buffer = n; |  | ||||||
| 			} |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
|  |  | ||||||
| 	if (cmd_fill_argument( |  | ||||||
| 	    self->entry->flags, &data->arg, &data->arg2, argc, argv) != 0) |  | ||||||
| 		goto usage; |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| error: |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_buffer_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_buffer_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->arg != NULL) |  | ||||||
| 		xfree(data->arg); |  | ||||||
| 	if (data->arg2 != NULL) |  | ||||||
| 		xfree(data->arg2); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_buffer_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_buffer_data	*data = self->data; |  | ||||||
| 	size_t			 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	off += cmd_print_flags(buf, len, off, data->chflags); |  | ||||||
| 	if (off < len && data->buffer != -1) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -b %d", data->buffer); |  | ||||||
| 	if (off < len && data->arg != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->arg); |  | ||||||
| 	if (off < len && data->arg2 != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->arg2); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
| @@ -28,21 +28,20 @@ int	cmd_has_session_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_has_session_entry = { | const struct cmd_entry cmd_has_session_entry = { | ||||||
| 	"has-session", "has", | 	"has-session", "has", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_SESSION_USAGE, | 	CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_has_session_exec, | 	cmd_has_session_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_has_session_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_has_session_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
|  |  | ||||||
| 	if (cmd_find_session(ctx, data->target) == NULL) | 	if (cmd_find_session(ctx, args_get(args, 't')) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
|   | |||||||
| @@ -35,13 +35,12 @@ void	cmd_if_shell_free(void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_if_shell_entry = { | const struct cmd_entry cmd_if_shell_entry = { | ||||||
| 	"if-shell", "if", | 	"if-shell", "if", | ||||||
|  | 	"", 2, 2, | ||||||
| 	"shell-command command", | 	"shell-command command", | ||||||
| 	CMD_ARG2, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_if_shell_exec, | 	cmd_if_shell_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_if_shell_data { | struct cmd_if_shell_data { | ||||||
| @@ -52,12 +51,12 @@ struct cmd_if_shell_data { | |||||||
| int | int | ||||||
| cmd_if_shell_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_if_shell_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_if_shell_data	*cdata; | 	struct cmd_if_shell_data	*cdata; | ||||||
| 	struct job			*job; | 	struct job			*job; | ||||||
|  |  | ||||||
| 	cdata = xmalloc(sizeof *cdata); | 	cdata = xmalloc(sizeof *cdata); | ||||||
| 	cdata->cmd = xstrdup(data->arg2); | 	cdata->cmd = xstrdup(args->argv[1]); | ||||||
| 	memcpy(&cdata->ctx, ctx, sizeof cdata->ctx); | 	memcpy(&cdata->ctx, ctx, sizeof cdata->ctx); | ||||||
|  |  | ||||||
| 	if (ctx->cmdclient != NULL) | 	if (ctx->cmdclient != NULL) | ||||||
| @@ -66,7 +65,7 @@ cmd_if_shell_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		ctx->curclient->references++; | 		ctx->curclient->references++; | ||||||
|  |  | ||||||
| 	job = job_add(NULL, 0, NULL, | 	job = job_add(NULL, 0, NULL, | ||||||
| 	    data->arg, cmd_if_shell_callback, cmd_if_shell_free, cdata); | 	    args->argv[0], cmd_if_shell_callback, cmd_if_shell_free, cdata); | ||||||
| 	job_run(job); | 	job_run(job); | ||||||
|  |  | ||||||
| 	return (1);	/* don't let client exit */ | 	return (1);	/* don't let client exit */ | ||||||
|   | |||||||
							
								
								
									
										196
									
								
								cmd-join-pane.c
									
									
									
									
									
								
							
							
						
						
									
										196
									
								
								cmd-join-pane.c
									
									
									
									
									
								
							| @@ -28,139 +28,54 @@ | |||||||
|  * Join a pane into another (like split/swap/kill). |  * Join a pane into another (like split/swap/kill). | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_join_pane_parse(struct cmd *, int, char **, char **); | void	cmd_join_pane_key_binding(struct cmd *, int); | ||||||
| int	cmd_join_pane_exec(struct cmd *, struct cmd_ctx *); | int	cmd_join_pane_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_join_pane_free(struct cmd *); |  | ||||||
| void	cmd_join_pane_init(struct cmd *, int); |  | ||||||
| size_t	cmd_join_pane_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_join_pane_data { |  | ||||||
| 	char	*src; |  | ||||||
| 	char	*dst; |  | ||||||
| 	int	 flag_detached; |  | ||||||
| 	int	 flag_horizontal; |  | ||||||
| 	int	 percentage; |  | ||||||
| 	int	 size; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_join_pane_entry = { | const struct cmd_entry cmd_join_pane_entry = { | ||||||
| 	"join-pane", "joinp", | 	"join-pane", "joinp", | ||||||
|  | 	"dhvp:l:s:t:", 0, 0, | ||||||
| 	"[-dhv] [-p percentage|-l size] [-s src-pane] [-t dst-pane]", | 	"[-dhv] [-p percentage|-l size] [-s src-pane] [-t dst-pane]", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_join_pane_init, | 	cmd_join_pane_key_binding, | ||||||
| 	cmd_join_pane_parse, | 	NULL, | ||||||
| 	cmd_join_pane_exec, | 	cmd_join_pane_exec | ||||||
| 	cmd_join_pane_free, |  | ||||||
| 	cmd_join_pane_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_join_pane_init(struct cmd *self, int key) | cmd_join_pane_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_join_pane_data	 *data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->src = NULL; |  | ||||||
| 	data->dst = NULL; |  | ||||||
| 	data->flag_detached = 0; |  | ||||||
| 	data->flag_horizontal = 0; |  | ||||||
| 	data->percentage = -1; |  | ||||||
| 	data->size = -1; |  | ||||||
|  |  | ||||||
| 	switch (key) { | 	switch (key) { | ||||||
| 	case '%': | 	case '%': | ||||||
| 		data->flag_horizontal = 1; | 		self->args = args_create(0); | ||||||
|  | 		args_set(self->args, 'h', NULL); | ||||||
| 		break; | 		break; | ||||||
| 	case '"': | 	default: | ||||||
| 		data->flag_horizontal = 0; | 		self->args = args_create(0); | ||||||
| 		break; | 		break; | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_join_pane_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_join_pane_data	*data; |  | ||||||
| 	int				 opt; |  | ||||||
| 	const char			*errstr; |  | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "dhl:p:s:t:v")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'd': |  | ||||||
| 			data->flag_detached = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'h': |  | ||||||
| 			data->flag_horizontal = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 's': |  | ||||||
| 			if (data->src == NULL) |  | ||||||
| 				data->src = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->dst == NULL) |  | ||||||
| 				data->dst = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 'l': |  | ||||||
| 			if (data->percentage != -1 || data->size != -1) |  | ||||||
| 				break; |  | ||||||
| 			data->size = strtonum(optarg, 1, INT_MAX, &errstr); |  | ||||||
| 			if (errstr != NULL) { |  | ||||||
| 				xasprintf(cause, "size %s", errstr); |  | ||||||
| 				goto error; |  | ||||||
| 			} |  | ||||||
| 			break; |  | ||||||
| 		case 'p': |  | ||||||
| 			if (data->size != -1 || data->percentage != -1) |  | ||||||
| 				break; |  | ||||||
| 			data->percentage = strtonum(optarg, 1, 100, &errstr); |  | ||||||
| 			if (errstr != NULL) { |  | ||||||
| 				xasprintf(cause, "percentage %s", errstr); |  | ||||||
| 				goto error; |  | ||||||
| 			} |  | ||||||
| 			break; |  | ||||||
| 		case 'v': |  | ||||||
| 			data->flag_horizontal = 0; |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc != 0) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| error: |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_join_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_join_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_join_pane_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct session			*dst_s; | 	struct session		*dst_s; | ||||||
| 	struct winlink			*src_wl, *dst_wl; | 	struct winlink		*src_wl, *dst_wl; | ||||||
| 	struct window			*src_w, *dst_w; | 	struct window		*src_w, *dst_w; | ||||||
| 	struct window_pane		*src_wp, *dst_wp; | 	struct window_pane	*src_wp, *dst_wp; | ||||||
| 	int				 size, dst_idx; | 	char			*cause; | ||||||
| 	enum layout_type		 type; | 	int			 size, percentage, dst_idx; | ||||||
| 	struct layout_cell		*lc; | 	enum layout_type	 type; | ||||||
|  | 	struct layout_cell	*lc; | ||||||
|  |  | ||||||
| 	if ((dst_wl = cmd_find_pane(ctx, data->dst, &dst_s, &dst_wp)) == NULL) | 	dst_wl = cmd_find_pane(ctx, args_get(args, 't'), &dst_s, &dst_wp); | ||||||
|  | 	if (dst_wl == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	dst_w = dst_wl->window; | 	dst_w = dst_wl->window; | ||||||
| 	dst_idx = dst_wl->idx; | 	dst_idx = dst_wl->idx; | ||||||
|  |  | ||||||
| 	if ((src_wl = cmd_find_pane(ctx, data->src, NULL, &src_wp)) == NULL) | 	src_wl = cmd_find_pane(ctx, args_get(args, 's'), NULL, &src_wp); | ||||||
|  | 	if (src_wl == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	src_w = src_wl->window; | 	src_w = src_wl->window; | ||||||
|  |  | ||||||
| @@ -170,17 +85,28 @@ cmd_join_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	type = LAYOUT_TOPBOTTOM; | 	type = LAYOUT_TOPBOTTOM; | ||||||
| 	if (data->flag_horizontal) | 	if (args_has(args, 'h')) | ||||||
| 		type = LAYOUT_LEFTRIGHT; | 		type = LAYOUT_LEFTRIGHT; | ||||||
|  |  | ||||||
| 	size = -1; | 	size = -1; | ||||||
| 	if (data->size != -1) | 	if (args_has(args, 's')) { | ||||||
| 		size = data->size; | 		size = args_strtonum(args, 's', 0, INT_MAX, &cause); | ||||||
| 	else if (data->percentage != -1) { | 		if (cause != NULL) { | ||||||
|  | 			ctx->error(ctx, "size %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
|  | 	} else if (args_has(args, 'p')) { | ||||||
|  | 		percentage = args_strtonum(args, 'p', 0, INT_MAX, &cause); | ||||||
|  | 		if (cause != NULL) { | ||||||
|  | 			ctx->error(ctx, "percentage %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
| 		if (type == LAYOUT_TOPBOTTOM) | 		if (type == LAYOUT_TOPBOTTOM) | ||||||
| 			size = (dst_wp->sy * data->percentage) / 100; | 			size = (dst_wp->sy * percentage) / 100; | ||||||
| 		else | 		else | ||||||
| 			size = (dst_wp->sx * data->percentage) / 100; | 			size = (dst_wp->sx * percentage) / 100; | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if ((lc = layout_split_pane(dst_wp, type, size)) == NULL) { | 	if ((lc = layout_split_pane(dst_wp, type, size)) == NULL) { | ||||||
| @@ -209,7 +135,7 @@ cmd_join_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	server_redraw_window(src_w); | 	server_redraw_window(src_w); | ||||||
| 	server_redraw_window(dst_w); | 	server_redraw_window(dst_w); | ||||||
|  |  | ||||||
| 	if (!data->flag_detached) { | 	if (!args_has(args, 'd')) { | ||||||
| 		window_set_active_pane(dst_w, src_wp); | 		window_set_active_pane(dst_w, src_wp); | ||||||
| 		session_select(dst_s, dst_idx); | 		session_select(dst_s, dst_idx); | ||||||
| 		server_redraw_session(dst_s); | 		server_redraw_session(dst_s); | ||||||
| @@ -218,41 +144,3 @@ cmd_join_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_join_pane_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_join_pane_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->src != NULL) |  | ||||||
| 		xfree(data->src); |  | ||||||
| 	if (data->dst != NULL) |  | ||||||
| 		xfree(data->dst); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_join_pane_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_join_pane_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->flag_detached) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -d"); |  | ||||||
| 	if (off < len && data->flag_horizontal) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -h"); |  | ||||||
| 	if (off < len && data->size > 0) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -l %d", data->size); |  | ||||||
| 	if (off < len && data->percentage > 0) { |  | ||||||
| 		off += xsnprintf( |  | ||||||
| 		    buf + off, len - off, " -p %d", data->percentage); |  | ||||||
| 	} |  | ||||||
| 	if (off < len && data->src != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -s ", data->src); |  | ||||||
| 	if (off < len && data->dst != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->dst); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -30,23 +30,22 @@ int	cmd_kill_pane_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_kill_pane_entry = { | const struct cmd_entry cmd_kill_pane_entry = { | ||||||
| 	"kill-pane", "killp", | 	"kill-pane", "killp", | ||||||
|  | 	"at:", 0, 0, | ||||||
| 	"[-a] " CMD_TARGET_PANE_USAGE, | 	"[-a] " CMD_TARGET_PANE_USAGE, | ||||||
| 	0, "a", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_kill_pane_exec, | 	cmd_kill_pane_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_kill_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_kill_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	struct window_pane	*loopwp, *nextwp, *wp; | 	struct window_pane	*loopwp, *nextwp, *wp; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_pane(ctx, data->target, NULL, &wp)) == NULL) | 	if ((wl = cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (window_count_panes(wl->window) == 1) { | 	if (window_count_panes(wl->window) == 1) { | ||||||
| @@ -56,7 +55,7 @@ cmd_kill_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		return (0); | 		return (0); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'a')) { | 	if (args_has(self->args, 'a')) { | ||||||
| 		loopwp = TAILQ_FIRST(&wl->window->panes); | 		loopwp = TAILQ_FIRST(&wl->window->panes); | ||||||
| 		while (loopwp != NULL) { | 		while (loopwp != NULL) { | ||||||
| 			nextwp = TAILQ_NEXT(loopwp, entry); | 			nextwp = TAILQ_NEXT(loopwp, entry); | ||||||
|   | |||||||
| @@ -31,13 +31,12 @@ int	cmd_kill_server_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_kill_server_entry = { | const struct cmd_entry cmd_kill_server_entry = { | ||||||
| 	"kill-server", NULL, | 	"kill-server", NULL, | ||||||
|  | 	"", 0, 0, | ||||||
| 	"", | 	"", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_kill_server_exec, | 	cmd_kill_server_exec | ||||||
| 	NULL, |  | ||||||
| 	NULL |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -31,22 +31,21 @@ int	cmd_kill_session_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_kill_session_entry = { | const struct cmd_entry cmd_kill_session_entry = { | ||||||
| 	"kill-session", NULL, | 	"kill-session", NULL, | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_SESSION_USAGE, | 	CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_kill_session_exec, | 	cmd_kill_session_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_kill_session_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_kill_session_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	server_destroy_session(s); | 	server_destroy_session(s); | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_kill_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_kill_window_entry = { | const struct cmd_entry cmd_kill_window_entry = { | ||||||
| 	"kill-window", "killw", | 	"kill-window", "killw", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_WINDOW_USAGE, | 	CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_kill_window_exec, | 	cmd_kill_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_kill_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_kill_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	server_kill_window(wl->window); | 	server_kill_window(wl->window); | ||||||
|   | |||||||
| @@ -28,23 +28,22 @@ int	cmd_last_pane_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_last_pane_entry = { | const struct cmd_entry cmd_last_pane_entry = { | ||||||
| 	"last-pane", "lastp", | 	"last-pane", "lastp", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_WINDOW_USAGE, | 	CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_last_pane_exec, | 	cmd_last_pane_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_last_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_last_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	struct window		*w; | 	struct window	*w; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	w = wl->window; | 	w = wl->window; | ||||||
|  |  | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_last_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_last_window_entry = { | const struct cmd_entry cmd_last_window_entry = { | ||||||
| 	"last-window", "last", | 	"last-window", "last", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_SESSION_USAGE, | 	CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_last_window_exec, | 	cmd_last_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_last_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_last_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (session_last(s) == 0) | 	if (session_last(s) == 0) | ||||||
|   | |||||||
| @@ -30,31 +30,30 @@ int	cmd_link_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_link_window_entry = { | const struct cmd_entry cmd_link_window_entry = { | ||||||
| 	"link-window", "linkw", | 	"link-window", "linkw", | ||||||
|  | 	"dks:t:", 0, 0, | ||||||
| 	"[-dk] " CMD_SRCDST_WINDOW_USAGE, | 	"[-dk] " CMD_SRCDST_WINDOW_USAGE, | ||||||
| 	0, "dk", | 	0, | ||||||
| 	cmd_srcdst_init, | 	NULL, | ||||||
| 	cmd_srcdst_parse, | 	NULL, | ||||||
| 	cmd_link_window_exec, | 	cmd_link_window_exec | ||||||
| 	cmd_srcdst_free, |  | ||||||
| 	cmd_srcdst_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_link_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_link_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_srcdst_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*src, *dst; | 	struct session	*src, *dst; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	char			*cause; | 	char		*cause; | ||||||
| 	int			 idx, kflag, dflag; | 	int		 idx, kflag, dflag; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->src, &src)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 's'), &src)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	if ((idx = cmd_find_index(ctx, data->dst, &dst)) == -2) | 	if ((idx = cmd_find_index(ctx, args_get(args, 't'), &dst)) == -2) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	kflag = cmd_check_flag(data->chflags, 'k'); | 	kflag = args_has(self->args, 'k'); | ||||||
| 	dflag = cmd_check_flag(data->chflags, 'd'); | 	dflag = args_has(self->args, 'd'); | ||||||
| 	if (server_link_window(src, wl, dst, idx, kflag, !dflag, &cause) != 0) { | 	if (server_link_window(src, wl, dst, idx, kflag, !dflag, &cause) != 0) { | ||||||
| 		ctx->error(ctx, "can't link window: %s", cause); | 		ctx->error(ctx, "can't link window: %s", cause); | ||||||
| 		xfree(cause); | 		xfree(cause); | ||||||
|   | |||||||
| @@ -30,13 +30,12 @@ int	cmd_list_buffers_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_list_buffers_entry = { | const struct cmd_entry cmd_list_buffers_entry = { | ||||||
| 	"list-buffers", "lsb", | 	"list-buffers", "lsb", | ||||||
|  | 	"", 0, 0, | ||||||
| 	"", | 	"", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_list_buffers_exec, | 	cmd_list_buffers_exec | ||||||
| 	NULL, |  | ||||||
| 	NULL	 |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -31,13 +31,12 @@ int	cmd_list_clients_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_list_clients_entry = { | const struct cmd_entry cmd_list_clients_entry = { | ||||||
| 	"list-clients", "lsc", | 	"list-clients", "lsc", | ||||||
|  | 	"", 0, 0, | ||||||
| 	"", | 	"", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_list_clients_exec, | 	cmd_list_clients_exec | ||||||
| 	NULL, |  | ||||||
| 	NULL |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -28,13 +28,12 @@ int	cmd_list_commands_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_list_commands_entry = { | const struct cmd_entry cmd_list_commands_entry = { | ||||||
| 	"list-commands", "lscm", | 	"list-commands", "lscm", | ||||||
|  | 	"", 0, 0, | ||||||
| 	"", | 	"", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_list_commands_exec, | 	cmd_list_commands_exec | ||||||
| 	NULL, |  | ||||||
| 	NULL |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -32,26 +32,25 @@ int	cmd_list_keys_table(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_list_keys_entry = { | const struct cmd_entry cmd_list_keys_entry = { | ||||||
| 	"list-keys", "lsk", | 	"list-keys", "lsk", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	"[-t key-table]", | 	"[-t key-table]", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_list_keys_exec, | 	cmd_list_keys_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_list_keys_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_list_keys_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct key_binding	*bd; | 	struct key_binding	*bd; | ||||||
| 	const char		*key; | 	const char		*key; | ||||||
| 	char			 tmp[BUFSIZ]; | 	char			 tmp[BUFSIZ]; | ||||||
| 	size_t			 used; | 	size_t			 used; | ||||||
| 	int			 width, keywidth; | 	int			 width, keywidth; | ||||||
|  |  | ||||||
| 	if (data->target != NULL) | 	if (args_has(args, 't')) | ||||||
| 		return (cmd_list_keys_table(self, ctx)); | 		return (cmd_list_keys_table(self, ctx)); | ||||||
|  |  | ||||||
| 	width = 0; | 	width = 0; | ||||||
| @@ -95,14 +94,16 @@ cmd_list_keys_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| int | int | ||||||
| cmd_list_keys_table(struct cmd *self, struct cmd_ctx *ctx) | cmd_list_keys_table(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
|  | 	const char			*tablename; | ||||||
| 	const struct mode_key_table	*mtab; | 	const struct mode_key_table	*mtab; | ||||||
| 	struct mode_key_binding		*mbind; | 	struct mode_key_binding		*mbind; | ||||||
| 	const char			*key, *cmdstr, *mode; | 	const char			*key, *cmdstr, *mode; | ||||||
| 	int			 	 width, keywidth; | 	int			 	 width, keywidth; | ||||||
|  |  | ||||||
| 	if ((mtab = mode_key_findtable(data->target)) == NULL) { | 	tablename = args_get(args, 't'); | ||||||
| 		ctx->error(ctx, "unknown key table: %s", data->target); | 	if ((mtab = mode_key_findtable(tablename)) == NULL) { | ||||||
|  | 		ctx->error(ctx, "unknown key table: %s", tablename); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
|   | |||||||
| @@ -30,19 +30,18 @@ int	cmd_list_panes_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_list_panes_entry = { | const struct cmd_entry cmd_list_panes_entry = { | ||||||
| 	"list-panes", "lsp", | 	"list-panes", "lsp", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_WINDOW_USAGE, | 	CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_list_panes_exec, | 	cmd_list_panes_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_list_panes_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_list_panes_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
| 	struct grid		*gd; | 	struct grid		*gd; | ||||||
| @@ -50,7 +49,7 @@ cmd_list_panes_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	u_int			 i, n; | 	u_int			 i, n; | ||||||
| 	unsigned long long	 size; | 	unsigned long long	 size; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	n = 0; | 	n = 0; | ||||||
|   | |||||||
| @@ -30,13 +30,13 @@ | |||||||
| int	cmd_list_sessions_exec(struct cmd *, struct cmd_ctx *); | int	cmd_list_sessions_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_list_sessions_entry = { | const struct cmd_entry cmd_list_sessions_entry = { | ||||||
| 	"list-sessions", "ls", "", | 	"list-sessions", "ls", | ||||||
| 	0, "", | 	"", 0, 0, | ||||||
|  | 	"", | ||||||
|  | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_list_sessions_exec, | 	cmd_list_sessions_exec | ||||||
| 	NULL, |  | ||||||
| 	NULL |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -30,24 +30,23 @@ int	cmd_list_windows_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_list_windows_entry = { | const struct cmd_entry cmd_list_windows_entry = { | ||||||
| 	"list-windows", "lsw", | 	"list-windows", "lsw", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_SESSION_USAGE, | 	CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_list_windows_exec, | 	cmd_list_windows_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_list_windows_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_list_windows_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	char			*layout; | 	char		*layout; | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	RB_FOREACH(wl, winlinks, &s->windows) { | 	RB_FOREACH(wl, winlinks, &s->windows) { | ||||||
|   | |||||||
| @@ -35,41 +35,57 @@ void	cmd_load_buffer_callback(struct client *, void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_load_buffer_entry = { | const struct cmd_entry cmd_load_buffer_entry = { | ||||||
| 	"load-buffer", "loadb", | 	"load-buffer", "loadb", | ||||||
|  | 	"b:", 1, 1, | ||||||
| 	CMD_BUFFER_USAGE " path", | 	CMD_BUFFER_USAGE " path", | ||||||
| 	CMD_ARG1, "", | 	0, | ||||||
| 	cmd_buffer_init, | 	NULL, | ||||||
| 	cmd_buffer_parse, | 	NULL, | ||||||
| 	cmd_load_buffer_exec, | 	cmd_load_buffer_exec | ||||||
| 	cmd_buffer_free, |  | ||||||
| 	cmd_buffer_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_load_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_load_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_buffer_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct client		*c = ctx->cmdclient; | 	struct client	*c = ctx->cmdclient; | ||||||
| 	FILE			*f; | 	FILE		*f; | ||||||
| 	char		      	*pdata, *new_pdata; | 	const char	*path; | ||||||
| 	size_t			 psize; | 	char		*pdata, *new_pdata, *cause; | ||||||
| 	u_int			 limit; | 	size_t		 psize; | ||||||
| 	int			 ch; | 	u_int		 limit; | ||||||
|  | 	int		 ch, buffer; | ||||||
|  | 	int		*buffer_ptr; | ||||||
|  |  | ||||||
| 	if (strcmp(data->arg, "-") == 0) { | 	if (!args_has(args, 'b')) | ||||||
|  | 		buffer = -1; | ||||||
|  | 	else { | ||||||
|  | 		buffer = args_strtonum(args, 'b', 0, INT_MAX, &cause); | ||||||
|  | 		if (cause != NULL) { | ||||||
|  | 			ctx->error(ctx, "buffer %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	path = args->argv[0]; | ||||||
|  | 	if (strcmp(path, "-") == 0) { | ||||||
| 		if (c == NULL) { | 		if (c == NULL) { | ||||||
| 			ctx->error(ctx, "%s: can't read from stdin", data->arg); | 			ctx->error(ctx, "%s: can't read from stdin", path); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		if (c->flags & CLIENT_TERMINAL) { | 		if (c->flags & CLIENT_TERMINAL) { | ||||||
| 			ctx->error(ctx, "%s: stdin is a tty", data->arg); | 			ctx->error(ctx, "%s: stdin is a tty", path); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		if (c->stdin_fd == -1) { | 		if (c->stdin_fd == -1) { | ||||||
| 			ctx->error(ctx, "%s: can't read from stdin", data->arg); | 			ctx->error(ctx, "%s: can't read from stdin", path); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
|  |  | ||||||
| 		c->stdin_data = &data->buffer; | 		buffer_ptr = xmalloc(sizeof *buffer_ptr); | ||||||
|  | 		*buffer_ptr = buffer; | ||||||
|  |  | ||||||
|  | 		c->stdin_data = buffer_ptr; | ||||||
| 		c->stdin_callback = cmd_load_buffer_callback; | 		c->stdin_callback = cmd_load_buffer_callback; | ||||||
|  |  | ||||||
| 		c->references++; | 		c->references++; | ||||||
| @@ -77,8 +93,8 @@ cmd_load_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		return (1); | 		return (1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if ((f = fopen(data->arg, "rb")) == NULL) { | 	if ((f = fopen(path, "rb")) == NULL) { | ||||||
| 		ctx->error(ctx, "%s: %s", data->arg, strerror(errno)); | 		ctx->error(ctx, "%s: %s", path, strerror(errno)); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| @@ -94,7 +110,7 @@ cmd_load_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		pdata[psize++] = ch; | 		pdata[psize++] = ch; | ||||||
| 	} | 	} | ||||||
| 	if (ferror(f)) { | 	if (ferror(f)) { | ||||||
| 		ctx->error(ctx, "%s: read error", data->arg); | 		ctx->error(ctx, "%s: read error", path); | ||||||
| 		goto error; | 		goto error; | ||||||
| 	} | 	} | ||||||
| 	if (pdata != NULL) | 	if (pdata != NULL) | ||||||
| @@ -103,12 +119,12 @@ cmd_load_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	fclose(f); | 	fclose(f); | ||||||
|  |  | ||||||
| 	limit = options_get_number(&global_options, "buffer-limit"); | 	limit = options_get_number(&global_options, "buffer-limit"); | ||||||
| 	if (data->buffer == -1) { | 	if (buffer == -1) { | ||||||
| 		paste_add(&global_buffers, pdata, psize, limit); | 		paste_add(&global_buffers, pdata, psize, limit); | ||||||
| 		return (0); | 		return (0); | ||||||
| 	} | 	} | ||||||
| 	if (paste_replace(&global_buffers, data->buffer, pdata, psize) != 0) { | 	if (paste_replace(&global_buffers, buffer, pdata, psize) != 0) { | ||||||
| 		ctx->error(ctx, "no buffer %d", data->buffer); | 		ctx->error(ctx, "no buffer %d", buffer); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| @@ -125,10 +141,10 @@ error: | |||||||
| void | void | ||||||
| cmd_load_buffer_callback(struct client *c, void *data) | cmd_load_buffer_callback(struct client *c, void *data) | ||||||
| { | { | ||||||
|  | 	int	*buffer = data; | ||||||
| 	char	*pdata; | 	char	*pdata; | ||||||
| 	size_t	 psize; | 	size_t	 psize; | ||||||
| 	u_int	 limit; | 	u_int	 limit; | ||||||
| 	int	*buffer = data; |  | ||||||
|  |  | ||||||
| 	/* | 	/* | ||||||
| 	 * Event callback has already checked client is not dead and reduced | 	 * Event callback has already checked client is not dead and reduced | ||||||
| @@ -137,12 +153,10 @@ cmd_load_buffer_callback(struct client *c, void *data) | |||||||
| 	c->flags |= CLIENT_EXIT; | 	c->flags |= CLIENT_EXIT; | ||||||
|  |  | ||||||
| 	psize = EVBUFFER_LENGTH(c->stdin_event->input); | 	psize = EVBUFFER_LENGTH(c->stdin_event->input); | ||||||
| 	if (psize == 0) | 	if (psize == 0 || (pdata = malloc(psize + 1)) == NULL) { | ||||||
| 		return; | 		free(data); | ||||||
|  |  | ||||||
| 	pdata = malloc(psize + 1); |  | ||||||
| 	if (pdata == NULL) |  | ||||||
| 		return; | 		return; | ||||||
|  | 	} | ||||||
| 	bufferevent_read(c->stdin_event, pdata, psize); | 	bufferevent_read(c->stdin_event, pdata, psize); | ||||||
| 	pdata[psize] = '\0'; | 	pdata[psize] = '\0'; | ||||||
|  |  | ||||||
| @@ -155,4 +169,6 @@ cmd_load_buffer_callback(struct client *c, void *data) | |||||||
| 		    c->stderr_event->output, "no buffer %d\n", *buffer); | 		    c->stderr_event->output, "no buffer %d\n", *buffer); | ||||||
| 		bufferevent_enable(c->stderr_event, EV_WRITE); | 		bufferevent_enable(c->stderr_event, EV_WRITE); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
|  | 	free (data); | ||||||
| } | } | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_lock_client_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_lock_client_entry = { | const struct cmd_entry cmd_lock_client_entry = { | ||||||
| 	"lock-client", "lockc", | 	"lock-client", "lockc", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_CLIENT_USAGE, | 	CMD_TARGET_CLIENT_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_lock_client_exec, | 	cmd_lock_client_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_lock_client_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_lock_client_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct client		*c; | 	struct client	*c; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	server_lock_client(c); | 	server_lock_client(c); | ||||||
|   | |||||||
| @@ -32,13 +32,12 @@ int	cmd_lock_server_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_lock_server_entry = { | const struct cmd_entry cmd_lock_server_entry = { | ||||||
| 	"lock-server", "lock", | 	"lock-server", "lock", | ||||||
|  | 	"", 0, 0, | ||||||
| 	"", | 	"", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, |  | ||||||
| 	NULL, |  | ||||||
| 	cmd_lock_server_exec, |  | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
|  | 	cmd_lock_server_exec | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_lock_session_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_lock_session_entry = { | const struct cmd_entry cmd_lock_session_entry = { | ||||||
| 	"lock-session", "locks", | 	"lock-session", "locks", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_SESSION_USAGE, | 	CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_lock_session_exec, | 	cmd_lock_session_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_lock_session_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_lock_session_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	server_lock_session(s); | 	server_lock_session(s); | ||||||
|   | |||||||
| @@ -30,31 +30,30 @@ int	cmd_move_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_move_window_entry = { | const struct cmd_entry cmd_move_window_entry = { | ||||||
| 	"move-window", "movew", | 	"move-window", "movew", | ||||||
|  | 	"dks:t:", 0, 0, | ||||||
| 	"[-dk] " CMD_SRCDST_WINDOW_USAGE, | 	"[-dk] " CMD_SRCDST_WINDOW_USAGE, | ||||||
| 	0, "dk", | 	0, | ||||||
| 	cmd_srcdst_init, | 	NULL, | ||||||
| 	cmd_srcdst_parse, | 	NULL, | ||||||
| 	cmd_move_window_exec, | 	cmd_move_window_exec | ||||||
| 	cmd_srcdst_free, |  | ||||||
| 	cmd_srcdst_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_move_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_move_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_srcdst_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*src, *dst; | 	struct session	*src, *dst; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	char			*cause; | 	char		*cause; | ||||||
| 	int			 idx, kflag, dflag; | 	int		 idx, kflag, dflag; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->src, &src)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 's'), &src)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	if ((idx = cmd_find_index(ctx, data->dst, &dst)) == -2) | 	if ((idx = cmd_find_index(ctx, args_get(args, 't'), &dst)) == -2) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	kflag = cmd_check_flag(data->chflags, 'k'); | 	kflag = args_has(self->args, 'k'); | ||||||
| 	dflag = cmd_check_flag(data->chflags, 'd'); | 	dflag = args_has(self->args, 'd'); | ||||||
| 	if (server_link_window(src, wl, dst, idx, kflag, !dflag, &cause) != 0) { | 	if (server_link_window(src, wl, dst, idx, kflag, !dflag, &cause) != 0) { | ||||||
| 		ctx->error(ctx, "can't move window: %s", cause); | 		ctx->error(ctx, "can't move window: %s", cause); | ||||||
| 		xfree(cause); | 		xfree(cause); | ||||||
|   | |||||||
| @@ -29,119 +29,55 @@ | |||||||
|  * Create a new session and attach to the current terminal unless -d is given. |  * Create a new session and attach to the current terminal unless -d is given. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_new_session_parse(struct cmd *, int, char **, char **); | int	cmd_new_session_check(struct args *); | ||||||
| int	cmd_new_session_exec(struct cmd *, struct cmd_ctx *); | int	cmd_new_session_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_new_session_free(struct cmd *); |  | ||||||
| void	cmd_new_session_init(struct cmd *, int); |  | ||||||
| size_t	cmd_new_session_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_new_session_data { |  | ||||||
| 	char	*target; |  | ||||||
| 	char	*newname; |  | ||||||
| 	char	*winname; |  | ||||||
| 	char	*cmd; |  | ||||||
| 	int	 flag_detached; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_new_session_entry = { | const struct cmd_entry cmd_new_session_entry = { | ||||||
| 	"new-session", "new", | 	"new-session", "new", | ||||||
|  | 	"dn:s:t:", 0, 1, | ||||||
| 	"[-d] [-n window-name] [-s session-name] [-t target-session] [command]", | 	"[-d] [-n window-name] [-s session-name] [-t target-session] [command]", | ||||||
| 	CMD_STARTSERVER|CMD_CANTNEST|CMD_SENDENVIRON, "", | 	CMD_STARTSERVER|CMD_CANTNEST|CMD_SENDENVIRON, | ||||||
| 	cmd_new_session_init, | 	NULL, | ||||||
| 	cmd_new_session_parse, | 	cmd_new_session_check, | ||||||
| 	cmd_new_session_exec, | 	cmd_new_session_exec | ||||||
| 	cmd_new_session_free, |  | ||||||
| 	cmd_new_session_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_new_session_init(struct cmd *self, unused int arg) |  | ||||||
| { |  | ||||||
| 	struct cmd_new_session_data	 *data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->flag_detached = 0; |  | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->newname = NULL; |  | ||||||
| 	data->winname = NULL; |  | ||||||
| 	data->cmd = NULL; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_new_session_parse(struct cmd *self, int argc, char **argv, char **cause) | cmd_new_session_check(struct args *args) | ||||||
| { | { | ||||||
| 	struct cmd_new_session_data	*data; | 	if (args_has(args, 't') && (args->argc != 0 || args_has(args, 'n'))) | ||||||
| 	int				 opt; | 		return (-1); | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "ds:t:n:")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'd': |  | ||||||
| 			data->flag_detached = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 's': |  | ||||||
| 			if (data->newname == NULL) |  | ||||||
| 				data->newname = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 'n': |  | ||||||
| 			if (data->winname == NULL) |  | ||||||
| 				data->winname = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc != 0 && argc != 1) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	if (data->target != NULL && (argc == 1 || data->winname != NULL)) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	if (argc == 1) |  | ||||||
| 		data->cmd = xstrdup(argv[0]); |  | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_new_session_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct session			*s, *old_s, *groupwith; | 	struct session		*s, *old_s, *groupwith; | ||||||
| 	struct window			*w; | 	struct window		*w; | ||||||
| 	struct window_pane		*wp; | 	struct window_pane	*wp; | ||||||
| 	struct environ			 env; | 	struct environ		 env; | ||||||
| 	struct termios			 tio, *tiop; | 	struct termios		 tio, *tiop; | ||||||
| 	struct passwd			*pw; | 	struct passwd		*pw; | ||||||
| 	const char			*update, *cwd; | 	const char		*newname, *target, *update, *cwd; | ||||||
| 	char				*overrides, *cmd, *cause; | 	char			*overrides, *cmd, *cause; | ||||||
| 	int				 detached, idx; | 	int			 detached, idx; | ||||||
| 	u_int				 sx, sy, i; | 	u_int			 sx, sy, i; | ||||||
|  |  | ||||||
| 	if (data->newname != NULL && session_find(data->newname) != NULL) { | 	newname = args_get(args, 's'); | ||||||
| 		ctx->error(ctx, "duplicate session: %s", data->newname); | 	if (newname != NULL && session_find(newname) != NULL) { | ||||||
|  | 		ctx->error(ctx, "duplicate session: %s", newname); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	groupwith = NULL; | 	target = args_get(args, 't'); | ||||||
| 	if (data->target != NULL && | 	if (target != NULL) { | ||||||
| 	    (groupwith = cmd_find_session(ctx, data->target)) == NULL) | 		groupwith = cmd_find_session(ctx, target); | ||||||
| 		return (-1); | 		if (groupwith == NULL) | ||||||
|  | 			return (-1); | ||||||
|  | 	} else | ||||||
|  | 		groupwith = NULL; | ||||||
|  |  | ||||||
| 	/* | 	/* | ||||||
| 	 * There are three cases: | 	 * There are three cases: | ||||||
| @@ -162,7 +98,7 @@ cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	 */ | 	 */ | ||||||
|  |  | ||||||
| 	/* Set -d if no client. */ | 	/* Set -d if no client. */ | ||||||
| 	detached = data->flag_detached; | 	detached = args_has(args, 'd'); | ||||||
| 	if (ctx->cmdclient == NULL && ctx->curclient == NULL) | 	if (ctx->cmdclient == NULL && ctx->curclient == NULL) | ||||||
| 		detached = 1; | 		detached = 1; | ||||||
|  |  | ||||||
| @@ -228,10 +164,10 @@ cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		sy = 1; | 		sy = 1; | ||||||
|  |  | ||||||
| 	/* Figure out the command for the new window. */ | 	/* Figure out the command for the new window. */ | ||||||
| 	if (data->target != NULL) | 	if (target != NULL) | ||||||
| 		cmd = NULL; | 		cmd = NULL; | ||||||
| 	else if (data->cmd != NULL) | 	else if (args->argc != 0) | ||||||
| 		cmd = data->cmd; | 		cmd = args->argv[0]; | ||||||
| 	else | 	else | ||||||
| 		cmd = options_get_string(&global_s_options, "default-command"); | 		cmd = options_get_string(&global_s_options, "default-command"); | ||||||
|  |  | ||||||
| @@ -243,8 +179,7 @@ cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	/* Create the new session. */ | 	/* Create the new session. */ | ||||||
| 	idx = -1 - options_get_number(&global_s_options, "base-index"); | 	idx = -1 - options_get_number(&global_s_options, "base-index"); | ||||||
| 	s = session_create( | 	s = session_create(newname, cmd, cwd, &env, tiop, idx, sx, sy, &cause); | ||||||
| 	    data->newname, cmd, cwd, &env, tiop, idx, sx, sy, &cause); |  | ||||||
| 	if (s == NULL) { | 	if (s == NULL) { | ||||||
| 		ctx->error(ctx, "create session failed: %s", cause); | 		ctx->error(ctx, "create session failed: %s", cause); | ||||||
| 		xfree(cause); | 		xfree(cause); | ||||||
| @@ -253,11 +188,11 @@ cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	environ_free(&env); | 	environ_free(&env); | ||||||
|  |  | ||||||
| 	/* Set the initial window name if one given. */ | 	/* Set the initial window name if one given. */ | ||||||
| 	if (cmd != NULL && data->winname != NULL) { | 	if (cmd != NULL && args_has(args, 'n')) { | ||||||
| 		w = s->curw->window; | 		w = s->curw->window; | ||||||
|  |  | ||||||
| 		xfree(w->name); | 		xfree(w->name); | ||||||
| 		w->name = xstrdup(data->winname); | 		w->name = xstrdup(args_get(args, 'n')); | ||||||
|  |  | ||||||
| 		options_set_number(&w->options, "automatic-rename", 0); | 		options_set_number(&w->options, "automatic-rename", 0); | ||||||
| 	} | 	} | ||||||
| @@ -316,39 +251,3 @@ cmd_new_session_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	return (!detached);	/* 1 means don't tell command client to exit */ | 	return (!detached);	/* 1 means don't tell command client to exit */ | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_new_session_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_new_session_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->newname != NULL) |  | ||||||
| 		xfree(data->newname); |  | ||||||
| 	if (data->winname != NULL) |  | ||||||
| 		xfree(data->winname); |  | ||||||
| 	if (data->cmd != NULL) |  | ||||||
| 		xfree(data->cmd); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_new_session_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_new_session_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->flag_detached) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -d"); |  | ||||||
| 	if (off < len && data->winname != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -n ", data->winname); |  | ||||||
| 	if (off < len && data->newname != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -s ", data->newname); |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
| 	if (off < len && data->cmd != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->cmd); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
							
								
								
									
										167
									
								
								cmd-new-window.c
									
									
									
									
									
								
							
							
						
						
									
										167
									
								
								cmd-new-window.c
									
									
									
									
									
								
							| @@ -26,115 +26,30 @@ | |||||||
|  * Create a new window. |  * Create a new window. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_new_window_parse(struct cmd *, int, char **, char **); |  | ||||||
| int	cmd_new_window_exec(struct cmd *, struct cmd_ctx *); | int	cmd_new_window_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_new_window_free(struct cmd *); |  | ||||||
| void	cmd_new_window_init(struct cmd *, int); |  | ||||||
| size_t	cmd_new_window_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_new_window_data { |  | ||||||
| 	char	*target; |  | ||||||
| 	char	*name; |  | ||||||
| 	char	*cmd; |  | ||||||
| 	int	 flag_insert_after; |  | ||||||
| 	int	 flag_detached; |  | ||||||
| 	int	 flag_kill; |  | ||||||
| 	int      flag_print; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_new_window_entry = { | const struct cmd_entry cmd_new_window_entry = { | ||||||
| 	"new-window", "neww", | 	"new-window", "neww", | ||||||
| 	"[-adkP] [-n window-name] [-t target-window] [command]", | 	"adkn:Pt:", 0, 1, | ||||||
| 	0, "", | 	"[-adk] [-n window-name] [-t target-window] [command]", | ||||||
| 	cmd_new_window_init, | 	0, | ||||||
| 	cmd_new_window_parse, | 	NULL, | ||||||
| 	cmd_new_window_exec, | 	NULL, | ||||||
| 	cmd_new_window_free, | 	cmd_new_window_exec | ||||||
| 	cmd_new_window_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_new_window_init(struct cmd *self, unused int arg) |  | ||||||
| { |  | ||||||
| 	struct cmd_new_window_data	 *data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->name = NULL; |  | ||||||
| 	data->cmd = NULL; |  | ||||||
| 	data->flag_insert_after = 0; |  | ||||||
| 	data->flag_detached = 0; |  | ||||||
| 	data->flag_kill = 0; |  | ||||||
| 	data->flag_print = 0; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_new_window_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_new_window_data	*data; |  | ||||||
| 	int				 opt; |  | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "adkt:n:P")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'a': |  | ||||||
| 			data->flag_insert_after = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'd': |  | ||||||
| 			data->flag_detached = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'k': |  | ||||||
| 			data->flag_kill = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 'n': |  | ||||||
| 			if (data->name == NULL) |  | ||||||
| 				data->name = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 'P': |  | ||||||
| 			data->flag_print = 1; |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc != 0 && argc != 1) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	if (argc == 1) |  | ||||||
| 		data->cmd = xstrdup(argv[0]); |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_new_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_new_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_new_window_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session			*s; | 	struct session	*s; | ||||||
| 	struct winlink			*wl; | 	struct winlink	*wl; | ||||||
| 	char				*cmd, *cwd, *cause; | 	char		*cmd, *cwd, *cause; | ||||||
| 	int				 idx, last; | 	int		 idx, last, detached; | ||||||
|  |  | ||||||
| 	if (data == NULL) | 	if (args_has(args, 'a')) { | ||||||
| 		return (0); | 		wl = cmd_find_window(ctx, args_get(args, 't'), &s); | ||||||
|  | 		if (wl == NULL) | ||||||
| 	if (data->flag_insert_after) { |  | ||||||
| 		if ((wl = cmd_find_window(ctx, data->target, &s)) == NULL) |  | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		idx = wl->idx + 1; | 		idx = wl->idx + 1; | ||||||
|  |  | ||||||
| @@ -155,14 +70,15 @@ cmd_new_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 			server_unlink_window(s, wl); | 			server_unlink_window(s, wl); | ||||||
| 		} | 		} | ||||||
| 	} else { | 	} else { | ||||||
| 		if ((idx = cmd_find_index(ctx, data->target, &s)) == -2) | 		if ((idx = cmd_find_index(ctx, args_get(args, 't'), &s)) == -2) | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 	} | 	} | ||||||
|  | 	detached = args_has(args, 'd'); | ||||||
|  |  | ||||||
| 	wl = NULL; | 	wl = NULL; | ||||||
| 	if (idx != -1) | 	if (idx != -1) | ||||||
| 		wl = winlink_find_by_index(&s->windows, idx); | 		wl = winlink_find_by_index(&s->windows, idx); | ||||||
| 	if (wl != NULL && data->flag_kill) { | 	if (wl != NULL && args_has(args, 'k')) { | ||||||
| 		/* | 		/* | ||||||
| 		 * Can't use session_detach as it will destroy session if this | 		 * Can't use session_detach as it will destroy session if this | ||||||
| 		 * makes it empty. | 		 * makes it empty. | ||||||
| @@ -173,14 +89,15 @@ cmd_new_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 		/* Force select/redraw if current. */ | 		/* Force select/redraw if current. */ | ||||||
| 		if (wl == s->curw) { | 		if (wl == s->curw) { | ||||||
| 			data->flag_detached = 0; | 			detached = 0; | ||||||
| 			s->curw = NULL; | 			s->curw = NULL; | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	cmd = data->cmd; | 	if (args->argc == 0) | ||||||
| 	if (cmd == NULL) |  | ||||||
| 		cmd = options_get_string(&s->options, "default-command"); | 		cmd = options_get_string(&s->options, "default-command"); | ||||||
|  | 	else | ||||||
|  | 		cmd = args->argv[0]; | ||||||
| 	cwd = options_get_string(&s->options, "default-path"); | 	cwd = options_get_string(&s->options, "default-path"); | ||||||
| 	if (*cwd == '\0') { | 	if (*cwd == '\0') { | ||||||
| 		if (ctx->cmdclient != NULL && ctx->cmdclient->cwd != NULL) | 		if (ctx->cmdclient != NULL && ctx->cmdclient->cwd != NULL) | ||||||
| @@ -191,55 +108,19 @@ cmd_new_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	if (idx == -1) | 	if (idx == -1) | ||||||
| 		idx = -1 - options_get_number(&s->options, "base-index"); | 		idx = -1 - options_get_number(&s->options, "base-index"); | ||||||
| 	wl = session_new(s, data->name, cmd, cwd, idx, &cause); | 	wl = session_new(s, args_get(args, 'n'), cmd, cwd, idx, &cause); | ||||||
| 	if (wl == NULL) { | 	if (wl == NULL) { | ||||||
| 		ctx->error(ctx, "create window failed: %s", cause); | 		ctx->error(ctx, "create window failed: %s", cause); | ||||||
| 		xfree(cause); | 		xfree(cause); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
| 	if (!data->flag_detached) { | 	if (!detached) { | ||||||
| 		session_select(s, wl->idx); | 		session_select(s, wl->idx); | ||||||
| 		server_redraw_session_group(s); | 		server_redraw_session_group(s); | ||||||
| 	} else | 	} else | ||||||
| 		server_status_session_group(s); | 		server_status_session_group(s); | ||||||
|  |  | ||||||
| 	if (data->flag_print) | 	if (args_has(args, 'P')) | ||||||
| 		ctx->print(ctx, "%s:%u", s->name, wl->idx); | 		ctx->print(ctx, "%s:%u", s->name, wl->idx); | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_new_window_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_new_window_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	if (data->name != NULL) |  | ||||||
| 		xfree(data->name); |  | ||||||
| 	if (data->cmd != NULL) |  | ||||||
| 		xfree(data->cmd); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_new_window_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_new_window_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->flag_detached) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -d"); |  | ||||||
| 	if (off < len && data->flag_print) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -P"); |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
| 	if (off < len && data->name != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -n ", data->name); |  | ||||||
| 	if (off < len && data->cmd != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->cmd); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -28,23 +28,22 @@ int	cmd_next_layout_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_next_layout_entry = { | const struct cmd_entry cmd_next_layout_entry = { | ||||||
| 	"next-layout", "nextl", | 	"next-layout", "nextl", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_WINDOW_USAGE, | 	CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_next_layout_exec, | 	cmd_next_layout_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_next_layout_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_next_layout_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	u_int			 layout; | 	u_int		 layout; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	layout = layout_set_next(wl->window); | 	layout = layout_set_next(wl->window); | ||||||
|   | |||||||
| @@ -24,44 +24,39 @@ | |||||||
|  * Move to next window. |  * Move to next window. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_next_window_init(struct cmd *, int); | void	cmd_next_window_key_binding(struct cmd *, int); | ||||||
| int	cmd_next_window_exec(struct cmd *, struct cmd_ctx *); | int	cmd_next_window_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_next_window_entry = { | const struct cmd_entry cmd_next_window_entry = { | ||||||
| 	"next-window", "next", | 	"next-window", "next", | ||||||
|  | 	"at:", 0, 0, | ||||||
| 	"[-a] " CMD_TARGET_SESSION_USAGE, | 	"[-a] " CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "a", | 	0, | ||||||
| 	cmd_next_window_init, | 	cmd_next_window_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_next_window_exec, | 	cmd_next_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_next_window_init(struct cmd *self, int key) | cmd_next_window_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	self->args = args_create(0); | ||||||
|  |  | ||||||
| 	cmd_target_init(self, key); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	if (key == ('n' | KEYC_ESCAPE)) | 	if (key == ('n' | KEYC_ESCAPE)) | ||||||
| 		cmd_set_flag(&data->chflags, 'a'); | 		args_set(self->args, 'a', NULL); | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_next_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_next_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
| 	int			 activity; | 	int		 activity; | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	activity = 0; | 	activity = 0; | ||||||
| 	if (cmd_check_flag(data->chflags, 'a')) | 	if (args_has(self->args, 'a')) | ||||||
| 		activity = 1; | 		activity = 1; | ||||||
|  |  | ||||||
| 	if (session_next(s, activity) == 0) | 	if (session_next(s, activity) == 0) | ||||||
|   | |||||||
| @@ -28,132 +28,73 @@ | |||||||
|  * Paste paste buffer if present. |  * Paste paste buffer if present. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| struct cmd_paste_buffer_data { |  | ||||||
| 	char	*target; |  | ||||||
| 	int	 buffer; |  | ||||||
|  |  | ||||||
| 	int	 flag_delete; |  | ||||||
| 	char	*sepstr; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| void	cmd_paste_buffer_init(struct cmd *, int); |  | ||||||
| int	cmd_paste_buffer_parse(struct cmd *, int, char **, char **); |  | ||||||
| int	cmd_paste_buffer_exec(struct cmd *, struct cmd_ctx *); | int	cmd_paste_buffer_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| void	cmd_paste_buffer_filter( | void	cmd_paste_buffer_filter( | ||||||
| 	    struct window_pane *, const char *, size_t, char *); | 	    struct window_pane *, const char *, size_t, const char *); | ||||||
| void	cmd_paste_buffer_free(struct cmd *); |  | ||||||
| size_t	cmd_paste_buffer_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_paste_buffer_entry = { | const struct cmd_entry cmd_paste_buffer_entry = { | ||||||
| 	"paste-buffer", "pasteb", | 	"paste-buffer", "pasteb", | ||||||
|  | 	"db:rs:t:", 0, 0, | ||||||
| 	"[-dr] [-s separator] [-b buffer-index] [-t target-pane]", | 	"[-dr] [-s separator] [-b buffer-index] [-t target-pane]", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_paste_buffer_init, | 	NULL, | ||||||
| 	cmd_paste_buffer_parse, | 	NULL, | ||||||
| 	cmd_paste_buffer_exec, | 	cmd_paste_buffer_exec | ||||||
| 	cmd_paste_buffer_free, |  | ||||||
| 	cmd_paste_buffer_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_paste_buffer_init(struct cmd *self, unused int arg) |  | ||||||
| { |  | ||||||
| 	struct cmd_paste_buffer_data	*data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->buffer = -1; |  | ||||||
| 	data->flag_delete = 0; |  | ||||||
| 	data->sepstr = xstrdup("\r"); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_paste_buffer_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_paste_buffer_data	*data; |  | ||||||
| 	int			 opt, n; |  | ||||||
| 	const char		*errstr; |  | ||||||
|  |  | ||||||
| 	cmd_paste_buffer_init(self, 0); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "b:ds:t:r")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'b': |  | ||||||
| 			if (data->buffer == -1) { |  | ||||||
| 				n = strtonum(optarg, 0, INT_MAX, &errstr); |  | ||||||
| 				if (errstr != NULL) { |  | ||||||
| 					xasprintf(cause, "buffer %s", errstr); |  | ||||||
| 					goto error; |  | ||||||
| 				} |  | ||||||
| 				data->buffer = n; |  | ||||||
| 			} |  | ||||||
| 			break; |  | ||||||
| 		case 'd': |  | ||||||
| 			data->flag_delete = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 's': |  | ||||||
| 			if (data->sepstr != NULL) |  | ||||||
| 				xfree(data->sepstr); |  | ||||||
| 			data->sepstr = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 'r': |  | ||||||
| 			if (data->sepstr != NULL) |  | ||||||
| 				xfree(data->sepstr); |  | ||||||
| 			data->sepstr = xstrdup("\n"); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| error: |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_paste_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_paste_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_paste_buffer_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct window_pane		*wp; | 	struct window_pane	*wp; | ||||||
| 	struct session			*s; | 	struct session		*s; | ||||||
| 	struct paste_buffer		*pb; | 	struct paste_buffer	*pb; | ||||||
|  | 	const char		*sepstr; | ||||||
|  | 	char			*cause; | ||||||
|  | 	int			 buffer; | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, &s, &wp) == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), &s, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (data->buffer == -1) | 	if (!args_has(args, 'b')) | ||||||
| 		pb = paste_get_top(&global_buffers); | 		buffer = -1; | ||||||
| 	else { | 	else { | ||||||
| 		pb = paste_get_index(&global_buffers, data->buffer); | 		buffer = args_strtonum(args, 'b', 0, INT_MAX, &cause); | ||||||
| 		if (pb == NULL) { | 		if (cause != NULL) { | ||||||
| 			ctx->error(ctx, "no buffer %d", data->buffer); | 			ctx->error(ctx, "buffer %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if (pb != NULL) | 	if (buffer == -1) | ||||||
| 		cmd_paste_buffer_filter(wp, pb->data, pb->size, data->sepstr); | 		pb = paste_get_top(&global_buffers); | ||||||
|  | 	else { | ||||||
|  | 		pb = paste_get_index(&global_buffers, buffer); | ||||||
|  | 		if (pb == NULL) { | ||||||
|  | 			ctx->error(ctx, "no buffer %d", buffer); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if (pb != NULL) { | ||||||
|  | 		sepstr = args_get(args, 's'); | ||||||
|  | 		if (sepstr == NULL) { | ||||||
|  | 			if (args_has(args, 'r')) | ||||||
|  | 				sepstr = "\n"; | ||||||
|  | 			else | ||||||
|  | 				sepstr = "\r"; | ||||||
|  | 		} | ||||||
|  | 		cmd_paste_buffer_filter(wp, pb->data, pb->size, sepstr); | ||||||
|  | 	} | ||||||
|  |  | ||||||
| 	/* Delete the buffer if -d. */ | 	/* Delete the buffer if -d. */ | ||||||
| 	if (data->flag_delete) { | 	if (args_has(args, 'd')) { | ||||||
| 		if (data->buffer == -1) | 		if (buffer == -1) | ||||||
| 			paste_free_top(&global_buffers); | 			paste_free_top(&global_buffers); | ||||||
| 		else | 		else | ||||||
| 			paste_free_index(&global_buffers, data->buffer); | 			paste_free_index(&global_buffers, buffer); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
| @@ -162,7 +103,7 @@ cmd_paste_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| /* Add bytes to a buffer and filter '\n' according to separator. */ | /* Add bytes to a buffer and filter '\n' according to separator. */ | ||||||
| void | void | ||||||
| cmd_paste_buffer_filter( | cmd_paste_buffer_filter( | ||||||
|     struct window_pane *wp, const char *data, size_t size, char *sep) |     struct window_pane *wp, const char *data, size_t size, const char *sep) | ||||||
| { | { | ||||||
| 	const char	*end = data + size; | 	const char	*end = data + size; | ||||||
| 	const char	*lf; | 	const char	*lf; | ||||||
| @@ -179,46 +120,3 @@ cmd_paste_buffer_filter( | |||||||
| 	if (end != data) | 	if (end != data) | ||||||
| 		bufferevent_write(wp->event, data, end - data); | 		bufferevent_write(wp->event, data, end - data); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_paste_buffer_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_paste_buffer_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	if (data->sepstr != NULL) |  | ||||||
| 		xfree(data->sepstr); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_paste_buffer_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_paste_buffer_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
| 	char                             tmp[BUFSIZ]; |  | ||||||
| 	int				 r_flag; |  | ||||||
|  |  | ||||||
| 	r_flag = 0; |  | ||||||
| 	if (data->sepstr != NULL) |  | ||||||
| 		r_flag = (data->sepstr[0] == '\n' && data->sepstr[1] == '\0'); |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->flag_delete) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -d"); |  | ||||||
| 	if (off < len && r_flag) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -r"); |  | ||||||
| 	if (off < len && data->buffer != -1) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -b %d", data->buffer); |  | ||||||
| 	if (off < len && data->sepstr != NULL && !r_flag) { |  | ||||||
| 		strnvis( |  | ||||||
| 		    tmp, data->sepstr, sizeof tmp, VIS_OCTAL|VIS_TAB|VIS_NL); |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -s ", tmp); |  | ||||||
| 	} |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -38,19 +38,18 @@ void	cmd_pipe_pane_error_callback(struct bufferevent *, short, void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_pipe_pane_entry = { | const struct cmd_entry cmd_pipe_pane_entry = { | ||||||
| 	"pipe-pane", "pipep", | 	"pipe-pane", "pipep", | ||||||
|  | 	"ot:", 0, 1, | ||||||
| 	CMD_TARGET_PANE_USAGE "[-o] [command]", | 	CMD_TARGET_PANE_USAGE "[-o] [command]", | ||||||
| 	CMD_ARG01, "o", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_pipe_pane_exec, | 	cmd_pipe_pane_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_pipe_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_pipe_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct client		*c; | 	struct client		*c; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
| 	char			*command; | 	char			*command; | ||||||
| @@ -59,7 +58,7 @@ cmd_pipe_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	if ((c = cmd_find_client(ctx, NULL)) == NULL) | 	if ((c = cmd_find_client(ctx, NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, NULL, &wp) == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	/* Destroy the old pipe. */ | 	/* Destroy the old pipe. */ | ||||||
| @@ -71,7 +70,7 @@ cmd_pipe_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	/* If no pipe command, that is enough. */ | 	/* If no pipe command, that is enough. */ | ||||||
| 	if (data->arg == NULL || *data->arg == '\0') | 	if (args->argc == 0 || *args->argv[0] == '\0') | ||||||
| 		return (0); | 		return (0); | ||||||
|  |  | ||||||
| 	/* | 	/* | ||||||
| @@ -80,7 +79,7 @@ cmd_pipe_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	 * | 	 * | ||||||
| 	 *	bind ^p pipep -o 'cat >>~/output' | 	 *	bind ^p pipep -o 'cat >>~/output' | ||||||
| 	 */ | 	 */ | ||||||
| 	if (cmd_check_flag(data->chflags, 'o') && old_fd != -1) | 	if (args_has(self->args, 'o') && old_fd != -1) | ||||||
| 		return (0); | 		return (0); | ||||||
|  |  | ||||||
| 	/* Open the new pipe. */ | 	/* Open the new pipe. */ | ||||||
| @@ -114,7 +113,7 @@ cmd_pipe_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 		closefrom(STDERR_FILENO + 1); | 		closefrom(STDERR_FILENO + 1); | ||||||
|  |  | ||||||
| 		command = status_replace(c, NULL, data->arg, time(NULL), 0); | 		command = status_replace(c, NULL, args->argv[0], time(NULL), 0); | ||||||
| 		execl(_PATH_BSHELL, "sh", "-c", command, (char *) NULL); | 		execl(_PATH_BSHELL, "sh", "-c", command, (char *) NULL); | ||||||
| 		_exit(1); | 		_exit(1); | ||||||
| 	default: | 	default: | ||||||
|   | |||||||
| @@ -28,23 +28,22 @@ int	cmd_previous_layout_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_previous_layout_entry = { | const struct cmd_entry cmd_previous_layout_entry = { | ||||||
| 	"previous-layout", "prevl", | 	"previous-layout", "prevl", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_WINDOW_USAGE, | 	CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_previous_layout_exec, | 	cmd_previous_layout_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_previous_layout_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_previous_layout_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	u_int			 layout; | 	u_int		 layout; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	layout = layout_set_previous(wl->window); | 	layout = layout_set_previous(wl->window); | ||||||
|   | |||||||
| @@ -24,44 +24,39 @@ | |||||||
|  * Move to previous window. |  * Move to previous window. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_previous_window_init(struct cmd *, int); | void	cmd_previous_window_key_binding(struct cmd *, int); | ||||||
| int	cmd_previous_window_exec(struct cmd *, struct cmd_ctx *); | int	cmd_previous_window_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_previous_window_entry = { | const struct cmd_entry cmd_previous_window_entry = { | ||||||
| 	"previous-window", "prev", | 	"previous-window", "prev", | ||||||
|  | 	"at:", 0, 0, | ||||||
| 	"[-a] " CMD_TARGET_SESSION_USAGE, | 	"[-a] " CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "a", | 	0, | ||||||
| 	cmd_previous_window_init, | 	cmd_previous_window_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_previous_window_exec, | 	cmd_previous_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_previous_window_init(struct cmd *self, int key) | cmd_previous_window_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	self->args = args_create(0); | ||||||
|  |  | ||||||
| 	cmd_target_init(self, key); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	if (key == ('p' | KEYC_ESCAPE)) | 	if (key == ('p' | KEYC_ESCAPE)) | ||||||
| 		cmd_set_flag(&data->chflags, 'a'); | 		args_set(self->args, 'a', NULL); | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_previous_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_previous_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
| 	int			 activity; | 	int		 activity; | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	activity = 0; | 	activity = 0; | ||||||
| 	if (cmd_check_flag(data->chflags, 'a')) | 	if (args_has(self->args, 'a')) | ||||||
| 		activity = 1; | 		activity = 1; | ||||||
|  |  | ||||||
| 	if (session_previous(s, activity) == 0) | 	if (session_previous(s, activity) == 0) | ||||||
|   | |||||||
| @@ -28,22 +28,21 @@ int	cmd_refresh_client_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_refresh_client_entry = { | const struct cmd_entry cmd_refresh_client_entry = { | ||||||
| 	"refresh-client", "refresh", | 	"refresh-client", "refresh", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_CLIENT_USAGE, | 	CMD_TARGET_CLIENT_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_refresh_client_exec, | 	cmd_refresh_client_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_refresh_client_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_refresh_client_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct client		*c; | 	struct client	*c; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	server_redraw_client(c); | 	server_redraw_client(c); | ||||||
|   | |||||||
| @@ -30,32 +30,33 @@ int	cmd_rename_session_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_rename_session_entry = { | const struct cmd_entry cmd_rename_session_entry = { | ||||||
| 	"rename-session", "rename", | 	"rename-session", "rename", | ||||||
|  | 	"t:", 1, 1, | ||||||
| 	CMD_TARGET_SESSION_USAGE " new-name", | 	CMD_TARGET_SESSION_USAGE " new-name", | ||||||
| 	CMD_ARG1, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_rename_session_exec, | 	cmd_rename_session_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_rename_session_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_rename_session_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
|  | 	const char	*newname; | ||||||
|  |  | ||||||
| 	if (data->arg != NULL && session_find(data->arg) != NULL) { | 	newname = args->argv[0]; | ||||||
| 		ctx->error(ctx, "duplicate session: %s", data->arg); | 	if (session_find(newname) != NULL) { | ||||||
|  | 		ctx->error(ctx, "duplicate session: %s", newname); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, data->target)) == NULL) | 	if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	RB_REMOVE(sessions, &sessions, s); | 	RB_REMOVE(sessions, &sessions, s); | ||||||
| 	xfree(s->name); | 	xfree(s->name); | ||||||
| 	s->name = xstrdup(data->arg); | 	s->name = xstrdup(newname); | ||||||
| 	RB_INSERT(sessions, &sessions, s); | 	RB_INSERT(sessions, &sessions, s); | ||||||
|  |  | ||||||
| 	server_status_session(s); | 	server_status_session(s); | ||||||
|   | |||||||
| @@ -30,27 +30,26 @@ int	cmd_rename_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_rename_window_entry = { | const struct cmd_entry cmd_rename_window_entry = { | ||||||
| 	"rename-window", "renamew", | 	"rename-window", "renamew", | ||||||
|  | 	"t:", 1, 1, | ||||||
| 	CMD_TARGET_WINDOW_USAGE " new-name", | 	CMD_TARGET_WINDOW_USAGE " new-name", | ||||||
| 	CMD_ARG1, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_rename_window_exec, | 	cmd_rename_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_rename_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_rename_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, &s)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), &s)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	xfree(wl->window->name); | 	xfree(wl->window->name); | ||||||
| 	wl->window->name = xstrdup(data->arg); | 	wl->window->name = xstrdup(args->argv[0]); | ||||||
| 	options_set_number(&wl->window->options, "automatic-rename", 0); | 	options_set_number(&wl->window->options, "automatic-rename", 0); | ||||||
|  |  | ||||||
| 	server_status_window(wl->window); | 	server_status_window(wl->window); | ||||||
|   | |||||||
| @@ -26,84 +26,90 @@ | |||||||
|  * Increase or decrease pane size. |  * Increase or decrease pane size. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_resize_pane_init(struct cmd *, int); | void	cmd_resize_pane_key_binding(struct cmd *, int); | ||||||
| int	cmd_resize_pane_exec(struct cmd *, struct cmd_ctx *); | int	cmd_resize_pane_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_resize_pane_entry = { | const struct cmd_entry cmd_resize_pane_entry = { | ||||||
| 	"resize-pane", "resizep", | 	"resize-pane", "resizep", | ||||||
|  | 	"DLRt:U", 0, 1, | ||||||
| 	"[-DLRU] " CMD_TARGET_PANE_USAGE " [adjustment]", | 	"[-DLRU] " CMD_TARGET_PANE_USAGE " [adjustment]", | ||||||
| 	CMD_ARG01, "DLRU", | 	0, | ||||||
| 	cmd_resize_pane_init, | 	cmd_resize_pane_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_resize_pane_exec, | 	cmd_resize_pane_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_resize_pane_init(struct cmd *self, int key) | cmd_resize_pane_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	switch (key) { | ||||||
|  | 	case KEYC_UP | KEYC_CTRL: | ||||||
| 	cmd_target_init(self, key); | 		self->args = args_create(0); | ||||||
| 	data = self->data; | 		args_set(self->args, 'U', NULL); | ||||||
|  | 		break; | ||||||
| 	if (key == (KEYC_UP | KEYC_CTRL)) | 	case KEYC_DOWN | KEYC_CTRL: | ||||||
| 		cmd_set_flag(&data->chflags, 'U'); | 		self->args = args_create(0); | ||||||
| 	if (key == (KEYC_DOWN | KEYC_CTRL)) | 		args_set(self->args, 'D', NULL); | ||||||
| 		cmd_set_flag(&data->chflags, 'D'); | 		break; | ||||||
| 	if (key == (KEYC_LEFT | KEYC_CTRL)) | 	case KEYC_LEFT | KEYC_CTRL: | ||||||
| 		cmd_set_flag(&data->chflags, 'L'); | 		self->args = args_create(0); | ||||||
| 	if (key == (KEYC_RIGHT | KEYC_CTRL)) | 		args_set(self->args, 'L', NULL); | ||||||
| 		cmd_set_flag(&data->chflags, 'R'); | 		break; | ||||||
|  | 	case KEYC_RIGHT | KEYC_CTRL: | ||||||
| 	if (key == (KEYC_UP | KEYC_ESCAPE)) { | 		self->args = args_create(0); | ||||||
| 		cmd_set_flag(&data->chflags, 'U'); | 		args_set(self->args, 'R', NULL); | ||||||
| 		data->arg = xstrdup("5"); | 		break; | ||||||
| 	} | 	case KEYC_UP | KEYC_ESCAPE: | ||||||
| 	if (key == (KEYC_DOWN | KEYC_ESCAPE)) { | 		self->args = args_create(1, "5"); | ||||||
| 		cmd_set_flag(&data->chflags, 'D'); | 		args_set(self->args, 'U', NULL); | ||||||
| 		data->arg = xstrdup("5"); | 		break; | ||||||
| 	} | 	case KEYC_DOWN | KEYC_ESCAPE: | ||||||
| 	if (key == (KEYC_LEFT | KEYC_ESCAPE)) { | 		self->args = args_create(1, "5"); | ||||||
| 		cmd_set_flag(&data->chflags, 'L'); | 		args_set(self->args, 'D', NULL); | ||||||
| 		data->arg = xstrdup("5"); | 		break; | ||||||
| 	} | 	case KEYC_LEFT | KEYC_ESCAPE: | ||||||
| 	if (key == (KEYC_RIGHT | KEYC_ESCAPE)) { | 		self->args = args_create(1, "5"); | ||||||
| 		cmd_set_flag(&data->chflags, 'R'); | 		args_set(self->args, 'L', NULL); | ||||||
| 		data->arg = xstrdup("5"); | 		break; | ||||||
|  | 	case KEYC_RIGHT | KEYC_ESCAPE: | ||||||
|  | 		self->args = args_create(1, "5"); | ||||||
|  | 		args_set(self->args, 'R', NULL); | ||||||
|  | 		break; | ||||||
|  | 	default: | ||||||
|  | 		self->args = args_create(0); | ||||||
|  | 		break; | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_resize_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_resize_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	const char	       	*errstr; | 	const char	       	*errstr; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
| 	u_int			 adjust; | 	u_int			 adjust; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_pane(ctx, data->target, NULL, &wp)) == NULL) | 	if ((wl = cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (data->arg == NULL) | 	if (args->argc == 0) | ||||||
| 		adjust = 1; | 		adjust = 1; | ||||||
| 	else { | 	else { | ||||||
| 		adjust = strtonum(data->arg, 1, INT_MAX, &errstr); | 		adjust = strtonum(args->argv[0], 1, INT_MAX, &errstr); | ||||||
| 		if (errstr != NULL) { | 		if (errstr != NULL) { | ||||||
| 			ctx->error(ctx, "adjustment %s: %s", errstr, data->arg); | 			ctx->error(ctx, "adjustment %s", errstr); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'L')) | 	if (args_has(self->args, 'L')) | ||||||
| 		layout_resize_pane(wp, LAYOUT_LEFTRIGHT, -adjust); | 		layout_resize_pane(wp, LAYOUT_LEFTRIGHT, -adjust); | ||||||
| 	else if (cmd_check_flag(data->chflags, 'R')) | 	else if (args_has(self->args, 'R')) | ||||||
| 		layout_resize_pane(wp, LAYOUT_LEFTRIGHT, adjust); | 		layout_resize_pane(wp, LAYOUT_LEFTRIGHT, adjust); | ||||||
| 	else if (cmd_check_flag(data->chflags, 'U')) | 	else if (args_has(self->args, 'U')) | ||||||
| 		layout_resize_pane(wp, LAYOUT_TOPBOTTOM, -adjust); | 		layout_resize_pane(wp, LAYOUT_TOPBOTTOM, -adjust); | ||||||
| 	else if (cmd_check_flag(data->chflags, 'D')) | 	else if (args_has(self->args, 'D')) | ||||||
| 		layout_resize_pane(wp, LAYOUT_TOPBOTTOM, adjust); | 		layout_resize_pane(wp, LAYOUT_TOPBOTTOM, adjust); | ||||||
| 	server_redraw_window(wl->window); | 	server_redraw_window(wl->window); | ||||||
|  |  | ||||||
|   | |||||||
| @@ -30,31 +30,31 @@ int	cmd_respawn_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_respawn_window_entry = { | const struct cmd_entry cmd_respawn_window_entry = { | ||||||
| 	"respawn-window", "respawnw", | 	"respawn-window", "respawnw", | ||||||
|  | 	"kt:", 0, 1, | ||||||
| 	"[-k] " CMD_TARGET_WINDOW_USAGE " [command]", | 	"[-k] " CMD_TARGET_WINDOW_USAGE " [command]", | ||||||
| 	CMD_ARG01, "k", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_respawn_window_exec, | 	cmd_respawn_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_respawn_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_respawn_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	struct window		*w; | 	struct window		*w; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
| 	struct session		*s; | 	struct session		*s; | ||||||
| 	struct environ		 env; | 	struct environ		 env; | ||||||
|  | 	const char		*cmd; | ||||||
| 	char		 	*cause; | 	char		 	*cause; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, &s)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), &s)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	w = wl->window; | 	w = wl->window; | ||||||
|  |  | ||||||
| 	if (!cmd_check_flag(data->chflags, 'k')) { | 	if (!args_has(self->args, 'k')) { | ||||||
| 		TAILQ_FOREACH(wp, &w->panes, entry) { | 		TAILQ_FOREACH(wp, &w->panes, entry) { | ||||||
| 			if (wp->fd == -1) | 			if (wp->fd == -1) | ||||||
| 				continue; | 				continue; | ||||||
| @@ -75,8 +75,11 @@ cmd_respawn_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	window_destroy_panes(w); | 	window_destroy_panes(w); | ||||||
| 	TAILQ_INSERT_HEAD(&w->panes, wp, entry); | 	TAILQ_INSERT_HEAD(&w->panes, wp, entry); | ||||||
| 	window_pane_resize(wp, w->sx, w->sy); | 	window_pane_resize(wp, w->sx, w->sy); | ||||||
| 	if (window_pane_spawn( | 	if (args->argc != 0) | ||||||
| 	    wp, data->arg, NULL, NULL, &env, s->tio, &cause) != 0) { | 		cmd = args->argv[0]; | ||||||
|  | 	else | ||||||
|  | 		cmd = NULL; | ||||||
|  | 	if (window_pane_spawn(wp, cmd, NULL, NULL, &env, s->tio, &cause) != 0) { | ||||||
| 		ctx->error(ctx, "respawn window failed: %s", cause); | 		ctx->error(ctx, "respawn window failed: %s", cause); | ||||||
| 		xfree(cause); | 		xfree(cause); | ||||||
| 		environ_free(&env); | 		environ_free(&env); | ||||||
|   | |||||||
| @@ -24,47 +24,42 @@ | |||||||
|  * Rotate the panes in a window. |  * Rotate the panes in a window. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_rotate_window_init(struct cmd *, int); | void	cmd_rotate_window_key_binding(struct cmd *, int); | ||||||
| int	cmd_rotate_window_exec(struct cmd *, struct cmd_ctx *); | int	cmd_rotate_window_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_rotate_window_entry = { | const struct cmd_entry cmd_rotate_window_entry = { | ||||||
| 	"rotate-window", "rotatew", | 	"rotate-window", "rotatew", | ||||||
|  | 	"Dt:U", 0, 0, | ||||||
| 	"[-DU] " CMD_TARGET_WINDOW_USAGE, | 	"[-DU] " CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "DU", | 	0, | ||||||
| 	cmd_rotate_window_init, | 	cmd_rotate_window_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_rotate_window_exec, | 	cmd_rotate_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_rotate_window_init(struct cmd *self, int key) | cmd_rotate_window_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	self->args = args_create(0); | ||||||
|  |  | ||||||
| 	cmd_target_init(self, key); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	if (key == ('o' | KEYC_ESCAPE)) | 	if (key == ('o' | KEYC_ESCAPE)) | ||||||
| 		cmd_set_flag(&data->chflags, 'D'); | 		args_set(self->args, 'D', NULL); | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_rotate_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_rotate_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	struct window		*w; | 	struct window		*w; | ||||||
| 	struct window_pane	*wp, *wp2; | 	struct window_pane	*wp, *wp2; | ||||||
| 	struct layout_cell	*lc; | 	struct layout_cell	*lc; | ||||||
| 	u_int			 sx, sy, xoff, yoff; | 	u_int			 sx, sy, xoff, yoff; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	w = wl->window; | 	w = wl->window; | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'D')) { | 	if (args_has(self->args, 'D')) { | ||||||
| 		wp = TAILQ_LAST(&w->panes, window_panes); | 		wp = TAILQ_LAST(&w->panes, window_panes); | ||||||
| 		TAILQ_REMOVE(&w->panes, wp, entry); | 		TAILQ_REMOVE(&w->panes, wp, entry); | ||||||
| 		TAILQ_INSERT_HEAD(&w->panes, wp, entry); | 		TAILQ_INSERT_HEAD(&w->panes, wp, entry); | ||||||
|   | |||||||
| @@ -35,13 +35,12 @@ void	cmd_run_shell_free(void *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_run_shell_entry = { | const struct cmd_entry cmd_run_shell_entry = { | ||||||
| 	"run-shell", "run", | 	"run-shell", "run", | ||||||
|  | 	"", 1, 1, | ||||||
| 	"command", | 	"command", | ||||||
| 	CMD_ARG1, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_run_shell_exec, | 	cmd_run_shell_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_run_shell_data { | struct cmd_run_shell_data { | ||||||
| @@ -52,12 +51,12 @@ struct cmd_run_shell_data { | |||||||
| int | int | ||||||
| cmd_run_shell_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_run_shell_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args			*args = self->args; | ||||||
| 	struct cmd_run_shell_data	*cdata; | 	struct cmd_run_shell_data	*cdata; | ||||||
| 	struct job			*job; | 	struct job			*job; | ||||||
|  |  | ||||||
| 	cdata = xmalloc(sizeof *cdata); | 	cdata = xmalloc(sizeof *cdata); | ||||||
| 	cdata->cmd = xstrdup(data->arg); | 	cdata->cmd = xstrdup(args->argv[0]); | ||||||
| 	memcpy(&cdata->ctx, ctx, sizeof cdata->ctx); | 	memcpy(&cdata->ctx, ctx, sizeof cdata->ctx); | ||||||
|  |  | ||||||
| 	if (ctx->cmdclient != NULL) | 	if (ctx->cmdclient != NULL) | ||||||
| @@ -66,7 +65,7 @@ cmd_run_shell_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 		ctx->curclient->references++; | 		ctx->curclient->references++; | ||||||
|  |  | ||||||
| 	job = job_add(NULL, 0, NULL, | 	job = job_add(NULL, 0, NULL, | ||||||
| 	    data->arg, cmd_run_shell_callback, cmd_run_shell_free, cdata); | 	    args->argv[0], cmd_run_shell_callback, cmd_run_shell_free, cdata); | ||||||
| 	job_run(job); | 	job_run(job); | ||||||
|  |  | ||||||
| 	return (1);	/* don't let client exit */ | 	return (1);	/* don't let client exit */ | ||||||
|   | |||||||
| @@ -32,56 +32,66 @@ int	cmd_save_buffer_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_save_buffer_entry = { | const struct cmd_entry cmd_save_buffer_entry = { | ||||||
| 	"save-buffer", "saveb", | 	"save-buffer", "saveb", | ||||||
| 	"[-a] " CMD_BUFFER_USAGE " path", | 	"ab:", 1, 1, | ||||||
| 	CMD_ARG1, "a", | 	"[-a] " CMD_BUFFER_USAGE, | ||||||
| 	cmd_buffer_init, | 	0, | ||||||
| 	cmd_buffer_parse, | 	NULL, | ||||||
| 	cmd_save_buffer_exec, | 	NULL, | ||||||
| 	cmd_buffer_free, | 	cmd_save_buffer_exec | ||||||
| 	cmd_buffer_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_save_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_save_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_buffer_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
|  | 	struct client		*c = ctx->cmdclient; | ||||||
| 	struct paste_buffer	*pb; | 	struct paste_buffer	*pb; | ||||||
|  | 	const char		*path; | ||||||
|  | 	char			*cause; | ||||||
|  | 	int			 buffer; | ||||||
| 	mode_t			 mask; | 	mode_t			 mask; | ||||||
| 	FILE			*f; | 	FILE			*f; | ||||||
|  |  | ||||||
| 	if (data->buffer == -1) { | 	if (!args_has(args, 'b')) { | ||||||
| 		if ((pb = paste_get_top(&global_buffers)) == NULL) { | 		if ((pb = paste_get_top(&global_buffers)) == NULL) { | ||||||
| 			ctx->error(ctx, "no buffers"); | 			ctx->error(ctx, "no buffers"); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} else { | 	} else { | ||||||
| 		pb = paste_get_index(&global_buffers, data->buffer); | 		buffer = args_strtonum(args, 'b', 0, INT_MAX, &cause); | ||||||
|  | 		if (cause != NULL) { | ||||||
|  | 			ctx->error(ctx, "buffer %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		pb = paste_get_index(&global_buffers, buffer); | ||||||
| 		if (pb == NULL) { | 		if (pb == NULL) { | ||||||
| 			ctx->error(ctx, "no buffer %d", data->buffer); | 			ctx->error(ctx, "no buffer %d", buffer); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if (strcmp(data->arg, "-") == 0) { | 	path = args->argv[0]; | ||||||
| 		if (ctx->cmdclient == NULL) { | 	if (strcmp(path, "-") == 0) { | ||||||
| 			ctx->error(ctx, "%s: can't write to stdout", data->arg); | 		if (c == NULL) { | ||||||
|  | 			ctx->error(ctx, "%s: can't write to stdout", path); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		bufferevent_write( | 		bufferevent_write(c->stdout_event, pb->data, pb->size); | ||||||
| 		    ctx->cmdclient->stdout_event, pb->data, pb->size); |  | ||||||
| 	} else { | 	} else { | ||||||
| 		mask = umask(S_IRWXG | S_IRWXO); | 		mask = umask(S_IRWXG | S_IRWXO); | ||||||
| 		if (cmd_check_flag(data->chflags, 'a')) | 		if (args_has(self->args, 'a')) | ||||||
| 			f = fopen(data->arg, "ab"); | 			f = fopen(path, "ab"); | ||||||
| 		else | 		else | ||||||
| 			f = fopen(data->arg, "wb"); | 			f = fopen(path, "wb"); | ||||||
| 		umask(mask); | 		umask(mask); | ||||||
| 		if (f == NULL) { | 		if (f == NULL) { | ||||||
| 			ctx->error(ctx, "%s: %s", data->arg, strerror(errno)); | 			ctx->error(ctx, "%s: %s", path, strerror(errno)); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		if (fwrite(pb->data, 1, pb->size, f) != pb->size) { | 		if (fwrite(pb->data, 1, pb->size, f) != pb->size) { | ||||||
| 			ctx->error(ctx, "%s: fwrite error", data->arg); | 			ctx->error(ctx, "%s: fwrite error", path); | ||||||
| 			fclose(f); | 			fclose(f); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
|   | |||||||
| @@ -24,43 +24,40 @@ | |||||||
|  * Switch window to selected layout. |  * Switch window to selected layout. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_select_layout_init(struct cmd *, int); | void	cmd_select_layout_key_binding(struct cmd *, int); | ||||||
| int	cmd_select_layout_exec(struct cmd *, struct cmd_ctx *); | int	cmd_select_layout_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_select_layout_entry = { | const struct cmd_entry cmd_select_layout_entry = { | ||||||
| 	"select-layout", "selectl", | 	"select-layout", "selectl", | ||||||
|  | 	"t:", 0, 1, | ||||||
| 	CMD_TARGET_WINDOW_USAGE " [layout-name]", | 	CMD_TARGET_WINDOW_USAGE " [layout-name]", | ||||||
| 	CMD_ARG01, "", | 	0, | ||||||
| 	cmd_select_layout_init, | 	cmd_select_layout_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_select_layout_exec, | 	cmd_select_layout_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_select_layout_init(struct cmd *self, int key) | cmd_select_layout_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; |  | ||||||
|  |  | ||||||
| 	cmd_target_init(self, key); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	switch (key) { | 	switch (key) { | ||||||
| 	case ('1' | KEYC_ESCAPE): | 	case '1' | KEYC_ESCAPE: | ||||||
| 		data->arg = xstrdup("even-horizontal"); | 		self->args = args_create(1, "even-horizontal"); | ||||||
| 		break; | 		break; | ||||||
| 	case ('2' | KEYC_ESCAPE): | 	case '2' | KEYC_ESCAPE: | ||||||
| 		data->arg = xstrdup("even-vertical"); | 		self->args = args_create(1, "even-vertical"); | ||||||
| 		break; | 		break; | ||||||
| 	case ('3' | KEYC_ESCAPE): | 	case '3' | KEYC_ESCAPE: | ||||||
| 		data->arg = xstrdup("main-horizontal"); | 		self->args = args_create(1, "main-horizontal"); | ||||||
| 		break; | 		break; | ||||||
| 	case ('4' | KEYC_ESCAPE): | 	case '4' | KEYC_ESCAPE: | ||||||
| 		data->arg = xstrdup("main-vertical"); | 		self->args = args_create(1, "main-vertical"); | ||||||
| 		break; | 		break; | ||||||
| 	case ('5' | KEYC_ESCAPE): | 	case '5' | KEYC_ESCAPE: | ||||||
| 		data->arg = xstrdup("tiled"); | 		self->args = args_create(1, "tiled"); | ||||||
|  | 		break; | ||||||
|  | 	default: | ||||||
|  | 		self->args = args_create(0); | ||||||
| 		break; | 		break; | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
| @@ -68,26 +65,32 @@ cmd_select_layout_init(struct cmd *self, int key) | |||||||
| int | int | ||||||
| cmd_select_layout_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_select_layout_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	int			 layout; | 	const char	*layoutname; | ||||||
|  | 	int		 layout; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, NULL)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (data->arg == NULL) { | 	if (args->argc == 0) | ||||||
| 		layout = wl->window->lastlayout; | 		layout = wl->window->lastlayout; | ||||||
| 		if (layout == -1) | 	else | ||||||
| 			return (0); | 		layout = layout_set_lookup(args->argv[0]); | ||||||
| 	} else if ((layout = layout_set_lookup(data->arg)) != -1) { | 	if (layout != -1) { | ||||||
| 		layout = layout_set_select(wl->window, layout); | 		layout = layout_set_select(wl->window, layout); | ||||||
| 		ctx->info(ctx, "arranging in: %s", layout_set_name(layout)); | 		ctx->info(ctx, "arranging in: %s", layout_set_name(layout)); | ||||||
| 	} else { | 		return (0); | ||||||
| 		if (layout_parse(wl->window, data->arg) == -1) { | 	} | ||||||
| 			ctx->error(ctx, "can't set layout: %s", data->arg); |  | ||||||
|  | 	if (args->argc != 0) { | ||||||
|  | 		layoutname = args->argv[0]; | ||||||
|  | 		if (layout_parse(wl->window, layoutname) == -1) { | ||||||
|  | 			ctx->error(ctx, "can't set layout: %s", layoutname); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		ctx->info(ctx, "arranging in: %s", data->arg); | 		ctx->info(ctx, "arranging in: %s", layoutname); | ||||||
|  | 		return (0); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
|   | |||||||
| @@ -24,62 +24,57 @@ | |||||||
|  * Select pane. |  * Select pane. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_select_pane_init(struct cmd *, int); | void	cmd_select_pane_key_binding(struct cmd *, int); | ||||||
| int	cmd_select_pane_exec(struct cmd *, struct cmd_ctx *); | int	cmd_select_pane_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_select_pane_entry = { | const struct cmd_entry cmd_select_pane_entry = { | ||||||
| 	"select-pane", "selectp", | 	"select-pane", "selectp", | ||||||
|  | 	"DLRt:U", 0, 0, | ||||||
| 	"[-DLRU] " CMD_TARGET_PANE_USAGE, | 	"[-DLRU] " CMD_TARGET_PANE_USAGE, | ||||||
| 	0, "DLRU", | 	0, | ||||||
| 	cmd_select_pane_init, | 	cmd_select_pane_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_select_pane_exec, | 	cmd_select_pane_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_select_pane_init(struct cmd *self, int key) | cmd_select_pane_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	self->args = args_create(0); | ||||||
|  |  | ||||||
| 	cmd_target_init(self, key); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	if (key == KEYC_UP) | 	if (key == KEYC_UP) | ||||||
| 		cmd_set_flag(&data->chflags, 'U'); | 		args_set(self->args, 'U', NULL); | ||||||
| 	if (key == KEYC_DOWN) | 	if (key == KEYC_DOWN) | ||||||
| 		cmd_set_flag(&data->chflags, 'D'); | 		args_set(self->args, 'D', NULL); | ||||||
| 	if (key == KEYC_LEFT) | 	if (key == KEYC_LEFT) | ||||||
| 		cmd_set_flag(&data->chflags, 'L'); | 		args_set(self->args, 'L', NULL); | ||||||
| 	if (key == KEYC_RIGHT) | 	if (key == KEYC_RIGHT) | ||||||
| 		cmd_set_flag(&data->chflags, 'R'); | 		args_set(self->args, 'R', NULL); | ||||||
| 	if (key == 'o') | 	if (key == 'o') | ||||||
| 		data->target = xstrdup(":.+"); | 		args_set(self->args, 't', ":.+"); | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_select_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_select_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_pane(ctx, data->target, NULL, &wp)) == NULL) | 	if ((wl = cmd_find_pane(ctx, args_get(args, 't'), NULL, &wp)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (!window_pane_visible(wp)) { | 	if (!window_pane_visible(wp)) { | ||||||
| 		ctx->error(ctx, "pane not visible: %s", data->target); | 		ctx->error(ctx, "pane not visible"); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'L')) | 	if (args_has(self->args, 'L')) | ||||||
| 		wp = window_pane_find_left(wp); | 		wp = window_pane_find_left(wp); | ||||||
| 	else if (cmd_check_flag(data->chflags, 'R')) | 	else if (args_has(self->args, 'R')) | ||||||
| 		wp = window_pane_find_right(wp); | 		wp = window_pane_find_right(wp); | ||||||
| 	else if (cmd_check_flag(data->chflags, 'U')) | 	else if (args_has(self->args, 'U')) | ||||||
| 		wp = window_pane_find_up(wp); | 		wp = window_pane_find_up(wp); | ||||||
| 	else if (cmd_check_flag(data->chflags, 'D')) | 	else if (args_has(self->args, 'D')) | ||||||
| 		wp = window_pane_find_down(wp); | 		wp = window_pane_find_down(wp); | ||||||
| 	if (wp == NULL) { | 	if (wp == NULL) { | ||||||
| 		ctx->error(ctx, "pane not found"); | 		ctx->error(ctx, "pane not found"); | ||||||
|   | |||||||
| @@ -26,39 +26,38 @@ | |||||||
|  * Select window by index. |  * Select window by index. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_select_window_init(struct cmd *, int); | void	cmd_select_window_key_binding(struct cmd *, int); | ||||||
| int	cmd_select_window_exec(struct cmd *, struct cmd_ctx *); | int	cmd_select_window_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_select_window_entry = { | const struct cmd_entry cmd_select_window_entry = { | ||||||
| 	"select-window", "selectw", | 	"select-window", "selectw", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_WINDOW_USAGE, | 	CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_select_window_init, | 	cmd_select_window_key_binding, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_select_window_exec, | 	cmd_select_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_select_window_init(struct cmd *self, int key) | cmd_select_window_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	char	tmp[16]; | ||||||
|  |  | ||||||
| 	cmd_target_init(self, key); | 	xsnprintf(tmp, sizeof tmp, ":%d", key - '0'); | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	xasprintf(&data->target, ":%d", key - '0'); | 	self->args = args_create(0); | ||||||
|  | 	args_set(self->args, 't', tmp); | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_select_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_select_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink	*wl; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, &s)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), &s)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (session_select(s, wl->idx) == 0) | 	if (session_select(s, wl->idx) == 0) | ||||||
|   | |||||||
							
								
								
									
										126
									
								
								cmd-send-keys.c
									
									
									
									
									
								
							
							
						
						
									
										126
									
								
								cmd-send-keys.c
									
									
									
									
									
								
							| @@ -26,128 +26,40 @@ | |||||||
|  * Send keys to client. |  * Send keys to client. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_send_keys_parse(struct cmd *, int, char **, char **); |  | ||||||
| int	cmd_send_keys_exec(struct cmd *, struct cmd_ctx *); | int	cmd_send_keys_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_send_keys_free(struct cmd *); |  | ||||||
| size_t	cmd_send_keys_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_send_keys_data { |  | ||||||
| 	char	*target; |  | ||||||
| 	u_int	 nkeys; |  | ||||||
| 	int	*keys; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_send_keys_entry = { | const struct cmd_entry cmd_send_keys_entry = { | ||||||
| 	"send-keys", "send", | 	"send-keys", "send", | ||||||
|  | 	"t:", 0, -1, | ||||||
| 	"[-t target-pane] key ...", | 	"[-t target-pane] key ...", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_send_keys_parse, | 	NULL, | ||||||
| 	cmd_send_keys_exec, | 	cmd_send_keys_exec | ||||||
| 	cmd_send_keys_free, |  | ||||||
| 	cmd_send_keys_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_send_keys_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_send_keys_data	*data; |  | ||||||
| 	int				 opt, key; |  | ||||||
| 	char				*s; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->nkeys = 0; |  | ||||||
| 	data->keys = NULL; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "t:")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc == 0) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	while (argc-- != 0) { |  | ||||||
| 		if ((key = key_string_lookup_string(*argv)) != KEYC_NONE) { |  | ||||||
| 			data->keys = xrealloc( |  | ||||||
| 			    data->keys, data->nkeys + 1, sizeof *data->keys); |  | ||||||
| 			data->keys[data->nkeys++] = key; |  | ||||||
| 		} else { |  | ||||||
| 			for (s = *argv; *s != '\0'; s++) { |  | ||||||
| 				data->keys = xrealloc(data->keys, |  | ||||||
| 				    data->nkeys + 1, sizeof *data->keys); |  | ||||||
| 				data->keys[data->nkeys++] = *s; |  | ||||||
| 			} |  | ||||||
| 		} |  | ||||||
|  |  | ||||||
| 		argv++; |  | ||||||
| 	} |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_send_keys_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_send_keys_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_send_keys_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct window_pane		*wp; | 	struct window_pane	*wp; | ||||||
| 	struct session			*s; | 	struct session		*s; | ||||||
| 	u_int				 i; | 	const char		*str; | ||||||
|  | 	int			 i, key; | ||||||
|  |  | ||||||
| 	if (data == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), &s, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, &s, &wp) == NULL) | 	for (i = 0; i < args->argc; i++) { | ||||||
| 		return (-1); | 		str = args->argv[i]; | ||||||
|  |  | ||||||
| 	for (i = 0; i < data->nkeys; i++) | 		if ((key = key_string_lookup_string(str)) != KEYC_NONE) { | ||||||
| 		window_pane_key(wp, s, data->keys[i]); | 			    window_pane_key(wp, s, key); | ||||||
|  | 		} else { | ||||||
|  | 			for (; *str != '\0'; str++) | ||||||
|  | 			    window_pane_key(wp, s, *str); | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_send_keys_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_send_keys_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_send_keys_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_send_keys_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
| 	u_int				 i; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
|  |  | ||||||
| 	for (i = 0; i < data->nkeys; i++) { |  | ||||||
| 		if (off >= len) |  | ||||||
| 			break; |  | ||||||
| 		off += xsnprintf(buf + off, |  | ||||||
| 		    len - off, " %s", key_string_lookup_key(data->keys[i])); |  | ||||||
| 	} |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -28,24 +28,23 @@ int	cmd_send_prefix_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_send_prefix_entry = { | const struct cmd_entry cmd_send_prefix_entry = { | ||||||
| 	"send-prefix", NULL, | 	"send-prefix", NULL, | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_PANE_USAGE, | 	CMD_TARGET_PANE_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_send_prefix_exec, | 	cmd_send_prefix_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_send_prefix_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_send_prefix_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct session		*s; | 	struct session		*s; | ||||||
| 	struct window_pane	*wp; | 	struct window_pane	*wp; | ||||||
| 	struct keylist		*keylist; | 	struct keylist		*keylist; | ||||||
|  |  | ||||||
| 	if (cmd_find_pane(ctx, data->target, &s, &wp) == NULL) | 	if (cmd_find_pane(ctx, args_get(args, 't'), &s, &wp) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	keylist = options_get_data(&s->options, "prefix"); | 	keylist = options_get_data(&s->options, "prefix"); | ||||||
|   | |||||||
| @@ -35,13 +35,12 @@ int	cmd_server_info_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_server_info_entry = { | const struct cmd_entry cmd_server_info_entry = { | ||||||
| 	"server-info", "info", | 	"server-info", "info", | ||||||
|  | 	"", 0, 0, | ||||||
| 	"", | 	"", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_server_info_exec, | 	cmd_server_info_exec | ||||||
| 	NULL, |  | ||||||
| 	NULL |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -30,36 +30,45 @@ int	cmd_set_buffer_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_set_buffer_entry = { | const struct cmd_entry cmd_set_buffer_entry = { | ||||||
| 	"set-buffer", "setb", | 	"set-buffer", "setb", | ||||||
|  | 	"b:", 1, 1, | ||||||
| 	CMD_BUFFER_USAGE " data", | 	CMD_BUFFER_USAGE " data", | ||||||
| 	CMD_ARG1, "", | 	0, | ||||||
| 	cmd_buffer_init, | 	NULL, | ||||||
| 	cmd_buffer_parse, | 	NULL, | ||||||
| 	cmd_set_buffer_exec, | 	cmd_set_buffer_exec | ||||||
| 	cmd_buffer_free, |  | ||||||
| 	cmd_buffer_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_set_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_set_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_buffer_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	u_int			 limit; | 	u_int		 limit; | ||||||
| 	char			*pdata; | 	char		*pdata, *cause; | ||||||
| 	size_t			 psize; | 	size_t		 psize; | ||||||
|  | 	int		 buffer; | ||||||
|  |  | ||||||
| 	limit = options_get_number(&global_options, "buffer-limit"); | 	limit = options_get_number(&global_options, "buffer-limit"); | ||||||
|  |  | ||||||
| 	pdata = xstrdup(data->arg); | 	pdata = xstrdup(args->argv[0]); | ||||||
| 	psize = strlen(pdata); | 	psize = strlen(pdata); | ||||||
|  |  | ||||||
| 	if (data->buffer == -1) { | 	if (!args_has(args, 'b')) { | ||||||
| 		paste_add(&global_buffers, pdata, psize, limit); | 		paste_add(&global_buffers, pdata, psize, limit); | ||||||
| 		return (0); | 		return (0); | ||||||
| 	} | 	} | ||||||
| 	if (paste_replace(&global_buffers, data->buffer, pdata, psize) != 0) { |  | ||||||
| 		ctx->error(ctx, "no buffer %d", data->buffer); | 	buffer = args_strtonum(args, 'b', 0, INT_MAX, &cause); | ||||||
|  | 	if (cause != NULL) { | ||||||
|  | 		ctx->error(ctx, "buffer %s", cause); | ||||||
|  | 		xfree(cause); | ||||||
|  | 		return (-1); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if (paste_replace(&global_buffers, buffer, pdata, psize) != 0) { | ||||||
|  | 		ctx->error(ctx, "no buffer %d", buffer); | ||||||
| 		xfree(pdata); | 		xfree(pdata); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|   | |||||||
| @@ -31,57 +31,63 @@ int	cmd_set_environment_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_set_environment_entry = { | const struct cmd_entry cmd_set_environment_entry = { | ||||||
| 	"set-environment", "setenv", | 	"set-environment", "setenv", | ||||||
|  | 	"grt:u", 1, 2, | ||||||
| 	"[-gru] " CMD_TARGET_SESSION_USAGE " name [value]", | 	"[-gru] " CMD_TARGET_SESSION_USAGE " name [value]", | ||||||
| 	CMD_ARG12, "gru", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_set_environment_exec, | 	cmd_set_environment_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_set_environment_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_set_environment_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct session		*s; | 	struct session	*s; | ||||||
| 	struct environ		*env; | 	struct environ	*env; | ||||||
|  | 	const char	*name, *value; | ||||||
|  |  | ||||||
| 	if (*data->arg == '\0') { | 	name = args->argv[0]; | ||||||
|  | 	if (*name == '\0') { | ||||||
| 		ctx->error(ctx, "empty variable name"); | 		ctx->error(ctx, "empty variable name"); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
| 	if (strchr(data->arg, '=') != NULL) { | 	if (strchr(name, '=') != NULL) { | ||||||
| 		ctx->error(ctx, "variable name contains ="); | 		ctx->error(ctx, "variable name contains ="); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'g')) | 	if (args->argc < 1) | ||||||
|  | 		value = NULL; | ||||||
|  | 	else | ||||||
|  | 		value = args->argv[1]; | ||||||
|  |  | ||||||
|  | 	if (args_has(self->args, 'g')) | ||||||
| 		env = &global_environ; | 		env = &global_environ; | ||||||
| 	else { | 	else { | ||||||
| 		if ((s = cmd_find_session(ctx, data->target)) == NULL) | 		if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		env = &s->environ; | 		env = &s->environ; | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'u')) { | 	if (args_has(self->args, 'u')) { | ||||||
| 		if (data->arg2 != NULL) { | 		if (value != NULL) { | ||||||
| 			ctx->error(ctx, "can't specify a value with -u"); | 			ctx->error(ctx, "can't specify a value with -u"); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		environ_unset(env, data->arg); | 		environ_unset(env, name); | ||||||
| 	} else if (cmd_check_flag(data->chflags, 'r')) { | 	} else if (args_has(self->args, 'r')) { | ||||||
| 		if (data->arg2 != NULL) { | 		if (value != NULL) { | ||||||
| 			ctx->error(ctx, "can't specify a value with -r"); | 			ctx->error(ctx, "can't specify a value with -r"); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		environ_set(env, data->arg, NULL); | 		environ_set(env, name, NULL); | ||||||
| 	} else { | 	} else { | ||||||
| 		if (data->arg2 == NULL) { | 		if (value == NULL) { | ||||||
| 			ctx->error(ctx, "no value specified"); | 			ctx->error(ctx, "no value specified"); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		environ_set(env, data->arg, data->arg2); | 		environ_set(env, name, value); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
|   | |||||||
							
								
								
									
										205
									
								
								cmd-set-option.c
									
									
									
									
									
								
							
							
						
						
									
										205
									
								
								cmd-set-option.c
									
									
									
									
									
								
							| @@ -30,40 +30,48 @@ | |||||||
| int	cmd_set_option_exec(struct cmd *, struct cmd_ctx *); | int	cmd_set_option_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| int	cmd_set_option_unset(struct cmd *, struct cmd_ctx *, | int	cmd_set_option_unset(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
| int	cmd_set_option_set(struct cmd *, struct cmd_ctx *, | int	cmd_set_option_set(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
|  |  | ||||||
| struct options_entry *cmd_set_option_string(struct cmd *, struct cmd_ctx *, | struct options_entry *cmd_set_option_string(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
| struct options_entry *cmd_set_option_number(struct cmd *, struct cmd_ctx *, | struct options_entry *cmd_set_option_number(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
| struct options_entry *cmd_set_option_keys(struct cmd *, struct cmd_ctx *, | struct options_entry *cmd_set_option_keys(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
| struct options_entry *cmd_set_option_colour(struct cmd *, struct cmd_ctx *, | struct options_entry *cmd_set_option_colour(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
| struct options_entry *cmd_set_option_attributes(struct cmd *, struct cmd_ctx *, | struct options_entry *cmd_set_option_attributes(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
| struct options_entry *cmd_set_option_flag(struct cmd *, struct cmd_ctx *, | struct options_entry *cmd_set_option_flag(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
| struct options_entry *cmd_set_option_choice(struct cmd *, struct cmd_ctx *, | struct options_entry *cmd_set_option_choice(struct cmd *, struct cmd_ctx *, | ||||||
| 	    const struct options_table_entry *, struct options *); | 	    const struct options_table_entry *, struct options *, | ||||||
|  | 	    const char *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_set_option_entry = { | const struct cmd_entry cmd_set_option_entry = { | ||||||
| 	"set-option", "set", | 	"set-option", "set", | ||||||
|  | 	"agst:uw", 1, 2, | ||||||
| 	"[-agsuw] [-t target-session|target-window] option [value]", | 	"[-agsuw] [-t target-session|target-window] option [value]", | ||||||
| 	CMD_ARG12, "agsuw", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_set_option_exec, | 	cmd_set_option_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_set_option_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_set_option_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data			*data = self->data; | 	struct args				*args = self->args; | ||||||
| 	const struct options_table_entry	*table, *oe, *oe_loop; | 	const struct options_table_entry	*table, *oe, *oe_loop; | ||||||
| 	struct session				*s; | 	struct session				*s; | ||||||
| 	struct winlink				*wl; | 	struct winlink				*wl; | ||||||
| @@ -71,61 +79,74 @@ cmd_set_option_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	struct options				*oo; | 	struct options				*oo; | ||||||
| 	struct jobs				*jobs; | 	struct jobs				*jobs; | ||||||
| 	struct job				*job, *nextjob; | 	struct job				*job, *nextjob; | ||||||
|  | 	const char				*optstr, *valstr; | ||||||
| 	u_int					 i; | 	u_int					 i; | ||||||
| 	int					 try_again; | 	int					 try_again; | ||||||
|  |  | ||||||
| 	/* Work out the options tree and table to use. */ | 	/* Work out the options tree and table to use. */ | ||||||
| 	if (cmd_check_flag(data->chflags, 's')) { | 	if (args_has(self->args, 's')) { | ||||||
| 		oo = &global_options; | 		oo = &global_options; | ||||||
| 		table = server_options_table; | 		table = server_options_table; | ||||||
| 	} else if (cmd_check_flag(data->chflags, 'w')) { | 	} else if (args_has(self->args, 'w')) { | ||||||
| 		table = window_options_table; | 		table = window_options_table; | ||||||
| 		if (cmd_check_flag(data->chflags, 'g')) | 		if (args_has(self->args, 'g')) | ||||||
| 			oo = &global_w_options; | 			oo = &global_w_options; | ||||||
| 		else { | 		else { | ||||||
| 			wl = cmd_find_window(ctx, data->target, NULL); | 			wl = cmd_find_window(ctx, args_get(args, 't'), NULL); | ||||||
| 			if (wl == NULL) | 			if (wl == NULL) | ||||||
| 				return (-1); | 				return (-1); | ||||||
| 			oo = &wl->window->options; | 			oo = &wl->window->options; | ||||||
| 		} | 		} | ||||||
| 	} else { | 	} else { | ||||||
| 		table = session_options_table; | 		table = session_options_table; | ||||||
| 		if (cmd_check_flag(data->chflags, 'g')) | 		if (args_has(self->args, 'g')) | ||||||
| 			oo = &global_s_options; | 			oo = &global_s_options; | ||||||
| 		else { | 		else { | ||||||
| 			s = cmd_find_session(ctx, data->target); | 			s = cmd_find_session(ctx, args_get(args, 't')); | ||||||
| 			if (s == NULL) | 			if (s == NULL) | ||||||
| 				return (-1); | 				return (-1); | ||||||
| 			oo = &s->options; | 			oo = &s->options; | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
|  | 	/* Get the option name and value. */ | ||||||
|  | 	optstr = args->argv[0]; | ||||||
|  | 	if (*optstr == '\0') { | ||||||
|  | 		ctx->error(ctx, "invalid option"); | ||||||
|  | 		return (-1); | ||||||
|  | 	} | ||||||
|  | 	if (args->argc < 1) | ||||||
|  | 		valstr = NULL; | ||||||
|  | 	else | ||||||
|  | 		valstr = args->argv[1]; | ||||||
|  |  | ||||||
| 	/* Find the option table entry. */ | 	/* Find the option table entry. */ | ||||||
| 	oe = NULL; | 	oe = NULL; | ||||||
| 	for (oe_loop = table; oe_loop->name != NULL; oe_loop++) { | 	for (oe_loop = table; oe_loop->name != NULL; oe_loop++) { | ||||||
| 		if (strncmp(oe_loop->name, data->arg, strlen(data->arg)) != 0) | 		if (strncmp(oe_loop->name, optstr, strlen(optstr)) != 0) | ||||||
| 			continue; | 			continue; | ||||||
|  |  | ||||||
| 		if (oe != NULL) { | 		if (oe != NULL) { | ||||||
| 			ctx->error(ctx, "ambiguous option: %s", data->arg); | 			ctx->error(ctx, "ambiguous option: %s", optstr); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 		oe = oe_loop; | 		oe = oe_loop; | ||||||
|  |  | ||||||
| 		/* Bail now if an exact match. */ | 		/* Bail now if an exact match. */ | ||||||
| 		if (strcmp(oe->name, data->arg) == 0) | 		if (strcmp(oe->name, optstr) == 0) | ||||||
| 			break; | 			break; | ||||||
| 	} | 	} | ||||||
| 	if (oe == NULL) { | 	if (oe == NULL) { | ||||||
| 		ctx->error(ctx, "unknown option: %s", data->arg); | 		ctx->error(ctx, "unknown option: %s", optstr); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	/* Unset or set the option. */ | 	/* Unset or set the option. */ | ||||||
| 	if (cmd_check_flag(data->chflags, 'u')) { | 	if (args_has(args, 'u')) { | ||||||
| 		if (cmd_set_option_unset(self, ctx, oe, oo) != 0) | 		if (cmd_set_option_unset(self, ctx, oe, oo, valstr) != 0) | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 	} else { | 	} else { | ||||||
| 		if (cmd_set_option_set(self, ctx, oe, oo) != 0) | 		if (cmd_set_option_set(self, ctx, oe, oo, valstr) != 0) | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| @@ -176,15 +197,15 @@ cmd_set_option_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| /* Unset an option. */ | /* Unset an option. */ | ||||||
| int | int | ||||||
| cmd_set_option_unset(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_unset(struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'g')) { | 	if (args_has(args, 'g')) { | ||||||
| 		ctx->error(ctx, "can't unset global option: %s", oe->name); | 		ctx->error(ctx, "can't unset global option: %s", oe->name); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
| 	if (data->arg2 != NULL) { | 	if (value != NULL) { | ||||||
| 		ctx->error(ctx, "value passed to unset option: %s", oe->name); | 		ctx->error(ctx, "value passed to unset option: %s", oe->name); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
| @@ -197,39 +218,38 @@ cmd_set_option_unset(struct cmd *self, struct cmd_ctx *ctx, | |||||||
| /* Set an option. */ | /* Set an option. */ | ||||||
| int | int | ||||||
| cmd_set_option_set(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_set(struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; |  | ||||||
| 	struct options_entry	*o; | 	struct options_entry	*o; | ||||||
| 	const char		*s; | 	const char		*s; | ||||||
|  |  | ||||||
| 	if (oe->type != OPTIONS_TABLE_FLAG && data->arg2 == NULL) { | 	if (oe->type != OPTIONS_TABLE_FLAG && value == NULL) { | ||||||
| 		ctx->error(ctx, "empty data->arg2"); | 		ctx->error(ctx, "empty value"); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	o = NULL; | 	o = NULL; | ||||||
| 	switch (oe->type) { | 	switch (oe->type) { | ||||||
| 	case OPTIONS_TABLE_STRING: | 	case OPTIONS_TABLE_STRING: | ||||||
| 		o = cmd_set_option_string(self, ctx, oe, oo); | 		o = cmd_set_option_string(self, ctx, oe, oo, value); | ||||||
| 		break; | 		break; | ||||||
| 	case OPTIONS_TABLE_NUMBER: | 	case OPTIONS_TABLE_NUMBER: | ||||||
| 		o = cmd_set_option_number(self, ctx, oe, oo); | 		o = cmd_set_option_number(self, ctx, oe, oo, value); | ||||||
| 		break; | 		break; | ||||||
| 	case OPTIONS_TABLE_KEYS: | 	case OPTIONS_TABLE_KEYS: | ||||||
| 		o = cmd_set_option_keys(self, ctx, oe, oo); | 		o = cmd_set_option_keys(self, ctx, oe, oo, value); | ||||||
| 		break; | 		break; | ||||||
| 	case OPTIONS_TABLE_COLOUR: | 	case OPTIONS_TABLE_COLOUR: | ||||||
| 		o = cmd_set_option_colour(self, ctx, oe, oo); | 		o = cmd_set_option_colour(self, ctx, oe, oo, value); | ||||||
| 		break; | 		break; | ||||||
| 	case OPTIONS_TABLE_ATTRIBUTES: | 	case OPTIONS_TABLE_ATTRIBUTES: | ||||||
| 		o = cmd_set_option_attributes(self, ctx, oe, oo); | 		o = cmd_set_option_attributes(self, ctx, oe, oo, value); | ||||||
| 		break; | 		break; | ||||||
| 	case OPTIONS_TABLE_FLAG: | 	case OPTIONS_TABLE_FLAG: | ||||||
| 		o = cmd_set_option_flag(self, ctx, oe, oo); | 		o = cmd_set_option_flag(self, ctx, oe, oo, value); | ||||||
| 		break; | 		break; | ||||||
| 	case OPTIONS_TABLE_CHOICE: | 	case OPTIONS_TABLE_CHOICE: | ||||||
| 		o = cmd_set_option_choice(self, ctx, oe, oo); | 		o = cmd_set_option_choice(self, ctx, oe, oo, value); | ||||||
| 		break; | 		break; | ||||||
| 	} | 	} | ||||||
| 	if (o == NULL) | 	if (o == NULL) | ||||||
| @@ -243,37 +263,35 @@ cmd_set_option_set(struct cmd *self, struct cmd_ctx *ctx, | |||||||
| /* Set a string option. */ | /* Set a string option. */ | ||||||
| struct options_entry * | struct options_entry * | ||||||
| cmd_set_option_string(struct cmd *self, unused struct cmd_ctx *ctx, | cmd_set_option_string(struct cmd *self, unused struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct options_entry	*o; | 	struct options_entry	*o; | ||||||
| 	char			*oldval, *newval; | 	char			*oldval, *newval; | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'a')) { | 	if (args_has(args, 'a')) { | ||||||
| 		oldval = options_get_string(oo, oe->name); | 		oldval = options_get_string(oo, oe->name); | ||||||
| 		xasprintf(&newval, "%s%s", oldval, data->arg2); | 		xasprintf(&newval, "%s%s", oldval, value); | ||||||
| 	} else | 	} else | ||||||
| 		newval = data->arg2; | 		newval = xstrdup(value); | ||||||
|  |  | ||||||
| 	o = options_set_string(oo, oe->name, "%s", newval); | 	o = options_set_string(oo, oe->name, "%s", newval); | ||||||
|  |  | ||||||
| 	if (newval != data->arg2) | 	xfree(newval); | ||||||
| 		xfree(newval); |  | ||||||
| 	return (o); | 	return (o); | ||||||
| } | } | ||||||
|  |  | ||||||
| /* Set a number option. */ | /* Set a number option. */ | ||||||
| struct options_entry * | struct options_entry * | ||||||
| cmd_set_option_number(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_number(unused struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	long long	 ll; | ||||||
| 	long long		 ll; | 	const char     	*errstr; | ||||||
| 	const char     		*errstr; |  | ||||||
|  |  | ||||||
| 	ll = strtonum(data->arg2, oe->minimum, oe->maximum, &errstr); | 	ll = strtonum(value, oe->minimum, oe->maximum, &errstr); | ||||||
| 	if (errstr != NULL) { | 	if (errstr != NULL) { | ||||||
| 		ctx->error(ctx, "value is %s: %s", errstr, data->arg2); | 		ctx->error(ctx, "value is %s: %s", errstr, value); | ||||||
| 		return (NULL); | 		return (NULL); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| @@ -282,18 +300,17 @@ cmd_set_option_number(struct cmd *self, struct cmd_ctx *ctx, | |||||||
|  |  | ||||||
| /* Set a keys option. */ | /* Set a keys option. */ | ||||||
| struct options_entry * | struct options_entry * | ||||||
| cmd_set_option_keys(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_keys(unused struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct keylist	*keylist; | ||||||
| 	struct keylist		*keylist; | 	char		*copy, *ptr, *s; | ||||||
| 	char			*copy, *ptr, *s; | 	int		 key; | ||||||
| 	int		 	 key; |  | ||||||
|  |  | ||||||
| 	keylist = xmalloc(sizeof *keylist); | 	keylist = xmalloc(sizeof *keylist); | ||||||
| 	ARRAY_INIT(keylist); | 	ARRAY_INIT(keylist); | ||||||
|  |  | ||||||
| 	ptr = copy = xstrdup(data->arg2); | 	ptr = copy = xstrdup(value); | ||||||
| 	while ((s = strsep(&ptr, ",")) != NULL) { | 	while ((s = strsep(&ptr, ",")) != NULL) { | ||||||
| 		if ((key = key_string_lookup_string(s)) == KEYC_NONE) { | 		if ((key = key_string_lookup_string(s)) == KEYC_NONE) { | ||||||
| 			ctx->error(ctx, "unknown key: %s", s); | 			ctx->error(ctx, "unknown key: %s", s); | ||||||
| @@ -310,14 +327,13 @@ cmd_set_option_keys(struct cmd *self, struct cmd_ctx *ctx, | |||||||
|  |  | ||||||
| /* Set a colour option. */ | /* Set a colour option. */ | ||||||
| struct options_entry * | struct options_entry * | ||||||
| cmd_set_option_colour(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_colour(unused struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	int	colour; | ||||||
| 	int			 colour; |  | ||||||
|  |  | ||||||
| 	if ((colour = colour_fromstring(data->arg2)) == -1) { | 	if ((colour = colour_fromstring(value)) == -1) { | ||||||
| 		ctx->error(ctx, "bad colour: %s", data->arg2); | 		ctx->error(ctx, "bad colour: %s", value); | ||||||
| 		return (NULL); | 		return (NULL); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| @@ -326,14 +342,13 @@ cmd_set_option_colour(struct cmd *self, struct cmd_ctx *ctx, | |||||||
|  |  | ||||||
| /* Set an attributes option. */ | /* Set an attributes option. */ | ||||||
| struct options_entry * | struct options_entry * | ||||||
| cmd_set_option_attributes(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_attributes(unused struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	int	attr; | ||||||
| 	int			 attr; |  | ||||||
|  |  | ||||||
| 	if ((attr = attributes_fromstring(data->arg2)) == -1) { | 	if ((attr = attributes_fromstring(value)) == -1) { | ||||||
| 		ctx->error(ctx, "bad attributes: %s", data->arg2); | 		ctx->error(ctx, "bad attributes: %s", value); | ||||||
| 		return (NULL); | 		return (NULL); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| @@ -342,25 +357,24 @@ cmd_set_option_attributes(struct cmd *self, struct cmd_ctx *ctx, | |||||||
|  |  | ||||||
| /* Set a flag option. */ | /* Set a flag option. */ | ||||||
| struct options_entry * | struct options_entry * | ||||||
| cmd_set_option_flag(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_flag(unused struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	int	flag; | ||||||
| 	int			 flag; |  | ||||||
|  |  | ||||||
| 	if (data->arg2 == NULL || *data->arg2 == '\0') | 	if (value == NULL || *value == '\0') | ||||||
| 		flag = !options_get_number(oo, oe->name); | 		flag = !options_get_number(oo, oe->name); | ||||||
| 	else { | 	else { | ||||||
| 		if ((data->arg2[0] == '1' && data->arg2[1] == '\0') || | 		if ((value[0] == '1' && value[1] == '\0') || | ||||||
| 		    strcasecmp(data->arg2, "on") == 0 || | 		    strcasecmp(value, "on") == 0 || | ||||||
| 		    strcasecmp(data->arg2, "yes") == 0) | 		    strcasecmp(value, "yes") == 0) | ||||||
| 			flag = 1; | 			flag = 1; | ||||||
| 		else if ((data->arg2[0] == '0' && data->arg2[1] == '\0') || | 		else if ((value[0] == '0' && value[1] == '\0') || | ||||||
| 		    strcasecmp(data->arg2, "off") == 0 || | 		    strcasecmp(value, "off") == 0 || | ||||||
| 		    strcasecmp(data->arg2, "no") == 0) | 		    strcasecmp(value, "no") == 0) | ||||||
| 			flag = 0; | 			flag = 0; | ||||||
| 		else { | 		else { | ||||||
| 			ctx->error(ctx, "bad value: %s", data->arg2); | 			ctx->error(ctx, "bad value: %s", value); | ||||||
| 			return (NULL); | 			return (NULL); | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
| @@ -370,27 +384,26 @@ cmd_set_option_flag(struct cmd *self, struct cmd_ctx *ctx, | |||||||
|  |  | ||||||
| /* Set a choice option. */ | /* Set a choice option. */ | ||||||
| struct options_entry * | struct options_entry * | ||||||
| cmd_set_option_choice(struct cmd *self, struct cmd_ctx *ctx, | cmd_set_option_choice(unused struct cmd *self, struct cmd_ctx *ctx, | ||||||
|     const struct options_table_entry *oe, struct options *oo) |     const struct options_table_entry *oe, struct options *oo, const char *value) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	const char	**choicep; | ||||||
| 	const char     	       **choicep; | 	int		  n, choice = -1; | ||||||
| 	int		 	 n, choice = -1; |  | ||||||
|  |  | ||||||
| 	n = 0; | 	n = 0; | ||||||
| 	for (choicep = oe->choices; *choicep != NULL; choicep++) { | 	for (choicep = oe->choices; *choicep != NULL; choicep++) { | ||||||
| 		n++; | 		n++; | ||||||
| 		if (strncmp(*choicep, data->arg2, strlen(data->arg2)) != 0) | 		if (strncmp(*choicep, value, strlen(value)) != 0) | ||||||
| 			continue; | 			continue; | ||||||
|  |  | ||||||
| 		if (choice != -1) { | 		if (choice != -1) { | ||||||
| 			ctx->error(ctx, "ambiguous value: %s", data->arg2); | 			ctx->error(ctx, "ambiguous value: %s", value); | ||||||
| 			return (NULL); | 			return (NULL); | ||||||
| 		} | 		} | ||||||
| 		choice = n - 1; | 		choice = n - 1; | ||||||
| 	} | 	} | ||||||
| 	if (choice == -1) { | 	if (choice == -1) { | ||||||
| 		ctx->error(ctx, "unknown value: %s", data->arg2); | 		ctx->error(ctx, "unknown value: %s", value); | ||||||
| 		return (NULL); | 		return (NULL); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
|   | |||||||
| @@ -28,20 +28,19 @@ int	cmd_set_window_option_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_set_window_option_entry = { | const struct cmd_entry cmd_set_window_option_entry = { | ||||||
| 	"set-window-option", "setw", | 	"set-window-option", "setw", | ||||||
|  | 	"agt:u", 1, 2, | ||||||
| 	"[-agu] " CMD_TARGET_WINDOW_USAGE " option [value]", | 	"[-agu] " CMD_TARGET_WINDOW_USAGE " option [value]", | ||||||
| 	CMD_ARG12, "agu", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_set_window_option_exec, | 	cmd_set_window_option_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_set_window_option_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_set_window_option_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args	*args = self->args; | ||||||
|  |  | ||||||
| 	cmd_set_flag(&data->chflags, 'w'); | 	args_set(args, 'w', NULL); | ||||||
| 	return (cmd_set_option_entry.exec(self, ctx)); | 	return (cmd_set_option_entry.exec(self, ctx)); | ||||||
| } | } | ||||||
|   | |||||||
| @@ -30,37 +30,44 @@ int	cmd_show_buffer_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_show_buffer_entry = { | const struct cmd_entry cmd_show_buffer_entry = { | ||||||
| 	"show-buffer", "showb", | 	"show-buffer", "showb", | ||||||
|  | 	"b:", 0, 0, | ||||||
| 	CMD_BUFFER_USAGE, | 	CMD_BUFFER_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_buffer_init, | 	NULL, | ||||||
| 	cmd_buffer_parse, | 	NULL, | ||||||
| 	cmd_show_buffer_exec, | 	cmd_show_buffer_exec | ||||||
| 	cmd_buffer_free, |  | ||||||
| 	cmd_buffer_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_show_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_show_buffer_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_buffer_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct session		*s; | 	struct session		*s; | ||||||
| 	struct paste_buffer	*pb; | 	struct paste_buffer	*pb; | ||||||
| 	char			*in, *buf, *ptr; | 	int			 buffer; | ||||||
|  | 	char			*in, *buf, *ptr, *cause; | ||||||
| 	size_t			 size, len; | 	size_t			 size, len; | ||||||
| 	u_int			 width; | 	u_int			 width; | ||||||
|  |  | ||||||
| 	if ((s = cmd_find_session(ctx, NULL)) == NULL) | 	if ((s = cmd_find_session(ctx, NULL)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	if (data->buffer == -1) { | 	if (!args_has(args, 'b')) { | ||||||
| 		if ((pb = paste_get_top(&global_buffers)) == NULL) { | 		if ((pb = paste_get_top(&global_buffers)) == NULL) { | ||||||
| 			ctx->error(ctx, "no buffers"); | 			ctx->error(ctx, "no buffers"); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} else { | 	} else { | ||||||
| 		pb = paste_get_index(&global_buffers, data->buffer); | 		buffer = args_strtonum(args, 'b', 0, INT_MAX, &cause); | ||||||
|  | 		if (cause != NULL) { | ||||||
|  | 			ctx->error(ctx, "buffer %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
|  |  | ||||||
|  | 		pb = paste_get_index(&global_buffers, buffer); | ||||||
| 		if (pb == NULL) { | 		if (pb == NULL) { | ||||||
| 			ctx->error(ctx, "no buffer %d", data->buffer); | 			ctx->error(ctx, "no buffer %d", buffer); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} | 	} | ||||||
|   | |||||||
| @@ -31,27 +31,26 @@ int	cmd_show_environment_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_show_environment_entry = { | const struct cmd_entry cmd_show_environment_entry = { | ||||||
| 	"show-environment", "showenv", | 	"show-environment", "showenv", | ||||||
|  | 	"gt:", 0, 0, | ||||||
| 	"[-g] " CMD_TARGET_SESSION_USAGE, | 	"[-g] " CMD_TARGET_SESSION_USAGE, | ||||||
| 	0, "g", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_show_environment_exec, | 	cmd_show_environment_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_show_environment_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_show_environment_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct session			*s; | 	struct session		*s; | ||||||
| 	struct environ			*env; | 	struct environ		*env; | ||||||
| 	struct environ_entry		*envent; | 	struct environ_entry	*envent; | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 'g')) | 	if (args_has(self->args, 'g')) | ||||||
| 		env = &global_environ; | 		env = &global_environ; | ||||||
| 	else { | 	else { | ||||||
| 		if ((s = cmd_find_session(ctx, data->target)) == NULL) | 		if ((s = cmd_find_session(ctx, args_get(args, 't'))) == NULL) | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		env = &s->environ; | 		env = &s->environ; | ||||||
| 	} | 	} | ||||||
|   | |||||||
| @@ -31,25 +31,24 @@ int	cmd_show_messages_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_show_messages_entry = { | const struct cmd_entry cmd_show_messages_entry = { | ||||||
| 	"show-messages", "showmsgs", | 	"show-messages", "showmsgs", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_CLIENT_USAGE, | 	CMD_TARGET_CLIENT_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_show_messages_exec, | 	cmd_show_messages_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_show_messages_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_show_messages_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct client			*c; | 	struct client		*c; | ||||||
| 	struct message_entry		*msg; | 	struct message_entry	*msg; | ||||||
| 	char				*tim; | 	char			*tim; | ||||||
| 	u_int				 i; | 	u_int			 i; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	for (i = 0; i < ARRAY_LENGTH(&c->message_log); i++) { | 	for (i = 0; i < ARRAY_LENGTH(&c->message_log); i++) { | ||||||
|   | |||||||
| @@ -31,19 +31,18 @@ int	cmd_show_options_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_show_options_entry = { | const struct cmd_entry cmd_show_options_entry = { | ||||||
| 	"show-options", "show", | 	"show-options", "show", | ||||||
|  | 	"gst:w", 0, 0, | ||||||
| 	"[-gsw] [-t target-session|target-window]", | 	"[-gsw] [-t target-session|target-window]", | ||||||
| 	0, "gsw", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_show_options_exec, | 	cmd_show_options_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_show_options_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_show_options_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data			*data = self->data; | 	struct args				*args = self->args; | ||||||
| 	const struct options_table_entry	*table, *oe; | 	const struct options_table_entry	*table, *oe; | ||||||
| 	struct session				*s; | 	struct session				*s; | ||||||
| 	struct winlink				*wl; | 	struct winlink				*wl; | ||||||
| @@ -51,25 +50,25 @@ cmd_show_options_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	struct options_entry			*o; | 	struct options_entry			*o; | ||||||
| 	const char				*optval; | 	const char				*optval; | ||||||
|  |  | ||||||
| 	if (cmd_check_flag(data->chflags, 's')) { | 	if (args_has(self->args, 's')) { | ||||||
| 		oo = &global_options; | 		oo = &global_options; | ||||||
| 		table = server_options_table; | 		table = server_options_table; | ||||||
| 	} else if (cmd_check_flag(data->chflags, 'w')) { | 	} else if (args_has(self->args, 'w')) { | ||||||
| 		table = window_options_table; | 		table = window_options_table; | ||||||
| 		if (cmd_check_flag(data->chflags, 'g')) | 		if (args_has(self->args, 'g')) | ||||||
| 			oo = &global_w_options; | 			oo = &global_w_options; | ||||||
| 		else { | 		else { | ||||||
| 			wl = cmd_find_window(ctx, data->target, NULL); | 			wl = cmd_find_window(ctx, args_get(args, 't'), NULL); | ||||||
| 			if (wl == NULL) | 			if (wl == NULL) | ||||||
| 				return (-1); | 				return (-1); | ||||||
| 			oo = &wl->window->options; | 			oo = &wl->window->options; | ||||||
| 		} | 		} | ||||||
| 	} else { | 	} else { | ||||||
| 		table = session_options_table; | 		table = session_options_table; | ||||||
| 		if (cmd_check_flag(data->chflags, 'g')) | 		if (args_has(self->args, 'g')) | ||||||
| 			oo = &global_s_options; | 			oo = &global_s_options; | ||||||
| 		else { | 		else { | ||||||
| 			s = cmd_find_session(ctx, data->target); | 			s = cmd_find_session(ctx, args_get(args, 't')); | ||||||
| 			if (s == NULL) | 			if (s == NULL) | ||||||
| 				return (-1); | 				return (-1); | ||||||
| 			oo = &s->options; | 			oo = &s->options; | ||||||
|   | |||||||
| @@ -31,20 +31,19 @@ int	cmd_show_window_options_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_show_window_options_entry = { | const struct cmd_entry cmd_show_window_options_entry = { | ||||||
| 	"show-window-options", "showw", | 	"show-window-options", "showw", | ||||||
|  | 	"gt:", 0, 0, | ||||||
| 	"[-g] " CMD_TARGET_WINDOW_USAGE, | 	"[-g] " CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "g", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_show_window_options_exec, | 	cmd_show_window_options_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_show_window_options_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_show_window_options_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data		*data = self->data; | 	struct args	*args = self->args; | ||||||
|  |  | ||||||
| 	cmd_set_flag(&data->chflags, 'w'); | 	args_set(args, 'w', NULL); | ||||||
| 	return (cmd_show_options_entry.exec(self, ctx)); | 	return (cmd_show_options_entry.exec(self, ctx)); | ||||||
| } | } | ||||||
|   | |||||||
| @@ -24,80 +24,31 @@ | |||||||
|  * Sources a configuration file. |  * Sources a configuration file. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_source_file_parse(struct cmd *, int, char **, char **); |  | ||||||
| int	cmd_source_file_exec(struct cmd *, struct cmd_ctx *); | int	cmd_source_file_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_source_file_free(struct cmd *); |  | ||||||
| void	cmd_source_file_init(struct cmd *, int); |  | ||||||
| size_t	cmd_source_file_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_source_file_data { |  | ||||||
| 	char *path; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_source_file_entry = { | const struct cmd_entry cmd_source_file_entry = { | ||||||
| 	"source-file", "source", | 	"source-file", "source", | ||||||
|  | 	"", 1, 1, | ||||||
| 	"path", | 	"path", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_source_file_init, | 	NULL, | ||||||
| 	cmd_source_file_parse, | 	NULL, | ||||||
| 	cmd_source_file_exec, | 	cmd_source_file_exec | ||||||
| 	cmd_source_file_free, |  | ||||||
| 	cmd_source_file_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ |  | ||||||
| void |  | ||||||
| cmd_source_file_init(struct cmd *self, unused int arg) |  | ||||||
| { |  | ||||||
| 	struct cmd_source_file_data	*data; |  | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->path = NULL; |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_source_file_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_source_file_data	*data; |  | ||||||
| 	int				 opt; |  | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc != 1) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	data->path = xstrdup(argv[0]); |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_source_file_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_source_file_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_source_file_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct causelist		 causes; | 	struct causelist	 causes; | ||||||
| 	char				*cause; | 	char			*cause; | ||||||
| 	struct window_pane		*wp; | 	struct window_pane	*wp; | ||||||
| 	int				 retval; | 	int			 retval; | ||||||
| 	u_int				 i; | 	u_int			 i; | ||||||
|  |  | ||||||
| 	ARRAY_INIT(&causes); | 	ARRAY_INIT(&causes); | ||||||
|  |  | ||||||
| 	retval = load_cfg(data->path, ctx, &causes); | 	retval = load_cfg(args->argv[0], ctx, &causes); | ||||||
| 	if (ARRAY_EMPTY(&causes)) | 	if (ARRAY_EMPTY(&causes)) | ||||||
| 		return (retval); | 		return (retval); | ||||||
|  |  | ||||||
| @@ -121,27 +72,3 @@ cmd_source_file_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	return (retval); | 	return (retval); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_source_file_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_source_file_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->path != NULL) |  | ||||||
| 		xfree(data->path); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_source_file_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_source_file_data	*data = self->data; |  | ||||||
| 	size_t				off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->path != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->path); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -28,142 +28,44 @@ | |||||||
|  * Split a window (add a new pane). |  * Split a window (add a new pane). | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_split_window_parse(struct cmd *, int, char **, char **); | void	cmd_split_window_key_binding(struct cmd *, int); | ||||||
| int	cmd_split_window_exec(struct cmd *, struct cmd_ctx *); | int	cmd_split_window_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_split_window_free(struct cmd *); |  | ||||||
| void	cmd_split_window_init(struct cmd *, int); |  | ||||||
| size_t	cmd_split_window_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_split_window_data { |  | ||||||
| 	char	*target; |  | ||||||
| 	char	*cmd; |  | ||||||
| 	int	 flag_detached; |  | ||||||
| 	int	 flag_horizontal; |  | ||||||
| 	int	 flag_print; |  | ||||||
| 	int	 percentage; |  | ||||||
| 	int	 size; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_split_window_entry = { | const struct cmd_entry cmd_split_window_entry = { | ||||||
| 	"split-window", "splitw", | 	"split-window", "splitw", | ||||||
|  | 	"dl:hp:Pt:v", 0, 1, | ||||||
| 	"[-dhvP] [-p percentage|-l size] [-t target-pane] [command]", | 	"[-dhvP] [-p percentage|-l size] [-t target-pane] [command]", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_split_window_init, | 	cmd_split_window_key_binding, | ||||||
| 	cmd_split_window_parse, | 	NULL, | ||||||
| 	cmd_split_window_exec, | 	cmd_split_window_exec | ||||||
| 	cmd_split_window_free, |  | ||||||
| 	cmd_split_window_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_split_window_init(struct cmd *self, int key) | cmd_split_window_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_split_window_data	 *data; | 	self->args = args_create(0); | ||||||
|  | 	if (key == '%') | ||||||
| 	self->data = data = xmalloc(sizeof *data); | 		args_set(self->args, 'h', NULL); | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->cmd = NULL; |  | ||||||
| 	data->flag_detached = 0; |  | ||||||
| 	data->flag_horizontal = 0; |  | ||||||
| 	data->flag_print = 0; |  | ||||||
| 	data->percentage = -1; |  | ||||||
| 	data->size = -1; |  | ||||||
|  |  | ||||||
| 	switch (key) { |  | ||||||
| 	case '%': |  | ||||||
| 		data->flag_horizontal = 1; |  | ||||||
| 		break; |  | ||||||
| 	case '"': |  | ||||||
| 		data->flag_horizontal = 0; |  | ||||||
| 		break; |  | ||||||
| 	} |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_split_window_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_split_window_data	*data; |  | ||||||
| 	int				 opt; |  | ||||||
| 	const char			*errstr; |  | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "dhl:p:Pt:v")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'd': |  | ||||||
| 			data->flag_detached = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'h': |  | ||||||
| 			data->flag_horizontal = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 'l': |  | ||||||
| 			if (data->percentage != -1 || data->size != -1) |  | ||||||
| 				break; |  | ||||||
| 			data->size = strtonum(optarg, 1, INT_MAX, &errstr); |  | ||||||
| 			if (errstr != NULL) { |  | ||||||
| 				xasprintf(cause, "size %s", errstr); |  | ||||||
| 				goto error; |  | ||||||
| 			} |  | ||||||
| 			break; |  | ||||||
| 		case 'p': |  | ||||||
| 			if (data->size != -1 || data->percentage != -1) |  | ||||||
| 				break; |  | ||||||
| 			data->percentage = strtonum(optarg, 1, 100, &errstr); |  | ||||||
| 			if (errstr != NULL) { |  | ||||||
| 				xasprintf(cause, "percentage %s", errstr); |  | ||||||
| 				goto error; |  | ||||||
| 			} |  | ||||||
| 			break; |  | ||||||
| 		case 'P': |  | ||||||
| 			data->flag_print = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'v': |  | ||||||
| 			data->flag_horizontal = 0; |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc != 0 && argc != 1) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	if (argc == 1) |  | ||||||
| 		data->cmd = xstrdup(argv[0]); |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| error: |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_split_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_split_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_split_window_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct session			*s; | 	struct session		*s; | ||||||
| 	struct winlink			*wl; | 	struct winlink		*wl; | ||||||
| 	struct window			*w; | 	struct window		*w; | ||||||
| 	struct window_pane		*wp, *new_wp = NULL; | 	struct window_pane	*wp, *new_wp = NULL; | ||||||
| 	struct environ			 env; | 	struct environ		 env; | ||||||
| 	char		 		*cmd, *cwd, *cause; | 	char		 	*cmd, *cwd, *cause; | ||||||
| 	const char			*shell; | 	const char		*shell; | ||||||
| 	u_int				 hlimit, paneidx; | 	u_int			 hlimit, paneidx; | ||||||
| 	int				 size; | 	int			 size, percentage; | ||||||
| 	enum layout_type		 type; | 	enum layout_type	 type; | ||||||
| 	struct layout_cell		*lc; | 	struct layout_cell	*lc; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_pane(ctx, data->target, &s, &wp)) == NULL) | 	if ((wl = cmd_find_pane(ctx, args_get(args, 't'), &s, &wp)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	w = wl->window; | 	w = wl->window; | ||||||
|  |  | ||||||
| @@ -172,9 +74,10 @@ cmd_split_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	environ_copy(&s->environ, &env); | 	environ_copy(&s->environ, &env); | ||||||
| 	server_fill_environ(s, &env); | 	server_fill_environ(s, &env); | ||||||
|  |  | ||||||
| 	cmd = data->cmd; | 	if (args->argc == 0) | ||||||
| 	if (cmd == NULL) |  | ||||||
| 		cmd = options_get_string(&s->options, "default-command"); | 		cmd = options_get_string(&s->options, "default-command"); | ||||||
|  | 	else | ||||||
|  | 		cmd = args->argv[0]; | ||||||
| 	cwd = options_get_string(&s->options, "default-path"); | 	cwd = options_get_string(&s->options, "default-path"); | ||||||
| 	if (*cwd == '\0') { | 	if (*cwd == '\0') { | ||||||
| 		if (ctx->cmdclient != NULL && ctx->cmdclient->cwd != NULL) | 		if (ctx->cmdclient != NULL && ctx->cmdclient->cwd != NULL) | ||||||
| @@ -184,17 +87,28 @@ cmd_split_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	type = LAYOUT_TOPBOTTOM; | 	type = LAYOUT_TOPBOTTOM; | ||||||
| 	if (data->flag_horizontal) | 	if (args_has(args, 'h')) | ||||||
| 		type = LAYOUT_LEFTRIGHT; | 		type = LAYOUT_LEFTRIGHT; | ||||||
|  |  | ||||||
| 	size = -1; | 	size = -1; | ||||||
| 	if (data->size != -1) | 	if (args_has(args, 's')) { | ||||||
| 		size = data->size; | 		size = args_strtonum(args, 's', 0, INT_MAX, &cause); | ||||||
| 	else if (data->percentage != -1) { | 		if (cause != NULL) { | ||||||
|  | 			ctx->error(ctx, "size %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
|  | 	} else if (args_has(args, 'p')) { | ||||||
|  | 		percentage = args_strtonum(args, 'p', 0, INT_MAX, &cause); | ||||||
|  | 		if (cause != NULL) { | ||||||
|  | 			ctx->error(ctx, "percentage %s", cause); | ||||||
|  | 			xfree(cause); | ||||||
|  | 			return (-1); | ||||||
|  | 		} | ||||||
| 		if (type == LAYOUT_TOPBOTTOM) | 		if (type == LAYOUT_TOPBOTTOM) | ||||||
| 			size = (wp->sy * data->percentage) / 100; | 			size = (wp->sy * percentage) / 100; | ||||||
| 		else | 		else | ||||||
| 			size = (wp->sx * data->percentage) / 100; | 			size = (wp->sx * percentage) / 100; | ||||||
| 	} | 	} | ||||||
| 	hlimit = options_get_number(&s->options, "history-limit"); | 	hlimit = options_get_number(&s->options, "history-limit"); | ||||||
|  |  | ||||||
| @@ -214,7 +128,7 @@ cmd_split_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	server_redraw_window(w); | 	server_redraw_window(w); | ||||||
|  |  | ||||||
| 	if (!data->flag_detached) { | 	if (!args_has(args, 'd')) { | ||||||
| 		window_set_active_pane(w, new_wp); | 		window_set_active_pane(w, new_wp); | ||||||
| 		session_select(s, wl->idx); | 		session_select(s, wl->idx); | ||||||
| 		server_redraw_session(s); | 		server_redraw_session(s); | ||||||
| @@ -223,7 +137,7 @@ cmd_split_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	environ_free(&env); | 	environ_free(&env); | ||||||
|  |  | ||||||
| 	if (data->flag_print) { | 	if (args_has(args, 'P')) { | ||||||
| 		paneidx = window_pane_index(wl->window, new_wp); | 		paneidx = window_pane_index(wl->window, new_wp); | ||||||
| 		ctx->print(ctx, "%s:%u.%u", s->name, wl->idx, paneidx); | 		ctx->print(ctx, "%s:%u.%u", s->name, wl->idx, paneidx); | ||||||
| 	} | 	} | ||||||
| @@ -237,43 +151,3 @@ error: | |||||||
| 	xfree(cause); | 	xfree(cause); | ||||||
| 	return (-1); | 	return (-1); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_split_window_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_split_window_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	if (data->cmd != NULL) |  | ||||||
| 		xfree(data->cmd); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_split_window_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_split_window_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->flag_detached) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -d"); |  | ||||||
| 	if (off < len && data->flag_horizontal) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -h"); |  | ||||||
| 	if (off < len && data->flag_print) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -P"); |  | ||||||
| 	if (off < len && data->size > 0) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, " -l %d", data->size); |  | ||||||
| 	if (off < len && data->percentage > 0) { |  | ||||||
| 		off += xsnprintf( |  | ||||||
| 		    buf + off, len - off, " -p %d", data->percentage); |  | ||||||
| 	} |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
| 	if (off < len && data->cmd != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " ", data->cmd); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -28,13 +28,12 @@ int	cmd_start_server_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_start_server_entry = { | const struct cmd_entry cmd_start_server_entry = { | ||||||
| 	"start-server", "start", | 	"start-server", "start", | ||||||
|  | 	"", 0, 0, | ||||||
| 	"", | 	"", | ||||||
| 	CMD_STARTSERVER, "", | 	CMD_STARTSERVER, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_start_server_exec, | 	cmd_start_server_exec | ||||||
| 	NULL, |  | ||||||
| 	NULL |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* ARGSUSED */ | /* ARGSUSED */ | ||||||
|   | |||||||
| @@ -31,22 +31,21 @@ int	cmd_suspend_client_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_suspend_client_entry = { | const struct cmd_entry cmd_suspend_client_entry = { | ||||||
| 	"suspend-client", "suspendc", | 	"suspend-client", "suspendc", | ||||||
|  | 	"t:", 0, 0, | ||||||
| 	CMD_TARGET_CLIENT_USAGE, | 	CMD_TARGET_CLIENT_USAGE, | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_suspend_client_exec, | 	cmd_suspend_client_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_suspend_client_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_suspend_client_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct client		*c; | 	struct client	*c; | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->target)) == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 't'))) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	tty_stop_tty(&c->tty); | 	tty_stop_tty(&c->tty); | ||||||
|   | |||||||
| @@ -26,66 +26,58 @@ | |||||||
|  * Swap two panes. |  * Swap two panes. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_swap_pane_init(struct cmd *, int); | void	cmd_swap_pane_key_binding(struct cmd *, int); | ||||||
| int	cmd_swap_pane_exec(struct cmd *, struct cmd_ctx *); | int	cmd_swap_pane_exec(struct cmd *, struct cmd_ctx *); | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_swap_pane_entry = { | const struct cmd_entry cmd_swap_pane_entry = { | ||||||
| 	"swap-pane", "swapp", | 	"swap-pane", "swapp", | ||||||
|  | 	"dDs:t:U", 0, 0, | ||||||
| 	"[-dDU] " CMD_SRCDST_PANE_USAGE, | 	"[-dDU] " CMD_SRCDST_PANE_USAGE, | ||||||
| 	0, "dDU", | 	0, | ||||||
| 	cmd_swap_pane_init, | 	cmd_swap_pane_key_binding, | ||||||
| 	cmd_srcdst_parse, | 	NULL, | ||||||
| 	cmd_swap_pane_exec, | 	cmd_swap_pane_exec | ||||||
| 	cmd_srcdst_free, |  | ||||||
| 	cmd_srcdst_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_swap_pane_init(struct cmd *self, int key) | cmd_swap_pane_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data; | 	self->args = args_create(0); | ||||||
|  |  | ||||||
| 	cmd_srcdst_init(self, key); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	if (key == '{') | 	if (key == '{') | ||||||
| 		cmd_set_flag(&data->chflags, 'U'); | 		args_set(self->args, 'U', NULL); | ||||||
| 	else if (key == '}') | 	else if (key == '}') | ||||||
| 		cmd_set_flag(&data->chflags, 'D'); | 		args_set(self->args, 'D', NULL); | ||||||
| } | } | ||||||
|  |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_swap_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_swap_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_srcdst_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*src_wl, *dst_wl; | 	struct winlink		*src_wl, *dst_wl; | ||||||
| 	struct window		*src_w, *dst_w; | 	struct window		*src_w, *dst_w; | ||||||
| 	struct window_pane	*tmp_wp, *src_wp, *dst_wp; | 	struct window_pane	*tmp_wp, *src_wp, *dst_wp; | ||||||
| 	struct layout_cell	*src_lc, *dst_lc; | 	struct layout_cell	*src_lc, *dst_lc; | ||||||
| 	u_int			 sx, sy, xoff, yoff; | 	u_int			 sx, sy, xoff, yoff; | ||||||
|  |  | ||||||
| 	if (data == NULL) | 	dst_wl = cmd_find_pane(ctx, args_get(args, 't'), NULL, &dst_wp); | ||||||
| 		return (0); | 	if (dst_wl == NULL) | ||||||
|  |  | ||||||
| 	if ((dst_wl = cmd_find_pane(ctx, data->dst, NULL, &dst_wp)) == NULL) |  | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	dst_w = dst_wl->window; | 	dst_w = dst_wl->window; | ||||||
|  |  | ||||||
| 	if (data->src == NULL) { | 	if (!args_has(args, 's')) { | ||||||
| 		src_w = dst_w; | 		src_w = dst_w; | ||||||
| 		if (cmd_check_flag(data->chflags, 'D')) { | 		if (args_has(self->args, 'D')) { | ||||||
| 			src_wp = TAILQ_NEXT(dst_wp, entry); | 			src_wp = TAILQ_NEXT(dst_wp, entry); | ||||||
| 			if (src_wp == NULL) | 			if (src_wp == NULL) | ||||||
| 				src_wp = TAILQ_FIRST(&dst_w->panes); | 				src_wp = TAILQ_FIRST(&dst_w->panes); | ||||||
| 		} else if (cmd_check_flag(data->chflags, 'U')) { | 		} else if (args_has(self->args, 'U')) { | ||||||
| 			src_wp = TAILQ_PREV(dst_wp, window_panes, entry); | 			src_wp = TAILQ_PREV(dst_wp, window_panes, entry); | ||||||
| 			if (src_wp == NULL) | 			if (src_wp == NULL) | ||||||
| 				src_wp = TAILQ_LAST(&dst_w->panes, window_panes); | 				src_wp = TAILQ_LAST(&dst_w->panes, window_panes); | ||||||
| 		} else | 		} else | ||||||
| 			return (0); | 			return (0); | ||||||
| 	} else { | 	} else { | ||||||
| 		src_wl = cmd_find_pane(ctx, data->src, NULL, &src_wp); | 		src_wl = cmd_find_pane(ctx, args_get(args, 's'), NULL, &src_wp); | ||||||
| 		if (src_wl == NULL) | 		if (src_wl == NULL) | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		src_w = src_wl->window; | 		src_w = src_wl->window; | ||||||
| @@ -121,7 +113,7 @@ cmd_swap_pane_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	dst_wp->xoff = xoff; dst_wp->yoff = yoff; | 	dst_wp->xoff = xoff; dst_wp->yoff = yoff; | ||||||
| 	window_pane_resize(dst_wp, sx, sy); | 	window_pane_resize(dst_wp, sx, sy); | ||||||
|  |  | ||||||
| 	if (!cmd_check_flag(data->chflags, 'd')) { | 	if (!args_has(self->args, 'd')) { | ||||||
| 		if (src_w != dst_w) { | 		if (src_w != dst_w) { | ||||||
| 			window_set_active_pane(src_w, dst_wp); | 			window_set_active_pane(src_w, dst_wp); | ||||||
| 			window_set_active_pane(dst_w, src_wp); | 			window_set_active_pane(dst_w, src_wp); | ||||||
|   | |||||||
| @@ -30,27 +30,29 @@ int	cmd_swap_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_swap_window_entry = { | const struct cmd_entry cmd_swap_window_entry = { | ||||||
| 	"swap-window", "swapw", | 	"swap-window", "swapw", | ||||||
|  | 	"ds:t:", 0, 0, | ||||||
| 	"[-d] " CMD_SRCDST_WINDOW_USAGE, | 	"[-d] " CMD_SRCDST_WINDOW_USAGE, | ||||||
| 	0, "d", | 	0, | ||||||
| 	cmd_srcdst_init, | 	NULL, | ||||||
| 	cmd_srcdst_parse, | 	NULL, | ||||||
| 	cmd_swap_window_exec, | 	cmd_swap_window_exec | ||||||
| 	cmd_srcdst_free, |  | ||||||
| 	cmd_srcdst_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_swap_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_swap_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_srcdst_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
|  | 	const char		*target_src, *target_dst; | ||||||
| 	struct session		*src, *dst; | 	struct session		*src, *dst; | ||||||
| 	struct session_group	*sg_src, *sg_dst; | 	struct session_group	*sg_src, *sg_dst; | ||||||
| 	struct winlink		*wl_src, *wl_dst; | 	struct winlink		*wl_src, *wl_dst; | ||||||
| 	struct window		*w; | 	struct window		*w; | ||||||
|  |  | ||||||
| 	if ((wl_src = cmd_find_window(ctx, data->src, &src)) == NULL) | 	target_src = args_get(args, 's'); | ||||||
|  | 	if ((wl_src = cmd_find_window(ctx, target_src, &src)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	if ((wl_dst = cmd_find_window(ctx, data->dst, &dst)) == NULL) | 	target_dst = args_get(args, 't'); | ||||||
|  | 	if ((wl_dst = cmd_find_window(ctx, target_dst, &dst)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	sg_src = session_group_find(src); | 	sg_src = session_group_find(src); | ||||||
| @@ -68,7 +70,7 @@ cmd_swap_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	wl_dst->window = wl_src->window; | 	wl_dst->window = wl_src->window; | ||||||
| 	wl_src->window = w; | 	wl_src->window = w; | ||||||
|  |  | ||||||
| 	if (!cmd_check_flag(data->chflags, 'd')) { | 	if (!args_has(self->args, 'd')) { | ||||||
| 		session_select(dst, wl_dst->idx); | 		session_select(dst, wl_dst->idx); | ||||||
| 		if (src != dst) | 		if (src != dst) | ||||||
| 			session_select(src, wl_src->idx); | 			session_select(src, wl_src->idx); | ||||||
|   | |||||||
| @@ -27,138 +27,58 @@ | |||||||
|  * Switch client to a different session. |  * Switch client to a different session. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| void	cmd_switch_client_init(struct cmd *, int); | void	cmd_switch_client_key_binding(struct cmd *, int); | ||||||
| int	cmd_switch_client_parse(struct cmd *, int, char **, char **); |  | ||||||
| int	cmd_switch_client_exec(struct cmd *, struct cmd_ctx *); | int	cmd_switch_client_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_switch_client_free(struct cmd *); |  | ||||||
| size_t	cmd_switch_client_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| struct cmd_switch_client_data { |  | ||||||
| 	char	*name; |  | ||||||
| 	char	*target; |  | ||||||
| 	int      flag_last; |  | ||||||
| 	int	 flag_next; |  | ||||||
| 	int	 flag_previous; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_switch_client_entry = { | const struct cmd_entry cmd_switch_client_entry = { | ||||||
| 	"switch-client", "switchc", | 	"switch-client", "switchc", | ||||||
|  | 	"lc:npt:", 0, 0, | ||||||
| 	"[-lnp] [-c target-client] [-t target-session]", | 	"[-lnp] [-c target-client] [-t target-session]", | ||||||
| 	0, "", | 	0, | ||||||
| 	cmd_switch_client_init, | 	cmd_switch_client_key_binding, | ||||||
| 	cmd_switch_client_parse, | 	NULL, | ||||||
| 	cmd_switch_client_exec, | 	cmd_switch_client_exec | ||||||
| 	cmd_switch_client_free, |  | ||||||
| 	cmd_switch_client_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| void | void | ||||||
| cmd_switch_client_init(struct cmd *self, int key) | cmd_switch_client_key_binding(struct cmd *self, int key) | ||||||
| { | { | ||||||
| 	struct cmd_switch_client_data	*data; | 	self->args = args_create(0); | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->name = NULL; |  | ||||||
| 	data->target = NULL; |  | ||||||
| 	data->flag_last = 0; |  | ||||||
| 	data->flag_next = 0; |  | ||||||
| 	data->flag_previous = 0; |  | ||||||
|  |  | ||||||
| 	switch (key) { | 	switch (key) { | ||||||
| 	case '(': | 	case '(': | ||||||
| 		data->flag_previous = 1; | 		args_set(self->args, 'p', NULL); | ||||||
| 		break; | 		break; | ||||||
| 	case ')': | 	case ')': | ||||||
| 		data->flag_next = 1; | 		args_set(self->args, 'n', NULL); | ||||||
| 		break; | 		break; | ||||||
| 	case 'L': | 	case 'L': | ||||||
| 		data->flag_last = 1; | 		args_set(self->args, 'l', NULL); | ||||||
| 		break; | 		break; | ||||||
| 	} | 	} | ||||||
| } | } | ||||||
|  |  | ||||||
| int |  | ||||||
| cmd_switch_client_parse(struct cmd *self, int argc, char **argv, char **cause) |  | ||||||
| { |  | ||||||
| 	struct cmd_switch_client_data	*data; |  | ||||||
| 	int				 opt; |  | ||||||
|  |  | ||||||
| 	self->entry->init(self, KEYC_NONE); |  | ||||||
| 	data = self->data; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "c:lnpt:")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'c': |  | ||||||
| 			if (data->name == NULL) |  | ||||||
| 				data->name = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		case 'l': |  | ||||||
| 			if (data->flag_next || data->flag_previous || |  | ||||||
| 			    data->target != NULL) |  | ||||||
| 				goto usage; |  | ||||||
| 			data->flag_last = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'n': |  | ||||||
| 			if (data->flag_previous || data->flag_last || |  | ||||||
| 			    data->target != NULL) |  | ||||||
| 				goto usage; |  | ||||||
| 			data->flag_next = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'p': |  | ||||||
| 			if (data->flag_next || data->flag_last || |  | ||||||
| 			    data->target != NULL) |  | ||||||
| 				goto usage; |  | ||||||
| 			data->flag_next = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->flag_next || data->flag_previous) |  | ||||||
| 				goto usage; |  | ||||||
| 			if (data->target == NULL) |  | ||||||
| 				data->target = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (argc != 0) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	return (0); |  | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| 	self->entry->free(self); |  | ||||||
| 	return (-1); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_switch_client_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_switch_client_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_switch_client_data	*data = self->data; | 	struct args	*args = self->args; | ||||||
| 	struct client			*c; | 	struct client	*c; | ||||||
| 	struct session			*s; | 	struct session	*s; | ||||||
|  |  | ||||||
| 	if (data == NULL) | 	if ((c = cmd_find_client(ctx, args_get(args, 'c'))) == NULL) | ||||||
| 		return (0); |  | ||||||
|  |  | ||||||
| 	if ((c = cmd_find_client(ctx, data->name)) == NULL) |  | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| 	s = NULL; | 	s = NULL; | ||||||
| 	if (data->flag_next) { | 	if (args_has(args, 'n')) { | ||||||
| 		if ((s = session_next_session(c->session)) == NULL) { | 		if ((s = session_next_session(c->session)) == NULL) { | ||||||
| 			ctx->error(ctx, "can't find next session"); | 			ctx->error(ctx, "can't find next session"); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} else if (data->flag_previous) { | 	} else if (args_has(args, 'p')) { | ||||||
| 		if ((s = session_previous_session(c->session)) == NULL) { | 		if ((s = session_previous_session(c->session)) == NULL) { | ||||||
| 			ctx->error(ctx, "can't find previous session"); | 			ctx->error(ctx, "can't find previous session"); | ||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} else if (data->flag_last) { | 	} else if (args_has(args, 'l')) { | ||||||
| 		if (c->last_session != NULL && session_alive(c->last_session)) | 		if (c->last_session != NULL && session_alive(c->last_session)) | ||||||
| 			s = c->last_session; | 			s = c->last_session; | ||||||
| 		if (s == NULL) { | 		if (s == NULL) { | ||||||
| @@ -166,7 +86,7 @@ cmd_switch_client_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 			return (-1); | 			return (-1); | ||||||
| 		} | 		} | ||||||
| 	} else | 	} else | ||||||
| 		s = cmd_find_session(ctx, data->target); | 		s = cmd_find_session(ctx, args_get(args, 't')); | ||||||
| 	if (s == NULL) | 	if (s == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
|  |  | ||||||
| @@ -181,37 +101,3 @@ cmd_switch_client_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_switch_client_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_switch_client_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->name != NULL) |  | ||||||
| 		xfree(data->name); |  | ||||||
| 	if (data->target != NULL) |  | ||||||
| 		xfree(data->target); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|  |  | ||||||
| size_t |  | ||||||
| cmd_switch_client_print(struct cmd *self, char *buf, size_t len) |  | ||||||
| { |  | ||||||
| 	struct cmd_switch_client_data	*data = self->data; |  | ||||||
| 	size_t				 off = 0; |  | ||||||
|  |  | ||||||
| 	off += xsnprintf(buf, len, "%s", self->entry->name); |  | ||||||
| 	if (data == NULL) |  | ||||||
| 		return (off); |  | ||||||
| 	if (off < len && data->flag_last) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, "%s", " -l"); |  | ||||||
| 	if (off < len && data->flag_next) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, "%s", " -n"); |  | ||||||
| 	if (off < len && data->flag_previous) |  | ||||||
| 		off += xsnprintf(buf + off, len - off, "%s", " -p"); |  | ||||||
| 	if (off < len && data->name != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -c ", data->name); |  | ||||||
| 	if (off < len && data->target != NULL) |  | ||||||
| 		off += cmd_prarg(buf + off, len - off, " -t ", data->target); |  | ||||||
| 	return (off); |  | ||||||
| } |  | ||||||
|   | |||||||
							
								
								
									
										128
									
								
								cmd-unbind-key.c
									
									
									
									
									
								
							
							
						
						
									
										128
									
								
								cmd-unbind-key.c
									
									
									
									
									
								
							| @@ -24,140 +24,80 @@ | |||||||
|  * Unbind key from command. |  * Unbind key from command. | ||||||
|  */ |  */ | ||||||
|  |  | ||||||
| int	cmd_unbind_key_parse(struct cmd *, int, char **, char **); | int	cmd_unbind_key_check(struct args *); | ||||||
| int	cmd_unbind_key_exec(struct cmd *, struct cmd_ctx *); | int	cmd_unbind_key_exec(struct cmd *, struct cmd_ctx *); | ||||||
| void	cmd_unbind_key_free(struct cmd *); |  | ||||||
|  |  | ||||||
| int	cmd_unbind_key_table(struct cmd *, struct cmd_ctx *); | int	cmd_unbind_key_table(struct cmd *, struct cmd_ctx *, int); | ||||||
|  |  | ||||||
| struct cmd_unbind_key_data { |  | ||||||
| 	int	key; |  | ||||||
|  |  | ||||||
| 	int	flag_all; |  | ||||||
| 	int	command_key; |  | ||||||
| 	char   *tablename; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| const struct cmd_entry cmd_unbind_key_entry = { | const struct cmd_entry cmd_unbind_key_entry = { | ||||||
| 	"unbind-key", "unbind", | 	"unbind-key", "unbind", | ||||||
|  | 	"acnt:", 1, 1, | ||||||
| 	"[-acn] [-t key-table] key", | 	"[-acn] [-t key-table] key", | ||||||
| 	0, "", | 	0, | ||||||
| 	NULL, | 	NULL, | ||||||
| 	cmd_unbind_key_parse, | 	cmd_unbind_key_check, | ||||||
| 	cmd_unbind_key_exec, | 	cmd_unbind_key_exec | ||||||
| 	cmd_unbind_key_free, |  | ||||||
| 	NULL |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_unbind_key_parse(struct cmd *self, int argc, char **argv, char **cause) | cmd_unbind_key_check(struct args *args) | ||||||
| { | { | ||||||
| 	struct cmd_unbind_key_data	*data; | 	if (args_has(args, 'a') && (args->argc != 0 || args_has(args, 't'))) | ||||||
| 	int				 opt, no_prefix = 0; | 		return (-1); | ||||||
|  |  | ||||||
| 	self->data = data = xmalloc(sizeof *data); |  | ||||||
| 	data->flag_all = 0; |  | ||||||
| 	data->command_key = 0; |  | ||||||
| 	data->tablename = NULL; |  | ||||||
|  |  | ||||||
| 	while ((opt = getopt(argc, argv, "acnt:")) != -1) { |  | ||||||
| 		switch (opt) { |  | ||||||
| 		case 'a': |  | ||||||
| 			data->flag_all = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'c': |  | ||||||
| 			data->command_key = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 'n': |  | ||||||
| 			no_prefix = 1; |  | ||||||
| 			break; |  | ||||||
| 		case 't': |  | ||||||
| 			if (data->tablename == NULL) |  | ||||||
| 				data->tablename = xstrdup(optarg); |  | ||||||
| 			break; |  | ||||||
| 		default: |  | ||||||
| 			goto usage; |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	argc -= optind; |  | ||||||
| 	argv += optind; |  | ||||||
| 	if (data->flag_all && (argc != 0 || data->tablename)) |  | ||||||
| 		goto usage; |  | ||||||
| 	if (!data->flag_all && argc != 1) |  | ||||||
| 		goto usage; |  | ||||||
|  |  | ||||||
| 	if (!data->flag_all) { |  | ||||||
| 		data->key = key_string_lookup_string(argv[0]); |  | ||||||
| 		if (data->key == KEYC_NONE) { |  | ||||||
| 			xasprintf(cause, "unknown key: %s", argv[0]); |  | ||||||
| 			goto error; |  | ||||||
| 		} |  | ||||||
| 		if (!no_prefix) |  | ||||||
| 			data->key |= KEYC_PREFIX; |  | ||||||
| 	} |  | ||||||
|  |  | ||||||
| 	return (0); | 	return (0); | ||||||
|  |  | ||||||
| usage: |  | ||||||
| 	xasprintf(cause, "usage: %s %s", self->entry->name, self->entry->usage); |  | ||||||
|  |  | ||||||
| error: |  | ||||||
| 	xfree(data); |  | ||||||
| 	return (-1); |  | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_unbind_key_exec(struct cmd *self, unused struct cmd_ctx *ctx) | cmd_unbind_key_exec(struct cmd *self, unused struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_unbind_key_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct key_binding		*bd; | 	struct key_binding	*bd; | ||||||
|  | 	int			 key; | ||||||
|  |  | ||||||
| 	if (data == NULL) | 	if (args_has(args, 'a')) { | ||||||
| 		return (0); |  | ||||||
| 	if (data->flag_all) { |  | ||||||
| 		while (!SPLAY_EMPTY(&key_bindings)) { | 		while (!SPLAY_EMPTY(&key_bindings)) { | ||||||
| 			bd = SPLAY_ROOT(&key_bindings); | 			bd = SPLAY_ROOT(&key_bindings); | ||||||
| 			SPLAY_REMOVE(key_bindings, &key_bindings, bd); | 			SPLAY_REMOVE(key_bindings, &key_bindings, bd); | ||||||
| 			cmd_list_free(bd->cmdlist); | 			cmd_list_free(bd->cmdlist); | ||||||
| 			xfree(bd); | 			xfree(bd); | ||||||
| 		} | 		} | ||||||
| 	} else { | 		return (0); | ||||||
| 		if (data->tablename != NULL) |  | ||||||
| 			return (cmd_unbind_key_table(self, ctx)); |  | ||||||
|  |  | ||||||
| 		key_bindings_remove(data->key); |  | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
|  | 	key = key_string_lookup_string(args->argv[0]); | ||||||
|  | 	if (key == KEYC_NONE) { | ||||||
|  | 		ctx->error(ctx, "unknown key: %s", args->argv[0]); | ||||||
|  | 		return (-1); | ||||||
|  | 	} | ||||||
|  |  | ||||||
|  | 	if (args_has(args, 't')) | ||||||
|  | 		return (cmd_unbind_key_table(self, ctx, key)); | ||||||
|  |  | ||||||
|  | 	if (!args_has(args, 'n')) | ||||||
|  | 		key |= KEYC_PREFIX; | ||||||
|  | 	key_bindings_remove(key); | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_unbind_key_table(struct cmd *self, struct cmd_ctx *ctx) | cmd_unbind_key_table(struct cmd *self, struct cmd_ctx *ctx, int key) | ||||||
| { | { | ||||||
| 	struct cmd_unbind_key_data	*data = self->data; | 	struct args			*args = self->args; | ||||||
|  | 	const char			*tablename; | ||||||
| 	const struct mode_key_table	*mtab; | 	const struct mode_key_table	*mtab; | ||||||
| 	struct mode_key_binding		*mbind, mtmp; | 	struct mode_key_binding		*mbind, mtmp; | ||||||
|  |  | ||||||
| 	if ((mtab = mode_key_findtable(data->tablename)) == NULL) { | 	tablename = args_get(args, 't'); | ||||||
| 		ctx->error(ctx, "unknown key table: %s", data->tablename); | 	if ((mtab = mode_key_findtable(tablename)) == NULL) { | ||||||
|  | 		ctx->error(ctx, "unknown key table: %s", tablename); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	mtmp.key = data->key & ~KEYC_PREFIX; | 	mtmp.key = key; | ||||||
| 	mtmp.mode = data->command_key ? 1 : 0; | 	mtmp.mode = !!args_has(args, 'c'); | ||||||
| 	if ((mbind = SPLAY_FIND(mode_key_tree, mtab->tree, &mtmp)) != NULL) { | 	if ((mbind = SPLAY_FIND(mode_key_tree, mtab->tree, &mtmp)) != NULL) { | ||||||
| 		SPLAY_REMOVE(mode_key_tree, mtab->tree, mbind); | 		SPLAY_REMOVE(mode_key_tree, mtab->tree, mbind); | ||||||
| 		xfree(mbind); | 		xfree(mbind); | ||||||
| 	} | 	} | ||||||
| 	return (0); | 	return (0); | ||||||
| } | } | ||||||
|  |  | ||||||
| void |  | ||||||
| cmd_unbind_key_free(struct cmd *self) |  | ||||||
| { |  | ||||||
| 	struct cmd_unbind_key_data	*data = self->data; |  | ||||||
|  |  | ||||||
| 	if (data->tablename != NULL) |  | ||||||
| 		xfree(data->tablename); |  | ||||||
| 	xfree(data); |  | ||||||
| } |  | ||||||
|   | |||||||
| @@ -28,26 +28,25 @@ int	cmd_unlink_window_exec(struct cmd *, struct cmd_ctx *); | |||||||
|  |  | ||||||
| const struct cmd_entry cmd_unlink_window_entry = { | const struct cmd_entry cmd_unlink_window_entry = { | ||||||
| 	"unlink-window", "unlinkw", | 	"unlink-window", "unlinkw", | ||||||
|  | 	"kt:", 0, 0, | ||||||
| 	"[-k] " CMD_TARGET_WINDOW_USAGE, | 	"[-k] " CMD_TARGET_WINDOW_USAGE, | ||||||
| 	0, "k", | 	0, | ||||||
| 	cmd_target_init, | 	NULL, | ||||||
| 	cmd_target_parse, | 	NULL, | ||||||
| 	cmd_unlink_window_exec, | 	cmd_unlink_window_exec | ||||||
| 	cmd_target_free, |  | ||||||
| 	cmd_target_print |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| int | int | ||||||
| cmd_unlink_window_exec(struct cmd *self, struct cmd_ctx *ctx) | cmd_unlink_window_exec(struct cmd *self, struct cmd_ctx *ctx) | ||||||
| { | { | ||||||
| 	struct cmd_target_data	*data = self->data; | 	struct args		*args = self->args; | ||||||
| 	struct winlink		*wl; | 	struct winlink		*wl; | ||||||
| 	struct window		*w; | 	struct window		*w; | ||||||
| 	struct session		*s, *s2; | 	struct session		*s, *s2; | ||||||
| 	struct session_group	*sg; | 	struct session_group	*sg; | ||||||
| 	u_int			 references; | 	u_int			 references; | ||||||
|  |  | ||||||
| 	if ((wl = cmd_find_window(ctx, data->target, &s)) == NULL) | 	if ((wl = cmd_find_window(ctx, args_get(args, 't'), &s)) == NULL) | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	w = wl->window; | 	w = wl->window; | ||||||
|  |  | ||||||
| @@ -59,7 +58,7 @@ cmd_unlink_window_exec(struct cmd *self, struct cmd_ctx *ctx) | |||||||
| 	} else | 	} else | ||||||
| 		references = 1; | 		references = 1; | ||||||
|  |  | ||||||
| 	if (!cmd_check_flag(data->chflags, 'k') && w->references == references) { | 	if (!args_has(self->args, 'k') && w->references == references) { | ||||||
| 		ctx->error(ctx, "window is only linked to one session"); | 		ctx->error(ctx, "window is only linked to one session"); | ||||||
| 		return (-1); | 		return (-1); | ||||||
| 	} | 	} | ||||||
|   | |||||||
							
								
								
									
										58
									
								
								cmd.c
									
									
									
									
									
								
							
							
						
						
									
										58
									
								
								cmd.c
									
									
									
									
									
								
							| @@ -167,7 +167,7 @@ cmd_unpack_argv(char *buf, size_t len, int argc, char ***argv) | |||||||
| } | } | ||||||
|  |  | ||||||
| char ** | char ** | ||||||
| cmd_copy_argv(int argc, char **argv) | cmd_copy_argv(int argc, char *const *argv) | ||||||
| { | { | ||||||
| 	char	**new_argv; | 	char	**new_argv; | ||||||
| 	int	  i; | 	int	  i; | ||||||
| @@ -201,8 +201,9 @@ cmd_parse(int argc, char **argv, char **cause) | |||||||
| { | { | ||||||
| 	const struct cmd_entry **entryp, *entry; | 	const struct cmd_entry **entryp, *entry; | ||||||
| 	struct cmd		*cmd; | 	struct cmd		*cmd; | ||||||
|  | 	struct args		*args; | ||||||
| 	char			 s[BUFSIZ]; | 	char			 s[BUFSIZ]; | ||||||
| 	int			 opt, ambiguous = 0; | 	int			 ambiguous = 0; | ||||||
|  |  | ||||||
| 	*cause = NULL; | 	*cause = NULL; | ||||||
| 	if (argc == 0) { | 	if (argc == 0) { | ||||||
| @@ -236,30 +237,19 @@ cmd_parse(int argc, char **argv, char **cause) | |||||||
| 		return (NULL); | 		return (NULL); | ||||||
| 	} | 	} | ||||||
|  |  | ||||||
| 	optreset = 1; | 	args = args_parse(entry->args_template, argc, argv); | ||||||
| 	optind = 1; | 	if (args == NULL) | ||||||
| 	if (entry->parse == NULL) { | 		goto usage; | ||||||
| 		while ((opt = getopt(argc, argv, "")) != -1) { | 	if (entry->args_lower != -1 && args->argc < entry->args_lower) | ||||||
| 			switch (opt) { | 		goto usage; | ||||||
| 			default: | 	if (entry->args_upper != -1 && args->argc > entry->args_upper) | ||||||
| 				goto usage; | 		goto usage; | ||||||
| 			} | 	if (entry->check != NULL && entry->check(args) != 0) | ||||||
| 		} | 		goto usage; | ||||||
| 		argc -= optind; |  | ||||||
| 		argv += optind; |  | ||||||
| 		if (argc != 0) |  | ||||||
| 			goto usage; |  | ||||||
| 	} |  | ||||||
|  |  | ||||||
| 	cmd = xmalloc(sizeof *cmd); | 	cmd = xmalloc(sizeof *cmd); | ||||||
| 	cmd->entry = entry; | 	cmd->entry = entry; | ||||||
| 	cmd->data = NULL; | 	cmd->args = args; | ||||||
| 	if (entry->parse != NULL) { |  | ||||||
| 		if (entry->parse(cmd, argc, argv, cause) != 0) { |  | ||||||
| 			xfree(cmd); |  | ||||||
| 			return (NULL); |  | ||||||
| 		} |  | ||||||
| 	} |  | ||||||
| 	return (cmd); | 	return (cmd); | ||||||
|  |  | ||||||
| ambiguous: | ambiguous: | ||||||
| @@ -277,6 +267,8 @@ ambiguous: | |||||||
| 	return (NULL); | 	return (NULL); | ||||||
|  |  | ||||||
| usage: | usage: | ||||||
|  | 	if (args != NULL) | ||||||
|  | 		args_free(args); | ||||||
| 	xasprintf(cause, "usage: %s %s", entry->name, entry->usage); | 	xasprintf(cause, "usage: %s %s", entry->name, entry->usage); | ||||||
| 	return (NULL); | 	return (NULL); | ||||||
| } | } | ||||||
| @@ -290,17 +282,27 @@ cmd_exec(struct cmd *cmd, struct cmd_ctx *ctx) | |||||||
| void | void | ||||||
| cmd_free(struct cmd *cmd) | cmd_free(struct cmd *cmd) | ||||||
| { | { | ||||||
| 	if (cmd->data != NULL && cmd->entry->free != NULL) | 	if (cmd->args != NULL) | ||||||
| 		cmd->entry->free(cmd); | 		args_free(cmd->args); | ||||||
| 	xfree(cmd); | 	xfree(cmd); | ||||||
| } | } | ||||||
|  |  | ||||||
| size_t | size_t | ||||||
| cmd_print(struct cmd *cmd, char *buf, size_t len) | cmd_print(struct cmd *cmd, char *buf, size_t len) | ||||||
| { | { | ||||||
| 	if (cmd->entry->print == NULL) | 	size_t	off, used; | ||||||
| 		return (xsnprintf(buf, len, "%s", cmd->entry->name)); |  | ||||||
| 	return (cmd->entry->print(cmd, buf, len)); | 	off = xsnprintf(buf, len, "%s ", cmd->entry->name); | ||||||
|  | 	if (off < len) { | ||||||
|  | 		used = args_print(cmd->args, buf + off, len - off); | ||||||
|  | 		if (used == 0) | ||||||
|  | 			buf[off - 1] = '\0'; | ||||||
|  | 		else { | ||||||
|  | 			off += used; | ||||||
|  | 			buf[off] = '\0'; | ||||||
|  | 		} | ||||||
|  | 	} | ||||||
|  | 	return (off); | ||||||
| } | } | ||||||
|  |  | ||||||
| /* | /* | ||||||
|   | |||||||
| @@ -187,9 +187,10 @@ key_bindings_init(void) | |||||||
|  |  | ||||||
| 		cmd = xmalloc(sizeof *cmd); | 		cmd = xmalloc(sizeof *cmd); | ||||||
| 		cmd->entry = table[i].entry; | 		cmd->entry = table[i].entry; | ||||||
| 		cmd->data = NULL; | 		if (cmd->entry->key_binding != NULL) | ||||||
| 		if (cmd->entry->init != NULL) | 			cmd->entry->key_binding(cmd, table[i].key); | ||||||
| 			cmd->entry->init(cmd, table[i].key); | 		else | ||||||
|  | 			cmd->args = args_create(0); | ||||||
| 		TAILQ_INSERT_HEAD(&cmdlist->list, cmd, qentry); | 		TAILQ_INSERT_HEAD(&cmdlist->list, cmd, qentry); | ||||||
|  |  | ||||||
| 		key_bindings_add( | 		key_bindings_add( | ||||||
|   | |||||||
							
								
								
									
										117
									
								
								tmux.h
									
									
									
									
									
								
							
							
						
						
									
										117
									
								
								tmux.h
									
									
									
									
									
								
							| @@ -1168,6 +1168,15 @@ struct client { | |||||||
| }; | }; | ||||||
| ARRAY_DECL(clients, struct client *); | ARRAY_DECL(clients, struct client *); | ||||||
|  |  | ||||||
|  | /* Parsed arguments. */ | ||||||
|  | struct args { | ||||||
|  | 	bitstr_t	*flags; | ||||||
|  | 	char		*values[SCHAR_MAX]; /* XXX This is awfully big. */ | ||||||
|  |  | ||||||
|  | 	int		 argc; | ||||||
|  | 	char	       **argv; | ||||||
|  | }; | ||||||
|  |  | ||||||
| /* Key/command line command. */ | /* Key/command line command. */ | ||||||
| struct cmd_ctx { | struct cmd_ctx { | ||||||
| 	/* | 	/* | ||||||
| @@ -1198,67 +1207,35 @@ struct cmd_ctx { | |||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd { | struct cmd { | ||||||
| 	const struct cmd_entry *entry; | 	const struct cmd_entry	*entry; | ||||||
| 	void		*data; | 	struct args		*args; | ||||||
|  |  | ||||||
| 	TAILQ_ENTRY(cmd) qentry; | 	TAILQ_ENTRY(cmd)	 qentry; | ||||||
| }; | }; | ||||||
| struct cmd_list { | struct cmd_list { | ||||||
| 	int		 references; | 	int		 	 references; | ||||||
| 	TAILQ_HEAD(, cmd) list; | 	TAILQ_HEAD(, cmd) 	 list; | ||||||
| }; | }; | ||||||
|  |  | ||||||
| struct cmd_entry { | struct cmd_entry { | ||||||
| 	const char	*name; | 	const char	*name; | ||||||
| 	const char	*alias; | 	const char	*alias; | ||||||
|  |  | ||||||
|  | 	const char	*args_template; | ||||||
|  | 	int		 args_lower; | ||||||
|  | 	int		 args_upper; | ||||||
|  |  | ||||||
| 	const char	*usage; | 	const char	*usage; | ||||||
|  |  | ||||||
| #define CMD_STARTSERVER 0x1 | #define CMD_STARTSERVER 0x1 | ||||||
| #define CMD_CANTNEST 0x2 | #define CMD_CANTNEST 0x2 | ||||||
| #define CMD_SENDENVIRON 0x4 | #define CMD_SENDENVIRON 0x4 | ||||||
| #define CMD_ARG1 0x8 | #define CMD_READONLY 0x8 | ||||||
| #define CMD_ARG01 0x10 |  | ||||||
| #define CMD_ARG2 0x20 |  | ||||||
| #define CMD_ARG12 0x40 |  | ||||||
| #define CMD_READONLY 0x80 |  | ||||||
| 	int		 flags; | 	int		 flags; | ||||||
|  |  | ||||||
| 	const char	*chflags; | 	void		 (*key_binding)(struct cmd *, int); | ||||||
|  | 	int		 (*check)(struct args *); | ||||||
| 	void		 (*init)(struct cmd *, int); |  | ||||||
| 	int		 (*parse)(struct cmd *, int, char **, char **); |  | ||||||
| 	int		 (*exec)(struct cmd *, struct cmd_ctx *); | 	int		 (*exec)(struct cmd *, struct cmd_ctx *); | ||||||
| 	void		 (*free)(struct cmd *); |  | ||||||
| 	size_t		 (*print)(struct cmd *, char *, size_t); |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| /* Generic command data. */ |  | ||||||
| struct cmd_target_data { |  | ||||||
| 	uint64_t chflags; |  | ||||||
|  |  | ||||||
| 	char	*target; |  | ||||||
|  |  | ||||||
| 	char	*arg; |  | ||||||
| 	char	*arg2; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| struct cmd_srcdst_data { |  | ||||||
| 	uint64_t chflags; |  | ||||||
|  |  | ||||||
| 	char	*src; |  | ||||||
| 	char	*dst; |  | ||||||
|  |  | ||||||
| 	char	*arg; |  | ||||||
| 	char	*arg2; |  | ||||||
| }; |  | ||||||
|  |  | ||||||
| struct cmd_buffer_data { |  | ||||||
| 	uint64_t chflags; |  | ||||||
|  |  | ||||||
| 	int	 buffer; |  | ||||||
|  |  | ||||||
| 	char	*arg; |  | ||||||
| 	char	*arg2; |  | ||||||
| }; | }; | ||||||
|  |  | ||||||
| /* Key binding. */ | /* Key binding. */ | ||||||
| @@ -1301,6 +1278,17 @@ struct options_table_entry { | |||||||
| /* List of configuration causes. */ | /* List of configuration causes. */ | ||||||
| ARRAY_DECL(causelist, char *); | ARRAY_DECL(causelist, char *); | ||||||
|  |  | ||||||
|  | /* Common command usages. */ | ||||||
|  | #define CMD_TARGET_PANE_USAGE "[-t target-pane]" | ||||||
|  | #define CMD_TARGET_WINDOW_USAGE "[-t target-window]" | ||||||
|  | #define CMD_TARGET_SESSION_USAGE "[-t target-session]" | ||||||
|  | #define CMD_TARGET_CLIENT_USAGE "[-t target-client]" | ||||||
|  | #define CMD_SRCDST_PANE_USAGE "[-s src-pane] [-t dst-pane]" | ||||||
|  | #define CMD_SRCDST_WINDOW_USAGE "[-s src-window] [-t dst-window]" | ||||||
|  | #define CMD_SRCDST_SESSION_USAGE "[-s src-session] [-t dst-session]" | ||||||
|  | #define CMD_SRCDST_CLIENT_USAGE "[-s src-client] [-t dst-client]" | ||||||
|  | #define CMD_BUFFER_USAGE "[-b buffer-index]" | ||||||
|  |  | ||||||
| /* tmux.c */ | /* tmux.c */ | ||||||
| extern struct options global_options; | extern struct options global_options; | ||||||
| extern struct options global_s_options; | extern struct options global_s_options; | ||||||
| @@ -1479,10 +1467,21 @@ char		*paste_print(struct paste_buffer *, size_t); | |||||||
| extern const char clock_table[14][5][5]; | extern const char clock_table[14][5][5]; | ||||||
| void		 clock_draw(struct screen_write_ctx *, int, int); | void		 clock_draw(struct screen_write_ctx *, int, int); | ||||||
|  |  | ||||||
|  | /* arguments.c */ | ||||||
|  | struct args	*args_create(int, ...); | ||||||
|  | struct args	*args_parse(const char *, int, char **); | ||||||
|  | void		 args_free(struct args *); | ||||||
|  | size_t		 args_print(struct args *, char *, size_t); | ||||||
|  | int		 args_has(struct args *, u_char); | ||||||
|  | void		 args_set(struct args *, u_char, const char *); | ||||||
|  | const char	*args_get(struct args *, u_char); | ||||||
|  | long long	 args_strtonum( | ||||||
|  | 		    struct args *, u_char, long long, long long, char **); | ||||||
|  |  | ||||||
| /* cmd.c */ | /* cmd.c */ | ||||||
| int		 cmd_pack_argv(int, char **, char *, size_t); | int		 cmd_pack_argv(int, char **, char *, size_t); | ||||||
| int		 cmd_unpack_argv(char *, size_t, int, char ***); | int		 cmd_unpack_argv(char *, size_t, int, char ***); | ||||||
| char	       **cmd_copy_argv(int, char **); | char	       **cmd_copy_argv(int, char *const *); | ||||||
| void		 cmd_free_argv(int, char **); | void		 cmd_free_argv(int, char **); | ||||||
| struct cmd	*cmd_parse(int, char **, char **); | struct cmd	*cmd_parse(int, char **, char **); | ||||||
| int		 cmd_exec(struct cmd *, struct cmd_ctx *); | int		 cmd_exec(struct cmd *, struct cmd_ctx *); | ||||||
| @@ -1592,32 +1591,6 @@ size_t		 cmd_list_print(struct cmd_list *, char *, size_t); | |||||||
| /* cmd-string.c */ | /* cmd-string.c */ | ||||||
| int	cmd_string_parse(const char *, struct cmd_list **, char **); | int	cmd_string_parse(const char *, struct cmd_list **, char **); | ||||||
|  |  | ||||||
| /* cmd-generic.c */ |  | ||||||
| size_t	cmd_prarg(char *, size_t, const char *, char *); |  | ||||||
| int	cmd_check_flag(uint64_t, int); |  | ||||||
| void	cmd_set_flag(uint64_t *, int); |  | ||||||
| #define CMD_TARGET_PANE_USAGE "[-t target-pane]" |  | ||||||
| #define CMD_TARGET_WINDOW_USAGE "[-t target-window]" |  | ||||||
| #define CMD_TARGET_SESSION_USAGE "[-t target-session]" |  | ||||||
| #define CMD_TARGET_CLIENT_USAGE "[-t target-client]" |  | ||||||
| void	cmd_target_init(struct cmd *, int); |  | ||||||
| int	cmd_target_parse(struct cmd *, int, char **, char **); |  | ||||||
| void	cmd_target_free(struct cmd *); |  | ||||||
| size_t	cmd_target_print(struct cmd *, char *, size_t); |  | ||||||
| #define CMD_SRCDST_PANE_USAGE "[-s src-pane] [-t dst-pane]" |  | ||||||
| #define CMD_SRCDST_WINDOW_USAGE "[-s src-window] [-t dst-window]" |  | ||||||
| #define CMD_SRCDST_SESSION_USAGE "[-s src-session] [-t dst-session]" |  | ||||||
| #define CMD_SRCDST_CLIENT_USAGE "[-s src-client] [-t dst-client]" |  | ||||||
| void	cmd_srcdst_init(struct cmd *, int); |  | ||||||
| int	cmd_srcdst_parse(struct cmd *, int, char **, char **); |  | ||||||
| void	cmd_srcdst_free(struct cmd *); |  | ||||||
| size_t	cmd_srcdst_print(struct cmd *, char *, size_t); |  | ||||||
| #define CMD_BUFFER_USAGE "[-b buffer-index]" |  | ||||||
| void	cmd_buffer_init(struct cmd *, int); |  | ||||||
| int	cmd_buffer_parse(struct cmd *, int, char **, char **); |  | ||||||
| void	cmd_buffer_free(struct cmd *); |  | ||||||
| size_t	cmd_buffer_print(struct cmd *, char *, size_t); |  | ||||||
|  |  | ||||||
| /* client.c */ | /* client.c */ | ||||||
| int	client_main(int, char **, int); | int	client_main(int, char **, int); | ||||||
|  |  | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user
	 Nicholas Marriott
					Nicholas Marriott