15 static char **events = NULL;
16 static int nevents = 0, negsize = 0;
19 static int sesslist_has_focus;
20 static int requested_help;
22 static struct prefslist cipherlist;
24 void force_normal(HWND hwnd)
26 static int recurse = 0;
34 wp.length = sizeof(wp);
35 if (GetWindowPlacement(hwnd, &wp) && wp.showCmd == SW_SHOWMAXIMIZED) {
36 wp.showCmd = SW_SHOWNORMAL;
37 SetWindowPlacement(hwnd, &wp);
42 static void MyGetDlgItemInt(HWND hwnd, int id, int *result)
46 n = GetDlgItemInt(hwnd, id, &ok, FALSE);
51 static void MyGetDlgItemFlt(HWND hwnd, int id, int *result, int scale)
55 ok = GetDlgItemText(hwnd, id, text, sizeof(text) - 1);
57 *result = (int) (scale * atof(text));
60 static void MySetDlgItemFlt(HWND hwnd, int id, double value)
63 sprintf(text, "%g", value);
64 SetDlgItemText(hwnd, id, text);
67 static int CALLBACK LogProc(HWND hwnd, UINT msg,
68 WPARAM wParam, LPARAM lParam)
75 static int tabs[4] = { 78, 108 };
76 SendDlgItemMessage(hwnd, IDN_LIST, LB_SETTABSTOPS, 2,
79 for (i = 0; i < nevents; i++)
80 SendDlgItemMessage(hwnd, IDN_LIST, LB_ADDSTRING,
81 0, (LPARAM) events[i]);
84 switch (LOWORD(wParam)) {
88 SetActiveWindow(GetParent(hwnd));
92 if (HIWORD(wParam) == BN_CLICKED ||
93 HIWORD(wParam) == BN_DOUBLECLICKED) {
96 selcount = SendDlgItemMessage(hwnd, IDN_LIST,
97 LB_GETSELCOUNT, 0, 0);
98 if (selcount == 0) { /* don't even try to copy zero items */
103 selitems = smalloc(selcount * sizeof(int));
105 int count = SendDlgItemMessage(hwnd, IDN_LIST,
112 static unsigned char sel_nl[] = SEL_NL;
114 if (count == 0) { /* can't copy zero stuff */
120 for (i = 0; i < count; i++)
122 strlen(events[selitems[i]]) + sizeof(sel_nl);
124 clipdata = smalloc(size);
127 for (i = 0; i < count; i++) {
128 char *q = events[selitems[i]];
129 int qlen = strlen(q);
132 memcpy(p, sel_nl, sizeof(sel_nl));
135 write_aclip(clipdata, size, TRUE);
140 for (i = 0; i < nevents; i++)
141 SendDlgItemMessage(hwnd, IDN_LIST, LB_SETSEL,
150 SetActiveWindow(GetParent(hwnd));
157 static int CALLBACK LicenceProc(HWND hwnd, UINT msg,
158 WPARAM wParam, LPARAM lParam)
164 switch (LOWORD(wParam)) {
177 static int CALLBACK AboutProc(HWND hwnd, UINT msg,
178 WPARAM wParam, LPARAM lParam)
182 SetDlgItemText(hwnd, IDA_VERSION, ver);
185 switch (LOWORD(wParam)) {
188 EndDialog(hwnd, TRUE);
191 EnableWindow(hwnd, 0);
192 DialogBox(hinst, MAKEINTRESOURCE(IDD_LICENCEBOX),
194 EnableWindow(hwnd, 1);
195 SetActiveWindow(hwnd);
199 /* Load web browser */
200 ShellExecute(hwnd, "open",
201 "http://www.chiark.greenend.org.uk/~sgtatham/putty/",
202 0, 0, SW_SHOWDEFAULT);
207 EndDialog(hwnd, TRUE);
214 * Null dialog procedure.
216 static int CALLBACK NullDlgProc(HWND hwnd, UINT msg,
217 WPARAM wParam, LPARAM lParam)
222 static char savedsession[2048];
225 IDC_ABOUT, IDCX_TVSTATIC, IDCX_TREEVIEW, controlstartvalue,
364 IDC_SCROLLBARFULLSCREEN,
379 IDC_FULLSCREENONALTENTER,
382 appearancepanelstart,
383 IDC_TITLE_APPEARANCE,
405 connectionpanelstart,
406 IDC_TITLE_CONNECTION,
525 translationpanelstart,
526 IDC_TITLE_TRANSLATION,
527 IDC_BOX_TRANSLATION1,
528 IDC_BOX_TRANSLATION2,
529 IDC_BOX_TRANSLATION3,
567 static const char *const colours[] = {
568 "Default Foreground", "Default Bold Foreground",
569 "Default Background", "Default Bold Background",
570 "Cursor Text", "Cursor Colour",
571 "ANSI Black", "ANSI Black Bold",
572 "ANSI Red", "ANSI Red Bold",
573 "ANSI Green", "ANSI Green Bold",
574 "ANSI Yellow", "ANSI Yellow Bold",
575 "ANSI Blue", "ANSI Blue Bold",
576 "ANSI Magenta", "ANSI Magenta Bold",
577 "ANSI Cyan", "ANSI Cyan Bold",
578 "ANSI White", "ANSI White Bold"
580 static const int permcolour[] = {
581 TRUE, FALSE, TRUE, FALSE, TRUE, TRUE,
582 TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE,
583 TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE
586 static void fmtfont(char *buf)
588 sprintf(buf, "Font: %s, ", cfg.font);
590 strcat(buf, "bold, ");
591 if (cfg.fontheight == 0)
592 strcat(buf, "default height");
594 sprintf(buf + strlen(buf), "%d-point",
595 (cfg.fontheight < 0 ? -cfg.fontheight : cfg.fontheight));
598 char *help_context_cmd(int id)
610 return "JI(`',`session.hostname')";
617 return "JI(`',`session.saved')";
622 return "JI(`',`session.coe')";
623 case IDC_LSTATSTATIC:
627 case IDC_LSTATPACKET:
628 return "JI(`',`logging.main')";
633 return "JI(`',`logging.filename')";
638 return "JI(`',`logging.exists')";
643 return "JI(`',`keyboard.backspace')";
647 return "JI(`',`keyboard.homeend')";
655 return "JI(`',`keyboard.funkeys')";
660 return "JI(`',`keyboard.appkeypad')";
665 return "JI(`',`keyboard.appcursor')";
667 return "JI(`',`keyboard.nethack')";
669 return "JI(`',`keyboard.compose')";
670 case IDC_CTRLALTKEYS:
671 return "JI(`',`keyboard.ctrlalt')";
674 return "JI(`',`terminal.autowrap')";
676 return "JI(`',`terminal.decom')";
678 return "JI(`',`terminal.lfhascr')";
680 return "JI(`',`terminal.bce')";
682 return "JI(`',`terminal.blink')";
685 return "JI(`',`terminal.answerback')";
687 case IDC_ECHOBACKEND:
690 return "JI(`',`terminal.localecho')";
692 case IDC_EDITBACKEND:
695 return "JI(`',`terminal.localedit')";
698 case IDC_BELL_DISABLED:
699 case IDC_BELL_DEFAULT:
700 case IDC_BELL_WAVEFILE:
701 case IDC_BELL_VISUAL:
702 case IDC_BELL_WAVESTATIC:
703 case IDC_BELL_WAVEEDIT:
704 case IDC_BELL_WAVEBROWSE:
705 return "JI(`',`bell.style')";
706 case IDC_B_IND_STATIC:
707 case IDC_B_IND_DISABLED:
708 case IDC_B_IND_FLASH:
709 case IDC_B_IND_STEADY:
710 return "JI(`',`bell.taskbar')";
712 case IDC_BELLOVLNSTATIC:
714 case IDC_BELLOVLTSTATIC:
716 case IDC_BELLOVLEXPLAIN:
717 case IDC_BELLOVLSSTATIC:
719 return "JI(`',`bell.overload')";
725 return "JI(`',`window.size')";
726 case IDC_RESIZESTATIC:
730 case IDC_RESIZEEITHER:
731 return "JI(`',`window.resize')";
733 case IDC_SCROLLBARFULLSCREEN:
738 return "JI(`',`window.scrollback')";
741 return "JI(`',`behaviour.closewarn')";
743 return "JI(`',`behaviour.altf4')";
745 return "JI(`',`behaviour.altspace')";
747 return "JI(`',`behaviour.altonly')";
748 case IDC_ALWAYSONTOP:
749 return "JI(`',`behaviour.alwaysontop')";
750 case IDC_FULLSCREENONALTENTER:
751 return "JI(`',`behaviour.altenter')";
753 case IDC_CURSORSTATIC:
758 return "JI(`',`appearance.cursor')";
761 return "JI(`',`appearance.font')";
765 return "JI(`',`appearance.title')";
767 return "JI(`',`appearance.hidemouse')";
771 return "JI(`',`appearance.border')";
775 return "JI(`',`connection.termtype')";
778 return "JI(`',`connection.username')";
781 return "JI(`',`connection.keepalive')";
783 return "JI(`',`connection.nodelay')";
787 return "JI(`',`telnet.termspeed')";
796 return "JI(`',`telnet.environ')";
800 return "JI(`',`telnet.oldenviron')";
804 return "JI(`',`telnet.passive')";
806 return "JI(`',`telnet.specialkeys')";
808 return "JI(`',`telnet.newline')";
812 return "JI(`',`rlogin.termspeed')";
813 case IDC_RLLUSERSTATIC:
814 case IDC_RLLUSEREDIT:
815 return "JI(`',`rlogin.localuser')";
818 return "JI(`',`ssh.nopty')";
819 case IDC_CIPHERSTATIC2:
824 return "JI(`',`ssh.ciphers')";
826 return "JI(`',`ssh.buggymac')";
827 case IDC_SSHPROTSTATIC:
830 return "JI(`',`ssh.protocol')";
833 return "JI(`',`ssh.command')";
835 return "JI(`',`ssh.compress')";
840 return "JI(`',`ssh.auth.privkey')";
842 return "JI(`',`ssh.auth.agentfwd')";
844 return "JI(`',`ssh.auth.changeuser')";
846 return "JI(`',`ssh.auth.tis')";
848 return "JI(`',`ssh.auth.ki')";
853 return "JI(`',`selection.buttons')";
854 case IDC_MOUSEOVERRIDE:
855 return "JI(`',`selection.shiftdrag')";
856 case IDC_SELTYPESTATIC:
858 case IDC_SELTYPERECT:
859 return "JI(`',`selection.rect')";
865 return "JI(`',`selection.charclasses')";
867 return "JI(`',`selection.linedraw')";
869 return "JI(`',`selection.rtf')";
872 return "JI(`',`colours.bold')";
874 return "JI(`',`colours.logpal')";
875 case IDC_COLOURSTATIC:
884 return "JI(`',`colours.config')";
886 case IDC_CODEPAGESTATIC:
888 return "JI(`',`translation.codepage')";
889 case IDC_CAPSLOCKCYR:
890 return "JI(`',`translation.cyrillic')";
897 return "JI(`',`translation.linedraw')";
899 case IDC_X11_FORWARD:
900 case IDC_X11_DISPSTATIC:
901 case IDC_X11_DISPLAY:
902 return "JI(`',`ssh.tunnels.x11')";
904 case IDC_PFWDSTATIC2:
908 case IDC_SPORTSTATIC:
910 case IDC_DPORTSTATIC:
914 return "JI(`',`ssh.tunnels.portfwd')";
917 return "JI(`',`ssh.tunnels.portfwd.localhost')";
924 /* 2nd arg: NZ => don't redraw session list (use when loading
926 static void init_dlg_ctrls(HWND hwnd, int keepsess)
929 char fontstatic[256];
931 SetDlgItemText(hwnd, IDC_HOST, cfg.host);
932 SetDlgItemText(hwnd, IDC_SESSEDIT, savedsession);
935 n = SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_GETCOUNT, 0, 0);
936 for (i = n; i-- > 0;)
937 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_DELETESTRING, i, 0);
938 for (i = 0; i < nsessions; i++)
939 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_ADDSTRING,
940 0, (LPARAM) (sessions[i]));
942 SetDlgItemInt(hwnd, IDC_PORT, cfg.port, FALSE);
943 CheckRadioButton(hwnd, IDC_PROTRAW, IDC_PROTSSH,
944 cfg.protocol == PROT_SSH ? IDC_PROTSSH :
945 cfg.protocol == PROT_TELNET ? IDC_PROTTELNET :
947 PROT_RLOGIN ? IDC_PROTRLOGIN : IDC_PROTRAW);
948 SetDlgItemInt(hwnd, IDC_PINGEDIT, cfg.ping_interval, FALSE);
949 CheckDlgButton(hwnd, IDC_NODELAY, cfg.tcp_nodelay);
951 CheckRadioButton(hwnd, IDC_DEL008, IDC_DEL127,
952 cfg.bksp_is_delete ? IDC_DEL127 : IDC_DEL008);
953 CheckRadioButton(hwnd, IDC_HOMETILDE, IDC_HOMERXVT,
954 cfg.rxvt_homeend ? IDC_HOMERXVT : IDC_HOMETILDE);
955 CheckRadioButton(hwnd, IDC_FUNCTILDE, IDC_FUNCSCO,
956 cfg.funky_type == 0 ? IDC_FUNCTILDE :
957 cfg.funky_type == 1 ? IDC_FUNCLINUX :
958 cfg.funky_type == 2 ? IDC_FUNCXTERM :
959 cfg.funky_type == 3 ? IDC_FUNCVT400 :
960 cfg.funky_type == 4 ? IDC_FUNCVT100P :
961 cfg.funky_type == 5 ? IDC_FUNCSCO : IDC_FUNCTILDE);
962 CheckDlgButton(hwnd, IDC_NOAPPLICC, cfg.no_applic_c);
963 CheckDlgButton(hwnd, IDC_NOAPPLICK, cfg.no_applic_k);
964 CheckRadioButton(hwnd, IDC_CURNORMAL, IDC_CURAPPLIC,
965 cfg.app_cursor ? IDC_CURAPPLIC : IDC_CURNORMAL);
966 CheckRadioButton(hwnd, IDC_KPNORMAL, IDC_KPNH,
967 cfg.nethack_keypad ? IDC_KPNH :
968 cfg.app_keypad ? IDC_KPAPPLIC : IDC_KPNORMAL);
969 CheckDlgButton(hwnd, IDC_ALTF4, cfg.alt_f4);
970 CheckDlgButton(hwnd, IDC_ALTSPACE, cfg.alt_space);
971 CheckDlgButton(hwnd, IDC_ALTONLY, cfg.alt_only);
972 CheckDlgButton(hwnd, IDC_COMPOSEKEY, cfg.compose_key);
973 CheckDlgButton(hwnd, IDC_CTRLALTKEYS, cfg.ctrlaltkeys);
974 CheckDlgButton(hwnd, IDC_TELNETKEY, cfg.telnet_keyboard);
975 CheckDlgButton(hwnd, IDC_TELNETRET, cfg.telnet_newline);
976 CheckRadioButton(hwnd, IDC_ECHOBACKEND, IDC_ECHONO,
977 cfg.localecho == LD_BACKEND ? IDC_ECHOBACKEND :
978 cfg.localecho == LD_YES ? IDC_ECHOYES : IDC_ECHONO);
979 CheckRadioButton(hwnd, IDC_EDITBACKEND, IDC_EDITNO,
980 cfg.localedit == LD_BACKEND ? IDC_EDITBACKEND :
981 cfg.localedit == LD_YES ? IDC_EDITYES : IDC_EDITNO);
982 SetDlgItemText(hwnd, IDC_ANSWEREDIT, cfg.answerback);
983 CheckDlgButton(hwnd, IDC_ALWAYSONTOP, cfg.alwaysontop);
984 CheckDlgButton(hwnd, IDC_FULLSCREENONALTENTER, cfg.fullscreenonaltenter);
985 CheckDlgButton(hwnd, IDC_SCROLLKEY, cfg.scroll_on_key);
986 CheckDlgButton(hwnd, IDC_SCROLLDISP, cfg.scroll_on_disp);
988 CheckDlgButton(hwnd, IDC_WRAPMODE, cfg.wrap_mode);
989 CheckDlgButton(hwnd, IDC_DECOM, cfg.dec_om);
990 CheckDlgButton(hwnd, IDC_LFHASCR, cfg.lfhascr);
991 SetDlgItemInt(hwnd, IDC_ROWSEDIT, cfg.height, FALSE);
992 SetDlgItemInt(hwnd, IDC_COLSEDIT, cfg.width, FALSE);
993 SetDlgItemInt(hwnd, IDC_SAVEEDIT, cfg.savelines, FALSE);
995 SetDlgItemText(hwnd, IDC_FONTSTATIC, fontstatic);
996 CheckRadioButton(hwnd, IDC_BELL_DISABLED, IDC_BELL_VISUAL,
997 cfg.beep == BELL_DISABLED ? IDC_BELL_DISABLED :
998 cfg.beep == BELL_DEFAULT ? IDC_BELL_DEFAULT :
999 cfg.beep == BELL_WAVEFILE ? IDC_BELL_WAVEFILE :
1001 BELL_VISUAL ? IDC_BELL_VISUAL : IDC_BELL_DEFAULT);
1002 CheckRadioButton(hwnd, IDC_B_IND_DISABLED, IDC_B_IND_STEADY,
1004 B_IND_DISABLED ? IDC_B_IND_DISABLED : cfg.beep_ind ==
1005 B_IND_FLASH ? IDC_B_IND_FLASH : cfg.beep_ind ==
1006 B_IND_STEADY ? IDC_B_IND_STEADY : IDC_B_IND_DISABLED);
1007 SetDlgItemText(hwnd, IDC_BELL_WAVEEDIT, cfg.bell_wavefile);
1008 CheckDlgButton(hwnd, IDC_BELLOVL, cfg.bellovl);
1009 SetDlgItemInt(hwnd, IDC_BELLOVLN, cfg.bellovl_n, FALSE);
1010 MySetDlgItemFlt(hwnd, IDC_BELLOVLT, cfg.bellovl_t / 1000.0);
1011 MySetDlgItemFlt(hwnd, IDC_BELLOVLS, cfg.bellovl_s / 1000.0);
1013 CheckDlgButton(hwnd, IDC_BCE, cfg.bce);
1014 CheckDlgButton(hwnd, IDC_BLINKTEXT, cfg.blinktext);
1016 SetDlgItemText(hwnd, IDC_WINEDIT, cfg.wintitle);
1017 CheckDlgButton(hwnd, IDC_WINNAME, cfg.win_name_always);
1018 CheckDlgButton(hwnd, IDC_HIDEMOUSE, cfg.hide_mouseptr);
1019 CheckDlgButton(hwnd, IDC_SUNKENEDGE, cfg.sunken_edge);
1020 SetDlgItemInt(hwnd, IDC_WINBEDIT, cfg.window_border, FALSE);
1021 CheckRadioButton(hwnd, IDC_CURBLOCK, IDC_CURVERT,
1022 cfg.cursor_type == 0 ? IDC_CURBLOCK :
1023 cfg.cursor_type == 1 ? IDC_CURUNDER : IDC_CURVERT);
1024 CheckDlgButton(hwnd, IDC_BLINKCUR, cfg.blink_cur);
1025 CheckDlgButton(hwnd, IDC_SCROLLBAR, cfg.scrollbar);
1026 CheckDlgButton(hwnd, IDC_SCROLLBARFULLSCREEN, cfg.scrollbar_in_fullscreen);
1027 CheckRadioButton(hwnd, IDC_RESIZETERM, IDC_RESIZEEITHER,
1028 cfg.resize_action == RESIZE_TERM ? IDC_RESIZETERM :
1029 cfg.resize_action == RESIZE_FONT ? IDC_RESIZEFONT :
1030 cfg.resize_action == RESIZE_EITHER ? IDC_RESIZEEITHER :
1032 CheckRadioButton(hwnd, IDC_COEALWAYS, IDC_COENORMAL,
1033 cfg.close_on_exit == COE_NORMAL ? IDC_COENORMAL :
1034 cfg.close_on_exit ==
1035 COE_NEVER ? IDC_COENEVER : IDC_COEALWAYS);
1036 CheckDlgButton(hwnd, IDC_CLOSEWARN, cfg.warn_on_close);
1038 SetDlgItemText(hwnd, IDC_TTEDIT, cfg.termtype);
1039 SetDlgItemText(hwnd, IDC_TSEDIT, cfg.termspeed);
1040 SetDlgItemText(hwnd, IDC_R_TSEDIT, cfg.termspeed);
1041 SetDlgItemText(hwnd, IDC_RLLUSEREDIT, cfg.localusername);
1042 SetDlgItemText(hwnd, IDC_LOGEDIT, cfg.username);
1043 SetDlgItemText(hwnd, IDC_LGFEDIT, cfg.logfilename);
1044 CheckRadioButton(hwnd, IDC_LSTATOFF, IDC_LSTATPACKET,
1045 cfg.logtype == LGTYP_NONE ? IDC_LSTATOFF :
1046 cfg.logtype == LGTYP_ASCII ? IDC_LSTATASCII :
1047 cfg.logtype == LGTYP_DEBUG ? IDC_LSTATRAW :
1049 CheckRadioButton(hwnd, IDC_LSTATXOVR, IDC_LSTATXASK,
1050 cfg.logxfovr == LGXF_OVR ? IDC_LSTATXOVR :
1051 cfg.logxfovr == LGXF_ASK ? IDC_LSTATXASK :
1054 char *p = cfg.environmt;
1055 SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_RESETCONTENT, 0, 0);
1057 SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_ADDSTRING, 0,
1063 SendDlgItemMessage(hwnd, IDC_PFWDLIST, LB_ADDSTRING, 0,
1068 CheckRadioButton(hwnd, IDC_EMBSD, IDC_EMRFC,
1069 cfg.rfc_environ ? IDC_EMRFC : IDC_EMBSD);
1070 CheckRadioButton(hwnd, IDC_TPASSIVE, IDC_TACTIVE,
1071 cfg.passive_telnet ? IDC_TPASSIVE : IDC_TACTIVE);
1073 SetDlgItemText(hwnd, IDC_TTEDIT, cfg.termtype);
1074 SetDlgItemText(hwnd, IDC_LOGEDIT, cfg.username);
1075 CheckDlgButton(hwnd, IDC_NOPTY, cfg.nopty);
1076 CheckDlgButton(hwnd, IDC_COMPRESS, cfg.compression);
1077 CheckDlgButton(hwnd, IDC_BUGGYMAC, cfg.buggymac);
1078 CheckDlgButton(hwnd, IDC_SSH2DES, cfg.ssh2_des_cbc);
1079 CheckDlgButton(hwnd, IDC_AGENTFWD, cfg.agentfwd);
1080 CheckDlgButton(hwnd, IDC_CHANGEUSER, cfg.change_username);
1081 CheckRadioButton(hwnd, IDC_SSHPROT1, IDC_SSHPROT2,
1082 cfg.sshprot == 1 ? IDC_SSHPROT1 : IDC_SSHPROT2);
1083 CheckDlgButton(hwnd, IDC_AUTHTIS, cfg.try_tis_auth);
1084 CheckDlgButton(hwnd, IDC_AUTHKI, cfg.try_ki_auth);
1085 SetDlgItemText(hwnd, IDC_PKEDIT, cfg.keyfile);
1086 SetDlgItemText(hwnd, IDC_CMDEDIT, cfg.remote_cmd);
1090 static const struct { char *s; int c; } ciphers[] = {
1091 { "3DES", CIPHER_3DES },
1092 { "Blowfish", CIPHER_BLOWFISH },
1093 { "DES", CIPHER_DES },
1094 { "AES (SSH 2 only)", CIPHER_AES },
1095 { "-- warn below here --", CIPHER_WARN }
1098 /* Set up the "selected ciphers" box. */
1099 /* (cipherlist assumed to contain all ciphers) */
1100 SendDlgItemMessage(hwnd, IDC_CIPHERLIST, LB_RESETCONTENT, 0, 0);
1101 for (i = 0; i < CIPHER_MAX; i++) {
1102 int c = cfg.ssh_cipherlist[i];
1105 for (j = 0; j < (sizeof ciphers) / (sizeof ciphers[0]); j++) {
1106 if (ciphers[j].c == c) {
1107 cstr = ciphers[j].s;
1111 pos = SendDlgItemMessage(hwnd, IDC_CIPHERLIST, LB_ADDSTRING,
1113 SendDlgItemMessage(hwnd, IDC_CIPHERLIST, LB_SETITEMDATA,
1119 CheckRadioButton(hwnd, IDC_MBWINDOWS, IDC_MBXTERM,
1120 cfg.mouse_is_xterm ? IDC_MBXTERM : IDC_MBWINDOWS);
1121 CheckRadioButton(hwnd, IDC_SELTYPELEX, IDC_SELTYPERECT,
1122 cfg.rect_select == 0 ? IDC_SELTYPELEX : IDC_SELTYPERECT);
1123 CheckDlgButton(hwnd, IDC_MOUSEOVERRIDE, cfg.mouse_override);
1124 CheckDlgButton(hwnd, IDC_RAWCNP, cfg.rawcnp);
1125 CheckDlgButton(hwnd, IDC_RTFPASTE, cfg.rtf_paste);
1127 static int tabs[4] = { 25, 61, 96, 128 };
1128 SendDlgItemMessage(hwnd, IDC_CCLIST, LB_SETTABSTOPS, 4,
1131 for (i = 0; i < 128; i++) {
1133 sprintf(str, "%d\t(0x%02X)\t%c\t%d", i, i,
1134 (i >= 0x21 && i != 0x7F) ? i : ' ', cfg.wordness[i]);
1135 SendDlgItemMessage(hwnd, IDC_CCLIST, LB_ADDSTRING, 0,
1139 CheckDlgButton(hwnd, IDC_BOLDCOLOUR, cfg.bold_colour);
1140 CheckDlgButton(hwnd, IDC_PALETTE, cfg.try_palette);
1143 n = SendDlgItemMessage(hwnd, IDC_COLOURLIST, LB_GETCOUNT, 0, 0);
1144 for (i = n; i-- > 0;)
1145 SendDlgItemMessage(hwnd, IDC_COLOURLIST,
1146 LB_DELETESTRING, i, 0);
1147 for (i = 0; i < 22; i++)
1148 if (cfg.bold_colour || permcolour[i])
1149 SendDlgItemMessage(hwnd, IDC_COLOURLIST, LB_ADDSTRING, 0,
1150 (LPARAM) colours[i]);
1152 SendDlgItemMessage(hwnd, IDC_COLOURLIST, LB_SETCURSEL, 0, 0);
1153 SetDlgItemInt(hwnd, IDC_RVALUE, cfg.colours[0][0], FALSE);
1154 SetDlgItemInt(hwnd, IDC_GVALUE, cfg.colours[0][1], FALSE);
1155 SetDlgItemInt(hwnd, IDC_BVALUE, cfg.colours[0][2], FALSE);
1160 strcpy(cfg.line_codepage, cp_name(decode_codepage(cfg.line_codepage)));
1161 SendDlgItemMessage(hwnd, IDC_CODEPAGE, CB_RESETCONTENT, 0, 0);
1162 CheckDlgButton (hwnd, IDC_CAPSLOCKCYR, cfg.xlat_capslockcyr);
1163 for (i = 0; (cp = cp_enumerate(i)) != NULL; i++) {
1164 SendDlgItemMessage(hwnd, IDC_CODEPAGE, CB_ADDSTRING,
1167 SetDlgItemText(hwnd, IDC_CODEPAGE, cfg.line_codepage);
1170 CheckRadioButton(hwnd, IDC_VTXWINDOWS, IDC_VTUNICODE,
1171 cfg.vtmode == VT_XWINDOWS ? IDC_VTXWINDOWS :
1172 cfg.vtmode == VT_OEMANSI ? IDC_VTOEMANSI :
1173 cfg.vtmode == VT_OEMONLY ? IDC_VTOEMONLY :
1174 cfg.vtmode == VT_UNICODE ? IDC_VTUNICODE :
1177 CheckDlgButton(hwnd, IDC_X11_FORWARD, cfg.x11_forward);
1178 SetDlgItemText(hwnd, IDC_X11_DISPLAY, cfg.x11_display);
1180 CheckDlgButton(hwnd, IDC_LPORT_ALL, cfg.lport_acceptall);
1181 CheckDlgButton(hwnd, IDC_RPORT_ALL, cfg.rport_acceptall);
1182 CheckRadioButton(hwnd, IDC_PFWDLOCAL, IDC_PFWDREMOTE, IDC_PFWDLOCAL);
1185 struct treeview_faff {
1187 HTREEITEM lastat[4];
1190 static HTREEITEM treeview_insert(struct treeview_faff *faff,
1191 int level, char *text)
1196 ins.hParent = (level > 0 ? faff->lastat[level - 1] : TVI_ROOT);
1197 ins.hInsertAfter = faff->lastat[level];
1198 #if _WIN32_IE >= 0x0400 && defined NONAMELESSUNION
1199 #define INSITEM DUMMYUNIONNAME.item
1201 #define INSITEM item
1203 ins.INSITEM.mask = TVIF_TEXT;
1204 ins.INSITEM.pszText = text;
1205 newitem = TreeView_InsertItem(faff->treeview, &ins);
1207 TreeView_Expand(faff->treeview, faff->lastat[level - 1],
1209 faff->lastat[level] = newitem;
1210 for (i = level + 1; i < 4; i++)
1211 faff->lastat[i] = NULL;
1216 * Create the panelfuls of controls in the configuration box.
1218 static void create_controls(HWND hwnd, int dlgtype, int panel)
1220 if (panel == sessionpanelstart) {
1221 /* The Session panel. Accelerators used: [acgo] nprtih elsd w */
1223 ctlposinit(&cp, hwnd, 80, 3, 13);
1224 bartitle(&cp, "Basic options for your PuTTY session",
1227 beginbox(&cp, "Specify your connection by host name or IP address",
1230 "Host &Name (or IP address)",
1231 IDC_HOSTSTATIC, IDC_HOST, 75,
1232 "&Port", IDC_PORTSTATIC, IDC_PORT, 25, NULL);
1233 if (backends[3].backend == NULL) {
1234 /* this is PuTTYtel, so only three protocols available */
1235 radioline(&cp, "Protocol:", IDC_PROTSTATIC, 3,
1236 "&Raw", IDC_PROTRAW,
1237 "&Telnet", IDC_PROTTELNET,
1238 "Rlog&in", IDC_PROTRLOGIN, NULL);
1240 radioline(&cp, "Protocol:", IDC_PROTSTATIC, 4,
1241 "&Raw", IDC_PROTRAW,
1242 "&Telnet", IDC_PROTTELNET,
1243 "Rlog&in", IDC_PROTRLOGIN,
1252 beginbox(&cp, "Load, save or delete a stored session",
1254 sesssaver(&cp, "Sav&ed Sessions",
1255 IDC_SESSSTATIC, IDC_SESSEDIT, IDC_SESSLIST,
1256 "&Load", IDC_SESSLOAD,
1257 "&Save", IDC_SESSSAVE, "&Delete", IDC_SESSDEL, NULL);
1260 beginbox(&cp, NULL, IDC_BOX_SESSION3);
1261 radioline(&cp, "Close &window on exit:", IDC_CLOSEEXIT, 4,
1262 "Always", IDC_COEALWAYS,
1263 "Never", IDC_COENEVER,
1264 "Only on clean exit", IDC_COENORMAL, NULL);
1268 if (panel == loggingpanelstart) {
1269 /* The Logging panel. Accelerators used: [acgo] tplsfwe */
1271 ctlposinit(&cp, hwnd, 80, 3, 13);
1272 bartitle(&cp, "Options controlling session logging",
1274 beginbox(&cp, NULL, IDC_BOX_LOGGING1);
1276 "Session logging:", IDC_LSTATSTATIC,
1277 "Logging &turned off completely", IDC_LSTATOFF,
1278 "Log &printable output only", IDC_LSTATASCII,
1279 "&Log all session output", IDC_LSTATRAW,
1280 "Log &SSH packet data", IDC_LSTATPACKET,
1282 editbutton(&cp, "Log &file name:",
1283 IDC_LGFSTATIC, IDC_LGFEDIT, "Bro&wse...",
1285 statictext(&cp, "(Log file name can contain &&Y, &&M, &&D for date,"
1286 " &&T for time, and &&H for host name)", 2, IDC_LGFEXPLAIN);
1288 "What to do if the log file already &exists:",
1289 IDC_LSTATXIST, "Always overwrite it", IDC_LSTATXOVR,
1290 "Always append to the end of it", IDC_LSTATXAPN,
1291 "Ask the user every time", IDC_LSTATXASK, NULL);
1295 if (panel == terminalpanelstart) {
1296 /* The Terminal panel. Accelerators used: [acgo] wdlen hts */
1298 ctlposinit(&cp, hwnd, 80, 3, 13);
1299 bartitle(&cp, "Options controlling the terminal emulation",
1300 IDC_TITLE_TERMINAL);
1301 beginbox(&cp, "Set various terminal options", IDC_BOX_TERMINAL1);
1302 checkbox(&cp, "Auto &wrap mode initially on", IDC_WRAPMODE);
1303 checkbox(&cp, "&DEC Origin Mode initially on", IDC_DECOM);
1304 checkbox(&cp, "Implicit CR in every &LF", IDC_LFHASCR);
1305 checkbox(&cp, "Use background colour to &erase screen", IDC_BCE);
1306 checkbox(&cp, "Enable bli&nking text", IDC_BLINKTEXT);
1308 "An&swerback to ^E:", IDC_ANSWERBACK,
1309 IDC_ANSWEREDIT, 100, NULL);
1312 beginbox(&cp, "Line discipline options", IDC_BOX_TERMINAL2);
1313 radioline(&cp, "Local ec&ho:", IDC_ECHOSTATIC, 3,
1314 "Auto", IDC_ECHOBACKEND,
1315 "Force on", IDC_ECHOYES, "Force off", IDC_ECHONO, NULL);
1316 radioline(&cp, "Local line edi&ting:", IDC_EDITSTATIC, 3,
1317 "Auto", IDC_EDITBACKEND,
1318 "Force on", IDC_EDITYES, "Force off", IDC_EDITNO, NULL);
1322 if (panel == bellpanelstart) {
1323 /* The Bell panel. Accelerators used: [acgo] bdsm wit */
1325 ctlposinit(&cp, hwnd, 80, 3, 13);
1326 bartitle(&cp, "Options controlling the terminal bell",
1328 beginbox(&cp, "Set the style of bell", IDC_BOX_BELL1);
1330 "Action to happen when a &bell occurs:", IDC_BELLSTATIC,
1331 "None (bell disabled)", IDC_BELL_DISABLED,
1332 "Play Windows Default Sound", IDC_BELL_DEFAULT,
1333 "Play a custom sound file", IDC_BELL_WAVEFILE,
1334 "Visual bell (flash window)", IDC_BELL_VISUAL, NULL);
1335 editbutton(&cp, "Custom sound file to play as a bell:",
1336 IDC_BELL_WAVESTATIC, IDC_BELL_WAVEEDIT,
1337 "Bro&wse...", IDC_BELL_WAVEBROWSE);
1338 radioline(&cp, "Taskbar/caption &indication on bell:",
1339 IDC_B_IND_STATIC, 3, "Disabled", IDC_B_IND_DISABLED,
1340 "Flashing", IDC_B_IND_FLASH, "Steady", IDC_B_IND_STEADY,
1343 beginbox(&cp, "Control the bell overload behaviour",
1345 checkbox(&cp, "Bell is temporarily &disabled when over-used",
1347 staticedit(&cp, "Over-use means this &many bells...",
1348 IDC_BELLOVLNSTATIC, IDC_BELLOVLN, 20);
1349 staticedit(&cp, "... in &this many seconds",
1350 IDC_BELLOVLTSTATIC, IDC_BELLOVLT, 20);
1352 "The bell is re-enabled after a few seconds of silence.",
1353 1, IDC_BELLOVLEXPLAIN);
1354 staticedit(&cp, "Seconds of &silence required", IDC_BELLOVLSSTATIC,
1359 if (panel == keyboardpanelstart) {
1360 /* The Keyboard panel. Accelerators used: [acgo] bhf ruyntd */
1362 ctlposinit(&cp, hwnd, 80, 3, 13);
1363 bartitle(&cp, "Options controlling the effects of keys",
1364 IDC_TITLE_KEYBOARD);
1365 beginbox(&cp, "Change the sequences sent by:", IDC_BOX_KEYBOARD1);
1366 radioline(&cp, "The &Backspace key", IDC_DELSTATIC, 2,
1367 "Control-H", IDC_DEL008,
1368 "Control-? (127)", IDC_DEL127, NULL);
1369 radioline(&cp, "The &Home and End keys", IDC_HOMESTATIC, 2,
1370 "Standard", IDC_HOMETILDE, "rxvt", IDC_HOMERXVT, NULL);
1371 radioline(&cp, "The &Function keys and keypad", IDC_FUNCSTATIC, 3,
1372 "ESC[n~", IDC_FUNCTILDE,
1373 "Linux", IDC_FUNCLINUX,
1374 "Xterm R6", IDC_FUNCXTERM,
1375 "VT400", IDC_FUNCVT400,
1376 "VT100+", IDC_FUNCVT100P, "SCO", IDC_FUNCSCO, NULL);
1378 beginbox(&cp, "Application keypad settings:", IDC_BOX_KEYBOARD2);
1380 "Application c&ursor keys totally disabled",
1382 radioline(&cp, "Initial state of cu&rsor keys:", IDC_CURSTATIC, 2,
1383 "Normal", IDC_CURNORMAL,
1384 "Application", IDC_CURAPPLIC, NULL);
1386 "Application ke&ypad keys totally disabled",
1388 radioline(&cp, "Initial state of &numeric keypad:", IDC_KPSTATIC,
1389 3, "Normal", IDC_KPNORMAL, "Application", IDC_KPAPPLIC,
1390 "NetHack", IDC_KPNH, NULL);
1392 beginbox(&cp, "Enable extra keyboard features:",
1394 checkbox(&cp, "AltGr ac&ts as Compose key", IDC_COMPOSEKEY);
1395 checkbox(&cp, "Control-Alt is &different from AltGr",
1400 if (panel == windowpanelstart) {
1401 /* The Window panel. Accelerators used: [acgo] rmz sdikp */
1403 ctlposinit(&cp, hwnd, 80, 3, 13);
1404 bartitle(&cp, "Options controlling PuTTY's window",
1406 beginbox(&cp, "Set the size of the window", IDC_BOX_WINDOW1);
1408 "&Rows", IDC_ROWSSTATIC, IDC_ROWSEDIT, 50,
1409 "Colu&mns", IDC_COLSSTATIC, IDC_COLSEDIT, 50, NULL);
1410 radiobig(&cp, "When window is resi&zed:", IDC_RESIZESTATIC,
1411 "Change the number of rows and columns", IDC_RESIZETERM,
1412 "Change the size of the font", IDC_RESIZEFONT,
1413 "Change font size only when maximised", IDC_RESIZEEITHER,
1414 "Forbid resizing completely", IDC_RESIZENONE, NULL);
1416 beginbox(&cp, "Control the scrollback in the window",
1418 staticedit(&cp, "Lines of &scrollback",
1419 IDC_SAVESTATIC, IDC_SAVEEDIT, 50);
1420 checkbox(&cp, "&Display scrollbar", IDC_SCROLLBAR);
1421 checkbox(&cp, "D&isplay scrollbar in full screen mode", IDC_SCROLLBARFULLSCREEN);
1422 checkbox(&cp, "Reset scrollback on &keypress", IDC_SCROLLKEY);
1423 checkbox(&cp, "Reset scrollback on dis&play activity",
1428 if (panel == appearancepanelstart) {
1429 /* The Appearance panel. Accelerators used: [acgo] luvb h ti p s */
1431 ctlposinit(&cp, hwnd, 80, 3, 13);
1432 bartitle(&cp, "Configure the appearance of PuTTY's window",
1433 IDC_TITLE_APPEARANCE);
1434 beginbox(&cp, "Adjust the use of the cursor", IDC_BOX_APPEARANCE1);
1435 radioline(&cp, "Cursor appearance:", IDC_CURSORSTATIC, 3,
1436 "B&lock", IDC_CURBLOCK,
1437 "&Underline", IDC_CURUNDER,
1438 "&Vertical line", IDC_CURVERT, NULL);
1439 checkbox(&cp, "Cursor &blinks", IDC_BLINKCUR);
1441 beginbox(&cp, "Set the font used in the terminal window",
1442 IDC_BOX_APPEARANCE2);
1443 staticbtn(&cp, "", IDC_FONTSTATIC, "C&hange...", IDC_CHOOSEFONT);
1445 beginbox(&cp, "Adjust the use of the window title",
1446 IDC_BOX_APPEARANCE3);
1448 "Window &title:", IDC_WINTITLE, IDC_WINEDIT, 100, NULL);
1449 checkbox(&cp, "Avoid ever using &icon title", IDC_WINNAME);
1451 beginbox(&cp, "Adjust the use of the mouse pointer",
1452 IDC_BOX_APPEARANCE4);
1453 checkbox(&cp, "Hide mouse &pointer when typing in window",
1456 beginbox(&cp, "Adjust the window border", IDC_BOX_APPEARANCE5);
1457 checkbox(&cp, "&Sunken-edge border (slightly thicker)",
1459 staticedit(&cp, "Gap between text and window edge",
1460 IDC_WINBSTATIC, IDC_WINBEDIT, 20);
1464 if (panel == behaviourpanelstart) {
1465 /* The Behaviour panel. Accelerators used: [acgo] w4yltf */
1467 ctlposinit(&cp, hwnd, 80, 3, 13);
1468 bartitle(&cp, "Configure the behaviour of PuTTY's window",
1470 beginbox(&cp, NULL, IDC_BOX_BEHAVIOUR1);
1471 checkbox(&cp, "&Warn before closing window", IDC_CLOSEWARN);
1472 checkbox(&cp, "Window closes on ALT-F&4", IDC_ALTF4);
1473 checkbox(&cp, "S&ystem menu appears on ALT-Space", IDC_ALTSPACE);
1474 checkbox(&cp, "System menu appears on A< alone", IDC_ALTONLY);
1475 checkbox(&cp, "Ensure window is always on &top", IDC_ALWAYSONTOP);
1476 checkbox(&cp, "&Full screen on Alt-Enter", IDC_FULLSCREENONALTENTER);
1480 if (panel == translationpanelstart) {
1481 /* The Translation panel. Accelerators used: [acgo] rxbepus */
1483 ctlposinit(&cp, hwnd, 80, 3, 13);
1484 bartitle(&cp, "Options controlling character set translation",
1485 IDC_TITLE_TRANSLATION);
1486 beginbox(&cp, "Character set translation on received data",
1487 IDC_BOX_TRANSLATION1);
1488 combobox(&cp, "&Received data assumed to be in which character set:",
1489 IDC_CODEPAGESTATIC, IDC_CODEPAGE);
1491 beginbox(&cp, "Enable character set translation on input data",
1492 IDC_BOX_TRANSLATION2);
1493 checkbox(&cp, "Cap&s Lock acts as Cyrillic switch",
1496 beginbox(&cp, "Adjust how PuTTY displays line drawing characters",
1497 IDC_BOX_TRANSLATION3);
1499 "Handling of line drawing characters:", IDC_VTSTATIC,
1500 "Font has &XWindows encoding", IDC_VTXWINDOWS,
1501 "Use font in &both ANSI and OEM modes", IDC_VTOEMANSI,
1502 "Use font in O&EM mode only", IDC_VTOEMONLY,
1503 "&Poor man's line drawing (" "+" ", " "-" " and " "|" ")",
1504 IDC_VTPOORMAN, "&Unicode mode", IDC_VTUNICODE, NULL);
1508 if (panel == selectionpanelstart) {
1509 /* The Selection panel. Accelerators used: [acgo] df wxp hst nr */
1511 ctlposinit(&cp, hwnd, 80, 3, 13);
1512 bartitle(&cp, "Options controlling copy and paste",
1513 IDC_TITLE_SELECTION);
1514 beginbox(&cp, "Translation of pasted characters",
1515 IDC_BOX_SELECTION1);
1517 "&Don't translate line drawing chars into +, - and |",
1520 "Paste to clipboard in RT&F as well as plain text",
1523 beginbox(&cp, "Control which mouse button does which thing",
1524 IDC_BOX_SELECTION2);
1525 radiobig(&cp, "Action of mouse buttons:", IDC_MBSTATIC,
1526 "&Windows (Right pastes, Middle extends)", IDC_MBWINDOWS,
1527 "&xterm (Right extends, Middle pastes)", IDC_MBXTERM,
1530 "Shift overrides a&pplication's use of mouse",
1533 "Default selection mode (Alt+drag does the other one):",
1534 IDC_SELTYPESTATIC, 2,
1535 "&Normal", IDC_SELTYPELEX,
1536 "&Rectangular block", IDC_SELTYPERECT, NULL);
1538 beginbox(&cp, "Control the select-one-word-at-a-time mode",
1539 IDC_BOX_SELECTION3);
1540 charclass(&cp, "C&haracter classes:", IDC_CCSTATIC, IDC_CCLIST,
1541 "&Set", IDC_CCSET, IDC_CCEDIT,
1542 "&to class", IDC_CCSTATIC2);
1546 if (panel == colourspanelstart) {
1547 /* The Colours panel. Accelerators used: [acgo] blum */
1549 ctlposinit(&cp, hwnd, 80, 3, 13);
1550 bartitle(&cp, "Options controlling use of colours",
1552 beginbox(&cp, "General options for colour usage",
1554 checkbox(&cp, "&Bolded text is a different colour",
1556 checkbox(&cp, "Attempt to use &logical palettes", IDC_PALETTE);
1558 beginbox(&cp, "Adjust the precise colours PuTTY displays",
1560 colouredit(&cp, "Select a colo&ur and then click to modify it:",
1561 IDC_COLOURSTATIC, IDC_COLOURLIST,
1562 "&Modify...", IDC_CHANGE,
1563 "Red:", IDC_RSTATIC, IDC_RVALUE,
1564 "Green:", IDC_GSTATIC, IDC_GVALUE,
1565 "Blue:", IDC_BSTATIC, IDC_BVALUE, NULL);
1569 if (panel == connectionpanelstart) {
1570 /* The Connection panel. Accelerators used: [acgo] tukn */
1572 ctlposinit(&cp, hwnd, 80, 3, 13);
1573 bartitle(&cp, "Options controlling the connection",
1574 IDC_TITLE_CONNECTION);
1576 beginbox(&cp, "Data to send to the server",
1577 IDC_BOX_CONNECTION1);
1578 staticedit(&cp, "Terminal-&type string", IDC_TTSTATIC,
1580 staticedit(&cp, "Auto-login &username", IDC_LOGSTATIC,
1584 beginbox(&cp, "Adjust telnet session.", IDC_BOX_CONNECTION1);
1585 checkbox(&cp, "Keyboard sends telnet Backspace and Interrupt",
1587 checkbox(&cp, "Return key sends telnet New Line instead of ^M",
1591 beginbox(&cp, "Sending of null packets to keep session active",
1592 IDC_BOX_CONNECTION2);
1593 staticedit(&cp, "Seconds between &keepalives (0 to turn off)",
1594 IDC_PINGSTATIC, IDC_PINGEDIT, 20);
1597 beginbox(&cp, "Low-level TCP connection options",
1598 IDC_BOX_CONNECTION3);
1599 checkbox(&cp, "Disable &Nagle's algorithm (TCP_NODELAY option)",
1605 if (panel == telnetpanelstart) {
1606 /* The Telnet panel. Accelerators used: [acgo] svldr bftk */
1608 ctlposinit(&cp, hwnd, 80, 3, 13);
1610 bartitle(&cp, "Options controlling Telnet connections",
1612 beginbox(&cp, "Data to send to the server", IDC_BOX_TELNET1);
1613 staticedit(&cp, "Terminal-&speed string", IDC_TSSTATIC,
1615 envsetter(&cp, "Environment variables:", IDC_ENVSTATIC,
1616 "&Variable", IDC_VARSTATIC, IDC_VAREDIT, "Va&lue",
1617 IDC_VALSTATIC, IDC_VALEDIT, IDC_ENVLIST, "A&dd",
1618 IDC_ENVADD, "&Remove", IDC_ENVREMOVE);
1620 beginbox(&cp, "Telnet protocol adjustments", IDC_BOX_TELNET2);
1621 radioline(&cp, "Handling of OLD_ENVIRON ambiguity:",
1622 IDC_EMSTATIC, 2, "&BSD (commonplace)", IDC_EMBSD,
1623 "R&FC 1408 (unusual)", IDC_EMRFC, NULL);
1624 radioline(&cp, "&Telnet negotiation mode:", IDC_ACTSTATIC, 2,
1625 "Passive", IDC_TPASSIVE, "Active",
1627 checkbox(&cp, "&Keyboard sends telnet Backspace and Interrupt",
1629 checkbox(&cp, "Return key sends telnet New Line instead of ^M",
1635 if (panel == rloginpanelstart) {
1636 /* The Rlogin panel. Accelerators used: [acgo] sl */
1638 ctlposinit(&cp, hwnd, 80, 3, 13);
1640 bartitle(&cp, "Options controlling Rlogin connections",
1642 beginbox(&cp, "Data to send to the server", IDC_BOX_RLOGIN1);
1643 staticedit(&cp, "Terminal-&speed string", IDC_R_TSSTATIC,
1645 staticedit(&cp, "&Local username:", IDC_RLLUSERSTATIC,
1646 IDC_RLLUSEREDIT, 50);
1651 if (panel == sshpanelstart) {
1652 /* The SSH panel. Accelerators used: [acgo] r pe12i sd */
1654 ctlposinit(&cp, hwnd, 80, 3, 13);
1656 bartitle(&cp, "Options controlling SSH connections",
1658 beginbox(&cp, "Data to send to the server", IDC_BOX_SSH1);
1660 "&Remote command:", IDC_CMDSTATIC, IDC_CMDEDIT, 100,
1663 beginbox(&cp, "Protocol options", IDC_BOX_SSH2);
1664 checkbox(&cp, "Don't allocate a &pseudo-terminal", IDC_NOPTY);
1665 checkbox(&cp, "Enable compr&ession", IDC_COMPRESS);
1666 radioline(&cp, "Preferred SSH protocol version:",
1667 IDC_SSHPROTSTATIC, 2,
1668 "&1", IDC_SSHPROT1, "&2", IDC_SSHPROT2, NULL);
1669 checkbox(&cp, "&Imitate SSH 2 MAC bug in commercial <= v2.3.x",
1672 beginbox(&cp, "Encryption options", IDC_BOX_SSH3);
1673 prefslist(&cipherlist, &cp, "Encryption cipher &selection policy:",
1674 IDC_CIPHERSTATIC2, IDC_CIPHERLIST, IDC_CIPHERUP,
1676 checkbox(&cp, "Enable non-standard use of single-&DES in SSH 2",
1682 if (panel == sshauthpanelstart) {
1683 /* The SSH authentication panel. Accelerators used: [acgo] m fkiw */
1685 ctlposinit(&cp, hwnd, 80, 3, 13);
1687 bartitle(&cp, "Options controlling SSH authentication",
1689 beginbox(&cp, "Authentication methods",
1691 checkbox(&cp, "Atte&mpt TIS or CryptoCard authentication (SSH1)",
1693 checkbox(&cp, "Attempt \"keyboard-&interactive\" authentication"
1694 " (SSH2)", IDC_AUTHKI);
1696 beginbox(&cp, "Authentication parameters",
1698 checkbox(&cp, "Allow agent &forwarding", IDC_AGENTFWD);
1699 checkbox(&cp, "Allow attempted changes of &username in SSH2",
1701 editbutton(&cp, "Private &key file for authentication:",
1702 IDC_PKSTATIC, IDC_PKEDIT, "Bro&wse...",
1708 if (panel == tunnelspanelstart) {
1709 /* The Tunnels panel. Accelerators used: [acgo] deilmrsthx */
1711 ctlposinit(&cp, hwnd, 80, 3, 13);
1713 bartitle(&cp, "Options controlling SSH tunnelling",
1715 beginbox(&cp, "X11 forwarding", IDC_BOX_TUNNELS1);
1716 checkbox(&cp, "&Enable X11 forwarding", IDC_X11_FORWARD);
1717 multiedit(&cp, "&X display location", IDC_X11_DISPSTATIC,
1718 IDC_X11_DISPLAY, 50, NULL);
1720 beginbox(&cp, "Port forwarding", IDC_BOX_TUNNELS2);
1721 checkbox(&cp, "Local ports accept connections from o&ther hosts",
1723 checkbox(&cp, "Remote ports do t&he same (SSH v2 only)",
1725 staticbtn(&cp, "Forwarded ports:", IDC_PFWDSTATIC,
1726 "&Remove", IDC_PFWDREMOVE);
1727 fwdsetter(&cp, IDC_PFWDLIST,
1728 "Add new forwarded port:", IDC_PFWDSTATIC2,
1729 "&Source port", IDC_SPORTSTATIC, IDC_SPORTEDIT,
1730 "Dest&ination", IDC_DPORTSTATIC, IDC_DPORTEDIT,
1731 "A&dd", IDC_PFWDADD);
1732 bareradioline(&cp, 2,
1733 "&Local", IDC_PFWDLOCAL,
1734 "Re&mote", IDC_PFWDREMOTE, NULL);
1742 * Helper function to load the session selected in SESSLIST
1743 * if any, as this is done in more than one place in
1744 * GenericMainDlgProc(). 0 => failure.
1746 static int load_selected_session(HWND hwnd)
1748 int n = SendDlgItemMessage(hwnd, IDC_SESSLIST,
1749 LB_GETCURSEL, 0, 0);
1755 isdef = !strcmp(sessions[n], "Default Settings");
1756 load_settings(sessions[n], !isdef, &cfg);
1757 init_dlg_ctrls(hwnd, TRUE);
1759 SetDlgItemText(hwnd, IDC_SESSEDIT, sessions[n]);
1761 SetDlgItemText(hwnd, IDC_SESSEDIT, "");
1762 /* Restore the selection, which will have been clobbered by
1763 * SESSEDIT handling. */
1764 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL, n, 0);
1769 * This function is the configuration box.
1771 static int GenericMainDlgProc(HWND hwnd, UINT msg,
1772 WPARAM wParam, LPARAM lParam, int dlgtype)
1775 struct treeview_faff tvfaff;
1778 char filename[sizeof(cfg.keyfile)];
1781 char fontstatic[256];
1783 struct servent *service;
1785 static UINT draglistmsg = WM_NULL;
1790 SetWindowLong(hwnd, GWL_USERDATA, 0);
1792 SetWindowLong(hwnd, GWL_EXSTYLE,
1793 GetWindowLong(hwnd, GWL_EXSTYLE) | WS_EX_CONTEXTHELP);
1795 HWND item = GetDlgItem(hwnd, IDC_HELPBTN);
1797 DestroyWindow(item);
1799 requested_help = FALSE;
1800 SendMessage(hwnd, WM_SETICON, (WPARAM) ICON_BIG,
1801 (LPARAM) LoadIcon(hinst, MAKEINTRESOURCE(IDI_CFGICON)));
1803 * Centre the window.
1805 { /* centre the window */
1808 hw = GetDesktopWindow();
1809 if (GetWindowRect(hw, &rs) && GetWindowRect(hwnd, &rd))
1811 (rs.right + rs.left + rd.left - rd.right) / 2,
1812 (rs.bottom + rs.top + rd.top - rd.bottom) / 2,
1813 rd.right - rd.left, rd.bottom - rd.top, TRUE);
1817 * Create the tree view.
1825 r.right = r.left + 75;
1827 r.bottom = r.top + 10;
1828 MapDialogRect(hwnd, &r);
1829 tvstatic = CreateWindowEx(0, "STATIC", "Cate&gory:",
1830 WS_CHILD | WS_VISIBLE,
1832 r.right - r.left, r.bottom - r.top,
1833 hwnd, (HMENU) IDCX_TVSTATIC, hinst,
1835 font = SendMessage(hwnd, WM_GETFONT, 0, 0);
1836 SendMessage(tvstatic, WM_SETFONT, font, MAKELPARAM(TRUE, 0));
1839 r.right = r.left + 75;
1841 r.bottom = r.top + 219;
1842 MapDialogRect(hwnd, &r);
1843 treeview = CreateWindowEx(WS_EX_CLIENTEDGE, WC_TREEVIEW, "",
1844 WS_CHILD | WS_VISIBLE |
1845 WS_TABSTOP | TVS_HASLINES |
1846 TVS_DISABLEDRAGDROP | TVS_HASBUTTONS
1848 TVS_SHOWSELALWAYS, r.left, r.top,
1849 r.right - r.left, r.bottom - r.top,
1850 hwnd, (HMENU) IDCX_TREEVIEW, hinst,
1852 font = SendMessage(hwnd, WM_GETFONT, 0, 0);
1853 SendMessage(treeview, WM_SETFONT, font, MAKELPARAM(TRUE, 0));
1854 tvfaff.treeview = treeview;
1855 memset(tvfaff.lastat, 0, sizeof(tvfaff.lastat));
1859 * Set up the tree view contents.
1861 hsession = treeview_insert(&tvfaff, 0, "Session");
1862 treeview_insert(&tvfaff, 1, "Logging");
1863 treeview_insert(&tvfaff, 0, "Terminal");
1864 treeview_insert(&tvfaff, 1, "Keyboard");
1865 treeview_insert(&tvfaff, 1, "Bell");
1866 treeview_insert(&tvfaff, 0, "Window");
1867 treeview_insert(&tvfaff, 1, "Appearance");
1868 treeview_insert(&tvfaff, 1, "Behaviour");
1869 treeview_insert(&tvfaff, 1, "Translation");
1870 treeview_insert(&tvfaff, 1, "Selection");
1871 treeview_insert(&tvfaff, 1, "Colours");
1872 treeview_insert(&tvfaff, 0, "Connection");
1874 treeview_insert(&tvfaff, 1, "Telnet");
1875 treeview_insert(&tvfaff, 1, "Rlogin");
1876 if (backends[3].backend != NULL) {
1877 treeview_insert(&tvfaff, 1, "SSH");
1878 /* XXX long name is ugly */
1879 /* XXX make it closed by default? */
1880 treeview_insert(&tvfaff, 2, "Auth");
1881 treeview_insert(&tvfaff, 2, "Tunnels");
1886 * Put the treeview selection on to the Session panel. This
1887 * should also cause creation of the relevant controls.
1889 TreeView_SelectItem(treeview, hsession);
1892 * Set focus into the first available control.
1896 ctl = GetDlgItem(hwnd, IDC_HOST);
1898 ctl = GetDlgItem(hwnd, IDC_CLOSEEXIT);
1902 SetWindowLong(hwnd, GWL_USERDATA, 1);
1903 sesslist_has_focus = 0;
1907 * Button release should trigger WM_OK if there was a
1908 * previous double click on the session list.
1912 SendMessage(hwnd, WM_COMMAND, IDOK, 0);
1915 if (LOWORD(wParam) == IDCX_TREEVIEW &&
1916 ((LPNMHDR) lParam)->code == TVN_SELCHANGED) {
1918 TreeView_GetSelection(((LPNMHDR) lParam)->hwndFrom);
1923 SendMessage (hwnd, WM_SETREDRAW, FALSE, 0);
1926 item.pszText = buffer;
1927 item.cchTextMax = sizeof(buffer);
1928 item.mask = TVIF_TEXT;
1929 TreeView_GetItem(((LPNMHDR) lParam)->hwndFrom, &item);
1930 for (j = controlstartvalue; j < controlendvalue; j++) {
1931 HWND item = GetDlgItem(hwnd, j);
1933 DestroyWindow(item);
1935 if (!strcmp(buffer, "Session"))
1936 create_controls(hwnd, dlgtype, sessionpanelstart);
1937 if (!strcmp(buffer, "Logging"))
1938 create_controls(hwnd, dlgtype, loggingpanelstart);
1939 if (!strcmp(buffer, "Keyboard"))
1940 create_controls(hwnd, dlgtype, keyboardpanelstart);
1941 if (!strcmp(buffer, "Terminal"))
1942 create_controls(hwnd, dlgtype, terminalpanelstart);
1943 if (!strcmp(buffer, "Bell"))
1944 create_controls(hwnd, dlgtype, bellpanelstart);
1945 if (!strcmp(buffer, "Window"))
1946 create_controls(hwnd, dlgtype, windowpanelstart);
1947 if (!strcmp(buffer, "Appearance"))
1948 create_controls(hwnd, dlgtype, appearancepanelstart);
1949 if (!strcmp(buffer, "Behaviour"))
1950 create_controls(hwnd, dlgtype, behaviourpanelstart);
1951 if (!strcmp(buffer, "Tunnels"))
1952 create_controls(hwnd, dlgtype, tunnelspanelstart);
1953 if (!strcmp(buffer, "Connection"))
1954 create_controls(hwnd, dlgtype, connectionpanelstart);
1955 if (!strcmp(buffer, "Telnet"))
1956 create_controls(hwnd, dlgtype, telnetpanelstart);
1957 if (!strcmp(buffer, "Rlogin"))
1958 create_controls(hwnd, dlgtype, rloginpanelstart);
1959 if (!strcmp(buffer, "SSH"))
1960 create_controls(hwnd, dlgtype, sshpanelstart);
1961 if (!strcmp(buffer, "Auth"))
1962 create_controls(hwnd, dlgtype, sshauthpanelstart);
1963 if (!strcmp(buffer, "Selection"))
1964 create_controls(hwnd, dlgtype, selectionpanelstart);
1965 if (!strcmp(buffer, "Colours"))
1966 create_controls(hwnd, dlgtype, colourspanelstart);
1967 if (!strcmp(buffer, "Translation"))
1968 create_controls(hwnd, dlgtype, translationpanelstart);
1970 init_dlg_ctrls(hwnd, FALSE);
1972 SendMessage (hwnd, WM_SETREDRAW, TRUE, 0);
1973 InvalidateRect (hwnd, NULL, TRUE);
1975 SetFocus(((LPNMHDR) lParam)->hwndFrom); /* ensure focus stays */
1981 * Only process WM_COMMAND once the dialog is fully formed.
1983 if (GetWindowLong(hwnd, GWL_USERDATA) == 1)
1984 switch (LOWORD(wParam)) {
1986 /* Behaviour of the "Open" button is different if the
1987 * session list has focus, *unless* the user just
1988 * double-clicked... */
1989 if (sesslist_has_focus && !readytogo) {
1990 if (!load_selected_session(hwnd)) {
1995 /* If at this point we have a valid session, go! */
1997 if (requested_help) {
1998 WinHelp(hwnd, help_path, HELP_QUIT, 0);
1999 requested_help = FALSE;
2006 if (HIWORD(wParam) == BN_CLICKED ||
2007 HIWORD(wParam) == BN_DOUBLECLICKED) {
2009 WinHelp(hwnd, help_path,
2010 help_has_contents ? HELP_FINDER : HELP_CONTENTS,
2012 requested_help = TRUE;
2017 if (requested_help) {
2018 WinHelp(hwnd, help_path, HELP_QUIT, 0);
2019 requested_help = FALSE;
2023 case IDC_PROTTELNET:
2024 case IDC_PROTRLOGIN:
2027 if (HIWORD(wParam) == BN_CLICKED ||
2028 HIWORD(wParam) == BN_DOUBLECLICKED) {
2029 int i = IsDlgButtonChecked(hwnd, IDC_PROTSSH);
2030 int j = IsDlgButtonChecked(hwnd, IDC_PROTTELNET);
2031 int k = IsDlgButtonChecked(hwnd, IDC_PROTRLOGIN);
2033 i ? PROT_SSH : j ? PROT_TELNET : k ? PROT_RLOGIN :
2035 if ((cfg.protocol == PROT_SSH && cfg.port != 22)
2036 || (cfg.protocol == PROT_TELNET && cfg.port != 23)
2037 || (cfg.protocol == PROT_RLOGIN
2038 && cfg.port != 513)) {
2039 cfg.port = i ? 22 : j ? 23 : 513;
2040 SetDlgItemInt(hwnd, IDC_PORT, cfg.port, FALSE);
2045 if (HIWORD(wParam) == EN_CHANGE)
2046 GetDlgItemText(hwnd, IDC_HOST, cfg.host,
2047 sizeof(cfg.host) - 1);
2050 if (HIWORD(wParam) == EN_CHANGE) {
2051 GetDlgItemText(hwnd, IDC_PORT, portname, 31);
2052 if (isdigit(portname[0]))
2053 MyGetDlgItemInt(hwnd, IDC_PORT, &cfg.port);
2055 service = getservbyname(portname, NULL);
2057 cfg.port = ntohs(service->s_port);
2064 if (HIWORD(wParam) == EN_CHANGE) {
2065 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL,
2067 GetDlgItemText(hwnd, IDC_SESSEDIT,
2068 savedsession, sizeof(savedsession) - 1);
2069 savedsession[sizeof(savedsession) - 1] = '\0';
2073 if (HIWORD(wParam) == BN_CLICKED ||
2074 HIWORD(wParam) == BN_DOUBLECLICKED) {
2079 GetDlgItemText(hwnd, IDC_SESSEDIT, str,
2082 int n = SendDlgItemMessage(hwnd, IDC_SESSLIST,
2083 LB_GETCURSEL, 0, 0);
2088 strcpy(str, sessions[n]);
2090 save_settings(str, !!strcmp(str, "Default Settings"),
2092 get_sesslist(FALSE);
2094 SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2096 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_RESETCONTENT,
2098 for (i = 0; i < nsessions; i++)
2099 SendDlgItemMessage(hwnd, IDC_SESSLIST,
2101 (LPARAM) (sessions[i]));
2102 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL,
2104 SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2106 InvalidateRect(GetDlgItem(hwnd, IDC_SESSLIST), NULL,
2112 if (LOWORD(wParam) == IDC_SESSLIST) {
2113 if (HIWORD(wParam) == LBN_SETFOCUS)
2114 sesslist_has_focus = 1;
2115 else if (HIWORD(wParam) == LBN_KILLFOCUS)
2116 sesslist_has_focus = 0;
2118 if (LOWORD(wParam) == IDC_SESSLOAD &&
2119 HIWORD(wParam) != BN_CLICKED &&
2120 HIWORD(wParam) != BN_DOUBLECLICKED) break;
2121 if (LOWORD(wParam) == IDC_SESSLIST &&
2122 HIWORD(wParam) != LBN_DBLCLK) break;
2123 /* Load the session selected in SESSLIST. */
2124 if (load_selected_session(hwnd) &&
2125 LOWORD(wParam) == IDC_SESSLIST) {
2127 * A double-click on a saved session should
2128 * actually start the session, not just load it.
2129 * Unless it's Default Settings or some other
2130 * host-less set of saved settings.
2139 if (HIWORD(wParam) == BN_CLICKED ||
2140 HIWORD(wParam) == BN_DOUBLECLICKED) {
2141 int n = SendDlgItemMessage(hwnd, IDC_SESSLIST,
2142 LB_GETCURSEL, 0, 0);
2143 if (n == LB_ERR || n == 0) {
2147 del_settings(sessions[n]);
2148 get_sesslist(FALSE);
2150 SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2152 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_RESETCONTENT,
2154 for (i = 0; i < nsessions; i++)
2155 SendDlgItemMessage(hwnd, IDC_SESSLIST,
2157 (LPARAM) (sessions[i]));
2158 SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL,
2160 SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2162 InvalidateRect(GetDlgItem(hwnd, IDC_SESSLIST), NULL,
2166 if (HIWORD(wParam) == EN_CHANGE)
2167 MyGetDlgItemInt(hwnd, IDC_PINGEDIT,
2168 &cfg.ping_interval);
2171 if (HIWORD(wParam) == BN_CLICKED ||
2172 HIWORD(wParam) == BN_DOUBLECLICKED)
2174 IsDlgButtonChecked(hwnd, IDC_NODELAY);
2178 if (HIWORD(wParam) == BN_CLICKED ||
2179 HIWORD(wParam) == BN_DOUBLECLICKED)
2180 cfg.bksp_is_delete =
2181 IsDlgButtonChecked(hwnd, IDC_DEL127);
2185 if (HIWORD(wParam) == BN_CLICKED ||
2186 HIWORD(wParam) == BN_DOUBLECLICKED)
2188 IsDlgButtonChecked(hwnd, IDC_HOMERXVT);
2194 case IDC_FUNCVT100P:
2196 if (HIWORD(wParam) == BN_CLICKED ||
2197 HIWORD(wParam) == BN_DOUBLECLICKED)
2198 switch (LOWORD(wParam)) {
2211 case IDC_FUNCVT100P:
2221 if (HIWORD(wParam) == BN_CLICKED ||
2222 HIWORD(wParam) == BN_DOUBLECLICKED) {
2224 IsDlgButtonChecked(hwnd, IDC_KPAPPLIC);
2225 cfg.nethack_keypad = FALSE;
2229 if (HIWORD(wParam) == BN_CLICKED ||
2230 HIWORD(wParam) == BN_DOUBLECLICKED) {
2231 cfg.app_keypad = FALSE;
2232 cfg.nethack_keypad = TRUE;
2237 if (HIWORD(wParam) == BN_CLICKED ||
2238 HIWORD(wParam) == BN_DOUBLECLICKED)
2240 IsDlgButtonChecked(hwnd, IDC_CURAPPLIC);
2243 if (HIWORD(wParam) == BN_CLICKED ||
2244 HIWORD(wParam) == BN_DOUBLECLICKED)
2246 IsDlgButtonChecked(hwnd, IDC_NOAPPLICC);
2249 if (HIWORD(wParam) == BN_CLICKED ||
2250 HIWORD(wParam) == BN_DOUBLECLICKED)
2252 IsDlgButtonChecked(hwnd, IDC_NOAPPLICK);
2255 if (HIWORD(wParam) == BN_CLICKED ||
2256 HIWORD(wParam) == BN_DOUBLECLICKED)
2257 cfg.alt_f4 = IsDlgButtonChecked(hwnd, IDC_ALTF4);
2260 if (HIWORD(wParam) == BN_CLICKED ||
2261 HIWORD(wParam) == BN_DOUBLECLICKED)
2263 IsDlgButtonChecked(hwnd, IDC_ALTSPACE);
2266 if (HIWORD(wParam) == BN_CLICKED ||
2267 HIWORD(wParam) == BN_DOUBLECLICKED)
2269 IsDlgButtonChecked(hwnd, IDC_ALTONLY);
2271 case IDC_ECHOBACKEND:
2274 if (HIWORD(wParam) == BN_CLICKED ||
2275 HIWORD(wParam) == BN_DOUBLECLICKED) {
2276 if (LOWORD(wParam) == IDC_ECHOBACKEND)
2277 cfg.localecho = LD_BACKEND;
2278 if (LOWORD(wParam) == IDC_ECHOYES)
2279 cfg.localecho = LD_YES;
2280 if (LOWORD(wParam) == IDC_ECHONO)
2281 cfg.localecho = LD_NO;
2284 case IDC_EDITBACKEND:
2287 if (HIWORD(wParam) == BN_CLICKED ||
2288 HIWORD(wParam) == BN_DOUBLECLICKED) {
2289 if (LOWORD(wParam) == IDC_EDITBACKEND)
2290 cfg.localedit = LD_BACKEND;
2291 if (LOWORD(wParam) == IDC_EDITYES)
2292 cfg.localedit = LD_YES;
2293 if (LOWORD(wParam) == IDC_EDITNO)
2294 cfg.localedit = LD_NO;
2297 case IDC_ANSWEREDIT:
2298 if (HIWORD(wParam) == EN_CHANGE)
2299 GetDlgItemText(hwnd, IDC_ANSWEREDIT, cfg.answerback,
2300 sizeof(cfg.answerback) - 1);
2302 case IDC_ALWAYSONTOP:
2303 if (HIWORD(wParam) == BN_CLICKED ||
2304 HIWORD(wParam) == BN_DOUBLECLICKED)
2306 IsDlgButtonChecked(hwnd, IDC_ALWAYSONTOP);
2308 case IDC_FULLSCREENONALTENTER:
2309 if (HIWORD(wParam) == BN_CLICKED ||
2310 HIWORD(wParam) == BN_DOUBLECLICKED)
2311 cfg.fullscreenonaltenter =
2312 IsDlgButtonChecked(hwnd, IDC_FULLSCREENONALTENTER);
2315 if (HIWORD(wParam) == BN_CLICKED ||
2316 HIWORD(wParam) == BN_DOUBLECLICKED)
2318 IsDlgButtonChecked(hwnd, IDC_SCROLLKEY);
2320 case IDC_SCROLLDISP:
2321 if (HIWORD(wParam) == BN_CLICKED ||
2322 HIWORD(wParam) == BN_DOUBLECLICKED)
2323 cfg.scroll_on_disp =
2324 IsDlgButtonChecked(hwnd, IDC_SCROLLDISP);
2326 case IDC_COMPOSEKEY:
2327 if (HIWORD(wParam) == BN_CLICKED ||
2328 HIWORD(wParam) == BN_DOUBLECLICKED)
2330 IsDlgButtonChecked(hwnd, IDC_COMPOSEKEY);
2332 case IDC_CTRLALTKEYS:
2333 if (HIWORD(wParam) == BN_CLICKED ||
2334 HIWORD(wParam) == BN_DOUBLECLICKED)
2336 IsDlgButtonChecked(hwnd, IDC_CTRLALTKEYS);
2339 if (HIWORD(wParam) == BN_CLICKED ||
2340 HIWORD(wParam) == BN_DOUBLECLICKED)
2341 cfg.telnet_keyboard =
2342 IsDlgButtonChecked(hwnd, IDC_TELNETKEY);
2345 if (HIWORD(wParam) == BN_CLICKED ||
2346 HIWORD(wParam) == BN_DOUBLECLICKED)
2347 cfg.telnet_newline =
2348 IsDlgButtonChecked(hwnd, IDC_TELNETRET);
2351 if (HIWORD(wParam) == BN_CLICKED ||
2352 HIWORD(wParam) == BN_DOUBLECLICKED)
2354 IsDlgButtonChecked(hwnd, IDC_WRAPMODE);
2357 if (HIWORD(wParam) == BN_CLICKED ||
2358 HIWORD(wParam) == BN_DOUBLECLICKED)
2359 cfg.dec_om = IsDlgButtonChecked(hwnd, IDC_DECOM);
2362 if (HIWORD(wParam) == BN_CLICKED ||
2363 HIWORD(wParam) == BN_DOUBLECLICKED)
2365 IsDlgButtonChecked(hwnd, IDC_LFHASCR);
2368 if (HIWORD(wParam) == EN_CHANGE)
2369 MyGetDlgItemInt(hwnd, IDC_ROWSEDIT, &cfg.height);
2372 if (HIWORD(wParam) == EN_CHANGE)
2373 MyGetDlgItemInt(hwnd, IDC_COLSEDIT, &cfg.width);
2376 if (HIWORD(wParam) == EN_CHANGE)
2377 MyGetDlgItemInt(hwnd, IDC_SAVEEDIT, &cfg.savelines);
2379 case IDC_CHOOSEFONT:
2382 lf.lfHeight = -MulDiv(cfg.fontheight,
2383 GetDeviceCaps(hdc, LOGPIXELSY),
2387 lf.lfWidth = lf.lfEscapement = lf.lfOrientation = 0;
2388 lf.lfItalic = lf.lfUnderline = lf.lfStrikeOut = 0;
2389 lf.lfWeight = (cfg.fontisbold ? FW_BOLD : 0);
2390 lf.lfCharSet = cfg.fontcharset;
2391 lf.lfOutPrecision = OUT_DEFAULT_PRECIS;
2392 lf.lfClipPrecision = CLIP_DEFAULT_PRECIS;
2393 lf.lfQuality = DEFAULT_QUALITY;
2394 lf.lfPitchAndFamily = FIXED_PITCH | FF_DONTCARE;
2395 strncpy(lf.lfFaceName, cfg.font,
2396 sizeof(lf.lfFaceName) - 1);
2397 lf.lfFaceName[sizeof(lf.lfFaceName) - 1] = '\0';
2399 cf.lStructSize = sizeof(cf);
2400 cf.hwndOwner = hwnd;
2402 cf.Flags = CF_FIXEDPITCHONLY | CF_FORCEFONTEXIST |
2403 CF_INITTOLOGFONTSTRUCT | CF_SCREENFONTS;
2405 if (ChooseFont(&cf)) {
2406 strncpy(cfg.font, lf.lfFaceName, sizeof(cfg.font) - 1);
2407 cfg.font[sizeof(cfg.font) - 1] = '\0';
2408 cfg.fontisbold = (lf.lfWeight == FW_BOLD);
2409 cfg.fontcharset = lf.lfCharSet;
2410 cfg.fontheight = cf.iPointSize / 10;
2411 fmtfont(fontstatic);
2412 SetDlgItemText(hwnd, IDC_FONTSTATIC, fontstatic);
2415 case IDC_BELL_DISABLED:
2416 case IDC_BELL_DEFAULT:
2417 case IDC_BELL_WAVEFILE:
2418 case IDC_BELL_VISUAL:
2419 if (HIWORD(wParam) == BN_CLICKED ||
2420 HIWORD(wParam) == BN_DOUBLECLICKED) {
2421 if (LOWORD(wParam) == IDC_BELL_DISABLED)
2422 cfg.beep = BELL_DISABLED;
2423 if (LOWORD(wParam) == IDC_BELL_DEFAULT)
2424 cfg.beep = BELL_DEFAULT;
2425 if (LOWORD(wParam) == IDC_BELL_WAVEFILE)
2426 cfg.beep = BELL_WAVEFILE;
2427 if (LOWORD(wParam) == IDC_BELL_VISUAL)
2428 cfg.beep = BELL_VISUAL;
2431 case IDC_B_IND_DISABLED:
2432 case IDC_B_IND_FLASH:
2433 case IDC_B_IND_STEADY:
2434 if (HIWORD(wParam) == BN_CLICKED ||
2435 HIWORD(wParam) == BN_DOUBLECLICKED) {
2436 if (LOWORD(wParam) == IDC_B_IND_DISABLED)
2437 cfg.beep_ind = B_IND_DISABLED;
2438 if (LOWORD(wParam) == IDC_B_IND_FLASH)
2439 cfg.beep_ind = B_IND_FLASH;
2440 if (LOWORD(wParam) == IDC_B_IND_STEADY)
2441 cfg.beep_ind = B_IND_STEADY;
2444 case IDC_BELL_WAVEBROWSE:
2445 memset(&of, 0, sizeof(of));
2446 #ifdef OPENFILENAME_SIZE_VERSION_400
2447 of.lStructSize = OPENFILENAME_SIZE_VERSION_400;
2449 of.lStructSize = sizeof(of);
2451 of.hwndOwner = hwnd;
2452 of.lpstrFilter = "Wave Files\0*.WAV\0AllFiles\0*\0\0\0";
2453 of.lpstrCustomFilter = NULL;
2454 of.nFilterIndex = 1;
2455 of.lpstrFile = filename;
2456 strcpy(filename, cfg.bell_wavefile);
2457 of.nMaxFile = sizeof(filename);
2458 of.lpstrFileTitle = NULL;
2459 of.lpstrInitialDir = NULL;
2460 of.lpstrTitle = "Select Bell Sound File";
2462 if (GetOpenFileName(&of)) {
2463 strcpy(cfg.bell_wavefile, filename);
2464 SetDlgItemText(hwnd, IDC_BELL_WAVEEDIT,
2468 case IDC_BELL_WAVEEDIT:
2469 if (HIWORD(wParam) == EN_CHANGE)
2470 GetDlgItemText(hwnd, IDC_BELL_WAVEEDIT,
2472 sizeof(cfg.bell_wavefile) - 1);
2475 if (HIWORD(wParam) == BN_CLICKED ||
2476 HIWORD(wParam) == BN_DOUBLECLICKED)
2478 IsDlgButtonChecked(hwnd, IDC_BELLOVL);
2481 if (HIWORD(wParam) == EN_CHANGE)
2482 MyGetDlgItemInt(hwnd, IDC_BELLOVLN, &cfg.bellovl_n);
2485 if (HIWORD(wParam) == EN_CHANGE)
2486 MyGetDlgItemFlt(hwnd, IDC_BELLOVLT, &cfg.bellovl_t,
2490 if (HIWORD(wParam) == EN_CHANGE)
2491 MyGetDlgItemFlt(hwnd, IDC_BELLOVLS, &cfg.bellovl_s,
2495 if (HIWORD(wParam) == BN_CLICKED ||
2496 HIWORD(wParam) == BN_DOUBLECLICKED)
2498 IsDlgButtonChecked(hwnd, IDC_BLINKTEXT);
2501 if (HIWORD(wParam) == BN_CLICKED ||
2502 HIWORD(wParam) == BN_DOUBLECLICKED)
2503 cfg.bce = IsDlgButtonChecked(hwnd, IDC_BCE);
2506 if (HIWORD(wParam) == BN_CLICKED ||
2507 HIWORD(wParam) == BN_DOUBLECLICKED)
2508 cfg.win_name_always =
2509 IsDlgButtonChecked(hwnd, IDC_WINNAME);
2512 if (HIWORD(wParam) == BN_CLICKED ||
2513 HIWORD(wParam) == BN_DOUBLECLICKED)
2515 IsDlgButtonChecked(hwnd, IDC_HIDEMOUSE);
2517 case IDC_SUNKENEDGE:
2518 if (HIWORD(wParam) == BN_CLICKED ||
2519 HIWORD(wParam) == BN_DOUBLECLICKED)
2521 IsDlgButtonChecked(hwnd, IDC_SUNKENEDGE);
2524 if (HIWORD(wParam) == EN_CHANGE)
2525 MyGetDlgItemInt(hwnd, IDC_WINBEDIT,
2526 &cfg.window_border);
2527 if (cfg.window_border > 32)
2528 cfg.window_border = 32;
2531 if (HIWORD(wParam) == BN_CLICKED ||
2532 HIWORD(wParam) == BN_DOUBLECLICKED)
2533 cfg.cursor_type = 0;
2536 if (HIWORD(wParam) == BN_CLICKED ||
2537 HIWORD(wParam) == BN_DOUBLECLICKED)
2538 cfg.cursor_type = 1;
2541 if (HIWORD(wParam) == BN_CLICKED ||
2542 HIWORD(wParam) == BN_DOUBLECLICKED)
2543 cfg.cursor_type = 2;
2546 if (HIWORD(wParam) == BN_CLICKED ||
2547 HIWORD(wParam) == BN_DOUBLECLICKED)
2549 IsDlgButtonChecked(hwnd, IDC_BLINKCUR);
2552 if (HIWORD(wParam) == BN_CLICKED ||
2553 HIWORD(wParam) == BN_DOUBLECLICKED)
2555 IsDlgButtonChecked(hwnd, IDC_SCROLLBAR);
2557 case IDC_SCROLLBARFULLSCREEN:
2558 if (HIWORD(wParam) == BN_CLICKED ||
2559 HIWORD(wParam) == BN_DOUBLECLICKED)
2560 cfg.scrollbar_in_fullscreen =
2561 IsDlgButtonChecked(hwnd, IDC_SCROLLBARFULLSCREEN);
2563 case IDC_RESIZETERM:
2564 case IDC_RESIZEFONT:
2565 case IDC_RESIZENONE:
2566 case IDC_RESIZEEITHER:
2567 if (HIWORD(wParam) == BN_CLICKED ||
2568 HIWORD(wParam) == BN_DOUBLECLICKED) {
2570 IsDlgButtonChecked(hwnd,
2571 IDC_RESIZETERM) ? RESIZE_TERM :
2572 IsDlgButtonChecked(hwnd,
2573 IDC_RESIZEFONT) ? RESIZE_FONT :
2574 IsDlgButtonChecked(hwnd,
2575 IDC_RESIZEEITHER) ? RESIZE_EITHER :
2580 if (HIWORD(wParam) == EN_CHANGE)
2581 GetDlgItemText(hwnd, IDC_WINEDIT, cfg.wintitle,
2582 sizeof(cfg.wintitle) - 1);
2587 if (HIWORD(wParam) == BN_CLICKED ||
2588 HIWORD(wParam) == BN_DOUBLECLICKED) {
2590 IsDlgButtonChecked(hwnd,
2591 IDC_COEALWAYS) ? COE_ALWAYS :
2592 IsDlgButtonChecked(hwnd,
2593 IDC_COENEVER) ? COE_NEVER :
2598 if (HIWORD(wParam) == BN_CLICKED ||
2599 HIWORD(wParam) == BN_DOUBLECLICKED)
2601 IsDlgButtonChecked(hwnd, IDC_CLOSEWARN);
2604 if (HIWORD(wParam) == EN_CHANGE)
2605 GetDlgItemText(hwnd, IDC_TTEDIT, cfg.termtype,
2606 sizeof(cfg.termtype) - 1);
2609 if (HIWORD(wParam) == EN_CHANGE)
2610 GetDlgItemText(hwnd, IDC_LGFEDIT, cfg.logfilename,
2611 sizeof(cfg.logfilename) - 1);
2614 memset(&of, 0, sizeof(of));
2615 #ifdef OPENFILENAME_SIZE_VERSION_400
2616 of.lStructSize = OPENFILENAME_SIZE_VERSION_400;
2618 of.lStructSize = sizeof(of);
2620 of.hwndOwner = hwnd;
2621 of.lpstrFilter = "All Files\0*\0\0\0";
2622 of.lpstrCustomFilter = NULL;
2623 of.nFilterIndex = 1;
2624 of.lpstrFile = filename;
2625 strcpy(filename, cfg.logfilename);
2626 of.nMaxFile = sizeof(filename);
2627 of.lpstrFileTitle = NULL;
2628 of.lpstrInitialDir = NULL;
2629 of.lpstrTitle = "Select session log file";
2631 if (GetSaveFileName(&of)) {
2632 strcpy(cfg.logfilename, filename);
2633 SetDlgItemText(hwnd, IDC_LGFEDIT, cfg.logfilename);
2637 case IDC_LSTATASCII:
2639 case IDC_LSTATPACKET:
2640 if (HIWORD(wParam) == BN_CLICKED ||
2641 HIWORD(wParam) == BN_DOUBLECLICKED) {
2642 if (IsDlgButtonChecked(hwnd, IDC_LSTATOFF))
2643 cfg.logtype = LGTYP_NONE;
2644 if (IsDlgButtonChecked(hwnd, IDC_LSTATASCII))
2645 cfg.logtype = LGTYP_ASCII;
2646 if (IsDlgButtonChecked(hwnd, IDC_LSTATRAW))
2647 cfg.logtype = LGTYP_DEBUG;
2648 if (IsDlgButtonChecked(hwnd, IDC_LSTATPACKET))
2649 cfg.logtype = LGTYP_PACKETS;
2655 if (HIWORD(wParam) == BN_CLICKED ||
2656 HIWORD(wParam) == BN_DOUBLECLICKED) {
2657 if (IsDlgButtonChecked(hwnd, IDC_LSTATXASK))
2658 cfg.logxfovr = LGXF_ASK;
2659 if (IsDlgButtonChecked(hwnd, IDC_LSTATXAPN))
2660 cfg.logxfovr = LGXF_APN;
2661 if (IsDlgButtonChecked(hwnd, IDC_LSTATXOVR))
2662 cfg.logxfovr = LGXF_OVR;
2667 if (HIWORD(wParam) == EN_CHANGE)
2668 GetDlgItemText(hwnd, LOWORD(wParam), cfg.termspeed,
2669 sizeof(cfg.termspeed) - 1);
2672 if (HIWORD(wParam) == EN_CHANGE)
2673 GetDlgItemText(hwnd, IDC_LOGEDIT, cfg.username,
2674 sizeof(cfg.username) - 1);
2676 case IDC_RLLUSEREDIT:
2677 if (HIWORD(wParam) == EN_CHANGE)
2678 GetDlgItemText(hwnd, IDC_RLLUSEREDIT,
2680 sizeof(cfg.localusername) - 1);
2684 cfg.rfc_environ = IsDlgButtonChecked(hwnd, IDC_EMRFC);
2688 cfg.passive_telnet =
2689 IsDlgButtonChecked(hwnd, IDC_TPASSIVE);
2692 if (HIWORD(wParam) == BN_CLICKED ||
2693 HIWORD(wParam) == BN_DOUBLECLICKED) {
2694 char str[sizeof(cfg.environmt)];
2696 GetDlgItemText(hwnd, IDC_VAREDIT, str,
2702 p = str + strlen(str);
2704 GetDlgItemText(hwnd, IDC_VALEDIT, p,
2705 sizeof(str) - 1 - (p - str));
2716 if ((p - cfg.environmt) + strlen(str) + 2 <
2717 sizeof(cfg.environmt)) {
2719 p[strlen(str) + 1] = '\0';
2720 SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_ADDSTRING,
2722 SetDlgItemText(hwnd, IDC_VAREDIT, "");
2723 SetDlgItemText(hwnd, IDC_VALEDIT, "");
2725 MessageBox(hwnd, "Environment too big",
2726 "PuTTY Error", MB_OK | MB_ICONERROR);
2731 if (HIWORD(wParam) != BN_CLICKED &&
2732 HIWORD(wParam) != BN_DOUBLECLICKED) break;
2734 SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_GETCURSEL, 0,
2741 SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_DELETESTRING,
2768 if (HIWORD(wParam) == BN_CLICKED ||
2769 HIWORD(wParam) == BN_DOUBLECLICKED)
2770 cfg.nopty = IsDlgButtonChecked(hwnd, IDC_NOPTY);
2773 if (HIWORD(wParam) == BN_CLICKED ||
2774 HIWORD(wParam) == BN_DOUBLECLICKED)
2776 IsDlgButtonChecked(hwnd, IDC_COMPRESS);
2779 if (HIWORD(wParam) == BN_CLICKED ||
2780 HIWORD(wParam) == BN_DOUBLECLICKED)
2782 IsDlgButtonChecked(hwnd, IDC_BUGGYMAC);
2785 if (HIWORD(wParam) == BN_CLICKED ||
2786 HIWORD(wParam) == BN_DOUBLECLICKED)
2788 IsDlgButtonChecked(hwnd, IDC_SSH2DES);
2791 if (HIWORD(wParam) == BN_CLICKED ||
2792 HIWORD(wParam) == BN_DOUBLECLICKED)
2794 IsDlgButtonChecked(hwnd, IDC_AGENTFWD);
2796 case IDC_CHANGEUSER:
2797 if (HIWORD(wParam) == BN_CLICKED ||
2798 HIWORD(wParam) == BN_DOUBLECLICKED)
2799 cfg.change_username =
2800 IsDlgButtonChecked(hwnd, IDC_CHANGEUSER);
2802 case IDC_CIPHERLIST:
2805 handle_prefslist(&cipherlist,
2806 cfg.ssh_cipherlist, CIPHER_MAX,
2807 0, hwnd, wParam, lParam);
2811 if (HIWORD(wParam) == BN_CLICKED ||
2812 HIWORD(wParam) == BN_DOUBLECLICKED) {
2813 if (IsDlgButtonChecked(hwnd, IDC_SSHPROT1))
2815 else if (IsDlgButtonChecked(hwnd, IDC_SSHPROT2))
2820 if (HIWORD(wParam) == BN_CLICKED ||
2821 HIWORD(wParam) == BN_DOUBLECLICKED)
2823 IsDlgButtonChecked(hwnd, IDC_AUTHTIS);
2826 if (HIWORD(wParam) == BN_CLICKED ||
2827 HIWORD(wParam) == BN_DOUBLECLICKED)
2829 IsDlgButtonChecked(hwnd, IDC_AUTHKI);
2832 if (HIWORD(wParam) == EN_CHANGE)
2833 GetDlgItemText(hwnd, IDC_PKEDIT, cfg.keyfile,
2834 sizeof(cfg.keyfile) - 1);
2837 if (HIWORD(wParam) == EN_CHANGE)
2838 GetDlgItemText(hwnd, IDC_CMDEDIT, cfg.remote_cmd,
2839 sizeof(cfg.remote_cmd) - 1);
2842 memset(&of, 0, sizeof(of));
2843 #ifdef OPENFILENAME_SIZE_VERSION_400
2844 of.lStructSize = OPENFILENAME_SIZE_VERSION_400;
2846 of.lStructSize = sizeof(of);
2848 of.hwndOwner = hwnd;
2849 of.lpstrFilter = "All Files\0*\0\0\0";
2850 of.lpstrCustomFilter = NULL;
2851 of.nFilterIndex = 1;
2852 of.lpstrFile = filename;
2853 strcpy(filename, cfg.keyfile);
2854 of.nMaxFile = sizeof(filename);
2855 of.lpstrFileTitle = NULL;
2856 of.lpstrInitialDir = NULL;
2857 of.lpstrTitle = "Select Private Key File";
2859 if (GetOpenFileName(&of)) {
2860 strcpy(cfg.keyfile, filename);
2861 SetDlgItemText(hwnd, IDC_PKEDIT, cfg.keyfile);
2865 cfg.rawcnp = IsDlgButtonChecked(hwnd, IDC_RAWCNP);
2868 cfg.rtf_paste = IsDlgButtonChecked(hwnd, IDC_RTFPASTE);
2872 cfg.mouse_is_xterm = IsDlgButtonChecked(hwnd, IDC_MBXTERM);
2874 case IDC_SELTYPELEX:
2875 case IDC_SELTYPERECT:
2876 cfg.rect_select = IsDlgButtonChecked(hwnd, IDC_SELTYPERECT);
2878 case IDC_MOUSEOVERRIDE:
2879 cfg.mouse_override = IsDlgButtonChecked(hwnd, IDC_MOUSEOVERRIDE);
2885 int n = GetDlgItemInt(hwnd, IDC_CCEDIT, &ok, FALSE);
2890 for (i = 0; i < 128; i++)
2891 if (SendDlgItemMessage
2892 (hwnd, IDC_CCLIST, LB_GETSEL, i, 0)) {
2894 cfg.wordness[i] = n;
2895 SendDlgItemMessage(hwnd, IDC_CCLIST,
2896 LB_DELETESTRING, i, 0);
2897 sprintf(str, "%d\t(0x%02X)\t%c\t%d", i, i,
2898 (i >= 0x21 && i != 0x7F) ? i : ' ',
2900 SendDlgItemMessage(hwnd, IDC_CCLIST,
2907 case IDC_BOLDCOLOUR:
2908 if (HIWORD(wParam) == BN_CLICKED ||
2909 HIWORD(wParam) == BN_DOUBLECLICKED) {
2912 IsDlgButtonChecked(hwnd, IDC_BOLDCOLOUR);
2913 SendDlgItemMessage(hwnd, IDC_COLOURLIST, WM_SETREDRAW,
2916 SendDlgItemMessage(hwnd, IDC_COLOURLIST,
2918 if (n != 12 + 10 * cfg.bold_colour) {
2919 for (i = n; i-- > 0;)
2920 SendDlgItemMessage(hwnd, IDC_COLOURLIST,
2921 LB_DELETESTRING, i, 0);
2922 for (i = 0; i < 22; i++)
2923 if (cfg.bold_colour || permcolour[i])
2924 SendDlgItemMessage(hwnd, IDC_COLOURLIST,
2926 (LPARAM) colours[i]);
2928 SendDlgItemMessage(hwnd, IDC_COLOURLIST, WM_SETREDRAW,
2930 InvalidateRect(GetDlgItem(hwnd, IDC_COLOURLIST), NULL,
2935 if (HIWORD(wParam) == BN_CLICKED ||
2936 HIWORD(wParam) == BN_DOUBLECLICKED)
2938 IsDlgButtonChecked(hwnd, IDC_PALETTE);
2940 case IDC_COLOURLIST:
2941 if (HIWORD(wParam) == LBN_DBLCLK ||
2942 HIWORD(wParam) == LBN_SELCHANGE) {
2944 SendDlgItemMessage(hwnd, IDC_COLOURLIST,
2947 if (!cfg.bold_colour)
2948 i = (i < 3 ? i * 2 : i == 3 ? 5 : i * 2 - 2);
2949 SetDlgItemInt(hwnd, IDC_RVALUE, cfg.colours[i][0],
2951 SetDlgItemInt(hwnd, IDC_GVALUE, cfg.colours[i][1],
2953 SetDlgItemInt(hwnd, IDC_BVALUE, cfg.colours[i][2],
2958 if (HIWORD(wParam) == BN_CLICKED ||
2959 HIWORD(wParam) == BN_DOUBLECLICKED) {
2960 static CHOOSECOLOR cc;
2961 static DWORD custom[16] = { 0 }; /* zero initialisers */
2963 SendDlgItemMessage(hwnd, IDC_COLOURLIST,
2966 if (!cfg.bold_colour)
2967 i = (i < 3 ? i * 2 : i == 3 ? 5 : i * 2 - 2);
2968 cc.lStructSize = sizeof(cc);
2969 cc.hwndOwner = hwnd;
2970 cc.hInstance = (HWND) hinst;
2971 cc.lpCustColors = custom;
2973 RGB(cfg.colours[i][0], cfg.colours[i][1],
2975 cc.Flags = CC_FULLOPEN | CC_RGBINIT;
2976 if (ChooseColor(&cc)) {
2978 (unsigned char) (cc.rgbResult & 0xFF);
2980 (unsigned char) (cc.rgbResult >> 8) & 0xFF;
2982 (unsigned char) (cc.rgbResult >> 16) & 0xFF;
2983 SetDlgItemInt(hwnd, IDC_RVALUE, cfg.colours[i][0],
2985 SetDlgItemInt(hwnd, IDC_GVALUE, cfg.colours[i][1],
2987 SetDlgItemInt(hwnd, IDC_BVALUE, cfg.colours[i][2],
2993 if (HIWORD(wParam) == CBN_SELCHANGE) {
2994 int index = SendDlgItemMessage(hwnd, IDC_CODEPAGE,
2995 CB_GETCURSEL, 0, 0);
2996 SendDlgItemMessage(hwnd, IDC_CODEPAGE, CB_GETLBTEXT,
2997 index, (LPARAM)cfg.line_codepage);
2998 } else if (HIWORD(wParam) == CBN_EDITCHANGE) {
2999 GetDlgItemText(hwnd, IDC_CODEPAGE, cfg.line_codepage,
3000 sizeof(cfg.line_codepage) - 1);
3001 } else if (HIWORD(wParam) == CBN_KILLFOCUS) {
3002 strcpy(cfg.line_codepage,
3003 cp_name(decode_codepage(cfg.line_codepage)));
3004 SetDlgItemText(hwnd, IDC_CODEPAGE, cfg.line_codepage);
3007 case IDC_CAPSLOCKCYR:
3008 if (HIWORD(wParam) == BN_CLICKED ||
3009 HIWORD(wParam) == BN_DOUBLECLICKED) {
3010 cfg.xlat_capslockcyr =
3011 IsDlgButtonChecked (hwnd, IDC_CAPSLOCKCYR);
3014 case IDC_VTXWINDOWS:
3020 (IsDlgButtonChecked(hwnd, IDC_VTXWINDOWS) ? VT_XWINDOWS
3021 : IsDlgButtonChecked(hwnd,
3022 IDC_VTOEMANSI) ? VT_OEMANSI :
3023 IsDlgButtonChecked(hwnd,
3024 IDC_VTOEMONLY) ? VT_OEMONLY :
3025 IsDlgButtonChecked(hwnd,
3026 IDC_VTUNICODE) ? VT_UNICODE :
3029 case IDC_X11_FORWARD:
3030 if (HIWORD(wParam) == BN_CLICKED ||
3031 HIWORD(wParam) == BN_DOUBLECLICKED)
3033 IsDlgButtonChecked(hwnd, IDC_X11_FORWARD);
3036 if (HIWORD(wParam) == BN_CLICKED ||
3037 HIWORD(wParam) == BN_DOUBLECLICKED)
3038 cfg.lport_acceptall =
3039 IsDlgButtonChecked(hwnd, IDC_LPORT_ALL);
3042 if (HIWORD(wParam) == BN_CLICKED ||
3043 HIWORD(wParam) == BN_DOUBLECLICKED)
3044 cfg.rport_acceptall =
3045 IsDlgButtonChecked(hwnd, IDC_RPORT_ALL);
3047 case IDC_X11_DISPLAY:
3048 if (HIWORD(wParam) == EN_CHANGE)
3049 GetDlgItemText(hwnd, IDC_X11_DISPLAY, cfg.x11_display,
3050 sizeof(cfg.x11_display) - 1);
3053 if (HIWORD(wParam) == BN_CLICKED ||
3054 HIWORD(wParam) == BN_DOUBLECLICKED) {
3055 char str[sizeof(cfg.portfwd)];
3057 if (IsDlgButtonChecked(hwnd, IDC_PFWDLOCAL))
3061 GetDlgItemText(hwnd, IDC_SPORTEDIT, str+1,
3065 "You need to specify a source port number",
3066 "PuTTY Error", MB_OK | MB_ICONERROR);
3069 p = str + strlen(str);
3071 GetDlgItemText(hwnd, IDC_DPORTEDIT, p,
3072 sizeof(str) - 1 - (p - str));
3073 if (!*p || !strchr(p, ':')) {
3075 "You need to specify a destination address\n"
3076 "in the form \"host.name:port\"",
3077 "PuTTY Error", MB_OK | MB_ICONERROR);
3086 if ((p - cfg.portfwd) + strlen(str) + 2 <
3087 sizeof(cfg.portfwd)) {
3089 p[strlen(str) + 1] = '\0';
3090 SendDlgItemMessage(hwnd, IDC_PFWDLIST, LB_ADDSTRING,
3092 SetDlgItemText(hwnd, IDC_SPORTEDIT, "");
3093 SetDlgItemText(hwnd, IDC_DPORTEDIT, "");
3095 MessageBox(hwnd, "Too many forwardings",
3096 "PuTTY Error", MB_OK | MB_ICONERROR);
3100 case IDC_PFWDREMOVE:
3101 if (HIWORD(wParam) != BN_CLICKED &&
3102 HIWORD(wParam) != BN_DOUBLECLICKED) break;
3103 i = SendDlgItemMessage(hwnd, IDC_PFWDLIST,
3104 LB_GETCURSEL, 0, 0);
3110 SendDlgItemMessage(hwnd, IDC_PFWDLIST, LB_DELETESTRING,
3140 int id = ((LPHELPINFO)lParam)->iCtrlId;
3141 char *cmd = help_context_cmd(id);
3143 WinHelp(hwnd, help_path, HELP_COMMAND, (DWORD)cmd);
3144 requested_help = TRUE;
3151 if (requested_help) {
3152 WinHelp(hwnd, help_path, HELP_QUIT, 0);
3153 requested_help = FALSE;
3158 /* Grrr Explorer will maximize Dialogs! */
3160 if (wParam == SIZE_MAXIMIZED)
3166 * Handle application-defined messages eg. DragListBox
3168 /* First find out what the number is (once). */
3169 if (draglistmsg == WM_NULL)
3170 draglistmsg = RegisterWindowMessage (DRAGLISTMSGSTRING);
3172 if (msg == draglistmsg) {
3173 /* Only process once dialog is fully formed. */
3174 if (GetWindowLong(hwnd, GWL_USERDATA) == 1) switch (LOWORD(wParam)) {
3175 case IDC_CIPHERLIST:
3176 return handle_prefslist(&cipherlist,
3177 cfg.ssh_cipherlist, CIPHER_MAX,
3178 1, hwnd, wParam, lParam);
3187 static int CALLBACK MainDlgProc(HWND hwnd, UINT msg,
3188 WPARAM wParam, LPARAM lParam)
3190 if (msg == WM_COMMAND && LOWORD(wParam) == IDOK) {
3192 if (msg == WM_COMMAND && LOWORD(wParam) == IDCX_ABOUT) {
3193 EnableWindow(hwnd, 0);
3194 DialogBox(hinst, MAKEINTRESOURCE(IDD_ABOUTBOX), hwnd, AboutProc);
3195 EnableWindow(hwnd, 1);
3196 SetActiveWindow(hwnd);
3198 return GenericMainDlgProc(hwnd, msg, wParam, lParam, 0);
3201 static int CALLBACK ReconfDlgProc(HWND hwnd, UINT msg,
3202 WPARAM wParam, LPARAM lParam)
3204 return GenericMainDlgProc(hwnd, msg, wParam, lParam, 1);
3207 void defuse_showwindow(void)
3210 * Work around the fact that the app's first call to ShowWindow
3211 * will ignore the default in favour of the shell-provided
3216 hwnd = CreateDialog(hinst, MAKEINTRESOURCE(IDD_ABOUTBOX),
3218 ShowWindow(hwnd, SW_HIDE);
3219 SetActiveWindow(hwnd);
3220 DestroyWindow(hwnd);
3229 savedsession[0] = '\0';
3231 DialogBox(hinst, MAKEINTRESOURCE(IDD_MAINBOX), NULL, MainDlgProc);
3232 get_sesslist(FALSE);
3237 int do_reconfig(HWND hwnd)
3242 backup_cfg = cfg; /* structure copy */
3244 DialogBox(hinst, MAKEINTRESOURCE(IDD_RECONF), hwnd, ReconfDlgProc);
3246 cfg = backup_cfg; /* structure copy */
3251 void logevent(char *string)
3256 if (nevents >= negsize) {
3258 events = srealloc(events, negsize * sizeof(*events));
3262 strftime(timebuf, sizeof(timebuf), "%Y-%m-%d %H:%M:%S\t",
3265 events[nevents] = smalloc(strlen(timebuf) + strlen(string) + 1);
3266 strcpy(events[nevents], timebuf);
3267 strcat(events[nevents], string);
3270 SendDlgItemMessage(logbox, IDN_LIST, LB_ADDSTRING,
3271 0, (LPARAM) events[nevents]);
3272 count = SendDlgItemMessage(logbox, IDN_LIST, LB_GETCOUNT, 0, 0);
3273 SendDlgItemMessage(logbox, IDN_LIST, LB_SETTOPINDEX, count - 1, 0);
3278 void showeventlog(HWND hwnd)
3281 logbox = CreateDialog(hinst, MAKEINTRESOURCE(IDD_LOGBOX),
3283 ShowWindow(logbox, SW_SHOWNORMAL);
3285 SetActiveWindow(logbox);
3288 void showabout(HWND hwnd)
3290 DialogBox(hinst, MAKEINTRESOURCE(IDD_ABOUTBOX), hwnd, AboutProc);
3293 void verify_ssh_host_key(char *host, int port, char *keytype,
3294 char *keystr, char *fingerprint)
3298 static const char absentmsg[] =
3299 "The server's host key is not cached in the registry. You\n"
3300 "have no guarantee that the server is the computer you\n"
3302 "The server's key fingerprint is:\n"
3304 "If you trust this host, hit Yes to add the key to\n"
3305 "PuTTY's cache and carry on connecting.\n"
3306 "If you want to carry on connecting just once, without\n"
3307 "adding the key to the cache, hit No.\n"
3308 "If you do not trust this host, hit Cancel to abandon the\n"
3311 static const char wrongmsg[] =
3312 "WARNING - POTENTIAL SECURITY BREACH!\n"
3314 "The server's host key does not match the one PuTTY has\n"
3315 "cached in the registry. This means that either the\n"
3316 "server administrator has changed the host key, or you\n"
3317 "have actually connected to another computer pretending\n"
3318 "to be the server.\n"
3319 "The new key fingerprint is:\n"
3321 "If you were expecting this change and trust the new key,\n"
3322 "hit Yes to update PuTTY's cache and continue connecting.\n"
3323 "If you want to carry on connecting but without updating\n"
3324 "the cache, hit No.\n"
3325 "If you want to abandon the connection completely, hit\n"
3326 "Cancel. Hitting Cancel is the ONLY guaranteed safe\n" "choice.\n";
3328 static const char mbtitle[] = "PuTTY Security Alert";
3331 /* sensible fingerprint max size */
3332 (sizeof(absentmsg) > sizeof(wrongmsg) ?
3333 sizeof(absentmsg) : sizeof(wrongmsg))];
3336 * Verify the key against the registry.
3338 ret = verify_host_key(host, port, keytype, keystr);
3340 if (ret == 0) /* success - key matched OK */
3342 if (ret == 2) { /* key was different */
3344 sprintf(message, wrongmsg, fingerprint);
3345 mbret = MessageBox(NULL, message, mbtitle,
3346 MB_ICONWARNING | MB_YESNOCANCEL);
3348 store_host_key(host, port, keytype, keystr);
3349 if (mbret == IDCANCEL)
3352 if (ret == 1) { /* key was absent */
3354 sprintf(message, absentmsg, fingerprint);
3355 mbret = MessageBox(NULL, message, mbtitle,
3356 MB_ICONWARNING | MB_YESNOCANCEL);
3358 store_host_key(host, port, keytype, keystr);
3359 if (mbret == IDCANCEL)
3365 * Ask whether the selected cipher is acceptable (since it was
3366 * below the configured 'warn' threshold).
3367 * cs: 0 = both ways, 1 = client->server, 2 = server->client
3369 void askcipher(char *ciphername, int cs)
3371 static const char mbtitle[] = "PuTTY Security Alert";
3372 static const char msg[] =
3373 "The first %.35scipher supported by the server\n"
3374 "is %.64s, which is below the configured\n"
3375 "warning threshold.\n"
3376 "Do you want to continue with this connection?\n";
3377 /* guessed cipher name + type max length */
3378 char message[100 + sizeof(msg)];
3381 sprintf(message, msg,
3383 (cs == 1) ? "client-to-server " :
3384 "server-to-client ",
3386 mbret = MessageBox(NULL, message, mbtitle,
3387 MB_ICONWARNING | MB_YESNO);
3395 * Ask whether to wipe a session log file before writing to it.
3396 * Returns 2 for wipe, 1 for append, 0 for cancel (don't log).
3398 int askappend(char *filename)
3400 static const char mbtitle[] = "PuTTY Log to File";
3401 static const char msgtemplate[] =
3402 "The session log file \"%.*s\" already exists.\n"
3403 "You can overwrite it with a new session log,\n"
3404 "append your session log to the end of it,\n"
3405 "or disable session logging for this session.\n"
3406 "Hit Yes to wipe the file, No to append to it,\n"
3407 "or Cancel to disable logging.";
3408 char message[sizeof(msgtemplate) + FILENAME_MAX];
3410 if (cfg.logxfovr != LGXF_ASK) {
3411 return ((cfg.logxfovr == LGXF_OVR) ? 2 : 1);
3413 sprintf(message, msgtemplate, FILENAME_MAX, filename);
3415 mbret = MessageBox(NULL, message, mbtitle,
3416 MB_ICONQUESTION | MB_YESNOCANCEL);
3419 else if (mbret == IDNO)
3426 * Warn about the obsolescent key file format.
3428 void old_keyfile_warning(void)
3430 static const char mbtitle[] = "PuTTY Key File Warning";
3431 static const char message[] =
3432 "You are loading an SSH 2 private key which has an\n"
3433 "old version of the file format. This means your key\n"
3434 "file is not fully tamperproof. Future versions of\n"
3435 "PuTTY may stop supporting this private key format,\n"
3436 "so we recommend you convert your key to the new\n"
3439 "You can perform this conversion by loading the key\n"
3440 "into PuTTYgen and then saving it again.";
3442 MessageBox(NULL, message, mbtitle, MB_OK);