mirror of
				https://github.com/tmux/tmux.git
				synced 2025-11-04 00:56:10 +00:00 
			
		
		
		
	Sync OpenBSD patchset 735:
Make pane/window wrapping more logical (so with 10 windows, +10 from window 5 stays in the same place), and tidy the code. From Tiago Cunha.
This commit is contained in:
		
							
								
								
									
										157
									
								
								cmd.c
									
									
									
									
									
								
							
							
						
						
									
										157
									
								
								cmd.c
									
									
									
									
									
								
							@@ -1,4 +1,4 @@
 | 
			
		||||
/* $Id: cmd.c,v 1.141 2010-06-22 23:35:20 tcunha Exp $ */
 | 
			
		||||
/* $Id: cmd.c,v 1.142 2010-07-17 14:38:13 tcunha Exp $ */
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
 | 
			
		||||
@@ -116,6 +116,9 @@ struct client	*cmd_lookup_client(const char *);
 | 
			
		||||
struct session	*cmd_lookup_session(const char *, int *);
 | 
			
		||||
struct winlink	*cmd_lookup_window(struct session *, const char *, int *);
 | 
			
		||||
int		 cmd_lookup_index(struct session *, const char *, int *);
 | 
			
		||||
struct winlink	*cmd_find_window_offset(const char *, struct session *, int *);
 | 
			
		||||
int		 cmd_find_index_offset(const char *, struct session *, int *);
 | 
			
		||||
struct window_pane	*cmd_find_pane_offset(const char *, struct winlink *);
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
cmd_pack_argv(int argc, char **argv, char *buf, size_t len)
 | 
			
		||||
@@ -660,7 +663,6 @@ cmd_find_window(struct cmd_ctx *ctx, const char *arg, struct session **sp)
 | 
			
		||||
	const char	*winptr;
 | 
			
		||||
	char		*sessptr = NULL;
 | 
			
		||||
	int		 ambiguous = 0;
 | 
			
		||||
	int		 n = 1;
 | 
			
		||||
 | 
			
		||||
	/*
 | 
			
		||||
	 * Find the current session. There must always be a current session, if
 | 
			
		||||
@@ -706,21 +708,9 @@ cmd_find_window(struct cmd_ctx *ctx, const char *arg, struct session **sp)
 | 
			
		||||
		wl = s->curw;
 | 
			
		||||
	else if (winptr[0] == '!' && winptr[1] == '\0')
 | 
			
		||||
		wl = TAILQ_FIRST(&s->lastw);
 | 
			
		||||
	else if (winptr[0] == '+' || winptr[0] == '-') {
 | 
			
		||||
		if (winptr[1] != '\0')
 | 
			
		||||
			n = strtonum(winptr + 1, 1, INT_MAX, NULL);
 | 
			
		||||
		if (n == 0)
 | 
			
		||||
			wl = cmd_lookup_window(s, winptr, &ambiguous);
 | 
			
		||||
		else {
 | 
			
		||||
			if (winptr[0] == '+')
 | 
			
		||||
				wl = winlink_next_by_number(s->curw, n);
 | 
			
		||||
	else if (winptr[0] == '+' || winptr[0] == '-')
 | 
			
		||||
		wl = cmd_find_window_offset(winptr, s, &ambiguous);
 | 
			
		||||
	else
 | 
			
		||||
				wl = winlink_previous_by_number(s->curw, n);
 | 
			
		||||
			/* Search by name before giving up. */
 | 
			
		||||
			if (wl == NULL)
 | 
			
		||||
				wl = cmd_lookup_window(s, winptr, &ambiguous);
 | 
			
		||||
		}
 | 
			
		||||
	} else
 | 
			
		||||
		wl = cmd_lookup_window(s, winptr, &ambiguous);
 | 
			
		||||
	if (wl == NULL)
 | 
			
		||||
		goto not_found;
 | 
			
		||||
@@ -738,20 +728,7 @@ no_colon:
 | 
			
		||||
		if ((wl = TAILQ_FIRST(&s->lastw)) == NULL)
 | 
			
		||||
			goto not_found;
 | 
			
		||||
	} else if (arg[0] == '+' || arg[0] == '-') {
 | 
			
		||||
		if (arg[1] != '\0')
 | 
			
		||||
			n = strtonum(arg + 1, 1, INT_MAX, NULL);
 | 
			
		||||
		if (n == 0)
 | 
			
		||||
			wl = cmd_lookup_window(s, arg, &ambiguous);
 | 
			
		||||
		else {
 | 
			
		||||
			if (arg[0] == '+')
 | 
			
		||||
				wl = winlink_next_by_number(s->curw, n);
 | 
			
		||||
			else
 | 
			
		||||
				wl = winlink_previous_by_number(s->curw, n);
 | 
			
		||||
			/* Search by name before giving up. */
 | 
			
		||||
			if (wl == NULL)
 | 
			
		||||
				wl = cmd_lookup_window(s, arg, &ambiguous);
 | 
			
		||||
		}
 | 
			
		||||
		if (wl == NULL)
 | 
			
		||||
		if ((wl = cmd_find_window_offset(arg, s, &ambiguous)) == NULL)
 | 
			
		||||
			goto lookup_session;
 | 
			
		||||
	} else if ((wl = cmd_lookup_window(s, arg, &ambiguous)) == NULL)
 | 
			
		||||
		goto lookup_session;
 | 
			
		||||
@@ -791,6 +768,26 @@ not_found:
 | 
			
		||||
	return (NULL);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct winlink *
 | 
			
		||||
cmd_find_window_offset(const char *winptr, struct session *s, int *ambiguous)
 | 
			
		||||
{
 | 
			
		||||
	struct winlink	*wl;
 | 
			
		||||
	int		 offset = 1;
 | 
			
		||||
 | 
			
		||||
	if (winptr[1] != '\0')
 | 
			
		||||
		offset = strtonum(winptr + 1, 1, INT_MAX, NULL);
 | 
			
		||||
	if (offset == 0)
 | 
			
		||||
		wl = cmd_lookup_window(s, winptr, ambiguous);
 | 
			
		||||
	else {
 | 
			
		||||
		if (winptr[0] == '+')
 | 
			
		||||
			wl = winlink_next_by_number(s->curw, s, offset);
 | 
			
		||||
		else
 | 
			
		||||
			wl = winlink_previous_by_number(s->curw, s, offset);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return (wl);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Find the target session and window index, whether or not it exists in the
 | 
			
		||||
 * session. Return -2 on error or -1 if no window index is specified. This is
 | 
			
		||||
@@ -805,7 +802,6 @@ cmd_find_index(struct cmd_ctx *ctx, const char *arg, struct session **sp)
 | 
			
		||||
	const char	*winptr;
 | 
			
		||||
	char		*sessptr = NULL;
 | 
			
		||||
	int		 idx, ambiguous = 0;
 | 
			
		||||
	int		 n = 1;
 | 
			
		||||
 | 
			
		||||
	/*
 | 
			
		||||
	 * Find the current session. There must always be a current session, if
 | 
			
		||||
@@ -854,19 +850,7 @@ cmd_find_index(struct cmd_ctx *ctx, const char *arg, struct session **sp)
 | 
			
		||||
			goto not_found;
 | 
			
		||||
		idx = wl->idx;
 | 
			
		||||
	} else if (winptr[0] == '+' || winptr[0] == '-') {
 | 
			
		||||
		if (winptr[1] != '\0')
 | 
			
		||||
			n = strtonum(winptr + 1, 1, INT_MAX, NULL);
 | 
			
		||||
		if (winptr[0] == '+' && s->curw->idx == INT_MAX)
 | 
			
		||||
			idx = cmd_lookup_index(s, winptr, &ambiguous);
 | 
			
		||||
		else if (winptr[0] == '-' && s->curw->idx == 0)
 | 
			
		||||
			idx = cmd_lookup_index(s, winptr, &ambiguous);
 | 
			
		||||
		else if (n == 0)
 | 
			
		||||
			idx = cmd_lookup_index(s, winptr, &ambiguous);
 | 
			
		||||
		else if (winptr[0] == '+')
 | 
			
		||||
			idx = s->curw->idx + n;
 | 
			
		||||
		else
 | 
			
		||||
			idx = s->curw->idx - n;
 | 
			
		||||
		if (idx < 0)
 | 
			
		||||
		if ((idx = cmd_find_index_offset(winptr, s, &ambiguous)) < 0)
 | 
			
		||||
			goto invalid_index;
 | 
			
		||||
	} else if ((idx = cmd_lookup_index(s, winptr, &ambiguous)) == -1)
 | 
			
		||||
		goto invalid_index;
 | 
			
		||||
@@ -885,19 +869,7 @@ no_colon:
 | 
			
		||||
			goto not_found;
 | 
			
		||||
		idx = wl->idx;
 | 
			
		||||
	} else if (arg[0] == '+' || arg[0] == '-') {
 | 
			
		||||
		if (arg[1] != '\0')
 | 
			
		||||
			n = strtonum(arg + 1, 1, INT_MAX, NULL);
 | 
			
		||||
		if (arg[0] == '+' && s->curw->idx == INT_MAX)
 | 
			
		||||
			idx = cmd_lookup_index(s, arg, &ambiguous);
 | 
			
		||||
		else if (arg[0] == '-' && s->curw->idx == 0)
 | 
			
		||||
			idx = cmd_lookup_index(s, arg, &ambiguous);
 | 
			
		||||
		else if (n == 0)
 | 
			
		||||
			idx = cmd_lookup_index(s, arg, &ambiguous);
 | 
			
		||||
		else if (arg[0] == '+')
 | 
			
		||||
			idx = s->curw->idx + n;
 | 
			
		||||
		else
 | 
			
		||||
			idx = s->curw->idx - n;
 | 
			
		||||
		if (idx < 0)
 | 
			
		||||
		if ((idx = cmd_find_index_offset(arg, s, &ambiguous)) < 0)
 | 
			
		||||
			goto lookup_session;
 | 
			
		||||
	} else if ((idx = cmd_lookup_index(s, arg, &ambiguous)) == -1)
 | 
			
		||||
		goto lookup_session;
 | 
			
		||||
@@ -946,6 +918,32 @@ not_found:
 | 
			
		||||
	return (-2);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int
 | 
			
		||||
cmd_find_index_offset(const char *winptr, struct session *s, int *ambiguous)
 | 
			
		||||
{
 | 
			
		||||
	int	idx, offset = 1;
 | 
			
		||||
 | 
			
		||||
	if (winptr[1] != '\0')
 | 
			
		||||
		offset = strtonum(winptr + 1, 1, INT_MAX, NULL);
 | 
			
		||||
	if (offset == 0)
 | 
			
		||||
		idx = cmd_lookup_index(s, winptr, ambiguous);
 | 
			
		||||
	else {
 | 
			
		||||
		if (winptr[0] == '+') {
 | 
			
		||||
			if (s->curw->idx == INT_MAX)
 | 
			
		||||
				idx = cmd_lookup_index(s, winptr, ambiguous);
 | 
			
		||||
			else
 | 
			
		||||
				idx = s->curw->idx + offset;
 | 
			
		||||
		} else {
 | 
			
		||||
			if (s->curw->idx == 0)
 | 
			
		||||
				idx = cmd_lookup_index(s, winptr, ambiguous);
 | 
			
		||||
			else
 | 
			
		||||
				idx = s->curw->idx - offset;
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return (idx);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Find the target session, window and pane number or report an error and
 | 
			
		||||
 * return NULL. The pane number is separated from the session:window by a .,
 | 
			
		||||
@@ -960,7 +958,7 @@ cmd_find_pane(struct cmd_ctx *ctx,
 | 
			
		||||
	struct layout_cell	*lc;
 | 
			
		||||
	const char		*period, *errstr;
 | 
			
		||||
	char			*winptr, *paneptr;
 | 
			
		||||
	u_int			 idx, n = 1;
 | 
			
		||||
	u_int			 idx;
 | 
			
		||||
 | 
			
		||||
	/* Get the current session. */
 | 
			
		||||
	if ((s = cmd_current_session(ctx)) == NULL) {
 | 
			
		||||
@@ -992,27 +990,9 @@ cmd_find_pane(struct cmd_ctx *ctx,
 | 
			
		||||
	paneptr = winptr + (period - arg) + 1;
 | 
			
		||||
	if (*paneptr == '\0')
 | 
			
		||||
		*wpp = wl->window->active;
 | 
			
		||||
	else if (paneptr[0] == '+' || paneptr[0] == '-') {
 | 
			
		||||
		if (paneptr[1] != '\0')
 | 
			
		||||
			n = strtonum(paneptr + 1, 1, INT_MAX, NULL);
 | 
			
		||||
		idx = window_pane_index(wl->window, wl->window->active);
 | 
			
		||||
		if (paneptr[0] == '+' && idx == INT_MAX)
 | 
			
		||||
			*wpp = TAILQ_FIRST(&wl->window->panes);
 | 
			
		||||
		else if (paneptr[0] == '-' && idx == 0)
 | 
			
		||||
			*wpp = TAILQ_LAST(&wl->window->panes, window_panes);
 | 
			
		||||
		else if (n == 0)
 | 
			
		||||
			*wpp = wl->window->active;
 | 
			
		||||
		else if (paneptr[0] == '+')
 | 
			
		||||
			*wpp = window_pane_at_index(wl->window, idx + n);
 | 
			
		||||
		else
 | 
			
		||||
			*wpp = window_pane_at_index(wl->window, idx - n);
 | 
			
		||||
		if (paneptr[0] == '+' && *wpp == NULL)
 | 
			
		||||
			*wpp = TAILQ_FIRST(&wl->window->panes);
 | 
			
		||||
		else if (paneptr[0] == '-' && *wpp == NULL)
 | 
			
		||||
			*wpp = TAILQ_LAST(&wl->window->panes, window_panes);
 | 
			
		||||
		else if (*wpp == NULL)
 | 
			
		||||
			goto error;
 | 
			
		||||
	} else {
 | 
			
		||||
	else if (paneptr[0] == '+' || paneptr[0] == '-')
 | 
			
		||||
		*wpp = cmd_find_pane_offset(paneptr, wl);
 | 
			
		||||
	else {
 | 
			
		||||
		idx = strtonum(paneptr, 0, INT_MAX, &errstr);
 | 
			
		||||
		if (errstr != NULL)
 | 
			
		||||
			goto lookup_string;
 | 
			
		||||
@@ -1064,6 +1044,25 @@ error:
 | 
			
		||||
	return (NULL);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct window_pane *
 | 
			
		||||
cmd_find_pane_offset(const char *paneptr, struct winlink *wl)
 | 
			
		||||
{
 | 
			
		||||
	struct window		*w = wl->window;
 | 
			
		||||
	struct window_pane	*wp = w->active;
 | 
			
		||||
	u_int			 offset = 1;
 | 
			
		||||
 | 
			
		||||
	if (paneptr[1] != '\0')
 | 
			
		||||
		offset = strtonum(paneptr + 1, 1, INT_MAX, NULL);
 | 
			
		||||
	if (offset > 0) {
 | 
			
		||||
		if (paneptr[0] == '+')
 | 
			
		||||
			wp = window_pane_next_by_number(w, wp, offset);
 | 
			
		||||
		else
 | 
			
		||||
			wp = window_pane_previous_by_number(w, wp, offset);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return (wp);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* Replace the first %% or %idx in template by s. */
 | 
			
		||||
char *
 | 
			
		||||
cmd_template_replace(char *template, const char *s, int idx)
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										12
									
								
								tmux.h
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								tmux.h
									
									
									
									
									
								
							@@ -1,4 +1,4 @@
 | 
			
		||||
/* $Id: tmux.h,v 1.570 2010-07-17 14:36:41 tcunha Exp $ */
 | 
			
		||||
/* $Id: tmux.h,v 1.571 2010-07-17 14:38:13 tcunha Exp $ */
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
 | 
			
		||||
@@ -1824,8 +1824,10 @@ struct winlink	*winlink_add(struct winlinks *, struct window *, int);
 | 
			
		||||
void		 winlink_remove(struct winlinks *, struct winlink *);
 | 
			
		||||
struct winlink	*winlink_next(struct winlink *);
 | 
			
		||||
struct winlink	*winlink_previous(struct winlink *);
 | 
			
		||||
struct winlink	*winlink_next_by_number(struct winlink *, int);
 | 
			
		||||
struct winlink	*winlink_previous_by_number(struct winlink *, int);
 | 
			
		||||
struct winlink	*winlink_next_by_number(struct winlink *, struct session *,
 | 
			
		||||
		     int);
 | 
			
		||||
struct winlink	*winlink_previous_by_number(struct winlink *, struct session *,
 | 
			
		||||
		     int);
 | 
			
		||||
void		 winlink_stack_push(struct winlink_stack *, struct winlink *);
 | 
			
		||||
void		 winlink_stack_remove(struct winlink_stack *, struct winlink *);
 | 
			
		||||
int		 window_index(struct window *, u_int *);
 | 
			
		||||
@@ -1840,6 +1842,10 @@ struct window_pane *window_add_pane(struct window *, u_int);
 | 
			
		||||
void		 window_resize(struct window *, u_int, u_int);
 | 
			
		||||
void		 window_remove_pane(struct window *, struct window_pane *);
 | 
			
		||||
struct window_pane *window_pane_at_index(struct window *, u_int);
 | 
			
		||||
struct window_pane *window_pane_next_by_number(struct window *,
 | 
			
		||||
		        struct window_pane *, u_int);
 | 
			
		||||
struct window_pane *window_pane_previous_by_number(struct window *,
 | 
			
		||||
		        struct window_pane *, u_int);
 | 
			
		||||
u_int		 window_pane_index(struct window *, struct window_pane *);
 | 
			
		||||
u_int		 window_count_panes(struct window *);
 | 
			
		||||
void		 window_destroy_panes(struct window *);
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										33
									
								
								window.c
									
									
									
									
									
								
							
							
						
						
									
										33
									
								
								window.c
									
									
									
									
									
								
							@@ -1,4 +1,4 @@
 | 
			
		||||
/* $Id: window.c,v 1.133 2010-06-22 23:29:05 tcunha Exp $ */
 | 
			
		||||
/* $Id: window.c,v 1.134 2010-07-17 14:38:13 tcunha Exp $ */
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
 * Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
 | 
			
		||||
@@ -171,22 +171,22 @@ winlink_previous(struct winlink *wl)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct winlink *
 | 
			
		||||
winlink_next_by_number(struct winlink *wl, int n)
 | 
			
		||||
winlink_next_by_number(struct winlink *wl, struct session *s, int n)
 | 
			
		||||
{
 | 
			
		||||
	for (; n > 0; n--) {
 | 
			
		||||
		if ((wl = RB_NEXT(winlinks, wwl, wl)) == NULL)
 | 
			
		||||
			break;
 | 
			
		||||
			wl = RB_MIN(winlinks, &s->windows);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return (wl);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct winlink *
 | 
			
		||||
winlink_previous_by_number(struct winlink *wl, int n)
 | 
			
		||||
winlink_previous_by_number(struct winlink *wl, struct session *s, int n)
 | 
			
		||||
{
 | 
			
		||||
	for (; n > 0; n--) {
 | 
			
		||||
		if ((wl = RB_PREV(winlinks, wwl, wl)) == NULL)
 | 
			
		||||
			break;
 | 
			
		||||
			wl = RB_MAX(winlinks, &s->windows);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return (wl);
 | 
			
		||||
@@ -389,6 +389,29 @@ window_pane_at_index(struct window *w, u_int idx)
 | 
			
		||||
	return (NULL);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct window_pane *
 | 
			
		||||
window_pane_next_by_number(struct window *w, struct window_pane *wp, u_int n)
 | 
			
		||||
{
 | 
			
		||||
	for (; n > 0; n--) {
 | 
			
		||||
		if ((wp = TAILQ_NEXT(wp, entry)) == NULL)
 | 
			
		||||
			wp = TAILQ_FIRST(&w->panes);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return (wp);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
struct window_pane *
 | 
			
		||||
window_pane_previous_by_number(struct window *w, struct window_pane *wp,
 | 
			
		||||
    u_int n)
 | 
			
		||||
{
 | 
			
		||||
	for (; n > 0; n--) {
 | 
			
		||||
		if ((wp = TAILQ_PREV(wp, window_panes, entry)) == NULL)
 | 
			
		||||
			wp = TAILQ_LAST(&w->panes, window_panes);
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	return (wp);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
u_int
 | 
			
		||||
window_pane_index(struct window *w, struct window_pane *wp)
 | 
			
		||||
{
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user