15 static char **events
= NULL
;
16 static int nevents
= 0, negsize
= 0;
20 void force_normal(HWND hwnd
)
22 static int recurse
= 0;
30 wp
.length
= sizeof(wp
);
31 if (GetWindowPlacement(hwnd
, &wp
) && wp
.showCmd
== SW_SHOWMAXIMIZED
) {
32 wp
.showCmd
= SW_SHOWNORMAL
;
33 SetWindowPlacement(hwnd
, &wp
);
38 static void MyGetDlgItemInt(HWND hwnd
, int id
, int *result
)
42 n
= GetDlgItemInt(hwnd
, id
, &ok
, FALSE
);
47 static void MyGetDlgItemFlt(HWND hwnd
, int id
, int *result
, int scale
)
51 ok
= GetDlgItemText(hwnd
, id
, text
, sizeof(text
) - 1);
53 *result
= (int) (scale
* atof(text
));
56 static void MySetDlgItemFlt(HWND hwnd
, int id
, double value
)
59 sprintf(text
, "%g", value
);
60 SetDlgItemText(hwnd
, id
, text
);
63 static int CALLBACK
LogProc(HWND hwnd
, UINT msg
,
64 WPARAM wParam
, LPARAM lParam
)
71 static int tabs
[4] = { 78, 108 };
72 SendDlgItemMessage(hwnd
, IDN_LIST
, LB_SETTABSTOPS
, 2,
75 for (i
= 0; i
< nevents
; i
++)
76 SendDlgItemMessage(hwnd
, IDN_LIST
, LB_ADDSTRING
,
77 0, (LPARAM
) events
[i
]);
80 switch (LOWORD(wParam
)) {
84 SetActiveWindow(GetParent(hwnd
));
88 if (HIWORD(wParam
) == BN_CLICKED
||
89 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
92 selcount
= SendDlgItemMessage(hwnd
, IDN_LIST
,
93 LB_GETSELCOUNT
, 0, 0);
94 if (selcount
== 0) { /* don't even try to copy zero items */
99 selitems
= smalloc(selcount
* sizeof(int));
101 int count
= SendDlgItemMessage(hwnd
, IDN_LIST
,
108 static unsigned char sel_nl
[] = SEL_NL
;
110 if (count
== 0) { /* can't copy zero stuff */
116 for (i
= 0; i
< count
; i
++)
118 strlen(events
[selitems
[i
]]) + sizeof(sel_nl
);
120 clipdata
= smalloc(size
);
123 for (i
= 0; i
< count
; i
++) {
124 char *q
= events
[selitems
[i
]];
125 int qlen
= strlen(q
);
128 memcpy(p
, sel_nl
, sizeof(sel_nl
));
131 write_clip(clipdata
, size
, TRUE
);
136 for (i
= 0; i
< nevents
; i
++)
137 SendDlgItemMessage(hwnd
, IDN_LIST
, LB_SETSEL
,
146 SetActiveWindow(GetParent(hwnd
));
153 static int CALLBACK
LicenceProc(HWND hwnd
, UINT msg
,
154 WPARAM wParam
, LPARAM lParam
)
160 switch (LOWORD(wParam
)) {
173 static int CALLBACK
AboutProc(HWND hwnd
, UINT msg
,
174 WPARAM wParam
, LPARAM lParam
)
178 SetDlgItemText(hwnd
, IDA_VERSION
, ver
);
181 switch (LOWORD(wParam
)) {
184 EndDialog(hwnd
, TRUE
);
187 EnableWindow(hwnd
, 0);
188 DialogBox(hinst
, MAKEINTRESOURCE(IDD_LICENCEBOX
),
190 EnableWindow(hwnd
, 1);
191 SetActiveWindow(hwnd
);
195 /* Load web browser */
196 ShellExecute(hwnd
, "open",
197 "http://www.chiark.greenend.org.uk/~sgtatham/putty/",
198 0, 0, SW_SHOWDEFAULT
);
203 EndDialog(hwnd
, TRUE
);
210 * Null dialog procedure.
212 static int CALLBACK
NullDlgProc(HWND hwnd
, UINT msg
,
213 WPARAM wParam
, LPARAM lParam
)
218 static char savedsession
[2048];
221 IDC_ABOUT
, IDCX_TVSTATIC
, IDCX_TREEVIEW
, controlstartvalue
,
362 appearancepanelstart
,
363 IDC_TITLE_APPEARANCE
,
383 connectionpanelstart
,
384 IDC_TITLE_CONNECTION
,
485 translationpanelstart
,
486 IDC_TITLE_TRANSLATION
,
487 IDC_BOX_TRANSLATION1
,
488 IDC_BOX_TRANSLATION2
,
489 IDC_BOX_TRANSLATION3
,
514 static const char *const colours
[] = {
515 "Default Foreground", "Default Bold Foreground",
516 "Default Background", "Default Bold Background",
517 "Cursor Text", "Cursor Colour",
518 "ANSI Black", "ANSI Black Bold",
519 "ANSI Red", "ANSI Red Bold",
520 "ANSI Green", "ANSI Green Bold",
521 "ANSI Yellow", "ANSI Yellow Bold",
522 "ANSI Blue", "ANSI Blue Bold",
523 "ANSI Magenta", "ANSI Magenta Bold",
524 "ANSI Cyan", "ANSI Cyan Bold",
525 "ANSI White", "ANSI White Bold"
527 static const int permcolour
[] = {
528 TRUE
, FALSE
, TRUE
, FALSE
, TRUE
, TRUE
,
529 TRUE
, FALSE
, TRUE
, FALSE
, TRUE
, FALSE
, TRUE
, FALSE
,
530 TRUE
, FALSE
, TRUE
, FALSE
, TRUE
, FALSE
, TRUE
, FALSE
533 static void fmtfont(char *buf
)
535 sprintf(buf
, "Font: %s, ", cfg
.font
);
537 strcat(buf
, "bold, ");
538 if (cfg
.fontheight
== 0)
539 strcat(buf
, "default height");
541 sprintf(buf
+ strlen(buf
), "%d-point",
542 (cfg
.fontheight
< 0 ?
-cfg
.fontheight
: cfg
.fontheight
));
545 static void init_dlg_ctrls(HWND hwnd
)
548 char fontstatic
[256];
550 SetDlgItemText(hwnd
, IDC_HOST
, cfg
.host
);
551 SetDlgItemText(hwnd
, IDC_SESSEDIT
, savedsession
);
554 n
= SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_GETCOUNT
, 0, 0);
555 for (i
= n
; i
-- > 0;)
556 SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_DELETESTRING
, i
, 0);
557 for (i
= 0; i
< nsessions
; i
++)
558 SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_ADDSTRING
,
559 0, (LPARAM
) (sessions
[i
]));
561 SetDlgItemInt(hwnd
, IDC_PORT
, cfg
.port
, FALSE
);
562 CheckRadioButton(hwnd
, IDC_PROTRAW
, IDC_PROTSSH
,
563 cfg
.protocol
== PROT_SSH ? IDC_PROTSSH
:
564 cfg
.protocol
== PROT_TELNET ? IDC_PROTTELNET
:
566 PROT_RLOGIN ? IDC_PROTRLOGIN
: IDC_PROTRAW
);
567 SetDlgItemInt(hwnd
, IDC_PINGEDIT
, cfg
.ping_interval
, FALSE
);
569 CheckRadioButton(hwnd
, IDC_DEL008
, IDC_DEL127
,
570 cfg
.bksp_is_delete ? IDC_DEL127
: IDC_DEL008
);
571 CheckRadioButton(hwnd
, IDC_HOMETILDE
, IDC_HOMERXVT
,
572 cfg
.rxvt_homeend ? IDC_HOMERXVT
: IDC_HOMETILDE
);
573 CheckRadioButton(hwnd
, IDC_FUNCTILDE
, IDC_FUNCSCO
,
574 cfg
.funky_type
== 0 ? IDC_FUNCTILDE
:
575 cfg
.funky_type
== 1 ? IDC_FUNCLINUX
:
576 cfg
.funky_type
== 2 ? IDC_FUNCXTERM
:
577 cfg
.funky_type
== 3 ? IDC_FUNCVT400
:
578 cfg
.funky_type
== 4 ? IDC_FUNCVT100P
:
579 cfg
.funky_type
== 5 ? IDC_FUNCSCO
: IDC_FUNCTILDE
);
580 CheckDlgButton(hwnd
, IDC_NOAPPLICC
, cfg
.no_applic_c
);
581 CheckDlgButton(hwnd
, IDC_NOAPPLICK
, cfg
.no_applic_k
);
582 CheckRadioButton(hwnd
, IDC_CURNORMAL
, IDC_CURAPPLIC
,
583 cfg
.app_cursor ? IDC_CURAPPLIC
: IDC_CURNORMAL
);
584 CheckRadioButton(hwnd
, IDC_KPNORMAL
, IDC_KPNH
,
585 cfg
.nethack_keypad ? IDC_KPNH
:
586 cfg
.app_keypad ? IDC_KPAPPLIC
: IDC_KPNORMAL
);
587 CheckDlgButton(hwnd
, IDC_ALTF4
, cfg
.alt_f4
);
588 CheckDlgButton(hwnd
, IDC_ALTSPACE
, cfg
.alt_space
);
589 CheckDlgButton(hwnd
, IDC_ALTONLY
, cfg
.alt_only
);
590 CheckDlgButton(hwnd
, IDC_COMPOSEKEY
, cfg
.compose_key
);
591 CheckDlgButton(hwnd
, IDC_CTRLALTKEYS
, cfg
.ctrlaltkeys
);
592 CheckDlgButton(hwnd
, IDC_TELNETKEY
, cfg
.telnet_keyboard
);
593 CheckRadioButton(hwnd
, IDC_ECHOBACKEND
, IDC_ECHONO
,
594 cfg
.localecho
== LD_BACKEND ? IDC_ECHOBACKEND
:
595 cfg
.localecho
== LD_YES ? IDC_ECHOYES
: IDC_ECHONO
);
596 CheckRadioButton(hwnd
, IDC_EDITBACKEND
, IDC_EDITNO
,
597 cfg
.localedit
== LD_BACKEND ? IDC_EDITBACKEND
:
598 cfg
.localedit
== LD_YES ? IDC_EDITYES
: IDC_EDITNO
);
599 SetDlgItemText(hwnd
, IDC_ANSWEREDIT
, cfg
.answerback
);
600 CheckDlgButton(hwnd
, IDC_ALWAYSONTOP
, cfg
.alwaysontop
);
601 CheckDlgButton(hwnd
, IDC_SCROLLKEY
, cfg
.scroll_on_key
);
602 CheckDlgButton(hwnd
, IDC_SCROLLDISP
, cfg
.scroll_on_disp
);
604 CheckDlgButton(hwnd
, IDC_WRAPMODE
, cfg
.wrap_mode
);
605 CheckDlgButton(hwnd
, IDC_DECOM
, cfg
.dec_om
);
606 CheckDlgButton(hwnd
, IDC_LFHASCR
, cfg
.lfhascr
);
607 SetDlgItemInt(hwnd
, IDC_ROWSEDIT
, cfg
.height
, FALSE
);
608 SetDlgItemInt(hwnd
, IDC_COLSEDIT
, cfg
.width
, FALSE
);
609 SetDlgItemInt(hwnd
, IDC_SAVEEDIT
, cfg
.savelines
, FALSE
);
611 SetDlgItemText(hwnd
, IDC_FONTSTATIC
, fontstatic
);
612 CheckRadioButton(hwnd
, IDC_BELL_DISABLED
, IDC_BELL_VISUAL
,
613 cfg
.beep
== BELL_DISABLED ? IDC_BELL_DISABLED
:
614 cfg
.beep
== BELL_DEFAULT ? IDC_BELL_DEFAULT
:
615 cfg
.beep
== BELL_WAVEFILE ? IDC_BELL_WAVEFILE
:
617 BELL_VISUAL ? IDC_BELL_VISUAL
: IDC_BELL_DEFAULT
);
618 SetDlgItemText(hwnd
, IDC_BELL_WAVEEDIT
, cfg
.bell_wavefile
);
619 CheckDlgButton(hwnd
, IDC_BELLOVL
, cfg
.bellovl
);
620 SetDlgItemInt(hwnd
, IDC_BELLOVLN
, cfg
.bellovl_n
, FALSE
);
621 MySetDlgItemFlt(hwnd
, IDC_BELLOVLT
, cfg
.bellovl_t
/ 1000.0);
622 MySetDlgItemFlt(hwnd
, IDC_BELLOVLS
, cfg
.bellovl_s
/ 1000.0);
624 CheckDlgButton(hwnd
, IDC_BCE
, cfg
.bce
);
625 CheckDlgButton(hwnd
, IDC_BLINKTEXT
, cfg
.blinktext
);
627 SetDlgItemText(hwnd
, IDC_WINEDIT
, cfg
.wintitle
);
628 CheckDlgButton(hwnd
, IDC_WINNAME
, cfg
.win_name_always
);
629 CheckDlgButton(hwnd
, IDC_HIDEMOUSE
, cfg
.hide_mouseptr
);
630 CheckDlgButton(hwnd
, IDC_SUNKENEDGE
, cfg
.sunken_edge
);
631 CheckRadioButton(hwnd
, IDC_CURBLOCK
, IDC_CURVERT
,
632 cfg
.cursor_type
== 0 ? IDC_CURBLOCK
:
633 cfg
.cursor_type
== 1 ? IDC_CURUNDER
: IDC_CURVERT
);
634 CheckDlgButton(hwnd
, IDC_BLINKCUR
, cfg
.blink_cur
);
635 CheckDlgButton(hwnd
, IDC_SCROLLBAR
, cfg
.scrollbar
);
636 CheckDlgButton(hwnd
, IDC_LOCKSIZE
, cfg
.locksize
);
637 CheckRadioButton(hwnd
, IDC_COEALWAYS
, IDC_COENORMAL
,
638 cfg
.close_on_exit
== COE_NORMAL ? IDC_COENORMAL
:
640 COE_NEVER ? IDC_COENEVER
: IDC_COEALWAYS
);
641 CheckDlgButton(hwnd
, IDC_CLOSEWARN
, cfg
.warn_on_close
);
643 SetDlgItemText(hwnd
, IDC_TTEDIT
, cfg
.termtype
);
644 SetDlgItemText(hwnd
, IDC_TSEDIT
, cfg
.termspeed
);
645 SetDlgItemText(hwnd
, IDC_R_TSEDIT
, cfg
.termspeed
);
646 SetDlgItemText(hwnd
, IDC_RLLUSEREDIT
, cfg
.localusername
);
647 SetDlgItemText(hwnd
, IDC_LOGEDIT
, cfg
.username
);
648 SetDlgItemText(hwnd
, IDC_LGFEDIT
, cfg
.logfilename
);
649 CheckRadioButton(hwnd
, IDC_LSTATOFF
, IDC_LSTATRAW
,
650 cfg
.logtype
== 0 ? IDC_LSTATOFF
:
651 cfg
.logtype
== 1 ? IDC_LSTATASCII
: IDC_LSTATRAW
);
652 CheckRadioButton(hwnd
, IDC_LSTATXOVR
, IDC_LSTATXASK
,
653 cfg
.logxfovr
== LGXF_OVR ? IDC_LSTATXOVR
:
654 cfg
.logxfovr
== LGXF_ASK ? IDC_LSTATXASK
:
657 char *p
= cfg
.environmt
;
659 SendDlgItemMessage(hwnd
, IDC_ENVLIST
, LB_ADDSTRING
, 0,
664 CheckRadioButton(hwnd
, IDC_EMBSD
, IDC_EMRFC
,
665 cfg
.rfc_environ ? IDC_EMRFC
: IDC_EMBSD
);
666 CheckRadioButton(hwnd
, IDC_TPASSIVE
, IDC_TACTIVE
,
667 cfg
.passive_telnet ? IDC_TPASSIVE
: IDC_TACTIVE
);
669 SetDlgItemText(hwnd
, IDC_TTEDIT
, cfg
.termtype
);
670 SetDlgItemText(hwnd
, IDC_LOGEDIT
, cfg
.username
);
671 CheckDlgButton(hwnd
, IDC_NOPTY
, cfg
.nopty
);
672 CheckDlgButton(hwnd
, IDC_COMPRESS
, cfg
.compression
);
673 CheckDlgButton(hwnd
, IDC_BUGGYMAC
, cfg
.buggymac
);
674 CheckDlgButton(hwnd
, IDC_AGENTFWD
, cfg
.agentfwd
);
675 CheckRadioButton(hwnd
, IDC_CIPHER3DES
, IDC_CIPHERAES
,
676 cfg
.cipher
== CIPHER_BLOWFISH ? IDC_CIPHERBLOWF
:
677 cfg
.cipher
== CIPHER_DES ? IDC_CIPHERDES
:
678 cfg
.cipher
== CIPHER_AES ? IDC_CIPHERAES
:
680 CheckRadioButton(hwnd
, IDC_SSHPROT1
, IDC_SSHPROT2
,
681 cfg
.sshprot
== 1 ? IDC_SSHPROT1
: IDC_SSHPROT2
);
682 CheckDlgButton(hwnd
, IDC_AUTHTIS
, cfg
.try_tis_auth
);
683 SetDlgItemText(hwnd
, IDC_PKEDIT
, cfg
.keyfile
);
684 SetDlgItemText(hwnd
, IDC_CMDEDIT
, cfg
.remote_cmd
);
686 CheckRadioButton(hwnd
, IDC_MBWINDOWS
, IDC_MBXTERM
,
687 cfg
.mouse_is_xterm ? IDC_MBXTERM
: IDC_MBWINDOWS
);
688 CheckDlgButton(hwnd
, IDC_RAWCNP
, cfg
.rawcnp
);
690 static int tabs
[4] = { 25, 61, 96, 128 };
691 SendDlgItemMessage(hwnd
, IDC_CCLIST
, LB_SETTABSTOPS
, 4,
694 for (i
= 0; i
< 256; i
++) {
696 sprintf(str
, "%d\t(0x%02X)\t%c\t%d", i
, i
,
697 (i
>= 0x21 && i
!= 0x7F) ? i
: ' ', cfg
.wordness
[i
]);
698 SendDlgItemMessage(hwnd
, IDC_CCLIST
, LB_ADDSTRING
, 0,
702 CheckDlgButton(hwnd
, IDC_BOLDCOLOUR
, cfg
.bold_colour
);
703 CheckDlgButton(hwnd
, IDC_PALETTE
, cfg
.try_palette
);
706 n
= SendDlgItemMessage(hwnd
, IDC_COLOURLIST
, LB_GETCOUNT
, 0, 0);
707 for (i
= n
; i
-- > 0;)
708 SendDlgItemMessage(hwnd
, IDC_COLOURLIST
,
709 LB_DELETESTRING
, i
, 0);
710 for (i
= 0; i
< 22; i
++)
711 if (cfg
.bold_colour
|| permcolour
[i
])
712 SendDlgItemMessage(hwnd
, IDC_COLOURLIST
, LB_ADDSTRING
, 0,
713 (LPARAM
) colours
[i
]);
715 SendDlgItemMessage(hwnd
, IDC_COLOURLIST
, LB_SETCURSEL
, 0, 0);
716 SetDlgItemInt(hwnd
, IDC_RVALUE
, cfg
.colours
[0][0], FALSE
);
717 SetDlgItemInt(hwnd
, IDC_GVALUE
, cfg
.colours
[0][1], FALSE
);
718 SetDlgItemInt(hwnd
, IDC_BVALUE
, cfg
.colours
[0][2], FALSE
);
720 CheckRadioButton(hwnd
, IDC_NOXLAT
, IDC_88592CP852
,
721 cfg
.xlat_88592w1250 ? IDC_88592WIN1250
:
722 cfg
.xlat_88592cp852 ? IDC_88592CP852
:
723 cfg
.xlat_enablekoiwin ? IDC_KOI8WIN1251
: IDC_NOXLAT
);
724 CheckDlgButton(hwnd
, IDC_CAPSLOCKCYR
, cfg
.xlat_capslockcyr
);
725 CheckRadioButton(hwnd
, IDC_VTXWINDOWS
, IDC_VTPOORMAN
,
726 cfg
.vtmode
== VT_XWINDOWS ? IDC_VTXWINDOWS
:
727 cfg
.vtmode
== VT_OEMANSI ? IDC_VTOEMANSI
:
728 cfg
.vtmode
== VT_OEMONLY ? IDC_VTOEMONLY
:
731 CheckDlgButton(hwnd
, IDC_X11_FORWARD
, cfg
.x11_forward
);
732 SetDlgItemText(hwnd
, IDC_X11_DISPLAY
, cfg
.x11_display
);
735 struct treeview_faff
{
740 static HTREEITEM
treeview_insert(struct treeview_faff
*faff
,
741 int level
, char *text
)
746 ins
.hParent
= (level
> 0 ? faff
->lastat
[level
- 1] : TVI_ROOT
);
747 ins
.hInsertAfter
= faff
->lastat
[level
];
748 #if _WIN32_IE >= 0x0400 && defined NONAMELESSUNION
749 #define INSITEM DUMMYUNIONNAME.item
753 ins
.INSITEM
.mask
= TVIF_TEXT
;
754 ins
.INSITEM
.pszText
= text
;
755 newitem
= TreeView_InsertItem(faff
->treeview
, &ins
);
757 TreeView_Expand(faff
->treeview
, faff
->lastat
[level
- 1],
759 faff
->lastat
[level
] = newitem
;
760 for (i
= level
+ 1; i
< 4; i
++)
761 faff
->lastat
[i
] = NULL
;
766 * Create the panelfuls of controls in the configuration box.
768 static void create_controls(HWND hwnd
, int dlgtype
, int panel
)
770 if (panel
== sessionpanelstart
) {
771 /* The Session panel. Accelerators used: [acgo] nprtih elsd w */
773 ctlposinit(&cp
, hwnd
, 80, 3, 13);
774 bartitle(&cp
, "Basic options for your PuTTY session",
777 beginbox(&cp
, "Specify your connection by host name",
780 "Host &Name", IDC_HOSTSTATIC
, IDC_HOST
, 75,
781 "&Port", IDC_PORTSTATIC
, IDC_PORT
, 25, NULL
);
782 if (backends
[3].backend
== NULL
) {
783 /* this is PuTTYtel, so only three protocols available */
784 radioline(&cp
, "Protocol:", IDC_PROTSTATIC
, 4,
786 "&Telnet", IDC_PROTTELNET
,
787 "Rlog&in", IDC_PROTRLOGIN
, NULL
);
789 radioline(&cp
, "Protocol:", IDC_PROTSTATIC
, 4,
791 "&Telnet", IDC_PROTTELNET
,
792 "Rlog&in", IDC_PROTRLOGIN
,
801 beginbox(&cp
, "Load, save or delete a stored session",
803 sesssaver(&cp
, "Sav&ed Sessions",
804 IDC_SESSSTATIC
, IDC_SESSEDIT
, IDC_SESSLIST
,
805 "&Load", IDC_SESSLOAD
,
806 "&Save", IDC_SESSSAVE
, "&Delete", IDC_SESSDEL
, NULL
);
809 beginbox(&cp
, NULL
, IDC_BOX_SESSION3
);
810 radioline(&cp
, "Close &window on exit:", IDC_CLOSEEXIT
, 4,
811 "Always", IDC_COEALWAYS
,
812 "Never", IDC_COENEVER
,
813 "Only on clean exit", IDC_COENORMAL
, NULL
);
817 if (panel
== loggingpanelstart
) {
818 /* The Logging panel. Accelerators used: [acgo] tplfwe */
820 ctlposinit(&cp
, hwnd
, 80, 3, 13);
821 bartitle(&cp
, "Options controlling session logging",
823 beginbox(&cp
, NULL
, IDC_BOX_LOGGING1
);
825 "Session logging:", IDC_LSTATSTATIC
,
826 "Logging &turned off completely", IDC_LSTATOFF
,
827 "Log &printable output only", IDC_LSTATASCII
,
828 "&Log all session output", IDC_LSTATRAW
, NULL
);
829 editbutton(&cp
, "Log &file name:",
830 IDC_LGFSTATIC
, IDC_LGFEDIT
, "Bro&wse...",
833 "What to do if the log file already &exists:",
834 IDC_LSTATXIST
, "Always overwrite it", IDC_LSTATXOVR
,
835 "Always append to the end of it", IDC_LSTATXAPN
,
836 "Ask the user every time", IDC_LSTATXASK
, NULL
);
840 if (panel
== terminalpanelstart
) {
841 /* The Terminal panel. Accelerators used: [acgo] wdlen hts */
843 ctlposinit(&cp
, hwnd
, 80, 3, 13);
844 bartitle(&cp
, "Options controlling the terminal emulation",
846 beginbox(&cp
, "Set various terminal options", IDC_BOX_TERMINAL1
);
847 checkbox(&cp
, "Auto &wrap mode initially on", IDC_WRAPMODE
);
848 checkbox(&cp
, "&DEC Origin Mode initially on", IDC_DECOM
);
849 checkbox(&cp
, "Implicit CR in every &LF", IDC_LFHASCR
);
850 checkbox(&cp
, "Use background colour to &erase screen", IDC_BCE
);
851 checkbox(&cp
, "Enable bli&nking text", IDC_BLINKTEXT
);
853 "An&swerback to ^E:", IDC_ANSWERBACK
,
854 IDC_ANSWEREDIT
, 100, NULL
);
857 beginbox(&cp
, "Line discipline options", IDC_BOX_TERMINAL2
);
858 radioline(&cp
, "Local ec&ho:", IDC_ECHOSTATIC
, 3,
859 "Auto", IDC_ECHOBACKEND
,
860 "Force on", IDC_ECHOYES
, "Force off", IDC_ECHONO
, NULL
);
861 radioline(&cp
, "Local line edi&ting:", IDC_EDITSTATIC
, 3,
862 "Auto", IDC_EDITBACKEND
,
863 "Force on", IDC_EDITYES
, "Force off", IDC_EDITNO
, NULL
);
867 if (panel
== bellpanelstart
) {
868 /* The Bell panel. Accelerators used: [acgo] bdsm wt */
870 ctlposinit(&cp
, hwnd
, 80, 3, 13);
871 bartitle(&cp
, "Options controlling the terminal bell",
873 beginbox(&cp
, "Set the style of bell", IDC_BOX_BELL1
);
875 "Action to happen when a &bell occurs:", IDC_BELLSTATIC
,
876 "None (bell disabled)", IDC_BELL_DISABLED
,
877 "Play Windows Default Sound", IDC_BELL_DEFAULT
,
878 "Play a custom sound file", IDC_BELL_WAVEFILE
,
879 "Visual bell (flash window)", IDC_BELL_VISUAL
, NULL
);
880 editbutton(&cp
, "Custom sound file to play as a bell:",
881 IDC_BELL_WAVESTATIC
, IDC_BELL_WAVEEDIT
,
882 "Bro&wse...", IDC_BELL_WAVEBROWSE
);
884 beginbox(&cp
, "Control the bell overload behaviour",
886 checkbox(&cp
, "Bell is temporarily &disabled when over-used",
888 staticedit(&cp
, "Over-use means this &many bells...",
889 IDC_BELLOVLNSTATIC
, IDC_BELLOVLN
, 20);
890 staticedit(&cp
, "... in &this many seconds",
891 IDC_BELLOVLTSTATIC
, IDC_BELLOVLT
, 20);
893 "The bell is re-enabled after a few seconds of silence.",
895 staticedit(&cp
, "Seconds of &silence required", IDC_BELLOVLSSTATIC
,
900 if (panel
== keyboardpanelstart
) {
901 /* The Keyboard panel. Accelerators used: [acgo] bhf ruyntd */
903 ctlposinit(&cp
, hwnd
, 80, 3, 13);
905 bartitle(&cp, "Options controlling the effects of keys",
908 beginbox(&cp
, "Change the sequences sent by:", IDC_BOX_KEYBOARD1
);
909 radioline(&cp
, "The &Backspace key", IDC_DELSTATIC
, 2,
910 "Control-H", IDC_DEL008
,
911 "Control-? (127)", IDC_DEL127
, NULL
);
912 radioline(&cp
, "The &Home and End keys", IDC_HOMESTATIC
, 2,
913 "Standard", IDC_HOMETILDE
, "rxvt", IDC_HOMERXVT
, NULL
);
914 radioline(&cp
, "The &Function keys and keypad", IDC_FUNCSTATIC
, 3,
915 "ESC[n~", IDC_FUNCTILDE
,
916 "Linux", IDC_FUNCLINUX
,
917 "Xterm R6", IDC_FUNCXTERM
,
918 "VT400", IDC_FUNCVT400
,
919 "VT100+", IDC_FUNCVT100P
, "SCO", IDC_FUNCSCO
, NULL
);
921 beginbox(&cp
, "Application keypad settings:", IDC_BOX_KEYBOARD2
);
923 "Application c&ursor keys totally disabled",
925 radioline(&cp
, "Initial state of cu&rsor keys:", IDC_CURSTATIC
, 2,
926 "Normal", IDC_CURNORMAL
,
927 "Application", IDC_CURAPPLIC
, NULL
);
929 "Application ke&ypad keys totally disabled",
931 radioline(&cp
, "Initial state of &numeric keypad:", IDC_KPSTATIC
,
932 3, "Normal", IDC_KPNORMAL
, "Application", IDC_KPAPPLIC
,
933 "NetHack", IDC_KPNH
, NULL
);
935 beginbox(&cp
, "Enable extra keyboard features:",
937 checkbox(&cp
, "AltGr ac&ts as Compose key", IDC_COMPOSEKEY
);
938 checkbox(&cp
, "Control-Alt is &different from AltGr",
943 if (panel
== windowpanelstart
) {
944 /* The Window panel. Accelerators used: [acgo] rmz sdkp w4ylt */
946 ctlposinit(&cp
, hwnd
, 80, 3, 13);
947 bartitle(&cp
, "Options controlling PuTTY's window",
949 beginbox(&cp
, "Set the size of the window", IDC_BOX_WINDOW1
);
951 "&Rows", IDC_ROWSSTATIC
, IDC_ROWSEDIT
, 50,
952 "Colu&mns", IDC_COLSSTATIC
, IDC_COLSEDIT
, 50, NULL
);
953 checkbox(&cp
, "Lock window size against resi&zing", IDC_LOCKSIZE
);
955 beginbox(&cp
, "Control the scrollback in the window",
957 staticedit(&cp
, "Lines of &scrollback",
958 IDC_SAVESTATIC
, IDC_SAVEEDIT
, 50);
959 checkbox(&cp
, "&Display scrollbar", IDC_SCROLLBAR
);
960 checkbox(&cp
, "Reset scrollback on &keypress", IDC_SCROLLKEY
);
961 checkbox(&cp
, "Reset scrollback on dis&play activity",
964 beginbox(&cp
, NULL
, IDC_BOX_WINDOW3
);
965 checkbox(&cp
, "&Warn before closing window", IDC_CLOSEWARN
);
966 checkbox(&cp
, "Window closes on ALT-F&4", IDC_ALTF4
);
967 checkbox(&cp
, "S&ystem menu appears on ALT-Space", IDC_ALTSPACE
);
968 checkbox(&cp
, "System menu appears on A< alone", IDC_ALTONLY
);
969 checkbox(&cp
, "Ensure window is always on &top", IDC_ALWAYSONTOP
);
973 if (panel
== appearancepanelstart
) {
974 /* The Appearance panel. Accelerators used: [acgo] luvb h ti p s */
976 ctlposinit(&cp
, hwnd
, 80, 3, 13);
977 bartitle(&cp
, "Options controlling PuTTY's appearance",
978 IDC_TITLE_APPEARANCE
);
979 beginbox(&cp
, "Adjust the use of the cursor", IDC_BOX_APPEARANCE1
);
980 radioline(&cp
, "Cursor appearance:", IDC_CURSORSTATIC
, 3,
981 "B&lock", IDC_CURBLOCK
,
982 "&Underline", IDC_CURUNDER
,
983 "&Vertical line", IDC_CURVERT
, NULL
);
984 checkbox(&cp
, "Cursor &blinks", IDC_BLINKCUR
);
986 beginbox(&cp
, "Set the font used in the terminal window",
987 IDC_BOX_APPEARANCE2
);
988 staticbtn(&cp
, "", IDC_FONTSTATIC
, "C&hange...", IDC_CHOOSEFONT
);
990 beginbox(&cp
, "Adjust the use of the window title",
991 IDC_BOX_APPEARANCE3
);
993 "Window &title:", IDC_WINTITLE
, IDC_WINEDIT
, 100, NULL
);
994 checkbox(&cp
, "Avoid ever using &icon title", IDC_WINNAME
);
996 beginbox(&cp
, "Adjust the use of the mouse pointer",
997 IDC_BOX_APPEARANCE4
);
998 checkbox(&cp
, "Hide mouse &pointer when typing in window",
1001 beginbox(&cp
, "Adjust the window border", IDC_BOX_APPEARANCE5
);
1002 checkbox(&cp
, "&Sunken-edge border (slightly thicker)",
1007 if (panel
== translationpanelstart
) {
1008 /* The Translation panel. Accelerators used: [acgo] xbep t s */
1010 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1011 bartitle(&cp
, "Options controlling character set translation",
1012 IDC_TITLE_TRANSLATION
);
1013 beginbox(&cp
, "Adjust how PuTTY displays line drawing characters",
1014 IDC_BOX_TRANSLATION1
);
1016 "Handling of line drawing characters:", IDC_VTSTATIC
,
1017 "Font has &XWindows encoding", IDC_VTXWINDOWS
,
1018 "Use font in &both ANSI and OEM modes", IDC_VTOEMANSI
,
1019 "Use font in O&EM mode only", IDC_VTOEMONLY
,
1020 "&Poor man's line drawing (" "+" ", " "-" " and " "|" ")",
1021 IDC_VTPOORMAN
, NULL
);
1023 beginbox(&cp
, "Enable character set translation on received data",
1024 IDC_BOX_TRANSLATION2
);
1026 "Character set &translation:", IDC_XLATSTATIC
,
1028 "KOI8 / Win-1251", IDC_KOI8WIN1251
,
1029 "ISO-8859-2 / Win-1250", IDC_88592WIN1250
,
1030 "ISO-8859-2 / CP852", IDC_88592CP852
, NULL
);
1032 beginbox(&cp
, "Enable character set translation on input data",
1033 IDC_BOX_TRANSLATION3
);
1034 checkbox(&cp
, "CAP&S LOCK acts as cyrillic switch",
1039 if (panel
== selectionpanelstart
) {
1040 /* The Selection panel. Accelerators used: [acgo] d wx hst */
1042 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1043 bartitle(&cp
, "Options controlling copy and paste",
1044 IDC_TITLE_SELECTION
);
1045 beginbox(&cp
, "Translation of pasted characters",
1046 IDC_BOX_SELECTION1
);
1048 "&Don't translate line drawing chars into +, - and |",
1051 beginbox(&cp
, "Control which mouse button does which thing",
1052 IDC_BOX_SELECTION2
);
1053 radiobig(&cp
, "Action of mouse buttons:", IDC_MBSTATIC
,
1054 "&Windows (Right pastes, Middle extends)", IDC_MBWINDOWS
,
1055 "&xterm (Right extends, Middle pastes)", IDC_MBXTERM
,
1058 beginbox(&cp
, "Control the select-one-word-at-a-time mode",
1059 IDC_BOX_SELECTION3
);
1060 charclass(&cp
, "C&haracter classes:", IDC_CCSTATIC
, IDC_CCLIST
,
1061 "&Set", IDC_CCSET
, IDC_CCEDIT
,
1062 "&to class", IDC_CCSTATIC2
);
1066 if (panel
== colourspanelstart
) {
1067 /* The Colours panel. Accelerators used: [acgo] blum */
1069 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1070 bartitle(&cp
, "Options controlling use of colours",
1072 beginbox(&cp
, "General options for colour usage",
1074 checkbox(&cp
, "&Bolded text is a different colour",
1076 checkbox(&cp
, "Attempt to use &logical palettes", IDC_PALETTE
);
1078 beginbox(&cp
, "Adjust the precise colours PuTTY displays",
1080 colouredit(&cp
, "Select a colo&ur and then click to modify it:",
1081 IDC_COLOURSTATIC
, IDC_COLOURLIST
,
1082 "&Modify...", IDC_CHANGE
,
1083 "Red:", IDC_RSTATIC
, IDC_RVALUE
,
1084 "Green:", IDC_GSTATIC
, IDC_GVALUE
,
1085 "Blue:", IDC_BSTATIC
, IDC_BVALUE
, NULL
);
1089 if (panel
== connectionpanelstart
) {
1090 /* The Connection panel. Accelerators used: [acgo] tuk */
1092 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1093 bartitle(&cp
, "Options controlling the connection",
1094 IDC_TITLE_CONNECTION
);
1096 beginbox(&cp
, "Data to send to the server",
1097 IDC_BOX_CONNECTION1
);
1098 staticedit(&cp
, "Terminal-&type string", IDC_TTSTATIC
,
1100 staticedit(&cp
, "Auto-login &username", IDC_LOGSTATIC
,
1104 beginbox(&cp
, "Adjust telnet session.", IDC_BOX_CONNECTION1
);
1105 checkbox(&cp
, "Keyboard sends telnet Backspace and Interrupt",
1109 beginbox(&cp
, "Sending of null packets to keep session active",
1110 IDC_BOX_CONNECTION2
);
1111 staticedit(&cp
, "Seconds between &keepalives (0 to turn off)",
1112 IDC_PINGSTATIC
, IDC_PINGEDIT
, 20);
1116 if (panel
== telnetpanelstart
) {
1117 /* The Telnet panel. Accelerators used: [acgo] svldr bftk */
1119 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1121 bartitle(&cp
, "Options controlling Telnet connections",
1123 beginbox(&cp
, "Data to send to the server", IDC_BOX_TELNET1
);
1124 staticedit(&cp
, "Terminal-&speed string", IDC_TSSTATIC
,
1126 envsetter(&cp
, "Environment variables:", IDC_ENVSTATIC
,
1127 "&Variable", IDC_VARSTATIC
, IDC_VAREDIT
, "Va&lue",
1128 IDC_VALSTATIC
, IDC_VALEDIT
, IDC_ENVLIST
, "A&dd",
1129 IDC_ENVADD
, "&Remove", IDC_ENVREMOVE
);
1131 beginbox(&cp
, "Telnet protocol adjustments", IDC_BOX_TELNET2
);
1132 radioline(&cp
, "Handling of OLD_ENVIRON ambiguity:",
1133 IDC_EMSTATIC
, 2, "&BSD (commonplace)", IDC_EMBSD
,
1134 "R&FC 1408 (unusual)", IDC_EMRFC
, NULL
);
1135 radioline(&cp
, "&Telnet negotiation mode:", IDC_ACTSTATIC
, 2,
1136 "Passive", IDC_TPASSIVE
, "Active",
1138 checkbox(&cp
, "&Keyboard sends telnet Backspace and Interrupt",
1144 if (panel
== rloginpanelstart
) {
1145 /* The Rlogin panel. Accelerators used: [acgo] sl */
1147 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1149 bartitle(&cp
, "Options controlling Rlogin connections",
1151 beginbox(&cp
, "Data to send to the server", IDC_BOX_RLOGIN1
);
1152 staticedit(&cp
, "Terminal-&speed string", IDC_R_TSSTATIC
,
1154 staticedit(&cp
, "&Local username:", IDC_RLLUSERSTATIC
,
1155 IDC_RLLUSEREDIT
, 50);
1160 if (panel
== sshpanelstart
) {
1161 /* The SSH panel. Accelerators used: [acgo] rmfkw pe123bds i */
1163 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1165 bartitle(&cp
, "Options controlling SSH connections",
1167 beginbox(&cp
, "Data to send to the server", IDC_BOX_SSH1
);
1169 "&Remote command:", IDC_CMDSTATIC
, IDC_CMDEDIT
, 100,
1172 beginbox(&cp
, "Authentication options", IDC_BOX_SSH2
);
1173 checkbox(&cp
, "Atte&mpt TIS or CryptoCard authentication",
1175 checkbox(&cp
, "Allow agent &forwarding", IDC_AGENTFWD
);
1176 editbutton(&cp
, "Private &key file for authentication:",
1177 IDC_PKSTATIC
, IDC_PKEDIT
, "Bro&wse...",
1180 beginbox(&cp
, "Protocol options", IDC_BOX_SSH3
);
1181 checkbox(&cp
, "Don't allocate a &pseudo-terminal", IDC_NOPTY
);
1182 checkbox(&cp
, "Enable compr&ession", IDC_COMPRESS
);
1183 radioline(&cp
, "Preferred SSH protocol version:",
1184 IDC_SSHPROTSTATIC
, 2,
1185 "&1", IDC_SSHPROT1
, "&2", IDC_SSHPROT2
, NULL
);
1186 radioline(&cp
, "Preferred encryption algorithm:",
1187 IDC_CIPHERSTATIC
, 4, "&3DES", IDC_CIPHER3DES
,
1188 "&Blowfish", IDC_CIPHERBLOWF
, "&DES", IDC_CIPHERDES
,
1189 "AE&S", IDC_CIPHERAES
, NULL
);
1190 checkbox(&cp
, "&Imitate SSH 2 MAC bug in commercial <= v2.3.x",
1196 if (panel
== tunnelspanelstart
) {
1197 /* The Tunnels panel. Accelerators used: [acgo] ex */
1199 ctlposinit(&cp
, hwnd
, 80, 3, 13);
1201 bartitle(&cp
, "Options controlling SSH tunnelling",
1203 beginbox(&cp
, "X11 forwarding options", IDC_BOX_TUNNELS
);
1204 checkbox(&cp
, "&Enable X11 forwarding", IDC_X11_FORWARD
);
1205 multiedit(&cp
, "&X display location", IDC_X11_DISPSTATIC
,
1206 IDC_X11_DISPLAY
, 50, NULL
);
1213 * This function is the configuration box.
1215 static int GenericMainDlgProc(HWND hwnd
, UINT msg
,
1216 WPARAM wParam
, LPARAM lParam
, int dlgtype
)
1219 struct treeview_faff tvfaff
;
1222 char filename
[sizeof(cfg
.keyfile
)];
1225 char fontstatic
[256];
1227 struct servent
*service
;
1233 SetWindowLong(hwnd
, GWL_USERDATA
, 0);
1235 * Centre the window.
1237 { /* centre the window */
1240 hw
= GetDesktopWindow();
1241 if (GetWindowRect(hw
, &rs
) && GetWindowRect(hwnd
, &rd
))
1243 (rs
.right
+ rs
.left
+ rd
.left
- rd
.right
) / 2,
1244 (rs
.bottom
+ rs
.top
+ rd
.top
- rd
.bottom
) / 2,
1245 rd
.right
- rd
.left
, rd
.bottom
- rd
.top
, TRUE
);
1249 * Create the tree view.
1257 r
.right
= r
.left
+ 75;
1259 r
.bottom
= r
.top
+ 10;
1260 MapDialogRect(hwnd
, &r
);
1261 tvstatic
= CreateWindowEx(0, "STATIC", "Cate&gory:",
1262 WS_CHILD
| WS_VISIBLE
,
1264 r
.right
- r
.left
, r
.bottom
- r
.top
,
1265 hwnd
, (HMENU
) IDCX_TVSTATIC
, hinst
,
1267 font
= SendMessage(hwnd
, WM_GETFONT
, 0, 0);
1268 SendMessage(tvstatic
, WM_SETFONT
, font
, MAKELPARAM(TRUE
, 0));
1271 r
.right
= r
.left
+ 75;
1273 r
.bottom
= r
.top
+ 206;
1274 MapDialogRect(hwnd
, &r
);
1275 treeview
= CreateWindowEx(WS_EX_CLIENTEDGE
, WC_TREEVIEW
, "",
1276 WS_CHILD
| WS_VISIBLE
|
1277 WS_TABSTOP
| TVS_HASLINES
|
1278 TVS_DISABLEDRAGDROP
| TVS_HASBUTTONS
1280 TVS_SHOWSELALWAYS
, r
.left
, r
.top
,
1281 r
.right
- r
.left
, r
.bottom
- r
.top
,
1282 hwnd
, (HMENU
) IDCX_TREEVIEW
, hinst
,
1284 font
= SendMessage(hwnd
, WM_GETFONT
, 0, 0);
1285 SendMessage(treeview
, WM_SETFONT
, font
, MAKELPARAM(TRUE
, 0));
1286 tvfaff
.treeview
= treeview
;
1287 memset(tvfaff
.lastat
, 0, sizeof(tvfaff
.lastat
));
1291 * Set up the tree view contents.
1293 hsession
= treeview_insert(&tvfaff
, 0, "Session");
1294 treeview_insert(&tvfaff
, 1, "Logging");
1295 treeview_insert(&tvfaff
, 0, "Terminal");
1296 treeview_insert(&tvfaff
, 1, "Keyboard");
1297 treeview_insert(&tvfaff
, 1, "Bell");
1298 treeview_insert(&tvfaff
, 0, "Window");
1299 treeview_insert(&tvfaff
, 1, "Appearance");
1300 treeview_insert(&tvfaff
, 1, "Translation");
1301 treeview_insert(&tvfaff
, 1, "Selection");
1302 treeview_insert(&tvfaff
, 1, "Colours");
1303 treeview_insert(&tvfaff
, 0, "Connection");
1305 treeview_insert(&tvfaff
, 1, "Telnet");
1306 treeview_insert(&tvfaff
, 1, "Rlogin");
1307 if (backends
[3].backend
!= NULL
) {
1308 treeview_insert(&tvfaff
, 1, "SSH");
1309 treeview_insert(&tvfaff
, 2, "Tunnels");
1314 * Put the treeview selection on to the Session panel. This
1315 * should also cause creation of the relevant controls.
1317 TreeView_SelectItem(treeview
, hsession
);
1320 * Set focus into the first available control.
1324 ctl
= GetDlgItem(hwnd
, IDC_HOST
);
1326 ctl
= GetDlgItem(hwnd
, IDC_CLOSEEXIT
);
1330 SetWindowLong(hwnd
, GWL_USERDATA
, 1);
1334 * Button release should trigger WM_OK if there was a
1335 * previous double click on the session list.
1339 SendMessage(hwnd
, WM_COMMAND
, IDOK
, 0);
1342 if (LOWORD(wParam
) == IDCX_TREEVIEW
&&
1343 ((LPNMHDR
) lParam
)->code
== TVN_SELCHANGED
) {
1345 TreeView_GetSelection(((LPNMHDR
) lParam
)->hwndFrom
);
1350 item
.pszText
= buffer
;
1351 item
.cchTextMax
= sizeof(buffer
);
1352 item
.mask
= TVIF_TEXT
;
1353 TreeView_GetItem(((LPNMHDR
) lParam
)->hwndFrom
, &item
);
1354 for (j
= controlstartvalue
; j
< controlendvalue
; j
++) {
1355 HWND item
= GetDlgItem(hwnd
, j
);
1357 DestroyWindow(item
);
1359 if (!strcmp(buffer
, "Session"))
1360 create_controls(hwnd
, dlgtype
, sessionpanelstart
);
1361 if (!strcmp(buffer
, "Logging"))
1362 create_controls(hwnd
, dlgtype
, loggingpanelstart
);
1363 if (!strcmp(buffer
, "Keyboard"))
1364 create_controls(hwnd
, dlgtype
, keyboardpanelstart
);
1365 if (!strcmp(buffer
, "Terminal"))
1366 create_controls(hwnd
, dlgtype
, terminalpanelstart
);
1367 if (!strcmp(buffer
, "Bell"))
1368 create_controls(hwnd
, dlgtype
, bellpanelstart
);
1369 if (!strcmp(buffer
, "Window"))
1370 create_controls(hwnd
, dlgtype
, windowpanelstart
);
1371 if (!strcmp(buffer
, "Appearance"))
1372 create_controls(hwnd
, dlgtype
, appearancepanelstart
);
1373 if (!strcmp(buffer
, "Tunnels"))
1374 create_controls(hwnd
, dlgtype
, tunnelspanelstart
);
1375 if (!strcmp(buffer
, "Connection"))
1376 create_controls(hwnd
, dlgtype
, connectionpanelstart
);
1377 if (!strcmp(buffer
, "Telnet"))
1378 create_controls(hwnd
, dlgtype
, telnetpanelstart
);
1379 if (!strcmp(buffer
, "Rlogin"))
1380 create_controls(hwnd
, dlgtype
, rloginpanelstart
);
1381 if (!strcmp(buffer
, "SSH"))
1382 create_controls(hwnd
, dlgtype
, sshpanelstart
);
1383 if (!strcmp(buffer
, "Selection"))
1384 create_controls(hwnd
, dlgtype
, selectionpanelstart
);
1385 if (!strcmp(buffer
, "Colours"))
1386 create_controls(hwnd
, dlgtype
, colourspanelstart
);
1387 if (!strcmp(buffer
, "Translation"))
1388 create_controls(hwnd
, dlgtype
, translationpanelstart
);
1390 init_dlg_ctrls(hwnd
);
1392 SetFocus(((LPNMHDR
) lParam
)->hwndFrom
); /* ensure focus stays */
1398 * Only process WM_COMMAND once the dialog is fully formed.
1400 if (GetWindowLong(hwnd
, GWL_USERDATA
) == 1)
1401 switch (LOWORD(wParam
)) {
1411 case IDC_PROTTELNET
:
1412 case IDC_PROTRLOGIN
:
1415 if (HIWORD(wParam
) == BN_CLICKED
||
1416 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1417 int i
= IsDlgButtonChecked(hwnd
, IDC_PROTSSH
);
1418 int j
= IsDlgButtonChecked(hwnd
, IDC_PROTTELNET
);
1419 int k
= IsDlgButtonChecked(hwnd
, IDC_PROTRLOGIN
);
1421 i ? PROT_SSH
: j ? PROT_TELNET
: k ? PROT_RLOGIN
:
1423 if ((cfg
.protocol
== PROT_SSH
&& cfg
.port
!= 22)
1424 || (cfg
.protocol
== PROT_TELNET
&& cfg
.port
!= 23)
1425 || (cfg
.protocol
== PROT_RLOGIN
1426 && cfg
.port
!= 513)) {
1427 cfg
.port
= i ?
22 : j ?
23 : 513;
1428 SetDlgItemInt(hwnd
, IDC_PORT
, cfg
.port
, FALSE
);
1433 if (HIWORD(wParam
) == EN_CHANGE
)
1434 GetDlgItemText(hwnd
, IDC_HOST
, cfg
.host
,
1435 sizeof(cfg
.host
) - 1);
1438 if (HIWORD(wParam
) == EN_CHANGE
) {
1439 GetDlgItemText(hwnd
, IDC_PORT
, portname
, 31);
1440 if (isdigit(portname
[0]))
1441 MyGetDlgItemInt(hwnd
, IDC_PORT
, &cfg
.port
);
1443 service
= getservbyname(portname
, NULL
);
1445 cfg
.port
= ntohs(service
->s_port
);
1452 if (HIWORD(wParam
) == EN_CHANGE
) {
1453 SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_SETCURSEL
,
1455 GetDlgItemText(hwnd
, IDC_SESSEDIT
,
1456 savedsession
, sizeof(savedsession
) - 1);
1457 savedsession
[sizeof(savedsession
) - 1] = '\0';
1461 if (HIWORD(wParam
) == BN_CLICKED
||
1462 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1467 GetDlgItemText(hwnd
, IDC_SESSEDIT
, str
,
1470 int n
= SendDlgItemMessage(hwnd
, IDC_SESSLIST
,
1471 LB_GETCURSEL
, 0, 0);
1476 strcpy(str
, sessions
[n
]);
1478 save_settings(str
, !!strcmp(str
, "Default Settings"),
1480 get_sesslist(FALSE
);
1482 SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_RESETCONTENT
,
1484 for (i
= 0; i
< nsessions
; i
++)
1485 SendDlgItemMessage(hwnd
, IDC_SESSLIST
,
1487 (LPARAM
) (sessions
[i
]));
1488 SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_SETCURSEL
,
1494 if (LOWORD(wParam
) == IDC_SESSLOAD
&&
1495 HIWORD(wParam
) != BN_CLICKED
&&
1496 HIWORD(wParam
) != BN_DOUBLECLICKED
) break;
1497 if (LOWORD(wParam
) == IDC_SESSLIST
&&
1498 HIWORD(wParam
) != LBN_DBLCLK
) break;
1500 int n
= SendDlgItemMessage(hwnd
, IDC_SESSLIST
,
1501 LB_GETCURSEL
, 0, 0);
1507 isdef
= !strcmp(sessions
[n
], "Default Settings");
1508 load_settings(sessions
[n
], !isdef
, &cfg
);
1509 init_dlg_ctrls(hwnd
);
1511 SetDlgItemText(hwnd
, IDC_SESSEDIT
, sessions
[n
]);
1513 SetDlgItemText(hwnd
, IDC_SESSEDIT
, "");
1515 if (LOWORD(wParam
) == IDC_SESSLIST
) {
1517 * A double-click on a saved session should
1518 * actually start the session, not just load it.
1519 * Unless it's Default Settings or some other
1520 * host-less set of saved settings.
1529 if (HIWORD(wParam
) == BN_CLICKED
||
1530 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1531 int n
= SendDlgItemMessage(hwnd
, IDC_SESSLIST
,
1532 LB_GETCURSEL
, 0, 0);
1533 if (n
== LB_ERR
|| n
== 0) {
1537 del_settings(sessions
[n
]);
1538 get_sesslist(FALSE
);
1540 SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_RESETCONTENT
,
1542 for (i
= 0; i
< nsessions
; i
++)
1543 SendDlgItemMessage(hwnd
, IDC_SESSLIST
,
1545 (LPARAM
) (sessions
[i
]));
1546 SendDlgItemMessage(hwnd
, IDC_SESSLIST
, LB_SETCURSEL
,
1550 if (HIWORD(wParam
) == EN_CHANGE
)
1551 MyGetDlgItemInt(hwnd
, IDC_PINGEDIT
,
1552 &cfg
.ping_interval
);
1556 if (HIWORD(wParam
) == BN_CLICKED
||
1557 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1558 cfg
.bksp_is_delete
=
1559 IsDlgButtonChecked(hwnd
, IDC_DEL127
);
1563 if (HIWORD(wParam
) == BN_CLICKED
||
1564 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1566 IsDlgButtonChecked(hwnd
, IDC_HOMERXVT
);
1572 case IDC_FUNCVT100P
:
1574 if (HIWORD(wParam
) == BN_CLICKED
||
1575 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1576 switch (LOWORD(wParam
)) {
1589 case IDC_FUNCVT100P
:
1599 if (HIWORD(wParam
) == BN_CLICKED
||
1600 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1602 IsDlgButtonChecked(hwnd
, IDC_KPAPPLIC
);
1603 cfg
.nethack_keypad
= FALSE
;
1607 if (HIWORD(wParam
) == BN_CLICKED
||
1608 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1609 cfg
.app_keypad
= FALSE
;
1610 cfg
.nethack_keypad
= TRUE
;
1615 if (HIWORD(wParam
) == BN_CLICKED
||
1616 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1618 IsDlgButtonChecked(hwnd
, IDC_CURAPPLIC
);
1621 if (HIWORD(wParam
) == BN_CLICKED
||
1622 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1624 IsDlgButtonChecked(hwnd
, IDC_NOAPPLICC
);
1627 if (HIWORD(wParam
) == BN_CLICKED
||
1628 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1630 IsDlgButtonChecked(hwnd
, IDC_NOAPPLICK
);
1633 if (HIWORD(wParam
) == BN_CLICKED
||
1634 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1635 cfg
.alt_f4
= IsDlgButtonChecked(hwnd
, IDC_ALTF4
);
1638 if (HIWORD(wParam
) == BN_CLICKED
||
1639 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1641 IsDlgButtonChecked(hwnd
, IDC_ALTSPACE
);
1644 if (HIWORD(wParam
) == BN_CLICKED
||
1645 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1647 IsDlgButtonChecked(hwnd
, IDC_ALTONLY
);
1649 case IDC_ECHOBACKEND
:
1652 if (HIWORD(wParam
) == BN_CLICKED
||
1653 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1654 if (LOWORD(wParam
) == IDC_ECHOBACKEND
)
1655 cfg
.localecho
= LD_BACKEND
;
1656 if (LOWORD(wParam
) == IDC_ECHOYES
)
1657 cfg
.localecho
= LD_YES
;
1658 if (LOWORD(wParam
) == IDC_ECHONO
)
1659 cfg
.localecho
= LD_NO
;
1662 case IDC_EDITBACKEND
:
1665 if (HIWORD(wParam
) == BN_CLICKED
||
1666 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1667 if (LOWORD(wParam
) == IDC_EDITBACKEND
)
1668 cfg
.localedit
= LD_BACKEND
;
1669 if (LOWORD(wParam
) == IDC_EDITYES
)
1670 cfg
.localedit
= LD_YES
;
1671 if (LOWORD(wParam
) == IDC_EDITNO
)
1672 cfg
.localedit
= LD_NO
;
1675 case IDC_ANSWEREDIT
:
1676 if (HIWORD(wParam
) == EN_CHANGE
)
1677 GetDlgItemText(hwnd
, IDC_ANSWEREDIT
, cfg
.answerback
,
1678 sizeof(cfg
.answerback
) - 1);
1680 case IDC_ALWAYSONTOP
:
1681 if (HIWORD(wParam
) == BN_CLICKED
||
1682 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1684 IsDlgButtonChecked(hwnd
, IDC_ALWAYSONTOP
);
1687 if (HIWORD(wParam
) == BN_CLICKED
||
1688 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1690 IsDlgButtonChecked(hwnd
, IDC_SCROLLKEY
);
1692 case IDC_SCROLLDISP
:
1693 if (HIWORD(wParam
) == BN_CLICKED
||
1694 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1695 cfg
.scroll_on_disp
=
1696 IsDlgButtonChecked(hwnd
, IDC_SCROLLDISP
);
1698 case IDC_COMPOSEKEY
:
1699 if (HIWORD(wParam
) == BN_CLICKED
||
1700 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1702 IsDlgButtonChecked(hwnd
, IDC_COMPOSEKEY
);
1704 case IDC_CTRLALTKEYS
:
1705 if (HIWORD(wParam
) == BN_CLICKED
||
1706 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1708 IsDlgButtonChecked(hwnd
, IDC_CTRLALTKEYS
);
1711 if (HIWORD(wParam
) == BN_CLICKED
||
1712 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1713 cfg
.telnet_keyboard
=
1714 IsDlgButtonChecked(hwnd
, IDC_TELNETKEY
);
1717 if (HIWORD(wParam
) == BN_CLICKED
||
1718 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1720 IsDlgButtonChecked(hwnd
, IDC_WRAPMODE
);
1723 if (HIWORD(wParam
) == BN_CLICKED
||
1724 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1725 cfg
.dec_om
= IsDlgButtonChecked(hwnd
, IDC_DECOM
);
1728 if (HIWORD(wParam
) == BN_CLICKED
||
1729 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1731 IsDlgButtonChecked(hwnd
, IDC_LFHASCR
);
1734 if (HIWORD(wParam
) == EN_CHANGE
)
1735 MyGetDlgItemInt(hwnd
, IDC_ROWSEDIT
, &cfg
.height
);
1738 if (HIWORD(wParam
) == EN_CHANGE
)
1739 MyGetDlgItemInt(hwnd
, IDC_COLSEDIT
, &cfg
.width
);
1742 if (HIWORD(wParam
) == EN_CHANGE
)
1743 MyGetDlgItemInt(hwnd
, IDC_SAVEEDIT
, &cfg
.savelines
);
1745 case IDC_CHOOSEFONT
:
1748 lf
.lfHeight
= -MulDiv(cfg
.fontheight
,
1749 GetDeviceCaps(hdc
, LOGPIXELSY
),
1753 lf
.lfWidth
= lf
.lfEscapement
= lf
.lfOrientation
= 0;
1754 lf
.lfItalic
= lf
.lfUnderline
= lf
.lfStrikeOut
= 0;
1755 lf
.lfWeight
= (cfg
.fontisbold ? FW_BOLD
: 0);
1756 lf
.lfCharSet
= cfg
.fontcharset
;
1757 lf
.lfOutPrecision
= OUT_DEFAULT_PRECIS
;
1758 lf
.lfClipPrecision
= CLIP_DEFAULT_PRECIS
;
1759 lf
.lfQuality
= DEFAULT_QUALITY
;
1760 lf
.lfPitchAndFamily
= FIXED_PITCH
| FF_DONTCARE
;
1761 strncpy(lf
.lfFaceName
, cfg
.font
,
1762 sizeof(lf
.lfFaceName
) - 1);
1763 lf
.lfFaceName
[sizeof(lf
.lfFaceName
) - 1] = '\0';
1765 cf
.lStructSize
= sizeof(cf
);
1766 cf
.hwndOwner
= hwnd
;
1768 cf
.Flags
= CF_FIXEDPITCHONLY
| CF_FORCEFONTEXIST
|
1769 CF_INITTOLOGFONTSTRUCT
| CF_SCREENFONTS
;
1771 if (ChooseFont(&cf
)) {
1772 strncpy(cfg
.font
, lf
.lfFaceName
, sizeof(cfg
.font
) - 1);
1773 cfg
.font
[sizeof(cfg
.font
) - 1] = '\0';
1774 cfg
.fontisbold
= (lf
.lfWeight
== FW_BOLD
);
1775 cfg
.fontcharset
= lf
.lfCharSet
;
1776 cfg
.fontheight
= cf
.iPointSize
/ 10;
1777 fmtfont(fontstatic
);
1778 SetDlgItemText(hwnd
, IDC_FONTSTATIC
, fontstatic
);
1781 case IDC_BELL_DISABLED
:
1782 case IDC_BELL_DEFAULT
:
1783 case IDC_BELL_WAVEFILE
:
1784 case IDC_BELL_VISUAL
:
1785 if (HIWORD(wParam
) == BN_CLICKED
||
1786 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1787 if (LOWORD(wParam
) == IDC_BELL_DISABLED
)
1788 cfg
.beep
= BELL_DISABLED
;
1789 if (LOWORD(wParam
) == IDC_BELL_DEFAULT
)
1790 cfg
.beep
= BELL_DEFAULT
;
1791 if (LOWORD(wParam
) == IDC_BELL_WAVEFILE
)
1792 cfg
.beep
= BELL_WAVEFILE
;
1793 if (LOWORD(wParam
) == IDC_BELL_VISUAL
)
1794 cfg
.beep
= BELL_VISUAL
;
1797 case IDC_BELL_WAVEBROWSE
:
1798 memset(&of
, 0, sizeof(of
));
1799 #ifdef OPENFILENAME_SIZE_VERSION_400
1800 of
.lStructSize
= OPENFILENAME_SIZE_VERSION_400
;
1802 of
.lStructSize
= sizeof(of
);
1804 of
.hwndOwner
= hwnd
;
1805 of
.lpstrFilter
= "Wave Files\0*.WAV\0AllFiles\0*\0\0\0";
1806 of
.lpstrCustomFilter
= NULL
;
1807 of
.nFilterIndex
= 1;
1808 of
.lpstrFile
= filename
;
1809 strcpy(filename
, cfg
.bell_wavefile
);
1810 of
.nMaxFile
= sizeof(filename
);
1811 of
.lpstrFileTitle
= NULL
;
1812 of
.lpstrInitialDir
= NULL
;
1813 of
.lpstrTitle
= "Select Bell Sound File";
1815 if (GetOpenFileName(&of
)) {
1816 strcpy(cfg
.bell_wavefile
, filename
);
1817 SetDlgItemText(hwnd
, IDC_BELL_WAVEEDIT
,
1821 case IDC_BELL_WAVEEDIT
:
1822 if (HIWORD(wParam
) == EN_CHANGE
)
1823 GetDlgItemText(hwnd
, IDC_BELL_WAVEEDIT
,
1825 sizeof(cfg
.bell_wavefile
) - 1);
1828 if (HIWORD(wParam
) == BN_CLICKED
||
1829 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1831 IsDlgButtonChecked(hwnd
, IDC_BELLOVL
);
1834 if (HIWORD(wParam
) == EN_CHANGE
)
1835 MyGetDlgItemInt(hwnd
, IDC_BELLOVLN
, &cfg
.bellovl_n
);
1838 if (HIWORD(wParam
) == EN_CHANGE
)
1839 MyGetDlgItemFlt(hwnd
, IDC_BELLOVLT
, &cfg
.bellovl_t
,
1843 if (HIWORD(wParam
) == EN_CHANGE
)
1844 MyGetDlgItemFlt(hwnd
, IDC_BELLOVLS
, &cfg
.bellovl_s
,
1848 if (HIWORD(wParam
) == BN_CLICKED
||
1849 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1851 IsDlgButtonChecked(hwnd
, IDC_BLINKTEXT
);
1854 if (HIWORD(wParam
) == BN_CLICKED
||
1855 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1856 cfg
.bce
= IsDlgButtonChecked(hwnd
, IDC_BCE
);
1859 if (HIWORD(wParam
) == BN_CLICKED
||
1860 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1861 cfg
.win_name_always
=
1862 IsDlgButtonChecked(hwnd
, IDC_WINNAME
);
1865 if (HIWORD(wParam
) == BN_CLICKED
||
1866 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1868 IsDlgButtonChecked(hwnd
, IDC_HIDEMOUSE
);
1870 case IDC_SUNKENEDGE
:
1871 if (HIWORD(wParam
) == BN_CLICKED
||
1872 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1874 IsDlgButtonChecked(hwnd
, IDC_SUNKENEDGE
);
1877 if (HIWORD(wParam
) == BN_CLICKED
||
1878 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1879 cfg
.cursor_type
= 0;
1882 if (HIWORD(wParam
) == BN_CLICKED
||
1883 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1884 cfg
.cursor_type
= 1;
1887 if (HIWORD(wParam
) == BN_CLICKED
||
1888 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1889 cfg
.cursor_type
= 2;
1892 if (HIWORD(wParam
) == BN_CLICKED
||
1893 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1895 IsDlgButtonChecked(hwnd
, IDC_BLINKCUR
);
1898 if (HIWORD(wParam
) == BN_CLICKED
||
1899 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1901 IsDlgButtonChecked(hwnd
, IDC_SCROLLBAR
);
1904 if (HIWORD(wParam
) == BN_CLICKED
||
1905 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1907 IsDlgButtonChecked(hwnd
, IDC_LOCKSIZE
);
1910 if (HIWORD(wParam
) == EN_CHANGE
)
1911 GetDlgItemText(hwnd
, IDC_WINEDIT
, cfg
.wintitle
,
1912 sizeof(cfg
.wintitle
) - 1);
1917 if (HIWORD(wParam
) == BN_CLICKED
||
1918 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1920 IsDlgButtonChecked(hwnd
,
1921 IDC_COEALWAYS
) ? COE_ALWAYS
:
1922 IsDlgButtonChecked(hwnd
,
1923 IDC_COENEVER
) ? COE_NEVER
:
1928 if (HIWORD(wParam
) == BN_CLICKED
||
1929 HIWORD(wParam
) == BN_DOUBLECLICKED
)
1931 IsDlgButtonChecked(hwnd
, IDC_CLOSEWARN
);
1934 if (HIWORD(wParam
) == EN_CHANGE
)
1935 GetDlgItemText(hwnd
, IDC_TTEDIT
, cfg
.termtype
,
1936 sizeof(cfg
.termtype
) - 1);
1939 if (HIWORD(wParam
) == EN_CHANGE
)
1940 GetDlgItemText(hwnd
, IDC_LGFEDIT
, cfg
.logfilename
,
1941 sizeof(cfg
.logfilename
) - 1);
1944 memset(&of
, 0, sizeof(of
));
1945 #ifdef OPENFILENAME_SIZE_VERSION_400
1946 of
.lStructSize
= OPENFILENAME_SIZE_VERSION_400
;
1948 of
.lStructSize
= sizeof(of
);
1950 of
.hwndOwner
= hwnd
;
1951 of
.lpstrFilter
= "All Files\0*\0\0\0";
1952 of
.lpstrCustomFilter
= NULL
;
1953 of
.nFilterIndex
= 1;
1954 of
.lpstrFile
= filename
;
1955 strcpy(filename
, cfg
.logfilename
);
1956 of
.nMaxFile
= sizeof(filename
);
1957 of
.lpstrFileTitle
= NULL
;
1958 of
.lpstrInitialDir
= NULL
;
1959 of
.lpstrTitle
= "Select session log file";
1961 if (GetSaveFileName(&of
)) {
1962 strcpy(cfg
.logfilename
, filename
);
1963 SetDlgItemText(hwnd
, IDC_LGFEDIT
, cfg
.logfilename
);
1967 case IDC_LSTATASCII
:
1969 if (HIWORD(wParam
) == BN_CLICKED
||
1970 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1971 if (IsDlgButtonChecked(hwnd
, IDC_LSTATOFF
))
1973 if (IsDlgButtonChecked(hwnd
, IDC_LSTATASCII
))
1975 if (IsDlgButtonChecked(hwnd
, IDC_LSTATRAW
))
1982 if (HIWORD(wParam
) == BN_CLICKED
||
1983 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
1984 if (IsDlgButtonChecked(hwnd
, IDC_LSTATXASK
))
1985 cfg
.logxfovr
= LGXF_ASK
;
1986 if (IsDlgButtonChecked(hwnd
, IDC_LSTATXAPN
))
1987 cfg
.logxfovr
= LGXF_APN
;
1988 if (IsDlgButtonChecked(hwnd
, IDC_LSTATXOVR
))
1989 cfg
.logxfovr
= LGXF_OVR
;
1994 if (HIWORD(wParam
) == EN_CHANGE
)
1995 GetDlgItemText(hwnd
, LOWORD(wParam
), cfg
.termspeed
,
1996 sizeof(cfg
.termspeed
) - 1);
1999 if (HIWORD(wParam
) == EN_CHANGE
)
2000 GetDlgItemText(hwnd
, IDC_LOGEDIT
, cfg
.username
,
2001 sizeof(cfg
.username
) - 1);
2003 case IDC_RLLUSEREDIT
:
2004 if (HIWORD(wParam
) == EN_CHANGE
)
2005 GetDlgItemText(hwnd
, IDC_RLLUSEREDIT
,
2007 sizeof(cfg
.localusername
) - 1);
2011 cfg
.rfc_environ
= IsDlgButtonChecked(hwnd
, IDC_EMRFC
);
2015 cfg
.passive_telnet
=
2016 IsDlgButtonChecked(hwnd
, IDC_TPASSIVE
);
2019 if (HIWORD(wParam
) == BN_CLICKED
||
2020 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
2021 char str
[sizeof(cfg
.environmt
)];
2023 GetDlgItemText(hwnd
, IDC_VAREDIT
, str
,
2029 p
= str
+ strlen(str
);
2031 GetDlgItemText(hwnd
, IDC_VALEDIT
, p
,
2032 sizeof(str
) - 1 - (p
- str
));
2043 if ((p
- cfg
.environmt
) + strlen(str
) + 2 <
2044 sizeof(cfg
.environmt
)) {
2046 p
[strlen(str
) + 1] = '\0';
2047 SendDlgItemMessage(hwnd
, IDC_ENVLIST
, LB_ADDSTRING
,
2049 SetDlgItemText(hwnd
, IDC_VAREDIT
, "");
2050 SetDlgItemText(hwnd
, IDC_VALEDIT
, "");
2052 MessageBox(hwnd
, "Environment too big",
2053 "PuTTY Error", MB_OK
| MB_ICONERROR
);
2058 if (HIWORD(wParam
) != BN_CLICKED
&&
2059 HIWORD(wParam
) != BN_DOUBLECLICKED
) break;
2061 SendDlgItemMessage(hwnd
, IDC_ENVLIST
, LB_GETCURSEL
, 0,
2068 SendDlgItemMessage(hwnd
, IDC_ENVLIST
, LB_DELETESTRING
,
2095 if (HIWORD(wParam
) == BN_CLICKED
||
2096 HIWORD(wParam
) == BN_DOUBLECLICKED
)
2097 cfg
.nopty
= IsDlgButtonChecked(hwnd
, IDC_NOPTY
);
2100 if (HIWORD(wParam
) == BN_CLICKED
||
2101 HIWORD(wParam
) == BN_DOUBLECLICKED
)
2103 IsDlgButtonChecked(hwnd
, IDC_COMPRESS
);
2106 if (HIWORD(wParam
) == BN_CLICKED
||
2107 HIWORD(wParam
) == BN_DOUBLECLICKED
)
2109 IsDlgButtonChecked(hwnd
, IDC_BUGGYMAC
);
2112 if (HIWORD(wParam
) == BN_CLICKED
||
2113 HIWORD(wParam
) == BN_DOUBLECLICKED
)
2115 IsDlgButtonChecked(hwnd
, IDC_AGENTFWD
);
2117 case IDC_CIPHER3DES
:
2118 case IDC_CIPHERBLOWF
:
2121 if (HIWORD(wParam
) == BN_CLICKED
||
2122 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
2123 if (IsDlgButtonChecked(hwnd
, IDC_CIPHER3DES
))
2124 cfg
.cipher
= CIPHER_3DES
;
2125 else if (IsDlgButtonChecked(hwnd
, IDC_CIPHERBLOWF
))
2126 cfg
.cipher
= CIPHER_BLOWFISH
;
2127 else if (IsDlgButtonChecked(hwnd
, IDC_CIPHERDES
))
2128 cfg
.cipher
= CIPHER_DES
;
2129 else if (IsDlgButtonChecked(hwnd
, IDC_CIPHERAES
))
2130 cfg
.cipher
= CIPHER_AES
;
2135 if (HIWORD(wParam
) == BN_CLICKED
||
2136 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
2137 if (IsDlgButtonChecked(hwnd
, IDC_SSHPROT1
))
2139 else if (IsDlgButtonChecked(hwnd
, IDC_SSHPROT2
))
2144 if (HIWORD(wParam
) == BN_CLICKED
||
2145 HIWORD(wParam
) == BN_DOUBLECLICKED
)
2147 IsDlgButtonChecked(hwnd
, IDC_AUTHTIS
);
2150 if (HIWORD(wParam
) == EN_CHANGE
)
2151 GetDlgItemText(hwnd
, IDC_PKEDIT
, cfg
.keyfile
,
2152 sizeof(cfg
.keyfile
) - 1);
2155 if (HIWORD(wParam
) == EN_CHANGE
)
2156 GetDlgItemText(hwnd
, IDC_CMDEDIT
, cfg
.remote_cmd
,
2157 sizeof(cfg
.remote_cmd
) - 1);
2160 memset(&of
, 0, sizeof(of
));
2161 #ifdef OPENFILENAME_SIZE_VERSION_400
2162 of
.lStructSize
= OPENFILENAME_SIZE_VERSION_400
;
2164 of
.lStructSize
= sizeof(of
);
2166 of
.hwndOwner
= hwnd
;
2167 of
.lpstrFilter
= "All Files\0*\0\0\0";
2168 of
.lpstrCustomFilter
= NULL
;
2169 of
.nFilterIndex
= 1;
2170 of
.lpstrFile
= filename
;
2171 strcpy(filename
, cfg
.keyfile
);
2172 of
.nMaxFile
= sizeof(filename
);
2173 of
.lpstrFileTitle
= NULL
;
2174 of
.lpstrInitialDir
= NULL
;
2175 of
.lpstrTitle
= "Select Public Key File";
2177 if (GetOpenFileName(&of
)) {
2178 strcpy(cfg
.keyfile
, filename
);
2179 SetDlgItemText(hwnd
, IDC_PKEDIT
, cfg
.keyfile
);
2183 cfg
.rawcnp
= IsDlgButtonChecked(hwnd
, IDC_RAWCNP
);
2186 cfg
.mouse_is_xterm
= IsDlgButtonChecked(hwnd
, IDC_MBXTERM
);
2192 int n
= GetDlgItemInt(hwnd
, IDC_CCEDIT
, &ok
, FALSE
);
2197 for (i
= 0; i
< 256; i
++)
2198 if (SendDlgItemMessage
2199 (hwnd
, IDC_CCLIST
, LB_GETSEL
, i
, 0)) {
2201 cfg
.wordness
[i
] = n
;
2202 SendDlgItemMessage(hwnd
, IDC_CCLIST
,
2203 LB_DELETESTRING
, i
, 0);
2204 sprintf(str
, "%d\t(0x%02X)\t%c\t%d", i
, i
,
2205 (i
>= 0x21 && i
!= 0x7F) ? i
: ' ',
2207 SendDlgItemMessage(hwnd
, IDC_CCLIST
,
2214 case IDC_BOLDCOLOUR
:
2215 if (HIWORD(wParam
) == BN_CLICKED
||
2216 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
2219 IsDlgButtonChecked(hwnd
, IDC_BOLDCOLOUR
);
2221 SendDlgItemMessage(hwnd
, IDC_COLOURLIST
,
2223 if (n
!= 12 + 10 * cfg
.bold_colour
) {
2224 for (i
= n
; i
-- > 0;)
2225 SendDlgItemMessage(hwnd
, IDC_COLOURLIST
,
2226 LB_DELETESTRING
, i
, 0);
2227 for (i
= 0; i
< 22; i
++)
2228 if (cfg
.bold_colour
|| permcolour
[i
])
2229 SendDlgItemMessage(hwnd
, IDC_COLOURLIST
,
2231 (LPARAM
) colours
[i
]);
2236 if (HIWORD(wParam
) == BN_CLICKED
||
2237 HIWORD(wParam
) == BN_DOUBLECLICKED
)
2239 IsDlgButtonChecked(hwnd
, IDC_PALETTE
);
2241 case IDC_COLOURLIST
:
2242 if (HIWORD(wParam
) == LBN_DBLCLK
||
2243 HIWORD(wParam
) == LBN_SELCHANGE
) {
2244 int i
= SendDlgItemMessage(hwnd
, IDC_COLOURLIST
,
2247 if (!cfg
.bold_colour
)
2248 i
= (i
< 3 ? i
* 2 : i
== 3 ?
5 : i
* 2 - 2);
2249 SetDlgItemInt(hwnd
, IDC_RVALUE
, cfg
.colours
[i
][0],
2251 SetDlgItemInt(hwnd
, IDC_GVALUE
, cfg
.colours
[i
][1],
2253 SetDlgItemInt(hwnd
, IDC_BVALUE
, cfg
.colours
[i
][2],
2258 if (HIWORD(wParam
) == BN_CLICKED
||
2259 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
2260 static CHOOSECOLOR cc
;
2261 static DWORD custom
[16] = { 0 }; /* zero initialisers */
2262 int i
= SendDlgItemMessage(hwnd
, IDC_COLOURLIST
,
2265 if (!cfg
.bold_colour
)
2266 i
= (i
< 3 ? i
* 2 : i
== 3 ?
5 : i
* 2 - 2);
2267 cc
.lStructSize
= sizeof(cc
);
2268 cc
.hwndOwner
= hwnd
;
2269 cc
.hInstance
= (HWND
) hinst
;
2270 cc
.lpCustColors
= custom
;
2272 RGB(cfg
.colours
[i
][0], cfg
.colours
[i
][1],
2274 cc
.Flags
= CC_FULLOPEN
| CC_RGBINIT
;
2275 if (ChooseColor(&cc
)) {
2277 (unsigned char) (cc
.rgbResult
& 0xFF);
2279 (unsigned char) (cc
.rgbResult
>> 8) & 0xFF;
2281 (unsigned char) (cc
.rgbResult
>> 16) & 0xFF;
2282 SetDlgItemInt(hwnd
, IDC_RVALUE
, cfg
.colours
[i
][0],
2284 SetDlgItemInt(hwnd
, IDC_GVALUE
, cfg
.colours
[i
][1],
2286 SetDlgItemInt(hwnd
, IDC_BVALUE
, cfg
.colours
[i
][2],
2292 case IDC_KOI8WIN1251
:
2293 case IDC_88592WIN1250
:
2294 case IDC_88592CP852
:
2295 cfg
.xlat_enablekoiwin
=
2296 IsDlgButtonChecked(hwnd
, IDC_KOI8WIN1251
);
2297 cfg
.xlat_88592w1250
=
2298 IsDlgButtonChecked(hwnd
, IDC_88592WIN1250
);
2299 cfg
.xlat_88592cp852
=
2300 IsDlgButtonChecked(hwnd
, IDC_88592CP852
);
2302 case IDC_CAPSLOCKCYR
:
2303 if (HIWORD(wParam
) == BN_CLICKED
||
2304 HIWORD(wParam
) == BN_DOUBLECLICKED
) {
2305 cfg
.xlat_capslockcyr
=
2306 IsDlgButtonChecked(hwnd
, IDC_CAPSLOCKCYR
);
2309 case IDC_VTXWINDOWS
:
2314 (IsDlgButtonChecked(hwnd
, IDC_VTXWINDOWS
) ? VT_XWINDOWS
2315 : IsDlgButtonChecked(hwnd
,
2316 IDC_VTOEMANSI
) ? VT_OEMANSI
:
2317 IsDlgButtonChecked(hwnd
,
2318 IDC_VTOEMONLY
) ? VT_OEMONLY
:
2321 case IDC_X11_FORWARD
:
2322 if (HIWORD(wParam
) == BN_CLICKED
||
2323 HIWORD(wParam
) == BN_DOUBLECLICKED
)
2325 IsDlgButtonChecked(hwnd
, IDC_X11_FORWARD
);
2327 case IDC_X11_DISPLAY
:
2328 if (HIWORD(wParam
) == EN_CHANGE
)
2329 GetDlgItemText(hwnd
, IDC_X11_DISPLAY
, cfg
.x11_display
,
2330 sizeof(cfg
.x11_display
) - 1);
2338 /* Grrr Explorer will maximize Dialogs! */
2340 if (wParam
== SIZE_MAXIMIZED
)
2347 static int CALLBACK
MainDlgProc(HWND hwnd
, UINT msg
,
2348 WPARAM wParam
, LPARAM lParam
)
2350 if (msg
== WM_COMMAND
&& LOWORD(wParam
) == IDOK
) {
2352 if (msg
== WM_COMMAND
&& LOWORD(wParam
) == IDCX_ABOUT
) {
2353 EnableWindow(hwnd
, 0);
2354 DialogBox(hinst
, MAKEINTRESOURCE(IDD_ABOUTBOX
),
2355 GetParent(hwnd
), AboutProc
);
2356 EnableWindow(hwnd
, 1);
2357 SetActiveWindow(hwnd
);
2359 return GenericMainDlgProc(hwnd
, msg
, wParam
, lParam
, 0);
2362 static int CALLBACK
ReconfDlgProc(HWND hwnd
, UINT msg
,
2363 WPARAM wParam
, LPARAM lParam
)
2365 return GenericMainDlgProc(hwnd
, msg
, wParam
, lParam
, 1);
2368 void defuse_showwindow(void)
2371 * Work around the fact that the app's first call to ShowWindow
2372 * will ignore the default in favour of the shell-provided
2377 hwnd
= CreateDialog(hinst
, MAKEINTRESOURCE(IDD_ABOUTBOX
),
2379 ShowWindow(hwnd
, SW_HIDE
);
2380 DestroyWindow(hwnd
);
2389 savedsession
[0] = '\0';
2391 DialogBox(hinst
, MAKEINTRESOURCE(IDD_MAINBOX
), NULL
, MainDlgProc
);
2392 get_sesslist(FALSE
);
2397 int do_reconfig(HWND hwnd
)
2402 backup_cfg
= cfg
; /* structure copy */
2404 DialogBox(hinst
, MAKEINTRESOURCE(IDD_RECONF
), hwnd
, ReconfDlgProc
);
2406 cfg
= backup_cfg
; /* structure copy */
2411 void logevent(char *string
)
2416 if (nevents
>= negsize
) {
2418 events
= srealloc(events
, negsize
* sizeof(*events
));
2422 strftime(timebuf
, sizeof(timebuf
), "%Y-%m-%d %H:%M:%S\t",
2425 events
[nevents
] = smalloc(strlen(timebuf
) + strlen(string
) + 1);
2426 strcpy(events
[nevents
], timebuf
);
2427 strcat(events
[nevents
], string
);
2430 SendDlgItemMessage(logbox
, IDN_LIST
, LB_ADDSTRING
,
2431 0, (LPARAM
) events
[nevents
]);
2432 count
= SendDlgItemMessage(logbox
, IDN_LIST
, LB_GETCOUNT
, 0, 0);
2433 SendDlgItemMessage(logbox
, IDN_LIST
, LB_SETTOPINDEX
, count
- 1, 0);
2438 void showeventlog(HWND hwnd
)
2441 logbox
= CreateDialog(hinst
, MAKEINTRESOURCE(IDD_LOGBOX
),
2443 ShowWindow(logbox
, SW_SHOWNORMAL
);
2445 SetActiveWindow(logbox
);
2448 void showabout(HWND hwnd
)
2450 DialogBox(hinst
, MAKEINTRESOURCE(IDD_ABOUTBOX
), hwnd
, AboutProc
);
2453 void verify_ssh_host_key(char *host
, int port
, char *keytype
,
2454 char *keystr
, char *fingerprint
)
2458 static const char absentmsg
[] =
2459 "The server's host key is not cached in the registry. You\n"
2460 "have no guarantee that the server is the computer you\n"
2462 "The server's key fingerprint is:\n"
2464 "If you trust this host, hit Yes to add the key to\n"
2465 "PuTTY's cache and carry on connecting.\n"
2466 "If you do not trust this host, hit No to abandon the\n"
2469 static const char wrongmsg
[] =
2470 "WARNING - POTENTIAL SECURITY BREACH!\n"
2472 "The server's host key does not match the one PuTTY has\n"
2473 "cached in the registry. This means that either the\n"
2474 "server administrator has changed the host key, or you\n"
2475 "have actually connected to another computer pretending\n"
2476 "to be the server.\n"
2477 "The new key fingerprint is:\n"
2479 "If you were expecting this change and trust the new key,\n"
2480 "hit Yes to update PuTTY's cache and continue connecting.\n"
2481 "If you want to carry on connecting but without updating\n"
2482 "the cache, hit No.\n"
2483 "If you want to abandon the connection completely, hit\n"
2484 "Cancel. Hitting Cancel is the ONLY guaranteed safe\n" "choice.\n";
2486 static const char mbtitle
[] = "PuTTY Security Alert";
2490 /* sensible fingerprint max size */
2491 (sizeof(absentmsg
) > sizeof(wrongmsg
) ?
2492 sizeof(absentmsg
) : sizeof(wrongmsg
))];
2495 * Verify the key against the registry.
2497 ret
= verify_host_key(host
, port
, keytype
, keystr
);
2499 if (ret
== 0) /* success - key matched OK */
2501 if (ret
== 2) { /* key was different */
2503 sprintf(message
, wrongmsg
, fingerprint
);
2504 mbret
= MessageBox(NULL
, message
, mbtitle
,
2505 MB_ICONWARNING
| MB_YESNOCANCEL
);
2507 store_host_key(host
, port
, keytype
, keystr
);
2508 if (mbret
== IDCANCEL
)
2511 if (ret
== 1) { /* key was absent */
2513 sprintf(message
, absentmsg
, fingerprint
);
2514 mbret
= MessageBox(NULL
, message
, mbtitle
,
2515 MB_ICONWARNING
| MB_YESNO
);
2518 store_host_key(host
, port
, keytype
, keystr
);
2523 * Ask whether to wipe a session log file before writing to it.
2524 * Returns 2 for wipe, 1 for append, 0 for cancel (don't log).
2526 int askappend(char *filename
)
2528 static const char mbtitle
[] = "PuTTY Log to File";
2529 static const char msgtemplate
[] =
2530 "The session log file \"%.*s\" already exists.\n"
2531 "You can overwrite it with a new session log,\n"
2532 "append your session log to the end of it,\n"
2533 "or disable session logging for this session.\n"
2534 "Hit Yes to wipe the file, No to append to it,\n"
2535 "or Cancel to disable logging.";
2536 char message
[sizeof(msgtemplate
) + FILENAME_MAX
];
2538 if (cfg
.logxfovr
!= LGXF_ASK
) {
2539 return ((cfg
.logxfovr
== LGXF_OVR
) ?
2 : 1);
2541 sprintf(message
, msgtemplate
, FILENAME_MAX
, filename
);
2543 mbret
= MessageBox(NULL
, message
, mbtitle
,
2544 MB_ICONQUESTION
| MB_YESNOCANCEL
);
2547 else if (mbret
== IDNO
)