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 5294 - (hide annotations) (download) (as text)
Tue May 28 11:23:53 2013 UTC (10 years, 10 months ago) by doda
Original Path: trunk/ttssh2/ttxssh/ttxssh.c
File MIME type: text/x-csrc
File size: 168037 byte(s)
設定の保存で SSHIcon 設定を書き込むようにした。

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