]> asedeno.scripts.mit.edu Git - PuTTY.git/blob - windlg.c
Support for doing DNS at the proxy end. I've invented a new type of
[PuTTY.git] / windlg.c
1 #include <windows.h>
2 #include <commctrl.h>
3 #include <commdlg.h>
4 #include <stdio.h>
5 #include <stdlib.h>
6 #include <ctype.h>
7 #include <time.h>
8
9 #include "ssh.h"
10 #include "putty.h"
11 #include "winstuff.h"
12 #include "win_res.h"
13 #include "storage.h"
14
15 #ifdef MSVC4
16 #define TVINSERTSTRUCT  TV_INSERTSTRUCT
17 #define TVITEM          TV_ITEM
18 #define ICON_BIG        1
19 #endif
20
21 static char **events = NULL;
22 static int nevents = 0, negsize = 0;
23
24 static int readytogo;
25 static int sesslist_has_focus;
26 static int requested_help;
27
28 static struct prefslist cipherlist;
29
30 struct sesslist sesslist;              /* exported to window.c */
31
32 #define PRINTER_DISABLED_STRING "None (printing disabled)"
33
34 void force_normal(HWND hwnd)
35 {
36     static int recurse = 0;
37
38     WINDOWPLACEMENT wp;
39
40     if (recurse)
41         return;
42     recurse = 1;
43
44     wp.length = sizeof(wp);
45     if (GetWindowPlacement(hwnd, &wp) && wp.showCmd == SW_SHOWMAXIMIZED) {
46         wp.showCmd = SW_SHOWNORMAL;
47         SetWindowPlacement(hwnd, &wp);
48     }
49     recurse = 0;
50 }
51
52 static void MyGetDlgItemInt(HWND hwnd, int id, int *result)
53 {
54     BOOL ok;
55     int n;
56     n = GetDlgItemInt(hwnd, id, &ok, FALSE);
57     if (ok)
58         *result = n;
59 }
60
61 static void MyGetDlgItemFlt(HWND hwnd, int id, int *result, int scale)
62 {
63     char text[80];
64     BOOL ok;
65     ok = GetDlgItemText(hwnd, id, text, sizeof(text) - 1);
66     if (ok && text[0])
67         *result = (int) (scale * atof(text));
68 }
69
70 static void MySetDlgItemFlt(HWND hwnd, int id, double value)
71 {
72     char text[80];
73     sprintf(text, "%g", value);
74     SetDlgItemText(hwnd, id, text);
75 }
76
77 static int CALLBACK LogProc(HWND hwnd, UINT msg,
78                             WPARAM wParam, LPARAM lParam)
79 {
80     int i;
81
82     switch (msg) {
83       case WM_INITDIALOG:
84         {
85             static int tabs[4] = { 78, 108 };
86             SendDlgItemMessage(hwnd, IDN_LIST, LB_SETTABSTOPS, 2,
87                                (LPARAM) tabs);
88         }
89         for (i = 0; i < nevents; i++)
90             SendDlgItemMessage(hwnd, IDN_LIST, LB_ADDSTRING,
91                                0, (LPARAM) events[i]);
92         return 1;
93       case WM_COMMAND:
94         switch (LOWORD(wParam)) {
95           case IDOK:
96           case IDCANCEL:
97             logbox = NULL;
98             SetActiveWindow(GetParent(hwnd));
99             DestroyWindow(hwnd);
100             return 0;
101           case IDN_COPY:
102             if (HIWORD(wParam) == BN_CLICKED ||
103                 HIWORD(wParam) == BN_DOUBLECLICKED) {
104                 int selcount;
105                 int *selitems;
106                 selcount = SendDlgItemMessage(hwnd, IDN_LIST,
107                                               LB_GETSELCOUNT, 0, 0);
108                 if (selcount == 0) {   /* don't even try to copy zero items */
109                     MessageBeep(0);
110                     break;
111                 }
112
113                 selitems = smalloc(selcount * sizeof(int));
114                 if (selitems) {
115                     int count = SendDlgItemMessage(hwnd, IDN_LIST,
116                                                    LB_GETSELITEMS,
117                                                    selcount,
118                                                    (LPARAM) selitems);
119                     int i;
120                     int size;
121                     char *clipdata;
122                     static unsigned char sel_nl[] = SEL_NL;
123
124                     if (count == 0) {  /* can't copy zero stuff */
125                         MessageBeep(0);
126                         break;
127                     }
128
129                     size = 0;
130                     for (i = 0; i < count; i++)
131                         size +=
132                             strlen(events[selitems[i]]) + sizeof(sel_nl);
133
134                     clipdata = smalloc(size);
135                     if (clipdata) {
136                         char *p = clipdata;
137                         for (i = 0; i < count; i++) {
138                             char *q = events[selitems[i]];
139                             int qlen = strlen(q);
140                             memcpy(p, q, qlen);
141                             p += qlen;
142                             memcpy(p, sel_nl, sizeof(sel_nl));
143                             p += sizeof(sel_nl);
144                         }
145                         write_aclip(NULL, clipdata, size, TRUE);
146                         sfree(clipdata);
147                     }
148                     sfree(selitems);
149
150                     for (i = 0; i < nevents; i++)
151                         SendDlgItemMessage(hwnd, IDN_LIST, LB_SETSEL,
152                                            FALSE, i);
153                 }
154             }
155             return 0;
156         }
157         return 0;
158       case WM_CLOSE:
159         logbox = NULL;
160         SetActiveWindow(GetParent(hwnd));
161         DestroyWindow(hwnd);
162         return 0;
163     }
164     return 0;
165 }
166
167 static int CALLBACK LicenceProc(HWND hwnd, UINT msg,
168                                 WPARAM wParam, LPARAM lParam)
169 {
170     switch (msg) {
171       case WM_INITDIALOG:
172         return 1;
173       case WM_COMMAND:
174         switch (LOWORD(wParam)) {
175           case IDOK:
176             EndDialog(hwnd, 1);
177             return 0;
178         }
179         return 0;
180       case WM_CLOSE:
181         EndDialog(hwnd, 1);
182         return 0;
183     }
184     return 0;
185 }
186
187 static int CALLBACK AboutProc(HWND hwnd, UINT msg,
188                               WPARAM wParam, LPARAM lParam)
189 {
190     switch (msg) {
191       case WM_INITDIALOG:
192         SetDlgItemText(hwnd, IDA_VERSION, ver);
193         return 1;
194       case WM_COMMAND:
195         switch (LOWORD(wParam)) {
196           case IDOK:
197           case IDCANCEL:
198             EndDialog(hwnd, TRUE);
199             return 0;
200           case IDA_LICENCE:
201             EnableWindow(hwnd, 0);
202             DialogBox(hinst, MAKEINTRESOURCE(IDD_LICENCEBOX),
203                       NULL, LicenceProc);
204             EnableWindow(hwnd, 1);
205             SetActiveWindow(hwnd);
206             return 0;
207
208           case IDA_WEB:
209             /* Load web browser */
210             ShellExecute(hwnd, "open",
211                          "http://www.chiark.greenend.org.uk/~sgtatham/putty/",
212                          0, 0, SW_SHOWDEFAULT);
213             return 0;
214         }
215         return 0;
216       case WM_CLOSE:
217         EndDialog(hwnd, TRUE);
218         return 0;
219     }
220     return 0;
221 }
222
223 /*
224  * Null dialog procedure.
225  */
226 static int CALLBACK NullDlgProc(HWND hwnd, UINT msg,
227                                 WPARAM wParam, LPARAM lParam)
228 {
229     return 0;
230 }
231
232 static char savedsession[2048];
233
234 enum { IDCX_ABOUT =
235         IDC_ABOUT, IDCX_TVSTATIC, IDCX_TREEVIEW, controlstartvalue,
236
237     sessionpanelstart,
238     IDC_TITLE_SESSION,
239     IDC_BOX_SESSION1,
240     IDC_BOX_SESSION2,
241     IDC_BOX_SESSION3,
242     IDC_HOSTSTATIC,
243     IDC_HOST,
244     IDC_PORTSTATIC,
245     IDC_PORT,
246     IDC_PROTSTATIC,
247     IDC_PROTRAW,
248     IDC_PROTTELNET,
249     IDC_PROTRLOGIN,
250     IDC_PROTSSH,
251     IDC_SESSSTATIC,
252     IDC_SESSEDIT,
253     IDC_SESSLIST,
254     IDC_SESSLOAD,
255     IDC_SESSSAVE,
256     IDC_SESSDEL,
257     IDC_CLOSEEXIT,
258     IDC_COEALWAYS,
259     IDC_COENEVER,
260     IDC_COENORMAL,
261     sessionpanelend,
262
263     loggingpanelstart,
264     IDC_TITLE_LOGGING,
265     IDC_BOX_LOGGING1,
266     IDC_LSTATSTATIC,
267     IDC_LSTATOFF,
268     IDC_LSTATASCII,
269     IDC_LSTATRAW,
270     IDC_LSTATPACKET,
271     IDC_LGFSTATIC,
272     IDC_LGFEDIT,
273     IDC_LGFBUTTON,
274     IDC_LGFEXPLAIN,
275     IDC_LSTATXIST,
276     IDC_LSTATXOVR,
277     IDC_LSTATXAPN,
278     IDC_LSTATXASK,
279     loggingpanelend,
280
281     keyboardpanelstart,
282     IDC_TITLE_KEYBOARD,
283     IDC_BOX_KEYBOARD1,
284     IDC_BOX_KEYBOARD2,
285     IDC_BOX_KEYBOARD3,
286     IDC_DELSTATIC,
287     IDC_DEL008,
288     IDC_DEL127,
289     IDC_HOMESTATIC,
290     IDC_HOMETILDE,
291     IDC_HOMERXVT,
292     IDC_FUNCSTATIC,
293     IDC_FUNCTILDE,
294     IDC_FUNCLINUX,
295     IDC_FUNCXTERM,
296     IDC_FUNCVT400,
297     IDC_FUNCVT100P,
298     IDC_FUNCSCO,
299     IDC_KPSTATIC,
300     IDC_KPNORMAL,
301     IDC_KPAPPLIC,
302     IDC_KPNH,
303     IDC_CURSTATIC,
304     IDC_CURNORMAL,
305     IDC_CURAPPLIC,
306     IDC_COMPOSEKEY,
307     IDC_CTRLALTKEYS,
308     keyboardpanelend,
309
310     terminalpanelstart,
311     IDC_TITLE_TERMINAL,
312     IDC_BOX_TERMINAL1,
313     IDC_BOX_TERMINAL2,
314     IDC_BOX_TERMINAL3,
315     IDC_WRAPMODE,
316     IDC_DECOM,
317     IDC_LFHASCR,
318     IDC_BCE,
319     IDC_BLINKTEXT,
320     IDC_ANSWERBACK,
321     IDC_ANSWEREDIT,
322     IDC_ECHOSTATIC,
323     IDC_ECHOBACKEND,
324     IDC_ECHOYES,
325     IDC_ECHONO,
326     IDC_EDITSTATIC,
327     IDC_EDITBACKEND,
328     IDC_EDITYES,
329     IDC_EDITNO,
330     IDC_PRINTERSTATIC,
331     IDC_PRINTER,
332     terminalpanelend,
333
334     featurespanelstart,
335     IDC_TITLE_FEATURES,
336     IDC_BOX_FEATURES1,
337     IDC_NOAPPLICK,
338     IDC_NOAPPLICC,
339     IDC_NOMOUSEREP,
340     IDC_NORESIZE,
341     IDC_NOALTSCREEN,
342     IDC_NOWINTITLE,
343     IDC_NODBACKSPACE,
344     IDC_NOCHARSET,
345     featurespanelend,
346
347     bellpanelstart,
348     IDC_TITLE_BELL,
349     IDC_BOX_BELL1,
350     IDC_BOX_BELL2,
351     IDC_BELLSTATIC,
352     IDC_BELL_DISABLED,
353     IDC_BELL_DEFAULT,
354     IDC_BELL_WAVEFILE,
355     IDC_BELL_VISUAL,
356     IDC_BELL_WAVESTATIC,
357     IDC_BELL_WAVEEDIT,
358     IDC_BELL_WAVEBROWSE,
359     IDC_B_IND_STATIC,
360     IDC_B_IND_DISABLED,
361     IDC_B_IND_FLASH,
362     IDC_B_IND_STEADY,
363     IDC_BELLOVL,
364     IDC_BELLOVLNSTATIC,
365     IDC_BELLOVLN,
366     IDC_BELLOVLTSTATIC,
367     IDC_BELLOVLT,
368     IDC_BELLOVLEXPLAIN,
369     IDC_BELLOVLSSTATIC,
370     IDC_BELLOVLS,
371     bellpanelend,
372
373     windowpanelstart,
374     IDC_TITLE_WINDOW,
375     IDC_BOX_WINDOW1,
376     IDC_BOX_WINDOW2,
377     IDC_BOX_WINDOW3,
378     IDC_ROWSSTATIC,
379     IDC_ROWSEDIT,
380     IDC_COLSSTATIC,
381     IDC_COLSEDIT,
382     IDC_RESIZESTATIC,
383     IDC_RESIZETERM,
384     IDC_RESIZEFONT,
385     IDC_RESIZENONE,
386     IDC_RESIZEEITHER,
387     IDC_SCROLLBAR,
388     IDC_SCROLLBARFULLSCREEN,
389     IDC_SAVESTATIC,
390     IDC_SAVEEDIT,
391     IDC_SCROLLKEY,
392     IDC_SCROLLDISP,
393     windowpanelend,
394
395     behaviourpanelstart,
396     IDC_TITLE_BEHAVIOUR,
397     IDC_BOX_BEHAVIOUR1,
398     IDC_CLOSEWARN,
399     IDC_ALTF4,
400     IDC_ALTSPACE,
401     IDC_ALTONLY,
402     IDC_ALWAYSONTOP,
403     IDC_FULLSCREENONALTENTER,
404     behaviourpanelend,
405
406     appearancepanelstart,
407     IDC_TITLE_APPEARANCE,
408     IDC_BOX_APPEARANCE1,
409     IDC_BOX_APPEARANCE2,
410     IDC_BOX_APPEARANCE3,
411     IDC_BOX_APPEARANCE4,
412     IDC_BOX_APPEARANCE5,
413     IDC_CURSORSTATIC,
414     IDC_CURBLOCK,
415     IDC_CURUNDER,
416     IDC_CURVERT,
417     IDC_BLINKCUR,
418     IDC_FONTSTATIC,
419     IDC_CHOOSEFONT,
420     IDC_WINTITLE,
421     IDC_WINEDIT,
422     IDC_WINNAME,
423     IDC_HIDEMOUSE,
424     IDC_SUNKENEDGE,
425     IDC_WINBSTATIC,
426     IDC_WINBEDIT,
427     appearancepanelend,
428
429     connectionpanelstart,
430     IDC_TITLE_CONNECTION,
431     IDC_BOX_CONNECTION1,
432     IDC_BOX_CONNECTION2,
433     IDC_BOX_CONNECTION3,
434     IDC_TTSTATIC,
435     IDC_TTEDIT,
436     IDC_LOGSTATIC,
437     IDC_LOGEDIT,
438     IDC_PINGSTATIC,
439     IDC_PINGEDIT,
440     IDC_NODELAY,
441     connectionpanelend,
442
443     proxypanelstart,
444     IDC_TITLE_PROXY,
445     IDC_BOX_PROXY1,
446     IDC_PROXYTYPESTATIC,
447     IDC_PROXYTYPENONE,
448     IDC_PROXYTYPEHTTP,
449     IDC_PROXYTYPESOCKS,
450     IDC_PROXYTYPETELNET,
451     IDC_PROXYHOSTSTATIC,
452     IDC_PROXYHOSTEDIT,
453     IDC_PROXYPORTSTATIC,
454     IDC_PROXYPORTEDIT,
455     IDC_PROXYEXCLUDESTATIC,
456     IDC_PROXYEXCLUDEEDIT,
457     IDC_PROXYLOCALHOST,
458     IDC_PROXYDNSSTATIC,
459     IDC_PROXYDNSNO,
460     IDC_PROXYDNSAUTO,
461     IDC_PROXYDNSYES,
462     IDC_PROXYUSERSTATIC,
463     IDC_PROXYUSEREDIT,
464     IDC_PROXYPASSSTATIC,
465     IDC_PROXYPASSEDIT,
466     IDC_BOX_PROXY2,
467     IDC_PROXYTELNETCMDSTATIC,
468     IDC_PROXYTELNETCMDEDIT,
469     IDC_PROXYSOCKSVERSTATIC,
470     IDC_PROXYSOCKSVER5,
471     IDC_PROXYSOCKSVER4,
472     proxypanelend,
473
474     telnetpanelstart,
475     IDC_TITLE_TELNET,
476     IDC_BOX_TELNET1,
477     IDC_BOX_TELNET2,
478     IDC_TSSTATIC,
479     IDC_TSEDIT,
480     IDC_ENVSTATIC,
481     IDC_VARSTATIC,
482     IDC_VAREDIT,
483     IDC_VALSTATIC,
484     IDC_VALEDIT,
485     IDC_ENVLIST,
486     IDC_ENVADD,
487     IDC_ENVREMOVE,
488     IDC_EMSTATIC,
489     IDC_EMBSD,
490     IDC_EMRFC,
491     IDC_ACTSTATIC,
492     IDC_TPASSIVE,
493     IDC_TACTIVE,
494     IDC_TELNETKEY,
495     IDC_TELNETRET,
496     telnetpanelend,
497
498     rloginpanelstart,
499     IDC_TITLE_RLOGIN,
500     IDC_BOX_RLOGIN1,
501     IDC_BOX_RLOGIN2,
502     IDC_R_TSSTATIC,
503     IDC_R_TSEDIT,
504     IDC_RLLUSERSTATIC,
505     IDC_RLLUSEREDIT,
506     rloginpanelend,
507
508     sshpanelstart,
509     IDC_TITLE_SSH,
510     IDC_BOX_SSH1,
511     IDC_BOX_SSH2,
512     IDC_BOX_SSH3,
513     IDC_NOPTY,
514     IDC_BOX_SSHCIPHER,
515     IDC_CIPHERSTATIC2,
516     IDC_CIPHERLIST,
517     IDC_CIPHERUP,
518     IDC_CIPHERDN,
519     IDC_SSH2DES,
520     IDC_SSHPROTSTATIC,
521     IDC_SSHPROT1ONLY,
522     IDC_SSHPROT1,
523     IDC_SSHPROT2,
524     IDC_SSHPROT2ONLY,
525     IDC_CMDSTATIC,
526     IDC_CMDEDIT,
527     IDC_COMPRESS,
528     sshpanelend,
529
530     sshauthpanelstart,
531     IDC_TITLE_SSHAUTH,
532     IDC_BOX_SSHAUTH1,
533     IDC_BOX_SSHAUTH2,
534     IDC_PKSTATIC,
535     IDC_PKEDIT,
536     IDC_PKBUTTON,
537     IDC_AGENTFWD,
538     IDC_CHANGEUSER,
539     IDC_AUTHTIS,
540     IDC_AUTHKI,
541     sshauthpanelend,
542
543     sshbugspanelstart,
544     IDC_TITLE_SSHBUGS,
545     IDC_BOX_SSHBUGS1,
546     IDC_BUGS_IGNORE1,
547     IDC_BUGD_IGNORE1,
548     IDC_BUGS_PLAINPW1,
549     IDC_BUGD_PLAINPW1,
550     IDC_BUGS_RSA1,
551     IDC_BUGD_RSA1,
552     IDC_BUGS_HMAC2,
553     IDC_BUGD_HMAC2,
554     IDC_BUGS_DERIVEKEY2,
555     IDC_BUGD_DERIVEKEY2,
556     IDC_BUGS_RSAPAD2,
557     IDC_BUGD_RSAPAD2,
558     IDC_BUGS_DHGEX2,
559     IDC_BUGD_DHGEX2,
560     sshbugspanelend,
561
562     selectionpanelstart,
563     IDC_TITLE_SELECTION,
564     IDC_BOX_SELECTION1,
565     IDC_BOX_SELECTION2,
566     IDC_BOX_SELECTION3,
567     IDC_MBSTATIC,
568     IDC_MBWINDOWS,
569     IDC_MBXTERM,
570     IDC_MOUSEOVERRIDE,
571     IDC_SELTYPESTATIC,
572     IDC_SELTYPELEX,
573     IDC_SELTYPERECT,
574     IDC_CCSTATIC,
575     IDC_CCLIST,
576     IDC_CCSET,
577     IDC_CCSTATIC2,
578     IDC_CCEDIT,
579     IDC_RAWCNP,
580     IDC_RTFPASTE,
581     selectionpanelend,
582
583     colourspanelstart,
584     IDC_TITLE_COLOURS,
585     IDC_BOX_COLOURS1,
586     IDC_BOX_COLOURS2,
587     IDC_BOLDCOLOUR,
588     IDC_PALETTE,
589     IDC_COLOURSTATIC,
590     IDC_COLOURLIST,
591     IDC_RSTATIC,
592     IDC_GSTATIC,
593     IDC_BSTATIC,
594     IDC_RVALUE,
595     IDC_GVALUE,
596     IDC_BVALUE,
597     IDC_CHANGE,
598     colourspanelend,
599
600     translationpanelstart,
601     IDC_TITLE_TRANSLATION,
602     IDC_BOX_TRANSLATION1,
603     IDC_BOX_TRANSLATION2,
604     IDC_BOX_TRANSLATION3,
605     IDC_CODEPAGESTATIC,
606     IDC_CODEPAGE,
607     IDC_CAPSLOCKCYR,
608     IDC_VTSTATIC,
609     IDC_VTXWINDOWS,
610     IDC_VTOEMANSI,
611     IDC_VTOEMONLY,
612     IDC_VTPOORMAN,
613     IDC_VTUNICODE,
614     translationpanelend,
615
616     tunnelspanelstart,
617     IDC_TITLE_TUNNELS,
618     IDC_BOX_TUNNELS1,
619     IDC_BOX_TUNNELS2,
620     IDC_X11_FORWARD,
621     IDC_X11_DISPSTATIC,
622     IDC_X11_DISPLAY,
623     IDC_LPORT_ALL,
624     IDC_RPORT_ALL,
625     IDC_PFWDSTATIC,
626     IDC_PFWDSTATIC2,
627     IDC_PFWDREMOVE,
628     IDC_PFWDLIST,
629     IDC_PFWDADD,
630     IDC_SPORTSTATIC,
631     IDC_SPORTEDIT,
632     IDC_DPORTSTATIC,
633     IDC_DPORTEDIT,
634     IDC_PFWDLOCAL,
635     IDC_PFWDREMOTE,
636
637     tunnelspanelend,
638
639     controlendvalue
640 };
641
642 static const char *const colours[] = {
643     "Default Foreground", "Default Bold Foreground",
644     "Default Background", "Default Bold Background",
645     "Cursor Text", "Cursor Colour",
646     "ANSI Black", "ANSI Black Bold",
647     "ANSI Red", "ANSI Red Bold",
648     "ANSI Green", "ANSI Green Bold",
649     "ANSI Yellow", "ANSI Yellow Bold",
650     "ANSI Blue", "ANSI Blue Bold",
651     "ANSI Magenta", "ANSI Magenta Bold",
652     "ANSI Cyan", "ANSI Cyan Bold",
653     "ANSI White", "ANSI White Bold"
654 };
655 static const int permcolour[] = {
656     TRUE, FALSE, TRUE, FALSE, TRUE, TRUE,
657     TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE,
658     TRUE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, FALSE
659 };
660
661 static void fmtfont(char *buf)
662 {
663     sprintf(buf, "Font: %s, ", cfg.font);
664     if (cfg.fontisbold)
665         strcat(buf, "bold, ");
666     if (cfg.fontheight == 0)
667         strcat(buf, "default height");
668     else
669         sprintf(buf + strlen(buf), "%d-point",
670                 (cfg.fontheight < 0 ? -cfg.fontheight : cfg.fontheight));
671 }
672
673 char *help_context_cmd(int id)
674 {
675     switch (id) {
676       case IDC_HOSTSTATIC:
677       case IDC_HOST:
678       case IDC_PORTSTATIC:
679       case IDC_PORT:
680       case IDC_PROTSTATIC:
681       case IDC_PROTRAW:
682       case IDC_PROTTELNET:
683       case IDC_PROTRLOGIN:
684       case IDC_PROTSSH:
685         return "JI(`',`session.hostname')";
686       case IDC_SESSSTATIC:
687       case IDC_SESSEDIT:
688       case IDC_SESSLIST:
689       case IDC_SESSLOAD:
690       case IDC_SESSSAVE:
691       case IDC_SESSDEL:
692         return "JI(`',`session.saved')";
693       case IDC_CLOSEEXIT:
694       case IDC_COEALWAYS:
695       case IDC_COENEVER:
696       case IDC_COENORMAL:
697         return "JI(`',`session.coe')";
698       case IDC_LSTATSTATIC:
699       case IDC_LSTATOFF:
700       case IDC_LSTATASCII:
701       case IDC_LSTATRAW:
702       case IDC_LSTATPACKET:
703         return "JI(`',`logging.main')";
704       case IDC_LGFSTATIC:
705       case IDC_LGFEDIT:
706       case IDC_LGFBUTTON:
707       case IDC_LGFEXPLAIN:
708         return "JI(`',`logging.filename')";
709       case IDC_LSTATXIST:
710       case IDC_LSTATXOVR:
711       case IDC_LSTATXAPN:
712       case IDC_LSTATXASK:
713         return "JI(`',`logging.exists')";
714
715       case IDC_DELSTATIC:
716       case IDC_DEL008:
717       case IDC_DEL127:
718         return "JI(`',`keyboard.backspace')";
719       case IDC_HOMESTATIC:
720       case IDC_HOMETILDE:
721       case IDC_HOMERXVT:
722         return "JI(`',`keyboard.homeend')";
723       case IDC_FUNCSTATIC:
724       case IDC_FUNCTILDE:
725       case IDC_FUNCLINUX:
726       case IDC_FUNCXTERM:
727       case IDC_FUNCVT400:
728       case IDC_FUNCVT100P:
729       case IDC_FUNCSCO:
730         return "JI(`',`keyboard.funkeys')";
731       case IDC_KPSTATIC:
732       case IDC_KPNORMAL:
733       case IDC_KPAPPLIC:
734         return "JI(`',`keyboard.appkeypad')";
735       case IDC_CURSTATIC:
736       case IDC_CURNORMAL:
737       case IDC_CURAPPLIC:
738         return "JI(`',`keyboard.appcursor')";
739       case IDC_KPNH:
740         return "JI(`',`keyboard.nethack')";
741       case IDC_COMPOSEKEY:
742         return "JI(`',`keyboard.compose')";
743       case IDC_CTRLALTKEYS:
744         return "JI(`',`keyboard.ctrlalt')";
745
746       case IDC_NOAPPLICK:
747       case IDC_NOAPPLICC:
748         return "JI(`',`features.application')";
749       case IDC_NOMOUSEREP:
750         return "JI(`',`features.mouse')";
751       case IDC_NORESIZE:
752         return "JI(`',`features.resize')";
753       case IDC_NOALTSCREEN:
754         return "JI(`',`features.altscreen')";
755       case IDC_NOWINTITLE:
756         return "JI(`',`features.retitle')";
757       case IDC_NODBACKSPACE:
758         return "JI(`',`features.dbackspace')";
759       case IDC_NOCHARSET:
760         return "JI(`',`features.charset')";
761
762       case IDC_WRAPMODE:
763         return "JI(`',`terminal.autowrap')";
764       case IDC_DECOM:
765         return "JI(`',`terminal.decom')";
766       case IDC_LFHASCR:
767         return "JI(`',`terminal.lfhascr')";
768       case IDC_BCE:
769         return "JI(`',`terminal.bce')";
770       case IDC_BLINKTEXT:
771         return "JI(`',`terminal.blink')";
772       case IDC_ANSWERBACK:
773       case IDC_ANSWEREDIT:
774         return "JI(`',`terminal.answerback')";
775       case IDC_ECHOSTATIC:
776       case IDC_ECHOBACKEND:
777       case IDC_ECHOYES:
778       case IDC_ECHONO:
779         return "JI(`',`terminal.localecho')";
780       case IDC_EDITSTATIC:
781       case IDC_EDITBACKEND:
782       case IDC_EDITYES:
783       case IDC_EDITNO:
784         return "JI(`',`terminal.localedit')";
785       case IDC_PRINTERSTATIC:
786       case IDC_PRINTER:
787         return "JI(`',`terminal.printing')";
788
789       case IDC_BELLSTATIC:
790       case IDC_BELL_DISABLED:
791       case IDC_BELL_DEFAULT:
792       case IDC_BELL_WAVEFILE:
793       case IDC_BELL_VISUAL:
794       case IDC_BELL_WAVESTATIC:
795       case IDC_BELL_WAVEEDIT:
796       case IDC_BELL_WAVEBROWSE:
797         return "JI(`',`bell.style')";
798       case IDC_B_IND_STATIC:
799       case IDC_B_IND_DISABLED:
800       case IDC_B_IND_FLASH:
801       case IDC_B_IND_STEADY:
802         return "JI(`',`bell.taskbar')";
803       case IDC_BELLOVL:
804       case IDC_BELLOVLNSTATIC:
805       case IDC_BELLOVLN:
806       case IDC_BELLOVLTSTATIC:
807       case IDC_BELLOVLT:
808       case IDC_BELLOVLEXPLAIN:
809       case IDC_BELLOVLSSTATIC:
810       case IDC_BELLOVLS:
811         return "JI(`',`bell.overload')";
812
813       case IDC_ROWSSTATIC:
814       case IDC_ROWSEDIT:
815       case IDC_COLSSTATIC:
816       case IDC_COLSEDIT:
817         return "JI(`',`window.size')";
818       case IDC_RESIZESTATIC:
819       case IDC_RESIZETERM:
820       case IDC_RESIZEFONT:
821       case IDC_RESIZENONE:
822       case IDC_RESIZEEITHER:
823         return "JI(`',`window.resize')";
824       case IDC_SCROLLBAR:
825       case IDC_SCROLLBARFULLSCREEN:
826       case IDC_SAVESTATIC:
827       case IDC_SAVEEDIT:
828       case IDC_SCROLLKEY:
829       case IDC_SCROLLDISP:
830         return "JI(`',`window.scrollback')";
831
832       case IDC_CLOSEWARN:
833         return "JI(`',`behaviour.closewarn')";
834       case IDC_ALTF4:
835         return "JI(`',`behaviour.altf4')";
836       case IDC_ALTSPACE:
837         return "JI(`',`behaviour.altspace')";
838       case IDC_ALTONLY:
839         return "JI(`',`behaviour.altonly')";
840       case IDC_ALWAYSONTOP:
841         return "JI(`',`behaviour.alwaysontop')";
842       case IDC_FULLSCREENONALTENTER:
843         return "JI(`',`behaviour.altenter')";
844
845       case IDC_CURSORSTATIC:
846       case IDC_CURBLOCK:
847       case IDC_CURUNDER:
848       case IDC_CURVERT:
849       case IDC_BLINKCUR:
850         return "JI(`',`appearance.cursor')";
851       case IDC_FONTSTATIC:
852       case IDC_CHOOSEFONT:
853         return "JI(`',`appearance.font')";
854       case IDC_WINTITLE:
855       case IDC_WINEDIT:
856       case IDC_WINNAME:
857         return "JI(`',`appearance.title')";
858       case IDC_HIDEMOUSE:
859         return "JI(`',`appearance.hidemouse')";
860       case IDC_SUNKENEDGE:
861       case IDC_WINBSTATIC:
862       case IDC_WINBEDIT:
863         return "JI(`',`appearance.border')";
864
865       case IDC_TTSTATIC:
866       case IDC_TTEDIT:
867         return "JI(`',`connection.termtype')";
868       case IDC_LOGSTATIC:
869       case IDC_LOGEDIT:
870         return "JI(`',`connection.username')";
871       case IDC_PINGSTATIC:
872       case IDC_PINGEDIT:
873         return "JI(`',`connection.keepalive')";
874       case IDC_NODELAY:
875         return "JI(`',`connection.nodelay')";
876
877       case IDC_PROXYTYPESTATIC:
878       case IDC_PROXYTYPENONE:
879       case IDC_PROXYTYPEHTTP:
880       case IDC_PROXYTYPESOCKS:
881       case IDC_PROXYTYPETELNET:
882         return "JI(`',`proxy.type')";
883       case IDC_PROXYHOSTSTATIC:
884       case IDC_PROXYHOSTEDIT:
885       case IDC_PROXYPORTSTATIC:
886       case IDC_PROXYPORTEDIT:
887         return "JI(`',`proxy.main')";
888       case IDC_PROXYEXCLUDESTATIC:
889       case IDC_PROXYEXCLUDEEDIT:
890       case IDC_PROXYLOCALHOST:
891         return "JI(`',`proxy.exclude')";
892       case IDC_PROXYDNSSTATIC:
893       case IDC_PROXYDNSNO:
894       case IDC_PROXYDNSAUTO:
895       case IDC_PROXYDNSYES:
896         return "JI(`',`proxy.dns')";
897       case IDC_PROXYUSERSTATIC:
898       case IDC_PROXYUSEREDIT:
899       case IDC_PROXYPASSSTATIC:
900       case IDC_PROXYPASSEDIT:
901         return "JI(`',`proxy.auth')";
902       case IDC_PROXYTELNETCMDSTATIC:
903       case IDC_PROXYTELNETCMDEDIT:
904         return "JI(`',`proxy.command')";
905       case IDC_PROXYSOCKSVERSTATIC:
906       case IDC_PROXYSOCKSVER5:
907       case IDC_PROXYSOCKSVER4:
908         return "JI(`',`proxy.socksver')";
909
910       case IDC_TSSTATIC:
911       case IDC_TSEDIT:
912         return "JI(`',`telnet.termspeed')";
913       case IDC_ENVSTATIC:
914       case IDC_VARSTATIC:
915       case IDC_VAREDIT:
916       case IDC_VALSTATIC:
917       case IDC_VALEDIT:
918       case IDC_ENVLIST:
919       case IDC_ENVADD:
920       case IDC_ENVREMOVE:
921         return "JI(`',`telnet.environ')";
922       case IDC_EMSTATIC:
923       case IDC_EMBSD:
924       case IDC_EMRFC:
925         return "JI(`',`telnet.oldenviron')";
926       case IDC_ACTSTATIC:
927       case IDC_TPASSIVE:
928       case IDC_TACTIVE:
929         return "JI(`',`telnet.passive')";
930       case IDC_TELNETKEY:
931         return "JI(`',`telnet.specialkeys')";
932       case IDC_TELNETRET:
933         return "JI(`',`telnet.newline')";
934
935       case IDC_R_TSSTATIC:
936       case IDC_R_TSEDIT:
937         return "JI(`',`rlogin.termspeed')";
938       case IDC_RLLUSERSTATIC:
939       case IDC_RLLUSEREDIT:
940         return "JI(`',`rlogin.localuser')";
941
942       case IDC_NOPTY:
943         return "JI(`',`ssh.nopty')";
944       case IDC_CIPHERSTATIC2:
945       case IDC_CIPHERLIST:
946       case IDC_CIPHERUP:
947       case IDC_CIPHERDN:
948       case IDC_SSH2DES:
949         return "JI(`',`ssh.ciphers')";
950       case IDC_SSHPROTSTATIC:
951       case IDC_SSHPROT1ONLY:
952       case IDC_SSHPROT1:
953       case IDC_SSHPROT2:
954       case IDC_SSHPROT2ONLY:
955         return "JI(`',`ssh.protocol')";
956       case IDC_CMDSTATIC:
957       case IDC_CMDEDIT:
958         return "JI(`',`ssh.command')";
959       case IDC_COMPRESS:
960         return "JI(`',`ssh.compress')";
961
962       case IDC_PKSTATIC:
963       case IDC_PKEDIT:
964       case IDC_PKBUTTON:
965         return "JI(`',`ssh.auth.privkey')";
966       case IDC_AGENTFWD:
967         return "JI(`',`ssh.auth.agentfwd')";
968       case IDC_CHANGEUSER:
969         return "JI(`',`ssh.auth.changeuser')";
970       case IDC_AUTHTIS:
971         return "JI(`',`ssh.auth.tis')";
972       case IDC_AUTHKI:
973         return "JI(`',`ssh.auth.ki')";
974
975       case IDC_MBSTATIC:
976       case IDC_MBWINDOWS:
977       case IDC_MBXTERM:
978         return "JI(`',`selection.buttons')";
979       case IDC_MOUSEOVERRIDE:
980         return "JI(`',`selection.shiftdrag')";
981       case IDC_SELTYPESTATIC:
982       case IDC_SELTYPELEX:
983       case IDC_SELTYPERECT:
984         return "JI(`',`selection.rect')";
985       case IDC_CCSTATIC:
986       case IDC_CCLIST:
987       case IDC_CCSET:
988       case IDC_CCSTATIC2:
989       case IDC_CCEDIT:
990         return "JI(`',`selection.charclasses')";
991       case IDC_RAWCNP:
992         return "JI(`',`selection.linedraw')";
993       case IDC_RTFPASTE:
994         return "JI(`',`selection.rtf')";
995
996       case IDC_BOLDCOLOUR:
997         return "JI(`',`colours.bold')";
998       case IDC_PALETTE:
999         return "JI(`',`colours.logpal')";
1000       case IDC_COLOURSTATIC:
1001       case IDC_COLOURLIST:
1002       case IDC_RSTATIC:
1003       case IDC_GSTATIC:
1004       case IDC_BSTATIC:
1005       case IDC_RVALUE:
1006       case IDC_GVALUE:
1007       case IDC_BVALUE:
1008       case IDC_CHANGE:
1009         return "JI(`',`colours.config')";
1010
1011       case IDC_CODEPAGESTATIC:
1012       case IDC_CODEPAGE:
1013         return "JI(`',`translation.codepage')";
1014       case IDC_CAPSLOCKCYR:
1015         return "JI(`',`translation.cyrillic')";
1016       case IDC_VTSTATIC:
1017       case IDC_VTXWINDOWS:
1018       case IDC_VTOEMANSI:
1019       case IDC_VTOEMONLY:
1020       case IDC_VTPOORMAN:
1021       case IDC_VTUNICODE:
1022         return "JI(`',`translation.linedraw')";
1023
1024       case IDC_X11_FORWARD:
1025       case IDC_X11_DISPSTATIC:
1026       case IDC_X11_DISPLAY:
1027         return "JI(`',`ssh.tunnels.x11')";
1028       case IDC_PFWDSTATIC:
1029       case IDC_PFWDSTATIC2:
1030       case IDC_PFWDREMOVE:
1031       case IDC_PFWDLIST:
1032       case IDC_PFWDADD:
1033       case IDC_SPORTSTATIC:
1034       case IDC_SPORTEDIT:
1035       case IDC_DPORTSTATIC:
1036       case IDC_DPORTEDIT:
1037       case IDC_PFWDLOCAL:
1038       case IDC_PFWDREMOTE:
1039         return "JI(`',`ssh.tunnels.portfwd')";
1040       case IDC_LPORT_ALL:
1041       case IDC_RPORT_ALL:
1042         return "JI(`',`ssh.tunnels.portfwd.localhost')";
1043
1044       case IDC_BUGS_IGNORE1:
1045       case IDC_BUGD_IGNORE1:
1046         return "JI(`',`ssh.bugs.ignore1')";
1047       case IDC_BUGS_PLAINPW1:
1048       case IDC_BUGD_PLAINPW1:
1049         return "JI(`',`ssh.bugs.plainpw1')";
1050       case IDC_BUGS_RSA1:
1051       case IDC_BUGD_RSA1:
1052         return "JI(`',`ssh.bugs.rsa1')";
1053       case IDC_BUGS_HMAC2:
1054       case IDC_BUGD_HMAC2:
1055         return "JI(`',`ssh.bugs.hmac2')";
1056       case IDC_BUGS_DERIVEKEY2:
1057       case IDC_BUGD_DERIVEKEY2:
1058         return "JI(`',`ssh.bugs.derivekey2')";
1059       case IDC_BUGS_RSAPAD2:
1060       case IDC_BUGD_RSAPAD2:
1061         return "JI(`',`ssh.bugs.rsapad2')";
1062       case IDC_BUGS_DHGEX2:
1063       case IDC_BUGD_DHGEX2:
1064         return "JI(`',`ssh.bugs.dhgex2')";
1065
1066       default:
1067         return NULL;
1068     }
1069 }
1070
1071 /* 2nd arg: NZ => don't redraw session list (use when loading
1072  * a new session) */
1073 static void init_dlg_ctrls(HWND hwnd, int keepsess)
1074 {
1075     int i;
1076     char fontstatic[256];
1077
1078     SetDlgItemText(hwnd, IDC_HOST, cfg.host);
1079     SetDlgItemText(hwnd, IDC_SESSEDIT, savedsession);
1080     if (!keepsess) {
1081         int i, n;
1082         n = SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_GETCOUNT, 0, 0);
1083         for (i = n; i-- > 0;)
1084             SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_DELETESTRING, i, 0);
1085         for (i = 0; i < sesslist.nsessions; i++)
1086             SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_ADDSTRING,
1087                                0, (LPARAM) (sesslist.sessions[i]));
1088     }
1089     SetDlgItemInt(hwnd, IDC_PORT, cfg.port, FALSE);
1090     CheckRadioButton(hwnd, IDC_PROTRAW, IDC_PROTSSH,
1091                      cfg.protocol == PROT_SSH ? IDC_PROTSSH :
1092                      cfg.protocol == PROT_TELNET ? IDC_PROTTELNET :
1093                      cfg.protocol ==
1094                      PROT_RLOGIN ? IDC_PROTRLOGIN : IDC_PROTRAW);
1095     SetDlgItemInt(hwnd, IDC_PINGEDIT, cfg.ping_interval, FALSE);
1096     CheckDlgButton(hwnd, IDC_NODELAY, cfg.tcp_nodelay);
1097
1098     CheckRadioButton(hwnd, IDC_DEL008, IDC_DEL127,
1099                      cfg.bksp_is_delete ? IDC_DEL127 : IDC_DEL008);
1100     CheckRadioButton(hwnd, IDC_HOMETILDE, IDC_HOMERXVT,
1101                      cfg.rxvt_homeend ? IDC_HOMERXVT : IDC_HOMETILDE);
1102     CheckRadioButton(hwnd, IDC_FUNCTILDE, IDC_FUNCSCO,
1103                      cfg.funky_type == 0 ? IDC_FUNCTILDE :
1104                      cfg.funky_type == 1 ? IDC_FUNCLINUX :
1105                      cfg.funky_type == 2 ? IDC_FUNCXTERM :
1106                      cfg.funky_type == 3 ? IDC_FUNCVT400 :
1107                      cfg.funky_type == 4 ? IDC_FUNCVT100P :
1108                      cfg.funky_type == 5 ? IDC_FUNCSCO : IDC_FUNCTILDE);
1109     CheckDlgButton(hwnd, IDC_NOAPPLICC, cfg.no_applic_c);
1110     CheckDlgButton(hwnd, IDC_NOAPPLICK, cfg.no_applic_k);
1111     CheckDlgButton(hwnd, IDC_NOMOUSEREP, cfg.no_mouse_rep);
1112     CheckDlgButton(hwnd, IDC_NORESIZE, cfg.no_remote_resize);
1113     CheckDlgButton(hwnd, IDC_NOALTSCREEN, cfg.no_alt_screen);
1114     CheckDlgButton(hwnd, IDC_NOWINTITLE, cfg.no_remote_wintitle);
1115     CheckDlgButton(hwnd, IDC_NODBACKSPACE, cfg.no_dbackspace);
1116     CheckDlgButton(hwnd, IDC_NOCHARSET, cfg.no_remote_charset);
1117     CheckRadioButton(hwnd, IDC_CURNORMAL, IDC_CURAPPLIC,
1118                      cfg.app_cursor ? IDC_CURAPPLIC : IDC_CURNORMAL);
1119     CheckRadioButton(hwnd, IDC_KPNORMAL, IDC_KPNH,
1120                      cfg.nethack_keypad ? IDC_KPNH :
1121                      cfg.app_keypad ? IDC_KPAPPLIC : IDC_KPNORMAL);
1122     CheckDlgButton(hwnd, IDC_ALTF4, cfg.alt_f4);
1123     CheckDlgButton(hwnd, IDC_ALTSPACE, cfg.alt_space);
1124     CheckDlgButton(hwnd, IDC_ALTONLY, cfg.alt_only);
1125     CheckDlgButton(hwnd, IDC_COMPOSEKEY, cfg.compose_key);
1126     CheckDlgButton(hwnd, IDC_CTRLALTKEYS, cfg.ctrlaltkeys);
1127     CheckDlgButton(hwnd, IDC_TELNETKEY, cfg.telnet_keyboard);
1128     CheckDlgButton(hwnd, IDC_TELNETRET, cfg.telnet_newline);
1129     CheckRadioButton(hwnd, IDC_ECHOBACKEND, IDC_ECHONO,
1130                      cfg.localecho == LD_BACKEND ? IDC_ECHOBACKEND :
1131                      cfg.localecho == LD_YES ? IDC_ECHOYES : IDC_ECHONO);
1132     CheckRadioButton(hwnd, IDC_EDITBACKEND, IDC_EDITNO,
1133                      cfg.localedit == LD_BACKEND ? IDC_EDITBACKEND :
1134                      cfg.localedit == LD_YES ? IDC_EDITYES : IDC_EDITNO);
1135     SetDlgItemText(hwnd, IDC_ANSWEREDIT, cfg.answerback);
1136     CheckDlgButton(hwnd, IDC_ALWAYSONTOP, cfg.alwaysontop);
1137     CheckDlgButton(hwnd, IDC_FULLSCREENONALTENTER, cfg.fullscreenonaltenter);
1138     CheckDlgButton(hwnd, IDC_SCROLLKEY, cfg.scroll_on_key);
1139     CheckDlgButton(hwnd, IDC_SCROLLDISP, cfg.scroll_on_disp);
1140
1141     CheckDlgButton(hwnd, IDC_WRAPMODE, cfg.wrap_mode);
1142     CheckDlgButton(hwnd, IDC_DECOM, cfg.dec_om);
1143     CheckDlgButton(hwnd, IDC_LFHASCR, cfg.lfhascr);
1144     SetDlgItemInt(hwnd, IDC_ROWSEDIT, cfg.height, FALSE);
1145     SetDlgItemInt(hwnd, IDC_COLSEDIT, cfg.width, FALSE);
1146     SetDlgItemInt(hwnd, IDC_SAVEEDIT, cfg.savelines, FALSE);
1147     fmtfont(fontstatic);
1148     SetDlgItemText(hwnd, IDC_FONTSTATIC, fontstatic);
1149     CheckRadioButton(hwnd, IDC_BELL_DISABLED, IDC_BELL_VISUAL,
1150                      cfg.beep == BELL_DISABLED ? IDC_BELL_DISABLED :
1151                      cfg.beep == BELL_DEFAULT ? IDC_BELL_DEFAULT :
1152                      cfg.beep == BELL_WAVEFILE ? IDC_BELL_WAVEFILE :
1153                      cfg.beep ==
1154                      BELL_VISUAL ? IDC_BELL_VISUAL : IDC_BELL_DEFAULT);
1155     CheckRadioButton(hwnd, IDC_B_IND_DISABLED, IDC_B_IND_STEADY,
1156                      cfg.beep_ind ==
1157                      B_IND_DISABLED ? IDC_B_IND_DISABLED : cfg.beep_ind ==
1158                      B_IND_FLASH ? IDC_B_IND_FLASH : cfg.beep_ind ==
1159                      B_IND_STEADY ? IDC_B_IND_STEADY : IDC_B_IND_DISABLED);
1160     SetDlgItemText(hwnd, IDC_BELL_WAVEEDIT, cfg.bell_wavefile);
1161     CheckDlgButton(hwnd, IDC_BELLOVL, cfg.bellovl);
1162     SetDlgItemInt(hwnd, IDC_BELLOVLN, cfg.bellovl_n, FALSE);
1163     MySetDlgItemFlt(hwnd, IDC_BELLOVLT, cfg.bellovl_t / 1000.0);
1164     MySetDlgItemFlt(hwnd, IDC_BELLOVLS, cfg.bellovl_s / 1000.0);
1165
1166     CheckDlgButton(hwnd, IDC_BCE, cfg.bce);
1167     CheckDlgButton(hwnd, IDC_BLINKTEXT, cfg.blinktext);
1168
1169     SetDlgItemText(hwnd, IDC_WINEDIT, cfg.wintitle);
1170     CheckDlgButton(hwnd, IDC_WINNAME, cfg.win_name_always);
1171     CheckDlgButton(hwnd, IDC_HIDEMOUSE, cfg.hide_mouseptr);
1172     CheckDlgButton(hwnd, IDC_SUNKENEDGE, cfg.sunken_edge);
1173     SetDlgItemInt(hwnd, IDC_WINBEDIT, cfg.window_border, FALSE);
1174     CheckRadioButton(hwnd, IDC_CURBLOCK, IDC_CURVERT,
1175                      cfg.cursor_type == 0 ? IDC_CURBLOCK :
1176                      cfg.cursor_type == 1 ? IDC_CURUNDER : IDC_CURVERT);
1177     CheckDlgButton(hwnd, IDC_BLINKCUR, cfg.blink_cur);
1178     CheckDlgButton(hwnd, IDC_SCROLLBAR, cfg.scrollbar);
1179     CheckDlgButton(hwnd, IDC_SCROLLBARFULLSCREEN, cfg.scrollbar_in_fullscreen);
1180     CheckRadioButton(hwnd, IDC_RESIZETERM, IDC_RESIZEEITHER,
1181                      cfg.resize_action == RESIZE_TERM ? IDC_RESIZETERM :
1182                      cfg.resize_action == RESIZE_FONT ? IDC_RESIZEFONT :
1183                      cfg.resize_action == RESIZE_EITHER ? IDC_RESIZEEITHER :
1184                      IDC_RESIZENONE);
1185     CheckRadioButton(hwnd, IDC_COEALWAYS, IDC_COENORMAL,
1186                      cfg.close_on_exit == COE_NORMAL ? IDC_COENORMAL :
1187                      cfg.close_on_exit ==
1188                      COE_NEVER ? IDC_COENEVER : IDC_COEALWAYS);
1189     CheckDlgButton(hwnd, IDC_CLOSEWARN, cfg.warn_on_close);
1190
1191     SetDlgItemText(hwnd, IDC_TTEDIT, cfg.termtype);
1192     SetDlgItemText(hwnd, IDC_TSEDIT, cfg.termspeed);
1193     SetDlgItemText(hwnd, IDC_R_TSEDIT, cfg.termspeed);
1194     SetDlgItemText(hwnd, IDC_RLLUSEREDIT, cfg.localusername);
1195     SetDlgItemText(hwnd, IDC_LOGEDIT, cfg.username);
1196     SetDlgItemText(hwnd, IDC_LGFEDIT, cfg.logfilename);
1197     CheckRadioButton(hwnd, IDC_LSTATOFF, IDC_LSTATPACKET,
1198                      cfg.logtype == LGTYP_NONE ? IDC_LSTATOFF :
1199                      cfg.logtype == LGTYP_ASCII ? IDC_LSTATASCII :
1200                      cfg.logtype == LGTYP_DEBUG ? IDC_LSTATRAW :
1201                      IDC_LSTATPACKET);
1202     CheckRadioButton(hwnd, IDC_LSTATXOVR, IDC_LSTATXASK,
1203                      cfg.logxfovr == LGXF_OVR ? IDC_LSTATXOVR :
1204                      cfg.logxfovr == LGXF_ASK ? IDC_LSTATXASK :
1205                      IDC_LSTATXAPN);
1206     {
1207         char *p = cfg.environmt;
1208         SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_RESETCONTENT, 0, 0);
1209         while (*p) {
1210             SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_ADDSTRING, 0,
1211                                (LPARAM) p);
1212             p += strlen(p) + 1;
1213         }
1214         p = cfg.portfwd;
1215         while (*p) {
1216             SendDlgItemMessage(hwnd, IDC_PFWDLIST, LB_ADDSTRING, 0,
1217                                (LPARAM) p);
1218             p += strlen(p) + 1;
1219         }
1220     }
1221     CheckRadioButton(hwnd, IDC_EMBSD, IDC_EMRFC,
1222                      cfg.rfc_environ ? IDC_EMRFC : IDC_EMBSD);
1223     CheckRadioButton(hwnd, IDC_TPASSIVE, IDC_TACTIVE,
1224                      cfg.passive_telnet ? IDC_TPASSIVE : IDC_TACTIVE);
1225
1226     SetDlgItemText(hwnd, IDC_TTEDIT, cfg.termtype);
1227     SetDlgItemText(hwnd, IDC_LOGEDIT, cfg.username);
1228     CheckDlgButton(hwnd, IDC_NOPTY, cfg.nopty);
1229     CheckDlgButton(hwnd, IDC_COMPRESS, cfg.compression);
1230     CheckDlgButton(hwnd, IDC_SSH2DES, cfg.ssh2_des_cbc);
1231     CheckDlgButton(hwnd, IDC_AGENTFWD, cfg.agentfwd);
1232     CheckDlgButton(hwnd, IDC_CHANGEUSER, cfg.change_username);
1233     CheckRadioButton(hwnd, IDC_SSHPROT1ONLY, IDC_SSHPROT2ONLY,
1234                      cfg.sshprot == 1 ? IDC_SSHPROT1 :
1235                      cfg.sshprot == 2 ? IDC_SSHPROT2 :
1236                      cfg.sshprot == 3 ? IDC_SSHPROT2ONLY : IDC_SSHPROT1ONLY);
1237     CheckDlgButton(hwnd, IDC_AUTHTIS, cfg.try_tis_auth);
1238     CheckDlgButton(hwnd, IDC_AUTHKI, cfg.try_ki_auth);
1239     SetDlgItemText(hwnd, IDC_PKEDIT, cfg.keyfile);
1240     SetDlgItemText(hwnd, IDC_CMDEDIT, cfg.remote_cmd);
1241
1242     {
1243         int i;
1244         static const struct { char *s; int c; } ciphers[] = {
1245             { "3DES",                   CIPHER_3DES },
1246             { "Blowfish",               CIPHER_BLOWFISH },
1247             { "DES",                    CIPHER_DES },
1248             { "AES (SSH 2 only)",       CIPHER_AES },
1249             { "-- warn below here --",  CIPHER_WARN }
1250         };
1251
1252         /* Set up the "selected ciphers" box. */
1253         /* (cipherlist assumed to contain all ciphers) */
1254         SendDlgItemMessage(hwnd, IDC_CIPHERLIST, LB_RESETCONTENT, 0, 0);
1255         for (i = 0; i < CIPHER_MAX; i++) {
1256             int c = cfg.ssh_cipherlist[i];
1257             int j, pos;
1258             char *cstr = NULL;
1259             for (j = 0; j < (sizeof ciphers) / (sizeof ciphers[0]); j++) {
1260                 if (ciphers[j].c == c) {
1261                     cstr = ciphers[j].s;
1262                     break;
1263                 }
1264             }
1265             pos = SendDlgItemMessage(hwnd, IDC_CIPHERLIST, LB_ADDSTRING,
1266                                      0, (LPARAM) cstr);
1267             SendDlgItemMessage(hwnd, IDC_CIPHERLIST, LB_SETITEMDATA,
1268                                pos, (LPARAM) c);
1269         }
1270
1271     }
1272
1273     CheckRadioButton(hwnd, IDC_MBWINDOWS, IDC_MBXTERM,
1274                      cfg.mouse_is_xterm ? IDC_MBXTERM : IDC_MBWINDOWS);
1275     CheckRadioButton(hwnd, IDC_SELTYPELEX, IDC_SELTYPERECT,
1276                      cfg.rect_select == 0 ? IDC_SELTYPELEX : IDC_SELTYPERECT);
1277     CheckDlgButton(hwnd, IDC_MOUSEOVERRIDE, cfg.mouse_override);
1278     CheckDlgButton(hwnd, IDC_RAWCNP, cfg.rawcnp);
1279     CheckDlgButton(hwnd, IDC_RTFPASTE, cfg.rtf_paste);
1280     {
1281         static int tabs[4] = { 25, 61, 96, 128 };
1282         SendDlgItemMessage(hwnd, IDC_CCLIST, LB_SETTABSTOPS, 4,
1283                            (LPARAM) tabs);
1284     }
1285     for (i = 0; i < 128; i++) {
1286         char str[100];
1287         sprintf(str, "%d\t(0x%02X)\t%c\t%d", i, i,
1288                 (i >= 0x21 && i != 0x7F) ? i : ' ', cfg.wordness[i]);
1289         SendDlgItemMessage(hwnd, IDC_CCLIST, LB_ADDSTRING, 0,
1290                            (LPARAM) str);
1291     }
1292
1293     CheckDlgButton(hwnd, IDC_BOLDCOLOUR, cfg.bold_colour);
1294     CheckDlgButton(hwnd, IDC_PALETTE, cfg.try_palette);
1295     {
1296         int i, n;
1297         n = SendDlgItemMessage(hwnd, IDC_COLOURLIST, LB_GETCOUNT, 0, 0);
1298         for (i = n; i-- > 0;)
1299             SendDlgItemMessage(hwnd, IDC_COLOURLIST,
1300                                LB_DELETESTRING, i, 0);
1301         for (i = 0; i < 22; i++)
1302             if (cfg.bold_colour || permcolour[i])
1303                 SendDlgItemMessage(hwnd, IDC_COLOURLIST, LB_ADDSTRING, 0,
1304                                    (LPARAM) colours[i]);
1305     }
1306     SendDlgItemMessage(hwnd, IDC_COLOURLIST, LB_SETCURSEL, 0, 0);
1307     SetDlgItemInt(hwnd, IDC_RVALUE, cfg.colours[0][0], FALSE);
1308     SetDlgItemInt(hwnd, IDC_GVALUE, cfg.colours[0][1], FALSE);
1309     SetDlgItemInt(hwnd, IDC_BVALUE, cfg.colours[0][2], FALSE);
1310
1311     {
1312         int i;
1313         char *cp;
1314         strcpy(cfg.line_codepage, cp_name(decode_codepage(cfg.line_codepage)));
1315         SendDlgItemMessage(hwnd, IDC_CODEPAGE, CB_RESETCONTENT, 0, 0);
1316         CheckDlgButton (hwnd, IDC_CAPSLOCKCYR, cfg.xlat_capslockcyr);
1317         for (i = 0; (cp = cp_enumerate(i)) != NULL; i++) {
1318             SendDlgItemMessage(hwnd, IDC_CODEPAGE, CB_ADDSTRING,
1319                                0, (LPARAM) cp);
1320         }
1321         SetDlgItemText(hwnd, IDC_CODEPAGE, cfg.line_codepage);
1322     }
1323
1324     {
1325         int i, nprinters;
1326         printer_enum *pe;
1327         pe = printer_start_enum(&nprinters);
1328         SendDlgItemMessage(hwnd, IDC_PRINTER, CB_RESETCONTENT, 0, 0);
1329         SendDlgItemMessage(hwnd, IDC_PRINTER, CB_ADDSTRING,
1330                            0, (LPARAM) PRINTER_DISABLED_STRING);
1331         for (i = 0; i < nprinters; i++) {
1332             char *printer_name = printer_get_name(pe, i);
1333             SendDlgItemMessage(hwnd, IDC_PRINTER, CB_ADDSTRING,
1334                                0, (LPARAM) printer_name);
1335         }
1336         printer_finish_enum(pe);
1337         SetDlgItemText(hwnd, IDC_PRINTER,
1338                        *cfg.printer ? cfg.printer : PRINTER_DISABLED_STRING);
1339     }
1340
1341     CheckRadioButton(hwnd, IDC_VTXWINDOWS, IDC_VTUNICODE,
1342                      cfg.vtmode == VT_XWINDOWS ? IDC_VTXWINDOWS :
1343                      cfg.vtmode == VT_OEMANSI ? IDC_VTOEMANSI :
1344                      cfg.vtmode == VT_OEMONLY ? IDC_VTOEMONLY :
1345                      cfg.vtmode == VT_UNICODE ? IDC_VTUNICODE :
1346                      IDC_VTPOORMAN);
1347
1348     CheckDlgButton(hwnd, IDC_X11_FORWARD, cfg.x11_forward);
1349     SetDlgItemText(hwnd, IDC_X11_DISPLAY, cfg.x11_display);
1350
1351     CheckDlgButton(hwnd, IDC_LPORT_ALL, cfg.lport_acceptall);
1352     CheckDlgButton(hwnd, IDC_RPORT_ALL, cfg.rport_acceptall);
1353     CheckRadioButton(hwnd, IDC_PFWDLOCAL, IDC_PFWDREMOTE, IDC_PFWDLOCAL);
1354
1355     /* proxy config */
1356     CheckRadioButton(hwnd, IDC_PROXYTYPENONE, IDC_PROXYTYPETELNET,
1357                      cfg.proxy_type == PROXY_HTTP ? IDC_PROXYTYPEHTTP :
1358                      cfg.proxy_type == PROXY_SOCKS ? IDC_PROXYTYPESOCKS :
1359                      cfg.proxy_type == PROXY_TELNET ? IDC_PROXYTYPETELNET : IDC_PROXYTYPENONE);
1360     SetDlgItemText(hwnd, IDC_PROXYHOSTEDIT, cfg.proxy_host);
1361     SetDlgItemInt(hwnd, IDC_PROXYPORTEDIT, cfg.proxy_port, FALSE);
1362     SetDlgItemText(hwnd, IDC_PROXYEXCLUDEEDIT, cfg.proxy_exclude_list);
1363     CheckDlgButton(hwnd, IDC_PROXYLOCALHOST, cfg.even_proxy_localhost);
1364     CheckRadioButton(hwnd, IDC_PROXYDNSNO, IDC_PROXYDNSYES,
1365                      cfg.proxy_dns == PROXYDNS_NO ? IDC_PROXYDNSNO :
1366                      cfg.proxy_dns == PROXYDNS_YES ? IDC_PROXYDNSYES :
1367                      IDC_PROXYDNSAUTO);
1368     SetDlgItemText(hwnd, IDC_PROXYTELNETCMDEDIT, cfg.proxy_telnet_command);
1369     SetDlgItemText(hwnd, IDC_PROXYUSEREDIT, cfg.proxy_username);
1370     SetDlgItemText(hwnd, IDC_PROXYPASSEDIT, cfg.proxy_password);
1371     CheckRadioButton(hwnd, IDC_PROXYSOCKSVER5, IDC_PROXYSOCKSVER4,
1372                      cfg.proxy_socks_version == 4 ? IDC_PROXYSOCKSVER4 : IDC_PROXYSOCKSVER5);
1373
1374     /* SSH bugs config */
1375     SendDlgItemMessage(hwnd, IDC_BUGD_IGNORE1, CB_RESETCONTENT, 0, 0);
1376     SendDlgItemMessage(hwnd, IDC_BUGD_IGNORE1, CB_ADDSTRING, 0, (LPARAM)"Auto");
1377     SendDlgItemMessage(hwnd, IDC_BUGD_IGNORE1, CB_ADDSTRING, 0, (LPARAM)"Off");
1378     SendDlgItemMessage(hwnd, IDC_BUGD_IGNORE1, CB_ADDSTRING, 0, (LPARAM)"On");
1379     SendDlgItemMessage(hwnd, IDC_BUGD_IGNORE1, CB_SETCURSEL,
1380                        cfg.sshbug_ignore1 == BUG_ON ? 2 :
1381                        cfg.sshbug_ignore1 == BUG_OFF ? 1 : 0, 0);
1382     SendDlgItemMessage(hwnd, IDC_BUGD_PLAINPW1, CB_RESETCONTENT, 0, 0);
1383     SendDlgItemMessage(hwnd, IDC_BUGD_PLAINPW1, CB_ADDSTRING, 0, (LPARAM)"Auto");
1384     SendDlgItemMessage(hwnd, IDC_BUGD_PLAINPW1, CB_ADDSTRING, 0, (LPARAM)"Off");
1385     SendDlgItemMessage(hwnd, IDC_BUGD_PLAINPW1, CB_ADDSTRING, 0, (LPARAM)"On");
1386     SendDlgItemMessage(hwnd, IDC_BUGD_PLAINPW1, CB_SETCURSEL,
1387                        cfg.sshbug_plainpw1 == BUG_ON ? 2 :
1388                        cfg.sshbug_plainpw1 == BUG_OFF ? 1 : 0, 0);
1389     SendDlgItemMessage(hwnd, IDC_BUGD_RSA1, CB_RESETCONTENT, 0, 0);
1390     SendDlgItemMessage(hwnd, IDC_BUGD_RSA1, CB_ADDSTRING, 0, (LPARAM)"Auto");
1391     SendDlgItemMessage(hwnd, IDC_BUGD_RSA1, CB_ADDSTRING, 0, (LPARAM)"Off");
1392     SendDlgItemMessage(hwnd, IDC_BUGD_RSA1, CB_ADDSTRING, 0, (LPARAM)"On");
1393     SendDlgItemMessage(hwnd, IDC_BUGD_RSA1, CB_SETCURSEL,
1394                        cfg.sshbug_rsa1 == BUG_ON ? 2 :
1395                        cfg.sshbug_rsa1 == BUG_OFF ? 1 : 0, 0);
1396     SendDlgItemMessage(hwnd, IDC_BUGD_HMAC2, CB_RESETCONTENT, 0, 0);
1397     SendDlgItemMessage(hwnd, IDC_BUGD_HMAC2, CB_ADDSTRING, 0, (LPARAM)"Auto");
1398     SendDlgItemMessage(hwnd, IDC_BUGD_HMAC2, CB_ADDSTRING, 0, (LPARAM)"Off");
1399     SendDlgItemMessage(hwnd, IDC_BUGD_HMAC2, CB_ADDSTRING, 0, (LPARAM)"On");
1400     SendDlgItemMessage(hwnd, IDC_BUGD_HMAC2, CB_SETCURSEL,
1401                        cfg.sshbug_hmac2 == BUG_ON ? 2 :
1402                        cfg.sshbug_hmac2 == BUG_OFF ? 1 : 0, 0);
1403     SendDlgItemMessage(hwnd, IDC_BUGD_DERIVEKEY2, CB_RESETCONTENT, 0, 0);
1404     SendDlgItemMessage(hwnd, IDC_BUGD_DERIVEKEY2, CB_ADDSTRING, 0, (LPARAM)"Auto");
1405     SendDlgItemMessage(hwnd, IDC_BUGD_DERIVEKEY2, CB_ADDSTRING, 0, (LPARAM)"Off");
1406     SendDlgItemMessage(hwnd, IDC_BUGD_DERIVEKEY2, CB_ADDSTRING, 0, (LPARAM)"On");
1407     SendDlgItemMessage(hwnd, IDC_BUGD_DERIVEKEY2, CB_SETCURSEL,
1408                        cfg.sshbug_derivekey2 == BUG_ON ? 2 :
1409                        cfg.sshbug_derivekey2 == BUG_OFF ? 1 : 0, 0);
1410     SendDlgItemMessage(hwnd, IDC_BUGD_RSAPAD2, CB_RESETCONTENT, 0, 0);
1411     SendDlgItemMessage(hwnd, IDC_BUGD_RSAPAD2, CB_ADDSTRING, 0, (LPARAM)"Auto");
1412     SendDlgItemMessage(hwnd, IDC_BUGD_RSAPAD2, CB_ADDSTRING, 0, (LPARAM)"Off");
1413     SendDlgItemMessage(hwnd, IDC_BUGD_RSAPAD2, CB_ADDSTRING, 0, (LPARAM)"On");
1414     SendDlgItemMessage(hwnd, IDC_BUGD_RSAPAD2, CB_SETCURSEL,
1415                        cfg.sshbug_rsapad2 == BUG_ON ? 2 :
1416                        cfg.sshbug_rsapad2 == BUG_OFF ? 1 : 0, 0);
1417     SendDlgItemMessage(hwnd, IDC_BUGD_DHGEX2, CB_RESETCONTENT, 0, 0);
1418     SendDlgItemMessage(hwnd, IDC_BUGD_DHGEX2, CB_ADDSTRING, 0, (LPARAM)"Auto");
1419     SendDlgItemMessage(hwnd, IDC_BUGD_DHGEX2, CB_ADDSTRING, 0, (LPARAM)"Off");
1420     SendDlgItemMessage(hwnd, IDC_BUGD_DHGEX2, CB_ADDSTRING, 0, (LPARAM)"On");
1421     SendDlgItemMessage(hwnd, IDC_BUGD_DHGEX2, CB_SETCURSEL,
1422                        cfg.sshbug_dhgex2 == BUG_ON ? 2 :
1423                        cfg.sshbug_dhgex2 == BUG_OFF ? 1 : 0, 0);
1424 }
1425
1426 struct treeview_faff {
1427     HWND treeview;
1428     HTREEITEM lastat[4];
1429 };
1430
1431 static HTREEITEM treeview_insert(struct treeview_faff *faff,
1432                                  int level, char *text)
1433 {
1434     TVINSERTSTRUCT ins;
1435     int i;
1436     HTREEITEM newitem;
1437     ins.hParent = (level > 0 ? faff->lastat[level - 1] : TVI_ROOT);
1438     ins.hInsertAfter = faff->lastat[level];
1439 #if _WIN32_IE >= 0x0400 && defined NONAMELESSUNION
1440 #define INSITEM DUMMYUNIONNAME.item
1441 #else
1442 #define INSITEM item
1443 #endif
1444     ins.INSITEM.mask = TVIF_TEXT;
1445     ins.INSITEM.pszText = text;
1446     newitem = TreeView_InsertItem(faff->treeview, &ins);
1447     if (level > 0)
1448         TreeView_Expand(faff->treeview, faff->lastat[level - 1],
1449                         TVE_EXPAND);
1450     faff->lastat[level] = newitem;
1451     for (i = level + 1; i < 4; i++)
1452         faff->lastat[i] = NULL;
1453     return newitem;
1454 }
1455
1456 /*
1457  * Create the panelfuls of controls in the configuration box.
1458  */
1459 static void create_controls(HWND hwnd, int dlgtype, int panel)
1460 {
1461     if (panel == sessionpanelstart) {
1462         /* The Session panel. Accelerators used: [acgoh] nprtis elvd w */
1463         struct ctlpos cp;
1464         ctlposinit(&cp, hwnd, 80, 3, 13);
1465         bartitle(&cp, "Basic options for your PuTTY session",
1466                  IDC_TITLE_SESSION);
1467         if (dlgtype == 0) {
1468             beginbox(&cp, "Specify your connection by host name or IP address",
1469                      IDC_BOX_SESSION1);
1470             multiedit(&cp,
1471                       "Host &Name (or IP address)",
1472                       IDC_HOSTSTATIC, IDC_HOST, 75,
1473                       "&Port", IDC_PORTSTATIC, IDC_PORT, 25, NULL);
1474             if (backends[3].backend == NULL) {
1475                 /* this is PuTTYtel, so only three protocols available */
1476                 radioline(&cp, "Protocol:", IDC_PROTSTATIC, 3,
1477                           "&Raw", IDC_PROTRAW,
1478                           "&Telnet", IDC_PROTTELNET,
1479                           "Rlog&in", IDC_PROTRLOGIN, NULL);
1480             } else {
1481                 radioline(&cp, "Protocol:", IDC_PROTSTATIC, 4,
1482                           "&Raw", IDC_PROTRAW,
1483                           "&Telnet", IDC_PROTTELNET,
1484                           "Rlog&in", IDC_PROTRLOGIN,
1485 #ifdef FWHACK
1486                           "&SSH/hack",
1487 #else
1488                           "&SSH",
1489 #endif
1490                           IDC_PROTSSH, NULL);
1491             }
1492             endbox(&cp);
1493             beginbox(&cp, "Load, save or delete a stored session",
1494                      IDC_BOX_SESSION2);
1495             sesssaver(&cp, "Sav&ed Sessions",
1496                       IDC_SESSSTATIC, IDC_SESSEDIT, IDC_SESSLIST,
1497                       "&Load", IDC_SESSLOAD,
1498                       "Sa&ve", IDC_SESSSAVE, "&Delete", IDC_SESSDEL, NULL);
1499             endbox(&cp);
1500         }
1501         beginbox(&cp, NULL, IDC_BOX_SESSION3);
1502         radioline(&cp, "Close &window on exit:", IDC_CLOSEEXIT, 4,
1503                   "Always", IDC_COEALWAYS,
1504                   "Never", IDC_COENEVER,
1505                   "Only on clean exit", IDC_COENORMAL, NULL);
1506         endbox(&cp);
1507     }
1508
1509     if (panel == loggingpanelstart) {
1510         /* The Logging panel. Accelerators used: [acgoh] tplsfwe */
1511         struct ctlpos cp;
1512         ctlposinit(&cp, hwnd, 80, 3, 13);
1513         bartitle(&cp, "Options controlling session logging",
1514                  IDC_TITLE_LOGGING);
1515         beginbox(&cp, NULL, IDC_BOX_LOGGING1);
1516         radiobig(&cp,
1517                  "Session logging:", IDC_LSTATSTATIC,
1518                  "Logging &turned off completely", IDC_LSTATOFF,
1519                  "Log &printable output only", IDC_LSTATASCII,
1520                  "&Log all session output", IDC_LSTATRAW,
1521                  "Log &SSH packet data", IDC_LSTATPACKET,
1522                  NULL);
1523         editbutton(&cp, "Log &file name:",
1524                    IDC_LGFSTATIC, IDC_LGFEDIT, "Bro&wse...",
1525                    IDC_LGFBUTTON);
1526         statictext(&cp, "(Log file name can contain &&Y, &&M, &&D for date,"
1527                    " &&T for time, and &&H for host name)", 2, IDC_LGFEXPLAIN);
1528         radiobig(&cp,
1529                  "What to do if the log file already &exists:",
1530                  IDC_LSTATXIST, "Always overwrite it", IDC_LSTATXOVR,
1531                  "Always append to the end of it", IDC_LSTATXAPN,
1532                  "Ask the user every time", IDC_LSTATXASK, NULL);
1533         endbox(&cp);
1534     }
1535
1536     if (panel == terminalpanelstart) {
1537         /* The Terminal panel. Accelerators used: [acgoh] wdren lts p */
1538         struct ctlpos cp;
1539         ctlposinit(&cp, hwnd, 80, 3, 13);
1540         bartitle(&cp, "Options controlling the terminal emulation",
1541                  IDC_TITLE_TERMINAL);
1542         beginbox(&cp, "Set various terminal options", IDC_BOX_TERMINAL1);
1543         checkbox(&cp, "Auto &wrap mode initially on", IDC_WRAPMODE);
1544         checkbox(&cp, "&DEC Origin Mode initially on", IDC_DECOM);
1545         checkbox(&cp, "Implicit C&R in every LF", IDC_LFHASCR);
1546         checkbox(&cp, "Use background colour to &erase screen", IDC_BCE);
1547         checkbox(&cp, "Enable bli&nking text", IDC_BLINKTEXT);
1548         multiedit(&cp,
1549                   "An&swerback to ^E:", IDC_ANSWERBACK,
1550                   IDC_ANSWEREDIT, 100, NULL);
1551         endbox(&cp);
1552
1553         beginbox(&cp, "Line discipline options", IDC_BOX_TERMINAL2);
1554         radioline(&cp, "&Local echo:", IDC_ECHOSTATIC, 3,
1555                   "Auto", IDC_ECHOBACKEND,
1556                   "Force on", IDC_ECHOYES, "Force off", IDC_ECHONO, NULL);
1557         radioline(&cp, "Local line edi&ting:", IDC_EDITSTATIC, 3,
1558                   "Auto", IDC_EDITBACKEND,
1559                   "Force on", IDC_EDITYES, "Force off", IDC_EDITNO, NULL);
1560         endbox(&cp);
1561
1562         beginbox(&cp, "Remote-controlled printing", IDC_BOX_TERMINAL3);
1563         combobox(&cp, "&Printer to send ANSI printer output to:",
1564                  IDC_PRINTERSTATIC, IDC_PRINTER);
1565         endbox(&cp);
1566     }
1567
1568     if (panel == featurespanelstart) {
1569         /* The Features panel. Accelerators used: [acgoh] ukswtbrx */
1570         struct ctlpos cp;
1571         ctlposinit(&cp, hwnd, 80, 3, 13);
1572         bartitle(&cp, "Enabling and disabling advanced terminal features ",
1573                  IDC_TITLE_FEATURES);
1574         beginbox(&cp, NULL, IDC_BOX_FEATURES1);
1575         checkbox(&cp, "Disable application c&ursor keys mode", IDC_NOAPPLICC);
1576         checkbox(&cp, "Disable application &keypad mode", IDC_NOAPPLICK);
1577         checkbox(&cp, "Disable &xterm-style mouse reporting", IDC_NOMOUSEREP);
1578         checkbox(&cp, "Disable remote-controlled terminal re&sizing",
1579                  IDC_NORESIZE);
1580         checkbox(&cp, "Disable s&witching to alternate terminal screen",
1581                  IDC_NOALTSCREEN);
1582         checkbox(&cp, "Disable remote-controlled window &title changing",
1583                  IDC_NOWINTITLE);
1584         checkbox(&cp, "Disable destructive &backspace on server sending ^?",
1585                  IDC_NODBACKSPACE);
1586         checkbox(&cp, "Disable remote-controlled cha&racter set configuration",
1587                  IDC_NOCHARSET);
1588         endbox(&cp);
1589     }
1590
1591     if (panel == bellpanelstart) {
1592         /* The Bell panel. Accelerators used: [acgoh] bdsm wit */
1593         struct ctlpos cp;
1594         ctlposinit(&cp, hwnd, 80, 3, 13);
1595         bartitle(&cp, "Options controlling the terminal bell",
1596                  IDC_TITLE_BELL);
1597         beginbox(&cp, "Set the style of bell", IDC_BOX_BELL1);
1598         radiobig(&cp,
1599                  "Action to happen when a &bell occurs:", IDC_BELLSTATIC,
1600                  "None (bell disabled)", IDC_BELL_DISABLED,
1601                  "Play Windows Default Sound", IDC_BELL_DEFAULT,
1602                  "Play a custom sound file", IDC_BELL_WAVEFILE,
1603                  "Visual bell (flash window)", IDC_BELL_VISUAL, NULL);
1604         editbutton(&cp, "Custom sound file to play as a bell:",
1605                    IDC_BELL_WAVESTATIC, IDC_BELL_WAVEEDIT,
1606                    "Bro&wse...", IDC_BELL_WAVEBROWSE);
1607         radioline(&cp, "Taskbar/caption &indication on bell:",
1608                   IDC_B_IND_STATIC, 3, "Disabled", IDC_B_IND_DISABLED,
1609                   "Flashing", IDC_B_IND_FLASH, "Steady", IDC_B_IND_STEADY,
1610                   NULL);
1611         endbox(&cp);
1612         beginbox(&cp, "Control the bell overload behaviour",
1613                  IDC_BOX_BELL2);
1614         checkbox(&cp, "Bell is temporarily &disabled when over-used",
1615                  IDC_BELLOVL);
1616         staticedit(&cp, "Over-use means this &many bells...",
1617                    IDC_BELLOVLNSTATIC, IDC_BELLOVLN, 20);
1618         staticedit(&cp, "... in &this many seconds",
1619                    IDC_BELLOVLTSTATIC, IDC_BELLOVLT, 20);
1620         statictext(&cp,
1621                    "The bell is re-enabled after a few seconds of silence.",
1622                    1, IDC_BELLOVLEXPLAIN);
1623         staticedit(&cp, "Seconds of &silence required", IDC_BELLOVLSSTATIC,
1624                    IDC_BELLOVLS, 20);
1625         endbox(&cp);
1626     }
1627
1628     if (panel == keyboardpanelstart) {
1629         /* The Keyboard panel. Accelerators used: [acgoh] bef rntd */
1630         struct ctlpos cp;
1631         ctlposinit(&cp, hwnd, 80, 3, 13);
1632         bartitle(&cp, "Options controlling the effects of keys",
1633                  IDC_TITLE_KEYBOARD);
1634         beginbox(&cp, "Change the sequences sent by:", IDC_BOX_KEYBOARD1);
1635         radioline(&cp, "The &Backspace key", IDC_DELSTATIC, 2,
1636                   "Control-H", IDC_DEL008,
1637                   "Control-? (127)", IDC_DEL127, NULL);
1638         radioline(&cp, "The Home and &End keys", IDC_HOMESTATIC, 2,
1639                   "Standard", IDC_HOMETILDE, "rxvt", IDC_HOMERXVT, NULL);
1640         radioline(&cp, "The &Function keys and keypad", IDC_FUNCSTATIC, 3,
1641                   "ESC[n~", IDC_FUNCTILDE,
1642                   "Linux", IDC_FUNCLINUX,
1643                   "Xterm R6", IDC_FUNCXTERM,
1644                   "VT400", IDC_FUNCVT400,
1645                   "VT100+", IDC_FUNCVT100P, "SCO", IDC_FUNCSCO, NULL);
1646         endbox(&cp);
1647         beginbox(&cp, "Application keypad settings:", IDC_BOX_KEYBOARD2);
1648         radioline(&cp, "Initial state of cu&rsor keys:", IDC_CURSTATIC, 2,
1649                   "Normal", IDC_CURNORMAL,
1650                   "Application", IDC_CURAPPLIC, NULL);
1651         radioline(&cp, "Initial state of &numeric keypad:", IDC_KPSTATIC,
1652                   3, "Normal", IDC_KPNORMAL, "Application", IDC_KPAPPLIC,
1653                   "NetHack", IDC_KPNH, NULL);
1654         endbox(&cp);
1655         beginbox(&cp, "Enable extra keyboard features:",
1656                  IDC_BOX_KEYBOARD3);
1657         checkbox(&cp, "AltGr ac&ts as Compose key", IDC_COMPOSEKEY);
1658         checkbox(&cp, "Control-Alt is &different from AltGr",
1659                  IDC_CTRLALTKEYS);
1660         endbox(&cp);
1661     }
1662
1663     if (panel == windowpanelstart) {
1664         /* The Window panel. Accelerators used: [acgoh] rmz sdikp */
1665         struct ctlpos cp;
1666         ctlposinit(&cp, hwnd, 80, 3, 13);
1667         bartitle(&cp, "Options controlling PuTTY's window",
1668                  IDC_TITLE_WINDOW);
1669         beginbox(&cp, "Set the size of the window", IDC_BOX_WINDOW1);
1670         multiedit(&cp,
1671                   "&Rows", IDC_ROWSSTATIC, IDC_ROWSEDIT, 50,
1672                   "Colu&mns", IDC_COLSSTATIC, IDC_COLSEDIT, 50, NULL);
1673         radiobig(&cp, "When window is resi&zed:", IDC_RESIZESTATIC,
1674                  "Change the number of rows and columns", IDC_RESIZETERM,
1675                  "Change the size of the font", IDC_RESIZEFONT,
1676                  "Change font size only when maximised", IDC_RESIZEEITHER,
1677                  "Forbid resizing completely", IDC_RESIZENONE, NULL);
1678         endbox(&cp);
1679         beginbox(&cp, "Control the scrollback in the window",
1680                  IDC_BOX_WINDOW2);
1681         staticedit(&cp, "Lines of &scrollback",
1682                    IDC_SAVESTATIC, IDC_SAVEEDIT, 50);
1683         checkbox(&cp, "&Display scrollbar", IDC_SCROLLBAR);
1684         checkbox(&cp, "D&isplay scrollbar in full screen mode", IDC_SCROLLBARFULLSCREEN);
1685         checkbox(&cp, "Reset scrollback on &keypress", IDC_SCROLLKEY);
1686         checkbox(&cp, "Reset scrollback on dis&play activity",
1687                  IDC_SCROLLDISP);
1688         endbox(&cp);
1689     }
1690
1691     if (panel == appearancepanelstart) {
1692         /* The Appearance panel. Accelerators used: [acgoh] luvb n ti p s */
1693         struct ctlpos cp;
1694         ctlposinit(&cp, hwnd, 80, 3, 13);
1695         bartitle(&cp, "Configure the appearance of PuTTY's window",
1696                  IDC_TITLE_APPEARANCE);
1697         beginbox(&cp, "Adjust the use of the cursor", IDC_BOX_APPEARANCE1);
1698         radioline(&cp, "Cursor appearance:", IDC_CURSORSTATIC, 3,
1699                   "B&lock", IDC_CURBLOCK,
1700                   "&Underline", IDC_CURUNDER,
1701                   "&Vertical line", IDC_CURVERT, NULL);
1702         checkbox(&cp, "Cursor &blinks", IDC_BLINKCUR);
1703         endbox(&cp);
1704         beginbox(&cp, "Set the font used in the terminal window",
1705                  IDC_BOX_APPEARANCE2);
1706         staticbtn(&cp, "", IDC_FONTSTATIC, "Cha&nge...", IDC_CHOOSEFONT);
1707         endbox(&cp);
1708         beginbox(&cp, "Adjust the use of the window title",
1709                  IDC_BOX_APPEARANCE3);
1710         multiedit(&cp,
1711                   "Window &title:", IDC_WINTITLE, IDC_WINEDIT, 100, NULL);
1712         checkbox(&cp, "Avoid ever using &icon title", IDC_WINNAME);
1713         endbox(&cp);
1714         beginbox(&cp, "Adjust the use of the mouse pointer",
1715                  IDC_BOX_APPEARANCE4);
1716         checkbox(&cp, "Hide mouse &pointer when typing in window",
1717                  IDC_HIDEMOUSE);
1718         endbox(&cp);
1719         beginbox(&cp, "Adjust the window border", IDC_BOX_APPEARANCE5);
1720         checkbox(&cp, "&Sunken-edge border (slightly thicker)",
1721                  IDC_SUNKENEDGE);
1722         staticedit(&cp, "Gap between text and window edge",
1723                    IDC_WINBSTATIC, IDC_WINBEDIT, 20);
1724         endbox(&cp);
1725     }
1726
1727     if (panel == behaviourpanelstart) {
1728         /* The Behaviour panel. Accelerators used: [acgoh] w4yltf */
1729         struct ctlpos cp;
1730         ctlposinit(&cp, hwnd, 80, 3, 13);
1731         bartitle(&cp, "Configure the behaviour of PuTTY's window",
1732                  IDC_TITLE_WINDOW);
1733         beginbox(&cp, NULL, IDC_BOX_BEHAVIOUR1);
1734         checkbox(&cp, "&Warn before closing window", IDC_CLOSEWARN);
1735         checkbox(&cp, "Window closes on ALT-F&4", IDC_ALTF4);
1736         checkbox(&cp, "S&ystem menu appears on ALT-Space", IDC_ALTSPACE);
1737         checkbox(&cp, "System menu appears on A&LT alone", IDC_ALTONLY);
1738         checkbox(&cp, "Ensure window is always on &top", IDC_ALWAYSONTOP);
1739         checkbox(&cp, "&Full screen on Alt-Enter", IDC_FULLSCREENONALTENTER);
1740         endbox(&cp);
1741     }
1742
1743     if (panel == translationpanelstart) {
1744         /* The Translation panel. Accelerators used: [acgoh] rxbepus */
1745         struct ctlpos cp;
1746         ctlposinit(&cp, hwnd, 80, 3, 13);
1747         bartitle(&cp, "Options controlling character set translation",
1748                  IDC_TITLE_TRANSLATION);
1749         beginbox(&cp, "Character set translation on received data",
1750                  IDC_BOX_TRANSLATION1);
1751         combobox(&cp, "&Received data assumed to be in which character set:",
1752                  IDC_CODEPAGESTATIC, IDC_CODEPAGE);
1753         endbox(&cp);
1754         beginbox(&cp, "Enable character set translation on input data",
1755                  IDC_BOX_TRANSLATION2);
1756         checkbox(&cp, "Cap&s Lock acts as Cyrillic switch",
1757                  IDC_CAPSLOCKCYR);
1758         endbox(&cp);
1759         beginbox(&cp, "Adjust how PuTTY displays line drawing characters",
1760                  IDC_BOX_TRANSLATION3);
1761         radiobig(&cp,
1762                  "Handling of line drawing characters:", IDC_VTSTATIC,
1763                  "Font has &XWindows encoding", IDC_VTXWINDOWS,
1764                  "Use font in &both ANSI and OEM modes", IDC_VTOEMANSI,
1765                  "Use font in O&EM mode only", IDC_VTOEMONLY,
1766                  "&Poor man's line drawing (" "+" ", " "-" " and " "|" ")",
1767                  IDC_VTPOORMAN, "&Unicode mode", IDC_VTUNICODE, NULL);
1768         endbox(&cp);
1769     }
1770
1771     if (panel == selectionpanelstart) {
1772         /* The Selection panel. Accelerators used: [acgoh] df wxp est nr */
1773         struct ctlpos cp;
1774         ctlposinit(&cp, hwnd, 80, 3, 13);
1775         bartitle(&cp, "Options controlling copy and paste",
1776                  IDC_TITLE_SELECTION);
1777         beginbox(&cp, "Translation of pasted characters",
1778                  IDC_BOX_SELECTION1);
1779         checkbox(&cp,
1780                  "&Don't translate line drawing chars into +, - and |",
1781                  IDC_RAWCNP);
1782         checkbox(&cp,
1783                  "Paste to clipboard in RT&F as well as plain text",
1784                  IDC_RTFPASTE);
1785         endbox(&cp);
1786         beginbox(&cp, "Control which mouse button does which thing",
1787                  IDC_BOX_SELECTION2);
1788         radiobig(&cp, "Action of mouse buttons:", IDC_MBSTATIC,
1789                  "&Windows (Right pastes, Middle extends)", IDC_MBWINDOWS,
1790                  "&xterm (Right extends, Middle pastes)", IDC_MBXTERM,
1791                  NULL);
1792         checkbox(&cp,
1793                  "Shift overrides a&pplication's use of mouse",
1794                  IDC_MOUSEOVERRIDE);
1795         radioline(&cp,
1796                   "Default selection mode (Alt+drag does the other one):",
1797                   IDC_SELTYPESTATIC, 2,
1798                   "&Normal", IDC_SELTYPELEX,
1799                   "&Rectangular block", IDC_SELTYPERECT, NULL);
1800         endbox(&cp);
1801         beginbox(&cp, "Control the select-one-word-at-a-time mode",
1802                  IDC_BOX_SELECTION3);
1803         charclass(&cp, "Charact&er classes:", IDC_CCSTATIC, IDC_CCLIST,
1804                   "&Set", IDC_CCSET, IDC_CCEDIT,
1805                   "&to class", IDC_CCSTATIC2);
1806         endbox(&cp);
1807     }
1808
1809     if (panel == colourspanelstart) {
1810         /* The Colours panel. Accelerators used: [acgoh] blum */
1811         struct ctlpos cp;
1812         ctlposinit(&cp, hwnd, 80, 3, 13);
1813         bartitle(&cp, "Options controlling use of colours",
1814                  IDC_TITLE_COLOURS);
1815         beginbox(&cp, "General options for colour usage",
1816                  IDC_BOX_COLOURS1);
1817         checkbox(&cp, "&Bolded text is a different colour",
1818                  IDC_BOLDCOLOUR);
1819         checkbox(&cp, "Attempt to use &logical palettes", IDC_PALETTE);
1820         endbox(&cp);
1821         beginbox(&cp, "Adjust the precise colours PuTTY displays",
1822                  IDC_BOX_COLOURS2);
1823         colouredit(&cp, "Select a colo&ur and then click to modify it:",
1824                    IDC_COLOURSTATIC, IDC_COLOURLIST,
1825                    "&Modify...", IDC_CHANGE,
1826                    "Red:", IDC_RSTATIC, IDC_RVALUE,
1827                    "Green:", IDC_GSTATIC, IDC_GVALUE,
1828                    "Blue:", IDC_BSTATIC, IDC_BVALUE, NULL);
1829         endbox(&cp);
1830     }
1831
1832     if (panel == connectionpanelstart) {
1833         /* The Connection panel. Accelerators used: [acgoh] tukn */
1834         struct ctlpos cp;
1835         ctlposinit(&cp, hwnd, 80, 3, 13);
1836         bartitle(&cp, "Options controlling the connection",
1837                  IDC_TITLE_CONNECTION);
1838         if (dlgtype == 0) {
1839             beginbox(&cp, "Data to send to the server",
1840                      IDC_BOX_CONNECTION1);
1841             staticedit(&cp, "Terminal-&type string", IDC_TTSTATIC,
1842                        IDC_TTEDIT, 50);
1843             staticedit(&cp, "Auto-login &username", IDC_LOGSTATIC,
1844                        IDC_LOGEDIT, 50);
1845             endbox(&cp);
1846         } else {
1847             beginbox(&cp, "Adjust telnet session.", IDC_BOX_CONNECTION1);
1848             checkbox(&cp, "Keyboard sends telnet Backspace and Interrupt",
1849                      IDC_TELNETKEY);
1850             checkbox(&cp, "Return key sends telnet New Line instead of ^M",
1851                      IDC_TELNETRET);
1852             endbox(&cp);
1853         }
1854         beginbox(&cp, "Sending of null packets to keep session active",
1855                  IDC_BOX_CONNECTION2);
1856         staticedit(&cp, "Seconds between &keepalives (0 to turn off)",
1857                    IDC_PINGSTATIC, IDC_PINGEDIT, 20);
1858         endbox(&cp);
1859         if (dlgtype == 0) {
1860             beginbox(&cp, "Low-level TCP connection options",
1861                      IDC_BOX_CONNECTION3);
1862             checkbox(&cp, "Disable &Nagle's algorithm (TCP_NODELAY option)",
1863                      IDC_NODELAY);
1864             endbox(&cp);
1865         }
1866     }
1867
1868     if (panel == proxypanelstart) {
1869         /* The Proxy panel. Accelerators used: [acgoh] ntslypeuwmvxd */
1870         struct ctlpos cp;
1871         ctlposinit(&cp, hwnd, 80, 3, 13);
1872         if (dlgtype == 0) {
1873             bartitle(&cp, "Options controlling proxy usage",
1874                      IDC_TITLE_PROXY);
1875             beginbox(&cp, "Proxy basics", IDC_BOX_PROXY1);
1876             radioline(&cp, "Proxy type:", IDC_PROXYTYPESTATIC, 4,
1877                       "&None", IDC_PROXYTYPENONE,
1878                       "H&TTP", IDC_PROXYTYPEHTTP,
1879                       "&SOCKS", IDC_PROXYTYPESOCKS,
1880                       "Te&lnet", IDC_PROXYTYPETELNET, NULL);
1881             multiedit(&cp,
1882                       "Prox&y Host", IDC_PROXYHOSTSTATIC, IDC_PROXYHOSTEDIT, 80,
1883                       "&Port", IDC_PROXYPORTSTATIC, IDC_PROXYPORTEDIT, 20, NULL);
1884             multiedit(&cp,
1885                       "&Exclude Hosts/IPs", IDC_PROXYEXCLUDESTATIC,
1886                       IDC_PROXYEXCLUDEEDIT, 100, NULL);
1887             checkbox(&cp, "Consider pro&xying local host connections",
1888                      IDC_PROXYLOCALHOST);
1889             radioline(&cp, "Do &DNS name lookup at proxy end:",
1890                       IDC_PROXYDNSSTATIC, 3,
1891                       "No", IDC_PROXYDNSNO,
1892                       "Auto", IDC_PROXYDNSAUTO,
1893                       "Yes", IDC_PROXYDNSYES, NULL);
1894             staticedit(&cp, "&Username", IDC_PROXYUSERSTATIC,
1895                        IDC_PROXYUSEREDIT, 60);
1896             staticpassedit(&cp, "Pass&word", IDC_PROXYPASSSTATIC,
1897                            IDC_PROXYPASSEDIT, 60);
1898             endbox(&cp);
1899             beginbox(&cp, "Misc. proxy settings", IDC_BOX_PROXY2);
1900             multiedit(&cp,
1901                       "Telnet co&mmand", IDC_PROXYTELNETCMDSTATIC,
1902                       IDC_PROXYTELNETCMDEDIT, 100, NULL);
1903             radioline(&cp, "SOCKS &Version", IDC_PROXYSOCKSVERSTATIC,
1904                       2, "Version 5", IDC_PROXYSOCKSVER5, "Version 4",
1905                       IDC_PROXYSOCKSVER4, NULL);
1906             endbox(&cp);
1907         }
1908     }
1909
1910     if (panel == telnetpanelstart) {
1911         /* The Telnet panel. Accelerators used: [acgoh] svldr bftk */
1912         struct ctlpos cp;
1913         ctlposinit(&cp, hwnd, 80, 3, 13);
1914         if (dlgtype == 0) {
1915             bartitle(&cp, "Options controlling Telnet connections",
1916                      IDC_TITLE_TELNET);
1917             beginbox(&cp, "Data to send to the server", IDC_BOX_TELNET1);
1918             staticedit(&cp, "Terminal-&speed string", IDC_TSSTATIC,
1919                        IDC_TSEDIT, 50);
1920             envsetter(&cp, "Environment variables:", IDC_ENVSTATIC,
1921                       "&Variable", IDC_VARSTATIC, IDC_VAREDIT, "Va&lue",
1922                       IDC_VALSTATIC, IDC_VALEDIT, IDC_ENVLIST, "A&dd",
1923                       IDC_ENVADD, "&Remove", IDC_ENVREMOVE);
1924             endbox(&cp);
1925             beginbox(&cp, "Telnet protocol adjustments", IDC_BOX_TELNET2);
1926             radioline(&cp, "Handling of OLD_ENVIRON ambiguity:",
1927                       IDC_EMSTATIC, 2, "&BSD (commonplace)", IDC_EMBSD,
1928                       "R&FC 1408 (unusual)", IDC_EMRFC, NULL);
1929             radioline(&cp, "&Telnet negotiation mode:", IDC_ACTSTATIC, 2,
1930                       "Passive", IDC_TPASSIVE, "Active",
1931                       IDC_TACTIVE, NULL);
1932             checkbox(&cp, "&Keyboard sends telnet Backspace and Interrupt",
1933                      IDC_TELNETKEY);
1934             checkbox(&cp, "Return key sends telnet New Line instead of ^M",
1935                      IDC_TELNETRET);
1936             endbox(&cp);
1937         }
1938     }
1939
1940     if (panel == rloginpanelstart) {
1941         /* The Rlogin panel. Accelerators used: [acgoh] sl */
1942         struct ctlpos cp;
1943         ctlposinit(&cp, hwnd, 80, 3, 13);
1944         if (dlgtype == 0) {
1945             bartitle(&cp, "Options controlling Rlogin connections",
1946                      IDC_TITLE_RLOGIN);
1947             beginbox(&cp, "Data to send to the server", IDC_BOX_RLOGIN1);
1948             staticedit(&cp, "Terminal-&speed string", IDC_R_TSSTATIC,
1949                        IDC_R_TSEDIT, 50);
1950             staticedit(&cp, "&Local username:", IDC_RLLUSERSTATIC,
1951                        IDC_RLLUSEREDIT, 50);
1952             endbox(&cp);
1953         }
1954     }
1955
1956     if (panel == sshpanelstart) {
1957         /* The SSH panel. Accelerators used: [acgoh] r pe12ni sd */
1958         struct ctlpos cp;
1959         ctlposinit(&cp, hwnd, 80, 3, 13);
1960         if (dlgtype == 0) {
1961             bartitle(&cp, "Options controlling SSH connections",
1962                      IDC_TITLE_SSH);
1963             beginbox(&cp, "Data to send to the server", IDC_BOX_SSH1);
1964             multiedit(&cp,
1965                       "&Remote command:", IDC_CMDSTATIC, IDC_CMDEDIT, 100,
1966                       NULL);
1967             endbox(&cp);
1968             beginbox(&cp, "Protocol options", IDC_BOX_SSH2);
1969             checkbox(&cp, "Don't allocate a &pseudo-terminal", IDC_NOPTY);
1970             checkbox(&cp, "Enable compr&ession", IDC_COMPRESS);
1971             radioline(&cp, "Preferred SSH protocol version:",
1972                       IDC_SSHPROTSTATIC, 4,
1973                       "1 on&ly", IDC_SSHPROT1ONLY,
1974                       "&1", IDC_SSHPROT1, "&2", IDC_SSHPROT2,
1975                       "2 o&nly", IDC_SSHPROT2ONLY, NULL);
1976             endbox(&cp);
1977             beginbox(&cp, "Encryption options", IDC_BOX_SSH3);
1978             prefslist(&cipherlist, &cp, "Encryption cipher &selection policy:",
1979                       IDC_CIPHERSTATIC2, IDC_CIPHERLIST, IDC_CIPHERUP,
1980                       IDC_CIPHERDN);
1981             checkbox(&cp, "Enable non-standard use of single-&DES in SSH 2",
1982                      IDC_SSH2DES);
1983             endbox(&cp);
1984         }
1985     }
1986
1987     if (panel == sshauthpanelstart) {
1988         /* The SSH authentication panel. Accelerators used: [acgoh] m fkiuw */
1989         struct ctlpos cp;
1990         ctlposinit(&cp, hwnd, 80, 3, 13);
1991         if (dlgtype == 0) {
1992             bartitle(&cp, "Options controlling SSH authentication",
1993                      IDC_TITLE_SSHAUTH);
1994             beginbox(&cp, "Authentication methods",
1995                      IDC_BOX_SSHAUTH1);
1996             checkbox(&cp, "Atte&mpt TIS or CryptoCard authentication (SSH1)",
1997                      IDC_AUTHTIS);
1998             checkbox(&cp, "Attempt \"keyboard-&interactive\" authentication"
1999                      " (SSH2)", IDC_AUTHKI);
2000             endbox(&cp);
2001             beginbox(&cp, "Authentication parameters",
2002                      IDC_BOX_SSHAUTH2);
2003             checkbox(&cp, "Allow agent &forwarding", IDC_AGENTFWD);
2004             checkbox(&cp, "Allow attempted changes of &username in SSH2",
2005                      IDC_CHANGEUSER);
2006             editbutton(&cp, "Private &key file for authentication:",
2007                        IDC_PKSTATIC, IDC_PKEDIT, "Bro&wse...",
2008                        IDC_PKBUTTON);
2009             endbox(&cp);
2010         }
2011     }
2012
2013     if (panel == sshbugspanelstart) {
2014         /* The SSH bugs panel. Accelerators used: [acgoh] isrmep */
2015         struct ctlpos cp;
2016         ctlposinit(&cp, hwnd, 80, 3, 13);
2017         if (dlgtype == 0) {
2018             bartitle(&cp, "Workarounds for SSH server bugs",
2019                      IDC_TITLE_SSHBUGS);
2020             beginbox(&cp, "Detection of known bugs in SSH servers",
2021                      IDC_BOX_SSHBUGS1);
2022             staticddl(&cp, "Chokes on SSH1 &ignore messages",
2023                       IDC_BUGS_IGNORE1, IDC_BUGD_IGNORE1, 20);
2024             staticddl(&cp, "Refuses all SSH1 pa&ssword camouflage",
2025                       IDC_BUGS_PLAINPW1, IDC_BUGD_PLAINPW1, 20);
2026             staticddl(&cp, "Chokes on SSH1 &RSA authentication",
2027                       IDC_BUGS_RSA1, IDC_BUGD_RSA1, 20);
2028             staticddl(&cp, "Miscomputes SSH2 H&MAC keys",
2029                       IDC_BUGS_HMAC2, IDC_BUGD_HMAC2, 20);
2030             staticddl(&cp, "Miscomputes SSH2 &encryption keys",
2031                       IDC_BUGS_DERIVEKEY2, IDC_BUGD_DERIVEKEY2, 20);
2032             staticddl(&cp, "Requires &padding on SSH2 RSA signatures",
2033                       IDC_BUGS_RSAPAD2, IDC_BUGD_RSAPAD2, 20);
2034             staticddl(&cp, "Chokes on &Diffie-Hellman group exchange",
2035                       IDC_BUGS_DHGEX2, IDC_BUGD_DHGEX2, 20);
2036             endbox(&cp);
2037         }
2038     }
2039
2040     if (panel == tunnelspanelstart) {
2041         /* The Tunnels panel. Accelerators used: [acgoh] deilmrstxp */
2042         struct ctlpos cp;
2043         ctlposinit(&cp, hwnd, 80, 3, 13);
2044         if (dlgtype == 0) {
2045             bartitle(&cp, "Options controlling SSH tunnelling",
2046                      IDC_TITLE_TUNNELS);
2047             beginbox(&cp, "X11 forwarding", IDC_BOX_TUNNELS1);
2048             checkbox(&cp, "&Enable X11 forwarding", IDC_X11_FORWARD);
2049             multiedit(&cp, "&X display location", IDC_X11_DISPSTATIC,
2050                       IDC_X11_DISPLAY, 50, NULL);
2051             endbox(&cp);
2052             beginbox(&cp, "Port forwarding", IDC_BOX_TUNNELS2);
2053             checkbox(&cp, "Local ports accept connections from o&ther hosts",
2054                      IDC_LPORT_ALL);
2055             checkbox(&cp, "Remote &ports do the same (SSH v2 only)",
2056                      IDC_RPORT_ALL);
2057             staticbtn(&cp, "Forwarded ports:", IDC_PFWDSTATIC,
2058                       "&Remove", IDC_PFWDREMOVE);
2059             fwdsetter(&cp, IDC_PFWDLIST,
2060                       "Add new forwarded port:", IDC_PFWDSTATIC2,
2061                       "&Source port", IDC_SPORTSTATIC, IDC_SPORTEDIT,
2062                       "Dest&ination", IDC_DPORTSTATIC, IDC_DPORTEDIT,
2063                       "A&dd", IDC_PFWDADD,
2064                       "&Local", IDC_PFWDLOCAL,
2065                       "Re&mote", IDC_PFWDREMOTE);
2066             endbox(&cp);
2067
2068         }
2069     }
2070 }
2071
2072 /* 
2073  * Helper function to load the session selected in SESSLIST
2074  * if any, as this is done in more than one place in
2075  * GenericMainDlgProc(). 0 => failure.
2076  */
2077 static int load_selected_session(HWND hwnd)
2078 {
2079     int n = SendDlgItemMessage(hwnd, IDC_SESSLIST,
2080                                LB_GETCURSEL, 0, 0);
2081     int isdef;
2082     if (n == LB_ERR) {
2083         MessageBeep(0);
2084         return 0;
2085     }
2086     isdef = !strcmp(sesslist.sessions[n], "Default Settings");
2087     load_settings(sesslist.sessions[n], !isdef, &cfg);
2088     init_dlg_ctrls(hwnd, TRUE);
2089     if (!isdef)
2090         SetDlgItemText(hwnd, IDC_SESSEDIT, sesslist.sessions[n]);
2091     else
2092         SetDlgItemText(hwnd, IDC_SESSEDIT, "");
2093     /* Restore the selection, which will have been clobbered by
2094      * SESSEDIT handling. */
2095     SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL, n, 0);
2096     return 1;
2097 }
2098
2099 /*
2100  * This function is the configuration box.
2101  */
2102 static int GenericMainDlgProc(HWND hwnd, UINT msg,
2103                               WPARAM wParam, LPARAM lParam, int dlgtype)
2104 {
2105     HWND hw, treeview;
2106     struct treeview_faff tvfaff;
2107     HTREEITEM hsession;
2108     OPENFILENAME of;
2109     char filename[sizeof(cfg.keyfile)];
2110     CHOOSEFONT cf;
2111     LOGFONT lf;
2112     char fontstatic[256];
2113     char portname[32];
2114     struct servent *service;
2115     int i;
2116     static UINT draglistmsg = WM_NULL;
2117
2118     switch (msg) {
2119       case WM_INITDIALOG:
2120         readytogo = 0;
2121         SetWindowLong(hwnd, GWL_USERDATA, 0);
2122         if (help_path)
2123             SetWindowLong(hwnd, GWL_EXSTYLE,
2124                           GetWindowLong(hwnd, GWL_EXSTYLE) | WS_EX_CONTEXTHELP);
2125         else {
2126             HWND item = GetDlgItem(hwnd, IDC_HELPBTN);
2127             if (item)
2128                 DestroyWindow(item);
2129         }
2130         requested_help = FALSE;
2131         SendMessage(hwnd, WM_SETICON, (WPARAM) ICON_BIG,
2132                     (LPARAM) LoadIcon(hinst, MAKEINTRESOURCE(IDI_CFGICON)));
2133         /*
2134          * Centre the window.
2135          */
2136         {                              /* centre the window */
2137             RECT rs, rd;
2138
2139             hw = GetDesktopWindow();
2140             if (GetWindowRect(hw, &rs) && GetWindowRect(hwnd, &rd))
2141                 MoveWindow(hwnd,
2142                            (rs.right + rs.left + rd.left - rd.right) / 2,
2143                            (rs.bottom + rs.top + rd.top - rd.bottom) / 2,
2144                            rd.right - rd.left, rd.bottom - rd.top, TRUE);
2145         }
2146
2147         /*
2148          * Create the tree view.
2149          */
2150         {
2151             RECT r;
2152             WPARAM font;
2153             HWND tvstatic;
2154
2155             r.left = 3;
2156             r.right = r.left + 75;
2157             r.top = 3;
2158             r.bottom = r.top + 10;
2159             MapDialogRect(hwnd, &r);
2160             tvstatic = CreateWindowEx(0, "STATIC", "Cate&gory:",
2161                                       WS_CHILD | WS_VISIBLE,
2162                                       r.left, r.top,
2163                                       r.right - r.left, r.bottom - r.top,
2164                                       hwnd, (HMENU) IDCX_TVSTATIC, hinst,
2165                                       NULL);
2166             font = SendMessage(hwnd, WM_GETFONT, 0, 0);
2167             SendMessage(tvstatic, WM_SETFONT, font, MAKELPARAM(TRUE, 0));
2168
2169             r.left = 3;
2170             r.right = r.left + 75;
2171             r.top = 13;
2172             r.bottom = r.top + 219;
2173             MapDialogRect(hwnd, &r);
2174             treeview = CreateWindowEx(WS_EX_CLIENTEDGE, WC_TREEVIEW, "",
2175                                       WS_CHILD | WS_VISIBLE |
2176                                       WS_TABSTOP | TVS_HASLINES |
2177                                       TVS_DISABLEDRAGDROP | TVS_HASBUTTONS
2178                                       | TVS_LINESATROOT |
2179                                       TVS_SHOWSELALWAYS, r.left, r.top,
2180                                       r.right - r.left, r.bottom - r.top,
2181                                       hwnd, (HMENU) IDCX_TREEVIEW, hinst,
2182                                       NULL);
2183             font = SendMessage(hwnd, WM_GETFONT, 0, 0);
2184             SendMessage(treeview, WM_SETFONT, font, MAKELPARAM(TRUE, 0));
2185             tvfaff.treeview = treeview;
2186             memset(tvfaff.lastat, 0, sizeof(tvfaff.lastat));
2187         }
2188
2189         /*
2190          * Set up the tree view contents.
2191          */
2192         hsession = treeview_insert(&tvfaff, 0, "Session");
2193         treeview_insert(&tvfaff, 1, "Logging");
2194         treeview_insert(&tvfaff, 0, "Terminal");
2195         treeview_insert(&tvfaff, 1, "Keyboard");
2196         treeview_insert(&tvfaff, 1, "Bell");
2197         treeview_insert(&tvfaff, 1, "Features");
2198         treeview_insert(&tvfaff, 0, "Window");
2199         treeview_insert(&tvfaff, 1, "Appearance");
2200         treeview_insert(&tvfaff, 1, "Behaviour");
2201         treeview_insert(&tvfaff, 1, "Translation");
2202         treeview_insert(&tvfaff, 1, "Selection");
2203         treeview_insert(&tvfaff, 1, "Colours");
2204         treeview_insert(&tvfaff, 0, "Connection");
2205         if (dlgtype == 0) {
2206             treeview_insert(&tvfaff, 1, "Proxy");
2207             treeview_insert(&tvfaff, 1, "Telnet");
2208             treeview_insert(&tvfaff, 1, "Rlogin");
2209             if (backends[3].backend != NULL) {
2210                 treeview_insert(&tvfaff, 1, "SSH");
2211                 /* XXX long name is ugly */
2212                 /* XXX make it closed by default? */
2213                 treeview_insert(&tvfaff, 2, "Auth");
2214                 treeview_insert(&tvfaff, 2, "Tunnels");
2215                 treeview_insert(&tvfaff, 2, "Bugs");
2216             }
2217         }
2218
2219         /*
2220          * Put the treeview selection on to the Session panel. This
2221          * should also cause creation of the relevant controls.
2222          */
2223         TreeView_SelectItem(treeview, hsession);
2224
2225         /*
2226          * Set focus into the first available control.
2227          */
2228         {
2229             HWND ctl;
2230             ctl = GetDlgItem(hwnd, IDC_HOST);
2231             if (!ctl)
2232                 ctl = GetDlgItem(hwnd, IDC_CLOSEEXIT);
2233             SetFocus(ctl);
2234         }
2235
2236         SetWindowLong(hwnd, GWL_USERDATA, 1);
2237         sesslist_has_focus = 0;
2238         return 0;
2239       case WM_LBUTTONUP:
2240         /*
2241          * Button release should trigger WM_OK if there was a
2242          * previous double click on the session list.
2243          */
2244         ReleaseCapture();
2245         if (readytogo)
2246             SendMessage(hwnd, WM_COMMAND, IDOK, 0);
2247         break;
2248       case WM_NOTIFY:
2249         if (LOWORD(wParam) == IDCX_TREEVIEW &&
2250             ((LPNMHDR) lParam)->code == TVN_SELCHANGED) {
2251             HTREEITEM i =
2252                 TreeView_GetSelection(((LPNMHDR) lParam)->hwndFrom);
2253             TVITEM item;
2254             int j;
2255             char buffer[64];
2256  
2257             SendMessage (hwnd, WM_SETREDRAW, FALSE, 0);
2258  
2259             item.hItem = i;
2260             item.pszText = buffer;
2261             item.cchTextMax = sizeof(buffer);
2262             item.mask = TVIF_TEXT;
2263             TreeView_GetItem(((LPNMHDR) lParam)->hwndFrom, &item);
2264             for (j = controlstartvalue; j < controlendvalue; j++) {
2265                 HWND item = GetDlgItem(hwnd, j);
2266                 if (item)
2267                     DestroyWindow(item);
2268             }
2269             if (!strcmp(buffer, "Session"))
2270                 create_controls(hwnd, dlgtype, sessionpanelstart);
2271             if (!strcmp(buffer, "Logging"))
2272                 create_controls(hwnd, dlgtype, loggingpanelstart);
2273             if (!strcmp(buffer, "Keyboard"))
2274                 create_controls(hwnd, dlgtype, keyboardpanelstart);
2275             if (!strcmp(buffer, "Terminal"))
2276                 create_controls(hwnd, dlgtype, terminalpanelstart);
2277             if (!strcmp(buffer, "Bell"))
2278                 create_controls(hwnd, dlgtype, bellpanelstart);
2279             if (!strcmp(buffer, "Features"))
2280                 create_controls(hwnd, dlgtype, featurespanelstart);
2281             if (!strcmp(buffer, "Window"))
2282                 create_controls(hwnd, dlgtype, windowpanelstart);
2283             if (!strcmp(buffer, "Appearance"))
2284                 create_controls(hwnd, dlgtype, appearancepanelstart);
2285             if (!strcmp(buffer, "Behaviour"))
2286                 create_controls(hwnd, dlgtype, behaviourpanelstart);
2287             if (!strcmp(buffer, "Tunnels"))
2288                 create_controls(hwnd, dlgtype, tunnelspanelstart);
2289             if (!strcmp(buffer, "Connection"))
2290                 create_controls(hwnd, dlgtype, connectionpanelstart);
2291             if (!strcmp(buffer, "Proxy"))
2292                 create_controls(hwnd, dlgtype, proxypanelstart);
2293             if (!strcmp(buffer, "Telnet"))
2294                 create_controls(hwnd, dlgtype, telnetpanelstart);
2295             if (!strcmp(buffer, "Rlogin"))
2296                 create_controls(hwnd, dlgtype, rloginpanelstart);
2297             if (!strcmp(buffer, "SSH"))
2298                 create_controls(hwnd, dlgtype, sshpanelstart);
2299             if (!strcmp(buffer, "Auth"))
2300                 create_controls(hwnd, dlgtype, sshauthpanelstart);
2301             if (!strcmp(buffer, "Bugs"))
2302                 create_controls(hwnd, dlgtype, sshbugspanelstart);
2303             if (!strcmp(buffer, "Selection"))
2304                 create_controls(hwnd, dlgtype, selectionpanelstart);
2305             if (!strcmp(buffer, "Colours"))
2306                 create_controls(hwnd, dlgtype, colourspanelstart);
2307             if (!strcmp(buffer, "Translation"))
2308                 create_controls(hwnd, dlgtype, translationpanelstart);
2309
2310             init_dlg_ctrls(hwnd, FALSE);
2311  
2312             SendMessage (hwnd, WM_SETREDRAW, TRUE, 0);
2313             InvalidateRect (hwnd, NULL, TRUE);
2314
2315             SetFocus(((LPNMHDR) lParam)->hwndFrom);     /* ensure focus stays */
2316             return 0;
2317         }
2318         break;
2319       case WM_COMMAND:
2320         /*
2321          * Only process WM_COMMAND once the dialog is fully formed.
2322          */
2323         if (GetWindowLong(hwnd, GWL_USERDATA) == 1)
2324             switch (LOWORD(wParam)) {
2325               case IDOK:
2326                 /* Behaviour of the "Open" button is different if the
2327                  * session list has focus, *unless* the user just
2328                  * double-clicked... */
2329                 if (sesslist_has_focus && !readytogo) {
2330                     if (!load_selected_session(hwnd)) {
2331                         MessageBeep(0);
2332                         return 0;
2333                     }
2334                 }
2335                 /* If at this point we have a valid session, go! */
2336                 if (*cfg.host) {
2337                     if (requested_help) {
2338                         WinHelp(hwnd, help_path, HELP_QUIT, 0);
2339                         requested_help = FALSE;
2340                     }
2341                     EndDialog(hwnd, 1);
2342                 } else
2343                     MessageBeep(0);
2344                 return 0;
2345               case IDC_HELPBTN:
2346                 if (HIWORD(wParam) == BN_CLICKED ||
2347                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2348                     if (help_path) {
2349                         WinHelp(hwnd, help_path,
2350                                 help_has_contents ? HELP_FINDER : HELP_CONTENTS,
2351                                 0);
2352                         requested_help = TRUE;
2353                     }
2354                 }
2355                 break;
2356               case IDCANCEL:
2357                 if (requested_help) {
2358                     WinHelp(hwnd, help_path, HELP_QUIT, 0);
2359                     requested_help = FALSE;
2360                 }
2361                 EndDialog(hwnd, 0);
2362                 return 0;
2363               case IDC_PROTTELNET:
2364               case IDC_PROTRLOGIN:
2365               case IDC_PROTSSH:
2366               case IDC_PROTRAW:
2367                 if (HIWORD(wParam) == BN_CLICKED ||
2368                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2369                     int i = IsDlgButtonChecked(hwnd, IDC_PROTSSH);
2370                     int j = IsDlgButtonChecked(hwnd, IDC_PROTTELNET);
2371                     int k = IsDlgButtonChecked(hwnd, IDC_PROTRLOGIN);
2372                     cfg.protocol =
2373                         i ? PROT_SSH : j ? PROT_TELNET : k ? PROT_RLOGIN :
2374                         PROT_RAW;
2375                     /*
2376                      * When switching using the arrow keys, we
2377                      * appear to get two of these messages, both
2378                      * mentioning the target button in
2379                      * LOWORD(wParam), but one of them called while
2380                      * the previous button is still checked. This
2381                      * causes an unnecessary reset of the port
2382                      * number field, which we fix by ensuring here
2383                      * that the button selected is indeed the one
2384                      * checked.
2385                      */
2386                     if (IsDlgButtonChecked(hwnd, LOWORD(wParam)) &&
2387                         ((cfg.protocol == PROT_SSH && cfg.port != 22)
2388                          || (cfg.protocol == PROT_TELNET && cfg.port != 23)
2389                          || (cfg.protocol == PROT_RLOGIN
2390                              && cfg.port != 513))) {
2391                         cfg.port = i ? 22 : j ? 23 : 513;
2392                         SetDlgItemInt(hwnd, IDC_PORT, cfg.port, FALSE);
2393                     }
2394                 }
2395                 break;
2396               case IDC_HOST:
2397                 if (HIWORD(wParam) == EN_CHANGE)
2398                     GetDlgItemText(hwnd, IDC_HOST, cfg.host,
2399                                    sizeof(cfg.host) - 1);
2400                 break;
2401               case IDC_PORT:
2402                 if (HIWORD(wParam) == EN_CHANGE) {
2403                     GetDlgItemText(hwnd, IDC_PORT, portname, 31);
2404                     if (isdigit(portname[0]))
2405                         MyGetDlgItemInt(hwnd, IDC_PORT, &cfg.port);
2406                     else {
2407                         service = getservbyname(portname, NULL);
2408                         if (service)
2409                             cfg.port = ntohs(service->s_port);
2410                         else
2411                             cfg.port = 0;
2412                     }
2413                 }
2414                 break;
2415               case IDC_SESSEDIT:
2416                 if (HIWORD(wParam) == EN_CHANGE) {
2417                     SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL,
2418                                        (WPARAM) - 1, 0);
2419                     GetDlgItemText(hwnd, IDC_SESSEDIT,
2420                                    savedsession, sizeof(savedsession) - 1);
2421                     savedsession[sizeof(savedsession) - 1] = '\0';
2422                 }
2423                 break;
2424               case IDC_SESSSAVE:
2425                 if (HIWORD(wParam) == BN_CLICKED ||
2426                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2427                     /*
2428                      * Save a session
2429                      */
2430                     char str[2048];
2431                     GetDlgItemText(hwnd, IDC_SESSEDIT, str,
2432                                    sizeof(str) - 1);
2433                     if (!*str) {
2434                         int n = SendDlgItemMessage(hwnd, IDC_SESSLIST,
2435                                                    LB_GETCURSEL, 0, 0);
2436                         if (n == LB_ERR) {
2437                             MessageBeep(0);
2438                             break;
2439                         }
2440                         strcpy(str, sesslist.sessions[n]);
2441                     }
2442                     save_settings(str, !!strcmp(str, "Default Settings"),
2443                                   &cfg);
2444                     get_sesslist(&sesslist, FALSE);
2445                     get_sesslist(&sesslist, TRUE);
2446                     SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2447                                        FALSE, 0);
2448                     SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_RESETCONTENT,
2449                                        0, 0);
2450                     for (i = 0; i < sesslist.nsessions; i++)
2451                         SendDlgItemMessage(hwnd, IDC_SESSLIST,
2452                                            LB_ADDSTRING, 0,
2453                                            (LPARAM) (sesslist.sessions[i]));
2454                     SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL,
2455                                        (WPARAM) - 1, 0);
2456                     SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2457                                        TRUE, 0);
2458                     InvalidateRect(GetDlgItem(hwnd, IDC_SESSLIST), NULL,
2459                                    TRUE);
2460                 }
2461                 break;
2462               case IDC_SESSLIST:
2463               case IDC_SESSLOAD:
2464                 if (LOWORD(wParam) == IDC_SESSLIST) {
2465                     if (HIWORD(wParam) == LBN_SETFOCUS)
2466                         sesslist_has_focus = 1;
2467                     else if (HIWORD(wParam) == LBN_KILLFOCUS)
2468                         sesslist_has_focus = 0;
2469                 }
2470                 if (LOWORD(wParam) == IDC_SESSLOAD &&
2471                     HIWORD(wParam) != BN_CLICKED &&
2472                     HIWORD(wParam) != BN_DOUBLECLICKED) break;
2473                 if (LOWORD(wParam) == IDC_SESSLIST &&
2474                     HIWORD(wParam) != LBN_DBLCLK) break;
2475                 /* Load the session selected in SESSLIST. */
2476                 if (load_selected_session(hwnd) &&
2477                     LOWORD(wParam) == IDC_SESSLIST) {
2478                     /*
2479                      * A double-click on a saved session should
2480                      * actually start the session, not just load it.
2481                      * Unless it's Default Settings or some other
2482                      * host-less set of saved settings.
2483                      */
2484                     if (*cfg.host) {
2485                         readytogo = TRUE;
2486                         SetCapture(hwnd);
2487                     }
2488                 }
2489                 break;
2490               case IDC_SESSDEL:
2491                 if (HIWORD(wParam) == BN_CLICKED ||
2492                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2493                     int n = SendDlgItemMessage(hwnd, IDC_SESSLIST,
2494                                                LB_GETCURSEL, 0, 0);
2495                     if (n == LB_ERR || n == 0) {
2496                         MessageBeep(0);
2497                         break;
2498                     }
2499                     del_settings(sesslist.sessions[n]);
2500                     get_sesslist(&sesslist, FALSE);
2501                     get_sesslist(&sesslist, TRUE);
2502                     SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2503                                        FALSE, 0);
2504                     SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_RESETCONTENT,
2505                                        0, 0);
2506                     for (i = 0; i < sesslist.nsessions; i++)
2507                         SendDlgItemMessage(hwnd, IDC_SESSLIST,
2508                                            LB_ADDSTRING, 0,
2509                                            (LPARAM) (sesslist.sessions[i]));
2510                     SendDlgItemMessage(hwnd, IDC_SESSLIST, LB_SETCURSEL,
2511                                        (WPARAM) - 1, 0);
2512                     SendDlgItemMessage(hwnd, IDC_SESSLIST, WM_SETREDRAW,
2513                                        TRUE, 0);
2514                     InvalidateRect(GetDlgItem(hwnd, IDC_SESSLIST), NULL,
2515                                    TRUE);
2516                 }
2517               case IDC_PINGEDIT:
2518                 if (HIWORD(wParam) == EN_CHANGE)
2519                     MyGetDlgItemInt(hwnd, IDC_PINGEDIT,
2520                                     &cfg.ping_interval);
2521                 break;
2522               case IDC_NODELAY:
2523                 if (HIWORD(wParam) == BN_CLICKED ||
2524                     HIWORD(wParam) == BN_DOUBLECLICKED)
2525                         cfg.tcp_nodelay =
2526                         IsDlgButtonChecked(hwnd, IDC_NODELAY);
2527                 break;
2528               case IDC_DEL008:
2529               case IDC_DEL127:
2530                 if (HIWORD(wParam) == BN_CLICKED ||
2531                     HIWORD(wParam) == BN_DOUBLECLICKED)
2532                         cfg.bksp_is_delete =
2533                         IsDlgButtonChecked(hwnd, IDC_DEL127);
2534                 break;
2535               case IDC_HOMETILDE:
2536               case IDC_HOMERXVT:
2537                 if (HIWORD(wParam) == BN_CLICKED ||
2538                     HIWORD(wParam) == BN_DOUBLECLICKED)
2539                         cfg.rxvt_homeend =
2540                         IsDlgButtonChecked(hwnd, IDC_HOMERXVT);
2541                 break;
2542               case IDC_FUNCTILDE:
2543               case IDC_FUNCLINUX:
2544               case IDC_FUNCXTERM:
2545               case IDC_FUNCVT400:
2546               case IDC_FUNCVT100P:
2547               case IDC_FUNCSCO:
2548                 if (HIWORD(wParam) == BN_CLICKED ||
2549                     HIWORD(wParam) == BN_DOUBLECLICKED)
2550                         switch (LOWORD(wParam)) {
2551                       case IDC_FUNCTILDE:
2552                         cfg.funky_type = 0;
2553                         break;
2554                       case IDC_FUNCLINUX:
2555                         cfg.funky_type = 1;
2556                         break;
2557                       case IDC_FUNCXTERM:
2558                         cfg.funky_type = 2;
2559                         break;
2560                       case IDC_FUNCVT400:
2561                         cfg.funky_type = 3;
2562                         break;
2563                       case IDC_FUNCVT100P:
2564                         cfg.funky_type = 4;
2565                         break;
2566                       case IDC_FUNCSCO:
2567                         cfg.funky_type = 5;
2568                         break;
2569                     }
2570                 break;
2571               case IDC_KPNORMAL:
2572               case IDC_KPAPPLIC:
2573                 if (HIWORD(wParam) == BN_CLICKED ||
2574                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2575                     cfg.app_keypad =
2576                         IsDlgButtonChecked(hwnd, IDC_KPAPPLIC);
2577                     cfg.nethack_keypad = FALSE;
2578                 }
2579                 break;
2580               case IDC_KPNH:
2581                 if (HIWORD(wParam) == BN_CLICKED ||
2582                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2583                     cfg.app_keypad = FALSE;
2584                     cfg.nethack_keypad = TRUE;
2585                 }
2586                 break;
2587               case IDC_CURNORMAL:
2588               case IDC_CURAPPLIC:
2589                 if (HIWORD(wParam) == BN_CLICKED ||
2590                     HIWORD(wParam) == BN_DOUBLECLICKED)
2591                         cfg.app_cursor =
2592                         IsDlgButtonChecked(hwnd, IDC_CURAPPLIC);
2593                 break;
2594               case IDC_NOAPPLICC:
2595                 if (HIWORD(wParam) == BN_CLICKED ||
2596                     HIWORD(wParam) == BN_DOUBLECLICKED)
2597                         cfg.no_applic_c =
2598                         IsDlgButtonChecked(hwnd, IDC_NOAPPLICC);
2599                 break;
2600               case IDC_NOAPPLICK:
2601                 if (HIWORD(wParam) == BN_CLICKED ||
2602                     HIWORD(wParam) == BN_DOUBLECLICKED)
2603                         cfg.no_applic_k =
2604                         IsDlgButtonChecked(hwnd, IDC_NOAPPLICK);
2605                 break;
2606               case IDC_NOMOUSEREP:
2607                 if (HIWORD(wParam) == BN_CLICKED ||
2608                     HIWORD(wParam) == BN_DOUBLECLICKED)
2609                         cfg.no_mouse_rep =
2610                         IsDlgButtonChecked(hwnd, IDC_NOMOUSEREP);
2611                 break;
2612               case IDC_NORESIZE:
2613                 if (HIWORD(wParam) == BN_CLICKED ||
2614                     HIWORD(wParam) == BN_DOUBLECLICKED)
2615                         cfg.no_remote_resize =
2616                         IsDlgButtonChecked(hwnd, IDC_NORESIZE);
2617                 break;
2618               case IDC_NOALTSCREEN:
2619                 if (HIWORD(wParam) == BN_CLICKED ||
2620                     HIWORD(wParam) == BN_DOUBLECLICKED)
2621                         cfg.no_alt_screen =
2622                         IsDlgButtonChecked(hwnd, IDC_NOALTSCREEN);
2623                 break;
2624               case IDC_NOWINTITLE:
2625                 if (HIWORD(wParam) == BN_CLICKED ||
2626                     HIWORD(wParam) == BN_DOUBLECLICKED)
2627                         cfg.no_remote_wintitle =
2628                         IsDlgButtonChecked(hwnd, IDC_NOWINTITLE);
2629                 break;
2630               case IDC_NODBACKSPACE:
2631                 if (HIWORD(wParam) == BN_CLICKED ||
2632                     HIWORD(wParam) == BN_DOUBLECLICKED)
2633                         cfg.no_dbackspace =
2634                         IsDlgButtonChecked(hwnd, IDC_NODBACKSPACE);
2635                 break;
2636               case IDC_NOCHARSET:
2637                 if (HIWORD(wParam) == BN_CLICKED ||
2638                     HIWORD(wParam) == BN_DOUBLECLICKED)
2639                         cfg.no_remote_charset =
2640                         IsDlgButtonChecked(hwnd, IDC_NOCHARSET);
2641                 break;
2642               case IDC_ALTF4:
2643                 if (HIWORD(wParam) == BN_CLICKED ||
2644                     HIWORD(wParam) == BN_DOUBLECLICKED)
2645                         cfg.alt_f4 = IsDlgButtonChecked(hwnd, IDC_ALTF4);
2646                 break;
2647               case IDC_ALTSPACE:
2648                 if (HIWORD(wParam) == BN_CLICKED ||
2649                     HIWORD(wParam) == BN_DOUBLECLICKED)
2650                         cfg.alt_space =
2651                         IsDlgButtonChecked(hwnd, IDC_ALTSPACE);
2652                 break;
2653               case IDC_ALTONLY:
2654                 if (HIWORD(wParam) == BN_CLICKED ||
2655                     HIWORD(wParam) == BN_DOUBLECLICKED)
2656                         cfg.alt_only =
2657                         IsDlgButtonChecked(hwnd, IDC_ALTONLY);
2658                 break;
2659               case IDC_ECHOBACKEND:
2660               case IDC_ECHOYES:
2661               case IDC_ECHONO:
2662                 if (HIWORD(wParam) == BN_CLICKED ||
2663                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2664                     if (LOWORD(wParam) == IDC_ECHOBACKEND)
2665                         cfg.localecho = LD_BACKEND;
2666                     if (LOWORD(wParam) == IDC_ECHOYES)
2667                         cfg.localecho = LD_YES;
2668                     if (LOWORD(wParam) == IDC_ECHONO)
2669                         cfg.localecho = LD_NO;
2670                 }
2671                 break;
2672               case IDC_EDITBACKEND:
2673               case IDC_EDITYES:
2674               case IDC_EDITNO:
2675                 if (HIWORD(wParam) == BN_CLICKED ||
2676                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2677                     if (LOWORD(wParam) == IDC_EDITBACKEND)
2678                         cfg.localedit = LD_BACKEND;
2679                     if (LOWORD(wParam) == IDC_EDITYES)
2680                         cfg.localedit = LD_YES;
2681                     if (LOWORD(wParam) == IDC_EDITNO)
2682                         cfg.localedit = LD_NO;
2683                 }
2684                 break;
2685               case IDC_ANSWEREDIT:
2686                 if (HIWORD(wParam) == EN_CHANGE)
2687                     GetDlgItemText(hwnd, IDC_ANSWEREDIT, cfg.answerback,
2688                                    sizeof(cfg.answerback) - 1);
2689                 break;
2690               case IDC_ALWAYSONTOP:
2691                 if (HIWORD(wParam) == BN_CLICKED ||
2692                     HIWORD(wParam) == BN_DOUBLECLICKED)
2693                         cfg.alwaysontop =
2694                         IsDlgButtonChecked(hwnd, IDC_ALWAYSONTOP);
2695                 break;
2696               case IDC_FULLSCREENONALTENTER:
2697                 if (HIWORD(wParam) == BN_CLICKED ||
2698                     HIWORD(wParam) == BN_DOUBLECLICKED)
2699                         cfg.fullscreenonaltenter =
2700                         IsDlgButtonChecked(hwnd, IDC_FULLSCREENONALTENTER);
2701                 break;
2702               case IDC_SCROLLKEY:
2703                 if (HIWORD(wParam) == BN_CLICKED ||
2704                     HIWORD(wParam) == BN_DOUBLECLICKED)
2705                         cfg.scroll_on_key =
2706                         IsDlgButtonChecked(hwnd, IDC_SCROLLKEY);
2707                 break;
2708               case IDC_SCROLLDISP:
2709                 if (HIWORD(wParam) == BN_CLICKED ||
2710                     HIWORD(wParam) == BN_DOUBLECLICKED)
2711                         cfg.scroll_on_disp =
2712                         IsDlgButtonChecked(hwnd, IDC_SCROLLDISP);
2713                 break;
2714               case IDC_COMPOSEKEY:
2715                 if (HIWORD(wParam) == BN_CLICKED ||
2716                     HIWORD(wParam) == BN_DOUBLECLICKED)
2717                         cfg.compose_key =
2718                         IsDlgButtonChecked(hwnd, IDC_COMPOSEKEY);
2719                 break;
2720               case IDC_CTRLALTKEYS:
2721                 if (HIWORD(wParam) == BN_CLICKED ||
2722                     HIWORD(wParam) == BN_DOUBLECLICKED)
2723                         cfg.ctrlaltkeys =
2724                         IsDlgButtonChecked(hwnd, IDC_CTRLALTKEYS);
2725                 break;
2726               case IDC_TELNETKEY:
2727                 if (HIWORD(wParam) == BN_CLICKED ||
2728                     HIWORD(wParam) == BN_DOUBLECLICKED)
2729                         cfg.telnet_keyboard =
2730                         IsDlgButtonChecked(hwnd, IDC_TELNETKEY);
2731                 break;
2732               case IDC_TELNETRET:
2733                 if (HIWORD(wParam) == BN_CLICKED ||
2734                     HIWORD(wParam) == BN_DOUBLECLICKED)
2735                         cfg.telnet_newline =
2736                         IsDlgButtonChecked(hwnd, IDC_TELNETRET);
2737                 break;
2738               case IDC_WRAPMODE:
2739                 if (HIWORD(wParam) == BN_CLICKED ||
2740                     HIWORD(wParam) == BN_DOUBLECLICKED)
2741                         cfg.wrap_mode =
2742                         IsDlgButtonChecked(hwnd, IDC_WRAPMODE);
2743                 break;
2744               case IDC_DECOM:
2745                 if (HIWORD(wParam) == BN_CLICKED ||
2746                     HIWORD(wParam) == BN_DOUBLECLICKED)
2747                         cfg.dec_om = IsDlgButtonChecked(hwnd, IDC_DECOM);
2748                 break;
2749               case IDC_LFHASCR:
2750                 if (HIWORD(wParam) == BN_CLICKED ||
2751                     HIWORD(wParam) == BN_DOUBLECLICKED)
2752                         cfg.lfhascr =
2753                         IsDlgButtonChecked(hwnd, IDC_LFHASCR);
2754                 break;
2755               case IDC_ROWSEDIT:
2756                 if (HIWORD(wParam) == EN_CHANGE)
2757                     MyGetDlgItemInt(hwnd, IDC_ROWSEDIT, &cfg.height);
2758                 break;
2759               case IDC_COLSEDIT:
2760                 if (HIWORD(wParam) == EN_CHANGE)
2761                     MyGetDlgItemInt(hwnd, IDC_COLSEDIT, &cfg.width);
2762                 break;
2763               case IDC_SAVEEDIT:
2764                 if (HIWORD(wParam) == EN_CHANGE)
2765                     MyGetDlgItemInt(hwnd, IDC_SAVEEDIT, &cfg.savelines);
2766                 break;
2767               case IDC_CHOOSEFONT:
2768                 {
2769                     HDC hdc = GetDC(0);
2770                     lf.lfHeight = -MulDiv(cfg.fontheight,
2771                                           GetDeviceCaps(hdc, LOGPIXELSY),
2772                                           72);
2773                     ReleaseDC(0, hdc);
2774                 }
2775                 lf.lfWidth = lf.lfEscapement = lf.lfOrientation = 0;
2776                 lf.lfItalic = lf.lfUnderline = lf.lfStrikeOut = 0;
2777                 lf.lfWeight = (cfg.fontisbold ? FW_BOLD : 0);
2778                 lf.lfCharSet = cfg.fontcharset;
2779                 lf.lfOutPrecision = OUT_DEFAULT_PRECIS;
2780                 lf.lfClipPrecision = CLIP_DEFAULT_PRECIS;
2781                 lf.lfQuality = DEFAULT_QUALITY;
2782                 lf.lfPitchAndFamily = FIXED_PITCH | FF_DONTCARE;
2783                 strncpy(lf.lfFaceName, cfg.font,
2784                         sizeof(lf.lfFaceName) - 1);
2785                 lf.lfFaceName[sizeof(lf.lfFaceName) - 1] = '\0';
2786
2787                 cf.lStructSize = sizeof(cf);
2788                 cf.hwndOwner = hwnd;
2789                 cf.lpLogFont = &lf;
2790                 cf.Flags = CF_FIXEDPITCHONLY | CF_FORCEFONTEXIST |
2791                     CF_INITTOLOGFONTSTRUCT | CF_SCREENFONTS;
2792
2793                 if (ChooseFont(&cf)) {
2794                     strncpy(cfg.font, lf.lfFaceName, sizeof(cfg.font) - 1);
2795                     cfg.font[sizeof(cfg.font) - 1] = '\0';
2796                     cfg.fontisbold = (lf.lfWeight == FW_BOLD);
2797                     cfg.fontcharset = lf.lfCharSet;
2798                     cfg.fontheight = cf.iPointSize / 10;
2799                     fmtfont(fontstatic);
2800                     SetDlgItemText(hwnd, IDC_FONTSTATIC, fontstatic);
2801                 }
2802                 break;
2803               case IDC_BELL_DISABLED:
2804               case IDC_BELL_DEFAULT:
2805               case IDC_BELL_WAVEFILE:
2806               case IDC_BELL_VISUAL:
2807                 if (HIWORD(wParam) == BN_CLICKED ||
2808                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2809                     if (LOWORD(wParam) == IDC_BELL_DISABLED)
2810                         cfg.beep = BELL_DISABLED;
2811                     if (LOWORD(wParam) == IDC_BELL_DEFAULT)
2812                         cfg.beep = BELL_DEFAULT;
2813                     if (LOWORD(wParam) == IDC_BELL_WAVEFILE)
2814                         cfg.beep = BELL_WAVEFILE;
2815                     if (LOWORD(wParam) == IDC_BELL_VISUAL)
2816                         cfg.beep = BELL_VISUAL;
2817                 }
2818                 break;
2819               case IDC_B_IND_DISABLED:
2820               case IDC_B_IND_FLASH:
2821               case IDC_B_IND_STEADY:
2822                 if (HIWORD(wParam) == BN_CLICKED ||
2823                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2824                     if (LOWORD(wParam) == IDC_B_IND_DISABLED)
2825                         cfg.beep_ind = B_IND_DISABLED;
2826                     if (LOWORD(wParam) == IDC_B_IND_FLASH)
2827                         cfg.beep_ind = B_IND_FLASH;
2828                     if (LOWORD(wParam) == IDC_B_IND_STEADY)
2829                         cfg.beep_ind = B_IND_STEADY;
2830                 }
2831                 break;
2832               case IDC_BELL_WAVEBROWSE:
2833                 memset(&of, 0, sizeof(of));
2834 #ifdef OPENFILENAME_SIZE_VERSION_400
2835                 of.lStructSize = OPENFILENAME_SIZE_VERSION_400;
2836 #else
2837                 of.lStructSize = sizeof(of);
2838 #endif
2839                 of.hwndOwner = hwnd;
2840                 of.lpstrFilter = "Wave Files\0*.WAV\0AllFiles\0*\0\0\0";
2841                 of.lpstrCustomFilter = NULL;
2842                 of.nFilterIndex = 1;
2843                 of.lpstrFile = filename;
2844                 strcpy(filename, cfg.bell_wavefile);
2845                 of.nMaxFile = sizeof(filename);
2846                 of.lpstrFileTitle = NULL;
2847                 of.lpstrInitialDir = NULL;
2848                 of.lpstrTitle = "Select Bell Sound File";
2849                 of.Flags = 0;
2850                 if (GetOpenFileName(&of)) {
2851                     strcpy(cfg.bell_wavefile, filename);
2852                     SetDlgItemText(hwnd, IDC_BELL_WAVEEDIT,
2853                                    cfg.bell_wavefile);
2854                 }
2855                 break;
2856               case IDC_BELL_WAVEEDIT:
2857                 if (HIWORD(wParam) == EN_CHANGE)
2858                     GetDlgItemText(hwnd, IDC_BELL_WAVEEDIT,
2859                                    cfg.bell_wavefile,
2860                                    sizeof(cfg.bell_wavefile) - 1);
2861                 break;
2862               case IDC_BELLOVL:
2863                 if (HIWORD(wParam) == BN_CLICKED ||
2864                     HIWORD(wParam) == BN_DOUBLECLICKED)
2865                         cfg.bellovl =
2866                         IsDlgButtonChecked(hwnd, IDC_BELLOVL);
2867                 break;
2868               case IDC_BELLOVLN:
2869                 if (HIWORD(wParam) == EN_CHANGE)
2870                     MyGetDlgItemInt(hwnd, IDC_BELLOVLN, &cfg.bellovl_n);
2871                 break;
2872               case IDC_BELLOVLT:
2873                 if (HIWORD(wParam) == EN_CHANGE)
2874                     MyGetDlgItemFlt(hwnd, IDC_BELLOVLT, &cfg.bellovl_t,
2875                                     1000);
2876                 break;
2877               case IDC_BELLOVLS:
2878                 if (HIWORD(wParam) == EN_CHANGE)
2879                     MyGetDlgItemFlt(hwnd, IDC_BELLOVLS, &cfg.bellovl_s,
2880                                     1000);
2881                 break;
2882               case IDC_BLINKTEXT:
2883                 if (HIWORD(wParam) == BN_CLICKED ||
2884                     HIWORD(wParam) == BN_DOUBLECLICKED)
2885                         cfg.blinktext =
2886                         IsDlgButtonChecked(hwnd, IDC_BLINKTEXT);
2887                 break;
2888               case IDC_BCE:
2889                 if (HIWORD(wParam) == BN_CLICKED ||
2890                     HIWORD(wParam) == BN_DOUBLECLICKED)
2891                         cfg.bce = IsDlgButtonChecked(hwnd, IDC_BCE);
2892                 break;
2893               case IDC_WINNAME:
2894                 if (HIWORD(wParam) == BN_CLICKED ||
2895                     HIWORD(wParam) == BN_DOUBLECLICKED)
2896                         cfg.win_name_always =
2897                         IsDlgButtonChecked(hwnd, IDC_WINNAME);
2898                 break;
2899               case IDC_HIDEMOUSE:
2900                 if (HIWORD(wParam) == BN_CLICKED ||
2901                     HIWORD(wParam) == BN_DOUBLECLICKED)
2902                         cfg.hide_mouseptr =
2903                         IsDlgButtonChecked(hwnd, IDC_HIDEMOUSE);
2904                 break;
2905               case IDC_SUNKENEDGE:
2906                 if (HIWORD(wParam) == BN_CLICKED ||
2907                     HIWORD(wParam) == BN_DOUBLECLICKED)
2908                         cfg.sunken_edge =
2909                         IsDlgButtonChecked(hwnd, IDC_SUNKENEDGE);
2910                 break;
2911               case IDC_WINBEDIT:
2912                 if (HIWORD(wParam) == EN_CHANGE)
2913                     MyGetDlgItemInt(hwnd, IDC_WINBEDIT,
2914                                     &cfg.window_border);
2915                 if (cfg.window_border > 32)
2916                     cfg.window_border = 32;
2917                 break;
2918               case IDC_CURBLOCK:
2919                 if (HIWORD(wParam) == BN_CLICKED ||
2920                     HIWORD(wParam) == BN_DOUBLECLICKED)
2921                         cfg.cursor_type = 0;
2922                 break;
2923               case IDC_CURUNDER:
2924                 if (HIWORD(wParam) == BN_CLICKED ||
2925                     HIWORD(wParam) == BN_DOUBLECLICKED)
2926                         cfg.cursor_type = 1;
2927                 break;
2928               case IDC_CURVERT:
2929                 if (HIWORD(wParam) == BN_CLICKED ||
2930                     HIWORD(wParam) == BN_DOUBLECLICKED)
2931                         cfg.cursor_type = 2;
2932                 break;
2933               case IDC_BLINKCUR:
2934                 if (HIWORD(wParam) == BN_CLICKED ||
2935                     HIWORD(wParam) == BN_DOUBLECLICKED)
2936                         cfg.blink_cur =
2937                         IsDlgButtonChecked(hwnd, IDC_BLINKCUR);
2938                 break;
2939               case IDC_SCROLLBAR:
2940                 if (HIWORD(wParam) == BN_CLICKED ||
2941                     HIWORD(wParam) == BN_DOUBLECLICKED)
2942                         cfg.scrollbar =
2943                         IsDlgButtonChecked(hwnd, IDC_SCROLLBAR);
2944                 break;
2945               case IDC_SCROLLBARFULLSCREEN:
2946                 if (HIWORD(wParam) == BN_CLICKED ||
2947                     HIWORD(wParam) == BN_DOUBLECLICKED)
2948                     cfg.scrollbar_in_fullscreen =
2949                     IsDlgButtonChecked(hwnd, IDC_SCROLLBARFULLSCREEN);
2950                 break;
2951               case IDC_RESIZETERM:
2952               case IDC_RESIZEFONT:
2953               case IDC_RESIZENONE:
2954               case IDC_RESIZEEITHER:
2955                 if (HIWORD(wParam) == BN_CLICKED ||
2956                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2957                     cfg.resize_action =
2958                         IsDlgButtonChecked(hwnd,
2959                                            IDC_RESIZETERM) ? RESIZE_TERM :
2960                         IsDlgButtonChecked(hwnd,
2961                                            IDC_RESIZEFONT) ? RESIZE_FONT :
2962                         IsDlgButtonChecked(hwnd,
2963                                            IDC_RESIZEEITHER) ? RESIZE_EITHER :
2964                         RESIZE_DISABLED;
2965                 }
2966                 break;
2967               case IDC_WINEDIT:
2968                 if (HIWORD(wParam) == EN_CHANGE)
2969                     GetDlgItemText(hwnd, IDC_WINEDIT, cfg.wintitle,
2970                                    sizeof(cfg.wintitle) - 1);
2971                 break;
2972               case IDC_COEALWAYS:
2973               case IDC_COENEVER:
2974               case IDC_COENORMAL:
2975                 if (HIWORD(wParam) == BN_CLICKED ||
2976                     HIWORD(wParam) == BN_DOUBLECLICKED) {
2977                     cfg.close_on_exit =
2978                         IsDlgButtonChecked(hwnd,
2979                                            IDC_COEALWAYS) ? COE_ALWAYS :
2980                         IsDlgButtonChecked(hwnd,
2981                                            IDC_COENEVER) ? COE_NEVER :
2982                         COE_NORMAL;
2983                 }
2984                 break;
2985               case IDC_CLOSEWARN:
2986                 if (HIWORD(wParam) == BN_CLICKED ||
2987                     HIWORD(wParam) == BN_DOUBLECLICKED)
2988                         cfg.warn_on_close =
2989                         IsDlgButtonChecked(hwnd, IDC_CLOSEWARN);
2990                 break;
2991               case IDC_TTEDIT:
2992                 if (HIWORD(wParam) == EN_CHANGE)
2993                     GetDlgItemText(hwnd, IDC_TTEDIT, cfg.termtype,
2994                                    sizeof(cfg.termtype) - 1);
2995                 break;
2996
2997                 /* proxy config */
2998               case IDC_PROXYHOSTEDIT:
2999                 if (HIWORD(wParam) == EN_CHANGE)
3000                     GetDlgItemText(hwnd, IDC_PROXYHOSTEDIT, cfg.proxy_host, 
3001                                    sizeof(cfg.proxy_host) - 1);
3002                 break;
3003               case IDC_PROXYPORTEDIT:
3004                 if (HIWORD(wParam) == EN_CHANGE) {
3005                     GetDlgItemText(hwnd, IDC_PROXYPORTEDIT, portname, 31);
3006                     if (isdigit(portname[0]))
3007                         MyGetDlgItemInt(hwnd, IDC_PROXYPORTEDIT, &cfg.proxy_port);
3008                     else {
3009                         service = getservbyname(portname, NULL);
3010                         if (service)
3011                             cfg.proxy_port = ntohs(service->s_port);
3012                         else
3013                             cfg.proxy_port = 0;
3014                     }
3015                 }
3016                 break;
3017               case IDC_PROXYEXCLUDEEDIT:
3018                 if (HIWORD(wParam) == EN_CHANGE)
3019                     GetDlgItemText(hwnd, IDC_PROXYEXCLUDEEDIT,
3020                                    cfg.proxy_exclude_list,
3021                                    sizeof(cfg.proxy_exclude_list) - 1);
3022                 break;
3023               case IDC_PROXYUSEREDIT:
3024                 if (HIWORD(wParam) == EN_CHANGE)
3025                     GetDlgItemText(hwnd, IDC_PROXYUSEREDIT,
3026                                    cfg.proxy_username, 
3027                                    sizeof(cfg.proxy_username) - 1);
3028                 break;
3029               case IDC_PROXYPASSEDIT:
3030                 if (HIWORD(wParam) == EN_CHANGE)
3031                     GetDlgItemText(hwnd, IDC_PROXYPASSEDIT,
3032                                    cfg.proxy_password, 
3033                                    sizeof(cfg.proxy_password) - 1);
3034                 break;
3035               case IDC_PROXYTELNETCMDEDIT:
3036                 if (HIWORD(wParam) == EN_CHANGE)
3037                     GetDlgItemText(hwnd, IDC_PROXYTELNETCMDEDIT,
3038                                    cfg.proxy_telnet_command,
3039                                    sizeof(cfg.proxy_telnet_command) - 1);
3040                 break;
3041               case IDC_PROXYSOCKSVER5:
3042               case IDC_PROXYSOCKSVER4:
3043                 if (HIWORD(wParam) == BN_CLICKED ||
3044                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3045                     cfg.proxy_socks_version =
3046                         IsDlgButtonChecked(hwnd, IDC_PROXYSOCKSVER4) ? 4 : 5;
3047                 }
3048                 break;
3049               case IDC_PROXYLOCALHOST:
3050                 if (HIWORD(wParam) == BN_CLICKED ||
3051                     HIWORD(wParam) == BN_DOUBLECLICKED)
3052                     cfg.even_proxy_localhost =
3053                     IsDlgButtonChecked(hwnd, IDC_PROXYLOCALHOST);
3054                 break;
3055               case IDC_PROXYDNSNO:
3056               case IDC_PROXYDNSAUTO:
3057               case IDC_PROXYDNSYES:
3058                 if (HIWORD(wParam) == BN_CLICKED ||
3059                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3060                     cfg.proxy_dns =
3061                         IsDlgButtonChecked(hwnd, IDC_PROXYDNSNO) ? PROXYDNS_NO :
3062                         IsDlgButtonChecked(hwnd, IDC_PROXYDNSYES) ? PROXYDNS_YES :
3063                         PROXYDNS_AUTO;
3064                 }
3065                 break;
3066               case IDC_PROXYTYPENONE:
3067               case IDC_PROXYTYPEHTTP:
3068               case IDC_PROXYTYPESOCKS:
3069               case IDC_PROXYTYPETELNET:
3070                 if (HIWORD(wParam) == BN_CLICKED ||
3071                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3072                     cfg.proxy_type =
3073                         IsDlgButtonChecked(hwnd, IDC_PROXYTYPEHTTP) ? PROXY_HTTP :
3074                         IsDlgButtonChecked(hwnd, IDC_PROXYTYPESOCKS) ? PROXY_SOCKS :
3075                         IsDlgButtonChecked(hwnd, IDC_PROXYTYPETELNET) ? PROXY_TELNET :
3076                         PROXY_NONE;
3077                 }
3078                 break;
3079
3080               case IDC_LGFEDIT:
3081                 if (HIWORD(wParam) == EN_CHANGE)
3082                     GetDlgItemText(hwnd, IDC_LGFEDIT, cfg.logfilename,
3083                                    sizeof(cfg.logfilename) - 1);
3084                 break;
3085               case IDC_LGFBUTTON:
3086                 memset(&of, 0, sizeof(of));
3087 #ifdef OPENFILENAME_SIZE_VERSION_400
3088                 of.lStructSize = OPENFILENAME_SIZE_VERSION_400;
3089 #else
3090                 of.lStructSize = sizeof(of);
3091 #endif
3092                 of.hwndOwner = hwnd;
3093                 of.lpstrFilter = "All Files\0*\0\0\0";
3094                 of.lpstrCustomFilter = NULL;
3095                 of.nFilterIndex = 1;
3096                 of.lpstrFile = filename;
3097                 strcpy(filename, cfg.logfilename);
3098                 of.nMaxFile = sizeof(filename);
3099                 of.lpstrFileTitle = NULL;
3100                 of.lpstrInitialDir = NULL;
3101                 of.lpstrTitle = "Select session log file";
3102                 of.Flags = 0;
3103                 if (GetSaveFileName(&of)) {
3104                     strcpy(cfg.logfilename, filename);
3105                     SetDlgItemText(hwnd, IDC_LGFEDIT, cfg.logfilename);
3106                 }
3107                 break;
3108               case IDC_LSTATOFF:
3109               case IDC_LSTATASCII:
3110               case IDC_LSTATRAW:
3111               case IDC_LSTATPACKET:
3112                 if (HIWORD(wParam) == BN_CLICKED ||
3113                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3114                     if (IsDlgButtonChecked(hwnd, IDC_LSTATOFF))
3115                         cfg.logtype = LGTYP_NONE;
3116                     if (IsDlgButtonChecked(hwnd, IDC_LSTATASCII))
3117                         cfg.logtype = LGTYP_ASCII;
3118                     if (IsDlgButtonChecked(hwnd, IDC_LSTATRAW))
3119                         cfg.logtype = LGTYP_DEBUG;
3120                     if (IsDlgButtonChecked(hwnd, IDC_LSTATPACKET))
3121                         cfg.logtype = LGTYP_PACKETS;
3122                 }
3123                 break;
3124               case IDC_LSTATXASK:
3125               case IDC_LSTATXAPN:
3126               case IDC_LSTATXOVR:
3127                 if (HIWORD(wParam) == BN_CLICKED ||
3128                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3129                     if (IsDlgButtonChecked(hwnd, IDC_LSTATXASK))
3130                         cfg.logxfovr = LGXF_ASK;
3131                     if (IsDlgButtonChecked(hwnd, IDC_LSTATXAPN))
3132                         cfg.logxfovr = LGXF_APN;
3133                     if (IsDlgButtonChecked(hwnd, IDC_LSTATXOVR))
3134                         cfg.logxfovr = LGXF_OVR;
3135                 }
3136                 break;
3137               case IDC_TSEDIT:
3138               case IDC_R_TSEDIT:
3139                 if (HIWORD(wParam) == EN_CHANGE)
3140                     GetDlgItemText(hwnd, LOWORD(wParam), cfg.termspeed,
3141                                    sizeof(cfg.termspeed) - 1);
3142                 break;
3143               case IDC_LOGEDIT:
3144                 if (HIWORD(wParam) == EN_CHANGE)
3145                     GetDlgItemText(hwnd, IDC_LOGEDIT, cfg.username,
3146                                    sizeof(cfg.username) - 1);
3147                 break;
3148               case IDC_RLLUSEREDIT:
3149                 if (HIWORD(wParam) == EN_CHANGE)
3150                     GetDlgItemText(hwnd, IDC_RLLUSEREDIT,
3151                                    cfg.localusername,
3152                                    sizeof(cfg.localusername) - 1);
3153                 break;
3154               case IDC_EMBSD:
3155               case IDC_EMRFC:
3156                 cfg.rfc_environ = IsDlgButtonChecked(hwnd, IDC_EMRFC);
3157                 break;
3158               case IDC_TPASSIVE:
3159               case IDC_TACTIVE:
3160                 cfg.passive_telnet =
3161                     IsDlgButtonChecked(hwnd, IDC_TPASSIVE);
3162                 break;
3163               case IDC_ENVADD:
3164                 if (HIWORD(wParam) == BN_CLICKED ||
3165                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3166                     char str[sizeof(cfg.environmt)];
3167                     char *p;
3168                     GetDlgItemText(hwnd, IDC_VAREDIT, str,
3169                                    sizeof(str) - 1);
3170                     if (!*str) {
3171                         MessageBeep(0);
3172                         break;
3173                     }
3174                     p = str + strlen(str);
3175                     *p++ = '\t';
3176                     GetDlgItemText(hwnd, IDC_VALEDIT, p,
3177                                    sizeof(str) - 1 - (p - str));
3178                     if (!*p) {
3179                         MessageBeep(0);
3180                         break;
3181                     }
3182                     p = cfg.environmt;
3183                     while (*p) {
3184                         while (*p)
3185                             p++;
3186                         p++;
3187                     }
3188                     if ((p - cfg.environmt) + strlen(str) + 2 <
3189                         sizeof(cfg.environmt)) {
3190                         strcpy(p, str);
3191                         p[strlen(str) + 1] = '\0';
3192                         SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_ADDSTRING,
3193                                            0, (LPARAM) str);
3194                         SetDlgItemText(hwnd, IDC_VAREDIT, "");
3195                         SetDlgItemText(hwnd, IDC_VALEDIT, "");
3196                     } else {
3197                         MessageBox(hwnd, "Environment too big",
3198                                    "PuTTY Error", MB_OK | MB_ICONERROR);
3199                     }
3200                 }
3201                 break;
3202               case IDC_ENVREMOVE:
3203                 if (HIWORD(wParam) != BN_CLICKED &&
3204                     HIWORD(wParam) != BN_DOUBLECLICKED) break;
3205                 i =
3206                     SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_GETCURSEL, 0,
3207                                        0);
3208                 if (i == LB_ERR)
3209                     MessageBeep(0);
3210                 else {
3211                     char *p, *q;
3212
3213                     SendDlgItemMessage(hwnd, IDC_ENVLIST, LB_DELETESTRING,
3214                                        i, 0);
3215                     p = cfg.environmt;
3216                     while (i > 0) {
3217                         if (!*p)
3218                             goto disaster;
3219                         while (*p)
3220                             p++;
3221                         p++;
3222                         i--;
3223                     }
3224                     q = p;
3225                     if (!*p)
3226                         goto disaster;
3227                     while (*p)
3228                         p++;
3229                     p++;
3230                     while (*p) {
3231                         while (*p)
3232                             *q++ = *p++;
3233                         *q++ = *p++;
3234                     }
3235                     *q = '\0';
3236                   disaster:;
3237                 }
3238                 break;
3239               case IDC_NOPTY:
3240                 if (HIWORD(wParam) == BN_CLICKED ||
3241                     HIWORD(wParam) == BN_DOUBLECLICKED)
3242                         cfg.nopty = IsDlgButtonChecked(hwnd, IDC_NOPTY);
3243                 break;
3244               case IDC_COMPRESS:
3245                 if (HIWORD(wParam) == BN_CLICKED ||
3246                     HIWORD(wParam) == BN_DOUBLECLICKED)
3247                         cfg.compression =
3248                         IsDlgButtonChecked(hwnd, IDC_COMPRESS);
3249                 break;
3250               case IDC_SSH2DES:
3251                 if (HIWORD(wParam) == BN_CLICKED ||
3252                     HIWORD(wParam) == BN_DOUBLECLICKED)
3253                         cfg.ssh2_des_cbc =
3254                         IsDlgButtonChecked(hwnd, IDC_SSH2DES);
3255                 break;
3256               case IDC_AGENTFWD:
3257                 if (HIWORD(wParam) == BN_CLICKED ||
3258                     HIWORD(wParam) == BN_DOUBLECLICKED)
3259                         cfg.agentfwd =
3260                         IsDlgButtonChecked(hwnd, IDC_AGENTFWD);
3261                 break;
3262               case IDC_CHANGEUSER:
3263                 if (HIWORD(wParam) == BN_CLICKED ||
3264                     HIWORD(wParam) == BN_DOUBLECLICKED)
3265                         cfg.change_username =
3266                         IsDlgButtonChecked(hwnd, IDC_CHANGEUSER);
3267                 break;
3268               case IDC_CIPHERLIST:
3269               case IDC_CIPHERUP:
3270               case IDC_CIPHERDN:
3271                 handle_prefslist(&cipherlist,
3272                                  cfg.ssh_cipherlist, CIPHER_MAX,
3273                                  0, hwnd, wParam, lParam);
3274                 break;
3275               case IDC_SSHPROT1ONLY:
3276               case IDC_SSHPROT1:
3277               case IDC_SSHPROT2:
3278               case IDC_SSHPROT2ONLY:
3279                 if (HIWORD(wParam) == BN_CLICKED ||
3280                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3281                     if (IsDlgButtonChecked(hwnd, IDC_SSHPROT1ONLY))
3282                         cfg.sshprot = 0;
3283                     if (IsDlgButtonChecked(hwnd, IDC_SSHPROT1))
3284                         cfg.sshprot = 1;
3285                     else if (IsDlgButtonChecked(hwnd, IDC_SSHPROT2))
3286                         cfg.sshprot = 2;
3287                     else if (IsDlgButtonChecked(hwnd, IDC_SSHPROT2ONLY))
3288                         cfg.sshprot = 3;
3289                 }
3290                 break;
3291               case IDC_AUTHTIS:
3292                 if (HIWORD(wParam) == BN_CLICKED ||
3293                     HIWORD(wParam) == BN_DOUBLECLICKED)
3294                         cfg.try_tis_auth =
3295                         IsDlgButtonChecked(hwnd, IDC_AUTHTIS);
3296                 break;
3297               case IDC_AUTHKI:
3298                 if (HIWORD(wParam) == BN_CLICKED ||
3299                     HIWORD(wParam) == BN_DOUBLECLICKED)
3300                         cfg.try_ki_auth =
3301                         IsDlgButtonChecked(hwnd, IDC_AUTHKI);
3302                 break;
3303               case IDC_PKEDIT:
3304                 if (HIWORD(wParam) == EN_CHANGE)
3305                     GetDlgItemText(hwnd, IDC_PKEDIT, cfg.keyfile,
3306                                    sizeof(cfg.keyfile) - 1);
3307                 break;
3308               case IDC_CMDEDIT:
3309                 if (HIWORD(wParam) == EN_CHANGE)
3310                     GetDlgItemText(hwnd, IDC_CMDEDIT, cfg.remote_cmd,
3311                                    sizeof(cfg.remote_cmd) - 1);
3312                 break;
3313               case IDC_PKBUTTON:
3314                 memset(&of, 0, sizeof(of));
3315 #ifdef OPENFILENAME_SIZE_VERSION_400
3316                 of.lStructSize = OPENFILENAME_SIZE_VERSION_400;
3317 #else
3318                 of.lStructSize = sizeof(of);
3319 #endif
3320                 of.hwndOwner = hwnd;
3321                 of.lpstrFilter = "PuTTY Private Key Files\0*.PPK\0"
3322                     "AllFiles\0*\0\0\0";
3323                 of.lpstrCustomFilter = NULL;
3324                 of.nFilterIndex = 1;
3325                 of.lpstrFile = filename;
3326                 strcpy(filename, cfg.keyfile);
3327                 of.nMaxFile = sizeof(filename);
3328                 of.lpstrFileTitle = NULL;
3329                 of.lpstrInitialDir = NULL;
3330                 of.lpstrTitle = "Select Private Key File";
3331                 of.Flags = 0;
3332                 if (GetOpenFileName(&of)) {
3333                     strcpy(cfg.keyfile, filename);
3334                     SetDlgItemText(hwnd, IDC_PKEDIT, cfg.keyfile);
3335                 }
3336                 break;
3337               case IDC_RAWCNP:
3338                 cfg.rawcnp = IsDlgButtonChecked(hwnd, IDC_RAWCNP);
3339                 break;
3340               case IDC_RTFPASTE:
3341                 cfg.rtf_paste = IsDlgButtonChecked(hwnd, IDC_RTFPASTE);
3342                 break;
3343               case IDC_MBWINDOWS:
3344               case IDC_MBXTERM:
3345                 cfg.mouse_is_xterm = IsDlgButtonChecked(hwnd, IDC_MBXTERM);
3346                 break;
3347               case IDC_SELTYPELEX:
3348               case IDC_SELTYPERECT:
3349                 cfg.rect_select = IsDlgButtonChecked(hwnd, IDC_SELTYPERECT);
3350                 break;
3351               case IDC_MOUSEOVERRIDE:
3352                 cfg.mouse_override = IsDlgButtonChecked(hwnd, IDC_MOUSEOVERRIDE);
3353                 break;
3354               case IDC_CCSET:
3355                 {
3356                     BOOL ok;
3357                     int i;
3358                     int n = GetDlgItemInt(hwnd, IDC_CCEDIT, &ok, FALSE);
3359
3360                     if (!ok)
3361                         MessageBeep(0);
3362                     else {
3363                         for (i = 0; i < 128; i++)
3364                             if (SendDlgItemMessage
3365                                 (hwnd, IDC_CCLIST, LB_GETSEL, i, 0)) {
3366                                 char str[100];
3367                                 cfg.wordness[i] = n;
3368                                 SendDlgItemMessage(hwnd, IDC_CCLIST,
3369                                                    LB_DELETESTRING, i, 0);
3370                                 sprintf(str, "%d\t(0x%02X)\t%c\t%d", i, i,
3371                                         (i >= 0x21 && i != 0x7F) ? i : ' ',
3372                                         cfg.wordness[i]);
3373                                 SendDlgItemMessage(hwnd, IDC_CCLIST,
3374                                                    LB_INSERTSTRING, i,
3375                                                    (LPARAM) str);
3376                             }
3377                     }
3378                 }
3379                 break;
3380               case IDC_BOLDCOLOUR:
3381                 if (HIWORD(wParam) == BN_CLICKED ||
3382                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3383                     int n, i;
3384                     cfg.bold_colour =
3385                         IsDlgButtonChecked(hwnd, IDC_BOLDCOLOUR);
3386                     SendDlgItemMessage(hwnd, IDC_COLOURLIST, WM_SETREDRAW,
3387                                        FALSE, 0);
3388                     n =
3389                         SendDlgItemMessage(hwnd, IDC_COLOURLIST,
3390                                            LB_GETCOUNT, 0, 0);
3391                     if (n != 12 + 10 * cfg.bold_colour) {
3392                         for (i = n; i-- > 0;)
3393                             SendDlgItemMessage(hwnd, IDC_COLOURLIST,
3394                                                LB_DELETESTRING, i, 0);
3395                         for (i = 0; i < 22; i++)
3396                             if (cfg.bold_colour || permcolour[i])
3397                                 SendDlgItemMessage(hwnd, IDC_COLOURLIST,
3398                                                    LB_ADDSTRING, 0,
3399                                                    (LPARAM) colours[i]);
3400                     }
3401                     SendDlgItemMessage(hwnd, IDC_COLOURLIST, WM_SETREDRAW,
3402                                        TRUE, 0);
3403                     InvalidateRect(GetDlgItem(hwnd, IDC_COLOURLIST), NULL,
3404                                    TRUE);
3405                 }
3406                 break;
3407               case IDC_PALETTE:
3408                 if (HIWORD(wParam) == BN_CLICKED ||
3409                     HIWORD(wParam) == BN_DOUBLECLICKED)
3410                         cfg.try_palette =
3411                         IsDlgButtonChecked(hwnd, IDC_PALETTE);
3412                 break;
3413               case IDC_COLOURLIST:
3414                 if (HIWORD(wParam) == LBN_DBLCLK ||
3415                     HIWORD(wParam) == LBN_SELCHANGE) {
3416                     int i =
3417                         SendDlgItemMessage(hwnd, IDC_COLOURLIST,
3418                                            LB_GETCURSEL,
3419                                            0, 0);
3420                     if (!cfg.bold_colour)
3421                         i = (i < 3 ? i * 2 : i == 3 ? 5 : i * 2 - 2);
3422                     SetDlgItemInt(hwnd, IDC_RVALUE, cfg.colours[i][0],
3423                                   FALSE);
3424                     SetDlgItemInt(hwnd, IDC_GVALUE, cfg.colours[i][1],
3425                                   FALSE);
3426                     SetDlgItemInt(hwnd, IDC_BVALUE, cfg.colours[i][2],
3427                                   FALSE);
3428                 }
3429                 break;
3430               case IDC_CHANGE:
3431                 if (HIWORD(wParam) == BN_CLICKED ||
3432                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3433                     static CHOOSECOLOR cc;
3434                     static DWORD custom[16] = { 0 };    /* zero initialisers */
3435                     int i =
3436                         SendDlgItemMessage(hwnd, IDC_COLOURLIST,
3437                                            LB_GETCURSEL,
3438                                            0, 0);
3439                     if (!cfg.bold_colour)
3440                         i = (i < 3 ? i * 2 : i == 3 ? 5 : i * 2 - 2);
3441                     cc.lStructSize = sizeof(cc);
3442                     cc.hwndOwner = hwnd;
3443                     cc.hInstance = (HWND) hinst;
3444                     cc.lpCustColors = custom;
3445                     cc.rgbResult =
3446                         RGB(cfg.colours[i][0], cfg.colours[i][1],
3447                             cfg.colours[i][2]);
3448                     cc.Flags = CC_FULLOPEN | CC_RGBINIT;
3449                     if (ChooseColor(&cc)) {
3450                         cfg.colours[i][0] =
3451                             (unsigned char) (cc.rgbResult & 0xFF);
3452                         cfg.colours[i][1] =
3453                             (unsigned char) (cc.rgbResult >> 8) & 0xFF;
3454                         cfg.colours[i][2] =
3455                             (unsigned char) (cc.rgbResult >> 16) & 0xFF;
3456                         SetDlgItemInt(hwnd, IDC_RVALUE, cfg.colours[i][0],
3457                                       FALSE);
3458                         SetDlgItemInt(hwnd, IDC_GVALUE, cfg.colours[i][1],
3459                                       FALSE);
3460                         SetDlgItemInt(hwnd, IDC_BVALUE, cfg.colours[i][2],
3461                                       FALSE);
3462                     }
3463                 }
3464                 break;
3465               case IDC_CODEPAGE:
3466                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3467                     int index = SendDlgItemMessage(hwnd, IDC_CODEPAGE,
3468                                                    CB_GETCURSEL, 0, 0);
3469                     SendDlgItemMessage(hwnd, IDC_CODEPAGE, CB_GETLBTEXT,
3470                                        index, (LPARAM)cfg.line_codepage);
3471                 } else if (HIWORD(wParam) == CBN_EDITCHANGE) {
3472                     GetDlgItemText(hwnd, IDC_CODEPAGE, cfg.line_codepage,
3473                                    sizeof(cfg.line_codepage) - 1);
3474                 } else if (HIWORD(wParam) == CBN_KILLFOCUS) {
3475                     strcpy(cfg.line_codepage,
3476                            cp_name(decode_codepage(cfg.line_codepage)));
3477                     SetDlgItemText(hwnd, IDC_CODEPAGE, cfg.line_codepage);
3478                 }
3479                 break;
3480               case IDC_PRINTER:
3481                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3482                     int index = SendDlgItemMessage(hwnd, IDC_PRINTER,
3483                                                    CB_GETCURSEL, 0, 0);
3484                     SendDlgItemMessage(hwnd, IDC_PRINTER, CB_GETLBTEXT,
3485                                        index, (LPARAM)cfg.printer);
3486                 } else if (HIWORD(wParam) == CBN_EDITCHANGE) {
3487                     GetDlgItemText(hwnd, IDC_PRINTER, cfg.printer,
3488                                    sizeof(cfg.printer) - 1);
3489                 }
3490                 if (!strcmp(cfg.printer, PRINTER_DISABLED_STRING))
3491                     *cfg.printer = '\0';
3492                 break;
3493               case IDC_CAPSLOCKCYR:
3494                 if (HIWORD(wParam) == BN_CLICKED ||
3495                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3496                     cfg.xlat_capslockcyr =
3497                         IsDlgButtonChecked (hwnd, IDC_CAPSLOCKCYR);
3498                 }
3499                 break;
3500               case IDC_VTXWINDOWS:
3501               case IDC_VTOEMANSI:
3502               case IDC_VTOEMONLY:
3503               case IDC_VTPOORMAN:
3504               case IDC_VTUNICODE:
3505                 cfg.vtmode =
3506                     (IsDlgButtonChecked(hwnd, IDC_VTXWINDOWS) ? VT_XWINDOWS
3507                      : IsDlgButtonChecked(hwnd,
3508                                           IDC_VTOEMANSI) ? VT_OEMANSI :
3509                      IsDlgButtonChecked(hwnd,
3510                                         IDC_VTOEMONLY) ? VT_OEMONLY :
3511                      IsDlgButtonChecked(hwnd,
3512                                         IDC_VTUNICODE) ? VT_UNICODE :
3513                      VT_POORMAN);
3514                 break;
3515               case IDC_X11_FORWARD:
3516                 if (HIWORD(wParam) == BN_CLICKED ||
3517                     HIWORD(wParam) == BN_DOUBLECLICKED)
3518                     cfg.x11_forward =
3519                     IsDlgButtonChecked(hwnd, IDC_X11_FORWARD);
3520                 break;
3521               case IDC_LPORT_ALL:
3522                 if (HIWORD(wParam) == BN_CLICKED ||
3523                     HIWORD(wParam) == BN_DOUBLECLICKED)
3524                     cfg.lport_acceptall =
3525                     IsDlgButtonChecked(hwnd, IDC_LPORT_ALL);
3526                 break;
3527               case IDC_RPORT_ALL:
3528                 if (HIWORD(wParam) == BN_CLICKED ||
3529                     HIWORD(wParam) == BN_DOUBLECLICKED)
3530                     cfg.rport_acceptall =
3531                     IsDlgButtonChecked(hwnd, IDC_RPORT_ALL);
3532                 break;
3533               case IDC_X11_DISPLAY:
3534                 if (HIWORD(wParam) == EN_CHANGE)
3535                     GetDlgItemText(hwnd, IDC_X11_DISPLAY, cfg.x11_display,
3536                                    sizeof(cfg.x11_display) - 1);
3537                 break;
3538               case IDC_PFWDADD:
3539                 if (HIWORD(wParam) == BN_CLICKED ||
3540                     HIWORD(wParam) == BN_DOUBLECLICKED) {
3541                     char str[sizeof(cfg.portfwd)];
3542                     char *p;
3543                     if (IsDlgButtonChecked(hwnd, IDC_PFWDLOCAL))
3544                         str[0] = 'L';
3545                     else
3546                         str[0] = 'R';
3547                     GetDlgItemText(hwnd, IDC_SPORTEDIT, str+1,
3548                                    sizeof(str) - 2);
3549                     if (!str[1]) {
3550                         MessageBox(hwnd,
3551                                    "You need to specify a source port number",
3552                                    "PuTTY Error", MB_OK | MB_ICONERROR);
3553                         break;
3554                     }
3555                     p = str + strlen(str);
3556                     *p++ = '\t';
3557                     GetDlgItemText(hwnd, IDC_DPORTEDIT, p,
3558                                    sizeof(str) - 1 - (p - str));
3559                     if (!*p || !strchr(p, ':')) {
3560                         MessageBox(hwnd,
3561                                    "You need to specify a destination address\n"
3562                                    "in the form \"host.name:port\"",
3563                                    "PuTTY Error", MB_OK | MB_ICONERROR);
3564                         break;
3565                     }
3566                     p = cfg.portfwd;
3567                     while (*p) {
3568                         while (*p)
3569                             p++;
3570                         p++;
3571                     }
3572                     if ((p - cfg.portfwd) + strlen(str) + 2 <
3573                         sizeof(cfg.portfwd)) {
3574                         strcpy(p, str);
3575                         p[strlen(str) + 1] = '\0';
3576                         SendDlgItemMessage(hwnd, IDC_PFWDLIST, LB_ADDSTRING,
3577                                            0, (LPARAM) str);
3578                         SetDlgItemText(hwnd, IDC_SPORTEDIT, "");
3579                         SetDlgItemText(hwnd, IDC_DPORTEDIT, "");
3580                     } else {
3581                         MessageBox(hwnd, "Too many forwardings",
3582                                    "PuTTY Error", MB_OK | MB_ICONERROR);
3583                     }
3584                 }
3585                 break;
3586               case IDC_PFWDREMOVE:
3587                 if (HIWORD(wParam) != BN_CLICKED &&
3588                     HIWORD(wParam) != BN_DOUBLECLICKED) break;
3589                 i = SendDlgItemMessage(hwnd, IDC_PFWDLIST,
3590                                        LB_GETCURSEL, 0, 0);
3591                 if (i == LB_ERR)
3592                     MessageBeep(0);
3593                 else {
3594                     char *p, *q;
3595
3596                     SendDlgItemMessage(hwnd, IDC_PFWDLIST, LB_DELETESTRING,
3597                                        i, 0);
3598                     p = cfg.portfwd;
3599                     while (i > 0) {
3600                         if (!*p)
3601                             goto disaster2;
3602                         while (*p)
3603                             p++;
3604                         p++;
3605                         i--;
3606                     }
3607                     q = p;
3608                     if (!*p)
3609                         goto disaster2;
3610                     while (*p)
3611                         p++;
3612                     p++;
3613                     while (*p) {
3614                         while (*p)
3615                             *q++ = *p++;
3616                         *q++ = *p++;
3617                     }
3618                     *q = '\0';
3619                   disaster2:;
3620                 }
3621                 break;
3622               case IDC_BUGD_IGNORE1:
3623                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3624                     int index = SendDlgItemMessage(hwnd, IDC_BUGD_IGNORE1,
3625                                                    CB_GETCURSEL, 0, 0);
3626                     cfg.sshbug_ignore1 = (index == 0 ? BUG_AUTO :
3627                                           index == 1 ? BUG_OFF : BUG_ON);
3628                 }
3629                 break;
3630               case IDC_BUGD_PLAINPW1:
3631                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3632                     int index = SendDlgItemMessage(hwnd, IDC_BUGD_PLAINPW1,
3633                                                    CB_GETCURSEL, 0, 0);
3634                     cfg.sshbug_plainpw1 = (index == 0 ? BUG_AUTO :
3635                                            index == 1 ? BUG_OFF : BUG_ON);
3636                 }
3637                 break;
3638               case IDC_BUGD_RSA1:
3639                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3640                     int index = SendDlgItemMessage(hwnd, IDC_BUGD_RSA1,
3641                                                    CB_GETCURSEL, 0, 0);
3642                     cfg.sshbug_rsa1 = (index == 0 ? BUG_AUTO :
3643                                        index == 1 ? BUG_OFF : BUG_ON);
3644                 }
3645                 break;
3646               case IDC_BUGD_HMAC2:
3647                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3648                     int index = SendDlgItemMessage(hwnd, IDC_BUGD_HMAC2,
3649                                                    CB_GETCURSEL, 0, 0);
3650                     cfg.sshbug_hmac2 = (index == 0 ? BUG_AUTO :
3651                                         index == 1 ? BUG_OFF : BUG_ON);
3652                 }
3653                 break;
3654               case IDC_BUGD_DERIVEKEY2:
3655                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3656                     int index = SendDlgItemMessage(hwnd, IDC_BUGD_DERIVEKEY2,
3657                                                    CB_GETCURSEL, 0, 0);
3658                     cfg.sshbug_derivekey2 = (index == 0 ? BUG_AUTO :
3659                                              index == 1 ? BUG_OFF : BUG_ON);
3660                 }
3661                 break;
3662               case IDC_BUGD_RSAPAD2:
3663                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3664                     int index = SendDlgItemMessage(hwnd, IDC_BUGD_RSAPAD2,
3665                                                    CB_GETCURSEL, 0, 0);
3666                     cfg.sshbug_rsapad2 = (index == 0 ? BUG_AUTO :
3667                                           index == 1 ? BUG_OFF : BUG_ON);
3668                 }
3669                 break;
3670               case IDC_BUGD_DHGEX2:
3671                 if (HIWORD(wParam) == CBN_SELCHANGE) {
3672                     int index = SendDlgItemMessage(hwnd, IDC_BUGD_DHGEX2,
3673                                                    CB_GETCURSEL, 0, 0);
3674                     cfg.sshbug_dhgex2 = (index == 0 ? BUG_AUTO :
3675                                          index == 1 ? BUG_OFF : BUG_ON);
3676                 }
3677                 break;
3678             }
3679         return 0;
3680       case WM_HELP:
3681         if (help_path) {
3682             int id = ((LPHELPINFO)lParam)->iCtrlId;
3683             char *cmd = help_context_cmd(id);
3684             if (cmd) {
3685                 WinHelp(hwnd, help_path, HELP_COMMAND, (DWORD)cmd);
3686                 requested_help = TRUE;
3687             } else {
3688                 MessageBeep(0);
3689             }
3690         }
3691         break;
3692       case WM_CLOSE:
3693         if (requested_help) {
3694             WinHelp(hwnd, help_path, HELP_QUIT, 0);
3695             requested_help = FALSE;
3696         }
3697         EndDialog(hwnd, 0);
3698         return 0;
3699
3700         /* Grrr Explorer will maximize Dialogs! */
3701       case WM_SIZE:
3702         if (wParam == SIZE_MAXIMIZED)
3703             force_normal(hwnd);
3704         return 0;
3705
3706       default:
3707         /*
3708          * Handle application-defined messages eg. DragListBox
3709          */
3710         /* First find out what the number is (once). */
3711         if (draglistmsg == WM_NULL)
3712             draglistmsg = RegisterWindowMessage (DRAGLISTMSGSTRING);
3713
3714         if (msg == draglistmsg) {
3715             /* Only process once dialog is fully formed. */
3716             if (GetWindowLong(hwnd, GWL_USERDATA) == 1) switch (LOWORD(wParam)) {
3717               case IDC_CIPHERLIST:
3718                 return handle_prefslist(&cipherlist,
3719                                         cfg.ssh_cipherlist, CIPHER_MAX,
3720                                         1, hwnd, wParam, lParam);
3721             }
3722         }
3723         return 0;
3724
3725     }
3726     return 0;
3727 }
3728
3729 static int CALLBACK MainDlgProc(HWND hwnd, UINT msg,
3730                                 WPARAM wParam, LPARAM lParam)
3731 {
3732     if (msg == WM_COMMAND && LOWORD(wParam) == IDOK) {
3733     }
3734     if (msg == WM_COMMAND && LOWORD(wParam) == IDCX_ABOUT) {
3735         EnableWindow(hwnd, 0);
3736         DialogBox(hinst, MAKEINTRESOURCE(IDD_ABOUTBOX), hwnd, AboutProc);
3737         EnableWindow(hwnd, 1);
3738         SetActiveWindow(hwnd);
3739     }
3740     return GenericMainDlgProc(hwnd, msg, wParam, lParam, 0);
3741 }
3742
3743 static int CALLBACK ReconfDlgProc(HWND hwnd, UINT msg,
3744                                   WPARAM wParam, LPARAM lParam)
3745 {
3746     return GenericMainDlgProc(hwnd, msg, wParam, lParam, 1);
3747 }
3748
3749 void defuse_showwindow(void)
3750 {
3751     /*
3752      * Work around the fact that the app's first call to ShowWindow
3753      * will ignore the default in favour of the shell-provided
3754      * setting.
3755      */
3756     {
3757         HWND hwnd;
3758         hwnd = CreateDialog(hinst, MAKEINTRESOURCE(IDD_ABOUTBOX),
3759                             NULL, NullDlgProc);
3760         ShowWindow(hwnd, SW_HIDE);
3761         SetActiveWindow(hwnd);
3762         DestroyWindow(hwnd);
3763     }
3764 }
3765
3766 int do_config(void)
3767 {
3768     int ret;
3769
3770     get_sesslist(&sesslist, TRUE);
3771     savedsession[0] = '\0';
3772     ret =
3773         DialogBox(hinst, MAKEINTRESOURCE(IDD_MAINBOX), NULL, MainDlgProc);
3774     get_sesslist(&sesslist, FALSE);
3775
3776     return ret;
3777 }
3778
3779 int do_reconfig(HWND hwnd)
3780 {
3781     Config backup_cfg;
3782     int ret;
3783
3784     backup_cfg = cfg;                  /* structure copy */
3785     ret =
3786         DialogBox(hinst, MAKEINTRESOURCE(IDD_RECONF), hwnd, ReconfDlgProc);
3787     if (!ret)
3788         cfg = backup_cfg;              /* structure copy */
3789
3790     return ret;
3791 }
3792
3793 void logevent(void *frontend, char *string)
3794 {
3795     char timebuf[40];
3796     time_t t;
3797
3798     log_eventlog(logctx, string);
3799
3800     if (nevents >= negsize) {
3801         negsize += 64;
3802         events = srealloc(events, negsize * sizeof(*events));
3803     }
3804
3805     time(&t);
3806     strftime(timebuf, sizeof(timebuf), "%Y-%m-%d %H:%M:%S\t",
3807              localtime(&t));
3808
3809     events[nevents] = smalloc(strlen(timebuf) + strlen(string) + 1);
3810     strcpy(events[nevents], timebuf);
3811     strcat(events[nevents], string);
3812     if (logbox) {
3813         int count;
3814         SendDlgItemMessage(logbox, IDN_LIST, LB_ADDSTRING,
3815                            0, (LPARAM) events[nevents]);
3816         count = SendDlgItemMessage(logbox, IDN_LIST, LB_GETCOUNT, 0, 0);
3817         SendDlgItemMessage(logbox, IDN_LIST, LB_SETTOPINDEX, count - 1, 0);
3818     }
3819     nevents++;
3820 }
3821
3822 void showeventlog(HWND hwnd)
3823 {
3824     if (!logbox) {
3825         logbox = CreateDialog(hinst, MAKEINTRESOURCE(IDD_LOGBOX),
3826                               hwnd, LogProc);
3827         ShowWindow(logbox, SW_SHOWNORMAL);
3828     }
3829     SetActiveWindow(logbox);
3830 }
3831
3832 void showabout(HWND hwnd)
3833 {
3834     DialogBox(hinst, MAKEINTRESOURCE(IDD_ABOUTBOX), hwnd, AboutProc);
3835 }
3836
3837 void verify_ssh_host_key(void *frontend, char *host, int port, char *keytype,
3838                          char *keystr, char *fingerprint)
3839 {
3840     int ret;
3841
3842     static const char absentmsg[] =
3843         "The server's host key is not cached in the registry. You\n"
3844         "have no guarantee that the server is the computer you\n"
3845         "think it is.\n"
3846         "The server's key fingerprint is:\n"
3847         "%s\n"
3848         "If you trust this host, hit Yes to add the key to\n"
3849         "PuTTY's cache and carry on connecting.\n"
3850         "If you want to carry on connecting just once, without\n"
3851         "adding the key to the cache, hit No.\n"
3852         "If you do not trust this host, hit Cancel to abandon the\n"
3853         "connection.\n";
3854
3855     static const char wrongmsg[] =
3856         "WARNING - POTENTIAL SECURITY BREACH!\n"
3857         "\n"
3858         "The server's host key does not match the one PuTTY has\n"
3859         "cached in the registry. This means that either the\n"
3860         "server administrator has changed the host key, or you\n"
3861         "have actually connected to another computer pretending\n"
3862         "to be the server.\n"
3863         "The new key fingerprint is:\n"
3864         "%s\n"
3865         "If you were expecting this change and trust the new key,\n"
3866         "hit Yes to update PuTTY's cache and continue connecting.\n"
3867         "If you want to carry on connecting but without updating\n"
3868         "the cache, hit No.\n"
3869         "If you want to abandon the connection completely, hit\n"
3870         "Cancel. Hitting Cancel is the ONLY guaranteed safe\n" "choice.\n";
3871
3872     static const char mbtitle[] = "PuTTY Security Alert";
3873
3874     char message[160 +
3875         /* sensible fingerprint max size */
3876         (sizeof(absentmsg) > sizeof(wrongmsg) ?
3877          sizeof(absentmsg) : sizeof(wrongmsg))];
3878
3879     /*
3880      * Verify the key against the registry.
3881      */
3882     ret = verify_host_key(host, port, keytype, keystr);
3883
3884     if (ret == 0)                      /* success - key matched OK */
3885         return;
3886     if (ret == 2) {                    /* key was different */
3887         int mbret;
3888         sprintf(message, wrongmsg, fingerprint);
3889         mbret = MessageBox(NULL, message, mbtitle,
3890                            MB_ICONWARNING | MB_YESNOCANCEL);
3891         if (mbret == IDYES)
3892             store_host_key(host, port, keytype, keystr);
3893         if (mbret == IDCANCEL)
3894             cleanup_exit(0);
3895     }
3896     if (ret == 1) {                    /* key was absent */
3897         int mbret;
3898         sprintf(message, absentmsg, fingerprint);
3899         mbret = MessageBox(NULL, message, mbtitle,
3900                            MB_ICONWARNING | MB_YESNOCANCEL);
3901         if (mbret == IDYES)
3902             store_host_key(host, port, keytype, keystr);
3903         if (mbret == IDCANCEL)
3904             cleanup_exit(0);
3905     }
3906 }
3907
3908 /*
3909  * Ask whether the selected cipher is acceptable (since it was
3910  * below the configured 'warn' threshold).
3911  * cs: 0 = both ways, 1 = client->server, 2 = server->client
3912  */
3913 void askcipher(void *frontend, char *ciphername, int cs)
3914 {
3915     static const char mbtitle[] = "PuTTY Security Alert";
3916     static const char msg[] =
3917         "The first %.35scipher supported by the server\n"
3918         "is %.64s, which is below the configured\n"
3919         "warning threshold.\n"
3920         "Do you want to continue with this connection?\n";
3921     /* guessed cipher name + type max length */
3922     char message[100 + sizeof(msg)];
3923     int mbret;
3924
3925     sprintf(message, msg,
3926             (cs == 0) ? "" :
3927             (cs == 1) ? "client-to-server " :
3928                         "server-to-client ",
3929             ciphername);
3930     mbret = MessageBox(NULL, message, mbtitle,
3931                        MB_ICONWARNING | MB_YESNO);
3932     if (mbret == IDYES)
3933         return;
3934     else
3935         cleanup_exit(0);
3936 }
3937
3938 /*
3939  * Ask whether to wipe a session log file before writing to it.
3940  * Returns 2 for wipe, 1 for append, 0 for cancel (don't log).
3941  */
3942 int askappend(void *frontend, char *filename)
3943 {
3944     static const char mbtitle[] = "PuTTY Log to File";
3945     static const char msgtemplate[] =
3946         "The session log file \"%.*s\" already exists.\n"
3947         "You can overwrite it with a new session log,\n"
3948         "append your session log to the end of it,\n"
3949         "or disable session logging for this session.\n"
3950         "Hit Yes to wipe the file, No to append to it,\n"
3951         "or Cancel to disable logging.";
3952     char message[sizeof(msgtemplate) + FILENAME_MAX];
3953     int mbret;
3954     if (cfg.logxfovr != LGXF_ASK) {
3955         return ((cfg.logxfovr == LGXF_OVR) ? 2 : 1);
3956     }
3957     sprintf(message, msgtemplate, FILENAME_MAX, filename);
3958
3959     mbret = MessageBox(NULL, message, mbtitle,
3960                        MB_ICONQUESTION | MB_YESNOCANCEL);
3961     if (mbret == IDYES)
3962         return 2;
3963     else if (mbret == IDNO)
3964         return 1;
3965     else
3966         return 0;
3967 }
3968
3969 /*
3970  * Warn about the obsolescent key file format.
3971  * 
3972  * Uniquely among these functions, this one does _not_ expect a
3973  * frontend handle. This means that if PuTTY is ported to a
3974  * platform which requires frontend handles, this function will be
3975  * an anomaly. Fortunately, the problem it addresses will not have
3976  * been present on that platform, so it can plausibly be
3977  * implemented as an empty function.
3978  */
3979 void old_keyfile_warning(void)
3980 {
3981     static const char mbtitle[] = "PuTTY Key File Warning";
3982     static const char message[] =
3983         "You are loading an SSH 2 private key which has an\n"
3984         "old version of the file format. This means your key\n"
3985         "file is not fully tamperproof. Future versions of\n"
3986         "PuTTY may stop supporting this private key format,\n"
3987         "so we recommend you convert your key to the new\n"
3988         "format.\n"
3989         "\n"
3990         "You can perform this conversion by loading the key\n"
3991         "into PuTTYgen and then saving it again.";
3992
3993     MessageBox(NULL, message, mbtitle, MB_OK);
3994 }