From 0ec45782b59967e776bcab7185067582b4fe34f4 Mon Sep 17 00:00:00 2001 From: Jacob Nevins Date: Sun, 21 Feb 2021 14:17:03 +0000 Subject: [PATCH] Mention any extant downstreams in close warning. Suggested by Brian Rak. --- putty.h | 6 ++++++ raw.c | 1 + rlogin.c | 1 + ssh.c | 15 +++++++++++++++ unix/gtkwin.c | 12 ++++++++++-- windows/window.c | 19 +++++++++++++------ 6 files changed, 46 insertions(+), 8 deletions(-) diff --git a/putty.h b/putty.h index db308427..f89ffc09 100644 --- a/putty.h +++ b/putty.h @@ -652,6 +652,12 @@ struct BackendVtable { /* Only implemented in the SSH protocol: check whether a * connection-sharing upstream exists for a given configuration. */ bool (*test_for_upstream)(const char *host, int port, Conf *conf); + /* Special-purpose function to return additional information to put + * in a "are you sure you want to close this session" dialog; + * return NULL if no such info, otherwise caller must free. + * Only implemented in the SSH protocol, to warn about downstream + * connections that would be lost if this one were terminated. */ + char *(*close_warn_text)(Backend *be); /* 'id' is a machine-readable name for the backend, used in * saved-session storage. 'displayname' is a human-readable name diff --git a/raw.c b/raw.c index 15f8d85e..a601213e 100644 --- a/raw.c +++ b/raw.c @@ -324,6 +324,7 @@ const BackendVtable raw_backend = { .unthrottle = raw_unthrottle, .cfg_info = raw_cfg_info, .test_for_upstream = NULL, + .close_warn_text = NULL, .id = "raw", .displayname = "Raw", .protocol = PROT_RAW, diff --git a/rlogin.c b/rlogin.c index 8c3d12d0..9e7a2359 100644 --- a/rlogin.c +++ b/rlogin.c @@ -422,6 +422,7 @@ const BackendVtable rlogin_backend = { .unthrottle = rlogin_unthrottle, .cfg_info = rlogin_cfg_info, .test_for_upstream = NULL, + .close_warn_text = NULL, .id = "rlogin", .displayname = "Rlogin", .protocol = PROT_RLOGIN, diff --git a/ssh.c b/ssh.c index d74a0ff2..00a516ea 100644 --- a/ssh.c +++ b/ssh.c @@ -691,6 +691,19 @@ static bool ssh_test_for_upstream(const char *host, int port, Conf *conf) return ret; } +static char *ssh_close_warn_text(Backend *be) +{ + Ssh *ssh = container_of(be, Ssh, backend); + if (!ssh->connshare) + return NULL; + int ndowns = share_ndownstreams(ssh->connshare); + if (ndowns == 0) + return NULL; + char *msg = dupprintf("This will also close %d downstream connection%s.", + ndowns, ndowns==1 ? "" : "s"); + return msg; +} + static const PlugVtable Ssh_plugvt = { .log = ssh_socket_log, .closing = ssh_closing, @@ -1204,6 +1217,7 @@ const BackendVtable ssh_backend = { .unthrottle = ssh_unthrottle, .cfg_info = ssh_cfg_info, .test_for_upstream = ssh_test_for_upstream, + .close_warn_text = ssh_close_warn_text, .id = "ssh", .displayname = "SSH", .protocol = PROT_SSH, @@ -1227,6 +1241,7 @@ const BackendVtable sshconn_backend = { .unthrottle = ssh_unthrottle, .cfg_info = ssh_cfg_info, .test_for_upstream = ssh_test_for_upstream, + .close_warn_text = ssh_close_warn_text, .id = "ssh-connection", .displayname = "Bare ssh-connection", .protocol = PROT_SSHCONN, diff --git a/unix/gtkwin.c b/unix/gtkwin.c index b9c5ad0e..cba7c1fd 100644 --- a/unix/gtkwin.c +++ b/unix/gtkwin.c @@ -618,13 +618,21 @@ gint delete_window(GtkWidget *widget, GdkEvent *event, GtkFrontend *inst) */ if (!find_and_raise_dialog(inst, DIALOG_SLOT_WARN_ON_CLOSE)) { char *title = dupcat(appname, " Exit Confirmation"); + char *msg, *additional = NULL; + if (inst && inst->backend && inst->backend->vt->close_warn_text) { + additional = inst->backend->vt->close_warn_text(inst->backend); + } + msg = dupprintf("Are you sure you want to close this session?%s%s", + additional ? "\n" : "", + additional ? additional : ""); GtkWidget *dialog = create_message_box( - inst->window, title, - "Are you sure you want to close this session?", + inst->window, title, msg, string_width("Most of the width of the above text"), false, &buttons_yn, warn_on_close_callback, inst); register_dialog(&inst->seat, DIALOG_SLOT_WARN_ON_CLOSE, dialog); sfree(title); + sfree(msg); + sfree(additional); } return true; } diff --git a/windows/window.c b/windows/window.c index ccfa6360..cc4bba8b 100644 --- a/windows/window.c +++ b/windows/window.c @@ -2122,16 +2122,23 @@ static LRESULT CALLBACK WndProc(HWND hwnd, UINT message, case WM_CREATE: break; case WM_CLOSE: { - char *str; + char *title, *msg, *additional = NULL; show_mouseptr(true); - str = dupprintf("%s Exit Confirmation", appname); + title = dupprintf("%s Exit Confirmation", appname); + if (backend && backend->vt->close_warn_text) { + additional = backend->vt->close_warn_text(backend); + } + msg = dupprintf("Are you sure you want to close this session?%s%s", + additional ? "\n" : "", + additional ? additional : ""); if (session_closed || !conf_get_bool(conf, CONF_warn_on_close) || - MessageBox(hwnd, - "Are you sure you want to close this session?", - str, MB_ICONWARNING | MB_OKCANCEL | MB_DEFBUTTON1) + MessageBox(hwnd, msg, title, + MB_ICONWARNING | MB_OKCANCEL | MB_DEFBUTTON1) == IDOK) DestroyWindow(hwnd); - sfree(str); + sfree(title); + sfree(msg); + sfree(additional); return 0; } case WM_DESTROY: