4 * Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
6 * Permission to use, copy, modify, and distribute this software for any
7 * purpose with or without fee is hereby granted, provided that the above
8 * copyright notice and this permission notice appear in all copies.
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
15 * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
16 * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
19 #include <sys/types.h>
24 * Attach existing session to the current terminal.
27 int cmd_attach_session_exec(struct cmd
*, struct cmd_ctx
*);
29 const struct cmd_entry cmd_attach_session_entry
= {
30 "attach-session", "attach",
31 "[-dr] " CMD_TARGET_SESSION_USAGE
,
32 CMD_CANTNEST
|CMD_STARTSERVER
|CMD_SENDENVIRON
, "dr",
35 cmd_attach_session_exec
,
41 cmd_attach_session_exec(struct cmd
*self
, struct cmd_ctx
*ctx
)
43 struct cmd_target_data
*data
= self
->data
;
47 char *overrides
, *cause
;
50 if (ARRAY_LENGTH(&sessions
) == 0) {
51 ctx
->error(ctx
, "no sessions");
54 if ((s
= cmd_find_session(ctx
, data
->target
)) == NULL
)
57 if (ctx
->cmdclient
== NULL
&& ctx
->curclient
== NULL
)
60 if (ctx
->cmdclient
== NULL
) {
61 if (cmd_check_flag(data
->chflags
, 'd')) {
63 * Can't use server_write_session in case attaching to
64 * the same session as currently attached to.
66 for (i
= 0; i
< ARRAY_LENGTH(&clients
); i
++) {
67 c
= ARRAY_ITEM(&clients
, i
);
68 if (c
== NULL
|| c
->session
!= s
)
70 if (c
== ctx
->curclient
)
72 server_write_client(c
, MSG_DETACH
, NULL
, 0);
76 ctx
->curclient
->session
= s
;
77 server_redraw_client(ctx
->curclient
);
79 if (!(ctx
->cmdclient
->flags
& CLIENT_TERMINAL
)) {
80 ctx
->error(ctx
, "not a terminal");
85 options_get_string(&s
->options
, "terminal-overrides");
86 if (tty_open(&ctx
->cmdclient
->tty
, overrides
, &cause
) != 0) {
87 ctx
->error(ctx
, "terminal open failed: %s", cause
);
92 if (cmd_check_flag(data
->chflags
, 'r'))
93 ctx
->cmdclient
->flags
|= CLIENT_READONLY
;
95 if (cmd_check_flag(data
->chflags
, 'd'))
96 server_write_session(s
, MSG_DETACH
, NULL
, 0);
98 ctx
->cmdclient
->session
= s
;
99 server_write_client(ctx
->cmdclient
, MSG_READY
, NULL
, 0);
101 update
= options_get_string(&s
->options
, "update-environment");
102 environ_update(update
, &ctx
->cmdclient
->environ
, &s
->environ
);
104 server_redraw_client(ctx
->cmdclient
);
107 server_update_socket();
109 return (1); /* 1 means don't tell command client to exit */