3238 Commits
2.0 ... 3.1c

Author SHA1 Message Date
Nicholas Marriott
25cae5d86f 3.1c. 2020-10-30 12:11:02 +00:00
nicm
d0ad34e94d Do not write after the end of the array and overwrite the stack when
colon-separated SGR sequences contain empty arguments. Reported by Sergey
Nizovtsev.
2020-10-30 12:09:52 +00:00
Nicholas Marriott
a10c4c60cb Add to CHANGES. 2020-05-04 09:06:57 +01:00
Nicholas Marriott
846b99e0cb Portable does not need sys/queue.h. 2020-05-03 10:49:16 +01:00
Nicholas Marriott
6a33a12798 Do not remove the automatic-rename option from the global set, only from
the window (it must stay in the global set or tmux will crash). GitHub
issue 2188.
2020-04-30 15:20:08 +01:00
Nicholas Marriott
d0fa520788 Update CHANGES. 2020-04-27 09:38:04 +01:00
Nicholas Marriott
646bfe403e Do not close stdout file descriptor in control mode since it will be needed for
printing the exit messages.
2020-04-27 09:36:30 +01:00
Nicholas Marriott
650d38962f tmux 3.1. 2020-04-24 09:57:49 +01:00
Nicholas Marriott
ccd7368cc5 Update CHANGES. 2020-04-22 12:59:50 +01:00
Nicholas Marriott
9077b212c3 job_run needs fewer arguments. 2020-04-06 16:14:09 +01:00
Nicholas Marriott
a4e19bcd80 Various fixes for copy mode from master. 2020-04-06 16:09:49 +01:00
nicm
bc36b473f1 Check previous line rather than an extra line, from Anindya Mukherjee. 2020-04-06 16:07:20 +01:00
nicm
10975961de Only search the visible part of the history when marking (highlighting)
search terms, much faster than searching the whole history.
2020-04-06 16:06:14 +01:00
nicm
8d2af4fb54 Add a 10 second timeout to prevent searches taking too much time, from
Anindya Mukherjee.
2020-04-06 16:04:51 +01:00
nicm
ac050b2583 Stop logging the entire command queue every time we add something,
spotted by tb & sthen.
2020-04-06 16:04:10 +01:00
nicm
3234017260 Add an argument to list-commands to show only a single command. 2020-04-06 16:03:39 +01:00
nicm
938ad5a98c Use new window and new pane as well for -P to new-session or new-window. 2020-04-06 16:03:33 +01:00
Nicholas Marriott
9f378a163f 3.1-rc4. 2020-04-01 10:09:49 +01:00
nicm
a5922546ac Do not go down the regex search path (which is expensive because we need
to convert the grid data into a string for regexec and reverse it to
find the grid position) if the search string does not contain any regex
special characters.
2020-04-01 10:09:03 +01:00
nicm
3476eccf48 Use a comparison to check for wrap and avoid an expensive modulus. 2020-04-01 10:08:54 +01:00
nicm
0dbf414578 Performance improvements for regex searching, most notably:
- Use the grid data directly instead of copying it.

- Special case the most typical one byte character cells and use memcmp
  for multiple bytes instead of a handrolled loop.

- Hoist regcomp out of the loop into the calling functions.

GitHub issue 2143.

Also a man page from from jmc@.
2020-04-01 10:08:39 +01:00
nicm
8dedccaa20 Add non-regex search variants to avoid the performance cost for people
with large histories or long lines.
2020-04-01 10:08:09 +01:00
Nicholas Marriott
e5fd85415d Update CHANGES. 2020-04-01 09:29:44 +01:00
Nicholas Marriott
af4b62d10b 3.1-rc3. 2020-03-18 07:55:33 +00:00
nicm
0c06409c9d getopt is not required to set optarg to NULL when there is no argument
and some do not, so set it explicitly each time.
2020-03-18 07:54:37 +00:00
nicm
617136c234 Turn off mouse mode 1003 as well as the rest when exiting. 2020-03-17 16:16:23 +00:00
nicm
f16085a362 Fix C-Space key string. 2020-03-17 16:16:09 +00:00
nicm
4ffbebedce Terminate the output buffer for control mode output - it is now used as
a string. GitHub issue 2114.
2020-03-17 16:14:51 +00:00
nicm
c0d74661b7 Do not attempt to close a NULL pane when failing to create a new one. 2020-03-17 16:14:25 +00:00
Nicholas Marriott
b21a9b1c4e getopt varies too much between platforms, and we already use compat/getopt.c
for Linux so just use it everywhere.
2020-03-17 16:14:12 +00:00
Nicholas Marriott
444e9f3c58 Bump 3.1-rc up to master. 2020-03-11 06:38:43 +00:00
Thomas Adam
59cb022c42 Merge branch 'obsd-master' 2020-03-07 12:01:25 +00:00
nicm
2991f4aad0 Use correct width of right marker so it doesn't draw over status right
when more than one character. Reported by Tyler Culp.
2020-03-07 10:58:32 +00:00
Thomas Adam
9e4d0b2b6d Merge branch 'obsd-master' 2020-03-06 18:01:26 +00:00
nicm
add75a06cd Update latest client for target session on switch-client. 2020-03-06 15:35:03 +00:00
Thomas Adam
ccd24c9cb2 Merge branch 'obsd-master' 2020-03-02 23:09:48 +00:00
nicm
8be179de46 Use current session for cwd of new sessions, not the new session which
doesn't have one yet. GitHub issue 2091.
2020-03-02 08:30:30 +00:00
nicm
f65b9c0d36 Change mouse selection so that after selecting a word, dragging selects
only words and similar for lines. From Anindya Mukherjee.
2020-02-24 09:53:59 +00:00
Nicholas Marriott
549b3599ef Update CHANGES. 2020-02-20 20:42:26 +00:00
Thomas Adam
4694afbed4 Merge branch 'obsd-master' 2020-02-20 10:01:29 +00:00
nicm
229be034fb Add selection_active format for when the selection is present but not
moving with the cursor, from Mark Kelly.
2020-02-20 07:34:57 +00:00
Thomas Adam
ba542e42b7 Merge branch 'obsd-master' 2020-02-19 16:01:27 +00:00
nicm
b20753f2a3 A few fixes to make modifier keys and dragging work - need to remove the
modifiers before checking for the dragging marker key, and apply them
before looking up the end key. Also fix key-to-string with modifiers for
special keys.
2020-02-19 14:25:00 +00:00
Nicholas Marriott
22e9cf04ca Add GitHub. 2020-02-19 06:01:54 +00:00
Nicholas Marriott
37919a6b6a This site is too stupid. 2020-02-17 12:20:53 +00:00
Nicholas Marriott
fdbc1116ef Add to FUNDING.yml. 2020-02-17 12:19:04 +00:00
Thomas Adam
0c6c8c4efc Merge branch 'obsd-master' 2020-02-15 16:01:25 +00:00
nicm
a1f6bd55b6 Add -a to list-keys to also list keys without notes with -N, suggested
by Shehu Dikko.
2020-02-15 15:08:08 +00:00
Thomas Adam
c391d50cbb Merge branch 'obsd-master' 2020-02-14 16:01:26 +00:00
nicm
58b47bf01b Fix top/bottom pane calculation with pane border status enabled,
reported by Stanislav Spassov.
2020-02-14 13:57:58 +00:00
Nicholas Marriott
9900ccd04e Change lock.yml options. 2020-02-14 11:43:12 +00:00
Nicholas Marriott
24cd726dae Add lock.yml file. 2020-02-14 11:40:32 +00:00
Thomas Adam
6c28d0dd06 Merge branch 'obsd-master' 2020-02-13 10:01:27 +00:00
nicm
f48b041cf2 Do not jump to next word end if already on a word end when selecting a
word. Fixes select-word with single character words and vi(1) keys. From
Mark Kelly.
2020-02-13 09:02:07 +00:00
Thomas Adam
a4d8437bc2 Merge branch 'obsd-master' 2020-02-11 08:01:30 +00:00
nicm
dc882adb2e Remove unused variables from Ben Boeckel, and a Pp from jmc. 2020-02-11 07:01:08 +00:00
Nicholas Marriott
470cba356d Merge branch '3.1-rc' 2020-02-07 16:43:41 +00:00
Nicholas Marriott
ae9ca620bd Remove duplicates, from Thomas Sattler. 2020-02-07 16:42:10 +00:00
Nicholas Marriott
400750bb26 Merge branch '3.1-rc' 2020-02-06 12:49:50 +00:00
nicm
096f0d35a6 Make list-keys description clearer in tmux.1 and remove an unused variable. 2020-02-06 12:49:02 +00:00
Thomas Adam
54553903de Merge branch 'obsd-master' 2020-02-05 14:01:26 +00:00
nicm
fb29242168 Make list-keys description clearer in tmux.1 and remove an unused variable. 2020-02-05 13:06:49 +00:00
Nicholas Marriott
c915cfc7e4 Merge branch '3.1-rc' 2020-02-04 07:46:59 +00:00
Nicholas Marriott
3ad4a7a571 Style nit in CHANGES. 2020-02-04 07:46:26 +00:00
Nicholas Marriott
47174f5130 Next is 3.2. 2020-02-04 07:45:29 +00:00
Nicholas Marriott
4822130b3c Merge branch '3.1-rc' 2020-02-04 07:44:49 +00:00
Nicholas Marriott
0bf153daa6 Update CONTRIBUTING.md 2020-02-04 07:43:34 +00:00
Nicholas Marriott
63a69fe085 3.1-rc. 2020-02-04 07:21:04 +00:00
Nicholas Marriott
43b36752ce Remove a duplicate entry. 2020-02-03 20:26:03 +00:00
Thomas Adam
19d5f4a0bd Merge branch 'obsd-master' 2020-02-03 14:01:25 +00:00
nicm
265164d251 Instead of passing titles through vis() which doubles backslashes, just
ignore any containing control characters or invalid UTF-8. GitHub issue 2070.
2020-02-03 13:46:27 +00:00
Thomas Adam
6f0241e645 Merge branch 'obsd-master' 2020-01-30 10:01:24 +00:00
nicm
87bcc0c7e0 Remove bind-key -c which doesn't do anything and is undocumented. 2020-01-30 08:02:25 +00:00
Thomas Adam
32be954bdd Merge branch 'obsd-master' 2020-01-29 18:01:24 +00:00
nicm
44dad918f8 Warn if a message type that is no longer used is received. 2020-01-29 16:22:32 +00:00
Thomas Adam
bc36700d05 Merge branch 'obsd-master' 2020-01-29 16:01:24 +00:00
nicm
531daba584 Do not send DA and DSR again if already have a response. 2020-01-29 15:07:49 +00:00
Thomas Adam
8b22da69b6 Merge branch 'obsd-master' 2020-01-29 10:01:25 +00:00
nicm
7a15d10bf4 Remove extra Pp (from jmc) and add a missing word. 2020-01-29 08:28:17 +00:00
Nicholas Marriott
7f3feb1896 Add to CHANGES. 2020-01-28 15:52:04 +00:00
Thomas Adam
7eada28f96 Merge branch 'obsd-master' 2020-01-28 14:01:25 +00:00
nicm
b905c5d455 If ALL clients are readonly, allow them to affect the size, suggested by Thomas Sattler. 2020-01-28 13:23:24 +00:00
nicm
e388702260 Ignore empty commands rather than adding them to the command list rather
than trying to skip them later, fixes problem reported by M Kelly.
2020-01-28 13:10:14 +00:00
Thomas Adam
60ab714451 Merge branch 'obsd-master' 2020-01-28 12:01:28 +00:00
nicm
a6129e9974 If we can identify the terminal as iTerm2 or as tmux, we can be sure
they support 256 and RGB colours, so set those flags too.
2020-01-28 11:39:51 +00:00
nicm
84995ae172 -V also needs to go in usage. 2020-01-28 11:31:31 +00:00
Nicholas Marriott
685eb381de Fix for version changes. 2020-01-28 11:28:30 +00:00
Thomas Adam
ee3d3db364 Merge branch 'obsd-master' 2020-01-28 11:17:08 +00:00
nicm
90e962fff8 Add support for the iTerm2 DSR 1337 sequence to get the terminal version. 2020-01-28 10:59:29 +00:00
nicm
f165221dc4 Reduce a difference with portable tmux by adding the -V flag and
#{version} format; on OpenBSD these just report the OpenBSD version.
2020-01-28 10:44:30 +00:00
nicm
32816eaebd Set up working directory before killing the existing pane on respawn. 2020-01-28 10:21:21 +00:00
Thomas Adam
7cdf5ee9bc Merge branch 'obsd-master' 2020-01-28 10:01:25 +00:00
nicm
24350879cd Add a define for flags meaning a client is not attached, and fix
unattached counter, reported by Thomas Sattler.
2020-01-28 08:06:11 +00:00
Thomas Adam
f3ea318a04 Merge branch 'obsd-master' 2020-01-27 10:01:27 +00:00
nicm
2c38e01b54 Expand description of start-server. 2020-01-27 09:04:47 +00:00
nicm
d0b8d036be Add support for adding a note to a key binding (with bind-key -N) and
use this to add descriptions to the default key bindings. A new -N flag
to list-keys shows key bindings with notes rather than the default
bind-key command used to create them. Change the default ? binding to
use this to show a readable summary of keys.

Also extend command-prompt to return the name of the key pressed and add
a default binding (/) to show the note for the next key pressed

Suggested by Alex Tremblay in GitHub issue 2000.
2020-01-27 08:53:13 +00:00
nicm
2e39b621c9 Change so that assignments may be specified alone - a command isn't
required. GitHub issue 2062.
2020-01-27 08:23:42 +00:00
Thomas Adam
0eb7b54731 Merge branch 'obsd-master' 2020-01-25 18:01:26 +00:00
Nicholas Marriott
74b424075c Use FNM_IGNORECASE if present, from Eric N Vander Weele in GitHub issue 2067. 2020-01-25 16:41:49 +00:00
nicm
9169ee0e87 Mention swap-window -d, GitHub issue 2068. 2020-01-25 16:40:32 +00:00
Nicholas Marriott
cdf138372c Add to CHANGES. 2020-01-14 16:02:22 +00:00
Thomas Adam
a01c9ffc6c Merge branch 'obsd-master' 2020-01-13 14:01:25 +00:00
nicm
da515570dc Stop handling DA and DSR after a second (they should be the first thing
sent) so this should be plenty.
2020-01-13 11:59:21 +00:00
Thomas Adam
8457f54edc Merge branch 'obsd-master' 2020-01-13 10:01:27 +00:00
nicm
835a6c0cf0 Be more specific in the DSR we are looking for so it doesn't get
confused with mouse sequences. Also set a flag and don't bother checking
for it if we have already seen it (same for DA), and don't check if we
never asked for it.
2020-01-13 08:12:53 +00:00
nicm
04eee2410d Treat plausible but invalid keys (like C-BSpace) as literal like any
other unrecognised string passed to send-keys. Reported by Anthony
Sottile in GitHub issue 2049.
2020-01-13 07:51:54 +00:00
Thomas Adam
3e701309a4 Merge branch 'obsd-master' 2020-01-13 00:01:24 +00:00
Thomas Adam
e9b1294331 Merge branch 'obsd-master' 2020-01-12 22:01:26 +00:00
nicm
381333c4a9 Detect iTerm2 and enable DECSLRM. 2020-01-12 22:00:20 +00:00
nicm
193e637de0 The terminal type was never as much use as I expected so remove it in
favour of a couple of flags for the features used (DECSLRM and DECFRA).
Also rename the flag for no xenl to be more obvious while here.
2020-01-12 21:07:07 +00:00
nicm
deb734c7f6 Loop over all DA features, don't skip the first. 2020-01-12 20:20:20 +00:00
Thomas Adam
61b075a263 Merge branch 'obsd-master' 2020-01-08 16:01:23 +00:00
nicm
36eb16ce7d Do not hang in format_trim_* on invalid UTF-8 characters. 2020-01-08 14:40:52 +00:00
Thomas Adam
ed16f51e26 Merge branch 'obsd-master' 2020-01-08 08:01:24 +00:00
nicm
6628e542b5 Add -Z to default switch-client command in tree mode, matches previous
behaviour.
2020-01-08 06:38:55 +00:00
Thomas Adam
507816b1d6 Merge branch 'obsd-master' 2020-01-05 22:01:24 +00:00
nicm
73b8c2ef3c Common function to free key bindings. 2020-01-05 20:39:25 +00:00
Thomas Adam
36169d8a68 Merge branch 'obsd-master' 2020-01-05 14:01:23 +00:00
nicm
7c6c66cc3c Send errors to stdout in control mode so they don't get reordered with
other output, reported by George Nachman in GitHub issue 2048.
2020-01-05 12:51:43 +00:00
Thomas Adam
6d3d47c25b Merge branch 'obsd-master' 2020-01-04 20:01:26 +00:00
nicm
1870cc70ef Add ~ to quoted characters for %%%, reported by tb@. 2020-01-04 18:01:56 +00:00
Thomas Adam
6b0091e185 Merge branch 'obsd-master' 2020-01-02 14:01:26 +00:00
nicm
a770a3bf7e Add CMD_FIND_DEFAULT_MARKED to join-pane like move-pane, from
davidegirardi in GitHub issue 2046.
2020-01-02 13:44:17 +00:00
Thomas Adam
7110226b96 Merge branch 'obsd-master' 2020-01-02 00:01:29 +00:00
nicm
ac85a3e0d3 Document client exit messages. 2020-01-01 22:12:05 +00:00
nicm
9cc603cbad Fix format expansion in window names, reported by Suraj N Kurapati. 2020-01-01 21:51:33 +00:00
Thomas Adam
566ab9aa28 Merge branch 'obsd-master' 2019-12-30 22:01:25 +00:00
nicm
206d878127 Do not let readonly clients limit the size, suggested by Max Barraclough
in GitHub issue 2042.
2019-12-30 21:24:55 +00:00
Thomas Adam
47d06cb023 Merge branch 'obsd-master' 2019-12-27 20:01:24 +00:00
nicm
4ea07716de Support regex search in copy mode, from Anindya Mukherjee in GitHub
issue 2038.
2019-12-27 18:42:49 +00:00
Thomas Adam
0aa6c6f647 Merge branch 'obsd-master' 2019-12-26 16:01:25 +00:00
nicm
88ee5b1a73 Pass correct value into iterator callback for time formats. 2019-12-26 14:48:29 +00:00
Thomas Adam
b931bbb319 Merge branch 'obsd-master' 2019-12-26 12:01:26 +00:00
nicm
817d199cbb Add a number of new formats to inspect what sessions and clients a
window is present or active in. From Tyler Culp in GitHub issue 2034.
2019-12-26 11:04:58 +00:00
Thomas Adam
67d2408279 Merge branch 'obsd-master' 2019-12-24 12:01:25 +00:00
nicm
07e37479c2 Fix name of option, GitHub issue 2030. 2019-12-24 09:57:11 +00:00
Thomas Adam
a6b1cbba02 Merge branch 'obsd-master' 2019-12-21 18:01:24 +00:00
tim
5cd00eda0b Restore source-file -q behaviour, broken in r1.42; OK nicm@ 2019-12-21 17:30:48 +00:00
Thomas Adam
745233d6a1 Merge branch 'obsd-master' 2019-12-19 10:01:26 +00:00
nicm
1764f66b7d When adding a list with multiple commands to the queue, the next item to
insert after needs to be the last one added, not the first. Reported by
Jason Kim in GitHub issue 2023.
2019-12-19 09:22:33 +00:00
Nicholas Marriott
54efe33799 Add back utempter code, reported by Peter Schellenbach. 2019-12-18 15:58:06 +00:00
Thomas Adam
d0cd68d5e4 Merge branch 'obsd-master' 2019-12-18 08:01:23 +00:00
nicm
ef54a08080 Do not rely on errno after glob(3) fails. 2019-12-18 07:48:56 +00:00
Thomas Adam
4223293ed8 Merge branch 'obsd-master' 2019-12-17 12:01:24 +00:00
nicm
f8cb759bdb Use the message that has already been built rather than the va_list. 2019-12-17 11:43:23 +00:00
Nicholas Marriott
3879509426 Define FNM_CASEFOLD to 0 for AIX, from Eric N Vander Weele. 2019-12-16 21:34:36 +00:00
Nicholas Marriott
479d411dda Remove imsg.h. 2019-12-16 20:01:26 +00:00
Thomas Adam
52b6ca5706 Merge branch 'obsd-master' 2019-12-16 18:01:31 +00:00
nicm
1bdd4828bd If /dev/fd/X is a symlink and realpath() expands symlinks, /dev/fd/X
ends up pointing to the wrong place before it is passed to the client.
The path is only used internally so there is no real need for
realpath(), remove it and move the get_path function to file.c where all
the callers are.
2019-12-16 16:39:03 +00:00
nicm
b4520aaf2c Need to include message size in the maximum buffer calculation. 2019-12-16 16:09:28 +00:00
nicm
eaa58d28dc Instead of using large buffers in imsgs, add the data or path onto the end. 2019-12-16 15:48:50 +00:00
Nicholas Marriott
e6b02dec19 Add to CHANGES. 2019-12-13 11:31:53 +00:00
Thomas Adam
00723f1f5c Merge branch 'obsd-master' 2019-12-13 10:01:24 +00:00
nicm
21f9b39f06 Show UTF-8 in choose-buffer mode. From KOIE Hidetaka. 2019-12-13 09:15:13 +00:00
Thomas Adam
e24e9867ec Merge branch 'obsd-master' 2019-12-13 08:01:24 +00:00
nicm
6ce943f4d9 Need to check in the error callback also. 2019-12-13 07:00:22 +00:00
nicm
828001ecc5 Do not spin waiting for exit, instead check in the write callback. 2019-12-13 06:55:12 +00:00
Thomas Adam
58908b045b Merge branch 'obsd-master' 2019-12-12 15:38:33 +00:00
nicm
dcf41ec927 Do not crash in tree modes if the pane is only 1 in width, reported by
KOIE Hidetaka in GitHub issue 2015.
2019-12-12 15:03:13 +00:00
nicm
2b2b193791 Add function to the right file. 2019-12-12 15:01:54 +00:00
Thomas Adam
7922f4ee7b Merge branch 'obsd-master' 2019-12-12 14:33:47 +00:00
nicm
5134666702 Change source-file to use new file code which allows it to read from
stdin.
2019-12-12 12:49:36 +00:00
nicm
268f2b047a Do not check if client is dead if it is NULL. 2019-12-12 11:51:32 +00:00
nicm
c284ebe0ad Rewrite the code for reading and writing files. Now, if the client is
not attached, the server process asks it to open the file, similar to
how works for stdin, stdout, stderr. This makes special files like
/dev/fd/X work (used by some shells). stdin, stdout and stderr and
control mode are now just special cases of the same mechanism. This will
also make it easier to use for other commands that read files such as
source-file.
2019-12-12 11:39:56 +00:00
Thomas Adam
0d99519c3d Merge branch 'obsd-master' 2019-12-11 20:01:25 +00:00
nicm
64fb7e472a Tweak previous to check the wrapped flag and stop if not set. 2019-12-11 18:30:29 +00:00
nicm
ab630f72ed Allow search across wrapped lines and fix some inconsistencies in how th
position is represented, GitHub issue 2014 from Anindya Mukherjee.
2019-12-11 18:23:34 +00:00
Thomas Adam
96abf400a5 Merge branch 'obsd-master' 2019-12-11 14:01:25 +00:00
nicm
f733d3f3eb Do not set cursor colour to default unless it has been changed, GitHub
issue 2013.
2019-12-11 12:13:37 +00:00
Nicholas Marriott
6aeb679066 Add to CHANGES. 2019-12-10 19:02:27 +00:00
Nicholas Marriott
15d7e564dd Add ~/.config/tmux/tmux.conf to the default search path for configuration files
(in Makefile.am, so portable tmux only).
2019-12-10 16:31:01 +00:00
Thomas Adam
5b2048fbb9 Merge branch 'obsd-master' 2019-12-10 16:01:25 +00:00
nicm
55eb3e4773 Make TMUX_CONF a list of files and expand leading $FOO or ~. 2019-12-10 14:22:15 +00:00
Nicholas Marriott
92ecd611f6 Check each _PATH_* define individually (Solaris has paths.h but not all of the
defines). From Eric N Vander Weele.
2019-12-03 18:53:23 +00:00
Thomas Adam
875139f5fa Merge branch 'obsd-master' 2019-12-03 12:01:26 +00:00
nicm
7826d40ff9 Style nits in function arguments. 2019-12-03 10:47:22 +00:00
Thomas Adam
edf96b06a5 Merge branch 'obsd-master' 2019-12-02 20:01:24 +00:00
nicm
ec1b8e5f05 Remove client menu, I don't think it adds anything. 2019-12-02 19:25:52 +00:00
Nicholas Marriott
2173365f4f Fix keys in CHANGES. 2019-12-01 21:15:21 +00:00
Nicholas Marriott
7836779e21 Merge branch '3.0a-rc' 2019-12-01 09:00:46 +00:00
Nicholas Marriott
25ae028695 Add to CHANGES. 2019-12-01 08:53:10 +00:00
nicm
1b0cc4503e REG_STARTEND is not portable, but it turns out we don't actually need
it. From Evan Green, GitHub issue 1982.
2019-12-01 08:52:47 +00:00
Nicholas Marriott
a52fe9cf7f Add to CHANGES. 2019-12-01 08:50:45 +00:00
Thomas Adam
866b053f25 Merge branch 'obsd-master' 2019-11-29 18:01:24 +00:00
nicm
48897fbc44 Fix respawn-pane/window if default-command is set, reported by Janos Barbero. 2019-11-29 17:21:32 +00:00
nicm
67d995d100 If a window appears in only one attached session, there is no point in
worrying about which is the latest client (there is only one).
2019-11-29 16:04:07 +00:00
nicm
ad98fad9a3 Do not crash when a format doesn't exist, reported by Thomas Sattler. 2019-11-28 22:23:40 +00:00
Thomas Adam
34084fe666 Merge branch 'obsd-master' 2019-11-28 22:01:24 +00:00
nicm
c5d74b1deb Do not crash when a format doesn't exist, reported by Thomas Sattler. 2019-11-28 21:18:38 +00:00
Nicholas Marriott
3bb11ec484 Revert "add missing definition"
This reverts commit 743939ec84.
2019-11-28 14:36:32 +00:00
Thomas Adam
743939ec84 add missing definition 2019-11-28 12:31:43 +00:00
Nicholas Marriott
e00730d149 Fix bad merge. 2019-11-28 12:30:43 +00:00
nicm
640149337f Missing after-kill-pane option. 2019-11-28 12:22:32 +00:00
Thomas Adam
5f5f029e3b Merge branch 'obsd-master' 2019-11-28 12:18:41 +00:00
nicm
fa409194d3 Missing after-kill-pane option. 2019-11-28 10:55:45 +00:00
nicm
08e2828592 Parse out DA features. 2019-11-28 10:17:22 +00:00
nicm
bc5881c4d2 Long lines and spacing fixes. 2019-11-28 09:56:25 +00:00
nicm
c416fe0da4 Add xrecallocarray. 2019-11-28 09:51:58 +00:00
nicm
9ea05b2fb3 Bump the escape sequence timeout to five seconds to allow for longer
legitimate sequences.
2019-11-28 09:50:09 +00:00
nicm
2349b1dbef Make a best effort to set xpixel and ypixel for each pane and add
formats for them.
2019-11-28 09:45:15 +00:00
nicm
067604bf8c Store xpixel/ypixel from TIOCGWINSZ and add formats. 2019-11-28 09:05:34 +00:00
nicm
7fb8eec8f1 status-left and status-right need push-default also, reported by Eric
Pruitt in GitHub issue 1989.
2019-11-28 08:38:04 +00:00
Thomas Adam
c13838436e Merge branch 'obsd-master' 2019-11-27 22:01:24 +00:00
Nicholas Marriott
7a30e6b941 Merge branch '3.0-rc' into 3.0a-rc 2019-11-27 20:55:19 +00:00
nicm
eb4d60b1ce REG_STARTEND is not portable, but it turns out we don't actually need
it. From Evan Green, GitHub issue 1982.
2019-11-27 20:54:30 +00:00
Nicholas Marriott
0134574a67 3.0a. 2019-11-27 20:49:59 +00:00
Nicholas Marriott
c942f11ba8 Use a malloc'd buffer for lsk since commands can be very long, from Gregory Pakosz. 2019-11-27 20:48:30 +00:00
nicm
5afe7eb850 Do not lazily use BUFSIZ for "I don't care what size" when building
strings because it is only guaranteed to be 256 bytes and even the
default 1024 is not always enough. Reported by Gregory Pakosz.
2019-11-27 20:48:03 +00:00
nicm
b2fd161b07 Do not crash trying to fix layout size if only one cell, from Azat Khuzhin. 2019-11-27 20:47:27 +00:00
Thomas Adam
d0655f321f Merge branch 'obsd-master' 2019-11-26 16:01:25 +00:00
nicm
fef8ee23c0 Add default # and * binding with vi(1) keys. 2019-11-26 15:35:56 +00:00
Nicholas Marriott
c16faa4fed Fixes to CHANGES. 2019-11-26 14:12:05 +00:00
Nicholas Marriott
bbcb199174 3.0 version. 2019-11-26 13:16:51 +00:00
nicm
47c0405b33 Some old tmux versions can sometimes generate layout strings which have
the incorrect size for the top cell. Previously tmux didn't care but now
that panes can be partly hidden, the size matters and is checked more
strictly. So add some code to fix up the most common problem and a
sanity check to reject layouts with any other size problems. Reported by
Aleksandrs Ledovskis in GitHub issue 1930.
2019-11-26 13:14:00 +00:00
Thomas Adam
f378a0b24d Merge branch 'obsd-master' 2019-11-26 00:01:25 +00:00
nicm
58f870ef6e Don't use motion flag uninitialized. 2019-11-25 22:38:36 +00:00
Thomas Adam
eaf526b1ea Merge branch 'obsd-master' 2019-11-25 22:01:56 +00:00
nicm
87a11a9214 Fix a warning in previous. 2019-11-25 20:43:32 +00:00
nicm
c2fde58701 Do not clear search marks on cursor movement with vi(1) keys, from Eric
Pruitt in GitHub issue 1985.
2019-11-25 20:42:18 +00:00
Thomas Adam
daa93b3fdc Merge branch 'obsd-master' 2019-11-25 16:01:27 +00:00
nicm
1ebd8c1234 Add p format modifier for padding to width. 2019-11-25 15:04:15 +00:00
nicm
5d0504ee11 Allow multiple substitutions in a single format. 2019-11-25 15:02:48 +00:00
Thomas Adam
81d4f95c2f Merge branch 'obsd-master' 2019-11-24 20:01:24 +00:00
nicm
20c1f1aec6 Only substitute patterns starting with ^ once. 2019-11-24 18:37:23 +00:00
Thomas Adam
82d0d85675 Merge branch 'obsd-master' 2019-11-20 12:01:23 +00:00
nicm
3c312a9150 Do not check the client readonly flag when there is no client, GitHub issue 1980. 2019-11-20 11:42:51 +00:00
Nicholas Marriott
0ed96c4609 Update CHANGES. 2019-11-18 12:56:24 +00:00
Thomas Adam
0d3f306c8e Merge branch 'obsd-master' 2019-11-18 10:01:25 +00:00
nicm
350a434939 Add -f for full size to join-pane (like split-window), from Theo Buehler. 2019-11-18 09:43:31 +00:00
nicm
4bc445f080 Keep modifiers on backspace when translating it. 2019-11-18 09:42:09 +00:00
Thomas Adam
dbdff241b2 Merge branch 'obsd-master' 2019-11-15 12:01:27 +00:00
nicm
5dfe9db788 Do not add path if it is NULL, duh. 2019-11-15 11:21:32 +00:00
nicm
f3dc38dcae Handle OSC 7 (a VTE extension) and put the result in a new format (pane_path). 2019-11-15 11:16:53 +00:00
Thomas Adam
48cbbb8757 Merge branch 'obsd-master' 2019-11-14 18:01:24 +00:00
nicm
1f966c495c Change window-size default from smallest to latest. 2019-11-14 16:23:23 +00:00
Thomas Adam
b67fd8f472 Merge branch 'obsd-master' 2019-11-14 16:01:25 +00:00
nicm
16b7719418 Fix parsing of DA with only one argument in the response and add 65 for VT520. 2019-11-14 15:37:19 +00:00
Thomas Adam
518a687886 Merge branch 'obsd-master' 2019-11-14 10:01:29 +00:00
nicm
2dbf062a89 Change new-session -A without a session name (that is, no -s option
also) to attach to the best existing session like attach-session rather
than creating a new one.
2019-11-14 08:00:30 +00:00
nicm
eb399e64d5 CUB and CUF are also limited by the margins so use CUP instead when
margins are enabled (we already do this for linefeed).
2019-11-14 07:56:32 +00:00
nicm
08b07b1a08 Add an option to set the key sent by backspace for those whose system
uses ^H rather than ^?. GitHub issue 1969.
2019-11-14 07:55:01 +00:00
Thomas Adam
eb215d3d3f Merge branch 'obsd-master' 2019-11-07 08:01:26 +00:00
nicm
c225262e13 Add -F flag to send-keys to expand formats in search-backward and
forward copy mode commands, this makes it easier to use the cursor_word
and cursor_line formats. From Anindya Mukherjee in GitHub issue 1964.
2019-11-07 07:11:25 +00:00
Thomas Adam
4408df1e8a Merge branch 'obsd-master' 2019-11-01 22:01:24 +00:00
nicm
bad95db878 Limit lazy resize to panes in attached sessions only - those in
unattached are likely to have been resized by something like
split-window where the user probably wants the resize to happen
immediately. GitHub issue 1963.
2019-11-01 20:26:21 +00:00
Thomas Adam
4fc8741794 Merge branch 'obsd-master' 2019-11-01 10:01:25 +00:00
nicm
d9c95c900c Handle the various different forms of rgb colour strings. 2019-11-01 09:09:53 +00:00
Nicholas Marriott
a1006db91b Create FUNDING.yml 2019-10-29 16:59:15 +00:00
Thomas Adam
57948a0dfc Merge branch 'obsd-master' 2019-10-28 10:01:25 +00:00
nicm
ccdebead79 Start with empty rather than NULL window name to avoid NULL printf if
window_name is evaluated early. Reported by Mikolaj Kucharski.
2019-10-28 09:07:59 +00:00
Thomas Adam
4e5f80dc62 Merge branch 'obsd-master' 2019-10-23 16:01:25 +01:00
nicm
6700018ce5 Document Any key, from Jason Felice. 2019-10-23 14:10:13 +00:00
Thomas Adam
b5de0a20d8 Merge branch 'obsd-master' 2019-10-23 10:01:27 +01:00
nicm
f7fb5df543 Use the existing code in format.c to add foramts for word and line at
cursor position in copy mode, from Anindya Mukherjee.
2019-10-23 07:42:05 +00:00
Thomas Adam
004ee66227 Merge branch 'obsd-master' 2019-10-19 22:01:25 +01:00
nicm
56e5067c46 Add formats for cursor and selection position in copy mode, from Jason Felice. 2019-10-19 19:20:14 +00:00
Thomas Adam
1b96902d73 Merge branch 'obsd-master' 2019-10-19 16:01:24 +01:00
nicm
2cb268d51b Do not crash trying to fix layout size if only one cell, from Azat Khuzhin. 2019-10-19 12:40:42 +00:00
Thomas Adam
fb7ce5b5d5 Merge branch 'obsd-master' 2019-10-15 10:01:28 +01:00
nicm
9fd62efcf0 Rewrite options_array_set to be clearer and remove a spurious warning
with newer GCC. From Ben Boeckel.
2019-10-15 08:30:36 +00:00
nicm
0c5e9c6efa Add support for percentage sizes for resize-pane ("-x 10%"). Also change
split-window and join-pane -l to accept similar percentages and
deprecate -p. From Anindya Mukherjee.
2019-10-15 08:25:37 +00:00
Thomas Adam
eb57cbcc29 Merge branch 'obsd-master' 2019-10-14 12:01:26 +01:00
nicm
b598bbcc2e Do not crash with pane_current_command if the pane is newly created and
has no shell set, from Thomas Adam.
2019-10-14 09:24:06 +00:00
nicm
f18cd5b19c Turn automatic-rename back on if the rename escape sequence is used with
an empty name, GitHub issue 1921.
2019-10-14 09:19:40 +00:00
nicm
bbe8ebf9c2 Some old tmux versions can sometimes generate layout strings which have
the incorrect size for the top cell. Previously tmux didn't care but now
that panes can be partly hidden, the size matters and is checked more
strictly. So add some code to fix up the most common problem and a
sanity check to reject layouts with any other size problems. Reported by
Aleksandrs Ledovskis in GitHub issue 1930.
2019-10-14 09:16:48 +00:00
nicm
68d59a16ce Memory leaks, from Igor Wong in GitHub issue 1934. 2019-10-14 08:38:07 +00:00
Thomas Adam
7323ffeef2 Merge branch 'obsd-master' 2019-10-07 10:01:24 +01:00
nicm
4e2cc0ae2a Fix respawn-pane/window if default-command is set, reported by Janos Barbero. 2019-10-07 07:14:07 +00:00
Thomas Adam
341b330a04 Merge branch 'obsd-master' 2019-10-03 14:01:23 +01:00
Thomas Adam
eeedb43ae8 Merge branch 'obsd-master' 2019-10-03 12:01:25 +01:00
nicm
02253d1e5c Use a malloc'd buffer for lsk since commands can be very long, from Gregory Pakosz. 2019-10-03 10:39:08 +00:00
nicm
f4c7141f5d Do not lazily use BUFSIZ for "I don't care what size" when building
strings because it is only guaranteed to be 256 bytes and even the
default 1024 is not always enough. Reported by Gregory Pakosz.
2019-10-03 10:24:05 +00:00
Thomas Adam
8cf21feefd Merge branch 'obsd-master' 2019-09-25 22:01:24 +01:00
nicm
bbd1032a2a Style and line length nits. 2019-09-25 19:05:59 +00:00
nicm
f0712a7569 Do not set uninitialized signal mask when creating an empty pane. 2019-09-25 15:56:53 +01:00
nicm
9d1cecea8e Up and Down are already used, use < and > instead. 2019-09-25 15:56:39 +01:00
nicm
e6995196f2 Change menu key bindings to Up and Down and also close it on any mouse
press if opened by key.
2019-09-25 15:56:30 +01:00
nicm
a74e37d32d Mouse formats don't work in copy mode so don't try to use them. 2019-09-25 15:54:52 +01:00
Thomas Adam
d89510e1aa Merge branch 'obsd-master' 2019-09-25 00:01:25 +01:00
nicm
e3359f8349 Some minor performance improvements - most notably, don't search the
input state table if the next character matches the same state as before.
2019-09-24 20:44:58 +00:00
Thomas Adam
2534aa4d2d Merge branch 'obsd-master' 2019-09-24 18:01:24 +01:00
nicm
e8adcae0f2 Couple of bits of minor cleanup. 2019-09-24 15:52:14 +00:00
nicm
48c684cbc2 Mouse formats don't work in copy mode so don't try to use them. 2019-09-24 14:50:08 +00:00
nicm
6f8f4bb206 Make select-pane -P set window-active-style also to match previous
behaviour, reported by Thomas Sattler.
2019-09-24 12:20:25 +01:00
Thomas Adam
cb1a626692 Merge branch 'obsd-master' 2019-09-24 12:01:23 +01:00
nicm
232050830b Make select-pane -P set window-active-style also to match previous
behaviour, reported by Thomas Sattler.
2019-09-24 09:58:58 +00:00
Thomas Adam
dd254b90d7 Merge branch 'obsd-master' 2019-09-23 18:01:24 +01:00
nicm
77deef733b Use the correct size for new windows when window-size is latest,
reported by Vamsi Krishna Avula in GitHub issue 1917.
2019-09-23 15:41:11 +00:00
Thomas Adam
24ab1bc714 Merge branch 'obsd-master' 2019-09-19 12:01:30 +01:00
nicm
647887b794 Add a "latest" window-size option which tries to size windows based on
the most recently used client. From Tommie Gannert in GitHub issue 1869
based on earlier changes from me.
2019-09-19 09:02:30 +00:00
nicm
d018477359 Do not use bright when emulating 256 colours on an 8 colour terminal
because it is also bold on some terminals. GitHub issue 1914.
2019-09-19 08:56:37 +00:00
Thomas Adam
827913102e Merge branch 'obsd-master' 2019-09-18 18:01:23 +01:00
nicm
1ee40307b5 Up and Down are already used, use < and > instead. 2019-09-18 15:09:05 +00:00
Thomas Adam
d30b612809 Merge branch 'obsd-master' 2019-09-18 14:01:24 +01:00
nicm
697f938355 Do not set uninitialized signal mask when creating an empty pane. 2019-09-18 11:37:58 +00:00
Thomas Adam
5ae2d421fb Merge branch 'obsd-master' 2019-09-16 16:01:23 +01:00
nicm
83be3afc54 Change menu key bindings to Up and Down and also close it on any mouse
press if opened by key.
2019-09-16 13:27:14 +00:00
Nicholas Marriott
c739772436 3.0-rc5. 2019-09-16 09:01:56 +01:00
Nicholas Marriott
7a1abd66e7 These are in 3.0 now. 2019-09-16 09:01:27 +01:00
Nicholas Marriott
d70d24d360 Merge branch '3.0-rc' 2019-09-16 09:01:09 +01:00
Nicholas Marriott
f27cac585c Add to CHANGES. 2019-09-16 09:00:56 +01:00
nicm
846d57e1b8 Make client exit if pane where input is going is closed. 2019-09-16 09:00:08 +01:00
Nicholas Marriott
54670d898f Missing headers from compat/asprintf.c, from cyyever at outlook dot com. 2019-09-16 08:59:57 +01:00
nicm
c45b255a88 It is not longer necessary to double-escape ; in %%%, problem reported
by Theo Buehler.
2019-09-16 08:59:49 +01:00
nicm
5e4f371408 Fix swap-window -d to work as intended, GitHub issue 1879 from Sam Stuewe. 2019-09-16 08:59:36 +01:00
nicm
7e4439beb7 Remove check for same size - size has already been changed so this
breaks reflow.
2019-09-16 08:58:35 +01:00
Nicholas Marriott
74f150670a In the right place. 2019-09-16 08:57:56 +01:00
Nicholas Marriott
3c355ec3b0 Add to CHANGES. 2019-09-16 08:57:22 +01:00
Thomas Adam
d346d692eb Merge branch 'obsd-master' 2019-09-16 00:01:25 +01:00
nicm
63e07b245f Add push-default and pop-default in styles to change the default colours
and attributes and use them to restore the previous behaviour of
window-status-style being the default for window-status-format in the
status line. From John Drouhard in GitHub issue 1912.
2019-09-15 21:42:57 +00:00
Thomas Adam
a5e36a4bd6 Merge branch 'obsd-master' 2019-09-13 04:01:25 +01:00
Thomas Adam
658ecb0777 Merge branch 'obsd-master' 2019-09-11 16:48:58 +01:00
nicm
a23ce1b45f Add window_marked_flag, GitHub issue 1887. 2019-09-11 06:43:17 +00:00
nicm
0feae4d8ae Make client exit if pane where input is going is closed. 2019-09-10 19:35:34 +00:00
nicm
4b7e97ba53 Set up format tree for %if, GitHub issue 1896. 2019-09-10 07:50:33 +00:00
nicm
b6b7486423 Clarify server options slightly. 2019-09-09 11:47:25 +00:00
Thomas Adam
2e90841f2e Merge branch 'obsd-master' 2019-09-09 12:02:32 +01:00
nicm
b31515fec3 Add cursor-down-and-cancel, from Mark Kelly. 2019-09-09 08:01:21 +00:00
Nicholas Marriott
9a476c5f29 Fix "make ctags", GitHub issue 1888. 2019-09-08 21:42:26 +01:00
Nicholas Marriott
5423bf6db8 Missing headers from compat/asprintf.c, from cyyever at outlook dot com. 2019-09-08 21:29:22 +01:00
Thomas Adam
648471ecee Merge branch 'obsd-master' 2019-08-29 18:02:29 +01:00
nicm
7ce8135138 It is not longer necessary to double-escape ; in %%%, problem reported
by Theo Buehler.
2019-08-29 07:13:48 +00:00
Thomas Adam
4fa1f961f3 Merge branch 'obsd-master' 2019-08-28 20:02:24 +01:00
nicm
df0334d3b3 The resize event was never deciding to actually resize the pane if there
was output in the pane faster than the timer would fire, so change how
it works to only defer the timer again if the pane was actually resized
within the last timer period. Reported by James Tai in GitHub issue
1880.
2019-08-28 07:34:32 +00:00
Thomas Adam
6640790bdc Merge branch 'obsd-master' 2019-08-27 10:02:31 +01:00
nicm
39c55d5b6f Fix swap-window -d to work as intended, GitHub issue 1879 from Sam Stuewe. 2019-08-26 16:35:41 +00:00
nicm
79f09b4d85 Add support for the SD (scroll down) escape sequence, GitHub issue 1861. 2019-08-26 17:28:24 +01:00
nicm
e85ea9f67d grid_view_delete_cells does need to clear, GitHub issue 1871. 2019-08-16 19:34:29 +01:00
Thomas Adam
2db9a18362 Merge branch 'obsd-master' 2019-08-16 17:02:29 +01:00
nicm
37583f0a69 Add a flag to reverse sort in the various choose modes, from Benjamin
Poirier in GitHub issue 1875.
2019-08-16 11:49:12 +00:00
Thomas Adam
06ad86053c Merge branch 'obsd-master' 2019-08-16 11:02:31 +01:00
nicm
5644d37876 grid_view_delete_cells does need to clear, GitHub issue 1871. 2019-08-16 08:52:25 +00:00
Thomas Adam
ed0f2831b4 Merge branch 'obsd-master' 2019-08-15 11:02:48 +01:00
nicm
21fae50089 Default to previous search string for search-forward and
search-backward, from Leah Neukirchen.
2019-08-14 10:02:24 +00:00
nicm
0f243f0388 Add -Z flag to rotate-window, select-pane, swap-pane, switch-client to
preserve zoomed state. GitHub issue 1839.
2019-08-14 09:58:31 +00:00
Thomas Adam
9b3fefc435 Merge branch 'obsd-master' 2019-08-06 07:02:33 +01:00
nicm
45f4ff5485 Add support for the SD (scroll down) escape sequence, GitHub issue 1861. 2019-08-05 06:42:02 +00:00
Nicholas Marriott
eb8eeab05e Merge branch '3.0-rc' 2019-08-01 18:52:44 +01:00
nicm
26f2740110 xterm 348 now disables margins when resized, so send DECLRMM again. 2019-08-01 18:52:33 +01:00
Thomas Adam
a2d7f380b2 Merge branch 'obsd-master' 2019-08-01 17:02:26 +01:00
nicm
c4744620af Correctly wrap search in copy mode even if at the very top left, GitHub
issue 1845.
2019-08-01 14:31:39 +00:00
nicm
3d660b0023 Select the correct word for select-word when already at the start of a
word, GitHub issue 1820.
2019-08-01 14:30:31 +00:00
nicm
49bf7dc77e xterm 348 now disables margins when resized, so send DECLRMM again. 2019-08-01 11:45:34 +00:00
Thomas Adam
11315c589a Merge branch 'obsd-master' 2019-08-01 11:02:26 +01:00
nicm
2db5f9c215 Add -N to capture-pane to preserve trailing spaces, from Leon Winter. 2019-08-01 08:42:34 +00:00
Thomas Adam
cea87758e7 Merge branch 'obsd-master' 2019-08-01 09:02:26 +01:00
nicm
58bbce09e2 Remove check for same size - size has already been changed so this
breaks reflow.
2019-08-01 07:08:13 +00:00
Thomas Adam
900e583c7a Merge branch 'obsd-master' 2019-07-30 13:02:26 +01:00
nicm
e698ee01dd Reorder some text in the windows & panes section and add some better
explanation of modes.
2019-07-30 10:10:02 +00:00
Nicholas Marriott
2dd9a4fb9c Bump version again. 2019-07-29 11:03:15 +01:00
Nicholas Marriott
b8b865fb17 Bump 3.0-rc up to master. 2019-07-29 10:53:04 +01:00
Nicholas Marriott
da552eb73b Merge branch 'master' into 3.0-rc 2019-07-29 10:51:30 +01:00
Thomas Adam
b90a9fcd13 Merge branch 'obsd-master' 2019-07-26 23:02:27 +01:00
Nicholas Marriott
e19622b8db Add to CHANGES. 2019-07-26 21:22:53 +01:00
nicm
8f40f791d9 Change "lost server" message to "server exited unexpectedly", from Neal
McBurnett in GitHub issue 1857.
2019-07-26 20:08:40 +00:00
Thomas Adam
bb9a123ddd Merge branch 'obsd-master' 2019-07-24 23:02:30 +01:00
nicm
90dba3ec66 Mark pane status line jobs with FORMAT_STATUS also so it redraws when
they finish, GitHub issue 1852.
2019-07-24 21:16:17 +00:00
Thomas Adam
47712fc113 Merge branch 'obsd-master' 2019-07-19 09:02:26 +01:00
nicm
bf6d1aeaa4 Add a few vi(1) key aliases, from D Ben Knoble. 2019-07-19 07:20:51 +00:00
nicm
df7b5292ab More man page fixes from lacygoill at lacygoill dot me, GitHub issue
1805.
2019-07-19 07:18:03 +00:00
Thomas Adam
7e7c8faa34 Merge branch 'obsd-master' 2019-07-17 21:02:26 +01:00
nicm
f6a9f6b4ad Use the right client for if -b. 2019-07-17 17:49:23 +00:00
nicm
9e7774bb96 Clear overlay on normal key press. 2019-07-17 17:46:51 +00:00
Nicholas Marriott
7c78ebce45 cc, make, libevent, ncurses are dependencies for all builds so no need to list
them for VCS build.
2019-07-17 08:57:22 +01:00
Nicholas Marriott
80b82c8d14 Mention dependencies earlier. 2019-07-17 08:56:10 +01:00
Thomas Adam
8e33cc61b1 Merge branch 'obsd-master' 2019-07-16 17:02:25 +01:00
nicm
99852f8401 Fix check for wrapping when redrawing entire lines, GitHub issue 1836. 2019-07-16 14:11:52 +00:00
Thomas Adam
b749a39cdb Merge branch 'obsd-master' 2019-07-16 13:02:24 +01:00
nicm
b89f2f28bb Fix grid clear code to correctly clear with the default background
colour rather than ending up with the used count higher than the total
size, GitHub issue 1829.
2019-07-16 10:30:56 +00:00
Thomas Adam
a786a59176 Merge branch 'obsd-master' 2019-07-15 21:02:26 +01:00
nicm
eac055bfaf Simplify code to work out if an extra line is needed in the cell. 2019-07-15 18:43:32 +00:00
nicm
6ceeceab7a Make layout_fix_offsets take a window like layout_fix_panes. 2019-07-15 18:25:07 +00:00
Thomas Adam
c9216493cf Merge branch 'obsd-master' 2019-07-10 17:02:25 +01:00
nicm
91b6145499 The command item changes so can't keep getting the target out of it, need to use
the one from the first item. Fixes crash reported by M Kelly.
2019-07-10 14:33:24 +00:00
Thomas Adam
9cbbdb90bf Merge branch 'obsd-master' 2019-07-10 13:02:26 +01:00
nicm
f4d858e7a0 Add -F to refresh-client to specify flags for control clients - one flag
at the moment, no-output which turns off forwarding pane output. From
Thomas Adam. GitHub issue 1834.
2019-07-10 11:20:10 +00:00
Thomas Adam
98ef369b27 Merge branch 'obsd-master' 2019-07-09 17:02:26 +01:00
nicm
fc2016dbb6 Add a -H flag to send-keys to send literal keys given as hex numbers
(needed for control clients to send mouse sequences). Also add some
format flags for UTF-8 and SGR mouse mode. Requested by Bradley Smith in
GitHub issues 1832 and 1833.
2019-07-09 14:03:12 +00:00
Thomas Adam
177599efb7 Merge branch 'obsd-master' 2019-07-09 15:02:25 +01:00
nicm
ad11d49d64 Do not leak empty lines, GitHub issue 1824. 2019-07-09 13:19:36 +00:00
nicm
b74b8be680 Add j and k for navigation in menus, GitHub issue 1828. 2019-07-09 12:44:47 +00:00
Thomas Adam
ab244cc7ad Merge branch 'obsd-master' 2019-07-08 23:02:26 +01:00
nicm
a4be028b76 Clear search marks before resize, GitHub issue 1823. 2019-07-08 20:29:11 +00:00
Thomas Adam
29b2d07b6b Merge branch 'obsd-master' 2019-07-08 15:02:25 +01:00
nicm
cbe781203f Use the clear history function for the 3J sequence rather than doing it manually. 2019-07-08 11:38:14 +00:00
Thomas Adam
3a4cf62aa9 Merge branch 'obsd-master' 2019-07-06 23:02:26 +01:00
nicm
ddf53d6e4e Correctly adjust mouse position if the status line is at the top and
more than one line. GitHub issue 1822.
2019-07-06 20:56:34 +00:00
nicm
3635b3cd6c Correctly clear underscore colour in grid_get_cell1, also fix struct
grid_cell to avoid padding. Fixes increased memory use reported by Suraj
N Kurapati.
2019-07-06 20:37:29 +00:00
Thomas Adam
bc112a8c89 Merge branch 'obsd-master' 2019-07-05 11:02:26 +01:00
nicm
55c694a467 Do not use uninitialized buffer name. 2019-07-05 07:52:27 +00:00
Thomas Adam
be5af704ad Merge branch 'obsd-master' 2019-07-02 23:02:26 +01:00
nicm
6a489fa7f6 Command prompt key presses need to avoid the command queue, GitHub issue
1817. Also a tmux.1 fix from jmc.
2019-07-02 20:09:19 +00:00
Thomas Adam
b9fbf02ad5 Merge branch 'obsd-master' 2019-07-01 09:02:25 +01:00
nicm
2da050413c Add a "fill" style attribute to clear the entire format drawing area in
a colour, GitHub issue 1815.
2019-07-01 06:56:00 +00:00
Thomas Adam
abcd4bd246 Merge branch 'obsd-master' 2019-06-30 21:02:26 +01:00
nicm
cf30e0f935 Do not double free window if pane fails to start. 2019-06-30 19:21:53 +00:00
Thomas Adam
68c2fc6824 Merge branch 'obsd-master' 2019-06-28 17:02:26 +01:00
deraadt
4ff7bc3eb3 When system calls indicate an error they return -1, not some arbitrary
value < 0.  errno is only updated in this case.  Change all (most?)
callers of syscalls to follow this better, and let's see if this strictness
helps us in the future.
2019-06-28 13:35:05 +00:00
Thomas Adam
b6b4f86cfc Merge branch 'obsd-master' 2019-06-28 09:02:24 +01:00
deraadt
6ce38b7395 asprintf returns -1, not an arbitrary value < 0. Also upon error the
(very sloppy specification) leaves an undefined value in *ret, so it is
wrong to inspect it, the error condition is enough.
discussed a little with nicm, and then much more with millert until we
were exasperated
2019-06-28 05:44:09 +00:00
Thomas Adam
a07df21e79 Merge branch 'obsd-master' 2019-06-27 21:02:25 +01:00
jmc
b434692db2 minor eol issues; 2019-06-27 17:29:16 +00:00
Thomas Adam
e483ce138f Merge branch 'obsd-master' 2019-06-27 17:02:26 +01:00
nicm
dae2868d12 Add support for underscore colours with Setulc capability, mostly from
Kai Moschcau.
2019-06-27 15:17:41 +00:00
nicm
5a501a8ae2 Pass keys that aren't 0-9 on to normal key processing when display-panes
is active (restores previous behaviour).
2019-06-27 15:49:43 +01:00
Thomas Adam
c4a9299956 Merge branch 'obsd-master' 2019-06-26 21:02:26 +01:00
nicm
3a6d90adad Fix a typo in window_pane_find_down (w not wp) and a missing PANE_STATUS_TOP. 2019-06-26 18:44:22 +00:00
nicm
87ea14328c Pass keys that aren't 0-9 on to normal key processing when display-panes
is active (restores previous behaviour).
2019-06-26 18:28:31 +00:00
Thomas Adam
f797ac9ff6 Merge branch 'obsd-master' 2019-06-26 15:02:26 +01:00
nicm
c599ad63f8 Log window and pane resizes. 2019-06-26 13:05:24 +00:00
nicm
80d76612b8 Fix some comments (top/bottom not left/right). 2019-06-26 13:05:06 +00:00
nicm
d83f356218 Add #define for the pane status line option position numbers. 2019-06-26 13:03:47 +00:00
Thomas Adam
a1d4bf20f7 Merge branch 'obsd-master' 2019-06-24 13:02:26 +01:00
nicm
20b938bcb1 Expand arguments to C and s format modifiers (matches m which already expands). 2019-06-24 10:04:29 +00:00
Thomas Adam
c14b0d7c00 Merge branch 'obsd-master' 2019-06-24 11:02:26 +01:00
nicm
bdab595095 Trim trailing spaces when matching. 2019-06-24 08:20:02 +00:00
Thomas Adam
50c4c5917d Merge branch 'obsd-master' 2019-06-23 13:02:26 +01:00
nicm
f1100f97f7 Do not always set scope for panes because the window check might fail,
GitHub issue 1810.
2019-06-23 10:00:29 +00:00
Thomas Adam
69a2f73449 Merge branch 'obsd-master' 2019-06-21 09:02:25 +01:00
nicm
e3c2772d2f Man page fixes from lacygoill at lacygoill dot me. 2019-06-21 07:11:01 +00:00
Thomas Adam
70775b3c28 Merge branch 'obsd-master' 2019-06-20 23:02:28 +01:00
nicm
1d8e545bc1 Add -r to find-window for regex instead of fnmatch. 2019-06-20 20:31:04 +00:00
Thomas Adam
c4a92e5799 Merge branch 'obsd-master' 2019-06-20 21:02:27 +01:00
nicm
97a317a656 Need to always check focus even if not current window. 2019-06-20 19:29:38 +00:00
nicm
cb5e681ef6 FIx return of options_scope_from_name on error. 2019-06-20 18:13:04 +00:00
Thomas Adam
5aae58295e Merge branch 'obsd-master' 2019-06-20 19:02:27 +01:00
Thomas Adam
4a44ae06bf Merge branch 'obsd-master' 2019-06-20 17:02:26 +01:00
nicm
f4e835754c Fix how regex substitution works with empty matches. 2019-06-20 15:40:14 +00:00
Thomas Adam
f8ad72b2ee Merge branch 'obsd-master' 2019-06-20 15:02:26 +01:00
nicm
fc1df91e03 allow-rename and alternate-screen can be pane options. 2019-06-20 13:40:22 +00:00
nicm
c1573727f0 Still need to walk the options tree for user options. 2019-06-20 13:39:17 +00:00
Nicholas Marriott
a0e2c1b4ca Add to CHANGES. 2019-06-20 13:08:22 +01:00
nicm
5f92f92908 Add a per-pane option set. Pane options inherit from window options (so
there should be no change to existing behaviour) and are set and shown
with set-option -p and show-options -p.

Change remain-on-exit and window-style/window-active-style to be pane
options (some others will be changed later).

This makes select-pane -P and -g unnecessary so no longer document them
(they still work) and no longer document set-window-option and
show-window-options in favour of set-option -w and show-options -w.
2019-06-20 11:59:59 +00:00
Thomas Adam
adca856806 Merge branch 'obsd-master' 2019-06-20 11:02:28 +01:00
Thomas Adam
03945276f7 Merge branch 'obsd-master' 2019-06-20 09:02:26 +01:00
nicm
c1ede507d9 Add a helper function to work out option table from name. 2019-06-20 07:41:29 +00:00
nicm
cd1fc42df6 Add a -A flag to show-options to show parent options as well. 2019-06-20 07:10:56 +00:00
nicm
ae541287d3 Expand command formats in %if and move the config file loading later (to
when the first client has identified) so all the client formats are
available, fixes problems reported by Thomas Sattler.
2019-06-20 06:51:36 +00:00
Nicholas Marriott
b3ca410bc3 Use KERN_PROC_CWD on NetBSD, from Leonardo Taccari. 2019-06-20 06:57:37 +01:00
Nicholas Marriott
ec151b79ec Merge branch '3.0-rc' 2019-06-18 19:43:20 +01:00
nicm
797042584e Handle comments more correctly inside {}, from Avi Halachmi. 2019-06-18 19:43:13 +01:00
Nicholas Marriott
df07723e20 Add a config. 2019-06-18 19:42:52 +01:00
Thomas Adam
ee9bc355f5 Merge branch 'obsd-master' 2019-06-18 13:02:28 +01:00
nicm
250fdd08be Handle comments more correctly inside {}, from Avi Halachmi. 2019-06-18 11:17:40 +00:00
nicm
9272fe36e2 Add a cmdq_continue function rather than twiddling the flag directly. 2019-06-18 11:08:42 +00:00
Thomas Adam
5895f1d9f7 Merge branch 'obsd-master' 2019-06-15 09:02:26 +01:00
Nicholas Marriott
fadbf497a4 Merge branch '3.0-rc' 2019-06-15 07:45:58 +01:00
Nicholas Marriott
748633c887 Remove a stray abort. 2019-06-15 07:45:41 +01:00
Nicholas Marriott
d53c2d0ebe Merge branch '3.0-rc' 2019-06-15 07:44:58 +01:00
Nicholas Marriott
08f55414e1 Remove cmd-list.c line in master. 2019-06-15 07:42:49 +01:00
Nicholas Marriott
7a4a286ea2 Merge branch '3.0-rc' 2019-06-15 07:38:01 +01:00
nicm
9ae658983c Do not loop forever if a menu item contains invisible characters,
reported by Thomas Sattler.
2019-06-15 07:37:44 +01:00
nicm
03da0ced46 Use the right format modifier when comparing, and remove a couple of
unused variables.
2019-06-15 06:33:48 +00:00
Thomas Adam
539a6e7fa0 Merge branch 'obsd-master' 2019-06-14 19:02:26 +01:00
nicm
c95cd9ed5e Do not loop forever if a menu item contains invisible characters,
reported by Thomas Sattler.
2019-06-14 15:35:58 +00:00
Nicholas Marriott
c22470bd14 3.0-rc3. 2019-06-14 16:17:34 +01:00
Nicholas Marriott
4c28ed4e4e Merge branch '3.0-rc' 2019-06-14 16:10:38 +01:00
Nicholas Marriott
31cb95893e #{ is no longer special. 2019-06-14 16:10:27 +01:00
Nicholas Marriott
ae83a5b010 Add to CHANGES. 2019-06-14 16:09:49 +01:00
Nicholas Marriott
29b70e2757 Merge branch '3.0-rc' 2019-06-14 16:06:20 +01:00
nicm
52b8274285 Do not crash if the environment variable is present but empty. 2019-06-14 16:06:12 +01:00
Nicholas Marriott
dcb2bb33a2 Merge branch '3.0-rc' 2019-06-14 16:05:26 +01:00
nicm
a924694820 Use the right client when working out where to save or load the buffer,
reported by kn@.
2019-06-14 16:04:57 +01:00
nicm
0a94dbe051 A couple of minor parser changes around conditions: 1) only treat #{
specially after a condition, otherwise as a comment (which is more as
most people expect) 2) allow formats to be quoted after a condition.
2019-06-14 16:04:52 +01:00
Nicholas Marriott
8da756c4f0 Restore missing functions. 2019-06-14 16:02:34 +01:00
Nicholas Marriott
7bb8ab1c0e Add a bit to {}. 2019-06-14 15:54:36 +01:00
Thomas Adam
5e9757b30b Merge branch 'obsd-master' 2019-06-14 15:51:09 +01:00
nicm
d1d3bbb458 Show filename with -v for source-file. 2019-06-14 13:34:45 +00:00
nicm
45203582ff A couple of minor parser changes around conditions: 1) only treat #{
specially after a condition, otherwise as a comment (which is more as
most people expect) 2) allow formats to be quoted after a condition.
2019-06-14 12:04:11 +00:00
Nicholas Marriott
ebc9dcb3bb Add a bit to {}. 2019-06-14 12:40:35 +01:00
Nicholas Marriott
4bbf941436 Merge branch '3.0-rc' 2019-06-14 10:34:05 +01:00
Nicholas Marriott
f31847db62 Improve description of #{. 2019-06-14 10:33:55 +01:00
nicm
f35f15b107 Use the right client when working out where to save or load the buffer,
reported by kn@.
2019-06-13 21:44:13 +00:00
nicm
eef11b64e1 Do not crash if the environment variable is present but empty. 2019-06-13 21:24:09 +00:00
jmc
b8a9c740bb tweak previous; 2019-06-13 21:04:21 +00:00
nicm
26b9a8e49b Set the cursor x at the same time as changing the y or the end of line
marker may not be redrawn.
2019-06-13 20:38:05 +00:00
nicm
3e72e98e3b Add regular expression support for the format search, match and
substitute modifiers.
2019-06-13 19:46:00 +00:00
Thomas Adam
d5902eeae9 Merge branch 'obsd-master' 2019-06-12 11:02:25 +01:00
nicm
7e6a26cc9d Do not use $TMUX to find the session because for windows in multiple
sessions it is wrong as often as it is right, and for windows in one
session it is pointless. Instead check TMUX_PANE to find the pane and
look for the MRU session as usual. GitHub issue 1793.
2019-06-12 09:10:29 +00:00
nicm
b12df01861 Pass target on to new commands with if -F. 2019-06-12 08:47:07 +00:00
nicm
9d42bd328c Do not always resize the window back to its original size after applying
a layout, let the normal window resize process do it. This means windows
are not resized at all if window-size is manual, and are not resized
multiple times if later attached to a different size terminal.
2019-06-12 08:08:33 +00:00
nicm
e337c1ba7d Do not try to parse command when unsetting, GitHub issue 1788. 2019-06-11 15:51:30 +01:00
Thomas Adam
057c04e32a Merge branch 'obsd-master' 2019-06-11 15:02:26 +01:00
Nicholas Marriott
8e971f187a Update README.md 2019-06-11 14:27:40 +01:00
Nicholas Marriott
e8814a7e93 Add to CHANGES. 2019-06-11 14:23:47 +01:00
nicm
1a9f9c09b4 Do not resize panes unless they are in an attached, active window. From
Morten M Neergaard in GitHub issue 1782.
2019-06-11 13:09:00 +00:00
Thomas Adam
d9ad461b5e Merge branch 'obsd-master' 2019-06-09 09:02:26 +01:00
nicm
915097d312 Exiting alternate screen mode should restore cursor position and
attributes even if already outside alternate screen mode. GitHub issue
1789.
2019-06-09 06:50:24 +00:00
Thomas Adam
181841fb67 Merge branch 'obsd-master' 2019-06-09 01:02:26 +01:00
nicm
43796bf131 Do not try to parse command when unsetting, GitHub issue 1788. 2019-06-08 21:48:29 +00:00
Thomas Adam
e13c1e5320 Merge branch 'obsd-master' 2019-06-07 23:02:26 +01:00
nicm
e37f34facc Do not load the config file if the server is exiting because it failed
to start, otherwise commands like lsk which start the server again can
end up looping infinitely. Also make the first client exit
correctly. Problem reported by Wael M Nasreddine.
2019-06-07 20:09:17 +00:00
Thomas Adam
c91680822d Merge branch 'obsd-master' 2019-06-05 23:02:26 +01:00
Nicholas Marriott
37bb993f53 Merge branch '3.0-rc' 2019-06-05 21:06:30 +01:00
nicm
db5a7c1740 Need to increment the argument to skip the prefix earlier, fixes
repeated incremental search in copy mode, reported by Kaushal Modi in
GitHub issue 1780.
2019-06-05 21:06:06 +01:00
Thomas Adam
1ec3fb5f30 Merge branch 'obsd-master' 2019-06-05 21:02:26 +01:00
nicm
8f40796f05 Add a -v flag to source-file to show the commands and line numbers. 2019-06-05 20:00:53 +00:00
nicm
09e90c1645 Need to increment the argument to skip the prefix earlier, fixes
repeated incremental search in copy mode, reported by Kaushal Modi in
GitHub issue 1780.
2019-06-05 19:00:36 +00:00
Nicholas Marriott
f274b1b9d7 Merge branch '3.0-rc' 2019-06-05 15:13:56 +01:00
Nicholas Marriott
53914e50b9 RC2. 2019-06-05 15:09:42 +01:00
Nicholas Marriott
e252984993 If only one of -x or -y is given, use the calculated size for the
other. Also fix some warnings. Pointed out by Ben Boeckel.
2019-06-05 06:44:08 +01:00
Thomas Adam
d3f0c72e20 Merge branch 'obsd-master' 2019-06-03 21:02:26 +01:00
nicm
4ca1de1b8b Add new-session -X and attach-session -x to send SIGHUP to parent when
detaching (like detach-client -P). From Colin Watson in GitHub issue
1773.
2019-06-03 18:28:37 +00:00
nicm
17bc11bd15 yacc(1) copies its union so it is not a good place to store
TAILQ_HEADs. Allocate them instead. Found from a problem reported by
sthen@.
2019-06-02 10:52:32 +01:00
Thomas Adam
f6933e43c2 Merge branch 'obsd-master' 2019-06-02 09:02:27 +01:00
nicm
900238a306 yacc(1) copies its union so it is not a good place to store
TAILQ_HEADs. Allocate them instead. Found from a problem reported by
sthen@.
2019-06-02 07:10:15 +00:00
Thomas Adam
027a7ac829 Merge branch 'obsd-master' 2019-06-01 19:02:26 +01:00
nicm
2c6c3a1d27 If only one of -x or -y is given, use the calculated size for the
other. Pointed out by Ben Boeckel.
2019-06-01 16:21:37 +00:00
Thomas Adam
8382ae65b7 Merge branch 'obsd-master' 2019-06-01 09:02:27 +01:00
Nicholas Marriott
ec690208a3 Move link. 2019-06-01 08:07:22 +01:00
Nicholas Marriott
b28b8312f2 Mention CHANGES. 2019-06-01 08:05:55 +01:00
Nicholas Marriott
c2d79add31 Should be caps. 2019-06-01 07:28:31 +01:00
Nicholas Marriott
feff55b92f Try this instead. 2019-06-01 07:26:39 +01:00
Nicholas Marriott
3d29b97768 Link to file. 2019-06-01 07:24:57 +01:00
nicm
39ea8a2787 Need stdlib.h, from Ben Boeckel. 2019-06-01 06:20:22 +00:00
Thomas Adam
480cdedcac Merge branch 'obsd-master' 2019-06-01 01:02:25 +01:00
Nicholas Marriott
88ee5a1a00 Add a crashing config. 2019-05-31 22:50:30 +01:00
nicm
2c5f3074bc Fix warnings, from Ben Boeckel. 2019-05-31 21:41:17 +00:00
Nicholas Marriott
9d2ef8bf0d Merge branch '3.0-rc' 2019-05-31 15:18:56 +01:00
nicm
1a3a973bd0 Allow % strings that are all numbers or %s, and fix a double free. Both
reported by George Nachman, GitHub issues 1765 and 1766.
2019-05-31 15:18:25 +01:00
Thomas Adam
adf9e77702 Merge branch 'obsd-master' 2019-05-31 15:02:27 +01:00
nicm
82e47403c6 Allow % strings that are all numbers or %s, and fix a double free. Both
reported by George Nachman, GitHub issues 1765 and 1766.
2019-05-31 11:34:09 +00:00
Thomas Adam
41b8bb4eef Merge branch 'obsd-master' 2019-05-30 23:02:27 +01:00
nicm
b26523c26d Remove a leftover abort and some fixes from cppcheck. 2019-05-30 20:54:03 +00:00
Nicholas Marriott
200a1c62c6 Merge branch '3.0-rc' 2019-05-30 13:12:50 +01:00
nicm
e4eec92852 No longer need to reduce line number by one. 2019-05-30 13:12:35 +01:00
Thomas Adam
2df757521a Merge branch 'obsd-master' 2019-05-30 13:02:26 +01:00
nicm
8fb796b5b3 No longer need to reduce line number by one. 2019-05-30 10:04:33 +00:00
Thomas Adam
82b25a9d62 Merge branch 'obsd-master' 2019-05-30 11:02:27 +01:00
nicm
89d2c7eb26 I had hoped that non-xenl terminals had died out, at least in fairly
modern OSs, but no - DragonFly BSD's console returns to haunt us. Fix it
at least somewhat. GitHub issue 1763.
2019-05-30 07:42:41 +00:00
Nicholas Marriott
026450c1a8 Add test for xenl terminals. 2019-05-30 07:52:24 +01:00
Nicholas Marriott
c5e2532b67 Merge branch '3.0-rc' 2019-05-29 23:04:28 +01:00
nicm
75d112c484 The line number needs to be updated only after the \n is processed by
the parser, so store a flag and update it next time around. Also each
new line needs its own shared data.
2019-05-29 23:04:22 +01:00
Thomas Adam
414208aab1 Merge branch 'obsd-master' 2019-05-29 23:02:25 +01:00
nicm
7dced37673 Use VIS_CSTYLE for the arguments and add the missing escapes it can
generate to the parser.
2019-05-29 20:05:14 +00:00
Nicholas Marriott
95d68fcba1 Merge branch '3.0-rc' 2019-05-29 20:43:29 +01:00
Nicholas Marriott
a05c3a7aa6 Add command order test. 2019-05-29 20:43:11 +01:00
nicm
c17edd594e The line number needs to be updated only after the \n is processed by
the parser, so store a flag and update it next time around. Also each
new line needs its own shared data.
2019-05-29 19:34:42 +00:00
Nicholas Marriott
47795d1695 Update .travis.yml from master. 2019-05-29 14:40:41 +01:00
Nicholas Marriott
2ce8e0110c Don't even need this? 2019-05-29 14:32:49 +01:00
Nicholas Marriott
4425c1e1b3 Tweak again. 2019-05-29 14:24:09 +01:00
Nicholas Marriott
409d52ed41 Try OS X. 2019-05-29 14:19:37 +01:00
Thomas Adam
e90b5dcea3 Merge branch 'obsd-master' 2019-05-29 13:02:35 +01:00
Nicholas Marriott
ffcc60211d Merge branch '3.0-rc' 2019-05-29 12:13:55 +01:00
Nicholas Marriott
7cdb1cfc8d as -> and. 2019-05-29 12:13:46 +01:00
Nicholas Marriott
480ba99a16 Merge branch '3.0-rc' 2019-05-29 12:07:05 +01:00
Nicholas Marriott
8827b7f9a6 Tweak {} text. 2019-05-29 11:25:07 +01:00
nicm
a4424fbebf Support \ooo escapes, from Avi Halachmi. 2019-05-29 10:08:36 +00:00
Nicholas Marriott
eefbbfde77 Merge branch '3.0-rc' 2019-05-28 21:05:00 +01:00
nicm
7eeb479705 Do not read past the end of the argument string if it is empty. 2019-05-28 21:04:41 +01:00
nicm
8d137233a9 Redraw status line if size changes, GitHub issue 1762. Also fix length
of target buffer when pasting into status line.
2019-05-28 21:04:35 +01:00
Thomas Adam
c96957583f Merge branch 'obsd-master' 2019-05-28 21:02:28 +01:00
nicm
580cd16f4c Redraw status line if size changes, GitHub issue 1762. Also fix length
of target buffer when pasting into status line.
2019-05-28 18:53:36 +00:00
nicm
4382538e4b Do not read past the end of the argument string if it is empty. 2019-05-28 18:30:30 +00:00
Nicholas Marriott
e7a530fe4c Next will be 3.1. 2019-05-28 15:48:31 +01:00
Nicholas Marriott
05d07413ff 3.0-rc. 2019-05-28 15:46:17 +01:00
Thomas Adam
b8360504f3 Merge branch 'obsd-master' 2019-05-28 15:02:26 +01:00
Nicholas Marriott
a062650d4b Tweak menu option. 2019-05-28 14:49:50 +01:00
Nicholas Marriott
f012db9be9 Add regress for conf files. 2019-05-28 13:21:19 +01:00
nicm
299d4f3aaa Exit 1 correctly if source-file fails. 2019-05-28 12:20:28 +00:00
Thomas Adam
eba6cf61c9 Merge branch 'obsd-master' 2019-05-28 13:02:27 +01:00
nicm
0ec410689c Allow source-file to take multiple arguments. 2019-05-28 11:46:30 +00:00
nicm
e0fd295054 Change the default right click pane to open the menu if not in a mode
and no application mouse.
2019-05-28 10:27:11 +00:00
nicm
99a8469ee4 Add key bindings to open the window and pane menus (C-m and M-m for now). 2019-05-28 10:05:24 +00:00
nicm
12255411f2 Allow menu items to be disabled by putting a - at the start of their
name, rather than just including #[dim] which still allowed them to be
chosen.
2019-05-28 09:50:54 +00:00
Thomas Adam
c0116b2c5b Merge branch 'obsd-master' 2019-05-28 09:02:26 +01:00
nicm
799a154b91 Change display-menu from taking a single string to a set of arguments,
which is much easier to work with. Based on a diff from Avi Halachmi.
2019-05-28 07:18:42 +00:00
Thomas Adam
793f4d89d6 Merge branch 'obsd-master' 2019-05-27 19:02:25 +01:00
nicm
90cd045cf3 Clarify newlines inside {} a little. 2019-05-27 16:22:32 +00:00
nicm
94f6488f0e Go less crazy with horizontal separators on default menus. 2019-05-27 15:29:46 +00:00
Thomas Adam
d4bf4bd7c7 Merge branch 'obsd-master' 2019-05-27 15:02:28 +01:00
Nicholas Marriott
522d1bd309 Add. 2019-05-27 14:39:44 +01:00
Nicholas Marriott
a21de4c483 Mention <><=>=. 2019-05-27 14:39:06 +01:00
Nicholas Marriott
714311a696 Add {}. 2019-05-27 14:37:47 +01:00
Nicholas Marriott
9f0904ce6f Remove unused fparseln compat code. 2019-05-27 14:28:05 +01:00
nicm
ae3eba6e08 Fix crash when killing the current window, reported by Jesus Rafael
Sanchez in GitHub issue 1760.
2019-05-27 12:48:52 +00:00
nicm
6b332127ca Add an additional {} syntax for defining strings in the configuration
file, making it much tidier to define commands that contain other tmux
or shell commands (like if-shell). Also tweak bind-key to expect a
string if it is only given one argument, so {} can be used with it as
well. From Avi Halachmi.
2019-05-27 12:16:27 +00:00
Thomas Adam
bd40d704e2 Merge branch 'obsd-master' 2019-05-27 09:02:26 +01:00
nicm
65e5e14561 Fix the intended ordering of items in buffer mode - it should not always
be tag 0 when the tree is empty. GitHub issue 1759.
2019-05-27 06:50:04 +00:00
Thomas Adam
103e44d936 Merge branch 'obsd-master' 2019-05-26 21:02:26 +01:00
nicm
097973e3d5 Add keys for new menu items. 2019-05-26 18:43:43 +00:00
nicm
5fef946df4 Always redraw overlay if it is on (so status line doesn't redraw over it). 2019-05-26 18:27:52 +00:00
nicm
023c2c5392 Do not accept choice unless mouse has actually moved before. 2019-05-26 18:19:52 +00:00
nicm
e90d4a6021 Add formats for word and line under the mouse and use them to add some
items to the pane menu.
2019-05-26 17:34:45 +00:00
Thomas Adam
2e84d1cf03 Merge branch 'obsd-master' 2019-05-26 15:02:25 +01:00
nicm
6431005169 Add a way to append or prepend to a format if the length has been limited. 2019-05-26 12:02:42 +00:00
Thomas Adam
9beb3eb593 Merge branch 'obsd-master' 2019-05-26 13:02:26 +01:00
nicm
6dee409981 Some other platforms doesn't support fmemopen(3) (not unexpectedly), so
don't use it - since we only use getc/ungetc on the file anyway it is
easy not to.
2019-05-26 10:08:50 +00:00
Thomas Adam
f3fc81b178 Merge branch 'master' of github.com:ThomasAdam/tmux 2019-05-25 18:50:05 +01:00
Thomas Adam
463bd8abb9 Merge branch 'obsd-master' 2019-05-25 18:41:51 +01:00
nicm
a65a6d62d1 Add <, >, <=, >= for formats, GitHub issue 1747. 2019-05-25 16:51:10 +00:00
nicm
207789dc2d Client name can actually be NULL, so use address in that case. 2019-05-25 10:46:55 +00:00
nicm
d7586d3d65 Use client name when logging command queue. 2019-05-25 10:44:09 +00:00
nicm
f8d3d247d8 Merge cmd_list_parse into cmd-parse.y so it can use the new alias
processing code.
2019-05-25 07:18:20 +00:00
nicm
6b0fa14470 Fix error handling in if-shell. 2019-05-25 07:15:53 +00:00
Nicholas Marriott
a69211aff5 Fix up regress test. 2019-05-25 08:09:23 +01:00
nicm
930245d7ff Make cmd_log_argv take a printf-like format for the prefix. 2019-05-25 06:58:10 +00:00
espie
0dc8b7d5d8 unbreak build, okay nicm@ 2019-05-23 21:36:42 +00:00
Thomas Adam
19a3a9ee20 Merge branch 'obsd-master' 2019-05-23 21:02:30 +01:00
nicm
f3e01ecc42 Fix line numbers - commands are added after the line ends so they need to
get line - 1.
2019-05-23 18:39:00 +00:00
nicm
6c260af56d Use the same argument escaping code for options as well. 2019-05-23 18:33:53 +00:00
Nicholas Marriott
e817821104 Mention \. 2019-05-23 19:27:41 +01:00
nicm
f006116bac Environment variables can start with { also. 2019-05-23 18:22:13 +00:00
Thomas Adam
43431e7e84 Merge branch 'obsd-master' 2019-05-23 17:02:25 +01:00
nicm
eb8b51effc Fix drawing of status-right when it is aligned to the centre, GitHub
issue 1754.
2019-05-23 14:44:33 +00:00
Nicholas Marriott
389cf63cbc Tweak text. 2019-05-23 15:18:20 +01:00
Thomas Adam
2148fe33cd CHANGES: remove note to packagers 2019-05-23 15:16:10 +01:00
Thomas Adam
1a6540fea0 CHANGES: remove note to packagers 2019-05-23 15:15:42 +01:00
nicm
7d702f3cef Don't remove group items for group 0 (no group). 2019-05-23 15:15:42 +01:00
nicm
d0c462f718 Fix length calculation for pasting UTF-8 characters in the status line,
GitHub issue 1753.
2019-05-23 15:15:42 +01:00
Thomas Adam
238d2aa870 CHANGES: mention yacc 2019-05-23 15:12:24 +01:00
Thomas Adam
6bb505eb73 CHANGES: mention yacc 2019-05-23 15:11:25 +01:00
Nicholas Marriott
83b9807370 Remove duplicate. 2019-05-23 15:11:25 +01:00
Nicholas Marriott
3e6e533779 Add yacc(1) bits. 2019-05-23 15:11:25 +01:00
nicm
27bfb56ad5 Break the argument escaping code into a separate function and use it to
escape key bindings in list-keys. Also escape ~ and ; and $ properly.
2019-05-23 14:03:44 +00:00
Thomas Adam
c49f2a0365 Merge branch 'obsd-master' 2019-05-23 15:02:28 +01:00
nicm
3e3eb1dd0f Don't remove group items for group 0 (no group). 2019-05-23 13:08:43 +00:00
nicm
a4fe7e81c8 Fix length calculation for pasting UTF-8 characters in the status line,
GitHub issue 1753.
2019-05-23 12:47:52 +00:00
Nicholas Marriott
4ce26b0393 Remove duplicate. 2019-05-23 13:32:18 +01:00
Thomas Adam
82bf0f4d48 configure.ac: add AC_PROC_YACC 2019-05-23 13:12:03 +01:00
Thomas Adam
8590ee65e6 TRAVIS: add bison to build deps 2019-05-23 13:12:03 +01:00
Thomas Adam
d67b99c7e4 configure.ac: add AC_PROC_YACC 2019-05-23 13:09:34 +01:00
Thomas Adam
092c7bfeb8 TRAVIS: add bison to build deps 2019-05-23 13:06:47 +01:00
Nicholas Marriott
bf2cf33fc6 Add yacc(1) bits. 2019-05-23 13:04:41 +01:00
Thomas Adam
75aeb733f2 Merge branch 'obsd-master' 2019-05-23 13:02:27 +01:00
nicm
723010ba72 Replace the split parser code (cfg.c and cmd-string.c) with a single
parser using yacc(1). This is a major change but is clearer and simpler
and allows some edge cases to be made more consistent, as well as
tidying up how aliases are handled. It will also allow some further
improvements later.

Entirely the same parser is now used for parsing the configuration file
and for string commands. This means that constructs previously only
available in .tmux.conf, such as %if, can now be used in string commands
(for example, those given to if-shell - not commands invoked from the
shell, they are still parsed by the shell itself).

The only syntax change I am aware of is that #{} outside quotes or a
comment is now considered a format and not a comment, so #{ is now a
syntax error (notably, if it is at the start of a line).

This also adds two new sections to the man page documenting the syntax
and outlining how parsing and command execution works.

Thanks to everyone who sent me test configs (they still all parse
without errors - but this doesn't mean they still work as intended!).

Thanks to Avi Halachmi for testing and man page improvements, also to
jmc@ for reviewing the man page changes.
2019-05-23 11:13:30 +00:00
Nicholas Marriott
7ca2e2fe88 Add a config. 2019-05-23 11:57:04 +01:00
Thomas Adam
9d450cc6d0 Merge branch 'obsd-master' 2019-05-22 21:02:28 +01:00
nicm
5571d7a21c Fix crash if window doesn't exist, GitHub issue 1751. 2019-05-22 18:58:31 +00:00
Nicholas Marriott
e353d0cab3 Another config. 2019-05-22 19:49:48 +01:00
Nicholas Marriott
282f7fbd37 Add a test config. 2019-05-22 13:31:20 +01:00
Nicholas Marriott
b68fc7f104 Two more configs. 2019-05-22 07:12:38 +01:00
Nicholas Marriott
54dfe36340 Another. 2019-05-21 17:07:08 +01:00
Thomas Adam
c4f4904f9b More configs 2019-05-21 16:43:34 +01:00
Nicholas Marriott
d769fec8d6 More configs. 2019-05-21 14:41:07 +01:00
Nicholas Marriott
f1ce611345 Add another one. 2019-05-21 11:28:12 +01:00
Thomas Adam
3856116069 Merge branch 'obsd-master' 2019-05-21 09:02:37 +01:00
Nicholas Marriott
afe231c94c Add a few test configs thanks to various people. 2019-05-21 08:02:17 +01:00
nicm
ae4cccb4f1 Fix a couple of Ta from Alphonse Mariya. 2019-05-21 07:01:14 +00:00
Thomas Adam
98ee93bde3 Merge branch 'obsd-master' 2019-05-20 15:02:40 +01:00
nicm
87d82170a6 Fix ordering of source-file with multiple files and add flags to load_cfg. 2019-05-20 13:23:32 +00:00
Thomas Adam
3a7e15511b Merge branch 'obsd-master' 2019-05-20 13:02:36 +01:00
nicm
e128c7fcd8 Replace the various identical error callbacks with a single one in cmd-queue.c. 2019-05-20 11:46:06 +00:00
nicm
8db89f8efb Add a helper to allocate a cmd_list. 2019-05-20 11:34:37 +00:00
Thomas Adam
c271cb9ff8 Merge branch 'obsd-master' 2019-05-20 07:02:36 +01:00
nicm
6e0c663a89 Fix the color space parameter in RGB SGR, from Brad Town. 2019-05-20 05:35:46 +00:00
Thomas Adam
56246c2936 README.md: mention TODO list on the tmux wiki 2019-05-19 13:31:09 +01:00
Thomas Adam
54da493476 Merge branch 'obsd-master' 2019-05-18 23:02:36 +01:00
nicm
82ebd98c5f Move the single command flag (CMD_CONTROL) into the shared flags. 2019-05-18 21:14:10 +00:00
Nicholas Marriott
831c67c2d8 Remove TODO, moving onto website. 2019-05-18 14:44:31 +01:00
Nicholas Marriott
d6f7be6345 Add to CHANGES. 2019-05-18 13:29:38 +01:00
Thomas Adam
eb064e8a62 Merge branch 'obsd-master' 2019-05-17 09:02:36 +01:00
nicm
9b83b1daa6 Change a couple of ACS characters to be more sensible and add a few
missing ones, reported by Ricardo Banffy.
2019-05-17 05:48:25 +00:00
nicm
4acd345c6a Initialize default size variables, from Thomas Adam. 2019-05-17 05:47:31 +00:00
Thomas Adam
d9ac0e7576 Merge branch 'obsd-master' 2019-05-15 22:50:42 +01:00
Nicholas Marriott
dcf0bc2cc9 Mention CONTRIBUTING. 2019-05-15 21:42:43 +01:00
nicm
cf4566b47b Fix dragging when in view mode rather than copy mode, GitHub issue 1740
from Brad Town.
2019-05-15 19:25:53 +00:00
Nicholas Marriott
50e77536fe Less headings. 2019-05-15 20:21:38 +01:00
Nicholas Marriott
cd4e467751 Kill tmux for logs. 2019-05-15 20:21:07 +01:00
Thomas Adam
9228fead48 Merge branch 'obsd-master' 2019-05-14 09:02:28 +01:00
nicm
38b8a198ba Fix sizing of main-vertical and main-horizontal layouts, GitHub issue 1736. 2019-05-14 07:37:50 +00:00
Thomas Adam
1eefbd28e8 Merge branch 'obsd-master' 2019-05-13 23:02:26 +01:00
nicm
1ee944a19d Add support for overline (SGR 53), from Ricardo Banffy. 2019-05-13 20:10:23 +00:00
nicm
1b0512aa7e Always include Lock in the menu. 2019-05-13 20:07:02 +00:00
Thomas Adam
b5b5d35eee Merge branch 'obsd-master' 2019-05-13 11:02:31 +01:00
nicm
c5f660e33a Fix column width for copy mode commands. 2019-05-13 08:56:07 +00:00
Nicholas Marriott
e1e520d741 Clarify a little. 2019-05-13 09:51:51 +01:00
Thomas Adam
699d9d2fac Merge branch 'obsd-master' 2019-05-12 21:02:27 +01:00
nicm
c3c3927c2b Oops, removed too much in last change. 2019-05-12 18:18:30 +00:00
nicm
00f19b7f91 Fix some indentation and dead assignments. 2019-05-12 18:16:33 +00:00
Thomas Adam
42da951edf README.md: avaailable -> available
Correct typo.
2019-05-12 18:37:32 +01:00
Thomas Adam
180bbab1fc Merge branch 'obsd-master' 2019-05-12 11:02:25 +01:00
Nicholas Marriott
69c59c52b6 Spelling error. 2019-05-12 10:06:42 +01:00
Nicholas Marriott
19370631ea Tweak text of menu CHANGES entry. 2019-05-12 10:05:10 +01:00
Nicholas Marriott
99c1853792 Scatter some `. 2019-05-12 10:00:31 +01:00
nicm
a131655235 Add simple menus to tree, client, buffer modes. 2019-05-12 08:58:09 +00:00
Thomas Adam
677bb168a9 Merge branch 'obsd-master' 2019-05-12 09:02:28 +01:00
nicm
c91323e4d6 Remove menu_create_from_items, I thought I would use it for some later
work but I don't need it.
2019-05-12 07:27:08 +00:00
Thomas Adam
50d1d04913 Merge branch 'obsd-master' 2019-05-11 09:02:29 +01:00
Nicholas Marriott
67e2f5869a Mention -vv. 2019-05-11 08:34:08 +01:00
Nicholas Marriott
3a9c199ae7 New ISSUE_TEMPLATE from Nicolas CARPi. 2019-05-11 08:23:14 +01:00
Nicholas Marriott
bd6d0b3101 Formatted README.md, from Nicolas CARPi. 2019-05-11 08:19:14 +01:00
Nicholas Marriott
f1dd65cbdf Another tweak. 2019-05-11 08:09:49 +01:00
Nicholas Marriott
c18d7c5fcb Update CONTRIBUTING.md, mostly from Nicolas CARPi. 2019-05-11 08:07:35 +01:00
Nicholas Marriott
0d64531f66 Tweaks to README, some from me, some from Nicolas CARPi. 2019-05-11 07:55:28 +01:00
Nicholas Marriott
f44dafd224 Add to CHANGES. 2019-05-11 07:43:18 +01:00
nicm
198b0a23a2 Don't use arguments with It and -enum, pointed out by jmc. 2019-05-11 06:40:01 +00:00
nicm
ad27b7decd Do not reduce window height by status line height for control mode
clients, from George Nachman.
2019-05-11 06:34:56 +00:00
Thomas Adam
fc00839adc Update CHANGES 2019-05-10 22:27:33 +01:00
Thomas Adam
aa13bd4016 Merge branch 'obsd-master' 2019-05-10 22:10:38 +01:00
nicm
d62fd78655 Fix a typo in previous (, -> :). 2019-05-10 18:09:51 +00:00
nicm
6dcca5fda4 Add support for simple menus usable with mouse or keyboard. New command
display-menu shows a menu (bound to the mouse on status line by default)
and a couple of extra formats for the default menus.
2019-05-10 18:04:06 +00:00
Thomas Adam
c5f6ea5c0d Merge branch 'obsd-master' 2019-05-10 17:02:27 +01:00
nicm
004a9b52f0 Add a function to draw a simple menu onto a screen. 2019-05-10 14:12:47 +00:00
Thomas Adam
e5f06d2cf6 Merge branch 'obsd-master' 2019-05-09 17:02:25 +01:00
nicm
cb10bfb8ef Save mouse buttons as well as position. 2019-05-09 14:09:32 +00:00
Thomas Adam
2e00d775e4 Merge branch 'obsd-master' 2019-05-09 15:02:26 +01:00
nicm
21d9750450 send-keys also needs to insert key commands in the right order. 2019-05-09 13:12:59 +00:00
Thomas Adam
f431e20f3d Merge branch 'obsd-master' 2019-05-09 11:02:25 +01:00
nicm
3c68e51609 Change swap-window -d to be the other way round (stay with src window),
so it works like swap-pane.
2019-05-09 08:39:09 +00:00
nicm
299b7289ea Add formats to show if pane is the marked pane and if any marked pane is set. 2019-05-09 08:38:13 +00:00
Thomas Adam
4bc45fc95a Merge branch 'obsd-master' 2019-05-08 21:02:25 +01:00
nicm
f9682d2e55 Add a flag to redraw only the overlay, and remove the overlay on resize. 2019-05-08 18:07:12 +00:00
nicm
a384245c5a Adjust how mouse targets are found so they always have a session, window
and pane.
2019-05-08 18:05:03 +00:00
Thomas Adam
b24d7d9c95 Merge branch 'obsd-master' 2019-05-07 23:02:30 +01:00
Thomas Adam
453a62c672 Merge branch 'obsd-master' 2019-05-07 21:02:25 +01:00
nicm
89db309e10 Move around the display-panes identify code to make it a bit more
generic and hide the display-panes specific bits into
cmd-display-panes.c.
2019-05-07 20:01:41 +00:00
nicm
d53d3bce59 Adjust the same bit to adjust the selection for history-top and
history-bottom as for cursor-up and cursor-down. GitHub issue 1723.
2019-05-07 19:46:17 +00:00
Thomas Adam
3439c02e9d Merge branch 'obsd-master' 2019-05-07 17:02:25 +01:00
schwarze
fcd0e3082b Rename the ENVIRONMENT section which was squatting on the standard
manual page section and create a new ENVIRONMENT with the expected
content.  Move some information that was misplaced below the -u
flag into that new section.
Feedback and OK nicm@ jmc@ tb@
2019-05-07 14:01:39 +00:00
Thomas Adam
d9767b8112 Merge branch 'obsd-master' 2019-05-07 13:02:27 +01:00
nicm
85a9c2f52b Treat keys in identify mode (display-panes) specially and handle them
immediately rather than queuing them (the command can block the queue
which means they were not being seen until it finished which was too
late). Reported by denis@ and solene@, ok solene@.
2019-05-07 11:24:03 +00:00
nicm
69440d19b7 Do not use evbuffer_add_buffer because it is destructive and doesn't
work in newer libevent.
2019-05-07 10:25:15 +00:00
Nicholas Marriott
eac30a86d7 -attr -> -style. 2019-05-06 21:57:32 +01:00
Thomas Adam
d4177e954c Merge branch 'obsd-master' 2019-05-03 23:02:28 +01:00
nicm
45ae9a8e35 Fix order of insertion in load_cfg. 2019-05-03 21:21:00 +00:00
nicm
9f75635596 Allow panes to be empty (no command), output can be piped to them with
split-window or display-message -I.
2019-05-03 20:44:24 +00:00
Thomas Adam
4d505574dc Merge branch 'obsd-master' 2019-05-03 21:02:26 +01:00
nicm
e8e4f4ec3e Insert after the right element on queue. 2019-05-03 18:59:58 +00:00
nicm
4097257bef Do not store the mouse position we calculate as the start of a drag back
into the mouse event that later code uses, it has been adjusted and they
should use the original position. GitHub issue 1710.
2019-05-03 18:42:40 +00:00
Thomas Adam
a14512e23e Merge branch 'obsd-master' 2019-05-03 19:02:27 +01:00
nicm
84e4652513 Use the right index for user-keys. 2019-05-03 18:00:19 +00:00
nicm
fc3d85e34b Fix mouse positioning when the pane is not entirely visible. 2019-05-03 16:51:29 +00:00
Nicholas Marriott
43656d4ea7 Sync up some tmux.1 bits. 2019-05-03 17:12:30 +01:00
Thomas Adam
fff85d854e Merge branch 'obsd-master' 2019-05-03 17:04:11 +01:00
nicm
cf6075fb29 Correct ordering when adding after an existing item. 2019-05-03 15:43:01 +00:00
nicm
33298d6df6 Instead of processing keys all together, put them up on the client
command queue so they are ordered correctly with the commands that they
execute.
2019-05-03 14:51:30 +00:00
nicm
4bb48998e0 Fix reverse attribute in status line, GitHub issue 1709. 2019-05-03 10:00:48 +00:00
nicm
5d9e591ae8 Fix up some bits about window-size that seem to have got lost. 2019-05-02 20:12:40 +00:00
Thomas Adam
4d16df9312 Merge branch 'obsd-master' 2019-05-01 09:02:27 +01:00
Nicholas Marriott
18e554aa61 Merge tag '2.9a'
2.9a
2019-05-01 07:29:23 +01:00
Nicholas Marriott
4cb13d95ba Add to CHANGES. 2019-05-01 07:16:20 +01:00
Nicholas Marriott
e36d6ee06a Version 2.9a. 2019-05-01 07:12:14 +01:00
nicm
901eed7b71 Do not loop forever if there is a nonprintable character in the format. 2019-05-01 07:12:02 +01:00
nicm
750d5830c2 Don't redraw control clients, from George Nachman. 2019-05-01 07:08:04 +01:00
nicm
e286178aa7 Unbreak main-vertical and main-horizontal layouts. 2019-05-01 07:07:52 +01:00
nicm
c176361788 Remove unused variable from Thomas Adam. 2019-05-01 06:07:14 +00:00
Thomas Adam
dc7e53897a Merge branch 'obsd-master' 2019-04-30 21:02:26 +01:00
nicm
429c4bc51b Fix user options after show-hooks merge, GitHub issue 1704. 2019-04-30 18:02:03 +00:00
Nicholas Marriott
1156d91cf8 Simple -C sanity test. 2019-04-30 18:39:07 +01:00
Thomas Adam
4c5b0fbbcc Merge branch 'obsd-master' 2019-04-30 09:02:29 +01:00
nicm
5a288b1efe Don't redraw control clients, from George Nachman. 2019-04-30 06:21:30 +00:00
nicm
82c789ee58 Fix memory leak in window tree search, from Amos Bird. 2019-04-30 06:19:51 +00:00
Nicholas Marriott
7e0f9ab3eb Don't think I will do this. 2019-04-29 21:48:15 +01:00
Nicholas Marriott
87bd8965c6 Add to CHANGES & remove from TODO. 2019-04-29 20:18:07 +01:00
Thomas Adam
2aa517c805 Merge branch 'obsd-master' 2019-04-29 09:02:25 +01:00
nicm
ec81bd2399 Add support for keys to jump between matching brackets - C-M-f and C-M-b
in emacs, % in vi. Suggested by and help from Chris Barber in GitHub
issue 1666.
2019-04-29 06:55:21 +00:00
Thomas Adam
3ab229da70 Merge branch 'obsd-master' 2019-04-28 23:02:30 +01:00
Nicholas Marriott
2cecabd75e Fix gseq use in RGB colour script. 2019-04-28 22:16:34 +01:00
nicm
c4b0da5513 Support multiple occurances of the same argument. Use this for a new
flag -e to new-window, split-window, respawn-window, respawn-pane to
pass environment variables into the newly created process. From Steffen
Christgau in GitHub issue 1697.
2019-04-28 20:05:50 +00:00
Thomas Adam
5489796737 Merge branch 'obsd-master' 2019-04-27 20:09:07 +01:00
Thomas Adam
85f09f9a4c Merge branch 'obsd-master' 2019-04-26 13:02:37 +01:00
Nicholas Marriott
293fd0d258 Update CHANGES and TODO. 2019-04-26 12:44:25 +01:00
nicm
dfb7bb6830 Merge hooks into options and make each one an array option. This allows
multiple commands to be easily bound to one hook. set-hook and
show-hooks remain but they are now variants of set-option and
show-options. show-options now has a -H flag to show hooks (by default
they are not shown).
2019-04-26 11:38:51 +00:00
nicm
f1e14f86c4 Destroy panes before options to avoid crash when forced into a mode by a
hook.
2019-04-26 10:24:26 +00:00
nicm
6644d209d2 Unbreak main-vertical and main-horizontal layouts. 2019-04-26 10:15:40 +00:00
Thomas Adam
7c4a2253e8 Merge branch 'obsd-master' 2019-04-25 21:02:43 +01:00
nicm
2d65bbd941 options_array_item_value cannot return NULL. 2019-04-25 19:36:59 +00:00
nicm
a609e6361a Need a fallback for -2 for aixterm colours. 2019-04-25 19:03:43 +00:00
nicm
32a81e197b Make options_tostring allocate its result instead of using a stack
buffer (needed for something in the future).
2019-04-25 18:18:55 +00:00
Thomas Adam
f2c0605d6d Merge branch 'obsd-master' 2019-04-25 17:02:37 +01:00
nicm
1677bb0dea Need to escape ]. 2019-04-25 15:35:07 +00:00
Nicholas Marriott
dddc544b8f Update CHANGES. 2019-04-25 13:00:32 +01:00
Thomas Adam
643eecde86 Merge branch 'obsd-master' 2019-04-25 09:02:36 +01:00
nicm
567d3e27ab Automatically scroll if dragging to create a selection with the mouse
and the cursor reaches the top or bottom line.
2019-04-25 06:34:57 +00:00
Nicholas Marriott
a2e08b587a Merge branch '2.9-rc' 2019-04-25 07:29:02 +01:00
Nicholas Marriott
cb75ec25c8 2.9 now. 2019-04-24 22:35:23 +01:00
nicm
7d06216289 Do not loop forever if there is a nonprintable character in the format. 2019-04-24 22:34:56 +01:00
Thomas Adam
4ab208ecc8 Merge branch 'obsd-master' 2019-04-24 22:09:57 +01:00
nicm
6aa0bedad2 Use bg not fg when adjusting for aixterm, from Ailin Nemui. 2019-04-24 20:32:31 +00:00
nicm
c6e39976c6 Do not loop forever if there is a nonprintable character in the format. 2019-04-24 20:27:52 +00:00
Thomas Adam
c869366133 Merge branch 'obsd-master' 2019-04-23 23:02:42 +01:00
nicm
b9022e33ea Somehow missed these bits in last commit. 2019-04-23 20:40:03 +00:00
nicm
772b3b7a06 Indicate an array option with a flag rather than a special type so that
in future will not have to be strings.
2019-04-23 20:36:55 +00:00
Thomas Adam
b0d7623b7e Merge branch 'obsd-master' 2019-04-23 13:02:37 +01:00
Thomas Adam
4a96f599f6 Merge branch 'obsd-master' 2019-04-23 11:02:36 +01:00
nicm
564e44adc6 Add -no-clear variants of copy-selection and copy-pipe which do not
clear the selection after copying. Make copy-pipe clear the selection by
default to be consistent with copy-selection. From Avi Halachmi.
2019-04-23 09:39:07 +00:00
nicm
6752f41c2a Do not try to resize if the parent cell is NULL, problem reported by
Sunil Nimmagadda.
2019-04-23 09:15:24 +00:00
Nicholas Marriott
51c09bf2b4 Merge branch '2.9-rc' 2019-04-18 22:14:55 +01:00
Nicholas Marriott
d24a44230a Update CHANGES for 2.9. 2019-04-18 22:12:15 +01:00
Nicholas Marriott
8d752f5aaa Update CHANGES. 2019-04-18 22:11:46 +01:00
Nicholas Marriott
e7827f8bc2 Remove duplicate entry. 2019-04-18 14:16:19 +01:00
Thomas Adam
f980e868dd Merge branch 'obsd-master' 2019-04-18 14:11:22 +01:00
Thomas Adam
3c1f0cfc34 Merge branch 'obsd-master' 2019-04-18 14:08:13 +01:00
nicm
5b9211d827 Copy the code to infer the option type to show-options and document it. 2019-04-18 12:22:07 +00:00
nicm
3f189945d8 Pass target client and session to load_cfg from source-file so formats
work. Reported by Thomas Sattler.
2019-04-18 11:07:28 +00:00
nicm
f3ab05e7cd Update session activity on focus event, from tafryn at gmail dot com. 2019-04-18 10:11:52 +00:00
jmc
2219f7cc73 mark up punctuation-as-macro-args properly; 2019-04-17 16:34:35 +00:00
nicm
1fd3b9ec1c Fix minimum size check on split and size of first cell on spread out
with a pane status line.
2019-04-17 14:44:33 +00:00
nicm
da31eddadc Rewrite main-vertical and horizontal to use the common spread out code
and to handle the case where the panes won't fit into the existing
window size.
2019-04-17 14:44:14 +00:00
nicm
c660e46149 Set the window size as well as the layout size when using the preset
layouts.
2019-04-17 14:43:49 +00:00
nicm
e3b1358bbc Do not let the size of the pane status screen go negative. 2019-04-17 14:41:08 +00:00
nicm
5943cd1907 Document that switch-client can change all of session,window,pane and
check for % in the target as well as ":.".
2019-04-17 14:39:37 +00:00
nicm
78287e27c8 Break new window and pane creation common code from various commands and
window.c into a separate file spawn.c.
2019-04-17 14:37:48 +00:00
Nicholas Marriott
82bc2c87a9 Add to TODO. 2019-04-17 09:10:23 +01:00
nicm
cd4c94f76b Current window style also needs to be tested for default. 2019-04-11 09:34:22 +01:00
Nicholas Marriott
bba1809eac Merge a number of fixes from master for layouts, mostly prompted by testing by
Thomas Sattler.
2019-04-11 09:26:34 +01:00
Nicholas Marriott
e6ee3e9504 Warning fixes from Carlo Marcelo Arenas Belón. 2019-04-10 19:27:09 +01:00
Nicholas Marriott
1c1ec84aa3 Fix minimum size check on split and size of first cell on spread out with a
pane status line.
2019-04-10 14:54:02 +01:00
Nicholas Marriott
f3fcf977e4 Use the right winlink pointer in new-window. 2019-04-10 11:40:59 +01:00
Nicholas Marriott
4a3ac3bd26 Remove unused variable. 2019-04-10 07:27:21 +01:00
Nicholas Marriott
3c5d3a3780 Add PATH_DEFPATH to compat.h from Carlo Marcelo Arenas Belón. 2019-04-09 21:31:50 +01:00
Nicholas Marriott
fe44f90e5b Do not let the size of the pane status screen go negative. 2019-04-09 21:30:03 +01:00
Nicholas Marriott
031e9bc854 Rewrite main-vertical and horizontal to use the common spread out code and to
handle the case where the panes won't fit into the existing window size.
2019-04-09 21:15:00 +01:00
Nicholas Marriott
0cbccc90ab Set the window size as well as the layout size when using the preset layouts
and calculate the sizes correctly.
2019-04-09 20:38:43 +01:00
Nicholas Marriott
71d90c11dd Solaris has no paths.h. 2019-04-09 07:52:54 +01:00
Thomas Adam
2546572e8e Merge branch 'obsd-master' 2019-04-08 21:02:37 +01:00
nicm
835ccbac46 select-word was missing from the command list, from pawel-slowik. 2019-04-08 17:55:51 +00:00
Nicholas Marriott
b5b67c5386 Document that switch-client can change all of session,window,pane and check for
% in the target as well as ":.".
2019-04-08 10:38:50 +01:00
Thomas Adam
fbe488e4de Merge branch 'obsd-master' 2019-04-07 23:02:37 +01:00
nicm
bb629f3be7 Current window style also needs to be tested for default. 2019-04-07 20:18:20 +00:00
Thomas Adam
883a428e27 Linux: remove include for util.h
Linux doesn't require this header.
2019-04-07 15:39:58 +01:00
Nicholas Marriott
e44e2c48dd Do not log NULL command. 2019-04-07 13:16:55 +01:00
Nicholas Marriott
ece737274e Forgot to add the file. 2019-04-07 13:11:55 +01:00
Nicholas Marriott
5ece386cdf Break new window and pane creation common code from various commands and
window.c into a separate file spawn.c.
2019-04-07 13:01:03 +01:00
Nicholas Marriott
7653328ce7 Remove from TODO one thing that I don't think is necessary and one that is
done.
2019-04-07 12:18:40 +01:00
Nicholas Marriott
fc111d2b12 Fix a duplicate entry in CHANGES and remove an item from TODO. 2019-04-07 12:07:26 +01:00
Thomas Adam
04402db616 Merge branch 'obsd-master' 2019-04-05 23:02:36 +01:00
nicm
1b5a8a0f09 Fix some warnings, from Thomas Adam. 2019-04-05 20:32:31 +00:00
Nicholas Marriott
e33b623f21 Merge branch '2.9-rc' 2019-04-04 18:31:54 +01:00
nicm
73b54a0e5f Fix size check for splitw -f and top level pane size for tiled layout,
problems reported by Thomas Sattler.
2019-04-04 18:31:35 +01:00
Thomas Adam
5a97af7961 Merge branch 'obsd-master' 2019-04-04 13:02:37 +01:00
nicm
f4aefb738e Fix size check for splitw -f and top level pane size for tiled layout,
problems reported by Thomas Sattler.
2019-04-04 10:25:35 +00:00
nicm
481c3f3f2e screen_write_fast_copy can no longer assume the target screen is default
(it isn't for the pane status lines).
2019-04-03 09:31:32 +01:00
Thomas Adam
cb039b986e Merge branch 'obsd-master' 2019-04-03 09:02:41 +01:00
nicm
f6c54f3f03 Do not load /etc/tmux.conf if given -f. 2019-04-03 06:43:19 +00:00
nicm
06d58b3b7b screen_write_fast_copy can no longer assume the target screen is default
(it isn't for the pane status lines).
2019-04-03 06:43:04 +00:00
nicm
8968acd678 Silence flag should use the same option as activity, reported by Thomas
Sattler.
2019-04-02 22:20:36 +01:00
Thomas Adam
c9ef144dca Merge branch 'obsd-master' 2019-04-02 21:02:37 +01:00
nicm
09f71ed1b2 Silence flag should use the same option as activity, reported by Thomas
Sattler.
2019-04-02 18:41:24 +00:00
Nicholas Marriott
f0ddc301b7 Add CHANGES. 2019-04-02 17:02:09 +01:00
Nicholas Marriott
916c4c499d Version RC2. 2019-04-02 11:12:24 +01:00
Nicholas Marriott
fac792dc27 Update regress from master. 2019-04-02 11:11:19 +01:00
nicm
bbcfee362f Store and restore cursor across reflow by working out a position based
on unwrapped lines, rather than a grid offset. Fixes problems reported
by Thomas Sattler and Paul de Weerd.
2019-04-02 11:11:12 +01:00
Thomas Adam
bfc1f0ca62 Merge branch 'obsd-master' 2019-04-02 11:02:44 +01:00
nicm
7bcc0d16f2 Add an argument to copy commands to set the prefix for the buffer name,
allows buffers for different sessions to be named separately.
2019-04-02 09:03:39 +00:00
Nicholas Marriott
f03776c262 Don't use a config file in tests. 2019-04-02 09:53:02 +01:00
nicm
ffa4d48967 Store and restore cursor across reflow by working out a position based
on unwrapped lines, rather than a grid offset. Fixes problems reported
by Thomas Sattler and Paul de Weerd.
2019-04-02 08:45:32 +00:00
Nicholas Marriott
79c3fd4f39 Add cursor regression tests. 2019-04-02 09:44:28 +01:00
nicm
6d071c468c Restore a check to stop scrolled lines becoming larger than total lines,
fixes a crash reported by Thomas Sattler.
2019-04-02 07:33:33 +01:00
Thomas Adam
294accea1b Merge branch 'obsd-master' 2019-04-01 21:02:37 +01:00
nicm
792fcb1dbf Restore a check to stop scrolled lines becoming larger than total lines,
fixes a crash reported by Thomas Sattler.
2019-04-01 19:33:38 +00:00
Nicholas Marriott
da359269cb Merge branch '2.9-rc' 2019-03-29 11:20:15 +00:00
nicm
92da105b58 Free old strings after they have been expanded in format_choose. 2019-03-29 11:19:55 +00:00
Thomas Adam
ecc5cea09b Merge branch 'obsd-master' 2019-03-29 10:02:36 +00:00
nicm
d68a17a1df Free old strings after they have been expanded in format_choose. 2019-03-29 09:33:24 +00:00
Nicholas Marriott
52cb7a6382 Merge branch '2.9-rc' 2019-03-29 07:05:50 +00:00
nicm
00fda57ddf Fix offset of list ranges. 2019-03-29 07:05:40 +00:00
Thomas Adam
405bb8435c Merge branch 'obsd-master' 2019-03-29 00:02:36 +00:00
nicm
c6c4960b35 Fix offset of list ranges. 2019-03-28 22:18:46 +00:00
Thomas Adam
2c4f2393ec Merge branch 'obsd-master' 2019-03-28 22:02:37 +00:00
nicm
08bc226527 Expand session and window formats for buffer filters. 2019-03-28 21:05:15 +00:00
Thomas Adam
6b38334b28 Merge branch 'obsd-master' 2019-03-27 14:02:36 +00:00
nicm
c1f0918f8a Fix stop-selection, from Avi Halachmi. 2019-03-27 13:25:11 +00:00
Thomas Adam
6861045d38 Merge branch 'obsd-master' 2019-03-26 22:02:36 +00:00
nicm
9f8d193b11 Break copy mode commands into individual functions instead of a big load
of if statements.
2019-03-26 21:01:19 +00:00
Nicholas Marriott
a13e57f701 Update TODO. 2019-03-26 17:04:47 +00:00
Nicholas Marriott
e722ba38e3 There is no examples directory anymore. 2019-03-26 15:10:05 +00:00
Nicholas Marriott
b1dc2b5353 Merge branch '2.9-rc' 2019-03-26 15:05:41 +00:00
Nicholas Marriott
e0e08fcd2d Update CHANGES & TODO. 2019-03-26 15:05:28 +00:00
Nicholas Marriott
0a913b09cf For 3.0. 2019-03-26 14:38:20 +00:00
Nicholas Marriott
4f7a5d1e40 2.9 bits. 2019-03-26 14:37:27 +00:00
Thomas Adam
6ac84585e6 Merge branch 'obsd-master' 2019-03-25 20:02:38 +00:00
nicm
d21f8ecc13 Add StatusDefault binding for the mouse on any otherwise unassigned
parts of the status line, from Avi Halachmi.
2019-03-25 18:59:55 +00:00
Thomas Adam
5e2150cf18 Merge branch 'obsd-master' 2019-03-25 16:00:36 +00:00
Thomas Adam
a07ad6b5a3 Merge branch 'obsd-master' 2019-03-25 15:57:47 +00:00
nicm
ff4d7d541f Fix columns of cursor_character format in list. 2019-03-25 14:29:36 +00:00
Nicholas Marriott
e8f4ca6a52 Tweaks to example config. 2019-03-25 12:05:58 +00:00
Nicholas Marriott
a084f2dcb7 Add to TODO. 2019-03-25 10:06:03 +00:00
nicm
517d673dbe Ignore mouse on status line which are not part of a range, GitHub issue 1649. 2019-03-25 09:22:09 +00:00
nicm
b4a301f8fe Clarify that styles can be space or comma separated, from Stephen Zapatka. 2019-03-22 10:45:17 +00:00
nicm
04a1fc9d36 I forgot to document resize-window, window-size and default-size;
reminded by okan@.
2019-03-22 09:33:04 +00:00
Thomas Adam
0292243b29 Merge branch 'obsd-master' 2019-03-20 20:02:37 +00:00
Nicholas Marriott
ef38a420b2 Update TODO. 2019-03-20 20:02:13 +00:00
Nicholas Marriott
7536d57b16 Update TODO. 2019-03-20 19:26:20 +00:00
nicm
9ee1a8f701 Improve cursor positioning after reflow by storing the position as an
offset into the entire history before reflow and restoring it aftewards.
2019-03-20 19:19:11 +00:00
Nicholas Marriott
0e0f2f765b Update CHANGES. 2019-03-20 14:01:46 +00:00
Thomas Adam
bff957a475 Merge branch 'obsd-master' 2019-03-20 08:02:38 +00:00
nicm
ed962e7612 Include function name in logging. 2019-03-20 07:30:05 +00:00
nicm
458b87150b Do not leak ranges on error. 2019-03-20 07:28:31 +00:00
nicm
ae46a19b8e Ignore invalid styles rather than throwing away the whole format, this
matches what we used to do.
2019-03-20 07:24:03 +00:00
nicm
3b959c05ff Bit more logging to show drawing errors. 2019-03-20 07:13:02 +00:00
Thomas Adam
46f642b030 Merge branch 'obsd-master' 2019-03-19 22:02:36 +00:00
nicm
8b74e959ef Include window-status-style and window-status-current style in the format. 2019-03-19 21:09:51 +00:00
Thomas Adam
320237fdb8 Merge branch 'obsd-master' 2019-03-19 20:02:37 +00:00
nicm
161b57869e Add a cursor_character format. 2019-03-19 19:01:50 +00:00
Nicholas Marriott
92732a2540 Add to TODO. 2019-03-19 14:39:55 +00:00
Thomas Adam
b3eebdec48 Merge branch 'obsd-master' 2019-03-19 14:02:36 +00:00
nicm
b24c9e34a9 Rename the first KEY BINDINGS section to DEFAULT KEY BINDINGS. 2019-03-19 13:35:42 +00:00
Thomas Adam
073d439965 Merge branch 'obsd-master' 2019-03-19 00:02:39 +00:00
Thomas Adam
f956c17c09 Merge branch 'obsd-master' 2019-03-18 22:02:36 +00:00
nicm
0406ec0ec2 Free temporary screens when writing format. 2019-03-18 21:55:04 +00:00
nicm
f34ebfed76 The individual -fg, -bg and -attr options have been deprecated (in
favour of -style), undocumented and hidden from show-options since
2014. Remove them, except for status-fg and status-bg.
2019-03-18 21:46:01 +00:00
Thomas Adam
962f255ee8 Merge branch 'obsd-master' 2019-03-18 21:24:49 +00:00
nicm
c62404673e Add some bits to the STATUS LINE section about the new option. 2019-03-18 21:01:04 +00:00
nicm
979313832c Extend the #[] style syntax and use that together with previous format
changes to allow the status line to be entirely configured with a single
option.

Now that it is possible to configure their content, enable the existing
code that lets the status line be multiple lines in height. The status
option can now take a value of 2, 3, 4 or 5 (as well as the previous on
or off) to configure more than one line. The new status-format array
option configures the format of each line, the default just references
the existing status-* options, although some of the more obscure status
options may be eliminated in time.

Additions to the #[] syntax are: "align" to specify alignment (left,
centre, right), "list" for the window list and "range" to configure
ranges of text for the mouse bindings.

The "align" keyword can also be used to specify alignment of entries in
tree mode and the pane status lines.
2019-03-18 20:53:33 +00:00
Thomas Adam
1d6fe43c7b Merge branch 'obsd-master' 2019-03-18 18:02:38 +00:00
Thomas Adam
4cbf596dc5 Merge branch 'obsd-master' 2019-03-18 15:30:55 +00:00
nicm
d738d51688 Mode init needs to be fired with the mode on the list or it will not be
resized correctly.
2019-03-18 15:25:36 +00:00
Thomas Adam
acb2413852 Merge branch 'obsd-master' 2019-03-18 15:07:51 +00:00
nicm
2628af573d Add format variables for the default formats for the various modes
(tree_mode_format and so on) and add a -a flag to display-message to
list variables with values.
2019-03-18 14:10:25 +00:00
Nicholas Marriott
aa2b3472c5 Update TODO. 2019-03-18 12:00:10 +00:00
nicm
ce6be7afd4 Make array options a sparse tree instead of an array of char * and
remove the size limit.
2019-03-18 11:58:40 +00:00
nicm
d2d43987d0 With force, kill previous job before starting new. Fixes problem
reported by Scott Mcdermott in GitHub issue 1627.
2019-03-18 09:46:42 +00:00
nicm
bd3332b211 Break description of styles into its own section. 2019-03-17 19:33:12 +00:00
Nicholas Marriott
3a298454ce Add to TODO. 2019-03-17 08:05:58 +00:00
nicm
b588b1729a Use a pointer for the active screen in the status line instead of
copying them around all the time.
2019-03-16 19:12:13 +00:00
nicm
818fda0363 Give status_save_old the client so it can do the reinit too. 2019-03-16 17:53:55 +00:00
nicm
b4f5b99e4b Tidy and rename some bits of status line code. 2019-03-16 17:14:07 +00:00
nicm
e8b33af780 Add a way to set individual defaults for an array option. 2019-03-15 21:54:47 +00:00
nicm
1d306e926a Add a : to make error messages clearer. 2019-03-15 15:20:00 +00:00
nicm
33595a255f Copy recursion counter into new formats when looping. 2019-03-15 15:02:25 +00:00
nicm
85044a634b Move status line free into its own function. 2019-03-15 14:46:58 +00:00
nicm
2d71bef0ca Remove unused member of struct client. 2019-03-15 10:48:05 +00:00
nicm
f6d34f066c Only print format logging when the flag is set, even if also sending to log_debug. 2019-03-15 10:22:57 +00:00
nicm
672c49d512 The pane and window loops need to pass the window and pane tags when
they build their format.
2019-03-15 10:07:24 +00:00
nicm
27578815da Add a -v flag to display-message to show verbose messages as the format
is parsed, this gives the user a way to debug problems with formats
rather than just being confronted with (for example) a blank status
line.
2019-03-15 10:04:13 +00:00
nicm
25e2e22791 Add a limit on how far format_expand can recurse. 2019-03-14 23:34:41 +00:00
nicm
10d60faba5 Store the time in the format tree rather than passing it around. 2019-03-14 23:14:27 +00:00
Thomas Adam
2c755e3c55 Merge branch 'obsd-master' 2019-03-14 22:02:39 +00:00
nicm
bace79a571 Remove some unnecessary temporary variables and be much less strict
about spacing in style_parse.
2019-03-14 21:46:08 +00:00
nicm
4206bcc10e Add format flags for start and end window. 2019-03-14 21:41:30 +00:00
nicm
38064e7593 Add T format modifier like E but also do strftime(3). 2019-03-14 21:31:43 +00:00
nicm
1416ceb575 Accept 0 time as a shorthand for now to format_expand_time. 2019-03-14 21:27:26 +00:00
Thomas Adam
d58bccfc63 Merge branch 'obsd-master' 2019-03-14 20:02:38 +00:00
nicm
9bd4b96766 Fix ED1 (clear end of screen), reported by Marc Reisner. 2019-03-14 17:58:52 +00:00
Thomas Adam
0b32fa81b6 Merge branch 'obsd-master' 2019-03-14 12:02:41 +00:00
nicm
0425e3178d A little tidying in style_parse. 2019-03-14 10:19:52 +00:00
nicm
13f9a061ac Add a wrapper (struct style) around styles rather than using the
grid_cell directly. There will be some non-cell members soon.
2019-03-14 09:53:52 +00:00
Thomas Adam
f33d2ab29e Merge branch 'obsd-master' 2019-03-14 08:02:37 +00:00
nicm
1e9f8a3523 Missing space in capture-pane usage, from Ben Boeckel.
Also man page fixed from jmc.
2019-03-14 06:36:21 +00:00
nicm
2fbd491ff0 Add actual HPA (\033[`), the existing one is CHA. From Marc Reisner. 2019-03-14 06:33:43 +00:00
Thomas Adam
81b393a493 Merge branch 'obsd-master' 2019-03-14 00:02:37 +00:00
nicm
5755bfc619 Need to set attributes before clearing. 2019-03-13 22:01:22 +00:00
nicm
10f0094be9 The pane's style should be initialized to default before parsing the
argument.
2019-03-13 21:39:21 +00:00
Thomas Adam
786f5e505e Merge branch 'obsd-master' 2019-03-13 20:02:36 +00:00
nicm
6dffbc4849 Tweak format_replace logging. 2019-03-13 18:09:12 +00:00
Thomas Adam
e6fd429d58 Merge branch 'obsd-master' 2019-03-13 16:02:41 +00:00
nicm
95ab1aaaec Add formats to list sessions, windows or panes. 2019-03-13 15:37:28 +00:00
Nicholas Marriott
f628afc850 Update TODO. 2019-03-13 14:51:19 +00:00
nicm
49f04a997a Apply length limits and substitution even to literal formats. 2019-03-13 14:27:17 +00:00
Nicholas Marriott
1aeac384f3 Add to TODO. 2019-03-13 14:20:58 +00:00
nicm
9032ac2a05 Add E: format to expand a format twice (useful to expand the value of an
option).
2019-03-13 14:19:54 +00:00
nicm
71e00c718c Make format parsing build the modifiers into a list, standardize how
arguments are given and allow multiple modifiers on a format (separated
by ;).
2019-03-13 14:10:34 +00:00
Nicholas Marriott
7a6b21de65 Add to TODO. 2019-03-13 09:30:42 +00:00
Nicholas Marriott
4f5cb88c2b Add to TODO. 2019-03-13 09:30:42 +00:00
Thomas Adam
0e6eda02a6 Merge branch 'obsd-master' 2019-03-13 08:02:35 +00:00
nicm
feaa5660a3 Do not use origin for VPA. 2019-03-13 07:34:36 +00:00
Thomas Adam
b03f58b977 Merge branch 'obsd-master' 2019-03-13 00:02:38 +00:00
nicm
b2bc34af12 Set a flag on cells are genuinely empty (cleared and never written to)
and use tty_clear_line (which will choose the best escape sequence) to
clear any batches of cells with that flag when redrawing a line from the
stored screen.
2019-03-12 23:21:45 +00:00
Thomas Adam
400529eea0 Merge branch 'obsd-master' 2019-03-12 22:02:42 +00:00
nicm
938156d73b DECRC and DECSC apparently need to preserve origin mode as well, based
on a fix from Marc Reisner.
2019-03-12 20:02:47 +00:00
Thomas Adam
ba4a884d75 Merge branch 'obsd-master' 2019-03-12 20:02:38 +00:00
nicm
2796ae81d0 Fix HPA in origin mode. 2019-03-12 18:30:08 +00:00
nicm
f3f534a3a0 Tidy up a lot of &ictx->ctx by using a local variable. 2019-03-12 18:26:57 +00:00
Nicholas Marriott
6c3ee42568 Add a couple of things. 2019-03-12 17:59:46 +00:00
Nicholas Marriott
2f0ffe6adb Add to TODO. 2019-03-12 17:52:22 +00:00
Nicholas Marriott
4002dbf0c1 Fix session size regress. 2019-03-12 17:36:58 +00:00
Thomas Adam
162d3cb1f4 Merge branch 'obsd-master' 2019-03-12 16:02:37 +00:00
Thomas Adam
7d2004a8dd Merge branch 'obsd-master' 2019-03-12 14:02:40 +00:00
Nicholas Marriott
860acecc0d Fix up regress test for control client size. 2019-03-12 13:57:06 +00:00
nicm
028f9d1d87 Fix resizing of control clients, should be ignored until SIZECHANGED flag set. 2019-03-12 13:56:30 +00:00
nicm
303d20a758 Fix wrapping after origin mode change. 2019-03-12 13:14:14 +00:00
nicm
3f0efc050a When asked for a window index, return it even if the window exists. 2019-03-12 13:14:04 +00:00
nicm
7804fa1b82 Revert to not clearing history on RIS, apparently some bootloaders send
this and it doesn't really do any harm.
2019-03-12 12:58:40 +00:00
nicm
7b819357ff Tweak target debug logging. 2019-03-12 12:49:46 +00:00
Nicholas Marriott
595b52490e Add to TODO. 2019-03-12 12:12:35 +00:00
Thomas Adam
3ec05e9405 Merge branch 'obsd-master' 2019-03-12 12:02:42 +00:00
Nicholas Marriott
f8a30e1588 Update CHANGES. 2019-03-12 11:20:21 +00:00
nicm
3f6bfbaf2b Allow multiple modes to be open in a pane. A stack of open modes is kept
and the previous restored when the top is exited. If a mode that is
already on the stack is entered, the existing instance is moved to the
top as the active mode rather than being opened new.
2019-03-12 11:16:49 +00:00
Thomas Adam
95d340cc4f Merge branch 'obsd-master' 2019-03-12 10:02:39 +00:00
nicm
ff4c80d53d Add support for origin mode (DECOM, SM/RM ?6), from Marc Reisner. 2019-03-12 07:39:27 +00:00
Thomas Adam
bc72cf2f52 Merge branch 'obsd-master' 2019-03-08 12:02:39 +00:00
nicm
de730f68a4 Make the mode used to view command output (a variant of copy mode) use
its own mode definition struct with a different init function rather
than calling special setup functions.
2019-03-08 10:34:20 +00:00
nicm
9cc04a0f9a Do not use window mode entry after free. 2019-03-08 10:29:25 +00:00
Thomas Adam
349aeb806a Merge branch 'obsd-master' 2019-03-07 22:02:42 +00:00
nicm
f98c66ece8 Add a separate mode struct for the active window mode if any. 2019-03-07 20:24:21 +00:00
Thomas Adam
a1009e7bd3 Merge branch 'obsd-master' 2019-03-07 20:02:41 +00:00
nicm
3c24bc5617 Tidy changing the mode into window_copy_init_for_output. 2019-03-07 19:34:22 +00:00
nicm
7f093fcddc Make adding mode formats a function pointer as well. 2019-03-07 19:01:21 +00:00
Nicholas Marriott
5a564a0c1a Add to TODO. 2019-03-07 15:34:24 +00:00
Thomas Adam
9ebd630675 Merge branch 'obsd-master' 2019-03-04 12:01:28 +00:00
nicm
5cdd578906 Fix sense of aggressive-resize flag. 2019-03-04 09:29:52 +00:00
nicm
a870c255c4 Don't set client offset if client is not a terminal 2019-03-04 09:29:40 +00:00
Thomas Adam
d5c837904b Merge branch 'obsd-master' 2019-02-16 20:02:36 +00:00
nicm
fa33603dc1 Do not look at next key byte if the length is 0, originally from Shingo
NISHIOKA in GitHub issue 1601.
2019-02-16 19:04:34 +00:00
Thomas Adam
fa8294436c Merge branch 'obsd-master' 2019-02-16 14:02:37 +00:00
nicm
82f0c859a2 Use starting client cwd in config file, GitHub issue 1606. 2019-02-16 11:42:08 +00:00
Thomas Adam
9768091ee4 Merge branch 'obsd-master' 2019-02-09 20:02:36 +00:00
nicm
f9c396db41 Completion of command-alias members. 2019-02-09 18:18:36 +00:00
Nicholas Marriott
bdb7e48cba Redirect which stderr. 2019-02-06 14:45:35 +00:00
Thomas Adam
c42e89a598 Merge branch 'obsd-master' 2019-02-06 08:02:37 +00:00
nicm
afd3127d89 Add -b to display-panes like run-shell, GitHub issue 1559. 2019-02-06 07:36:06 +00:00
Thomas Adam
4ab3b18b36 Merge branch 'obsd-master' 2019-01-20 18:02:36 +00:00
nicm
2ea22fce5e Should use DECFRA if not default, not if default. From Karl Beldan. 2019-01-20 15:57:27 +00:00
Thomas Adam
cd8a7fb07b Merge branch 'obsd-master' 2019-01-15 14:02:37 +00:00
nicm
cd39920abd Should save the bg colour when setting it to default, not the fg. 2019-01-15 12:08:53 +00:00
Thomas Adam
469a9e9439 Merge branch 'obsd-master' 2019-01-15 12:02:36 +00:00
nicm
34c0807be6 Do not highlight characters which will not be copied, reported by
Jaroslaw Rzeszotko.
2019-01-15 09:56:31 +00:00
Thomas Adam
c9d482ab48 Merge branch 'obsd-master' 2018-12-18 14:02:40 +00:00
nicm
bde0224deb Pass window into mode functions. 2018-12-18 13:20:44 +00:00
Thomas Adam
b6cdac05c7 Merge branch 'obsd-master' 2018-12-18 00:02:37 +00:00
nicm
4e3d661284 Fix parsing of empty colon-separated fields, reported by Siarhei Siniak. 2018-12-17 21:52:59 +00:00
Thomas Adam
1c5093c1c4 Merge branch 'obsd-master' 2018-11-30 10:02:37 +00:00
nicm
67254ed8df Clear PANE_EXITED flag when starting new child process in case the pane
has been respawned.
2018-11-30 08:44:40 +00:00
Nicholas Marriott
6cf2f74fe9 osdep_get_cwd for NetBSD, from Leonardo Taccari. 2018-11-29 10:37:27 +00:00
Thomas Adam
1ed994a6c8 Merge branch 'obsd-master' 2018-11-28 12:02:36 +00:00
nicm
40d246b29c Handle UTF-8 in word-separators option, GitHub issue 1551. 2018-11-28 11:20:13 +00:00
Thomas Adam
2977317243 Merge branch 'obsd-master' 2018-11-22 12:02:38 +00:00
nicm
3a7b9d5735 Do not use PWD unless it actually matches the real working directory. 2018-11-22 10:36:40 +00:00
Nicholas Marriott
2eca63b98e Add to TODO. 2018-11-21 09:50:53 +00:00
Nicholas Marriott
c4b04b1624 Fixes for GNU/kFreeBSD from James Clarke. 2018-11-21 08:50:22 +00:00
Thomas Adam
efd01f3bfd Merge branch 'obsd-master' 2018-11-19 14:02:41 +00:00
nicm
749f67b7d8 evbuffer_new and bufferevent_new can both fail (when malloc fails) and
return NULL. GitHub issue 1547.
2018-11-19 13:35:40 +00:00
Thomas Adam
a7da2357a5 Merge branch 'obsd-master' 2018-11-15 12:02:37 +00:00
kn
f103927a52 Add [template] to display-panes and choose-{buffer,client,tree} usage
OK nicm
2018-11-15 10:38:53 +00:00
Thomas Adam
0fd73f238d Merge branch 'obsd-master' 2018-11-13 12:02:38 +00:00
nicm
50cdfc06fb Initialize context property in alignment test handler function. 2018-11-13 11:36:37 +00:00
Thomas Adam
3c6cdf0115 Merge branch 'obsd-master' 2018-11-12 16:02:37 +00:00
nicm
86e648d906 Allow style #[] in mode formats. 2018-11-12 14:18:10 +00:00
Thomas Adam
849d06c0df Merge branch 'obsd-master' 2018-11-08 20:02:37 +00:00
nicm
09aee53763 It isn't possible to specify buffer name to copy mode commands now, so
remove the function argument.
2018-11-08 18:49:19 +00:00
Thomas Adam
4efba0bf9f Merge branch 'obsd-master' 2018-11-07 10:02:39 +00:00
nicm
0c7f64458f If a non-repeating key is used when repeating, it should be treated as
an entirely new key press, not checked in root table and ignored if not
found. GitHub issue 1513.
2018-11-07 08:06:28 +00:00
Nicholas Marriott
ff77010f70 Add to TODO. 2018-11-07 08:00:15 +00:00
nicm
7339845c01 There is no reason wait-for has to be restricted to outside tmux. 2018-11-07 07:58:16 +00:00
Thomas Adam
99072e1d81 Merge branch 'obsd-master' 2018-11-06 16:02:37 +00:00
nicm
f9881b3b5d Correctly unzoom and redraw panes in switch-client. 2018-11-06 15:13:13 +00:00
Thomas Adam
b1ad075d11 Merge branch 'obsd-master' 2018-10-31 12:02:38 +00:00
nicm
ef904cfef2 Reset all flags in screen_write_reset, reported by Benjamin Poirier. 2018-10-31 10:05:47 +00:00
Thomas Adam
ddffda4da5 Merge branch 'obsd-master' 2018-10-28 18:02:36 +00:00
nicm
d5b92ac37e Do not printf NULL. 2018-10-28 16:10:02 +00:00
Thomas Adam
0a54a07909 Merge branch 'obsd-master' 2018-10-28 16:02:37 +00:00
nicm
65dd7345e0 Do not check for a key again without an escape if only \033 is present. 2018-10-28 15:34:27 +00:00
Nicholas Marriott
0cefdff1b6 Add to CHANGES. 2018-10-26 11:36:36 +01:00
Thomas Adam
e771f10dc6 Merge branch 'obsd-master' 2018-10-25 17:02:42 +01:00
nicm
fc41bf46ac Add a "terminal" colour which can be used instead of "default" in style
options for the terminal default colour, bypassing any inheritance from
other options. Prompted by a discussion with abieber@.
2018-10-25 15:13:38 +00:00
Nicholas Marriott
2808f8261c Tweak wording. 2018-10-19 08:38:12 +01:00
Nicholas Marriott
c234032fcf Do not use master here. 2018-10-19 08:37:31 +01:00
Nicholas Marriott
bc6211cca5 Instead of "master" for the version number, use "next-X.X". It is more
useful to include the next version number.
2018-10-19 08:35:23 +01:00
Thomas Adam
164590e34c Merge branch 'obsd-master' 2018-10-18 15:02:38 +01:00
nicm
9feb35b7c4 Document new refresh-client flags. 2018-10-18 13:03:45 +00:00
Thomas Adam
f44d02c7f5 Merge branch 'obsd-master' 2018-10-18 11:09:54 +01:00
nicm
646995384d Support for windows larger than visible on the attached client. This has
been a limitation for a long time.

There are two new options, window-size and default-size, and a new
command, resize-window. The force-width and force-height options and the
session_width and session_height formats have been removed.

The new window-size option tells tmux how to work out the size of
windows: largest means it picks the size of the largest session,
smallest the smallest session (similar to the old behaviour) and manual
means that it does not automatically resize windows. The default is
currently largest but this may change. aggressive-resize modifies the
choice of session for largest and smallest as it did before.

If a window is in a session attached to a client that is too small, only
part of the window is shown. tmux attempts to keep the cursor visible,
so the part of the window displayed is changed as the cursor moves (with
a small delay, to try and avoid excess redrawing when applications
redraw status lines or similar that are not currently visible). The
offset of the visible portion of the window is shown in status-right.

Drawing windows which are larger than the client is not as efficient as
those which fit, particularly when the cursor moves, so it is
recommended to avoid using this on slow machines or networks (set
window-size to smallest or manual).

The resize-window command can be used to resize a window manually. If it
is used, the window-size option is automatically set to manual for the
window (undo this with "setw -u window-size"). resize-window works in a
similar way to resize-pane (-U -D -L -R -x -y flags) but also has -a and
-A flags. -a sets the window to the size of the smallest client (what it
would be if window-size was smallest) and -A the largest.

For the same behaviour as force-width or force-height, use resize-window
-x or -y, and "setw -u window-size" to revert to automatic sizing..

If the global window-size option is set to manual, the default-size
option is used for new windows. If -x or -y is used with new-session,
that sets the default-size option for the new session.

The maximum size of a window is 10000x10000. But expect applications to
complain and much higher memory use if making a window excessively
big. The minimum size is the size required for the current layout
including borders.

The refresh-client command can be used to pan around a window, -U -D -L
-R moves up, down, left or right and -c returns to automatic cursor
tracking. The position is reset when the current window is changed.
2018-10-18 08:38:01 +00:00
Nicholas Marriott
2dfdb55ace Handle pan correctly when the terminal is bigger than the window. 2018-10-18 09:24:15 +01:00
nicm
a51668ca06 Support OSC 52 ? to read the top buffer inside tmux (when set-clipboard
is changed to on), also add refresh-client -l to ask tmux to use the
same mechanism to get the clipboard from the terminal outside
tmux. GitHub issue 1477.
2018-10-18 08:04:14 +00:00
nicm
bc0e527f32 Support for extended underline styles on terminals which offer them,
enabled by adding the Smulx capability with terminal-overrides (add
something like ',vte*:Smulx=\E[4\:%p1%dm'). GitHub issue 1492.
2018-10-18 07:57:57 +00:00
Nicholas Marriott
f54f171d5c Merge branch '2.8-rc' 2018-10-17 19:33:43 +01:00
Nicholas Marriott
01918cb017 tmux 2.8. 2018-10-17 19:29:35 +01:00
Nicholas Marriott
a2c52d9f26 Add to TODO. 2018-10-16 14:16:48 +01:00
Nicholas Marriott
407075d8c7 Add to TODO. 2018-10-16 14:12:33 +01:00
Nicholas Marriott
cdd8c93f54 Add to TODO file. 2018-10-15 09:09:40 +01:00
Nicholas Marriott
c88e945bc5 Support OSC 52 ? to read the top buffer inside tmux, also add
refresh-client -l to get the clipboard outside tmux. GitHub issue
1477.
2018-10-11 16:20:14 +01:00
Nicholas Marriott
018f1b8a80 Use :: for escaping : in terminal-overrides not \:. 2018-10-08 19:42:55 +01:00
Nicholas Marriott
4b9e76aaaa Support for extended underline styles, enabled by adding the Smulx
capability with terminal-overrides (add something like
'vte*:Smulx=\E[4\:%p1%dm'). GitHub issue 1492.
2018-10-08 13:21:37 +01:00
Nicholas Marriott
46847e9b2e Update TODO. 2018-10-08 13:06:37 +01:00
Nicholas Marriott
1952b3f746 Update CHANGES. 2018-10-07 15:06:40 +01:00
Nicholas Marriott
546060f340 Update TODO. 2018-10-07 15:01:41 +01:00
Thomas Adam
c44bb2df17 Merge branch 'obsd-master' 2018-10-03 17:02:38 +01:00
nicm
f7c85f3ed8 Do not move the cursor when the mouse wheel is used, GitHub issue 1493. 2018-10-03 15:27:55 +00:00
Nicholas Marriott
5a7cf897f2 Correctly check offset for drawing multiple cells, GitHub issue 1481. 2018-10-01 19:47:58 +01:00
Nicholas Marriott
8053b65f1e Fix select-pane -m, GitHub issuie 1490. 2018-09-28 09:38:22 +01:00
Thomas Adam
a00cdcdfcb Merge branch 'obsd-master' 2018-09-27 11:02:37 +01:00
nicm
228e1a3951 Use same working directory rules for jobs as new windows rather than
always starting in home, GitHub issue 1488.
2018-09-27 07:43:18 +00:00
Nicholas Marriott
ebaf54251a Add formats for when window is larger than client, and show offset in
status-right by default when larger.
2018-09-26 18:41:18 +01:00
Nicholas Marriott
b74b047730 More of revert. 2018-09-26 16:49:03 +01:00
Nicholas Marriott
04c6db2d0f Revert "Add a B flag to mark windows bigger than the client."
This reverts commit b4e74f4310.
2018-09-26 16:42:29 +01:00
Nicholas Marriott
6abb62df1e Change the B into a +. 2018-09-25 21:57:29 +01:00
Thomas Adam
7cf00d6b72 Merge branch 'obsd-master' 2018-09-25 17:02:41 +01:00
nicm
7d59f82cf9 Allow panes to be 1 line or column by redrawing instead of using the
scroll region, from Soeren Tempel in GitHub issue 1487.
2018-09-25 14:27:20 +00:00
Nicholas Marriott
cbf1504fca Do not clamp to needed size since it may be too big. 2018-09-25 15:15:44 +01:00
Nicholas Marriott
83b2d5c513 window_printable_flags needs an additional argument. 2018-09-25 09:55:49 +01:00
Nicholas Marriott
b4e74f4310 Add a B flag to mark windows bigger than the client. 2018-09-25 09:54:47 +01:00
Nicholas Marriott
26d73a7736 Ignore clients that are suspended or exiting. 2018-09-25 09:48:48 +01:00
Nicholas Marriott
57069287a1 Add to TODO. 2018-09-25 08:27:53 +01:00
Thomas Adam
4799f43298 Merge branch 'obsd-master' 2018-09-24 17:02:38 +01:00
nicm
7bc6c105b7 Only include pane status in minimum size if it is turned on, GitHub
issue 1480.
2018-09-24 15:29:56 +00:00
Nicholas Marriott
ad71e7f9d2 Calculate size when trimming RHS correctly. 2018-09-24 12:17:29 +01:00
Nicholas Marriott
71d2ab184b Fix up merge. 2018-09-12 07:15:27 +01:00
Thomas Adam
c067af8e7d Merge branch 'obsd-master' 2018-09-11 20:11:11 +01:00
Nicholas Marriott
3fa538181b Restore window_pane_visible for drawing panes and borders, fixes issue
1458 reported by Felix Rosencrantz, problem located by Avi Halachmi.
2018-09-11 18:34:53 +01:00
nicm
be2201200f The cursor position is limited to the margins for CUF and CUB, so turn
margins off for printing cells (like most everything else already
does). Problem reported by Thomas Sattler.
2018-09-11 17:31:01 +00:00
Nicholas Marriott
84df87011c x,y -> px,py. 2018-09-11 09:39:28 +01:00
Thomas Adam
5e36d52651 Merge branch 'obsd-master' 2018-09-11 09:21:16 +01:00
nicm
bd9133b31d Do not check for mouse events on pane borders when zoomed, based on a
fix from Avi Halachmi.
2018-09-11 06:37:54 +00:00
Thomas Adam
9b32758a0c Merge branch 'obsd-master' 2018-09-10 09:02:39 +01:00
Nicholas Marriott
5aa435a9f0 window_get_active_at needs to check visible also. 2018-09-10 07:51:11 +01:00
nicm
1b92afa799 Do not clear selection when searching. 2018-09-10 06:48:01 +00:00
Nicholas Marriott
a618271e12 Bring back window_pane_visible to stop input going to panes which are
hidden by zoom.
2018-09-10 07:19:17 +01:00
Nicholas Marriott
8598fd1bc5 Add to TODO. 2018-09-09 07:52:28 +01:00
Nicholas Marriott
59df942e09 Fixes to resize-window from Ben Boeckel. 2018-09-05 08:43:58 +01:00
Nicholas Marriott
621bb15b83 Cast parameters to tparm, from Christos Zoulas via Leonardo Taccari. 2018-09-05 08:42:17 +01:00
Thomas Adam
8e24b0bb3e Makefile.am: Add space between -f and argument
Required for some (older) aek instance -- namely NetBSD.
2018-09-04 13:13:32 +01:00
Thomas Adam
0c07b10b30 Merge branch 'obsd-master' 2018-09-03 11:02:39 +01:00
nicm
8f9491ddfe Allow a large line number to go to the end with goto-line, from Mark
Kelly in GitHub issue 1460.
2018-09-03 08:51:43 +00:00
nicm
9bab73f489 Fix selection test, from Takeshi Banse. 2018-09-03 08:47:27 +00:00
Nicholas Marriott
4e867202e8 Add to TODO. 2018-08-31 14:10:51 +01:00
Thomas Adam
e27b588b6c Merge branch 'obsd-master' 2018-08-29 21:02:37 +01:00
Nicholas Marriott
479cac4896 Fix target line for fast path in tty_draw_pane. 2018-08-29 20:52:27 +01:00
nicm
95e3e363ff Reset line flag when clearing selection, GitHub issue 1454. 2018-08-29 18:54:23 +00:00
Nicholas Marriott
7637518b07 Fix refresh-client flags. 2018-08-29 18:59:43 +01:00
Nicholas Marriott
9263a65b5f Update TODO. 2018-08-29 18:52:04 +01:00
Thomas Adam
b29028a914 Merge branch 'obsd-master' 2018-08-29 13:02:38 +01:00
Thomas Adam
1ea17a72f0 Merge branch 'obsd-master' 2018-08-29 11:02:36 +01:00
nicm
f57aa143c1 Keep any text killed in the command prompt with C-w and yank it with
C-y, only use the top buffer if no text has previously been killed. This
and previous change promped by discussion with kn@.
2018-08-29 09:50:32 +00:00
nicm
e53094bc5f Add C-Left and C-Right as aliases for M-b and M-f. 2018-08-29 08:56:51 +00:00
Thomas Adam
18b611bc8d Merge branch 'obsd-master' 2018-08-27 13:02:38 +01:00
nicm
79d2351ce8 Memory leaks, from Gang Fan in GitHub issue 1453. 2018-08-27 11:03:34 +00:00
Nicholas Marriott
79a9472dbc tty_clamp_* need to use wp->xoff and wp->yoff for the check (which
don't include status line, line ox and oy), but ctx->xoff and yp->off
to calculate the position (which do have the statu line).
2018-08-26 14:10:39 +01:00
Thomas Adam
d64daf874f Merge branch 'obsd-master' 2018-08-26 11:02:38 +01:00
nicm
1b4402c823 Add q: format prefix to escape sh(1) special characters. Suggested by
someone ages ago and then more recently in GitHub issue 1449.
2018-08-26 09:28:42 +00:00
Nicholas Marriott
7fbd2f5498 Do not draw cells which have no cell (zoomed and they are not active). 2018-08-25 13:55:50 +01:00
Thomas Adam
45841400f2 Merge branch 'obsd-master' 2018-08-23 21:02:36 +01:00
nicm
f38b5a1b58 all_jobs can be static. 2018-08-23 18:39:12 +00:00
Thomas Adam
da5d563375 Merge branch 'obsd-master' 2018-08-23 19:02:40 +01:00
nicm
bceccc6b63 Move job struct into job.c. 2018-08-23 15:45:05 +00:00
Nicholas Marriott
183193bdbc Update CHANGES. 2018-08-23 08:52:22 +01:00
Thomas Adam
5b93f0fcd3 Merge branch 'obsd-master' 2018-08-22 23:02:43 +01:00
Nicholas Marriott
ee3e0eb183 Update TODO. 2018-08-22 21:29:30 +01:00
nicm
55db3623bf Add StatusLeft and StatusRight mouse key modifiers for the left and
right parts of the status line.
2018-08-22 20:06:14 +00:00
Nicholas Marriott
db8849e7ca Update TODO. 2018-08-21 09:29:12 +01:00
Nicholas Marriott
bfc9fb4b3b Add flags to refresh-client (-U -D -L -R and -c) to pan a window that
is larger than the client manually. Bound to S-Up, S-Down, S-Left,
S-Right and Delete manually.

Also add aliases for keys DC = Delete, IC = Insert, and make
refresh-client -C accept XxY as well as X,Y to match default-size.
2018-08-21 09:27:19 +01:00
Nicholas Marriott
314ee137a9 The stored mouse position should not include the status line offset if any. 2018-08-21 09:10:23 +01:00
Thomas Adam
f36d2ecb07 Merge branch 'obsd-master' 2018-08-20 23:02:38 +01:00
nicm
98a478ceb3 Move offset of window list into status struct. 2018-08-20 20:41:58 +00:00
Nicholas Marriott
9f39470b38 Only screen-redraw.c needs to adjust for message or prompt when the
status line is off, get rid of tty_status_lines and just pass the
client into status_line_size so it can check the CLIENT_STATUSOFF flag
as well.
2018-08-20 20:05:34 +01:00
Nicholas Marriott
458b4b7701 Need to adjust for lines if at top. 2018-08-20 19:45:32 +01:00
Nicholas Marriott
31508228bc Use the y offset from the context which has already been adjusted for
the status line, also make tty_clamp_line adjust the y position.
2018-08-20 19:34:04 +01:00
Nicholas Marriott
1e8c9fb490 Update CHANGES. 2018-08-20 17:52:27 +01:00
Thomas Adam
098967a085 Merge branch 'obsd-master' 2018-08-20 17:02:39 +01:00
nicm
665f046950 Add -Z to find-window as well. 2018-08-20 15:00:42 +00:00
Nicholas Marriott
641191ab20 Support for windows larger than the client.
This adds two new options, window-size and default-size, and a new
command, resize-window.

The force-width and force-height options, and the session_width and
session_height formats have been removed.

The new window-size option tells tmux how to work out the size of
windows: largest means it picks the size of the largest session,
smallest the smallest session (similar to the old behaviour) and
manual means that it does not automatically resize
windows. aggressive-resize modifies the choice of session for largest
and smallest as it did before.

If a window is in a session attached to a client that is too small,
only part of the window is shown. tmux attempts to keep the cursor
visible, so the part of the window displayed is changed as the cursor
moves (with a small delay, to try and avoid excess redrawing when
applications redraw status lines or similar that are not currently
visible).

Drawing windows which are larger than the client is not as efficient
as those which fit, particularly when the cursor moves, so it is
recommended to avoid using this on slow machines or networks (set
window-size to smallest or manual).

The resize-window command can be used to resize a window manually. If
it is used, the window-size option is automatically set to manual for
the window (undo this with "setw -u window-size"). resize-window works
in a similar way to resize-pane (-U -D -L -R -x -y flags) but also has
-a and -A flags. -a sets the window to the size of the smallest client
(what it would be if window-size was smallest) and -A the largest.

For the same behaviour as force-width or force-height, use
resize-width -x or -y.

If the global window-size option is set to manual, the default-size
option is used for new windows. If -x or -y is used with new-session,
that sets the default-size option for the new session.

The maximum size of a window is 10000x10000. But expect applications
to complain and higher memory use if you make a window that big. The
minimum size is the size required for the current layout including
borders.

This change allows some code improvements, most notably that since
windows can now never be cropped, that code can be removed from the
layout code, and since panes can now never be outside the size of the
window, window_pane_visible can be removed.
2018-08-20 15:22:14 +01:00
nicm
9f2db6a0af Fix problems with page scrolling in copy mode, GitHub issue 1440 from
Amos Bird.
2018-08-20 13:51:09 +00:00
Thomas Adam
bf03197e18 Merge branch 'obsd-master' 2018-08-19 21:40:26 +01:00
nicm
cac4eadca0 Add a flag to force redrawing of the status line even if the content
hasn't changed, needed for resizing.
2018-08-19 20:13:07 +00:00
Thomas Adam
3310972d75 Merge branch 'obsd-master' 2018-08-19 21:02:37 +01:00
nicm
d95fad3d5f Expand \u and \U escape sequences in command strings, from Christopher
Hunt in GitHub issue 1443.
2018-08-19 19:03:46 +00:00
Thomas Adam
9ecf657703 Merge branch 'obsd-master' 2018-08-19 19:02:40 +01:00
nicm
88327c7698 Add a client redraw-window flag instead of the redraw-all flag and for
all just use the three flags together (window, borders, status).
2018-08-19 16:45:03 +00:00
Thomas Adam
e811132b05 Merge branch 'obsd-master' 2018-08-18 23:02:40 +01:00
nicm
bd2896b65e SESSION_UNATTACHED flag is no longer necessary now we have an attached
count instead.
2018-08-18 20:08:52 +00:00
Thomas Adam
522d751eee Merge branch 'obsd-master' 2018-08-18 19:02:39 +01:00
nicm
3bc08b0dc0 Some tidying and helper functions. 2018-08-18 16:14:03 +00:00
Nicholas Marriott
af679326b2 Now master again. 2018-08-17 11:46:08 +01:00
Nicholas Marriott
aa6e6fa0f2 2.8. 2018-08-17 11:45:40 +01:00
Nicholas Marriott
9bdbe171b7 2.8-rc. 2018-08-17 11:31:16 +01:00
Thomas Adam
98a3c98c28 Merge branch 'obsd-master' 2018-08-17 11:20:20 +01:00
Nicholas Marriott
de2ddddd60 Add a full stop. 2018-08-17 10:30:04 +01:00
nicm
a9ffb56b65 Add the KEYC_XTERM flag to all function keys that imply a modifier so
that they are correctly translated into xterm(1)-style keys. GitHub
issue 1437.
2018-08-16 14:04:03 +00:00
nicm
14b97fc889 Add size to arguments struct too. 2018-08-14 11:38:05 +00:00
nicm
d0a600ccaa Some tidying, use a struct for arguments (there will be more later) and
add a helper function.
2018-08-14 11:31:34 +00:00
Thomas Adam
a368548645 Merge branch 'obsd-master' 2018-08-10 11:41:07 +01:00
Nicholas Marriott
13fe06a459 Update CHANGES. 2018-08-10 10:21:40 +01:00
nicm
87e87030fe Whoops, didn't mean to commit this. 2018-08-09 09:54:22 +00:00
nicm
a5ef1f2ed6 Bump the UTF-8 character array up to 18 to allow for more combining
characters (some languages use up to five). This size doesn't make as
much difference now that UTF-8 goes into an extended cell. GitHub issue
1430.
2018-08-09 09:53:44 +00:00
nicm
f5d7a80272 calloc the mode data instead of malloc and initialize everything. 2018-08-05 08:59:30 +00:00
Thomas Adam
33f9b316a3 Merge branch 'obsd-master' 2018-08-02 21:02:25 +01:00
nicm
d6ff630498 Log command arguments. 2018-08-02 18:35:21 +00:00
Thomas Adam
eceaa9a493 Merge branch 'obsd-master' 2018-08-02 15:02:25 +01:00
Thomas Adam
2e19a5ecb9 Merge branch 'obsd-master' 2018-08-02 13:02:26 +01:00
nicm
fb1f0fee5a session_groups can be static also. 2018-08-02 11:56:12 +00:00
nicm
6048b0f483 Make key trees and some other bits static. 2018-08-02 11:44:07 +00:00
nicm
f12b857415 Minor tidying. 2018-08-02 11:18:34 +00:00
Thomas Adam
79bdca4638 Merge branch 'obsd-master' 2018-08-02 11:02:25 +01:00
nicm
21f8ac2766 Make display-panes block the client until a pane is chosen or it times out. 2018-08-02 07:55:16 +00:00
Thomas Adam
89b56c3451 Merge branch 'obsd-master' 2018-08-01 17:02:25 +01:00
nicm
fe7486d43b Initialize new lineflag member. 2018-08-01 15:22:40 +00:00
Thomas Adam
400b807d75 Merge branch 'obsd-master' 2018-07-31 17:02:31 +01:00
nicm
5f07da6227 Do not leak path or use it after free. 2018-07-31 13:06:44 +00:00
Thomas Adam
7eb3ef66e5 Merge branch 'obsd-master' 2018-07-31 13:02:25 +01:00
nicm
82776c456e Move struct screen_sel into screen.c and tidy up members that are only
used by copy mode.
2018-07-31 11:49:26 +00:00
nicm
80bdd89856 Clear history on RIS like most other terminals do. 2018-07-31 10:32:19 +00:00
Thomas Adam
ed6327c87b Merge branch 'obsd-master' 2018-07-30 13:02:25 +01:00
nicm
b21a710de7 Remove a leftover unused struct. 2018-07-30 11:24:55 +00:00
Thomas Adam
aa32457772 Merge branch 'obsd-master' 2018-07-23 21:02:25 +01:00
kn
5c78b48cdf Point to glob in section 7 for the actual list of special characters instead
the C API in section 3.

OK millert jmc nicm, "the right idea" deraadt
2018-07-23 19:02:49 +00:00
Thomas Adam
5fc2d4a4fc Merge branch 'obsd-master' 2018-07-17 21:02:24 +01:00
nicm
969af935f3 When a key isn't in the first table, we need to try the same key again
not the any key. Also rename some labels. Fixes GitHub issue 1406
reeported by Mark Kelly.
2018-07-17 18:02:40 +00:00
Thomas Adam
4f04b2094c Merge branch 'obsd-master' 2018-07-16 11:02:25 +01:00
nicm
0d88f8a78b Add an "Any" key to run a command if a key is pressed that is not bound
in the current key table. GitHub issue 1404.
2018-07-16 08:48:22 +00:00
Thomas Adam
6de991d855 Merge branch 'obsd-master' 2018-07-15 11:02:25 +01:00
nicm
ff67ef945d Fix new-window -k, GitHub issue 1403. 2018-07-15 06:57:13 +00:00
Thomas Adam
711b8164bb Merge branch 'obsd-master' 2018-07-11 11:02:26 +01:00
Nicholas Marriott
35985c0add Updates to CHANGES. 2018-07-11 09:51:18 +01:00
nicm
cfc81692e6 Expand formats in load-buffer and save-buffer. 2018-07-11 08:29:21 +00:00
Thomas Adam
a4a7c3c68d Merge branch 'obsd-master' 2018-07-11 09:02:25 +01:00
nicm
e7d53020b4 Helper function to shorten history. 2018-07-11 06:51:39 +00:00
nicm
03519021b9 Add function comments. 2018-07-11 06:43:45 +00:00
Thomas Adam
6f2698004e Merge branch 'obsd-master' 2018-07-06 09:02:24 +01:00
nicm
28a5bc8fae Add a rectangle_toggle format, from Hirokazu Hata. 2018-07-06 07:11:23 +00:00
Thomas Adam
20154f391e Merge branch 'obsd-master' 2018-07-04 15:02:25 +01:00
jmc
98c4291df2 whitespace needed between macro args and punctuation; 2018-07-04 13:27:32 +00:00
Nicholas Marriott
5c0ce192ed +README.ja. 2018-07-04 13:45:40 +01:00
nicm
cc743dc296 Add set-hook -R to run a hook immediately (useful to set multiple hooks
to the same thing).
2018-07-04 12:30:52 +00:00
nicm
d254293a6d Add pane focus hooks. 2018-07-04 12:25:26 +00:00
Thomas Adam
850c26dd46 Merge branch 'obsd-master' 2018-07-04 13:02:25 +01:00
Nicholas Marriott
db07f33886 Japanese README from Kohei Takada. 2018-07-04 10:47:14 +01:00
nicm
2fae6a5761 Add accessors for grid linedata member, for some future work. From Dan
Aloni.
2018-07-04 09:44:07 +00:00
Thomas Adam
2ee0962c96 Merge branch 'obsd-master' 2018-07-02 15:02:25 +01:00
nicm
42935bde71 Fire notify for select-layout, from George Nachman. 2018-07-02 12:39:14 +00:00
Nicholas Marriott
ffebf00585 Solaris 11.4 and later prefers mdoc, from Alan Coopersmith. 2018-07-02 13:36:44 +01:00
Thomas Adam
ead6d652ff Merge branch 'obsd-master' 2018-06-27 19:02:25 +01:00
nicm
a14aa788d4 Allow any punctuation (except :) as separator in s/x/y/, not only
/. From JINNOUCHI Yasushi in GitHub issue 1386.
2018-06-27 17:36:10 +00:00
Thomas Adam
d8721b35a0 Merge branch 'obsd-master' 2018-06-26 15:02:25 +01:00
nicm
97738921cd Style nit. 2018-06-26 13:21:28 +00:00
Thomas Adam
486ce9b098 Merge branch 'obsd-master' 2018-06-26 13:02:25 +01:00
nicm
8fb6666f17 Do not take address of a member of a NULL pointer. GitHub issue 1382
from Kamil Rytarowski.
2018-06-26 11:14:05 +00:00
Thomas Adam
cb77c2aa78 Merge branch 'obsd-master' 2018-06-25 19:02:24 +01:00
nicm
0c94c3fbee If there are only two panes, always use the other pane as the last
pane. Based on a change from Duy Nguyen in GitHub issue 1377.
2018-06-25 17:23:16 +00:00
Thomas Adam
94712a8b0d Merge branch 'obsd-master' 2018-06-24 23:02:25 +01:00
nicm
dec6ec9e29 Minor cosmetic improvement from KOIE Hidetaka. 2018-06-24 21:24:09 +00:00
Thomas Adam
9da78d72de Merge branch 'obsd-master' 2018-06-11 13:02:25 +01:00
nicm
d0c992306d Fix some compiler warnings; from Thomas Adam. 2018-06-11 11:14:10 +00:00
Thomas Adam
54c2d48d7d Merge branch 'obsd-master' 2018-06-09 19:02:29 +01:00
nicm
e6cbeb4f38 Make it possible to resize multiple panes by dragging corners, from Dan
Aloni in GitHub issue 1376.
2018-06-09 17:05:52 +00:00
Thomas Adam
4581240ced Merge branch 'obsd-master' 2018-06-08 23:02:25 +01:00
nicm
f6bad7efd7 Instead of working out which pane to resize with the mouse by walking
the panes list, look through the layout cells for the nearest border and
resize that cell. From Dan Aloni in GitHub issue 1374.
2018-06-08 20:54:22 +00:00
Thomas Adam
713e0ddef3 Merge branch 'obsd-master' 2018-06-08 13:02:25 +01:00
nicm
ff45b2d343 Tweak previous - check for a NULL client and simplify manual text. 2018-06-08 09:43:58 +00:00
Thomas Adam
91280f1fca Linux: include sys/file.h for flock() 2018-06-07 09:17:05 +01:00
Thomas Adam
7de25d86e1 Merge branch 'obsd-master' 2018-06-03 13:02:31 +01:00
nicm
ba31d3a88c Increment the lines counter when skipping a line to avoid an infinite
loop, and fix a check to avoid a potential out-of-bounds access. Problem
reported by Yuxiang Qin and tracked down by Karl Beldan; GitHub issue
1352.

Also a man page fix request by jmc@.
2018-06-03 10:17:30 +00:00
Thomas Adam
54cd292f09 Merge branch 'obsd-master' 2018-05-29 11:02:26 +01:00
nicm
d1f5142dab If foo doesn't exist and can't be expanded in #{?foo,a,b} then assume it
is false.
2018-05-29 09:10:30 +00:00
Thomas Adam
058d2b94dc Merge branch 'obsd-master' 2018-05-28 15:02:31 +01:00
nicm
c177a627d2 When looking for panes, ignore dead ones (with -1 file
descriptor). GitHub issue 1354.
2018-05-28 11:50:47 +00:00
Nicholas Marriott
8f8e0975f1 Add format string test, from "sadie-parayno" in GitHub issue 1358. 2018-05-28 12:48:15 +01:00
nicm
b602c1fb9a Document escaping inside conditionals, from "sadie-parayno" in GitHub
issue 1359.
2018-05-28 11:45:26 +00:00
Thomas Adam
7448b38327 Merge branch 'obsd-master' 2018-05-24 13:02:29 +01:00
Thomas Adam
85d5a377c5 Merge branch 'obsd-master' 2018-05-24 11:02:25 +01:00
nicm
b9a6162d2f Make server_client_get_cwd used (almost) everywhere we need to work out
the cwd, and do not fall back to "." as it is pretty useless. GitHub
issue 1331.
2018-05-24 09:42:49 +00:00
nicm
8f5903d7c3 Improve logging of the environment etc for new panes. 2018-05-24 09:34:54 +00:00
Thomas Adam
f0ac0d6793 Merge branch 'obsd-master' 2018-05-22 11:02:33 +01:00
nicm
2a04665626 Allow escaping , and } with # in #{}; GitHub issue 1332. 2018-05-22 08:49:12 +00:00
Nicholas Marriott
07c0970f54 Sync tmux description with manual. 2018-05-22 08:02:43 +01:00
Thomas Adam
546123f950 Merge branch 'obsd-master' 2018-05-20 15:02:25 +01:00
nicm
f2f9605c63 -T should not actually select the pane. 2018-05-20 11:48:34 +00:00
Thomas Adam
e4e060f2be Merge branch 'obsd-master' 2018-05-15 17:02:31 +01:00
nicm
e3b034fac7 Fix switch-client -l, from Jean-Marc Eurin in GitHub issue 1343. 2018-05-15 14:58:09 +00:00
Thomas Adam
82c0eed36d Merge branch 'obsd-master' 2018-05-09 19:02:35 +01:00
nicm
80994a8de1 Mention allow-rename with \033k. 2018-05-09 16:20:50 +00:00
Thomas Adam
9e1093b7d7 Merge branch 'obsd-master' 2018-05-09 11:02:26 +01:00
nicm
f2029f9d9e Another check for NULL window if looking for index. 2018-05-09 07:50:03 +00:00
Thomas Adam
b2a2c3a1e9 Merge branch 'obsd-master' 2018-05-07 17:02:31 +01:00
nicm
f915a4bf0c Handle terminfo colors > 256 correctly, GitHub issue 1337. 2018-05-07 13:39:09 +00:00
Thomas Adam
91b220525b Merge branch 'obsd-master' 2018-05-04 11:02:31 +01:00
nicm
988c6bc433 Improve logging of sessions. 2018-05-04 08:21:42 +00:00
Thomas Adam
1d858aa89e Merge branch 'obsd-master' 2018-05-03 19:02:26 +01:00
nicm
e24a077752 Use window target if specified and exists even when looking for an
index, fixes neww -a with -t as well.
2018-05-03 16:56:59 +00:00
Thomas Adam
645fe9013f Merge branch 'obsd-master' 2018-04-26 17:02:31 +01:00
guenther
896c1da7da Use <fcntl.h> instead of <sys/file.h> for open() and friends.
Delete a bunch of unnecessary #includes and sort to match style(9)
while doing the above cleanup.

ok deraadt@ krw@
2018-04-26 12:42:51 +00:00
Thomas Adam
d24bd7394d Merge branch 'obsd-master' 2018-04-23 17:02:32 +01:00
Nicholas Marriott
aebb17dc75 Sync imsg from OpenBSD. 2018-04-23 15:40:15 +01:00
nicm
d9d2f84a4b Add KRB5CCNAME to update-environment. 2018-04-23 14:03:06 +00:00
nicm
068d1b97b2 #aabbcc will use RGB if supported so don't say it is closest match. 2018-04-23 13:51:21 +00:00
nicm
4bf6f2706e Check whether cursor is at start or end when copying rectangular
selections, from tb@.
2018-04-23 13:46:34 +00:00
nicm
9f39652d87 Remove unnecessary brackets. 2018-04-23 13:43:08 +00:00
Thomas Adam
c48440fd40 Merge branch 'obsd-master' 2018-04-23 11:02:27 +01:00
nicm
1afe71cc0a rxvt-unicode has some funny behaviour when scrolling with the cursor not
at column 1, so move it back there first if possible. GitHub issue 1318.
2018-04-23 07:41:30 +00:00
Thomas Adam
0e1b339c10 Merge branch 'obsd-master' 2018-04-18 17:02:28 +01:00
nicm
3dceddd70e Change how display-message uses the client. Originally it was only
intended as the target client where the message should be displayed but
at some point (perhaps when -p was added), it was used for format
expansion too. This means it can get a bit weird where you have client
formats expanding for a client with a different current session than the
target session.

However, it is nice that display-message can be used to show information
about a specific client. So change so that the -c client will be used if
the session matches the target session (-t or default), otherwise the
best client will be chosen.
2018-04-18 14:35:37 +00:00
nicm
2595718dd3 Include source function name in grid_check_y logging. 2018-04-18 14:31:42 +00:00
Thomas Adam
6ebd737590 Merge branch 'obsd-master' 2018-04-18 15:02:25 +01:00
nicm
e64d078a4c Fix || example. 2018-04-18 12:50:11 +00:00
Nicholas Marriott
ae0b7c7d72 Some changes. 2018-04-13 17:59:11 +01:00
Nicholas Marriott
a770ef3e2a Merge branch '2.7-rc' 2018-04-13 17:50:40 +01:00
Nicholas Marriott
b95d1de8fd 2.7. 2018-04-13 17:47:36 +01:00
Thomas Adam
7e5262ae9a Merge branch 'obsd-master' 2018-04-11 13:02:28 +01:00
nicm
14ecb5032e Allow no client for rename-session, from Ryan Freeman. 2018-04-11 09:54:45 +00:00
Thomas Adam
1bd66b65a3 Merge branch 'obsd-master' 2018-04-10 13:02:28 +01:00
nicm
051a29ca03 A couple of fixes to the : form of SGR. Apparently there is an extra
argument that nobody knew about, so skip that if it exists. Also there
are a bunch of useless optional arguments at the end, so ignore those.
2018-04-10 11:20:15 +00:00
nicm
c6975b3bb4 Add x and X to choose-tree (with a confirmation prompt) to kill an
item. Suggested by Matt Zagrabelny.
2018-04-10 10:48:44 +00:00
Nicholas Marriott
68bf7c532b Merge branch '2.7-rc' 2018-04-06 12:53:43 +01:00
Thomas Adam
9b73d76ddd Merge branch 'obsd-master' 2018-04-06 11:02:24 +01:00
nicm
5d616f4c72 Fix link, from Eliran Gonen. 2018-04-06 09:09:38 +00:00
nicm
8a81993ae1 Do not crash on empty window, reported by Jamie Macdonald in GitHub
issue 1299. Patch from Thomas Adam.
2018-03-29 13:19:19 +01:00
Thomas Adam
b5c0b2cae2 Merge branch 'obsd-master' 2018-03-29 10:28:18 +01:00
nicm
803b8815bd Do not crash on empty window, reported by Jamie Macdonald in GitHub
issue 1299. Patch from Thomas Adam.
2018-03-29 08:03:51 +00:00
nicm
785ce66ab9 Fix a regression: do not warn about no client in rename-window. 2018-03-26 07:39:12 +01:00
Thomas Adam
640d97afd0 Merge branch 'obsd-master' 2018-03-23 20:02:31 +00:00
nicm
194e9f611b Fix a regression: do not warn about no client in rename-window. 2018-03-23 19:17:03 +00:00
nicm
ea295ac397 Fix size calculation when spreading out panes. 2018-03-23 10:07:54 +00:00
Thomas Adam
5512de6a61 Merge branch 'obsd-master' 2018-03-23 10:02:30 +00:00
nicm
26792b9035 Fix size calculation when spreading out panes. 2018-03-23 07:44:44 +00:00
Nicholas Marriott
919f55ac4a Merge branch '2.7-rc' 2018-03-22 11:26:32 +00:00
Nicholas Marriott
2cd0ba5057 CHANGES for 2.7. 2018-03-22 11:25:58 +00:00
Nicholas Marriott
80283f99fb Revert "2.7-rc."
This reverts commit ced74bd72c.
2018-03-22 11:18:26 +00:00
Nicholas Marriott
ced74bd72c 2.7-rc. 2018-03-22 11:18:05 +00:00
Nicholas Marriott
50e3e3e72f Remove EVENT_* variables from environment after initializing libevent so they
are not carried into child processes; from Henry Qin.
2018-03-21 08:15:15 +00:00
Thomas Adam
c8a706117f Merge branch 'obsd-master' 2018-03-17 18:02:26 +00:00
nicm
0b3911631b Fix negative window index range check (> not <). Reported by Juan Pablo
in GitHub issue 1283.
2018-03-17 16:48:17 +00:00
Thomas Adam
0ca78ee51f Merge branch 'obsd-master' 2018-03-16 16:02:28 +00:00
nicm
f87d80737e Insert full size panes at the right position, from KOIE Hidetaka in
GitHub issue 1284.
2018-03-16 15:15:39 +00:00
Thomas Adam
9fd9952752 Merge branch 'obsd-master' 2018-03-08 10:02:26 +00:00
nicm
19f3a5c612 Add a missing client-detached hook when the server shuts down, and do
not exit until jobs started from run-shell/if-shell have finished (add a
job flags member and a flag to indicate other jobs). GitHub issue 1245.
2018-03-08 08:09:10 +00:00
Thomas Adam
3c451a64b5 Merge branch 'obsd-master' 2018-03-05 14:02:29 +00:00
nicm
85c48aafff For some reason tmux treats SGR 10 as SGR 0. It has done since the first
version and I'm not sure why since no other terminal appears to. Change
to just ignore SGR 10 instead.
2018-03-05 12:32:28 +00:00
Nicholas Marriott
61ea49c6dd Fix cmp use. 2018-03-02 15:08:34 +00:00
Thomas Adam
3b8f92359d Merge branch 'obsd-master' 2018-03-01 14:02:27 +00:00
nicm
182357f24b Expand formats in window and session names. 2018-03-01 12:53:08 +00:00
Thomas Adam
0ca9664ecf Merge branch 'obsd-master' 2018-02-28 10:02:29 +00:00
nicm
508e2f0b3a Add -Z flag to choose-tree, choose-client, choose-buffer to
automatically zoom the pane when the mode is entered and unzoom when it
exits, assuming the pane is not already zoomed. Add -Z to the default
key bindings.
2018-02-28 08:55:44 +00:00
Thomas Adam
f5a37d0071 Merge branch 'obsd-master' 2018-02-26 10:02:30 +00:00
nicm
4d72b8fff7 C-g for modes too, from Mike Hamrick. 2018-02-26 08:09:56 +00:00
Thomas Adam
9464b94f64 Merge branch 'obsd-master' 2018-02-22 14:02:30 +00:00
Thomas Adam
c2aa40449c Merge branch 'obsd-master' 2018-02-22 12:02:31 +00:00
nicm
3f3f13fbd7 Remove an unused variable. 2018-02-22 11:42:41 +00:00
nicm
e97daead43 Check prefix when retrying so it is checked while repeat flag is
set. GitHub issue 1239.
2018-02-22 10:58:12 +00:00
nicm
623f4b12d3 Add exit-empty option to exit server if no sessions (defaults to on). 2018-02-22 10:54:51 +00:00
Thomas Adam
5a44e18490 Merge branch 'obsd-master' 2018-02-20 12:02:23 +00:00
nicm
ab6f0bb348 Do not leak memory when working out job name in formats. 2018-02-20 10:43:46 +00:00
Thomas Adam
4e8b1b9ac2 Merge branch 'obsd-master' 2018-02-19 22:02:29 +00:00
Nicholas Marriott
d81aec2439 Update CHANGES. 2018-02-19 21:24:17 +00:00
nicm
6ae04dd5a0 Support ISO colon-separated SGR. 2018-02-19 21:20:10 +00:00
Thomas Adam
968296bb07 Merge branch 'obsd-master' 2018-02-16 12:02:29 +00:00
nicm
320abba341 Reflowing the grid in-place involved way too much memmove() for a big
performance cost with a large history. Instead change back to using a
second grid and copying modified lines over which is much faster (this
doesn't revert to the old code however which didn't support UTF-8
properly). GitHub issue 1249.
2018-02-16 09:51:41 +00:00
Thomas Adam
88711e885e Merge branch 'obsd-master' 2018-02-05 10:02:31 +00:00
nicm
7f4513ec34 Add struct status_line to hold status line members of struct client, not
used yet but will be soon. From Thomas Adam.
2018-02-05 08:21:54 +00:00
Thomas Adam
2d5101621b Merge branch 'obsd-master' 2018-02-05 08:02:27 +00:00
nicm
0817132f97 Show if filter is active/no matches in modes. 2018-02-05 06:51:41 +00:00
Thomas Adam
24abfb72eb Merge branch 'obsd-master' 2018-02-04 12:02:24 +00:00
nicm
fe7a871a23 Upstream ncurses has introduced terminfo capabilities to specify RGB
colour ("true" or "direct" colour). These consist of new entries (such
as "xterm-direct") which have a different setaf/setab implementation,
colors and pairs set to 0x1000000 and 0x10000, and a new RGB flag.

The setaf/setab definitions seem to be geared towards what ncurses (or
emacs maybe) needs, in that the new versions do only ANSI and RGB
colours (they can't be used for the 256 colour palette); they rely on
the silly ISO colon-separated version of SGR; and they use a weird
multiplication scheme so they still only need one argument. The higher
values of colors and pairs require a recent ncurses to parse.

tmux can use the RGB flag to detect RGB colour support (keeping the old
Tc extension for backwards compatibility for now). However, as we still
want to send 256 colour information unchanged when possible, the new
setaf/setab are awkward. So when RGB is present, reserve setaf/setab
only for ANSI colours and use the escape sequences directly for 256 and
RGB colours. (To my knowledge no recent terminal uses unusual escape
sequences for these in any case.)
2018-02-04 10:10:39 +00:00
Nicholas Marriott
4e4c500879 Add more to TODO. 2018-01-29 12:46:52 +00:00
Nicholas Marriott
0407d847a4 Add to TODO. 2018-01-29 12:44:31 +00:00
Thomas Adam
19afd842bf Merge branch 'obsd-master' 2018-01-18 16:02:25 +00:00
nicm
17d4c39f24 Discard all but the last line when reading from a #() command - the
callback is just going to be fired again straight away to go through all
the lines, it is better just to use the last one straight away.
2018-01-18 14:28:11 +00:00
Thomas Adam
d9e740f86d Merge branch 'obsd-master' 2018-01-18 08:02:30 +00:00
nicm
c9037fde1c Remove unused hooks_run function, from Thomas Adam. 2018-01-18 07:10:53 +00:00
Thomas Adam
84ddc72744 Merge branch 'obsd-master' 2018-01-17 11:26:10 +00:00
nicm
75842bfe66 Fix drawing of ACS characters (they need to go character-at-a-time),
accidentally broken in last commit.
2018-01-16 17:03:18 +00:00
nicm
5849b73b81 Add -I to pipe-pane to connect pane stdin as well as stdout, suggested
by Kristof Kovacs in GitHub issue 1186.
2018-01-16 09:00:38 +00:00
Nicholas Marriott
58e9d12f23 msys is apparently a cygwin variant that doesn't say it is cygwin... 2018-01-16 08:29:15 +00:00
nicm
53b25635da Another redundant check, GitHub issue 1219. 2018-01-15 15:30:03 +00:00
nicm
481703d669 Some unused code, GitHub issue 1219. 2018-01-15 15:27:03 +00:00
nicm
b0c1cefeda Do not collect top-bit-set characters in case they need to be replaced. 2018-01-12 16:43:47 +00:00
nicm
2c5a6f9af5 Simplify character replacement on non-UTF-8 terminals and make a common
function.
2018-01-12 16:41:00 +00:00
nicm
c03565611e Simplify UTF-8 states down into one state. 2018-01-12 16:32:12 +00:00
nicm
f32fd2df69 Improve error message if creating socket parent directory fails, from
Thomas Adam for GitHub issue 1215.
2018-01-12 10:22:02 +00:00
nicm
829fe38ab1 Improve logging for layout cells. 2018-01-12 10:16:03 +00:00
Thomas Adam
06684c93de Merge branch 'obsd-master' 2018-01-01 12:01:13 +00:00
nicm
d17c90583a Prefer PWD for current directory if present in client, from Wei Zhao in
GitHub issue 1183.
2018-01-01 11:19:08 +00:00
nicm
fe26f977e6 Add C-g at command prompt for emacs people, GitHub issue 1213. 2018-01-01 11:03:54 +00:00
Thomas Adam
6e99a2f4bb Merge branch 'obsd-master' 2017-12-31 22:01:15 +00:00
nicm
c9896d9554 Initialize the size of new panes created by the even-* layout correctly;
reported by Andreas Kahari and Anton Lindqvist.
2017-12-31 20:00:44 +00:00
Thomas Adam
ad417f6eb7 Merge branch 'obsd-master' 2017-12-28 14:01:14 +00:00
nicm
299c552e33 Redrawing status is needed after changing window flags or title does not
update if status line is off, GitHub issue 1191.
2017-12-28 12:10:50 +00:00
Thomas Adam
cd46568ebe Merge branch 'obsd-master' 2017-12-27 14:43:20 +00:00
nicm
937f8ed095 Draw command prompt correctly with status line off. 2017-12-27 13:55:42 +00:00
Nicholas Marriott
6ce8fe0537 Still need to globfree on failure. 2017-12-27 13:54:37 +00:00
nicm
c363c236aa Fix memory leak in screen_redraw_make_pane_status. 2017-12-22 23:16:41 +00:00
Thomas Adam
e19df0e869 Merge branch 'obsd-master' 2017-12-22 12:01:22 +00:00
nicm
7ba5ad4cfb Do not try to set default value on user options (they don't have one),
from Charles Howard in GitHub issue 1161.
2017-12-22 10:18:51 +00:00
nicm
5c82432200 Remove duplicate WheelUp/WheelDown entries in list, GitHub issue 1184. 2017-12-22 10:16:36 +00:00
Thomas Adam
74ecc866cf Merge branch 'obsd-master' 2017-12-19 16:01:20 +00:00
nicm
b20a00f93e Report better error from server when socket create fails, GitHub issue
1201.
2017-12-19 15:00:39 +00:00
Thomas Adam
641a885af8 Merge branch 'obsd-master' 2017-12-19 00:01:18 +00:00
nicm
62144b9f57 Do not try to put more in command message than will fit when sending
(the server will treat as a fatal error). GitHub issue 1200.
2017-12-18 22:13:36 +00:00
Thomas Adam
43a1294ed9 Merge branch 'obsd-master' 2017-12-18 14:01:18 +00:00
nicm
58f6456af7 Remove unused variable from Thomas Adam. 2017-12-18 12:39:34 +00:00
Thomas Adam
2c6af068d7 Merge branch 'obsd-master' 2017-11-17 12:01:17 +00:00
nicm
695dc5a153 Allow formats in selectp -T, from Thomas Adam. 2017-11-17 09:52:18 +00:00
Thomas Adam
5fddddbe21 Merge branch 'obsd-master' 2017-11-16 12:01:18 +00:00
nicm
e5ae9dd53d Add -and-cancel variants for scrolling commands to exit copy mode when
the bottom is reached, from Stephen Hicks.
2017-11-16 11:16:15 +00:00
Thomas Adam
102df8dc80 Merge branch 'obsd-master' 2017-11-15 22:01:22 +00:00
Nicholas Marriott
e58d16b2df Add to CHANGES. 2017-11-15 20:14:49 +00:00
Thomas Adam
e755ca37b3 Merge branch 'obsd-master' 2017-11-15 20:01:22 +00:00
nicm
3b649d2fcd Add a common function for spreading out cells and use it for the two
even layouts and to add a -E flag to select-layout to spread out cells
evenly without changing parent cells.
2017-11-15 19:59:27 +00:00
nicm
533a5719c5 Completely rewrite the reflow code to correctly handle double width
characters (previously they were not accounted for).
2017-11-15 19:21:24 +00:00
nicm
aeda2e5808 If there is a double width character at the very end of the line with
not enough room to draw it, just leave it out.
2017-11-15 19:18:57 +00:00
Thomas Adam
392da897ff Merge branch 'obsd-master' 2017-11-13 14:01:18 +00:00
nicm
d81fa579c3 When searching in copy mode, do not scroll if the result is already on
screen. GitHub issue 1150.
2017-11-13 11:49:11 +00:00
Thomas Adam
515da63d2b Merge branch 'obsd-master' 2017-11-10 00:01:19 +00:00
nicm
384736e955 If we successfully change the directory, set PWD too to give the shell a
hint in case of symlinks.
2017-11-09 23:02:13 +00:00
Thomas Adam
6f3b6c8d92 Merge branch 'obsd-master' 2017-11-03 18:01:21 +00:00
nicm
a2681ffcee Clear key properly if on space with nothing in it. 2017-11-03 17:11:20 +00:00
nicm
50a5f84cb4 Support mouse on preview in tree mode. 2017-11-03 17:02:33 +00:00
Thomas Adam
24c387206c Merge branch 'obsd-master' 2017-11-03 16:01:17 +00:00
nicm
ba93a647f1 Change mouse in modes so that one click moves the cursor and a double
click chooses the line.
2017-11-03 14:23:44 +00:00
Thomas Adam
e1606172dd Merge branch 'obsd-master' 2017-11-03 00:01:20 +00:00
Thomas Adam
c9ec33d0d0 Merge branch 'obsd-master' 2017-11-02 22:01:20 +00:00
nicm
43264dfbf4 Make the mode draw function use the parent screen directly rather than
its own to avoid copying twice.
2017-11-02 22:00:42 +00:00
nicm
8d37f699ad Add a "fast" version of screen_write_copy for tree mode that doesn't do
all the checks and selection and marking stuff needed for copy mode.
2017-11-02 21:29:17 +00:00
Thomas Adam
8c29f7413b Merge branch 'obsd-master' 2017-11-02 20:01:26 +00:00
nicm
17655e5ba6 Format for group list of "other sessions" is a bit weird, just list all
the sessions in the group.
2017-11-02 18:52:05 +00:00
nicm
95850e1aca Tweak previous slightly so that current session is chosen if it is in
the group rather than first.
2017-11-02 18:43:51 +00:00
nicm
c1f62f1fde Only show the first member of session groups in tree mode (-G flag
disables).
2017-11-02 18:27:35 +00:00
nicm
3887d95bca There is no point in reflowing panes which have not changed width. 2017-11-02 18:26:38 +00:00
Thomas Adam
cf782c4f54 Merge branch 'obsd-master' 2017-10-26 10:01:18 +01:00
nicm
e91e8a2a6c Fix crash exiting command prompt (from Alex Maese in GitHub issue 1139)
and a man page tweak from jmc.
2017-10-26 08:17:12 +00:00
Thomas Adam
d36ac3db15 Merge branch 'obsd-master' 2017-10-25 18:01:17 +01:00
nicm
be4c01697c Note that notifications are also hooks. 2017-10-25 15:20:10 +00:00
Thomas Adam
0072bc65e6 Merge branch 'obsd-master' 2017-10-25 16:01:22 +01:00
Nicholas Marriott
37f83adca8 Update CHANGES. 2017-10-25 15:26:54 +01:00
nicm
578a63bbc9 Default allow-rename to off because it is ridiculous that applications
are even able to do this and confusing when they do.
2017-10-25 14:14:52 +00:00
Thomas Adam
6b83ca0077 Merge branch 'obsd-master' 2017-10-25 14:01:26 +01:00
nicm
78ae4ee82c h/l keys for expand and collapse. 2017-10-25 12:13:20 +00:00
Nicholas Marriott
d6edd06749 Merge branch 'master' of github.com:tmux/tmux 2017-10-25 12:29:23 +01:00
Nicholas Marriott
6e8d29e9a2 Update TODO. 2017-10-25 12:29:10 +01:00
nicm
8dd776106d Add P key to paste tagged in buffer mode, and trim some code that should
no longer be necessary.
2017-10-25 11:26:11 +00:00
Thomas Adam
e85213a944 Merge branch 'obsd-master' 2017-10-22 15:47:07 +01:00
nicm
26f1857154 Use window_pane_index() when drawing pane numbers (so pane-base-index is
applied), from Thomas Adam. GitHub issue 1125.
2017-10-22 13:16:54 +00:00
Nicholas Marriott
f7a037ba26 Apparently vim(1) now has syntax highlighting built in, GitHub issue 1124. 2017-10-22 14:14:14 +01:00
Thomas Adam
61114c6c72 Merge branch 'obsd-master' 2017-10-20 16:01:17 +01:00
nicm
d3e8709ab5 Clear status line with spaces again so reverse works, spotted by sthen. 2017-10-20 13:10:54 +00:00
Nicholas Marriott
37531673a3 Need compat for queue.h. 2017-10-20 13:26:54 +01:00
Thomas Adam
31901e3c07 Merge branch 'obsd-master'
Conflicts:
	server-fn.c
2017-10-20 12:36:29 +01:00
Nicholas Marriott
a34de2e378 Save and restore LIBS when checking for b64_ntop, reported by Ralf Friedl. 2017-10-17 10:35:35 +01:00
nicm
2f6935a630 Infrastructure for drawing status lines of more than one line in height,
still only one is allowed but this lets tmux draw bigger ones.
2017-10-16 19:30:53 +00:00
nicm
a5fd5782f8 Show exit status and time in the remain-on-exit pane text, mostly from
Timo Boettcher in GitHub issue 1103.
2017-10-12 11:32:27 +00:00
Nicholas Marriott
fb02df66cc Merge branch 'master' of github.com:tmux/tmux 2017-10-12 11:56:32 +01:00
Nicholas Marriott
d10def5b0b Check missed during merge. 2017-10-12 11:56:06 +01:00
Thomas Adam
2357bfb254 Merge branch 'obsd-master' 2017-10-11 16:01:17 +01:00
Thomas Adam
87babfa473 Merge branch 'obsd-master' 2017-10-11 14:01:17 +01:00
nicm
eb9839fd32 Box around label in preview. 2017-10-11 12:57:49 +00:00
nicm
6e5121be7e Clear to end of line properly with UTF-8 present. 2017-10-11 11:26:58 +00:00
Thomas Adam
4efd41f3af Merge branch 'obsd-master' 2017-10-11 10:01:19 +01:00
nicm
99351c9cae Add C-n and C-p keys for tree mode, and choose the right initial line
when no panes.
2017-10-11 08:08:16 +00:00
Nicholas Marriott
60074a6bc6 Merge branch 'master' of github.com:tmux/tmux 2017-10-11 08:03:55 +01:00
Nicholas Marriott
a3967de9a5 Include headers if found regardless of forkpty. 2017-10-11 08:03:31 +01:00
Thomas Adam
044019d9d6 Merge branch 'obsd-master' 2017-10-09 14:01:16 +01:00
nicm
db44151a37 kind should be S-Down not S-Up. 2017-10-09 11:35:35 +00:00
Thomas Adam
ceab7154d4 Merge branch 'obsd-master' 2017-10-08 18:40:41 +01:00
nicm
0b4c408168 Fix description of history_size, from Campbell Barton. 2017-10-08 16:45:01 +00:00
Thomas Adam
f069c0ba09 Merge branch 'obsd-master' 2017-10-06 20:01:17 +01:00
nicm
9c4caf49a2 Support %else in config files to match %if, from Brad Town in GitHub
issue 1071.
2017-10-06 18:02:30 +00:00
Thomas Adam
2be01ab4ec Merge branch 'obsd-master' 2017-10-06 13:33:32 +01:00
nicm
b462063cd5 Add -- to some key bindings so leading -s work. 2017-10-05 13:43:34 +00:00
Nicholas Marriott
8aaf86a6ea Merge branch '2.6-rc' 2017-10-05 14:39:33 +01:00
Nicholas Marriott
bd71cbbe27 2.6. 2017-10-05 14:31:23 +01:00
nicm
88517ceebb Add support for the xterm(1) title stack, from Brad Town, GitHub issue
1075.
2017-10-05 13:29:18 +00:00
nicm
6a292f09ba When writing batches of characters to the screen, we need to clear
padding or later UTF-8 characters could be displayed incorrectly. GitHub
issue 1090.
2017-10-05 08:12:24 +00:00
nicm
71ec616e4d Initialize alerts timer event where it is used, avoids crash with new windows. 2017-09-22 17:58:30 +01:00
Thomas Adam
ff526e43de Merge branch 'obsd-master' 2017-09-22 12:01:13 +01:00
nicm
d563aa7c7b Initialize alerts timer event where it is used, avoids crash with new windows. 2017-09-22 09:04:46 +00:00
Thomas Adam
ae5a62a514 Merge branch 'obsd-master' 2017-09-13 10:01:10 +01:00
nicm
c86d83f835 Remove unused (always 1) arguments from some functions, from Daniel
Mueller in GitHub issue 1073.
2017-09-13 07:31:07 +00:00
Thomas Adam
9a1b9f15a1 Merge branch 'obsd-master' 2017-09-11 22:01:10 +01:00
nicm
af2c7ce646 Check event is initialized before delete; fixes crash reported by
Michael Nickerson in GitHub issue 1068.
2017-09-11 20:11:45 +00:00
Nicholas Marriott
b541a97821 2.6-rc3. 2017-09-11 10:12:25 +01:00
Nicholas Marriott
a8b84b7cfa 2.6-rc3. 2017-09-11 10:08:28 +01:00
Nicholas Marriott
495e2ed17f Merge branch 'master' into 2.6-rc 2017-09-11 10:08:15 +01:00
Thomas Adam
d8c397d1b7 Merge branch 'obsd-master' 2017-09-11 10:01:11 +01:00
nicm
d8d6c2746e Mention that filter is a format. 2017-09-11 06:53:06 +00:00
nicm
6fdaaa0637 Do not free more lines than are available in the history. 2017-09-11 06:40:46 +00:00
Nicholas Marriott
034b19b734 2.6-rc2. 2017-09-10 16:08:22 +01:00
Nicholas Marriott
cb8eba1530 Merge branch 'master' into 2.6-rc 2017-09-10 16:07:44 +01:00
Thomas Adam
7aa8b8a25c Merge branch 'obsd-master' 2017-09-10 16:01:14 +01:00
Nicholas Marriott
abcbfcb0e8 Merge branch 'master' into 2.6-rc 2017-09-10 15:38:02 +01:00
nicm
70bc07a358 Previously, extended cell data was never reduced in size even when the
cell was overwritten. With a large history this can be a substantial
amount of memory. To reduce this, compact each extended cell list to
only cells in use as it is scrolled off the visible screen into the
history. From Dan Aloni in GitHub issue 1062.
2017-09-10 14:36:12 +00:00
Thomas Adam
7f83b53027 Merge branch 'obsd-master'
Conflicts:
	server-client.c
2017-09-10 11:39:45 +01:00
nicm
8405fcdd9b Apply timeout to CAN and RS which also wait for ST. 2017-09-10 08:01:23 +00:00
nicm
f56f09ea38 Fix a few errors in how the selected line is chosen after resize,
reported by Felix Rosencrantz in GitHub issue 1059.
2017-09-08 16:28:41 +00:00
Nicholas Marriott
c62cfe64c8 Add to CHANGES. 2017-09-08 14:22:34 +01:00
nicm
78cf3c14ca When removing a key table clear it out of clients, fixes issue with
unbind -a reported by Thomas Sattler.
2017-09-08 08:45:27 +00:00
nicm
89e057dc4a Do not fail if unset an option that is already unset, reported by Thomas
Sattler.
2017-09-07 13:18:44 +00:00
nicm
466066c3a1 Do not attempt to use TIOCSWINSZ on a -1 file descriptor (possible if
the pane has already died).
2017-09-06 07:12:41 +00:00
Thomas Adam
ff3d05d92f Merge branch 'obsd-master' 2017-09-04 12:01:11 +01:00
nicm
eadd79acec Move to current mouse position not last when clcking in copy mode; fixes
GitHub issue 1055. Also a man page fix from jmc.
2017-09-04 09:18:51 +00:00
Thomas Adam
d019821281 Merge branch 'obsd-master' 2017-09-02 20:01:18 +01:00
nicm
f4848b437f Add selectp -T to set pane title. 2017-09-02 17:51:54 +00:00
Nicholas Marriott
e941e532fa Mention GitHub for code. 2017-08-30 21:49:31 +01:00
Nicholas Marriott
a1986c5973 Add to CHANGES. 2017-08-30 21:24:16 +01:00
Nicholas Marriott
6e2b3f435a Add to CHANGES. 2017-08-30 21:23:26 +01:00
Nicholas Marriott
07d3c4d882 Merge branch 'master' into 2.6-rc 2017-08-30 20:04:37 +01:00
Thomas Adam
f81e87f1e2 Merge branch 'obsd-master' 2017-08-30 20:01:11 +01:00
nicm
6abfd9b8ff Instead of overloading the line clear function to mean free if
background is default (8), introduce an explicit free function and use
it where a free alone is needed. Likewise, use memmove directly rather
than grid_move_lines where it makes sense. Based on a memory leak fix by
Dan Aloni in GitHub issue 1051.
2017-08-30 18:13:47 +00:00
Nicholas Marriott
07c679b52d Merge branch 'master' into 2.6-rc 2017-08-30 12:04:09 +01:00
Nicholas Marriott
b4c633cc40 Merge branch 'master' of github.com:tmux/tmux 2017-08-30 12:03:59 +01:00
Thomas Adam
54c5070767 Merge branch 'obsd-master' 2017-08-30 12:01:10 +01:00
nicm
17cf1b21c6 Pass flags into cmd_find_from_* to fix prefer-unattached, reported by
Thomas Sattler.
2017-08-30 10:33:57 +00:00
Nicholas Marriott
8f364053ca Add to TODO. 2017-08-30 11:21:20 +01:00
Nicholas Marriott
2e4e521629 2.6-rc version. 2017-08-30 09:34:27 +01:00
Nicholas Marriott
fa20f19494 Fix position of -v, pointed out by Thomas Sattler. 2017-08-30 09:33:53 +01:00
Nicholas Marriott
c1d8b0f74e Back to master. 2017-08-29 22:19:46 +01:00
Nicholas Marriott
3815e4f05e This is not true now... 2017-08-29 22:19:27 +01:00
Nicholas Marriott
72488b526b Merge branch 'master' into 2.6-rc 2017-08-29 22:06:22 +01:00
Nicholas Marriott
5fec6c598e Merge branch 'master' of github.com:tmux/tmux 2017-08-29 22:06:06 +01:00
Thomas Adam
dee6bb5a31 Merge branch 'obsd-master' 2017-08-29 22:01:11 +01:00
Nicholas Marriott
566b9623b3 Merge branch 'master' into 2.6-rc 2017-08-29 21:42:15 +01:00
Nicholas Marriott
3f3fb43850 More style. 2017-08-29 21:42:05 +01:00
Nicholas Marriott
2248b886fe 2.6-rc version. 2017-08-29 21:37:51 +01:00
Nicholas Marriott
82b30f2322 Style of headings. 2017-08-29 21:34:56 +01:00
Nicholas Marriott
6b841a036a Fix example from Adam Spiers. 2017-08-29 21:32:09 +01:00
nicm
a7d1ee5433 Redraw rectangle selections properly when cursor at end, GitHub issue 992. 2017-08-29 20:26:25 +00:00
Thomas Adam
0f7160eb2f Merge branch 'obsd-master' 2017-08-29 12:01:25 +01:00
Nicholas Marriott
91d6bff8b8 Merge branch 'master' of github.com:tmux/tmux 2017-08-29 11:13:54 +01:00
Nicholas Marriott
5cdccf78a1 Update CHANGES. 2017-08-29 11:13:35 +01:00
nicm
5fc0be5045 Support REP escape sequence (\033[b). 2017-08-29 09:28:45 +00:00
nicm
9852bd743c Check for complete keys before escape prefix, allows keys to be defined
with a leading escape. GitHub issue 1048.
2017-08-29 09:18:48 +00:00
Thomas Adam
7d3bf6453e Merge branch 'obsd-master' 2017-08-28 14:01:17 +01:00
nicm
fe4467ad2b Do not forbid targets to specify non-visible panes - the checks for
visibility are better where the target is used. GitHub issue 1049.
2017-08-28 12:36:38 +00:00
Thomas Adam
b2322b3893 Merge branch 'obsd-master' 2017-08-27 11:48:44 +01:00
nicm
fccfc4e4be Do not allow the current line of screen when the preview is toggled,
from Thomas Adam.
2017-08-27 09:08:36 +00:00
Thomas Adam
e65cc09276 Merge branch 'obsd-master' 2017-08-27 10:01:15 +01:00
nicm
25cf126de8 Use kind and kri for S-Up/Down as well as kUP and kDN. 2017-08-27 08:33:55 +00:00
Thomas Adam
1492c9d7d9 Merge branch 'obsd-master' 2017-08-24 12:01:10 +01:00
nicm
3c63ad4a9c When tty is error or closed, remove client. Reported by Thomas Sattler. 2017-08-24 08:48:37 +00:00
Thomas Adam
3b40f8e42c Merge branch 'obsd-master' 2017-08-23 12:01:13 +01:00
nicm
08b125194e Key (v) and flag (-N) to toggle preview in choose modes. 2017-08-23 09:39:11 +00:00
nicm
1d60dd5872 Fix searching when match is at end of line, from Brad Town. 2017-08-23 09:18:22 +00:00
nicm
f0ce29c341 Allow multiple bells even if there is an existing bell (but not activity
or silence), from Brad Town.
2017-08-23 09:16:39 +00:00
nicm
e1b3dc89d2 Run alert hooks based on the options rather than unconditionally, from
Brad Town.
2017-08-23 09:14:21 +00:00
Nicholas Marriott
0f708dd6e2 Add to TODO. 2017-08-22 13:02:20 +01:00
Thomas Adam
730312e60f Merge branch 'obsd-master' 2017-08-22 00:01:10 +01:00
nicm
bbe9da063e Same as previous for \r alone. 2017-08-21 21:02:58 +00:00
nicm
7ec2a2b9ce Do not emit \r\n to move to column 0 if there are margins, because it
will instead move to the margin left.
2017-08-21 21:01:21 +00:00
Thomas Adam
ccdc369025 Merge branch 'obsd-master' 2017-08-20 00:01:22 +01:00
nicm
768740ae98 Fix example for user-keys. 2017-08-19 20:40:16 +00:00
Thomas Adam
07a13697e1 Merge branch 'obsd-master' 2017-08-17 12:01:17 +01:00
nicm
8daa1d5f54 Add monitor-bell window option to match the activity and silence
options, from Brad Town.
2017-08-17 08:37:38 +00:00
Nicholas Marriott
de86bf1856 Add to CHANGES. 2017-08-16 16:23:58 +01:00
Thomas Adam
2103a09430 Merge branch 'obsd-master' 2017-08-16 14:01:15 +01:00
nicm
c6a8ad23a1 Add -d flag to display-panes to specify timeout, and make 0 mean no
timeout. From Laurens Post.
2017-08-16 12:12:54 +00:00
nicm
c1ec28a34b Rename BELL_* values to ALERT_* now they are used by more than bells,
based on a diff from Brad Town.
2017-08-16 11:46:08 +00:00
Thomas Adam
0824850bbc Merge branch 'obsd-master' 2017-08-09 16:01:10 +01:00
Thomas Adam
27c3852103 Merge branch 'obsd-master'
Conflicts:
	tmux.1
2017-08-09 15:07:18 +01:00
nicm
ac2ba0961b Fix filtering so it works after the change to only show windows if they
have multiple panes.
2017-08-09 13:44:36 +00:00
Nicholas Marriott
237b7a50f4 Update CHANGES and TODO. 2017-08-09 12:48:54 +01:00
nicm
5dd5543fe4 Add -F to choose-tree, choose-client, choose-buffer to specify the
format of each line, as well as adding a couple of formats needed for
the default display.
2017-08-09 11:43:45 +00:00
Thomas Adam
4bb5bb9450 Merge branch 'obsd-master' 2017-08-08 12:01:15 +01:00
nicm
31b06571aa Hooks for after-select-pane and after-select-window. 2017-08-08 09:21:20 +00:00
Thomas Adam
e7b1e05bbd Merge branch 'obsd-master' 2017-08-02 14:01:10 +01:00
nicm
6f9b9655d7 Add selection_present format so commands in copy mode can use it, GitHub
issue 1028.
2017-08-02 11:10:48 +00:00
Nicholas Marriott
45ee118b26 Merge branch 'master' of github.com:tmux/tmux 2017-07-28 15:14:35 +01:00
Nicholas Marriott
0d6fc7eb1e I already mentioned these... revert previous. 2017-07-28 15:14:01 +01:00
Thomas Adam
ed8ddf2449 Merge branch 'obsd-master' 2017-07-28 14:01:13 +01:00
nicm
b4c9f6edba Show pane title in window list for windows with only one pane. 2017-07-28 10:59:58 +00:00
Nicholas Marriott
a704f57971 This is a big meaningless. 2017-07-27 23:25:39 +01:00
Nicholas Marriott
6b60a5c6d6 Update CHANGES. 2017-07-27 23:22:54 +01:00
Thomas Adam
147740ed40 Merge branch 'obsd-master' 2017-07-27 14:01:13 +01:00
nicm
3df7c91f1a Add pane_at_left/right/top/bottom formats, from Amos Bird. 2017-07-27 10:42:05 +00:00
Thomas Adam
58744de3eb Merge branch 'obsd-master' 2017-07-26 18:01:16 +01:00
nicm
b1bd0c7fc1 Always reset the alerts timer so it works even if activity and silence
are enabled on the same window.
2017-07-26 16:16:25 +00:00
nicm
76887b1d27 Make bell, activity and silence alerting more consistent:
- remove the bell-on-alert option;

- add activity-action and silence-action options with the same possible
  values as the existing bell-action;

- add "both" value for the visual-bell, visual-activity and
  visual-silence options to trigger both a bell and a message.

This means all three work the same way. Based on changes from Yvain Thonnart.
2017-07-26 16:14:08 +00:00
Nicholas Marriott
06a2644ab2 Update CHANGES. 2017-07-26 11:25:33 +01:00
Nicholas Marriott
ef9afddd1a Merge branch 'master' of github.com:tmux/tmux 2017-07-26 08:41:45 +01:00
Nicholas Marriott
3065b21375 Mention autoconf and automake. 2017-07-26 08:38:37 +01:00
Thomas Adam
358df10191 Merge branch 'obsd-master' 2017-07-22 02:01:13 +01:00
nicm
3bb426d92c Use the actual width written rather than the possible width to clear. 2017-07-21 22:55:45 +00:00
Thomas Adam
26db50d6df Merge branch 'obsd-master' 2017-07-21 16:01:13 +01:00
nicm
8c6ad55320 Trim trailing spaces from full line when it is clearly OK to do so. 2017-07-21 14:25:29 +00:00
nicm
e0d49ad758 Allow ispunct() as well as isalnum() when parsing initial window names. 2017-07-21 12:58:02 +00:00
Thomas Adam
e725b96a59 Merge branch 'obsd-master' 2017-07-21 12:01:16 +01:00
nicm
11e2af6df7 Add -c for respawn-pane and respawn-window, from J Raynor. 2017-07-21 09:17:19 +00:00
Thomas Adam
acbbc93501 Merge branch 'obsd-master' 2017-07-14 22:01:10 +01:00
nicm
932f6cfbfc Because ignore SIGCHLD early, letting signal_del restore it doesn't work
correctly, so set it explicitly back to default (and the others for good
measure).
2017-07-14 18:49:07 +00:00
Thomas Adam
1265e212e4 Merge branch 'obsd-master' 2017-07-14 10:01:11 +01:00
Nicholas Marriott
e4cd8751a2 Update CHANGES. 2017-07-14 09:14:23 +01:00
nicm
2678fe53f5 Fix redraw defer code in the presence of multiple clients - the timer
may be needed for all of them, so don't delete it on the first; and
don't skip setting the redraw flag if the timer is already running.

Reported by Pol Van Aubel in GitHub issue 1003.
2017-07-14 08:04:23 +00:00
Thomas Adam
e3698e6e1f Merge branch 'obsd-master' 2017-07-12 16:01:11 +01:00
nicm
8b84fc177c Line up keys in tree mode, and don't expand windows with one pane. From
Thomas Adam.
2017-07-12 14:31:06 +00:00
Thomas Adam
5122f3477f Merge branch 'obsd-master' 2017-07-12 14:01:13 +01:00
Thomas Adam
1076a2e26c Merge branch 'obsd-master'
Conflicts:
	cmd-pipe-pane.c
	proc.c
	tmux.c
	window.c
2017-07-12 13:43:08 +01:00
nicm
fba6140a4a Do not need to set up USR2 twice. 2017-07-12 12:35:31 +00:00
nicm
51112221ee Block signals between forking and clearing signal handlers (or calling
event_reinit) - if the child gets a signal and fires the libevent signal
handler during this period it could write a signal into the parent's
signal pipe. GitHub issue 1001 from Aaron van Geffen.
2017-07-12 10:04:51 +00:00
nicm
0453ad0146 Move signal code into proc.c. 2017-07-12 09:24:17 +00:00
nicm
ed3cfaafb2 Make shell_command a global like other stuff rather than making it an
exception and using callback argument.
2017-07-12 09:21:25 +00:00
nicm
d0d42dc4cb proc_send_s now seems unnecessary. 2017-07-12 09:07:52 +00:00
Thomas Adam
fbbf5a108b Merge branch 'obsd-master' 2017-07-10 00:01:15 +01:00
nicm
58b796608f Some extra logging to show why tmux might exit. 2017-07-09 22:33:09 +00:00
Thomas Adam
05062e7d2d Merge branch 'obsd-master' 2017-07-07 18:01:15 +01:00
nicm
bfaa885f10 Fix size of rightmost preview section. 2017-07-07 16:27:26 +00:00
nicm
9913cce3ba Add a pane_pipe format to show if pipe-pane is active, GitHub issue 990. 2017-07-07 14:39:45 +00:00
Thomas Adam
1029f2b277 Merge branch 'obsd-master' 2017-07-07 10:01:09 +01:00
nicm
1f7ca973c5 When working out the current client (for example for switch-client with
no target), prefer clients attached to the current session if there is
one. GitHub issue 995 from Jan Larres.
2017-07-07 07:13:14 +00:00
Thomas Adam
6b1ceca86a Merge branch 'obsd-master' 2017-07-05 00:01:10 +01:00
nicm
53d4ed22e8 < and > keys to scroll preview list left and right in tree mode. 2017-07-04 22:21:31 +00:00
Thomas Adam
feb044bd2d Merge branch 'obsd-master' 2017-07-04 14:01:15 +01:00
nicm
bedf8bd437 Handle 0 size of preview box in caller. 2017-07-04 12:26:14 +00:00
Thomas Adam
6cb4a3bb19 Merge branch 'obsd-master' 2017-07-04 02:01:13 +01:00
nicm
4039802fce Change session and window preview so that the current window or pane is
always shown.
2017-07-03 22:48:02 +00:00
Thomas Adam
5e98770936 Merge branch 'obsd-master' 2017-07-03 16:01:14 +01:00
nicm
6ee0afb579 Change previous to not wait for both process exit and pty close -
instead if there is a pipe-pane active, do not exit until all data is
read (including any libevent hasn't seen yet). Fixes problem reported by
Theo Buehler and still seems to solve the original issue.
2017-07-03 12:38:50 +00:00
Thomas Adam
4e01036cb6 Merge branch 'obsd-master' 2017-07-03 10:01:14 +01:00
nicm
28687f2d55 Do not close panes until process has exited and any outstanding data
has been written to the pipe-pane event if there is one. GitHub issue 991.
2017-07-03 08:16:03 +00:00
nicm
42285ac989 Try C.UTF-8 which is also a commonly useful locale on some platforms,
from Romain Francoise.
2017-07-03 08:08:30 +00:00
Thomas Adam
6fba9a39b7 Merge branch 'obsd-master' 2017-07-01 00:01:21 +01:00
nicm
fa677fc0e1 Don't write over right border. 2017-06-30 22:37:35 +00:00
nicm
b565644c81 Fix previous when we end up able to show no panes. 2017-06-30 22:36:11 +00:00
nicm
7247553c77 Try to show a better preview of sessions and windows in tree mode. 2017-06-30 22:24:08 +00:00
Thomas Adam
f059fe3ef2 Merge branch 'obsd-master' 2017-06-30 00:01:14 +01:00
nicm
8b0fd63ddb Use 100 as the example for command-alias because the defaults are from 0
to (currently) 5.
2017-06-29 22:02:19 +00:00
Thomas Adam
336beeb09a Merge branch 'obsd-master' 2017-06-28 14:01:13 +01:00
nicm
a00b0d13ed Apply the xterm key flag when needed for send-keys, fixes problem
reported by Franky Spamschleuder.
2017-06-28 11:36:39 +00:00
Thomas Adam
1ca920bbeb Merge branch 'obsd-master' 2017-06-28 10:01:16 +01:00
nicm
1e376be13d Fix visual-silence (check accidentally the wrong way round), from Brad
Town. Plus some tmux.1 fixes from jmc@.
2017-06-28 06:45:31 +00:00
Thomas Adam
6995497e5b Merge branch 'obsd-master' 2017-06-23 18:01:11 +01:00
nicm
95ed7d48c8 Add user-keys option to allow user-defined keys to be set, from Dan
Aloni.
2017-06-23 15:36:52 +00:00
Thomas Adam
a61200776d Merge branch 'obsd-master' 2017-06-16 18:01:13 +01:00
nicm
a67df17763 Tweak some logging. 2017-06-16 15:12:38 +00:00
Thomas Adam
233bae6992 Merge branch 'obsd-master' 2017-06-16 14:01:14 +01:00
nicm
d685604d04 Log terminal capabilities for each new terminal. 2017-06-16 11:50:06 +00:00
Thomas Adam
91dec25fc9 Merge branch 'obsd-master' 2017-06-14 10:01:10 +01:00
nicm
af93453190 Don't overwrite error message when it is available in
cmd_string_parse. Reported by Jimi Damon in GitHub issue 975.
2017-06-14 07:42:41 +00:00
Nicholas Marriott
6e57401610 New test. 2017-06-14 08:37:58 +01:00
nicm
dec00d3579 Add missing error message when no target, GitHub issue 971. 2017-06-14 07:37:17 +00:00
Thomas Adam
154c95d0c9 Merge branch 'obsd-master' 2017-06-13 13:48:37 +01:00
nicm
ac7080b31b Remove xterm flag from key before checking prefix, reported by Peter
Fern in GitHub issue 974.
2017-06-13 07:12:33 +00:00
Thomas Adam
a073d11c3e Merge branch 'obsd-master' 2017-06-12 14:01:14 +01:00
nicm
e028ab3476 Need to flush out the linefeed after wrapper. GitHub issue 970. 2017-06-12 10:57:35 +00:00
Thomas Adam
5362f956f0 Merge branch 'obsd-master' 2017-06-12 10:01:15 +01:00
nicm
8037159f93 Add explicit keys for the bracketed paste sequences, both to avoid mix
ups with other keys and to make logs clearer.
2017-06-12 07:04:24 +00:00
Thomas Adam
4dbab75855 Merge branch 'obsd-master' 2017-06-09 18:01:14 +01:00
nicm
adcd5aff6f Extend filters (f key) to buffer and client mode and add -f flag to
specify to command.
2017-06-09 16:01:39 +00:00
nicm
bab4da5133 Add -O option to choose-* to set initial sort order. 2017-06-09 15:29:15 +00:00
nicm
3ec28ceb9b Default sort for buffer mode should be time not name. 2017-06-09 15:17:20 +00:00
Thomas Adam
ed45052d6d Merge branch 'obsd-master' 2017-06-09 16:01:13 +01:00
Nicholas Marriott
411640c032 Merge branch 'master' of github.com:tmux/tmux 2017-06-09 15:57:13 +01:00
Nicholas Marriott
eea93638c6 Set AM_CFLAGS for ncurses libraries, reported by Peter Schow. 2017-06-09 15:56:50 +01:00
nicm
a2ca51c27a Use brackets around prompts which looks better and matches the other modes. 2017-06-09 14:00:46 +00:00
Thomas Adam
e640907d24 Merge branch 'obsd-master' 2017-06-09 12:01:17 +01:00
nicm
74b2deae1c Add a hook when the clipboard is set. 2017-06-09 09:21:24 +00:00
Nicholas Marriott
143ccd27b4 Add memmem to compat. 2017-06-09 08:53:58 +01:00
Nicholas Marriott
a4d2fa1b6d Update TODO. 2017-06-08 17:21:30 +01:00
Nicholas Marriott
065c360730 Typo. 2017-06-08 14:08:04 +01:00
Nicholas Marriott
738d9aece7 Note what to have for building Git. 2017-06-08 13:40:24 +01:00
Nicholas Marriott
8c38409aef Merge branch 'master' of github.com:tmux/tmux 2017-06-08 13:29:59 +01:00
Nicholas Marriott
61ed6425bd Move FAQ online and do not ship TODO. 2017-06-08 13:29:36 +01:00
Thomas Adam
6e8c93afdd Merge branch 'obsd-master' 2017-06-08 10:01:10 +01:00
nicm
8c4ae1c938 Add size to client descriptions in list, suggested by Greg Hurrell. 2017-06-08 07:48:04 +00:00
Thomas Adam
4aa02c3743 Merge branch 'obsd-master' 2017-06-07 18:01:13 +01:00
nicm
356fab7bcb Return 1 if name matches not 0, also fix some spaces. 2017-06-07 15:27:46 +00:00
Nicholas Marriott
9543f076fd Use osdep_get_name. 2017-06-07 16:21:01 +01:00
Thomas Adam
86d6666fe7 Merge branch 'obsd-master' 2017-06-07 16:01:10 +01:00
nicm
405cc337f3 Add simple searching (C-s and n) to the various choose modes: by name
for client and tree, and by name and content for buffer.
2017-06-07 14:37:30 +00:00
Nicholas Marriott
772dacc89b Tweak title. 2017-06-07 11:27:04 +01:00
Nicholas Marriott
696d2889f4 Mention U8, from Carles Cufi. 2017-06-07 11:19:04 +01:00
Nicholas Marriott
9316b9b57a Typo. 2017-06-07 11:15:36 +01:00
Nicholas Marriott
fb288ef9a7 Remove a bunch of out-of-date stuff from the FAQ or stuff that is documentation
for other programs.
2017-06-07 11:13:05 +01:00
Thomas Adam
7077980055 Merge branch 'obsd-master' 2017-06-06 18:01:13 +01:00
nicm
50b27c8c0d Continue and pass keys through if they are repeated keys, so that the
first key after a repeated key doesn't get lost.
2017-06-06 15:49:35 +00:00
nicm
bbc35b0b19 Do not pass a state into commands when fired on individual items in tree
mode, rely on the %% target substitution in the command for the chosen
pane and leave the default target as the current pane (where the mode
is). Otherwise, joinp and similar end up with -t and -s the
same. Reported by Jacob Niehus in GitHub issue 960.
2017-06-06 15:07:35 +00:00
nicm
d7280917da Delete input event when evbuffer_read() fails to avoid just spinning
around a dead file descriptor. Seems to fix a problem reported by Greg
Hurrell in GitHub issue 941.
2017-06-06 14:53:28 +00:00
Nicholas Marriott
78352fdd32 Add a small dance to daemon() to reattach tmux to the user's namespace (which
allows access to the clipboard) on OS X 10.10 and above.

Chis Johnsen has done much work on and documentation of this issue, the code is
copied (with some tweaks) from his reattach-to-user-namespace at:

    https://github.com/ChrisJohnsen/tmux-MacOSX-pasteboard

Tested by Enrico Ghirardi.

Will see how this goes, if it breaks stuff it might go away again.
2017-06-06 07:59:53 +01:00
Nicholas Marriott
63f8a2cb89 Merge branch 'master' of github.com:tmux/tmux 2017-06-05 12:02:10 +01:00
Nicholas Marriott
e1686c26dd Update CHANGES. 2017-06-05 12:01:58 +01:00
Thomas Adam
a999f6f876 Linux build fixes
Linux doesn't have vis.h
2017-06-05 12:00:52 +01:00
Thomas Adam
e62e17d046 Merge branch 'obsd-master'
Conflicts:
	tmux.1
	window.c
2017-06-05 11:59:38 +01:00
nicm
2f04108f3a Do not leak command, from David CARLIER. 2017-06-04 15:36:33 +00:00
Nicholas Marriott
1c83c0ebcd tparm() fix for Solaris. 2017-06-04 11:27:35 +01:00
Nicholas Marriott
8ec6c323b6 signal.h for utempter, from David CARLIER. 2017-06-04 11:23:48 +01:00
nicm
c5b7faaefc Add a timeout to prevent the sequences which wait for a specific
terminator (OSC, APC and DCS) waiting forever, which helps to avoid
garbage (cat /dev/random) locking up panes completely. This (and the
last commit) prompted by a discussion with theo.
2017-06-04 09:22:34 +00:00
nicm
467ece53e6 Remove unused variable. 2017-06-04 09:02:57 +00:00
nicm
8149bc3fa6 Be more strict about escape sequences that rename windows or set titles:
ignore any that not valid UTF-8 outright, and for good measure pass the
result through our UTF-8-aware vis(3).
2017-06-04 09:02:36 +00:00
nicm
adf5628087 Support SIGUSR2 to stop and start logging for an existing server. Also
we currently only have two log levels so just use -v and -vv rather than
-v and -vvvv, and clarify the man page entry for -v.
2017-06-04 08:25:57 +00:00
Nicholas Marriott
67cd496b39 Update CHANGES. 2017-06-04 09:09:31 +01:00
nicm
184039044a Typo/style; plus man page escaping from jmc. 2017-06-04 08:02:20 +00:00
Thomas Adam
757eb060cd Merge branch 'obsd-master' 2017-06-03 20:01:10 +01:00
nicm
3442066054 Make set-clipboard a three-state option so tmux itself can ignore the
sequencess.
2017-06-03 17:43:01 +00:00
Thomas Adam
80235d6fdd Merge branch 'obsd-master' 2017-06-03 10:01:10 +01:00
nicm
493a1846d0 Foreground colours with the bright attribute set need to use the bright
entries in the palette. GitHub issue 954.
2017-06-03 07:15:23 +00:00
Thomas Adam
73b9328c1f Merge branch 'obsd-master'
Conflicts:
	window-buffer.c
2017-06-01 18:29:36 +01:00
nicm
248aa54bfd Style and spacing nits. 2017-05-31 17:56:48 +00:00
nicm
70cc8f2c7e Shut up a warning. 2017-05-31 16:44:33 +00:00
Nicholas Marriott
92d86586b7 Update TODO. 2017-05-31 17:38:34 +01:00
Nicholas Marriott
a8e0363914 Add setrgbf setrgbb. 2017-05-31 17:22:43 +01:00
Nicholas Marriott
35008200bd Differences to OpenBSD. 2017-05-31 16:34:39 +01:00
Nicholas Marriott
113356c848 Build fixes. 2017-05-31 16:29:07 +01:00
nicm
b3d0ed4057 time.h here too. 2017-05-31 15:27:57 +00:00
nicm
61c0189bb1 Need time.h. 2017-05-31 15:26:41 +00:00
Thomas Adam
f17ecaa495 Merge branch 'obsd-master'
Conflicts:
	Makefile.am
	cfg.c
	server-client.c
2017-05-31 15:56:13 +01:00
Nicholas Marriott
9c4d0d454a Some changes that will appear when we sync up. 2017-05-31 13:56:07 +01:00
nicm
d60663ea86 Some applications like vi(1) and tmux until 10 minutes or so ago, do not
redraw on SIGWINCH if the size returns to the original size between the
original SIGWINCH and when they get around to calling TIOCGWINSZ. So use
the existing resize timer to introduce a small delay between the two
resizes.
2017-05-31 11:00:00 +00:00
nicm
ea6428a5d2 It is not OK to ignore SIGWINCH if SIOCGWINSZ reports the size has
unchanged, because it may have changed and changed back in the time
between us getting the signal and calling ioctl(). Always redraw when we
see SIGWINCH.
2017-05-31 10:29:15 +00:00
nicm
80c6b487dc Because we defer actually resizing applications (calling TIOCSWINSZ)
until the end of the server loop, tmux may have gone through several
internal resizes in between. This can be a problem if the final size is
the same as the initial size (what the application things it currently
is), because the application may choose not to redraw, assuming the
screen state is unchanged, when in fact tmux has thrown away parts of
the screen, assuming the application will redraw them.

To avoid this, do an extra resize if the new size is the same size as
the initial size. This should force the application to redraw when tmux
needs it to, while retaining the benefits of deferring (so we now resize
at most two times instead of at most one - and only two very rarely).

Fixes a problem with break-pane and zoomed panes reported by Michal
Mazurek.
2017-05-31 10:15:51 +00:00
nicm
7eb496c00c Look for setrgbf and setrgbb terminfo extensions for RGB colour. This is
the most reasonable of the various (some bizarre) suggestions for
capabilities.
2017-05-31 08:43:44 +00:00
nicm
aad4e4ddb1 Rewrite of choose mode, both to simplify and tidy the code and to add
some modern features.

Now the common code is in mode-tree.c, which provides an API used by the
three modes now separated into window-{buffer,client,tree}.c. Buffer
mode shows buffers, client mode clients and tree mode a tree of
sessions, windows and panes.

Each mode has a common set of key bindings plus a few that are specific
to the mode. Other changes are:

- each mode has a preview pane: for buffers this is the buffer content
  (very useful), for others it is a preview of the pane;

- items may be sorted in different ways ('O' key);

- multiple items may be tagged and an operation applied to all of them
  (for example, to delete multiple buffers at once);

- in tree mode a command may be run on the selected item (session,
  window, pane) or on tagged items (key ':');

- displayed items may be filtered in tree mode by using a format (this
  is used to implement find-window) (key 'f');

- the custom format (-F) for the display is no longer available;

- shortcut keys change from 0-9, a-z, A-Z which was always a bit weird
  with keys used for other uses to 0-9, M-a to M-z.

Now that the code is simpler, other improvements will come later.

Primary key bindings for each mode are documented under the commands in
the man page (choose-buffer, choose-client, choose-tree).

Parts written by Thomas Adam.
2017-05-30 21:44:59 +00:00
Thomas Adam
cea83c0e1f Merge branch 'obsd-master' 2017-05-30 10:01:12 +01:00
nicm
bd39fcbeea Preserve search string when entering prompt again. 2017-05-30 08:13:48 +00:00
Thomas Adam
0d073907b5 Merge branch 'obsd-master' 2017-05-30 00:01:14 +01:00
Thomas Adam
5ee6dc2120 Merge branch 'obsd-master' 2017-05-29 22:01:15 +01:00
nicm
64552ae304 Add a flag to stop the prompt input being expanded. 2017-05-29 20:42:53 +00:00
nicm
b95e5827c1 Store a copy of the old status line, will be needed soon for new choose mode. 2017-05-29 20:41:29 +00:00
nicm
8a214b2f8e Function to count clients. 2017-05-29 20:37:30 +00:00
Thomas Adam
5bc5fe5e7e Merge branch 'obsd-master' 2017-05-29 20:01:12 +01:00
nicm
a2ace9da24 Add ||, && format operators and C: to search pane content. 2017-05-29 18:06:34 +00:00
Thomas Adam
d3959a2118 Merge branch 'obsd-master' 2017-05-29 18:01:14 +01:00
nicm
1257501499 Add m: for fnmatch(3) format matching. 2017-05-29 15:43:48 +00:00
Thomas Adam
bfd7209053 Merge branch 'obsd-master' 2017-05-29 10:01:15 +01:00
nicm
1883d299bf Do not factor in screen_hsize() for the visible copy mode screen when
adjusting the selection, it should never have any useful history (and
when it does, after resize, we shouldn't use it). From Michal Mazurek.
2017-05-29 07:58:33 +00:00
nicm
15253448af Tweak text to mention initial size, from John Hood. 2017-05-29 07:46:32 +00:00
Nicholas Marriott
b017dc7e32 Update release text. 2017-05-29 08:40:33 +01:00
Nicholas Marriott
b5a6458cde Merge branch '2.5-rc' 2017-05-29 08:23:03 +01:00
Nicholas Marriott
caa90735cf 2.5. 2017-05-29 08:12:25 +01:00
Nicholas Marriott
de45957c42 Add to CHANGES. 2017-05-29 08:11:47 +01:00
Thomas Adam
f4a42738af Merge branch 'obsd-master' 2017-05-29 02:01:15 +01:00
nicm
d5158620bb Support OSC 10 and 11 to set foreground and background colours, from
"bertnp" in GitHub issue 942.
2017-05-28 23:23:40 +00:00
Nicholas Marriott
bf5a196c78 Changes in master. 2017-05-28 22:10:17 +01:00
Thomas Adam
5d7dfefa36 Merge branch 'obsd-master' 2017-05-28 22:01:11 +01:00
nicm
dbc8cae18c Change so that sessions created detached (-d or no client) are always
80x24 and the status line is not applied until they attach. Also make -x
and -y work for control clients whether the session is detached or not.
2017-05-28 19:46:55 +00:00
Nicholas Marriott
1e1e0f1fbb Add test for -x and -y too. 2017-05-28 20:15:45 +01:00
nicm
385bf084a5 Also recalculate session sizes when refreh-client -C is used. GitHub
issue 947.
2017-05-28 19:00:52 +00:00
Nicholas Marriott
eb1f362687 Do not need /dev/null. 2017-05-28 19:53:08 +01:00
Nicholas Marriott
5386e6583d Add some tests. 2017-05-28 19:52:51 +01:00
Thomas Adam
d1497527c6 Merge branch 'obsd-master' 2017-05-17 18:01:14 +01:00
nicm
91d202da7e Tidy command prompt callbacks and pass in the client. 2017-05-17 15:20:23 +00:00
Nicholas Marriott
3888bf9d12 Need to check libutil for fparseln. 2017-05-17 12:48:42 +01:00
Thomas Adam
3df4e78492 Merge branch 'obsd-master' 2017-05-16 16:01:28 +01:00
Nicholas Marriott
b74b6dc77f Missed during merge. 2017-05-16 14:15:35 +01:00
nicm
31625c2d17 Line length and spaces to tabs. 2017-05-16 12:57:26 +00:00
Thomas Adam
dcdaf5c8b9 Merge branch 'obsd-master' 2017-05-15 20:01:14 +01:00
Thomas Adam
36181775cd Merge branch 'obsd-master' 2017-05-15 18:01:14 +01:00
nicm
1ba7f1d03f Check the terminfo(5) U8 capability and disable using UTF-8 for ACS if
it is present and zero. This is useful for users with terminals or fonts
that do not correctly support UTF-8 line drawing characters. GitHub
issue 927, reported by Hiroaki Yamazoe and Akinori Hattori.
2017-05-15 16:44:04 +00:00
nicm
b160de5cb4 Notify layout changed when choosing predefined layouts, from Joshua Brot. 2017-05-15 14:57:29 +00:00
Thomas Adam
7edaedf3a1 Merge branch 'obsd-master' 2017-05-15 10:01:16 +01:00
nicm
cb5fcb3d22 The Konsole SU bug means it can't clear the entire scroll region (it
ignores if >= size, not if > as I first thought). So we can't
effectively fix it in code - remove the workarounds which just cause
bugs on other terminals.
2017-05-15 07:54:44 +00:00
Thomas Adam
58f8421eac Merge branch 'obsd-master' 2017-05-13 10:01:16 +01:00
nicm
7a4c66b7f5 Scroll the right number of lines off the region when clearing. 2017-05-13 07:41:59 +00:00
nicm
d58c3793d6 Some other unused variables. 2017-05-13 07:30:50 +00:00
Nicholas Marriott
ea190d862a Merge branch '2.5-rc' 2017-05-13 08:20:01 +01:00
Nicholas Marriott
0f26739c9f 2.5-rc2. 2017-05-13 08:17:01 +01:00
Nicholas Marriott
ae2c5ad768 Reset updated flag when restarting job so new output is detected, reported by
Gregory Pakosz in GitHub issue 922.
2017-05-13 08:16:11 +01:00
Thomas Adam
9f9f8c8e76 Merge branch 'obsd-master' 2017-05-13 02:01:13 +01:00
nicm
50f1f1dce9 Compare >= for columns not >. 2017-05-12 23:10:19 +00:00
nicm
0264ef094a Can scroll away full lines to clear them too. 2017-05-12 23:06:43 +00:00
nicm
f688653710 Remove an unused variable. 2017-05-12 22:43:15 +00:00
Thomas Adam
886d896098 Merge branch 'obsd-master' 2017-05-12 18:01:14 +01:00
Nicholas Marriott
8331000764 Merge branch '2.5-rc' 2017-05-12 16:18:31 +01:00
nicm
0cd74723e1 When expanding a line in order to clear it, we need to use the default
background colour - there may be portions that we do not want to clear
with the new background colour.
2017-05-12 15:18:13 +00:00
Nicholas Marriott
2bff5e7867 ECH needs to use background colour. 2017-05-12 16:16:16 +01:00
nicm
90f2a417af Need to clear tty context before using it. 2017-05-12 16:04:13 +01:00
nicm
7c07f5f640 Cannot rely on cursor position after DL and IL (some terminals move to
column 0, some do not).
2017-05-12 16:03:49 +01:00
Thomas Adam
20e30593a5 Merge branch 'obsd-master' 2017-05-12 16:01:14 +01:00
nicm
e2a18e2b37 Need to store bg for ECH. 2017-05-12 14:56:56 +00:00
nicm
da724fe1c0 Cannot rely on cursor position after DL and IL (some terminals move to
column 0, some do not).
2017-05-12 14:13:54 +00:00
nicm
ffd8beb6f6 Need to clear tty context before using it. 2017-05-12 13:29:05 +00:00
nicm
5d3cf2ff15 Only redraw single client, and tweak some logging. 2017-05-12 13:27:57 +00:00
Thomas Adam
7f813dcb6a Merge branch 'obsd-master' 2017-05-12 14:01:17 +01:00
nicm
18bab30792 Scrolling needs to use background colour. 2017-05-12 13:00:56 +00:00
nicm
60f7b05c0c Regions can't be smaller than 2 so don't try to clear them by scrolling if so. 2017-05-12 11:19:24 +00:00
nicm
7f626c8959 Can use INDN to clear regions with default background colour if margins
are supported.
2017-05-12 11:13:43 +00:00
nicm
886d50dcab ECH needs to use background colour. 2017-05-12 10:50:11 +00:00
nicm
7d3e2c83d4 Store copy mode search string in pane so search-again command works even
if you exit and reenter copy mode (it doesn't remember the position,
just the search string), suggested by espie@.
2017-05-12 10:45:38 +00:00
Nicholas Marriott
1cdc4568bd Merge branch '2.5-rc' 2017-05-11 23:28:56 +01:00
nicm
69df38f8d8 Clear to start of screen needs to use background colour. 2017-05-11 23:28:44 +01:00
nicm
5e30b81825 Need to redraw out to cellsize (total cells used in a line) rather than
cellused (only non-space cells) because there may be cells with a
nondefault background.
2017-05-11 23:28:22 +01:00
Thomas Adam
99582befc4 Merge branch 'obsd-master' 2017-05-11 14:01:10 +01:00
nicm
c0d3f204b0 Clear to start of screen needs to use background colour. 2017-05-11 11:39:30 +00:00
nicm
989cdca95f Need to redraw out to cellsize (total cells used in a line) rather than
cellused (only non-space cells) because there may be cells with a
nondefault background.
2017-05-11 11:38:49 +00:00
Thomas Adam
def8f852e3 Merge branch 'obsd-master' 2017-05-11 10:01:10 +01:00
nicm
349cdd6110 Make environ_log prefix take a format. 2017-05-11 07:34:54 +00:00
nicm
c54a5b3690 Change how we resolve which pane is dragging when there are multiple
options - choose the largest pane, which is more likely to be the one the
user wants to resize. Prompted by a report from Thomas Sattler.
2017-05-11 07:24:42 +00:00
Thomas Adam
6d961d672d Merge branch 'obsd-master' 2017-05-10 22:01:13 +01:00
Thomas Adam
247ec2ad88 Merge branch 'obsd-master' 2017-05-10 20:01:17 +01:00
nicm
8ab2753521 Move to the right cursor position before using spaces to clear. 2017-05-10 18:40:13 +00:00
nicm
2dc9bfd93a Prevent control clients from affecting the session size until they have
specified a size with refresh-client -C. Prompted by a different change
with the same purpose from George Nachman.
2017-05-10 16:48:36 +00:00
nicm
9dc6946ebf We can use ECH to clear sections of lines, so use it for internal panes
(that don't touch an edge). Move all the tty clear code into two common
functions rather than having the same bunch of checks everywhere.
2017-05-10 16:47:03 +00:00
Thomas Adam
0868512bbc Merge branch 'obsd-master' 2017-05-10 16:01:10 +01:00
nicm
b519551153 Expand formats in option names and add -F flag to do so in option values as well. 2017-05-10 13:05:41 +00:00
Thomas Adam
f8b3f1622d Merge branch 'obsd-master' 2017-05-10 14:01:11 +01:00
nicm
0e3c5ebe1a Insert copy mode bindings at the right place in the command queue. 2017-05-10 10:46:59 +00:00
Nicholas Marriott
daef51e038 Typo. 2017-05-09 23:18:48 +01:00
Nicholas Marriott
e82c42661b Back to master. 2017-05-09 23:11:01 +01:00
Nicholas Marriott
3a47dec424 Fix test. 2017-05-09 23:01:10 +01:00
Nicholas Marriott
7b17618890 2.5-rc and changes. 2017-05-09 22:53:36 +01:00
Nicholas Marriott
71bc255e6f Merge branch 'master' of github.com:tmux/tmux 2017-05-09 22:34:15 +01:00
Nicholas Marriott
8f990c573c Update TODO. 2017-05-09 22:33:39 +01:00
Thomas Adam
3f1d6102f3 Merge branch 'obsd-master' 2017-05-09 20:01:10 +01:00
nicm
3712b41aba If the target pane for send-keys in in a mode with a key table (that is,
copy mode), then look the key up in the table and fire any command
instead of delivering the key to the pane directly where it will be
ignored. This makes C-b C-b (send-prefix) work in copy mode again.
2017-05-09 17:56:55 +00:00
Thomas Adam
4bcb64f8c1 Merge branch 'obsd-master' 2017-05-09 15:44:33 +01:00
Thomas Adam
a651b08a2f Merge branch 'obsd-master'
Conflicts:
	format.c
2017-05-09 15:44:13 +01:00
nicm
3b35daacf7 If the current screen was complex enough, it was possible to make redraw
itself hit the "terminal can't keep up" check. To avoid this, record how
much data we send during redraw (we know we will be starting with 0) and
skip the check until it has been flushed. GitHub issue 912.
2017-05-09 13:04:36 +00:00
nicm
18f36906a9 Set current pane in rotate-window. 2017-05-09 11:00:48 +00:00
nicm
5fee4638e0 Add a format for the name of the pane's mode, lets it be used as a
conditional for key bindings.
2017-05-07 22:27:57 +00:00
nicm
d52f579fd5 Up to now, tmux sees \033\033[OA as M-Up and since we turned on
xterm-keys by default, generates \033[1;3A instead of
\033\033[OA. Unfortunately this confuses vi, which doesn't understand
xterm keys and now sees Escape+Up pressed within escape-time as Escape
followed by A.

The issue doesn't happen in xterm itself because it gets the keys from X
and can distinguish between a genuine M-Up and Escape+Up.

Because xterm can, tmux can too: xterm will give us \033[1;3A (that is,
kUP3) for a real M-Up and \033\033OA for Escape+Up - in fact, we can be
sure any \033 preceding an xterm key is a real Escape key press because
Meta would be part of the xterm key instead of a separate \033.

So change tmux to recognise both sequences as M-Up for its own purposes,
but generate the xterm version of M-Up only if it originally received
the xterm version from the terminal.

This means we will return to sending \033\033OA instead of the xterm key
for terminals that do not support xterm keys themselves, but there is no
practical way around this because they do not allow us to distinguish
between Escape+Up and M-Up. xterm style escape sequences are now the de
facto standard for these keys in any case.

Problem reported by jsing@ and subsequently by Cecile Tonglet in GitHub
issue 907.
2017-05-07 21:25:59 +00:00
nicm
2fef10b9ac Add some formats to look at the session window stack, suggested by Scott
ROCHFORD.
2017-05-05 11:59:47 +00:00
Thomas Adam
f3221941f2 Merge branch 'obsd-master' 2017-05-04 10:01:12 +01:00
nicm
d98d316903 Some new notifications, mainly for active pane and current window and
session:

    pane-mode-changed
    window-pane-changed
    client-session-changed
    session-window-changed

From Joshua Brot.
2017-05-04 07:16:43 +00:00
Thomas Adam
97ecb4f9d8 Merge branch 'obsd-master' 2017-05-03 08:01:14 +01:00
nicm
ca6a121e63 Add a format for the last search string in copy mode and fix the prompt
so it can work when in -I, suggested by Suraj N Kurapati.
2017-05-03 05:53:34 +00:00
Thomas Adam
e354b0e40f Merge branch 'obsd-master' 2017-05-01 14:01:14 +01:00
nicm
0ccfb61bb0 In order that people can use formats like #D in #() in the status line
and not have to wait for an update when they change pane, we allow
commands to run more than once a second if the expanded form
changes. Unfortunately this can mean them being run far too often
(pretty much continually) when multiple clients exist, because some
formats (including #D) will always differ between clients.

To avoid this, give each client its own tree of jobs which means that
the same command will be different instances for each client - similar
to how we have the tag to separate commands for different panes.

GitHub issue 889; test case reported by Paul Johnson.
2017-05-01 12:20:55 +00:00
Nicholas Marriott
4b39120d22 .NOTPARALLEL. 2017-04-30 13:55:32 +01:00
Nicholas Marriott
76950a6401 Add regress/Makefile. 2017-04-30 13:47:25 +01:00
Nicholas Marriott
909d962d3a Make example match reality; Greg Hurrell. 2017-04-30 08:27:23 +01:00
Nicholas Marriott
dde53cfde1 Add to TODO. 2017-04-30 08:23:14 +01:00
Thomas Adam
0adb60b3a6 Merge branch 'obsd-master' 2017-04-30 00:01:17 +01:00
nicm
a2dd7daf4e Fix UTF-8 combining characters in column 0, based on a diff from Keith
Winstein.
2017-04-29 21:27:46 +00:00
Thomas Adam
3a8e56b282 Merge branch 'obsd-master' 2017-04-28 22:01:18 +01:00
Nicholas Marriott
36202a63e9 Merge branch 'master' of github.com:tmux/tmux 2017-04-28 20:22:31 +01:00
Nicholas Marriott
abad809e7a Test that kill-session closes the panes (processes end up dead). 2017-04-28 20:22:01 +01:00
nicm
0f2f783584 Log what is happening with window and session reference counts much more
obviously.
2017-04-28 19:13:55 +00:00
nicm
bcd6b41674 Remove a reference from the right window when removing from a winlink's
list.
2017-04-28 19:12:15 +00:00
nicm
92053cb492 Do not put the window on the alerts queue and add a reference unless the
alert is enabled and we are actually going to add the alerts event.
2017-04-28 19:10:48 +00:00
Thomas Adam
14cb489a3b Merge branch 'obsd-master' 2017-04-28 20:01:14 +01:00
nicm
54e2205e54 Konsole incorrectly ignores SU (CSI S) if the parameter is bigger than
the scroll region, so clamp it. Reported by Moritz Bunkus.
2017-04-28 17:58:44 +00:00
Thomas Adam
99b0f48b2e Merge branch 'obsd-master' 2017-04-28 16:01:12 +01:00
nicm
c12711affd Default for xterm-keys was wrong, stop documenting it. 2017-04-28 13:39:59 +00:00
Nicholas Marriott
e4b4125310 source-file too. 2017-04-27 13:14:14 +01:00
Nicholas Marriott
6b2d850e54 Tests for some new session and new window bits. 2017-04-27 13:09:08 +01:00
Thomas Adam
0daeefefdb Merge branch 'obsd-master' 2017-04-25 20:01:11 +01:00
nicm
d520dae6ac Make full width panes try to play more nicely with terminal copy and
paste by avoiding explicit line wraps if we think the terminal will wrap
anyway.
2017-04-25 18:30:29 +00:00
nicm
03d01eabb5 When we write out the grid including escape sequences, an SGR 0 needs to
cause the colours to be written again. Also treat colours separately
from attributes so that RGB colours will work.
2017-04-25 18:20:51 +00:00
Thomas Adam
65d6278f88 Merge branch 'obsd-master' 2017-04-25 18:01:11 +01:00
nicm
c48d09ec88 Do not update TERM into config file parsing has finished. 2017-04-25 15:35:10 +00:00
nicm
4a51a9d9d5 Block the initial client if there is one until the configuration file
has finished loading.
2017-04-25 14:46:23 +00:00
Nicholas Marriott
b938212563 Another test. 2017-04-25 15:40:10 +01:00
Nicholas Marriott
accaff8ac0 Remove stuff from TODO. 2017-04-25 14:31:05 +01:00
Nicholas Marriott
45965fb020 And another test. 2017-04-25 14:30:58 +01:00
Thomas Adam
6ac39d5cdb Merge branch 'obsd-master' 2017-04-25 14:01:16 +01:00
Nicholas Marriott
9794c03537 And another. 2017-04-25 13:50:44 +01:00
Nicholas Marriott
1b221a56ea Try to start writing test scripts. 2017-04-25 13:37:03 +01:00
nicm
eb6fd6ff80 if-shell doesn't need to queue its error message into a callback, and in
fact it can't do so because the item it was working with will have been
freed. Reported by Daniel Hahler.
2017-04-25 11:49:35 +00:00
Thomas Adam
9d041d8e6c Merge branch 'obsd-master' 2017-04-23 20:01:13 +01:00
nicm
5172014668 Only use ED for clear screen if at the bottom, same as earlier fix to
clear end of screen.
2017-04-23 18:13:24 +00:00
Thomas Adam
b853054e71 Merge branch 'obsd-master' 2017-04-22 16:01:19 +01:00
Thomas Adam
a6a294c8f8 Merge branch 'obsd-master' 2017-04-22 14:01:15 +01:00
nicm
1e0eb914d9 Memory leak from David CARLIER. 2017-04-22 12:55:06 +00:00
nicm
ae1a6c2fc5 Do not need getopt.h. 2017-04-22 12:08:41 +00:00
Thomas Adam
e802b683ea Merge branch 'obsd-master' 2017-04-22 12:01:19 +01:00
nicm
55cd4c7bc7 Can't collect UTF-8 characters of more than one byte at the moment. 2017-04-22 10:30:56 +00:00
nicm
a4eaac359a new -A should use the session name. 2017-04-22 10:26:44 +00:00
nicm
ee45a8a149 Get rid of the extra layer of flags and cmd_prepare() and just store the
CMD_FIND_* flags in the cmd_entry and call it for the command. Commands
with special requirements call it themselves and update the target for
hooks to use.
2017-04-22 10:22:39 +00:00
Thomas Adam
b08e451c91 Merge branch 'obsd-master' 2017-04-22 10:01:51 +01:00
nicm
2c0f826c36 Mouse bindings and hooks set up an initial current state when running a
command. This is used for the session, window and pane for all commands
in the command sequence if there is no -t or -s.

However, using it for all commands in the command sequence means that if
the active pane or current session is changed, subsequent commands still
use the previous state. So make commands which explicitly change the
current state (such as neww and selectp) update it themselves for later
commands. Commands which may invalidate the state (like killp) are
already OK because an invalid state will be ignored.

Also fill in the current state for all key bindings rather than just the
mouse, so that any omissions are easier to spot.
2017-04-22 08:56:24 +00:00
nicm
bcab77e266 We need to collect UTF-8 characters so that width != 1 characters are
correctly flushed.
2017-04-22 08:33:28 +00:00
Thomas Adam
d8398af770 Merge branch 'obsd-master' 2017-04-22 08:01:54 +01:00
nicm
30348edc7c Fix if-shell without a client (so in the config file). Reported by Theo
Buehler.
2017-04-22 06:27:15 +00:00
nicm
59ff9b8128 Typo in example. 2017-04-22 06:15:22 +00:00
nicm
2c9bdd9e32 Memory leaks, from David CARLIER. 2017-04-22 06:13:30 +00:00
Thomas Adam
21240c1a8f Merge branch 'obsd-master' 2017-04-22 00:01:11 +01:00
nicm
c8ecbf38ab Log error properly when no current state, and some other minor tweaks. 2017-04-21 22:23:24 +00:00
nicm
194a121ef6 Make sure cmd_find_from_* clear the state if they fail. 2017-04-21 22:00:06 +00:00
nicm
8867951144 Rename a variable. 2017-04-21 21:02:26 +00:00
Thomas Adam
fd13731049 Merge branch 'obsd-master' 2017-04-21 22:01:14 +01:00
nicm
c68ceca8cd Clear shared state if not filling it in. 2017-04-21 20:34:05 +00:00
nicm
efaf4c16cf Make the cmd_find_* functions more obvious when looking for a client,
rather than having it inside other functions. Should be no change to the
way targets are resolved just yet.
2017-04-21 20:26:34 +00:00
nicm
2ad09ab5af Key needs to be initialized to zero now it has flags in it. 2017-04-21 19:33:07 +00:00
Thomas Adam
1f209ed030 Merge branch 'obsd-master' 2017-04-21 20:01:18 +01:00
nicm
3c876235cc Style nits and an unused struct. 2017-04-21 18:18:17 +00:00
nicm
afa4e3ed9c Add cmd_find_from_winlink_pane and use it in a couple of places, and
make functions that can't fail void.
2017-04-21 17:22:20 +00:00
Thomas Adam
c376c5a817 Merge branch 'obsd-master' 2017-04-21 18:01:11 +01:00
nicm
92a77e7654 It is annoying that the copy mode key table (or any other key table)
will suppress root key table bindings. So change to always check the
root table if no binding is found in the current table (whether it be
the prefix table from pressing the prefix or the copy mode table from a
pane).

A root key binding can be blocked by binding the key to a command that
does nothing (like send-keys with no arguments).

Problem reported by Thomas Sattler.
2017-04-21 16:04:18 +00:00
Thomas Adam
4612419c14 Merge branch 'obsd-master' 2017-04-21 16:01:18 +01:00
nicm
c799425069 More unnecessary arguments now winlink points back to session. 2017-04-21 14:09:44 +00:00
nicm
428be9803c History needs to be loaded after config parsing is done - now that
commands are queued, that's in cfg_done not after start_cfg finishes.
2017-04-21 14:04:54 +00:00
nicm
bba588752f Store state shared between multiple commands in the queue in a shared
structure.
2017-04-21 14:01:19 +00:00
nicm
311dad8c28 Do not run the config file in the context of the first client, instead
use no client like we did before. This means commands like new-session
won't try to attach if they are in the config file.
2017-04-21 13:15:43 +00:00
Thomas Adam
93062ad099 Fix after merge 2017-04-21 09:29:22 +01:00
Thomas Adam
22e594fcea Merge branch 'obsd-master'
Conflicts:
	Makefile.am
	pty.c
2017-04-21 09:25:07 +01:00
Nicholas Marriott
02580ac134 Typo; Daniel Hahler. 2017-04-21 06:49:38 +01:00
Nicholas Marriott
b723f50e65 Do not need getopt.h for getopt, from Eric N Vander Weele. 2017-04-20 20:35:11 +01:00
Nicholas Marriott
4a2e75fc8c Merge branch 'master' of github.com:tmux/tmux 2017-04-20 19:09:36 +01:00
Nicholas Marriott
9420758127 getptmfd() and fdforkpty() compat. 2017-04-20 19:09:07 +01:00
nicm
87997efe8d Use fdforkpty() instead of our own unwrapped versions. 2017-04-20 17:49:26 +00:00
Thomas Adam
69e0f28333 Merge branch 'obsd-master' 2017-04-20 18:01:12 +01:00
nicm
51a0dbb172 Only set up a current target for mouse key bindings. Fixes:
bind q select-pane -U \; resize-pane -Z

(There is still some possible weirdness with the way we do current
targets, it should probably be done in a different way at some point.)
2017-04-20 15:16:20 +00:00
Nicholas Marriott
7934e7a6b5 Notes on target resolution. 2017-04-20 15:40:28 +01:00
Nicholas Marriott
aebbb15fe2 Turn on debug if $VERSION is master rather than commenting and uncommenting. 2017-04-20 12:06:39 +01:00
Thomas Adam
48371216df Merge branch 'obsd-master' 2017-04-20 12:01:14 +01:00
Nicholas Marriott
e30f9dc1fa Merge tag '2.4'
Version 2.4.
2017-04-20 11:59:07 +01:00
Nicholas Marriott
f21cb71fbe Enter date of release. 2017-04-20 11:52:16 +01:00
Nicholas Marriott
990218739a Missing :. 2017-04-20 11:03:23 +01:00
Nicholas Marriott
e7c2f53f2a Changes to CHANGES. 2017-04-20 11:00:15 +01:00
nicm
21993105e5 Now that struct winlink has a session pointer, can remove some arguments. 2017-04-20 09:43:45 +00:00
Thomas Adam
9b2f02efbd Update CHANGES file 2017-04-20 10:39:16 +01:00
nicm
0f25ad3ca3 There is no real need for window_printable_flags to allocate, make it
return a buffer from the stack.
2017-04-20 09:39:07 +00:00
Nicholas Marriott
f9c7c50a93 Update TODO. 2017-04-20 10:20:42 +01:00
nicm
0b44ad99b5 If a #() command doesn't exit, use its most recent line of output (it
must be a full line). Don't let it redraw the status line more than once
a second.

Requested by someone about 10 years ago...
2017-04-20 09:20:22 +00:00
Nicholas Marriott
78d707dc83 Add to TODO. 2017-04-20 08:53:03 +01:00
nicm
b087483538 load_cfg returns < 0 on error, not != 0. Problem reported by Kaushal Modi. 2017-04-19 22:19:22 +01:00
Thomas Adam
3385159c94 Merge branch 'obsd-master' 2017-04-19 20:01:11 +01:00
nicm
f184c6f06c load_cfg returns < 0 on error, not != 0. Problem reported by Kaushal Modi. 2017-04-19 16:59:54 +00:00
Thomas Adam
5a551ac57f Merge branch 'obsd-master' 2017-04-19 16:01:14 +01:00
nicm
53fde21bb8 Add a suspend helper function, and do not allow detaching or suspending
while already doing so.
2017-04-19 14:00:28 +00:00
Nicholas Marriott
b946bf43f5 Version 2.4. 2017-04-19 13:51:49 +01:00
Nicholas Marriott
d64a815e8d Missed freezero. 2017-04-19 13:50:52 +01:00
nicm
689f4bfac2 Style nits and a missing cast. 2017-04-19 12:44:29 +00:00
Thomas Adam
85af9c9c9d Merge branch 'obsd-master' 2017-04-19 10:01:12 +01:00
Nicholas Marriott
95c38087db Missed freezero. 2017-04-19 07:58:45 +01:00
nicm
fa6deb5866 When the data we have buffered to write to a terminal grows beyond a
reasonable amount (currently width * height * 8 bytes), discard all
output to the terminal and start trying to redraw periodically
instead. Continue with this until the amount of data we are trying to
write falls to a low level again.

This helps to prevent tmux sitting on a huge buffer of data when there
are processes with fast output running inside tmux but the outside
terminal is slow.

A new client_discarded format holds the amount of data that has been
discarded due to this mechanism.

The three variables (when to start this, when to stop, and how often to
redraw) are basically "works for me" at the moment, this is going in to
see how it goes and if it causes problems for anyone else.
2017-04-19 06:52:27 +00:00
Thomas Adam
a71c262d5f Merge branch 'obsd-master' 2017-04-19 00:01:15 +01:00
nicm
f731ae4a2d Revert use of DECSLRM on iTerm2, it doesn't help as much as we throught,
and there are some question marks about it's support.
2017-04-18 21:41:42 +00:00
nicm
8c8ce08d79 On terminals without DECSLRM, when a pane that is less than the full
with of the terminal scrolls, tmux needs to redraw the entire pane. This
results in a large amount of output data which can cause slow terminals
to struggle, particularly when many lines are scrolled together quickly.

This can be reduced by only redrawing when tmux doesn't hold any
buffered data for the terminal. If a redraw is required and data is
buffered, the redraw is deferred until all that data is consumed (it is
checked after every event loop, a timer is used to ensure this happens
at some point). While a redraw is pending, no additional data will be
written to the terminal.

The redraw still happens, now it is just pushed back if it is possible
it would just add more data on top of a terminal that is already
behind. This both gives the terminal a chance to catch up, and allows
tmux to process more scrolling (that would require additional redraws)
in the meantime.

Helps with a problem reported by Greg Hurrell.
2017-04-18 20:37:49 +00:00
Thomas Adam
de4f817bd6 Merge branch 'obsd-master' 2017-04-18 20:01:12 +01:00
nicm
623e35f594 Detect iTerm2 and use DECSLRM for it as well. 2017-04-18 18:21:37 +00:00
Thomas Adam
a54309147d Merge branch 'obsd-master' 2017-04-18 18:01:17 +01:00
nicm
fb3c5efa50 Add a format for number of bytes writtent to client, useful for debugging. 2017-04-18 15:44:17 +00:00
nicm
aace1ead1e Do not check for BCE for a background colour that isn't needed, use
colour 8 instead.
2017-04-18 15:27:47 +00:00
Thomas Adam
0aa959d7a3 Merge branch 'obsd-master' 2017-04-18 16:01:18 +01:00
nicm
83ff1e9bd3 Include client name in key logging. 2017-04-18 13:34:04 +00:00
Thomas Adam
28833efb48 Merge branch 'obsd-master' 2017-04-17 10:01:13 +01:00
nicm
175d1854d4 Don't bother moving the cursor for empty lines. 2017-04-17 08:10:44 +00:00
nicm
7461c165b5 Remove a couple of redraw flags that no longer have any effect. 2017-04-17 06:40:32 +00:00
Thomas Adam
d912687be7 Merge branch 'obsd-master' 2017-04-16 22:01:19 +01:00
nicm
d566c780e5 Memory leak, from David CARLIER. 2017-04-16 20:33:46 +00:00
nicm
54bcaab70e Use EL1 to clear lines when redrawing the leftmost pane, rather than
spaces.
2017-04-16 20:32:14 +00:00
Nicholas Marriott
9583878a7b Accept NULL pointer. 2017-04-12 07:41:11 +01:00
Nicholas Marriott
d720a1487b Update imsg*.c from OpenBSD. 2017-04-11 11:51:25 +01:00
Thomas Adam
5f662d91db Merge branch 'obsd-master'
Conflicts:
	server-client.c
	tmux.1
2017-04-06 11:10:17 +01:00
nicm
94b71bcb64 Add Home and End for copy mode. 2017-04-05 12:14:18 +00:00
nicm
36882ec789 Try again to resolve problems with mistaking sessions for windows: now
do not look up windows as sessions (and panes as windows) when they are
qualified with a ':' or a '.'. So 'foo' as a window target will look for
windows and sessions called 'foo', but ':foo' will only look for
windows, and 'foo:' only for sessions. This means the common case of
using an unadorned session as a window target (send -tfoo) should
continue to work, but an explicit window will not get confused with a
session (send -t:foo).
2017-04-05 11:04:48 +00:00
nicm
9b28200578 Give each client a name. This defaults to the tty name as before but
falls back to an alternative if the tty name is not available. This is
clearer than overloading the client ttyname member and allows us to
remove the path stored in the tty struct, it should always be the same
as the client.
2017-04-05 10:49:46 +00:00
nicm
ab4a4b2ad0 cfg_file can be static. 2017-04-05 10:45:39 +00:00
Thomas Adam
05c97d7fe9 Merge branch 'obsd-master' 2017-03-25 14:01:12 +00:00
nicm
b9a4beb6e7 Write raw strings in one go rather than character at a time. 2017-03-24 14:45:00 +00:00
Nicholas Marriott
2d84ee9001 Merge branch 'master' of github.com:tmux/tmux 2017-03-24 10:06:22 +00:00
Nicholas Marriott
2e5664d2df Update imsg*.[ch] from OpenBSD, add some compat bits it needs and remove some
bits it doesn't.
2017-03-24 10:05:53 +00:00
Thomas Adam
1384525dc1 Merge branch 'obsd-master' 2017-03-24 08:01:13 +00:00
nicm
591b26e46f Show count of search results in copy mode. 2017-03-24 07:14:27 +00:00
Nicholas Marriott
e87d808594 Remove coverage and profile flags. 2017-03-22 21:59:43 +00:00
Nicholas Marriott
1cb8145dc5 Tweak some comments. 2017-03-22 21:29:07 +00:00
Nicholas Marriott
c57039bc3d Can shorten these by using LIBOBJ. 2017-03-22 19:22:32 +00:00
Nicholas Marriott
9c0520f2c5 Merge branch 'master' of github.com:tmux/tmux 2017-03-22 08:46:12 +00:00
Nicholas Marriott
c3dbbdaadf Bump automake and autoconf versions. 2017-03-22 08:45:53 +00:00
Thomas Adam
843e605b89 Merge branch 'obsd-master' 2017-03-22 08:01:17 +00:00
Nicholas Marriott
643813c6ed DEFS -> AM_CPPFLAGS. 2017-03-22 07:54:30 +00:00
Nicholas Marriott
223ed4a989 Should not need -D_POSIX_PTHREAD_SEMANTICS. 2017-03-22 07:49:27 +00:00
Nicholas Marriott
080080fa23 Use AC_USE_SYSTEM_EXTENSIONS and explicitly check for daemon() in headers. 2017-03-22 07:42:45 +00:00
nicm
df3ab87964 Add support for the strikethrough attribute (SGR 9), using the new smxx
terminfo capability. This means there are now nine attribute bits, so
anything above 0xff uses an extended cell.
2017-03-22 07:16:54 +00:00
Nicholas Marriott
3cc2486106 Merge branch 'master' of github.com:tmux/tmux 2017-03-21 21:38:03 +00:00
Nicholas Marriott
57cb6ef3a2 Add to TODO. 2017-03-21 21:28:37 +00:00
Thomas Adam
02ddd4ce70 Merge branch 'obsd-master' 2017-03-21 20:01:16 +00:00
Nicholas Marriott
b008a07ebb Do not test for term.h since we don't use the result. 2017-03-21 19:41:25 +00:00
nicm
04e17a7e11 Use uid_t for UID not u_int. 2017-03-21 19:28:03 +00:00
Nicholas Marriott
cd7550cdf1 Some __unused. 2017-03-21 19:27:18 +00:00
Nicholas Marriott
c2b53598ad Bad merge. 2017-03-21 14:48:44 +00:00
Thomas Adam
57b4d3d593 Merge branch 'obsd-master' 2017-03-21 12:01:14 +00:00
nicm
cdaa758340 Fix movement after select-line, from Omar Sandoval. 2017-03-21 09:51:00 +00:00
nicm
c916feaf29 Fix pane movement by direction (up, down, left, right) when
pane-border-status is set, from KOIE Hidetaka.
2017-03-21 09:49:10 +00:00
Thomas Adam
31ae09efa0 Merge branch 'obsd-master'
Conflicts:
	utf8.c
2017-03-20 13:45:18 +00:00
Nicholas Marriott
066575fd5a Add to TODO. 2017-03-20 11:50:54 +00:00
Nicholas Marriott
792455ce87 Tweak test for program_invocation_short_name. 2017-03-18 14:37:37 +00:00
Nicholas Marriott
4eec3270ec Clarify that release instructions will install. 2017-03-18 08:33:15 +00:00
Nicholas Marriott
640666fb36 Fix some warnings. 2017-03-17 14:55:33 +00:00
nicm
67d2335130 Fix a couple of argument types. 2017-03-17 14:51:41 +00:00
nicm
481e48d119 Add h and l for collapse and expand in choose mode with vi(1) keys, from
Gregory Pakosz.
2017-03-17 14:41:54 +00:00
Thomas Adam
1ea19245b3 Merge branch 'obsd-master' 2017-03-16 22:01:18 +00:00
nicm
b69efbdd30 Redraw after killp -a. 2017-03-16 20:05:14 +00:00
Thomas Adam
0dd694f5fd Merge branch 'obsd-master' 2017-03-15 16:01:13 +00:00
nicm
2a9d697771 Invalidate the cursor when we think we should have wrapped. 2017-03-15 15:22:14 +00:00
Thomas Adam
4e809a3130 Merge branch 'obsd-master' 2017-03-15 10:01:11 +00:00
nicm
3c3c08b6d9 Try to avoid moving the cursor to the start of the next line when
printing cells if it is already at the very end of the line and the
terminal will wrap it to the next line itself, this means terminals
still see it as a wrapped line for the purposes of their own mouse
selection. Reported by millert@.
2017-03-15 09:21:21 +00:00
Thomas Adam
cc6c6edb6f Merge branch 'obsd-master' 2017-03-13 18:01:13 +00:00
nicm
8e9b10062b Log where panes are created. 2017-03-13 17:20:11 +00:00
Thomas Adam
12c6c723a9 Merge branch 'obsd-master' 2017-03-13 12:01:13 +00:00
nicm
fd65210139 Revert previous, breaks normal short targets, reported by Theo Buehler. 2017-03-13 10:53:32 +00:00
Thomas Adam
266e662fae Merge branch 'obsd-master' 2017-03-11 16:01:12 +00:00
nicm
d455da45eb Fix calculation of size for full size splits. 2017-03-11 15:16:35 +00:00
nicm
0fe3b739a1 Only look for window and pane parts of target as a sesson and window if
they look like an ID.
2017-03-11 15:16:08 +00:00
Thomas Adam
392253f032 Merge branch 'obsd-master' 2017-03-10 00:01:16 +00:00
Nicholas Marriott
385a361bf8 Merge branch 'master' of github.com:tmux/tmux 2017-03-09 22:21:29 +00:00
Nicholas Marriott
a24cf4a5e1 Can only check for one with AC_CHECK_LIB. 2017-03-09 22:21:12 +00:00
nicm
55e73e3612 Clear the bracket paste mode when in the command prompt. 2017-03-09 22:00:46 +00:00
Thomas Adam
c5bdae466e Merge branch 'obsd-master' 2017-03-09 18:01:16 +00:00
nicm
bce1dee034 Move the client identify (display-panes) code into server-client.c. 2017-03-09 17:06:35 +00:00
nicm
dbfee6a468 Move server_fill_environ into environ.c and move some other common code
into it.
2017-03-09 17:02:38 +00:00
Nicholas Marriott
fd96ccfd80 No extra : for errx and warnx. 2017-03-09 16:49:37 +00:00
Nicholas Marriott
b79df1dc29 Compat code for strndup and strnlen. 2017-03-09 15:43:08 +00:00
Nicholas Marriott
180ebf0208 Merge branch 'master' of github.com:tmux/tmux 2017-03-09 15:39:36 +00:00
Nicholas Marriott
514a723f74 Solaris fixes, mostly from Dagobert Michelsen. 2017-03-09 15:39:13 +00:00
Thomas Adam
92434b0afd Merge branch 'obsd-master' 2017-03-08 22:01:19 +00:00
nicm
e8f2609ca4 Skip over padding cells when moving the cursor left or right. 2017-03-08 20:05:25 +00:00
Thomas Adam
41a01fc629 Merge branch 'obsd-master' 2017-03-08 16:01:15 +00:00
nicm
41b31fe240 Handle empty options correctly. 2017-03-08 14:43:40 +00:00
nicm
78ca1b0265 Always send smkx to the terminal outside, the keys we get from terminfo
are the keys when it is on.
2017-03-08 14:34:35 +00:00
Thomas Adam
3ea36830f3 Merge branch 'obsd-master' 2017-03-08 14:01:23 +00:00
nicm
6b2009ad72 Add a helper function for the most common format_create/defaults/expand
pattern.
2017-03-08 13:36:12 +00:00
Thomas Adam
5d3296c53b Merge branch 'obsd-master' 2017-03-07 15:32:28 +00:00
nicm
1e6e606f54 Need to flush before writing out cells we are not collecting, also add
some extra logging.
2017-03-07 13:48:28 +00:00
nicm
daac28febb If moving cells outside the current used count, update it. 2017-03-07 13:47:56 +00:00
Thomas Adam
69257bc0aa Merge branch 'obsd-master' 2017-03-06 10:01:21 +00:00
Nicholas Marriott
8684e60f51 Merge branch 'master' of github.com:tmux/tmux 2017-03-06 09:26:16 +00:00
Nicholas Marriott
fa27cbd035 Expand on OS X faffing, based on a diff from Kurtis Rader. 2017-03-06 09:24:41 +00:00
nicm
dc8fefe902 Collect strings correctly when on terminals that don't support UTF-8. 2017-03-06 09:02:59 +00:00
nicm
fba9ebcc0c When redrawing a combined UTF-8 characters in its existing position,
need to save and restore the cursor so that the next character goes into
the right place.
2017-03-06 09:02:36 +00:00
Thomas Adam
48a3dba6b9 Merge branch 'obsd-master' 2017-02-27 14:01:20 +00:00
Nicholas Marriott
2fa16eee53 Change to vim(1) script by Eric Pruitt. 2017-02-27 13:21:04 +00:00
nicm
e741a0bcd7 If splitw -b is used, insert the new pane before the current one in the
pane list. This means the numbering is in order (for example for
display-panes) and fixes a problem with redrawing the active pane
borders.
2017-02-27 13:07:57 +00:00
Thomas Adam
14dc2acc25 Merge branch 'obsd-master' 2017-02-22 10:01:12 +00:00
nicm
0414b1fc78 Minor bits: fix an array size, add comment, make grid_cell_entry static. 2017-02-22 09:01:32 +00:00
Thomas Adam
4b112c19f1 Merge branch 'obsd-master' 2017-02-21 18:01:12 +00:00
nicm
8a0b279c31 Change pane redraw to collect cells up as well, and simplify it a bit. 2017-02-21 16:25:04 +00:00
Thomas Adam
6b45464120 Merge branch 'obsd-master' 2017-02-21 16:01:15 +00:00
nicm
27ee34e7fa Don't need is1,is2,is3 so remove them. 2017-02-21 14:18:12 +00:00
Thomas Adam
e9819eef3c Merge branch 'obsd-master' 2017-02-21 12:01:16 +00:00
nicm
9e4c5133c8 Scrolling at least needs to be flushed before sending EL to the terminal
(but it is simpler to flush everything, so do that instead).
2017-02-21 10:30:15 +00:00
Thomas Adam
11e7915195 Reflect OBSD Makefile changes in Makefile.am 2017-02-21 09:24:53 +00:00
Thomas Adam
0ad2beae7e Merge branch 'obsd-master'
Conflicts:
	Makefile
2017-02-21 09:23:50 +00:00
Nicholas Marriott
55e76edd3c Improve NetBSD KERN_PROC2 bit, mostly from Kamil Rytarowski. 2017-02-19 08:31:05 +00:00
nicm
f27e1d07fc Add SGR 28 to clear hidden flag. 2017-02-19 07:55:11 +00:00
Nicholas Marriott
203d604bf7 Add to TODO. 2017-02-17 10:52:40 +00:00
Nicholas Marriott
ee7acde149 Update TODO. 2017-02-16 15:06:20 +00:00
nicm
82db1fa9e5 There are buggy terminals out there that do not move the cursor to 0,0
after CSR, so invalidate the cursor position rather than assuming 0,0.
2017-02-16 12:56:01 +00:00
nicm
c948c6b697 Handle insert cells when cursor at edge of screen correctly, and do a
full flush before insert.
2017-02-16 12:43:08 +00:00
nicm
c889e11375 Merge clear-history into capture-pane. 2017-02-16 12:18:38 +00:00
Thomas Adam
f734d81074 Merge branch 'obsd-master' 2017-02-16 12:01:21 +00:00
nicm
8b8d0963da Style nits. 2017-02-16 10:53:25 +00:00
Thomas Adam
c9f2dc5ee5 Merge branch 'obsd-master' 2017-02-15 12:01:15 +00:00
nicm
dd25a6cdc2 Do not clear to end of screen unless the pane is at the bottom. 2017-02-15 11:22:13 +00:00
Nicholas Marriott
47bc867ab9 Merge branch 'master' of github.com:tmux/tmux 2017-02-15 10:34:38 +00:00
Nicholas Marriott
b9b7daf3b2 Copy 24-bit-color.sh from iTerm2. 2017-02-15 10:34:20 +00:00
Thomas Adam
631a89954f Merge branch 'obsd-master' 2017-02-15 10:01:17 +00:00
Nicholas Marriott
36734afdd8 Hide or fix some warnings. 2017-02-15 08:54:21 +00:00
nicm
640d9e54b7 "status bar" -> "status line" for consistency, from Benjamin Dopplinger. 2017-02-15 08:47:55 +00:00
Nicholas Marriott
2b4c144f96 Remove vis.h. 2017-02-15 08:37:11 +00:00
Thomas Adam
ba3c1534e0 Merge branch 'obsd-master' 2017-02-14 20:01:12 +00:00
nicm
e340df2034 Make source-file look for files relative to the client working directory
(like load-buffer and save-buffer), from Chris Pickel. Also break the
where-is-this-file code out into its own function for loadb and saveb.
2017-02-14 18:13:05 +00:00
Thomas Adam
02e04477de Merge branch 'obsd-master'
Conflicts:
	server.c
2017-02-14 13:55:16 +00:00
nicm
4c2a78029d Collected cells may still need to be extended for RGB colours. 2017-02-13 16:05:30 +00:00
nicm
921880e00b Add not delete the event if more to write. 2017-02-10 15:39:43 +00:00
nicm
d22c15107b Don't use a bufferevent for the tty, so we can keep better track of what
is being written and when.

Also a manpage typo fix from jmc@.
2017-02-10 12:59:18 +00:00
nicm
c6a3446398 Instead of numbering session groups, give them a name which may be given
to -t instead of a target session. Also allow them to contain only one
session.
2017-02-09 15:04:53 +00:00
nicm
8de4c15dfa Document refresh-client -C. 2017-02-09 14:49:00 +00:00
Nicholas Marriott
c75cced07d Add to TODO. 2017-02-09 14:40:30 +00:00
Thomas Adam
96ad1d7779 Merge branch 'obsd-master' 2017-02-09 14:01:18 +00:00
nicm
b1fa3e25e4 Break the message storage function into its own function, useful for
debugging.
2017-02-09 12:09:33 +00:00
Thomas Adam
cb50a51127 Merge branch 'obsd-master' 2017-02-09 12:01:12 +00:00
nicm
b7ddfb39f3 Don't lie about the default size in the man page. 2017-02-09 12:00:42 +00:00
nicm
ddb3750c8b Combining characters need a full flush. 2017-02-09 10:09:14 +00:00
Thomas Adam
79409dc1cc Merge branch 'obsd-master' 2017-02-09 10:01:18 +00:00
nicm
fd6e46596d When an ordinary (not collected) cell is received, we need to flush any
delayed scrolling before drawing it.
2017-02-09 09:33:15 +00:00
Thomas Adam
743f772bef Merge branch 'obsd-master' 2017-02-09 02:01:17 +00:00
Thomas Adam
be033b1ed0 Merge branch 'obsd-master' 2017-02-09 00:01:12 +00:00
nicm
1811dc5271 Another helper function to write to terminal and log. 2017-02-08 23:53:03 +00:00
nicm
2f854969ff Do not adjust region lower by pane offset when scrolling up, it is
already an absolute position.
2017-02-08 22:42:07 +00:00
Thomas Adam
130b77edc7 Merge branch 'obsd-master' 2017-02-08 18:01:17 +00:00
nicm
05802a6fe3 window_copy_pagedown shouldn't reset the mode anymore, instead let the
caller do it so it can free the marks. Problem reported by attila at
stalphonsos dot com.
2017-02-08 17:33:51 +00:00
nicm
e100d465da Add support for scroll up escape sequence (CSI S) and use it when
possible instead of sending individual line feeds.
2017-02-08 17:31:09 +00:00
nicm
13a0b6bb3f Collect sequences of printable ASCII characters and process them
together instead of handling them one by one. This is significantly
faster. Sequences are terminated when we reach the end of the line, fill
the internal buffer, or a different character is seen by the input
parser (an escape sequence, or UTF-8).

Rather than writing collected sequences out immediately, hold them until
it is necessary (another screen modification, or we consume all
available data). This means we can discard changes that would have no
effect (for example, lines that would just be scrolled off the screen or
cleared). This reduces the total amount of data we write out to the
terminal - not important for fast terminals, but a big help with slow
(like xterm).
2017-02-08 16:45:18 +00:00
nicm
d4b006b9fa Fix clear start of line. 2017-02-08 16:18:20 +00:00
Thomas Adam
e09625e38b Merge branch 'obsd-master' 2017-02-08 16:01:17 +00:00
nicm
7475165cd8 Some other tidying bits. 2017-02-08 15:49:29 +00:00
nicm
ac1f294bb9 Add a helper to store a cell, and some tidying. 2017-02-08 15:41:41 +00:00
nicm
96b66f8fc3 Remove unnecessary duplicate check. 2017-02-08 15:24:48 +00:00
nicm
713f3b05f3 Improve some of the logging on resize. 2017-02-08 13:53:32 +00:00
Nicholas Marriott
9af5f3ff81 Give an example, from Timothee Cour. 2017-02-08 11:52:42 +00:00
Thomas Adam
a9a0039be4 Merge branch 'obsd-master' 2017-02-08 10:01:22 +00:00
nicm
cb80901d33 Log size of output buffer as well. 2017-02-08 08:54:45 +00:00
nicm
9cc02d1498 Trying to avoid the occasional newline by saving the last cell on screen
is not actually helping us much and just adds complexity, so don't
bother.
2017-02-08 08:50:10 +00:00
nicm
acb4bd9e56 Tweak how much we expand lines by. 2017-02-08 08:26:35 +00:00
nicm
35a0606de1 Remove event watermarks, don't work well enough to be worth it. 2017-02-08 08:25:12 +00:00
Thomas Adam
5aaf640629 Merge branch 'obsd-master' 2017-02-07 20:01:14 +00:00
nicm
c0a34821c1 Do not clear the scroll region, instead set it to the scroll region we
actually want.
2017-02-07 18:27:46 +00:00
nicm
20f5e377fb Remove a debugging leftover. 2017-02-07 18:06:42 +00:00
Thomas Adam
178289fb4c Merge branch 'obsd-master' 2017-02-07 18:01:13 +00:00
nicm
6ea36afc4b DECSLRM in xterm(1) appears to have a quirk where it can generate an
extra scroll of the entire terminal; issuing DECSTBM first prevents
this. Do that for now.
2017-02-07 17:13:28 +00:00
Thomas Adam
97fd291079 Merge branch 'obsd-master' 2017-02-07 16:01:13 +00:00
nicm
9491a5c1cf Unfortunately DECFRA does not handle default colours properly (it does
not reset colours when in SGR 0), so we can't use it without more
trouble than it is worth. Abandon the idea for now.
2017-02-07 14:33:37 +00:00
Nicholas Marriott
8872a0da8e Merge branch 'master' of github.com:tmux/tmux 2017-02-07 13:41:17 +00:00
Nicholas Marriott
0f5a2c86da Look for libtinfo before libncurses. 2017-02-07 13:40:36 +00:00
Thomas Adam
9f66fb4fd7 Merge branch 'obsd-master' 2017-02-07 00:01:13 +00:00
nicm
d60e585d9e Use DECFRA on VT420 compatible terminals (so, xterm) and ED on all
others for clearing panes.
2017-02-06 22:05:11 +00:00
Thomas Adam
dfdc23d86c Merge branch 'obsd-master' 2017-02-06 22:01:16 +00:00
Thomas Adam
7417e391d5 Merge branch 'obsd-master' 2017-02-06 20:01:15 +00:00
nicm
68e04907de Do not go through the whole attributes setting process if the new cell
is the same as the previous one.
2017-02-06 19:45:23 +00:00
nicm
10e14ae504 Add BCE for clear to start of screen, which was somehow missed. 2017-02-06 19:26:49 +00:00
Thomas Adam
1199f8fc59 Merge branch 'obsd-master' 2017-02-06 16:01:20 +00:00
nicm
e67548dc36 Cancel key table when switching session, unless the key is going to
repeat. Reported by Amos Bird.
2017-02-06 15:00:41 +00:00
Thomas Adam
446177a832 Merge branch 'obsd-master' 2017-02-06 14:01:16 +00:00
Nicholas Marriott
4eabd7ec90 Do not declare program_invocation_short_name because people can't make up their
mind what type it should be.
2017-02-06 13:34:19 +00:00
nicm
d150d9b384 Fix logging of CSI parameters. 2017-02-06 13:25:15 +00:00
nicm
3fd34e70e5 Only redraw the modified character when adding combining characters, not
the whole line.
2017-02-06 13:23:00 +00:00
Nicholas Marriott
50f25a8f05 Merge branch 'master' of github.com:tmux/tmux 2017-02-06 10:06:14 +00:00
Nicholas Marriott
c7c1018e9b Update sys/queue.h from OpenBSD. 2017-02-06 10:05:56 +00:00
Thomas Adam
7bccc82284 Merge branch 'obsd-master' 2017-02-05 02:01:12 +00:00
nicm
d091253a5d Missing va_end, from Anton Lindqvist. 2017-02-04 23:42:53 +00:00
Thomas Adam
e1c283325e Merge branch 'obsd-master' 2017-02-03 22:01:18 +00:00
nicm
5e6a8177e5 Cache status line position to reduce option lookups during output. 2017-02-03 21:01:02 +00:00
nicm
75adf8368a Expand lines more aggressively to reduce rate of allocations. 2017-02-03 20:53:03 +00:00
Thomas Adam
6c333cc486 Merge branch 'obsd-master' 2017-02-03 14:01:13 +00:00
nicm
7d23d019c0 Add a window or pane id "tag" to each format tree and use it to separate
jobs, this means that if the same job is used for different windows or
panes (for example in pane-border-format), it will be run separately for
each pane.
2017-02-03 11:57:27 +00:00
Thomas Adam
9b1f620aa0 Merge branch 'obsd-master' 2017-02-01 12:01:18 +00:00
nicm
dd0c814779 Implement "all event" (1003) mouse mode but in a way that works. The
main issue is that if we have two panes, A with 1002 and B with 1003, we
need to set 1003 outside tmux in order to get all the mouse events, but
then we need to suppress the ones that pane A doesn't want. This is easy
in SGR mouse mode, because buttons == 3 is only used for movement events
(for other events the trailing m/M marks a release instead), but in
normal mouse mode we can't tell so easily. So for that, look at the
previous event instead - if it is drag+release as well, then the current
event is a movement event.
2017-02-01 09:55:07 +00:00
Nicholas Marriott
9b9a5a292d Merge branch 'master' of github.com:tmux/tmux 2017-01-31 12:52:50 +00:00
Nicholas Marriott
c54a5d9fb3 Add wchar.h to compat.h, from Koichi Shiraishi. 2017-01-31 12:51:53 +00:00
Thomas Adam
d8da761d54 Merge branch 'obsd-master' 2017-01-31 00:01:12 +00:00
nicm
3408595f77 When a flag option is used in a format, it should use the number form
not string.
2017-01-30 21:41:17 +00:00
Thomas Adam
9094f01c6b Merge branch 'obsd-master' 2017-01-30 00:01:13 +00:00
nicm
b6099f31ea Add -n to break-pane. 2017-01-29 22:10:55 +00:00
Thomas Adam
4b482c95c3 Merge branch 'obsd-master' 2017-01-28 18:01:12 +00:00
nicm
54309cc25d Do not clear the key table when changing session on a client, so that
switch-client and friends work with bind -n.
2017-01-28 16:11:27 +00:00
Nicholas Marriott
503af3df54 This link is better. 2017-01-26 19:57:16 +00:00
Nicholas Marriott
b2e909b252 Merge branch 'master' of github.com:tmux/tmux 2017-01-26 19:55:45 +00:00
Nicholas Marriott
a4367b44fb Add ISSUE_TEMPLATE. 2017-01-26 19:55:16 +00:00
Thomas Adam
78c0b96004 Merge branch 'obsd-master' 2017-01-26 02:01:12 +00:00
nicm
776ce8a9d5 Clear option before adding to array if no -a, reported by Michael
Nickerson.
2017-01-25 23:50:51 +00:00
Nicholas Marriott
ea70e68a51 -paths.h. 2017-01-25 16:39:02 +00:00
Nicholas Marriott
0f9354eec2 Bad merge. 2017-01-25 16:38:13 +00:00
Thomas Adam
21d8f77a0d Merge branch 'obsd-master' 2017-01-25 16:01:13 +00:00
nicm
163732e89f Revert previous for now, it will break TERM=screen. 2017-01-25 14:36:08 +00:00
nicm
0a63ab4f0f If xterm-keys is on, use xterm(1) style keys for Home and End as well as
modified keys.
2017-01-25 14:24:54 +00:00
Nicholas Marriott
3e495b4001 compat/* should not include tmux.h. 2017-01-25 13:49:01 +00:00
Thomas Adam
418ab1a553 Merge branch 'obsd-master' 2017-01-24 22:01:13 +00:00
nicm
ffc28a7765 Fix set -u on array options. 2017-01-24 20:24:54 +00:00
nicm
4b2821ff98 Make update-environment an array as well. 2017-01-24 20:15:32 +00:00
nicm
b77dd75b57 Convert terminal-overrides to an array option. 2017-01-24 20:05:15 +00:00
nicm
16e43d6a42 Remove some lies about terminal-overrides from tmux.1. 2017-01-24 20:01:34 +00:00
Thomas Adam
f38a6bbd81 Merge branch 'obsd-master' 2017-01-24 20:01:12 +00:00
nicm
126d364abe server-info can become an alias rather than a command. 2017-01-24 19:59:19 +00:00
nicm
85338bb75f Add support for custom command aliases, this is an array option which
contains items of the form "alias=command". This is consulted when an
unknown command is parsed.
2017-01-24 19:53:37 +00:00
nicm
61fce272ea If given an array option without an index either show or set all items,
and support -a for array options. Allow the separator for set to be
specified in the options table (will be used for backwards compatibility
later).
2017-01-24 19:11:46 +00:00
Thomas Adam
f1282a683d Merge branch 'obsd-master' 2017-01-24 14:01:15 +00:00
Nicholas Marriott
c68ea386d1 pty.c needs compat.h. 2017-01-24 13:34:08 +00:00
nicm
3d74e89a39 Shorten a long line, and don't leak buffer in paste_add if size is zero. 2017-01-24 13:28:33 +00:00
Nicholas Marriott
a3d5bfcece Define away pledge() on !OpenBSD. 2017-01-23 12:27:58 +00:00
Nicholas Marriott
1ebe79dd62 Use forkpty() except on OpenBSD. 2017-01-23 12:26:06 +00:00
Thomas Adam
b3a724f30c Merge branch 'obsd-master'
Conflicts:
	Makefile
	tmux.c
2017-01-23 12:20:43 +00:00
nicm
98e7fbb2ac Open /dev/ptm before pledge() and save it to be used for PTMGET later
(this means inlining forkpty()).

ok deraadt
2017-01-23 10:09:43 +00:00
Thomas Adam
d2eab39ffa Merge branch 'obsd-master' 2017-01-22 20:01:12 +00:00
Nicholas Marriott
aa70f28069 Merge branch 'master' of github.com:tmux/tmux 2017-01-22 19:14:10 +00:00
Nicholas Marriott
acf331f7f1 Add b64_pton as well. 2017-01-22 19:12:15 +00:00
nicm
4ede35c48c Accept the OSC 52 escape sequence inside tmux to add a new buffer, from
harry dot gindi at live dot com.
2017-01-22 19:00:01 +00:00
Thomas Adam
c17b0a202a Merge branch 'obsd-master' 2017-01-20 16:01:11 +00:00
nicm
46572ba904 Print error rather than fatal() if tcgetattr() fails, which is much more
useful to user.
2017-01-20 14:02:33 +00:00
Nicholas Marriott
61af9d7cc2 Look for ncursesw as well as ncurses, based on a change from Bert van Hall. 2017-01-19 15:31:22 +00:00
Nicholas Marriott
b98b4e23a3 Put version in log in portable tmux. 2017-01-18 17:35:41 +00:00
Nicholas Marriott
7e4908f751 If --enable-{utf8proc,utempter} is given, do not build without it. 2017-01-18 14:32:50 +00:00
Nicholas Marriott
787f9de5d8 vis.h comes from compat.h. 2017-01-18 12:16:14 +00:00
Thomas Adam
044999ce6d Merge branch 'obsd-master' 2017-01-18 12:01:11 +00:00
nicm
faa0570309 Plain stravis() because it will mangle UTF-8 characters, so add
utf8_stravis() which calls our existing utf8_strvis() and use it instead
2017-01-18 10:08:05 +00:00
Thomas Adam
6d37984f4f Merge branch 'obsd-master' 2017-01-18 10:01:12 +00:00
nicm
4bb5a1d6a7 Run arguments through vis() as well when printing them. 2017-01-18 10:00:50 +00:00
nicm
649c0d8e91 Do not reset idx, it has just been set. 2017-01-18 08:43:21 +00:00
nicm
373541104b options_match needs to explicitly check for user options. 2017-01-18 08:40:50 +00:00
Thomas Adam
64c486ae81 Merge branch 'obsd-master' 2017-01-17 02:01:11 +00:00
nicm
6b6b0e91d0 Correctly handle -style options without all of a corresponding -fg/-bg/-attr. 2017-01-16 23:45:08 +00:00
Nicholas Marriott
c0346701df Fix VIS_DQ check. 2017-01-16 18:20:50 +00:00
Thomas Adam
7e110b9d99 Merge branch 'obsd-master' 2017-01-16 15:36:02 +00:00
Nicholas Marriott
f20e3ee62c We need VIS_DQ in vis.h as well. 2017-01-16 15:01:14 +00:00
nicm
ef15b4195f Revert WIP parts of previous I didn't mean to commit yet. 2017-01-16 14:52:25 +00:00
nicm
68db958477 getopt() has a struct option so just return to using options_entry. 2017-01-16 14:49:14 +00:00
Nicholas Marriott
997b11741c Remove vis.h which comes from compat. 2017-01-16 12:09:04 +00:00
Thomas Adam
7b60645732 Merge branch 'obsd-master' 2017-01-16 00:01:10 +00:00
Thomas Adam
c9fcb76651 Merge branch 'obsd-master' 2017-01-15 22:01:11 +00:00
nicm
52847a9518 It is silly for cmd_list_parse to return an integer error when it could
just return NULL.
2017-01-15 22:00:56 +00:00
nicm
3054846143 -q flag now needs to be checked in a couple more places. 2017-01-15 20:50:34 +00:00
nicm
2b0bc9f1c5 Major tidy up and rework of options tree and set-option/show-options
commands this pushes more of the code into options.c and ties it more
closely to the options table rather than having an unnecessary
split. Also add support for array options (will be used later). Only
(intentional) user visible change is that show-options output is now
passed through vis(3) with VIS_DQ so quotes are escaped.
2017-01-15 20:48:41 +00:00
nicm
404214b0ac Remove unused quiet option. 2017-01-15 20:16:22 +00:00
nicm
a3cf995017 Append needs to go old,new not new,old... 2017-01-15 20:14:36 +00:00
Thomas Adam
4f077fe62c Merge branch 'obsd-master' 2017-01-14 20:01:13 +00:00
nicm
e06efab9da killp -a should not kill the window if only one pane. 2017-01-14 18:53:08 +00:00
Thomas Adam
780dd7ac82 Merge branch 'obsd-master' 2017-01-13 14:01:13 +00:00
Thomas Adam
2311bbd28a Merge branch 'obsd-master' 2017-01-13 12:01:12 +00:00
nicm
08d21936e4 options_get_style return const too. 2017-01-13 11:58:49 +00:00
nicm
22a528905d Make options_get_string return const string. 2017-01-13 11:56:43 +00:00
nicm
95950bf668 Add -E to detach-client to exec a command to replace the client instead
of exiting it, useful if tmux wasn't exec'd itself. From Jenna Magius.
2017-01-13 10:12:12 +00:00
Thomas Adam
d4cb178249 Merge branch 'obsd-master' 2017-01-12 16:01:13 +00:00
nicm
24cba5907b Simplify appending to string options. 2017-01-12 15:36:35 +00:00
Thomas Adam
1eb9500644 Merge branch 'obsd-master' 2017-01-12 12:01:10 +00:00
nicm
dad3090d32 Put all palette functions together in the file. 2017-01-12 10:15:55 +00:00
Thomas Adam
4a76861925 Merge branch 'obsd-master' 2017-01-12 02:01:11 +00:00
nicm
9b6aeacdc0 aixterm colours can be used if -2 is given, as well as if TERM tells us
the terminal has >=16 colours.
2017-01-12 00:30:41 +00:00
nicm
0752fdaf6a Erm the aixterm colours should start at 8, not 7. 2017-01-12 00:24:28 +00:00
nicm
9e786030df Fix setting the palette of aixterm colours (90-97). 2017-01-12 00:19:32 +00:00
Thomas Adam
33ebb9ec39 Merge branch 'obsd-master' 2017-01-12 00:01:13 +00:00
nicm
74c40d04ea Be less aggressive about turning margins off. 2017-01-11 23:10:04 +00:00
nicm
3bb14001b9 Add some missing special keys to key_string_lookup_key, fix a mouse
check in server_client_handle_key, and tweak a comment.
2017-01-11 22:36:07 +00:00
Thomas Adam
d87ab0cadf Merge branch 'obsd-master' 2017-01-11 18:01:13 +00:00
nicm
bf6a5c056d Add a format for terminal type. 2017-01-11 16:09:57 +00:00
nicm
7497ecd979 Use a macro for looking up tty types. 2017-01-11 16:05:46 +00:00
Thomas Adam
0d19d78fff Merge branch 'obsd-master' 2017-01-11 16:01:16 +00:00
nicm
458b6eb600 Some tidying and tweaks to options code. 2017-01-11 14:56:44 +00:00
Thomas Adam
8f79b079cd Merge branch 'obsd-master' 2017-01-10 22:01:14 +00:00
Thomas Adam
db8dff6814 Merge branch 'obsd-master' 2017-01-10 20:01:12 +00:00
nicm
5526627558 Minor tidying in a couple of commands. 2017-01-10 19:45:55 +00:00
Nicholas Marriott
ba35e8f292 15 minutes is not 1800 seconds, but just remove lock-after-time because it won't work for Linux folks without additional configuration 2017-01-10 19:33:22 +00:00
Nicholas Marriott
2283f19876 -temacs-copy should now be -Tcopy-mode 2017-01-10 19:31:34 +00:00
Nicholas Marriott
152bfa02f0 Merge branch 'master' of github.com:tmux/tmux 2017-01-10 19:27:23 +00:00
Nicholas Marriott
a5c89a1802 Change around the example .tmux.conf to show some newer features. 2017-01-10 19:26:54 +00:00
nicm
aa4de2d4b2 Need to escape ; twice because the command list parser will eat one,
reported by Theo Buehler.
2017-01-10 18:10:24 +00:00
Thomas Adam
570943beb7 Merge branch 'obsd-master' 2017-01-10 14:01:12 +00:00
Thomas Adam
1e12e1d843 Merge branch 'obsd-master' 2017-01-10 12:01:10 +00:00
nicm
5ea7a00eba Quote backslash as well for %%%. 2017-01-10 11:58:30 +00:00
nicm
e78142232f Some manpage fixes: rephrase a convoluted sentence, make the names of
some keys more standard, and use Ql instead of Dq.
2017-01-10 10:08:59 +00:00
Thomas Adam
628f3ad9f4 Merge branch 'obsd-master' 2017-01-10 10:01:11 +00:00
jmc
40fddfbdd6 avoid unneccessary markup; tweaked and ok nicm 2017-01-10 07:55:48 +00:00
Thomas Adam
2c862b04af Merge branch 'obsd-master' 2017-01-09 22:01:12 +00:00
Nicholas Marriott
36619607ba Add a format for the version. 2017-01-09 21:44:19 +00:00
nicm
d2d984647e Add %if/%endif for conditionals when parsing configuration files, the
argument is a format (the new == and != are useful).
2017-01-09 21:28:56 +00:00
nicm
844f2eacf4 Add simple comparisons in formats: #{==:a,b} and #{!=:a,b} ("a" and "b"
are expanded so can compare formats). And expand the condition to
#{?a,b,c} (the "a" part) if it doesn't work as a simple lookup.

Also add FORMAT_NOJOBS flag to disable jobs in a format.
2017-01-09 21:03:25 +00:00
Thomas Adam
95f5d406e5 Merge branch 'obsd-master' 2017-01-09 20:01:12 +00:00
nicm
561b5c6fdb source-file -q needs to apply to glob(3) too. 2017-01-09 19:29:12 +00:00
nicm
5330a2a85d Run the source-file pattern through glob(3). 2017-01-09 19:27:00 +00:00
Nicholas Marriott
d90fa2ec13 Tweak TODO file. 2017-01-09 17:48:30 +00:00
Thomas Adam
325c85a5c1 Merge branch 'obsd-master' 2017-01-07 18:01:11 +00:00
Thomas Adam
29e64a8c64 Merge branch 'obsd-master' 2017-01-07 16:01:17 +00:00
nicm
c05002b0f2 Add note about ccc and initc so people who want it can see it is
possible.
2017-01-07 15:40:23 +00:00
nicm
314e933914 Add support for the OSC 4 and OSC 104 palette setting escape sequences,
from S Gilles.
2017-01-07 15:28:13 +00:00
Thomas Adam
a3428487a7 Merge branch 'obsd-master' 2017-01-06 14:01:15 +00:00
nicm
cae0fbbe8c Nits found with clang. 2017-01-06 13:26:09 +00:00
nicm
461217d0f0 Incremental search in copy mode (on for emacs keys by default) - much
the same as normal searching but updates the cursor position and marked
search terms as you type. C-r and C-s in the prompt repeat the search,
once finished searching (with Enter), N and n work as before.
2017-01-06 11:57:03 +00:00
Thomas Adam
58642011df Merge branch 'obsd-master' 2017-01-05 10:01:11 +00:00
nicm
9a56671a75 Highlight all occurrences of search string after searching in copy mode. 2017-01-05 09:07:15 +00:00
Thomas Adam
45dbbb78b0 Merge branch 'obsd-master' 2017-01-03 00:01:12 +00:00
nicm
43e8f60bc6 Escape backspace for capture-pane -P, from George Nachman. 2017-01-02 22:42:19 +00:00
Thomas Adam
f5c5847788 Merge branch 'obsd-master' 2016-12-30 16:01:15 +00:00
nicm
1015b124d5 Change the xterm-keys option to default to on, so that tmux will
generate xterm(1) escape sequences for function keys with modifiers.

With the option off most of these keys are ignored by default, except
for ctrl + arrows which use a variant that nothing else seems to use and
I don't remember why we chose. The xterm escape sequences are now the
most common.

Prompted by a question from mpi@.
2016-12-30 13:49:34 +00:00
Thomas Adam
d3328a3b1e Merge branch 'obsd-master' 2016-12-28 12:01:14 +00:00
nicm
70ba3c147f Fix the prefer unattached session behaviour of
attach-session/switch-client, reported by Thomas Sattle.
2016-12-28 10:34:34 +00:00
Nicholas Marriott
af56e50f74 utempter is no longer the default, and mention ncurses. 2016-12-20 16:28:11 +00:00
Thomas Adam
00445ebadd Merge branch 'obsd-master' 2016-12-14 20:01:11 +00:00
nicm
e36f932f62 Fix up winlink lists after swap-window. 2016-12-14 17:38:59 +00:00
Thomas Adam
dda701d95f Merge branch 'obsd-master' 2016-12-12 02:01:27 +00:00
nicm
b851c628f4 -N without arguments needs to set prefix count for the mode command, so
that M-1 etc work. Reported by Theo Buehler.
2016-12-11 22:55:25 +00:00
Thomas Adam
a64b7cfe5d Merge branch 'obsd-master' 2016-12-10 00:01:11 +00:00
nicm
bee95bf378 Spacing nits. 2016-12-09 21:39:27 +00:00
Thomas Adam
75135ded09 Merge branch 'obsd-master' 2016-12-09 00:01:12 +00:00
nicm
2a7b4bb017 Fix send-keys with UTF-8. 2016-12-08 22:15:37 +00:00
Thomas Adam
d3ede11212 Merge branch 'obsd-master' 2016-12-08 00:01:10 +00:00
nicm
5819d2a9d7 Do not clear the prompt when a message is shown, just leave it around and
return to it when the message is finished.
2016-12-07 23:03:04 +00:00
Thomas Adam
b9fa8f12d7 Merge branch 'obsd-master' 2016-12-07 10:01:12 +00:00
nicm
5ea143f521 Only skip moving the cursor if it is already in the last position _on
the same line_, fixes redraw bug reported by patrick keshishian.
2016-12-07 09:16:55 +00:00
nicm
a8f3ad4487 Make prefix work in all tables (except the prefix table). Users who want
to avoid this can set prefix to "none" and bind send-prefix
themselves. Allows C-b t be bound in the copy mode tables again, pointed
out by millert@.
2016-12-07 09:16:13 +00:00
Thomas Adam
6749a30a6e Merge branch 'obsd-master' 2016-11-30 14:01:11 +00:00
nicm
1a6156d8fd Fix check for cursor at end of line. 2016-11-30 13:20:02 +00:00
Thomas Adam
1fccfd7be5 Merge branch 'obsd-master' 2016-11-29 14:01:11 +00:00
nicm
6b46c62bb4 Make send -N work for all keys, not just in copy mode. From Artem Fokin. 2016-11-29 12:54:46 +00:00
Thomas Adam
d7837cca52 Merge branch 'obsd-master' 2016-11-28 20:01:10 +00:00
nicm
9fc925ac51 When comparing ocy to orlower in tty_cmd_cell, there is no need to add
yoff (because they are both already relative to the pane). Also fix some
other minor nits.
2016-11-28 17:50:00 +00:00
Thomas Adam
2864a31311 Merge branch 'obsd-master' 2016-11-24 20:01:10 +00:00
nicm
6f8cedb1bc The mouse valid flag needs to be correct before we fire the dragging
callback, so move the callback outside of server_client_check_mouse and
use a new special key code to indicate it.
2016-11-24 18:45:45 +00:00
Thomas Adam
a02d95a313 Merge branch 'obsd-master' 2016-11-24 16:01:11 +00:00
nicm
84319aa8f0 If in the middle of a drag, don't use an invalid key, just use
KEYC_MOUSE as a placeholder. Reported by Artem Fokin.
2016-11-24 14:38:55 +00:00
nicm
0d1be2e328 Fix so that we work out the right pane from mouse events - we were doing
so too early, before the mouse event was necessarily valid, so could end
up using the pane from the previous mouse event, or the active pane.

It is important that we use the right pane now that different panes can
have different key tables (for copy mode).

Fixes problem reported by Greg Hurrell.
2016-11-24 13:46:50 +00:00
nicm
7e6c2cb238 Make the selection able to exist independent of the cursor position, so
that it is not affected by scrolling. If MouseDragEnd1Pane is bound to
the new "stop-selection" command:

    bind -Tcopy-mode MouseDragEnd1Pane stop-selection

A selection made with the mouse will stay as it is after button 1 is
released. (It also works bound to a key.)

From Artem Fokin.
2016-11-24 13:38:44 +00:00
Thomas Adam
8a8001350d Merge branch 'obsd-master' 2016-11-23 18:01:19 +00:00
nicm
6de466cf8b For mouse keys, use the mouse pane as the default current pane. 2016-11-23 17:01:24 +00:00
nicm
24916f2f6e Error on invalid modifier keys. 2016-11-23 16:44:42 +00:00
Thomas Adam
442e49f51c Merge branch 'obsd-master' 2016-11-17 12:01:10 +00:00
nicm
3cf19d6dd0 Key running commands for #() by the unexpanded command, and run them
again if the expanded form changes (otherwise at most once per second as
usual). Fixes issues reported by Gregory Pakosz.
2016-11-17 10:06:08 +00:00
Thomas Adam
759953cb8d Merge branch 'obsd-master' 2016-11-16 14:01:11 +00:00
nicm
ddf7ac5ae4 Fix calculation of whether we need a region for drawing a cell (only if
full width and at the edge of the region), otherwise clear the region entirely.
2016-11-16 13:31:22 +00:00
Thomas Adam
06fd3b00ff Merge branch 'obsd-master' 2016-11-16 12:01:11 +00:00
nicm
a8e2d851fe Don't error if renaming a session to its current name, from shik dot
chen at gmail dot com.
2016-11-16 11:41:17 +00:00
nicm
81f1d625af Do not stop dragging when the wheel is pressed, from Artem Fokin. 2016-11-16 11:37:16 +00:00
Thomas Adam
0f5b7814b5 Merge branch 'obsd-master' 2016-11-16 10:01:10 +00:00
nicm
5636d38a9d Initialize modeprefix to 1 properly in window_pane_create, from Artem Fokin. 2016-11-16 09:22:16 +00:00
Thomas Adam
12c49fa3bd Merge branch 'obsd-master' 2016-11-16 02:01:11 +00:00
nicm
e88b74350f The target validity check used window_pane_visible but that may be false
if the pane is zoomed, so instead add a new function to just check if
the pane is actually on screen (most commands still want to accept panes
invisible by zoom). Also reject panes outside the window for various
special targets. Problem reported by Sean Haugh.
2016-11-16 00:24:03 +00:00
Thomas Adam
1afe9e98de Merge branch 'obsd-master' 2016-11-15 16:01:10 +00:00
nicm
c34a79b152 Turn on margins, with a couple of fixes (only limit to the pane for line
feeds, and do not move cursor to end for full width panes).
2016-11-15 15:17:28 +00:00
nicm
d81a5c630f And of course I just find a bug, disable previous for now. 2016-11-15 14:08:27 +00:00
nicm
0ace779cde Initial attempt to make use of left and right margins if the terminal
supports them (that is, if it advertises itself as a VT420 - probably
just xterm). These are the vertical equivalent of the scroll region and
allow much faster scrolling of panes that do not take up the full width
of the terminal.
2016-11-15 14:02:32 +00:00
Thomas Adam
fe7d9af331 Merge branch 'obsd-master' 2016-11-15 12:01:18 +00:00
nicm
9fe43d6acb Add copy-pipe-and-cancel, from Artem Fokin. 2016-11-15 09:53:23 +00:00
Thomas Adam
9908681ba8 Merge branch 'obsd-master' 2016-11-14 18:01:13 +00:00
nicm
afbf0d42a7 rotate-window needs to unzoom, problem reported by Sean Haugh. 2016-11-14 16:27:12 +00:00
Thomas Adam
7177eeaa42 Merge branch 'obsd-master' 2016-11-12 20:01:10 +00:00
nicm
db2412e2ac Apply the right fix for run -b, used the wrong diff before. 2016-11-12 19:05:53 +00:00
nicm
b7398a4918 Do not execute commands for a client until it has identified, fixes
problem reported by Frank Terbeck.
2016-11-12 19:04:41 +00:00
Thomas Adam
afdef6d122 Merge branch 'obsd-master' 2016-11-11 12:01:11 +00:00
nicm
36f8fa316d Do not crash with run-shell -b and no window pane available, reported by
Sergei Dyshel.
2016-11-11 11:37:25 +00:00
Thomas Adam
13f1a922e1 Merge branch 'obsd-master' 2016-11-04 20:01:11 +00:00
nicm
f947d25c9d Do not try to set the CHANGED flag on windows with no active pane, fixes
problem reported by Nelo-T Wallus.
2016-11-04 18:56:25 +00:00
Thomas Adam
1de107c405 Merge branch 'obsd-master' 2016-11-04 16:01:11 +00:00
nicm
353439acee enum values need to fit in 32 bits; we only use enum for numbering and
Unicode characters fit in 24 bits, so we can leave key_code as 64 bits
and change KEYC_BASE down to 0x10000000.
2016-11-04 14:47:38 +00:00
Nicholas Marriott
a44024a795 Note about TERM. 2016-11-04 13:18:09 +00:00
Thomas Adam
15b6774f9b Merge branch 'obsd-master' 2016-11-02 14:01:10 +00:00
nicm
382e09bed1 Make an empty state on error rather than leaving something partially
created (which now is now a fatal() later).
2016-11-02 13:35:36 +00:00
Thomas Adam
5da94182ae Merge branch 'obsd-master' 2016-11-01 10:01:10 +00:00
nicm
c83feeb6f8 Clear window alert flags after setting winlink alert flags, fixes problem
reported by Tommy Allen.
2016-11-01 09:07:18 +00:00
Nicholas Marriott
178894b0fe Do not force symbols to width 1, from Yen Chi Hsuan. 2016-10-28 19:58:14 +01:00
Nicholas Marriott
4dbbcff72b Merge branch 'master' of github.com:tmux/tmux 2016-10-27 18:28:53 +01:00
Nicholas Marriott
4aa5dd0ee0 Add a CONTRIBUTING file with some information on opening issues. 2016-10-27 18:28:21 +01:00
Thomas Adam
b6f00a3945 Merge branch 'obsd-master' 2016-10-26 14:01:13 +01:00
nicm
abea17afd9 Buffer name can be NULL, check before strdup(). 2016-10-26 11:48:07 +00:00
Thomas Adam
f523fddf6a Merge branch 'obsd-master' 2016-10-25 10:01:09 +01:00
nicm
99946aaaaf Do not handle activity or silence alerts in the current window, reported
by jasper@.
2016-10-25 07:24:10 +00:00
Thomas Adam
5f9ba2f223 Merge branch 'obsd-master' 2016-10-21 16:01:11 +01:00
nicm
8084a2c9e6 Add %%% to substitute with quotes escaped (convert " to \"). Use this
for the prompts in copy mode. Fixes problems with jumping to ' reported
by Theo Buehler.
2016-10-21 13:51:59 +00:00
Nicholas Marriott
b951f0621c Put AM_* back, but this time do a dance in configure.ac so that we can keep
using CFLAGS for the tests.
2016-10-19 15:20:21 +01:00
Thomas Adam
28a31201d3 Merge branch 'obsd-master' 2016-10-19 12:01:11 +01:00
nicm
99c262b7d0 Do not have a default binding for C-b in copy-mode-vi or it conflicts
with the default prefix. Reported by natano@.
2016-10-19 09:24:57 +00:00
nicm
899e629bf0 Alerts are too slow, so rather than walking all sessions and windows,
add a link of winlinks to each window and a pointer to the session to
each winlink. Also rewrite the alerts processing to return to the old
behaviour (alert in any window sets the flag on any winlink).
2016-10-19 09:22:07 +00:00
Thomas Adam
4c6eb6cc2f Merge branch 'obsd-master' 2016-10-19 10:01:10 +01:00
nicm
bc27451e15 Move session-create hook out of session_create so it works with grouped sessions. 2016-10-19 08:17:11 +00:00
Nicholas Marriott
1fbb7f1a41 Merge branch 'master' of github.com:tmux/tmux 2016-10-18 23:23:49 +01:00
Nicholas Marriott
3742f66abb Revert the AM_* change, I can't find a way to make AC_CHECK_HEADER use
LIBEVENT_CFLAGS.
2016-10-18 23:19:08 +01:00
Thomas Adam
3a6beea064 Merge branch 'obsd-master' 2016-10-18 22:01:12 +01:00
nicm
e0e9a54a32 Clear cell entry with grid_default_entry not grid_default_cell. 2016-10-18 19:52:49 +00:00
Nicholas Marriott
ec47907772 I don't remember why we have make clean in dist-hook; remove it. 2016-10-18 20:41:31 +01:00
Nicholas Marriott
bd1dc89a5d *.h can go in dist_tmux_SOURCES, from Dilyan Palauzov. 2016-10-18 20:34:18 +01:00
nicm
fb109ae97d xterm-keys was in the wrong place in the list; Dilyan Palauzov. 2016-10-18 19:25:26 +00:00
Nicholas Marriott
66d637be3d Merge branch 'master' of github.com:tmux/tmux 2016-10-18 20:21:13 +01:00
Nicholas Marriott
ba9f47c544 Rename found_debug to enable_debug. 2016-10-18 20:19:24 +01:00
Thomas Adam
9b991a7301 Merge branch 'obsd-master' 2016-10-18 18:01:11 +01:00
Thomas Adam
0041e40ca8 Merge branch 'obsd-master' 2016-10-18 16:01:11 +01:00
nicm
a0998e42b7 Make grid_clear_cell set up the entry properly for 256 and RGB cells. 2016-10-18 14:56:17 +00:00
nicm
cf7289662f Tweak a couple of log statements. 2016-10-18 12:51:26 +00:00
Thomas Adam
8576ecaf32 Merge branch 'obsd-master' 2016-10-18 12:01:10 +01:00
Thomas Adam
b3ab39c4d9 Merge branch 'obsd-master' 2016-10-18 10:01:11 +01:00
nicm
2e5c49a1fd Give each item on queue a name for better logging. 2016-10-18 08:46:43 +00:00
nicm
8763bced76 Zero dirty count after flushing. 2016-10-18 08:39:18 +00:00
nicm
c2f88373e7 Store the right size in the pipe offset for pipe-pane. 2016-10-18 07:38:16 +00:00
Nicholas Marriott
7d5fd5fcd0 Preserve existing AM_CPPFLAGS and AM_LDFLAGS values. 2016-10-17 21:51:21 +01:00
Nicholas Marriott
f6c49cecc1 One extra empty line not in OpenBSD, and tweak a #define style. 2016-10-17 19:25:45 +01:00
Nicholas Marriott
7ba845297f CFLAGS/CPPFLAGS/LDFLAGS -> AM_*, requested by Dilyan Palauzov. 2016-10-17 19:14:56 +01:00
Nicholas Marriott
733185d0a9 Can use enable_* rather than adding our own found_* variables, from Dilyan Palauzov. 2016-10-17 19:09:38 +01:00
Thomas Adam
d54e990c4f Merge branch 'obsd-master' 2016-10-17 00:01:11 +01:00
nicm
fe106842c8 Use notifys for alerts too. 2016-10-16 22:18:04 +00:00
nicm
41e633acf5 Use the notify name string instead of going via an enum and change
existing hooks to use notifys instead.
2016-10-16 22:06:40 +00:00
Thomas Adam
1a6e696b08 Merge branch 'obsd-master' 2016-10-16 22:01:14 +01:00
Nicholas Marriott
d401340c51 Update TODO. 2016-10-16 20:59:43 +01:00
nicm
d15d54c2c8 Add hook_session and hook_window formats to get information on the
affected session or window when a hook fires. Enable session-created and
session-closed hooks now that that is available.
2016-10-16 19:55:52 +00:00
nicm
3f35b5299f Provide a way for hooks to tag formats onto the commands they fire so
that the user can get at additional information - now used for the
"hook" format, more to come.
2016-10-16 19:36:37 +00:00
nicm
026ad08b56 Notifys can go via the command queue instead of using their own queue. 2016-10-16 19:15:02 +00:00
nicm
b342bd0b46 Mass rename struct cmd_q to struct cmdq_item and related. 2016-10-16 19:04:05 +00:00
Thomas Adam
c67b702588 Merge branch 'obsd-master' 2016-10-16 20:01:10 +01:00
nicm
ddc4512d2e Rewrite command queue handling. Each client still has a command queue,
but there is also now a global command queue. Instead of command queues
being dispatched on demand from wherever the command happens to be
added, they are now all dispatched from the top level server
loop. Command queues may now also include callbacks as well as commands,
and items may be inserted after the current command as well as at the end.

This all makes command queues significantly more predictable and easier
to use, and avoids the complex multiple nested command queues used by
source-file, if-shell and friends.

A mass rename of struct cmdq to a better name (cmdq_item probably) is
coming.
2016-10-16 17:55:14 +00:00
Thomas Adam
3d8efdf310 Merge branch 'obsd-master' 2016-10-16 02:01:11 +01:00
nicm
bfe14b5312 Only use pane with run-shell if -t is given. 2016-10-15 23:06:39 +00:00
Thomas Adam
a15939b502 Merge branch 'obsd-master' 2016-10-15 14:01:10 +01:00
jmc
4fbf564292 zap double .Pp; 2016-10-15 12:34:02 +00:00
Thomas Adam
59d1147469 Merge branch 'obsd-master' 2016-10-15 12:01:14 +01:00
nicm
e7990375cb Give window_create and window_create1 better names. 2016-10-15 09:27:52 +00:00
Thomas Adam
623e54788e Merge branch 'obsd-master' 2016-10-15 02:01:12 +01:00
nicm
3f138dc40c Rename a function for consistency and some spacing nits. 2016-10-15 00:12:58 +00:00
nicm
63b2547a02 Fire hooks on the simple notifys (window-renamed and session-renamed),
the complicated ones get no hooks for now (more to come).
2016-10-15 00:09:30 +00:00
nicm
9b3ae84993 Drain notifys once at the end of the server loop instead of doing it
from the end of every command queue (which could be nested).
2016-10-15 00:01:01 +00:00
Thomas Adam
3d2686a236 Merge branch 'obsd-master' 2016-10-15 00:01:10 +01:00
nicm
ed971268be Add CMD_AFTERHOOK flag to the easy commands that don't need any special handling. 2016-10-14 22:14:22 +00:00
nicm
d413a945ac Don't make assumptions about line wrap on !xenl terminals, means that
using a wrong TERM without xenl is not so broken if used on a sensible
terminal.
2016-10-14 21:48:00 +00:00
Thomas Adam
9d58febc8f Merge branch 'obsd-master' 2016-10-14 22:01:11 +01:00
Thomas Adam
33fbf82ac0 Merge branch 'obsd-master' 2016-10-14 20:01:13 +01:00
nicm
1721d1994e source-file and some other commands can recurse back into cmdq_continue,
which could potentially free the currently running command, so we need
to take a reference to it in cmdq_continue_one.

Fixes problem reported by Theo Buehler.
2016-10-14 18:41:53 +00:00
nicm
0ec18e537d Missing flags in capture-pane, and tweak choose-tree text. From Dilyan Palauzov. 2016-10-14 17:40:47 +00:00
Thomas Adam
117737c6ca Merge branch 'obsd-master' 2016-10-14 02:01:14 +01:00
Thomas Adam
a7ce19347a Merge branch 'obsd-master' 2016-10-14 00:01:13 +01:00
nicm
4289a1ebfa Trying to do hooks generically is way too complicated and unreliable and
confusing, particularly trying to automatically figure out what target
hooks should be using. So simplify it:

- drop before hooks entirely, they don't seem to be very useful;

- commands with special requirements now fire their own after hook (for
  example, if they change session or window, or if they have -t and -s
  and need to choose which one the hook uses as current target);

- commands with no special requirements can have the CMD_AFTERHOOK flag
  added and they will use the -t state.

At the moment new-session, new-window, split-window fire their own hook,
and display-message uses the flag. The remaining commands still need to
be looked at.
2016-10-13 22:48:51 +00:00
Nicholas Marriott
5d2288b22a Update TODO. 2016-10-13 22:40:20 +01:00
nicm
7a1a01feef Remove the set-remain-on-exit option, it was always a hack and can now
be done with hooks instead.
2016-10-13 21:37:03 +00:00
Nicholas Marriott
e6f7180af1 tmux no longer uses openat() so we can remove the compatibilty function. 2016-10-13 22:17:29 +01:00
Thomas Adam
ad5a561adb Merge branch 'obsd-master' 2016-10-13 22:01:12 +01:00
nicm
4179b42424 Add support for BCE (background colour erase). This makes various escape
sequences (notable EL and ED but also IL, DL, ICH, DCH) create blank
cells using the current background colour rather than the default
colour.

On modern systems BCE doesn't really have many benefits, but most other
terminals now support it, some (lazy) applications rely on it, and it is
not hard to include now that we have pane background colours anyway.

Mostly written by Sean Haugh.
2016-10-13 20:27:27 +00:00
Nicholas Marriott
f691d46a16 Update TODO. 2016-10-13 21:14:33 +01:00
nicm
1bd08f903b Remove mention of key tables than no longer exist. 2016-10-13 20:09:19 +00:00
Thomas Adam
6270392d04 Merge branch 'obsd-master' 2016-10-13 12:01:11 +01:00
nicm
4d9e6ea310 Some improvements and bug fixes for hooks:
- Prepare the state again before the "after" hooks are run, because the
  command may have killed or moved windows.

- Use the hooks list from the newly prepared target, not the old hooks
  list (only matters for new-session really).

- Correctly detect an invalid current state and ignore it in
  cmd_find_target ("killw; swapw").

- Change neww, new, killp, killw, splitw, swapp, swapw to update the
  current state (used if no explicit target is given) to something more
  useful after they have finished. For example, neww changes it to the
  newly created window.

Hooks are still relatively new and primitive so there are likely to be
more changes to come.

Parts based on bug reports from Uwe Werler and Iblis Lin.
2016-10-13 10:01:49 +00:00
nicm
05dac2e42c -f missed from splitw usage, from Felix Rosencrantz. 2016-10-13 09:06:48 +00:00
Thomas Adam
6551f4bb3b Merge branch 'obsd-master'
Conflicts:
	paste.c
2016-10-13 08:09:47 +01:00
nicm
e0add119ea Compare to see if pane status line has actually changed, not just size, and
do not draw if pane is not visible.
2016-10-12 17:36:52 +00:00
nicm
e83ebf50de Fix a couple of problems with insert mode: flush dirty cells before we
modify the screen, not after; and use grid_view_insert_cells to make
space not grid_move_cells.
2016-10-12 15:43:51 +00:00
nicm
40253048ca bind-key -c has gone, remove from man page, and unused table declarations. 2016-10-12 15:26:37 +00:00
nicm
c484c5a2a1 Drop the edit mode key tables and just use fixed key bindings for the
command prompt.
2016-10-12 14:50:14 +00:00
nicm
4160df4ca4 Redraw selection in tty_draw_line, so it appears when redrawing whole
pane. Reported by Theo Buehler.
2016-10-12 13:24:07 +00:00
nicm
68bebe1fb7 The repeat prompt in both emacs and vi (and the old one in tmux) doesn't
support line editing and instead executes a command as soon as a
non-number key is pressed. Add a -N flag to command-prompt for the same
in copy mode. Reported by Theo Buehler.
2016-10-12 13:03:27 +00:00
Nicholas Marriott
76a9e6f27b NetBSD needs _OPENBSD_SOURCE for reallocarray. 2016-10-12 10:52:04 +01:00
nicm
22a8afee9e Unused variable and missing time.h. 2016-10-12 09:07:58 +00:00
Thomas Adam
12efb40dc5 Linux: #include <time.h> for time() 2016-10-12 09:53:30 +01:00
Thomas Adam
0f7d39c410 Add missing function protype 2016-10-12 09:49:16 +01:00
Thomas Adam
b9dc855016 Merge branch 'obsd-master'
Conflicts:
	format.c
	osdep-openbsd.c
2016-10-12 09:45:49 +01:00
nicm
5c49e1d0c1 Some other stuff that can be local to one file. 2016-10-11 13:45:47 +00:00
nicm
e45401846f Add static in window-*.c and move some internal functions out of tmux.h. 2016-10-11 13:21:59 +00:00
nicm
85d7afaefc Support double and triple clicks (they are cumulative, so double is
fired then triple), and use for select-word and select-line in copy
mode. Inspired by a different solution from Omar Sandoval.
2016-10-11 09:30:36 +00:00
nicm
76d6d3641f Fundamental change to how copy mode key bindings work:
The vi-copy and emacs-copy mode key tables are gone, and instead copy
mode commands are bound in one of two normal key tables ("copy-mode" or
"copy-mode-vi"). Keys are bound to "send-keys -X copy-mode-command". So:

    bind -temacs-copy C-Up scroll-up
    bind -temacs-copy -R5 WheelUpPane scroll-up

Becomes:

    bind -Tcopy-mode C-Up send -X scroll-up
    bind -Tcopy-mode WheelUpPane send -N5 -X scroll-up

This allows the full command parser and command set to be used - for
example, we can use the normal command prompt for searching, jumping,
and so on instead of a custom one:

    bind -Tcopy-mode C-r command-prompt -p'search up' "send -X search-backward '%%'"

command-prompt also gets a -1 option to only require on key press, which
is needed for jumping.

The plan is to get rid of mode keys entirely, so more to come eventually.
2016-10-11 07:23:34 +00:00
nicm
8b804fb589 Support UTF-8 entry into the command prompt. 2016-10-11 07:11:40 +00:00
nicm
a81685bfac Add static in cmd-* and fix a few other nits. 2016-10-10 21:51:39 +00:00
nicm
c426e485e5 Loads more static, except for cmd-*.c and window-*.c. 2016-10-10 21:29:23 +00:00
Thomas Adam
27126f8797 Merge branch 'obsd-master' 2016-10-10 20:01:11 +01:00
nicm
66b5477cc1 Do not allow the opposite pane to resize when dragging with the mouse
because it is not possible to keep the mouse on the border when the
minimum size is reached.
2016-10-10 17:28:30 +00:00
Thomas Adam
226b6a2192 Merge branch 'obsd-master' 2016-10-10 16:01:12 +01:00
nicm
7d4b416fe6 Some more static. 2016-10-10 13:54:47 +00:00
Thomas Adam
215d3f8c0d Merge branch 'obsd-master' 2016-10-09 18:01:10 +01:00
nicm
b8f2dd8237 Make the CLIENT_STATUS flag imply that pane status lines are redrawn if
they are enabled and break the actual screen generation code into a
separate function. Fixes problems reported by Romain Francoise.
2016-10-09 16:24:34 +00:00
Thomas Adam
526e860a7a Merge branch 'obsd-master' 2016-10-09 10:01:12 +01:00
nicm
1db6d6fea6 Pass file/line to new command for if-shell so that errors appear
sensibly.
2016-10-09 08:06:51 +00:00
nicm
48dd250af1 Handle NULL window or session for user options. 2016-10-09 07:58:35 +00:00
nicm
44449b305b Use xsnprintf not snprintf for the prompt in window_copy_write_line
because we don't care if it is truncated to the screen width, we don't
want it to be fatal.
2016-10-09 07:30:28 +00:00
Thomas Adam
fb0b2cd37a Merge branch 'obsd-master' 2016-10-06 00:01:11 +01:00
nicm
30086e504c screen_write_copy tried to be clever and clear the line if it reached
the end of the source, but it was wrong and causes problems that are
only showing up now we are more aggressive about skipping redundant
screen updates. Remove the optimization entirely as more trouble than it
is worth to fix (and it'll have to go when BCE is done anyway).
2016-10-05 22:00:29 +00:00
Thomas Adam
5b8f033e06 Merge branch 'obsd-master' 2016-10-05 14:01:10 +01:00
nicm
f55c991a1b Wrap some long lines in screen-write.c. 2016-10-05 12:36:36 +00:00
nicm
4117a7ed19 Keep buffer creation time and add accessors for it and the order number. 2016-10-05 12:34:05 +00:00
nicm
b4f95c43fc Allow cmd_mouse_at return arguments to be NULL. 2016-10-05 12:32:13 +00:00
Thomas Adam
4740ecbeae Merge branch 'obsd-master' 2016-10-04 02:01:11 +01:00
Thomas Adam
ddfed259f6 Merge branch 'obsd-master' 2016-10-04 00:01:11 +01:00
nicm
1b31d148c9 Remove some dead code in cmd-move-window.c and make a load of local
functions static.
2016-10-03 22:52:11 +00:00
Thomas Adam
6943fbbb81 Merge branch 'obsd-master' 2016-10-03 22:01:12 +01:00
nicm
305c832a97 Document set-hook -u. 2016-10-03 20:58:39 +00:00
nicm
61dfbe702e Remove some redundant checks and make ich/dch consistent. 2016-10-03 19:19:18 +00:00
Thomas Adam
23254f59da Fix typos 2016-09-30 09:50:40 +01:00
Thomas Adam
bb7cc8e8fd Start working on 2.4 2016-09-29 22:00:00 +01:00
Thomas Adam
52869ed182 Release tmux 2.3 2016-09-29 21:54:12 +01:00
Thomas Adam
19104d592b Merge branch 'obsd-master' 2016-09-29 12:01:11 +01:00
nicm
cf7f3a436a Check padding when writing any character with width > 1, in case they
overlap after the first character (for example with cells xy and ab, y
is replacing a).
2016-09-29 08:50:43 +00:00
Thomas Adam
c41916ee16 Merge branch 'obsd-master' 2016-09-28 18:01:11 +01:00
nicm
bb5798aa0e Couple of vasprintf -> xvasprintf. 2016-09-28 14:40:07 +00:00
Thomas Adam
27591570c4 Merge branch 'obsd-master' 2016-09-28 10:01:11 +01:00
nicm
acacb718e5 Rate limit TIOCSWINSZ on a timer to avoid programs getting hammered with
SIGWINCH when the size changes rapidly. To help a problem reported by
Rui Pinheiro.
2016-09-28 08:30:44 +00:00
Thomas Adam
30f2e8ff29 Merge branch 'obsd-master' 2016-09-26 12:01:12 +01:00
nicm
69e980602b Support set -a (append) with user options, suggested by Xandor Schiefer. 2016-09-26 09:02:34 +00:00
Nicholas Marriott
cbde98f67b Merge branch 'master' of github.com:tmux/tmux 2016-09-16 18:09:51 +01:00
Thomas Adam
895f1d93d5 Merge branch 'obsd-master' 2016-09-16 16:01:16 +01:00
nicm
eb50e7a2c8 Swap watermarks from high (4096) to low (128) when we get full buffers
into the read callback several times in succession; swap back when we
see empty buffers several times. This hopefully limits how much programs
that print a lot for a long period can monopolize tmux (like large, fast
compiling), without penalizing programs that print a lot briefly (like
most curses applications). Helps a lot for me, the actual numbers may
need tweaking later.
2016-09-16 13:43:41 +00:00
Nicholas Marriott
6e8f400edc Do not use utf8proc by default. 2016-09-15 20:37:48 +01:00
Thomas Adam
a5b29a1250 Merge branch 'obsd-master' 2016-09-12 18:01:12 +01:00
nicm
2e5584c2b4 Allow repeat count to be specified in mode key tables with bind-key -R,
and set the default repeat count to 5 for WheelUp and WheelDown in
copy-mode.
2016-09-12 15:40:58 +00:00
Nicholas Marriott
060515684d Apple have changed their API again, from Gregory Pakosz. 2016-09-12 11:06:35 +01:00
Nicholas Marriott
c6cdab1f79 Use ncurses OR curses, don't mix header and library. Tested by Rob Paisley. 2016-09-08 19:28:56 +01:00
Nicholas Marriott
3ed0973493 Solaris build fixes from Rob Paisley. 2016-09-08 15:32:15 +01:00
Thomas Adam
f68a908c8a Merge branch 'obsd-master' 2016-09-04 20:01:16 +01:00
nicm
fed1e384ad Add support for performing a full width split (with splitw -f), rather
than splitting the current cell. From Stephen Kent.
2016-09-04 17:37:06 +00:00
Thomas Adam
999c1c771b Merge branch 'obsd-master' 2016-09-03 00:01:14 +01:00
Nicholas Marriott
727ce7e4bb Check for headers for ncurses and libevent as well as libraries. 2016-09-02 22:05:06 +01:00
nicm
2627ab322e Remember the number of lines scrolled into the history (versus cleared
into the history) and when resizing only use scrolled lines and not
cleared lines (which are probably not intended to reappear). From
Chaoren Lin.
2016-09-02 20:57:20 +00:00
Nicholas Marriott
6c94774b70 Add support for using utf8proc with --enable-utf8proc, useful for platforms
(like OS X) where the system implementation is crap. From Joshua Rubin.
2016-09-01 20:40:03 +01:00
Thomas Adam
ae297cb487 Merge branch 'obsd-master' 2016-08-28 02:01:11 +01:00
nicm
537964b92d Kill empty window after moving pane and updating current window, so that
index is still valid before renumber-windows happens. Fixes issue
reported by Eric Pruitt.
2016-08-27 23:35:00 +00:00
Thomas Adam
1bc467fe52 Merge branch 'obsd-master' 2016-08-25 12:01:10 +01:00
nicm
6bf033beae Do not crash if display-message used without a client, issue reported by
Serge Aleynikov, fix from Thomas Adam.
2016-08-25 09:33:14 +00:00
Thomas Adam
88eb302221 Merge branch 'obsd-master' 2016-08-22 22:01:13 +01:00
nicm
43f292b2e0 Two minor fixes from dilyan palauzov. 2016-08-22 20:07:58 +00:00
Thomas Adam
baf1550227 Merge branch 'obsd-master' 2016-08-03 12:01:11 +01:00
nicm
f811127bb6 We only replace the first %%, not multiple (use %2 for second). 2016-08-03 09:08:40 +00:00
nicm
f8cc48a43f Fix minimum size when pane status line is enabled, reported by Y Petremann. 2016-08-03 09:07:02 +00:00
Nicholas Marriott
af38936473 Merge branch 'master' of github.com:tmux/tmux 2016-07-19 10:43:10 +01:00
Nicholas Marriott
0e11036055 Add to .mailmap. 2016-07-19 10:42:44 +01:00
Thomas Adam
a24260bb23 Merge branch 'obsd-master' 2016-07-15 12:01:10 +01:00
nicm
9436a31603 Tweak output of environment logging. 2016-07-15 09:52:34 +00:00
nicm
1718420c48 Log environment to new panes. 2016-07-15 09:28:32 +00:00
nicm
68b1fd0cc6 Wrap some long lines and apply some static. 2016-07-15 09:27:35 +00:00
Thomas Adam
d4eeeb5498 Merge branch 'obsd-master' 2016-07-15 04:01:12 +01:00
nicm
0f73af876f Don't update cells in each block of data read from a pane immediately,
instead track them as change (dirty) and update them once at the end,
saves much time if repeatedly writing the same cell. Also fix comparison
of cells being equal in a few places (memcmp is not enough).
2016-07-15 00:49:08 +00:00
nicm
1fd6ca2260 Instead of representing colours in several different forms with various
cell flags, convert to use an int with flags marking 256 or RGB colours
in the top byte (except in cells, which we don't want to make any
bigger). From Brad Town.
2016-07-15 00:42:56 +00:00
Thomas Adam
2d843b5021 Merge branch 'obsd-master' 2016-07-07 12:01:11 +01:00
semarie
fc118e13a9 tmux: only consider ACCESSPERMS for setting mode on socket_path.
it explicitly removes any S_ISUID|S_ISGID|S_ISTXT bits, instead of letting
pledge(2) silenciously remove them.

ok nicm@ beck@ deraadt@
2016-07-07 09:24:09 +00:00
Nicholas Marriott
25e128d398 Remove duplicate daemon.c and time.h. 2016-06-27 10:57:02 +01:00
Thomas Adam
93f42d360b Merge branch 'obsd-master' 2016-06-16 14:01:11 +01:00
nicm
325cbe90d9 Allow a command to be specified to display-panes, similar to
command-prompt, rather than always just selecting the pane.
2016-06-16 10:55:47 +00:00
Thomas Adam
d35a9ac5f2 Linux: <time.h> 2016-06-16 11:43:05 +01:00
Thomas Adam
1ad7c6b8f8 Merge branch 'obsd-master' 2016-06-15 18:01:11 +01:00
nicm
0c7ddae2ab Add missing buffer_name format, from Awal Garg. 2016-06-15 14:43:06 +00:00
Thomas Adam
5c12230a08 Merge branch 'obsd-master' 2016-06-15 12:01:11 +01:00
nicm
bee3e3e28d Copy mode needs to keep the original grid intact so it can copy from it
if needed, so it disables reading from the pane. This can be problem
with some programs. So make tmux automatically exit all modes after 180
seconds of inactivity and if there is pending output.
2016-06-15 09:13:46 +00:00
nicm
068b8b03ad Add -F to list-commands. 2016-06-15 08:54:11 +00:00
Nicholas Marriott
150c9f3fe0 Add *.dSYM for OS X. 2016-06-15 09:51:08 +01:00
Nicholas Marriott
697b912f26 Merge branch 'master' of github.com:tmux/tmux 2016-06-10 16:38:52 +01:00
Nicholas Marriott
b9c95937ed Add to TODO. 2016-06-10 16:38:40 +01:00
Thomas Adam
1a53e79057 Merge branch 'obsd-master' 2016-06-10 14:01:10 +01:00
Nicholas Marriott
c84ed36719 Spelling, from Josh Soref. 2016-06-10 12:47:15 +01:00
nicm
17e4744459 Spelling error (incrased -> increased), from Josh Soref. 2016-06-10 11:46:15 +00:00
Thomas Adam
fa68d0a16e Merge branch 'obsd-master' 2016-06-06 12:01:10 +01:00
nicm
d9450bfccd Much faster (and smaller) method of mapping RGB colour to an xterm(1)
colour, from Avi Halachmi.
2016-06-06 10:12:58 +00:00
Thomas Adam
cc096ae929 Merge branch 'obsd-master' 2016-06-06 10:01:11 +01:00
Nicholas Marriott
1f75c98f49 Note how to subscribe to ML. 2016-06-06 09:30:39 +01:00
nicm
aba4438013 Cache selected state so that cells going from selected to unselected are not
skipped, reported by Omar Sandoval.
2016-06-06 07:28:52 +00:00
nicm
00cf5fbde6 Insert new panes after the pane being split in the list rather than
always after the active pane. This is more sensible when doing it with
commands rather than keys.
2016-06-06 07:24:31 +00:00
nicm
3c10df4f87 Allow #[] in window-status-separator. 2016-06-06 07:23:36 +00:00
Nicholas Marriott
89c17e44fb Updated link for bash(1) completions. 2016-06-01 00:06:02 +01:00
Nicholas Marriott
20d2a31b40 Update TODO. 2016-05-31 22:13:44 +01:00
Thomas Adam
c7a0f56c71 Merge branch 'obsd-master' 2016-05-30 12:01:13 +01:00
nicm
1921fac814 Cache the window styles and do not look up the window-style options
unless they have changed.
2016-05-30 09:50:20 +00:00
nicm
36ab4c7c49 Do not draw character to screen if it has not changed, and do not save
last character if it won't be used. This (and last few commits) prompted
by a report from Hubert depesz Lubaczewski.
2016-05-30 09:32:24 +00:00
nicm
7d105738b6 Send two cub1 instead of using cub for moving the cursor two left. This
is normally better because using cub1 will be ^H^H (so two bytes) but
cub would be ^[[2D (four).
2016-05-30 09:26:49 +00:00
Nicholas Marriott
5e9412608e No longer set __progname, we have getprogname(). 2016-05-30 10:02:08 +01:00
Thomas Adam
7a2fed494b Merge branch 'obsd-master' 2016-05-28 02:01:10 +01:00
nicm
344a6a6202 Padding cell is always the same so use a static. 2016-05-27 23:06:12 +00:00
nicm
382222af8e Break the save-last-cell code into a separate function (so it can be
called conditionally later).
2016-05-27 23:02:17 +00:00
nicm
9892d80d6f Most of the utf8_data is fixed so simplify utf8_set to use a memcpy. 2016-05-27 22:57:27 +00:00
Thomas Adam
c10d83b4df __progname -> getprogname()
Fix fallout from recent use of getprogname(), which deprecates __progname.
2016-05-27 20:11:32 +01:00
Thomas Adam
a2e0db67cc Merge branch 'obsd-master' 2016-05-27 20:01:11 +01:00
nicm
fcb00a4161 Use getprogname() instead of __progname to make portability easier. 2016-05-27 17:05:42 +00:00
Nicholas Marriott
762fa58ce8 Merge branch 'master' of github.com:tmux/tmux 2016-05-27 18:04:45 +01:00
Nicholas Marriott
cfef0c6658 getprogname() and setproctitle() on Linux. 2016-05-27 18:04:25 +01:00
Nicholas Marriott
f2ec81cf21 Add flag for -pg. 2016-05-27 10:37:06 +01:00
Thomas Adam
20d97eb849 Merge branch 'obsd-master' 2016-05-26 18:01:09 +01:00
nicm
ec7f5305b1 Extend 0x1234 keys form to more bits so that Unicode keys work. 2016-05-26 14:49:48 +00:00
Thomas Adam
95e304d111 Merge branch 'obsd-master' 2016-05-26 14:01:10 +01:00
nicm
cd14ac0486 Just nuke environ instead of trying to unsetenv everything because that
doesn't necessarily work if there is an entry with an empty name.
2016-05-26 12:15:42 +00:00
Thomas Adam
05ec232f3e Merge branch 'obsd-master' 2016-05-24 00:01:09 +01:00
Thomas Adam
266918a580 Merge branch 'obsd-master' 2016-05-23 22:01:10 +01:00
nicm
95a4cc3bce Use a fixed buffer for strftime() because there is no portable way to
tell if the buffer is too small, and an expanding buffer is overkill
anyway.
2016-05-23 20:39:26 +00:00
nicm
e81a92449e Remove unused variable, from Ben Boeckel. 2016-05-23 20:03:14 +00:00
Nicholas Marriott
7411f21c5f Use osdep_event_init() so that LIBEVENT_NOEPOLL and so on are set to turn off
broken event methods. Reported by Suraj N Kurapati.
2016-05-20 07:54:30 +01:00
Nicholas Marriott
2377092a70 Merge branch 'master' of github.com:tmux/tmux 2016-05-13 08:32:46 +01:00
Nicholas Marriott
af25cab11b Fix a typo, issue 406. 2016-05-13 08:31:45 +01:00
Thomas Adam
6cb74f4b7d Merge branch 'obsd-master' 2016-05-12 18:01:10 +01:00
tim
fdd368a294 - Rework load_cfg() error handling a little.
- Add -q to source-file to suppress errors about nonexistent files.

Input and OK nicm@
2016-05-12 16:05:33 +00:00
Thomas Adam
3ec7e3c006 Merge branch 'obsd-master' 2016-05-12 16:01:10 +01:00
nicm
9715c61de0 set-hook needs CANFAIL like the other set commands. 2016-05-12 13:21:56 +00:00
Thomas Adam
e76d44a640 Merge branch 'obsd-master' 2016-05-12 00:01:10 +01:00
nicm
373b13b240 Add on alerts rather than ignoring them if the event has already been
queued, for example bell and activity together. From Marcel Lippmann via
Romain Francoise.
2016-05-11 20:56:58 +00:00
Nicholas Marriott
fe4e9470bb Add --static to PKG_CONFIG rather than replacing it. 2016-05-05 15:18:58 +01:00
Nicholas Marriott
29763d006a Do not mention OpenBSD FAQ. 2016-05-05 13:09:22 +01:00
Thomas Adam
f4648c1ca1 Merge branch 'obsd-master' 2016-05-05 00:01:11 +01:00
nicm
9f045787a5 Fix up a couple of long lines. 2016-05-04 21:29:47 +00:00
Thomas Adam
ce1ec90fcc Merge branch 'obsd-master' 2016-05-03 16:01:10 +01:00
nicm
28e0658fa9 Some tidying of copy mode search functions, based on a diff from Lukasz
Piatkowski (initial changes to help some more to come).
2016-05-03 13:40:50 +00:00
Thomas Adam
96538b489b Merge branch 'obsd-master' 2016-05-01 16:01:11 +01:00
nicm
4a6eca5bd7 Use the same code for half page scrolling as full, from Michal Mazurek. 2016-05-01 13:39:05 +00:00
Thomas Adam
fe4ef307b7 Merge branch 'obsd-master' 2016-05-01 14:01:12 +01:00
nicm
87be2da4e1 Missing format (window_activity_flag) and a missing Ta. 2016-05-01 11:46:12 +00:00
Nicholas Marriott
2b9f8ae485 Update TODO. 2016-04-30 20:04:41 +01:00
nicm
88bd5b15ff tty_client_ready can not be internal to tty.c again. 2016-04-30 18:59:02 +00:00
Thomas Adam
5849c950d0 Merge branch 'obsd-master' 2016-04-30 00:01:10 +01:00
jmc
0c7895076e tweak previous; 2016-04-29 20:57:10 +00:00
Thomas Adam
bc4f725820 Merge branch 'obsd-master' 2016-04-29 20:01:09 +01:00
nicm
975aa3ccd6 Expand client formats (like run-shell), from Stephen M Coakley. 2016-04-29 17:12:12 +00:00
Thomas Adam
55d472a9fe Merge branch 'obsd-master' 2016-04-29 18:01:09 +01:00
nicm
eb8e76d433 Compact a small table into text. 2016-04-29 15:58:52 +00:00
Thomas Adam
ba9f32b464 Merge branch 'obsd-master' 2016-04-29 16:01:12 +01:00
nicm
0509be0740 Add option to include status text in the pane borders. If
pane-border-status is set to "top" or "bottom" (rather than "off"),
every pane has a permanent top or bottom border containing the text from
pane-border-format.

Based on a diff sent long ago by Jonathan Slenders, mostly rewritten and
simplified by me.
2016-04-29 15:00:48 +00:00
nicm
0d84fdd953 Final parts of command hooks, add before- and after- hooks to each command. 2016-04-29 14:05:24 +00:00
nicm
c5443da2d3 The backoff timer is causing no end of trouble with disconnected clients
stopping data in attached ones. So get rid of it and see how we get on
with just a high watermark on each pane.
2016-04-29 13:36:10 +00:00
nicm
5f2bfd9807 Make the grid_cell passed into screen_write_* const. 2016-04-29 13:21:33 +00:00
Thomas Adam
e7de2fe552 Merge branch 'obsd-master' 2016-04-29 14:01:09 +01:00
Nicholas Marriott
65e4c57d3a Only assume width 1 when wcwidth() returns -1 on non-OpenBSD platforms. 2016-04-29 12:47:15 +01:00
Thomas Adam
a9d501e975 Merge branch 'obsd-master' 2016-04-29 12:01:09 +01:00
nicm
97417a1813 Fix keys parsing again to correctly accept Unicode when not prefixed
with Escape.
2016-04-29 10:42:16 +00:00
nicm
7abdfbe20e OpenBSD wcwidth() is sensible and complete so if it returns -1 it means
that a character is not printable, so return to ignoring such
characters.
2016-04-29 09:11:19 +00:00
Thomas Adam
7a02910feb Merge branch 'obsd-master' 2016-04-28 10:01:10 +01:00
nicm
dd8ba0b5a8 memmove() the right size when expanding tree. 2016-04-28 07:20:26 +00:00
nicm
36976ce5e6 After unlock, Update activity time after recalculate_sizes() so that the
session attached flag is correct.
2016-04-28 06:51:56 +00:00
Thomas Adam
bac7a68023 Merge branch 'obsd-master' 2016-04-27 20:01:10 +01:00
nicm
fc70ac4d59 Apply backspace check after working out the actual key, so that M-BSpace
can work.
2016-04-27 16:46:21 +00:00
Nicholas Marriott
fb4585bbe0 Merge branch 'master' of github.com:tmux/tmux 2016-04-27 13:10:55 +01:00
Nicholas Marriott
61f231a496 Add to TODO. 2016-04-27 13:10:34 +01:00
Thomas Adam
55fdaab365 Merge branch 'obsd-master' 2016-04-27 12:01:10 +01:00
nicm
1cedf78284 Add next/previous paragraph, from J Raynor. 2016-04-27 09:39:09 +00:00
nicm
23fdbc9ea6 Loads of platforms appear to have old or broken Unicode character type
information and are missing widths for relatively common Unicode
characters (so mbtowc() works, but wcwidth() fails). So if wcwidth()
returns -1, assume a width of 1 instead of ignoring the character.
2016-04-27 09:36:25 +00:00
Thomas Adam
394589d493 Merge branch 'obsd-master' 2016-04-27 00:01:09 +01:00
nicm
d3546cc85c Simplify next key matching and fix problems with meta and Unicode keys. 2016-04-26 22:19:22 +00:00
Nicholas Marriott
447ead940e No more array.h. 2016-04-26 12:06:35 +01:00
Thomas Adam
7b9c0ced21 Merge branch 'obsd-master' 2016-04-26 12:01:09 +01:00
nicm
fb1c929dc6 Remove last uses of array.h. 2016-04-26 10:18:57 +00:00
Thomas Adam
819ad1a007 Merge branch 'obsd-master' 2016-04-26 10:01:16 +01:00
nicm
d303e55258 Log wcwidth() and mbtowc() failure to make it easier to debug a Unicode
codepoint not appearing.
2016-04-26 07:33:36 +00:00
Thomas Adam
3b833a0c01 Merge branch 'obsd-master' 2016-04-25 20:01:10 +01:00
nicm
6bf2a43e67 Don't overwrite modifiers in the buffer when making UTF-8 strings,
append instead.
2016-04-25 17:05:53 +00:00
Thomas Adam
5391342b08 Start working on 2.3 2016-04-11 01:07:07 +01:00
Thomas Adam
9a4b45dc0f Add CHANGES notes for 2.2 release 2016-04-11 01:00:35 +01:00
Thomas Adam
ad2532c3f4 Merge branch 'obsd-master' 2016-04-04 18:01:11 +01:00
nicm
075c086d29 fatalx() not fatal(). 2016-04-04 16:19:43 +00:00
Nicholas Marriott
7b8dcbaa86 Merge branch 'master' of github.com:tmux/tmux 2016-04-03 23:55:56 +01:00
Nicholas Marriott
75b2c1693e Add --disable-utempter to build without it. 2016-04-03 23:55:38 +01:00
Thomas Adam
1394420c37 Merge branch 'obsd-master' 2016-03-30 16:01:19 +01:00
nicm
ec82fcdfea Bump the listen() backlog up, some people have scripts that run up a lot
of clients quickly.
2016-03-30 13:20:07 +00:00
Nicholas Marriott
5658b628b9 Look for utempter_add_record to be sure we have the new utempter API, the old
utempter API was also using utempter.h.
2016-03-26 20:17:17 +00:00
Nicholas Marriott
b429a00cce Add to TODO. 2016-03-20 08:14:14 +00:00
Thomas Adam
410ccce4a3 Merge branch 'obsd-master' 2016-03-18 16:01:15 +00:00
nicm
312a7a1e62 Make scrolling behaviour more sensible and maintain cursor position, as
if the same had been done line-by-line. From Michal Mazurek.
2016-03-18 14:27:24 +00:00
Thomas Adam
ed598e9fe1 Merge branch 'obsd-master' 2016-03-18 08:01:18 +00:00
nicm
fa97b0a95b Instead of reusing MouseUp at the finish of a drag, add a new key
MouseDragEnd. It can be useful to bind them separately in copy mode.
2016-03-18 07:28:27 +00:00
Nicholas Marriott
3dfc79fb09 Tweak a comment. 2016-03-17 15:11:40 +00:00
Thomas Adam
5fc5c03dad Merge branch 'obsd-master'
Conflicts:
	tmux.c
2016-03-05 17:58:12 +00:00
nicm
0d6de44a37 If setlocale("en_US.UTF-8") succeeds, then don't do the check for UTF-8
locale since if it isn't UTF-8 the system is broken anyway. If it fails,
try "" and check for UTF-8 with nl_langinfo(CODESET) rather than
wcwidth(). Based on a diff from schwarze@, nl_langinfo also suggested by
stsp@.
2016-03-05 16:08:38 +00:00
Thomas Adam
81f78f0da7 Merge branch 'obsd-master' 2016-03-05 10:01:09 +00:00
nicm
c38e0a4bbc Do not use c->cwd or s->cwd if it is NULL, found by Ben Boeckel. 2016-03-05 07:47:52 +00:00
nicm
1f0b317088 Although we always have en_US.UTF-8 on OpenBSD, some platforms do not,
so fall back to setlocale(LC_CTYPE, ""). tmux requires a UTF-8 locale,
so check with wcwidth() on a UTF-8 character after setlocale().
2016-03-05 07:44:31 +00:00
Thomas Adam
6c35d17800 Merge branch 'obsd-master' 2016-03-03 16:01:11 +00:00
nicm
df0983af39 show-* and set-* need to handle a missing target. 2016-03-03 14:15:22 +00:00
nicm
fa81d838da Accept clients as sessions in cmd_find_get_session. 2016-03-03 14:14:46 +00:00
Thomas Adam
45d62482da Merge branch 'obsd-master' 2016-03-03 14:01:10 +00:00
nicm
bcb41a09b3 RGB colours shouldn't be mixed up with aixterm colours, return before
that happens when working out if they are supported.
2016-03-03 12:58:15 +00:00
Nicholas Marriott
9e2fbb31ec +wchar.h 2016-03-02 18:19:13 +00:00
Nicholas Marriott
985504ff2c Merge branch 'next' 2016-03-02 18:16:51 +00:00
Thomas Adam
e304673c65 Merge branch 'obsd-master'
Conflicts:
	utf8.c
2016-03-02 18:10:51 +00:00
nicm
b8a102d26f Handle wcwidth() and mbtowc() failures in better style and drop
characters where we can't find the width (wcwidth() fails) on input, the
same as we drop invalid UTF-8. Suggested by schwarze@.
2016-03-02 15:36:02 +00:00
nicm
d980d965dd Limit x, y and b to 0x7ff for UTF-8 mouse input, suggested by schwarze@. 2016-03-02 15:33:36 +00:00
nicm
f0239a8fe9 Remove some more unused variables, and use RB_FOREACH_SAFE in
key_bindings_unref_table.
2016-03-01 12:06:07 +00:00
nicm
2e4503ad4e Redraw status on mode entry and exit. 2016-03-01 12:05:15 +00:00
nicm
54ea8f74ae When a mouse drag is finished, fire a MouseUp key press, instead of
doing the drag end in code. From Stephen Coakley.
2016-03-01 12:04:43 +00:00
nicm
e647eeb0c9 Remove unused variables, from Michal Mazurek. 2016-03-01 12:02:54 +00:00
nicm
26945d7956 Use system wcwidth() instead of carrying around UTF-8 width tables. 2016-03-01 12:02:08 +00:00
nicm
c7851e0ee7 Fix break-pane synopsis and some other tmux.1 bits. 2016-03-01 11:58:45 +00:00
Nicholas Marriott
a011b67f56 Remove unused variables. 2016-02-19 16:45:35 +00:00
Nicholas Marriott
c3f93e7178 Add to TODO. 2016-02-19 16:45:15 +00:00
Nicholas Marriott
931b1c6d59 Merge branch 'master' into next 2016-02-19 13:37:18 +00:00
Nicholas Marriott
e9d369a09e Fixed fgetln(3) implementation (from Joerg Jung) which does not depend on *BSD
fgets(3) semantics.
2016-02-19 13:35:46 +00:00
Nicholas Marriott
6adf561507 Redraw status on mode entry and exit. 2016-02-19 13:29:59 +00:00
Nicholas Marriott
95adc0e6ba When a mouse drag is finished, fire a MouseUp key press, instead of doing the
drag end in code. From Stephen Coakley.
2016-02-19 13:28:03 +00:00
Nicholas Marriott
02753ba9ea Remove unused variables, from Michal Mazurek. 2016-02-19 13:15:22 +00:00
Nicholas Marriott
acc1090e77 Use system wcwidth() instead of carrying around UTF-8 width tables. 2016-02-19 13:14:17 +00:00
Nicholas Marriott
fc864529f5 Remove malloc_options debug bit (already gone from OpenBSD). 2016-02-19 13:11:10 +00:00
Nicholas Marriott
782dd941da Fire SIGCHLD after utempter_add_record since it probably eats it. 2016-02-17 23:21:58 +00:00
Thomas Adam
ba8290aeae Merge branch 'obsd-master' 2016-02-12 14:01:14 +00:00
nicm
4f6bc0a0a9 Expand client formats in run-shell. 2016-02-12 12:24:52 +00:00
Thomas Adam
f7c8f1ae29 xmalloc: define __bounded__ where necessary 2016-02-07 00:04:46 +00:00
Thomas Adam
ba97ae1737 EXTRA_DIST: add example_tmux.conf / xmalloc.h 2016-02-06 19:04:21 +00:00
Thomas Adam
7669cfb330 Merge branch 'obsd-master' 2016-02-05 12:01:10 +00:00
nicm
bc0c9c7920 Do not wrap cursor at start or end of history, from Michal Mazurek. 2016-02-05 10:20:06 +00:00
Nicholas Marriott
07c23ccc05 Merge branch 'master' of github.com:tmux/tmux 2016-02-05 10:08:55 +00:00
Nicholas Marriott
2130a07b70 Add to TODO. 2016-02-05 10:08:39 +00:00
Thomas Adam
26f899be10 Merge branch 'obsd-master' 2016-02-04 16:01:13 +00:00
nicm
bdb8bb790e Set up -t flag properly when passing new-session -A off to
attach-session, GitHub issue 295.
2016-02-04 14:11:20 +00:00
Thomas Adam
8760f877e1 Merge branch 'obsd-master' 2016-01-31 16:01:09 +00:00
nicm
97882f9ce2 Clear RGB flags during selection. 2016-01-31 14:11:49 +00:00
Thomas Adam
5fce21728e Merge branch 'obsd-master' 2016-01-31 12:01:09 +00:00
nicm
fa64b89ad7 Whoops, need this for the previous reverse trim commit too. 2016-01-31 09:57:41 +00:00
nicm
49e9f93738 Add RGB escape sequences for capture-pane -e. 2016-01-31 09:57:09 +00:00
nicm
8028560f82 Support negative trim values (#{=-10:pane_title}) to trim from the end,
suggested by Kevin Brubeck Unhammer.
2016-01-31 09:54:46 +00:00
nicm
225a384dbb Fix new-session with -t after command flags changes, reported by Michael Graczyk. 2016-01-31 09:52:01 +00:00
Nicholas Marriott
404379049a examples/ has gone, so delete some text about it. 2016-01-29 15:45:32 +00:00
Nicholas Marriott
2a1bb91bf7 Remove old examples in favour of one example configuration file. 2016-01-29 14:53:28 +00:00
Nicholas Marriott
a33bb3e876 Link to the bash(1) completion file from README rather than including it in
examples.
2016-01-29 14:40:30 +00:00
Thomas Adam
8cf1504ba6 Merge branch 'obsd-master' 2016-01-29 12:01:16 +00:00
nicm
427b820426 Support for RGB colour, using the extended cell mechanism to avoid
wasting unnecessary space. The 'Tc' flag must be set in the external
TERM entry (using terminal-overrides or a custom terminfo entry), if not
tmux will map to the closest of the 256 or 16 colour palettes.

Mostly from Suraj N Kurapati, based on a diff originally by someone else.
2016-01-29 11:13:56 +00:00
Nicholas Marriott
1d6bd50343 libevent.org URL. 2016-01-29 10:58:08 +00:00
Nicholas Marriott
ca29dc9abc Update my email address. 2016-01-19 18:07:25 +00:00
Thomas Adam
dc42c35f1f Merge branch 'obsd-master' 2016-01-19 18:01:15 +00:00
nicm
b5b5221c13 Split out getting the current state from the target search so it can be
replaced if we already know the current.
2016-01-19 16:01:30 +00:00
nicm
995af0e2b7 I no longer use my SourceForge address so replace it. 2016-01-19 15:59:12 +00:00
Thomas Adam
5d21faa99c Merge branch 'obsd-master' 2016-01-16 02:01:10 +00:00
nicm
c9815307eb Add hooks for alerts (bell, silence, activity), from Thomas Adam. 2016-01-16 00:36:53 +00:00
Thomas Adam
506adf3764 Merge branch 'obsd-master' 2016-01-15 12:01:11 +00:00
nicm
d551ab8e5c Clear the environment properly by looping until it is empty rather than
looping over it (which may skip entries), from Brad King.
2016-01-15 11:33:41 +00:00
nicm
68d797587e A couple of missing printflike attributes, from Andrey Starodubtsev. 2016-01-15 11:31:47 +00:00
Thomas Adam
ea9873e60e Merge branch 'obsd-master' 2016-01-02 18:01:12 +00:00
nicm
cfb78654c2 clock-mode needs CMD_PANE. 2016-01-02 17:16:25 +00:00
Thomas Adam
051cf5437a Merge branch 'obsd-master' 2016-01-01 10:01:11 +00:00
nicm
311be04d61 Don't rely on a calculation wrapping when applying message-limit, and
break out of the loop early. From Nicolas Viennot.
2016-01-01 08:04:20 +00:00
Thomas Adam
5e59c301b7 Merge branch 'obsd-master' 2015-12-31 20:01:09 +00:00
nicm
7e67db79dc Remove an extra unzoom call which was probably a merge error. 2015-12-31 18:34:47 +00:00
nicm
f84d32ca5e Use saved pipe buffer offset when writing to pipe, from Nicolas Viennot. 2015-12-31 18:14:13 +00:00
Thomas Adam
5dd0e82809 Merge branch 'obsd-master' 2015-12-28 16:01:09 +00:00
nicm
2a1f27eb1a Couple of trivial style nits. 2015-12-28 14:02:52 +00:00
Nicholas Marriott
e15a8a7c46 Keith Smiley is going to maintain the vim syntax file. 2015-12-24 16:59:12 +00:00
Thomas Adam
ed65535c41 Merge branch 'obsd-master' 2015-12-23 02:01:14 +00:00
nicm
60cbdf9ccd Repair switch-client -l and switch-client with a window target. 2015-12-23 00:12:57 +00:00
Thomas Adam
5083e93957 Merge branch 'obsd-master' 2015-12-21 10:01:08 +00:00
nicm
f2ec911b8a Detach the right session with -d. 2015-12-21 09:20:13 +00:00
Nicholas Marriott
c83d6ee0b1 Merge branch 'master' of github.com:tmux/tmux 2015-12-20 11:26:12 +00:00
Nicholas Marriott
83c96d2685 No need to set cwd on Cygwin now, from Yuya Adachi. 2015-12-20 11:25:13 +00:00
Thomas Adam
58b3d66229 Merge branch 'obsd-master' 2015-12-19 10:01:08 +00:00
nicm
bdbec099cc Make input off flag (selectp -d) apply to synchronize-panes too. 2015-12-19 08:43:04 +00:00
Thomas Adam
2ad9caad3f Merge branch 'obsd-master' 2015-12-18 00:01:08 +00:00
nicm
a337403868 As well as setting up the state, actually use it in cmd_find_target. 2015-12-17 23:08:22 +00:00
Thomas Adam
e0cae08c04 Merge branch 'obsd-master' 2015-12-17 00:01:08 +00:00
nicm
99e9a4c786 send-keys -R should reset the input parser to ground state (so it can be
used to escape from, for example, printf '\033]2;').
2015-12-16 22:05:35 +00:00
Thomas Adam
7c94dae702 Merge branch 'obsd-master' 2015-12-16 22:01:08 +00:00
nicm
021c64310d Add infrastructure to work out the best target given a pane or window
alone and use it to add pane_died and pane_exited hooks.
2015-12-16 21:50:37 +00:00
nicm
8eb1a7d5dc showenv and setenv need to be CANFAIL. 2015-12-16 21:47:00 +00:00
Thomas Adam
f7a6482e6b Merge branch 'obsd-master' 2015-12-15 16:01:12 +00:00
nicm
909b737289 Copy state directly rather than dereferencing wl (which could be NULL). 2015-12-15 14:32:55 +00:00
Thomas Adam
e5caf64815 Merge branch 'obsd-master' 2015-12-15 14:01:12 +00:00
nicm
ac9778395f Some hooks API changes to fire a hook while waiting another cmdq and
infrastructure that will be needed soon.
2015-12-15 13:43:07 +00:00
Thomas Adam
1a33ea9671 Merge branch 'obsd-master' 2015-12-15 02:01:14 +00:00
nicm
9d88d82d5e Allow list-keys and list-commands to be run without a running server. 2015-12-15 00:52:17 +00:00
nicm
6f417ec943 We changed somewhat recently to us the pty when tmux was run inside
itself to work out the current pane. This is confusing in many cases
(particularly notable is that "tmux neww\; splitw" would not split the
new window), and the few advantages do not make up for the confusion.

So drop this behaviour and return to using the current window and pane;
keep the pty check but only use it to limit the list of possible current
sessions.
2015-12-15 00:45:02 +00:00
nicm
56d097cfe0 Don't copy marked pane when can just point to it. 2015-12-15 00:11:24 +00:00
Thomas Adam
6ab17e3e15 Merge branch 'obsd-master' 2015-12-15 00:01:08 +00:00
nicm
12da13c9d1 Make the marked pane a cmd_find_state. 2015-12-15 00:00:01 +00:00
nicm
d5999f8b5c Use cmd_find_clear_state instead of an extra function doing the same. 2015-12-14 23:30:58 +00:00
Thomas Adam
bc6137f9e4 Merge branch 'obsd-master' 2015-12-14 01:30:15 +00:00
nicm
a585a1b81a Remove some stray debug code. 2015-12-14 00:32:19 +00:00
nicm
a3129fd4e8 Instead of combined flags for -c, -s, -t, split into different sets
using an enum and simplify the parsing code.
2015-12-14 00:31:54 +00:00
Thomas Adam
5caec3020d Merge branch 'obsd-master' 2015-12-13 23:46:58 +00:00
Thomas Adam
f4adcfa0e2 Merge branch 'obsd-master' 2015-12-13 22:01:08 +00:00
nicm
ecfeee2e82 Use member names in cmd_entry definitions so I stop getting confused
about the order.
2015-12-13 21:53:57 +00:00
nicm
899bee0056 Actually I thought cmd_get_state_client was unnecessary but it will be
needed.
2015-12-13 21:17:37 +00:00
Thomas Adam
00da99f2c4 Merge branch 'obsd-master' 2015-12-13 20:01:09 +00:00
nicm
72948d9f1d -c needs to be able for fail for display-message. 2015-12-13 18:31:47 +00:00
nicm
66d1193a00 Remove an unnecessary function. 2015-12-13 18:27:47 +00:00
nicm
fd47084224 show-options and environment need CANFAIL flag. 2015-12-13 18:15:13 +00:00
Thomas Adam
d37a580085 Merge branch 'obsd-master' 2015-12-13 18:01:11 +00:00
nicm
50f8ead4e6 Don't log an error when doing the first check for move-window. 2015-12-13 17:58:26 +00:00
nicm
9f5aca62a9 Use struct cmd_find_state directly and remove cmd_state_flag, also
change so that winlink is set even if an index is too.
2015-12-13 17:55:14 +00:00
nicm
9b7697db62 Change cmd_find_target to use a state struct from the caller. 2015-12-13 16:44:35 +00:00
nicm
208e2dad1e If command returns error, report it. 2015-12-13 16:11:42 +00:00
Thomas Adam
ae5ddfdc1a Merge branch 'obsd-master' 2015-12-13 16:01:13 +00:00
nicm
ff599f4004 Remove the cmd_find_{session,window,pane,index} functions (which are
just wrappers around cmd_find_target) and just use cmd_find_target
directly.
2015-12-13 15:32:12 +00:00
nicm
9d191a6093 Move logging into cmd_find_target rather than each function. 2015-12-13 15:00:37 +00:00
nicm
4a4daf1303 Instead of every command resolving the target (-t or -s) itself, prepare
the state (client, session, winlink, pane) for it it before entering the
command. Each command provides some flags that tell the prepare step
what it is expecting.

This is a requirement for having hooks on commands (for example, if you
hook "select-window -t1:2", the hook command should to operate on window
1:2 not whatever it thinks is the current window), and should allow some
other target improvements.

The old cmd_find_* functions remain for the moment but that layer will
be dropped later.

Joint work with Thomas Adam.
2015-12-13 14:32:38 +00:00
Nicholas Marriott
92f187d1c2 Need to use pkg-config --static when doing a static build. 2015-12-12 22:04:25 +00:00
Thomas Adam
845a664bb2 Merge branch 'obsd-master' 2015-12-12 20:01:15 +00:00
nicm
5ed17e84fa Add key-table option to set the default key table for a session, allows
different key bindings for different sessions and a few other things.
2015-12-12 18:32:24 +00:00
nicm
6a50cf89b4 Return after changing key table. 2015-12-12 18:28:47 +00:00
nicm
39cf9c9d31 Allow prefix and prefix2 to be set to None to disable (useful if you
would rather bind the prefix in the root table).
2015-12-12 18:19:00 +00:00
Nicholas Marriott
5a5db02b85 Merge branch 'master' of github.com:tmux/tmux 2015-12-11 19:59:08 +00:00
Nicholas Marriott
38cc1a1843 Look for ncurses with PKG_CONFIG, and remove libtinfo because it just causes
confusion.
2015-12-11 19:58:41 +00:00
Thomas Adam
2a6b215328 Merge branch 'obsd-master' 2015-12-11 18:01:11 +00:00
nicm
88bc8f3528 Style nits and line wrapping of function declarations. 2015-12-11 16:37:21 +00:00
nicm
f2be3ad46f Mention {src,dst}-{window,pane} where we define target-{window,pane}. 2015-12-11 16:27:01 +00:00
Thomas Adam
2a3456cd3b Merge branch 'obsd-master' 2015-12-11 16:01:16 +00:00
nicm
bd5918760e We cannot do hooks_find and then hooks_remove because it might have come
from the parent (global) tree, instead make it remove by name like options.

While here, also tidy up a few bits of options and hooks handling (use
RB_FOREACH_SAFE, and a helper function for the free).
2015-12-11 15:46:57 +00:00
Thomas Adam
4909a70174 Merge branch 'obsd-master' 2015-12-11 13:24:45 +00:00
nicm
d7e11d0af7 Check alerts when session changes, from Patrick Palka. 2015-12-11 12:39:47 +00:00
nicm
01831da5f5 Add cmdq as an argument to format_create and add a format for the
command name (will also be used for more later).
2015-12-11 12:27:36 +00:00
Thomas Adam
af8134a6ff Merge branch 'obsd-master' 2015-12-08 10:01:16 +00:00
Nicholas Marriott
a988c36ccb Add to .mailmap, and sort. 2015-12-08 08:46:06 +00:00
nicm
e0f26dcda3 Remove format_create_flags and just pass flags to format_create. 2015-12-08 08:34:18 +00:00
nicm
8f671d3eef Spacing nits. 2015-12-08 08:14:04 +00:00
Thomas Adam
3182728b70 Merge branch 'obsd-master' 2015-12-08 07:12:13 +00:00
Thomas Adam
5862f59ed7 Conflicts:
Makefile
2015-12-08 07:11:09 +00:00
jmc
1f94274b92 Ed was meant to be El; 2015-12-08 06:42:07 +00:00
nicm
d2fb0efcd1 Add hooks infrastructure, basic commands (set-hook, show-hooks) and a
couple of not very useful client hooks. This will eventually let
commands be run at various points and on notifications. Joint work with
Thomas Adam.
2015-12-08 01:10:31 +00:00
mmcc
dbfce2a4d8 Use ^= instead of a verbose alternative. ok nicm@ 2015-12-08 00:51:17 +00:00
Nicholas Marriott
98994a8bb1 termios(4) 2015-12-08 00:49:10 +00:00
Nicholas Marriott
b580a55191 pty(7) -> pty(4) 2015-12-08 00:48:22 +00:00
Nicholas Marriott
ff16836d1d pty is in section 4 2015-12-08 00:47:27 +00:00
Nicholas Marriott
5411033f66 Update tmux.vim from Teubel Gyorgy. 2015-12-07 12:54:34 +00:00
Nicholas Marriott
8383409e88 Merge branch 'master' of github.com:tmux/tmux 2015-12-07 12:51:20 +00:00
Nicholas Marriott
d20a3ef57c Update .mailmap file. 2015-12-07 12:51:06 +00:00
Thomas Adam
bac8c72381 Merge branch 'obsd-master' 2015-12-07 10:01:09 +00:00
nicm
b9563340b7 Fix bell indicators across detach, reported by Torbjorn Lonnemark, diff
from Thomas Adam.
2015-12-07 09:47:41 +00:00
Thomas Adam
8ae9329aa8 Merge branch 'obsd-master' 2015-12-05 14:01:09 +00:00
claudio
0417f1f2be EAGAIN handling for imsg_read. OK henning@ benno@ 2015-12-05 13:18:24 +00:00
Nicholas Marriott
4d5cab4085 Merge branch 'master' of github.com:tmux/tmux 2015-12-03 14:43:33 +00:00
Nicholas Marriott
3cdb2f0bb7 Add to TODO. 2015-12-03 14:43:24 +00:00
Thomas Adam
66bad2e979 Merge branch 'obsd-master' 2015-12-03 00:01:08 +00:00
nicm
7236838dea Mark new active pane changed after pane lost in window, and after
break-pane. Reported by tim@.
2015-12-02 23:09:22 +00:00
Thomas Adam
eb5ee80c74 Merge branch 'obsd-master' 2015-12-01 10:01:13 +00:00
nicm
a785a7f700 Do not deref wp if window_get_active_at returns NULL which can happen on
very large terminals, from Michael Graczyk.
2015-12-01 09:41:03 +00:00
Thomas Adam
742976893e Merge branch 'obsd-master' 2015-11-29 18:01:08 +00:00
guenther
1d331c7e62 Delete a duplicated line
ok jmc@
2015-11-29 17:06:59 +00:00
Thomas Adam
9fe8b28746 Merge branch 'obsd-master' 2015-11-27 15:41:28 +00:00
nicm
6a2ca34216 Do not set a limit on the length of commands when printing them. 2015-11-27 15:06:43 +00:00
Nicholas Marriott
3b83bda29c Add to TODO. 2015-11-25 23:35:24 +00:00
Thomas Adam
a1bc339340 log_open() isn't conditional on proctitle 2015-11-25 16:51:17 +00:00
Thomas Adam
260de2cb5e Remove logfile() 2015-11-25 16:48:47 +00:00
Thomas Adam
890d8da2e3 Merge branch 'obsd-master'
Conflicts:
	log.c
	proc.c
	tmux.c
2015-11-25 16:37:30 +00:00
nicm
ac8678aefe Don't print error if none to print. 2015-11-25 07:58:55 +00:00
nicm
62d3af17f9 Make environ_set va_args and use it to tidy up some calls. Also add a
missing word in manpage (from jmc).
2015-11-24 23:46:15 +00:00
nicm
3ff46b2e43 Shell command from -c doesn't have to be global, pass it as an argument. 2015-11-24 23:22:51 +00:00
nicm
dca93c56e0 Do lock failures slightly better, return a special value so we don't
unlink the wrong thing.
2015-11-24 23:01:51 +00:00
nicm
73e30cbda8 Actually show something (even if it not that helpful) if the server
fails to start (for example if it can't create the socket), rather than
hanging or showing nothing.
2015-11-24 22:45:44 +00:00
nicm
c18fbefe93 Document socket_path format. 2015-11-24 22:27:59 +00:00
nicm
c913fb99b6 Tidy the code that works out the socket path, and just use the full path
in the global socket_path rather than copying it.
2015-11-24 22:27:22 +00:00
nicm
8976dac9e0 Remove malloc_options DEBUG bit. 2015-11-24 22:09:53 +00:00
nicm
bef217b241 Switch a fprintf to a fatal, and wrap some long lines. 2015-11-24 22:04:36 +00:00
nicm
1e2df2d464 Remove the -I part of show-messages which isn't really that useful; the
server start time can now be accessed with a new start_time format (use:
tmux display -p '#{t:start_time}')
2015-11-24 21:52:06 +00:00
nicm
9fd3318dd8 All kill-session -C to clear alerts in all windows, suggested by Aaron
U'Ren.
2015-11-24 21:50:06 +00:00
nicm
4e3015a892 Log some system and libevent information at startup. 2015-11-24 21:32:36 +00:00
nicm
bdbbd9711c Show libevent version in showmsgs -I. 2015-11-24 21:23:44 +00:00
nicm
9cccb8c115 Make the log stuff a bit tidier with some helper functions. 2015-11-24 21:19:46 +00:00
nicm
4ec61bef46 Fix usage of detach-client. 2015-11-24 20:40:51 +00:00
Nicholas Marriott
0a2ef2b932 Merge branch 'master' of github.com:tmux/tmux 2015-11-24 18:50:24 +00:00
Nicholas Marriott
7b085136a7 -sys/queue.h in proc.c, and nuke the unnecessary C++ header guards stuff and
sys/cdefs.h in vis.h (it causes problems on some platforms). Reported by
someone on GitHub, issue 212.
2015-11-24 18:48:07 +00:00
Thomas Adam
534f9e3ab1 Merge branch 'obsd-master' 2015-11-24 10:01:13 +00:00
nicm
b32ce34cf2 Don't allow options in table without scope set. 2015-11-24 09:34:55 +00:00
Thomas Adam
3f47ff6ecd Merge branch 'obsd-master' 2015-11-24 00:01:16 +00:00
nicm
2adf3f42ee Partly revert previous, it is harmless to keep support for UTF-8 mouse
mode inside tmux, just no longer support it for tmux itself.
2015-11-23 23:47:57 +00:00
Thomas Adam
b642b3c8e3 Merge branch 'obsd-master' 2015-11-23 21:21:12 +00:00
Thomas Adam
d63de1e407 Merge branch 'obsd-master'
Conflicts:
	server.c
	tmux.c
2015-11-23 21:20:54 +00:00
nicm
32e510bd70 Remove support for the UTF-8 mouse extension. This was a briefly used,
poor idea that was fairly quickly replaced by SGR mouse input (which is
now widespread). It is impossible to tell the difference between UTF-8
and non-UTF-8 mouse input; since the mouse-utf8 option was removed tmux
has not handled it correctly in any case; and it is ridiculous to have
three different forms of mouse input.
2015-11-23 20:53:09 +00:00
nicm
28e72ae34d Don't leak extddata, memset after freeing it, not before. From Patrick
Palka.
2015-11-22 19:42:57 +00:00
nicm
01a2ddf3f8 Add getpw to pledge, makes tmux work in YP environments, discovered by
matthieu, ok deraadt
2015-11-22 19:41:19 +00:00
tim
4fcc02ee9d If display-time is set to 0, show status messages until a key is pressed;
OK nicm@
2015-11-22 18:28:01 +00:00
Thomas Adam
78a00c845c Merge branch 'obsd-master'
Conflicts:
	tmux.h
2015-11-21 14:24:33 +00:00
Nicholas Marriott
2c482939fd Move tmux.h below system includes. 2015-11-21 08:03:18 +00:00
nicm
933929cd62 Memory leaks and an uninitialized part of utf8_data, from Patrick Palka. 2015-11-20 22:02:54 +00:00
nicm
40fefe2cbc The alerts callback should be fired for bells even if bell-action is
none because it also affects the status line bell indicator (and
bell-action does not). Fixes a problem reported by tim@.
2015-11-20 16:33:46 +00:00
nicm
fce56c56ef Instead of separate tables for different types of options, give each
option a scope type (server, session, window) in one table.
2015-11-20 12:01:19 +00:00
nicm
374e273df5 Only assume pasting with at least two characters, reduces problems for
people who can type ^B c very fast, or who are using tmux inside
something else that buffers.
2015-11-19 22:46:46 +00:00
Thomas Adam
cf688db4b5 Merge branch 'obsd-master' 2015-11-19 16:01:12 +00:00
nicm
98967c5ec9 The activity flag could already be set, so queue the callback always (if
not already queued) rather than only if the flag is being added. Fixes a
problem reported by tim@
2015-11-19 14:55:25 +00:00
Thomas Adam
45b4e337cb Merge branch 'obsd-master' 2015-11-18 18:01:13 +00:00
nicm
82760a9960 Use format_expand_time for display-message. 2015-11-18 16:49:13 +00:00
Nicholas Marriott
c15487318b unused -> __unused. 2015-11-18 16:45:44 +00:00
Nicholas Marriott
a58eaec540 Merge branch 'master' of github.com:tmux/tmux 2015-11-18 16:42:25 +00:00
Thomas Adam
7fe8edc396 Merge branch 'obsd-master' 2015-11-18 16:01:23 +00:00
Nicholas Marriott
8b4b3ff4fc Add __unused, will be needed shortly. 2015-11-18 14:37:08 +00:00
nicm
577c0e3e5a Use __unused rather than rolling our own. 2015-11-18 14:27:44 +00:00
nicm
5a5b950e8b Add s/foo/bar/: prefix for formats to substitute bar for foo. 2015-11-18 14:13:55 +00:00
Nicholas Marriott
f8a1f8843c Add -Wno-attributes. 2015-11-18 14:10:48 +00:00
Nicholas Marriott
9bba26f8c5 Add reallocarray prototype. 2015-11-18 14:09:17 +00:00
Thomas Adam
8fa822b521 Merge branch 'obsd-master' 2015-11-18 14:01:12 +00:00
nicm
64571368dc Sync the entire xmalloc.[ch] with the other users, but with the addition
of xrealloc, xvasprintf, xvsnprintf.
2015-11-18 13:06:54 +00:00
Nicholas Marriott
93742ed5df Merge branch 'master' of github.com:tmux/tmux 2015-11-18 12:55:22 +00:00
Nicholas Marriott
a77960c540 Add reallocarray to compat. 2015-11-18 12:54:29 +00:00
Thomas Adam
4b703d3049 Merge branch 'obsd-master' 2015-11-18 10:01:11 +00:00
nicm
ca5e6bf5f2 Don't update activity time twice for new sessions, and add some logging. 2015-11-18 09:22:29 +00:00
Thomas Adam
44cad8f4ed Merge branch 'obsd-master' 2015-11-17 20:01:12 +00:00
tobias
d0505fd042 Merge xmalloc.[ch] files across base, skipping OpenSSH for now.
ok nicm
2015-11-17 18:25:03 +00:00
Thomas Adam
349a62ed4f Merge branch 'obsd-master' 2015-11-17 00:01:09 +00:00
nicm
775fb562bd 0x7f is a valid key. 2015-11-16 22:57:51 +00:00
Thomas Adam
1686a15fb6 Merge branch 'obsd-master' 2015-11-16 00:01:10 +00:00
nicm
661d0dfac9 Make key_code unsigned long long not uint64_t which is more portable for
printf formats, and move UTF8_SIZE define down to near the rest of the
UTF-8 bits.
2015-11-15 22:50:38 +00:00
Thomas Adam
8213558cc7 Merge branch 'obsd-master'
Conflicts:
	server.c
	tmux.c
2015-11-15 22:49:25 +00:00
nicm
a582b62287 Accidentally turned off pledge, turn it back on. 2015-11-15 14:32:48 +00:00
Thomas Adam
bb820fa761 Merge branch 'obsd-master' 2015-11-14 14:01:08 +00:00
nicm
14d90e4901 The character is an int so use %x not %hhx. 2015-11-14 12:20:19 +00:00
nicm
3db0d50df4 The private use area at U+E000 to U+F8FF is not very useful if it is
width 0, make it width 1 instead.
2015-11-14 12:03:23 +00:00
Thomas Adam
f12d7f0d4b Merge branch 'obsd-master' 2015-11-14 12:01:09 +00:00
nicm
205d15e82d All these return values from utf8_* are confusing, use an enum. 2015-11-14 11:45:43 +00:00
Thomas Adam
7b4b78b419 Merge branch 'obsd-master' 2015-11-14 11:38:52 +00:00
Thomas Adam
7b749eff35 Merge branch 'obsd-master'
Conflicts:
	server.c
	tmux.c
2015-11-14 11:38:30 +00:00
nicm
f401791a56 Rename a variable in utf8_combine for consistency and use 0xfffd for
unknown Unicode.
2015-11-14 11:13:44 +00:00
nicm
dab63b029e Couple of assignments to remove compiler warnings. 2015-11-14 10:57:59 +00:00
nicm
64333e3ef8 Be more strict about invalid UTF-8. 2015-11-14 10:56:31 +00:00
nicm
c56b81a2ce Push stdout and stderr to clients more aggressively, and add an event to
continue if the send fails.
2015-11-14 09:41:06 +00:00
Nicholas Marriott
23266e8e09 Merge branch 'master' of github.com:tmux/tmux 2015-11-14 09:04:41 +00:00
Nicholas Marriott
31d880f751 Update the TODO file. 2015-11-14 09:04:13 +00:00
nicm
908e6bb68f Log more of UTF-8 input. 2015-11-14 08:25:12 +00:00
Thomas Adam
276ca5f04c Merge branch 'obsd-master' 2015-11-13 18:01:13 +00:00
nicm
c4893d8efd Log option names in fatal() for missing option. 2015-11-13 16:06:43 +00:00
Nicholas Marriott
1016f112bf Merge branch 'master' of github.com:tmux/tmux 2015-11-13 16:06:11 +00:00
Nicholas Marriott
b7397bf413 utf8 option is gone. 2015-11-13 16:05:58 +00:00
Thomas Adam
45a10dde95 Merge branch 'obsd-master' 2015-11-13 14:01:10 +00:00
nicm
88aa1c8dc3 Two spacing and spelling nits. 2015-11-13 12:18:52 +00:00
Thomas Adam
e2917b2627 Merge branch 'obsd-master' 2015-11-13 10:43:07 +00:00
Thomas Adam
3df4959f51 Merge branch 'obsd-master'
Conflicts:
	Makefile
2015-11-13 10:42:45 +00:00
nicm
531869bd92 Add window_visible_layout which ignores zoomed panes and use it for
control mode (which needs to know all panes), from George Nachman.
2015-11-13 10:00:26 +00:00
nicm
c5689a5a40 Long overdue change to the way we store cells in the grid: now, instead
of storing a full grid_cell with UTF-8 data and everything, store a new
type grid_cell_entry. This can either be the cell itself (for ASCII
cells), or an offset into an extended array (per line) for UTF-8
data.

This avoid a large (8 byte) overhead on non-UTF-8 cells (by far the
majority for most users) without the complexity of the shadow array we
had before. Grid memory without any UTF-8 is about half.

The disadvantage that cells can no longer be modified in place and need
to be copied out of the grid and back but it turned out to be lot less
complicated than I expected.
2015-11-13 08:09:28 +00:00
Thomas Adam
a7027ed8e5 Merge branch 'obsd-master' 2015-11-13 00:01:15 +00:00
nicm
e71a915412 Rename overly-long utf8data to ud throughout. 2015-11-12 22:04:37 +00:00
Thomas Adam
b2f19c9d06 Merge branch 'obsd-master' 2015-11-12 16:01:09 +00:00
nicm
f2d03f4fdd grid_put_utf8 is unused, remove it. 2015-11-12 14:50:57 +00:00
Thomas Adam
4f88344df3 Merge branch 'obsd-master' 2015-11-12 14:01:14 +00:00
nicm
a209ea3953 Add utf8_padcstr and use it to align columns in list-keys. 2015-11-12 12:43:36 +00:00
jmc
1da7475d0e tweak previous; ok nicm 2015-11-12 12:36:34 +00:00
nicm
d6daf37df4 Tidy utf8.c a little: build table on first use, and make utf8_width take
a u_int rather than splitting and then combining again in utf8_split.
2015-11-12 12:19:57 +00:00
Thomas Adam
5f483499f3 Merge branch 'obsd-master' 2015-11-12 12:01:17 +00:00
nicm
0cc812ae34 tmux is UTF-8, so if $TMUX is set (tmux running in tmux), the client is
UTF-8. Also try to make the existing checks more readable.
2015-11-12 11:24:08 +00:00
nicm
c41673f3fa If we know the terminal outside tmux is not UTF-8, replace UTF-8 in
error messages and whatnot with underscores the same as we do when we
draw UTF-8 characters as part of the screen.
2015-11-12 11:10:50 +00:00
nicm
1b86f520ea Nuke the utf8 and status-utf8 options and make tmux only a UTF-8
terminal. We still support non-UTF-8 terminals outside tmux, but inside
it is always UTF-8 (as when the utf8 and status-utf8 options were on).
2015-11-12 11:09:11 +00:00
nicm
a0f3999ce7 Remove the mouse_utf8_flag format as well. 2015-11-12 11:07:10 +00:00
nicm
69e0b8326a Support UTF-8 key bindings by expanding the key type from int to
uint64_t and converting UTF-8 to Unicode on input and the reverse on
output. (This allows key bindings, there are still omissions - the
largest being that the various prompts do not accept UTF-8.)
2015-11-12 11:05:34 +00:00
Thomas Adam
333da3b64b Merge branch 'obsd-master' 2015-11-12 10:01:09 +00:00
nicm
7062b0e65d Default history-file should be "" not NULL, from Greg Onufe. 2015-11-12 08:19:18 +00:00
Thomas Adam
f2e4aa8d1c Merge branch 'obsd-master' 2015-11-12 00:01:10 +00:00
nicm
00c34df186 Drop mouse-utf8 option and always turn on UTF-8 mouse if the client says
it supports UTF-8.
2015-11-11 23:23:33 +00:00
Thomas Adam
35fd6d134a Merge branch 'obsd-master'
Conflicts:
	utf8.c
2015-11-11 08:14:36 +00:00
nicm
6f3475c6c7 If realpath() fails just try the original path. 2015-11-10 22:33:47 +00:00
nicm
005e462e01 Handle absolute paths properly, and don't use resolved path in
realpath() fails.
2015-11-10 22:29:33 +00:00
nicm
dcdccf8333 Same bug as last commit, but in the other copy of the loop in this file... 2015-11-05 23:32:21 +00:00
schwarze
e9b58d9de4 Update the internal wcwidth(3) table of tmux(1) to match the data
in /usr/src/share/locale/ctype/en_US.UTF-8.src, with one single
exception:  Keep U+00AD SOFT HYPHEN at width 1 rather than moving
it to width 0, a tradition already observed in the old
https://www.cl.cam.ac.uk/~mgk25/ucs/wcwidth.c .
While here, manually rebalance the btree for optimal lookup speed.
OK nicm@
2015-11-05 16:44:25 +00:00
Thomas Adam
896581628d Merge branch 'obsd-master' 2015-11-05 12:01:08 +00:00
nicm
5577535891 Pass through right click if mouse is on, from Patrick Palka. 2015-11-05 11:05:30 +00:00
Thomas Adam
696826913c Merge branch 'obsd-master' 2015-11-03 16:01:11 +00:00
nicm
455284f1c0 Detach the client we are looping over, from Thomas Adam. 2015-11-03 15:07:36 +00:00
Thomas Adam
c975de2e07 Merge branch 'obsd-master'
Conflicts:
	server.c
2015-10-31 23:56:35 +00:00
nicm
ba7fb49fb9 Fall back silently to ~ or / rather than checking -c with access(), this
was the old behaviour.
2015-10-31 14:51:15 +00:00
nicm
b0a99e85b6 Don't shift version out of peerid, it is needed later. 2015-10-31 13:43:38 +00:00
nicm
abb4e9e2fa The output log is only useful once and it means creating a file, so open
it once at startup instead of in every call to tty_open.
2015-10-31 13:12:03 +00:00
Thomas Adam
17f6c3be8e Merge branch 'obsd-master' 2015-10-31 10:01:12 +00:00
nicm
01defc9f49 Because pledge(2) does not allow us to pass directory file descriptors
around, we can't use file descriptors for the working directory because
we will be unable to pass it to a privileged process to tell it where to
read or write files or spawn children. So move tmux back to using
strings for the current working directory. We try to check it exists
with access() when it is set but ultimately fall back to ~ if it fails
at time of use (or / if that fails too).
2015-10-31 08:13:58 +00:00
Thomas Adam
e8bb385d6d Merge branch 'obsd-master' 2015-10-29 10:01:09 +00:00
nicm
45f3cea263 Break version check into a separate function, and limit version to 8 bits. 2015-10-29 09:35:31 +00:00
Thomas Adam
a5e4d3a2d8 Merge branch 'obsd-master' 2015-10-28 12:01:11 +00:00
nicm
bf9c933cae Like options, move the environ struct into environ.c. 2015-10-28 09:51:55 +00:00
Thomas Adam
da1f6fc2c8 Merge branch 'obsd-master'
Conflicts:
	Makefile
	client.c
	server-client.c
	server.c
	tmux.c
	tmux.h
2015-10-27 23:27:26 +00:00
nicm
44657bf932 Move struct options into options.c. 2015-10-27 15:58:42 +00:00
nicm
67c3a014b9 No more TMPDIR. 2015-10-27 14:51:35 +00:00
nicm
07b0ea03c3 Break the common process set up, event loop and imsg dispatch code
between server and client out into a separate internal API. This will
make it easier to add another process.
2015-10-27 13:23:24 +00:00
Thomas Adam
147b5ae514 Merge branch 'obsd-master' 2015-10-27 10:01:13 +00:00
nicm
9952201ca7 Count brackets in #{?...} so that nested conditional formats work, from
Daniel De Graaf.
2015-10-27 09:28:31 +00:00
nicm
17c2c4219d The format callback may not always succeed, so we need to check for
NULL. From Patrick Palka.
2015-10-27 09:18:06 +00:00
nicm
3fc001d0a2 Use copy-mode -et= in WheelUpPane binding, from Patrick Palka. 2015-10-27 09:15:21 +00:00
Thomas Adam
9c69a79f9a Merge branch 'obsd-master' 2015-10-27 00:01:09 +00:00
nicm
640c6fdd5f If a mouse event has no key binding, pass it through to the pane it
happened in, not the active pane like normal key presses. Fixes problems
seen by Enrico Ghirardi.
2015-10-26 23:16:18 +00:00
nicm
380a1ea8ef Default bindings for mouse wheel on status line to change window (like
we had before), from Patrick Palka.
2015-10-26 23:06:18 +00:00
nicm
b85be36d1c Handle unknown keys more gracefully, return a string instead of NULL. 2015-10-26 22:03:04 +00:00
Thomas Adam
54a3ed751e Merge branch 'obsd-master' 2015-10-26 18:01:12 +00:00
nicm
a22fe33aa0 Some extra logging of where keys are actually going. 2015-10-26 17:17:06 +00:00
Thomas Adam
e95df0bc39 Merge branch 'obsd-master' 2015-10-26 02:01:09 +00:00
jmc
c582f7d177 space before punctuation; 2015-10-26 00:15:37 +00:00
Thomas Adam
ca29903c82 Merge branch 'obsd-master' 2015-10-26 00:01:10 +00:00
nicm
e65306d8e7 Extend the modifiers allowed before formats: as well as the existing
#{=10:...}  length limit, add #{t:...} to convert a time_t format to a
string, #{b:...} for basename and #{d:...} for dirname. Remove all the
foo_string time formats as they can now be replaced by "t:", for example
#{window_activity_string} becomes #{t:window_activity}.
2015-10-25 22:29:17 +00:00
Nicholas Marriott
c14fb5b633 -sys/types.h 2015-10-25 09:38:08 +00:00
Thomas Adam
ad437f13d5 Add missing headers for getpid() 2015-10-25 09:34:56 +00:00
Thomas Adam
4681415a15 Merge branch 'master' of github.com:tmux/tmux 2015-10-25 09:33:11 +00:00
Nicholas Marriott
7930cb54c0 ifdef __OpenBSD__ around pledge(). 2015-10-25 09:31:46 +00:00
Thomas Adam
91f53d590b __OpenBSD__ around pledge() 2015-10-25 09:31:07 +00:00
Thomas Adam
3e0d31c4e9 Merge branch 'obsd-master' 2015-10-25 09:22:20 +00:00
Thomas Adam
4acc8d0ff5 Merge branch 'obsd-master'
Conflicts:
	cmd-find.c
2015-10-25 09:21:37 +00:00
nicm
3faa51a0ca Pass output from jobs through format_expand() so they are expanded again
(this was the previous behaviour).
2015-10-25 08:59:26 +00:00
deraadt
3034a71488 Let's see if anyone screams about not being able to specify $TMPDIR
for their tmux sockets.

(Over the years, I have seen $TMPDIR set up worse than /tmp many times,
and don't know how this practice infected other parts of the system.
Nothing uses tmpdir(3), nor a huge-temporary-file program like sort.)
ok nicm
2015-10-25 07:48:16 +00:00
nicm
2e2b8a95bd Pasting mouse escape sequences is unlikely, so skip them when working
out whether the user is pasting.
2015-10-23 23:46:36 +00:00
nicm
26a55ddcf9 Remove some unnecessary checks before free(). 2015-10-23 16:30:15 +00:00
nicm
1a4ddfa8a7 If $TMUX is set, and we are unsure about the session, use it. 2015-10-23 16:29:07 +00:00
nicm
5383b047d1 tmux can call pledge() in main with large set and then reduce it
slightly in the server to "stdio rpath wpath cpath fattr unix recvfd
proc exec tty ps".
2015-10-23 16:07:29 +00:00
nicm
14da999408 Format for scroll position, from Jorge Morante. 2015-10-23 16:02:21 +00:00
nicm
63a3fd3c0f Use tty_term_flag not _has for XT, and make -2 force direct use of
256-colour escape sequences (so setaf/setab can be bypassed if needed).
2015-10-23 15:52:54 +00:00
Thomas Adam
8c39813665 Merge branch 'obsd-master' 2015-10-22 14:01:12 +01:00
nicm
3ebcf25149 If the pane is still on all_window_panes but not actually connected to
window or session (which can happen if it is killed during a command
sequence and something else has a reference), fall back to the best
effort. Fixes "tmux killw\; detach" for Rudis Muiznieks.
2015-10-22 11:23:00 +00:00
nicm
a05c27a7e1 Unzoom before -LRUD, reported by Andy Weidenbaum. 2015-10-22 11:19:31 +00:00
Thomas Adam
6bc3902f5d Merge branch 'obsd-master' 2015-10-22 12:01:09 +01:00
nicm
c2c2d44c72 Log identify messages. 2015-10-22 11:00:51 +00:00
nicm
515dfea4b7 This should not be changed. 2015-10-22 10:48:30 +00:00
nicm
31fd071faa Rename shutdown to exit. 2015-10-22 10:46:24 +00:00
Thomas Adam
0bfa615997 Merge branch 'obsd-master' 2015-10-21 16:01:08 +01:00
nicm
60ca29df64 client_key_table was missing. 2015-10-21 13:14:36 +00:00
Thomas Adam
35f582583a Merge branch 'obsd-master' 2015-10-21 14:01:09 +01:00
nicm
ddbc4a0f6c By popular demand add a default binding for mouse wheel up to scroll
into history (if the mouse is, on of course).
2015-10-21 11:13:47 +00:00
Thomas Adam
1f4a5b5dfe Merge branch 'obsd-master' 2015-10-21 00:01:19 +01:00
nicm
076034345a Use client pointer not file descriptor in logging. 2015-10-20 21:12:08 +00:00
Thomas Adam
af2d48f4d2 Merge branch 'obsd-master' 2015-10-20 16:01:11 +01:00
nicm
8c8cddbe02 The table could change when retrying so don't save it at start of
server_client_handle_key.
2015-10-20 14:19:27 +00:00
Thomas Adam
bbdc08780c Merge branch 'obsd-master' 2015-10-18 22:01:08 +01:00
nicm
174a2ad731 Pass current directory as a string rather than a file descriptor because
pledge doesn't let us pass directory file descriptors.
2015-10-18 20:42:42 +00:00
Thomas Adam
7c78b2b756 Start working on tmux 2.2 2015-10-18 18:19:08 +01:00
Thomas Adam
310f0a960c Update for 2.1 release. 2015-10-18 18:10:43 +01:00
Nicholas Marriott
6c3ade76df __OpenBSD__ around pledge(). 2015-10-17 20:16:12 +01:00
Thomas Adam
487285b325 Merge branch 'obsd-master' 2015-10-17 20:01:08 +01:00
nicm
9c601ebde8 Add pledge "stdio unix sendfd proc exec tty" to tmux client process,
"sendfd" is dropped after first message from the server.
2015-10-17 18:30:43 +00:00
Nicholas Marriott
0273d809d0 Merge branch 'master' of github.com:tmux/tmux 2015-10-17 18:48:45 +01:00
Nicholas Marriott
e0527d7731 time.h is not needed now tzset() is not in log.c. 2015-10-17 18:48:22 +01:00
Thomas Adam
a204595e4c Merge branch 'obsd-master' 2015-10-16 10:01:09 +01:00
nicm
cf89abb013 Don't free after calling paste_set but do after evbuffer_add, from Theo
Buehler.
2015-10-16 07:43:29 +00:00
Nicholas Marriott
c06c14fb29 Some header fixes. 2015-10-15 21:42:17 +01:00
Nicholas Marriott
716550021e Merge branch 'master' of github.com:tmux/tmux 2015-10-15 09:25:21 +01:00
Nicholas Marriott
f199fb6a2b Fix available_fds when there is no AF_INET, reported by Mathieu Arnold. 2015-10-15 09:24:25 +01:00
Thomas Adam
f69e09a67e Merge branch 'obsd-master' 2015-10-11 02:01:14 +01:00
guenther
241fd72f75 Userspace doesn't need to use SUN_LEN(): connect() and bind() must accept
sizeof(struct sockaddr_un), so do the simple, portable thing

ok beck@ deraadt@
2015-10-11 00:26:23 +00:00
Thomas Adam
5b13dafbab Merge branch 'obsd-master' 2015-10-07 12:01:21 +01:00
nicm
7340d5adfd Couple of memory leaks in error paths, from Frederik Vanderstraeten. 2015-10-07 09:52:58 +00:00
Thomas Adam
7120ab2f16 Merge branch 'obsd-master' 2015-09-26 02:01:16 +01:00
nicm
695a591f8e Adding colors=256 to *256color* was always pretty stupid and now it
won't work (without adding setaf@:setab@ too).
2015-09-25 23:30:24 +00:00
nicm
03d7dba5d8 If the terminal has colors=256, only try to use setaf/setab if they
exist, reported by Filipe Brandenburger.
2015-09-25 23:30:12 +00:00
Thomas Adam
20c3adca41 Merge branch 'obsd-master' 2015-09-25 18:01:09 +01:00
nicm
28f23f18e9 Free the history when it is cleared, based on a diff from Carlo Cannas. 2015-09-25 15:53:07 +00:00
Thomas Adam
b0372840e7 Merge branch 'obsd-master' 2015-09-24 14:01:10 +01:00
nicm
2a62917444 Don't leak fd and path on failure. 2015-09-24 12:06:20 +00:00
nicm
69ea6b9373 Do not leak log file descriptor. 2015-09-24 12:03:58 +00:00
Thomas Adam
ed17760a52 Merge branch 'obsd-master' 2015-09-24 10:01:09 +01:00
nicm
ddb2d1221b Assign flag not number for flag types (we got away with it so far
because that are a union). From Filipe Brandenburger.
2015-09-24 07:02:18 +00:00
Nicholas Marriott
06d4553a15 Merge branch 'master' of github.com:tmux/tmux 2015-09-23 14:27:11 +01:00
Nicholas Marriott
1caebaa49a Add to TODO. 2015-09-23 14:26:53 +01:00
Thomas Adam
7e9b87f396 Merge branch 'obsd-master' 2015-09-23 00:01:09 +01:00
nicm
dc66795e35 Don't update last session when the session is unchanged, from Sina Siadat. 2015-09-22 21:56:16 +00:00
Thomas Adam
d6d05883ad Merge branch 'obsd-master' 2015-09-21 12:01:11 +01:00
nicm
d5f223a3fe Reset the alerts timer always on activity, from Thomas Adam. 2015-09-21 09:34:52 +00:00
Thomas Adam
983357603a Merge branch 'obsd-master' 2015-09-18 12:01:07 +01:00
nicm
6b709e655e -l should apply to the new not the old pane with -b, from "MadMaverick9"
on GitHub.
2015-09-18 09:55:22 +00:00
Thomas Adam
c624382929 Merge branch 'obsd-master' 2015-09-17 16:01:08 +01:00
nicm
8b5d5dca9f Redraw both src and dst sessions in break-pane. 2015-09-17 14:11:55 +00:00
Thomas Adam
a3bce7a322 Merge branch 'obsd-master' 2015-09-17 00:01:08 +01:00
nicm
c1d0b6a6ee Log when cmdq_continue is called. 2015-09-16 22:41:00 +00:00
nicm
232a0ffc34 Give some variables less silly names. 2015-09-16 22:40:27 +00:00
nicm
ecb257f0ef A few minor style nits. 2015-09-16 22:40:05 +00:00
nicm
d1b73be6e1 Hoist some common code out of both branches of an if/else. 2015-09-16 22:29:30 +00:00
nicm
a4b4b29987 Rename cmd_q dead flag to a general flags bitmask (will be more flags later). 2015-09-16 22:24:54 +00:00
Nicholas Marriott
57ad1f6ddf Merge branch 'master' of github.com:tmux/tmux 2015-09-15 13:57:57 +01:00
Nicholas Marriott
54bd761286 Add BCE to TODO. 2015-09-15 13:57:46 +01:00
Thomas Adam
b5d789a531 Merge branch 'obsd-master' 2015-09-14 16:01:08 +01:00
Nicholas Marriott
166aa97f75 No more $Id$. 2015-09-14 15:59:21 +01:00
Thomas Adam
d47789620b Add missing <time.h> 2015-09-14 14:39:51 +01:00
nicm
16ee4de5df Remove some extra blank lines. 2015-09-14 13:22:02 +00:00
Thomas Adam
4afe26fa82 Merge branch 'obsd-master' 2015-09-14 14:01:09 +01:00
nicm
62bb6e37e0 Should add buffer if no -b. 2015-09-14 12:52:22 +00:00
nicm
216ddf3da5 Move tzset() from log_open to main. 2015-09-14 12:12:24 +00:00
nicm
8da6de3e66 Style nit, int for flags not u_int. 2015-09-14 11:57:22 +00:00
Thomas Adam
74b958ecbe Merge branch 'obsd-master'
Conflicts:
	Makefile
2015-09-14 12:42:19 +01:00
nicm
af16ce6ad9 When the active pane changes, redraw panes if the style has
changed. From Cam Hutchison.
2015-09-14 11:34:50 +00:00
nicm
16efa84838 Make refresh-client force update of jobs, from Sina Siadat. 2015-09-14 10:25:52 +00:00
nicm
901c2eb20a Add copy-mode -e to exit copy mode when scrolling off the bottom, useful
for quick view of history, from Cam Hutchison.
2015-09-13 13:31:40 +00:00
nicm
ede0f2f633 Set woken flag when flushing so that the channel is freed, while here
use the same loop construct for both loops.
2015-09-13 10:45:55 +00:00
nicm
a3de5dbab1 Merge delete-buffer into cmd-set-buffer.c and change the paste buffer
API so it has one paste_free() rather than free_top and free_name
(everywhere that uses it already has the right pointer).
2015-09-11 14:41:50 +00:00
Nicholas Marriott
ef35c9f765 Add --enable-coverage for gcov. 2015-09-11 13:16:35 +01:00
Nicholas Marriott
66c4ed98d6 Fix bad merge. 2015-09-10 14:59:16 +01:00
Nicholas Marriott
eb1084754c Merge branch 'master' of github.com:tmux/tmux 2015-09-10 12:42:25 +01:00
Nicholas Marriott
79e5b62907 osdep_event_init not event_init. 2015-09-10 12:41:49 +01:00
Thomas Adam
1fd756066c Merge branch 'obsd-master' 2015-09-10 12:01:08 +01:00
nicm
cfabe30bec Add session_last_attached time and format, from Sina Siadat. 2015-09-10 08:58:14 +00:00
Thomas Adam
5af2f68a2c Merge branch 'obsd-master' 2015-09-09 14:01:08 +01:00
nicm
67ee995cc1 No need to keep global options around for client which doesn't use them. 2015-09-09 12:09:21 +00:00
Thomas Adam
fe536457cc Fix includes
Let compat/ work out the includes; otherwise works on OpenBSD.
2015-09-06 21:29:36 +01:00
Thomas Adam
76688d2040 Merge branch 'obsd-master'
Conflicts:
	cfg.c
	tmux.c
2015-09-06 20:47:50 +01:00
nicm
aceae73b9a Change wait-for to work when the signal comes before the wait, also use
some helper functions and add some logging.
2015-09-04 12:02:44 +00:00
nicm
82326dcbe2 A couple of style nits. 2015-09-03 14:30:23 +00:00
nicm
6c10fc659a Log pane which received input data. 2015-09-02 17:52:57 +00:00
nicm
38e3baab2a A one line helper function is a little silly. 2015-09-02 17:43:25 +00:00
nicm
8121127606 We no longer need the terminal service class, so don't bother asking for it. 2015-09-02 17:37:54 +00:00
nicm
a45164f2e0 Fix indentation of grid_string_cells_fg. 2015-09-02 17:12:07 +00:00
Nicholas Marriott
2ebef95994 Sync up vis.* for stravis(). 2015-09-01 21:08:19 +01:00
nicm
93b946ee50 Tweak some error messages/comments. 2015-09-01 19:50:09 +00:00
nicm
66a2720c56 Log the whole new input buffer once rather than each byte. 2015-09-01 19:16:00 +00:00
nicm
364a885b0c Pass logging through vis(3). 2015-09-01 19:14:43 +00:00
nicm
fa3d4fab85 Fix a spelling error, sesson -> session. 2015-09-01 18:50:16 +00:00
nicm
69a2d46ee5 Remove dead_clients which is no longer used. 2015-09-01 11:13:39 +00:00
nicm
952ba84611 Work out config file when needed not at startup. 2015-09-01 10:10:59 +00:00
nicm
83157c02d6 Move initial conf load into cfg.c. 2015-09-01 10:01:56 +00:00
nicm
2a836bc306 All the cmd_*_entry declarations do not need to be in tmux.h. 2015-09-01 09:48:34 +00:00
Nicholas Marriott
2c6ea705fd Bring back pane_current_path. 2015-08-31 19:57:37 +01:00
nicm
6a539c00df Path from $TMUX does not need to be global anymore. 2015-08-30 22:56:36 +00:00
nicm
c6e9160c67 Login shell can be a client flag, and move the exec code into client.c. 2015-08-30 22:40:25 +00:00
nicm
dd92b6e83d Event base does not need to be global. 2015-08-30 22:19:07 +00:00
Thomas Adam
29f2120e5b Linux: get_proc_name() -> osdep_get_name() 2015-08-30 21:47:50 +01:00
Thomas Adam
cb89f2f2a1 Merge branch 'obsd-master'
Conflicts:
	Makefile
	format.c
2015-08-30 21:44:01 +01:00
nicm
b87dc608d9 Some style nits and dead assignments. 2015-08-30 15:43:40 +00:00
nicm
5047670693 Remove some old prototypes and unused functions. 2015-08-29 23:55:55 +00:00
nicm
52bbac506c struct args_entry can go into arguments.c. 2015-08-29 23:19:52 +00:00
nicm
373ef850e0 paste_send_pane can be merged into cmd-paste-buffer.c now. 2015-08-29 09:36:46 +00:00
nicm
b569585000 Move struct paste_buffer out of tmux.h. 2015-08-29 09:25:00 +00:00
nicm
b9f0571780 We already loop over the windows in server_client_loop, so don't do it
again in server_loop just to check names.
2015-08-29 08:54:41 +00:00
nicm
b5aaefc727 Move alerts onto events rather than checking every loop. 2015-08-29 08:30:54 +00:00
nicm
5267ce8ff4 Treat entering or leaving a mode as pane changed. 2015-08-29 00:39:18 +00:00
nicm
b7861f34ba Better take on reducing the name timer. Again check for name changes in
the main loop after events that may have changed the pane, but do so at
most once every 500 millis. If the pane changed too soon, use a timer to
ensure that a check happens later.
2015-08-29 00:29:15 +00:00
nicm
73bd816076 Microseconds in log time. 2015-08-29 00:24:44 +00:00
nicm
d9b3133321 Only set default title to hostname on screens that are being used for a
window pane, no point in calling gethostname() for temporary screens.
2015-08-28 17:11:12 +00:00
nicm
5f122af556 Make a few more expensive (ish) formats functions instead of inline. 2015-08-28 17:01:42 +00:00
nicm
983ebb2689 Allow formats to be specified as functions (in the code) so they are
only evaluated on demand rather than each time a format tree is
constructed. Use this for expensive formats like pane_current_command.
2015-08-28 16:46:40 +00:00
nicm
55b8d74561 Revert previous; we do need a timer, until I have a better idea. We
can't do the name check every loop, because that is too expensive, and
we can't make sure it only happens infrequently because we have no idea
when the next change will happen.
2015-08-28 16:10:46 +00:00
nicm
e2100c5f5f We now only checking for name changes when the active pane has changed,
but that can only happen when we have already been woken up by a read
event, so there is no need for a timer, we can just check the changed
flag on the end of that read event (we already loop over the windows to
check for bells etc anyway).
2015-08-28 15:51:48 +00:00
Thomas Adam
486421ceff Merge branch 'obsd-master' 2015-08-28 16:01:09 +01:00
nicm
b0940bdf54 Check changed flag after restarting timer. 2015-08-28 13:26:41 +00:00
nicm
f957db81d9 Remove unused prototypes. 2015-08-28 13:21:25 +00:00
nicm
ed2a486f46 Don't leak name when freeing session, from Kuang-che Wu. 2015-08-28 13:16:03 +00:00
nicm
f6a0f8730e Per-session timers for locking, and remove the global one-second timer. 2015-08-28 13:12:20 +00:00
Thomas Adam
84eabb2658 Merge branch 'obsd-master' 2015-08-28 14:01:11 +01:00
nicm
57cc4d45d5 Make session_update_activity more useful and use it in more places. 2015-08-28 13:01:03 +00:00
nicm
675def0396 Remove the lock-server option which is a bit redundant, it isn't that
different without it.
2015-08-28 12:31:55 +00:00
nicm
6419f66523 Give clock mode its own timer. 2015-08-28 12:25:42 +00:00
nicm
75d10058a4 Run status update on a per-client timer at status-interval. 2015-08-28 12:16:28 +00:00
nicm
18d4802a7b Log time with message. 2015-08-28 12:15:54 +00:00
nicm
b6618b631b Move format job cleanup onto its own timer. 2015-08-28 11:38:27 +00:00
Thomas Adam
31c027a37a Merge branch 'obsd-master' 2015-08-28 12:01:07 +01:00
nicm
ee9f708500 Allow environment variables in #{}. 2015-08-28 10:06:52 +00:00
Thomas Adam
031d7ce840 Merge branch 'obsd-master' 2015-08-28 10:01:08 +01:00
nicm
25faca41eb Error messages should not have a trailing period. 2015-08-28 07:55:43 +00:00
nicm
fc58e44f89 Only do the automatic-rename dance if the pane has changed (seen output,
or new active pane).
2015-08-28 07:49:24 +00:00
Thomas Adam
ce20572ace Merge branch 'obsd-master' 2015-08-25 18:01:07 +01:00
nicm
2ffbd5b5f0 When searching for tabs, start from screen width, fixes out-of-bounds
read found by Kuang-che Wu.
2015-08-25 15:00:05 +00:00
Thomas Adam
429f86397b Merge branch 'obsd-master' 2015-08-25 02:01:16 +01:00
nicm
3219e0314e In grid_duplicate_lines, if the line is empty (cellsize == 0) then clear
the destination celldata pointer rather than leaving a stale copy of the
source pointer (which may later be freed). Fixes a crash found by
Kuang-che Wu.
2015-08-24 22:49:13 +00:00
Thomas Adam
65b45c9c32 Merge branch 'obsd-master' 2015-08-16 12:01:06 +01:00
nicm
58b659a26e Come out of copy mode when history is cleared. 2015-08-16 08:57:34 +00:00
Nicholas Marriott
f5357ed940 Handle \ at EOL from Daniel Hahler. 2015-08-15 09:53:19 +01:00
Thomas Adam
778612d152 Merge branch 'obsd-master' 2015-08-13 18:01:07 +01:00
nicm
46aa92420a right-up should be right-of, also rename the values too. 2015-08-13 15:02:23 +00:00
Thomas Adam
6447404cc2 Merge branch 'obsd-master' 2015-08-12 12:01:09 +01:00
nicm
13b7fd82c1 Rename left/right/up/down relative to active pane to add -of suffix
(left-of/right-of/etc) to remove conflict with left/right meaning
leftmost or rightmost pane. From Ben Boeckel.
2015-08-12 08:55:20 +00:00
Nicholas Marriott
3c9b8a28c6 Merge branch 'master' of github.com:tmux/tmux 2015-08-07 15:08:26 +01:00
Nicholas Marriott
736d8350e9 +history-file, from Ben Boeckel. 2015-08-07 15:06:17 +01:00
Thomas Adam
73b4d098ce Merge branch 'obsd-master' 2015-07-29 14:01:09 +01:00
nicm
5ec3621101 status_out and associated data structures are no longer used. 2015-07-29 11:56:02 +00:00
Thomas Adam
a568aaa0c0 Merge branch 'obsd-master' 2015-07-28 18:01:08 +01:00
nicm
b254115acd Tidy up the way terminals are described and move some structs out of tmux.h. 2015-07-28 15:18:10 +00:00
Thomas Adam
ff18787b2c Merge branch 'obsd-master' 2015-07-27 10:01:08 +01:00
nicm
d33adc4fd0 Make -q suppress ambiguous option warnings too, from Cam Hutchison. 2015-07-27 08:45:45 +00:00
Nicholas Marriott
e4cdc9fa0b Merge branch 'master' of github.com:tmux/tmux 2015-07-24 09:10:21 +01:00
Nicholas Marriott
669059aa19 Fix a warning, from Kosta Zertsekel. 2015-07-24 09:06:15 +01:00
Thomas Adam
18a64ad52d Merge branch 'obsd-master' 2015-07-20 18:01:10 +01:00
nicm
92af3766ec Add an option (history-file) for a file to save/restore command prompt
history, from Olof-Joachim Frahm.
2015-07-20 15:50:04 +00:00
Thomas Adam
dedd9edf7f Merge branch 'obsd-master' 2015-07-20 12:01:07 +01:00
nicm
d4ce210713 Correct the tsl/fsl sequence to ]0 not ]2 (from Marcel Korpel). While
here, Xr xterm and remove some advice about elinks that is better
elsewhere.
2015-07-20 10:34:11 +00:00
Nicholas Marriott
e6facdcb0c Merge branch 'master' of github.com:tmux/tmux 2015-07-19 08:10:07 +01:00
Nicholas Marriott
96dcbe217b Update tmux.vim from Ben Boeckel. 2015-07-19 08:07:55 +01:00
Thomas Adam
e45f42db29 Merge branch 'obsd-master' 2015-07-17 16:01:07 +01:00
nicm
bad8d0fd20 Do not call window_unzoom from window_destroy because it will try to add
a notification which will get confused because the reference count is
already zero and end up back in window_destroy and a double
free. Instead, just destroy the layouts directly. Noticed by Thomas
Adam.
2015-07-17 13:09:07 +00:00
Thomas Adam
b886393042 Merge branch 'obsd-master' 2015-07-17 10:01:09 +01:00
nicm
3192178f15 Initialize client fd to -1 as well, from Bobby Powers. 2015-07-17 06:53:47 +00:00
Nicholas Marriott
8c96e2a6d9 Implement osdep_get_name and osdep_get_cwd for AIX, from J Raynor. 2015-07-15 08:46:35 +01:00
Nicholas Marriott
5ffb869e1a Merge branch 'master' of github.com:tmux/tmux 2015-07-14 08:15:05 +01:00
Nicholas Marriott
bed3069fd7 Add _LINUX_SOURCE_COMPAT on AIX. 2015-07-14 08:14:35 +01:00
Thomas Adam
dcc28434f4 Merge branch 'obsd-master' 2015-07-13 20:01:08 +01:00
nicm
8dcea2cc14 Reset G0/G1 state when resetting everything else with send-keys -R. 2015-07-13 18:45:18 +00:00
nicm
4e637b1b61 Ignore environment variables that are too long to send to the server. 2015-07-13 18:10:26 +00:00
Thomas Adam
07aef38591 Merge branch 'obsd-master' 2015-07-13 18:01:09 +01:00
nicm
e45d624df2 Fix line endings. 2015-07-13 15:51:31 +00:00
nicm
c7374c31c4 Initialize cwd fd to -1 so that we don't close fd 0 if the client is
destroyed before it is changed. Also allow ttyname() to fail. Fixes
problems when running out of file descriptors reported by Bruno Sutic.
2015-07-13 15:49:31 +00:00
nicm
81069f66f9 Add a format to show if client is a control client. From Bruno Sutic. 2015-07-13 15:37:26 +00:00
Thomas Adam
38d4d69639 Merge branch 'obsd-master' 2015-07-13 16:01:09 +01:00
nicm
6308c48efd Add a -s flag to show-environment to output Bourne shell commands a la
ssh-agent. Mostly from Cam Hutchison with some changes by me.
2015-07-13 13:36:29 +00:00
nicm
cc768d77ec Revert to marking lines as wrapped on newlines, fixes problems with
capturep -J.
2015-07-13 13:28:50 +00:00
Nicholas Marriott
73f9f0334c Check for flock in libbsd for AIX, and remove some getopt.h includes. From J
Raynor.
2015-07-13 14:19:50 +01:00
Nicholas Marriott
28c33f67bc Merge branch 'master' of github.com:tmux/tmux 2015-07-12 19:47:47 +01:00
Nicholas Marriott
235e0bd65a Update imsg*.[ch] from OpenBSD, including bzero->memset. 2015-07-12 19:46:58 +01:00
Thomas Adam
9a0ce98c54 Merge branch 'obsd-master' 2015-07-06 16:01:10 +01:00
nicm
b298478435 Update environment with -E when attach-session used on an already
attached session or switch-client used on the current session. From Cam
Hutchison.
2015-07-06 14:24:57 +00:00
Thomas Adam
78723af99f README: Clarify SYNCING is under the ISC 2015-06-28 12:01:19 +01:00
Nicholas Marriott
8b8a007e8e Merge branch 'master' of github.com:tmux/tmux 2015-06-20 08:45:19 +01:00
Nicholas Marriott
8abcea18a2 Remove monitor-content options which have been removed, from Guy Hughes. 2015-06-20 08:43:55 +01:00
Thomas Adam
0ef3e28609 Merge branch 'obsd-master' 2015-06-19 02:01:10 +01:00
nicm
f557c7d8ca Use the SRCDST define for usage. 2015-06-18 23:56:01 +00:00
nicm
b43b13faf9 Use xsnprintf. 2015-06-18 23:55:24 +00:00
nicm
164ba041c9 Remove a stray : and tweak paragraph. 2015-06-18 23:53:56 +00:00
Thomas Adam
86018a3947 Merge branch 'obsd-master' 2015-06-17 22:01:13 +01:00
nicm
85120b37ea Change break-pane to take target and source panes (-t and -s) in line
with other commands, from Thomas Adam.
2015-06-17 19:56:08 +00:00
Thomas Adam
21a2ccc5f1 Merge branch 'obsd-master' 2015-06-17 20:01:12 +01:00
nicm
84f0622c85 Break cmdq_continue inner loop into a helper function. 2015-06-17 17:02:15 +00:00
Thomas Adam
a584e11d6b Merge branch 'obsd-master' 2015-06-17 18:01:07 +01:00
nicm
0ff335961e Move the shuffle code from new-window -a into a function and add a -a
flag for move-window too. From Thomas Adam.
2015-06-17 16:50:28 +00:00
nicm
021cdbe1c0 Use an explicit job state instead of avoid closing our side of the
socketpair and setting it to -1 to mark when the other side is
closed. This avoids closing it while the libevent bufferevent still has
it (it could try to add it to the polled set which some mechanisms don't
like). Fixes part a problem reported by Bruno Sutic.
2015-06-17 16:44:49 +00:00
Thomas Adam
9fdc3a069a Merge branch 'obsd-master' 2015-06-15 14:01:09 +01:00
nicm
d96ab34019 Add window_activity format, from Thomas Adam based on a diff originally
from propos6 at gmail dot com.
2015-06-15 10:58:01 +00:00
Thomas Adam
37005d04a9 Merge branch 'obsd-master' 2015-06-14 12:01:10 +01:00
nicm
29c29e7717 Add a format for client PID (client_pid) and server PID (pid). Diff for
client_pid from Thomas Adam.
2015-06-14 10:07:44 +00:00
Thomas Adam
48a46e066e Merge branch 'obsd-master' 2015-06-10 16:01:08 +01:00
Nicholas Marriott
ba665e24e3 Merge branch 'master' of github.com:tmux/tmux 2015-06-10 15:41:35 +01:00
Nicholas Marriott
dca084e703 Don't leak dotfd if fchdir fails. From ettl dot martin78 at gmail dot com. 2015-06-10 15:39:23 +01:00
nicm
bbc0898060 wp->tty is a char [] not a char * so it can't be NULL. From Thomas Adam. 2015-06-10 12:56:04 +00:00
Thomas Adam
0ff172fabf Merge branch 'obsd-master' 2015-06-09 10:01:10 +01:00
nicm
a412dd616f Fix loop comparison broken in last commit, from Thomas Adam. 2015-06-09 07:07:06 +00:00
Nicholas Marriott
02a848d77c It isn't supposed to... 2015-06-08 09:46:14 +01:00
Thomas Adam
7acc4addb5 Merge branch 'obsd-master'
Conflicts:
	client.c
	tmux.1
	tmux.c
2015-06-07 23:42:25 +01:00
nicm
c4e811e519 Add -E flag when attaching or switching client to bypass
update-environment, from Steven Lu.
2015-06-07 21:39:39 +00:00
Nicholas Marriott
a5c55e4393 Update TODO. 2015-06-07 08:36:03 +01:00
nicm
ed6c036ee3 Use ints for the calculations rather than u_char, they could end up
signed.
2015-06-05 22:50:27 +00:00
nicm
55b96a5bd5 Handle the RGB colour escape sequence (\033[38;2;<r>;<g>;<b>m and 48;2)
like xterm(1) does, by mapping to the nearest in the 256 colour palette.
2015-06-05 22:33:39 +00:00
nicm
1cb073d48e Use fixed colour tables rather than generated and do a quick search for
exact match before doing the distance comparison.
2015-06-05 22:01:17 +00:00
nicm
641a9cd3f5 Similarly, for sessions use a callback to free rather than checking
every loop.
2015-06-05 18:18:32 +00:00
nicm
10e90ae01f Change deref to the more sensible unref, and add a couple I missed before. 2015-06-05 18:06:30 +00:00
nicm
8c93b768e4 Instead of putting dead clients on a list and checking it every loop,
use event_once to queue a callback to deal with them. Also dead clients
with references would never actually be freed because the wrap-up
functions (the callback for stdin, or status_prompt_clear) would never
be called. So call them in server_client_lost.
2015-06-05 18:01:12 +00:00
nicm
b0782df8a6 Do not use the key variable uninitialized (in a debug log statement),
reported by jungleboogie0 at gmail dot com.
2015-06-05 15:10:13 +00:00
Nicholas Marriott
f7598b8a26 Only need *.ch in compat. 2015-06-05 12:44:15 +01:00
nicm
2f586905fc Fix a warning. 2015-06-05 09:09:08 +00:00
nicm
4219939c10 Make it so that if a window or session target is prefixed with an =,
only an exact name or index match is accepted, no special character,
prefix match, or fnmatch.
2015-06-05 08:14:16 +00:00
nicm
6b2129696f Move the nested check from client to server and compare the client tty
name to all the pane pty names instead of comparing socket paths. This
means that "new -d" will work without unsetting $TMUX.
2015-06-04 23:27:51 +00:00
jmc
dc0d34e137 tweak SYNOPSIS and usage(); 2015-06-04 20:34:22 +00:00
Thomas Adam
83a70172a4 Merge branch 'obsd-master' 2015-06-04 16:01:07 +01:00
nicm
4a6c06d6a9 Make unsetting a global option restore it to the default. Diff lying
around for a while, I have forgotten who suggested it :-/.
2015-06-04 14:29:33 +00:00
Thomas Adam
02e348c069 Merge branch 'obsd-master' 2015-06-04 12:59:41 +01:00
nicm
a863834574 Add support for a single "marked pane". There is one marked pane in the
server at a time; it may be toggled or cleared with select-pane -m and
-M (the border is highlighted). A new target '~' or '{marked}' specifies
the marked pane to commands and it is the default target for the
swap-pane and join-pane -s flag (this makes them much simpler to use -
mark the source pane and then change to the target pane to run swapp or
joinp).
2015-06-04 11:43:51 +00:00
Nicholas Marriott
1de74e27e5 Spaces -> tabs. 2015-06-04 11:40:27 +01:00
Nicholas Marriott
d058e963fd Update mailmap. 2015-06-04 11:36:44 +01:00
Thomas Adam
13808ccede Merge branch 'obsd-master' 2015-06-04 11:17:39 +01:00
nicm
a3edfd9e84 teminal -> terminal, from Corey Farwell. 2015-06-04 09:42:29 +00:00
Nicholas Marriott
75b70be4a6 Merge branch 'master' of github.com:tmux/tmux 2015-06-04 10:38:04 +01:00
Nicholas Marriott
b67db455a8 Update TODO with some items from old SF tickets. 2015-06-04 10:37:39 +01:00
Thomas Adam
2c29b3e82c SYNCING: Few tweaks 2015-06-04 10:35:40 +01:00
Thomas Adam
8fcac1b794 SYNCING: Update for GH
Explain the release process now that we're using GH.
2015-06-04 09:26:35 +01:00
Nicholas Marriott
75061cb45d I no longer need to care about GCC 3. 2015-06-04 08:50:20 +01:00
Nicholas Marriott
20598dff25 Note version this happened. 2015-06-04 08:47:23 +01:00
Nicholas Marriott
0b22d574e0 Update FAQ for new behaviour. 2015-06-04 08:46:49 +01:00
Nicholas Marriott
1df39aa962 I don't think we should carry around scripts. I'm not too sure about examples/
at all, nobody is maintaining it...
2015-06-04 08:26:50 +01:00
Nicholas Marriott
9d80ad16f9 Remove old tools. 2015-06-04 08:25:39 +01:00
Nicholas Marriott
c0a790453c Add a couple of presentations I wrote a few years ago. One for the ill-fated
AsiaBSDCon in 2011 (canceled due to Fukushima) and the other for LinuxTag 11 in
Berlin.
2015-06-04 08:23:40 +01:00
Nicholas Marriott
dbc5d7b331 Fix clone URL. 2015-06-04 01:27:47 +01:00
Nicholas Marriott
3ed03df23f Remove this file. 2015-06-04 01:26:03 +01:00
Nicholas Marriott
32bc8f4dd4 HTML bits are now elsewhere. 2015-06-04 01:21:41 +01:00
Nicholas Marriott
d2b35e19cd No more SF. 2015-06-04 00:44:22 +01:00
Nicholas Marriott
89131c3e90 No $Id$. 2015-06-04 00:38:01 +01:00
Nicholas Marriott
fc2fb0eb95 Update mailing list addresses. 2015-06-03 18:57:35 +01:00
Nicholas Marriott
dfd72f5250 -$Id$. 2015-06-03 18:42:36 +01:00
Nicholas Marriott
11ae6d16e5 $Id$ -> $OpenBSD$. 2015-06-03 18:35:44 +01:00
Nicholas Marriott
09bcbc57da $Id$ -> $OpenBSD$. 2015-06-03 18:28:26 +01:00
Nicholas Marriott
1c3e1bae41 Remove $Id$. 2015-06-03 18:26:25 +01:00
Nicholas Marriott
3821ca4917 Update TODO. 2015-06-02 15:16:13 +01:00
Thomas Adam
7bf5d4b946 Merge branch 'obsd-master' 2015-06-01 16:01:19 +01:00
nicm
a3c6172495 Missing t at end of response, from Vincent Bernat. 2015-06-01 13:59:57 +00:00
Thomas Adam
b675e6b2d5 Merge branch 'obsd-master' 2015-06-01 12:01:17 +01:00
nicm
58b50fb543 Clear signal handlers before event_reinit as apparently it can otherwise
cause libevent to go strange.
2015-06-01 09:20:19 +00:00
Thomas Adam
7712e6f82b Merge branch 'obsd-master' 2015-06-01 02:01:17 +01:00
deraadt
7e067cb9dc does not need syslog.h 2015-05-31 23:27:06 +00:00
Thomas Adam
c39dfb17ae Merge branch 'obsd-master' 2015-05-30 02:01:18 +01:00
nicm
2a8c2648f0 Don't use special strings if #() commands fail, just remove the format
(as if the command produced nothing). Makes constructions that can fail
like '#(test whatever && echo foo)' work as they did before.
2015-05-29 23:26:52 +00:00
nicm
74c755f2ab Expand formats again inside #(), and free the temporaries. 2015-05-29 23:12:38 +00:00
nicm
a55e569af5 Use RB_MIN to get the lowest index for the current window when creating
grouped sessions, rather than using RB_ROOT.
2015-05-29 23:02:27 +00:00
Thomas Adam
beffdf6575 Merge branch 'obsd-master' 2015-05-27 16:01:22 +01:00
nicm
379400cfa6 Move the jobs output cache into the formats code so that #() work more
generally (for example, again working in set-titles-string).
2015-05-27 13:28:04 +00:00
Thomas Adam
f538f2ae9b Merge branch 'obsd-master' 2015-05-20 10:01:19 +01:00
nicm
7140cce7f3 Return empty string if format is empty rather than attempting to
allocate zero bytes.
2015-05-20 06:39:02 +00:00
n6tadam
1ec93570bf Merge branch 'obsd-master' 2015-05-19 12:01:20 +01:00
nicm
2c53b23d59 In terminfo, sometimes cvvis implies cnorm and sometimes it doesn't, so
don't assume it does. Fixes missing cursor with emacs-in-tmux-in-tmux.
2015-05-19 08:48:37 +00:00
Thomas Adam
4123d69b51 README.md: github-specific readme
This is the same as the current README, but allows for markdown to be used.
We could switch this over to using the README file at some point.
2015-05-17 14:52:58 +01:00
Thomas Adam
35d21be19a TRAVIS-CI: correct path to configure
Specify path to ./configure
2015-05-17 14:39:04 +01:00
Thomas Adam
beb0c01c27 Hook repo to Travis-CI
From now on, all pushes to master will result in tmux compiling against a
linux-based distribution (Debian).  This will make it easier for automatic
merges between OpenBSD and portable to be tested, without the need for so
much manual syncing.

Any build failures will be reported to me, and fixed accordingly.
2015-05-17 14:36:34 +01:00
Thomas Adam
00471dc783 Merge branch 'obsd-master' 2015-05-13 09:44:11 +01:00
nicm
3f4ee98162 To replace c0-*, add a high watermark to the pty event, and also backoff
when the any of the ttys the pane is going to write to has buffered
enough data.
2015-05-12 22:40:38 +00:00
nicm
37ae8a9e0f Tidy blank lines when outputting server info. 2015-05-12 19:36:08 +00:00
nicm
ec34439f9c Add a session_alerts format which is a list of all the alerts in the
current session in symbolic form (something like "0!,4~,5!"). Use this
in the default set-titles-string. Prompted by a request from Jan ONDREJ.
2015-05-12 15:29:29 +00:00
nicm
e958db09a7 Add bell-action "other" to pass through bells in all windows except the
current, suggested by Jan ONDREJ.
2015-05-12 15:27:46 +00:00
nicm
b833fabeb2 Left the c0-* options behind in the table. 2015-05-11 10:58:22 +00:00
nicm
44364d7112 Remove the c0-* options which never really worked satisfactorily. Going
to try something else...
2015-05-11 10:10:16 +00:00
Thomas Adam
4165ed96f8 Add back __CYGWIN__ block
This went missing during the merge from OpenBSD.
2015-05-09 20:03:24 +01:00
Thomas Adam
c11f628342 Merge branch 'master' of ssh://git.code.sf.net/p/tmux/tmux-code 2015-05-09 12:53:53 +01:00
Thomas Adam
504b97b6a4 Merge branch 'obsd-master'
Conflicts:
	tmux.h
2015-05-09 12:52:38 +01:00
nicm
92faa2eaeb Put the tty structs together, and tabify. 2015-05-08 16:48:12 +00:00
nicm
592cb73a69 grid_marker_cell is no longer used. 2015-05-08 16:44:03 +00:00
nicm
74b2c40b1b mode_key_entry can go into mode-key.c; also a few spaces->tabs. 2015-05-08 16:33:29 +00:00
nicm
a538141a72 window_choose_mode_item can move into window-choose.c. 2015-05-08 16:23:34 +00:00
nicm
c4a4bd6ac5 Move input parser structs into input.c (removing fairly useless
saved_cursor_[xy] formats as a side-effect).
2015-05-08 16:18:04 +00:00
nicm
879de25583 Remove some stuff that accidentally ended up here from portable, and
remove a little-used debug function.
2015-05-08 15:56:49 +00:00
nicm
d174b9cfcc Update environment when switching sessions as well as attaching, from Si
Beaumont.
2015-05-07 14:07:16 +00:00
nicm
8e9b6e0948 Style spacing nits. 2015-05-07 11:42:56 +00:00
Nicholas Marriott
63b7a031a5 queue.h should come from compat.h. 2015-05-07 11:43:52 +01:00
nicm
1282bb81fe array.h can be local to window-choose.c now. 2015-05-07 08:08:54 +00:00
nicm
7becf326e3 Use a TAILQ not array for find-window. 2015-05-07 07:59:52 +00:00
nicm
73c871ba0a Simplify environ_push so it doesn't need the ARRAY_* functions. 2015-05-07 07:35:31 +00:00
nicm
b6be03f01a If status line is at the top, the offset needs to be adjusted when
drawing pane numbers.  Based on a diff from John O'Meara.
2015-05-07 07:16:14 +00:00
nicm
0b39e6427f Remove ARRAY_* from history and expand completion to complete a) layout
names and b) targets beginning with -t or -s.
2015-05-06 23:56:46 +00:00
Thomas Adam
6525ca5158 Start working on 2.1 2015-05-07 00:00:44 +01:00
Thomas Adam
e362d42dc6 CHANGES for tmux 2.0 2015-05-07 00:00:44 +01:00
Thomas Adam
f10d3675f8 Merge branch 'obsd-master' 2015-05-06 10:03:52 +01:00
nicm
31b1ab4852 Add a format window_linked which is 1 if a window has been linked
multiple times, also remove the default space in window_flags and use a
conditional to add it in window-status-format (this means additional
flags can be added in the option without extra spaces). From Thomas Adam
with tweaks by me.
2015-05-06 08:35:39 +00:00
nicm
33a585c47f Turn cursor off during redraw, pointed out by George Nachman. 2015-05-06 07:52:06 +00:00
nicm
672df72b71 Use the right index when expanding/collapsing tree, from Thomas Adam. 2015-05-04 13:04:10 +00:00
Thomas Adam
c0cf4843e5 Merge branch 'obsd-master' 2015-04-29 18:42:12 +01:00
nicm
69b8f100b7 Do not complain when directions fail. 2015-04-29 16:26:17 +00:00
nicm
7382ba82c5 If default-terminal is set to "screen" or "screen-*", emulate screen's
historical (incorrect) behaviour for SGR 3 and send smso
(standout). Previously, we would send sitm (italics) if the terminal
outside had it and smso otherwise. This was acceptably until recently
because xterm's terminfo entry lacked sitm, so most users got smso.

People who want italics should set default-terminal to the forthcoming
"tmux" entry (and be prepared to deal with it being missing on older
hosts).

As a side-effect this changes default-terminal to be a server rather
than a session option.

suggested by and ok naddy
2015-04-29 15:59:08 +00:00
Nicholas Marriott
8794562a85 Add tmux4.png. 2015-04-28 16:04:07 +01:00
Nicholas Marriott
31ab5caa35 Renumber screenshots. 2015-04-28 15:34:09 +01:00
Nicholas Marriott
1ed5326f5a Merge branch 'master' of ssh://git.code.sf.net/p/tmux/tmux-code 2015-04-28 15:18:53 +01:00
Nicholas Marriott
ab5f9ab55b Update two of the screenshots. 2015-04-28 15:12:45 +01:00
Thomas Adam
dc2adc6bc1 Merge branch 'obsd-master' 2015-04-28 14:57:15 +01:00
Nicholas Marriott
7981e653d8 But this does work. 2015-04-28 14:01:03 +01:00
Nicholas Marriott
bc9198072b Upload all the files. 2015-04-28 13:58:17 +01:00
Nicholas Marriott
e88c48ce0e This doesn't work. 2015-04-28 13:58:00 +01:00
Nicholas Marriott
f54f3e2abe Add logo to www, also centre the page. 2015-04-28 13:47:54 +01:00
Nicholas Marriott
bb210ce773 Add tmux logo, createed by Jason Long. 2015-04-28 13:46:47 +01:00
nicm
e36fab2f70 If looking for an index, don't fill in window when given a session. 2015-04-28 12:09:24 +00:00
nicm
14d8cd6445 Do not do a search for the tty path if there isn't one. 2015-04-28 11:57:20 +00:00
nicm
094a047ddf If can't find pane as a pane, try as a window; likewise if can't find
window as a session.
2015-04-28 11:33:17 +00:00
nicm
771744426e Add select-layout -o to undo the last layout change (apply the previously
set layout).
2015-04-28 10:43:13 +00:00
Nicholas Marriott
3eb40a520a No paths.h on Solaris. 2015-04-28 10:36:17 +01:00
Thomas Adam
7d98c51805 Merge branch 'obsd-master' 2015-04-28 09:10:51 +01:00
nicm
c2bc84aa4d Do not include unattached clients when trying to find one for target. 2015-04-27 22:58:58 +00:00
nicm
b7777e7ef3 Reset cfg_ncauses to 0 as well or we could allocate the wrong size if
called again.
2015-04-27 22:50:35 +00:00
nicm
91f6347485 Assign to the right variable when comparing clients. 2015-04-27 22:42:10 +00:00
Thomas Adam
94a8ef1cae Merge branch 'obsd-master'
Conflicts:
	Makefile
	tmux.1
2015-04-27 21:21:55 +01:00
nicm
95195f5258 Rewrite of the target resolution internals to be simpler and more
consistent but with much less duplication, but keeping the same internal
API. Also adds more readable aliases for some of the special tokens used
in targets (eg "{start}" instead of "^"). Some behaviours may have
changed, for example prefix matches now happen before fnmatch.
2015-04-27 16:25:57 +00:00
nicm
a70762c9b5 If the requested pane is already active, do not unzoom the window (or do
anything else). Prevents mouse clicking when zoomed causing unzoom,
reported by Jose Antonio Delgado Alfonso (with a different fix).
2015-04-27 07:49:36 +00:00
nicm
5bd5c9c84e Remove panes from layout if spawning them fails, reported by Anthony J
Bentley.
2015-04-26 20:25:20 +00:00
Thomas Adam
72e9ebf2ec Merge branch 'obsd-master' 2015-04-25 20:45:02 +00:00
nicm
05e7fbd60f Get rid of window_choose_list type. 2015-04-25 18:56:05 +00:00
nicm
1d1208e335 Fix some char* -> char *. 2015-04-25 18:49:01 +00:00
nicm
a568b9cadc Use a char **,u_int pair for cfg_causes. 2015-04-25 18:47:01 +00:00
nicm
07dfdb974d Make message log a TAILQ. 2015-04-25 18:33:59 +00:00
nicm
6dbd63ba4f Move the functions to convert ids from strings into session.c and window.c. 2015-04-25 18:09:28 +00:00
nicm
d23af6cca0 Explicitly cancel mouse "button" mode, this happens implicitly with some
one of the other things we send with xterm, but not with urxvt. Reported
by sthen@.
2015-04-25 15:57:48 +00:00
Thomas Adam
56e1132db4 Merge branch 'obsd-master' 2015-04-25 10:02:46 +00:00
nicm
aeedb464a6 Convert clients list into a TAILQ. 2015-04-24 23:17:11 +00:00
nicm
583b4ab72b Set working directory for run-shell and if-shell. 2015-04-24 22:19:36 +00:00
nicm
5a2d0533a8 Allow choice options (multiple states) to be toggled between states 0
and 1.
2015-04-24 21:38:18 +00:00
nicm
a5a873dccc Set up signal handler earlier so that we don't get zombies, reported by
sobrado@.
2015-04-24 20:58:44 +00:00
deraadt
ab73997cc5 use reallocarray instead of calloc; avoid the zero before infill
ok nicm
2015-04-23 07:45:50 +00:00
nicm
9a453dd354 Make session_has return a flag, returning the first winlink found is a
recipe for errors.
2015-04-22 15:32:33 +00:00
nicm
8d66f4fba4 Change the windows array into an RB tree and fix some places where we
were only looking at the first winlink for a window in a session.
2015-04-22 15:30:11 +00:00
nicm
89e80cabd5 window_index is only used in one place (window_destroy) so inline it there. 2015-04-22 15:05:03 +00:00
Thomas Adam
0a88377086 Merge branch 'obsd-master' 2015-04-22 10:05:54 +01:00
nicm
3909aff06a Look up indexes as number before name, makes more sense if windows are
named starting with numbers. From Thomas Adam.
2015-04-21 22:42:27 +00:00
nicm
69f292a90e Always format real layout even when zoomed. 2015-04-21 22:38:49 +00:00
nicm
93b2871cab Do not die on USR1 if any of the socket parent directories are
missing. Reported by Robin Powell.
2015-04-21 22:32:40 +00:00
nicm
7a72eff4a4 Simplify error messages when socket connect fails, suggested by "Karthik K". 2015-04-21 22:21:41 +00:00
nicm
d16b640fe8 The free callback could end up being fired before the done callback
(happens on Cygwin), so use a reference count instead of a single
flag. SF bug 188 reported by "iceboy".
2015-04-21 21:31:02 +00:00
nicm
0e7219d437 Fix moving windows to nonexistent indexes when renumber-windows is
off. From Thomas Adam, reported by Daniel Levai and Theo Buehler.
2015-04-21 21:24:49 +00:00
nicm
d1337053b6 Bind mouse dragging so that it is passed through to applications if they
want it rather than entering copy mode.
2015-04-21 15:34:32 +00:00
nicm
4cf4302962 Don't eat the mouse event that triggers a drag end because we may want
to pass it on to application inside the pane.
2015-04-21 15:21:41 +00:00
nicm
1f404f6a23 Put mouse_any_flag back, don't know where it went to (still in man page). 2015-04-21 15:18:38 +00:00
nicm
bc3786ece9 Pass mouse events through to commands for if-shell. 2015-04-21 15:18:06 +00:00
nicm
0610f44380 cmd_mouse_pane can return NULL, check for that. 2015-04-21 15:16:06 +00:00
nicm
07d93db427 Remove unused-but-set variables, from Thomas Adam. 2015-04-20 15:41:32 +00:00
nicm
bded743706 Support for multiple key tables to commands to be bound to sequences of
keys. The default key bindings become the "prefix" table and -n the
"root" table. Keys may be bound in new tables with bind -T and
switch-client -T used to specify the table in which the next key should
be looked up. Based on a diff from Keith Amling.
2015-04-20 15:34:56 +00:00
nicm
3497843f02 Style nit - unnecessary brackets. 2015-04-20 14:48:55 +00:00
Thomas Adam
b25dc423b0 Merge branch 'obsd-master' 2015-04-20 15:44:27 +01:00
nicm
0fd9a97202 Make jump-to-backward/jump-to-forward repeatable with
jump-reverse/jump-again, from Jacob Niehus.
2015-04-20 09:39:21 +00:00
nicm
6f587570ed Use a more sensible buffer size for flags string. 2015-04-20 07:50:49 +00:00
Nicholas Marriott
acb8248ba6 +. 2015-04-20 08:46:21 +01:00
jmc
8101f1ef16 tweak previous; 2015-04-19 22:10:30 +00:00
nicm
bbac2aee1f Honour renumber-windows when unlinking a window, from Thomas Adam. 2015-04-19 21:46:52 +00:00
nicm
bf635e7741 Rewrite of tmux mouse support which was a mess. Instead of having
options for "mouse-this" and "mouse-that", mouse events may be bound as
keys and there is one option "mouse" that turns on mouse support
entirely (set -g mouse on).

See the new MOUSE SUPPORT section of the man page for description of the
key names and new flags (-t= to specify the pane or window under mouse
as a target, and send-keys -M to pass through a mouse event).

The default builtin bindings for the mouse are:

    bind -n   MouseDown1Pane select-pane -t=; send-keys -M
    bind -n MouseDown1Status select-window -t=
    bind -n   MouseDrag1Pane copy-mode -M
    bind -n MouseDrag1Border resize-pane -M

To get the effect of turning mode-mouse off, do:

    unbind -n MouseDrag1Pane
    unbind -temacs-copy MouseDrag1Pane

The old mouse options are now gone, set-option -q may be used to
suppress warnings if mixing configuration files.
2015-04-19 21:34:21 +00:00
nicm
ee123c2489 Support setting the default window and pane background colours (window
and active pane via window-style and window-active-style options, an
individual pane by a new select-pane -P flag). From J Raynor.
2015-04-19 21:05:27 +00:00
Nicholas Marriott
24c8f523eb +. 2015-04-19 19:40:12 +01:00
Nicholas Marriott
aaad44bbe7 +. 2015-04-19 19:34:58 +01:00
Thomas Adam
370cf75458 Merge branch 'obsd-master' 2015-04-19 14:44:56 +01:00
nicm
4a7587931c Fix some issues in bright colour handling. Bold background doesn't exist
so there is no reason for tty_check_bg to mess with the BRIGHT flag at
all, ever. Also use aixterm colours for 256-to-16 translation if the
terminal supports them. And there is no reason for tty_colours_bg to
worry about whether the terminal supports them - tty_check_bg has
already taken care of it.
2015-04-15 22:34:46 +00:00
nicm
eec27f9257 Use tty_term_flag not _has for flags, also fix a typo (position not
permission).
2015-04-15 22:10:13 +00:00
nicm
f922920609 Fix setting old-style window -fg/-bg/-attr options that aren't global. 2015-04-15 15:44:40 +00:00
nicm
0cd55eb1e7 Add a -x flag to copy-selection, append-selection and start-named-buffer
to prevent it exiting copy mode after copying. From J Raynor with a few
tweaks by me.
2015-04-10 16:00:08 +00:00
nicm
009a5e4213 in the case -> in this case. 2015-04-10 07:23:14 +00:00
nicm
6920be311b When replacing, don't free the old paste until after the new one's name
has been copied. Fixes a use-after-free in window-copy.c. Bug reported
by J Raynor (who also provided a different fix).
2015-04-07 13:06:22 +00:00
nicm
3aa72b42b2 Add a helper function to convert time, and add session_activity formats
(the latter from Takatoshi Matsumoto).
2015-03-31 17:58:36 +00:00
nicm
02df86079b Fix some format specifier nits, from Ben Boeckel. 2015-03-31 17:45:10 +00:00
Nicholas Marriott
5e956f1148 Make place const to avoid a warning, from Ben Boeckel. 2015-03-31 09:26:37 +01:00
nicm
cd9ccbc1e9 set-titles-string now uses formats, not the status bits (so no #() for
now). Reported by landry.
2015-03-11 08:17:37 +00:00
281 changed files with 51206 additions and 23464 deletions

78
.github/CONTRIBUTING.md vendored Normal file
View File

@@ -0,0 +1,78 @@
## What should I do before opening an issue?
Before opening an issue, please ensure that:
- Your problem is a specific problem or question or suggestion, not a general
complaint.
- `$TERM` inside tmux is screen, screen-256color, tmux or tmux-256color. Check
by running `echo $TERM` inside tmux.
- You can reproduce the problem with the latest tmux release, or a build from
Git master.
- Your question or issue is not covered [in the
manual](https://man.openbsd.org/tmux.1) (run `man tmux`).
- Your problem is not mentioned in [the CHANGES
file](https://raw.githubusercontent.com/tmux/tmux/master/CHANGES).
- Nobody else has opened the same issue recently.
## What should I include in an issue?
Please include the output of:
~~~bash
uname -sp && tmux -V && echo $TERM
~~~
Also include:
- Your platform (Linux, OS X, or whatever).
- A brief description of the problem with steps to reproduce.
- A minimal tmux config, if you can't reproduce without a config.
- Your terminal, and `$TERM` inside and outside of tmux.
- Logs from tmux (see below).
- At most one or two screenshots, if helpful.
## How do I test without a .tmux.conf?
Run a separate tmux server with `-f/dev/null` to skip loading `.tmux.conf`:
~~~bash
tmux -Ltest kill-server
tmux -Ltest -f/dev/null new
~~~
## How do I get logs from tmux?
Add `-vv` to tmux to create three log files in the current directory. If you can
reproduce without a configuration file:
~~~bash
tmux -Ltest kill-server
tmux -vv -Ltest -f/dev/null new
~~~
Or if you need your configuration:
~~~base
tmux kill-server
tmux -vv new
~~~
The log files are:
- `tmux-server*.log`: server log file.
- `tmux-client*.log`: client log file.
- `tmux-out*.log`: output log file.
Please attach the log files to your issue.

2
.github/FUNDING.yml vendored Normal file
View File

@@ -0,0 +1,2 @@
github: nicm
liberapay: tmux

22
.github/ISSUE_TEMPLATE.md vendored Normal file
View File

@@ -0,0 +1,22 @@
### Issue description
Please read https://github.com/tmux/tmux/blob/master/.github/CONTRIBUTING.md
before opening an issue.
If you have upgraded, make sure your issue is not covered in the CHANGES file
for your version: https://raw.githubusercontent.com/tmux/tmux/master/CHANGES
Describe the problem and the steps to reproduce. Add a minimal tmux config if
necessary. Screenshots can be helpful, but no more than one or two.
Do not report bugs (crashes, incorrect behaviour) without reproducing on a tmux
built from the latest code in Git.
### Required information
Please provide the following information:
* tmux version (`tmux -V`).
* Platform (`uname -sp`).
* $TERM inside and outside of tmux (`echo $TERM`).
* Logs from tmux (`tmux kill-server; tmux -vv new`).

83
.github/README.md vendored Normal file
View File

@@ -0,0 +1,83 @@
# Welcome to tmux!
tmux is a terminal multiplexer: it enables a number of terminals to be created,
accessed, and controlled from a single screen. tmux may be detached from a
screen and continue running in the background, then later reattached.
This release runs on OpenBSD, FreeBSD, NetBSD, Linux, OS X and Solaris.
## Dependencies
tmux depends on [libevent](https://libevent.org) 2.x, available from [this
page](https://github.com/libevent/libevent/releases/latest).
It also depends on [ncurses](https://www.gnu.org/software/ncurses/), available
from [this page](https://invisible-mirror.net/archives/ncurses/).
## Installation
### From release tarball
To build and install tmux from a release tarball, use:
~~~bash
./configure && make
sudo make install
~~~
tmux can use the utempter library to update utmp(5), if it is installed - run
configure with `--enable-utempter` to enable this.
### From version control
To get and build the latest from version control - note that this requires
`autoconf`, `automake` and `pkg-config`:
~~~bash
git clone https://github.com/tmux/tmux.git
cd tmux
sh autogen.sh
./configure && make
~~~
## Contributing
Bug reports, feature suggestions and especially code contributions are most
welcome. Please send by email to:
tmux-users@googlegroups.com
Or open a GitHub issue or pull request. **Please read [this
document](CONTRIBUTING.md) before opening an issue.**
There is [a list of suggestions for contributions](https://github.com/tmux/tmux/wiki/Contributing).
Please feel free to ask on the mailing list if you're thinking of working on something or need
further information.
## Documentation
For documentation on using tmux, see the tmux.1 manpage. View it from the
source tree with:
~~~bash
nroff -mdoc tmux.1|less
~~~
A small example configuration is in `example_tmux.conf`.
And a bash(1) completion file at:
https://github.com/imomaliev/tmux-bash-completion
For debugging, run tmux with `-v` or `-vv` to generate server and client log
files in the current directory.
## Support
The tmux mailing list for general discussion and bug reports is:
https://groups.google.com/forum/#!forum/tmux-users
Subscribe by sending an email to:
tmux-users+subscribe@googlegroups.com

10
.github/lock.yml vendored Normal file
View File

@@ -0,0 +1,10 @@
daysUntilLock: 180
skipCreatedBefore: false
exemptLabels: []
lockLabel: false
lockComment: >
This thread has been automatically locked since there has not been
any recent activity after it was closed. Please open a new issue for
related bugs.
setLockReason: false
#only: issues

2
.gitignore vendored
View File

@@ -17,3 +17,5 @@ Makefile
Makefile.in
configure
tmux.1.*
*.dSYM
cmd-parse.c

View File

@@ -1,24 +1,37 @@
Bob Beck <beck@openbsd.org> beck <beck>
Igor Sobrado <sobrado@openbsd.org> sobrado <sobrado>
Jacek Masiulaniec <jacekm@openbsd.org> jacekm <jacekm>
Jason McIntyre <jmc@openbsd.org> jcm <jcm>
Bob Beck <beck@openbsd.org> beck <beck>
Claudio Jeker <claudio@openbsd.org> claudio <claudio>
Igor Sobrado <sobrado@openbsd.org> sobrado <sobrado>
Ingo Schwarze <schwarze@openbsd.org> schwarze <schwarze>
Jacek Masiulaniec <jacekm@openbsd.org> jacekm <jacekm>
Jason McIntyre <jmc@openbsd.org> jmc <jmc>
Joel Sing <jsing@openbsd.org> jsing <jsing>
Marc Espie <espie@openbsd.org> espie <espie>
Matthew Dempsky <matthew@openbsd.org> matthew <matthew>
Matthias Kilian <kili@openbsd.org> kili <kili>
Matthieu Herrb <matthieu@openbsd.org> matthieu <matthieu>
Miod Vallat <miod@openbsd.org> miod <miod>
Nicholas Marriott <nicm@openbsd.org> nicm <nicm>
Nicholas Marriott <nicm@openbsd.org> no_author <no_author@example.org>
<nicm@openbsd.org> <nicholas.marriott@gmail.com>
Okan Demirmen <okan@openbsd.org> okan <okan>
Jonathan Gray <jsg@openbsd.org> jsg <jsg>
Kenneth R Westerback <krw@openbsd.org> krw <krw>
Marc Espie <espie@openbsd.org> espie <espie>
Matthew Dempsky <matthew@openbsd.org> matthew <matthew>
Matthias Kilian <kili@openbsd.org> kili <kili>
Matthieu Herrb <matthieu@openbsd.org> matthieu <matthieu>
Michael McConville <mmcc@openbsd.org> mmcc <mmcc>
Miod Vallat <miod@openbsd.org> miod <miod>
Nicholas Marriott <nicholas.marriott@gmail.com> Nicholas Marriott <nicm@openbsd.org>
Nicholas Marriott <nicholas.marriott@gmail.com> nicm <nicm>
Nicholas Marriott <nicholas.marriott@gmail.com> no_author <no_author@example.org>
Okan Demirmen <okan@openbsd.org> okan <okan>
Philip Guenther <guenther@openbsd.org> guenther <guenther>
Pierre-Yves Ritschard <pyr@openbsd.org> pyr <pyr>
Ray Lai <ray@openbsd.org> ray <ray>
Pierre-Yves Ritschard <pyr@openbsd.org> pyr <pyr>
Ray Lai <ray@openbsd.org> ray <ray>
Ryan McBride <mcbride@openbsd.org> mcbride <mcbride>
Stefan Sperling <stsp@openbsd.org> stsp <stsp>
Stuart Henderson <sthen@openbsd.org> sthen <sthen>
Ted Unangst <tedu@openbsd.org> tedu <tedu>
Theo Deraadt <deraadt@openbsd.org> deraadt <deraadt>
Sebastian Benoit <benno@openbsd.org> benno <benno>
Sebastien Marie <semarie@openbsd.org> semarie <semarie>
Stefan Sperling <stsp@openbsd.org> stsp <stsp>
Stuart Henderson <sthen@openbsd.org> sthen <sthen>
Ted Unangst <tedu@openbsd.org> tedu <tedu>
Theo de Raadt <deraadt@openbsd.org> Theo Deraadt <deraadt@openbsd.org>
Theo de Raadt <deraadt@openbsd.org> deraadt <deraadt>
Thomas Adam <thomas@xteddy.org> Thomas <thomas@xteddy.org>
William Yodlowsky <william@openbsd.org> william <william>
Thomas Adam <thomas@xteddy.org> Thomas Adam <thomas.adam@smoothwall.net>
Thomas Adam <thomas@xteddy.org> n6tadam <n6tadam@xteddy.org>
Tim van der Molen <tim@openbsd.org> tim <tim>
Tobias Stoeckmann <tobias@openbsd.org> tobias <tobias>
Todd C Miller <millert@openbsd.org> millert <millert>
William Yodlowsky <william@openbsd.org> william <william>

16
.travis.yml Normal file
View File

@@ -0,0 +1,16 @@
language: c
os:
- linux
- osx
compiler:
- gcc
- clang
before_install:
- if [ "$TRAVIS_OS_NAME" = "linux" ]; then sudo apt-get update -qq; fi
- if [ "$TRAVIS_OS_NAME" = "linux" ]; then sudo apt-get -y install bison autotools-dev libncurses5-dev libevent-dev pkg-config libutempter-dev build-essential; fi
script:
- ./autogen.sh && ./configure && make

1014
CHANGES

File diff suppressed because it is too large Load Diff

View File

@@ -1,10 +1,7 @@
THIS IS FOR INFORMATION ONLY, CODE IS UNDER THE LICENCE AT THE TOP OF ITS FILE.
The README, CHANGES, FAQ and TODO files are licensed under the ISC
license. Files under examples/ remain copyright their authors unless otherwise
stated in the file but permission has been received to distribute them with
tmux. All other files have a license and copyright notice at their start,
typically:
The README, CHANGES, FAQ and TODO files are licensed under the ISC license. All
other files have a license and copyright notice at their start, typically:
Copyright (c) <author>

465
FAQ
View File

@@ -1,465 +0,0 @@
tmux frequently asked questions
******************************************************************************
* PLEASE NOTE: most display problems are due to incorrect TERM! Before *
* reporting problems make SURE that TERM settings are correct inside and *
* outside tmux. *
* *
* Inside tmux TERM must be "screen" or similar (such as "screen-256color"). *
* Don't bother reporting problems where it isn't! *
* *
* Outside, it must match your terminal: particularly, use "rxvt" for rxvt *
* and derivatives. *
******************************************************************************
* How is tmux different from GNU screen?
tmux and GNU screen have many similarities. Some of the main differences I am
aware of are (bearing in mind I haven't used screen for a few years now):
- tmux uses a client-server model. Each server has single Unix domain socket in
/tmp and within one server there are multiple sessions which may be attached
to multiple clients (terminals).
This has advantages, notably: windows may be linked simultaneously to
multiple sessions; windows may be moved freely between sessions; and a client
may be switched between sessions easily (C-b D). There is one major
disadvantage: if the server crashes, game over, all sessions die. In
practice, however, tmux is quite stable and gets more so as people report any
bugs they hit :-).
This model is different from screen, where typically each new screen instance
is independent. tmux supports the same behaviour by using multiple servers
with the -L option but it is not typically recommended.
- Different command interfaces. One of the goals of tmux is that the shell
should be easily usable as a scripting language - almost all tmux commands
can be used from the shell and behave identically whether used from the
shell, from a key binding or from the command prompt. Personally I also find
tmux's command interface much more consistent and clearer, but this is
subjective.
- tmux calls window names (what you see in the status line) "names", screen
calls them "titles".
- tmux has a multiple paste buffers. Not a major one but comes in handy quite a
lot.
- tmux supports automatically renaming windows to the running application
without gross hacks using escape sequences. Its even on by default.
- tmux has a choice of vi or emacs key layouts. Again, not major, but I use
emacs so if tmux did support only one key set it would be emacs and then all
the vi users would get humpy. Key bindings may be completely reconfigured in
any case.
- tmux has an option to limit the window size.
- tmux has search in windows (C-b f).
- The window split (pane) model is different. tmux has two objects, windows and
panes; screen has just windows. This difference has several implications:
* In screen you can have a window appear in several layouts, in tmux a pane
can only be in one window (fixing this is a big todo item but quite
invasive).
* tmux layouts are immutable and do not get changed unless you modify them.
* In tmux, all panes are closed when you kill a window.
* tmux panes do not have individual names, titles and so on.
I think tmux's model is much easier to manage and navigate within a window,
but breaking panes off from and joining them to windows is more clumsy.
tmux also has support for preset pane layouts.
- tmux's status line syntax is more readable and easier to use. I think it'd be
hard for anyone to argue with this. tmux doesn't support running a command
constantly and always using the last line of its output, commands must be run
again each time.
- tmux has modern, easily extended code. Again hard to argue screen is better
if you have looked at the code.
- tmux depends on libevent. I don't see this as a disadvantage: libevent is
small and portable, and on modern systems with current package management
systems dependencies are not an issue. libevent brings advantages in code
simplicity and performance.
- screen allows the window to be bigger than the terminal and can pan around
it. tmux limits the size to the largest attached client. This is a big todo
item for tmux but it is not trivial.
- screen has builtin serial and telnet support; this is bloat and is unlikely
to be added to tmux.
- Environment handling is different.
- tmux tends to be more demanding on the terminal so tends to show up terminal
and application bugs which screen does not.
- screen has wider platform support, for example IRIX, and for odd terminals.
* I found a bug! What do I do?
Check the latest version of tmux from Git to see if the problem is still
reproducible. Sometimes the length of time between releases means a lot of
fixes can be sitting in Git and the problem might already be fixed.
Please send bug reports by email to nicm@users.sourceforge.net or
tmux-users@lists.sourceforge.net. Please include as much of the following
information as possible:
- the version of tmux you are running;
- the operating system you are using and its version;
- the terminal emulator you are using and the TERM setting when tmux was
started;
- a description of the problem;
- if the problem is repeatable, the steps to repeat the problem;
- for screen corruption issues, a screenshot and the output of "infocmp $TERM"
from outside tmux are often very useful.
* Why doesn't tmux do $x?
Please send feature requests by email to nicm@users.sourceforge.net.
* Why do you use the screen terminal description inside tmux? It sucks.
It is already widely available. It is planned to change to something else such
as xterm-xfree86 at some point, if possible.
* I don't see any colour in my terminal! Help!
On some platforms, common terminal descriptions such as xterm do not include
colour. screen ignores this, tmux does not. If the terminal emulator in use
supports colour, use a value for TERM which correctly lists this, such as
xterm-color.
* tmux freezes my terminal when I attach to a session. I even have to kill -9
the shell it was started from to recover!
Some consoles really really don't like attempts to set the window title. Tell
tmux not to do this by turning off the "set-titles" option (you can do this
in .tmux.conf):
set -g set-titles off
If this doesn't fix it, send a bug report.
* Why is C-b the prefix key? How do I change it?
The default key is C-b because the prototype of tmux was originally developed
inside screen and C-b was chosen not to clash with the screen meta key. It
also has the advantage of not interfering with the use of C-a for start-of-line
in emacs and the shell (although it does interfere with previous-character).
Changing is simple: change the "prefix-key" option, and - if required - move
the binding of the "send-prefix" command from C-b (C-b C-b sends C-b by
default) to the new key. For example:
set -g prefix C-a
unbind C-b
bind C-a send-prefix
* How do I use UTF-8?
When running tmux in a UTF-8 capable terminal, UTF-8 must be turned on in tmux;
as of release 0.9, tmux attempts to autodetect a UTF-8-capable terminal by
checking the LC_ALL, LC_CTYPE and LANG environment variables. list-clients may
be used to check if this is detected correctly; if not, the -u command-line
flag may be specified when creating or attaching a client to a tmux session:
$ tmux -u new
Since the 1.0 release, tmux will turn on UTF-8 related options automatically
(ie status-utf8, and utf8) if the above conditions are met.
* How do I use a 256 colour terminal?
Provided the underlying terminal supports 256 colours, it is usually sufficient
to add the following to ~/.tmux.conf:
set -g default-terminal "screen-256color"
Note that some platforms do not support "screen-256color" ("infocmp
screen-256color" will return an error) - in this case see the next entry in
this FAQ.
tmux attempts to detect a 256 colour terminal both by looking at the colors
terminfo entry and by looking for the string "256col" in the TERM environment
variable.
If both these methods fail, the -2 flag may be passed to tmux when attaching
to a session to indicate the terminal supports 256 colours.
* vim or $otherprogram doesn't display 256 colours. What's up?
Some programs attempt to detect the number of colours a terminal is capable of
by checking the colors terminfo or Co termcap entry. However, this is not
reliable, and in any case is missing from the "screen" terminal description
used inside tmux.
There are two options (aside from using "screen-256color") to allow programs to
recognise they are running on a 256-colour terminal inside tmux:
- Manually force the application to use 256 colours always or if TERM is set to
screen. For vim, you can do this by overriding the t_Co option, see
http://vim.wikia.com/wiki/256_colors_in_vim.
- Creating a custom terminfo file that includes colors#256 in ~/.terminfo and
using it instead. These may be compiled with tic(1).
* How do I make Ctrl-PgUp and Ctrl-PgDn work in vim?
tmux supports passing through ctrl (and where supported by the client terminal,
alt and shift) modifiers to function keys using xterm(1)-style key sequences.
This may be enabled per window, or globally with the tmux command:
setw -g xterm-keys on
Because the TERM variable inside tmux must be set to "screen", vim will not
automatically detect these keys are available; however, the appropriate key
sequences can be overridden in .vimrc using the following:
if &term == "screen"
set t_kN=^[[6;*~
set t_kP=^[[5;*~
endif
And similarly for any other keys for which modifiers are desired.
Please note that the "xterm-keys" setting may affect other programs, in the
same way as running them in a standard xterm; for example most shells do not
expect to receive xterm(1)-style key sequences so this setting may prevent keys
such as ctrl-left and ctrl-right working correctly. tmux also passes through
the ctrl (bit 5 set, for example ^[[5~ to ^[[5^) modifier in non-xterm(1) mode;
it may be possible to configure vim to accept these, an example of how to do so
would be welcome.
vim users may also want to set the "ttyfast" option inside tmux.
* How do I make ctrl and shift arrow keys work in emacs?
The terminal-init-screen function in term/screen.el is called for new frames,
but it doesn't configure any function keys.
If the tmux xterm-keys option is on, it is enough to define the same keys as
xterm. Add the following to init.el or .emacs to do this:
(defadvice terminal-init-screen
;; The advice is named `tmux', and is run before `terminal-init-screen' runs.
(before tmux activate)
;; Docstring. This describes the advice and is made available inside emacs;
;; for example when doing C-h f terminal-init-screen RET
"Apply xterm keymap, allowing use of keys passed through tmux."
;; This is the elisp code that is run before `terminal-init-screen'.
(if (getenv "TMUX")
(let ((map (copy-keymap xterm-function-map)))
(set-keymap-parent map (keymap-parent input-decode-map))
(set-keymap-parent input-decode-map map))))
And ensure .tmux.conf contains "set -g xterm-keys on".
Alternatively, the screen.el file can be copied to the load path and
customized.
* Why doesn't elinks set the window title inside tmux?
There isn't a way to detect if a terminal supports setting the window title, so
elinks attempts to guess by looking at the environment. Rather than looking for
TERM=screen, it uses the STY variable to detect if it is running in screen;
tmux does not use this so the check fails. A workaround is to set STY before
running elinks.
The following shell function does this, and also clears the window title on
exit (elinks, for some strange reason, sets it to the value of TERM):
elinks() {
STY= `which elinks` $*
echo -ne \\033]0\;\\007;
}
* What is the proper way to escape characters with #(command)?
When using the #(command) construction to include the output from a command in
the status line, the command will be parsed twice. First, when it's read by the
configuration file or the command-prompt parser, and second when the status
line is being drawn and the command is passed to the shell. For example, to
echo the string "(test)" to the status line, either single or double quotes
could be used:
set -g status-right "#(echo \\\\(test\\\\))"
set -g status-right '#(echo \\\(test\\\))'
In both cases, the status-right option will be set to the string "#(echo
\\(test\\))" and the command executed will be "echo \(test\)".
* tmux uses too much CPU. What do I do?
Automatic window renaming may use a lot of CPU, particularly on slow computers:
if this is a problem, turn it off with "setw -g automatic-rename off". If this
doesn't fix it, please report the problem.
* I use PuTTY and my tmux window pane separators are all qqqqqqqqq's!
PuTTY is using a character set translation that doesn't support ACS line
drawing. With a Unicode font, try setting PuTTY to use a different translation
on the Window -> Translation configuration page. For example, change UTF-8 to
ISO-8859-1 or CP437. It may also be necessary to adjust the way PuTTY treats
line drawing characters in the lower part of the same configuration page.
* What is the best way to display the load average? Why no #L?
It isn't possible to get the load average portably in code and it is preferable
not to add portability goop. The following works on at least Linux, *BSD and OS
X:
uptime|awk '{split(substr($0, index($0, "load")), a, ":"); print a[2]}'
* How do I attach the same session to multiple clients but with a different
current window, like screen -x?
One or more of the windows can be linked into multiple sessions manually with
link-window, or a grouped session with all the windows can be created with
new-session -t.
* Ctrl and arrow keys doesn't work in putty! What do I do?
putty inverts the sense of the cursor key mode on ctrl, which is a bit hard for
tmux to detect properly. To get ctrl keys right, change the terminfo settings
so kUP5 (Ctrl-Up etc) are the adjusted versions, and disable smkx/rmkx so tmux
doesn't change the mode. For example with this line in .tmux.conf (assuming you
have TERM set to xterm):
set -g terminal-overrides "xterm*:kLFT5=\eOD:kRIT5=\eOC:kUP5=\eOA:kDN5=\eOB:smkx@:rmkx@"
Note that this will only work in tmux 1.2 and above.
* How can I blank the tmux window?
GNU screen has a feature whereby it will blank the screen after a period of
inactivity. To do the same thing in tmux, use the lock-command setting, for
example (with GNU bash):
set -g lock-command 'tput civis && read -s -n1'
This will remove the cursor and tell the shell to quit once a key has been
pressed. For zsh, use "read -s -k1".
In addition, it's possible to have both blanking and locking (for instance via
lock(1) or vlock(1)) by using the following:
bind x set lock-command '/usr/bin/vlock' \; lock-client \; set lock-command 'tput civis && read -s -n1'
* vim displays reverse video instead of italics, while less displays italics
(or just regular text) instead of reverse. What's wrong?
Screen's terminfo description lacks italics mode and has standout mode in its
place, but using the same escape sequence that urxvt uses for italics. This
means applications (like vim) looking for italics will not find it and might
turn to reverse in its place, while applications (like less) asking for
standout will end up with italics instead of reverse. To make applications
aware that tmux supports italics and to use a proper escape sequence for
standout, you'll need to create a new terminfo file with modified sgr, smso,
rmso, sitm and ritm entries:
$ mkdir $HOME/.terminfo/
$ screen_terminfo="screen"
$ infocmp "$screen_terminfo" | sed \
-e 's/^screen[^|]*|[^,]*,/screen-it|screen with italics support,/' \
-e 's/%?%p1%t;3%/%?%p1%t;7%/' \
-e 's/smso=[^,]*,/smso=\\E[7m,/' \
-e 's/rmso=[^,]*,/rmso=\\E[27m,/' \
-e '$s/$/ sitm=\\E[3m, ritm=\\E[23m,/' > /tmp/screen.terminfo
$ tic /tmp/screen.terminfo
And tell tmux to use it in ~/.tmux.conf:
set -g default-terminal "screen-it"
If your terminal supports 256 colors, use:
$ screen_terminfo="screen-256color"
instead of "screen". See the FAQ entry about 256 colors support for more info.
Also note that tmux will still display reverse video on terminals that do not
support italics.
If your urxvt cannot display italics at all, make sure you have an italics
capable font enabled, for example, add to ~/.Xdefaults:
urxvt.italicFont: xft:Bitstream Vera Sans Mono:italic:autohint=true
* How can I make tmux use my terminal's scrollback buffer?
Normally, tmux enables the terminal's "alternate screen". Most terminals (such
as xterm) do not save scrollback for the alternate screen. You might prefer
tmux to use the normal screen, so it uses your terminal's scrollback
buffer. This way, you can access the scrollback buffer as usual, for example
using the mouse wheel - although there is no guarantee output inside tmux will
always (or ever) be added to the scrollback.
You can make tmux use the normal screen by telling it that your terminal does
not have an alternate screen. Put the following in ~/.tmux.conf:
set -ga terminal-overrides ',xterm*:smcup@:rmcup@'
Adjust if your $TERM does not start with xterm.
tmux will still emulate the alternate screen for applications run under tmux,
so you don't really lose anything with this setting. The only disadvantage is
that when you exit tmux, it will not restore whatever was there before you
started.
* How do I see the default configuration?
Show the default session options by starting a new tmux server with no
configuration file:
$ tmux -Lfoo -f/dev/null start\; show -g
Or the default window options:
$ tmux -Lfoo -f/dev/null start\; show -gw
* How do I copy a selection from tmux to the system's clipboard?
When running in xterm(1), tmux can automatically send copied text to the
clipboard. This is controlled by the set-clipboard option and also needs this
X resource to be set:
XTerm*disallowedWindowOps: 20,21,SetXprop
For rxvt-unicode (urxvt), there is an unofficial Perl extension here:
http://anti.teamidiot.de/static/nei/*/Code/urxvt/
Otherwise a key binding for copy mode using xclip (or xsel) works:
bind -temacs-copy C-y copy-pipe "xclip -i >/dev/null"
Or for inside and outside copy mode with the prefix key:
bind C-y run -b "tmux save-buffer - | xclip -i"
On OS X, reattach-to-usernamespace lets pbcopy/pbpaste work:
https://github.com/ChrisJohnsen/tmux-MacOSX-pasteboard
* Why do I see dots around a session when I attach to it?
tmux limits the size of the window to the smallest attached session. If
it didn't do this then it would be impossible to see the entire window.
The dots mark the size of the window tmux can display.
To avoid this, detach all other clients when attaching:
$ tmux attach -d
Or from inside tmux by detaching individual clients with C-b D or all
using:
C-b : attach -d
$Id$

View File

@@ -1,66 +1,66 @@
# $Id$
# Makefile.am
# Obvious program stuff.
bin_PROGRAMS = tmux
CLEANFILES = tmux.1.mdoc tmux.1.man
CLEANFILES = tmux.1.mdoc tmux.1.man cmd-parse.c
# Distribution tarball options.
EXTRA_DIST = \
CHANGES FAQ README TODO COPYING examples compat \
array.h compat.h tmux.h osdep-*.c mdoc2man.awk tmux.1
dist-hook:
make clean
grep "^#found_debug=" configure
find $(distdir) -name .svn -type d|xargs rm -Rf
CHANGES README README.ja COPYING example_tmux.conf \
osdep-*.c mdoc2man.awk tmux.1
dist_EXTRA_tmux_SOURCES = compat/*.[ch]
# Preprocessor flags.
CPPFLAGS += @XOPEN_DEFINES@ -DTMUX_CONF="\"$(sysconfdir)/tmux.conf\""
AM_CPPFLAGS += @XOPEN_DEFINES@ \
-DTMUX_VERSION="\"@VERSION@\"" \
-DTMUX_CONF="\"$(sysconfdir)/tmux.conf:~/.tmux.conf:~/.config/tmux/tmux.conf\""
# glibc as usual does things ass-backwards and hides useful things by default,
# so everyone has to add this.
if IS_GLIBC
CFLAGS += -D_GNU_SOURCE
endif
# Additional object files.
LDADD = $(LIBOBJS)
# Set flags for gcc. gcc4 whines abouts silly stuff so it needs slightly
# different flags.
# Set flags for gcc.
if IS_GCC
CFLAGS += -std=gnu99 -O2
AM_CFLAGS += -std=gnu99 -O2
if IS_DEBUG
CFLAGS += -g
CFLAGS += -Wno-long-long -Wall -W -Wnested-externs -Wformat=2
CFLAGS += -Wmissing-prototypes -Wstrict-prototypes -Wmissing-declarations
CFLAGS += -Wwrite-strings -Wshadow -Wpointer-arith -Wsign-compare
CFLAGS += -Wundef -Wbad-function-cast -Winline -Wcast-align
CFLAGS += -Wdeclaration-after-statement
CPPFLAGS += -DDEBUG
endif
if IS_GCC4
CPPFLAGS += -iquote.
if IS_DEBUG
CFLAGS += -Wno-pointer-sign
endif
else
CPPFLAGS += -I. -I-
AM_CFLAGS += -g
AM_CFLAGS += -Wno-long-long -Wall -W -Wformat=2
AM_CFLAGS += -Wmissing-prototypes -Wstrict-prototypes -Wmissing-declarations
AM_CFLAGS += -Wwrite-strings -Wshadow -Wpointer-arith -Wsign-compare
AM_CFLAGS += -Wundef -Wbad-function-cast -Winline -Wcast-align
AM_CFLAGS += -Wdeclaration-after-statement -Wno-pointer-sign -Wno-attributes
AM_CFLAGS += -Wno-unused-result
AM_CPPFLAGS += -DDEBUG
endif
AM_CPPFLAGS += -iquote.
endif
# Set flags for Solaris.
if IS_SUNOS
if IS_GCC
CPPFLAGS += -D_XPG6 -D__EXTENSIONS__ -D_POSIX_PTHREAD_SEMANTICS
AM_CPPFLAGS += -D_XPG6
else
CPPFLAGS += -D_XPG4_2 -D__EXTENSIONS__ -D_POSIX_PTHREAD_SEMANTICS
AM_CPPFLAGS += -D_XPG4_2
endif
endif
# Set flags for Sun CC.
if IS_SUNCC
CFLAGS += -erroff=E_EMPTY_DECLARATION
AM_CFLAGS += -erroff=E_EMPTY_DECLARATION
endif
# Set _LINUX_SOURCE_COMPAT for AIX for malloc(0).
if IS_AIX
AM_CPPFLAGS += -D_LINUX_SOURCE_COMPAT=1
endif
# Set flags for NetBSD.
if IS_NETBSD
AM_CPPFLAGS += -D_OPENBSD_SOURCE
endif
# List of sources.
dist_tmux_SOURCES = \
alerts.c \
arguments.c \
attributes.c \
cfg.c \
@@ -69,18 +69,16 @@ dist_tmux_SOURCES = \
cmd-bind-key.c \
cmd-break-pane.c \
cmd-capture-pane.c \
cmd-choose-buffer.c \
cmd-choose-client.c \
cmd-choose-tree.c \
cmd-clear-history.c \
cmd-command-prompt.c \
cmd-confirm-before.c \
cmd-copy-mode.c \
cmd-delete-buffer.c \
cmd-detach-client.c \
cmd-display-menu.c \
cmd-display-message.c \
cmd-display-panes.c \
cmd-find-window.c \
cmd-find.c \
cmd-if-shell.c \
cmd-join-pane.c \
cmd-kill-pane.c \
@@ -93,12 +91,12 @@ dist_tmux_SOURCES = \
cmd-list-panes.c \
cmd-list-sessions.c \
cmd-list-windows.c \
cmd-list.c \
cmd-load-buffer.c \
cmd-lock-server.c \
cmd-move-window.c \
cmd-new-session.c \
cmd-new-window.c \
cmd-parse.y \
cmd-paste-buffer.c \
cmd-pipe-pane.c \
cmd-queue.c \
@@ -106,6 +104,7 @@ dist_tmux_SOURCES = \
cmd-rename-session.c \
cmd-rename-window.c \
cmd-resize-pane.c \
cmd-resize-window.c \
cmd-respawn-pane.c \
cmd-respawn-window.c \
cmd-rotate-window.c \
@@ -123,7 +122,6 @@ dist_tmux_SOURCES = \
cmd-show-options.c \
cmd-source-file.c \
cmd-split-window.c \
cmd-string.c \
cmd-swap-pane.c \
cmd-swap-window.c \
cmd-switch-client.c \
@@ -131,11 +129,13 @@ dist_tmux_SOURCES = \
cmd-wait-for.c \
cmd.c \
colour.c \
control.c \
compat.h \
control-notify.c \
control.c \
environ.c \
file.c \
format.c \
grid-cell.c \
format-draw.c \
grid-view.c \
grid.c \
input-keys.c \
@@ -147,92 +147,52 @@ dist_tmux_SOURCES = \
layout-set.c \
layout.c \
log.c \
mode-key.c \
menu.c \
mode-tree.c \
names.c \
notify.c \
options-table.c \
options.c \
paste.c \
proc.c \
regsub.c \
resize.c \
screen-redraw.c \
screen-write.c \
screen.c \
server-client.c \
server-fn.c \
server-window.c \
server.c \
session.c \
signal.c \
spawn.c \
status.c \
style.c \
tmux.c \
tmux.h \
tty-acs.c \
tty-keys.c \
tty-term.c \
tty.c \
utf8.c \
window-choose.c \
window-buffer.c \
window-client.c \
window-clock.c \
window-copy.c \
window-tree.c \
window.c \
xmalloc.c \
xmalloc.h \
xterm-keys.c
nodist_tmux_SOURCES = osdep-@PLATFORM@.c
# Pile in all the compat/ stuff that is needed.
if NO_FORKPTY
# Add compat file for forkpty.
if NEED_FORKPTY
nodist_tmux_SOURCES += compat/forkpty-@PLATFORM@.c
endif
if NO_IMSG
nodist_tmux_SOURCES += compat/imsg.c compat/imsg-buffer.c
endif
if NO_CLOSEFROM
nodist_tmux_SOURCES += compat/closefrom.c
endif
if NO_DAEMON
nodist_tmux_SOURCES += compat/daemon.c
endif
if NO_SETENV
nodist_tmux_SOURCES += compat/setenv.c
endif
if NO_STRLCAT
nodist_tmux_SOURCES += compat/strlcat.c
endif
if NO_STRLCPY
nodist_tmux_SOURCES += compat/strlcpy.c
endif
if NO_ASPRINTF
nodist_tmux_SOURCES += compat/asprintf.c
endif
if NO_FGETLN
nodist_tmux_SOURCES += compat/fgetln.c
endif
if NO_FPARSELN
nodist_tmux_SOURCES += compat/fparseln.c
endif
if NO_GETOPT
nodist_tmux_SOURCES += compat/getopt.c
endif
if NO_STRCASESTR
nodist_tmux_SOURCES += compat/strcasestr.c
endif
if NO_STRSEP
nodist_tmux_SOURCES += compat/strsep.c
endif
if NO_VIS
nodist_tmux_SOURCES += compat/vis.c compat/unvis.c
endif
if NO_STRTONUM
nodist_tmux_SOURCES += compat/strtonum.c
endif
if NO_B64_NTOP
nodist_tmux_SOURCES += compat/b64_ntop.c
endif
if NO_CFMAKERAW
nodist_tmux_SOURCES += compat/cfmakeraw.c
endif
if NO_OPENAT
nodist_tmux_SOURCES += compat/openat.c
# Add compat file for utf8proc.
if HAVE_UTF8PROC
nodist_tmux_SOURCES += compat/utf8proc.c
endif
# Install tmux.1 in the right format.
@@ -242,23 +202,8 @@ install-exec-hook:
>$(srcdir)/tmux.1.mdoc; \
else \
sed -e "s|@SYSCONFDIR@|$(sysconfdir)|g" $(srcdir)/tmux.1| \
$(AWK) -f$(srcdir)/mdoc2man.awk >$(srcdir)/tmux.1.man; \
$(AWK) -f $(srcdir)/mdoc2man.awk >$(srcdir)/tmux.1.man; \
fi
$(mkdir_p) $(DESTDIR)$(mandir)/man1
$(INSTALL_DATA) $(srcdir)/tmux.1.@MANFORMAT@ \
$(DESTDIR)$(mandir)/man1/tmux.1
# Update SF web site.
upload-index.html: update-index.html
scp www/index.html www/main.css www/images/*.png \
${USER},tmux@web.sf.net:/home/groups/t/tm/tmux/htdocs
rm -f www/index.html www/images/small-*
update-index.html:
(cd www/images && \
rm -f small-* && \
for i in *.png; do \
convert "$$i" -resize 200x150 "small-$$i"; \
done \
)
sed "s/%%RELEASE%%/${RELEASE}/g" www/index.html.in >www/index.html

91
README
View File

@@ -1,60 +1,75 @@
Welcome to tmux!
tmux is a "terminal multiplexer", it enables a number of terminals (or windows)
to be accessed and controlled from a single terminal. tmux is intended to be a
simple, modern, BSD-licensed alternative to programs such as GNU screen.
tmux is a terminal multiplexer: it enables a number of terminals to be created,
accessed, and controlled from a single screen. tmux may be detached from a
screen and continue running in the background, then later reattached.
This release runs on OpenBSD, FreeBSD, NetBSD, Linux and OS X and may still
run on Solaris and AIX (although they haven't been tested in a while).
This release runs on OpenBSD, FreeBSD, NetBSD, Linux, OS X and Solaris.
tmux depends on libevent 2.x. Download it from:
* Dependencies
http://www.monkey.org/~provos/libevent/
tmux depends on libevent 2.x, available from:
To build tmux from a release tarball, do:
https://github.com/libevent/libevent/releases/latest
It also depends on ncurses, available from:
https://invisible-mirror.net/archives/ncurses/
* Installation
To build and install tmux from a release tarball, use:
$ ./configure && make
$ sudo make install
To get and build the latest from version control:
tmux can use the utempter library to update utmp(5), if it is installed - run
configure with --enable-utempter to enable this.
$ git clone git://git.code.sf.net/p/tmux/tmux-code tmux
To get and build the latest from version control - note that this requires
autoconf, automake and pkg-config:
$ git clone https://github.com/tmux/tmux.git
$ cd tmux
$ sh autogen.sh
$ ./configure && make
For more information see https://sourceforge.net/scm/?type=git&group_id=200378
and http://git-scm.com. Patches should be sent by email to the mailing list at
tmux-users@lists.sourceforge.net.
For documentation on using tmux, see the tmux.1 manpage. It can be viewed from
the source tree with:
$ nroff -mdoc tmux.1|less
Some common questions are answered in the FAQ file and a more extensive (but
slightly out of date) guide is available in the OpenBSD FAQ at
http://www.openbsd.org/faq/faq7.html#tmux. A rough todo list is in the TODO
file and some example configurations and a Vim syntax file are in the examples
directory.
For debugging, running tmux with -v or -vv will generate server and client log
files in the current directory.
tmux mailing lists are available. Visit:
https://sourceforge.net/mail/?group_id=200378
* Contributing
Bug reports, feature suggestions and especially code contributions are most
welcome. Please send by email to:
tmux-users@lists.sourceforge.net
tmux-users@googlegroups.com
This file and the CHANGES, FAQ and TODO files are licensed under the ISC
license. Files under examples/ remain copyright their authors unless otherwise
stated in the file but permission has been received to distribute them with
tmux. All other files have a license and copyright notice at their start.
Or open a GitHub issue or pull request.
-- Nicholas Marriott <nicm@users.sf.net>
* Documentation
$Id$
For documentation on using tmux, see the tmux.1 manpage. View it from the
source tree with:
$ nroff -mdoc tmux.1|less
A small example configuration is in example_tmux.conf.
A bash(1) completion file is at:
https://github.com/imomaliev/tmux-bash-completion
For debugging, run tmux with -v and -vv to generate server and client log files
in the current directory.
* Support
The tmux mailing list for general discussion and bug reports is:
https://groups.google.com/forum/#!forum/tmux-users
Subscribe by sending an email to:
tmux-users+subscribe@googlegroups.com
* License
This file and the CHANGES files are licensed under the ISC license. All other
files have a license and copyright notice at their start.

62
README.ja Normal file
View File

@@ -0,0 +1,62 @@
tmuxへようこそ!
tmuxはターミナルマルチプレクサーです。複数のターミナルを一つのスクリーン内に作成し、操作することができます。
バックグラウンドで処理を実行中に一度スクリーンから離れて後から復帰することも可能です。
OpenBSD、FreeBSD、NetBSD、Linux、OS X、Solarisで実行できます。
tmuxはlibevent 2.x.に依存します。 下記からダウンロードしてください。
http://libevent.org
また、ncursesも必要です。こちらからどうぞ。
http://invisible-island.net/ncurses/
tarballでのtmuxのビルドとインストール方法。
$ ./configure && make
$ sudo make install
tmuxはutmp(5)をアップデートするためにutempterを使うことができます。もしインストール済みであればオプション「--enable-utempter」をつけて実行してください。
リポジトリから最新バージョンを手に入れるためには下記を実行。
$ git clone https://github.com/tmux/tmux.git
$ cd tmux
$ sh autogen.sh
$ ./configure && make
(ビルドのためにはlibevent、ncurses libraries、headersに加えて、C compiler、make、autoconf、automake、pkg-configが必要です。)
詳しい情報はhttp://git-scm.comをご覧ください。修正はメール<tmux-users@googlegroups.com>宛、もしくはhttps://github.com/tmux/tmux/issuesにて受け付けています。
tmuxのドキュメントについてはtmux.1マニュアルをご覧ください。こちらのコマンドで参照可能です。
$ nroff -mdoc tmux.1|less
サンプル設定は本リポジトリのexample_tmux.confに
また、bash-completionファイルは下記にあります。
https://github.com/imomaliev/tmux-bash-completion
「-v」や「-vv」を指定することでデバッグモードでの起動が可能です。カレントディレクトリにサーバーやクライアントのログファイルが生成されます。
議論やバグレポート用のメーリングリストにはこちらから参加可能です。
https://groups.google.com/forum/#!forum/tmux-users
gitコミットについての連絡先
https://groups.google.com/forum/#!forum/tmux-git
購読は<tmux-users+subscribe@googlegroups.com>までメールをお願いします。
バグレポートや機能追加(特にコードへの貢献)は大歓迎です。こちらにご連絡ください。
tmux-users@googlegroups.com
本ファイル、CHANGES、 FAQ、SYNCINGそしてTODOはISC licenseで保護されています。
その他のファイルのライセンスや著作権については、ファイルの上部に明記されています。
-- Nicholas Marriott <nicholas.marriott@gmail.com>

82
SYNCING
View File

@@ -1,10 +1,10 @@
Preamble
========
Tmux on SourceForge has two git repositories [1] "tmux-code" and "tmux-openbsd".
Tmux portable relies on repositories "tmux" and "tmux-openbsd".
Here's a description of them:
* "tmux-code" is the portable version, the one which contains code for other
* "tmux" is the portable version, the one which contains code for other
operating systems, and autotools, etc., which isn't found or needed in the
OpenBSD base system.
@@ -17,9 +17,6 @@ repository will take at least that long to appear in this git repository.
(It might take longer, depending on the CVS mirror used to import the
OpenBSD code).
It is assumed that the person doing the sync has read/write access to the
tmux-code repository on SourceForge already.
If you've never used git before, git tracks meta-data about the committer
and the author, as part of a commit, hence:
@@ -37,11 +34,11 @@ this information has ever been set before.
Cloning repositories
====================
This involves having both tmux-code and tmux-openbsd cloned, as in:
This involves having both tmux and tmux-openbsd cloned, as in:
% cd /some/where/useful
% git clone ssh://${USER}@git.code.sf.net/p/tmux/tmux
% git clone ssh://${USER}@git.code.sf.net/p/tmux/tmux-openbsd
% git clone https://github.com/tmux/tmux.git
% git clone https://github.com/ThomasAdam/tmux-openbsd.git
Note that you do not need additional checkouts to manage the sync -- an
existing clone of either repositories will suffice. So if you already have
@@ -50,56 +47,56 @@ these checkouts existing, skip that.
Adding in git-remotes
=====================
Because the portable "tmux-code" git repository and the "tmux-openbsd"
Because the portable "tmux" git repository and the "tmux-openbsd"
repository do not inherently share any history between each other, the
history has been faked between them. This "faking of history" is something
which has to be told to git for the purposes of comparing the "tmux" and
"tmux-openbsd" repositories for syncing. To do this, we must reference the
clone of the "tmux-openbsd" repository from the "tmux-code" repository, as
clone of the "tmux-openbsd" repository from the "tmux" repository, as
shown by the following command:
% cd /path/to/tmux-code
% cd /path/to/tmux
% git remote add obsd-tmux file:///path/to/tmux-openbsd
So that now, the remote "obsd-tmux" can be used to reference branches and
commits from the "tmux-openbsd" repository, but from the context of the
portable "tmux-code" repository, which makes sense because it's the "tmux"
portable "tmux" repository, which makes sense because it's the "tmux"
repository which will have the updates applied to them.
Fetching updates
================
To ensure the latest commits from "tmux-openbsd" can be found from within
"tmux-code", we have to ensure the "master" branch from "tmux-openbsd" is
up-to-date first, and then reference that update in "tmux-code", as in:
"tmux", we have to ensure the "master" branch from "tmux-openbsd" is
up-to-date first, and then reference that update in "tmux", as in:
% cd /path/to/tmux-openbsd
% git checkout master
% git pull
Then back in "tmux-code":
Then back in "tmux":
% cd /path/to/tmux-code
% git fetch obsd-tmux-code
% cd /path/to/tmux
% git fetch obsd-tmux
Creating the necessary branches
===============================
Now that "tmux-code" can see commits and branches from "tmux-openbsd" by way
Now that "tmux" can see commits and branches from "tmux-openbsd" by way
of the remote name "obsd-tmux", we can now create the master branch from
"tmux-openbsd" in the "tmux-code" repository:
"tmux-openbsd" in the "tmux" repository:
% git checkout -b obsd-master obsd-tmux/master
Adding in the fake history points
=================================
To tie both the "master" branch from "tmux-code" and the "obsd-master"
To tie both the "master" branch from "tmux" and the "obsd-master"
branch from "tmux-openbsd" together, the fake history points added to the
"tmux-code" repository need to be added. To do this, we must add an
"tmux" repository need to be added. To do this, we must add an
additional refspec line, as in:
% cd /path/to/tmux-code
% cd /path/to/tmux
% git config --add remote.origin.fetch '+refs/replace/*:refs/replace/*'
% git fetch origin
@@ -110,7 +107,7 @@ Make sure the "master" branch is checked out:
% git checkout master
The following will show commits on OpenBSD not yet synched with "tmux-code":
The following will show commits on OpenBSD not yet synched with "tmux":
% git log master..obsd-master
@@ -118,7 +115,7 @@ From there, merge the result in, fixing up any conflicts which might arise.
% git merge obsd-master
Then ensure things look correct by BULDING the result of that sync:
Then ensure things look correct by BUILDING the result of that sync:
% make clean && ./autogen.sh && ./configure && make
@@ -143,41 +140,34 @@ to compat/ as and when appropriate.
Release tmux for next version
=============================
1. Comment the "found_debug=yes" line in configure.ac, since releases
don't have debugging enabled, otherwise make(1) aborts when
preparing the distribution.
2. Update and commit README and CHANGES. The former should be checked for
1. Update and commit README and CHANGES. The former should be checked for
anything outdated and updated with a list of things that might break
upgrades and the latter should mention all the major changes since
the last version.
2. Make sure configure.ac has the new version number.
3. Tag with:
% git tag -a 1.X
% git tag -a 2.X
Where "1.X" is the next version.
Where "2.X" is the next version.
Push the tag out with:
% git push 1.X
% git push --tags
4. Build the tarball with make dist. Now that it's using autoconf there
shouldn't be any weird files (such as the original and rejection files
from patch(1)) but it doesn't hurt taking a quick look at it.
4. Build the tarball with 'make dist'.
5. Split the release changes into a new file. This should be named
tmux-$VERSION-readme to make sourceforge show it automagically in specific
parts of the project page.
5. Check the tarball. If it's good, go here to select the tag just pushed:
6. Upload the tarball and the above file. Make the tarball the default
download by selecting all operating systems under the file details.
https://github.com/tmux/tmux/tags
7. Run make update-index.html upload-index.html to replace %%VERSION%%.
Click the "Add release notes", upload the tarball and add a link in the
description field to the CHANGES file.
8. Bump version in configure.ac and uncomment "found_debug=yes" to create
a debug build by default.
6. Clone the tmux.github.io repository, and change the RELEASE version in the
Makefile. Commit it, and run 'make' to replace %%RELEASE%%. Push the
result out.
9. Update freshmeat.
[1] https://sourceforge.net/p/tmux/_list/git
7. Change version back to master in configure.ac.

155
TODO
View File

@@ -1,155 +0,0 @@
- command bits and pieces:
* why doesn't command-prompt work if made read-only?
* allow multiple targets: fnmatch for -t/-c, for example detach all
clients with -t*
* add -c for new-session like new-window
* attach should take a pane and select it as well as attaching
* ' and " should be parsed the same (eg "\e" vs '\e') in config
and command prompt
* last-pane across sessions
* exact match operator for targets (or break the substring match
and require eg x* instead of just x)
- make command sequences more usable
* don't require space after ;
* options for error handling: && and ||?
- options bits and pieces:
* set-remain-on-exit is a complete hack
* way to set socket path from config file
- format improvements:
* last bits of status_replace into formats?
* option to quote format (#{session_name:quoted})
* formats need conditions for >0 (for #P)
* some way to pad # stuff with spaces, #!2T maybe
* last window update time and format for it
* formats to show if a window is linked into multiple sessions, into
multiple attached sessions, and is the active window in multiple
attached sessions?
- choose mode improvements:
* choose-pane command (augment choose-tree to do this?)
* choose-mode and copy-mode are very similar, make choose-mode a subset?
* flag to choose-* for sort order
* choose mode would be better per client than per window?
* two choices (first one then second, for swap-pane and join-pane)
- improve monitor-*:
* straighten out rules for multiple clients
* think about what happens across sessions
* monitor changes within a region
* perhaps monitor /all/ panes in the window not just one
- improve mouse support:
* bind commands to mouse in different areas?
* more fine-grained options?
* commands executed when clicking on a pattern (URL)
* mouse-select-pane will screw up with !MODE_MOUSE_STANDARD (it sets
the flag on w/o checking the others before calling tty_update_mode)
* mouse can be like normal key bindings?
- {button-{1,2,3},wheel-{up,down}}-{status,pane,border} and
drag-{start,end}-{status,pane,border} plus the modifiers
- resize and copy can be special cases - once you call something
like copy-mode -M or resize-pane -M to start the drag, it tracks
mouse until you call -m to stop the drag. or just keep drags
entirely special?
- what happens with stuff that wants mouse inside? especially for
pane clicks which need to run command AND pass event through
(like mouse-select-pane). maybe just a flag to say whether it
always runs or only if pane hasn't taken mouse? or it could be
eg bind Button1Pane "select-pane -t=; send-keys -Mt='
- also need a) some way to tell commands bound to key which
window or pane the mouse key binding applies to (maybe a new
special char in target, or pass targets through formats?) b) a
way to bind repeat count to mode keys so that wheel up/down can
do multiple lines c) send-keys -M to pass a mouse event through?
- what does the mouse->KEYC_* conversion and find-the-pane bit?
server_client_handle_key?
- hooks!
- warts on current naming:
* display-time but message-fg/bg/attr
* list-* vs show-*
* split-window -> split-pane??
- better UTF-8 support:
* window names and titles
* message display
* prompt input
* multibyte key input
- copy/paste improvements:
* incremental searching
* append to buffer
* paste w/o trailing whitespace
* command to toggle selection not to move it in copy-mode
- layout stuff
* way to tag a layout as a number/name
* maybe keep last layout + size around and if size reverts just put it
back
* revamp layouts: they are too complicated, should be more closely
integrated, should support hints, layout sets should just be a
special case of custom layouts, and we should support panes that are
not attached to a cell at all. this could be the time to introduce
panelink to replace layout_cell
* way to set hints/limits about pane size for resizing
* panning over window (window larger than visible)
* a mode where one application can cross two panes (ie x|y, width =
COLUMNS/2 but height = ROWS * 2)
* general key to space cells out evenly (horiz or vert) within their
parent cell (could replace even-vert/even-horiz layouts)
- terminfo bits
* use a better termcap internally instead of screen, perhaps xterm
* use screen-256color when started on 256 colour terminal?
* need a tmux terminfo entry to document the extensions we are using in
upstream terminfo
- code cleanup
* instead of separate window and session options, just one master
options list with each option having a type (window or session), then
options on window, on session, and global. for window options we look
window->session->global, and for session we look session->global
* the way pane, window, session destroy is handled is too complicated
and the distinction between session.c, window.c and server-fn.c
functions is not clear. could we just have kill_pane(),
kill_window(), unlink_window(), kill_session() that fix up all data
structures (flagging sessions as dead) and return a value to say
whether clients need to be checked for dead sessions? sort of like
session_detach now but more so. or some other scheme to make it
simpler and clearer? also would be nice to remove/rename server-fn.c
* more readable way to work out the various things commands need to
know about the client, notably:
- is this the config file? (cmdq->c == NULL)
- is this a command client? (cmdq->c != NULL &&
cmdq->c->session == NULL)
- is this a control client?
- can i do stdin or stdout to this client?
or even guarantee that cmdq->c != NULL and provide a better way to
tell when in the config file - then we use cmdq->c if we need a
client w/o a session else cmd_current_client
* optimize pane redraws, 20120318184853.GK10965@yelena.nicm.ath.cx
* cmd_find_* could be much simpler - parse everything the same, only
difference is what to choose when not given a ":" or "." (such as a
plain "0" could be session, window or pane). So just cmd_find_target
with a type (session, window, or pane)..
- miscellaneous
* way to keep a job running just read its last line of output for #()
* link panes into multiple windows
* live update: server started with -U connects to server, requests
sessions and windows, receives file descriptors
* there are inconsistencies in what we get from old shell and what
comes from config for new sessions and windows. likewise, panes and
jobs and run-shell and lock command all start with slightly different
environments
* multiline status line?
* bind commands to key sequences -- make it so ALL keys go through a
table, first an implicit table in which C-b is the only default
binding to a command that says "next key from $othertable" and so
on. means -n can go away as well
* customizable command aliases
* any remaining clients in wait-for should be woken when server exits

323
alerts.c Normal file
View File

@@ -0,0 +1,323 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2015 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* 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 <event.h>
#include <stdlib.h>
#include "tmux.h"
static int alerts_fired;
static void alerts_timer(int, short, void *);
static int alerts_enabled(struct window *, int);
static void alerts_callback(int, short, void *);
static void alerts_reset(struct window *);
static int alerts_action_applies(struct winlink *, const char *);
static int alerts_check_all(struct window *);
static int alerts_check_bell(struct window *);
static int alerts_check_activity(struct window *);
static int alerts_check_silence(struct window *);
static void alerts_set_message(struct winlink *, const char *,
const char *);
static TAILQ_HEAD(, window) alerts_list = TAILQ_HEAD_INITIALIZER(alerts_list);
static void
alerts_timer(__unused int fd, __unused short events, void *arg)
{
struct window *w = arg;
log_debug("@%u alerts timer expired", w->id);
alerts_queue(w, WINDOW_SILENCE);
}
static void
alerts_callback(__unused int fd, __unused short events, __unused void *arg)
{
struct window *w, *w1;
int alerts;
TAILQ_FOREACH_SAFE(w, &alerts_list, alerts_entry, w1) {
alerts = alerts_check_all(w);
log_debug("@%u alerts check, alerts %#x", w->id, alerts);
w->alerts_queued = 0;
TAILQ_REMOVE(&alerts_list, w, alerts_entry);
w->flags &= ~WINDOW_ALERTFLAGS;
window_remove_ref(w, __func__);
}
alerts_fired = 0;
}
static int
alerts_action_applies(struct winlink *wl, const char *name)
{
int action;
/*
* {bell,activity,silence}-action determines when to alert: none means
* nothing happens, current means only do something for the current
* window and other means only for windows other than the current.
*/
action = options_get_number(wl->session->options, name);
if (action == ALERT_ANY)
return (1);
if (action == ALERT_CURRENT)
return (wl == wl->session->curw);
if (action == ALERT_OTHER)
return (wl != wl->session->curw);
return (0);
}
static int
alerts_check_all(struct window *w)
{
int alerts;
alerts = alerts_check_bell(w);
alerts |= alerts_check_activity(w);
alerts |= alerts_check_silence(w);
return (alerts);
}
void
alerts_check_session(struct session *s)
{
struct winlink *wl;
RB_FOREACH(wl, winlinks, &s->windows)
alerts_check_all(wl->window);
}
static int
alerts_enabled(struct window *w, int flags)
{
if (flags & WINDOW_BELL) {
if (options_get_number(w->options, "monitor-bell"))
return (1);
}
if (flags & WINDOW_ACTIVITY) {
if (options_get_number(w->options, "monitor-activity"))
return (1);
}
if (flags & WINDOW_SILENCE) {
if (options_get_number(w->options, "monitor-silence") != 0)
return (1);
}
return (0);
}
void
alerts_reset_all(void)
{
struct window *w;
RB_FOREACH(w, windows, &windows)
alerts_reset(w);
}
static void
alerts_reset(struct window *w)
{
struct timeval tv;
if (!event_initialized(&w->alerts_timer))
evtimer_set(&w->alerts_timer, alerts_timer, w);
w->flags &= ~WINDOW_SILENCE;
event_del(&w->alerts_timer);
timerclear(&tv);
tv.tv_sec = options_get_number(w->options, "monitor-silence");
log_debug("@%u alerts timer reset %u", w->id, (u_int)tv.tv_sec);
if (tv.tv_sec != 0)
event_add(&w->alerts_timer, &tv);
}
void
alerts_queue(struct window *w, int flags)
{
alerts_reset(w);
if ((w->flags & flags) != flags) {
w->flags |= flags;
log_debug("@%u alerts flags added %#x", w->id, flags);
}
if (alerts_enabled(w, flags)) {
if (!w->alerts_queued) {
w->alerts_queued = 1;
TAILQ_INSERT_TAIL(&alerts_list, w, alerts_entry);
window_add_ref(w, __func__);
}
if (!alerts_fired) {
log_debug("alerts check queued (by @%u)", w->id);
event_once(-1, EV_TIMEOUT, alerts_callback, NULL, NULL);
alerts_fired = 1;
}
}
}
static int
alerts_check_bell(struct window *w)
{
struct winlink *wl;
struct session *s;
if (~w->flags & WINDOW_BELL)
return (0);
if (!options_get_number(w->options, "monitor-bell"))
return (0);
TAILQ_FOREACH(wl, &w->winlinks, wentry)
wl->session->flags &= ~SESSION_ALERTED;
TAILQ_FOREACH(wl, &w->winlinks, wentry) {
/*
* Bells are allowed even if there is an existing bell (so do
* not check WINLINK_BELL).
*/
s = wl->session;
if (s->curw != wl) {
wl->flags |= WINLINK_BELL;
server_status_session(s);
}
if (!alerts_action_applies(wl, "bell-action"))
continue;
notify_winlink("alert-bell", wl);
if (s->flags & SESSION_ALERTED)
continue;
s->flags |= SESSION_ALERTED;
alerts_set_message(wl, "Bell", "visual-bell");
}
return (WINDOW_BELL);
}
static int
alerts_check_activity(struct window *w)
{
struct winlink *wl;
struct session *s;
if (~w->flags & WINDOW_ACTIVITY)
return (0);
if (!options_get_number(w->options, "monitor-activity"))
return (0);
TAILQ_FOREACH(wl, &w->winlinks, wentry)
wl->session->flags &= ~SESSION_ALERTED;
TAILQ_FOREACH(wl, &w->winlinks, wentry) {
if (wl->flags & WINLINK_ACTIVITY)
continue;
s = wl->session;
if (s->curw != wl) {
wl->flags |= WINLINK_ACTIVITY;
server_status_session(s);
}
if (!alerts_action_applies(wl, "activity-action"))
continue;
notify_winlink("alert-activity", wl);
if (s->flags & SESSION_ALERTED)
continue;
s->flags |= SESSION_ALERTED;
alerts_set_message(wl, "Activity", "visual-activity");
}
return (WINDOW_ACTIVITY);
}
static int
alerts_check_silence(struct window *w)
{
struct winlink *wl;
struct session *s;
if (~w->flags & WINDOW_SILENCE)
return (0);
if (options_get_number(w->options, "monitor-silence") == 0)
return (0);
TAILQ_FOREACH(wl, &w->winlinks, wentry)
wl->session->flags &= ~SESSION_ALERTED;
TAILQ_FOREACH(wl, &w->winlinks, wentry) {
if (wl->flags & WINLINK_SILENCE)
continue;
s = wl->session;
if (s->curw != wl) {
wl->flags |= WINLINK_SILENCE;
server_status_session(s);
}
if (!alerts_action_applies(wl, "silence-action"))
continue;
notify_winlink("alert-silence", wl);
if (s->flags & SESSION_ALERTED)
continue;
s->flags |= SESSION_ALERTED;
alerts_set_message(wl, "Silence", "visual-silence");
}
return (WINDOW_SILENCE);
}
static void
alerts_set_message(struct winlink *wl, const char *type, const char *option)
{
struct client *c;
int visual;
/*
* We have found an alert (bell, activity or silence), so we need to
* pass it on to the user. For each client attached to this session,
* decide whether a bell, message or both is needed.
*
* If visual-{bell,activity,silence} is on, then a message is
* substituted for a bell; if it is off, a bell is sent as normal; both
* mean both a bell and message is sent.
*/
visual = options_get_number(wl->session->options, option);
TAILQ_FOREACH(c, &clients, entry) {
if (c->session != wl->session || c->flags & CLIENT_CONTROL)
continue;
if (visual == VISUAL_OFF || visual == VISUAL_BOTH)
tty_putcode(&c->tty, TTYC_BEL);
if (visual == VISUAL_OFF)
continue;
if (c->session->curw == wl)
status_message_set(c, "%s in current window", type);
else
status_message_set(c, "%s in window %d", type, wl->idx);
}
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2010 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2010 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,7 +18,6 @@
#include <sys/types.h>
#include <getopt.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
@@ -29,43 +28,33 @@
* Manipulate command arguments.
*/
struct args_entry *args_find(struct args *, u_char);
struct args_value {
char *value;
TAILQ_ENTRY(args_value) entry;
};
TAILQ_HEAD(args_values, args_value);
RB_GENERATE(args_tree, args_entry, entry, args_cmp);
struct args_entry {
u_char flag;
struct args_values values;
u_int count;
RB_ENTRY(args_entry) entry;
};
static struct args_entry *args_find(struct args *, u_char);
static int args_cmp(struct args_entry *, struct args_entry *);
RB_GENERATE_STATIC(args_tree, args_entry, entry, args_cmp);
/* Arguments tree comparison function. */
int
static int
args_cmp(struct args_entry *a1, struct args_entry *a2)
{
return (a1->flag - a2->flag);
}
/* 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);
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);
}
/* Find a flag in the arguments tree. */
struct args_entry *
static struct args_entry *
args_find(struct args *args, u_char ch)
{
struct args_entry entry;
@@ -85,6 +74,7 @@ args_parse(const char *template, int argc, char **argv)
optreset = 1;
optind = 1;
optarg = NULL;
while ((opt = getopt(argc, argv, template)) != -1) {
if (opt < 0)
@@ -94,6 +84,7 @@ args_parse(const char *template, int argc, char **argv)
return (NULL);
}
args_set(args, opt, optarg);
optarg = NULL;
}
argc -= optind;
argv += optind;
@@ -110,116 +101,183 @@ args_free(struct args *args)
{
struct args_entry *entry;
struct args_entry *entry1;
struct args_value *value;
struct args_value *value1;
cmd_free_argv(args->argc, args->argv);
RB_FOREACH_SAFE(entry, args_tree, &args->tree, entry1) {
RB_REMOVE(args_tree, &args->tree, entry);
free(entry->value);
TAILQ_FOREACH_SAFE(value, &entry->values, entry, value1) {
TAILQ_REMOVE(&entry->values, value, entry);
free(value->value);
free(value);
}
free(entry);
}
free(args);
}
/* Print a set of arguments. */
size_t
args_print(struct args *args, char *buf, size_t len)
/* Add to string. */
static void printflike(3, 4)
args_print_add(char **buf, size_t *len, const char *fmt, ...)
{
size_t off, used;
int i;
const char *quotes;
struct args_entry *entry;
va_list ap;
char *s;
size_t slen;
/* There must be at least one byte at the start. */
if (len == 0)
return (0);
off = 0;
va_start(ap, fmt);
slen = xvasprintf(&s, fmt, ap);
va_end(ap);
*len += slen;
*buf = xrealloc(*buf, *len);
strlcat(*buf, s, *len);
free(s);
}
/* Add value to string. */
static void
args_print_add_value(char **buf, size_t *len, struct args_entry *entry,
struct args_value *value)
{
char *escaped;
if (**buf != '\0')
args_print_add(buf, len, " -%c ", entry->flag);
else
args_print_add(buf, len, "-%c ", entry->flag);
escaped = args_escape(value->value);
args_print_add(buf, len, "%s", escaped);
free(escaped);
}
/* Add argument to string. */
static void
args_print_add_argument(char **buf, size_t *len, const char *argument)
{
char *escaped;
if (**buf != '\0')
args_print_add(buf, len, " ");
escaped = args_escape(argument);
args_print_add(buf, len, "%s", escaped);
free(escaped);
}
/* Print a set of arguments. */
char *
args_print(struct args *args)
{
size_t len;
char *buf;
int i;
u_int j;
struct args_entry *entry;
struct args_value *value;
len = 1;
buf = xcalloc(1, len);
/* Process the flags first. */
buf[off++] = '-';
RB_FOREACH(entry, args_tree, &args->tree) {
if (entry->value != NULL)
if (!TAILQ_EMPTY(&entry->values))
continue;
if (off == len - 1) {
buf[off] = '\0';
return (len);
}
buf[off++] = entry->flag;
buf[off] = '\0';
if (*buf == '\0')
args_print_add(&buf, &len, "-");
for (j = 0; j < entry->count; j++)
args_print_add(&buf, &len, "%c", entry->flag);
}
if (off == 1)
buf[--off] = '\0';
/* Then the flags with arguments. */
RB_FOREACH(entry, args_tree, &args->tree) {
if (entry->value == NULL)
continue;
if (off >= len) {
/* snprintf will have zero terminated. */
return (len);
}
if (strchr(entry->value, ' ') != NULL)
quotes = "\"";
else
quotes = "";
used = xsnprintf(buf + off, len - off, "%s-%c %s%s%s",
off != 0 ? " " : "", entry->flag, quotes, entry->value,
quotes);
if (used > len - off)
used = len - off;
off += used;
TAILQ_FOREACH(value, &entry->values, entry)
args_print_add_value(&buf, &len, entry, value);
}
/* And finally the argument vector. */
for (i = 0; i < args->argc; i++) {
if (off >= len) {
/* snprintf will have zero terminated. */
return (len);
}
for (i = 0; i < args->argc; i++)
args_print_add_argument(&buf, &len, args->argv[i]);
if (strchr(args->argv[i], ' ') != NULL)
quotes = "\"";
else
quotes = "";
used = xsnprintf(buf + off, len - off, "%s%s%s%s",
off != 0 ? " " : "", quotes, args->argv[i], quotes);
if (used > len - off)
used = len - off;
off += used;
return (buf);
}
/* Escape an argument. */
char *
args_escape(const char *s)
{
static const char quoted[] = " #\"';${}";
char *escaped, *result;
int flags;
if (*s == '\0')
return (xstrdup(s));
if (s[0] != ' ' &&
(strchr(quoted, s[0]) != NULL || s[0] == '~') &&
s[1] == '\0') {
xasprintf(&escaped, "\\%c", s[0]);
return (escaped);
}
return (off);
flags = VIS_OCTAL|VIS_CSTYLE|VIS_TAB|VIS_NL;
if (s[strcspn(s, quoted)] != '\0')
flags |= VIS_DQ;
utf8_stravis(&escaped, s, flags);
if (flags & VIS_DQ) {
if (*escaped == '~')
xasprintf(&result, "\"\\%s\"", escaped);
else
xasprintf(&result, "\"%s\"", escaped);
} else {
if (*escaped == '~')
xasprintf(&result, "\\%s", escaped);
else
result = xstrdup(escaped);
}
free(escaped);
return (result);
}
/* Return if an argument is present. */
int
args_has(struct args *args, u_char ch)
{
return (args_find(args, ch) == NULL ? 0 : 1);
struct args_entry *entry;
entry = args_find(args, ch);
if (entry == NULL)
return (0);
return (entry->count);
}
/* Set argument value in the arguments tree. */
void
args_set(struct args *args, u_char ch, const char *value)
args_set(struct args *args, u_char ch, const char *s)
{
struct args_entry *entry;
struct args_value *value;
/* Replace existing argument. */
if ((entry = args_find(args, ch)) != NULL) {
free(entry->value);
entry->value = NULL;
} else {
entry = args_find(args, ch);
if (entry == NULL) {
entry = xcalloc(1, sizeof *entry);
entry->flag = ch;
entry->count = 1;
TAILQ_INIT(&entry->values);
RB_INSERT(args_tree, &args->tree, entry);
}
} else
entry->count++;
if (value != NULL)
entry->value = xstrdup(value);
if (s != NULL) {
value = xcalloc(1, sizeof *value);
value->value = xstrdup(s);
TAILQ_INSERT_TAIL(&entry->values, value, entry);
}
}
/* Get argument value. Will be NULL if it isn't present. */
@@ -230,7 +288,34 @@ args_get(struct args *args, u_char ch)
if ((entry = args_find(args, ch)) == NULL)
return (NULL);
return (entry->value);
return (TAILQ_LAST(&entry->values, args_values)->value);
}
/* Get first value in argument. */
const char *
args_first_value(struct args *args, u_char ch, struct args_value **value)
{
struct args_entry *entry;
if ((entry = args_find(args, ch)) == NULL)
return (NULL);
*value = TAILQ_FIRST(&entry->values);
if (*value == NULL)
return (NULL);
return ((*value)->value);
}
/* Get next value in argument. */
const char *
args_next_value(struct args_value **value)
{
if (*value == NULL)
return (NULL);
*value = TAILQ_NEXT(*value, entry);
if (*value == NULL)
return (NULL);
return ((*value)->value);
}
/* Convert an argument value to a number. */
@@ -241,13 +326,15 @@ args_strtonum(struct args *args, u_char ch, long long minval, long long maxval,
const char *errstr;
long long ll;
struct args_entry *entry;
struct args_value *value;
if ((entry = args_find(args, ch)) == NULL) {
*cause = xstrdup("missing");
return (0);
}
value = TAILQ_LAST(&entry->values, args_values);
ll = strtonum(entry->value, minval, maxval, &errstr);
ll = strtonum(value->value, minval, maxval, &errstr);
if (errstr != NULL) {
*cause = xstrdup(errstr);
return (0);

120
array.h
View File

@@ -1,120 +0,0 @@
/* $Id$ */
/*
* Copyright (c) 2006 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.
*/
#ifndef ARRAY_H
#define ARRAY_H
#define ARRAY_INITIALIZER { NULL, 0, 0 }
#define ARRAY_DECL(n, c) \
struct n { \
c *list; \
u_int num; \
size_t space; \
}
#define ARRAY_ITEM(a, i) ((a)->list[i])
#define ARRAY_ITEMSIZE(a) (sizeof *(a)->list)
#define ARRAY_INITIALSPACE(a) (10 * ARRAY_ITEMSIZE(a))
#define ARRAY_ENSURE(a, n) do { \
if (UINT_MAX - (n) < (a)->num) \
fatalx("number too big"); \
if (SIZE_MAX / ((a)->num + (n)) < ARRAY_ITEMSIZE(a)) \
fatalx("size too big"); \
if ((a)->space == 0) { \
(a)->space = ARRAY_INITIALSPACE(a); \
(a)->list = xrealloc((a)->list, (a)->space); \
} \
while ((a)->space <= ((a)->num + (n)) * ARRAY_ITEMSIZE(a)) { \
(a)->list = xreallocarray((a)->list, 2, (a)->space); \
(a)->space *= 2; \
} \
} while (0)
#define ARRAY_EMPTY(a) (((void *) (a)) == NULL || (a)->num == 0)
#define ARRAY_LENGTH(a) ((a)->num)
#define ARRAY_DATA(a) ((a)->list)
#define ARRAY_FIRST(a) ARRAY_ITEM(a, 0)
#define ARRAY_LAST(a) ARRAY_ITEM(a, (a)->num - 1)
#define ARRAY_INIT(a) do { \
(a)->num = 0; \
(a)->list = NULL; \
(a)->space = 0; \
} while (0)
#define ARRAY_CLEAR(a) do { \
(a)->num = 0; \
} while (0)
#define ARRAY_SET(a, i, s) do { \
(a)->list[i] = s; \
} while (0)
#define ARRAY_ADD(a, s) do { \
ARRAY_ENSURE(a, 1); \
(a)->list[(a)->num] = s; \
(a)->num++; \
} while (0)
#define ARRAY_INSERT(a, i, s) do { \
ARRAY_ENSURE(a, 1); \
if ((i) < (a)->num) { \
memmove((a)->list + (i) + 1, (a)->list + (i), \
ARRAY_ITEMSIZE(a) * ((a)->num - (i))); \
} \
(a)->list[i] = s; \
(a)->num++; \
} while (0)
#define ARRAY_REMOVE(a, i) do { \
if ((i) < (a)->num - 1) { \
memmove((a)->list + (i), (a)->list + (i) + 1, \
ARRAY_ITEMSIZE(a) * ((a)->num - (i) - 1)); \
} \
(a)->num--; \
if ((a)->num == 0) \
ARRAY_FREE(a); \
} while (0)
#define ARRAY_EXPAND(a, n) do { \
ARRAY_ENSURE(a, n); \
(a)->num += n; \
} while (0)
#define ARRAY_TRUNC(a, n) do { \
if ((a)->num > n) \
(a)->num -= n; \
else \
ARRAY_FREE(a); \
} while (0)
#define ARRAY_CONCAT(a, b) do { \
ARRAY_ENSURE(a, (b)->num); \
memcpy((a)->list + (a)->num, (b)->list, (b)->num * ARRAY_ITEMSIZE(a)); \
(a)->num += (b)->num; \
} while (0)
#define ARRAY_FREE(a) do { \
free((a)->list); \
ARRAY_INIT(a); \
} while (0)
#define ARRAY_FREEALL(a) do { \
ARRAY_FREE(a); \
free(a); \
} while (0)
#endif

View File

@@ -23,22 +23,28 @@
#include "tmux.h"
const char *
attributes_tostring(u_char attr)
attributes_tostring(int attr)
{
static char buf[128];
static char buf[512];
size_t len;
if (attr == 0)
return ("none");
len = xsnprintf(buf, sizeof buf, "%s%s%s%s%s%s%s",
attr & GRID_ATTR_BRIGHT ? "bright," : "",
attr & GRID_ATTR_DIM ? "dim," : "",
attr & GRID_ATTR_UNDERSCORE ? "underscore," : "",
attr & GRID_ATTR_BLINK ? "blink," : "",
attr & GRID_ATTR_REVERSE ? "reverse," : "",
attr & GRID_ATTR_HIDDEN ? "hidden," : "",
attr & GRID_ATTR_ITALICS ? "italics," : "");
len = xsnprintf(buf, sizeof buf, "%s%s%s%s%s%s%s%s%s%s%s%s%s",
(attr & GRID_ATTR_BRIGHT) ? "bright," : "",
(attr & GRID_ATTR_DIM) ? "dim," : "",
(attr & GRID_ATTR_UNDERSCORE) ? "underscore," : "",
(attr & GRID_ATTR_BLINK)? "blink," : "",
(attr & GRID_ATTR_REVERSE) ? "reverse," : "",
(attr & GRID_ATTR_HIDDEN) ? "hidden," : "",
(attr & GRID_ATTR_ITALICS) ? "italics," : "",
(attr & GRID_ATTR_STRIKETHROUGH) ? "strikethrough," : "",
(attr & GRID_ATTR_UNDERSCORE_2) ? "double-underscore," : "",
(attr & GRID_ATTR_UNDERSCORE_3) ? "curly-underscore," : "",
(attr & GRID_ATTR_UNDERSCORE_4) ? "dotted-underscore," : "",
(attr & GRID_ATTR_UNDERSCORE_5) ? "dashed-underscore," : "",
(attr & GRID_ATTR_OVERLINE) ? "overline," : "");
if (len > 0)
buf[len - 1] = '\0';
@@ -49,8 +55,28 @@ int
attributes_fromstring(const char *str)
{
const char delimiters[] = " ,|";
u_char attr;
int attr;
size_t end;
u_int i;
struct {
const char *name;
int attr;
} table[] = {
{ "bright", GRID_ATTR_BRIGHT },
{ "bold", GRID_ATTR_BRIGHT },
{ "dim", GRID_ATTR_DIM },
{ "underscore", GRID_ATTR_UNDERSCORE },
{ "blink", GRID_ATTR_BLINK },
{ "reverse", GRID_ATTR_REVERSE },
{ "hidden", GRID_ATTR_HIDDEN },
{ "italics", GRID_ATTR_ITALICS },
{ "strikethrough", GRID_ATTR_STRIKETHROUGH },
{ "double-underscore", GRID_ATTR_UNDERSCORE_2 },
{ "curly-underscore", GRID_ATTR_UNDERSCORE_3 },
{ "dotted-underscore", GRID_ATTR_UNDERSCORE_4 },
{ "dashed-underscore", GRID_ATTR_UNDERSCORE_5 },
{ "overline", GRID_ATTR_OVERLINE }
};
if (*str == '\0' || strcspn(str, delimiters) == 0)
return (-1);
@@ -63,22 +89,15 @@ attributes_fromstring(const char *str)
attr = 0;
do {
end = strcspn(str, delimiters);
if ((end == 6 && strncasecmp(str, "bright", end) == 0) ||
(end == 4 && strncasecmp(str, "bold", end) == 0))
attr |= GRID_ATTR_BRIGHT;
else if (end == 3 && strncasecmp(str, "dim", end) == 0)
attr |= GRID_ATTR_DIM;
else if (end == 10 && strncasecmp(str, "underscore", end) == 0)
attr |= GRID_ATTR_UNDERSCORE;
else if (end == 5 && strncasecmp(str, "blink", end) == 0)
attr |= GRID_ATTR_BLINK;
else if (end == 7 && strncasecmp(str, "reverse", end) == 0)
attr |= GRID_ATTR_REVERSE;
else if (end == 6 && strncasecmp(str, "hidden", end) == 0)
attr |= GRID_ATTR_HIDDEN;
else if (end == 7 && strncasecmp(str, "italics", end) == 0)
attr |= GRID_ATTR_ITALICS;
else
for (i = 0; i < nitems(table); i++) {
if (end != strlen(table[i].name))
continue;
if (strncasecmp(str, table[i].name, end) == 0) {
attr |= table[i].attr;
break;
}
}
if (i == nitems(table))
return (-1);
str += end + strspn(str + end, delimiters);
} while (*str != '\0');

View File

@@ -1,9 +1,8 @@
#!/bin/sh
# $Id$
if [ "x$(uname)" = "xOpenBSD" ]; then
[ -z "$AUTOMAKE_VERSION" ] && export AUTOMAKE_VERSION=1.10
[ -z "$AUTOCONF_VERSION" ] && export AUTOCONF_VERSION=2.65
[ -z "$AUTOMAKE_VERSION" ] && export AUTOMAKE_VERSION=1.15
[ -z "$AUTOCONF_VERSION" ] && export AUTOCONF_VERSION=2.69
fi
die()

327
cfg.c
View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,135 +26,270 @@
#include "tmux.h"
struct cmd_q *cfg_cmd_q;
int cfg_finished;
int cfg_references;
ARRAY_DECL (, char *) cfg_causes = ARRAY_INITIALIZER;
struct client *cfg_client;
struct client *cfg_client;
static char *cfg_file;
int cfg_finished;
static char **cfg_causes;
static u_int cfg_ncauses;
static struct cmdq_item *cfg_item;
int
load_cfg(const char *path, struct cmd_q *cmdq, char **cause)
static enum cmd_retval
cfg_client_done(__unused struct cmdq_item *item, __unused void *data)
{
FILE *f;
char delim[3] = { '\\', '\\', '\0' };
u_int found;
size_t line = 0;
char *buf, *cause1, *p;
struct cmd_list *cmdlist;
log_debug("loading %s", path);
if ((f = fopen(path, "rb")) == NULL) {
xasprintf(cause, "%s: %s", path, strerror(errno));
return (-1);
}
found = 0;
while ((buf = fparseln(f, NULL, &line, delim, 0))) {
log_debug("%s: %s", path, buf);
/* Skip empty lines. */
p = buf;
while (isspace((u_char) *p))
p++;
if (*p == '\0') {
free(buf);
continue;
}
/* Parse and run the command. */
if (cmd_string_parse(p, &cmdlist, path, line, &cause1) != 0) {
free(buf);
if (cause1 == NULL)
continue;
cfg_add_cause("%s:%zu: %s", path, line, cause1);
free(cause1);
continue;
}
free(buf);
if (cmdlist == NULL)
continue;
cmdq_append(cmdq, cmdlist);
cmd_list_free(cmdlist);
found++;
}
fclose(f);
return (found);
if (!cfg_finished)
return (CMD_RETURN_WAIT);
return (CMD_RETURN_NORMAL);
}
void
cfg_default_done(unused struct cmd_q *cmdq)
static enum cmd_retval
cfg_done(__unused struct cmdq_item *item, __unused void *data)
{
if (--cfg_references != 0)
return;
if (cfg_finished)
return (CMD_RETURN_NORMAL);
cfg_finished = 1;
if (!RB_EMPTY(&sessions))
cfg_show_causes(RB_MIN(sessions, &sessions));
cmdq_free(cfg_cmd_q);
cfg_cmd_q = NULL;
if (cfg_item != NULL)
cmdq_continue(cfg_item);
if (cfg_client != NULL) {
/*
* The client command queue starts with client_exit set to 1 so
* only continue if not empty (that is, we have been delayed
* during configuration parsing for long enough that the
* MSG_COMMAND has arrived), else the client will exit before
* the MSG_COMMAND which might tell it not to.
*/
if (!TAILQ_EMPTY(&cfg_client->cmdq->queue))
cmdq_continue(cfg_client->cmdq);
cfg_client->references--;
cfg_client = NULL;
}
status_prompt_load_history();
return (CMD_RETURN_NORMAL);
}
void
cfg_add_cause(const char* fmt, ...)
set_cfg_file(const char *path)
{
va_list ap;
char* msg;
free(cfg_file);
cfg_file = xstrdup(path);
}
static char *
expand_cfg_file(const char *path, const char *home)
{
char *expanded, *name;
const char *end;
struct environ_entry *value;
if (strncmp(path, "~/", 2) == 0) {
if (home == NULL)
return (NULL);
xasprintf(&expanded, "%s%s", home, path + 1);
return (expanded);
}
if (*path == '$') {
end = strchr(path, '/');
if (end == NULL)
name = xstrdup(path + 1);
else
name = xstrndup(path + 1, end - path - 1);
value = environ_find(global_environ, name);
free(name);
if (value == NULL)
return (NULL);
if (end == NULL)
end = "";
xasprintf(&expanded, "%s%s", value->value, end);
return (expanded);
}
return (xstrdup(path));
}
void
start_cfg(void)
{
const char *home = find_home();
struct client *c;
char *path, *copy, *next, *expanded;
/*
* Configuration files are loaded without a client, so commands are run
* in the global queue with item->client NULL.
*
* However, we must block the initial client (but just the initial
* client) so that its command runs after the configuration is loaded.
* Because start_cfg() is called so early, we can be sure the client's
* command queue is currently empty and our callback will be at the
* front - we need to get in before MSG_COMMAND.
*/
cfg_client = c = TAILQ_FIRST(&clients);
if (c != NULL) {
cfg_item = cmdq_get_callback(cfg_client_done, NULL);
cmdq_append(c, cfg_item);
}
if (cfg_file == NULL) {
path = copy = xstrdup(TMUX_CONF);
while ((next = strsep(&path, ":")) != NULL) {
expanded = expand_cfg_file(next, home);
if (expanded == NULL) {
log_debug("couldn't expand %s", next);
continue;
}
log_debug("expanded %s to %s", next, expanded);
load_cfg(expanded, c, NULL, CMD_PARSE_QUIET, NULL);
free(expanded);
}
free(copy);
} else
load_cfg(cfg_file, c, NULL, 0, NULL);
cmdq_append(NULL, cmdq_get_callback(cfg_done, NULL));
}
int
load_cfg(const char *path, struct client *c, struct cmdq_item *item, int flags,
struct cmdq_item **new_item)
{
FILE *f;
struct cmd_parse_input pi;
struct cmd_parse_result *pr;
struct cmdq_item *new_item0;
if (new_item != NULL)
*new_item = NULL;
log_debug("loading %s", path);
if ((f = fopen(path, "rb")) == NULL) {
if (errno == ENOENT && (flags & CMD_PARSE_QUIET))
return (0);
cfg_add_cause("%s: %s", path, strerror(errno));
return (-1);
}
memset(&pi, 0, sizeof pi);
pi.flags = flags;
pi.file = path;
pi.line = 1;
pi.item = item;
pi.c = c;
pr = cmd_parse_from_file(f, &pi);
fclose(f);
if (pr->status == CMD_PARSE_EMPTY)
return (0);
if (pr->status == CMD_PARSE_ERROR) {
cfg_add_cause("%s", pr->error);
free(pr->error);
return (-1);
}
if (flags & CMD_PARSE_PARSEONLY) {
cmd_list_free(pr->cmdlist);
return (0);
}
new_item0 = cmdq_get_command(pr->cmdlist, NULL, NULL, 0);
if (item != NULL)
new_item0 = cmdq_insert_after(item, new_item0);
else
new_item0 = cmdq_append(NULL, new_item0);
cmd_list_free(pr->cmdlist);
if (new_item != NULL)
*new_item = new_item0;
return (0);
}
int
load_cfg_from_buffer(const void *buf, size_t len, const char *path,
struct client *c, struct cmdq_item *item, int flags,
struct cmdq_item **new_item)
{
struct cmd_parse_input pi;
struct cmd_parse_result *pr;
struct cmdq_item *new_item0;
if (new_item != NULL)
*new_item = NULL;
log_debug("loading %s", path);
memset(&pi, 0, sizeof pi);
pi.flags = flags;
pi.file = path;
pi.line = 1;
pi.item = item;
pi.c = c;
pr = cmd_parse_from_buffer(buf, len, &pi);
if (pr->status == CMD_PARSE_EMPTY)
return (0);
if (pr->status == CMD_PARSE_ERROR) {
cfg_add_cause("%s", pr->error);
free(pr->error);
return (-1);
}
if (flags & CMD_PARSE_PARSEONLY) {
cmd_list_free(pr->cmdlist);
return (0);
}
new_item0 = cmdq_get_command(pr->cmdlist, NULL, NULL, 0);
if (item != NULL)
new_item0 = cmdq_insert_after(item, new_item0);
else
new_item0 = cmdq_append(NULL, new_item0);
cmd_list_free(pr->cmdlist);
if (new_item != NULL)
*new_item = new_item0;
return (0);
}
void
cfg_add_cause(const char *fmt, ...)
{
va_list ap;
char *msg;
va_start(ap, fmt);
xvasprintf(&msg, fmt, ap);
va_end (ap);
va_end(ap);
ARRAY_ADD(&cfg_causes, msg);
cfg_ncauses++;
cfg_causes = xreallocarray(cfg_causes, cfg_ncauses, sizeof *cfg_causes);
cfg_causes[cfg_ncauses - 1] = msg;
}
void
cfg_print_causes(struct cmd_q *cmdq)
cfg_print_causes(struct cmdq_item *item)
{
char *cause;
u_int i;
for (i = 0; i < ARRAY_LENGTH(&cfg_causes); i++) {
cause = ARRAY_ITEM(&cfg_causes, i);
cmdq_print(cmdq, "%s", cause);
free(cause);
for (i = 0; i < cfg_ncauses; i++) {
cmdq_print(item, "%s", cfg_causes[i]);
free(cfg_causes[i]);
}
ARRAY_FREE(&cfg_causes);
free(cfg_causes);
cfg_causes = NULL;
cfg_ncauses = 0;
}
void
cfg_show_causes(struct session *s)
{
struct window_pane *wp;
char *cause;
u_int i;
struct window_pane *wp;
struct window_mode_entry *wme;
u_int i;
if (s == NULL || ARRAY_EMPTY(&cfg_causes))
if (s == NULL || cfg_ncauses == 0)
return;
wp = s->curw->window->active;
window_pane_set_mode(wp, &window_copy_mode);
window_copy_init_for_output(wp);
for (i = 0; i < ARRAY_LENGTH(&cfg_causes); i++) {
cause = ARRAY_ITEM(&cfg_causes, i);
window_copy_add(wp, "%s", cause);
free(cause);
wme = TAILQ_FIRST(&wp->modes);
if (wme == NULL || wme->mode != &window_view_mode)
window_pane_set_mode(wp, &window_view_mode, NULL, NULL);
for (i = 0; i < cfg_ncauses; i++) {
window_copy_add(wp, "%s", cfg_causes[i]);
free(cfg_causes[i]);
}
ARRAY_FREE(&cfg_causes);
free(cfg_causes);
cfg_causes = NULL;
cfg_ncauses = 0;
}

972
client.c

File diff suppressed because it is too large Load Diff

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -30,159 +30,156 @@
* Attach existing session to the current terminal.
*/
enum cmd_retval cmd_attach_session_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_attach_session_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_attach_session_entry = {
"attach-session", "attach",
"c:drt:", 0, 0,
"[-dr] [-c working-directory] " CMD_TARGET_SESSION_USAGE,
CMD_CANTNEST|CMD_STARTSERVER,
cmd_attach_session_exec
.name = "attach-session",
.alias = "attach",
.args = { "c:dErt:x", 0, 0 },
.usage = "[-dErx] [-c working-directory] " CMD_TARGET_SESSION_USAGE,
/* -t is special */
.flags = CMD_STARTSERVER,
.exec = cmd_attach_session_exec
};
enum cmd_retval
cmd_attach_session(struct cmd_q *cmdq, const char *tflag, int dflag, int rflag,
const char *cflag)
cmd_attach_session(struct cmdq_item *item, const char *tflag, int dflag,
int xflag, int rflag, const char *cflag, int Eflag)
{
struct cmd_find_state *current = &item->shared->current;
enum cmd_find_type type;
int flags;
struct client *c = item->client, *c_loop;
struct session *s;
struct client *c;
struct winlink *wl = NULL;
struct window *w = NULL;
struct window_pane *wp = NULL;
const char *update;
struct winlink *wl;
struct window_pane *wp;
char *cause;
u_int i;
int fd;
struct format_tree *ft;
char *cp;
enum msgtype msgtype;
if (RB_EMPTY(&sessions)) {
cmdq_error(cmdq, "no sessions");
cmdq_error(item, "no sessions");
return (CMD_RETURN_ERROR);
}
if (tflag == NULL) {
if ((s = cmd_find_session(cmdq, tflag, 1)) == NULL)
return (CMD_RETURN_ERROR);
} else if (tflag[strcspn(tflag, ":.")] != '\0') {
if ((wl = cmd_find_pane(cmdq, tflag, &s, &wp)) == NULL)
return (CMD_RETURN_ERROR);
} else {
if ((s = cmd_find_session(cmdq, tflag, 1)) == NULL)
return (CMD_RETURN_ERROR);
w = cmd_lookup_windowid(tflag);
if (w == NULL && (wp = cmd_lookup_paneid(tflag)) != NULL)
w = wp->window;
if (w != NULL)
wl = winlink_find_by_window(&s->windows, w);
if (c == NULL)
return (CMD_RETURN_NORMAL);
if (server_client_check_nested(c)) {
cmdq_error(item, "sessions should be nested with care, "
"unset $TMUX to force");
return (CMD_RETURN_ERROR);
}
if (cmdq->client == NULL)
return (CMD_RETURN_NORMAL);
if (tflag != NULL && tflag[strcspn(tflag, ":.")] != '\0') {
type = CMD_FIND_PANE;
flags = 0;
} else {
type = CMD_FIND_SESSION;
flags = CMD_FIND_PREFER_UNATTACHED;
}
if (cmd_find_target(&item->target, item, tflag, type, flags) != 0)
return (CMD_RETURN_ERROR);
s = item->target.s;
wl = item->target.wl;
wp = item->target.wp;
if (wl != NULL) {
if (wp != NULL)
window_set_active_pane(wp->window, wp);
window_set_active_pane(wp->window, wp, 1);
session_set_current(s, wl);
if (wp != NULL)
cmd_find_from_winlink_pane(current, wl, wp, 0);
else
cmd_find_from_winlink(current, wl, 0);
}
if (cmdq->client->session != NULL) {
if (dflag) {
/*
* Can't use server_write_session in case attaching to
* the same session as currently attached to.
*/
for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
c = ARRAY_ITEM(&clients, i);
if (c == NULL || c->session != s)
if (cflag != NULL) {
free((void *)s->cwd);
s->cwd = format_single(item, cflag, c, s, wl, wp);
}
c->last_session = c->session;
if (c->session != NULL) {
if (dflag || xflag) {
if (xflag)
msgtype = MSG_DETACHKILL;
else
msgtype = MSG_DETACH;
TAILQ_FOREACH(c_loop, &clients, entry) {
if (c_loop->session != s || c == c_loop)
continue;
if (c == cmdq->client)
continue;
server_write_client(c, MSG_DETACH,
c->session->name,
strlen(c->session->name) + 1);
server_client_detach(c_loop, msgtype);
}
}
if (!Eflag)
environ_update(s->options, c->environ, s->environ);
if (cflag != NULL) {
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s,
NULL, NULL);
cp = format_expand(ft, cflag);
format_free(ft);
fd = open(cp, O_RDONLY|O_DIRECTORY);
free(cp);
if (fd == -1) {
cmdq_error(cmdq, "bad working directory: %s",
strerror(errno));
return (CMD_RETURN_ERROR);
}
close(s->cwd);
s->cwd = fd;
}
cmdq->client->session = s;
notify_attached_session_changed(cmdq->client);
session_update_activity(s);
server_redraw_client(cmdq->client);
c->session = s;
if (~item->shared->flags & CMDQ_SHARED_REPEAT)
server_client_set_key_table(c, NULL);
tty_update_client_offset(c);
status_timer_start(c);
notify_client("client-session-changed", c);
session_update_activity(s, NULL);
gettimeofday(&s->last_attached_time, NULL);
server_redraw_client(c);
s->curw->flags &= ~WINLINK_ALERTFLAGS;
s->curw->window->latest = c;
} else {
if (server_client_open(cmdq->client, &cause) != 0) {
cmdq_error(cmdq, "open terminal failed: %s", cause);
if (server_client_open(c, &cause) != 0) {
cmdq_error(item, "open terminal failed: %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
if (cflag != NULL) {
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s,
NULL, NULL);
cp = format_expand(ft, cflag);
format_free(ft);
fd = open(cp, O_RDONLY|O_DIRECTORY);
free(cp);
if (fd == -1) {
cmdq_error(cmdq, "bad working directory: %s",
strerror(errno));
return (CMD_RETURN_ERROR);
}
close(s->cwd);
s->cwd = fd;
}
if (rflag)
cmdq->client->flags |= CLIENT_READONLY;
c->flags |= CLIENT_READONLY;
if (dflag) {
server_write_session(s, MSG_DETACH, s->name,
strlen(s->name) + 1);
if (dflag || xflag) {
if (xflag)
msgtype = MSG_DETACHKILL;
else
msgtype = MSG_DETACH;
TAILQ_FOREACH(c_loop, &clients, entry) {
if (c_loop->session != s || c == c_loop)
continue;
server_client_detach(c_loop, msgtype);
}
}
if (!Eflag)
environ_update(s->options, c->environ, s->environ);
update = options_get_string(&s->options, "update-environment");
environ_update(update, &cmdq->client->environ, &s->environ);
cmdq->client->session = s;
notify_attached_session_changed(cmdq->client);
session_update_activity(s);
server_redraw_client(cmdq->client);
c->session = s;
server_client_set_key_table(c, NULL);
tty_update_client_offset(c);
status_timer_start(c);
notify_client("client-session-changed", c);
session_update_activity(s, NULL);
gettimeofday(&s->last_attached_time, NULL);
server_redraw_client(c);
s->curw->flags &= ~WINLINK_ALERTFLAGS;
s->curw->window->latest = c;
server_write_ready(cmdq->client);
cmdq->client_exit = 0;
if (~c->flags & CLIENT_CONTROL)
proc_send(c->peer, MSG_READY, -1, NULL, 0);
notify_client("client-attached", c);
c->flags |= CLIENT_ATTACHED;
}
recalculate_sizes();
alerts_check_session(s);
server_update_socket();
return (CMD_RETURN_NORMAL);
}
enum cmd_retval
cmd_attach_session_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_attach_session_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
return (cmd_attach_session(cmdq, args_get(args, 't'),
args_has(args, 'd'), args_has(args, 'r'), args_get(args, 'c')));
return (cmd_attach_session(item, args_get(args, 't'),
args_has(args, 'd'), args_has(args, 'x'), args_has(args, 'r'),
args_get(args, 'c'), args_has(args, 'E')));
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -24,109 +24,63 @@
#include "tmux.h"
/*
* Bind a key to a command, this recurses through cmd_*.
* Bind a key to a command.
*/
enum cmd_retval cmd_bind_key_exec(struct cmd *, struct cmd_q *);
enum cmd_retval cmd_bind_key_mode_table(struct cmd *, struct cmd_q *, int);
static enum cmd_retval cmd_bind_key_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_bind_key_entry = {
"bind-key", "bind",
"cnrt:", 1, -1,
"[-cnr] [-t mode-table] key command [arguments]",
0,
cmd_bind_key_exec
.name = "bind-key",
.alias = "bind",
.args = { "nrN:T:", 2, -1 },
.usage = "[-nr] [-T key-table] [-N note] key "
"command [arguments]",
.flags = CMD_AFTERHOOK,
.exec = cmd_bind_key_exec
};
enum cmd_retval
cmd_bind_key_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_bind_key_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
char *cause;
struct cmd_list *cmdlist;
int key;
struct args *args = self->args;
key_code key;
const char *tablename, *note;
struct cmd_parse_result *pr;
char **argv = args->argv;
int argc = args->argc, repeat;
if (args_has(args, 't')) {
if (args->argc != 2 && args->argc != 3) {
cmdq_error(cmdq, "not enough arguments");
return (CMD_RETURN_ERROR);
}
} else {
if (args->argc < 2) {
cmdq_error(cmdq, "not enough arguments");
return (CMD_RETURN_ERROR);
}
}
key = key_string_lookup_string(args->argv[0]);
if (key == KEYC_NONE) {
cmdq_error(cmdq, "unknown key: %s", args->argv[0]);
key = key_string_lookup_string(argv[0]);
if (key == KEYC_NONE || key == KEYC_UNKNOWN) {
cmdq_error(item, "unknown key: %s", argv[0]);
return (CMD_RETURN_ERROR);
}
if (args_has(args, 't'))
return (cmd_bind_key_mode_table(self, cmdq, key));
if (args_has(args, 'T'))
tablename = args_get(args, 'T');
else if (args_has(args, 'n'))
tablename = "root";
else
tablename = "prefix";
repeat = args_has(args, 'r');
cmdlist = cmd_list_parse(args->argc - 1, args->argv + 1, NULL, 0,
&cause);
if (cmdlist == NULL) {
cmdq_error(cmdq, "%s", cause);
free(cause);
if (argc == 2)
pr = cmd_parse_from_string(argv[1], NULL);
else
pr = cmd_parse_from_arguments(argc - 1, argv + 1, NULL);
switch (pr->status) {
case CMD_PARSE_EMPTY:
cmdq_error(item, "empty command");
return (CMD_RETURN_ERROR);
case CMD_PARSE_ERROR:
cmdq_error(item, "%s", pr->error);
free(pr->error);
return (CMD_RETURN_ERROR);
case CMD_PARSE_SUCCESS:
break;
}
if (!args_has(args, 'n'))
key |= KEYC_PREFIX;
key_bindings_add(key, args_has(args, 'r'), cmdlist);
return (CMD_RETURN_NORMAL);
}
enum cmd_retval
cmd_bind_key_mode_table(struct cmd *self, struct cmd_q *cmdq, int key)
{
struct args *args = self->args;
const char *tablename;
const struct mode_key_table *mtab;
struct mode_key_binding *mbind, mtmp;
enum mode_key_cmd cmd;
const char *arg;
tablename = args_get(args, 't');
if ((mtab = mode_key_findtable(tablename)) == NULL) {
cmdq_error(cmdq, "unknown key table: %s", tablename);
return (CMD_RETURN_ERROR);
}
cmd = mode_key_fromstring(mtab->cmdstr, args->argv[1]);
if (cmd == MODEKEY_NONE) {
cmdq_error(cmdq, "unknown command: %s", args->argv[1]);
return (CMD_RETURN_ERROR);
}
if (cmd != MODEKEYCOPY_COPYPIPE) {
if (args->argc != 2) {
cmdq_error(cmdq, "no argument allowed");
return (CMD_RETURN_ERROR);
}
arg = NULL;
} else {
if (args->argc != 3) {
cmdq_error(cmdq, "no argument given");
return (CMD_RETURN_ERROR);
}
arg = args->argv[2];
}
mtmp.key = key;
mtmp.mode = !!args_has(args, 'c');
if ((mbind = RB_FIND(mode_key_tree, mtab->tree, &mtmp)) == NULL) {
mbind = xmalloc(sizeof *mbind);
mbind->key = mtmp.key;
mbind->mode = mtmp.mode;
RB_INSERT(mode_key_tree, mtab->tree, mbind);
}
mbind->cmd = cmd;
mbind->arg = arg != NULL ? xstrdup(arg) : NULL;
note = args_get(args, 'N');
key_bindings_add(tablename, key, note, repeat, pr->cmdlist);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -28,74 +28,94 @@
#define BREAK_PANE_TEMPLATE "#{session_name}:#{window_index}.#{pane_index}"
enum cmd_retval cmd_break_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_break_pane_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_break_pane_entry = {
"break-pane", "breakp",
"dPF:t:", 0, 0,
"[-dP] [-F format] " CMD_TARGET_PANE_USAGE,
0,
cmd_break_pane_exec
.name = "break-pane",
.alias = "breakp",
.args = { "dPF:n:s:t:", 0, 0 },
.usage = "[-dP] [-F format] [-n window-name] [-s src-pane] "
"[-t dst-window]",
.source = { 's', CMD_FIND_PANE, 0 },
.target = { 't', CMD_FIND_WINDOW, CMD_FIND_WINDOW_INDEX },
.flags = 0,
.exec = cmd_break_pane_exec
};
enum cmd_retval
cmd_break_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_break_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct session *s;
struct window_pane *wp;
struct window *w;
char *name;
char *cause;
int base_idx;
struct format_tree *ft;
struct cmd_find_state *current = &item->shared->current;
struct client *c = cmd_find_client(item, NULL, 1);
struct winlink *wl = item->source.wl;
struct session *src_s = item->source.s;
struct session *dst_s = item->target.s;
struct window_pane *wp = item->source.wp;
struct window *w = wl->window;
char *name, *cause;
int idx = item->target.idx;
const char *template;
char *cp;
if ((wl = cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp)) == NULL)
return (CMD_RETURN_ERROR);
if (window_count_panes(wl->window) == 1) {
cmdq_error(cmdq, "can't break with only one pane");
if (idx != -1 && winlink_find_by_index(&dst_s->windows, idx) != NULL) {
cmdq_error(item, "index %d already in use", idx);
return (CMD_RETURN_ERROR);
}
w = wl->window;
if (window_count_panes(w) == 1) {
cmdq_error(item, "can't break with only one pane");
return (CMD_RETURN_ERROR);
}
server_unzoom_window(w);
TAILQ_REMOVE(&w->panes, wp, entry);
window_lost_pane(w, wp);
layout_close_pane(wp);
w = wp->window = window_create1(s->sx, s->sy);
w = wp->window = window_create(w->sx, w->sy, w->xpixel, w->ypixel);
options_set_parent(wp->options, w->options);
wp->flags |= PANE_STYLECHANGED;
TAILQ_INSERT_HEAD(&w->panes, wp, entry);
w->active = wp;
name = default_window_name(w);
window_set_name(w, name);
free(name);
w->latest = c;
if (!args_has(args, 'n')) {
name = default_window_name(w);
window_set_name(w, name);
free(name);
} else {
window_set_name(w, args_get(args, 'n'));
options_set_number(w->options, "automatic-rename", 0);
}
layout_init(w, wp);
wp->flags |= PANE_CHANGED;
base_idx = options_get_number(&s->options, "base-index");
wl = session_attach(s, w, -1 - base_idx, &cause); /* can't fail */
if (!args_has(self->args, 'd'))
session_select(s, wl->idx);
if (idx == -1)
idx = -1 - options_get_number(dst_s->options, "base-index");
wl = session_attach(dst_s, w, idx, &cause); /* can't fail */
if (!args_has(self->args, 'd')) {
session_select(dst_s, wl->idx);
cmd_find_from_session(current, dst_s, 0);
}
server_redraw_session(s);
server_status_session_group(s);
server_redraw_session(src_s);
if (src_s != dst_s)
server_redraw_session(dst_s);
server_status_session_group(src_s);
if (src_s != dst_s)
server_status_session_group(dst_s);
if (args_has(args, 'P')) {
if ((template = args_get(args, 'F')) == NULL)
template = BREAK_PANE_TEMPLATE;
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s, wl, wp);
cp = format_expand(ft, template);
cmdq_print(cmdq, "%s", cp);
cp = format_single(item, template, c, dst_s, wl, wp);
cmdq_print(item, "%s", cp);
free(cp);
format_free(ft);
}
return (CMD_RETURN_NORMAL);
}

View File

@@ -27,24 +27,42 @@
* Write the entire contents of a pane to a buffer or stdout.
*/
enum cmd_retval cmd_capture_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_capture_pane_exec(struct cmd *, struct cmdq_item *);
char *cmd_capture_pane_append(char *, size_t *, char *, size_t);
char *cmd_capture_pane_pending(struct args *, struct window_pane *,
static char *cmd_capture_pane_append(char *, size_t *, char *, size_t);
static char *cmd_capture_pane_pending(struct args *, struct window_pane *,
size_t *);
char *cmd_capture_pane_history(struct args *, struct cmd_q *,
static char *cmd_capture_pane_history(struct args *, struct cmdq_item *,
struct window_pane *, size_t *);
const struct cmd_entry cmd_capture_pane_entry = {
"capture-pane", "capturep",
"ab:CeE:JpPqS:t:", 0, 0,
"[-aCeJpPq] " CMD_BUFFER_USAGE " [-E end-line] [-S start-line]"
CMD_TARGET_PANE_USAGE,
0,
cmd_capture_pane_exec
.name = "capture-pane",
.alias = "capturep",
.args = { "ab:CeE:JNpPqS:t:", 0, 0 },
.usage = "[-aCeJNpPq] " CMD_BUFFER_USAGE " [-E end-line] "
"[-S start-line] " CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_capture_pane_exec
};
char *
const struct cmd_entry cmd_clear_history_entry = {
.name = "clear-history",
.alias = "clearhist",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_capture_pane_exec
};
static char *
cmd_capture_pane_append(char *buf, size_t *len, char *line, size_t linelen)
{
buf = xrealloc(buf, *len + linelen + 1);
@@ -53,28 +71,30 @@ cmd_capture_pane_append(char *buf, size_t *len, char *line, size_t linelen)
return (buf);
}
char *
static char *
cmd_capture_pane_pending(struct args *args, struct window_pane *wp,
size_t *len)
{
char *buf, *line, tmp[5];
size_t linelen;
u_int i;
struct evbuffer *pending;
char *buf, *line, tmp[5];
size_t linelen;
u_int i;
if (wp->ictx.since_ground == NULL)
pending = input_pending(wp);
if (pending == NULL)
return (xstrdup(""));
line = EVBUFFER_DATA(wp->ictx.since_ground);
linelen = EVBUFFER_LENGTH(wp->ictx.since_ground);
line = EVBUFFER_DATA(pending);
linelen = EVBUFFER_LENGTH(pending);
buf = xstrdup("");
if (args_has(args, 'C')) {
for (i = 0; i < linelen; i++) {
if (line[i] >= ' ') {
if (line[i] >= ' ' && line[i] != '\\') {
tmp[0] = line[i];
tmp[1] = '\0';
} else
xsnprintf(tmp, sizeof tmp, "\\%03o", line[i]);
xsnprintf(tmp, sizeof tmp, "\\%03hho", line[i]);
buf = cmd_capture_pane_append(buf, len, tmp,
strlen(tmp));
}
@@ -83,14 +103,14 @@ cmd_capture_pane_pending(struct args *args, struct window_pane *wp,
return (buf);
}
char *
cmd_capture_pane_history(struct args *args, struct cmd_q *cmdq,
static char *
cmd_capture_pane_history(struct args *args, struct cmdq_item *item,
struct window_pane *wp, size_t *len)
{
struct grid *gd;
const struct grid_line *gl;
struct grid_cell *gc = NULL;
int n, with_codes, escape_c0, join_lines;
int n, with_codes, escape_c0, join_lines, no_trim;
u_int i, sx, top, bottom, tmp;
char *cause, *buf, *line;
const char *Sflag, *Eflag;
@@ -101,7 +121,7 @@ cmd_capture_pane_history(struct args *args, struct cmd_q *cmdq,
gd = wp->saved_grid;
if (gd == NULL) {
if (!args_has(args, 'q')) {
cmdq_error(cmdq, "no alternate screen");
cmdq_error(item, "no alternate screen");
return (NULL);
}
return (xstrdup(""));
@@ -150,11 +170,12 @@ cmd_capture_pane_history(struct args *args, struct cmd_q *cmdq,
with_codes = args_has(args, 'e');
escape_c0 = args_has(args, 'C');
join_lines = args_has(args, 'J');
no_trim = args_has(args, 'N');
buf = NULL;
for (i = top; i <= bottom; i++) {
line = grid_string_cells(gd, 0, i, sx, &gc, with_codes,
escape_c0, !join_lines);
escape_c0, !join_lines && !no_trim);
linelen = strlen(line);
buf = cmd_capture_pane_append(buf, len, line, linelen);
@@ -168,48 +189,49 @@ cmd_capture_pane_history(struct args *args, struct cmd_q *cmdq,
return (buf);
}
enum cmd_retval
cmd_capture_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_capture_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct window_pane *wp;
struct client *c = item->client;
struct window_pane *wp = item->target.wp;
char *buf, *cause;
const char *bufname;
size_t len;
if (cmd_find_pane(cmdq, args_get(args, 't'), NULL, &wp) == NULL)
return (CMD_RETURN_ERROR);
if (self->entry == &cmd_clear_history_entry) {
window_pane_reset_mode_all(wp);
grid_clear_history(wp->base.grid);
return (CMD_RETURN_NORMAL);
}
len = 0;
if (args_has(args, 'P'))
buf = cmd_capture_pane_pending(args, wp, &len);
else
buf = cmd_capture_pane_history(args, cmdq, wp, &len);
buf = cmd_capture_pane_history(args, item, wp, &len);
if (buf == NULL)
return (CMD_RETURN_ERROR);
if (args_has(args, 'p')) {
c = cmdq->client;
if (c == NULL ||
(c->session != NULL && !(c->flags & CLIENT_CONTROL))) {
cmdq_error(cmdq, "can't write to stdout");
if (!file_can_print(c)) {
cmdq_error(item, "can't write output to client");
free(buf);
return (CMD_RETURN_ERROR);
}
evbuffer_add(c->stdout_data, buf, len);
file_print_buffer(c, buf, len);
if (args_has(args, 'P') && len > 0)
evbuffer_add(c->stdout_data, "\n", 1);
server_push_stdout(c);
file_print(c, "\n");
free(buf);
} else {
bufname = NULL;
if (args_has(args, 'b'))
bufname = args_get(args, 'b');
if (paste_set(buf, len, bufname, &cause) != 0) {
cmdq_error(cmdq, "%s", cause);
free(buf);
cmdq_error(item, "%s", cause);
free(cause);
free(buf);
return (CMD_RETURN_ERROR);
}
}

View File

@@ -1,100 +0,0 @@
/* $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 <ctype.h>
#include <stdlib.h>
#include "tmux.h"
/*
* Enter choice mode to choose a buffer.
*/
#define CHOOSE_BUFFER_TEMPLATE \
"#{buffer_name}: #{buffer_size} bytes: #{buffer_sample}"
enum cmd_retval cmd_choose_buffer_exec(struct cmd *, struct cmd_q *);
const struct cmd_entry cmd_choose_buffer_entry = {
"choose-buffer", NULL,
"F:t:", 0, 1,
CMD_TARGET_WINDOW_USAGE " [-F format] [template]",
0,
cmd_choose_buffer_exec
};
enum cmd_retval
cmd_choose_buffer_exec(struct cmd *self, struct cmd_q *cmdq)
{
struct args *args = self->args;
struct client *c;
struct window_choose_data *cdata;
struct winlink *wl;
struct paste_buffer *pb;
char *action, *action_data;
const char *template;
u_int idx;
int utf8flag;
if ((c = cmd_current_client(cmdq)) == NULL) {
cmdq_error(cmdq, "no client available");
return (CMD_RETURN_ERROR);
}
if ((template = args_get(args, 'F')) == NULL)
template = CHOOSE_BUFFER_TEMPLATE;
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), NULL)) == NULL)
return (CMD_RETURN_ERROR);
utf8flag = options_get_number(&wl->window->options, "utf8");
if (paste_get_top() == NULL)
return (CMD_RETURN_NORMAL);
if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0)
return (CMD_RETURN_NORMAL);
if (args->argc != 0)
action = xstrdup(args->argv[0]);
else
action = xstrdup("paste-buffer -b '%%'");
idx = 0;
pb = NULL;
while ((pb = paste_walk(pb)) != NULL) {
cdata = window_choose_data_create(TREE_OTHER, c, c->session);
cdata->idx = idx;
cdata->ft_template = xstrdup(template);
format_defaults_paste_buffer(cdata->ft, pb, utf8flag);
xasprintf(&action_data, "%s", pb->name);
cdata->command = cmd_template_replace(action, action_data, 1);
free(action_data);
window_choose_add(wl->window->active, cdata);
idx++;
}
free(action);
window_choose_ready(wl->window->active, 0, NULL);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,128 +0,0 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 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 <ctype.h>
#include <stdlib.h>
#include "tmux.h"
/*
* Enter choice mode to choose a client.
*/
#define CHOOSE_CLIENT_TEMPLATE \
"#{client_tty}: #{session_name} " \
"[#{client_width}x#{client_height} #{client_termname}]" \
"#{?client_utf8, (utf8),}#{?client_readonly, (ro),} " \
"(last used #{client_activity_string})"
enum cmd_retval cmd_choose_client_exec(struct cmd *, struct cmd_q *);
void cmd_choose_client_callback(struct window_choose_data *);
const struct cmd_entry cmd_choose_client_entry = {
"choose-client", NULL,
"F:t:", 0, 1,
CMD_TARGET_WINDOW_USAGE " [-F format] [template]",
0,
cmd_choose_client_exec
};
struct cmd_choose_client_data {
struct client *client;
};
enum cmd_retval
cmd_choose_client_exec(struct cmd *self, struct cmd_q *cmdq)
{
struct args *args = self->args;
struct client *c;
struct client *c1;
struct window_choose_data *cdata;
struct winlink *wl;
const char *template;
char *action;
u_int i, idx, cur;
if ((c = cmd_current_client(cmdq)) == NULL) {
cmdq_error(cmdq, "no client available");
return (CMD_RETURN_ERROR);
}
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), NULL)) == NULL)
return (CMD_RETURN_ERROR);
if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0)
return (CMD_RETURN_NORMAL);
if ((template = args_get(args, 'F')) == NULL)
template = CHOOSE_CLIENT_TEMPLATE;
if (args->argc != 0)
action = xstrdup(args->argv[0]);
else
action = xstrdup("detach-client -t '%%'");
cur = idx = 0;
for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
c1 = ARRAY_ITEM(&clients, i);
if (c1 == NULL || c1->session == NULL || c1->tty.path == NULL)
continue;
if (c1 == cmdq->client)
cur = idx;
idx++;
cdata = window_choose_data_create(TREE_OTHER, c, c->session);
cdata->idx = i;
cdata->ft_template = xstrdup(template);
format_add(cdata->ft, "line", "%u", i);
format_defaults(cdata->ft, c1, NULL, NULL, NULL);
cdata->command = cmd_template_replace(action, c1->tty.path, 1);
window_choose_add(wl->window->active, cdata);
}
free(action);
window_choose_ready(wl->window->active, cur,
cmd_choose_client_callback);
return (CMD_RETURN_NORMAL);
}
void
cmd_choose_client_callback(struct window_choose_data *cdata)
{
struct client *c;
if (cdata == NULL)
return;
if (cdata->start_client->flags & CLIENT_DEAD)
return;
if (cdata->idx > ARRAY_LENGTH(&clients) - 1)
return;
c = ARRAY_ITEM(&clients, cdata->idx);
if (c == NULL || c->session == NULL)
return;
window_choose_data_run(cdata);
}

View File

@@ -18,224 +18,74 @@
#include <sys/types.h>
#include <ctype.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
#define CMD_CHOOSE_TREE_WINDOW_ACTION "select-window -t '%%'"
#define CMD_CHOOSE_TREE_SESSION_ACTION "switch-client -t '%%'"
/*
* Enter choice mode to choose a session and/or window.
* Enter a mode.
*/
#define CHOOSE_TREE_SESSION_TEMPLATE \
"#{session_name}: #{session_windows} windows" \
"#{?session_grouped, (group ,}" \
"#{session_group}#{?session_grouped,),}" \
"#{?session_attached, (attached),}"
#define CHOOSE_TREE_WINDOW_TEMPLATE \
"#{window_index}: #{window_name}#{window_flags} " \
"\"#{pane_title}\""
enum cmd_retval cmd_choose_tree_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_choose_tree_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_choose_tree_entry = {
"choose-tree", NULL,
"S:W:swub:c:t:", 0, 1,
"[-suw] [-b session-template] [-c window template] [-S format] " \
"[-W format] " CMD_TARGET_WINDOW_USAGE,
0,
cmd_choose_tree_exec
.name = "choose-tree",
.alias = NULL,
.args = { "F:Gf:NO:rst:wZ", 0, 1 },
.usage = "[-GNrswZ] [-F format] [-f filter] [-O sort-order] "
CMD_TARGET_PANE_USAGE " [template]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_choose_tree_exec
};
const struct cmd_entry cmd_choose_session_entry = {
"choose-session", NULL,
"F:t:", 0, 1,
CMD_TARGET_WINDOW_USAGE " [-F format] [template]",
0,
cmd_choose_tree_exec
const struct cmd_entry cmd_choose_client_entry = {
.name = "choose-client",
.alias = NULL,
.args = { "F:f:NO:rt:Z", 0, 1 },
.usage = "[-NrZ] [-F format] [-f filter] [-O sort-order] "
CMD_TARGET_PANE_USAGE " [template]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_choose_tree_exec
};
const struct cmd_entry cmd_choose_window_entry = {
"choose-window", NULL,
"F:t:", 0, 1,
CMD_TARGET_WINDOW_USAGE "[-F format] [template]",
0,
cmd_choose_tree_exec
const struct cmd_entry cmd_choose_buffer_entry = {
.name = "choose-buffer",
.alias = NULL,
.args = { "F:f:NO:rt:Z", 0, 1 },
.usage = "[-NrZ] [-F format] [-f filter] [-O sort-order] "
CMD_TARGET_PANE_USAGE " [template]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_choose_tree_exec
};
enum cmd_retval
cmd_choose_tree_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_choose_tree_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl, *wm;
struct session *s, *s2;
struct client *c;
struct window_choose_data *wcd = NULL;
const char *ses_template, *win_template;
char *final_win_action, *cur_win_template;
char *final_win_template_middle;
char *final_win_template_last;
const char *ses_action, *win_action;
u_int cur_win, idx_ses, win_ses, win_max;
u_int wflag, sflag;
struct window_pane *wp = item->target.wp;
const struct window_mode *mode;
ses_template = win_template = NULL;
ses_action = win_action = NULL;
if ((c = cmd_current_client(cmdq)) == NULL) {
cmdq_error(cmdq, "no client available");
return (CMD_RETURN_ERROR);
}
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), &s)) == NULL)
return (CMD_RETURN_ERROR);
if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0)
return (CMD_RETURN_NORMAL);
/* Sort out which command this is. */
wflag = sflag = 0;
if (self->entry == &cmd_choose_session_entry) {
sflag = 1;
if ((ses_template = args_get(args, 'F')) == NULL)
ses_template = CHOOSE_TREE_SESSION_TEMPLATE;
if (args->argc != 0)
ses_action = args->argv[0];
else
ses_action = CMD_CHOOSE_TREE_SESSION_ACTION;
} else if (self->entry == &cmd_choose_window_entry) {
wflag = 1;
if ((win_template = args_get(args, 'F')) == NULL)
win_template = CHOOSE_TREE_WINDOW_TEMPLATE;
if (args->argc != 0)
win_action = args->argv[0];
else
win_action = CMD_CHOOSE_TREE_WINDOW_ACTION;
} else {
wflag = args_has(args, 'w');
sflag = args_has(args, 's');
if ((ses_action = args_get(args, 'b')) == NULL)
ses_action = CMD_CHOOSE_TREE_SESSION_ACTION;
if ((win_action = args_get(args, 'c')) == NULL)
win_action = CMD_CHOOSE_TREE_WINDOW_ACTION;
if ((ses_template = args_get(args, 'S')) == NULL)
ses_template = CHOOSE_TREE_SESSION_TEMPLATE;
if ((win_template = args_get(args, 'W')) == NULL)
win_template = CHOOSE_TREE_WINDOW_TEMPLATE;
}
/*
* If not asking for windows and sessions, assume no "-ws" given and
* hence display the entire tree outright.
*/
if (!wflag && !sflag)
wflag = sflag = 1;
/*
* If we're drawing in tree mode, including sessions, then pad the
* window template, otherwise just render the windows as a flat list
* without any padding.
*/
if (wflag && sflag) {
xasprintf(&final_win_template_middle,
" \001tq\001> %s", win_template);
xasprintf(&final_win_template_last,
" \001mq\001> %s", win_template);
} else if (wflag) {
final_win_template_middle = xstrdup(win_template);
final_win_template_last = xstrdup(win_template);
if (self->entry == &cmd_choose_buffer_entry) {
if (paste_get_top(NULL) == NULL)
return (CMD_RETURN_NORMAL);
mode = &window_buffer_mode;
} else if (self->entry == &cmd_choose_client_entry) {
if (server_client_how_many() == 0)
return (CMD_RETURN_NORMAL);
mode = &window_client_mode;
} else
final_win_template_middle = final_win_template_last = NULL;
idx_ses = cur_win = -1;
RB_FOREACH(s2, sessions, &sessions) {
idx_ses++;
/*
* If we're just choosing windows, jump straight there. Note
* that this implies the current session, so only choose
* windows when the session matches this one.
*/
if (wflag && !sflag) {
if (s != s2)
continue;
goto windows_only;
}
wcd = window_choose_add_session(wl->window->active,
c, s2, ses_template, ses_action, idx_ses);
/* If we're just choosing sessions, skip choosing windows. */
if (sflag && !wflag) {
if (s == s2)
cur_win = idx_ses;
continue;
}
windows_only:
win_ses = win_max = -1;
RB_FOREACH(wm, winlinks, &s2->windows)
win_max++;
RB_FOREACH(wm, winlinks, &s2->windows) {
win_ses++;
if (sflag && wflag)
idx_ses++;
if (wm == s2->curw && s == s2) {
if (wflag && !sflag) {
/*
* Then we're only counting windows.
* So remember which is the current
* window in the list.
*/
cur_win = win_ses;
} else
cur_win = idx_ses;
}
xasprintf(&final_win_action, "%s %s %s",
wcd != NULL ? wcd->command : "",
wcd != NULL ? ";" : "", win_action);
if (win_ses != win_max)
cur_win_template = final_win_template_middle;
else
cur_win_template = final_win_template_last;
window_choose_add_window(wl->window->active,
c, s2, wm, cur_win_template,
final_win_action,
(wflag && !sflag) ? win_ses : idx_ses);
free(final_win_action);
}
/*
* If we're just drawing windows, don't consider moving on to
* other sessions as we only list windows in this session.
*/
if (wflag && !sflag)
break;
}
free(final_win_template_middle);
free(final_win_template_last);
window_choose_ready(wl->window->active, cur_win, NULL);
if (args_has(args, 'u')) {
window_choose_expand_all(wl->window->active);
window_choose_set_current(wl->window->active, cur_win);
}
mode = &window_tree_mode;
window_pane_set_mode(wp, mode, &item->target, args);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -29,31 +29,40 @@
* Prompt for command in client.
*/
enum cmd_retval cmd_command_prompt_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_command_prompt_exec(struct cmd *,
struct cmdq_item *);
int cmd_command_prompt_callback(void *, const char *);
void cmd_command_prompt_free(void *);
static int cmd_command_prompt_callback(struct client *, void *,
const char *, int);
static void cmd_command_prompt_free(void *);
const struct cmd_entry cmd_command_prompt_entry = {
"command-prompt", NULL,
"I:p:t:", 0, 1,
"[-I inputs] [-p prompts] " CMD_TARGET_CLIENT_USAGE " [template]",
0,
cmd_command_prompt_exec
.name = "command-prompt",
.alias = NULL,
.args = { "1kiI:Np:t:", 0, 1 },
.usage = "[-1kiN] [-I inputs] [-p prompts] " CMD_TARGET_CLIENT_USAGE " "
"[template]",
.flags = 0,
.exec = cmd_command_prompt_exec
};
struct cmd_command_prompt_cdata {
struct client *c;
char *inputs;
char *next_input;
char *next_prompt;
char *prompts;
char *template;
int idx;
int flags;
char *inputs;
char *next_input;
char *prompts;
char *next_prompt;
char *template;
int idx;
};
enum cmd_retval
cmd_command_prompt_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_command_prompt_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
const char *inputs, *prompts;
@@ -62,20 +71,22 @@ cmd_command_prompt_exec(struct cmd *self, struct cmd_q *cmdq)
char *prompt, *ptr, *input = NULL;
size_t n;
if ((c = cmd_find_client(cmdq, args_get(args, 't'), 0)) == NULL)
if ((c = cmd_find_client(item, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
if (c->prompt_string != NULL)
return (CMD_RETURN_NORMAL);
cdata = xmalloc(sizeof *cdata);
cdata->c = c;
cdata->idx = 1;
cdata = xcalloc(1, sizeof *cdata);
cdata->inputs = NULL;
cdata->next_input = NULL;
cdata->next_prompt = NULL;
cdata->prompts = NULL;
cdata->next_prompt = NULL;
cdata->template = NULL;
cdata->idx = 1;
if (args->argc != 0)
cdata->template = xstrdup(args->argv[0]);
@@ -105,34 +116,47 @@ cmd_command_prompt_exec(struct cmd *self, struct cmd_q *cmdq)
input = strsep(&cdata->next_input, ",");
}
if (args_has(args, '1'))
cdata->flags |= PROMPT_SINGLE;
else if (args_has(args, 'N'))
cdata->flags |= PROMPT_NUMERIC;
else if (args_has(args, 'i'))
cdata->flags |= PROMPT_INCREMENTAL;
else if (args_has(args, 'k'))
cdata->flags |= PROMPT_KEY;
status_prompt_set(c, prompt, input, cmd_command_prompt_callback,
cmd_command_prompt_free, cdata, 0);
cmd_command_prompt_free, cdata, cdata->flags);
free(prompt);
return (CMD_RETURN_NORMAL);
}
int
cmd_command_prompt_callback(void *data, const char *s)
static int
cmd_command_prompt_callback(struct client *c, void *data, const char *s,
int done)
{
struct cmd_command_prompt_cdata *cdata = data;
struct client *c = cdata->c;
struct cmd_list *cmdlist;
char *cause, *new_template, *prompt, *ptr;
struct cmdq_item *new_item;
char *new_template, *prompt, *ptr;
char *input = NULL;
struct cmd_parse_result *pr;
if (s == NULL)
return (0);
if (done && (cdata->flags & PROMPT_INCREMENTAL))
return (0);
new_template = cmd_template_replace(cdata->template, s, cdata->idx);
free(cdata->template);
cdata->template = new_template;
if (done) {
free(cdata->template);
cdata->template = new_template;
}
/*
* Check if there are more prompts; if so, get its respective input
* and update the prompt data.
*/
if ((ptr = strsep(&cdata->next_prompt, ",")) != NULL) {
if (done && (ptr = strsep(&cdata->next_prompt, ",")) != NULL) {
xasprintf(&prompt, "%s ", ptr);
input = strsep(&cdata->next_input, ",");
status_prompt_update(c, prompt, input);
@@ -142,24 +166,31 @@ cmd_command_prompt_callback(void *data, const char *s)
return (1);
}
if (cmd_string_parse(new_template, &cmdlist, NULL, 0, &cause) != 0) {
if (cause != NULL) {
*cause = toupper((u_char) *cause);
status_message_set(c, "%s", cause);
free(cause);
}
return (0);
pr = cmd_parse_from_string(new_template, NULL);
switch (pr->status) {
case CMD_PARSE_EMPTY:
new_item = NULL;
break;
case CMD_PARSE_ERROR:
new_item = cmdq_get_error(pr->error);
free(pr->error);
cmdq_append(c, new_item);
break;
case CMD_PARSE_SUCCESS:
new_item = cmdq_get_command(pr->cmdlist, NULL, NULL, 0);
cmd_list_free(pr->cmdlist);
cmdq_append(c, new_item);
break;
}
cmdq_run(c->cmdq, cmdlist);
cmd_list_free(cmdlist);
if (c->prompt_callbackfn != (void *) &cmd_command_prompt_callback)
if (!done)
free(new_template);
if (c->prompt_inputcb != cmd_command_prompt_callback)
return (1);
return (0);
}
void
static void
cmd_command_prompt_free(void *data)
{
struct cmd_command_prompt_cdata *cdata = data;

View File

@@ -28,26 +28,30 @@
* Asks for confirmation before executing a command.
*/
enum cmd_retval cmd_confirm_before_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_confirm_before_exec(struct cmd *,
struct cmdq_item *);
int cmd_confirm_before_callback(void *, const char *);
void cmd_confirm_before_free(void *);
static int cmd_confirm_before_callback(struct client *, void *,
const char *, int);
static void cmd_confirm_before_free(void *);
const struct cmd_entry cmd_confirm_before_entry = {
"confirm-before", "confirm",
"p:t:", 1, 1,
"[-p prompt] " CMD_TARGET_CLIENT_USAGE " command",
0,
cmd_confirm_before_exec
.name = "confirm-before",
.alias = "confirm",
.args = { "p:t:", 1, 1 },
.usage = "[-p prompt] " CMD_TARGET_CLIENT_USAGE " command",
.flags = 0,
.exec = cmd_confirm_before_exec
};
struct cmd_confirm_before_data {
char *cmd;
struct client *client;
char *cmd;
};
enum cmd_retval
cmd_confirm_before_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_confirm_before_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct cmd_confirm_before_data *cdata;
@@ -55,7 +59,7 @@ cmd_confirm_before_exec(struct cmd *self, struct cmd_q *cmdq)
char *cmd, *copy, *new_prompt, *ptr;
const char *prompt;
if ((c = cmd_find_client(cmdq, args_get(args, 't'), 0)) == NULL)
if ((c = cmd_find_client(item, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
if ((prompt = args_get(args, 'p')) != NULL)
@@ -70,9 +74,6 @@ cmd_confirm_before_exec(struct cmd *self, struct cmd_q *cmdq)
cdata = xmalloc(sizeof *cdata);
cdata->cmd = xstrdup(args->argv[0]);
cdata->client = c;
cdata->client->references++;
status_prompt_set(c, new_prompt, NULL,
cmd_confirm_before_callback, cmd_confirm_before_free, cdata,
PROMPT_SINGLE);
@@ -81,43 +82,46 @@ cmd_confirm_before_exec(struct cmd *self, struct cmd_q *cmdq)
return (CMD_RETURN_NORMAL);
}
int
cmd_confirm_before_callback(void *data, const char *s)
static int
cmd_confirm_before_callback(struct client *c, void *data, const char *s,
__unused int done)
{
struct cmd_confirm_before_data *cdata = data;
struct client *c = cdata->client;
struct cmd_list *cmdlist;
char *cause;
struct cmdq_item *new_item;
struct cmd_parse_result *pr;
if (c->flags & CLIENT_DEAD)
return (0);
if (s == NULL || *s == '\0')
return (0);
if (tolower((u_char) s[0]) != 'y' || s[1] != '\0')
if (tolower((u_char)s[0]) != 'y' || s[1] != '\0')
return (0);
if (cmd_string_parse(cdata->cmd, &cmdlist, NULL, 0, &cause) != 0) {
if (cause != NULL) {
cmdq_error(c->cmdq, "%s", cause);
free(cause);
}
return (0);
pr = cmd_parse_from_string(cdata->cmd, NULL);
switch (pr->status) {
case CMD_PARSE_EMPTY:
new_item = NULL;
break;
case CMD_PARSE_ERROR:
new_item = cmdq_get_error(pr->error);
free(pr->error);
cmdq_append(c, new_item);
break;
case CMD_PARSE_SUCCESS:
new_item = cmdq_get_command(pr->cmdlist, NULL, NULL, 0);
cmd_list_free(pr->cmdlist);
cmdq_append(c, new_item);
break;
}
cmdq_run(c->cmdq, cmdlist);
cmd_list_free(cmdlist);
return (0);
}
void
static void
cmd_confirm_before_free(void *data)
{
struct cmd_confirm_before_data *cdata = data;
struct client *c = cdata->client;
c->references--;
free(cdata->cmd);
free(cdata);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -24,45 +24,66 @@
* Enter copy or clock mode.
*/
enum cmd_retval cmd_copy_mode_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_copy_mode_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_copy_mode_entry = {
"copy-mode", NULL,
"t:u", 0, 0,
"[-u] " CMD_TARGET_PANE_USAGE,
0,
cmd_copy_mode_exec
.name = "copy-mode",
.alias = NULL,
.args = { "eHMt:uq", 0, 0 },
.usage = "[-eHMuq] " CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_copy_mode_exec
};
const struct cmd_entry cmd_clock_mode_entry = {
"clock-mode", NULL,
"t:", 0, 0,
CMD_TARGET_PANE_USAGE,
0,
cmd_copy_mode_exec
.name = "clock-mode",
.alias = NULL,
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_copy_mode_exec
};
enum cmd_retval
cmd_copy_mode_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_copy_mode_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct window_pane *wp;
struct cmdq_shared *shared = item->shared;
struct client *c = item->client;
struct session *s;
struct window_pane *wp = item->target.wp;
if (cmd_find_pane(cmdq, args_get(args, 't'), NULL, &wp) == NULL)
return (CMD_RETURN_ERROR);
if (self->entry == &cmd_clock_mode_entry) {
window_pane_set_mode(wp, &window_clock_mode);
if (args_has(args, 'q')) {
window_pane_reset_mode_all(wp);
return (CMD_RETURN_NORMAL);
}
if (wp->mode != &window_copy_mode) {
if (window_pane_set_mode(wp, &window_copy_mode) != 0)
if (args_has(args, 'M')) {
if ((wp = cmd_mouse_pane(&shared->mouse, &s, NULL)) == NULL)
return (CMD_RETURN_NORMAL);
if (c == NULL || c->session != s)
return (CMD_RETURN_NORMAL);
window_copy_init_from_pane(wp);
}
if (wp->mode == &window_copy_mode && args_has(self->args, 'u'))
window_copy_pageup(wp);
if (self->entry == &cmd_clock_mode_entry) {
window_pane_set_mode(wp, &window_clock_mode, NULL, NULL);
return (CMD_RETURN_NORMAL);
}
if (!window_pane_set_mode(wp, &window_copy_mode, NULL, args)) {
if (args_has(args, 'M'))
window_copy_start_drag(c, &shared->mouse);
}
if (args_has(self->args, 'u'))
window_copy_pageup(wp, 0);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,39 +26,48 @@
* Detach a client.
*/
enum cmd_retval cmd_detach_client_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_detach_client_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_detach_client_entry = {
"detach-client", "detach",
"as:t:P", 0, 0,
"[-P] [-a] [-s target-session] " CMD_TARGET_CLIENT_USAGE,
CMD_READONLY,
cmd_detach_client_exec
.name = "detach-client",
.alias = "detach",
.args = { "aE:s:t:P", 0, 0 },
.usage = "[-aP] [-E shell-command] "
"[-s target-session] " CMD_TARGET_CLIENT_USAGE,
.source = { 's', CMD_FIND_SESSION, CMD_FIND_CANFAIL },
.flags = CMD_READONLY,
.exec = cmd_detach_client_exec
};
const struct cmd_entry cmd_suspend_client_entry = {
"suspend-client", "suspendc",
"t:", 0, 0,
CMD_TARGET_CLIENT_USAGE,
0,
cmd_detach_client_exec
.name = "suspend-client",
.alias = "suspendc",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_CLIENT_USAGE,
.flags = 0,
.exec = cmd_detach_client_exec
};
enum cmd_retval
cmd_detach_client_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_detach_client_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c, *cloop;
struct session *s;
enum msgtype msgtype;
u_int i;
const char *cmd = args_get(args, 'E');
if ((c = cmd_find_client(item, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
if (self->entry == &cmd_suspend_client_entry) {
if ((c = cmd_find_client(cmdq, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
tty_stop_tty(&c->tty);
c->flags |= CLIENT_SUSPENDED;
server_write_client(c, MSG_SUSPEND, NULL, 0);
server_client_suspend(c);
return (CMD_RETURN_NORMAL);
}
@@ -68,40 +77,35 @@ cmd_detach_client_exec(struct cmd *self, struct cmd_q *cmdq)
msgtype = MSG_DETACH;
if (args_has(args, 's')) {
s = cmd_find_session(cmdq, args_get(args, 's'), 0);
s = item->source.s;
if (s == NULL)
return (CMD_RETURN_ERROR);
for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
cloop = ARRAY_ITEM(&clients, i);
if (cloop == NULL || cloop->session != s)
continue;
server_write_client(cloop, msgtype,
cloop->session->name,
strlen(cloop->session->name) + 1);
return (CMD_RETURN_NORMAL);
TAILQ_FOREACH(cloop, &clients, entry) {
if (cloop->session == s) {
if (cmd != NULL)
server_client_exec(cloop, cmd);
else
server_client_detach(cloop, msgtype);
}
}
return (CMD_RETURN_STOP);
}
c = cmd_find_client(cmdq, args_get(args, 't'), 0);
if (c == NULL)
return (CMD_RETURN_ERROR);
if (args_has(args, 'a')) {
for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
cloop = ARRAY_ITEM(&clients, i);
if (cloop == NULL || cloop->session == NULL)
continue;
if (cloop == c)
continue;
server_write_client(cloop, msgtype,
cloop->session->name,
strlen(cloop->session->name) + 1);
TAILQ_FOREACH(cloop, &clients, entry) {
if (cloop->session != NULL && cloop != c) {
if (cmd != NULL)
server_client_exec(cloop, cmd);
else
server_client_detach(cloop, msgtype);
}
}
return (CMD_RETURN_NORMAL);
}
server_write_client(c, msgtype, c->session->name,
strlen(c->session->name) + 1);
if (cmd != NULL)
server_client_exec(c, cmd);
else
server_client_detach(c, msgtype);
return (CMD_RETURN_STOP);
}

178
cmd-display-menu.c Normal file
View File

@@ -0,0 +1,178 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2019 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* 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"
/*
* Display a menu on a client.
*/
static enum cmd_retval cmd_display_menu_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_display_menu_entry = {
.name = "display-menu",
.alias = "menu",
.args = { "c:t:T:x:y:", 1, -1 },
.usage = "[-c target-client] " CMD_TARGET_PANE_USAGE " [-T title] "
"[-x position] [-y position] name key command ...",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_display_menu_exec
};
static enum cmd_retval
cmd_display_menu_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct window_pane *wp = item->target.wp;
struct cmd_find_state *fs = &item->target;
struct menu *menu = NULL;
struct style_range *sr;
struct menu_item menu_item;
const char *xp, *yp, *key;
char *title, *name;
int at, flags, i;
u_int px, py, ox, oy, sx, sy;
if ((c = cmd_find_client(item, args_get(args, 'c'), 0)) == NULL)
return (CMD_RETURN_ERROR);
if (c->overlay_draw != NULL)
return (CMD_RETURN_NORMAL);
at = status_at_line(c);
if (args_has(args, 'T'))
title = format_single(NULL, args_get(args, 'T'), c, s, wl, wp);
else
title = xstrdup("");
menu = menu_create(title);
for (i = 0; i != args->argc; /* nothing */) {
name = args->argv[i++];
if (*name == '\0') {
menu_add_item(menu, NULL, item, c, fs);
continue;
}
if (args->argc - i < 2) {
cmdq_error(item, "not enough arguments");
free(title);
menu_free(menu);
return (CMD_RETURN_ERROR);
}
key = args->argv[i++];
menu_item.name = name;
menu_item.key = key_string_lookup_string(key);
menu_item.command = args->argv[i++];
menu_add_item(menu, &menu_item, item, c, fs);
}
free(title);
if (menu == NULL) {
cmdq_error(item, "invalid menu arguments");
return (CMD_RETURN_ERROR);
}
if (menu->count == 0) {
menu_free(menu);
return (CMD_RETURN_NORMAL);
}
xp = args_get(args, 'x');
if (xp == NULL)
px = 0;
else if (strcmp(xp, "R") == 0)
px = c->tty.sx - 1;
else if (strcmp(xp, "P") == 0) {
tty_window_offset(&c->tty, &ox, &oy, &sx, &sy);
if (wp->xoff >= ox)
px = wp->xoff - ox;
else
px = 0;
} else if (strcmp(xp, "M") == 0 && item->shared->mouse.valid) {
if (item->shared->mouse.x > (menu->width + 4) / 2)
px = item->shared->mouse.x - (menu->width + 4) / 2;
else
px = 0;
}
else if (strcmp(xp, "W") == 0) {
if (at == -1)
px = 0;
else {
TAILQ_FOREACH(sr, &c->status.entries[0].ranges, entry) {
if (sr->type != STYLE_RANGE_WINDOW)
continue;
if (sr->argument == (u_int)wl->idx)
break;
}
if (sr != NULL)
px = sr->start;
else
px = 0;
}
} else
px = strtoul(xp, NULL, 10);
if (px + menu->width + 4 >= c->tty.sx)
px = c->tty.sx - menu->width - 4;
yp = args_get(args, 'y');
if (yp == NULL)
py = 0;
else if (strcmp(yp, "P") == 0) {
tty_window_offset(&c->tty, &ox, &oy, &sx, &sy);
if (wp->yoff + wp->sy >= oy)
py = wp->yoff + wp->sy - oy;
else
py = 0;
} else if (strcmp(yp, "M") == 0 && item->shared->mouse.valid)
py = item->shared->mouse.y + menu->count + 2;
else if (strcmp(yp, "S") == 0) {
if (at == -1)
py = c->tty.sy;
else if (at == 0)
py = status_line_size(c) + menu->count + 2;
else
py = at;
} else
py = strtoul(yp, NULL, 10);
if (py < menu->count + 2)
py = 0;
else
py -= menu->count + 2;
if (py + menu->count + 2 >= c->tty.sy)
py = c->tty.sy - menu->count - 2;
flags = 0;
if (!item->shared->mouse.valid)
flags |= MENU_NOMOUSE;
if (menu_display(menu, flags, item, px, py, c, fs, NULL, NULL) != 0)
return (CMD_RETURN_NORMAL);
return (CMD_RETURN_WAIT);
}

View File

@@ -32,78 +32,94 @@
"#{window_name}, current pane #{pane_index} " \
"- (%H:%M %d-%b-%y)"
enum cmd_retval cmd_display_message_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_display_message_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_display_message_entry = {
"display-message", "display",
"c:pt:F:", 0, 1,
"[-p] [-c target-client] [-F format] " CMD_TARGET_PANE_USAGE
" [message]",
0,
cmd_display_message_exec
.name = "display-message",
.alias = "display",
.args = { "ac:Ipt:F:v", 0, 1 },
.usage = "[-aIpv] [-c target-client] [-F format] "
CMD_TARGET_PANE_USAGE " [message]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_display_message_exec
};
enum cmd_retval
cmd_display_message_exec(struct cmd *self, struct cmd_q *cmdq)
static void
cmd_display_message_each(const char *key, const char *value, void *arg)
{
struct cmdq_item *item = arg;
cmdq_print(item, "%s=%s", key, value);
}
static enum cmd_retval
cmd_display_message_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct session *s;
struct winlink *wl;
struct window_pane *wp;
struct client *c, *target_c;
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct window_pane *wp = item->target.wp;
const char *template;
char *msg;
char *msg, *cause;
struct format_tree *ft;
char out[BUFSIZ];
time_t t;
size_t len;
int flags;
if (args_has(args, 't')) {
wl = cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp);
if (wl == NULL)
return (CMD_RETURN_ERROR);
} else {
wl = cmd_find_pane(cmdq, NULL, &s, &wp);
if (wl == NULL)
if (args_has(args, 'I')) {
if (window_pane_start_input(wp, item, &cause) != 0) {
cmdq_error(item, "%s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_WAIT);
}
if (args_has(args, 'F') && args->argc != 0) {
cmdq_error(cmdq, "only one of -F or argument must be given");
cmdq_error(item, "only one of -F or argument must be given");
return (CMD_RETURN_ERROR);
}
if (args_has(args, 'c')) {
c = cmd_find_client(cmdq, args_get(args, 'c'), 0);
if (c == NULL)
return (CMD_RETURN_ERROR);
} else {
c = cmd_current_client(cmdq);
if (c == NULL && !args_has(self->args, 'p')) {
cmdq_error(cmdq, "no client available");
return (CMD_RETURN_ERROR);
}
}
template = args_get(args, 'F');
if (args->argc != 0)
template = args->argv[0];
if (template == NULL)
template = DISPLAY_MESSAGE_TEMPLATE;
ft = format_create();
format_defaults(ft, c, s, wl, wp);
t = time(NULL);
len = strftime(out, sizeof out, template, localtime(&t));
out[len] = '\0';
msg = format_expand(ft, out);
if (args_has(self->args, 'p'))
cmdq_print(cmdq, "%s", msg);
/*
* -c is intended to be the client where the message should be
* displayed if -p is not given. But it makes sense to use it for the
* formats too, assuming it matches the session. If it doesn't, use the
* best client for the session.
*/
c = cmd_find_client(item, args_get(args, 'c'), 1);
if (c != NULL && c->session == s)
target_c = c;
else
target_c = cmd_find_best_client(s);
if (args_has(self->args, 'v'))
flags = FORMAT_VERBOSE;
else
flags = 0;
ft = format_create(item->client, item, FORMAT_NONE, flags);
format_defaults(ft, target_c, s, wl, wp);
if (args_has(args, 'a')) {
format_each(ft, cmd_display_message_each, item);
return (CMD_RETURN_NORMAL);
}
msg = format_expand_time(ft, template);
if (args_has(self->args, 'p'))
cmdq_print(item, "%s", msg);
else if (c != NULL)
status_message_set(c, "%s", msg);
free(msg);
format_free(ft);
return (CMD_RETURN_NORMAL);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,32 +18,265 @@
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
/*
* Display panes on a client.
*/
enum cmd_retval cmd_display_panes_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_display_panes_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_display_panes_entry = {
"display-panes", "displayp",
"t:", 0, 0,
CMD_TARGET_CLIENT_USAGE,
0,
cmd_display_panes_exec
.name = "display-panes",
.alias = "displayp",
.args = { "bd:t:", 0, 1 },
.usage = "[-b] [-d duration] " CMD_TARGET_CLIENT_USAGE " [template]",
.flags = CMD_AFTERHOOK,
.exec = cmd_display_panes_exec
};
enum cmd_retval
cmd_display_panes_exec(struct cmd *self, struct cmd_q *cmdq)
struct cmd_display_panes_data {
struct cmdq_item *item;
char *command;
};
static void
cmd_display_panes_draw_pane(struct screen_redraw_ctx *ctx,
struct window_pane *wp)
{
struct args *args = self->args;
struct client *c;
struct client *c = ctx->c;
struct tty *tty = &c->tty;
struct session *s = c->session;
struct options *oo = s->options;
struct window *w = wp->window;
struct grid_cell gc;
u_int idx, px, py, i, j, xoff, yoff, sx, sy;
int colour, active_colour;
char buf[16], *ptr;
size_t len;
if ((c = cmd_find_client(cmdq, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
if (wp->xoff + wp->sx <= ctx->ox ||
wp->xoff >= ctx->ox + ctx->sx ||
wp->yoff + wp->sy <= ctx->oy ||
wp->yoff >= ctx->oy + ctx->sy)
return;
server_set_identify(c);
if (wp->xoff >= ctx->ox && wp->xoff + wp->sx <= ctx->ox + ctx->sx) {
/* All visible. */
xoff = wp->xoff - ctx->ox;
sx = wp->sx;
} else if (wp->xoff < ctx->ox &&
wp->xoff + wp->sx > ctx->ox + ctx->sx) {
/* Both left and right not visible. */
xoff = 0;
sx = ctx->sx;
} else if (wp->xoff < ctx->ox) {
/* Left not visible. */
xoff = 0;
sx = wp->sx - (ctx->ox - wp->xoff);
} else {
/* Right not visible. */
xoff = wp->xoff - ctx->ox;
sx = wp->sx - xoff;
}
if (wp->yoff >= ctx->oy && wp->yoff + wp->sy <= ctx->oy + ctx->sy) {
/* All visible. */
yoff = wp->yoff - ctx->oy;
sy = wp->sy;
} else if (wp->yoff < ctx->oy &&
wp->yoff + wp->sy > ctx->oy + ctx->sy) {
/* Both top and bottom not visible. */
yoff = 0;
sy = ctx->sy;
} else if (wp->yoff < ctx->oy) {
/* Top not visible. */
yoff = 0;
sy = wp->sy - (ctx->oy - wp->yoff);
} else {
/* Bottom not visible. */
yoff = wp->yoff - ctx->oy;
sy = wp->sy - yoff;
}
return (CMD_RETURN_NORMAL);
if (ctx->statustop)
yoff += ctx->statuslines;
px = sx / 2;
py = sy / 2;
if (window_pane_index(wp, &idx) != 0)
fatalx("index not found");
len = xsnprintf(buf, sizeof buf, "%u", idx);
if (sx < len)
return;
colour = options_get_number(oo, "display-panes-colour");
active_colour = options_get_number(oo, "display-panes-active-colour");
if (sx < len * 6 || sy < 5) {
tty_cursor(tty, xoff + px - len / 2, yoff + py);
goto draw_text;
}
px -= len * 3;
py -= 2;
memcpy(&gc, &grid_default_cell, sizeof gc);
if (w->active == wp)
gc.bg = active_colour;
else
gc.bg = colour;
gc.flags |= GRID_FLAG_NOPALETTE;
tty_attributes(tty, &gc, wp);
for (ptr = buf; *ptr != '\0'; ptr++) {
if (*ptr < '0' || *ptr > '9')
continue;
idx = *ptr - '0';
for (j = 0; j < 5; j++) {
for (i = px; i < px + 5; i++) {
tty_cursor(tty, xoff + i, yoff + py + j);
if (window_clock_table[idx][j][i - px])
tty_putc(tty, ' ');
}
}
px += 6;
}
len = xsnprintf(buf, sizeof buf, "%ux%u", wp->sx, wp->sy);
if (sx < len || sy < 6)
return;
tty_cursor(tty, xoff + sx - len, yoff);
draw_text:
memcpy(&gc, &grid_default_cell, sizeof gc);
if (w->active == wp)
gc.fg = active_colour;
else
gc.fg = colour;
gc.flags |= GRID_FLAG_NOPALETTE;
tty_attributes(tty, &gc, wp);
tty_puts(tty, buf);
tty_cursor(tty, 0, 0);
}
static void
cmd_display_panes_draw(struct client *c, struct screen_redraw_ctx *ctx)
{
struct window *w = c->session->curw->window;
struct window_pane *wp;
log_debug("%s: %s @%u", __func__, c->name, w->id);
TAILQ_FOREACH(wp, &w->panes, entry) {
if (window_pane_visible(wp))
cmd_display_panes_draw_pane(ctx, wp);
}
}
static void
cmd_display_panes_free(struct client *c)
{
struct cmd_display_panes_data *cdata = c->overlay_data;
if (cdata->item != NULL)
cmdq_continue(cdata->item);
free(cdata->command);
free(cdata);
}
static int
cmd_display_panes_key(struct client *c, struct key_event *event)
{
struct cmd_display_panes_data *cdata = c->overlay_data;
struct cmdq_item *new_item;
char *cmd, *expanded;
struct window *w = c->session->curw->window;
struct window_pane *wp;
struct cmd_parse_result *pr;
if (event->key < '0' || event->key > '9')
return (-1);
wp = window_pane_at_index(w, event->key - '0');
if (wp == NULL)
return (1);
window_unzoom(w);
xasprintf(&expanded, "%%%u", wp->id);
cmd = cmd_template_replace(cdata->command, expanded, 1);
pr = cmd_parse_from_string(cmd, NULL);
switch (pr->status) {
case CMD_PARSE_EMPTY:
new_item = NULL;
break;
case CMD_PARSE_ERROR:
new_item = cmdq_get_error(pr->error);
free(pr->error);
cmdq_append(c, new_item);
break;
case CMD_PARSE_SUCCESS:
new_item = cmdq_get_command(pr->cmdlist, NULL, NULL, 0);
cmd_list_free(pr->cmdlist);
cmdq_append(c, new_item);
break;
}
free(cmd);
free(expanded);
return (1);
}
static enum cmd_retval
cmd_display_panes_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct session *s;
u_int delay;
char *cause;
struct cmd_display_panes_data *cdata;
if ((c = cmd_find_client(item, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
s = c->session;
if (c->overlay_draw != NULL)
return (CMD_RETURN_NORMAL);
if (args_has(args, 'd')) {
delay = args_strtonum(args, 'd', 0, UINT_MAX, &cause);
if (cause != NULL) {
cmdq_error(item, "delay %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
} else
delay = options_get_number(s->options, "display-panes-time");
cdata = xmalloc(sizeof *cdata);
if (args->argc != 0)
cdata->command = xstrdup(args->argv[0]);
else
cdata->command = xstrdup("select-pane -t '%%'");
if (args_has(args, 'b'))
cdata->item = NULL;
else
cdata->item = item;
server_client_set_overlay(c, delay, cmd_display_panes_draw,
cmd_display_panes_key, cmd_display_panes_free, cdata);
if (args_has(args, 'b'))
return (CMD_RETURN_NORMAL);
return (CMD_RETURN_WAIT);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,9 +18,7 @@
#include <sys/types.h>
#include <fnmatch.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
@@ -28,205 +26,100 @@
* Find window containing text.
*/
#define FIND_WINDOW_TEMPLATE \
"#{window_index}: #{window_name} " \
"[#{window_width}x#{window_height}] " \
"(#{window_panes} panes) #{window_find_matches}"
enum cmd_retval cmd_find_window_exec(struct cmd *, struct cmd_q *);
void cmd_find_window_callback(struct window_choose_data *);
/* Flags for determining matching behavior. */
#define CMD_FIND_WINDOW_BY_TITLE 0x1
#define CMD_FIND_WINDOW_BY_CONTENT 0x2
#define CMD_FIND_WINDOW_BY_NAME 0x4
#define CMD_FIND_WINDOW_ALL \
(CMD_FIND_WINDOW_BY_TITLE | \
CMD_FIND_WINDOW_BY_CONTENT | \
CMD_FIND_WINDOW_BY_NAME)
static enum cmd_retval cmd_find_window_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_find_window_entry = {
"find-window", "findw",
"F:CNt:T", 1, 4,
"[-CNT] [-F format] " CMD_TARGET_WINDOW_USAGE " match-string",
0,
cmd_find_window_exec
.name = "find-window",
.alias = "findw",
.args = { "CNrt:TZ", 1, 1 },
.usage = "[-CNrTZ] " CMD_TARGET_PANE_USAGE " match-string",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_find_window_exec
};
struct cmd_find_window_data {
struct winlink *wl;
char *list_ctx;
u_int pane_id;
};
ARRAY_DECL(cmd_find_window_data_list, struct cmd_find_window_data);
u_int cmd_find_window_match_flags(struct args *);
void cmd_find_window_match(struct cmd_find_window_data_list *, int,
struct winlink *, const char *, const char *);
u_int
cmd_find_window_match_flags(struct args *args)
static enum cmd_retval
cmd_find_window_exec(struct cmd *self, struct cmdq_item *item)
{
u_int match_flags = 0;
struct args *args = self->args, *new_args;
struct window_pane *wp = item->target.wp;
const char *s = args->argv[0];
char *filter, *argv = { NULL };
int C, N, T;
/* Turn on flags based on the options. */
if (args_has(args, 'T'))
match_flags |= CMD_FIND_WINDOW_BY_TITLE;
if (args_has(args, 'C'))
match_flags |= CMD_FIND_WINDOW_BY_CONTENT;
if (args_has(args, 'N'))
match_flags |= CMD_FIND_WINDOW_BY_NAME;
C = args_has(args, 'C');
N = args_has(args, 'N');
T = args_has(args, 'T');
/* If none of the flags were set, default to matching anything. */
if (match_flags == 0)
match_flags = CMD_FIND_WINDOW_ALL;
if (!C && !N && !T)
C = N = T = 1;
return (match_flags);
}
void
cmd_find_window_match(struct cmd_find_window_data_list *find_list,
int match_flags, struct winlink *wl, const char *str,
const char *searchstr)
{
struct cmd_find_window_data find_data;
struct window_pane *wp;
u_int i, line;
char *sres;
memset(&find_data, 0, sizeof find_data);
i = 0;
TAILQ_FOREACH(wp, &wl->window->panes, entry) {
i++;
if ((match_flags & CMD_FIND_WINDOW_BY_NAME) &&
fnmatch(searchstr, wl->window->name, 0) == 0) {
find_data.list_ctx = xstrdup("");
break;
}
if ((match_flags & CMD_FIND_WINDOW_BY_TITLE) &&
fnmatch(searchstr, wp->base.title, 0) == 0) {
xasprintf(&find_data.list_ctx,
"pane %u title: \"%s\"", i - 1, wp->base.title);
break;
}
if (match_flags & CMD_FIND_WINDOW_BY_CONTENT &&
(sres = window_pane_search(wp, str, &line)) != NULL) {
xasprintf(&find_data.list_ctx,
"pane %u line %u: \"%s\"", i - 1, line + 1, sres);
free(sres);
break;
}
}
if (find_data.list_ctx != NULL) {
find_data.wl = wl;
find_data.pane_id = i - 1;
ARRAY_ADD(find_list, find_data);
}
}
enum cmd_retval
cmd_find_window_exec(struct cmd *self, struct cmd_q *cmdq)
{
struct args *args = self->args;
struct client *c;
struct window_choose_data *cdata;
struct session *s;
struct winlink *wl, *wm;
struct cmd_find_window_data_list find_list;
char *str, *searchstr;
const char *template;
u_int i, match_flags;
if ((c = cmd_current_client(cmdq)) == NULL) {
cmdq_error(cmdq, "no client available");
return (CMD_RETURN_ERROR);
}
s = c->session;
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), NULL)) == NULL)
return (CMD_RETURN_ERROR);
if ((template = args_get(args, 'F')) == NULL)
template = FIND_WINDOW_TEMPLATE;
match_flags = cmd_find_window_match_flags(args);
str = args->argv[0];
ARRAY_INIT(&find_list);
xasprintf(&searchstr, "*%s*", str);
RB_FOREACH(wm, winlinks, &s->windows)
cmd_find_window_match(&find_list, match_flags, wm, str, searchstr);
free(searchstr);
if (ARRAY_LENGTH(&find_list) == 0) {
cmdq_error(cmdq, "no windows matching: %s", str);
ARRAY_FREE(&find_list);
return (CMD_RETURN_ERROR);
if (!args_has(args, 'r')) {
if (C && N && T) {
xasprintf(&filter,
"#{||:"
"#{C:%s},#{||:#{m:*%s*,#{window_name}},"
"#{m:*%s*,#{pane_title}}}}",
s, s, s);
} else if (C && N) {
xasprintf(&filter,
"#{||:#{C:%s},#{m:*%s*,#{window_name}}}",
s, s);
} else if (C && T) {
xasprintf(&filter,
"#{||:#{C:%s},#{m:*%s*,#{pane_title}}}",
s, s);
} else if (N && T) {
xasprintf(&filter,
"#{||:#{m:*%s*,#{window_name}},"
"#{m:*%s*,#{pane_title}}}",
s, s);
} else if (C)
xasprintf(&filter, "#{C:%s}", s);
else if (N)
xasprintf(&filter, "#{m:*%s*,#{window_name}}", s);
else
xasprintf(&filter, "#{m:*%s*,#{pane_title}}", s);
} else {
if (C && N && T) {
xasprintf(&filter,
"#{||:"
"#{C/r:%s},#{||:#{m/r:%s,#{window_name}},"
"#{m/r:%s,#{pane_title}}}}",
s, s, s);
} else if (C && N) {
xasprintf(&filter,
"#{||:#{C/r:%s},#{m/r:%s,#{window_name}}}",
s, s);
} else if (C && T) {
xasprintf(&filter,
"#{||:#{C/r:%s},#{m/r:%s,#{pane_title}}}",
s, s);
} else if (N && T) {
xasprintf(&filter,
"#{||:#{m/r:%s,#{window_name}},"
"#{m/r:%s,#{pane_title}}}",
s, s);
} else if (C)
xasprintf(&filter, "#{C/r:%s}", s);
else if (N)
xasprintf(&filter, "#{m/r:%s,#{window_name}}", s);
else
xasprintf(&filter, "#{m/r:%s,#{pane_title}}", s);
}
if (ARRAY_LENGTH(&find_list) == 1) {
if (session_select(s, ARRAY_FIRST(&find_list).wl->idx) == 0)
server_redraw_session(s);
recalculate_sizes();
goto out;
}
new_args = args_parse("", 1, &argv);
if (args_has(args, 'Z'))
args_set(new_args, 'Z', NULL);
args_set(new_args, 'f', filter);
if (window_pane_set_mode(wl->window->active, &window_choose_mode) != 0)
goto out;
window_pane_set_mode(wp, &window_tree_mode, &item->target, new_args);
for (i = 0; i < ARRAY_LENGTH(&find_list); i++) {
wm = ARRAY_ITEM(&find_list, i).wl;
args_free(new_args);
free(filter);
cdata = window_choose_data_create(TREE_OTHER, c, c->session);
cdata->idx = wm->idx;
cdata->wl = wm;
cdata->ft_template = xstrdup(template);
cdata->pane_id = ARRAY_ITEM(&find_list, i).pane_id;
format_add(cdata->ft, "line", "%u", i);
format_add(cdata->ft, "window_find_matches", "%s",
ARRAY_ITEM(&find_list, i).list_ctx);
format_defaults(cdata->ft, NULL, s, wm, NULL);
window_choose_add(wl->window->active, cdata);
}
window_choose_ready(wl->window->active, 0, cmd_find_window_callback);
out:
for (i = 0; i < ARRAY_LENGTH(&find_list); i++)
free(ARRAY_ITEM(&find_list, i).list_ctx);
ARRAY_FREE(&find_list);
return (CMD_RETURN_NORMAL);
}
void
cmd_find_window_callback(struct window_choose_data *cdata)
{
struct session *s;
struct window_pane *wp;
if (cdata == NULL)
return;
s = cdata->start_session;
if (!session_alive(s))
return;
wp = window_pane_at_index(cdata->wl->window, cdata->pane_id);
if (wp != NULL && window_pane_visible(wp))
window_set_active_pane(cdata->wl->window, wp);
if (session_select(s, cdata->idx) == 0) {
server_redraw_session(s);
recalculate_sizes();
}
}

1300
cmd-find.c Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -29,165 +29,193 @@
* Executes a tmux command if a shell command returns true or false.
*/
enum cmd_retval cmd_if_shell_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_if_shell_exec(struct cmd *, struct cmdq_item *);
void cmd_if_shell_callback(struct job *);
void cmd_if_shell_done(struct cmd_q *);
void cmd_if_shell_free(void *);
static void cmd_if_shell_callback(struct job *);
static void cmd_if_shell_free(void *);
const struct cmd_entry cmd_if_shell_entry = {
"if-shell", "if",
"bFt:", 2, 3,
"[-bF] " CMD_TARGET_PANE_USAGE " shell-command command [command]",
0,
cmd_if_shell_exec
.name = "if-shell",
.alias = "if",
.args = { "bFt:", 2, 3 },
.usage = "[-bF] " CMD_TARGET_PANE_USAGE " shell-command command "
"[command]",
.target = { 't', CMD_FIND_PANE, CMD_FIND_CANFAIL },
.flags = 0,
.exec = cmd_if_shell_exec
};
struct cmd_if_shell_data {
char *cmd_if;
char *cmd_else;
struct cmd_q *cmdq;
int bflag;
int started;
struct cmd_parse_input input;
char *cmd_if;
char *cmd_else;
struct client *client;
struct cmdq_item *item;
struct mouse_event mouse;
};
enum cmd_retval
cmd_if_shell_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_if_shell_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct mouse_event *m = &item->shared->mouse;
struct cmd_if_shell_data *cdata;
char *shellcmd, *cmd, *cause;
struct cmd_list *cmdlist;
struct client *c;
struct session *s = NULL;
struct winlink *wl = NULL;
struct window_pane *wp = NULL;
struct format_tree *ft;
if (args_has(args, 't'))
wl = cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp);
else {
c = cmd_find_client(cmdq, NULL, 1);
if (c != NULL && c->session != NULL) {
s = c->session;
wl = s->curw;
wp = wl->window->active;
}
}
ft = format_create();
format_defaults(ft, NULL, s, wl, wp);
shellcmd = format_expand(ft, args->argv[0]);
format_free(ft);
char *shellcmd, *cmd;
struct cmdq_item *new_item;
struct cmd_find_state *fs = &item->target;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = fs->s;
struct winlink *wl = fs->wl;
struct window_pane *wp = fs->wp;
struct cmd_parse_input pi;
struct cmd_parse_result *pr;
shellcmd = format_single(item, args->argv[0], c, s, wl, wp);
if (args_has(args, 'F')) {
cmd = NULL;
if (*shellcmd != '0' && *shellcmd != '\0')
cmd = args->argv[1];
else if (args->argc == 3)
cmd = args->argv[2];
else
cmd = NULL;
free(shellcmd);
if (cmd == NULL)
return (CMD_RETURN_NORMAL);
if (cmd_string_parse(cmd, &cmdlist, NULL, 0, &cause) != 0) {
if (cause != NULL) {
cmdq_error(cmdq, "%s", cause);
free(cause);
}
memset(&pi, 0, sizeof pi);
if (self->file != NULL)
pi.file = self->file;
pi.line = self->line;
pi.item = item;
pi.c = c;
cmd_find_copy_state(&pi.fs, fs);
pr = cmd_parse_from_string(cmd, &pi);
switch (pr->status) {
case CMD_PARSE_EMPTY:
break;
case CMD_PARSE_ERROR:
cmdq_error(item, "%s", pr->error);
free(pr->error);
return (CMD_RETURN_ERROR);
case CMD_PARSE_SUCCESS:
new_item = cmdq_get_command(pr->cmdlist, fs, m, 0);
cmdq_insert_after(item, new_item);
cmd_list_free(pr->cmdlist);
break;
}
cmdq_run(cmdq, cmdlist);
cmd_list_free(cmdlist);
return (CMD_RETURN_NORMAL);
}
cdata = xmalloc(sizeof *cdata);
cdata = xcalloc(1, sizeof *cdata);
cdata->cmd_if = xstrdup(args->argv[1]);
if (args->argc == 3)
cdata->cmd_else = xstrdup(args->argv[2]);
else
cdata->cmd_else = NULL;
cdata->bflag = args_has(args, 'b');
memcpy(&cdata->mouse, m, sizeof cdata->mouse);
cdata->started = 0;
cdata->cmdq = cmdq;
cmdq->references++;
if (!args_has(args, 'b'))
cdata->client = item->client;
else
cdata->client = c;
if (cdata->client != NULL)
cdata->client->references++;
job_run(shellcmd, s, cmd_if_shell_callback, cmd_if_shell_free, cdata);
if (!args_has(args, 'b'))
cdata->item = item;
else
cdata->item = NULL;
memset(&cdata->input, 0, sizeof cdata->input);
if (self->file != NULL)
cdata->input.file = xstrdup(self->file);
cdata->input.line = self->line;
cdata->input.item = cdata->item;
cdata->input.c = c;
if (cdata->input.c != NULL)
cdata->input.c->references++;
cmd_find_copy_state(&cdata->input.fs, fs);
if (job_run(shellcmd, s, server_client_get_cwd(item->client, s), NULL,
cmd_if_shell_callback, cmd_if_shell_free, cdata, 0) == NULL) {
cmdq_error(item, "failed to run command: %s", shellcmd);
free(shellcmd);
free(cdata);
return (CMD_RETURN_ERROR);
}
free(shellcmd);
if (cdata->bflag)
if (args_has(args, 'b'))
return (CMD_RETURN_NORMAL);
return (CMD_RETURN_WAIT);
}
void
static void
cmd_if_shell_callback(struct job *job)
{
struct cmd_if_shell_data *cdata = job->data;
struct cmd_q *cmdq = cdata->cmdq, *cmdq1;
struct cmd_list *cmdlist;
char *cause, *cmd;
struct cmd_if_shell_data *cdata = job_get_data(job);
struct client *c = cdata->client;
struct mouse_event *m = &cdata->mouse;
struct cmdq_item *new_item = NULL;
char *cmd;
int status;
struct cmd_parse_result *pr;
if (cmdq->dead)
return;
if (!WIFEXITED(job->status) || WEXITSTATUS(job->status) != 0)
status = job_get_status(job);
if (!WIFEXITED(status) || WEXITSTATUS(status) != 0)
cmd = cdata->cmd_else;
else
cmd = cdata->cmd_if;
if (cmd == NULL)
return;
goto out;
if (cmd_string_parse(cmd, &cmdlist, NULL, 0, &cause) != 0) {
if (cause != NULL) {
cmdq_error(cmdq, "%s", cause);
free(cause);
}
return;
pr = cmd_parse_from_string(cmd, &cdata->input);
switch (pr->status) {
case CMD_PARSE_EMPTY:
break;
case CMD_PARSE_ERROR:
if (cdata->item != NULL)
cmdq_error(cdata->item, "%s", pr->error);
free(pr->error);
break;
case CMD_PARSE_SUCCESS:
new_item = cmdq_get_command(pr->cmdlist, NULL, m, 0);
cmd_list_free(pr->cmdlist);
break;
}
if (new_item != NULL) {
if (cdata->item == NULL)
cmdq_append(c, new_item);
else
cmdq_insert_after(cdata->item, new_item);
}
cdata->started = 1;
cmdq1 = cmdq_new(cmdq->client);
cmdq1->emptyfn = cmd_if_shell_done;
cmdq1->data = cdata;
cmdq_run(cmdq1, cmdlist);
cmd_list_free(cmdlist);
out:
if (cdata->item != NULL)
cmdq_continue(cdata->item);
}
void
cmd_if_shell_done(struct cmd_q *cmdq1)
{
struct cmd_if_shell_data *cdata = cmdq1->data;
struct cmd_q *cmdq = cdata->cmdq;
if (cmdq1->client_exit >= 0)
cmdq->client_exit = cmdq1->client_exit;
if (!cmdq_free(cmdq) && !cdata->bflag)
cmdq_continue(cmdq);
cmdq_free(cmdq1);
free(cdata->cmd_else);
free(cdata->cmd_if);
free(cdata);
}
void
static void
cmd_if_shell_free(void *data)
{
struct cmd_if_shell_data *cdata = data;
struct cmd_q *cmdq = cdata->cmdq;
if (cdata->started)
return;
if (!cmdq_free(cmdq) && !cdata->bflag)
cmdq_continue(cmdq);
if (cdata->client != NULL)
server_client_unref(cdata->client);
free(cdata->cmd_else);
free(cdata->cmd_if);
if (cdata->input.c != NULL)
server_client_unref(cdata->input.c);
free((void *)cdata->input.file);
free(cdata);
}

View File

@@ -2,7 +2,7 @@
/*
* Copyright (c) 2011 George Nachman <tmux@georgester.com>
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -20,6 +20,7 @@
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include "tmux.h"
@@ -28,64 +29,76 @@
* Join or move a pane into another (like split/swap/kill).
*/
enum cmd_retval cmd_join_pane_exec(struct cmd *, struct cmd_q *);
enum cmd_retval join_pane(struct cmd *, struct cmd_q *, int);
static enum cmd_retval cmd_join_pane_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_join_pane_entry = {
"join-pane", "joinp",
"bdhvp:l:s:t:", 0, 0,
"[-bdhv] [-p percentage|-l size] [-s src-pane] [-t dst-pane]",
0,
cmd_join_pane_exec
.name = "join-pane",
.alias = "joinp",
.args = { "bdfhvp:l:s:t:", 0, 0 },
.usage = "[-bdfhv] [-l size] " CMD_SRCDST_PANE_USAGE,
.source = { 's', CMD_FIND_PANE, CMD_FIND_DEFAULT_MARKED },
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_join_pane_exec
};
const struct cmd_entry cmd_move_pane_entry = {
"move-pane", "movep",
"bdhvp:l:s:t:", 0, 0,
"[-bdhv] [-p percentage|-l size] [-s src-pane] [-t dst-pane]",
0,
cmd_join_pane_exec
.name = "move-pane",
.alias = "movep",
.args = { "bdhvp:l:s:t:", 0, 0 },
.usage = "[-bdhv] [-p percentage|-l size] " CMD_SRCDST_PANE_USAGE,
.source = { 's', CMD_FIND_PANE, CMD_FIND_DEFAULT_MARKED },
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_join_pane_exec
};
enum cmd_retval
cmd_join_pane_exec(struct cmd *self, struct cmd_q *cmdq)
{
return (join_pane(self, cmdq, self->entry == &cmd_join_pane_entry));
}
enum cmd_retval
join_pane(struct cmd *self, struct cmd_q *cmdq, int not_same_window)
static enum cmd_retval
cmd_join_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct cmd_find_state *current = &item->shared->current;
struct session *dst_s;
struct winlink *src_wl, *dst_wl;
struct window *src_w, *dst_w;
struct window_pane *src_wp, *dst_wp;
char *cause;
int size, percentage, dst_idx;
char *cause, *copy;
const char *errstr, *p;
size_t plen;
int size, percentage, dst_idx, not_same_window;
int flags;
enum layout_type type;
struct layout_cell *lc;
dst_wl = cmd_find_pane(cmdq, args_get(args, 't'), &dst_s, &dst_wp);
if (dst_wl == NULL)
return (CMD_RETURN_ERROR);
if (self->entry == &cmd_join_pane_entry)
not_same_window = 1;
else
not_same_window = 0;
dst_s = item->target.s;
dst_wl = item->target.wl;
dst_wp = item->target.wp;
dst_w = dst_wl->window;
dst_idx = dst_wl->idx;
server_unzoom_window(dst_w);
src_wl = cmd_find_pane(cmdq, args_get(args, 's'), NULL, &src_wp);
if (src_wl == NULL)
return (CMD_RETURN_ERROR);
src_wl = item->source.wl;
src_wp = item->source.wp;
src_w = src_wl->window;
server_unzoom_window(src_w);
if (not_same_window && src_w == dst_w) {
cmdq_error(cmdq, "can't join a pane to its own window");
cmdq_error(item, "can't join a pane to its own window");
return (CMD_RETURN_ERROR);
}
if (!not_same_window && src_wp == dst_wp) {
cmdq_error(cmdq, "source and target panes must be different");
cmdq_error(item, "source and target panes must be different");
return (CMD_RETURN_ERROR);
}
@@ -94,17 +107,33 @@ join_pane(struct cmd *self, struct cmd_q *cmdq, int not_same_window)
type = LAYOUT_LEFTRIGHT;
size = -1;
if (args_has(args, 'l')) {
size = args_strtonum(args, 'l', 0, INT_MAX, &cause);
if (cause != NULL) {
cmdq_error(cmdq, "size %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
if ((p = args_get(args, 'l')) != NULL) {
plen = strlen(p);
if (p[plen - 1] == '%') {
copy = xstrdup(p);
copy[plen - 1] = '\0';
percentage = strtonum(copy, 0, INT_MAX, &errstr);
free(copy);
if (errstr != NULL) {
cmdq_error(item, "percentage %s", errstr);
return (CMD_RETURN_ERROR);
}
if (type == LAYOUT_TOPBOTTOM)
size = (dst_wp->sy * percentage) / 100;
else
size = (dst_wp->sx * percentage) / 100;
} else {
size = args_strtonum(args, 'l', 0, INT_MAX, &cause);
if (cause != NULL) {
cmdq_error(item, "size %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
}
} else if (args_has(args, 'p')) {
percentage = args_strtonum(args, 'p', 0, 100, &cause);
if (cause != NULL) {
cmdq_error(cmdq, "percentage %s", cause);
cmdq_error(item, "percentage %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
@@ -113,9 +142,16 @@ join_pane(struct cmd *self, struct cmd_q *cmdq, int not_same_window)
else
size = (dst_wp->sx * percentage) / 100;
}
lc = layout_split_pane(dst_wp, type, size, args_has(args, 'b'));
flags = 0;
if (args_has(args, 'b'))
flags |= SPAWN_BEFORE;
if (args_has(args, 'f'))
flags |= SPAWN_FULLSIZE;
lc = layout_split_pane(dst_wp, type, size, flags);
if (lc == NULL) {
cmdq_error(cmdq, "create pane failed: pane too small");
cmdq_error(item, "create pane failed: pane too small");
return (CMD_RETURN_ERROR);
}
@@ -124,12 +160,9 @@ join_pane(struct cmd *self, struct cmd_q *cmdq, int not_same_window)
window_lost_pane(src_w, src_wp);
TAILQ_REMOVE(&src_w->panes, src_wp, entry);
if (window_count_panes(src_w) == 0)
server_kill_window(src_w);
else
notify_window_layout_changed(src_w);
src_wp->window = dst_w;
options_set_parent(src_wp->options, dst_w->options);
src_wp->flags |= PANE_STYLECHANGED;
TAILQ_INSERT_AFTER(&dst_w->panes, dst_wp, src_wp, entry);
layout_assign_pane(lc, src_wp);
@@ -139,12 +172,18 @@ join_pane(struct cmd *self, struct cmd_q *cmdq, int not_same_window)
server_redraw_window(dst_w);
if (!args_has(args, 'd')) {
window_set_active_pane(dst_w, src_wp);
window_set_active_pane(dst_w, src_wp, 1);
session_select(dst_s, dst_idx);
cmd_find_from_session(current, dst_s, 0);
server_redraw_session(dst_s);
} else
server_status_session(dst_s);
notify_window_layout_changed(dst_w);
if (window_count_panes(src_w) == 0)
server_kill_window(src_w);
else
notify_window("window-layout-changed", src_w);
notify_window("window-layout-changed", dst_w);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,46 +26,39 @@
* Kill pane.
*/
enum cmd_retval cmd_kill_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_kill_pane_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_kill_pane_entry = {
"kill-pane", "killp",
"at:", 0, 0,
"[-a] " CMD_TARGET_PANE_USAGE,
0,
cmd_kill_pane_exec
.name = "kill-pane",
.alias = "killp",
.args = { "at:", 0, 0 },
.usage = "[-a] " CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_kill_pane_exec
};
enum cmd_retval
cmd_kill_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_kill_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct window_pane *loopwp, *tmpwp, *wp;
if ((wl = cmd_find_pane(cmdq, args_get(args, 't'), NULL, &wp)) == NULL)
return (CMD_RETURN_ERROR);
server_unzoom_window(wl->window);
if (window_count_panes(wl->window) == 1) {
/* Only one pane, kill the window. */
server_kill_window(wl->window);
recalculate_sizes();
return (CMD_RETURN_NORMAL);
}
struct winlink *wl = item->target.wl;
struct window_pane *loopwp, *tmpwp, *wp = item->target.wp;
if (args_has(self->args, 'a')) {
server_unzoom_window(wl->window);
TAILQ_FOREACH_SAFE(loopwp, &wl->window->panes, entry, tmpwp) {
if (loopwp == wp)
continue;
layout_close_pane(loopwp);
window_remove_pane(wl->window, loopwp);
}
} else {
layout_close_pane(wp);
window_remove_pane(wl->window, wp);
server_redraw_window(wl->window);
return (CMD_RETURN_NORMAL);
}
server_redraw_window(wl->window);
server_kill_pane(wp);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,26 +27,32 @@
* Kill the server and do nothing else.
*/
enum cmd_retval cmd_kill_server_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_kill_server_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_kill_server_entry = {
"kill-server", NULL,
"", 0, 0,
"",
0,
cmd_kill_server_exec
.name = "kill-server",
.alias = NULL,
.args = { "", 0, 0 },
.usage = "",
.flags = 0,
.exec = cmd_kill_server_exec
};
const struct cmd_entry cmd_start_server_entry = {
"start-server", "start",
"", 0, 0,
"",
CMD_STARTSERVER,
cmd_kill_server_exec
.name = "start-server",
.alias = "start",
.args = { "", 0, 0 },
.usage = "",
.flags = CMD_STARTSERVER,
.exec = cmd_kill_server_exec
};
enum cmd_retval
cmd_kill_server_exec(struct cmd *self, unused struct cmd_q *cmdq)
static enum cmd_retval
cmd_kill_server_exec(struct cmd *self, __unused struct cmdq_item *item)
{
if (self->entry == &cmd_kill_server_entry)
kill(getpid(), SIGTERM);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,35 +27,46 @@
* Note this deliberately has no alias to make it hard to hit by accident.
*/
enum cmd_retval cmd_kill_session_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_kill_session_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_kill_session_entry = {
"kill-session", NULL,
"at:", 0, 0,
"[-a] " CMD_TARGET_SESSION_USAGE,
0,
cmd_kill_session_exec
.name = "kill-session",
.alias = NULL,
.args = { "aCt:", 0, 0 },
.usage = "[-aC] " CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = 0,
.exec = cmd_kill_session_exec
};
enum cmd_retval
cmd_kill_session_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_kill_session_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s, *s2, *s3;
struct session *s, *sloop, *stmp;
struct winlink *wl;
if ((s = cmd_find_session(cmdq, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
s = item->target.s;
if (args_has(args, 'a')) {
RB_FOREACH_SAFE(s2, sessions, &sessions, s3) {
if (s != s2) {
server_destroy_session(s2);
session_destroy(s2);
if (args_has(args, 'C')) {
RB_FOREACH(wl, winlinks, &s->windows) {
wl->window->flags &= ~WINDOW_ALERTFLAGS;
wl->flags &= ~WINLINK_ALERTFLAGS;
}
server_redraw_session(s);
} else if (args_has(args, 'a')) {
RB_FOREACH_SAFE(sloop, sessions, &sessions, stmp) {
if (sloop != s) {
server_destroy_session(sloop);
session_destroy(sloop, 1, __func__);
}
}
} else {
server_destroy_session(s);
session_destroy(s);
session_destroy(s, 1, __func__);
}
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -24,46 +24,45 @@
* Destroy window.
*/
enum cmd_retval cmd_kill_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_kill_window_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_kill_window_entry = {
"kill-window", "killw",
"at:", 0, 0,
"[-a] " CMD_TARGET_WINDOW_USAGE,
0,
cmd_kill_window_exec
.name = "kill-window",
.alias = "killw",
.args = { "at:", 0, 0 },
.usage = "[-a] " CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = 0,
.exec = cmd_kill_window_exec
};
const struct cmd_entry cmd_unlink_window_entry = {
"unlink-window", "unlinkw",
"kt:", 0, 0,
"[-k] " CMD_TARGET_WINDOW_USAGE,
0,
cmd_kill_window_exec
.name = "unlink-window",
.alias = "unlinkw",
.args = { "kt:", 0, 0 },
.usage = "[-k] " CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = 0,
.exec = cmd_kill_window_exec
};
enum cmd_retval
cmd_kill_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_kill_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl, *wl2, *wl3;
struct window *w;
struct session *s;
struct session_group *sg;
u_int references;
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), &s)) == NULL)
return (CMD_RETURN_ERROR);
w = wl->window;
struct winlink *wl = item->target.wl, *wl2, *wl3;
struct window *w = wl->window;
struct session *s = item->target.s;
if (self->entry == &cmd_unlink_window_entry) {
sg = session_group_find(s);
if (sg != NULL)
references = session_group_count(sg);
else
references = 1;
if (!args_has(self->args, 'k') && w->references == references) {
cmdq_error(cmdq, "window only linked to one session");
if (!args_has(self->args, 'k') && !session_is_linked(s, w)) {
cmdq_error(item, "window only linked to one session");
return (CMD_RETURN_ERROR);
}
server_unlink_window(s, wl);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -30,18 +30,21 @@
#define LIST_BUFFERS_TEMPLATE \
"#{buffer_name}: #{buffer_size} bytes: \"#{buffer_sample}\""
enum cmd_retval cmd_list_buffers_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_list_buffers_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_list_buffers_entry = {
"list-buffers", "lsb",
"F:", 0, 0,
"[-F format]",
0,
cmd_list_buffers_exec
.name = "list-buffers",
.alias = "lsb",
.args = { "F:", 0, 0 },
.usage = "[-F format]",
.flags = CMD_AFTERHOOK,
.exec = cmd_list_buffers_exec
};
enum cmd_retval
cmd_list_buffers_exec(unused struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_list_buffers_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct paste_buffer *pb;
@@ -54,11 +57,11 @@ cmd_list_buffers_exec(unused struct cmd *self, struct cmd_q *cmdq)
pb = NULL;
while ((pb = paste_walk(pb)) != NULL) {
ft = format_create();
format_defaults_paste_buffer(ft, pb, 0);
ft = format_create(item->client, item, FORMAT_NONE, 0);
format_defaults_paste_buffer(ft, pb);
line = format_expand(ft, template);
cmdq_print(cmdq, "%s", line);
cmdq_print(item, "%s", line);
free(line);
format_free(ft);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -29,58 +29,60 @@
*/
#define LIST_CLIENTS_TEMPLATE \
"#{client_tty}: #{session_name} " \
"#{client_name}: #{session_name} " \
"[#{client_width}x#{client_height} #{client_termname}]" \
"#{?client_utf8, (utf8),} #{?client_readonly, (ro),}"
enum cmd_retval cmd_list_clients_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_list_clients_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_list_clients_entry = {
"list-clients", "lsc",
"F:t:", 0, 0,
"[-F format] " CMD_TARGET_SESSION_USAGE,
CMD_READONLY,
cmd_list_clients_exec
.name = "list-clients",
.alias = "lsc",
.args = { "F:t:", 0, 0 },
.usage = "[-F format] " CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = CMD_READONLY|CMD_AFTERHOOK,
.exec = cmd_list_clients_exec
};
enum cmd_retval
cmd_list_clients_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_list_clients_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct session *s;
struct format_tree *ft;
const char *template;
u_int i;
u_int idx;
char *line;
if (args_has(args, 't')) {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
return (CMD_RETURN_ERROR);
} else
if (args_has(args, 't'))
s = item->target.s;
else
s = NULL;
if ((template = args_get(args, 'F')) == NULL)
template = LIST_CLIENTS_TEMPLATE;
for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
c = ARRAY_ITEM(&clients, i);
if (c == NULL || c->session == NULL)
idx = 0;
TAILQ_FOREACH(c, &clients, entry) {
if (c->session == NULL || (s != NULL && s != c->session))
continue;
if (s != NULL && s != c->session)
continue;
ft = format_create();
format_add(ft, "line", "%u", i);
ft = format_create(item->client, item, FORMAT_NONE, 0);
format_add(ft, "line", "%u", idx);
format_defaults(ft, c, NULL, NULL, NULL);
line = format_expand(ft, template);
cmdq_print(cmdq, "%s", line);
cmdq_print(item, "%s", line);
free(line);
format_free(ft);
idx++;
}
return (CMD_RETURN_NORMAL);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,6 +18,7 @@
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
@@ -26,156 +27,337 @@
* List key bindings.
*/
enum cmd_retval cmd_list_keys_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_list_keys_exec(struct cmd *, struct cmdq_item *);
enum cmd_retval cmd_list_keys_table(struct cmd *, struct cmd_q *);
enum cmd_retval cmd_list_keys_commands(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_list_keys_commands(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_list_keys_entry = {
"list-keys", "lsk",
"t:", 0, 0,
"[-t key-table]",
0,
cmd_list_keys_exec
.name = "list-keys",
.alias = "lsk",
.args = { "1aNP:T:", 0, 1 },
.usage = "[-1aN] [-P prefix-string] [-T key-table] [key]",
.flags = CMD_STARTSERVER|CMD_AFTERHOOK,
.exec = cmd_list_keys_exec
};
const struct cmd_entry cmd_list_commands_entry = {
"list-commands", "lscm",
"", 0, 0,
"",
0,
cmd_list_keys_exec
.name = "list-commands",
.alias = "lscm",
.args = { "F:", 0, 1 },
.usage = "[-F format] [command]",
.flags = CMD_STARTSERVER|CMD_AFTERHOOK,
.exec = cmd_list_keys_exec
};
enum cmd_retval
cmd_list_keys_exec(struct cmd *self, struct cmd_q *cmdq)
static u_int
cmd_list_keys_get_width(const char *tablename, key_code only)
{
struct args *args = self->args;
struct key_table *table;
struct key_binding *bd;
const char *key;
char tmp[BUFSIZ], flags[8];
size_t used;
int width, keywidth;
u_int width, keywidth = 0;
if (self->entry == &cmd_list_commands_entry)
return (cmd_list_keys_commands(self, cmdq));
if (args_has(args, 't'))
return (cmd_list_keys_table(self, cmdq));
width = 0;
RB_FOREACH(bd, key_bindings, &key_bindings) {
key = key_string_lookup_key(bd->key & ~KEYC_PREFIX);
if (key == NULL)
table = key_bindings_get_table(tablename, 0);
if (table == NULL)
return (0);
bd = key_bindings_first(table);
while (bd != NULL) {
if ((only != KEYC_UNKNOWN && bd->key != only) ||
KEYC_IS_MOUSE(bd->key) ||
bd->note == NULL) {
bd = key_bindings_next(table, bd);
continue;
}
width = utf8_cstrwidth(key_string_lookup_key(bd->key));
if (width > keywidth)
keywidth = width;
keywidth = strlen(key);
if (!(bd->key & KEYC_PREFIX)) {
if (bd->can_repeat)
keywidth += 4;
else
keywidth += 3;
} else if (bd->can_repeat)
keywidth += 3;
if (keywidth > width)
width = keywidth;
bd = key_bindings_next(table, bd);
}
RB_FOREACH(bd, key_bindings, &key_bindings) {
key = key_string_lookup_key(bd->key & ~KEYC_PREFIX);
if (key == NULL)
continue;
*flags = '\0';
if (!(bd->key & KEYC_PREFIX)) {
if (bd->can_repeat)
xsnprintf(flags, sizeof flags, "-rn ");
else
xsnprintf(flags, sizeof flags, "-n ");
} else if (bd->can_repeat)
xsnprintf(flags, sizeof flags, "-r ");
used = xsnprintf(tmp, sizeof tmp, "%s%*s ",
flags, (int) (width - strlen(flags)), key);
if (used >= sizeof tmp)
continue;
cmd_list_print(bd->cmdlist, tmp + used, (sizeof tmp) - used);
cmdq_print(cmdq, "bind-key %s", tmp);
}
return (CMD_RETURN_NORMAL);
return (keywidth);
}
enum cmd_retval
cmd_list_keys_table(struct cmd *self, struct cmd_q *cmdq)
static int
cmd_list_keys_print_notes(struct cmdq_item *item, struct args *args,
const char *tablename, u_int keywidth, key_code only, const char *prefix)
{
struct args *args = self->args;
const char *tablename;
const struct mode_key_table *mtab;
struct mode_key_binding *mbind;
const char *key, *cmdstr, *mode;
int width, keywidth, any_mode;
struct client *c = cmd_find_client(item, NULL, 1);
struct key_table *table;
struct key_binding *bd;
const char *key;
char *tmp, *note;
int found = 0;
tablename = args_get(args, 't');
if ((mtab = mode_key_findtable(tablename)) == NULL) {
cmdq_error(cmdq, "unknown key table: %s", tablename);
table = key_bindings_get_table(tablename, 0);
if (table == NULL)
return (0);
bd = key_bindings_first(table);
while (bd != NULL) {
if ((only != KEYC_UNKNOWN && bd->key != only) ||
KEYC_IS_MOUSE(bd->key) ||
(bd->note == NULL && !args_has(args, 'a'))) {
bd = key_bindings_next(table, bd);
continue;
}
found = 1;
key = key_string_lookup_key(bd->key);
if (bd->note == NULL)
note = cmd_list_print(bd->cmdlist, 1);
else
note = xstrdup(bd->note);
tmp = utf8_padcstr(key, keywidth + 1);
if (args_has(args, '1') && c != NULL)
status_message_set(c, "%s%s%s", prefix, tmp, note);
else
cmdq_print(item, "%s%s%s", prefix, tmp, note);
free(tmp);
free(note);
if (args_has(args, '1'))
break;
bd = key_bindings_next(table, bd);
}
return (found);
}
static char *
cmd_list_keys_get_prefix(struct args *args, key_code *prefix)
{
char *s;
*prefix = options_get_number(global_s_options, "prefix");
if (!args_has(args, 'P')) {
if (*prefix != KEYC_NONE)
xasprintf(&s, "%s ", key_string_lookup_key(*prefix));
else
s = xstrdup("");
} else
s = xstrdup(args_get(args, 'P'));
return (s);
}
static enum cmd_retval
cmd_list_keys_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct key_table *table;
struct key_binding *bd;
const char *tablename, *r;
char *key, *cp, *tmp, *start, *empty;
key_code prefix, only = KEYC_UNKNOWN;
int repeat, width, tablewidth, keywidth, found = 0;
size_t tmpsize, tmpused, cplen;
if (self->entry == &cmd_list_commands_entry)
return (cmd_list_keys_commands(self, item));
if (args->argc != 0) {
only = key_string_lookup_string(args->argv[0]);
if (only == KEYC_UNKNOWN) {
cmdq_error(item, "invalid key: %s", args->argv[0]);
return (CMD_RETURN_ERROR);
}
}
tablename = args_get(args, 'T');
if (tablename != NULL && key_bindings_get_table(tablename, 0) == NULL) {
cmdq_error(item, "table %s doesn't exist", tablename);
return (CMD_RETURN_ERROR);
}
width = 0;
any_mode = 0;
RB_FOREACH(mbind, mode_key_tree, mtab->tree) {
key = key_string_lookup_key(mbind->key);
if (key == NULL)
continue;
if (args_has(args, 'N')) {
if (tablename == NULL) {
start = cmd_list_keys_get_prefix(args, &prefix);
keywidth = cmd_list_keys_get_width("root", only);
if (prefix != KEYC_NONE) {
width = cmd_list_keys_get_width("prefix", only);
if (width == 0)
prefix = KEYC_NONE;
else if (width > keywidth)
keywidth = width;
}
empty = utf8_padcstr("", utf8_cstrwidth(start));
if (mbind->mode != 0)
any_mode = 1;
found = cmd_list_keys_print_notes(item, args, "root",
keywidth, only, empty);
if (prefix != KEYC_NONE) {
if (cmd_list_keys_print_notes(item, args,
"prefix", keywidth, only, start))
found = 1;
}
free(empty);
} else {
if (args_has(args, 'P'))
start = xstrdup(args_get(args, 'P'));
else
start = xstrdup("");
keywidth = cmd_list_keys_get_width(tablename, only);
found = cmd_list_keys_print_notes(item, args, tablename,
keywidth, only, start);
keywidth = strlen(key);
if (keywidth > width)
width = keywidth;
}
RB_FOREACH(mbind, mode_key_tree, mtab->tree) {
key = key_string_lookup_key(mbind->key);
if (key == NULL)
continue;
mode = "";
if (mbind->mode != 0)
mode = "c";
cmdstr = mode_key_tostring(mtab->cmdstr, mbind->cmd);
if (cmdstr != NULL) {
cmdq_print(cmdq, "bind-key -%st %s%s %*s %s%s%s%s",
mode, any_mode && *mode == '\0' ? " " : "",
mtab->name, (int) width, key, cmdstr,
mbind->arg != NULL ? " \"" : "",
mbind->arg != NULL ? mbind->arg : "",
mbind->arg != NULL ? "\"": "");
}
free(start);
goto out;
}
repeat = 0;
tablewidth = keywidth = 0;
table = key_bindings_first_table ();
while (table != NULL) {
if (tablename != NULL && strcmp(table->name, tablename) != 0) {
table = key_bindings_next_table(table);
continue;
}
bd = key_bindings_first(table);
while (bd != NULL) {
if (only != KEYC_UNKNOWN && bd->key != only) {
bd = key_bindings_next(table, bd);
continue;
}
key = args_escape(key_string_lookup_key(bd->key));
if (bd->flags & KEY_BINDING_REPEAT)
repeat = 1;
width = utf8_cstrwidth(table->name);
if (width > tablewidth)
tablewidth = width;
width = utf8_cstrwidth(key);
if (width > keywidth)
keywidth = width;
free(key);
bd = key_bindings_next(table, bd);
}
table = key_bindings_next_table(table);
}
tmpsize = 256;
tmp = xmalloc(tmpsize);
table = key_bindings_first_table ();
while (table != NULL) {
if (tablename != NULL && strcmp(table->name, tablename) != 0) {
table = key_bindings_next_table(table);
continue;
}
bd = key_bindings_first(table);
while (bd != NULL) {
if (only != KEYC_UNKNOWN && bd->key != only) {
bd = key_bindings_next(table, bd);
continue;
}
found = 1;
key = args_escape(key_string_lookup_key(bd->key));
if (!repeat)
r = "";
else if (bd->flags & KEY_BINDING_REPEAT)
r = "-r ";
else
r = " ";
tmpused = xsnprintf(tmp, tmpsize, "%s-T ", r);
cp = utf8_padcstr(table->name, tablewidth);
cplen = strlen(cp) + 1;
while (tmpused + cplen + 1 >= tmpsize) {
tmpsize *= 2;
tmp = xrealloc(tmp, tmpsize);
}
tmpused = strlcat(tmp, cp, tmpsize);
tmpused = strlcat(tmp, " ", tmpsize);
free(cp);
cp = utf8_padcstr(key, keywidth);
cplen = strlen(cp) + 1;
while (tmpused + cplen + 1 >= tmpsize) {
tmpsize *= 2;
tmp = xrealloc(tmp, tmpsize);
}
tmpused = strlcat(tmp, cp, tmpsize);
tmpused = strlcat(tmp, " ", tmpsize);
free(cp);
cp = cmd_list_print(bd->cmdlist, 1);
cplen = strlen(cp);
while (tmpused + cplen + 1 >= tmpsize) {
tmpsize *= 2;
tmp = xrealloc(tmp, tmpsize);
}
strlcat(tmp, cp, tmpsize);
free(cp);
cmdq_print(item, "bind-key %s", tmp);
free(key);
bd = key_bindings_next(table, bd);
}
table = key_bindings_next_table(table);
}
free(tmp);
out:
if (only != KEYC_UNKNOWN && !found) {
cmdq_error(item, "unknown key: %s", args->argv[0]);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
}
enum cmd_retval
cmd_list_keys_commands(unused struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_list_keys_commands(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
const struct cmd_entry **entryp;
const struct cmd_entry *entry;
struct format_tree *ft;
const char *template, *s, *command = NULL;
char *line;
if (args->argc != 0)
command = args->argv[0];
if ((template = args_get(args, 'F')) == NULL) {
template = "#{command_list_name}"
"#{?command_list_alias, (#{command_list_alias}),} "
"#{command_list_usage}";
}
ft = format_create(item->client, item, FORMAT_NONE, 0);
format_defaults(ft, NULL, NULL, NULL, NULL);
for (entryp = cmd_table; *entryp != NULL; entryp++) {
entry = *entryp;
if (entry->alias == NULL) {
cmdq_print(cmdq, "%s %s", entry->name, entry->usage);
continue;
}
cmdq_print(cmdq, "%s (%s) %s", entry->name, entry->alias,
entry->usage);
if (command != NULL &&
(strcmp(entry->name, command) != 0 &&
(entry->alias == NULL ||
strcmp(entry->alias, command) != 0)))
continue;
format_add(ft, "command_list_name", "%s", entry->name);
if (entry->alias != NULL)
s = entry->alias;
else
s = "";
format_add(ft, "command_list_alias", "%s", s);
if (entry->usage != NULL)
s = entry->usage;
else
s = "";
format_add(ft, "command_list_usage", "%s", s);
line = format_expand(ft, template);
if (*line != '\0')
cmdq_print(item, "%s", line);
free(line);
}
format_free(ft);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -19,7 +19,6 @@
#include <sys/types.h>
#include <stdlib.h>
#include <unistd.h>
#include "tmux.h"
@@ -27,68 +26,66 @@
* List panes on given window.
*/
enum cmd_retval cmd_list_panes_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_list_panes_exec(struct cmd *, struct cmdq_item *);
void cmd_list_panes_server(struct cmd *, struct cmd_q *);
void cmd_list_panes_session(
struct cmd *, struct session *, struct cmd_q *, int);
void cmd_list_panes_window(struct cmd *,
struct session *, struct winlink *, struct cmd_q *, int);
static void cmd_list_panes_server(struct cmd *, struct cmdq_item *);
static void cmd_list_panes_session(struct cmd *, struct session *,
struct cmdq_item *, int);
static void cmd_list_panes_window(struct cmd *, struct session *,
struct winlink *, struct cmdq_item *, int);
const struct cmd_entry cmd_list_panes_entry = {
"list-panes", "lsp",
"asF:t:", 0, 0,
"[-as] [-F format] " CMD_TARGET_WINDOW_USAGE,
0,
cmd_list_panes_exec
.name = "list-panes",
.alias = "lsp",
.args = { "asF:t:", 0, 0 },
.usage = "[-as] [-F format] " CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_list_panes_exec
};
enum cmd_retval
cmd_list_panes_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_list_panes_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
struct winlink *wl;
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
if (args_has(args, 'a'))
cmd_list_panes_server(self, cmdq);
else if (args_has(args, 's')) {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
return (CMD_RETURN_ERROR);
cmd_list_panes_session(self, s, cmdq, 1);
} else {
wl = cmd_find_window(cmdq, args_get(args, 't'), &s);
if (wl == NULL)
return (CMD_RETURN_ERROR);
cmd_list_panes_window(self, s, wl, cmdq, 0);
}
cmd_list_panes_server(self, item);
else if (args_has(args, 's'))
cmd_list_panes_session(self, s, item, 1);
else
cmd_list_panes_window(self, s, wl, item, 0);
return (CMD_RETURN_NORMAL);
}
void
cmd_list_panes_server(struct cmd *self, struct cmd_q *cmdq)
static void
cmd_list_panes_server(struct cmd *self, struct cmdq_item *item)
{
struct session *s;
RB_FOREACH(s, sessions, &sessions)
cmd_list_panes_session(self, s, cmdq, 2);
cmd_list_panes_session(self, s, item, 2);
}
void
cmd_list_panes_session(
struct cmd *self, struct session *s, struct cmd_q *cmdq, int type)
static void
cmd_list_panes_session(struct cmd *self, struct session *s,
struct cmdq_item *item, int type)
{
struct winlink *wl;
RB_FOREACH(wl, winlinks, &s->windows)
cmd_list_panes_window(self, s, wl, cmdq, type);
cmd_list_panes_window(self, s, wl, item, type);
}
void
cmd_list_panes_window(struct cmd *self,
struct session *s, struct winlink *wl, struct cmd_q *cmdq, int type)
static void
cmd_list_panes_window(struct cmd *self, struct session *s, struct winlink *wl,
struct cmdq_item *item, int type)
{
struct args *args = self->args;
struct window_pane *wp;
@@ -115,9 +112,9 @@ cmd_list_panes_window(struct cmd *self,
"#{?pane_active, (active),}#{?pane_dead, (dead),}";
break;
case 2:
template = "#{session_name}:#{window_index}.#{pane_index}: "
"[#{pane_width}x#{pane_height}] [history "
"#{history_size}/#{history_limit}, "
template = "#{session_name}:#{window_index}."
"#{pane_index}: [#{pane_width}x#{pane_height}] "
"[history #{history_size}/#{history_limit}, "
"#{history_bytes} bytes] #{pane_id}"
"#{?pane_active, (active),}#{?pane_dead, (dead),}";
break;
@@ -126,12 +123,12 @@ cmd_list_panes_window(struct cmd *self,
n = 0;
TAILQ_FOREACH(wp, &wl->window->panes, entry) {
ft = format_create();
ft = format_create(item->client, item, FORMAT_NONE, 0);
format_add(ft, "line", "%u", n);
format_defaults(ft, NULL, s, wl, wp);
line = format_expand(ft, template);
cmdq_print(cmdq, "%s", line);
cmdq_print(item, "%s", line);
free(line);
format_free(ft);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -30,24 +30,27 @@
#define LIST_SESSIONS_TEMPLATE \
"#{session_name}: #{session_windows} windows " \
"(created #{session_created_string}) " \
"[#{session_width}x#{session_height}]" \
"(created #{t:session_created})" \
"#{?session_grouped, (group ,}" \
"#{session_group}#{?session_grouped,),}" \
"#{?session_attached, (attached),}"
enum cmd_retval cmd_list_sessions_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_list_sessions_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_list_sessions_entry = {
"list-sessions", "ls",
"F:", 0, 0,
"[-F format]",
0,
cmd_list_sessions_exec
.name = "list-sessions",
.alias = "ls",
.args = { "F:", 0, 0 },
.usage = "[-F format]",
.flags = CMD_AFTERHOOK,
.exec = cmd_list_sessions_exec
};
enum cmd_retval
cmd_list_sessions_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_list_sessions_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
@@ -61,12 +64,12 @@ cmd_list_sessions_exec(struct cmd *self, struct cmd_q *cmdq)
n = 0;
RB_FOREACH(s, sessions, &sessions) {
ft = format_create();
ft = format_create(item->client, item, FORMAT_NONE, 0);
format_add(ft, "line", "%u", n);
format_defaults(ft, NULL, s, NULL, NULL);
line = format_expand(ft, template);
cmdq_print(cmdq, "%s", line);
cmdq_print(item, "%s", line);
free(line);
format_free(ft);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -39,54 +39,54 @@
"(#{window_panes} panes) " \
"[#{window_width}x#{window_height}] "
enum cmd_retval cmd_list_windows_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_list_windows_exec(struct cmd *, struct cmdq_item *);
void cmd_list_windows_server(struct cmd *, struct cmd_q *);
void cmd_list_windows_session(struct cmd *, struct session *,
struct cmd_q *, int);
static void cmd_list_windows_server(struct cmd *, struct cmdq_item *);
static void cmd_list_windows_session(struct cmd *, struct session *,
struct cmdq_item *, int);
const struct cmd_entry cmd_list_windows_entry = {
"list-windows", "lsw",
"F:at:", 0, 0,
"[-a] [-F format] " CMD_TARGET_SESSION_USAGE,
0,
cmd_list_windows_exec
.name = "list-windows",
.alias = "lsw",
.args = { "F:at:", 0, 0 },
.usage = "[-a] [-F format] " CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_list_windows_exec
};
enum cmd_retval
cmd_list_windows_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_list_windows_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
if (args_has(args, 'a'))
cmd_list_windows_server(self, cmdq);
else {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
return (CMD_RETURN_ERROR);
cmd_list_windows_session(self, s, cmdq, 0);
}
cmd_list_windows_server(self, item);
else
cmd_list_windows_session(self, item->target.s, item, 0);
return (CMD_RETURN_NORMAL);
}
void
cmd_list_windows_server(struct cmd *self, struct cmd_q *cmdq)
static void
cmd_list_windows_server(struct cmd *self, struct cmdq_item *item)
{
struct session *s;
RB_FOREACH(s, sessions, &sessions)
cmd_list_windows_session(self, s, cmdq, 1);
cmd_list_windows_session(self, s, item, 1);
}
void
cmd_list_windows_session(
struct cmd *self, struct session *s, struct cmd_q *cmdq, int type)
static void
cmd_list_windows_session(struct cmd *self, struct session *s,
struct cmdq_item *item, int type)
{
struct args *args = self->args;
struct winlink *wl;
u_int n;
u_int n;
struct format_tree *ft;
const char *template;
char *line;
@@ -105,12 +105,12 @@ cmd_list_windows_session(
n = 0;
RB_FOREACH(wl, winlinks, &s->windows) {
ft = format_create();
ft = format_create(item->client, item, FORMAT_NONE, 0);
format_add(ft, "line", "%u", n);
format_defaults(ft, NULL, s, wl, NULL);
line = format_expand(ft, template);
cmdq_print(cmdq, "%s", line);
cmdq_print(item, "%s", line);
free(line);
format_free(ft);

View File

@@ -1,123 +0,0 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 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"
struct cmd_list *
cmd_list_parse(int argc, char **argv, const char *file, u_int line,
char **cause)
{
struct cmd_list *cmdlist;
struct cmd *cmd;
int i, lastsplit;
size_t arglen, new_argc;
char **copy_argv, **new_argv;
copy_argv = cmd_copy_argv(argc, argv);
cmdlist = xcalloc(1, sizeof *cmdlist);
cmdlist->references = 1;
TAILQ_INIT(&cmdlist->list);
lastsplit = 0;
for (i = 0; i < argc; i++) {
arglen = strlen(copy_argv[i]);
if (arglen == 0 || copy_argv[i][arglen - 1] != ';')
continue;
copy_argv[i][arglen - 1] = '\0';
if (arglen > 1 && copy_argv[i][arglen - 2] == '\\') {
copy_argv[i][arglen - 2] = ';';
continue;
}
new_argc = i - lastsplit;
new_argv = copy_argv + lastsplit;
if (arglen != 1)
new_argc++;
cmd = cmd_parse(new_argc, new_argv, file, line, cause);
if (cmd == NULL)
goto bad;
TAILQ_INSERT_TAIL(&cmdlist->list, cmd, qentry);
lastsplit = i + 1;
}
if (lastsplit != argc) {
cmd = cmd_parse(argc - lastsplit, copy_argv + lastsplit,
file, line, cause);
if (cmd == NULL)
goto bad;
TAILQ_INSERT_TAIL(&cmdlist->list, cmd, qentry);
}
cmd_free_argv(argc, copy_argv);
return (cmdlist);
bad:
cmd_list_free(cmdlist);
cmd_free_argv(argc, copy_argv);
return (NULL);
}
void
cmd_list_free(struct cmd_list *cmdlist)
{
struct cmd *cmd, *cmd1;
if (--cmdlist->references != 0)
return;
TAILQ_FOREACH_SAFE(cmd, &cmdlist->list, qentry, cmd1) {
TAILQ_REMOVE(&cmdlist->list, cmd, qentry);
args_free(cmd->args);
free(cmd->file);
free(cmd);
}
free(cmdlist);
}
size_t
cmd_list_print(struct cmd_list *cmdlist, char *buf, size_t len)
{
struct cmd *cmd;
size_t off, used;
off = 0;
TAILQ_FOREACH(cmd, &cmdlist->list, qentry) {
if (off >= len)
break;
off += cmd_print(cmd, buf + off, len - off);
if (off >= len)
break;
if (TAILQ_NEXT(cmd, qentry) != NULL) {
used = xsnprintf(buf + off, len - off, " ; ");
if (used > len - off)
used = len - off;
off += used;
}
}
return (off);
}

View File

@@ -31,127 +31,77 @@
* Loads a paste buffer from a file.
*/
enum cmd_retval cmd_load_buffer_exec(struct cmd *, struct cmd_q *);
void cmd_load_buffer_callback(struct client *, int, void *);
static enum cmd_retval cmd_load_buffer_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_load_buffer_entry = {
"load-buffer", "loadb",
"b:", 1, 1,
CMD_BUFFER_USAGE " path",
0,
cmd_load_buffer_exec
.name = "load-buffer",
.alias = "loadb",
.args = { "b:", 1, 1 },
.usage = CMD_BUFFER_USAGE " path",
.flags = CMD_AFTERHOOK,
.exec = cmd_load_buffer_exec
};
enum cmd_retval
cmd_load_buffer_exec(struct cmd *self, struct cmd_q *cmdq)
struct cmd_load_buffer_data {
struct cmdq_item *item;
char *name;
};
static void
cmd_load_buffer_done(__unused struct client *c, const char *path, int error,
int closed, struct evbuffer *buffer, void *data)
{
struct args *args = self->args;
struct client *c = cmdq->client;
struct session *s;
FILE *f;
const char *path, *bufname;
char *pdata, *new_pdata, *cause;
size_t psize;
int ch, error, cwd, fd;
bufname = NULL;
if (args_has(args, 'b'))
bufname = args_get(args, 'b');
path = args->argv[0];
if (strcmp(path, "-") == 0) {
error = server_set_stdin_callback(c, cmd_load_buffer_callback,
(void *)bufname, &cause);
if (error != 0) {
cmdq_error(cmdq, "%s: %s", path, cause);
free(cause);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_WAIT);
}
if (c != NULL && c->session == NULL)
cwd = c->cwd;
else if ((s = cmd_current_session(cmdq, 0)) != NULL)
cwd = s->cwd;
else
cwd = AT_FDCWD;
if ((fd = openat(cwd, path, O_RDONLY)) == -1 ||
(f = fdopen(fd, "rb")) == NULL) {
if (fd != -1)
close(fd);
cmdq_error(cmdq, "%s: %s", path, strerror(errno));
return (CMD_RETURN_ERROR);
}
pdata = NULL;
psize = 0;
while ((ch = getc(f)) != EOF) {
/* Do not let the server die due to memory exhaustion. */
if ((new_pdata = realloc(pdata, psize + 2)) == NULL) {
cmdq_error(cmdq, "realloc error: %s", strerror(errno));
goto error;
}
pdata = new_pdata;
pdata[psize++] = ch;
}
if (ferror(f)) {
cmdq_error(cmdq, "%s: read error", path);
goto error;
}
if (pdata != NULL)
pdata[psize] = '\0';
fclose(f);
if (paste_set(pdata, psize, bufname, &cause) != 0) {
cmdq_error(cmdq, "%s", cause);
free(pdata);
free(cause);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
error:
free(pdata);
if (f != NULL)
fclose(f);
return (CMD_RETURN_ERROR);
}
void
cmd_load_buffer_callback(struct client *c, int closed, void *data)
{
const char *bufname = data;
char *pdata, *cause;
size_t psize;
struct cmd_load_buffer_data *cdata = data;
struct cmdq_item *item = cdata->item;
void *bdata = EVBUFFER_DATA(buffer);
size_t bsize = EVBUFFER_LENGTH(buffer);
void *copy;
char *cause;
if (!closed)
return;
c->stdin_callback = NULL;
c->references--;
if (c->flags & CLIENT_DEAD)
return;
psize = EVBUFFER_LENGTH(c->stdin_data);
if (psize == 0 || (pdata = malloc(psize + 1)) == NULL)
goto out;
memcpy(pdata, EVBUFFER_DATA(c->stdin_data), psize);
pdata[psize] = '\0';
evbuffer_drain(c->stdin_data, psize);
if (paste_set(pdata, psize, bufname, &cause) != 0) {
/* No context so can't use server_client_msg_error. */
evbuffer_add_printf(c->stderr_data, "%s", cause);
server_push_stderr(c);
free(pdata);
free(cause);
if (error != 0)
cmdq_error(item, "%s: %s", path, strerror(error));
else if (bsize != 0) {
copy = xmalloc(bsize);
memcpy(copy, bdata, bsize);
if (paste_set(copy, bsize, cdata->name, &cause) != 0) {
cmdq_error(item, "%s", cause);
free(cause);
free(copy);
}
}
cmdq_continue(item);
out:
cmdq_continue(c->cmdq);
free(cdata->name);
free(cdata);
}
static enum cmd_retval
cmd_load_buffer_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct cmd_load_buffer_data *cdata;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct window_pane *wp = item->target.wp;
const char *bufname = args_get(args, 'b');
char *path;
cdata = xmalloc(sizeof *cdata);
cdata->item = item;
if (bufname != NULL)
cdata->name = xstrdup(bufname);
else
cdata->name = NULL;
path = format_single(item, args->argv[0], c, s, wl, wp);
file_read(item->client, path, cmd_load_buffer_done, cdata);
free(path);
return (CMD_RETURN_WAIT);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -24,49 +24,55 @@
* Lock commands.
*/
enum cmd_retval cmd_lock_server_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_lock_server_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_lock_server_entry = {
"lock-server", "lock",
"", 0, 0,
"",
0,
cmd_lock_server_exec
.name = "lock-server",
.alias = "lock",
.args = { "", 0, 0 },
.usage = "",
.flags = CMD_AFTERHOOK,
.exec = cmd_lock_server_exec
};
const struct cmd_entry cmd_lock_session_entry = {
"lock-session", "locks",
"t:", 0, 0,
CMD_TARGET_SESSION_USAGE,
0,
cmd_lock_server_exec
.name = "lock-session",
.alias = "locks",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_lock_server_exec
};
const struct cmd_entry cmd_lock_client_entry = {
"lock-client", "lockc",
"t:", 0, 0,
CMD_TARGET_CLIENT_USAGE,
0,
cmd_lock_server_exec
.name = "lock-client",
.alias = "lockc",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_CLIENT_USAGE,
.flags = CMD_AFTERHOOK,
.exec = cmd_lock_server_exec
};
enum cmd_retval
cmd_lock_server_exec(struct cmd *self, unused struct cmd_q *cmdq)
static enum cmd_retval
cmd_lock_server_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct session *s;
if (self->entry == &cmd_lock_server_entry)
server_lock();
else if (self->entry == &cmd_lock_session_entry) {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
return (CMD_RETURN_ERROR);
server_lock_session(s);
} else {
c = cmd_find_client(cmdq, args_get(args, 't'), 0);
if (c == NULL)
else if (self->entry == &cmd_lock_session_entry)
server_lock_session(item->target.s);
else {
if ((c = cmd_find_client(item, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
server_lock_client(c);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,59 +26,92 @@
* Move a window.
*/
enum cmd_retval cmd_move_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_move_window_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_move_window_entry = {
"move-window", "movew",
"dkrs:t:", 0, 0,
"[-dkr] " CMD_SRCDST_WINDOW_USAGE,
0,
cmd_move_window_exec
.name = "move-window",
.alias = "movew",
.args = { "adkrs:t:", 0, 0 },
.usage = "[-dkr] " CMD_SRCDST_WINDOW_USAGE,
.source = { 's', CMD_FIND_WINDOW, 0 },
/* -t is special */
.flags = 0,
.exec = cmd_move_window_exec
};
const struct cmd_entry cmd_link_window_entry = {
"link-window", "linkw",
"dks:t:", 0, 0,
"[-dk] " CMD_SRCDST_WINDOW_USAGE,
0,
cmd_move_window_exec
.name = "link-window",
.alias = "linkw",
.args = { "adks:t:", 0, 0 },
.usage = "[-dk] " CMD_SRCDST_WINDOW_USAGE,
.source = { 's', CMD_FIND_WINDOW, 0 },
/* -t is special */
.flags = 0,
.exec = cmd_move_window_exec
};
enum cmd_retval
cmd_move_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_move_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *src, *dst, *s;
const char *tflag = args_get(args, 't');
struct session *src;
struct session *dst;
struct winlink *wl;
char *cause;
int idx, kflag, dflag;
int idx, kflag, dflag, sflag;
if (args_has(args, 'r')) {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
if (cmd_find_target(&item->target, item, tflag,
CMD_FIND_SESSION, CMD_FIND_QUIET) != 0)
return (CMD_RETURN_ERROR);
session_renumber_windows(s);
session_renumber_windows(item->target.s);
recalculate_sizes();
server_status_session(item->target.s);
return (CMD_RETURN_NORMAL);
}
if ((wl = cmd_find_window(cmdq, args_get(args, 's'), &src)) == NULL)
return (CMD_RETURN_ERROR);
if ((idx = cmd_find_index(cmdq, args_get(args, 't'), &dst)) == -2)
if (cmd_find_target(&item->target, item, tflag, CMD_FIND_WINDOW,
CMD_FIND_WINDOW_INDEX) != 0)
return (CMD_RETURN_ERROR);
src = item->source.s;
dst = item->target.s;
wl = item->source.wl;
idx = item->target.idx;
kflag = args_has(self->args, 'k');
dflag = args_has(self->args, 'd');
sflag = args_has(self->args, 's');
if (args_has(self->args, 'a')) {
if ((idx = winlink_shuffle_up(dst, dst->curw)) == -1)
return (CMD_RETURN_ERROR);
}
if (server_link_window(src, wl, dst, idx, kflag, !dflag,
&cause) != 0) {
cmdq_error(cmdq, "can't link window: %s", cause);
cmdq_error(item, "can't link window: %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
if (self->entry == &cmd_move_window_entry)
server_unlink_window(src, wl);
/*
* Renumber the winlinks in the src session only, the destination
* session already has the correct winlink id to us, either
* automatically or specified by -s.
*/
if (!sflag && options_get_number(src->options, "renumber-windows"))
session_renumber_windows(src);
recalculate_sizes();
return (CMD_RETURN_NORMAL);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -33,83 +33,123 @@
#define NEW_SESSION_TEMPLATE "#{session_name}:"
enum cmd_retval cmd_new_session_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_new_session_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_new_session_entry = {
"new-session", "new",
"Ac:dDF:n:Ps:t:x:y:", 0, -1,
"[-AdDP] [-c start-directory] [-F format] [-n window-name] "
"[-s session-name] " CMD_TARGET_SESSION_USAGE " [-x width] "
"[-y height] [command]",
CMD_STARTSERVER|CMD_CANTNEST,
cmd_new_session_exec
.name = "new-session",
.alias = "new",
.args = { "Ac:dDEF:n:Ps:t:x:Xy:", 0, -1 },
.usage = "[-AdDEPX] [-c start-directory] [-F format] [-n window-name] "
"[-s session-name] " CMD_TARGET_SESSION_USAGE " [-x width] "
"[-y height] [command]",
.target = { 't', CMD_FIND_SESSION, CMD_FIND_CANFAIL },
.flags = CMD_STARTSERVER,
.exec = cmd_new_session_exec
};
const struct cmd_entry cmd_has_session_entry = {
"has-session", "has",
"t:", 0, 0,
CMD_TARGET_SESSION_USAGE,
0,
cmd_new_session_exec
.name = "has-session",
.alias = "has",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = 0,
.exec = cmd_new_session_exec
};
enum cmd_retval
cmd_new_session_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_new_session_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c = cmdq->client, *c0;
struct session *s, *groupwith;
struct window *w;
struct environ env;
struct client *c = item->client;
struct session *s, *as, *groupwith;
struct environ *env;
struct options *oo;
struct termios tio, *tiop;
const char *newname, *target, *update, *errstr, *template;
const char *path;
char **argv, *cmd, *cause, *cp;
int detached, already_attached, idx, cwd, fd = -1;
int argc;
u_int sx, sy;
struct format_tree *ft;
struct environ_entry *envent;
struct session_group *sg;
const char *errstr, *template, *group, *prefix, *tmp;
char *cause, *cwd = NULL, *cp, *newname = NULL;
int detached, already_attached, is_control = 0;
u_int sx, sy, dsx, dsy;
struct spawn_context sc;
enum cmd_retval retval;
struct cmd_find_state fs;
if (self->entry == &cmd_has_session_entry) {
if (cmd_find_session(cmdq, args_get(args, 't'), 0) == NULL)
return (CMD_RETURN_ERROR);
/*
* cmd_find_target() will fail if the session cannot be found,
* so always return success here.
*/
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 't') && (args->argc != 0 || args_has(args, 'n'))) {
cmdq_error(cmdq, "command or window name given with target");
cmdq_error(item, "command or window name given with target");
return (CMD_RETURN_ERROR);
}
newname = args_get(args, 's');
if (newname != NULL) {
tmp = args_get(args, 's');
if (tmp != NULL) {
newname = format_single(item, tmp, c, NULL, NULL, NULL);
if (!session_check_name(newname)) {
cmdq_error(cmdq, "bad session name: %s", newname);
return (CMD_RETURN_ERROR);
}
if (session_find(newname) != NULL) {
if (args_has(args, 'A')) {
return (cmd_attach_session(cmdq, newname,
args_has(args, 'D'), 0, NULL));
}
cmdq_error(cmdq, "duplicate session: %s", newname);
return (CMD_RETURN_ERROR);
cmdq_error(item, "bad session name: %s", newname);
goto fail;
}
}
if (args_has(args, 'A')) {
if (newname != NULL)
as = session_find(newname);
else
as = item->target.s;
if (as != NULL) {
retval = cmd_attach_session(item, as->name,
args_has(args, 'D'), args_has(args, 'X'), 0, NULL,
args_has(args, 'E'));
free(newname);
return (retval);
}
}
if (newname != NULL && session_find(newname) != NULL) {
cmdq_error(item, "duplicate session: %s", newname);
goto fail;
}
target = args_get(args, 't');
if (target != NULL) {
groupwith = cmd_find_session(cmdq, target, 0);
if (groupwith == NULL)
return (CMD_RETURN_ERROR);
} else
/* Is this going to be part of a session group? */
group = args_get(args, 't');
if (group != NULL) {
groupwith = item->target.s;
if (groupwith == NULL) {
if (!session_check_name(group)) {
cmdq_error(item, "bad group name: %s", group);
goto fail;
}
sg = session_group_find(group);
} else
sg = session_group_contains(groupwith);
if (sg != NULL)
prefix = sg->name;
else if (groupwith != NULL)
prefix = groupwith->name;
else
prefix = group;
} else {
groupwith = NULL;
sg = NULL;
prefix = NULL;
}
/* Set -d if no client. */
detached = args_has(args, 'd');
if (c == NULL)
detached = 1;
else if (c->flags & CLIENT_CONTROL)
is_control = 1;
/* Is this client already attached? */
already_attached = 0;
@@ -117,43 +157,26 @@ cmd_new_session_exec(struct cmd *self, struct cmd_q *cmdq)
already_attached = 1;
/* Get the new session working directory. */
if (args_has(args, 'c')) {
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), NULL, NULL,
NULL);
cp = format_expand(ft, args_get(args, 'c'));
format_free(ft);
if (cp != NULL && *cp != '\0') {
fd = open(cp, O_RDONLY|O_DIRECTORY);
free(cp);
if (fd == -1) {
cmdq_error(cmdq, "bad working directory: %s",
strerror(errno));
return (CMD_RETURN_ERROR);
}
} else if (cp != NULL)
free(cp);
cwd = fd;
} else if (c != NULL && c->session == NULL)
cwd = c->cwd;
else if ((c0 = cmd_current_client(cmdq)) != NULL)
cwd = c0->session->cwd;
else {
fd = open(".", O_RDONLY);
cwd = fd;
}
if ((tmp = args_get(args, 'c')) != NULL)
cwd = format_single(item, tmp, c, NULL, NULL, NULL);
else
cwd = xstrdup(server_client_get_cwd(c, NULL));
/*
* Save the termios settings, part of which is used for new windows in
* this session.
* If this is a new client, check for nesting and save the termios
* settings (part of which is used for new windows in this session).
*
* This is read again with tcgetattr() rather than using tty.tio as if
* detached, tty_open won't be called. Because of this, it must be done
* before opening the terminal as that calls tcsetattr() to prepare for
* tmux taking over.
* tcgetattr() is used rather than using tty.tio since if the client is
* detached, tty_open won't be called. It must be done before opening
* the terminal as that calls tcsetattr() to prepare for tmux taking
* over.
*/
if (!detached && !already_attached && c->tty.fd != -1) {
if (server_client_check_nested(item->client)) {
cmdq_error(item, "sessions should be nested with care, "
"unset $TMUX to force");
goto fail;
}
if (tcgetattr(c->tty.fd, &tio) != 0)
fatal("tcgetattr failed");
tiop = &tio;
@@ -163,112 +186,138 @@ cmd_new_session_exec(struct cmd *self, struct cmd_q *cmdq)
/* Open the terminal if necessary. */
if (!detached && !already_attached) {
if (server_client_open(c, &cause) != 0) {
cmdq_error(cmdq, "open terminal failed: %s", cause);
cmdq_error(item, "open terminal failed: %s", cause);
free(cause);
goto error;
goto fail;
}
}
/* Get default session size. */
if (args_has(args, 'x')) {
tmp = args_get(args, 'x');
if (strcmp(tmp, "-") == 0) {
if (c != NULL)
dsx = c->tty.sx;
else
dsx = 80;
} else {
dsx = strtonum(tmp, 1, USHRT_MAX, &errstr);
if (errstr != NULL) {
cmdq_error(item, "width %s", errstr);
goto fail;
}
}
}
if (args_has(args, 'y')) {
tmp = args_get(args, 'y');
if (strcmp(tmp, "-") == 0) {
if (c != NULL)
dsy = c->tty.sy;
else
dsy = 24;
} else {
dsy = strtonum(tmp, 1, USHRT_MAX, &errstr);
if (errstr != NULL) {
cmdq_error(item, "height %s", errstr);
goto fail;
}
}
}
/* Find new session size. */
if (c != NULL) {
if (!detached && !is_control) {
sx = c->tty.sx;
sy = c->tty.sy;
if (sy > 0 && options_get_number(global_s_options, "status"))
sy--;
} else {
sx = 80;
sy = 24;
}
if (detached && args_has(args, 'x')) {
sx = strtonum(args_get(args, 'x'), 1, USHRT_MAX, &errstr);
if (errstr != NULL) {
cmdq_error(cmdq, "width %s", errstr);
goto error;
tmp = options_get_string(global_s_options, "default-size");
if (sscanf(tmp, "%ux%u", &sx, &sy) != 2) {
sx = 80;
sy = 24;
}
if (args_has(args, 'x'))
sx = dsx;
if (args_has(args, 'y'))
sy = dsy;
}
if (detached && args_has(args, 'y')) {
sy = strtonum(args_get(args, 'y'), 1, USHRT_MAX, &errstr);
if (errstr != NULL) {
cmdq_error(cmdq, "height %s", errstr);
goto error;
}
}
if (sy > 0 && options_get_number(&global_s_options, "status"))
sy--;
if (sx == 0)
sx = 1;
if (sy == 0)
sy = 1;
/* Figure out the command for the new window. */
argc = -1;
argv = NULL;
if (target == NULL && args->argc != 0) {
argc = args->argc;
argv = args->argv;
} else if (target == NULL) {
cmd = options_get_string(&global_s_options, "default-command");
if (cmd != NULL && *cmd != '\0') {
argc = 1;
argv = &cmd;
} else {
argc = 0;
argv = NULL;
}
}
path = NULL;
if (c != NULL && c->session == NULL)
envent = environ_find(&c->environ, "PATH");
else
envent = environ_find(&global_environ, "PATH");
if (envent != NULL)
path = envent->value;
/* Construct the environment. */
environ_init(&env);
update = options_get_string(&global_s_options, "update-environment");
if (c != NULL)
environ_update(update, &c->environ, &env);
/* Create the new session. */
idx = -1 - options_get_number(&global_s_options, "base-index");
s = session_create(newname, argc, argv, path, cwd, &env, tiop, idx, sx,
sy, &cause);
if (s == NULL) {
cmdq_error(cmdq, "create session failed: %s", cause);
free(cause);
goto error;
oo = options_create(global_s_options);
if (args_has(args, 'x') || args_has(args, 'y')) {
if (!args_has(args, 'x'))
dsx = sx;
if (!args_has(args, 'y'))
dsy = sy;
options_set_string(oo, "default-size", 0, "%ux%u", dsx, dsy);
}
environ_free(&env);
env = environ_create();
if (c != NULL && !args_has(args, 'E'))
environ_update(global_s_options, c->environ, env);
s = session_create(prefix, newname, cwd, env, oo, tiop);
/* Set the initial window name if one given. */
if (argc >= 0 && args_has(args, 'n')) {
w = s->curw->window;
window_set_name(w, args_get(args, 'n'));
options_set_number(&w->options, "automatic-rename", 0);
/* Spawn the initial window. */
memset(&sc, 0, sizeof sc);
sc.item = item;
sc.s = s;
sc.c = c;
sc.name = args_get(args, 'n');
sc.argc = args->argc;
sc.argv = args->argv;
sc.idx = -1;
sc.cwd = args_get(args, 'c');
sc.flags = 0;
if (spawn_window(&sc, &cause) == NULL) {
session_destroy(s, 0, __func__);
cmdq_error(item, "create window failed: %s", cause);
free(cause);
goto fail;
}
/*
* If a target session is given, this is to be part of a session group,
* so add it to the group and synchronize.
*/
if (groupwith != NULL) {
session_group_add(groupwith, s);
if (group != NULL) {
if (sg == NULL) {
if (groupwith != NULL) {
sg = session_group_new(groupwith->name);
session_group_add(sg, groupwith);
} else
sg = session_group_new(group);
}
session_group_add(sg, s);
session_group_synchronize_to(s);
session_select(s, RB_ROOT(&s->windows)->idx);
session_select(s, RB_MIN(winlinks, &s->windows)->idx);
}
notify_session("session-created", s);
/*
* Set the client to the new session. If a command client exists, it is
* taking this session and needs to get MSG_READY and stay around.
*/
if (!detached) {
if (!already_attached)
server_write_ready(c);
else if (c->session != NULL)
if (!already_attached) {
if (~c->flags & CLIENT_CONTROL)
proc_send(c->peer, MSG_READY, -1, NULL, 0);
} else if (c->session != NULL)
c->last_session = c->session;
c->session = s;
notify_attached_session_changed(c);
session_update_activity(s);
if (~item->shared->flags & CMDQ_SHARED_REPEAT)
server_client_set_key_table(c, NULL);
tty_update_client_offset(c);
status_timer_start(c);
notify_client("client-session-changed", c);
session_update_activity(s, NULL);
gettimeofday(&s->last_attached_time, NULL);
server_redraw_client(c);
}
recalculate_sizes();
@@ -285,27 +334,25 @@ cmd_new_session_exec(struct cmd *self, struct cmd_q *cmdq)
if (args_has(args, 'P')) {
if ((template = args_get(args, 'F')) == NULL)
template = NEW_SESSION_TEMPLATE;
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s, NULL,
NULL);
cp = format_expand(ft, template);
cmdq_print(cmdq, "%s", cp);
cp = format_single(item, template, c, s, s->curw, NULL);
cmdq_print(item, "%s", cp);
free(cp);
format_free(ft);
}
if (!detached)
cmdq->client_exit = 0;
if (!detached) {
c->flags |= CLIENT_ATTACHED;
cmd_find_from_session(&item->shared->current, s, 0);
}
if (fd != -1)
close(fd);
cmd_find_from_session(&fs, s, 0);
cmdq_insert_hook(s, item, &fs, "after-new-session");
free(cwd);
free(newname);
return (CMD_RETURN_NORMAL);
error:
if (fd != -1)
close(fd);
fail:
free(cwd);
free(newname);
return (CMD_RETURN_ERROR);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -32,134 +32,75 @@
#define NEW_WINDOW_TEMPLATE "#{session_name}:#{window_index}.#{pane_index}"
enum cmd_retval cmd_new_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_new_window_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_new_window_entry = {
"new-window", "neww",
"ac:dF:kn:Pt:", 0, -1,
"[-adkP] [-c start-directory] [-F format] [-n window-name] "
CMD_TARGET_WINDOW_USAGE " [command]",
0,
cmd_new_window_exec
.name = "new-window",
.alias = "neww",
.args = { "ac:de:F:kn:Pt:", 0, -1 },
.usage = "[-adkP] [-c start-directory] [-e environment] [-F format] "
"[-n window-name] " CMD_TARGET_WINDOW_USAGE " [command]",
.target = { 't', CMD_FIND_WINDOW, CMD_FIND_WINDOW_INDEX },
.flags = 0,
.exec = cmd_new_window_exec
};
enum cmd_retval
cmd_new_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_new_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
struct winlink *wl;
const char *cmd, *path, *template;
char **argv, *cause, *cp;
int argc, idx, last, detached, cwd, fd = -1;
struct format_tree *ft;
struct environ_entry *envent;
struct cmd_find_state *current = &item->shared->current;
struct spawn_context sc;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
int idx = item->target.idx;
struct winlink *new_wl;
char *cause = NULL, *cp;
const char *template, *add;
struct cmd_find_state fs;
struct args_value *value;
if (args_has(args, 'a')) {
wl = cmd_find_window(cmdq, args_get(args, 't'), &s);
if (wl == NULL)
return (CMD_RETURN_ERROR);
idx = wl->idx + 1;
/* Find the next free index. */
for (last = idx; last < INT_MAX; last++) {
if (winlink_find_by_index(&s->windows, last) == NULL)
break;
}
if (last == INT_MAX) {
cmdq_error(cmdq, "no free window indexes");
return (CMD_RETURN_ERROR);
}
/* Move everything from last - 1 to idx up a bit. */
for (; last > idx; last--) {
wl = winlink_find_by_index(&s->windows, last - 1);
server_link_window(s, wl, s, last, 0, 0, NULL);
server_unlink_window(s, wl);
}
} else {
idx = cmd_find_index(cmdq, args_get(args, 't'), &s);
if (idx == -2)
return (CMD_RETURN_ERROR);
}
detached = args_has(args, 'd');
if (args->argc == 0) {
cmd = options_get_string(&s->options, "default-command");
if (cmd != NULL && *cmd != '\0') {
argc = 1;
argv = (char **)&cmd;
} else {
argc = 0;
argv = NULL;
}
} else {
argc = args->argc;
argv = args->argv;
if (args_has(args, 'a') && (idx = winlink_shuffle_up(s, wl)) == -1) {
cmdq_error(item, "couldn't get a window index");
return (CMD_RETURN_ERROR);
}
path = NULL;
if (cmdq->client != NULL && cmdq->client->session == NULL)
envent = environ_find(&cmdq->client->environ, "PATH");
else
envent = environ_find(&s->environ, "PATH");
if (envent != NULL)
path = envent->value;
memset(&sc, 0, sizeof sc);
sc.item = item;
sc.s = s;
sc.c = c;
if (args_has(args, 'c')) {
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s, NULL,
NULL);
cp = format_expand(ft, args_get(args, 'c'));
format_free(ft);
sc.name = args_get(args, 'n');
sc.argc = args->argc;
sc.argv = args->argv;
sc.environ = environ_create();
if (cp != NULL && *cp != '\0') {
fd = open(cp, O_RDONLY|O_DIRECTORY);
free(cp);
if (fd == -1) {
cmdq_error(cmdq, "bad working directory: %s",
strerror(errno));
return (CMD_RETURN_ERROR);
}
} else if (cp != NULL)
free(cp);
cwd = fd;
} else if (cmdq->client != NULL && cmdq->client->session == NULL)
cwd = cmdq->client->cwd;
else
cwd = s->cwd;
wl = NULL;
if (idx != -1)
wl = winlink_find_by_index(&s->windows, idx);
if (wl != NULL && args_has(args, 'k')) {
/*
* Can't use session_detach as it will destroy session if this
* makes it empty.
*/
notify_window_unlinked(s, wl->window);
wl->flags &= ~WINLINK_ALERTFLAGS;
winlink_stack_remove(&s->lastw, wl);
winlink_remove(&s->windows, wl);
/* Force select/redraw if current. */
if (wl == s->curw) {
detached = 0;
s->curw = NULL;
}
add = args_first_value(args, 'e', &value);
while (add != NULL) {
environ_put(sc.environ, add);
add = args_next_value(&value);
}
if (idx == -1)
idx = -1 - options_get_number(&s->options, "base-index");
wl = session_new(s, args_get(args, 'n'), argc, argv, path, cwd, idx,
&cause);
if (wl == NULL) {
cmdq_error(cmdq, "create window failed: %s", cause);
sc.idx = idx;
sc.cwd = args_get(args, 'c');
sc.flags = 0;
if (args_has(args, 'd'))
sc.flags |= SPAWN_DETACHED;
if (args_has(args, 'k'))
sc.flags |= SPAWN_KILL;
if ((new_wl = spawn_window(&sc, &cause)) == NULL) {
cmdq_error(item, "create window failed: %s", cause);
free(cause);
goto error;
return (CMD_RETURN_ERROR);
}
if (!detached) {
session_select(s, wl->idx);
if (!args_has(args, 'd') || new_wl == s->curw) {
cmd_find_from_winlink(current, new_wl, 0);
server_redraw_session_group(s);
} else
server_status_session_group(s);
@@ -167,24 +108,15 @@ cmd_new_window_exec(struct cmd *self, struct cmd_q *cmdq)
if (args_has(args, 'P')) {
if ((template = args_get(args, 'F')) == NULL)
template = NEW_WINDOW_TEMPLATE;
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s, wl,
NULL);
cp = format_expand(ft, template);
cmdq_print(cmdq, "%s", cp);
cp = format_single(item, template, c, s, new_wl,
new_wl->window->active);
cmdq_print(item, "%s", cp);
free(cp);
format_free(ft);
}
if (fd != -1)
close(fd);
return (CMD_RETURN_NORMAL);
cmd_find_from_winlink(&fs, new_wl, 0);
cmdq_insert_hook(s, item, &fs, "after-new-window");
error:
if (fd != -1)
close(fd);
return (CMD_RETURN_ERROR);
environ_free(sc.environ);
return (CMD_RETURN_NORMAL);
}

1567
cmd-parse.y Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,46 +27,47 @@
* Paste paste buffer if present.
*/
enum cmd_retval cmd_paste_buffer_exec(struct cmd *, struct cmd_q *);
void cmd_paste_buffer_filter(struct window_pane *,
const char *, size_t, const char *, int);
static enum cmd_retval cmd_paste_buffer_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_paste_buffer_entry = {
"paste-buffer", "pasteb",
"db:prs:t:", 0, 0,
"[-dpr] [-s separator] " CMD_BUFFER_USAGE " " CMD_TARGET_PANE_USAGE,
0,
cmd_paste_buffer_exec
.name = "paste-buffer",
.alias = "pasteb",
.args = { "db:prs:t:", 0, 0 },
.usage = "[-dpr] [-s separator] " CMD_BUFFER_USAGE " "
CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_paste_buffer_exec
};
enum cmd_retval
cmd_paste_buffer_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_paste_buffer_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct window_pane *wp;
struct session *s;
struct window_pane *wp = item->target.wp;
struct paste_buffer *pb;
const char *sepstr, *bufname;
if (cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp) == NULL)
return (CMD_RETURN_ERROR);
const char *sepstr, *bufname, *bufdata, *bufend, *line;
size_t seplen, bufsize;
int bracket = args_has(args, 'p');
bufname = NULL;
if (args_has(args, 'b'))
bufname = args_get(args, 'b');
if (bufname == NULL)
pb = paste_get_top();
pb = paste_get_top(NULL);
else {
pb = paste_get_name(bufname);
if (pb == NULL) {
cmdq_error(cmdq, "no buffer %s", bufname);
cmdq_error(item, "no buffer %s", bufname);
return (CMD_RETURN_ERROR);
}
}
if (pb != NULL) {
if (pb != NULL && ~wp->flags & PANE_INPUTOFF) {
sepstr = args_get(args, 's');
if (sepstr == NULL) {
if (args_has(args, 'r'))
@@ -74,16 +75,33 @@ cmd_paste_buffer_exec(struct cmd *self, struct cmd_q *cmdq)
else
sepstr = "\r";
}
paste_send_pane(pb, wp, sepstr, args_has(args, 'p'));
seplen = strlen(sepstr);
if (bracket && (wp->screen->mode & MODE_BRACKETPASTE))
bufferevent_write(wp->event, "\033[200~", 6);
bufdata = paste_buffer_data(pb, &bufsize);
bufend = bufdata + bufsize;
for (;;) {
line = memchr(bufdata, '\n', bufend - bufdata);
if (line == NULL)
break;
bufferevent_write(wp->event, bufdata, line - bufdata);
bufferevent_write(wp->event, sepstr, seplen);
bufdata = line + 1;
}
if (bufdata != bufend)
bufferevent_write(wp->event, bufdata, bufend - bufdata);
if (bracket && (wp->screen->mode & MODE_BRACKETPASTE))
bufferevent_write(wp->event, "\033[201~", 6);
}
/* Delete the buffer if -d. */
if (args_has(args, 'd')) {
if (bufname == NULL)
paste_free_top();
else
paste_free_name(bufname);
}
if (pb != NULL && args_has(args, 'd'))
paste_free(pb);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -21,6 +21,7 @@
#include <errno.h>
#include <fcntl.h>
#include <signal.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
@@ -32,33 +33,37 @@
* Open pipe to redirect pane output. If already open, close first.
*/
enum cmd_retval cmd_pipe_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_pipe_pane_exec(struct cmd *, struct cmdq_item *);
void cmd_pipe_pane_error_callback(struct bufferevent *, short, void *);
static void cmd_pipe_pane_read_callback(struct bufferevent *, void *);
static void cmd_pipe_pane_write_callback(struct bufferevent *, void *);
static void cmd_pipe_pane_error_callback(struct bufferevent *, short, void *);
const struct cmd_entry cmd_pipe_pane_entry = {
"pipe-pane", "pipep",
"ot:", 0, 1,
"[-o] " CMD_TARGET_PANE_USAGE " [command]",
0,
cmd_pipe_pane_exec
.name = "pipe-pane",
.alias = "pipep",
.args = { "IOot:", 0, 1 },
.usage = "[-IOo] " CMD_TARGET_PANE_USAGE " [command]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_pipe_pane_exec
};
enum cmd_retval
cmd_pipe_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_pipe_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct session *s;
struct winlink *wl;
struct window_pane *wp;
struct client *c = cmd_find_client(item, NULL, 1);
struct window_pane *wp = item->target.wp;
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
char *cmd;
int old_fd, pipe_fd[2], null_fd;
int old_fd, pipe_fd[2], null_fd, in, out;
struct format_tree *ft;
if ((wl = cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp)) == NULL)
return (CMD_RETURN_ERROR);
c = cmd_find_client(cmdq, NULL, 1);
sigset_t set, oldset;
/* Destroy the old pipe. */
old_fd = wp->pipe_fd;
@@ -66,6 +71,11 @@ cmd_pipe_pane_exec(struct cmd *self, struct cmd_q *cmdq)
bufferevent_free(wp->pipe_event);
close(wp->pipe_fd);
wp->pipe_fd = -1;
if (window_pane_destroy_ready(wp)) {
server_destroy_pane(wp, 1);
return (CMD_RETURN_NORMAL);
}
}
/* If no pipe command, that is enough. */
@@ -81,72 +91,135 @@ cmd_pipe_pane_exec(struct cmd *self, struct cmd_q *cmdq)
if (args_has(self->args, 'o') && old_fd != -1)
return (CMD_RETURN_NORMAL);
/* What do we want to do? Neither -I or -O is -O. */
if (args_has(self->args, 'I')) {
in = 1;
out = args_has(self->args, 'O');
} else {
in = 0;
out = 1;
}
/* Open the new pipe. */
if (socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC, pipe_fd) != 0) {
cmdq_error(cmdq, "socketpair error: %s", strerror(errno));
cmdq_error(item, "socketpair error: %s", strerror(errno));
return (CMD_RETURN_ERROR);
}
/* Expand the command. */
ft = format_create();
ft = format_create(item->client, item, FORMAT_NONE, 0);
format_defaults(ft, c, s, wl, wp);
cmd = format_expand_time(ft, args->argv[0], time(NULL));
cmd = format_expand_time(ft, args->argv[0]);
format_free(ft);
/* Fork the child. */
sigfillset(&set);
sigprocmask(SIG_BLOCK, &set, &oldset);
switch (fork()) {
case -1:
cmdq_error(cmdq, "fork error: %s", strerror(errno));
sigprocmask(SIG_SETMASK, &oldset, NULL);
cmdq_error(item, "fork error: %s", strerror(errno));
free(cmd);
return (CMD_RETURN_ERROR);
case 0:
/* Child process. */
proc_clear_signals(server_proc, 1);
sigprocmask(SIG_SETMASK, &oldset, NULL);
close(pipe_fd[0]);
clear_signals(1);
if (dup2(pipe_fd[1], STDIN_FILENO) == -1)
_exit(1);
if (pipe_fd[1] != STDIN_FILENO)
close(pipe_fd[1]);
null_fd = open(_PATH_DEVNULL, O_WRONLY, 0);
if (dup2(null_fd, STDOUT_FILENO) == -1)
_exit(1);
if (out) {
if (dup2(pipe_fd[1], STDIN_FILENO) == -1)
_exit(1);
} else {
if (dup2(null_fd, STDIN_FILENO) == -1)
_exit(1);
}
if (in) {
if (dup2(pipe_fd[1], STDOUT_FILENO) == -1)
_exit(1);
if (pipe_fd[1] != STDOUT_FILENO)
close(pipe_fd[1]);
} else {
if (dup2(null_fd, STDOUT_FILENO) == -1)
_exit(1);
}
if (dup2(null_fd, STDERR_FILENO) == -1)
_exit(1);
if (null_fd != STDOUT_FILENO && null_fd != STDERR_FILENO)
close(null_fd);
closefrom(STDERR_FILENO + 1);
execl(_PATH_BSHELL, "sh", "-c", cmd, (char *) NULL);
_exit(1);
default:
/* Parent process. */
sigprocmask(SIG_SETMASK, &oldset, NULL);
close(pipe_fd[1]);
wp->pipe_fd = pipe_fd[0];
wp->pipe_off = EVBUFFER_LENGTH(wp->event->input);
wp->pipe_event = bufferevent_new(wp->pipe_fd,
NULL, NULL, cmd_pipe_pane_error_callback, wp);
bufferevent_enable(wp->pipe_event, EV_WRITE);
if (wp->fd != -1)
wp->pipe_off = EVBUFFER_LENGTH(wp->event->input);
else
wp->pipe_off = 0;
setblocking(wp->pipe_fd, 0);
wp->pipe_event = bufferevent_new(wp->pipe_fd,
cmd_pipe_pane_read_callback,
cmd_pipe_pane_write_callback,
cmd_pipe_pane_error_callback,
wp);
if (wp->pipe_event == NULL)
fatalx("out of memory");
if (out)
bufferevent_enable(wp->pipe_event, EV_WRITE);
if (in)
bufferevent_enable(wp->pipe_event, EV_READ);
free(cmd);
return (CMD_RETURN_NORMAL);
}
}
void
cmd_pipe_pane_error_callback(
unused struct bufferevent *bufev, unused short what, void *data)
static void
cmd_pipe_pane_read_callback(__unused struct bufferevent *bufev, void *data)
{
struct window_pane *wp = data;
struct evbuffer *evb = wp->pipe_event->input;
size_t available;
available = EVBUFFER_LENGTH(evb);
log_debug("%%%u pipe read %zu", wp->id, available);
bufferevent_write(wp->event, EVBUFFER_DATA(evb), available);
evbuffer_drain(evb, available);
if (window_pane_destroy_ready(wp))
server_destroy_pane(wp, 1);
}
static void
cmd_pipe_pane_write_callback(__unused struct bufferevent *bufev, void *data)
{
struct window_pane *wp = data;
log_debug("%%%u pipe empty", wp->id);
if (window_pane_destroy_ready(wp))
server_destroy_pane(wp, 1);
}
static void
cmd_pipe_pane_error_callback(__unused struct bufferevent *bufev,
__unused short what, void *data)
{
struct window_pane *wp = data;
log_debug("%%%u pipe error", wp->id);
bufferevent_free(wp->pipe_event);
close(wp->pipe_fd);
wp->pipe_fd = -1;
if (window_pane_destroy_ready(wp))
server_destroy_pane(wp, 1);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2013 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2013 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -20,93 +20,533 @@
#include <ctype.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include "tmux.h"
/* Create new command queue. */
struct cmd_q *
cmdq_new(struct client *c)
/* Global command queue. */
static struct cmdq_list global_queue = TAILQ_HEAD_INITIALIZER(global_queue);
/* Get command queue name. */
static const char *
cmdq_name(struct client *c)
{
struct cmd_q *cmdq;
static char s[256];
cmdq = xcalloc(1, sizeof *cmdq);
cmdq->references = 1;
cmdq->dead = 0;
cmdq->client = c;
cmdq->client_exit = -1;
TAILQ_INIT(&cmdq->queue);
cmdq->item = NULL;
cmdq->cmd = NULL;
return (cmdq);
if (c == NULL)
return ("<global>");
if (c->name != NULL)
xsnprintf(s, sizeof s, "<%s>", c->name);
else
xsnprintf(s, sizeof s, "<%p>", c);
return (s);
}
/* Free command queue */
int
cmdq_free(struct cmd_q *cmdq)
/* Get command queue from client. */
static struct cmdq_list *
cmdq_get(struct client *c)
{
if (--cmdq->references != 0)
return (cmdq->dead);
if (c == NULL)
return (&global_queue);
return (&c->queue);
}
cmdq_flush(cmdq);
free(cmdq);
return (1);
/* Append an item. */
struct cmdq_item *
cmdq_append(struct client *c, struct cmdq_item *item)
{
struct cmdq_list *queue = cmdq_get(c);
struct cmdq_item *next;
do {
next = item->next;
item->next = NULL;
if (c != NULL)
c->references++;
item->client = c;
item->queue = queue;
TAILQ_INSERT_TAIL(queue, item, entry);
log_debug("%s %s: %s", __func__, cmdq_name(c), item->name);
item = next;
} while (item != NULL);
return (TAILQ_LAST(queue, cmdq_list));
}
/* Insert an item. */
struct cmdq_item *
cmdq_insert_after(struct cmdq_item *after, struct cmdq_item *item)
{
struct client *c = after->client;
struct cmdq_list *queue = after->queue;
struct cmdq_item *next;
do {
next = item->next;
item->next = after->next;
after->next = item;
if (c != NULL)
c->references++;
item->client = c;
item->queue = queue;
TAILQ_INSERT_AFTER(queue, after, item, entry);
log_debug("%s %s: %s after %s", __func__, cmdq_name(c),
item->name, after->name);
after = item;
item = next;
} while (item != NULL);
return (after);
}
/* Insert a hook. */
void
cmdq_insert_hook(struct session *s, struct cmdq_item *item,
struct cmd_find_state *fs, const char *fmt, ...)
{
struct options *oo;
va_list ap;
char *name;
struct cmdq_item *new_item;
struct options_entry *o;
struct options_array_item *a;
struct cmd_list *cmdlist;
if (item->flags & CMDQ_NOHOOKS)
return;
if (s == NULL)
oo = global_s_options;
else
oo = s->options;
va_start(ap, fmt);
xvasprintf(&name, fmt, ap);
va_end(ap);
o = options_get(oo, name);
if (o == NULL) {
free(name);
return;
}
log_debug("running hook %s (parent %p)", name, item);
a = options_array_first(o);
while (a != NULL) {
cmdlist = options_array_item_value(a)->cmdlist;
if (cmdlist == NULL) {
a = options_array_next(a);
continue;
}
new_item = cmdq_get_command(cmdlist, fs, NULL, CMDQ_NOHOOKS);
cmdq_format(new_item, "hook", "%s", name);
if (item != NULL)
item = cmdq_insert_after(item, new_item);
else
item = cmdq_append(NULL, new_item);
a = options_array_next(a);
}
free(name);
}
/* Continue processing command queue. */
void
cmdq_continue(struct cmdq_item *item)
{
item->flags &= ~CMDQ_WAITING;
}
/* Remove an item. */
static void
cmdq_remove(struct cmdq_item *item)
{
if (item->shared != NULL && --item->shared->references == 0) {
if (item->shared->formats != NULL)
format_free(item->shared->formats);
free(item->shared);
}
if (item->client != NULL)
server_client_unref(item->client);
if (item->cmdlist != NULL)
cmd_list_free(item->cmdlist);
TAILQ_REMOVE(item->queue, item, entry);
free(item->name);
free(item);
}
/* Remove all subsequent items that match this item's group. */
static void
cmdq_remove_group(struct cmdq_item *item)
{
struct cmdq_item *this, *next;
if (item->group == 0)
return;
this = TAILQ_NEXT(item, entry);
while (this != NULL) {
next = TAILQ_NEXT(this, entry);
if (this->group == item->group)
cmdq_remove(this);
this = next;
}
}
/* Get a command for the command queue. */
struct cmdq_item *
cmdq_get_command(struct cmd_list *cmdlist, struct cmd_find_state *current,
struct mouse_event *m, int flags)
{
struct cmdq_item *item, *first = NULL, *last = NULL;
struct cmd *cmd;
struct cmdq_shared *shared = NULL;
u_int group = 0;
TAILQ_FOREACH(cmd, &cmdlist->list, qentry) {
if (cmd->group != group) {
shared = xcalloc(1, sizeof *shared);
if (current != NULL)
cmd_find_copy_state(&shared->current, current);
else
cmd_find_clear_state(&shared->current, 0);
if (m != NULL)
memcpy(&shared->mouse, m, sizeof shared->mouse);
group = cmd->group;
}
item = xcalloc(1, sizeof *item);
xasprintf(&item->name, "[%s/%p]", cmd->entry->name, item);
item->type = CMDQ_COMMAND;
item->group = cmd->group;
item->flags = flags;
item->shared = shared;
item->cmdlist = cmdlist;
item->cmd = cmd;
log_debug("%s: %s group %u", __func__, item->name, item->group);
shared->references++;
cmdlist->references++;
if (first == NULL)
first = item;
if (last != NULL)
last->next = item;
last = item;
}
return (first);
}
/* Fill in flag for a command. */
static enum cmd_retval
cmdq_find_flag(struct cmdq_item *item, struct cmd_find_state *fs,
const struct cmd_entry_flag *flag)
{
const char *value;
if (flag->flag == 0) {
cmd_find_clear_state(fs, 0);
return (CMD_RETURN_NORMAL);
}
value = args_get(item->cmd->args, flag->flag);
if (cmd_find_target(fs, item, value, flag->type, flag->flags) != 0) {
cmd_find_clear_state(fs, 0);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
}
/* Fire command on command queue. */
static enum cmd_retval
cmdq_fire_command(struct cmdq_item *item)
{
struct client *c = item->client;
const char *name = cmdq_name(c);
struct cmdq_shared *shared = item->shared;
struct cmd *cmd = item->cmd;
const struct cmd_entry *entry = cmd->entry;
enum cmd_retval retval;
struct cmd_find_state *fsp, fs;
int flags;
char *tmp;
if (log_get_level() > 1) {
tmp = cmd_print(cmd);
log_debug("%s %s: (%u) %s", __func__, name, item->group, tmp);
free(tmp);
}
flags = !!(shared->flags & CMDQ_SHARED_CONTROL);
cmdq_guard(item, "begin", flags);
if (item->client == NULL)
item->client = cmd_find_client(item, NULL, 1);
retval = cmdq_find_flag(item, &item->source, &entry->source);
if (retval == CMD_RETURN_ERROR)
goto out;
retval = cmdq_find_flag(item, &item->target, &entry->target);
if (retval == CMD_RETURN_ERROR)
goto out;
retval = entry->exec(cmd, item);
if (retval == CMD_RETURN_ERROR)
goto out;
if (entry->flags & CMD_AFTERHOOK) {
if (cmd_find_valid_state(&item->target))
fsp = &item->target;
else if (cmd_find_valid_state(&item->shared->current))
fsp = &item->shared->current;
else if (cmd_find_from_client(&fs, item->client, 0) == 0)
fsp = &fs;
else
goto out;
cmdq_insert_hook(fsp->s, item, fsp, "after-%s", entry->name);
}
out:
item->client = c;
if (retval == CMD_RETURN_ERROR)
cmdq_guard(item, "error", flags);
else
cmdq_guard(item, "end", flags);
return (retval);
}
/* Get a callback for the command queue. */
struct cmdq_item *
cmdq_get_callback1(const char *name, cmdq_cb cb, void *data)
{
struct cmdq_item *item;
item = xcalloc(1, sizeof *item);
xasprintf(&item->name, "[%s/%p]", name, item);
item->type = CMDQ_CALLBACK;
item->group = 0;
item->flags = 0;
item->cb = cb;
item->data = data;
return (item);
}
/* Generic error callback. */
static enum cmd_retval
cmdq_error_callback(struct cmdq_item *item, void *data)
{
char *error = data;
cmdq_error(item, "%s", error);
free(error);
return (CMD_RETURN_NORMAL);
}
/* Get an error callback for the command queue. */
struct cmdq_item *
cmdq_get_error(const char *error)
{
return (cmdq_get_callback(cmdq_error_callback, xstrdup(error)));
}
/* Fire callback on callback queue. */
static enum cmd_retval
cmdq_fire_callback(struct cmdq_item *item)
{
return (item->cb(item, item->data));
}
/* Add a format to command queue. */
void
cmdq_format(struct cmdq_item *item, const char *key, const char *fmt, ...)
{
struct cmdq_shared *shared = item->shared;
va_list ap;
char *value;
va_start(ap, fmt);
xvasprintf(&value, fmt, ap);
va_end(ap);
if (shared->formats == NULL)
shared->formats = format_create(NULL, NULL, FORMAT_NONE, 0);
format_add(shared->formats, key, "%s", value);
free(value);
}
/* Process next item on command queue. */
u_int
cmdq_next(struct client *c)
{
struct cmdq_list *queue = cmdq_get(c);
const char *name = cmdq_name(c);
struct cmdq_item *item;
enum cmd_retval retval;
u_int items = 0;
static u_int number;
if (TAILQ_EMPTY(queue)) {
log_debug("%s %s: empty", __func__, name);
return (0);
}
if (TAILQ_FIRST(queue)->flags & CMDQ_WAITING) {
log_debug("%s %s: waiting", __func__, name);
return (0);
}
log_debug("%s %s: enter", __func__, name);
for (;;) {
item = TAILQ_FIRST(queue);
if (item == NULL)
break;
log_debug("%s %s: %s (%d), flags %x", __func__, name,
item->name, item->type, item->flags);
/*
* Any item with the waiting flag set waits until an external
* event clears the flag (for example, a job - look at
* run-shell).
*/
if (item->flags & CMDQ_WAITING)
goto waiting;
/*
* Items are only fired once, once the fired flag is set, a
* waiting flag can only be cleared by an external event.
*/
if (~item->flags & CMDQ_FIRED) {
item->time = time(NULL);
item->number = ++number;
switch (item->type) {
case CMDQ_COMMAND:
retval = cmdq_fire_command(item);
/*
* If a command returns an error, remove any
* subsequent commands in the same group.
*/
if (retval == CMD_RETURN_ERROR)
cmdq_remove_group(item);
break;
case CMDQ_CALLBACK:
retval = cmdq_fire_callback(item);
break;
default:
retval = CMD_RETURN_ERROR;
break;
}
item->flags |= CMDQ_FIRED;
if (retval == CMD_RETURN_WAIT) {
item->flags |= CMDQ_WAITING;
goto waiting;
}
items++;
}
cmdq_remove(item);
}
log_debug("%s %s: exit (empty)", __func__, name);
return (items);
waiting:
log_debug("%s %s: exit (wait)", __func__, name);
return (items);
}
/* Print a guard line. */
void
cmdq_guard(struct cmdq_item *item, const char *guard, int flags)
{
struct client *c = item->client;
long t = item->time;
u_int number = item->number;
if (c != NULL && (c->flags & CLIENT_CONTROL))
file_print(c, "%%%s %ld %u %d\n", guard, t, number, flags);
}
/* Show message from command. */
void
cmdq_print(struct cmd_q *cmdq, const char *fmt, ...)
cmdq_print(struct cmdq_item *item, const char *fmt, ...)
{
struct client *c = cmdq->client;
struct window *w;
va_list ap;
struct client *c = item->client;
struct window_pane *wp;
struct window_mode_entry *wme;
va_list ap;
char *tmp, *msg;
va_start(ap, fmt);
xvasprintf(&msg, fmt, ap);
va_end(ap);
log_debug("%s: %s", __func__, msg);
if (c == NULL)
/* nothing */;
else if (c->session == NULL || (c->flags & CLIENT_CONTROL)) {
evbuffer_add_vprintf(c->stdout_data, fmt, ap);
evbuffer_add(c->stdout_data, "\n", 1);
server_push_stdout(c);
} else {
w = c->session->curw->window;
if (w->active->mode != &window_copy_mode) {
window_pane_reset_mode(w->active);
window_pane_set_mode(w->active, &window_copy_mode);
window_copy_init_for_output(w->active);
if (~c->flags & CLIENT_UTF8) {
tmp = msg;
msg = utf8_sanitize(tmp);
free(tmp);
}
window_copy_vadd(w->active, fmt, ap);
file_print(c, "%s\n", msg);
} else {
wp = c->session->curw->window->active;
wme = TAILQ_FIRST(&wp->modes);
if (wme == NULL || wme->mode != &window_view_mode)
window_pane_set_mode(wp, &window_view_mode, NULL, NULL);
window_copy_add(wp, "%s", msg);
}
va_end(ap);
free(msg);
}
/* Show error from command. */
void
cmdq_error(struct cmd_q *cmdq, const char *fmt, ...)
cmdq_error(struct cmdq_item *item, const char *fmt, ...)
{
struct client *c = cmdq->client;
struct cmd *cmd = cmdq->cmd;
struct client *c = item->client;
struct cmd *cmd = item->cmd;
va_list ap;
char *msg;
size_t msglen;
char *tmp;
va_start(ap, fmt);
msglen = xvasprintf(&msg, fmt, ap);
xvasprintf(&msg, fmt, ap);
va_end(ap);
log_debug("%s: %s", __func__, msg);
if (c == NULL)
cfg_add_cause("%s:%u: %s", cmd->file, cmd->line, msg);
else if (c->session == NULL || (c->flags & CLIENT_CONTROL)) {
evbuffer_add(c->stderr_data, msg, msglen);
evbuffer_add(c->stderr_data, "\n", 1);
server_push_stderr(c);
if (~c->flags & CLIENT_UTF8) {
tmp = msg;
msg = utf8_sanitize(tmp);
free(tmp);
}
if (c->flags & CLIENT_CONTROL)
file_print(c, "%s\n", msg);
else
file_error(c, "%s\n", msg);
c->retval = 1;
} else {
*msg = toupper((u_char) *msg);
@@ -115,132 +555,3 @@ cmdq_error(struct cmd_q *cmdq, const char *fmt, ...)
free(msg);
}
/* Print a guard line. */
void
cmdq_guard(struct cmd_q *cmdq, const char *guard, int flags)
{
struct client *c = cmdq->client;
if (c == NULL || !(c->flags & CLIENT_CONTROL))
return;
evbuffer_add_printf(c->stdout_data, "%%%s %ld %u %d\n", guard,
(long) cmdq->time, cmdq->number, flags);
server_push_stdout(c);
}
/* Add command list to queue and begin processing if needed. */
void
cmdq_run(struct cmd_q *cmdq, struct cmd_list *cmdlist)
{
cmdq_append(cmdq, cmdlist);
if (cmdq->item == NULL) {
cmdq->cmd = NULL;
cmdq_continue(cmdq);
}
}
/* Add command list to queue. */
void
cmdq_append(struct cmd_q *cmdq, struct cmd_list *cmdlist)
{
struct cmd_q_item *item;
item = xcalloc(1, sizeof *item);
item->cmdlist = cmdlist;
TAILQ_INSERT_TAIL(&cmdq->queue, item, qentry);
cmdlist->references++;
}
/* Continue processing command queue. Returns 1 if finishes empty. */
int
cmdq_continue(struct cmd_q *cmdq)
{
struct cmd_q_item *next;
enum cmd_retval retval;
int empty, flags;
char s[1024];
cmdq->references++;
notify_disable();
empty = TAILQ_EMPTY(&cmdq->queue);
if (empty)
goto empty;
if (cmdq->item == NULL) {
cmdq->item = TAILQ_FIRST(&cmdq->queue);
cmdq->cmd = TAILQ_FIRST(&cmdq->item->cmdlist->list);
} else
cmdq->cmd = TAILQ_NEXT(cmdq->cmd, qentry);
do {
while (cmdq->cmd != NULL) {
cmd_print(cmdq->cmd, s, sizeof s);
log_debug("cmdq %p: %s (client %d)", cmdq, s,
cmdq->client != NULL ? cmdq->client->ibuf.fd : -1);
cmdq->time = time(NULL);
cmdq->number++;
flags = !!(cmdq->cmd->flags & CMD_CONTROL);
cmdq_guard(cmdq, "begin", flags);
retval = cmdq->cmd->entry->exec(cmdq->cmd, cmdq);
if (retval == CMD_RETURN_ERROR)
cmdq_guard(cmdq, "error", flags);
else
cmdq_guard(cmdq, "end", flags);
if (retval == CMD_RETURN_ERROR)
break;
if (retval == CMD_RETURN_WAIT)
goto out;
if (retval == CMD_RETURN_STOP) {
cmdq_flush(cmdq);
goto empty;
}
cmdq->cmd = TAILQ_NEXT(cmdq->cmd, qentry);
}
next = TAILQ_NEXT(cmdq->item, qentry);
TAILQ_REMOVE(&cmdq->queue, cmdq->item, qentry);
cmd_list_free(cmdq->item->cmdlist);
free(cmdq->item);
cmdq->item = next;
if (cmdq->item != NULL)
cmdq->cmd = TAILQ_FIRST(&cmdq->item->cmdlist->list);
} while (cmdq->item != NULL);
empty:
if (cmdq->client_exit > 0)
cmdq->client->flags |= CLIENT_EXIT;
if (cmdq->emptyfn != NULL)
cmdq->emptyfn(cmdq);
empty = 1;
out:
notify_enable();
cmdq_free(cmdq);
return (empty);
}
/* Flush command queue. */
void
cmdq_flush(struct cmd_q *cmdq)
{
struct cmd_q_item *item, *item1;
TAILQ_FOREACH_SAFE(item, &cmdq->queue, qentry, item1) {
TAILQ_REMOVE(&cmdq->queue, item, qentry);
cmd_list_free(item->cmdlist);
free(item);
}
cmdq->item = NULL;
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,58 +18,144 @@
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
/*
* Refresh client.
*/
enum cmd_retval cmd_refresh_client_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_refresh_client_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_refresh_client_entry = {
"refresh-client", "refresh",
"C:St:", 0, 0,
"[-S] [-C size] " CMD_TARGET_CLIENT_USAGE,
0,
cmd_refresh_client_exec
.name = "refresh-client",
.alias = "refresh",
.args = { "cC:DF:lLRSt:U", 0, 1 },
.usage = "[-cDlLRSU] [-C XxY] [-F flags] " CMD_TARGET_CLIENT_USAGE
" [adjustment]",
.flags = CMD_AFTERHOOK,
.exec = cmd_refresh_client_exec
};
enum cmd_retval
cmd_refresh_client_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_refresh_client_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
const char *size;
u_int w, h;
struct tty *tty;
struct window *w;
const char *size, *errstr;
char *copy, *next, *s;
u_int x, y, adjust;
if ((c = cmd_find_client(cmdq, args_get(args, 't'), 0)) == NULL)
if ((c = cmd_find_client(item, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
tty = &c->tty;
if (args_has(args, 'C')) {
if ((size = args_get(args, 'C')) == NULL) {
cmdq_error(cmdq, "missing size");
return (CMD_RETURN_ERROR);
if (args_has(args, 'c') ||
args_has(args, 'L') ||
args_has(args, 'R') ||
args_has(args, 'U') ||
args_has(args, 'D'))
{
if (args->argc == 0)
adjust = 1;
else {
adjust = strtonum(args->argv[0], 1, INT_MAX, &errstr);
if (errstr != NULL) {
cmdq_error(item, "adjustment %s", errstr);
return (CMD_RETURN_ERROR);
}
}
if (sscanf(size, "%u,%u", &w, &h) != 2) {
cmdq_error(cmdq, "bad size argument");
return (CMD_RETURN_ERROR);
if (args_has(args, 'c'))
c->pan_window = NULL;
else {
w = c->session->curw->window;
if (c->pan_window != w) {
c->pan_window = w;
c->pan_ox = tty->oox;
c->pan_oy = tty->ooy;
}
if (args_has(args, 'L')) {
if (c->pan_ox > adjust)
c->pan_ox -= adjust;
else
c->pan_ox = 0;
} else if (args_has(args, 'R')) {
c->pan_ox += adjust;
if (c->pan_ox > w->sx - tty->osx)
c->pan_ox = w->sx - tty->osx;
} else if (args_has(args, 'U')) {
if (c->pan_oy > adjust)
c->pan_oy -= adjust;
else
c->pan_oy = 0;
} else if (args_has(args, 'D')) {
c->pan_oy += adjust;
if (c->pan_oy > w->sy - tty->osy)
c->pan_oy = w->sy - tty->osy;
}
}
if (w < PANE_MINIMUM || w > 5000 ||
h < PANE_MINIMUM || h > 5000) {
cmdq_error(cmdq, "size too small or too big");
return (CMD_RETURN_ERROR);
}
if (!(c->flags & CLIENT_CONTROL)) {
cmdq_error(cmdq, "not a control client");
return (CMD_RETURN_ERROR);
}
if (tty_set_size(&c->tty, w, h))
recalculate_sizes();
} else if (args_has(args, 'S')) {
status_update_jobs(c);
server_status_client(c);
} else
tty_update_client_offset(c);
server_redraw_client(c);
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 'l')) {
if (c->session != NULL)
tty_putcode_ptr2(&c->tty, TTYC_MS, "", "?");
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 'C') || args_has(args, 'F')) {
if (args_has(args, 'C')) {
if (!(c->flags & CLIENT_CONTROL)) {
cmdq_error(item, "not a control client");
return (CMD_RETURN_ERROR);
}
size = args_get(args, 'C');
if (sscanf(size, "%u,%u", &x, &y) != 2 &&
sscanf(size, "%ux%u", &x, &y) != 2) {
cmdq_error(item, "bad size argument");
return (CMD_RETURN_ERROR);
}
if (x < WINDOW_MINIMUM || x > WINDOW_MAXIMUM ||
y < WINDOW_MINIMUM || y > WINDOW_MAXIMUM) {
cmdq_error(item, "size too small or too big");
return (CMD_RETURN_ERROR);
}
tty_set_size(&c->tty, x, y, 0, 0);
c->flags |= CLIENT_SIZECHANGED;
recalculate_sizes();
}
if (args_has(args, 'F')) {
if (!(c->flags & CLIENT_CONTROL)) {
cmdq_error(item, "not a control client");
return (CMD_RETURN_ERROR);
}
s = copy = xstrdup(args_get(args, 'F'));
while ((next = strsep(&s, ",")) != NULL) {
/* Unknown flags are ignored. */
if (strcmp(next, "no-output") == 0)
c->flags |= CLIENT_CONTROL_NOOUTPUT;
}
free(copy);
}
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 'S')) {
c->flags |= CLIENT_STATUSFORCE;
server_status_client(c);
} else {
c->flags |= CLIENT_STATUSFORCE;
server_redraw_client(c);
}
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -19,6 +19,7 @@
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
@@ -26,43 +27,54 @@
* Change session name.
*/
enum cmd_retval cmd_rename_session_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_rename_session_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_rename_session_entry = {
"rename-session", "rename",
"t:", 1, 1,
CMD_TARGET_SESSION_USAGE " new-name",
0,
cmd_rename_session_exec
.name = "rename-session",
.alias = "rename",
.args = { "t:", 1, 1 },
.usage = CMD_TARGET_SESSION_USAGE " new-name",
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_rename_session_exec
};
enum cmd_retval
cmd_rename_session_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_rename_session_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
const char *newname;
struct args *args = self->args;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
char *newname;
newname = format_single(item, args->argv[0], c, s, NULL, NULL);
if (strcmp(newname, s->name) == 0) {
free(newname);
return (CMD_RETURN_NORMAL);
}
newname = args->argv[0];
if (!session_check_name(newname)) {
cmdq_error(cmdq, "bad session name: %s", newname);
cmdq_error(item, "bad session name: %s", newname);
free(newname);
return (CMD_RETURN_ERROR);
}
if (session_find(newname) != NULL) {
cmdq_error(cmdq, "duplicate session: %s", newname);
cmdq_error(item, "duplicate session: %s", newname);
free(newname);
return (CMD_RETURN_ERROR);
}
if ((s = cmd_find_session(cmdq, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
RB_REMOVE(sessions, &sessions, s);
free(s->name);
s->name = xstrdup(newname);
s->name = newname;
RB_INSERT(sessions, &sessions, s);
server_status_session(s);
notify_session_renamed(s);
notify_session("session-renamed", s);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,30 +26,37 @@
* Rename a window.
*/
enum cmd_retval cmd_rename_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_rename_window_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_rename_window_entry = {
"rename-window", "renamew",
"t:", 1, 1,
CMD_TARGET_WINDOW_USAGE " new-name",
0,
cmd_rename_window_exec
.name = "rename-window",
.alias = "renamew",
.args = { "t:", 1, 1 },
.usage = CMD_TARGET_WINDOW_USAGE " new-name",
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_rename_window_exec
};
enum cmd_retval
cmd_rename_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_rename_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
struct winlink *wl;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
char *newname;
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), &s)) == NULL)
return (CMD_RETURN_ERROR);
window_set_name(wl->window, args->argv[0]);
options_set_number(&wl->window->options, "automatic-rename", 0);
newname = format_single(item, args->argv[0], c, s, wl, NULL);
window_set_name(wl->window, newname);
options_set_number(wl->window->options, "automatic-rename", 0);
server_status_window(wl->window);
free(newname);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -19,6 +19,7 @@
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
@@ -26,31 +27,50 @@
* Increase or decrease pane size.
*/
enum cmd_retval cmd_resize_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_resize_pane_exec(struct cmd *, struct cmdq_item *);
static void cmd_resize_pane_mouse_update(struct client *,
struct mouse_event *);
const struct cmd_entry cmd_resize_pane_entry = {
"resize-pane", "resizep",
"DLRt:Ux:y:Z", 0, 1,
"[-DLRUZ] [-x width] [-y height] " CMD_TARGET_PANE_USAGE " [adjustment]",
0,
cmd_resize_pane_exec
.name = "resize-pane",
.alias = "resizep",
.args = { "DLMRt:Ux:y:Z", 0, 1 },
.usage = "[-DLMRUZ] [-x width] [-y height] " CMD_TARGET_PANE_USAGE " "
"[adjustment]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_resize_pane_exec
};
enum cmd_retval
cmd_resize_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_resize_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct window *w;
const char *errstr;
char *cause;
struct window_pane *wp;
struct cmdq_shared *shared = item->shared;
struct window_pane *wp = item->target.wp;
struct winlink *wl = item->target.wl;
struct window *w = wl->window;
struct client *c = item->client;
struct session *s = item->target.s;
const char *errstr, *p;
char *cause, *copy;
u_int adjust;
int x, y;
int x, y, percentage;
size_t plen;
if ((wl = cmd_find_pane(cmdq, args_get(args, 't'), NULL, &wp)) == NULL)
return (CMD_RETURN_ERROR);
w = wl->window;
if (args_has(args, 'M')) {
if (cmd_mouse_window(&shared->mouse, &s) == NULL)
return (CMD_RETURN_NORMAL);
if (c == NULL || c->session != s)
return (CMD_RETURN_NORMAL);
c->tty.mouse_drag_update = cmd_resize_pane_mouse_update;
cmd_resize_pane_mouse_update(c, &shared->mouse);
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 'Z')) {
if (w->flags & WINDOW_ZOOMED)
@@ -68,41 +88,142 @@ cmd_resize_pane_exec(struct cmd *self, struct cmd_q *cmdq)
else {
adjust = strtonum(args->argv[0], 1, INT_MAX, &errstr);
if (errstr != NULL) {
cmdq_error(cmdq, "adjustment %s", errstr);
cmdq_error(item, "adjustment %s", errstr);
return (CMD_RETURN_ERROR);
}
}
if (args_has(self->args, 'x')) {
x = args_strtonum(self->args, 'x', PANE_MINIMUM, INT_MAX,
&cause);
if (cause != NULL) {
cmdq_error(cmdq, "width %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
if ((p = args_get(args, 'x')) != NULL) {
plen = strlen(p);
if (p[plen - 1] == '%') {
copy = xstrdup(p);
copy[plen - 1] = '\0';
percentage = strtonum(copy, 0, INT_MAX, &errstr);
free(copy);
if (errstr != NULL) {
cmdq_error(item, "width %s", errstr);
return (CMD_RETURN_ERROR);
}
x = (w->sx * percentage) / 100;
if (x < PANE_MINIMUM)
x = PANE_MINIMUM;
if (x > INT_MAX)
x = INT_MAX;
} else {
x = args_strtonum(args, 'x', PANE_MINIMUM, INT_MAX,
&cause);
if (cause != NULL) {
cmdq_error(item, "width %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
}
layout_resize_pane_to(wp, LAYOUT_LEFTRIGHT, x);
}
if (args_has(self->args, 'y')) {
y = args_strtonum(self->args, 'y', PANE_MINIMUM, INT_MAX,
&cause);
if (cause != NULL) {
cmdq_error(cmdq, "height %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
if ((p = args_get(args, 'y')) != NULL) {
plen = strlen(p);
if (p[plen - 1] == '%') {
copy = xstrdup(p);
copy[plen - 1] = '\0';
percentage = strtonum(copy, 0, INT_MAX, &errstr);
free(copy);
if (errstr != NULL) {
cmdq_error(item, "height %s", errstr);
return (CMD_RETURN_ERROR);
}
y = (w->sy * percentage) / 100;
if (y < PANE_MINIMUM)
y = PANE_MINIMUM;
if (y > INT_MAX)
y = INT_MAX;
}
else {
y = args_strtonum(args, 'y', PANE_MINIMUM, INT_MAX,
&cause);
if (cause != NULL) {
cmdq_error(item, "height %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
}
layout_resize_pane_to(wp, LAYOUT_TOPBOTTOM, y);
}
if (args_has(self->args, 'L'))
layout_resize_pane(wp, LAYOUT_LEFTRIGHT, -adjust);
else if (args_has(self->args, 'R'))
layout_resize_pane(wp, LAYOUT_LEFTRIGHT, adjust);
else if (args_has(self->args, 'U'))
layout_resize_pane(wp, LAYOUT_TOPBOTTOM, -adjust);
else if (args_has(self->args, 'D'))
layout_resize_pane(wp, LAYOUT_TOPBOTTOM, adjust);
if (args_has(args, 'L'))
layout_resize_pane(wp, LAYOUT_LEFTRIGHT, -adjust, 1);
else if (args_has(args, 'R'))
layout_resize_pane(wp, LAYOUT_LEFTRIGHT, adjust, 1);
else if (args_has(args, 'U'))
layout_resize_pane(wp, LAYOUT_TOPBOTTOM, -adjust, 1);
else if (args_has(args, 'D'))
layout_resize_pane(wp, LAYOUT_TOPBOTTOM, adjust, 1);
server_redraw_window(wl->window);
return (CMD_RETURN_NORMAL);
}
static void
cmd_resize_pane_mouse_update(struct client *c, struct mouse_event *m)
{
struct winlink *wl;
struct window *w;
u_int y, ly, x, lx;
static const int offsets[][2] = {
{ 0, 0 }, { 0, 1 }, { 1, 0 }, { 0, -1 }, { -1, 0 },
};
struct layout_cell *cells[nitems(offsets)], *lc;
u_int ncells = 0, i, j, resizes = 0;
enum layout_type type;
wl = cmd_mouse_window(m, NULL);
if (wl == NULL) {
c->tty.mouse_drag_update = NULL;
return;
}
w = wl->window;
y = m->y + m->oy; x = m->x + m->ox;
if (m->statusat == 0 && y >= m->statuslines)
y -= m->statuslines;
else if (m->statusat > 0 && y >= (u_int)m->statusat)
y = m->statusat - 1;
ly = m->ly + m->oy; lx = m->lx + m->ox;
if (m->statusat == 0 && ly >= m->statuslines)
ly -= m->statuslines;
else if (m->statusat > 0 && ly >= (u_int)m->statusat)
ly = m->statusat - 1;
for (i = 0; i < nitems(cells); i++) {
lc = layout_search_by_border(w->layout_root, lx + offsets[i][0],
ly + offsets[i][1]);
if (lc == NULL)
continue;
for (j = 0; j < ncells; j++) {
if (cells[j] == lc) {
lc = NULL;
break;
}
}
if (lc == NULL)
continue;
cells[ncells] = lc;
ncells++;
}
if (ncells == 0)
return;
for (i = 0; i < ncells; i++) {
type = cells[i]->parent->type;
if (y != ly && type == LAYOUT_TOPBOTTOM) {
layout_resize_layout(w, cells[i], type, y - ly, 0);
resizes++;
} else if (x != lx && type == LAYOUT_LEFTRIGHT) {
layout_resize_layout(w, cells[i], type, x - lx, 0);
resizes++;
}
}
if (resizes != 0)
server_redraw_window(w);
}

113
cmd-resize-window.c Normal file
View File

@@ -0,0 +1,113 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2018 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* 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 "tmux.h"
/*
* Increase or decrease window size.
*/
static enum cmd_retval cmd_resize_window_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_resize_window_entry = {
.name = "resize-window",
.alias = "resizew",
.args = { "aADLRt:Ux:y:", 0, 1 },
.usage = "[-aADLRU] [-x width] [-y height] " CMD_TARGET_WINDOW_USAGE " "
"[adjustment]",
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_resize_window_exec
};
static enum cmd_retval
cmd_resize_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl = item->target.wl;
struct window *w = wl->window;
struct session *s = item->target.s;
const char *errstr;
char *cause;
u_int adjust, sx, sy;
int xpixel = -1, ypixel = -1;
if (args->argc == 0)
adjust = 1;
else {
adjust = strtonum(args->argv[0], 1, INT_MAX, &errstr);
if (errstr != NULL) {
cmdq_error(item, "adjustment %s", errstr);
return (CMD_RETURN_ERROR);
}
}
sx = w->sx;
sy = w->sy;
if (args_has(args, 'x')) {
sx = args_strtonum(args, 'x', WINDOW_MINIMUM, WINDOW_MAXIMUM,
&cause);
if (cause != NULL) {
cmdq_error(item, "width %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
}
if (args_has(args, 'y')) {
sy = args_strtonum(args, 'y', WINDOW_MINIMUM, WINDOW_MAXIMUM,
&cause);
if (cause != NULL) {
cmdq_error(item, "height %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
}
if (args_has(args, 'L')) {
if (sx >= adjust)
sx -= adjust;
} else if (args_has(args, 'R'))
sx += adjust;
else if (args_has(args, 'U')) {
if (sy >= adjust)
sy -= adjust;
} else if (args_has(args, 'D'))
sy += adjust;
if (args_has(args, 'A')) {
default_window_size(NULL, s, w, &sx, &sy, &xpixel, &ypixel,
WINDOW_SIZE_LARGEST);
} else if (args_has(args, 'a')) {
default_window_size(NULL, s, w, &sx, &sy, &xpixel, &ypixel,
WINDOW_SIZE_SMALLEST);
}
options_set_number(w->options, "window-size", WINDOW_SIZE_MANUAL);
resize_window(w, sx, sy, xpixel, ypixel);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
* Copyright (c) 2011 Marcel P. Partap <mpartap@gmx.net>
*
* Permission to use, copy, modify, and distribute this software for any
@@ -20,7 +20,7 @@
#include <sys/types.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include "tmux.h"
@@ -28,69 +28,69 @@
* Respawn a pane (restart the command). Kill existing if -k given.
*/
enum cmd_retval cmd_respawn_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_respawn_pane_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_respawn_pane_entry = {
"respawn-pane", "respawnp",
"kt:", 0, -1,
"[-k] " CMD_TARGET_PANE_USAGE " [command]",
0,
cmd_respawn_pane_exec
.name = "respawn-pane",
.alias = "respawnp",
.args = { "c:e:kt:", 0, -1 },
.usage = "[-k] [-c start-directory] [-e environment] "
CMD_TARGET_PANE_USAGE " [command]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_respawn_pane_exec
};
enum cmd_retval
cmd_respawn_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_respawn_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct window *w;
struct window_pane *wp;
struct session *s;
struct environ env;
const char *path;
char *cause;
u_int idx;
struct environ_entry *envent;
struct spawn_context sc;
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct window_pane *wp = item->target.wp;
char *cause = NULL;
const char *add;
struct args_value *value;
if ((wl = cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp)) == NULL)
return (CMD_RETURN_ERROR);
w = wl->window;
memset(&sc, 0, sizeof sc);
sc.item = item;
sc.s = s;
sc.wl = wl;
if (!args_has(self->args, 'k') && wp->fd != -1) {
if (window_pane_index(wp, &idx) != 0)
fatalx("index not found");
cmdq_error(cmdq, "pane still active: %s:%u.%u",
s->name, wl->idx, idx);
return (CMD_RETURN_ERROR);
sc.wp0 = wp;
sc.lc = NULL;
sc.name = NULL;
sc.argc = args->argc;
sc.argv = args->argv;
sc.environ = environ_create();
add = args_first_value(args, 'e', &value);
while (add != NULL) {
environ_put(sc.environ, add);
add = args_next_value(&value);
}
environ_init(&env);
environ_copy(&global_environ, &env);
environ_copy(&s->environ, &env);
server_fill_environ(s, &env);
sc.idx = -1;
sc.cwd = args_get(args, 'c');
window_pane_reset_mode(wp);
screen_reinit(&wp->base);
input_init(wp);
sc.flags = SPAWN_RESPAWN;
if (args_has(args, 'k'))
sc.flags |= SPAWN_KILL;
path = NULL;
if (cmdq->client != NULL && cmdq->client->session == NULL)
envent = environ_find(&cmdq->client->environ, "PATH");
else
envent = environ_find(&s->environ, "PATH");
if (envent != NULL)
path = envent->value;
if (window_pane_spawn(wp, args->argc, args->argv, path, NULL, -1, &env,
s->tio, &cause) != 0) {
cmdq_error(cmdq, "respawn pane failed: %s", cause);
if (spawn_pane(&sc, &cause) == NULL) {
cmdq_error(item, "respawn pane failed: %s", cause);
free(cause);
environ_free(&env);
return (CMD_RETURN_ERROR);
}
wp->flags |= PANE_REDRAW;
server_status_window(w);
environ_free(&env);
wp->flags |= PANE_REDRAW;
server_status_window(wp->window);
environ_free(sc.environ);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -19,7 +19,7 @@
#include <sys/types.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include "tmux.h"
@@ -27,80 +27,66 @@
* Respawn a window (restart the command). Kill existing if -k given.
*/
enum cmd_retval cmd_respawn_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_respawn_window_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_respawn_window_entry = {
"respawn-window", "respawnw",
"kt:", 0, -1,
"[-k] " CMD_TARGET_WINDOW_USAGE " [command]",
0,
cmd_respawn_window_exec
.name = "respawn-window",
.alias = "respawnw",
.args = { "c:e:kt:", 0, -1 },
.usage = "[-k] [-c start-directory] [-e environment] "
CMD_TARGET_WINDOW_USAGE " [command]",
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = 0,
.exec = cmd_respawn_window_exec
};
enum cmd_retval
cmd_respawn_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_respawn_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct window *w;
struct window_pane *wp;
struct session *s;
struct environ env;
const char *path;
char *cause;
struct environ_entry *envent;
struct spawn_context sc;
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
char *cause = NULL;
const char *add;
struct args_value *value;
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), &s)) == NULL)
return (CMD_RETURN_ERROR);
w = wl->window;
memset(&sc, 0, sizeof sc);
sc.item = item;
sc.s = s;
sc.wl = wl;
sc.c = cmd_find_client(item, NULL, 1);
if (!args_has(self->args, 'k')) {
TAILQ_FOREACH(wp, &w->panes, entry) {
if (wp->fd == -1)
continue;
cmdq_error(cmdq,
"window still active: %s:%d", s->name, wl->idx);
return (CMD_RETURN_ERROR);
}
sc.name = NULL;
sc.argc = args->argc;
sc.argv = args->argv;
sc.environ = environ_create();
add = args_first_value(args, 'e', &value);
while (add != NULL) {
environ_put(sc.environ, add);
add = args_next_value(&value);
}
environ_init(&env);
environ_copy(&global_environ, &env);
environ_copy(&s->environ, &env);
server_fill_environ(s, &env);
sc.idx = -1;
sc.cwd = args_get(args, 'c');
wp = TAILQ_FIRST(&w->panes);
TAILQ_REMOVE(&w->panes, wp, entry);
layout_free(w);
window_destroy_panes(w);
TAILQ_INSERT_HEAD(&w->panes, wp, entry);
window_pane_resize(wp, w->sx, w->sy);
sc.flags = SPAWN_RESPAWN;
if (args_has(args, 'k'))
sc.flags |= SPAWN_KILL;
path = NULL;
if (cmdq->client != NULL && cmdq->client->session == NULL)
envent = environ_find(&cmdq->client->environ, "PATH");
else
envent = environ_find(&s->environ, "PATH");
if (envent != NULL)
path = envent->value;
if (window_pane_spawn(wp, args->argc, args->argv, path, NULL, -1, &env,
s->tio, &cause) != 0) {
cmdq_error(cmdq, "respawn window failed: %s", cause);
if (spawn_window(&sc, &cause) == NULL) {
cmdq_error(item, "respawn window failed: %s", cause);
free(cause);
environ_free(&env);
server_destroy_pane(wp);
return (CMD_RETURN_ERROR);
}
layout_init(w, wp);
window_pane_reset_mode(wp);
screen_reinit(&wp->base);
input_init(wp);
window_set_active_pane(w, wp);
recalculate_sizes();
server_redraw_window(w);
server_redraw_window(wl->window);
environ_free(&env);
environ_free(sc.environ);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -24,29 +24,33 @@
* Rotate the panes in a window.
*/
enum cmd_retval cmd_rotate_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_rotate_window_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_rotate_window_entry = {
"rotate-window", "rotatew",
"Dt:U", 0, 0,
"[-DU] " CMD_TARGET_WINDOW_USAGE,
0,
cmd_rotate_window_exec
.name = "rotate-window",
.alias = "rotatew",
.args = { "Dt:UZ", 0, 0 },
.usage = "[-DUZ] " CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = 0,
.exec = cmd_rotate_window_exec
};
enum cmd_retval
cmd_rotate_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_rotate_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct window *w;
struct cmd_find_state *current = &item->shared->current;
struct winlink *wl = item->target.wl;
struct window *w = wl->window;
struct window_pane *wp, *wp2;
struct layout_cell *lc;
u_int sx, sy, xoff, yoff;
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), NULL)) == NULL)
return (CMD_RETURN_ERROR);
w = wl->window;
window_push_zoom(w, args_has(self->args, 'Z'));
if (args_has(self->args, 'D')) {
wp = TAILQ_LAST(&w->panes, window_panes);
@@ -73,8 +77,6 @@ cmd_rotate_window_exec(struct cmd *self, struct cmd_q *cmdq)
if ((wp = TAILQ_PREV(w->active, window_panes, entry)) == NULL)
wp = TAILQ_LAST(&w->panes, window_panes);
window_set_active_pane(w, wp);
server_redraw_window(w);
} else {
wp = TAILQ_FIRST(&w->panes);
TAILQ_REMOVE(&w->panes, wp, entry);
@@ -100,9 +102,12 @@ cmd_rotate_window_exec(struct cmd *self, struct cmd_q *cmdq)
if ((wp = TAILQ_NEXT(w->active, entry)) == NULL)
wp = TAILQ_FIRST(&w->panes);
window_set_active_pane(w, wp);
server_redraw_window(w);
}
window_set_active_pane(w, wp, 1);
cmd_find_from_winlink_pane(current, wl, wp, 0);
window_pop_zoom(w);
server_redraw_window(w);
return (CMD_RETURN_NORMAL);
}

View File

@@ -29,145 +29,139 @@
* Runs a command without a window.
*/
enum cmd_retval cmd_run_shell_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_run_shell_exec(struct cmd *, struct cmdq_item *);
void cmd_run_shell_callback(struct job *);
void cmd_run_shell_free(void *);
void cmd_run_shell_print(struct job *, const char *);
static void cmd_run_shell_callback(struct job *);
static void cmd_run_shell_free(void *);
static void cmd_run_shell_print(struct job *, const char *);
const struct cmd_entry cmd_run_shell_entry = {
"run-shell", "run",
"bt:", 1, 1,
"[-b] " CMD_TARGET_PANE_USAGE " shell-command",
0,
cmd_run_shell_exec
.name = "run-shell",
.alias = "run",
.args = { "bt:", 1, 1 },
.usage = "[-b] " CMD_TARGET_PANE_USAGE " shell-command",
.target = { 't', CMD_FIND_PANE, CMD_FIND_CANFAIL },
.flags = 0,
.exec = cmd_run_shell_exec
};
struct cmd_run_shell_data {
char *cmd;
struct cmd_q *cmdq;
int bflag;
int wp_id;
char *cmd;
struct cmdq_item *item;
int wp_id;
};
void
static void
cmd_run_shell_print(struct job *job, const char *msg)
{
struct cmd_run_shell_data *cdata = job->data;
struct cmd_run_shell_data *cdata = job_get_data(job);
struct window_pane *wp = NULL;
struct cmd_find_state fs;
struct window_mode_entry *wme;
if (cdata->wp_id != -1)
wp = window_pane_find_by_id(cdata->wp_id);
if (wp == NULL) {
cmdq_print(cdata->cmdq, "%s", msg);
return;
if (cdata->item != NULL) {
cmdq_print(cdata->item, "%s", msg);
return;
}
if (cmd_find_from_nothing(&fs, 0) != 0)
return;
wp = fs.wp;
if (wp == NULL)
return;
}
if (window_pane_set_mode(wp, &window_copy_mode) == 0)
window_copy_init_for_output(wp);
if (wp->mode == &window_copy_mode)
window_copy_add(wp, "%s", msg);
wme = TAILQ_FIRST(&wp->modes);
if (wme == NULL || wme->mode != &window_view_mode)
window_pane_set_mode(wp, &window_view_mode, NULL, NULL);
window_copy_add(wp, "%s", msg);
}
enum cmd_retval
cmd_run_shell_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_run_shell_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct cmd_run_shell_data *cdata;
char *shellcmd;
struct client *c;
struct session *s = NULL;
struct winlink *wl = NULL;
struct window_pane *wp = NULL;
struct format_tree *ft;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct window_pane *wp = item->target.wp;
if (args_has(args, 't'))
wl = cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp);
else {
c = cmd_find_client(cmdq, NULL, 1);
if (c != NULL && c->session != NULL) {
s = c->session;
wl = s->curw;
wp = wl->window->active;
}
cdata = xcalloc(1, sizeof *cdata);
cdata->cmd = format_single(item, args->argv[0], c, s, wl, wp);
if (args_has(args, 't') && wp != NULL)
cdata->wp_id = wp->id;
else
cdata->wp_id = -1;
if (!args_has(args, 'b'))
cdata->item = item;
if (job_run(cdata->cmd, s, server_client_get_cwd(item->client, s), NULL,
cmd_run_shell_callback, cmd_run_shell_free, cdata, 0) == NULL) {
cmdq_error(item, "failed to run command: %s", cdata->cmd);
free(cdata);
return (CMD_RETURN_ERROR);
}
ft = format_create();
format_defaults(ft, NULL, s, wl, wp);
shellcmd = format_expand(ft, args->argv[0]);
format_free(ft);
cdata = xmalloc(sizeof *cdata);
cdata->cmd = shellcmd;
cdata->bflag = args_has(args, 'b');
cdata->wp_id = wp != NULL ? (int) wp->id : -1;
cdata->cmdq = cmdq;
cmdq->references++;
job_run(shellcmd, s, cmd_run_shell_callback, cmd_run_shell_free, cdata);
if (cdata->bflag)
if (args_has(args, 'b'))
return (CMD_RETURN_NORMAL);
return (CMD_RETURN_WAIT);
}
void
static void
cmd_run_shell_callback(struct job *job)
{
struct cmd_run_shell_data *cdata = job->data;
struct cmd_q *cmdq = cdata->cmdq;
char *cmd, *msg, *line;
struct cmd_run_shell_data *cdata = job_get_data(job);
struct bufferevent *event = job_get_event(job);
char *cmd = cdata->cmd, *msg = NULL, *line;
size_t size;
int retcode;
u_int lines;
int retcode, status;
if (cmdq->dead)
return;
cmd = cdata->cmd;
lines = 0;
do {
if ((line = evbuffer_readline(job->event->input)) != NULL) {
if ((line = evbuffer_readline(event->input)) != NULL) {
cmd_run_shell_print(job, line);
free(line);
lines++;
}
} while (line != NULL);
size = EVBUFFER_LENGTH(job->event->input);
size = EVBUFFER_LENGTH(event->input);
if (size != 0) {
line = xmalloc(size + 1);
memcpy(line, EVBUFFER_DATA(job->event->input), size);
memcpy(line, EVBUFFER_DATA(event->input), size);
line[size] = '\0';
cmd_run_shell_print(job, line);
lines++;
free(line);
}
msg = NULL;
if (WIFEXITED(job->status)) {
if ((retcode = WEXITSTATUS(job->status)) != 0)
status = job_get_status(job);
if (WIFEXITED(status)) {
if ((retcode = WEXITSTATUS(status)) != 0)
xasprintf(&msg, "'%s' returned %d", cmd, retcode);
} else if (WIFSIGNALED(job->status)) {
retcode = WTERMSIG(job->status);
} else if (WIFSIGNALED(status)) {
retcode = WTERMSIG(status);
xasprintf(&msg, "'%s' terminated by signal %d", cmd, retcode);
}
if (msg != NULL)
cmd_run_shell_print(job, msg);
free(msg);
if (cdata->item != NULL)
cmdq_continue(cdata->item);
}
void
static void
cmd_run_shell_free(void *data)
{
struct cmd_run_shell_data *cdata = data;
struct cmd_q *cmdq = cdata->cmdq;
if (!cmdq_free(cmdq) && !cdata->bflag)
cmdq_continue(cmdq);
free(cdata->cmd);
free(cdata);

View File

@@ -31,127 +31,83 @@
* Saves a paste buffer to a file.
*/
enum cmd_retval cmd_save_buffer_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_save_buffer_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_save_buffer_entry = {
"save-buffer", "saveb",
"ab:", 1, 1,
"[-a] " CMD_BUFFER_USAGE " path",
0,
cmd_save_buffer_exec
.name = "save-buffer",
.alias = "saveb",
.args = { "ab:", 1, 1 },
.usage = "[-a] " CMD_BUFFER_USAGE " path",
.flags = CMD_AFTERHOOK,
.exec = cmd_save_buffer_exec
};
const struct cmd_entry cmd_show_buffer_entry = {
"show-buffer", "showb",
"b:", 0, 0,
CMD_BUFFER_USAGE,
0,
cmd_save_buffer_exec
.name = "show-buffer",
.alias = "showb",
.args = { "b:", 0, 0 },
.usage = CMD_BUFFER_USAGE,
.flags = CMD_AFTERHOOK,
.exec = cmd_save_buffer_exec
};
enum cmd_retval
cmd_save_buffer_exec(struct cmd *self, struct cmd_q *cmdq)
static void
cmd_save_buffer_done(__unused struct client *c, const char *path, int error,
__unused int closed, __unused struct evbuffer *buffer, void *data)
{
struct cmdq_item *item = data;
if (!closed)
return;
if (error != 0)
cmdq_error(item, "%s: %s", path, strerror(error));
cmdq_continue(item);
}
static enum cmd_retval
cmd_save_buffer_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c = cmdq->client;
struct session *s;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct window_pane *wp = item->target.wp;
struct paste_buffer *pb;
const char *path, *bufname;
char *start, *end, *msg;
size_t size, used, msglen;
int cwd, fd;
FILE *f;
int flags;
const char *bufname = args_get(args, 'b'), *bufdata;
size_t bufsize;
char *path;
if (!args_has(args, 'b')) {
if ((pb = paste_get_top()) == NULL) {
cmdq_error(cmdq, "no buffers");
if (bufname == NULL) {
if ((pb = paste_get_top(NULL)) == NULL) {
cmdq_error(item, "no buffers");
return (CMD_RETURN_ERROR);
}
} else {
bufname = args_get(args, 'b');
pb = paste_get_name(bufname);
if (pb == NULL) {
cmdq_error(cmdq, "no buffer %s", bufname);
cmdq_error(item, "no buffer %s", bufname);
return (CMD_RETURN_ERROR);
}
}
bufdata = paste_buffer_data(pb, &bufsize);
if (self->entry == &cmd_show_buffer_entry)
path = "-";
path = xstrdup("-");
else
path = args->argv[0];
if (strcmp(path, "-") == 0) {
if (c == NULL) {
cmdq_error(cmdq, "can't write to stdout");
return (CMD_RETURN_ERROR);
}
if (c->session == NULL || (c->flags & CLIENT_CONTROL))
goto do_stdout;
goto do_print;
}
if (c != NULL && c->session == NULL)
cwd = c->cwd;
else if ((s = cmd_current_session(cmdq, 0)) != NULL)
cwd = s->cwd;
path = format_single(item, args->argv[0], c, s, wl, wp);
if (args_has(self->args, 'a'))
flags = O_APPEND;
else
cwd = AT_FDCWD;
flags = 0;
file_write(item->client, path, flags, bufdata, bufsize,
cmd_save_buffer_done, item);
free(path);
f = NULL;
if (args_has(self->args, 'a')) {
fd = openat(cwd, path, O_CREAT|O_RDWR|O_APPEND, 0600);
if (fd != -1)
f = fdopen(fd, "ab");
} else {
fd = openat(cwd, path, O_CREAT|O_RDWR|O_TRUNC, 0600);
if (fd != -1)
f = fdopen(fd, "wb");
}
if (f == NULL) {
if (fd != -1)
close(fd);
cmdq_error(cmdq, "%s: %s", path, strerror(errno));
return (CMD_RETURN_ERROR);
}
if (fwrite(pb->data, 1, pb->size, f) != pb->size) {
cmdq_error(cmdq, "%s: fwrite error", path);
fclose(f);
return (CMD_RETURN_ERROR);
}
fclose(f);
return (CMD_RETURN_NORMAL);
do_stdout:
evbuffer_add(c->stdout_data, pb->data, pb->size);
server_push_stdout(c);
return (CMD_RETURN_NORMAL);
do_print:
if (pb->size > (INT_MAX / 4) - 1) {
cmdq_error(cmdq, "buffer too big");
return (CMD_RETURN_ERROR);
}
msg = NULL;
used = 0;
while (used != pb->size) {
start = pb->data + used;
end = memchr(start, '\n', pb->size - used);
if (end != NULL)
size = end - start;
else
size = pb->size - used;
msglen = size * 4 + 1;
msg = xrealloc(msg, msglen);
strvisx(msg, start, size, VIS_OCTAL|VIS_TAB);
cmdq_print(cmdq, "%s", msg);
used += size + (end != NULL);
}
free(msg);
return (CMD_RETURN_NORMAL);
return (CMD_RETURN_WAIT);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,83 +18,130 @@
#include <sys/types.h>
#include <stdlib.h>
#include "tmux.h"
/*
* Switch window to selected layout.
*/
enum cmd_retval cmd_select_layout_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_select_layout_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_select_layout_entry = {
"select-layout", "selectl",
"npt:", 0, 1,
"[-np] " CMD_TARGET_WINDOW_USAGE " [layout-name]",
0,
cmd_select_layout_exec
.name = "select-layout",
.alias = "selectl",
.args = { "Enopt:", 0, 1 },
.usage = "[-Enop] " CMD_TARGET_PANE_USAGE " [layout-name]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_select_layout_exec
};
const struct cmd_entry cmd_next_layout_entry = {
"next-layout", "nextl",
"t:", 0, 0,
CMD_TARGET_WINDOW_USAGE,
0,
cmd_select_layout_exec
.name = "next-layout",
.alias = "nextl",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_select_layout_exec
};
const struct cmd_entry cmd_previous_layout_entry = {
"previous-layout", "prevl",
"t:", 0, 0,
CMD_TARGET_WINDOW_USAGE,
0,
cmd_select_layout_exec
.name = "previous-layout",
.alias = "prevl",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_select_layout_exec
};
enum cmd_retval
cmd_select_layout_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_select_layout_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
const char *layoutname;
int next, previous, layout;
struct args *args = self->args;
struct winlink *wl = item->target.wl;
struct window *w = wl->window;
struct window_pane *wp = item->target.wp;
const char *layoutname;
char *oldlayout;
int next, previous, layout;
if ((wl = cmd_find_window(cmdq, args_get(args, 't'), NULL)) == NULL)
return (CMD_RETURN_ERROR);
server_unzoom_window(wl->window);
server_unzoom_window(w);
next = self->entry == &cmd_next_layout_entry;
if (args_has(self->args, 'n'))
if (args_has(args, 'n'))
next = 1;
previous = self->entry == &cmd_previous_layout_entry;
if (args_has(self->args, 'p'))
if (args_has(args, 'p'))
previous = 1;
oldlayout = w->old_layout;
w->old_layout = layout_dump(w->layout_root);
if (next || previous) {
if (next)
layout = layout_set_next(wl->window);
layout_set_next(w);
else
layout = layout_set_previous(wl->window);
server_redraw_window(wl->window);
return (CMD_RETURN_NORMAL);
layout_set_previous(w);
goto changed;
}
if (args->argc == 0)
layout = wl->window->lastlayout;
else
layout = layout_set_lookup(args->argv[0]);
if (layout != -1) {
layout = layout_set_select(wl->window, layout);
server_redraw_window(wl->window);
return (CMD_RETURN_NORMAL);
if (args_has(args, 'E')) {
layout_spread_out(wp);
goto changed;
}
if (args->argc != 0) {
layoutname = args->argv[0];
if (layout_parse(wl->window, layoutname) == -1) {
cmdq_error(cmdq, "can't set layout: %s", layoutname);
return (CMD_RETURN_ERROR);
if (!args_has(args, 'o')) {
if (args->argc == 0)
layout = w->lastlayout;
else
layout = layout_set_lookup(args->argv[0]);
if (layout != -1) {
layout_set_select(w, layout);
goto changed;
}
server_redraw_window(wl->window);
}
if (args->argc != 0)
layoutname = args->argv[0];
else if (args_has(args, 'o'))
layoutname = oldlayout;
else
layoutname = NULL;
if (layoutname != NULL) {
if (layout_parse(w, layoutname) == -1) {
cmdq_error(item, "can't set layout: %s", layoutname);
goto error;
}
goto changed;
}
free(oldlayout);
return (CMD_RETURN_NORMAL);
changed:
free(oldlayout);
recalculate_sizes();
server_redraw_window(w);
notify_window("window-layout-changed", w);
return (CMD_RETURN_NORMAL);
error:
free(w->old_layout);
w->old_layout = oldlayout;
return (CMD_RETURN_ERROR);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,91 +18,203 @@
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
/*
* Select pane.
*/
enum cmd_retval cmd_select_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_select_pane_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_select_pane_entry = {
"select-pane", "selectp",
"DdeLlRt:U", 0, 0,
"[-DdeLlRU] " CMD_TARGET_PANE_USAGE,
0,
cmd_select_pane_exec
.name = "select-pane",
.alias = "selectp",
.args = { "DdegLlMmP:RT:t:UZ", 0, 0 }, /* -P and -g deprecated */
.usage = "[-DdeLlMmRUZ] [-T title] " CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_select_pane_exec
};
const struct cmd_entry cmd_last_pane_entry = {
"last-pane", "lastp",
"det:", 0, 0,
"[-de] " CMD_TARGET_WINDOW_USAGE,
0,
cmd_select_pane_exec
.name = "last-pane",
.alias = "lastp",
.args = { "det:Z", 0, 0 },
.usage = "[-deZ] " CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = 0,
.exec = cmd_select_pane_exec
};
enum cmd_retval
cmd_select_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static void
cmd_select_pane_redraw(struct window *w)
{
struct client *c;
/*
* Redraw entire window if it is bigger than the client (the
* offset may change), otherwise just draw borders.
*/
TAILQ_FOREACH(c, &clients, entry) {
if (c->session == NULL || (c->flags & CLIENT_CONTROL))
continue;
if (c->session->curw->window == w && tty_window_bigger(&c->tty))
server_redraw_client(c);
else {
if (c->session->curw->window == w)
c->flags |= CLIENT_REDRAWBORDERS;
if (session_has(c->session, w))
c->flags |= CLIENT_REDRAWSTATUS;
}
}
}
static enum cmd_retval
cmd_select_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct window_pane *wp;
struct cmd_find_state *current = &item->shared->current;
struct client *c = cmd_find_client(item, NULL, 1);
struct winlink *wl = item->target.wl;
struct window *w = wl->window;
struct session *s = item->target.s;
struct window_pane *wp = item->target.wp, *lastwp, *markedwp;
char *pane_title;
const char *style;
struct style *sy;
struct options_entry *o;
if (self->entry == &cmd_last_pane_entry || args_has(args, 'l')) {
wl = cmd_find_window(cmdq, args_get(args, 't'), NULL);
if (wl == NULL)
return (CMD_RETURN_ERROR);
if (wl->window->last == NULL) {
cmdq_error(cmdq, "no last pane");
lastwp = w->last;
if (lastwp == NULL && window_count_panes(w) == 2) {
lastwp = TAILQ_PREV(w->active, window_panes, entry);
if (lastwp == NULL)
lastwp = TAILQ_NEXT(w->active, entry);
}
if (lastwp == NULL) {
cmdq_error(item, "no last pane");
return (CMD_RETURN_ERROR);
}
if (args_has(self->args, 'e'))
wl->window->last->flags &= ~PANE_INPUTOFF;
lastwp->flags &= ~PANE_INPUTOFF;
else if (args_has(self->args, 'd'))
wl->window->last->flags |= PANE_INPUTOFF;
lastwp->flags |= PANE_INPUTOFF;
else {
server_unzoom_window(wl->window);
window_set_active_pane(wl->window, wl->window->last);
server_status_window(wl->window);
server_redraw_window_borders(wl->window);
if (window_push_zoom(w, args_has(self->args, 'Z')))
server_redraw_window(w);
window_redraw_active_switch(w, lastwp);
if (window_set_active_pane(w, lastwp, 1)) {
cmd_find_from_winlink(current, wl, 0);
cmd_select_pane_redraw(w);
}
if (window_pop_zoom(w))
server_redraw_window(w);
}
return (CMD_RETURN_NORMAL);
}
if ((wl = cmd_find_pane(cmdq, args_get(args, 't'), NULL, &wp)) == NULL)
return (CMD_RETURN_ERROR);
if (args_has(args, 'm') || args_has(args, 'M')) {
if (args_has(args, 'm') && !window_pane_visible(wp))
return (CMD_RETURN_NORMAL);
lastwp = marked_pane.wp;
server_unzoom_window(wp->window);
if (!window_pane_visible(wp)) {
cmdq_error(cmdq, "pane not visible");
return (CMD_RETURN_ERROR);
if (args_has(args, 'M') || server_is_marked(s, wl, wp))
server_clear_marked();
else
server_set_marked(s, wl, wp);
markedwp = marked_pane.wp;
if (lastwp != NULL) {
server_redraw_window_borders(lastwp->window);
server_status_window(lastwp->window);
}
if (markedwp != NULL) {
server_redraw_window_borders(markedwp->window);
server_status_window(markedwp->window);
}
return (CMD_RETURN_NORMAL);
}
if (args_has(self->args, 'L'))
if (args_has(self->args, 'P') || args_has(self->args, 'g')) {
if ((style = args_get(args, 'P')) != NULL) {
o = options_set_style(wp->options, "window-style", 0,
style);
if (o == NULL) {
cmdq_error(item, "bad style: %s", style);
return (CMD_RETURN_ERROR);
}
options_set_style(wp->options, "window-active-style", 0,
style);
wp->flags |= (PANE_REDRAW|PANE_STYLECHANGED);
}
if (args_has(self->args, 'g')) {
sy = options_get_style(wp->options, "window-style");
cmdq_print(item, "%s", style_tostring(sy));
}
return (CMD_RETURN_NORMAL);
}
if (args_has(self->args, 'L')) {
window_push_zoom(w, 1);
wp = window_pane_find_left(wp);
else if (args_has(self->args, 'R'))
window_pop_zoom(w);
} else if (args_has(self->args, 'R')) {
window_push_zoom(w, 1);
wp = window_pane_find_right(wp);
else if (args_has(self->args, 'U'))
window_pop_zoom(w);
} else if (args_has(self->args, 'U')) {
window_push_zoom(w, 1);
wp = window_pane_find_up(wp);
else if (args_has(self->args, 'D'))
window_pop_zoom(w);
} else if (args_has(self->args, 'D')) {
window_push_zoom(w, 1);
wp = window_pane_find_down(wp);
if (wp == NULL) {
cmdq_error(cmdq, "pane not found");
return (CMD_RETURN_ERROR);
window_pop_zoom(w);
}
if (wp == NULL)
return (CMD_RETURN_NORMAL);
if (args_has(self->args, 'e')) {
wp->flags &= ~PANE_INPUTOFF;
return (CMD_RETURN_NORMAL);
}
if (args_has(self->args, 'd')) {
wp->flags |= PANE_INPUTOFF;
return (CMD_RETURN_NORMAL);
}
if (args_has(self->args, 'e'))
wp->flags &= ~PANE_INPUTOFF;
else if (args_has(self->args, 'd'))
wp->flags |= PANE_INPUTOFF;
else if (window_set_active_pane(wl->window, wp)) {
server_status_window(wl->window);
server_redraw_window_borders(wl->window);
if (args_has(self->args, 'T')) {
pane_title = format_single(item, args_get(self->args, 'T'),
c, s, wl, wp);
if (screen_set_title(&wp->base, pane_title))
server_status_window(wp->window);
free(pane_title);
return (CMD_RETURN_NORMAL);
}
if (wp == w->active)
return (CMD_RETURN_NORMAL);
if (window_push_zoom(w, args_has(self->args, 'Z')))
server_redraw_window(w);
window_redraw_active_switch(w, wp);
if (window_set_active_pane(w, wp, 1)) {
cmd_find_from_winlink_pane(current, wl, wp, 0);
cmdq_insert_hook(s, item, current, "after-select-pane");
cmd_select_pane_redraw(w);
}
if (window_pop_zoom(w))
server_redraw_window(w);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,47 +26,68 @@
* Select window by index.
*/
enum cmd_retval cmd_select_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_select_window_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_select_window_entry = {
"select-window", "selectw",
"lnpTt:", 0, 0,
"[-lnpT] " CMD_TARGET_WINDOW_USAGE,
0,
cmd_select_window_exec
.name = "select-window",
.alias = "selectw",
.args = { "lnpTt:", 0, 0 },
.usage = "[-lnpT] " CMD_TARGET_WINDOW_USAGE,
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = 0,
.exec = cmd_select_window_exec
};
const struct cmd_entry cmd_next_window_entry = {
"next-window", "next",
"at:", 0, 0,
"[-a] " CMD_TARGET_SESSION_USAGE,
0,
cmd_select_window_exec
.name = "next-window",
.alias = "next",
.args = { "at:", 0, 0 },
.usage = "[-a] " CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = 0,
.exec = cmd_select_window_exec
};
const struct cmd_entry cmd_previous_window_entry = {
"previous-window", "prev",
"at:", 0, 0,
"[-a] " CMD_TARGET_SESSION_USAGE,
0,
cmd_select_window_exec
.name = "previous-window",
.alias = "prev",
.args = { "at:", 0, 0 },
.usage = "[-a] " CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = 0,
.exec = cmd_select_window_exec
};
const struct cmd_entry cmd_last_window_entry = {
"last-window", "last",
"t:", 0, 0,
CMD_TARGET_SESSION_USAGE,
0,
cmd_select_window_exec
.name = "last-window",
.alias = "last",
.args = { "t:", 0, 0 },
.usage = CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = 0,
.exec = cmd_select_window_exec
};
enum cmd_retval
cmd_select_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_select_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *wl;
struct session *s;
int next, previous, last, activity;
struct cmd_find_state *current = &item->shared->current;
struct winlink *wl = item->target.wl;
struct session *s = item->target.s;
int next, previous, last, activity;
next = self->entry == &cmd_next_window_entry;
if (args_has(self->args, 'n'))
@@ -79,46 +100,44 @@ cmd_select_window_exec(struct cmd *self, struct cmd_q *cmdq)
last = 1;
if (next || previous || last) {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
return (CMD_RETURN_ERROR);
activity = args_has(self->args, 'a');
if (next) {
if (session_next(s, activity) != 0) {
cmdq_error(cmdq, "no next window");
cmdq_error(item, "no next window");
return (CMD_RETURN_ERROR);
}
} else if (previous) {
if (session_previous(s, activity) != 0) {
cmdq_error(cmdq, "no previous window");
cmdq_error(item, "no previous window");
return (CMD_RETURN_ERROR);
}
} else {
if (session_last(s) != 0) {
cmdq_error(cmdq, "no last window");
cmdq_error(item, "no last window");
return (CMD_RETURN_ERROR);
}
}
cmd_find_from_session(current, s, 0);
server_redraw_session(s);
cmdq_insert_hook(s, item, current, "after-select-window");
} else {
wl = cmd_find_window(cmdq, args_get(args, 't'), &s);
if (wl == NULL)
return (CMD_RETURN_ERROR);
/*
* If -T and select-window is invoked on same window as
* current, switch to previous window.
*/
if (args_has(self->args, 'T') && wl == s->curw) {
if (session_last(s) != 0) {
cmdq_error(cmdq, "no last window");
cmdq_error(item, "no last window");
return (-1);
}
if (current->s == s)
cmd_find_from_session(current, s, 0);
server_redraw_session(s);
} else if (session_select(s, wl->idx) == 0)
} else if (session_select(s, wl->idx) == 0) {
cmd_find_from_session(current, s, 0);
server_redraw_session(s);
}
cmdq_insert_hook(s, item, current, "after-select-window");
}
recalculate_sizes();

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,72 +27,177 @@
* Send keys to client.
*/
enum cmd_retval cmd_send_keys_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_send_keys_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_send_keys_entry = {
"send-keys", "send",
"lRt:", 0, -1,
"[-lR] " CMD_TARGET_PANE_USAGE " key ...",
0,
cmd_send_keys_exec
.name = "send-keys",
.alias = "send",
.args = { "FHlMN:Rt:X", 0, -1 },
.usage = "[-FHlMRX] [-N repeat-count] " CMD_TARGET_PANE_USAGE
" key ...",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_send_keys_exec
};
const struct cmd_entry cmd_send_prefix_entry = {
"send-prefix", NULL,
"2t:", 0, 0,
"[-2] " CMD_TARGET_PANE_USAGE,
0,
cmd_send_keys_exec
.name = "send-prefix",
.alias = NULL,
.args = { "2t:", 0, 0 },
.usage = "[-2] " CMD_TARGET_PANE_USAGE,
.target = { 't', CMD_FIND_PANE, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_send_keys_exec
};
enum cmd_retval
cmd_send_keys_exec(struct cmd *self, struct cmd_q *cmdq)
static struct cmdq_item *
cmd_send_keys_inject_key(struct client *c, struct cmd_find_state *fs,
struct cmdq_item *item, key_code key)
{
struct args *args = self->args;
struct window_pane *wp;
struct session *s;
struct input_ctx *ictx;
const u_char *str;
int i, key;
struct session *s = fs->s;
struct winlink *wl = fs->wl;
struct window_pane *wp = fs->wp;
struct window_mode_entry *wme;
struct key_table *table;
struct key_binding *bd;
if (cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp) == NULL)
return (CMD_RETURN_ERROR);
wme = TAILQ_FIRST(&fs->wp->modes);
if (wme == NULL || wme->mode->key_table == NULL) {
if (options_get_number(fs->wp->window->options, "xterm-keys"))
key |= KEYC_XTERM;
if (window_pane_key(wp, item->client, s, wl, key, NULL) != 0)
return (NULL);
return (item);
}
table = key_bindings_get_table(wme->mode->key_table(wme), 1);
bd = key_bindings_get(table, key & ~KEYC_XTERM);
if (bd != NULL) {
table->references++;
item = key_bindings_dispatch(bd, item, c, NULL, &item->target);
key_bindings_unref_table(table);
}
return (item);
}
static struct cmdq_item *
cmd_send_keys_inject_string(struct client *c, struct cmd_find_state *fs,
struct cmdq_item *item, struct args *args, int i)
{
const char *s = args->argv[i];
struct cmdq_item *new_item;
struct utf8_data *ud, *uc;
wchar_t wc;
key_code key;
char *endptr;
long n;
int literal;
if (args_has(args, 'H')) {
n = strtol(s, &endptr, 16);
if (*s =='\0' || n < 0 || n > 0xff || *endptr != '\0')
return (item);
return (cmd_send_keys_inject_key(c, fs, item, KEYC_LITERAL|n));
}
literal = args_has(args, 'l');
if (!literal) {
key = key_string_lookup_string(s);
if (key != KEYC_NONE && key != KEYC_UNKNOWN) {
new_item = cmd_send_keys_inject_key(c, fs, item, key);
if (new_item != NULL)
return (new_item);
}
literal = 1;
}
if (literal) {
ud = utf8_fromcstr(s);
for (uc = ud; uc->size != 0; uc++) {
if (utf8_combine(uc, &wc) != UTF8_DONE)
continue;
item = cmd_send_keys_inject_key(c, fs, item, wc);
}
free(ud);
}
return (item);
}
static enum cmd_retval
cmd_send_keys_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c = cmd_find_client(item, NULL, 1);
struct cmd_find_state *fs = &item->target;
struct window_pane *wp = item->target.wp;
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct mouse_event *m = &item->shared->mouse;
struct window_mode_entry *wme = TAILQ_FIRST(&wp->modes);
int i;
key_code key;
u_int np = 1;
char *cause = NULL;
if (args_has(args, 'N')) {
np = args_strtonum(args, 'N', 1, UINT_MAX, &cause);
if (cause != NULL) {
cmdq_error(item, "repeat count %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
if (wme != NULL && (args_has(args, 'X') || args->argc == 0)) {
if (wme == NULL || wme->mode->command == NULL) {
cmdq_error(item, "not in a mode");
return (CMD_RETURN_ERROR);
}
wme->prefix = np;
}
}
if (args_has(args, 'X')) {
if (wme == NULL || wme->mode->command == NULL) {
cmdq_error(item, "not in a mode");
return (CMD_RETURN_ERROR);
}
if (!m->valid)
m = NULL;
wme->mode->command(wme, c, s, wl, args, m);
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 'M')) {
wp = cmd_mouse_pane(m, &s, NULL);
if (wp == NULL) {
cmdq_error(item, "no mouse target");
return (CMD_RETURN_ERROR);
}
window_pane_key(wp, item->client, s, wl, m->key, m);
return (CMD_RETURN_NORMAL);
}
if (self->entry == &cmd_send_prefix_entry) {
if (args_has(args, '2'))
key = options_get_number(&s->options, "prefix2");
key = options_get_number(s->options, "prefix2");
else
key = options_get_number(&s->options, "prefix");
window_pane_key(wp, s, key);
key = options_get_number(s->options, "prefix");
cmd_send_keys_inject_key(c, fs, item, key);
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 'R')) {
ictx = &wp->ictx;
memcpy(&ictx->cell, &grid_default_cell, sizeof ictx->cell);
memcpy(&ictx->old_cell, &ictx->cell, sizeof ictx->old_cell);
ictx->old_cx = 0;
ictx->old_cy = 0;
if (wp->mode == NULL)
screen_write_start(&ictx->ctx, wp, &wp->base);
else
screen_write_start(&ictx->ctx, NULL, &wp->base);
screen_write_reset(&ictx->ctx);
screen_write_stop(&ictx->ctx);
window_pane_reset_palette(wp);
input_reset(wp, 1);
}
for (i = 0; i < args->argc; i++) {
str = args->argv[i];
if (!args_has(args, 'l') &&
(key = key_string_lookup_string(str)) != KEYC_NONE) {
window_pane_key(wp, s, key);
} else {
for (; *str != '\0'; str++)
window_pane_key(wp, s, *str);
}
for (; np != 0; np--) {
for (i = 0; i < args->argc; i++)
item = cmd_send_keys_inject_string(c, fs, item, args, i);
}
return (CMD_RETURN_NORMAL);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -24,92 +24,97 @@
#include "tmux.h"
/*
* Add, set, or append to a paste buffer.
* Add, set, append to or delete a paste buffer.
*/
enum cmd_retval cmd_set_buffer_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_set_buffer_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_set_buffer_entry = {
"set-buffer", "setb",
"ab:n:", 0, 1,
"[-a] " CMD_BUFFER_USAGE " [-n new-buffer-name] data",
0,
cmd_set_buffer_exec
.name = "set-buffer",
.alias = "setb",
.args = { "ab:n:", 0, 1 },
.usage = "[-a] " CMD_BUFFER_USAGE " [-n new-buffer-name] data",
.flags = CMD_AFTERHOOK,
.exec = cmd_set_buffer_exec
};
enum cmd_retval
cmd_set_buffer_exec(struct cmd *self, struct cmd_q *cmdq)
const struct cmd_entry cmd_delete_buffer_entry = {
.name = "delete-buffer",
.alias = "deleteb",
.args = { "b:", 0, 0 },
.usage = CMD_BUFFER_USAGE,
.flags = CMD_AFTERHOOK,
.exec = cmd_set_buffer_exec
};
static enum cmd_retval
cmd_set_buffer_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct paste_buffer *pb;
char *pdata, *cause;
const char *bufname;
size_t psize, newsize;
char *bufdata, *cause;
const char *bufname, *olddata;
size_t bufsize, newsize;
bufname = NULL;
bufname = args_get(args, 'b');
if (bufname == NULL)
pb = NULL;
else
pb = paste_get_name(bufname);
if (args_has(args, 'n')) {
if (args->argc > 0) {
cmdq_error(cmdq, "don't provide data with n flag");
if (self->entry == &cmd_delete_buffer_entry) {
if (pb == NULL)
pb = paste_get_top(&bufname);
if (pb == NULL) {
cmdq_error(item, "no buffer");
return (CMD_RETURN_ERROR);
}
paste_free(pb);
return (CMD_RETURN_NORMAL);
}
if (args_has(args, 'b'))
bufname = args_get(args, 'b');
if (bufname == NULL) {
pb = paste_get_top();
if (pb == NULL) {
cmdq_error(cmdq, "no buffer");
return (CMD_RETURN_ERROR);
}
bufname = pb->name;
if (args_has(args, 'n')) {
if (pb == NULL)
pb = paste_get_top(&bufname);
if (pb == NULL) {
cmdq_error(item, "no buffer");
return (CMD_RETURN_ERROR);
}
if (paste_rename(bufname, args_get(args, 'n'), &cause) != 0) {
cmdq_error(cmdq, "%s", cause);
cmdq_error(item, "%s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
}
if (args->argc != 1) {
cmdq_error(cmdq, "no data specified");
cmdq_error(item, "no data specified");
return (CMD_RETURN_ERROR);
}
psize = 0;
pdata = NULL;
pb = NULL;
if ((newsize = strlen(args->argv[0])) == 0)
return (CMD_RETURN_NORMAL);
if (args_has(args, 'b')) {
bufname = args_get(args, 'b');
pb = paste_get_name(bufname);
} else if (args_has(args, 'a')) {
pb = paste_get_top();
if (pb != NULL)
bufname = pb->name;
}
bufsize = 0;
bufdata = NULL;
if (args_has(args, 'a') && pb != NULL) {
psize = pb->size;
pdata = xmalloc(psize);
memcpy(pdata, pb->data, psize);
olddata = paste_buffer_data(pb, &bufsize);
bufdata = xmalloc(bufsize);
memcpy(bufdata, olddata, bufsize);
}
pdata = xrealloc(pdata, psize + newsize);
memcpy(pdata + psize, args->argv[0], newsize);
psize += newsize;
bufdata = xrealloc(bufdata, bufsize + newsize);
memcpy(bufdata + bufsize, args->argv[0], newsize);
bufsize += newsize;
if (paste_set(pdata, psize, bufname, &cause) != 0) {
cmdq_error(cmdq, "%s", cause);
free(pdata);
if (paste_set(bufdata, bufsize, bufname, &cause) != 0) {
cmdq_error(item, "%s", cause);
free(bufdata);
free(cause);
return (CMD_RETURN_ERROR);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,31 +27,36 @@
* Set an environment variable.
*/
enum cmd_retval cmd_set_environment_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_set_environment_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_set_environment_entry = {
"set-environment", "setenv",
"grt:u", 1, 2,
"[-gru] " CMD_TARGET_SESSION_USAGE " name [value]",
0,
cmd_set_environment_exec
.name = "set-environment",
.alias = "setenv",
.args = { "grt:u", 1, 2 },
.usage = "[-gru] " CMD_TARGET_SESSION_USAGE " name [value]",
.target = { 't', CMD_FIND_SESSION, CMD_FIND_CANFAIL },
.flags = CMD_AFTERHOOK,
.exec = cmd_set_environment_exec
};
enum cmd_retval
cmd_set_environment_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_set_environment_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
struct environ *env;
const char *name, *value;
const char *name, *value, *target;
name = args->argv[0];
if (*name == '\0') {
cmdq_error(cmdq, "empty variable name");
cmdq_error(item, "empty variable name");
return (CMD_RETURN_ERROR);
}
if (strchr(name, '=') != NULL) {
cmdq_error(cmdq, "variable name contains =");
cmdq_error(item, "variable name contains =");
return (CMD_RETURN_ERROR);
}
@@ -61,31 +66,37 @@ cmd_set_environment_exec(struct cmd *self, struct cmd_q *cmdq)
value = args->argv[1];
if (args_has(self->args, 'g'))
env = &global_environ;
env = global_environ;
else {
if ((s = cmd_find_session(cmdq, args_get(args, 't'), 0)) == NULL)
if (item->target.s == NULL) {
target = args_get(args, 't');
if (target != NULL)
cmdq_error(item, "no such session: %s", target);
else
cmdq_error(item, "no current session");
return (CMD_RETURN_ERROR);
env = &s->environ;
}
env = item->target.s->environ;
}
if (args_has(self->args, 'u')) {
if (value != NULL) {
cmdq_error(cmdq, "can't specify a value with -u");
cmdq_error(item, "can't specify a value with -u");
return (CMD_RETURN_ERROR);
}
environ_unset(env, name);
} else if (args_has(self->args, 'r')) {
if (value != NULL) {
cmdq_error(cmdq, "can't specify a value with -r");
cmdq_error(item, "can't specify a value with -r");
return (CMD_RETURN_ERROR);
}
environ_set(env, name, NULL);
environ_clear(env, name);
} else {
if (value == NULL) {
cmdq_error(cmdq, "no value specified");
cmdq_error(item, "no value specified");
return (CMD_RETURN_ERROR);
}
environ_set(env, name, value);
environ_set(env, name, "%s", value);
}
return (CMD_RETURN_NORMAL);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -18,6 +18,7 @@
#include <sys/types.h>
#include <fnmatch.h>
#include <stdlib.h>
#include <string.h>
@@ -27,402 +28,337 @@
* Set an option.
*/
enum cmd_retval cmd_set_option_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_set_option_exec(struct cmd *, struct cmdq_item *);
enum cmd_retval cmd_set_option_user(struct cmd *, struct cmd_q *,
const char *, const char *);
int cmd_set_option_unset(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
int cmd_set_option_set(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_string(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_number(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_key(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_colour(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_attributes(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_flag(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_choice(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
struct options_entry *cmd_set_option_style(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *,
const char *);
static int cmd_set_option_set(struct cmd *, struct cmdq_item *,
struct options *, struct options_entry *, const char *);
static int cmd_set_option_flag(struct cmdq_item *,
const struct options_table_entry *, struct options *,
const char *);
static int cmd_set_option_choice(struct cmdq_item *,
const struct options_table_entry *, struct options *,
const char *);
const struct cmd_entry cmd_set_option_entry = {
"set-option", "set",
"agoqst:uw", 1, 2,
"[-agosquw] [-t target-session|target-window] option [value]",
0,
cmd_set_option_exec
.name = "set-option",
.alias = "set",
.args = { "aFgopqst:uw", 1, 2 },
.usage = "[-aFgopqsuw] " CMD_TARGET_PANE_USAGE " option [value]",
.target = { 't', CMD_FIND_PANE, CMD_FIND_CANFAIL },
.flags = CMD_AFTERHOOK,
.exec = cmd_set_option_exec
};
const struct cmd_entry cmd_set_window_option_entry = {
"set-window-option", "setw",
"agoqt:u", 1, 2,
"[-agoqu] " CMD_TARGET_WINDOW_USAGE " option [value]",
0,
cmd_set_option_exec
.name = "set-window-option",
.alias = "setw",
.args = { "aFgoqt:u", 1, 2 },
.usage = "[-aFgoqu] " CMD_TARGET_WINDOW_USAGE " option [value]",
.target = { 't', CMD_FIND_WINDOW, CMD_FIND_CANFAIL },
.flags = CMD_AFTERHOOK,
.exec = cmd_set_option_exec
};
enum cmd_retval
cmd_set_option_exec(struct cmd *self, struct cmd_q *cmdq)
const struct cmd_entry cmd_set_hook_entry = {
.name = "set-hook",
.alias = NULL,
.args = { "agRt:u", 1, 2 },
.usage = "[-agRu] " CMD_TARGET_SESSION_USAGE " hook [command]",
.target = { 't', CMD_FIND_SESSION, CMD_FIND_CANFAIL },
.flags = CMD_AFTERHOOK,
.exec = cmd_set_option_exec
};
static enum cmd_retval
cmd_set_option_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
const struct options_table_entry *table, *oe;
struct session *s;
struct winlink *wl;
struct client *c;
struct options *oo;
struct window *w;
const char *optstr, *valstr;
u_int i;
struct args *args = self->args;
int append = args_has(args, 'a');
struct cmd_find_state *fs = &item->target;
struct client *c, *loop;
struct session *s = fs->s;
struct winlink *wl = fs->wl;
struct window *w;
struct window_pane *wp;
struct options *oo;
struct options_entry *parent, *o;
char *name, *argument, *value = NULL, *cause;
int window, idx, already, error, ambiguous;
int scope;
struct style *sy;
/* Get the option name and value. */
optstr = args->argv[0];
if (*optstr == '\0') {
cmdq_error(cmdq, "invalid option");
return (CMD_RETURN_ERROR);
}
if (args->argc < 2)
valstr = NULL;
else
valstr = args->argv[1];
window = (self->entry == &cmd_set_window_option_entry);
/* Is this a user option? */
if (*optstr == '@')
return (cmd_set_option_user(self, cmdq, optstr, valstr));
/* Expand argument. */
c = cmd_find_client(item, NULL, 1);
argument = format_single(item, args->argv[0], c, s, wl, NULL);
/* Find the option entry, try each table. */
table = oe = NULL;
if (options_table_find(optstr, &table, &oe) != 0) {
cmdq_error(cmdq, "ambiguous option: %s", optstr);
return (CMD_RETURN_ERROR);
}
if (oe == NULL) {
if (!args_has(args, 'q')) {
cmdq_error(cmdq, "unknown option: %s", optstr);
return (CMD_RETURN_ERROR);
}
/* If set-hook -R, fire the hook straight away. */
if (self->entry == &cmd_set_hook_entry && args_has(args, 'R')) {
notify_hook(item, argument);
free(argument);
return (CMD_RETURN_NORMAL);
}
/* Work out the tree from the table. */
if (table == server_options_table)
oo = &global_options;
else if (table == window_options_table) {
if (args_has(self->args, 'g'))
oo = &global_w_options;
else {
wl = cmd_find_window(cmdq, args_get(args, 't'), NULL);
if (wl == NULL) {
cmdq_error(cmdq,
"couldn't set '%s'%s", optstr,
(!args_has(args, 't') && !args_has(args,
'g')) ? " need target window or -g" : "");
return (CMD_RETURN_ERROR);
}
oo = &wl->window->options;
}
} else if (table == session_options_table) {
if (args_has(self->args, 'g'))
oo = &global_s_options;
else {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL) {
cmdq_error(cmdq,
"couldn't set '%s'%s", optstr,
(!args_has(args, 't') && !args_has(args,
'g')) ? " need target session or -g" : "");
return (CMD_RETURN_ERROR);
}
oo = &s->options;
}
} else {
cmdq_error(cmdq, "unknown table");
return (CMD_RETURN_ERROR);
/* Parse option name and index. */
name = options_match(argument, &idx, &ambiguous);
if (name == NULL) {
if (args_has(args, 'q'))
goto out;
if (ambiguous)
cmdq_error(item, "ambiguous option: %s", argument);
else
cmdq_error(item, "invalid option: %s", argument);
goto fail;
}
if (args->argc < 2)
value = NULL;
else if (args_has(args, 'F'))
value = format_single(item, args->argv[1], c, s, wl, NULL);
else
value = xstrdup(args->argv[1]);
/* Get the scope and table for the option .*/
scope = options_scope_from_name(args, window, name, fs, &oo, &cause);
if (scope == OPTIONS_TABLE_NONE) {
if (args_has(args, 'q'))
goto out;
cmdq_error(item, "%s", cause);
free(cause);
goto fail;
}
o = options_get_only(oo, name);
parent = options_get(oo, name);
/* Check that array options and indexes match up. */
if (idx != -1 && (*name == '@' || !options_isarray(parent))) {
cmdq_error(item, "not an array: %s", argument);
goto fail;
}
/* Unset or set the option. */
/* With -o, check this option is not already set. */
if (!args_has(args, 'u') && args_has(args, 'o')) {
if (idx == -1)
already = (o != NULL);
else {
if (o == NULL)
already = 0;
else
already = (options_array_get(o, idx) != NULL);
}
if (already) {
if (args_has(args, 'q'))
goto out;
cmdq_error(item, "already set: %s", argument);
goto fail;
}
}
/* Change the option. */
if (args_has(args, 'u')) {
if (cmd_set_option_unset(self, cmdq, oe, oo, valstr) != 0)
return (CMD_RETURN_ERROR);
} else {
if (args_has(args, 'o') && options_find1(oo, optstr) != NULL) {
if (!args_has(args, 'q')) {
cmdq_error(cmdq, "already set: %s", optstr);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
if (o == NULL)
goto out;
if (idx == -1) {
if (*name == '@')
options_remove(o);
else if (oo == global_options ||
oo == global_s_options ||
oo == global_w_options)
options_default(oo, options_table_entry(o));
else
options_remove(o);
} else if (options_array_set(o, idx, NULL, 0, &cause) != 0) {
cmdq_error(item, "%s", cause);
free(cause);
goto fail;
}
} else if (*name == '@') {
if (value == NULL) {
cmdq_error(item, "empty value");
goto fail;
}
options_set_string(oo, name, append, "%s", value);
} else if (idx == -1 && !options_isarray(parent)) {
error = cmd_set_option_set(self, item, oo, parent, value);
if (error != 0)
goto fail;
} else {
if (value == NULL) {
cmdq_error(item, "empty value");
goto fail;
}
if (o == NULL)
o = options_empty(oo, options_table_entry(parent));
if (idx == -1) {
if (!append)
options_array_clear(o);
if (options_array_assign(o, value, &cause) != 0) {
cmdq_error(item, "%s", cause);
free(cause);
goto fail;
}
} else if (options_array_set(o, idx, value, append,
&cause) != 0) {
cmdq_error(item, "%s", cause);
free(cause);
goto fail;
}
if (cmd_set_option_set(self, cmdq, oe, oo, valstr) != 0)
return (CMD_RETURN_ERROR);
}
/* Start or stop timers when automatic-rename changed. */
if (strcmp(oe->name, "automatic-rename") == 0) {
for (i = 0; i < ARRAY_LENGTH(&windows); i++) {
if ((w = ARRAY_ITEM(&windows, i)) == NULL)
/* Update timers and so on for various options. */
if (strcmp(name, "automatic-rename") == 0) {
RB_FOREACH(w, windows, &windows) {
if (w->active == NULL)
continue;
if (options_get_number(&w->options, "automatic-rename"))
queue_window_name(w);
else if (event_initialized(&w->name_timer))
evtimer_del(&w->name_timer);
if (options_get_number(w->options, "automatic-rename"))
w->active->flags |= PANE_CHANGED;
}
}
if (strcmp(name, "key-table") == 0) {
TAILQ_FOREACH(loop, &clients, entry)
server_client_set_key_table(loop, NULL);
}
if (strcmp(name, "user-keys") == 0) {
TAILQ_FOREACH(loop, &clients, entry) {
if (loop->tty.flags & TTY_OPENED)
tty_keys_build(&loop->tty);
}
}
if (strcmp(name, "status-fg") == 0 || strcmp(name, "status-bg") == 0) {
sy = options_get_style(oo, "status-style");
sy->gc.fg = options_get_number(oo, "status-fg");
sy->gc.bg = options_get_number(oo, "status-bg");
}
if (strcmp(name, "status-style") == 0) {
sy = options_get_style(oo, "status-style");
options_set_number(oo, "status-fg", sy->gc.fg);
options_set_number(oo, "status-bg", sy->gc.bg);
}
if (strcmp(name, "status") == 0 ||
strcmp(name, "status-interval") == 0)
status_timer_start_all();
if (strcmp(name, "monitor-silence") == 0)
alerts_reset_all();
if (strcmp(name, "window-style") == 0 ||
strcmp(name, "window-active-style") == 0) {
RB_FOREACH(wp, window_pane_tree, &all_window_panes)
wp->flags |= PANE_STYLECHANGED;
}
if (strcmp(name, "pane-border-status") == 0) {
RB_FOREACH(w, windows, &windows)
layout_fix_panes(w);
}
RB_FOREACH(s, sessions, &sessions)
status_update_cache(s);
/* Update sizes and redraw. May not need it but meh. */
/*
* Update sizes and redraw. May not always be necessary but do it
* anyway.
*/
recalculate_sizes();
for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
c = ARRAY_ITEM(&clients, i);
if (c != NULL && c->session != NULL)
server_redraw_client(c);
TAILQ_FOREACH(loop, &clients, entry) {
if (loop->session != NULL)
server_redraw_client(loop);
}
out:
free(argument);
free(value);
free(name);
return (CMD_RETURN_NORMAL);
fail:
free(argument);
free(value);
free(name);
return (CMD_RETURN_ERROR);
}
/* Set user option. */
enum cmd_retval
cmd_set_option_user(struct cmd *self, struct cmd_q *cmdq, const char *optstr,
const char *valstr)
static int
cmd_set_option_set(struct cmd *self, struct cmdq_item *item, struct options *oo,
struct options_entry *parent, const char *value)
{
struct args *args = self->args;
struct session *s;
struct winlink *wl;
struct options *oo;
const struct options_table_entry *oe;
struct args *args = self->args;
int append = args_has(args, 'a');
struct options_entry *o;
long long number;
const char *errstr, *new;
char *old;
key_code key;
if (args_has(args, 's'))
oo = &global_options;
else if (args_has(self->args, 'w') ||
self->entry == &cmd_set_window_option_entry) {
if (args_has(self->args, 'g'))
oo = &global_w_options;
else {
wl = cmd_find_window(cmdq, args_get(args, 't'), NULL);
if (wl == NULL)
return (CMD_RETURN_ERROR);
oo = &wl->window->options;
}
} else {
if (args_has(self->args, 'g'))
oo = &global_s_options;
else {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
return (CMD_RETURN_ERROR);
oo = &s->options;
}
}
if (args_has(args, 'u')) {
if (options_find1(oo, optstr) == NULL) {
if (!args_has(args, 'q')) {
cmdq_error(cmdq, "unknown option: %s", optstr);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
}
if (valstr != NULL) {
cmdq_error(cmdq, "value passed to unset option: %s",
optstr);
return (CMD_RETURN_ERROR);
}
options_remove(oo, optstr);
} else {
if (valstr == NULL) {
cmdq_error(cmdq, "empty value");
return (CMD_RETURN_ERROR);
}
if (args_has(args, 'o') && options_find1(oo, optstr) != NULL) {
if (!args_has(args, 'q')) {
cmdq_error(cmdq, "already set: %s", optstr);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
}
options_set_string(oo, optstr, "%s", valstr);
}
return (CMD_RETURN_NORMAL);
}
/* Unset an option. */
int
cmd_set_option_unset(struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
struct args *args = self->args;
if (args_has(args, 'g')) {
cmdq_error(cmdq, "can't unset global option: %s", oe->name);
return (-1);
}
if (value != NULL) {
cmdq_error(cmdq, "value passed to unset option: %s", oe->name);
oe = options_table_entry(parent);
if (value == NULL &&
oe->type != OPTIONS_TABLE_FLAG &&
oe->type != OPTIONS_TABLE_CHOICE) {
cmdq_error(item, "empty value");
return (-1);
}
options_remove(oo, oe->name);
return (0);
}
/* Set an option. */
int
cmd_set_option_set(struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
struct options_entry *o;
if (oe->type != OPTIONS_TABLE_FLAG && value == NULL) {
cmdq_error(cmdq, "empty value");
return (-1);
}
o = NULL;
switch (oe->type) {
case OPTIONS_TABLE_STRING:
o = cmd_set_option_string(self, cmdq, oe, oo, value);
break;
old = xstrdup(options_get_string(oo, oe->name));
options_set_string(oo, oe->name, append, "%s", value);
new = options_get_string(oo, oe->name);
if (oe->pattern != NULL && fnmatch(oe->pattern, new, 0) != 0) {
options_set_string(oo, oe->name, 0, "%s", old);
free(old);
cmdq_error(item, "value is invalid: %s", value);
return (-1);
}
free(old);
return (0);
case OPTIONS_TABLE_NUMBER:
o = cmd_set_option_number(self, cmdq, oe, oo, value);
break;
number = strtonum(value, oe->minimum, oe->maximum, &errstr);
if (errstr != NULL) {
cmdq_error(item, "value is %s: %s", errstr, value);
return (-1);
}
options_set_number(oo, oe->name, number);
return (0);
case OPTIONS_TABLE_KEY:
o = cmd_set_option_key(self, cmdq, oe, oo, value);
break;
key = key_string_lookup_string(value);
if (key == KEYC_UNKNOWN) {
cmdq_error(item, "bad key: %s", value);
return (-1);
}
options_set_number(oo, oe->name, key);
return (0);
case OPTIONS_TABLE_COLOUR:
o = cmd_set_option_colour(self, cmdq, oe, oo, value);
if (o != NULL)
style_update_new(oo, o->name, oe->style);
break;
case OPTIONS_TABLE_ATTRIBUTES:
o = cmd_set_option_attributes(self, cmdq, oe, oo, value);
if (o != NULL)
style_update_new(oo, o->name, oe->style);
break;
if ((number = colour_fromstring(value)) == -1) {
cmdq_error(item, "bad colour: %s", value);
return (-1);
}
options_set_number(oo, oe->name, number);
return (0);
case OPTIONS_TABLE_FLAG:
o = cmd_set_option_flag(self, cmdq, oe, oo, value);
break;
return (cmd_set_option_flag(item, oe, oo, value));
case OPTIONS_TABLE_CHOICE:
o = cmd_set_option_choice(self, cmdq, oe, oo, value);
break;
return (cmd_set_option_choice(item, oe, oo, value));
case OPTIONS_TABLE_STYLE:
o = cmd_set_option_style(self, cmdq, oe, oo, value);
o = options_set_style(oo, oe->name, append, value);
if (o == NULL) {
cmdq_error(item, "bad style: %s", value);
return (-1);
}
return (0);
case OPTIONS_TABLE_COMMAND:
break;
}
if (o == NULL)
return (-1);
return (0);
return (-1);
}
/* Set a string option. */
struct options_entry *
cmd_set_option_string(struct cmd *self, unused struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
struct args *args = self->args;
struct options_entry *o;
char *oldval, *newval;
if (args_has(args, 'a')) {
oldval = options_get_string(oo, oe->name);
xasprintf(&newval, "%s%s", oldval, value);
} else
newval = xstrdup(value);
o = options_set_string(oo, oe->name, "%s", newval);
free(newval);
return (o);
}
/* Set a number option. */
struct options_entry *
cmd_set_option_number(unused struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
long long ll;
const char *errstr;
ll = strtonum(value, oe->minimum, oe->maximum, &errstr);
if (errstr != NULL) {
cmdq_error(cmdq, "value is %s: %s", errstr, value);
return (NULL);
}
return (options_set_number(oo, oe->name, ll));
}
/* Set a key option. */
struct options_entry *
cmd_set_option_key(unused struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
int key;
if ((key = key_string_lookup_string(value)) == KEYC_NONE) {
cmdq_error(cmdq, "bad key: %s", value);
return (NULL);
}
return (options_set_number(oo, oe->name, key));
}
/* Set a colour option. */
struct options_entry *
cmd_set_option_colour(unused struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
int colour;
if ((colour = colour_fromstring(value)) == -1) {
cmdq_error(cmdq, "bad colour: %s", value);
return (NULL);
}
return (options_set_number(oo, oe->name, colour));
}
/* Set an attributes option. */
struct options_entry *
cmd_set_option_attributes(unused struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
int attr;
if ((attr = attributes_fromstring(value)) == -1) {
cmdq_error(cmdq, "bad attributes: %s", value);
return (NULL);
}
return (options_set_number(oo, oe->name, attr));
}
/* Set a flag option. */
struct options_entry *
cmd_set_option_flag(unused struct cmd *self, struct cmd_q *cmdq,
static int
cmd_set_option_flag(struct cmdq_item *item,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
@@ -430,69 +366,46 @@ cmd_set_option_flag(unused struct cmd *self, struct cmd_q *cmdq,
if (value == NULL || *value == '\0')
flag = !options_get_number(oo, oe->name);
else if (strcmp(value, "1") == 0 ||
strcasecmp(value, "on") == 0 ||
strcasecmp(value, "yes") == 0)
flag = 1;
else if (strcmp(value, "0") == 0 ||
strcasecmp(value, "off") == 0 ||
strcasecmp(value, "no") == 0)
flag = 0;
else {
if ((value[0] == '1' && value[1] == '\0') ||
strcasecmp(value, "on") == 0 ||
strcasecmp(value, "yes") == 0)
flag = 1;
else if ((value[0] == '0' && value[1] == '\0') ||
strcasecmp(value, "off") == 0 ||
strcasecmp(value, "no") == 0)
flag = 0;
else {
cmdq_error(cmdq, "bad value: %s", value);
return (NULL);
}
cmdq_error(item, "bad value: %s", value);
return (-1);
}
return (options_set_number(oo, oe->name, flag));
options_set_number(oo, oe->name, flag);
return (0);
}
/* Set a choice option. */
struct options_entry *
cmd_set_option_choice(unused struct cmd *self, struct cmd_q *cmdq,
static int
cmd_set_option_choice(struct cmdq_item *item,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
const char **choicep;
const char **cp;
int n, choice = -1;
n = 0;
for (choicep = oe->choices; *choicep != NULL; choicep++) {
n++;
if (strncmp(*choicep, value, strlen(value)) != 0)
continue;
if (choice != -1) {
cmdq_error(cmdq, "ambiguous value: %s", value);
return (NULL);
if (value == NULL) {
choice = options_get_number(oo, oe->name);
if (choice < 2)
choice = !choice;
} else {
n = 0;
for (cp = oe->choices; *cp != NULL; cp++) {
if (strcmp(*cp, value) == 0)
choice = n;
n++;
}
if (choice == -1) {
cmdq_error(item, "unknown value: %s", value);
return (-1);
}
choice = n - 1;
}
if (choice == -1) {
cmdq_error(cmdq, "unknown value: %s", value);
return (NULL);
}
return (options_set_number(oo, oe->name, choice));
}
/* Set a style option. */
struct options_entry *
cmd_set_option_style(struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *oe, struct options *oo,
const char *value)
{
struct args *args = self->args;
struct options_entry *o;
int append;
append = args_has(args, 'a');
if ((o = options_set_style(oo, oe->name, value, append)) == NULL) {
cmdq_error(cmdq, "bad style: %s", value);
return (NULL);
}
style_update_old(oo, oe->name, &o->style);
return (o);
options_set_number(oo, oe->name, choice);
return (0);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,51 +27,110 @@
* Show environment.
*/
enum cmd_retval cmd_show_environment_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_show_environment_exec(struct cmd *,
struct cmdq_item *);
static char *cmd_show_environment_escape(struct environ_entry *);
static void cmd_show_environment_print(struct cmd *, struct cmdq_item *,
struct environ_entry *);
const struct cmd_entry cmd_show_environment_entry = {
"show-environment", "showenv",
"gt:", 0, 1,
"[-g] " CMD_TARGET_SESSION_USAGE " [name]",
0,
cmd_show_environment_exec
.name = "show-environment",
.alias = "showenv",
.args = { "gst:", 0, 1 },
.usage = "[-gs] " CMD_TARGET_SESSION_USAGE " [name]",
.target = { 't', CMD_FIND_SESSION, CMD_FIND_CANFAIL },
.flags = CMD_AFTERHOOK,
.exec = cmd_show_environment_exec
};
enum cmd_retval
cmd_show_environment_exec(struct cmd *self, struct cmd_q *cmdq)
static char *
cmd_show_environment_escape(struct environ_entry *envent)
{
const char *value = envent->value;
char c, *out, *ret;
out = ret = xmalloc(strlen(value) * 2 + 1); /* at most twice the size */
while ((c = *value++) != '\0') {
/* POSIX interprets $ ` " and \ in double quotes. */
if (c == '$' || c == '`' || c == '"' || c == '\\')
*out++ = '\\';
*out++ = c;
}
*out = '\0';
return (ret);
}
static void
cmd_show_environment_print(struct cmd *self, struct cmdq_item *item,
struct environ_entry *envent)
{
char *escaped;
if (!args_has(self->args, 's')) {
if (envent->value != NULL)
cmdq_print(item, "%s=%s", envent->name, envent->value);
else
cmdq_print(item, "-%s", envent->name);
return;
}
if (envent->value != NULL) {
escaped = cmd_show_environment_escape(envent);
cmdq_print(item, "%s=\"%s\"; export %s;", envent->name, escaped,
envent->name);
free(escaped);
} else
cmdq_print(item, "unset %s;", envent->name);
}
static enum cmd_retval
cmd_show_environment_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
struct environ *env;
struct environ_entry *envent;
const char *target;
if ((target = args_get(args, 't')) != NULL) {
if (item->target.s == NULL) {
cmdq_error(item, "no such session: %s", target);
return (CMD_RETURN_ERROR);
}
}
if (args_has(self->args, 'g'))
env = &global_environ;
env = global_environ;
else {
if ((s = cmd_find_session(cmdq, args_get(args, 't'), 0)) == NULL)
if (item->target.s == NULL) {
target = args_get(args, 't');
if (target != NULL)
cmdq_error(item, "no such session: %s", target);
else
cmdq_error(item, "no current session");
return (CMD_RETURN_ERROR);
env = &s->environ;
}
env = item->target.s->environ;
}
if (args->argc != 0) {
envent = environ_find(env, args->argv[0]);
if (envent == NULL) {
cmdq_error(cmdq, "unknown variable: %s", args->argv[0]);
cmdq_error(item, "unknown variable: %s", args->argv[0]);
return (CMD_RETURN_ERROR);
}
if (envent->value != NULL)
cmdq_print(cmdq, "%s=%s", envent->name, envent->value);
else
cmdq_print(cmdq, "-%s", envent->name);
cmd_show_environment_print(self, item, envent);
return (CMD_RETURN_NORMAL);
}
RB_FOREACH(envent, environ, env) {
if (envent->value != NULL)
cmdq_print(cmdq, "%s=%s", envent->name, envent->value);
else
cmdq_print(cmdq, "-%s", envent->name);
envent = environ_first(env);
while (envent != NULL) {
cmd_show_environment_print(self, item, envent);
envent = environ_next(envent);
}
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -28,140 +28,72 @@
* Show client message log.
*/
enum cmd_retval cmd_show_messages_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_show_messages_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_show_messages_entry = {
"show-messages", "showmsgs",
"IJTt:", 0, 0,
"[-IJT] " CMD_TARGET_CLIENT_USAGE,
0,
cmd_show_messages_exec
.name = "show-messages",
.alias = "showmsgs",
.args = { "JTt:", 0, 0 },
.usage = "[-JT] " CMD_TARGET_CLIENT_USAGE,
.flags = CMD_AFTERHOOK,
.exec = cmd_show_messages_exec
};
const struct cmd_entry cmd_server_info_entry = {
"server-info", "info",
"", 0, 0,
"",
0,
cmd_show_messages_exec
};
static int cmd_show_messages_terminals(struct cmdq_item *, int);
void cmd_show_messages_server(struct cmd_q *);
void cmd_show_messages_terminals(struct cmd_q *);
void cmd_show_messages_jobs(struct cmd_q *);
void
cmd_show_messages_server(struct cmd_q *cmdq)
static int
cmd_show_messages_terminals(struct cmdq_item *item, int blank)
{
char *tim;
tim = ctime(&start_time);
*strchr(tim, '\n') = '\0';
cmdq_print(cmdq, "started %s", tim);
cmdq_print(cmdq, "socket path %s", socket_path);
cmdq_print(cmdq, "debug level %d", debug_level);
cmdq_print(cmdq, "protocol version %d", PROTOCOL_VERSION);
}
void
cmd_show_messages_terminals(struct cmd_q *cmdq)
{
struct tty_term *term;
const struct tty_term_code_entry *ent;
struct tty_code *code;
u_int i, n;
char out[80];
struct tty_term *term;
u_int i, n;
n = 0;
LIST_FOREACH(term, &tty_terms, entry) {
cmdq_print(cmdq,
"Terminal %u: %s [references=%u, flags=0x%x]:",
if (blank) {
cmdq_print(item, "%s", "");
blank = 0;
}
cmdq_print(item, "Terminal %u: %s [references=%u, flags=0x%x]:",
n, term->name, term->references, term->flags);
n++;
for (i = 0; i < NTTYCODE; i++) {
ent = &tty_term_codes[i];
code = &term->codes[ent->code];
switch (code->type) {
case TTYCODE_NONE:
cmdq_print(cmdq, "%4u: %s: [missing]",
ent->code, ent->name);
break;
case TTYCODE_STRING:
strnvis(out, code->value.string, sizeof out,
VIS_OCTAL|VIS_TAB|VIS_NL);
cmdq_print(cmdq, "%4u: %s: (string) %s",
ent->code, ent->name, out);
break;
case TTYCODE_NUMBER:
cmdq_print(cmdq, "%4u: %s: (number) %d",
ent->code, ent->name, code->value.number);
break;
case TTYCODE_FLAG:
cmdq_print(cmdq, "%4u: %s: (flag) %s",
ent->code, ent->name,
code->value.flag ? "true" : "false");
break;
}
}
for (i = 0; i < tty_term_ncodes(); i++)
cmdq_print(item, "%s", tty_term_describe(term, i));
}
return (n != 0);
}
void
cmd_show_messages_jobs(struct cmd_q *cmdq)
{
struct job *job;
u_int n;
n = 0;
LIST_FOREACH(job, &all_jobs, lentry) {
cmdq_print(cmdq,
"Job %u: %s [fd=%d, pid=%d, status=%d]",
n, job->cmd, job->fd, job->pid, job->status);
n++;
}
}
enum cmd_retval
cmd_show_messages_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_show_messages_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct client *c;
struct message_entry *msg;
char *tim;
u_int i;
int done;
int done, blank;
done = 0;
if (args_has(args, 'I') || self->entry == &cmd_server_info_entry) {
cmd_show_messages_server(cmdq);
if ((c = cmd_find_client(item, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
done = blank = 0;
if (args_has(args, 'T')) {
blank = cmd_show_messages_terminals(item, blank);
done = 1;
}
if (args_has(args, 'T') || self->entry == &cmd_server_info_entry) {
if (done)
cmdq_print(cmdq, "%s", "");
cmd_show_messages_terminals(cmdq);
done = 1;
}
if (args_has(args, 'J') || self->entry == &cmd_server_info_entry) {
if (done)
cmdq_print(cmdq, "%s", "");
cmd_show_messages_jobs(cmdq);
if (args_has(args, 'J')) {
job_print_summary(item, blank);
done = 1;
}
if (done)
return (CMD_RETURN_NORMAL);
if ((c = cmd_find_client(cmdq, args_get(args, 't'), 0)) == NULL)
return (CMD_RETURN_ERROR);
for (i = 0; i < ARRAY_LENGTH(&c->message_log); i++) {
msg = &ARRAY_ITEM(&c->message_log, i);
TAILQ_FOREACH(msg, &c->message_log, entry) {
tim = ctime(&msg->msg_time);
*strchr(tim, '\n') = '\0';
cmdq_print(cmdq, "%s %s", tim, msg->msg);
cmdq_print(item, "%s %s", tim, msg->msg);
}
return (CMD_RETURN_NORMAL);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,151 +27,226 @@
* Show options.
*/
enum cmd_retval cmd_show_options_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_show_options_exec(struct cmd *, struct cmdq_item *);
enum cmd_retval cmd_show_options_one(struct cmd *, struct cmd_q *,
struct options *, int);
enum cmd_retval cmd_show_options_all(struct cmd *, struct cmd_q *,
const struct options_table_entry *, struct options *);
static void cmd_show_options_print(struct cmd *, struct cmdq_item *,
struct options_entry *, int, int);
static enum cmd_retval cmd_show_options_all(struct cmd *, struct cmdq_item *,
int, struct options *);
const struct cmd_entry cmd_show_options_entry = {
"show-options", "show",
"gqst:vw", 0, 1,
"[-gqsvw] [-t target-session|target-window] [option]",
0,
cmd_show_options_exec
.name = "show-options",
.alias = "show",
.args = { "AgHpqst:vw", 0, 1 },
.usage = "[-AgHpqsvw] " CMD_TARGET_PANE_USAGE " [option]",
.target = { 't', CMD_FIND_PANE, CMD_FIND_CANFAIL },
.flags = CMD_AFTERHOOK,
.exec = cmd_show_options_exec
};
const struct cmd_entry cmd_show_window_options_entry = {
"show-window-options", "showw",
"gvt:", 0, 1,
"[-gv] " CMD_TARGET_WINDOW_USAGE " [option]",
0,
cmd_show_options_exec
.name = "show-window-options",
.alias = "showw",
.args = { "gvt:", 0, 1 },
.usage = "[-gv] " CMD_TARGET_WINDOW_USAGE " [option]",
.target = { 't', CMD_FIND_WINDOW, CMD_FIND_CANFAIL },
.flags = CMD_AFTERHOOK,
.exec = cmd_show_options_exec
};
enum cmd_retval
cmd_show_options_exec(struct cmd *self, struct cmd_q *cmdq)
const struct cmd_entry cmd_show_hooks_entry = {
.name = "show-hooks",
.alias = NULL,
.args = { "gt:", 0, 1 },
.usage = "[-g] " CMD_TARGET_SESSION_USAGE,
.target = { 't', CMD_FIND_SESSION, 0 },
.flags = CMD_AFTERHOOK,
.exec = cmd_show_options_exec
};
static enum cmd_retval
cmd_show_options_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
struct winlink *wl;
const struct options_table_entry *table;
struct options *oo;
int quiet;
struct args *args = self->args;
struct cmd_find_state *fs = &item->target;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct options *oo;
char *argument, *name = NULL, *cause;
int window, idx, ambiguous, parent, scope;
struct options_entry *o;
if (args_has(self->args, 's')) {
oo = &global_options;
table = server_options_table;
} else if (args_has(self->args, 'w') ||
self->entry == &cmd_show_window_options_entry) {
table = window_options_table;
if (args_has(self->args, 'g'))
oo = &global_w_options;
else {
wl = cmd_find_window(cmdq, args_get(args, 't'), NULL);
if (wl == NULL)
return (CMD_RETURN_ERROR);
oo = &wl->window->options;
}
} else {
table = session_options_table;
if (args_has(self->args, 'g'))
oo = &global_s_options;
else {
s = cmd_find_session(cmdq, args_get(args, 't'), 0);
if (s == NULL)
return (CMD_RETURN_ERROR);
oo = &s->options;
}
}
window = (self->entry == &cmd_show_window_options_entry);
quiet = args_has(self->args, 'q');
if (args->argc == 0)
return (cmd_show_options_all(self, cmdq, table, oo));
else
return (cmd_show_options_one(self, cmdq, oo, quiet));
}
enum cmd_retval
cmd_show_options_one(struct cmd *self, struct cmd_q *cmdq,
struct options *oo, int quiet)
{
struct args *args = self->args;
const char *name = args->argv[0];
const struct options_table_entry *table, *oe;
struct options_entry *o;
const char *optval;
retry:
if (*name == '@') {
if ((o = options_find1(oo, name)) == NULL) {
if (quiet)
if (args->argc == 0) {
scope = options_scope_from_flags(args, window, fs, &oo, &cause);
if (scope == OPTIONS_TABLE_NONE) {
if (args_has(args, 'q'))
return (CMD_RETURN_NORMAL);
cmdq_error(cmdq, "unknown option: %s", name);
cmdq_error(item, "%s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
if (args_has(self->args, 'v'))
cmdq_print(cmdq, "%s", o->str);
else
cmdq_print(cmdq, "%s \"%s\"", o->name, o->str);
return (CMD_RETURN_NORMAL);
return (cmd_show_options_all(self, item, scope, oo));
}
argument = format_single(item, args->argv[0], c, s, wl, NULL);
table = oe = NULL;
if (options_table_find(name, &table, &oe) != 0) {
cmdq_error(cmdq, "ambiguous option: %s", name);
return (CMD_RETURN_ERROR);
name = options_match(argument, &idx, &ambiguous);
if (name == NULL) {
if (args_has(args, 'q'))
goto fail;
if (ambiguous)
cmdq_error(item, "ambiguous option: %s", argument);
else
cmdq_error(item, "invalid option: %s", argument);
goto fail;
}
if (oe == NULL) {
if (quiet)
return (CMD_RETURN_NORMAL);
cmdq_error(cmdq, "unknown option: %s", name);
return (CMD_RETURN_ERROR);
scope = options_scope_from_name(args, window, name, fs, &oo, &cause);
if (scope == OPTIONS_TABLE_NONE) {
if (args_has(args, 'q'))
goto fail;
cmdq_error(item, "%s", cause);
free(cause);
goto fail;
}
if (oe->style != NULL) {
name = oe->style;
goto retry;
}
if ((o = options_find1(oo, oe->name)) == NULL)
return (CMD_RETURN_NORMAL);
optval = options_table_print_entry(oe, o, args_has(self->args, 'v'));
if (args_has(self->args, 'v'))
cmdq_print(cmdq, "%s", optval);
else
cmdq_print(cmdq, "%s %s", oe->name, optval);
o = options_get_only(oo, name);
if (args_has(args, 'A') && o == NULL) {
o = options_get(oo, name);
parent = 1;
} else
parent = 0;
if (o != NULL)
cmd_show_options_print(self, item, o, idx, parent);
free(name);
free(argument);
return (CMD_RETURN_NORMAL);
fail:
free(name);
free(argument);
return (CMD_RETURN_ERROR);
}
enum cmd_retval
cmd_show_options_all(struct cmd *self, struct cmd_q *cmdq,
const struct options_table_entry *table, struct options *oo)
static void
cmd_show_options_print(struct cmd *self, struct cmdq_item *item,
struct options_entry *o, int idx, int parent)
{
struct options_array_item *a;
const char *name = options_name(o);
char *value, *tmp = NULL, *escaped;
if (idx != -1) {
xasprintf(&tmp, "%s[%d]", name, idx);
name = tmp;
} else {
if (options_isarray(o)) {
a = options_array_first(o);
if (a == NULL) {
if (!args_has(self->args, 'v'))
cmdq_print(item, "%s", name);
return;
}
while (a != NULL) {
idx = options_array_item_index(a);
cmd_show_options_print(self, item, o, idx,
parent);
a = options_array_next(a);
}
return;
}
}
value = options_tostring(o, idx, 0);
if (args_has(self->args, 'v'))
cmdq_print(item, "%s", value);
else if (options_isstring(o)) {
escaped = args_escape(value);
if (parent)
cmdq_print(item, "%s* %s", name, escaped);
else
cmdq_print(item, "%s %s", name, escaped);
free(escaped);
} else {
if (parent)
cmdq_print(item, "%s* %s", name, value);
else
cmdq_print(item, "%s %s", name, value);
}
free(value);
free(tmp);
}
static enum cmd_retval
cmd_show_options_all(struct cmd *self, struct cmdq_item *item, int scope,
struct options *oo)
{
const struct options_table_entry *oe;
struct options_entry *o;
const char *optval;
struct options_array_item *a;
const char *name;
u_int idx;
int parent;
RB_FOREACH(o, options_tree, &oo->tree) {
if (*o->name == '@') {
if (args_has(self->args, 'v'))
cmdq_print(cmdq, "%s", o->str);
else
cmdq_print(cmdq, "%s \"%s\"", o->name, o->str);
o = options_first(oo);
while (o != NULL) {
if (options_table_entry(o) == NULL)
cmd_show_options_print(self, item, o, -1, 0);
o = options_next(o);
}
for (oe = options_table; oe->name != NULL; oe++) {
if (~oe->scope & scope)
continue;
if ((self->entry != &cmd_show_hooks_entry &&
!args_has(self->args, 'H') &&
oe != NULL &&
(oe->flags & OPTIONS_TABLE_IS_HOOK)) ||
(self->entry == &cmd_show_hooks_entry &&
(oe == NULL ||
(~oe->flags & OPTIONS_TABLE_IS_HOOK))))
continue;
o = options_get_only(oo, oe->name);
if (o == NULL) {
if (!args_has(self->args, 'A'))
continue;
o = options_get(oo, oe->name);
if (o == NULL)
continue;
parent = 1;
} else
parent = 0;
if (!options_isarray(o))
cmd_show_options_print(self, item, o, -1, parent);
else if ((a = options_array_first(o)) == NULL) {
if (!args_has(self->args, 'v')) {
name = options_name(o);
if (parent)
cmdq_print(item, "%s*", name);
else
cmdq_print(item, "%s", name);
}
} else {
while (a != NULL) {
idx = options_array_item_index(a);
cmd_show_options_print(self, item, o, idx,
parent);
a = options_array_next(a);
}
}
}
for (oe = table; oe->name != NULL; oe++) {
if (oe->style != NULL)
continue;
if ((o = options_find1(oo, oe->name)) == NULL)
continue;
optval = options_table_print_entry(oe, o,
args_has(self->args, 'v'));
if (args_has(self->args, 'v'))
cmdq_print(cmdq, "%s", optval);
else
cmdq_print(cmdq, "%s %s", oe->name, optval);
}
return (CMD_RETURN_NORMAL);
}

View File

@@ -18,7 +18,10 @@
#include <sys/types.h>
#include <errno.h>
#include <glob.h>
#include <stdlib.h>
#include <string.h>
#include "tmux.h"
@@ -26,71 +29,164 @@
* Sources a configuration file.
*/
enum cmd_retval cmd_source_file_exec(struct cmd *, struct cmd_q *);
void cmd_source_file_done(struct cmd_q *);
static enum cmd_retval cmd_source_file_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_source_file_entry = {
"source-file", "source",
"", 1, 1,
"path",
0,
cmd_source_file_exec
.name = "source-file",
.alias = "source",
.args = { "nqv", 1, -1 },
.usage = "[-nqv] path ...",
.flags = 0,
.exec = cmd_source_file_exec
};
enum cmd_retval
cmd_source_file_exec(struct cmd *self, struct cmd_q *cmdq)
struct cmd_source_file_data {
struct cmdq_item *item;
int flags;
struct cmdq_item *after;
enum cmd_retval retval;
u_int current;
char **files;
u_int nfiles;
};
static enum cmd_retval
cmd_source_file_complete_cb(struct cmdq_item *item, __unused void *data)
{
struct args *args = self->args;
struct cmd_q *cmdq1;
char *cause;
cfg_print_causes(item);
return (CMD_RETURN_NORMAL);
}
cmdq1 = cmdq_new(NULL);
cmdq1->client = cmdq->client;
cmdq1->emptyfn = cmd_source_file_done;
cmdq1->data = cmdq;
static void
cmd_source_file_complete(struct client *c, struct cmd_source_file_data *cdata)
{
struct cmdq_item *new_item;
switch (load_cfg(args->argv[0], cmdq1, &cause)) {
case -1:
if (cfg_references == 0) {
cmdq_free(cmdq1);
cmdq_error(cmdq, "%s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
cfg_add_cause("%s", cause);
free(cause);
/* FALLTHROUGH */
case 0:
if (cfg_references == 0)
cfg_print_causes(cmdq);
cmdq_free(cmdq1);
return (CMD_RETURN_NORMAL);
if (cfg_finished) {
if (cdata->retval == CMD_RETURN_ERROR && c->session == NULL)
c->retval = 1;
new_item = cmdq_get_callback(cmd_source_file_complete_cb, NULL);
cmdq_insert_after(cdata->after, new_item);
}
cmdq->references++;
cfg_references++;
cmdq_continue(cmdq1);
return (CMD_RETURN_WAIT);
free(cdata->files);
free(cdata);
}
void
cmd_source_file_done(struct cmd_q *cmdq1)
static void
cmd_source_file_done(struct client *c, const char *path, int error,
int closed, struct evbuffer *buffer, void *data)
{
struct cmd_q *cmdq = cmdq1->data;
struct cmd_source_file_data *cdata = data;
struct cmdq_item *item = cdata->item;
void *bdata = EVBUFFER_DATA(buffer);
size_t bsize = EVBUFFER_LENGTH(buffer);
u_int n;
struct cmdq_item *new_item;
if (cmdq1->client_exit >= 0)
cmdq->client_exit = cmdq1->client_exit;
cmdq_free(cmdq1);
cfg_references--;
if (cmdq_free(cmdq))
if (!closed)
return;
if (cfg_references == 0)
cfg_print_causes(cmdq);
cmdq_continue(cmdq);
if (error != 0)
cmdq_error(item, "%s: %s", path, strerror(error));
else if (bsize != 0) {
if (load_cfg_from_buffer(bdata, bsize, path, c, cdata->after,
cdata->flags, &new_item) < 0)
cdata->retval = CMD_RETURN_ERROR;
else if (new_item != NULL)
cdata->after = new_item;
}
n = ++cdata->current;
if (n < cdata->nfiles)
file_read(c, cdata->files[n], cmd_source_file_done, cdata);
else {
cmd_source_file_complete(c, cdata);
cmdq_continue(item);
}
}
static void
cmd_source_file_add(struct cmd_source_file_data *cdata, const char *path)
{
log_debug("%s: %s", __func__, path);
cdata->files = xreallocarray(cdata->files, cdata->nfiles + 1,
sizeof *cdata->files);
cdata->files[cdata->nfiles++] = xstrdup(path);
}
static enum cmd_retval
cmd_source_file_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct cmd_source_file_data *cdata;
struct client *c = item->client;
enum cmd_retval retval = CMD_RETURN_NORMAL;
char *pattern, *cwd;
const char *path, *error;
glob_t g;
int i, result;
u_int j;
cdata = xcalloc(1, sizeof *cdata);
cdata->item = item;
if (args_has(args, 'q'))
cdata->flags |= CMD_PARSE_QUIET;
if (args_has(args, 'n'))
cdata->flags |= CMD_PARSE_PARSEONLY;
if (args_has(args, 'v'))
cdata->flags |= CMD_PARSE_VERBOSE;
utf8_stravis(&cwd, server_client_get_cwd(c, NULL), VIS_GLOB);
for (i = 0; i < args->argc; i++) {
path = args->argv[i];
if (strcmp(path, "-") == 0) {
cmd_source_file_add(cdata, "-");
continue;
}
if (*path == '/')
pattern = xstrdup(path);
else
xasprintf(&pattern, "%s/%s", cwd, path);
log_debug("%s: %s", __func__, pattern);
if ((result = glob(pattern, 0, NULL, &g)) != 0) {
if (result != GLOB_NOMATCH ||
(~cdata->flags & CMD_PARSE_QUIET)) {
if (result == GLOB_NOMATCH)
error = strerror(ENOENT);
else if (result == GLOB_NOSPACE)
error = strerror(ENOMEM);
else
error = strerror(EINVAL);
cmdq_error(item, "%s: %s", path, error);
retval = CMD_RETURN_ERROR;
}
free(pattern);
continue;
}
free(pattern);
for (j = 0; j < g.gl_pathc; j++)
cmd_source_file_add(cdata, g.gl_pathv[j]);
}
cdata->after = item;
cdata->retval = retval;
if (cdata->nfiles != 0) {
file_read(c, cdata->files[0], cmd_source_file_done, cdata);
retval = CMD_RETURN_WAIT;
} else
cmd_source_file_complete(c, cdata);
free(cwd);
return (retval);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -32,172 +32,156 @@
#define SPLIT_WINDOW_TEMPLATE "#{session_name}:#{window_index}.#{pane_index}"
enum cmd_retval cmd_split_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_split_window_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_split_window_entry = {
"split-window", "splitw",
"bc:dF:l:hp:Pt:v", 0, -1,
"[-bdhvP] [-c start-directory] [-F format] [-p percentage|-l size] "
CMD_TARGET_PANE_USAGE " [command]",
0,
cmd_split_window_exec
.name = "split-window",
.alias = "splitw",
.args = { "bc:de:fF:hIl:p:Pt:v", 0, -1 },
.usage = "[-bdefhIPv] [-c start-directory] [-e environment] "
"[-F format] [-l size] " CMD_TARGET_PANE_USAGE " [command]",
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_split_window_exec
};
enum cmd_retval
cmd_split_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_split_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct session *s;
struct winlink *wl;
struct window *w;
struct window_pane *wp, *new_wp = NULL;
struct environ env;
const char *cmd, *path, *shell, *template;
char **argv, *cause, *new_cause, *cp;
u_int hlimit;
int argc, size, percentage, cwd, fd = -1;
struct cmd_find_state *current = &item->shared->current;
struct spawn_context sc;
struct client *c = cmd_find_client(item, NULL, 1);
struct session *s = item->target.s;
struct winlink *wl = item->target.wl;
struct window_pane *wp = item->target.wp, *new_wp;
enum layout_type type;
struct layout_cell *lc;
struct format_tree *ft;
struct environ_entry *envent;
struct cmd_find_state fs;
int size, percentage, flags, input;
const char *template, *add, *errstr, *p;
char *cause, *cp, *copy;
size_t plen;
struct args_value *value;
if ((wl = cmd_find_pane(cmdq, args_get(args, 't'), &s, &wp)) == NULL)
return (CMD_RETURN_ERROR);
w = wl->window;
server_unzoom_window(w);
environ_init(&env);
environ_copy(&global_environ, &env);
environ_copy(&s->environ, &env);
server_fill_environ(s, &env);
if (args->argc == 0) {
cmd = options_get_string(&s->options, "default-command");
if (cmd != NULL && *cmd != '\0') {
argc = 1;
argv = (char **)&cmd;
} else {
argc = 0;
argv = NULL;
}
} else {
argc = args->argc;
argv = args->argv;
}
if (args_has(args, 'c')) {
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s, NULL,
NULL);
cp = format_expand(ft, args_get(args, 'c'));
format_free(ft);
if (cp != NULL && *cp != '\0') {
fd = open(cp, O_RDONLY|O_DIRECTORY);
free(cp);
if (fd == -1) {
cmdq_error(cmdq, "bad working directory: %s",
strerror(errno));
return (CMD_RETURN_ERROR);
}
} else if (cp != NULL)
free(cp);
cwd = fd;
} else if (cmdq->client != NULL && cmdq->client->session == NULL)
cwd = cmdq->client->cwd;
else
cwd = s->cwd;
type = LAYOUT_TOPBOTTOM;
if (args_has(args, 'h'))
type = LAYOUT_LEFTRIGHT;
size = -1;
if (args_has(args, 'l')) {
size = args_strtonum(args, 'l', 0, INT_MAX, &cause);
if (cause != NULL) {
xasprintf(&new_cause, "size %s", cause);
free(cause);
cause = new_cause;
goto error;
else
type = LAYOUT_TOPBOTTOM;
if ((p = args_get(args, 'l')) != NULL) {
plen = strlen(p);
if (p[plen - 1] == '%') {
copy = xstrdup(p);
copy[plen - 1] = '\0';
percentage = strtonum(copy, 0, INT_MAX, &errstr);
free(copy);
if (errstr != NULL) {
cmdq_error(item, "percentage %s", errstr);
return (CMD_RETURN_ERROR);
}
if (type == LAYOUT_TOPBOTTOM)
size = (wp->sy * percentage) / 100;
else
size = (wp->sx * percentage) / 100;
} else {
size = args_strtonum(args, 'l', 0, INT_MAX, &cause);
if (cause != NULL) {
cmdq_error(item, "lines %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
}
} else if (args_has(args, 'p')) {
percentage = args_strtonum(args, 'p', 0, INT_MAX, &cause);
if (cause != NULL) {
xasprintf(&new_cause, "percentage %s", cause);
cmdq_error(item, "create pane failed: -p %s", cause);
free(cause);
cause = new_cause;
goto error;
return (CMD_RETURN_ERROR);
}
if (type == LAYOUT_TOPBOTTOM)
size = (wp->sy * percentage) / 100;
else
size = (wp->sx * percentage) / 100;
}
hlimit = options_get_number(&s->options, "history-limit");
shell = options_get_string(&s->options, "default-shell");
if (*shell == '\0' || areshell(shell))
shell = _PATH_BSHELL;
lc = layout_split_pane(wp, type, size, args_has(args, 'b'));
if (lc == NULL) {
cause = xstrdup("pane too small");
goto error;
}
new_wp = window_add_pane(w, hlimit);
path = NULL;
if (cmdq->client != NULL && cmdq->client->session == NULL)
envent = environ_find(&cmdq->client->environ, "PATH");
else
envent = environ_find(&s->environ, "PATH");
if (envent != NULL)
path = envent->value;
if (window_pane_spawn(new_wp, argc, argv, path, shell, cwd, &env,
s->tio, &cause) != 0)
goto error;
layout_assign_pane(lc, new_wp);
server_redraw_window(w);
if (!args_has(args, 'd')) {
window_set_active_pane(w, new_wp);
session_select(s, wl->idx);
server_redraw_session(s);
} else
server_status_session(s);
size = -1;
environ_free(&env);
server_unzoom_window(wp->window);
input = (args_has(args, 'I') && args->argc == 0);
flags = 0;
if (args_has(args, 'b'))
flags |= SPAWN_BEFORE;
if (args_has(args, 'f'))
flags |= SPAWN_FULLSIZE;
if (input || (args->argc == 1 && *args->argv[0] == '\0'))
flags |= SPAWN_EMPTY;
lc = layout_split_pane(wp, type, size, flags);
if (lc == NULL) {
cmdq_error(item, "no space for new pane");
return (CMD_RETURN_ERROR);
}
memset(&sc, 0, sizeof sc);
sc.item = item;
sc.s = s;
sc.wl = wl;
sc.wp0 = wp;
sc.lc = lc;
sc.name = NULL;
sc.argc = args->argc;
sc.argv = args->argv;
sc.environ = environ_create();
add = args_first_value(args, 'e', &value);
while (add != NULL) {
environ_put(sc.environ, add);
add = args_next_value(&value);
}
sc.idx = -1;
sc.cwd = args_get(args, 'c');
sc.flags = flags;
if (args_has(args, 'd'))
sc.flags |= SPAWN_DETACHED;
if ((new_wp = spawn_pane(&sc, &cause)) == NULL) {
cmdq_error(item, "create pane failed: %s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
if (input && window_pane_start_input(new_wp, item, &cause) != 0) {
layout_close_pane(new_wp);
window_remove_pane(wp->window, new_wp);
cmdq_error(item, "%s", cause);
free(cause);
return (CMD_RETURN_ERROR);
}
if (!args_has(args, 'd'))
cmd_find_from_winlink_pane(current, wl, new_wp, 0);
server_redraw_window(wp->window);
server_status_session(s);
if (args_has(args, 'P')) {
if ((template = args_get(args, 'F')) == NULL)
template = SPLIT_WINDOW_TEMPLATE;
ft = format_create();
format_defaults(ft, cmd_find_client(cmdq, NULL, 1), s, wl,
new_wp);
cp = format_expand(ft, template);
cmdq_print(cmdq, "%s", cp);
cp = format_single(item, template, c, s, wl, new_wp);
cmdq_print(item, "%s", cp);
free(cp);
format_free(ft);
}
notify_window_layout_changed(w);
if (fd != -1)
close(fd);
cmd_find_from_winlink_pane(&fs, wl, new_wp, 0);
cmdq_insert_hook(s, item, &fs, "after-split-window");
environ_free(sc.environ);
if (input)
return (CMD_RETURN_WAIT);
return (CMD_RETURN_NORMAL);
error:
environ_free(&env);
if (new_wp != NULL)
window_remove_pane(w, new_wp);
cmdq_error(cmdq, "create pane failed: %s", cause);
free(cause);
if (fd != -1)
close(fd);
return (CMD_RETURN_ERROR);
}

View File

@@ -1,359 +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 <errno.h>
#include <pwd.h>
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <unistd.h>
#include "tmux.h"
/*
* Parse a command from a string.
*/
int cmd_string_getc(const char *, size_t *);
void cmd_string_ungetc(size_t *);
void cmd_string_copy(char **, char *, size_t *);
char *cmd_string_string(const char *, size_t *, char, int);
char *cmd_string_variable(const char *, size_t *);
char *cmd_string_expand_tilde(const char *, size_t *);
int
cmd_string_getc(const char *s, size_t *p)
{
const u_char *ucs = s;
if (ucs[*p] == '\0')
return (EOF);
return (ucs[(*p)++]);
}
void
cmd_string_ungetc(size_t *p)
{
(*p)--;
}
/*
* Parse command string. Returns -1 on error. If returning -1, cause is error
* string, or NULL for empty command.
*/
int
cmd_string_parse(const char *s, struct cmd_list **cmdlist, const char *file,
u_int line, char **cause)
{
size_t p;
int ch, i, argc, rval;
char **argv, *buf, *t;
const char *whitespace, *equals;
size_t len;
argv = NULL;
argc = 0;
buf = NULL;
len = 0;
*cause = NULL;
*cmdlist = NULL;
rval = -1;
p = 0;
for (;;) {
ch = cmd_string_getc(s, &p);
switch (ch) {
case '\'':
if ((t = cmd_string_string(s, &p, '\'', 0)) == NULL)
goto error;
cmd_string_copy(&buf, t, &len);
break;
case '"':
if ((t = cmd_string_string(s, &p, '"', 1)) == NULL)
goto error;
cmd_string_copy(&buf, t, &len);
break;
case '$':
if ((t = cmd_string_variable(s, &p)) == NULL)
goto error;
cmd_string_copy(&buf, t, &len);
break;
case '#':
/* Comment: discard rest of line. */
while ((ch = cmd_string_getc(s, &p)) != EOF)
;
/* FALLTHROUGH */
case EOF:
case ' ':
case '\t':
if (buf != NULL) {
buf = xrealloc(buf, len + 1);
buf[len] = '\0';
argv = xreallocarray(argv, argc + 1,
sizeof *argv);
argv[argc++] = buf;
buf = NULL;
len = 0;
}
if (ch != EOF)
break;
while (argc != 0) {
equals = strchr(argv[0], '=');
whitespace = argv[0] + strcspn(argv[0], " \t");
if (equals == NULL || equals > whitespace)
break;
environ_put(&global_environ, argv[0]);
argc--;
memmove(argv, argv + 1, argc * (sizeof *argv));
}
if (argc == 0)
goto out;
*cmdlist = cmd_list_parse(argc, argv, file, line, cause);
if (*cmdlist == NULL)
goto out;
rval = 0;
goto out;
case '~':
if (buf == NULL) {
t = cmd_string_expand_tilde(s, &p);
if (t == NULL)
goto error;
cmd_string_copy(&buf, t, &len);
break;
}
/* FALLTHROUGH */
default:
if (len >= SIZE_MAX - 2)
goto error;
buf = xrealloc(buf, len + 1);
buf[len++] = ch;
break;
}
}
error:
xasprintf(cause, "invalid or unknown command: %s", s);
out:
free(buf);
if (argv != NULL) {
for (i = 0; i < argc; i++)
free(argv[i]);
free(argv);
}
return (rval);
}
void
cmd_string_copy(char **dst, char *src, size_t *len)
{
size_t srclen;
srclen = strlen(src);
*dst = xrealloc(*dst, *len + srclen + 1);
strlcpy(*dst + *len, src, srclen + 1);
*len += srclen;
free(src);
}
char *
cmd_string_string(const char *s, size_t *p, char endch, int esc)
{
int ch;
char *buf, *t;
size_t len;
buf = NULL;
len = 0;
while ((ch = cmd_string_getc(s, p)) != endch) {
switch (ch) {
case EOF:
goto error;
case '\\':
if (!esc)
break;
switch (ch = cmd_string_getc(s, p)) {
case EOF:
goto error;
case 'e':
ch = '\033';
break;
case 'r':
ch = '\r';
break;
case 'n':
ch = '\n';
break;
case 't':
ch = '\t';
break;
}
break;
case '$':
if (!esc)
break;
if ((t = cmd_string_variable(s, p)) == NULL)
goto error;
cmd_string_copy(&buf, t, &len);
continue;
}
if (len >= SIZE_MAX - 2)
goto error;
buf = xrealloc(buf, len + 1);
buf[len++] = ch;
}
buf = xrealloc(buf, len + 1);
buf[len] = '\0';
return (buf);
error:
free(buf);
return (NULL);
}
char *
cmd_string_variable(const char *s, size_t *p)
{
int ch, fch;
char *buf, *t;
size_t len;
struct environ_entry *envent;
#define cmd_string_first(ch) ((ch) == '_' || \
((ch) >= 'a' && (ch) <= 'z') || ((ch) >= 'A' && (ch) <= 'Z'))
#define cmd_string_other(ch) ((ch) == '_' || \
((ch) >= 'a' && (ch) <= 'z') || ((ch) >= 'A' && (ch) <= 'Z') || \
((ch) >= '0' && (ch) <= '9'))
buf = NULL;
len = 0;
fch = EOF;
switch (ch = cmd_string_getc(s, p)) {
case EOF:
goto error;
case '{':
fch = '{';
ch = cmd_string_getc(s, p);
if (!cmd_string_first(ch))
goto error;
/* FALLTHROUGH */
default:
if (!cmd_string_first(ch)) {
xasprintf(&t, "$%c", ch);
return (t);
}
buf = xrealloc(buf, len + 1);
buf[len++] = ch;
for (;;) {
ch = cmd_string_getc(s, p);
if (ch == EOF || !cmd_string_other(ch))
break;
else {
if (len >= SIZE_MAX - 3)
goto error;
buf = xrealloc(buf, len + 1);
buf[len++] = ch;
}
}
}
if (fch == '{' && ch != '}')
goto error;
if (ch != EOF && fch != '{')
cmd_string_ungetc(p); /* ch */
buf = xrealloc(buf, len + 1);
buf[len] = '\0';
envent = environ_find(&global_environ, buf);
free(buf);
if (envent == NULL)
return (xstrdup(""));
return (xstrdup(envent->value));
error:
free(buf);
return (NULL);
}
char *
cmd_string_expand_tilde(const char *s, size_t *p)
{
struct passwd *pw;
struct environ_entry *envent;
char *home, *path, *user, *cp;
int last;
home = NULL;
last = cmd_string_getc(s, p);
if (last == EOF || last == '/' || last == ' '|| last == '\t') {
envent = environ_find(&global_environ, "HOME");
if (envent != NULL && *envent->value != '\0')
home = envent->value;
else if ((pw = getpwuid(getuid())) != NULL)
home = pw->pw_dir;
} else {
cmd_string_ungetc(p);
cp = user = xmalloc(strlen(s));
for (;;) {
last = cmd_string_getc(s, p);
if (last == EOF || last == '/' || last == ' '|| last == '\t')
break;
*cp++ = last;
}
*cp = '\0';
if ((pw = getpwnam(user)) != NULL)
home = pw->pw_dir;
free(user);
}
if (home == NULL)
return (NULL);
if (last != EOF)
xasprintf(&path, "%s%c", home, last);
else
xasprintf(&path, "%s", home);
return (path);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2009 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2009 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,58 +26,56 @@
* Swap two panes.
*/
enum cmd_retval cmd_swap_pane_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_swap_pane_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_swap_pane_entry = {
"swap-pane", "swapp",
"dDs:t:U", 0, 0,
"[-dDU] " CMD_SRCDST_PANE_USAGE,
0,
cmd_swap_pane_exec
.name = "swap-pane",
.alias = "swapp",
.args = { "dDs:t:UZ", 0, 0 },
.usage = "[-dDUZ] " CMD_SRCDST_PANE_USAGE,
.source = { 's', CMD_FIND_PANE, CMD_FIND_DEFAULT_MARKED },
.target = { 't', CMD_FIND_PANE, 0 },
.flags = 0,
.exec = cmd_swap_pane_exec
};
enum cmd_retval
cmd_swap_pane_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_swap_pane_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct winlink *src_wl, *dst_wl;
struct window *src_w, *dst_w;
struct window_pane *tmp_wp, *src_wp, *dst_wp;
struct layout_cell *src_lc, *dst_lc;
u_int sx, sy, xoff, yoff;
dst_wl = cmd_find_pane(cmdq, args_get(args, 't'), NULL, &dst_wp);
if (dst_wl == NULL)
return (CMD_RETURN_ERROR);
dst_w = dst_wl->window;
server_unzoom_window(dst_w);
dst_w = item->target.wl->window;
dst_wp = item->target.wp;
src_w = item->source.wl->window;
src_wp = item->source.wp;
if (!args_has(args, 's')) {
if (window_push_zoom(dst_w, args_has(args, 'Z')))
server_redraw_window(dst_w);
if (args_has(args, 'D')) {
src_w = dst_w;
if (args_has(self->args, 'D')) {
src_wp = TAILQ_NEXT(dst_wp, entry);
if (src_wp == NULL)
src_wp = TAILQ_FIRST(&dst_w->panes);
} else if (args_has(self->args, 'U')) {
src_wp = TAILQ_PREV(dst_wp, window_panes, entry);
if (src_wp == NULL)
src_wp = TAILQ_LAST(&dst_w->panes, window_panes);
} else {
src_wl = cmd_find_pane(cmdq, NULL, NULL, &src_wp);
if (src_wl == NULL)
return (CMD_RETURN_ERROR);
src_w = src_wl->window;
}
} else {
src_wl = cmd_find_pane(cmdq, args_get(args, 's'), NULL, &src_wp);
if (src_wl == NULL)
return (CMD_RETURN_ERROR);
src_w = src_wl->window;
src_wp = TAILQ_NEXT(dst_wp, entry);
if (src_wp == NULL)
src_wp = TAILQ_FIRST(&dst_w->panes);
} else if (args_has(args, 'U')) {
src_w = dst_w;
src_wp = TAILQ_PREV(dst_wp, window_panes, entry);
if (src_wp == NULL)
src_wp = TAILQ_LAST(&dst_w->panes, window_panes);
}
server_unzoom_window(src_w);
if (src_w != dst_w && window_push_zoom(src_w, args_has(args, 'Z')))
server_redraw_window(src_w);
if (src_wp == dst_wp)
return (CMD_RETURN_NORMAL);
goto out;
tmp_wp = TAILQ_PREV(dst_wp, window_panes, entry);
TAILQ_REMOVE(&dst_w->panes, dst_wp, entry);
@@ -97,7 +95,11 @@ cmd_swap_pane_exec(struct cmd *self, struct cmd_q *cmdq)
src_wp->layout_cell = dst_lc;
src_wp->window = dst_w;
options_set_parent(src_wp->options, dst_w->options);
src_wp->flags |= PANE_STYLECHANGED;
dst_wp->window = src_w;
options_set_parent(dst_wp->options, src_w->options);
dst_wp->flags |= PANE_STYLECHANGED;
sx = src_wp->sx; sy = src_wp->sy;
xoff = src_wp->xoff; yoff = src_wp->yoff;
@@ -106,21 +108,19 @@ cmd_swap_pane_exec(struct cmd *self, struct cmd_q *cmdq)
dst_wp->xoff = xoff; dst_wp->yoff = yoff;
window_pane_resize(dst_wp, sx, sy);
if (!args_has(self->args, 'd')) {
if (!args_has(args, 'd')) {
if (src_w != dst_w) {
window_set_active_pane(src_w, dst_wp);
window_set_active_pane(dst_w, src_wp);
window_set_active_pane(src_w, dst_wp, 1);
window_set_active_pane(dst_w, src_wp, 1);
} else {
tmp_wp = dst_wp;
if (!window_pane_visible(tmp_wp))
tmp_wp = src_wp;
window_set_active_pane(src_w, tmp_wp);
window_set_active_pane(src_w, tmp_wp, 1);
}
} else {
if (src_w->active == src_wp)
window_set_active_pane(src_w, dst_wp);
window_set_active_pane(src_w, dst_wp, 1);
if (dst_w->active == dst_wp)
window_set_active_pane(dst_w, src_wp);
window_set_active_pane(dst_w, src_wp, 1);
}
if (src_w != dst_w) {
if (src_w->last == src_wp)
@@ -131,5 +131,10 @@ cmd_swap_pane_exec(struct cmd *self, struct cmd_q *cmdq)
server_redraw_window(src_w);
server_redraw_window(dst_w);
out:
if (window_pop_zoom(src_w))
server_redraw_window(src_w);
if (src_w != dst_w && window_pop_zoom(dst_w))
server_redraw_window(dst_w);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,49 +26,58 @@
* Swap one window with another.
*/
enum cmd_retval cmd_swap_window_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_swap_window_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_swap_window_entry = {
"swap-window", "swapw",
"ds:t:", 0, 0,
"[-d] " CMD_SRCDST_WINDOW_USAGE,
0,
cmd_swap_window_exec
.name = "swap-window",
.alias = "swapw",
.args = { "ds:t:", 0, 0 },
.usage = "[-d] " CMD_SRCDST_WINDOW_USAGE,
.source = { 's', CMD_FIND_WINDOW, CMD_FIND_DEFAULT_MARKED },
.target = { 't', CMD_FIND_WINDOW, 0 },
.flags = 0,
.exec = cmd_swap_window_exec
};
enum cmd_retval
cmd_swap_window_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_swap_window_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
const char *target_src, *target_dst;
struct session *src, *dst;
struct session_group *sg_src, *sg_dst;
struct winlink *wl_src, *wl_dst;
struct window *w;
struct window *w_src, *w_dst;
target_src = args_get(args, 's');
if ((wl_src = cmd_find_window(cmdq, target_src, &src)) == NULL)
return (CMD_RETURN_ERROR);
target_dst = args_get(args, 't');
if ((wl_dst = cmd_find_window(cmdq, target_dst, &dst)) == NULL)
return (CMD_RETURN_ERROR);
wl_src = item->source.wl;
src = item->source.s;
sg_src = session_group_contains(src);
sg_src = session_group_find(src);
sg_dst = session_group_find(dst);
if (src != dst &&
sg_src != NULL && sg_dst != NULL && sg_src == sg_dst) {
cmdq_error(cmdq, "can't move window, sessions are grouped");
wl_dst = item->target.wl;
dst = item->target.s;
sg_dst = session_group_contains(dst);
if (src != dst && sg_src != NULL && sg_dst != NULL &&
sg_src == sg_dst) {
cmdq_error(item, "can't move window, sessions are grouped");
return (CMD_RETURN_ERROR);
}
if (wl_dst->window == wl_src->window)
return (CMD_RETURN_NORMAL);
w = wl_dst->window;
wl_dst->window = wl_src->window;
wl_src->window = w;
w_dst = wl_dst->window;
TAILQ_REMOVE(&w_dst->winlinks, wl_dst, wentry);
w_src = wl_src->window;
TAILQ_REMOVE(&w_src->winlinks, wl_src, wentry);
if (!args_has(self->args, 'd')) {
wl_dst->window = w_src;
TAILQ_INSERT_TAIL(&w_src->winlinks, wl_dst, wentry);
wl_src->window = w_dst;
TAILQ_INSERT_TAIL(&w_dst->winlinks, wl_src, wentry);
if (args_has(self->args, 'd')) {
session_select(dst, wl_dst->idx);
if (src != dst)
session_select(src, wl_src->idx);

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -27,92 +27,127 @@
* Switch client to a different session.
*/
enum cmd_retval cmd_switch_client_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_switch_client_exec(struct cmd *,
struct cmdq_item *);
const struct cmd_entry cmd_switch_client_entry = {
"switch-client", "switchc",
"lc:npt:r", 0, 0,
"[-lnpr] [-c target-client] [-t target-session]",
CMD_READONLY,
cmd_switch_client_exec
.name = "switch-client",
.alias = "switchc",
.args = { "lc:Enpt:rT:Z", 0, 0 },
.usage = "[-ElnprZ] [-c target-client] [-t target-session] "
"[-T key-table]",
/* -t is special */
.flags = CMD_READONLY,
.exec = cmd_switch_client_exec
};
enum cmd_retval
cmd_switch_client_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_switch_client_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
const char *tflag = args_get(args, 't');
enum cmd_find_type type;
int flags;
struct client *c;
struct session *s = NULL;
struct winlink *wl = NULL;
struct window *w = NULL;
struct window_pane *wp = NULL;
const char *tflag;
struct session *s;
struct winlink *wl;
struct window *w;
struct window_pane *wp;
const char *tablename;
struct key_table *table;
if ((c = cmd_find_client(cmdq, args_get(args, 'c'), 0)) == NULL)
if ((c = cmd_find_client(item, args_get(args, 'c'), 0)) == NULL)
return (CMD_RETURN_ERROR);
if (args_has(args, 'r')) {
if (c->flags & CLIENT_READONLY)
c->flags &= ~CLIENT_READONLY;
else
c->flags |= CLIENT_READONLY;
if (tflag != NULL && tflag[strcspn(tflag, ":.%")] != '\0') {
type = CMD_FIND_PANE;
flags = 0;
} else {
type = CMD_FIND_SESSION;
flags = CMD_FIND_PREFER_UNATTACHED;
}
if (cmd_find_target(&item->target, item, tflag, type, flags) != 0)
return (CMD_RETURN_ERROR);
s = item->target.s;
wl = item->target.wl;
w = wl->window;
wp = item->target.wp;
if (args_has(args, 'r'))
c->flags ^= CLIENT_READONLY;
tablename = args_get(args, 'T');
if (tablename != NULL) {
table = key_bindings_get_table(tablename, 0);
if (table == NULL) {
cmdq_error(item, "table %s doesn't exist", tablename);
return (CMD_RETURN_ERROR);
}
table->references++;
key_bindings_unref_table(c->keytable);
c->keytable = table;
return (CMD_RETURN_NORMAL);
}
tflag = args_get(args, 't');
if (args_has(args, 'n')) {
if ((s = session_next_session(c->session)) == NULL) {
cmdq_error(cmdq, "can't find next session");
cmdq_error(item, "can't find next session");
return (CMD_RETURN_ERROR);
}
} else if (args_has(args, 'p')) {
if ((s = session_previous_session(c->session)) == NULL) {
cmdq_error(cmdq, "can't find previous session");
cmdq_error(item, "can't find previous session");
return (CMD_RETURN_ERROR);
}
} else if (args_has(args, 'l')) {
if (c->last_session != NULL && session_alive(c->last_session))
s = c->last_session;
else
s = NULL;
if (s == NULL) {
cmdq_error(cmdq, "can't find last session");
cmdq_error(item, "can't find last session");
return (CMD_RETURN_ERROR);
}
} else {
if (tflag == NULL) {
if ((s = cmd_find_session(cmdq, tflag, 1)) == NULL)
return (CMD_RETURN_ERROR);
} else if (tflag[strcspn(tflag, ":.")] != '\0') {
if ((wl = cmd_find_pane(cmdq, tflag, &s, &wp)) == NULL)
return (CMD_RETURN_ERROR);
} else {
if ((s = cmd_find_session(cmdq, tflag, 1)) == NULL)
return (CMD_RETURN_ERROR);
w = cmd_lookup_windowid(tflag);
if (w == NULL &&
(wp = cmd_lookup_paneid(tflag)) != NULL)
w = wp->window;
if (w != NULL)
wl = winlink_find_by_window(&s->windows, w);
}
if (cmdq->client == NULL)
if (item->client == NULL)
return (CMD_RETURN_NORMAL);
if (wl != NULL && wp != NULL) {
if (window_push_zoom(w, args_has(self->args, 'Z')))
server_redraw_window(w);
window_redraw_active_switch(w, wp);
window_set_active_pane(w, wp, 1);
if (window_pop_zoom(w))
server_redraw_window(w);
}
if (wl != NULL) {
if (wp != NULL)
window_set_active_pane(wp->window, wp);
session_set_current(s, wl);
cmd_find_from_session(&item->shared->current, s, 0);
}
}
if (c->session != NULL)
if (!args_has(args, 'E'))
environ_update(s->options, c->environ, s->environ);
if (c->session != NULL && c->session != s)
c->last_session = c->session;
c->session = s;
session_update_activity(s);
if (~item->shared->flags & CMDQ_SHARED_REPEAT)
server_client_set_key_table(c, NULL);
tty_update_client_offset(c);
status_timer_start(c);
notify_client("client-session-changed", c);
session_update_activity(s, NULL);
gettimeofday(&s->last_attached_time, NULL);
recalculate_sizes();
server_check_unattached();
server_redraw_client(c);
s->curw->flags &= ~WINLINK_ALERTFLAGS;
s->curw->window->latest = c;
recalculate_sizes();
alerts_check_session(s);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -26,87 +26,69 @@
* Unbind key from command.
*/
enum cmd_retval cmd_unbind_key_exec(struct cmd *, struct cmd_q *);
enum cmd_retval cmd_unbind_key_mode_table(struct cmd *, struct cmd_q *, int);
static enum cmd_retval cmd_unbind_key_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_unbind_key_entry = {
"unbind-key", "unbind",
"acnt:", 0, 1,
"[-acn] [-t mode-table] key",
0,
cmd_unbind_key_exec
.name = "unbind-key",
.alias = "unbind",
.args = { "anT:", 0, 1 },
.usage = "[-an] [-T key-table] key",
.flags = CMD_AFTERHOOK,
.exec = cmd_unbind_key_exec
};
enum cmd_retval
cmd_unbind_key_exec(struct cmd *self, struct cmd_q *cmdq)
static enum cmd_retval
cmd_unbind_key_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
struct key_binding *bd;
int key;
struct args *args = self->args;
key_code key;
const char *tablename;
if (!args_has(args, 'a')) {
if (args->argc != 1) {
cmdq_error(cmdq, "missing key");
cmdq_error(item, "missing key");
return (CMD_RETURN_ERROR);
}
key = key_string_lookup_string(args->argv[0]);
if (key == KEYC_NONE) {
cmdq_error(cmdq, "unknown key: %s", args->argv[0]);
if (key == KEYC_NONE || key == KEYC_UNKNOWN) {
cmdq_error(item, "unknown key: %s", args->argv[0]);
return (CMD_RETURN_ERROR);
}
} else {
if (args->argc != 0) {
cmdq_error(cmdq, "key given with -a");
cmdq_error(item, "key given with -a");
return (CMD_RETURN_ERROR);
}
key = KEYC_NONE;
key = KEYC_UNKNOWN;
}
if (args_has(args, 't'))
return (cmd_unbind_key_mode_table(self, cmdq, key));
if (key == KEYC_NONE) {
while (!RB_EMPTY(&key_bindings)) {
bd = RB_ROOT(&key_bindings);
key_bindings_remove(bd->key);
if (key == KEYC_UNKNOWN) {
tablename = args_get(args, 'T');
if (tablename == NULL) {
key_bindings_remove_table("root");
key_bindings_remove_table("prefix");
return (CMD_RETURN_NORMAL);
}
if (key_bindings_get_table(tablename, 0) == NULL) {
cmdq_error(item, "table %s doesn't exist", tablename);
return (CMD_RETURN_ERROR);
}
key_bindings_remove_table(tablename);
return (CMD_RETURN_NORMAL);
}
if (!args_has(args, 'n'))
key |= KEYC_PREFIX;
key_bindings_remove(key);
return (CMD_RETURN_NORMAL);
}
enum cmd_retval
cmd_unbind_key_mode_table(struct cmd *self, struct cmd_q *cmdq, int key)
{
struct args *args = self->args;
const char *tablename;
const struct mode_key_table *mtab;
struct mode_key_binding *mbind, mtmp;
tablename = args_get(args, 't');
if ((mtab = mode_key_findtable(tablename)) == NULL) {
cmdq_error(cmdq, "unknown key table: %s", tablename);
return (CMD_RETURN_ERROR);
}
if (key == KEYC_NONE) {
while (!RB_EMPTY(mtab->tree)) {
mbind = RB_ROOT(mtab->tree);
RB_REMOVE(mode_key_tree, mtab->tree, mbind);
free(mbind);
if (args_has(args, 'T')) {
tablename = args_get(args, 'T');
if (key_bindings_get_table(tablename, 0) == NULL) {
cmdq_error(item, "table %s doesn't exist", tablename);
return (CMD_RETURN_ERROR);
}
return (CMD_RETURN_NORMAL);
}
mtmp.key = key;
mtmp.mode = !!args_has(args, 'c');
if ((mbind = RB_FIND(mode_key_tree, mtab->tree, &mtmp)) != NULL) {
RB_REMOVE(mode_key_tree, mtab->tree, mbind);
free(mbind);
}
} else if (args_has(args, 'n'))
tablename = "root";
else
tablename = "prefix";
key_bindings_remove(tablename, key);
return (CMD_RETURN_NORMAL);
}

View File

@@ -1,7 +1,7 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2013 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2013 Nicholas Marriott <nicholas.marriott@gmail.com>
* Copyright (c) 2013 Thiago de Arruda <tpadilha84@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
@@ -28,49 +28,97 @@
* Block or wake a client on a named wait channel.
*/
enum cmd_retval cmd_wait_for_exec(struct cmd *, struct cmd_q *);
static enum cmd_retval cmd_wait_for_exec(struct cmd *, struct cmdq_item *);
const struct cmd_entry cmd_wait_for_entry = {
"wait-for", "wait",
"LSU", 1, 1,
"[-L|-S|-U] channel",
0,
cmd_wait_for_exec
.name = "wait-for",
.alias = "wait",
.args = { "LSU", 1, 1 },
.usage = "[-L|-S|-U] channel",
.flags = 0,
.exec = cmd_wait_for_exec
};
struct wait_item {
struct cmdq_item *item;
TAILQ_ENTRY(wait_item) entry;
};
struct wait_channel {
const char *name;
int locked;
int woken;
TAILQ_HEAD(, cmd_q) waiters;
TAILQ_HEAD(, cmd_q) lockers;
TAILQ_HEAD(, wait_item) waiters;
TAILQ_HEAD(, wait_item) lockers;
RB_ENTRY(wait_channel) entry;
};
RB_HEAD(wait_channels, wait_channel);
struct wait_channels wait_channels = RB_INITIALIZER(wait_channels);
static struct wait_channels wait_channels = RB_INITIALIZER(wait_channels);
int wait_channel_cmp(struct wait_channel *, struct wait_channel *);
RB_PROTOTYPE(wait_channels, wait_channel, entry, wait_channel_cmp);
RB_GENERATE(wait_channels, wait_channel, entry, wait_channel_cmp);
static int wait_channel_cmp(struct wait_channel *, struct wait_channel *);
RB_GENERATE_STATIC(wait_channels, wait_channel, entry, wait_channel_cmp);
int
static int
wait_channel_cmp(struct wait_channel *wc1, struct wait_channel *wc2)
{
return (strcmp(wc1->name, wc2->name));
}
enum cmd_retval cmd_wait_for_signal(struct cmd_q *, const char *,
struct wait_channel *);
enum cmd_retval cmd_wait_for_wait(struct cmd_q *, const char *,
struct wait_channel *);
enum cmd_retval cmd_wait_for_lock(struct cmd_q *, const char *,
struct wait_channel *);
enum cmd_retval cmd_wait_for_unlock(struct cmd_q *, const char *,
struct wait_channel *);
static enum cmd_retval cmd_wait_for_signal(struct cmdq_item *, const char *,
struct wait_channel *);
static enum cmd_retval cmd_wait_for_wait(struct cmdq_item *, const char *,
struct wait_channel *);
static enum cmd_retval cmd_wait_for_lock(struct cmdq_item *, const char *,
struct wait_channel *);
static enum cmd_retval cmd_wait_for_unlock(struct cmdq_item *, const char *,
struct wait_channel *);
enum cmd_retval
cmd_wait_for_exec(struct cmd *self, struct cmd_q *cmdq)
static struct wait_channel *cmd_wait_for_add(const char *);
static void cmd_wait_for_remove(struct wait_channel *);
static struct wait_channel *
cmd_wait_for_add(const char *name)
{
struct wait_channel *wc;
wc = xmalloc(sizeof *wc);
wc->name = xstrdup(name);
wc->locked = 0;
wc->woken = 0;
TAILQ_INIT(&wc->waiters);
TAILQ_INIT(&wc->lockers);
RB_INSERT(wait_channels, &wait_channels, wc);
log_debug("add wait channel %s", wc->name);
return (wc);
}
static void
cmd_wait_for_remove(struct wait_channel *wc)
{
if (wc->locked)
return;
if (!TAILQ_EMPTY(&wc->waiters) || !wc->woken)
return;
log_debug("remove wait channel %s", wc->name);
RB_REMOVE(wait_channels, &wait_channels, wc);
free((void *)wc->name);
free(wc);
}
static enum cmd_retval
cmd_wait_for_exec(struct cmd *self, struct cmdq_item *item)
{
struct args *args = self->args;
const char *name = args->argv[0];
@@ -80,85 +128,88 @@ cmd_wait_for_exec(struct cmd *self, struct cmd_q *cmdq)
wc = RB_FIND(wait_channels, &wait_channels, &wc0);
if (args_has(args, 'S'))
return (cmd_wait_for_signal(cmdq, name, wc));
return (cmd_wait_for_signal(item, name, wc));
if (args_has(args, 'L'))
return (cmd_wait_for_lock(cmdq, name, wc));
return (cmd_wait_for_lock(item, name, wc));
if (args_has(args, 'U'))
return (cmd_wait_for_unlock(cmdq, name, wc));
return (cmd_wait_for_wait(cmdq, name, wc));
return (cmd_wait_for_unlock(item, name, wc));
return (cmd_wait_for_wait(item, name, wc));
}
enum cmd_retval
cmd_wait_for_signal(struct cmd_q *cmdq, const char *name,
static enum cmd_retval
cmd_wait_for_signal(__unused struct cmdq_item *item, const char *name,
struct wait_channel *wc)
{
struct cmd_q *wq, *wq1;
struct wait_item *wi, *wi1;
if (wc == NULL || TAILQ_EMPTY(&wc->waiters)) {
cmdq_error(cmdq, "no waiting clients on %s", name);
return (CMD_RETURN_ERROR);
}
TAILQ_FOREACH_SAFE(wq, &wc->waiters, waitentry, wq1) {
TAILQ_REMOVE(&wc->waiters, wq, waitentry);
if (!cmdq_free(wq))
cmdq_continue(wq);
}
if (!wc->locked) {
RB_REMOVE(wait_channels, &wait_channels, wc);
free((void *)wc->name);
free(wc);
if (wc == NULL)
wc = cmd_wait_for_add(name);
if (TAILQ_EMPTY(&wc->waiters) && !wc->woken) {
log_debug("signal wait channel %s, no waiters", wc->name);
wc->woken = 1;
return (CMD_RETURN_NORMAL);
}
log_debug("signal wait channel %s, with waiters", wc->name);
TAILQ_FOREACH_SAFE(wi, &wc->waiters, entry, wi1) {
cmdq_continue(wi->item);
TAILQ_REMOVE(&wc->waiters, wi, entry);
free(wi);
}
cmd_wait_for_remove(wc);
return (CMD_RETURN_NORMAL);
}
enum cmd_retval
cmd_wait_for_wait(struct cmd_q *cmdq, const char *name,
static enum cmd_retval
cmd_wait_for_wait(struct cmdq_item *item, const char *name,
struct wait_channel *wc)
{
if (cmdq->client == NULL || cmdq->client->session != NULL) {
cmdq_error(cmdq, "not able to wait");
struct client *c = item->client;
struct wait_item *wi;
if (c == NULL) {
cmdq_error(item, "not able to wait");
return (CMD_RETURN_ERROR);
}
if (wc == NULL) {
wc = xmalloc(sizeof *wc);
wc->name = xstrdup(name);
wc->locked = 0;
TAILQ_INIT(&wc->waiters);
TAILQ_INIT(&wc->lockers);
RB_INSERT(wait_channels, &wait_channels, wc);
}
if (wc == NULL)
wc = cmd_wait_for_add(name);
TAILQ_INSERT_TAIL(&wc->waiters, cmdq, waitentry);
cmdq->references++;
if (wc->woken) {
log_debug("wait channel %s already woken (%p)", wc->name, c);
cmd_wait_for_remove(wc);
return (CMD_RETURN_NORMAL);
}
log_debug("wait channel %s not woken (%p)", wc->name, c);
wi = xcalloc(1, sizeof *wi);
wi->item = item;
TAILQ_INSERT_TAIL(&wc->waiters, wi, entry);
return (CMD_RETURN_WAIT);
}
enum cmd_retval
cmd_wait_for_lock(struct cmd_q *cmdq, const char *name,
static enum cmd_retval
cmd_wait_for_lock(struct cmdq_item *item, const char *name,
struct wait_channel *wc)
{
if (cmdq->client == NULL || cmdq->client->session != NULL) {
cmdq_error(cmdq, "not able to lock");
struct wait_item *wi;
if (item->client == NULL) {
cmdq_error(item, "not able to lock");
return (CMD_RETURN_ERROR);
}
if (wc == NULL) {
wc = xmalloc(sizeof *wc);
wc->name = xstrdup(name);
wc->locked = 0;
TAILQ_INIT(&wc->waiters);
TAILQ_INIT(&wc->lockers);
RB_INSERT(wait_channels, &wait_channels, wc);
}
if (wc == NULL)
wc = cmd_wait_for_add(name);
if (wc->locked) {
TAILQ_INSERT_TAIL(&wc->lockers, cmdq, waitentry);
cmdq->references++;
wi = xcalloc(1, sizeof *wi);
wi->item = item;
TAILQ_INSERT_TAIL(&wc->lockers, wi, entry);
return (CMD_RETURN_WAIT);
}
wc->locked = 1;
@@ -166,28 +217,24 @@ cmd_wait_for_lock(struct cmd_q *cmdq, const char *name,
return (CMD_RETURN_NORMAL);
}
enum cmd_retval
cmd_wait_for_unlock(struct cmd_q *cmdq, const char *name,
static enum cmd_retval
cmd_wait_for_unlock(struct cmdq_item *item, const char *name,
struct wait_channel *wc)
{
struct cmd_q *wq;
struct wait_item *wi;
if (wc == NULL || !wc->locked) {
cmdq_error(cmdq, "channel %s not locked", name);
cmdq_error(item, "channel %s not locked", name);
return (CMD_RETURN_ERROR);
}
if ((wq = TAILQ_FIRST(&wc->lockers)) != NULL) {
TAILQ_REMOVE(&wc->lockers, wq, waitentry);
if (!cmdq_free(wq))
cmdq_continue(wq);
if ((wi = TAILQ_FIRST(&wc->lockers)) != NULL) {
cmdq_continue(wi->item);
TAILQ_REMOVE(&wc->lockers, wi, entry);
free(wi);
} else {
wc->locked = 0;
if (TAILQ_EMPTY(&wc->waiters)) {
RB_REMOVE(wait_channels, &wait_channels, wc);
free((void *)wc->name);
free(wc);
}
cmd_wait_for_remove(wc);
}
return (CMD_RETURN_NORMAL);
@@ -197,21 +244,21 @@ void
cmd_wait_for_flush(void)
{
struct wait_channel *wc, *wc1;
struct cmd_q *wq, *wq1;
struct wait_item *wi, *wi1;
RB_FOREACH_SAFE(wc, wait_channels, &wait_channels, wc1) {
TAILQ_FOREACH_SAFE(wq, &wc->waiters, waitentry, wq1) {
TAILQ_REMOVE(&wc->waiters, wq, waitentry);
if (!cmdq_free(wq))
cmdq_continue(wq);
TAILQ_FOREACH_SAFE(wi, &wc->waiters, entry, wi1) {
cmdq_continue(wi->item);
TAILQ_REMOVE(&wc->waiters, wi, entry);
free(wi);
}
while ((wq = TAILQ_FIRST(&wc->lockers)) != NULL) {
TAILQ_REMOVE(&wc->lockers, wq, waitentry);
if (!cmdq_free(wq))
cmdq_continue(wq);
wc->woken = 1;
TAILQ_FOREACH_SAFE(wi, &wc->lockers, entry, wi1) {
cmdq_continue(wi->item);
TAILQ_REMOVE(&wc->lockers, wi, entry);
free(wi);
}
RB_REMOVE(wait_channels, &wait_channels, wc);
free((void *)wc->name);
free(wc);
wc->locked = 0;
cmd_wait_for_remove(wc);
}
}

1357
cmd.c

File diff suppressed because it is too large Load Diff

342
colour.c
View File

@@ -1,7 +1,8 @@
/* $OpenBSD$ */
/*
* Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2008 Nicholas Marriott <nicholas.marriott@gmail.com>
* Copyright (c) 2016 Avi Halachmi <avihpit@yahoo.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -24,120 +25,83 @@
#include "tmux.h"
static int
colour_dist_sq(int R, int G, int B, int r, int g, int b)
{
return ((R - r) * (R - r) + (G - g) * (G - g) + (B - b) * (B - b));
}
static int
colour_to_6cube(int v)
{
if (v < 48)
return (0);
if (v < 114)
return (1);
return ((v - 35) / 40);
}
/*
* Colour to string conversion functions. Bit 8 of the colour means it is one
* of the 256 colour palette.
* Convert an RGB triplet to the xterm(1) 256 colour palette.
*
* xterm provides a 6x6x6 colour cube (16 - 231) and 24 greys (232 - 255). We
* map our RGB colour to the closest in the cube, also work out the closest
* grey, and use the nearest of the two.
*
* Note that the xterm has much lower resolution for darker colours (they are
* not evenly spread out), so our 6 levels are not evenly spread: 0x0, 0x5f
* (95), 0x87 (135), 0xaf (175), 0xd7 (215) and 0xff (255). Greys are more
* evenly spread (8, 18, 28 ... 238).
*/
/* An RGB colour. */
struct colour_rgb {
u_char r;
u_char g;
u_char b;
};
/* 256 colour RGB table, generated on first use. */
struct colour_rgb *colour_rgb_256;
void colour_rgb_generate256(void);
u_int colour_rgb_distance(struct colour_rgb *, struct colour_rgb *);
int colour_rgb_find(struct colour_rgb *);
/* Generate 256 colour RGB table. */
void
colour_rgb_generate256(void)
{
struct colour_rgb *rgb;
u_int i, r, g, b;
/*
* Allocate the table. The first 16 colours are often changed by users
* and terminals so don't include them.
*/
colour_rgb_256 = xcalloc(240, sizeof *colour_rgb_256);
/* Add the colours first. */
r = g = b = 0;
for (i = 240; i > 24; i--) {
rgb = &colour_rgb_256[240 - i];
if (r != 0)
rgb->r = (r * 40) + 55;
if (g != 0)
rgb->g = (g * 40) + 55;
if (b != 0)
rgb->b = (b * 40) + 55;
b++;
if (b > 5) {
b = 0;
g++;
}
if (g > 5) {
g = 0;
r++;
}
}
/* Then add the greys. */
for (i = 24; i > 0; i--) {
rgb = &colour_rgb_256[240 - i];
rgb->r = 8 + (24 - i) * 10;
rgb->g = 8 + (24 - i) * 10;
rgb->b = 8 + (24 - i) * 10;
}
}
/* Get colour RGB distance. */
u_int
colour_rgb_distance(struct colour_rgb *rgb1, struct colour_rgb *rgb2)
{
int r, g, b;
r = rgb1->r - rgb2->r;
g = rgb1->g - rgb2->g;
b = rgb1->b - rgb2->b;
return (r * r + g * g + b * b);
}
/* Work out the nearest colour from the 256 colour set. */
int
colour_rgb_find(struct colour_rgb *rgb)
colour_find_rgb(u_char r, u_char g, u_char b)
{
u_int distance, lowest, colour, i;
static const int q2c[6] = { 0x00, 0x5f, 0x87, 0xaf, 0xd7, 0xff };
int qr, qg, qb, cr, cg, cb, d, idx;
int grey_avg, grey_idx, grey;
if (colour_rgb_256 == NULL)
colour_rgb_generate256();
/* Map RGB to 6x6x6 cube. */
qr = colour_to_6cube(r); cr = q2c[qr];
qg = colour_to_6cube(g); cg = q2c[qg];
qb = colour_to_6cube(b); cb = q2c[qb];
colour = 16;
lowest = UINT_MAX;
for (i = 0; i < 240; i++) {
distance = colour_rgb_distance(&colour_rgb_256[i], rgb);
if (distance < lowest) {
lowest = distance;
colour = 16 + i;
}
}
return (colour);
/* If we have hit the colour exactly, return early. */
if (cr == r && cg == g && cb == b)
return ((16 + (36 * qr) + (6 * qg) + qb) | COLOUR_FLAG_256);
/* Work out the closest grey (average of RGB). */
grey_avg = (r + g + b) / 3;
if (grey_avg > 238)
grey_idx = 23;
else
grey_idx = (grey_avg - 3) / 10;
grey = 8 + (10 * grey_idx);
/* Is grey or 6x6x6 colour closest? */
d = colour_dist_sq(cr, cg, cb, r, g, b);
if (colour_dist_sq(grey, grey, grey, r, g, b) < d)
idx = 232 + grey_idx;
else
idx = 16 + (36 * qr) + (6 * qg) + qb;
return (idx | COLOUR_FLAG_256);
}
/* Set grid cell foreground colour. */
void
colour_set_fg(struct grid_cell *gc, int c)
/* Join RGB into a colour. */
int
colour_join_rgb(u_char r, u_char g, u_char b)
{
if (c & 0x100)
gc->flags |= GRID_FLAG_FG256;
gc->fg = c;
return ((((int)((r) & 0xff)) << 16) |
(((int)((g) & 0xff)) << 8) |
(((int)((b) & 0xff))) | COLOUR_FLAG_RGB);
}
/* Set grid cell background colour. */
/* Split colour into RGB. */
void
colour_set_bg(struct grid_cell *gc, int c)
colour_split_rgb(int c, u_char *r, u_char *g, u_char *b)
{
if (c & 0x100)
gc->flags |= GRID_FLAG_BG256;
gc->bg = c;
*r = (c >> 16) & 0xff;
*g = (c >> 8) & 0xff;
*b = c & 0xff;
}
/* Convert colour to a string. */
@@ -145,9 +109,16 @@ const char *
colour_tostring(int c)
{
static char s[32];
u_char r, g, b;
if (c & 0x100) {
xsnprintf(s, sizeof s, "colour%u", c & ~0x100);
if (c & COLOUR_FLAG_RGB) {
colour_split_rgb(c, &r, &g, &b);
xsnprintf(s, sizeof s, "#%02x%02x%02x", r, g, b);
return (s);
}
if (c & COLOUR_FLAG_256) {
xsnprintf(s, sizeof s, "colour%u", c & 0xff);
return (s);
}
@@ -170,6 +141,8 @@ colour_tostring(int c)
return ("white");
case 8:
return ("default");
case 9:
return ("terminal");
case 90:
return ("brightblack");
case 91:
@@ -187,86 +160,155 @@ colour_tostring(int c)
case 97:
return ("brightwhite");
}
return (NULL);
return ("invalid");
}
/* Convert colour from string. */
int
colour_fromstring(const char *s)
{
const char *errstr;
const char *cp;
struct colour_rgb rgb;
int n;
const char *errstr;
const char *cp;
int n;
u_char r, g, b;
if (*s == '#' && strlen(s) == 7) {
for (cp = s + 1; isxdigit((u_char) *cp); cp++)
;
if (*cp != '\0')
return (-1);
n = sscanf(s + 1, "%2hhx%2hhx%2hhx", &rgb.r, &rgb.g, &rgb.b);
n = sscanf(s + 1, "%2hhx%2hhx%2hhx", &r, &g, &b);
if (n != 3)
return (-1);
return (colour_rgb_find(&rgb) | 0x100);
return (colour_join_rgb(r, g, b));
}
if (strncasecmp(s, "colour", (sizeof "colour") - 1) == 0) {
n = strtonum(s + (sizeof "colour") - 1, 0, 255, &errstr);
if (errstr != NULL)
return (-1);
return (n | 0x100);
return (n | COLOUR_FLAG_256);
}
if (strcasecmp(s, "black") == 0 || (s[0] == '0' && s[1] == '\0'))
return (0);
if (strcasecmp(s, "red") == 0 || (s[0] == '1' && s[1] == '\0'))
return (1);
if (strcasecmp(s, "green") == 0 || (s[0] == '2' && s[1] == '\0'))
return (2);
if (strcasecmp(s, "yellow") == 0 || (s[0] == '3' && s[1] == '\0'))
return (3);
if (strcasecmp(s, "blue") == 0 || (s[0] == '4' && s[1] == '\0'))
return (4);
if (strcasecmp(s, "magenta") == 0 || (s[0] == '5' && s[1] == '\0'))
return (5);
if (strcasecmp(s, "cyan") == 0 || (s[0] == '6' && s[1] == '\0'))
return (6);
if (strcasecmp(s, "white") == 0 || (s[0] == '7' && s[1] == '\0'))
return (7);
if (strcasecmp(s, "default") == 0 || (s[0] == '8' && s[1] == '\0'))
if (strcasecmp(s, "default") == 0)
return (8);
if (strcasecmp(s, "brightblack") == 0 ||
(s[0] == '9' && s[1] == '0' && s[2] == '\0'))
if (strcasecmp(s, "terminal") == 0)
return (9);
if (strcasecmp(s, "black") == 0 || strcmp(s, "0") == 0)
return (0);
if (strcasecmp(s, "red") == 0 || strcmp(s, "1") == 0)
return (1);
if (strcasecmp(s, "green") == 0 || strcmp(s, "2") == 0)
return (2);
if (strcasecmp(s, "yellow") == 0 || strcmp(s, "3") == 0)
return (3);
if (strcasecmp(s, "blue") == 0 || strcmp(s, "4") == 0)
return (4);
if (strcasecmp(s, "magenta") == 0 || strcmp(s, "5") == 0)
return (5);
if (strcasecmp(s, "cyan") == 0 || strcmp(s, "6") == 0)
return (6);
if (strcasecmp(s, "white") == 0 || strcmp(s, "7") == 0)
return (7);
if (strcasecmp(s, "brightblack") == 0 || strcmp(s, "90") == 0)
return (90);
if (strcasecmp(s, "brightred") == 0 ||
(s[0] == '9' && s[1] == '1' && s[2] == '\0'))
if (strcasecmp(s, "brightred") == 0 || strcmp(s, "91") == 0)
return (91);
if (strcasecmp(s, "brightgreen") == 0 ||
(s[0] == '9' && s[1] == '2' && s[2] == '\0'))
if (strcasecmp(s, "brightgreen") == 0 || strcmp(s, "92") == 0)
return (92);
if (strcasecmp(s, "brightyellow") == 0 ||
(s[0] == '9' && s[1] == '3' && s[2] == '\0'))
if (strcasecmp(s, "brightyellow") == 0 || strcmp(s, "93") == 0)
return (93);
if (strcasecmp(s, "brightblue") == 0 ||
(s[0] == '9' && s[1] == '4' && s[2] == '\0'))
if (strcasecmp(s, "brightblue") == 0 || strcmp(s, "94") == 0)
return (94);
if (strcasecmp(s, "brightmagenta") == 0 ||
(s[0] == '9' && s[1] == '5' && s[2] == '\0'))
if (strcasecmp(s, "brightmagenta") == 0 || strcmp(s, "95") == 0)
return (95);
if (strcasecmp(s, "brightcyan") == 0 ||
(s[0] == '9' && s[1] == '6' && s[2] == '\0'))
if (strcasecmp(s, "brightcyan") == 0 || strcmp(s, "96") == 0)
return (96);
if (strcasecmp(s, "brightwhite") == 0 ||
(s[0] == '9' && s[1] == '7' && s[2] == '\0'))
if (strcasecmp(s, "brightwhite") == 0 || strcmp(s, "97") == 0)
return (97);
return (-1);
}
/* Convert 256 colour palette to 16. */
u_char
colour_256to16(u_char c)
/* Convert 256 colour to RGB colour. */
int
colour_256toRGB(int c)
{
static const u_char table[256] = {
static const int table[256] = {
0x000000, 0x800000, 0x008000, 0x808000,
0x000080, 0x800080, 0x008080, 0xc0c0c0,
0x808080, 0xff0000, 0x00ff00, 0xffff00,
0x0000ff, 0xff00ff, 0x00ffff, 0xffffff,
0x000000, 0x00005f, 0x000087, 0x0000af,
0x0000d7, 0x0000ff, 0x005f00, 0x005f5f,
0x005f87, 0x005faf, 0x005fd7, 0x005fff,
0x008700, 0x00875f, 0x008787, 0x0087af,
0x0087d7, 0x0087ff, 0x00af00, 0x00af5f,
0x00af87, 0x00afaf, 0x00afd7, 0x00afff,
0x00d700, 0x00d75f, 0x00d787, 0x00d7af,
0x00d7d7, 0x00d7ff, 0x00ff00, 0x00ff5f,
0x00ff87, 0x00ffaf, 0x00ffd7, 0x00ffff,
0x5f0000, 0x5f005f, 0x5f0087, 0x5f00af,
0x5f00d7, 0x5f00ff, 0x5f5f00, 0x5f5f5f,
0x5f5f87, 0x5f5faf, 0x5f5fd7, 0x5f5fff,
0x5f8700, 0x5f875f, 0x5f8787, 0x5f87af,
0x5f87d7, 0x5f87ff, 0x5faf00, 0x5faf5f,
0x5faf87, 0x5fafaf, 0x5fafd7, 0x5fafff,
0x5fd700, 0x5fd75f, 0x5fd787, 0x5fd7af,
0x5fd7d7, 0x5fd7ff, 0x5fff00, 0x5fff5f,
0x5fff87, 0x5fffaf, 0x5fffd7, 0x5fffff,
0x870000, 0x87005f, 0x870087, 0x8700af,
0x8700d7, 0x8700ff, 0x875f00, 0x875f5f,
0x875f87, 0x875faf, 0x875fd7, 0x875fff,
0x878700, 0x87875f, 0x878787, 0x8787af,
0x8787d7, 0x8787ff, 0x87af00, 0x87af5f,
0x87af87, 0x87afaf, 0x87afd7, 0x87afff,
0x87d700, 0x87d75f, 0x87d787, 0x87d7af,
0x87d7d7, 0x87d7ff, 0x87ff00, 0x87ff5f,
0x87ff87, 0x87ffaf, 0x87ffd7, 0x87ffff,
0xaf0000, 0xaf005f, 0xaf0087, 0xaf00af,
0xaf00d7, 0xaf00ff, 0xaf5f00, 0xaf5f5f,
0xaf5f87, 0xaf5faf, 0xaf5fd7, 0xaf5fff,
0xaf8700, 0xaf875f, 0xaf8787, 0xaf87af,
0xaf87d7, 0xaf87ff, 0xafaf00, 0xafaf5f,
0xafaf87, 0xafafaf, 0xafafd7, 0xafafff,
0xafd700, 0xafd75f, 0xafd787, 0xafd7af,
0xafd7d7, 0xafd7ff, 0xafff00, 0xafff5f,
0xafff87, 0xafffaf, 0xafffd7, 0xafffff,
0xd70000, 0xd7005f, 0xd70087, 0xd700af,
0xd700d7, 0xd700ff, 0xd75f00, 0xd75f5f,
0xd75f87, 0xd75faf, 0xd75fd7, 0xd75fff,
0xd78700, 0xd7875f, 0xd78787, 0xd787af,
0xd787d7, 0xd787ff, 0xd7af00, 0xd7af5f,
0xd7af87, 0xd7afaf, 0xd7afd7, 0xd7afff,
0xd7d700, 0xd7d75f, 0xd7d787, 0xd7d7af,
0xd7d7d7, 0xd7d7ff, 0xd7ff00, 0xd7ff5f,
0xd7ff87, 0xd7ffaf, 0xd7ffd7, 0xd7ffff,
0xff0000, 0xff005f, 0xff0087, 0xff00af,
0xff00d7, 0xff00ff, 0xff5f00, 0xff5f5f,
0xff5f87, 0xff5faf, 0xff5fd7, 0xff5fff,
0xff8700, 0xff875f, 0xff8787, 0xff87af,
0xff87d7, 0xff87ff, 0xffaf00, 0xffaf5f,
0xffaf87, 0xffafaf, 0xffafd7, 0xffafff,
0xffd700, 0xffd75f, 0xffd787, 0xffd7af,
0xffd7d7, 0xffd7ff, 0xffff00, 0xffff5f,
0xffff87, 0xffffaf, 0xffffd7, 0xffffff,
0x080808, 0x121212, 0x1c1c1c, 0x262626,
0x303030, 0x3a3a3a, 0x444444, 0x4e4e4e,
0x585858, 0x626262, 0x6c6c6c, 0x767676,
0x808080, 0x8a8a8a, 0x949494, 0x9e9e9e,
0xa8a8a8, 0xb2b2b2, 0xbcbcbc, 0xc6c6c6,
0xd0d0d0, 0xdadada, 0xe4e4e4, 0xeeeeee
};
return (table[c & 0xff] | COLOUR_FLAG_RGB);
}
/* Convert 256 colour to 16 colour. */
int
colour_256to16(int c)
{
static const char table[256] = {
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15,
0, 4, 4, 4, 12, 12, 2, 6, 4, 4, 12, 12, 2, 2, 6, 4,
12, 12, 2, 2, 2, 6, 12, 12, 10, 10, 10, 10, 14, 12, 10, 10,
@@ -285,5 +327,5 @@ colour_256to16(u_char c)
8, 8, 8, 8, 7, 7, 7, 7, 7, 7, 15, 15, 15, 15, 15, 15
};
return (table[c]);
return (table[c & 0xff]);
}

181
compat.h
View File

@@ -1,7 +1,5 @@
/* $Id$ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2007 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -19,10 +17,23 @@
#ifndef COMPAT_H
#define COMPAT_H
#include <sys/types.h>
#include <sys/ioctl.h>
#include <sys/uio.h>
#include <fnmatch.h>
#include <limits.h>
#include <stdio.h>
#include <termios.h>
#include <wchar.h>
#ifndef __GNUC__
#define __attribute__(a)
#endif
#ifndef __unused
#define __unused __attribute__ ((__unused__))
#endif
#ifndef __dead
#define __dead __attribute__ ((__noreturn__))
#endif
@@ -34,21 +45,61 @@
#define ECHOPRT 0
#endif
#ifndef HAVE_BSD_TYPES
typedef uint8_t u_int8_t;
typedef uint16_t u_int16_t;
typedef uint32_t u_int32_t;
typedef uint64_t u_int64_t;
#ifndef ACCESSPERMS
#define ACCESSPERMS (S_IRWXU|S_IRWXG|S_IRWXO)
#endif
#ifndef HAVE_PATHS_H
#define _PATH_BSHELL "/bin/sh"
#define _PATH_TMP "/tmp/"
#if !defined(FIONREAD) && defined(__sun)
#include <sys/filio.h>
#endif
#ifdef HAVE_ERR_H
#include <err.h>
#else
void err(int, const char *, ...);
void errx(int, const char *, ...);
void warn(const char *, ...);
void warnx(const char *, ...);
#endif
#ifdef HAVE_PATHS_H
#include <paths.h>
#endif
#ifndef _PATH_BSHELL
#define _PATH_BSHELL "/bin/sh"
#endif
#ifndef _PATH_TMP
#define _PATH_TMP "/tmp/"
#endif
#ifndef _PATH_DEVNULL
#define _PATH_DEVNULL "/dev/null"
#endif
#ifndef _PATH_TTY
#define _PATH_TTY "/dev/tty"
#endif
#ifndef _PATH_DEV
#define _PATH_DEV "/dev/"
#endif
#ifndef _PATH_DEFPATH
#define _PATH_DEFPATH "/usr/bin:/bin"
#endif
#ifndef __OpenBSD__
#define pledge(s, p) (0)
#endif
#ifdef HAVE_STDINT_H
#include <stdint.h>
#else
#include <inttypes.h>
#endif
#ifdef HAVE_QUEUE_H
#include <sys/queue.h>
#else
@@ -67,21 +118,17 @@ typedef uint64_t u_int64_t;
#include "compat/bitstring.h"
#endif
#ifdef HAVE_PATHS_H
#include <paths.h>
#endif
#ifdef HAVE_FORKPTY
#ifdef HAVE_LIBUTIL_H
#include <libutil.h>
#endif
#ifdef HAVE_PTY_H
#include <pty.h>
#endif
#ifdef HAVE_UTIL_H
#include <util.h>
#endif
#endif
#ifdef HAVE_VIS
#include <vis.h>
@@ -95,12 +142,6 @@ typedef uint64_t u_int64_t;
#include "compat/imsg.h"
#endif
#ifdef HAVE_STDINT_H
#include <stdint.h>
#else
#include <inttypes.h>
#endif
#ifdef BROKEN_CMSG_FIRSTHDR
#undef CMSG_FIRSTHDR
#define CMSG_FIRSTHDR(mhdr) \
@@ -129,6 +170,14 @@ typedef uint64_t u_int64_t;
#define O_DIRECTORY 0
#endif
#ifndef FNM_CASEFOLD
#ifdef FNM_IGNORECASE
#define FNM_CASEFOLD FNM_IGNORECASE
#else
#define FNM_CASEFOLD 0
#endif
#endif
#ifndef INFTIM
#define INFTIM -1
#endif
@@ -187,14 +236,19 @@ typedef uint64_t u_int64_t;
#define flock(fd, op) (0)
#endif
#ifndef HAVE_BZERO
#undef bzero
#define bzero(buf, len) memset(buf, 0, len);
#ifndef HAVE_EXPLICIT_BZERO
/* explicit_bzero.c */
void explicit_bzero(void *, size_t);
#endif
#ifndef HAVE_GETDTABLECOUNT
/* getdtablecount.c */
int getdtablecount(void);
#endif
#ifndef HAVE_CLOSEFROM
/* closefrom.c */
void closefrom(int);
void closefrom(int);
#endif
#ifndef HAVE_STRCASESTR
@@ -222,20 +276,53 @@ size_t strlcpy(char *, const char *, size_t);
size_t strlcat(char *, const char *, size_t);
#endif
#ifndef HAVE_STRNLEN
/* strnlen.c */
size_t strnlen(const char *, size_t);
#endif
#ifndef HAVE_STRNDUP
/* strndup.c */
char *strndup(const char *, size_t);
#endif
#ifndef HAVE_MEMMEM
/* memmem.c */
void *memmem(const void *, size_t, const void *, size_t);
#endif
#ifndef HAVE_DAEMON
/* daemon.c */
int daemon(int, int);
#endif
#ifndef HAVE_GETPROGNAME
/* getprogname.c */
const char *getprogname(void);
#endif
#ifndef HAVE_SETPROCTITLE
/* setproctitle.c */
void setproctitle(const char *, ...);
#endif
#ifndef HAVE_B64_NTOP
/* b64_ntop.c */
#undef b64_ntop /* for Cygwin */
/* base64.c */
#undef b64_ntop
#undef b64_pton
int b64_ntop(const char *, size_t, char *, size_t);
int b64_pton(const char *, u_char *, size_t);
#endif
#ifndef HAVE_FDFORKPTY
/* fdforkpty.c */
int getptmfd(void);
pid_t fdforkpty(int, int *, char *, struct termios *,
struct winsize *);
#endif
#ifndef HAVE_FORKPTY
/* forkpty.c */
#include <sys/ioctl.h>
pid_t forkpty(int *, char *, struct termios *, struct winsize *);
#endif
@@ -250,10 +337,6 @@ int vasprintf(char **, const char *, va_list);
char *fgetln(FILE *, size_t *);
#endif
#ifndef HAVE_FPARSELN
char *fparseln(FILE *, size_t *, size_t *, const char *, int);
#endif
#ifndef HAVE_SETENV
/* setenv.c */
int setenv(const char *, const char *, int);
@@ -262,18 +345,31 @@ int unsetenv(const char *);
#ifndef HAVE_CFMAKERAW
/* cfmakeraw.c */
void cfmakeraw(struct termios *);
void cfmakeraw(struct termios *);
#endif
#ifndef HAVE_OPENAT
/* openat.c */
#define AT_FDCWD -100
int openat(int, const char *, int, ...);
#ifndef HAVE_FREEZERO
/* freezero.c */
void freezero(void *, size_t);
#endif
#ifndef HAVE_REALLOCARRAY
/* reallocarray.c */
void *reallocarray(void *, size_t, size_t);
#endif
#ifndef HAVE_RECALLOCARRAY
/* recallocarray.c */
void *recallocarray(void *, size_t, size_t, size_t);
#endif
#ifdef HAVE_UTF8PROC
/* utf8proc.c */
int utf8proc_wcwidth(wchar_t);
int utf8proc_mbtowc(wchar_t *, const char *, size_t);
int utf8proc_wctomb(char *, wchar_t);
#endif
#ifdef HAVE_GETOPT
#include <getopt.h>
#else
/* getopt.c */
extern int BSDopterr;
extern int BSDoptind;
@@ -287,6 +383,5 @@ int BSDgetopt(int, char *const *, const char *);
#define optopt BSDoptopt
#define optreset BSDoptreset
#define optarg BSDoptarg
#endif
#endif /* COMPAT_H */

View File

@@ -1,5 +1,5 @@
/*
* Copyright (c) 2006 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2006 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -14,16 +14,15 @@
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include <sys/types.h>
#include <stdarg.h>
#include <stdio.h>
#ifdef HAVE_STDINT_H
#include <stdint.h>
#else
#include <inttypes.h>
#endif
#include <string.h>
#include <stdlib.h>
#include "tmux.h"
#include "compat.h"
#include "xmalloc.h"
int
asprintf(char **ret, const char *fmt, ...)

View File

@@ -1,5 +1,7 @@
/* $OpenBSD: base64.c,v 1.8 2015/01/16 16:48:51 deraadt Exp $ */
/*
* Copyright (c) 1996, 1998 by Internet Software Consortium.
* Copyright (c) 1996 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -41,19 +43,18 @@
*/
#include <sys/types.h>
#include <sys/param.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <arpa/nameser.h>
#include <ctype.h>
#include <resolv.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define Assert(Cond) if (!(Cond)) abort()
static const char Base64[] =
"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
static const char Pad64 = '=';
@@ -122,11 +123,16 @@ static const char Pad64 = '=';
*/
int
b64_ntop(uint8_t const *src, size_t srclength, char *target, size_t targsize) {
b64_ntop(src, srclength, target, targsize)
u_char const *src;
size_t srclength;
char *target;
size_t targsize;
{
size_t datalength = 0;
uint8_t input[3];
uint8_t output[4];
size_t i;
u_char input[3];
u_char output[4];
int i;
while (2 < srclength) {
input[0] = *src++;
@@ -138,10 +144,6 @@ b64_ntop(uint8_t const *src, size_t srclength, char *target, size_t targsize) {
output[1] = ((input[0] & 0x03) << 4) + (input[1] >> 4);
output[2] = ((input[1] & 0x0f) << 2) + (input[2] >> 6);
output[3] = input[2] & 0x3f;
Assert(output[0] < 64);
Assert(output[1] < 64);
Assert(output[2] < 64);
Assert(output[3] < 64);
if (datalength + 4 > targsize)
return (-1);
@@ -161,9 +163,6 @@ b64_ntop(uint8_t const *src, size_t srclength, char *target, size_t targsize) {
output[0] = input[0] >> 2;
output[1] = ((input[0] & 0x03) << 4) + (input[1] >> 4);
output[2] = ((input[1] & 0x0f) << 2) + (input[2] >> 6);
Assert(output[0] < 64);
Assert(output[1] < 64);
Assert(output[2] < 64);
if (datalength + 4 > targsize)
return (-1);
@@ -180,3 +179,137 @@ b64_ntop(uint8_t const *src, size_t srclength, char *target, size_t targsize) {
target[datalength] = '\0'; /* Returned value doesn't count \0. */
return (datalength);
}
/* skips all whitespace anywhere.
converts characters, four at a time, starting at (or after)
src from base - 64 numbers into three 8 bit bytes in the target area.
it returns the number of data bytes stored at the target, or -1 on error.
*/
int
b64_pton(src, target, targsize)
char const *src;
u_char *target;
size_t targsize;
{
int tarindex, state, ch;
u_char nextbyte;
char *pos;
state = 0;
tarindex = 0;
while ((ch = (unsigned char)*src++) != '\0') {
if (isspace(ch)) /* Skip whitespace anywhere. */
continue;
if (ch == Pad64)
break;
pos = strchr(Base64, ch);
if (pos == 0) /* A non-base64 character. */
return (-1);
switch (state) {
case 0:
if (target) {
if (tarindex >= targsize)
return (-1);
target[tarindex] = (pos - Base64) << 2;
}
state = 1;
break;
case 1:
if (target) {
if (tarindex >= targsize)
return (-1);
target[tarindex] |= (pos - Base64) >> 4;
nextbyte = ((pos - Base64) & 0x0f) << 4;
if (tarindex + 1 < targsize)
target[tarindex+1] = nextbyte;
else if (nextbyte)
return (-1);
}
tarindex++;
state = 2;
break;
case 2:
if (target) {
if (tarindex >= targsize)
return (-1);
target[tarindex] |= (pos - Base64) >> 2;
nextbyte = ((pos - Base64) & 0x03) << 6;
if (tarindex + 1 < targsize)
target[tarindex+1] = nextbyte;
else if (nextbyte)
return (-1);
}
tarindex++;
state = 3;
break;
case 3:
if (target) {
if (tarindex >= targsize)
return (-1);
target[tarindex] |= (pos - Base64);
}
tarindex++;
state = 0;
break;
}
}
/*
* We are done decoding Base-64 chars. Let's see if we ended
* on a byte boundary, and/or with erroneous trailing characters.
*/
if (ch == Pad64) { /* We got a pad char. */
ch = (unsigned char)*src++; /* Skip it, get next. */
switch (state) {
case 0: /* Invalid = in first position */
case 1: /* Invalid = in second position */
return (-1);
case 2: /* Valid, means one byte of info */
/* Skip any number of spaces. */
for (; ch != '\0'; ch = (unsigned char)*src++)
if (!isspace(ch))
break;
/* Make sure there is another trailing = sign. */
if (ch != Pad64)
return (-1);
ch = (unsigned char)*src++; /* Skip the = */
/* Fall through to "single trailing =" case. */
/* FALLTHROUGH */
case 3: /* Valid, means two bytes of info */
/*
* We know this char is an =. Is there anything but
* whitespace after it?
*/
for (; ch != '\0'; ch = (unsigned char)*src++)
if (!isspace(ch))
return (-1);
/*
* Now make sure for cases 2 and 3 that the "extra"
* bits that slopped past the last full byte were
* zeros. If we don't check them, they become a
* subliminal channel.
*/
if (target && tarindex < targsize &&
target[tarindex] != 0)
return (-1);
}
} else {
/*
* We ended by seeing the end of the string. Make sure we
* have no partial bytes lying around.
*/
if (state != 0)
return (-1);
}
return (tarindex);
}

View File

@@ -1,6 +1,6 @@
/*
* Copyright (c) 2013 Dagobert Michelsen
* Copyright (c) 2013 Nicholas Marriott <nicm@users.sourceforge.net>
* Copyright (c) 2013 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
@@ -15,9 +15,12 @@
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include <string.h>
#include <sys/types.h>
#include "tmux.h"
#include <string.h>
#include <termios.h>
#include "compat.h"
void
cfmakeraw(struct termios *tio)

View File

@@ -14,8 +14,6 @@
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include "tmux.h"
#ifndef HAVE_CLOSEFROM
#include <sys/types.h>
@@ -47,6 +45,8 @@
# endif
#endif
#include "compat.h"
#ifndef OPEN_MAX
# define OPEN_MAX 256
#endif

85
compat/daemon-darwin.c Normal file
View File

@@ -0,0 +1,85 @@
/*
* Copyright (c) 2017 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* 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.
*/
/*
* Copyright (c) 2011-2013, Chris Johnsen <chris_johnsen@pobox.com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
*
* 1. Redistributions of source code must retain the above
* copyright notice, this list of conditions and the following
* disclaimer.
*
* 2. Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following
* disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
* COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
* ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <sys/types.h>
#include <mach/mach.h>
#include <Availability.h>
#include <unistd.h>
void daemon_darwin(void);
#ifdef __MAC_10_10
extern kern_return_t bootstrap_look_up_per_user(mach_port_t, const char *,
uid_t, mach_port_t *);
extern kern_return_t bootstrap_get_root(mach_port_t, mach_port_t *);
void
daemon_darwin(void)
{
mach_port_t root = MACH_PORT_NULL;
mach_port_t s = MACH_PORT_NULL;
uid_t uid;
uid = getuid();
if (bootstrap_get_root(bootstrap_port, &root) == KERN_SUCCESS &&
bootstrap_look_up_per_user(root, NULL, uid, &s) == KERN_SUCCESS &&
task_set_bootstrap_port(mach_task_self(), s) == KERN_SUCCESS &&
mach_port_deallocate(mach_task_self(), bootstrap_port) == KERN_SUCCESS)
bootstrap_port = s;
}
#else
void
daemon_darwin(void)
{
}
#endif

View File

@@ -28,11 +28,17 @@
* SUCH DAMAGE.
*/
#include <sys/types.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdlib.h>
#include "tmux.h"
#include "compat.h"
#ifdef __APPLE__
extern void daemon_darwin(void);
#endif
int
daemon(int nochdir, int noclose)
@@ -61,5 +67,9 @@ daemon(int nochdir, int noclose)
if (fd > 2)
(void)close (fd);
}
#ifdef __APPLE__
daemon_darwin();
#endif
return (0);
}

93
compat/err.c Normal file
View File

@@ -0,0 +1,93 @@
/*
* Copyright (c) 2017 Nicholas Marriott <nicholas.marriott@gmail.com>
*
* 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 <errno.h>
#include <stdarg.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include "compat.h"
void
err(int eval, const char *fmt, ...)
{
va_list ap;
int saved_errno = errno;
fprintf(stderr, "%s: ", getprogname());
va_start(ap, fmt);
if (fmt != NULL) {
vfprintf(stderr, fmt, ap);
fprintf(stderr, ": ");
}
va_end(ap);
fprintf(stderr, "%s\n", strerror(saved_errno));
exit(eval);
}
void
errx(int eval, const char *fmt, ...)
{
va_list ap;
fprintf(stderr, "%s: ", getprogname());
va_start(ap, fmt);
if (fmt != NULL)
vfprintf(stderr, fmt, ap);
va_end(ap);
putc('\n', stderr);
exit(eval);
}
void
warn(const char *fmt, ...)
{
va_list ap;
int saved_errno = errno;
fprintf(stderr, "%s: ", getprogname());
va_start(ap, fmt);
if (fmt != NULL) {
vfprintf(stderr, fmt, ap);
fprintf(stderr, ": ");
}
va_end(ap);
fprintf(stderr, "%s\n", strerror(saved_errno));
}
void
warnx(const char *fmt, ...)
{
va_list ap;
fprintf(stderr, "%s: ", getprogname());
va_start(ap, fmt);
if (fmt != NULL)
vfprintf(stderr, fmt, ap);
va_end(ap);
putc('\n', stderr);
}

15
compat/explicit_bzero.c Normal file
View File

@@ -0,0 +1,15 @@
/* $OpenBSD: explicit_bzero.c,v 1.4 2015/08/31 02:53:57 guenther Exp $ */
/*
* Public domain.
* Written by Matthew Dempsky.
*/
#include <string.h>
#include "compat.h"
void
explicit_bzero(void *buf, size_t len)
{
memset(buf, 0, len);
}

Some files were not shown because too many files have changed in this diff Show More