Develop and Download Open Source Software

Browse Subversion Repository

Annotation of /branches/ssh_chacha20poly1305/ttssh2/ttxssh/ttxssh.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 6774 - (hide annotations) (download) (as text)
Mon Jun 5 11:30:41 2017 UTC (6 years, 10 months ago) by doda
Original Path: trunk/ttssh2/ttxssh/ttxssh.c
File MIME type: text/x-csrc
File size: 185720 byte(s)
デバッグログを ISO-8601 形式で出力するようにした。

デバッグログは基本的にはユーザが見る物では無いので、ユーザ指定の形式を反映しなくても大丈夫?
タイムゾーンを取るのが面倒なので UTC にしているけれど、これも問題ない?
1 maya 3227 /*
2     Copyright (c) 1998-2001, Robert O'Callahan
3     All rights reserved.
4    
5     Redistribution and use in source and binary forms, with or without modification,
6     are permitted provided that the following conditions are met:
7    
8     Redistributions of source code must retain the above copyright notice, this list of
9     conditions and the following disclaimer.
10    
11     Redistributions in binary form must reproduce the above copyright notice, this list
12     of conditions and the following disclaimer in the documentation and/or other materials
13     provided with the distribution.
14    
15     The name of Robert O'Callahan may not be used to endorse or promote products derived from
16     this software without specific prior written permission.
17    
18     THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND
19     ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20     OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
21     THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
22     EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23     SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
24     HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
25     OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
26     SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27     */
28    
29     /* Tera Term extension mechanism
30     Robert O'Callahan (roc+tt@cs.cmu.edu)
31    
32     Tera Term by Takashi Teranishi (teranishi@rikaxp.riken.go.jp)
33     */
34    
35     #include "ttxssh.h"
36     #include "fwdui.h"
37     #include "util.h"
38     #include "ssh.h"
39     #include "ttcommon.h"
40 r850 3298 #include "ttlib.h"
41 yutakapon 5545 #include "keyfiles.h"
42 doda 6250 #include "arc4random.h"
43 maya 3227
44     #include <stdlib.h>
45     #include <stdio.h>
46     #include <string.h>
47     #include <io.h>
48     #include <fcntl.h>
49     #include <sys/stat.h>
50     #include <time.h>
51 doda 3232 #include <mbstring.h>
52 maya 3227
53     #include "resource.h"
54     #include <commctrl.h>
55     #include <commdlg.h>
56     #include <winsock2.h>
57     static char FAR *ProtocolFamilyList[] = { "UNSPEC", "IPv6", "IPv4", NULL };
58    
59     #include <Lmcons.h>
60    
61     // include OpenSSL header file
62     #include <openssl/evp.h>
63     #include <openssl/rsa.h>
64     #include <openssl/dsa.h>
65     #include <openssl/bn.h>
66     #include <openssl/pem.h>
67     #include <openssl/rand.h>
68     #include <openssl/rc4.h>
69     #include <openssl/md5.h>
70    
71     // include ZLib header file
72     #include <zlib.h>
73    
74     #include "buffer.h"
75     #include "cipher.h"
76 maya 4321 #include "key.h"
77 maya 3227
78     #include "sftp.h"
79    
80     #include "compat_w95.h"
81    
82 maya 6625 #include "libputty.h"
83 yutakapon 4533
84 maya 3227 #define MATCH_STR(s, o) strncmp((s), (o), NUM_ELEM(o) - 1)
85     #define MATCH_STR_I(s, o) _strnicmp((s), (o), NUM_ELEM(o) - 1)
86    
87     /* This extension implements SSH, so we choose a load order in the
88     "protocols" range. */
89     #define ORDER 2500
90    
91     static HICON SecureLargeIcon = NULL;
92     static HICON SecureSmallIcon = NULL;
93 doda 6691 static HICON SecureNotifyIcon = NULL;
94     static HICON OldNotifyIcon = NULL;
95 maya 3227
96     static HFONT DlgHostFont;
97     static HFONT DlgAboutFont;
98 yutakapon 5578 static HFONT DlgAboutTextFont;
99 maya 3227 static HFONT DlgSetupFont;
100     static HFONT DlgKeygenFont;
101    
102     static TInstVar FAR *pvar;
103    
104     typedef struct {
105 maya 4307 int cnt;
106     HWND dlg;
107 maya 4378 ssh_keytype type;
108 maya 3227 } cbarg_t;
109    
110     /* WIN32 allows multiple instances of a DLL */
111     static TInstVar InstVar;
112    
113     /*
114     This code makes lots of assumptions about the order in which Tera Term
115     does things, and how. A key assumption is that the Notification window
116     passed into WSAAsyncSelect is the main terminal window. We also assume
117     that the socket used in the first WSAconnect is the main session socket.
118     */
119    
120     static void init_TTSSH(PTInstVar pvar)
121     {
122     pvar->socket = INVALID_SOCKET;
123     pvar->OldLargeIcon = NULL;
124     pvar->OldSmallIcon = NULL;
125     pvar->NotificationWindow = NULL;
126     pvar->hostdlg_activated = FALSE;
127     pvar->socket = INVALID_SOCKET;
128     pvar->NotificationWindow = NULL;
129     pvar->protocol_major = 0;
130     pvar->protocol_minor = 0;
131    
132     PKT_init(pvar);
133     SSH_init(pvar);
134     CRYPT_init(pvar);
135     AUTH_init(pvar);
136     HOSTS_init(pvar);
137     FWD_init(pvar);
138     FWDUI_init(pvar);
139    
140     ssh_heartbeat_lock_initialize();
141     }
142    
143     static void uninit_TTSSH(PTInstVar pvar)
144     {
145     halt_ssh_heartbeat_thread(pvar);
146    
147     ssh2_channel_free();
148    
149     SSH_end(pvar);
150     PKT_end(pvar);
151     AUTH_end(pvar);
152     CRYPT_end(pvar);
153     HOSTS_end(pvar);
154     FWD_end(pvar);
155     FWDUI_end(pvar);
156    
157     if (pvar->OldLargeIcon != NULL) {
158     PostMessage(pvar->NotificationWindow, WM_SETICON, ICON_BIG,
159     (LPARAM) pvar->OldLargeIcon);
160     pvar->OldLargeIcon = NULL;
161     }
162     if (pvar->OldSmallIcon != NULL) {
163     PostMessage(pvar->NotificationWindow, WM_SETICON, ICON_SMALL,
164     (LPARAM) pvar->OldSmallIcon);
165     pvar->OldSmallIcon = NULL;
166     }
167 doda 6691 if (OldNotifyIcon) {
168     SetCustomNotifyIcon(OldNotifyIcon);
169     }
170 maya 3227
171     ssh_heartbeat_lock_finalize();
172     }
173    
174     static void PASCAL FAR TTXInit(PTTSet ts, PComVar cv)
175     {
176     pvar->settings = *pvar->ts_SSH;
177     pvar->ts = ts;
178     pvar->cv = cv;
179     pvar->fatal_error = FALSE;
180     pvar->showing_err = FALSE;
181     pvar->err_msg = NULL;
182    
183     init_TTSSH(pvar);
184     }
185    
186 maya 4378 static void normalize_generic_order(char *buf, char default_strings[], int default_strings_len)
187     {
188     char listed[max(KEX_DH_MAX,max(SSH_CIPHER_MAX,max(KEY_MAX,max(HMAC_MAX,COMP_MAX)))) + 1];
189     char allowed[max(KEX_DH_MAX,max(SSH_CIPHER_MAX,max(KEY_MAX,max(HMAC_MAX,COMP_MAX)))) + 1];
190 maya 6031 int i, j, k=-1;
191 maya 4378
192     memset(listed, 0, sizeof(listed));
193     memset(allowed, 0, sizeof(allowed));
194 yutakapon 6508
195     // �����������������������X�g�������B
196 maya 4378 for (i = 0; i < default_strings_len ; i++) {
197     allowed[default_strings[i]] = 1;
198     }
199    
200 yutakapon 6508 // �w�����������������������A���������������������A�d���������������������B
201     //
202     // ex. (i=5 ����������������)
203     // i=012345
204     // >:=9<87;A@?B3026(\0)
205     // i+1
206     // <------------>
207     // ��
208     // >:=9<7;A@?B3026(\0)
209     //
210 maya 4378 for (i = 0; buf[i] != 0; i++) {
211     int num = buf[i] - '0';
212    
213     if (num < 0 || num > default_strings_len
214     || !allowed[num]
215     || listed[num]) {
216     memmove(buf + i, buf + i + 1, strlen(buf + i + 1) + 1);
217     i--;
218     } else {
219     listed[num] = 1;
220     }
221 maya 6031
222 yutakapon 6508 // disabled line���������A���u���o���������B
223 maya 6031 if (num == 0) {
224     k = i;
225     }
226 maya 4378 }
227    
228 yutakapon 6508 // �w���������������������������Adisabled line�����O���}�������B
229     //
230     // ex. (Z���}������)
231     // k
232     // >:=9<87;A@?B3026(\0)
233     // k+1
234     // <---->
235     // �� k
236     // >:=9<87;A@?B30026(\0)
237     // �� k
238     // >:=9<87;A@?B3Z026(\0)
239     //
240 maya 6031 for (j = 0; j < default_strings_len && default_strings[j] != 0; j++) {
241     int num = default_strings[j];
242    
243     if (!listed[num] && k >= 0) {
244 yutakapon 6508 int copylen = strlen(buf + k + 1) + 1;
245    
246     memmove(buf + k + 1, buf + k, copylen);
247     buf[k + 1 + copylen] = '\0'; // �I�[���Y�������t�����B
248 maya 6031 buf[k] = num + '0';
249     k++;
250     i++;
251     }
252     }
253     if (k < 0) {
254     j = 0;
255     }
256     else {
257     j++;
258     }
259 yutakapon 6508
260     // disabled line�������������������A�����������������������B
261 maya 6031 for (; j < default_strings_len ; j++) {
262     int num = default_strings[j];
263    
264     if (!listed[num]) {
265     buf[i] = num + '0';
266     i++;
267     }
268     }
269 maya 4378
270     buf[i] = 0;
271     }
272    
273 maya 3227 /*
274     * Remove unsupported cipher or duplicated cipher.
275     * Add unspecified ciphers at the end of list.
276     */
277     static void normalize_cipher_order(char FAR * buf)
278     {
279     /* SSH_CIPHER_NONE means that all ciphers below that one are disabled.
280     We *never* allow no encryption. */
281 maya 4378 static char default_strings[] = {
282 doda 4433 SSH2_CIPHER_CAMELLIA256_CTR,
283 maya 3227 SSH2_CIPHER_AES256_CTR,
284 doda 4433 SSH2_CIPHER_CAMELLIA256_CBC,
285 maya 3227 SSH2_CIPHER_AES256_CBC,
286 doda 4433 SSH2_CIPHER_CAMELLIA192_CTR,
287 maya 3227 SSH2_CIPHER_AES192_CTR,
288 doda 4433 SSH2_CIPHER_CAMELLIA192_CBC,
289 maya 3227 SSH2_CIPHER_AES192_CBC,
290 doda 4433 SSH2_CIPHER_CAMELLIA128_CTR,
291 maya 3227 SSH2_CIPHER_AES128_CTR,
292 doda 4433 SSH2_CIPHER_CAMELLIA128_CBC,
293 maya 3227 SSH2_CIPHER_AES128_CBC,
294 doda 3850 SSH2_CIPHER_3DES_CTR,
295 maya 3227 SSH2_CIPHER_3DES_CBC,
296 doda 3850 SSH2_CIPHER_BLOWFISH_CTR,
297 maya 3227 SSH2_CIPHER_BLOWFISH_CBC,
298 doda 3850 SSH2_CIPHER_CAST128_CTR,
299 maya 3227 SSH2_CIPHER_CAST128_CBC,
300     SSH_CIPHER_3DES,
301     SSH_CIPHER_NONE,
302 maya 5917 SSH2_CIPHER_ARCFOUR256,
303     SSH2_CIPHER_ARCFOUR128,
304     SSH2_CIPHER_ARCFOUR,
305     SSH_CIPHER_BLOWFISH,
306 maya 3227 SSH_CIPHER_DES,
307 maya 4432 0, 0, 0 // Dummy for SSH_CIPHER_IDEA, SSH_CIPHER_TSS, SSH_CIPHER_RC4
308 maya 3227 };
309    
310 maya 4378 normalize_generic_order(buf, default_strings, NUM_ELEM(default_strings));
311 maya 3227 }
312    
313 yutakapon 4367 static void normalize_kex_order(char FAR * buf)
314     {
315     static char default_strings[] = {
316     KEX_ECDH_SHA2_256,
317     KEX_ECDH_SHA2_384,
318     KEX_ECDH_SHA2_521,
319 doda 6310 KEX_DH_GRP18_SHA512,
320     KEX_DH_GRP16_SHA512,
321 doda 6263 KEX_DH_GRP14_SHA256,
322 yutakapon 4367 KEX_DH_GEX_SHA256,
323     KEX_DH_GEX_SHA1,
324     KEX_DH_GRP14_SHA1,
325     KEX_DH_GRP1_SHA1,
326     KEX_DH_NONE,
327     };
328    
329     normalize_generic_order(buf, default_strings, NUM_ELEM(default_strings));
330     }
331    
332     static void normalize_host_key_order(char FAR * buf)
333     {
334     static char default_strings[] = {
335     KEY_ECDSA256,
336     KEY_ECDSA384,
337     KEY_ECDSA521,
338 yutakapon 5545 KEY_ED25519,
339 yutakapon 4367 KEY_RSA,
340     KEY_DSA,
341     KEY_NONE,
342     };
343    
344     normalize_generic_order(buf, default_strings, NUM_ELEM(default_strings));
345     }
346    
347     static void normalize_mac_order(char FAR * buf)
348     {
349     static char default_strings[] = {
350 doda 4434 HMAC_SHA2_512,
351     HMAC_SHA2_256,
352 yutakapon 4367 HMAC_SHA1,
353 doda 4423 HMAC_RIPEMD160,
354 yutakapon 4367 HMAC_MD5,
355 doda 4426 HMAC_NONE,
356 doda 4434 HMAC_SHA1_96,
357     HMAC_MD5_96,
358 doda 5016 0, // Dummy for HMAC_SHA2_512_96,
359     0, // Dummy for HMAC_SHA2_256_96,
360 yutakapon 4367 };
361    
362     normalize_generic_order(buf, default_strings, NUM_ELEM(default_strings));
363     }
364    
365     static void normalize_comp_order(char FAR * buf)
366     {
367     static char default_strings[] = {
368 doda 4371 COMP_DELAYED,
369     COMP_ZLIB,
370 maya 4378 COMP_NOCOMP,
371 yutakapon 4367 COMP_NONE,
372     };
373    
374     normalize_generic_order(buf, default_strings, NUM_ELEM(default_strings));
375     }
376    
377    
378 maya 3227 /* Remove local settings from the shared memory block. */
379     static void clear_local_settings(PTInstVar pvar)
380     {
381     pvar->ts_SSH->TryDefaultAuth = FALSE;
382     }
383    
384     static BOOL read_BOOL_option(PCHAR fileName, char FAR * keyName, BOOL def)
385     {
386     char buf[1024];
387    
388     buf[0] = 0;
389     GetPrivateProfileString("TTSSH", keyName, "", buf, sizeof(buf),
390     fileName);
391     if (buf[0] == 0) {
392     return def;
393     } else {
394     return atoi(buf) != 0 ||
395     _stricmp(buf, "yes") == 0 ||
396     _stricmp(buf, "y") == 0;
397     }
398     }
399    
400     static void read_string_option(PCHAR fileName, char FAR * keyName,
401     char FAR * def, char FAR * buf, int bufSize)
402     {
403    
404     buf[0] = 0;
405     GetPrivateProfileString("TTSSH", keyName, def, buf, bufSize, fileName);
406     }
407    
408     static void read_ssh_options(PTInstVar pvar, PCHAR fileName)
409     {
410     char buf[1024];
411     TS_SSH FAR *settings = pvar->ts_SSH;
412    
413     #define READ_STD_STRING_OPTION(name) \
414     read_string_option(fileName, #name, "", settings->name, sizeof(settings->name))
415    
416     settings->Enabled = read_BOOL_option(fileName, "Enabled", FALSE);
417    
418     buf[0] = 0;
419     GetPrivateProfileString("TTSSH", "Compression", "", buf, sizeof(buf),
420     fileName);
421     settings->CompressionLevel = atoi(buf);
422     if (settings->CompressionLevel < 0 || settings->CompressionLevel > 9) {
423     settings->CompressionLevel = 0;
424     }
425    
426     READ_STD_STRING_OPTION(DefaultUserName);
427     READ_STD_STRING_OPTION(DefaultForwarding);
428     READ_STD_STRING_OPTION(DefaultRhostsLocalUserName);
429     READ_STD_STRING_OPTION(DefaultRhostsHostPrivateKeyFile);
430     READ_STD_STRING_OPTION(DefaultRSAPrivateKeyFile);
431    
432     READ_STD_STRING_OPTION(CipherOrder);
433     normalize_cipher_order(settings->CipherOrder);
434    
435 yutakapon 4367 // KEX order
436     READ_STD_STRING_OPTION(KexOrder);
437     normalize_kex_order(settings->KexOrder);
438     // Host Key algorithm order
439     READ_STD_STRING_OPTION(HostKeyOrder);
440     normalize_host_key_order(settings->HostKeyOrder);
441     // H-MAC order
442     READ_STD_STRING_OPTION(MacOrder);
443     normalize_mac_order(settings->MacOrder);
444     // Compression algorithm order
445     READ_STD_STRING_OPTION(CompOrder);
446     normalize_comp_order(settings->CompOrder);
447    
448 maya 3227 read_string_option(fileName, "KnownHostsFiles", "ssh_known_hosts",
449     settings->KnownHostsFiles,
450     sizeof(settings->KnownHostsFiles));
451    
452     buf[0] = 0;
453     GetPrivateProfileString("TTSSH", "DefaultAuthMethod", "", buf,
454     sizeof(buf), fileName);
455     settings->DefaultAuthMethod = atoi(buf);
456     if (settings->DefaultAuthMethod != SSH_AUTH_PASSWORD
457     && settings->DefaultAuthMethod != SSH_AUTH_RSA
458     && settings->DefaultAuthMethod != SSH_AUTH_TIS // add (2005.3.12 yutaka)
459     && settings->DefaultAuthMethod != SSH_AUTH_RHOSTS
460     && settings->DefaultAuthMethod != SSH_AUTH_PAGEANT) {
461     /* this default can never be SSH_AUTH_RHOSTS_RSA because that is not a
462     selection in the dialog box; SSH_AUTH_RHOSTS_RSA is automatically chosen
463     when the dialog box has rhosts selected and an host private key file
464     is supplied. */
465     settings->DefaultAuthMethod = SSH_AUTH_PASSWORD;
466     }
467    
468     buf[0] = 0;
469     GetPrivateProfileString("TTSSH", "LogLevel", "", buf, sizeof(buf),
470     fileName);
471     settings->LogLevel = atoi(buf);
472    
473     buf[0] = 0;
474     GetPrivateProfileString("TTSSH", "WriteBufferSize", "", buf,
475     sizeof(buf), fileName);
476     settings->WriteBufferSize = atoi(buf);
477     if (settings->WriteBufferSize <= 0) {
478     settings->WriteBufferSize = (PACKET_MAX_SIZE / 2); // 2MB
479     }
480    
481     // SSH protocol version (2004.10.11 yutaka)
482     // default is SSH2 (2004.11.30 yutaka)
483     settings->ssh_protocol_version = GetPrivateProfileInt("TTSSH", "ProtocolVersion", 2, fileName);
484    
485     // SSH heartbeat time(second) (2004.12.11 yutaka)
486     settings->ssh_heartbeat_overtime = GetPrivateProfileInt("TTSSH", "HeartBeat", 60, fileName);
487    
488     // �p�X���[�h�F�����������J���F�����g���p�X���[�h����������������������������������
489     // �\���B(2006.8.5 yutaka)
490     settings->remember_password = GetPrivateProfileInt("TTSSH", "RememberPassword", 1, fileName);
491    
492     // �������F���_�C�A���O���T�|�[�g�������������\�b�h���`�F�b�N���A
493     // ���������\�b�h���O���C�A�E�g���� (2007.9.24 maya)
494     settings->CheckAuthListFirst = read_BOOL_option(fileName, "CheckAuthListFirst", FALSE);
495    
496     // 768bit ������ RSA ���������T�[�o�����������L�������� (2008.9.11 maya)
497     settings->EnableRsaShortKeyServer = read_BOOL_option(fileName, "EnableRsaShortKeyServer", FALSE);
498    
499     // agent forward ���L�������� (2008.11.25 maya)
500     settings->ForwardAgent = read_BOOL_option(fileName, "ForwardAgent", FALSE);
501    
502 maya 4229 // agent forward �m�F���L��������
503     settings->ForwardAgentConfirm = read_BOOL_option(fileName, "ForwardAgentConfirm", TRUE);
504    
505 doda 6663 // agent forward �m�F���L��������
506     settings->ForwardAgentNotify = read_BOOL_option(fileName, "ForwardAgentNotify", TRUE);
507    
508 doda 4531 // �z�X�g���� DNS �����`�F�b�N (RFC 4255)
509 doda 4619 settings->VerifyHostKeyDNS = read_BOOL_option(fileName, "VerifyHostKeyDNS", TRUE);
510 doda 4531
511 doda 5261 // icon
512     GetPrivateProfileString("TTSSH", "SSHIcon", "", buf, sizeof(buf), fileName);
513     if ((_stricmp(buf, "old") == 0) ||
514     (_stricmp(buf, "yellow") == 0) ||
515     (_stricmp(buf, "securett_yellow") == 0)) {
516     settings->IconID = IDI_SECURETT_YELLOW;
517     }
518 maya 6386 else if ((_stricmp(buf, "green") == 0) ||
519     (_stricmp(buf, "securett_green") == 0)) {
520     settings->IconID = IDI_SECURETT_GREEN;
521     }
522 doda 5261 else {
523     settings->IconID = IDI_SECURETT;
524     }
525    
526 yutakapon 5620 // �G���[�������x�������|�b�v�A�b�v���b�Z�[�W���}�~���� (2014.6.26 yutaka)
527     settings->DisablePopupMessage = GetPrivateProfileInt("TTSSH", "DisablePopupMessage", 0, fileName);
528    
529 doda 5793 READ_STD_STRING_OPTION(X11Display);
530    
531 yutakapon 5849 settings->UpdateHostkeys = GetPrivateProfileInt("TTSSH", "UpdateHostkeys", 0, fileName);
532 yutakapon 5839
533 doda 5900 settings->GexMinimalGroupSize = GetPrivateProfileInt("TTSSH", "GexMinimalGroupSize", 0, fileName);
534    
535 maya 3227 clear_local_settings(pvar);
536     }
537    
538     static void write_ssh_options(PTInstVar pvar, PCHAR fileName,
539 maya 5868 TS_SSH FAR * settings, BOOL copy_forward)
540 maya 3227 {
541     char buf[1024];
542    
543     WritePrivateProfileString("TTSSH", "Enabled",
544     settings->Enabled ? "1" : "0", fileName);
545    
546     _itoa(settings->CompressionLevel, buf, 10);
547     WritePrivateProfileString("TTSSH", "Compression", buf, fileName);
548    
549     WritePrivateProfileString("TTSSH", "DefaultUserName",
550     settings->DefaultUserName, fileName);
551    
552     if (copy_forward) {
553     WritePrivateProfileString("TTSSH", "DefaultForwarding",
554 maya 5960 settings->DefaultForwarding, fileName);
555 maya 3227 }
556    
557     WritePrivateProfileString("TTSSH", "CipherOrder",
558     settings->CipherOrder, fileName);
559    
560 yutakapon 4367 WritePrivateProfileString("TTSSH", "KexOrder",
561     settings->KexOrder, fileName);
562    
563     WritePrivateProfileString("TTSSH", "HostKeyOrder",
564     settings->HostKeyOrder, fileName);
565    
566     WritePrivateProfileString("TTSSH", "MacOrder",
567     settings->MacOrder, fileName);
568    
569     WritePrivateProfileString("TTSSH", "CompOrder",
570     settings->CompOrder, fileName);
571    
572 maya 3227 WritePrivateProfileString("TTSSH", "KnownHostsFiles",
573     settings->KnownHostsFiles, fileName);
574    
575     WritePrivateProfileString("TTSSH", "DefaultRhostsLocalUserName",
576     settings->DefaultRhostsLocalUserName,
577     fileName);
578    
579     WritePrivateProfileString("TTSSH", "DefaultRhostsHostPrivateKeyFile",
580     settings->DefaultRhostsHostPrivateKeyFile,
581     fileName);
582    
583     WritePrivateProfileString("TTSSH", "DefaultRSAPrivateKeyFile",
584     settings->DefaultRSAPrivateKeyFile,
585     fileName);
586    
587     _itoa(settings->DefaultAuthMethod, buf, 10);
588     WritePrivateProfileString("TTSSH", "DefaultAuthMethod", buf, fileName);
589    
590     _itoa(settings->LogLevel, buf, 10);
591     WritePrivateProfileString("TTSSH", "LogLevel", buf, fileName);
592    
593     _itoa(settings->WriteBufferSize, buf, 10);
594     WritePrivateProfileString("TTSSH", "WriteBufferSize", buf, fileName);
595    
596     // SSH protocol version (2004.10.11 yutaka)
597     WritePrivateProfileString("TTSSH", "ProtocolVersion",
598     settings->ssh_protocol_version==2 ? "2" : "1",
599     fileName);
600    
601     // SSH heartbeat time(second) (2004.12.11 yutaka)
602     _snprintf_s(buf, sizeof(buf), _TRUNCATE,
603     "%d", settings->ssh_heartbeat_overtime);
604     WritePrivateProfileString("TTSSH", "HeartBeat", buf, fileName);
605    
606     // Remember password (2006.8.5 yutaka)
607     WritePrivateProfileString("TTSSH", "RememberPassword",
608     settings->remember_password ? "1" : "0",
609     fileName);
610    
611     // �������F���_�C�A���O���T�|�[�g�������������\�b�h���`�F�b�N���A
612     // ���������\�b�h���O���C�A�E�g���� (2007.9.24 maya)
613     WritePrivateProfileString("TTSSH", "CheckAuthListFirst",
614     settings->CheckAuthListFirst ? "1" : "0", fileName);
615    
616     // 768bit ������ RSA ���������T�[�o�����������L�������� (2008.9.11 maya)
617     WritePrivateProfileString("TTSSH", "EnableRsaShortKeyServer",
618     settings->EnableRsaShortKeyServer ? "1" : "0", fileName);
619    
620     // agent forward ���L�������� (2008.11.25 maya)
621     WritePrivateProfileString("TTSSH", "ForwardAgent",
622     settings->ForwardAgent ? "1" : "0", fileName);
623 maya 4229
624     // agent forward �m�F���L��������
625     WritePrivateProfileString("TTSSH", "ForwardAgentConfirm",
626     settings->ForwardAgentConfirm ? "1" : "0", fileName);
627 doda 4531
628 doda 6663 // agent forward ���m���L��������
629     WritePrivateProfileString("TTSSH", "ForwardAgentNotify",
630     settings->ForwardAgentNotify ? "1" : "0", fileName);
631    
632 doda 4531 // �z�X�g���� DNS �����`�F�b�N (RFC 4255)
633     WritePrivateProfileString("TTSSH", "VerifyHostKeyDNS",
634     settings->VerifyHostKeyDNS ? "1" : "0", fileName);
635 doda 5294
636     // SSH �A�C�R��
637 maya 6386 if (settings->IconID==IDI_SECURETT_YELLOW) {
638     WritePrivateProfileString("TTSSH", "SSHIcon", "yellow", fileName);
639     }
640     else if (settings->IconID==IDI_SECURETT_GREEN) {
641     WritePrivateProfileString("TTSSH", "SSHIcon", "green", fileName);
642     }
643     else {
644     WritePrivateProfileString("TTSSH", "SSHIcon", "Default", fileName);
645     }
646 yutakapon 5620
647     _itoa(settings->DisablePopupMessage, buf, 10);
648     WritePrivateProfileString("TTSSH", "DisablePopupMessage", buf, fileName);
649 doda 5793
650     WritePrivateProfileString("TTSSH", "X11Display", settings->X11Display, fileName);
651 yutakapon 5839
652 yutakapon 5849 _snprintf_s(buf, sizeof(buf), _TRUNCATE,
653     "%d", settings->UpdateHostkeys);
654     WritePrivateProfileString("TTSSH", "UpdateHostkeys", buf, fileName);
655 doda 5900
656     _itoa_s(settings->GexMinimalGroupSize, buf, sizeof(buf), 10);
657     WritePrivateProfileString("TTSSH", "GexMinimalGroupSize", buf, fileName);
658 maya 3227 }
659    
660    
661     /* find free port in all protocol family */
662     static unsigned short find_local_port(PTInstVar pvar)
663     {
664     int tries;
665     SOCKET connecter;
666     struct addrinfo hints;
667     struct addrinfo FAR *res;
668     struct addrinfo FAR *res0;
669     unsigned short port;
670     char pname[NI_MAXHOST];
671    
672     if (pvar->session_settings.DefaultAuthMethod != SSH_AUTH_RHOSTS) {
673     return 0;
674     }
675    
676     /* The random numbers here are only used to try to get fresh
677     ports across runs (dangling ports can cause bind errors
678     if we're unlucky). They do not need to be (and are not)
679     cryptographically strong.
680     */
681     srand((unsigned) GetTickCount());
682    
683     for (tries = 20; tries > 0; tries--) {
684     memset(&hints, 0, sizeof(hints));
685     hints.ai_family = pvar->ts->ProtocolFamily;
686     hints.ai_flags = AI_PASSIVE;
687     hints.ai_socktype = SOCK_STREAM;
688     port = (unsigned) rand() % 512 + 512;
689     _snprintf_s(pname, sizeof(pname), _TRUNCATE, "%d", (int) port);
690     if (getaddrinfo(NULL, pname, &hints, &res0)) {
691     return 0;
692     /* NOT REACHED */
693     }
694    
695     for (res = res0; res; res = res->ai_next) {
696     if (res->ai_family == AF_INET || res->ai_family == AF_INET6)
697     continue;
698    
699     connecter =
700     socket(res->ai_family, res->ai_socktype, res->ai_protocol);
701     if (connecter == INVALID_SOCKET) {
702     freeaddrinfo(res0);
703     return 0;
704     }
705    
706     if (bind(connecter, res->ai_addr, res->ai_addrlen) !=
707     SOCKET_ERROR) {
708     return port;
709     freeaddrinfo(res0);
710     closesocket(connecter);
711     } else if (WSAGetLastError() != WSAEADDRINUSE) {
712     closesocket(connecter);
713     freeaddrinfo(res0);
714     return 0;
715     }
716    
717     closesocket(connecter);
718     }
719     freeaddrinfo(res0);
720     }
721    
722     return 0;
723     }
724    
725     static int PASCAL FAR TTXconnect(SOCKET s,
726     const struct sockaddr FAR * name,
727     int namelen)
728     {
729 maya 4584 if (pvar->socket == INVALID_SOCKET || pvar->socket != s) {
730 maya 3227 struct sockaddr_storage ss;
731     int len;
732    
733     pvar->socket = s;
734    
735     memset(&ss, 0, sizeof(ss));
736     switch (pvar->ts->ProtocolFamily) {
737     case AF_INET:
738     len = sizeof(struct sockaddr_in);
739     ((struct sockaddr_in FAR *) &ss)->sin_family = AF_INET;
740     ((struct sockaddr_in FAR *) &ss)->sin_addr.s_addr = INADDR_ANY;
741     ((struct sockaddr_in FAR *) &ss)->sin_port =
742     htons(find_local_port(pvar));
743     break;
744     case AF_INET6:
745     len = sizeof(struct sockaddr_in6);
746     ((struct sockaddr_in6 FAR *) &ss)->sin6_family = AF_INET6;
747     memset(&((struct sockaddr_in6 FAR *) &ss)->sin6_addr, 0,
748     sizeof(struct in_addr6));
749     ((struct sockaddr_in6 FAR *) &ss)->sin6_port =
750     htons(find_local_port(pvar));
751     break;
752     default:
753 maya 4586 /* UNSPEC */
754 maya 3227 break;
755     }
756    
757     bind(s, (struct sockaddr FAR *) &ss, len);
758     }
759    
760     return (pvar->Pconnect) (s, name, namelen);
761     }
762    
763     static int PASCAL FAR TTXWSAAsyncSelect(SOCKET s, HWND hWnd, u_int wMsg,
764     long lEvent)
765     {
766     if (s == pvar->socket) {
767     pvar->notification_events = lEvent;
768     pvar->notification_msg = wMsg;
769    
770     if (pvar->NotificationWindow == NULL) {
771     pvar->NotificationWindow = hWnd;
772     AUTH_advance_to_next_cred(pvar);
773     }
774     }
775    
776     return (pvar->PWSAAsyncSelect) (s, hWnd, wMsg, lEvent);
777     }
778    
779     static int PASCAL FAR TTXrecv(SOCKET s, char FAR * buf, int len, int flags)
780     {
781     if (s == pvar->socket) {
782     int ret;
783    
784     ssh_heartbeat_lock();
785     ret = PKT_recv(pvar, buf, len);
786     ssh_heartbeat_unlock();
787     return (ret);
788    
789     } else {
790     return (pvar->Precv) (s, buf, len, flags);
791     }
792     }
793    
794     static int PASCAL FAR TTXsend(SOCKET s, char const FAR * buf, int len,
795     int flags)
796     {
797     if (s == pvar->socket) {
798     ssh_heartbeat_lock();
799     SSH_send(pvar, buf, len);
800     ssh_heartbeat_unlock();
801     return len;
802     } else {
803     return (pvar->Psend) (s, buf, len, flags);
804     }
805     }
806    
807     void notify_established_secure_connection(PTInstVar pvar)
808     {
809     int fuLoad = LR_DEFAULTCOLOR;
810    
811 yutakapon 6286 if (IsWindowsNT4()) {
812 maya 3227 fuLoad = LR_VGACOLOR;
813     }
814    
815     // LoadIcon �������� LoadImage ���g�����������A
816     // 16x16 ���A�C�R���������I�������������������� (2006.8.9 maya)
817     if (SecureLargeIcon == NULL) {
818 doda 5261 SecureLargeIcon = LoadImage(hInst, MAKEINTRESOURCE(pvar->settings.IconID),
819 maya 3227 IMAGE_ICON, 0, 0, fuLoad);
820     }
821     if (SecureSmallIcon == NULL) {
822 doda 5261 SecureSmallIcon = LoadImage(hInst, MAKEINTRESOURCE(pvar->settings.IconID),
823 maya 3227 IMAGE_ICON, 16, 16, fuLoad);
824     }
825    
826     if (SecureLargeIcon != NULL && SecureSmallIcon != NULL) {
827     pvar->OldLargeIcon =
828 maya 3454 (HICON) SendMessage(pvar->NotificationWindow, WM_GETICON,
829     ICON_BIG, 0);
830 maya 3227 pvar->OldSmallIcon =
831     (HICON) SendMessage(pvar->NotificationWindow, WM_GETICON,
832     ICON_SMALL, 0);
833    
834     PostMessage(pvar->NotificationWindow, WM_SETICON, ICON_BIG,
835     (LPARAM) SecureLargeIcon);
836     PostMessage(pvar->NotificationWindow, WM_SETICON, ICON_SMALL,
837     (LPARAM) SecureSmallIcon);
838     }
839    
840 doda 6691 if (IsWindows2000()) {
841     if (SecureNotifyIcon == NULL) {
842     SecureNotifyIcon = LoadImage(hInst, MAKEINTRESOURCE(pvar->settings.IconID),
843     IMAGE_ICON, 0, 0, LR_VGACOLOR | LR_SHARED);
844     }
845     OldNotifyIcon = GetCustomNotifyIcon();
846     SetCustomNotifyIcon(SecureNotifyIcon);
847     }
848    
849 maya 3227 notify_verbose_message(pvar, "Entering secure mode",
850     LOG_LEVEL_VERBOSE);
851     }
852    
853 maya 5678 void notify_closed_connection(PTInstVar pvar, char FAR * send_msg)
854 maya 3227 {
855 maya 5678 SSH_notify_disconnecting(pvar, send_msg);
856 maya 3227 AUTH_notify_disconnecting(pvar);
857     HOSTS_notify_disconnecting(pvar);
858    
859     PostMessage(pvar->NotificationWindow, WM_USER_COMMNOTIFY,
860     pvar->socket, MAKELPARAM(FD_CLOSE, 0));
861     }
862    
863     static void add_err_msg(PTInstVar pvar, char FAR * msg)
864     {
865     if (pvar->err_msg != NULL) {
866     int buf_len = strlen(pvar->err_msg) + 3 + strlen(msg);
867     char FAR *buf = (char FAR *) malloc(buf_len);
868    
869     strncpy_s(buf, buf_len, pvar->err_msg, _TRUNCATE);
870     strncat_s(buf, buf_len, "\n\n", _TRUNCATE);
871     strncat_s(buf, buf_len, msg, _TRUNCATE);
872     free(pvar->err_msg);
873     pvar->err_msg = buf;
874     } else {
875     pvar->err_msg = _strdup(msg);
876     }
877     }
878    
879     void notify_nonfatal_error(PTInstVar pvar, char FAR * msg)
880     {
881     if (!pvar->showing_err) {
882     // �������������������m���E�B���h�E�����������A�f�X�N�g�b�v���I�[�i�[������
883     // ���b�Z�[�W�{�b�N�X���o���������B(2006.6.11 yutaka)
884     if (pvar->NotificationWindow == NULL) {
885 doda 6688 UTIL_get_lang_msg("MSG_NONFATAL_ERROR", pvar,
886 maya 3227 "Tera Term: not fatal error");
887     MessageBox(NULL, msg, pvar->ts->UIMsg, MB_OK|MB_ICONINFORMATION);
888     msg[0] = '\0';
889    
890     } else {
891     PostMessage(pvar->NotificationWindow, WM_COMMAND,
892     ID_SSHASYNCMESSAGEBOX, 0);
893     }
894     }
895     if (msg[0] != 0) {
896     notify_verbose_message(pvar, msg, LOG_LEVEL_ERROR);
897     add_err_msg(pvar, msg);
898     }
899     }
900    
901 maya 5678 void notify_fatal_error(PTInstVar pvar, char FAR * msg, BOOL send_disconnect)
902 maya 3227 {
903     if (msg[0] != 0) {
904     notify_verbose_message(pvar, msg, LOG_LEVEL_FATAL);
905     add_err_msg(pvar, msg);
906     }
907    
908     if (!pvar->fatal_error) {
909     pvar->fatal_error = TRUE;
910    
911 maya 5678 if (send_disconnect) {
912     SSH_notify_disconnecting(pvar, msg);
913     }
914 maya 3227 AUTH_notify_disconnecting(pvar);
915     HOSTS_notify_disconnecting(pvar);
916    
917     PostMessage(pvar->NotificationWindow, WM_USER_COMMNOTIFY,
918     pvar->socket, MAKELPARAM(FD_CLOSE,
919     (pvar->PWSAGetLastError) ()));
920     }
921     }
922    
923     void notify_verbose_message(PTInstVar pvar, char FAR * msg, int level)
924     {
925     if (level <= pvar->session_settings.LogLevel) {
926     char buf[1024];
927     int file;
928    
929     get_teraterm_dir_relative_name(buf, NUM_ELEM(buf), "TTSSH.LOG");
930     file = _open(buf, _O_RDWR | _O_APPEND | _O_CREAT | _O_TEXT,
931     _S_IREAD | _S_IWRITE);
932    
933     if (file >= 0) {
934 doda 6774 char *strtime = mctimelocal("%Y-%m-%dT%H:%M:%S,%NZ", TRUE);
935 maya 4546 DWORD processid;
936 maya 3227 char tmp[26];
937 maya 4546
938     _write(file, strtime, strlen(strtime));
939 maya 3227 GetWindowThreadProcessId(pvar->cv->HWin, &processid);
940     _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, " [%lu] ",processid);
941     _write(file, tmp, strlen(tmp));
942     _write(file, msg, strlen(msg));
943     _write(file, "\n", 1);
944     _close(file);
945     }
946     }
947     }
948    
949 doda 6533 void logprintf(PTInstVar pv, int level, char *fmt, ...)
950 doda 6051 {
951     char buff[4096];
952     va_list params;
953    
954 doda 6533 if (pv == NULL) {
955     pv = pvar;
956     }
957    
958     if (level <= pv->session_settings.LogLevel) {
959 doda 6051 va_start(params, fmt);
960     vsnprintf_s(buff, sizeof(buff), _TRUNCATE, fmt, params);
961     va_end(params);
962    
963 doda 6533 notify_verbose_message(pv, buff, level);
964 doda 6051 }
965     }
966    
967 yutakapon 6302 static void format_line_hexdump(char *buf, int buflen, int addr, int *bytes, int byte_cnt)
968     {
969     int i, c;
970     char tmp[128];
971    
972     buf[0] = 0;
973    
974     /* �������A�h���X�\�� */
975     _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, "%08X : ", addr);
976     strncat_s(buf, buflen, tmp, _TRUNCATE);
977    
978     /* �o�C�i���\���i4�o�C�g�������������}���j*/
979     for (i = 0; i < byte_cnt; i++) {
980     if (i > 0 && i % 4 == 0) {
981     strncat_s(buf, buflen, " ", _TRUNCATE);
982     }
983    
984     _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, "%02X", bytes[i]);
985     strncat_s(buf, buflen, tmp, _TRUNCATE);
986     }
987    
988     /* ASCII�\���������������������� */
989     _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, " %*s%*s", (16 - byte_cnt) * 2 + 1, " ", (16 - byte_cnt + 3) / 4, " ");
990     strncat_s(buf, buflen, tmp, _TRUNCATE);
991    
992     /* ASCII�\�� */
993     for (i = 0; i < byte_cnt; i++) {
994     c = bytes[i];
995     if (isprint(c)) {
996     _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, "%c", c);
997     strncat_s(buf, buflen, tmp, _TRUNCATE);
998     }
999     else {
1000     strncat_s(buf, buflen, ".", _TRUNCATE);
1001     }
1002     }
1003    
1004     //strncat_s(buf, buflen, "\n", _TRUNCATE);
1005     }
1006    
1007     void logprintf_hexdump(PTInstVar pvar, int level, char *data, int len, char *fmt, ...)
1008     {
1009     char buff[4096];
1010     va_list params;
1011     int c, addr;
1012     int bytes[16], *ptr;
1013     int byte_cnt;
1014     int i;
1015    
1016     if (level <= pvar->session_settings.LogLevel) {
1017     va_start(params, fmt);
1018     vsnprintf_s(buff, sizeof(buff), _TRUNCATE, fmt, params);
1019     va_end(params);
1020    
1021     notify_verbose_message(pvar, buff, level);
1022    
1023     addr = 0;
1024     byte_cnt = 0;
1025     ptr = bytes;
1026     for (i = 0; i < len; i++) {
1027     c = data[i];
1028     *ptr++ = c & 0xff;
1029     byte_cnt++;
1030    
1031     if (byte_cnt == 16) {
1032     format_line_hexdump(buff, sizeof(buff), addr, bytes, byte_cnt);
1033     notify_verbose_message(pvar, buff, level);
1034    
1035     addr += 16;
1036     byte_cnt = 0;
1037     ptr = bytes;
1038     }
1039     }
1040    
1041     if (byte_cnt > 0) {
1042     format_line_hexdump(buff, sizeof(buff), addr, bytes, byte_cnt);
1043     notify_verbose_message(pvar, buff, level);
1044     }
1045     }
1046     }
1047    
1048 maya 3227 static void PASCAL FAR TTXOpenTCP(TTXSockHooks FAR * hooks)
1049     {
1050     if (pvar->settings.Enabled) {
1051     // TCPLocalEcho/TCPCRSend ������������ (maya 2007.4.25)
1052 doda 3579 pvar->origDisableTCPEchoCR = pvar->ts->DisableTCPEchoCR;
1053 maya 3227 pvar->ts->DisableTCPEchoCR = TRUE;
1054    
1055     pvar->session_settings = pvar->settings;
1056    
1057     notify_verbose_message(pvar, "---------------------------------------------------------------------", LOG_LEVEL_VERBOSE);
1058     notify_verbose_message(pvar, "Initiating SSH session", LOG_LEVEL_VERBOSE);
1059    
1060     FWDUI_load_settings(pvar);
1061    
1062     pvar->cv->TelAutoDetect = FALSE;
1063     /* This next line should not be needed because Tera Term's
1064     CommLib should find ts->Telnet == 0 ... but we'll do this
1065     just to be on the safe side. */
1066     pvar->cv->TelFlag = FALSE;
1067 doda 3495 pvar->cv->TelLineMode = FALSE;
1068 maya 3227
1069     pvar->Precv = *hooks->Precv;
1070     pvar->Psend = *hooks->Psend;
1071     pvar->PWSAAsyncSelect = *hooks->PWSAAsyncSelect;
1072     pvar->Pconnect = *hooks->Pconnect;
1073     pvar->PWSAGetLastError = *hooks->PWSAGetLastError;
1074    
1075     *hooks->Precv = TTXrecv;
1076     *hooks->Psend = TTXsend;
1077     *hooks->PWSAAsyncSelect = TTXWSAAsyncSelect;
1078     *hooks->Pconnect = TTXconnect;
1079    
1080     SSH_open(pvar);
1081     HOSTS_open(pvar);
1082     FWDUI_open(pvar);
1083    
1084     // ������ myproposal �����f���������A�������O�����������B (2006.6.26 maya)
1085     SSH2_update_cipher_myproposal(pvar);
1086 yutakapon 4367 SSH2_update_kex_myproposal(pvar);
1087     SSH2_update_host_key_myproposal(pvar);
1088     SSH2_update_hmac_myproposal(pvar);
1089 maya 3227 SSH2_update_compression_myproposal(pvar);
1090     }
1091     }
1092    
1093     static void PASCAL FAR TTXCloseTCP(TTXSockHooks FAR * hooks)
1094     {
1095     if (pvar->session_settings.Enabled) {
1096     pvar->socket = INVALID_SOCKET;
1097    
1098     notify_verbose_message(pvar, "Terminating SSH session...",
1099     LOG_LEVEL_VERBOSE);
1100    
1101     *hooks->Precv = pvar->Precv;
1102     *hooks->Psend = pvar->Psend;
1103     *hooks->PWSAAsyncSelect = pvar->PWSAAsyncSelect;
1104     *hooks->Pconnect = pvar->Pconnect;
1105 doda 3579
1106     pvar->ts->DisableTCPEchoCR = pvar->origDisableTCPEchoCR;
1107 maya 3227 }
1108    
1109     uninit_TTSSH(pvar);
1110     init_TTSSH(pvar);
1111     }
1112    
1113     static void enable_dlg_items(HWND dlg, int from, int to, BOOL enabled)
1114     {
1115     for (; from <= to; from++) {
1116     EnableWindow(GetDlgItem(dlg, from), enabled);
1117     }
1118     }
1119    
1120     // C-p/C-n/C-b/C-f/C-a/C-e ���T�|�[�g (2007.9.5 maya)
1121     // C-d/C-k ���T�|�[�g (2007.10.3 yutaka)
1122     // �h���b�v�_�E���������G�f�B�b�g�R���g���[����
1123     // �T�u�N���X�������������E�C���h�E�v���V�[�W��
1124     WNDPROC OrigHostnameEditProc; // Original window procedure
1125     LRESULT CALLBACK HostnameEditProc(HWND dlg, UINT msg,
1126 maya 5868 WPARAM wParam, LPARAM lParam)
1127 maya 3227 {
1128     HWND parent;
1129     int max, select, len;
1130     char *str, *orgstr;
1131    
1132     switch (msg) {
1133     // �L�[�����������������m����
1134     case WM_KEYDOWN:
1135     if (GetKeyState(VK_CONTROL) < 0) {
1136     switch (wParam) {
1137     case 0x50: // Ctrl+p ... up
1138     parent = GetParent(dlg);
1139     select = SendMessage(parent, CB_GETCURSEL, 0, 0);
1140     if (select > 0) {
1141     PostMessage(parent, CB_SETCURSEL, select - 1, 0);
1142     }
1143     return 0;
1144     case 0x4e: // Ctrl+n ... down
1145     parent = GetParent(dlg);
1146     max = SendMessage(parent, CB_GETCOUNT, 0, 0);
1147     select = SendMessage(parent, CB_GETCURSEL, 0, 0);
1148     if (select < max - 1) {
1149     PostMessage(parent, CB_SETCURSEL, select + 1, 0);
1150     }
1151     return 0;
1152     case 0x42: // Ctrl+b ... left
1153     SendMessage(dlg, EM_GETSEL, 0, (LPARAM)&select);
1154     PostMessage(dlg, EM_SETSEL, select-1, select-1);
1155     return 0;
1156     case 0x46: // Ctrl+f ... right
1157     SendMessage(dlg, EM_GETSEL, 0, (LPARAM)&select);
1158     max = GetWindowTextLength(dlg) ;
1159     PostMessage(dlg, EM_SETSEL, select+1, select+1);
1160     return 0;
1161     case 0x41: // Ctrl+a ... home
1162     PostMessage(dlg, EM_SETSEL, 0, 0);
1163     return 0;
1164     case 0x45: // Ctrl+e ... end
1165     max = GetWindowTextLength(dlg) ;
1166     PostMessage(dlg, EM_SETSEL, max, max);
1167     return 0;
1168    
1169     case 0x44: // Ctrl+d
1170     case 0x4b: // Ctrl+k
1171     case 0x55: // Ctrl+u
1172     SendMessage(dlg, EM_GETSEL, 0, (LPARAM)&select);
1173     max = GetWindowTextLength(dlg);
1174     max++; // '\0'
1175     orgstr = str = malloc(max);
1176     if (str != NULL) {
1177     len = GetWindowText(dlg, str, max);
1178     if (select >= 0 && select < len) {
1179     if (wParam == 0x44) { // �J�[�\���z����������������������
1180     memmove(&str[select], &str[select + 1], len - select - 1);
1181     str[len - 1] = '\0';
1182    
1183     } else if (wParam == 0x4b) { // �J�[�\�������s��������������
1184     str[select] = '\0';
1185    
1186     }
1187     }
1188    
1189     if (wParam == 0x55) { // �J�[�\����������������������
1190     if (select >= len) {
1191     str[0] = '\0';
1192     } else {
1193     str = &str[select];
1194     }
1195     select = 0;
1196     }
1197    
1198     SetWindowText(dlg, str);
1199     SendMessage(dlg, EM_SETSEL, select, select);
1200     free(orgstr);
1201     return 0;
1202     }
1203     break;
1204     }
1205     }
1206     break;
1207    
1208     // �����L�[��������������������������������������������
1209     case WM_CHAR:
1210     switch (wParam) {
1211     case 0x01:
1212     case 0x02:
1213     case 0x04:
1214     case 0x05:
1215     case 0x06:
1216     case 0x0b:
1217     case 0x0e:
1218     case 0x10:
1219     case 0x15:
1220     return 0;
1221     }
1222     }
1223    
1224     return CallWindowProc(OrigHostnameEditProc, dlg, msg, wParam, lParam);
1225     }
1226    
1227     static BOOL CALLBACK TTXHostDlg(HWND dlg, UINT msg, WPARAM wParam,
1228     LPARAM lParam)
1229     {
1230     static char *ssh_version[] = {"SSH1", "SSH2", NULL};
1231     PGetHNRec GetHNRec;
1232     char EntName[128];
1233     char TempHost[HostNameMaxLength + 1];
1234     WORD i, j, w;
1235     WORD ComPortTable[MAXCOMPORT];
1236     static char *ComPortDesc[MAXCOMPORT];
1237     int comports;
1238     BOOL Ok;
1239     LOGFONT logfont;
1240     HFONT font;
1241     char uimsg[MAX_UIMSG];
1242     static HWND hwndHostname = NULL; // HOSTNAME dropdown
1243     static HWND hwndHostnameEdit = NULL; // Edit control on HOSTNAME dropdown
1244    
1245     switch (msg) {
1246     case WM_INITDIALOG:
1247     GetHNRec = (PGetHNRec) lParam;
1248     SetWindowLong(dlg, DWL_USER, lParam);
1249    
1250     GetWindowText(dlg, uimsg, sizeof(uimsg));
1251     UTIL_get_lang_msg("DLG_HOST_TITLE", pvar, uimsg);
1252     SetWindowText(dlg, pvar->ts->UIMsg);
1253     GetDlgItemText(dlg, IDC_HOSTNAMELABEL, uimsg, sizeof(uimsg));
1254     UTIL_get_lang_msg("DLG_HOST_TCPIPHOST", pvar, uimsg);
1255     SetDlgItemText(dlg, IDC_HOSTNAMELABEL, pvar->ts->UIMsg);
1256     GetDlgItemText(dlg, IDC_HISTORY, uimsg, sizeof(uimsg));
1257     UTIL_get_lang_msg("DLG_HOST_TCPIPHISTORY", pvar, uimsg);
1258     SetDlgItemText(dlg, IDC_HISTORY, pvar->ts->UIMsg);
1259     GetDlgItemText(dlg, IDC_SERVICELABEL, uimsg, sizeof(uimsg));
1260     UTIL_get_lang_msg("DLG_HOST_TCPIPSERVICE", pvar, uimsg);
1261     SetDlgItemText(dlg, IDC_SERVICELABEL, pvar->ts->UIMsg);
1262     GetDlgItemText(dlg, IDC_HOSTOTHER, uimsg, sizeof(uimsg));
1263     UTIL_get_lang_msg("DLG_HOST_TCPIPOTHER", pvar, uimsg);
1264     SetDlgItemText(dlg, IDC_HOSTOTHER, pvar->ts->UIMsg);
1265     GetDlgItemText(dlg, IDC_HOSTTCPPORTLABEL, uimsg, sizeof(uimsg));
1266     UTIL_get_lang_msg("DLG_HOST_TCPIPPORT", pvar, uimsg);
1267     SetDlgItemText(dlg, IDC_HOSTTCPPORTLABEL, pvar->ts->UIMsg);
1268     GetDlgItemText(dlg, IDC_SSH_VERSION_LABEL, uimsg, sizeof(uimsg));
1269     UTIL_get_lang_msg("DLG_HOST_TCPIPSSHVERSION", pvar, uimsg);
1270     SetDlgItemText(dlg, IDC_SSH_VERSION_LABEL, pvar->ts->UIMsg);
1271     GetDlgItemText(dlg, IDC_HOSTTCPPROTOCOLLABEL, uimsg, sizeof(uimsg));
1272     UTIL_get_lang_msg("DLG_HOST_TCPIPPROTOCOL", pvar, uimsg);
1273     SetDlgItemText(dlg, IDC_HOSTTCPPROTOCOLLABEL, pvar->ts->UIMsg);
1274     GetDlgItemText(dlg, IDC_HOSTSERIAL, uimsg, sizeof(uimsg));
1275     UTIL_get_lang_msg("DLG_HOST_SERIAL", pvar, uimsg);
1276     SetDlgItemText(dlg, IDC_HOSTSERIAL, pvar->ts->UIMsg);
1277     GetDlgItemText(dlg, IDC_HOSTCOMLABEL, uimsg, sizeof(uimsg));
1278     UTIL_get_lang_msg("DLG_HOST_SERIALPORT", pvar, uimsg);
1279     SetDlgItemText(dlg, IDC_HOSTCOMLABEL, pvar->ts->UIMsg);
1280     GetDlgItemText(dlg, IDC_HOSTHELP, uimsg, sizeof(uimsg));
1281     UTIL_get_lang_msg("DLG_HOST_HELP", pvar, uimsg);
1282     SetDlgItemText(dlg, IDC_HOSTHELP, pvar->ts->UIMsg);
1283     GetDlgItemText(dlg, IDOK, uimsg, sizeof(uimsg));
1284     UTIL_get_lang_msg("BTN_OK", pvar, uimsg);
1285     SetDlgItemText(dlg, IDOK, pvar->ts->UIMsg);
1286     GetDlgItemText(dlg, IDCANCEL, uimsg, sizeof(uimsg));
1287     UTIL_get_lang_msg("BTN_CANCEL", pvar, uimsg);
1288     SetDlgItemText(dlg, IDCANCEL, pvar->ts->UIMsg);
1289    
1290     // �z�X�g�q�X�g�����`�F�b�N�{�b�N�X������ (2005.10.21 yutaka)
1291     if (pvar->ts->HistoryList > 0) {
1292     SendMessage(GetDlgItem(dlg, IDC_HISTORY), BM_SETCHECK, BST_CHECKED, 0);
1293     } else {
1294     SendMessage(GetDlgItem(dlg, IDC_HISTORY), BM_SETCHECK, BST_UNCHECKED, 0);
1295     }
1296    
1297 yutakapon 4860 // �t�@�C�����������O�t���p�C�v�������ATCP/IP�����������B
1298     if (GetHNRec->PortType == IdFile ||
1299     GetHNRec->PortType == IdNamedPipe
1300     )
1301 maya 3227 GetHNRec->PortType = IdTCPIP;
1302    
1303     strncpy_s(EntName, sizeof(EntName), "Host", _TRUNCATE);
1304    
1305     i = 1;
1306     do {
1307     _snprintf_s(&EntName[4], sizeof(EntName)-4, _TRUNCATE, "%d", i);
1308     GetPrivateProfileString("Hosts", EntName, "",
1309     TempHost, sizeof(TempHost),
1310     GetHNRec->SetupFN);
1311     if (strlen(TempHost) > 0)
1312     SendDlgItemMessage(dlg, IDC_HOSTNAME, CB_ADDSTRING,
1313     0, (LPARAM) TempHost);
1314     i++;
1315 maya 4963 } while (i <= MAXHOSTLIST);
1316 maya 3227
1317     SendDlgItemMessage(dlg, IDC_HOSTNAME, EM_LIMITTEXT,
1318     HostNameMaxLength - 1, 0);
1319    
1320     SendDlgItemMessage(dlg, IDC_HOSTNAME, CB_SETCURSEL, 0, 0);
1321    
1322     // C-n/C-p ���������T�u�N���X�� (2007.9.4 maya)
1323     hwndHostname = GetDlgItem(dlg, IDC_HOSTNAME);
1324     hwndHostnameEdit = GetWindow(hwndHostname, GW_CHILD);
1325     OrigHostnameEditProc = (WNDPROC)GetWindowLong(hwndHostnameEdit, GWL_WNDPROC);
1326     SetWindowLong(hwndHostnameEdit, GWL_WNDPROC, (LONG)HostnameEditProc);
1327    
1328     CheckRadioButton(dlg, IDC_HOSTTELNET, IDC_HOSTOTHER,
1329     pvar->settings.Enabled ? IDC_HOSTSSH : GetHNRec->
1330     Telnet ? IDC_HOSTTELNET : IDC_HOSTOTHER);
1331     SendDlgItemMessage(dlg, IDC_HOSTTCPPORT, EM_LIMITTEXT, 5, 0);
1332     SetDlgItemInt(dlg, IDC_HOSTTCPPORT, GetHNRec->TCPPort, FALSE);
1333     for (i = 0; ProtocolFamilyList[i]; ++i) {
1334     SendDlgItemMessage(dlg, IDC_HOSTTCPPROTOCOL, CB_ADDSTRING,
1335     0, (LPARAM) ProtocolFamilyList[i]);
1336     }
1337     SendDlgItemMessage(dlg, IDC_HOSTTCPPROTOCOL, EM_LIMITTEXT,
1338     ProtocolFamilyMaxLength - 1, 0);
1339     SendDlgItemMessage(dlg, IDC_HOSTTCPPROTOCOL, CB_SETCURSEL, 0, 0);
1340    
1341     /////// SSH version
1342     for (i = 0; ssh_version[i]; ++i) {
1343     SendDlgItemMessage(dlg, IDC_SSH_VERSION, CB_ADDSTRING,
1344     0, (LPARAM) ssh_version[i]);
1345     }
1346     SendDlgItemMessage(dlg, IDC_SSH_VERSION, EM_LIMITTEXT,
1347     NUM_ELEM(ssh_version) - 1, 0);
1348    
1349     if (pvar->settings.ssh_protocol_version == 1) {
1350     SendDlgItemMessage(dlg, IDC_SSH_VERSION, CB_SETCURSEL, 0, 0); // SSH1
1351     } else {
1352     SendDlgItemMessage(dlg, IDC_SSH_VERSION, CB_SETCURSEL, 1, 0); // SSH2
1353     }
1354    
1355     if (IsDlgButtonChecked(dlg, IDC_HOSTSSH)) {
1356     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, TRUE); // enabled
1357     } else {
1358     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, FALSE); // disabled
1359     }
1360     /////// SSH version
1361    
1362    
1363     j = 0;
1364     w = 1;
1365     if ((comports=DetectComPorts(ComPortTable, GetHNRec->MaxComPort, ComPortDesc)) >= 0) {
1366     for (i=0; i<comports; i++) {
1367     // MaxComPort ���z�����|�[�g���\��������
1368     if (ComPortTable[i] > GetHNRec->MaxComPort) {
1369     continue;
1370     }
1371    
1372     // �g�p�����|�[�g���\��������
1373     if (CheckCOMFlag(ComPortTable[i]) == 1) {
1374     continue;
1375     }
1376    
1377     _snprintf_s(EntName, sizeof(EntName), _TRUNCATE, "COM%d", ComPortTable[i]);
1378     if (ComPortDesc[i] != NULL) {
1379     strncat_s(EntName, sizeof(EntName), ": ", _TRUNCATE);
1380     strncat_s(EntName, sizeof(EntName), ComPortDesc[i], _TRUNCATE);
1381     }
1382     SendDlgItemMessage(dlg, IDC_HOSTCOM, CB_ADDSTRING,
1383     0, (LPARAM)EntName);
1384     j++;
1385     if (GetHNRec->ComPort == ComPortTable[i])
1386     w = j;
1387     }
1388    
1389     } else {
1390     for (i = 1; i <= GetHNRec->MaxComPort; i++) {
1391     // �g�p�����|�[�g���\��������
1392     if (CheckCOMFlag(i) == 1) {
1393     continue;
1394     }
1395    
1396     _snprintf_s(EntName, sizeof(EntName), _TRUNCATE, "COM%d", i);
1397     SendDlgItemMessage(dlg, IDC_HOSTCOM, CB_ADDSTRING,
1398     0, (LPARAM) EntName);
1399     j++;
1400     if (GetHNRec->ComPort == i)
1401     w = j;
1402     }
1403     }
1404    
1405     if (j > 0)
1406     SendDlgItemMessage(dlg, IDC_HOSTCOM, CB_SETCURSEL, w - 1, 0);
1407     else { /* All com ports are already used */
1408     GetHNRec->PortType = IdTCPIP;
1409     enable_dlg_items(dlg, IDC_HOSTSERIAL, IDC_HOSTSERIAL, FALSE);
1410     }
1411    
1412     CheckRadioButton(dlg, IDC_HOSTTCPIP, IDC_HOSTSERIAL,
1413     IDC_HOSTTCPIP + GetHNRec->PortType - 1);
1414    
1415     if (GetHNRec->PortType == IdTCPIP) {
1416     enable_dlg_items(dlg, IDC_HOSTCOMLABEL, IDC_HOSTCOM, FALSE);
1417    
1418     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, TRUE);
1419     enable_dlg_items(dlg, IDC_SSH_VERSION_LABEL, IDC_SSH_VERSION_LABEL, TRUE);
1420    
1421     enable_dlg_items(dlg, IDC_HISTORY, IDC_HISTORY, TRUE); // enabled
1422     }
1423     else {
1424     enable_dlg_items(dlg, IDC_HOSTNAMELABEL, IDC_HOSTTCPPORT,
1425     FALSE);
1426     enable_dlg_items(dlg, IDC_HOSTTCPPROTOCOLLABEL,
1427     IDC_HOSTTCPPROTOCOL, FALSE);
1428    
1429     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, FALSE); // disabled
1430     enable_dlg_items(dlg, IDC_SSH_VERSION_LABEL, IDC_SSH_VERSION_LABEL, FALSE); // disabled (2004.11.23 yutaka)
1431    
1432     enable_dlg_items(dlg, IDC_HISTORY, IDC_HISTORY, FALSE); // disabled
1433     }
1434    
1435     // Host dialog���t�H�[�J�X�������� (2004.10.2 yutaka)
1436     if (GetHNRec->PortType == IdTCPIP) {
1437     HWND hwnd = GetDlgItem(dlg, IDC_HOSTNAME);
1438     SetFocus(hwnd);
1439     } else {
1440     HWND hwnd = GetDlgItem(dlg, IDC_HOSTCOM);
1441     SetFocus(hwnd);
1442     }
1443    
1444     font = (HFONT)SendMessage(dlg, WM_GETFONT, 0, 0);
1445     GetObject(font, sizeof(LOGFONT), &logfont);
1446     if (UTIL_get_lang_font("DLG_SYSTEM_FONT", dlg, &logfont, &DlgHostFont, pvar)) {
1447     SendDlgItemMessage(dlg, IDC_HOSTTCPIP, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1448     SendDlgItemMessage(dlg, IDC_HOSTNAMELABEL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1449     SendDlgItemMessage(dlg, IDC_HOSTNAME, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1450     SendDlgItemMessage(dlg, IDC_HISTORY, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1451     SendDlgItemMessage(dlg, IDC_SERVICELABEL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1452     SendDlgItemMessage(dlg, IDC_HOSTTELNET, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1453     SendDlgItemMessage(dlg, IDC_HOSTSSH, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1454     SendDlgItemMessage(dlg, IDC_HOSTOTHER, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1455     SendDlgItemMessage(dlg, IDC_HOSTTCPPORTLABEL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1456     SendDlgItemMessage(dlg, IDC_HOSTTCPPORT, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1457     SendDlgItemMessage(dlg, IDC_SSH_VERSION_LABEL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1458     SendDlgItemMessage(dlg, IDC_SSH_VERSION, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1459     SendDlgItemMessage(dlg, IDC_HOSTTCPPROTOCOLLABEL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1460     SendDlgItemMessage(dlg, IDC_HOSTTCPPROTOCOL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1461     SendDlgItemMessage(dlg, IDC_HOSTSERIAL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1462     SendDlgItemMessage(dlg, IDC_HOSTCOMLABEL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1463     SendDlgItemMessage(dlg, IDC_HOSTCOM, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1464     SendDlgItemMessage(dlg, IDOK, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1465     SendDlgItemMessage(dlg, IDCANCEL, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1466     SendDlgItemMessage(dlg, IDC_HOSTHELP, WM_SETFONT, (WPARAM)DlgHostFont, MAKELPARAM(TRUE,0));
1467     }
1468     else {
1469     DlgHostFont = NULL;
1470     }
1471    
1472     // SetFocus()���t�H�[�J�X���������������AFALSE�������K�v�������B
1473     // TRUE���������ATABSTOP�������������������R���g���[�����I�������B
1474     // (2004.11.23 yutaka)
1475     return FALSE;
1476     //return TRUE;
1477    
1478     case WM_COMMAND:
1479     switch (LOWORD(wParam)) {
1480     case IDOK:
1481     GetHNRec = (PGetHNRec) GetWindowLong(dlg, DWL_USER);
1482     if (GetHNRec != NULL) {
1483     if (IsDlgButtonChecked(dlg, IDC_HOSTTCPIP)) {
1484     char afstr[BUFSIZ];
1485     i = GetDlgItemInt(dlg, IDC_HOSTTCPPORT, &Ok, FALSE);
1486     if (Ok) {
1487     GetHNRec->TCPPort = i;
1488     } else {
1489     UTIL_get_lang_msg("MSG_TCPPORT_NAN_ERROR", pvar,
1490     "The TCP port must be a number.");
1491     MessageBox(dlg, pvar->ts->UIMsg,
1492     "Tera Term", MB_OK | MB_ICONEXCLAMATION);
1493     return TRUE;
1494     }
1495     #define getaf(str) \
1496     ((strcmp((str), "IPv6") == 0) ? AF_INET6 : \
1497     ((strcmp((str), "IPv4") == 0) ? AF_INET : AF_UNSPEC))
1498     memset(afstr, 0, sizeof(afstr));
1499     GetDlgItemText(dlg, IDC_HOSTTCPPROTOCOL, afstr,
1500     sizeof(afstr));
1501     GetHNRec->ProtocolFamily = getaf(afstr);
1502     GetHNRec->PortType = IdTCPIP;
1503     GetDlgItemText(dlg, IDC_HOSTNAME, GetHNRec->HostName,
1504     HostNameMaxLength);
1505     pvar->hostdlg_activated = TRUE;
1506     pvar->hostdlg_Enabled = FALSE;
1507     if (IsDlgButtonChecked(dlg, IDC_HOSTTELNET)) {
1508     GetHNRec->Telnet = TRUE;
1509     } else if (IsDlgButtonChecked(dlg, IDC_HOSTSSH)) {
1510     pvar->hostdlg_Enabled = TRUE;
1511    
1512     // check SSH protocol version
1513     memset(afstr, 0, sizeof(afstr));
1514     GetDlgItemText(dlg, IDC_SSH_VERSION, afstr, sizeof(afstr));
1515     if (_stricmp(afstr, "SSH1") == 0) {
1516     pvar->settings.ssh_protocol_version = 1;
1517     } else {
1518     pvar->settings.ssh_protocol_version = 2;
1519     }
1520     }
1521 doda 3541 else { // IDC_HOSTOTHER
1522     GetHNRec->Telnet = FALSE;
1523     }
1524 maya 3227
1525     // host history check button
1526     if (SendMessage(GetDlgItem(dlg, IDC_HISTORY), BM_GETCHECK, 0, 0) == BST_CHECKED) {
1527     pvar->ts->HistoryList = 1;
1528     } else {
1529     pvar->ts->HistoryList = 0;
1530     }
1531    
1532     } else {
1533     GetHNRec->PortType = IdSerial;
1534     GetHNRec->HostName[0] = 0;
1535     memset(EntName, 0, sizeof(EntName));
1536     GetDlgItemText(dlg, IDC_HOSTCOM, EntName,
1537     sizeof(EntName) - 1);
1538     if (strncmp(EntName, "COM", 3) == 0 && EntName[3] != '\0') {
1539     GetHNRec->ComPort = atoi(&EntName[3]);
1540     if (GetHNRec->ComPort > GetHNRec->MaxComPort)
1541     GetHNRec->ComPort = 1;
1542     } else {
1543     GetHNRec->ComPort = 1;
1544     }
1545     }
1546     }
1547     SetWindowLong(hwndHostnameEdit, GWL_WNDPROC, (LONG)OrigHostnameEditProc);
1548     EndDialog(dlg, 1);
1549    
1550     if (DlgHostFont != NULL) {
1551     DeleteObject(DlgHostFont);
1552     }
1553    
1554     return TRUE;
1555    
1556     case IDCANCEL:
1557     SetWindowLong(hwndHostnameEdit, GWL_WNDPROC, (LONG)OrigHostnameEditProc);
1558     EndDialog(dlg, 0);
1559    
1560     if (DlgHostFont != NULL) {
1561     DeleteObject(DlgHostFont);
1562     }
1563    
1564     return TRUE;
1565    
1566     case IDC_HOSTTCPIP:
1567     enable_dlg_items(dlg, IDC_HOSTNAMELABEL, IDC_HOSTTCPPORT,
1568     TRUE);
1569     enable_dlg_items(dlg, IDC_HOSTTCPPROTOCOLLABEL,
1570     IDC_HOSTTCPPROTOCOL, TRUE);
1571     enable_dlg_items(dlg, IDC_HOSTCOMLABEL, IDC_HOSTCOM, FALSE);
1572    
1573     enable_dlg_items(dlg, IDC_SSH_VERSION_LABEL, IDC_SSH_VERSION_LABEL, TRUE); // disabled (2004.11.23 yutaka)
1574     if (IsDlgButtonChecked(dlg, IDC_HOSTSSH)) {
1575     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, TRUE);
1576     } else {
1577     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, FALSE); // disabled
1578     }
1579    
1580     enable_dlg_items(dlg, IDC_HISTORY, IDC_HISTORY, TRUE); // disabled
1581    
1582     return TRUE;
1583    
1584     case IDC_HOSTSERIAL:
1585     enable_dlg_items(dlg, IDC_HOSTCOMLABEL, IDC_HOSTCOM, TRUE);
1586     enable_dlg_items(dlg, IDC_HOSTNAMELABEL, IDC_HOSTTCPPORT,
1587     FALSE);
1588     enable_dlg_items(dlg, IDC_HOSTTCPPROTOCOLLABEL,
1589     IDC_HOSTTCPPROTOCOL, FALSE);
1590     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, FALSE); // disabled
1591     enable_dlg_items(dlg, IDC_SSH_VERSION_LABEL, IDC_SSH_VERSION_LABEL, FALSE); // disabled (2004.11.23 yutaka)
1592    
1593     enable_dlg_items(dlg, IDC_HISTORY, IDC_HISTORY, FALSE); // disabled
1594    
1595     return TRUE;
1596    
1597     case IDC_HOSTSSH:
1598     enable_dlg_items(dlg, IDC_SSH_VERSION,
1599     IDC_SSH_VERSION, TRUE);
1600     goto hostssh_enabled;
1601    
1602     case IDC_HOSTTELNET:
1603     case IDC_HOSTOTHER:
1604     enable_dlg_items(dlg, IDC_SSH_VERSION, IDC_SSH_VERSION, FALSE); // disabled
1605     hostssh_enabled:
1606    
1607     GetHNRec = (PGetHNRec) GetWindowLong(dlg, DWL_USER);
1608    
1609     if (IsDlgButtonChecked(dlg, IDC_HOSTTELNET)) {
1610     if (GetHNRec != NULL)
1611     SetDlgItemInt(dlg, IDC_HOSTTCPPORT, GetHNRec->TelPort,
1612     FALSE);
1613     } else if (IsDlgButtonChecked(dlg, IDC_HOSTSSH)) {
1614     SetDlgItemInt(dlg, IDC_HOSTTCPPORT, 22, FALSE);
1615     }
1616     return TRUE;
1617    
1618     case IDC_HOSTCOM:
1619     if(HIWORD(wParam) == CBN_DROPDOWN) {
1620     HWND hostcom = GetDlgItem(dlg, IDC_HOSTCOM);
1621     int count = SendMessage(hostcom, CB_GETCOUNT, 0, 0);
1622     int i, len, max_len = 0;
1623     char *lbl;
1624     HDC TmpDC = GetDC(hostcom);
1625     SIZE s;
1626     for (i=0; i<count; i++) {
1627     len = SendMessage(hostcom, CB_GETLBTEXTLEN, i, 0);
1628     lbl = (char *)calloc(len+1, sizeof(char));
1629     SendMessage(hostcom, CB_GETLBTEXT, i, (LPARAM)lbl);
1630     GetTextExtentPoint32(TmpDC, lbl, len, &s);
1631     if (s.cx > max_len)
1632     max_len = s.cx;
1633     free(lbl);
1634     }
1635     SendMessage(hostcom, CB_SETDROPPEDWIDTH,
1636     max_len + GetSystemMetrics(SM_CXVSCROLL), 0);
1637     }
1638     break;
1639    
1640     case IDC_HOSTHELP:
1641     PostMessage(GetParent(dlg), WM_USER_DLGHELP2, 0, 0);
1642     }
1643     }
1644     return FALSE;
1645     }
1646    
1647     static BOOL FAR PASCAL TTXGetHostName(HWND parent, PGetHNRec rec)
1648     {
1649     return (BOOL) DialogBoxParam(hInst, MAKEINTRESOURCE(IDD_HOSTDLG),
1650     parent, TTXHostDlg, (LONG) rec);
1651     }
1652    
1653     static void PASCAL FAR TTXGetUIHooks(TTXUIHooks FAR * hooks)
1654     {
1655     *hooks->GetHostName = TTXGetHostName;
1656     }
1657    
1658     static void FAR PASCAL TTXReadINIFile(PCHAR fileName, PTTSet ts)
1659     {
1660     (pvar->ReadIniFile) (fileName, ts);
1661     read_ssh_options(pvar, fileName);
1662     pvar->settings = *pvar->ts_SSH;
1663     notify_verbose_message(pvar, "Reading INI file", LOG_LEVEL_VERBOSE);
1664     FWDUI_load_settings(pvar);
1665     }
1666    
1667     static void FAR PASCAL TTXWriteINIFile(PCHAR fileName, PTTSet ts)
1668     {
1669     (pvar->WriteIniFile) (fileName, ts);
1670     *pvar->ts_SSH = pvar->settings;
1671     clear_local_settings(pvar);
1672     notify_verbose_message(pvar, "Writing INI file", LOG_LEVEL_VERBOSE);
1673     write_ssh_options(pvar, fileName, pvar->ts_SSH, TRUE);
1674     }
1675    
1676     static void read_ssh_options_from_user_file(PTInstVar pvar,
1677     char FAR * user_file_name)
1678     {
1679     if (user_file_name[0] == '.') {
1680     read_ssh_options(pvar, user_file_name);
1681     } else {
1682     char buf[1024];
1683    
1684     get_teraterm_dir_relative_name(buf, sizeof(buf), user_file_name);
1685     read_ssh_options(pvar, buf);
1686     }
1687    
1688     pvar->settings = *pvar->ts_SSH;
1689     FWDUI_load_settings(pvar);
1690     }
1691    
1692     // Percent-encode������������src���f�R�[�h����dst���R�s�[�����B
1693     // dstlen��dst���T�C�Y�B�����������������������A�����������������������B
1694     static void percent_decode(char *dst, int dstlen, char *src) {
1695     if (src == NULL || dst == NULL || dstlen < 1) {
1696     return;
1697     }
1698    
1699     while (*src != 0 && dstlen > 1) {
1700     if (*src == '%' && isxdigit(*(src+1)) && isxdigit(*(src+2))) {
1701     src++; *dst = (isalpha(*src) ? (*src|0x20) - 'a' + 10 : *src - '0') << 4;
1702     src++; *dst |= (isalpha(*src) ? (*src|0x20) - 'a' + 10 : *src - '0');
1703     src++; dst++;
1704     }
1705     else {
1706     *dst++ = *src++;
1707     }
1708     dstlen--;
1709     }
1710     *dst = 0;
1711     return;
1712     }
1713    
1714 doda 5799 void add_forward_param(PTInstVar pvar, char *param)
1715     {
1716     if (pvar->settings.DefaultForwarding[0] == 0) {
1717     strncpy_s(pvar->settings.DefaultForwarding,
1718     sizeof(pvar->settings.DefaultForwarding),
1719     param, _TRUNCATE);
1720     } else {
1721     strncat_s(pvar->settings.DefaultForwarding,
1722     sizeof(pvar->settings.DefaultForwarding),
1723     ";", _TRUNCATE);
1724     strncat_s(pvar->settings.DefaultForwarding,
1725     sizeof(pvar->settings.DefaultForwarding),
1726     param, _TRUNCATE);
1727     }
1728     }
1729    
1730 maya 5869 static void FAR PASCAL TTXParseParam(PCHAR param, PTTSet ts, PCHAR DDETopic) {
1731     int param_len=strlen(param);
1732     int opt_len = param_len+1;
1733     char *option = (char *)calloc(opt_len, sizeof(char));
1734 maya 5882 char *option2 = (char *)calloc(opt_len, sizeof(char));
1735 maya 5869 int action;
1736 maya 5874 PCHAR start, cur, next;
1737 maya 5908 size_t i;
1738 maya 5869
1739     if (pvar->hostdlg_activated) {
1740     pvar->settings.Enabled = pvar->hostdlg_Enabled;
1741     }
1742    
1743 maya 5874 /* the first term shuld be executable filename of Tera Term */
1744     start = GetParam(option, opt_len, param);
1745    
1746     cur = start;
1747 maya 5869 while (next = GetParam(option, opt_len, cur)) {
1748 doda 6140 DequoteParam(option, opt_len, option);
1749 maya 5869 action = OPTION_NONE;
1750    
1751     if ((option[0] == '-' || option[0] == '/')) {
1752     if (MATCH_STR(option + 1, "ssh") == 0) {
1753     if (MATCH_STR(option + 4, "-f=") == 0) {
1754 doda 6140 strncpy_s(option2, opt_len, option + 7, _TRUNCATE);
1755 maya 5882 read_ssh_options_from_user_file(pvar, option2);
1756 maya 5869 action = OPTION_CLEAR;
1757     } else if (MATCH_STR(option + 4, "-consume=") == 0) {
1758 doda 6140 strncpy_s(option2, opt_len, option + 13, _TRUNCATE);
1759 maya 5882 read_ssh_options_from_user_file(pvar, option2);
1760     DeleteFile(option2);
1761 maya 5869 action = OPTION_CLEAR;
1762     }
1763    
1764     // ttermpro.exe �� /F= �w������ TTSSH ������������ (2006.10.11 maya)
1765     } else if (MATCH_STR_I(option + 1, "f=") == 0) {
1766 doda 6140 strncpy_s(option2, opt_len, option + 3, _TRUNCATE);
1767 maya 5882 read_ssh_options_from_user_file(pvar, option2);
1768 maya 5869 // Tera Term���������������K�v������������������
1769     }
1770     }
1771    
1772     switch (action) {
1773     case OPTION_CLEAR:
1774     memset(cur, ' ', next-cur);
1775     break;
1776     case OPTION_REPLACE:
1777     memset(cur, ' ', next-cur);
1778     memcpy(cur+1, option, strlen(option));
1779     break;
1780     }
1781    
1782     cur = next;
1783     }
1784    
1785 maya 5874 cur = start;
1786 maya 5869 while (next = GetParam(option, opt_len, cur)) {
1787 doda 6140 DequoteParam(option, opt_len, option);
1788 maya 5869 action = OPTION_NONE;
1789    
1790     if ((option[0] == '-' || option[0] == '/')) {
1791     action = OPTION_CLEAR;
1792     if (MATCH_STR(option + 1, "ssh") == 0) {
1793     if (option[4] == 0) {
1794     pvar->settings.Enabled = 1;
1795     } else if (MATCH_STR(option + 4, "-L") == 0 ||
1796 doda 5959 MATCH_STR(option + 4, "-R") == 0) {
1797     char *p = option + 5;
1798     option2[0] = *p;
1799     i = 1;
1800     while (*++p) {
1801     if (*p == ';' || *p == ',') {
1802     option2[i] = 0;
1803     add_forward_param(pvar, option2);
1804     i = 1;
1805 maya 5908 }
1806 doda 5959 else {
1807     option2[i++] = *p;
1808     }
1809 maya 5908 }
1810 doda 5959 if (i > 1) {
1811     option2[i] = 0;
1812     add_forward_param(pvar, option2);
1813     }
1814 maya 5869 } else if (MATCH_STR(option + 4, "-X") == 0) {
1815     add_forward_param(pvar, "X");
1816 doda 5959 if (option+6 != 0) {
1817     strncpy_s(pvar->settings.X11Display,
1818     sizeof(pvar->settings.X11Display),
1819     option + 6, _TRUNCATE);
1820     }
1821 doda 6473 } else if (strcmp(option + 4, "-v") == 0) {
1822 maya 5869 pvar->settings.LogLevel = LOG_LEVEL_VERBOSE;
1823     } else if (_stricmp(option + 4, "-autologin") == 0 ||
1824     _stricmp(option + 4, "-autologon") == 0) {
1825     pvar->settings.TryDefaultAuth = TRUE;
1826     } else if (MATCH_STR_I(option + 4, "-agentconfirm=") == 0) {
1827     if ((_stricmp(option+18, "off") == 0) ||
1828     (_stricmp(option+18, "no") == 0) ||
1829     (_stricmp(option+18, "false") == 0) ||
1830     (_stricmp(option+18, "0") == 0) ||
1831     (_stricmp(option+18, "n") == 0)) {
1832     pvar->settings.ForwardAgentConfirm = 0;
1833     }
1834     else {
1835     pvar->settings.ForwardAgentConfirm = 1;
1836     }
1837 doda 6473 } else if (strcmp(option + 4, "-a") == 0) {
1838 maya 5869 pvar->settings.ForwardAgent = FALSE;
1839 doda 6473 } else if (strcmp(option + 4, "-A") == 0) {
1840 maya 5869 pvar->settings.ForwardAgent = TRUE;
1841    
1842     } else if (MATCH_STR(option + 4, "-C=") == 0) {
1843     pvar->settings.CompressionLevel = atoi(option+7);
1844     if (pvar->settings.CompressionLevel < 0) {
1845     pvar->settings.CompressionLevel = 0;
1846     }
1847     else if (pvar->settings.CompressionLevel > 9) {
1848     pvar->settings.CompressionLevel = 9;
1849     }
1850 doda 6473 } else if (strcmp(option + 4, "-C") == 0) {
1851 maya 5869 pvar->settings.CompressionLevel = 6;
1852 doda 6473 } else if (strcmp(option + 4, "-c") == 0) {
1853 maya 5869 pvar->settings.CompressionLevel = 0;
1854     } else if (MATCH_STR_I(option + 4, "-icon=") == 0) {
1855     if ((_stricmp(option+10, "old") == 0) ||
1856     (_stricmp(option+10, "yellow") == 0) ||
1857     (_stricmp(option+10, "securett_yellow") == 0)) {
1858     pvar->settings.IconID = IDI_SECURETT_YELLOW;
1859     }
1860 maya 6386 else if ((_stricmp(option+10, "green") == 0) ||
1861     (_stricmp(option+10, "securett_green") == 0)) {
1862     pvar->settings.IconID = IDI_SECURETT_GREEN;
1863     }
1864 maya 5869 else {
1865     pvar->settings.IconID = IDI_SECURETT;
1866     }
1867 doda 6717 } else if (MATCH_STR(option + 4, "-subsystem=") == 0) {
1868     pvar->use_subsystem = TRUE;
1869     strncpy_s(pvar->subsystem_name,
1870     sizeof(pvar->subsystem_name),
1871     option + 15, _TRUNCATE);
1872 maya 5869
1873     // /ssh1 �� /ssh2 �I�v�V�������V�K���� (2006.9.16 maya)
1874 doda 6473 } else if (strcmp(option + 4, "1") == 0) {
1875 maya 5869 pvar->settings.Enabled = 1;
1876     pvar->settings.ssh_protocol_version = 1;
1877 doda 6473 } else if (strcmp(option + 4, "2") == 0) {
1878 maya 5869 pvar->settings.Enabled = 1;
1879     pvar->settings.ssh_protocol_version = 2;
1880    
1881     } else {
1882     char buf[1024];
1883    
1884     UTIL_get_lang_msg("MSG_UNKNOWN_OPTION_ERROR", pvar,
1885     "Unrecognized command-line option: %s");
1886     _snprintf_s(buf, sizeof(buf), _TRUNCATE, pvar->ts->UIMsg, option);
1887    
1888     MessageBox(NULL, buf, "TTSSH", MB_OK | MB_ICONEXCLAMATION);
1889     }
1890    
1891     // ttermpro.exe �� /T= �w�������p�������A������������ (2006.10.19 maya)
1892     } else if (MATCH_STR_I(option + 1, "t=") == 0) {
1893     if (strcmp(option + 3, "2") == 0) {
1894     pvar->settings.Enabled = 1;
1895     // /t=2��ttssh�������g������������
1896     } else {
1897     pvar->settings.Enabled = 0;
1898     action = OPTION_NONE; // Tera Term������������������������
1899     }
1900    
1901     // /1 ������ /2 �I�v�V�������V�K���� (2004.10.3 yutaka)
1902 doda 6473 } else if (strcmp(option + 1, "1") == 0) {
1903 maya 5869 // command line: /ssh /1 is SSH1 only
1904     pvar->settings.ssh_protocol_version = 1;
1905    
1906 doda 6473 } else if (strcmp(option + 1, "2") == 0) {
1907 maya 5869 // command line: /ssh /2 is SSH2 & SSH1
1908     pvar->settings.ssh_protocol_version = 2;
1909    
1910 doda 6473 } else if (strcmp(option + 1, "nossh") == 0) {
1911 maya 5869 // '/nossh' �I�v�V�����������B
1912     // TERATERM.INI ��SSH���L�������������������A������Cygterm���N��������������
1913     // �����������������B(2004.10.11 yutaka)
1914     pvar->settings.Enabled = 0;
1915    
1916 doda 6473 } else if (strcmp(option + 1, "telnet") == 0) {
1917 maya 5869 // '/telnet' ���w�������������������� '/nossh' ��������
1918     // SSH������������ (2006.9.16 maya)
1919     pvar->settings.Enabled = 0;
1920     // Tera Term �� Telnet �t���O���t����
1921     pvar->ts->Telnet = 1;
1922    
1923 doda 6473 } else if (MATCH_STR(option + 1, "auth=") == 0) {
1924 maya 5869 // SSH2�������O�C���I�v�V����������
1925     //
1926     // SYNOPSIS: /ssh /auth=passowrd /user=���[�U�� /passwd=�p�X���[�h
1927     // /ssh /auth=publickey /user=���[�U�� /passwd=�p�X���[�h /keyfile=�p�X
1928 doda 6472 // EXAMPLE: /ssh /auth=password /user=nike /passwd="a b""c" ; �p�X���[�h: �ua b"c�v
1929 maya 5869 // /ssh /auth=publickey /user=foo /passwd=bar /keyfile=d:\tmp\id_rsa
1930 doda 6472 // NOTICE: �p�X���[�h���p�X���������Z�~�R���������������������_�u���N�H�[�g " ������
1931     // �p�X���[�h���_�u���N�H�[�g�����������������A�������_�u���N�H�[�g "" ���u��������
1932 maya 5869 //
1933     pvar->ssh2_autologin = 1; // for SSH2 (2004.11.30 yutaka)
1934    
1935 doda 6473 if (_stricmp(option + 6, "password") == 0) { // �p�X���[�h
1936 maya 5869 //pvar->auth_state.cur_cred.method = SSH_AUTH_PASSWORD;
1937     pvar->ssh2_authmethod = SSH_AUTH_PASSWORD;
1938    
1939     // /auth=challenge ������ (2007.10.5 maya)
1940 doda 6473 } else if (_stricmp(option + 6, "challenge") == 0) { // keyboard-interactive�F��
1941 maya 5869 //pvar->auth_state.cur_cred.method = SSH_AUTH_TIS;
1942     pvar->ssh2_authmethod = SSH_AUTH_TIS;
1943    
1944 doda 6473 } else if (_stricmp(option + 6, "publickey") == 0) { // ���J���F��
1945 maya 5869 //pvar->auth_state.cur_cred.method = SSH_AUTH_RSA;
1946     pvar->ssh2_authmethod = SSH_AUTH_RSA;
1947    
1948 doda 6473 } else if (_stricmp(option + 6, "pageant") == 0) { // ���J���F�� by Pageant
1949 maya 5869 //pvar->auth_state.cur_cred.method = SSH_AUTH_RSA;
1950     pvar->ssh2_authmethod = SSH_AUTH_PAGEANT;
1951    
1952     } else {
1953     // TODO:
1954     }
1955    
1956     } else if (MATCH_STR(option + 1, "user=") == 0) {
1957 doda 6140 _snprintf_s(pvar->ssh2_username, sizeof(pvar->ssh2_username), _TRUNCATE, "%s", option+6);
1958 maya 5869
1959     } else if (MATCH_STR(option + 1, "passwd=") == 0) {
1960 doda 6140 _snprintf_s(pvar->ssh2_password, sizeof(pvar->ssh2_password), _TRUNCATE, "%s", option+8);
1961 maya 5869
1962     } else if (MATCH_STR(option + 1, "keyfile=") == 0) {
1963 doda 6140 _snprintf_s(pvar->ssh2_keyfile, sizeof(pvar->ssh2_keyfile), _TRUNCATE, "%s", option+9);
1964 maya 5869
1965 doda 6473 } else if (strcmp(option + 1, "ask4passwd") == 0) {
1966 maya 5869 // �p�X���[�h������ (2006.9.18 maya)
1967     pvar->ask4passwd = 1;
1968    
1969 doda 6473 } else if (strcmp(option + 1, "nosecuritywarning") == 0) {
1970 maya 5869 // known_hosts�`�F�b�N���������B���Y�I�v�V�������g�����A�Z�L�����e�B������������
1971     // �����A�B���I�v�V���������������B
1972     // (2009.10.4 yutaka)
1973     pvar->nocheck_known_hosts = TRUE;
1974    
1975     }
1976     else { // Other (not ttssh) option
1977     action = OPTION_NONE; // ttssh���I�v�V������������������������
1978     }
1979    
1980     // �p�X���[�h�������������������O�C��������������
1981     // /auth ���F�����\�b�h���w�������������p������ (2006.9.18 maya)
1982     if (pvar->ask4passwd == 1) {
1983     pvar->ssh2_autologin = 0;
1984     }
1985    
1986     }
1987     else if ((MATCH_STR_I(option, "ssh://") == 0) ||
1988     (MATCH_STR_I(option, "ssh1://") == 0) ||
1989     (MATCH_STR_I(option, "ssh2://") == 0) ||
1990     (MATCH_STR_I(option, "slogin://") == 0) ||
1991     (MATCH_STR_I(option, "slogin1://") == 0) ||
1992     (MATCH_STR_I(option, "slogin2://") == 0)) {
1993     //
1994     // ssh://user@host/ ����URL�`�����T�|�[�g
1995     // ���{�I�������� telnet:// URL��������
1996     //
1997     // �Q�l:
1998     // RFC3986: Uniform Resource Identifier (URI): Generic Syntax
1999     // RFC4248: The telnet URI Scheme
2000     //
2001     char *p, *p2, *p3;
2002     int optlen, hostlen;
2003    
2004     optlen = strlen(option);
2005    
2006     // ������':'���O�����������������������A������ssh�v���g�R���o�[�W������������
2007     p = _mbschr(option, ':');
2008     switch (*(p-1)) {
2009     case '1':
2010     pvar->settings.ssh_protocol_version = 1;
2011     break;
2012     case '2':
2013     pvar->settings.ssh_protocol_version = 2;
2014     break;
2015     }
2016    
2017     // authority part �����|�C���^������
2018     p += 3;
2019    
2020     // path part ������������
2021     if ((p2 = _mbschr(p, '/')) != NULL) {
2022     *p2 = 0;
2023     }
2024    
2025     // '@'�������������A���������O�����[�U����
2026     if ((p2 = _mbschr(p, '@')) != NULL) {
2027     *p2 = 0;
2028     // ':'���~���p�X���[�h
2029     if ((p3 = _mbschr(p, ':')) != NULL) {
2030     *p3 = 0;
2031     percent_decode(pvar->ssh2_password, sizeof(pvar->ssh2_password), p3 + 1);
2032     }
2033     percent_decode(pvar->ssh2_username, sizeof(pvar->ssh2_username), p);
2034     // p �� host part ������('@'����������)����������������
2035     p = p2 + 1;
2036     }
2037    
2038     // host part �� option �����������������Ascheme part ������
2039     // port�w����������������port���������������������m��������������
2040     hostlen = strlen(p);
2041     memmove_s(option, optlen, p, hostlen);
2042     option[hostlen] = 0;
2043    
2044     // �|�[�g�w������������":22"������
2045     if (option[0] == '[' && option[hostlen-1] == ']' || // IPv6 raw address without port
2046     option[0] != '[' && _mbschr(option, ':') == NULL) { // hostname or IPv4 raw address without port
2047     memcpy_s(option+hostlen, optlen-hostlen, ":22", 3);
2048     hostlen += 3;
2049     }
2050    
2051     // �|�[�g�w�����������������X�y�[�X������
2052     memset(option+hostlen, ' ', optlen-hostlen);
2053    
2054     pvar->settings.Enabled = 1;
2055    
2056     action = OPTION_REPLACE;
2057     }
2058     else if (_mbschr(option, '@') != NULL) {
2059     //
2060     // user@host �`�����T�|�[�g
2061     // ����������ssh�������T�|�[�g�����A���[�U����ttssh���������B
2062     // (ssh�������O -- ttssh�������W������������)
2063     // �����I��telnet authentication option���T�|�[�g��������
2064     // Tera Term�{�����������������������\���B
2065     //
2066     char *p;
2067     p = _mbschr(option, '@');
2068     *p = 0;
2069    
2070     strncpy_s(pvar->ssh2_username, sizeof(pvar->ssh2_username), option, _TRUNCATE);
2071    
2072     // ���[�U���������X�y�[�X�������B
2073     // ������TTX��Tera Term�{�������������������X�y�[�X�����������������A
2074     // �z�X�g�����������l�����K�v�������B
2075     memset(option, ' ', p-option+1);
2076    
2077     action = OPTION_REPLACE;
2078     }
2079    
2080    
2081     switch (action) {
2082     case OPTION_CLEAR:
2083     memset(cur, ' ', next-cur);
2084     break;
2085     case OPTION_REPLACE:
2086     memset(cur, ' ', next-cur);
2087     memcpy(cur+1, option, strlen(option));
2088     break;
2089     }
2090    
2091     cur = next;
2092     }
2093    
2094     free(option);
2095    
2096     FWDUI_load_settings(pvar);
2097    
2098     (pvar->ParseParam) (param, ts, DDETopic);
2099     }
2100 maya 3227
2101     static void PASCAL FAR TTXGetSetupHooks(TTXSetupHooks FAR * hooks)
2102     {
2103     pvar->ReadIniFile = *hooks->ReadIniFile;
2104     pvar->WriteIniFile = *hooks->WriteIniFile;
2105     pvar->ParseParam = *hooks->ParseParam;
2106    
2107     *hooks->ReadIniFile = TTXReadINIFile;
2108     *hooks->WriteIniFile = TTXWriteINIFile;
2109     *hooks->ParseParam = TTXParseParam;
2110     }
2111    
2112     static void PASCAL FAR TTXSetWinSize(int rows, int cols)
2113     {
2114     SSH_notify_win_size(pvar, cols, rows);
2115     }
2116    
2117     static void insertMenuBeforeItem(HMENU menu, WORD beforeItemID, WORD flags,
2118     WORD newItemID, char FAR * text)
2119     {
2120     int i, j;
2121    
2122     for (i = GetMenuItemCount(menu) - 1; i >= 0; i--) {
2123     HMENU submenu = GetSubMenu(menu, i);
2124    
2125     for (j = GetMenuItemCount(submenu) - 1; j >= 0; j--) {
2126     if (GetMenuItemID(submenu, j) == beforeItemID) {
2127     InsertMenu(submenu, j, MF_BYPOSITION | flags, newItemID, text);
2128     return;
2129     }
2130     }
2131     }
2132     }
2133    
2134 doda 4463 #define GetFileMenu(menu) GetSubMenuByChildID(menu, 50110) // ID_FILE_NEWCONNECTION
2135     #define GetEditMenu(menu) GetSubMenuByChildID(menu, 50210) // ID_EDIT_COPY2
2136     #define GetSetupMenu(menu) GetSubMenuByChildID(menu, 50310) // ID_SETUP_TERMINAL
2137     #define GetControlMenu(menu) GetSubMenuByChildID(menu, 50410) // ID_CONTROL_RESETTERMINAL
2138     #define GetHelpMenu(menu) GetSubMenuByChildID(menu, 50990) // ID_HELP_ABOUT
2139    
2140     HMENU GetSubMenuByChildID(HMENU menu, UINT id) {
2141     int i, j, items, subitems, cur_id;
2142     HMENU m;
2143    
2144     items = GetMenuItemCount(menu);
2145    
2146     for (i=0; i<items; i++) {
2147     if (m = GetSubMenu(menu, i)) {
2148     subitems = GetMenuItemCount(m);
2149     for (j=0; j<subitems; j++) {
2150     cur_id = GetMenuItemID(m, j);
2151     if (cur_id == id) {
2152     return m;
2153     }
2154     }
2155     }
2156     }
2157     return NULL;
2158     }
2159    
2160 maya 3227 static void PASCAL FAR TTXModifyMenu(HMENU menu)
2161     {
2162 doda 4463 pvar->FileMenu = GetFileMenu(menu);
2163    
2164 maya 3227 /* inserts before ID_HELP_ABOUT */
2165     UTIL_get_lang_msg("MENU_ABOUT", pvar, "About &TTSSH...");
2166     insertMenuBeforeItem(menu, 50990, MF_ENABLED, ID_ABOUTMENU, pvar->ts->UIMsg);
2167    
2168     /* inserts before ID_SETUP_TCPIP */
2169     UTIL_get_lang_msg("MENU_SSH", pvar, "SS&H...");
2170     insertMenuBeforeItem(menu, 50360, MF_ENABLED, ID_SSHSETUPMENU, pvar->ts->UIMsg);
2171     /* inserts before ID_SETUP_TCPIP */
2172     UTIL_get_lang_msg("MENU_SSH_AUTH", pvar, "SSH &Authentication...");
2173     insertMenuBeforeItem(menu, 50360, MF_ENABLED, ID_SSHAUTHSETUPMENU, pvar->ts->UIMsg);
2174     /* inserts before ID_SETUP_TCPIP */
2175     UTIL_get_lang_msg("MENU_SSH_FORWARD", pvar, "SSH F&orwarding...");
2176     insertMenuBeforeItem(menu, 50360, MF_ENABLED, ID_SSHFWDSETUPMENU, pvar->ts->UIMsg);
2177     UTIL_get_lang_msg("MENU_SSH_KEYGEN", pvar, "SSH KeyGe&nerator...");
2178     insertMenuBeforeItem(menu, 50360, MF_ENABLED, ID_SSHKEYGENMENU, pvar->ts->UIMsg);
2179    
2180     /* inserts before ID_FILE_CHANGEDIR */
2181     UTIL_get_lang_msg("MENU_SSH_SCP", pvar, "SS&H SCP...");
2182 doda 4463 insertMenuBeforeItem(menu, 50170, MF_GRAYED, ID_SSHSCPMENU, pvar->ts->UIMsg);
2183 maya 3227 }
2184    
2185 doda 4463 static void PASCAL FAR TTXModifyPopupMenu(HMENU menu) {
2186     if (menu == pvar->FileMenu) {
2187     if (pvar->cv->Ready && pvar->settings.Enabled)
2188     EnableMenuItem(menu, ID_SSHSCPMENU, MF_BYCOMMAND | MF_ENABLED);
2189     else
2190     EnableMenuItem(menu, ID_SSHSCPMENU, MF_BYCOMMAND | MF_GRAYED);
2191     }
2192     }
2193    
2194 maya 3227 // ���s�t�@�C�������o�[�W�������������� (2005.2.28 yutaka)
2195     void get_file_version(char *exefile, int *major, int *minor, int *release, int *build)
2196     {
2197     typedef struct {
2198     WORD wLanguage;
2199     WORD wCodePage;
2200     } LANGANDCODEPAGE, *LPLANGANDCODEPAGE;
2201     LPLANGANDCODEPAGE lplgcode;
2202     UINT unLen;
2203     DWORD size;
2204     char *buf = NULL;
2205     BOOL ret;
2206     int i;
2207     char fmt[80];
2208     char *pbuf;
2209    
2210     size = GetFileVersionInfoSize(exefile, NULL);
2211     if (size == 0) {
2212     goto error;
2213     }
2214     buf = malloc(size);
2215     ZeroMemory(buf, size);
2216    
2217     if (GetFileVersionInfo(exefile, 0, size, buf) == FALSE) {
2218     goto error;
2219     }
2220    
2221     ret = VerQueryValue(buf,
2222     "\\VarFileInfo\\Translation",
2223     (LPVOID *)&lplgcode, &unLen);
2224     if (ret == FALSE)
2225     goto error;
2226    
2227     for (i = 0 ; i < (int)(unLen / sizeof(LANGANDCODEPAGE)) ; i++) {
2228     _snprintf_s(fmt, sizeof(fmt), _TRUNCATE,
2229     "\\StringFileInfo\\%04x%04x\\FileVersion",
2230     lplgcode[i].wLanguage, lplgcode[i].wCodePage);
2231     VerQueryValue(buf, fmt, &pbuf, &unLen);
2232     if (unLen > 0) { // get success
2233     int n, a, b, c, d;
2234    
2235     n = sscanf(pbuf, "%d, %d, %d, %d", &a, &b, &c, &d);
2236     if (n == 4) { // convert success
2237     *major = a;
2238     *minor = b;
2239     *release = c;
2240     *build = d;
2241     break;
2242     }
2243     }
2244     }
2245    
2246     free(buf);
2247     return;
2248    
2249     error:
2250     free(buf);
2251     *major = *minor = *release = *build = 0;
2252     }
2253    
2254 maya 6132 static void about_dlg_set_abouttext(PTInstVar pvar, HWND dlg, digest_algorithm dgst_alg)
2255 maya 3227 {
2256 maya 6135 char buf[1024], buf2[2048];
2257 yutakapon 5575 char *fp = NULL;
2258 maya 3227
2259     // TTSSH�_�C�A���O���\������SSH������������ (2004.10.30 yutaka)
2260     if (pvar->socket != INVALID_SOCKET) {
2261 maya 6135 buf2[0] = '\0';
2262 maya 6132
2263 maya 3227 if (SSHv1(pvar)) {
2264 maya 6135 UTIL_get_lang_msg("DLG_ABOUT_SERVERID", pvar, "Server ID:");
2265     strncat_s(buf2, sizeof(buf2), pvar->ts->UIMsg, _TRUNCATE);
2266     strncat_s(buf2, sizeof(buf2), " ", _TR