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 6302 - (hide annotations) (download) (as text)
Sat Feb 13 14:52:14 2016 UTC (8 years, 1 month ago) by yutakapon
Original Path: trunk/ttssh2/ttxssh/ttxssh.c
File MIME type: text/x-csrc
File size: 198780 byte(s)
下記に示すHMAC受信時エラーの問題調査のため、HMAC受信処理におけるエラーログを追加した。
TTSSH.LOGへのログ追加で、16進ダンプ出力ができる logprintf_hexdump() を新設した。

TTSSH Error: Detected Corrupted Data
http://logmett.com/support-forums/8/ttssh-error-detected-corrupted-data-2827

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