xref: /freebsd/crypto/openssh/readconf.c (revision 1404c3a4b87f21b33148e520ed889d1f8374ea37)
1 /*
2  * Author: Tatu Ylonen <ylo@cs.hut.fi>
3  * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
4  *                    All rights reserved
5  * Functions for reading the configuration files.
6  *
7  * As far as I am concerned, the code I have written for this software
8  * can be used freely for any purpose.  Any derived versions of this
9  * software must be clearly marked as such, and if the derived work is
10  * incompatible with the protocol description in the RFC file, it must be
11  * called by a name other than "ssh" or "Secure Shell".
12  */
13 
14 #include "includes.h"
15 RCSID("$OpenBSD: readconf.c,v 1.139 2005/03/10 22:01:05 deraadt Exp $");
16 RCSID("$FreeBSD$");
17 
18 #include "ssh.h"
19 #include "xmalloc.h"
20 #include "compat.h"
21 #include "cipher.h"
22 #include "pathnames.h"
23 #include "log.h"
24 #include "readconf.h"
25 #include "match.h"
26 #include "misc.h"
27 #include "kex.h"
28 #include "mac.h"
29 
30 /* Format of the configuration file:
31 
32    # Configuration data is parsed as follows:
33    #  1. command line options
34    #  2. user-specific file
35    #  3. system-wide file
36    # Any configuration value is only changed the first time it is set.
37    # Thus, host-specific definitions should be at the beginning of the
38    # configuration file, and defaults at the end.
39 
40    # Host-specific declarations.  These may override anything above.  A single
41    # host may match multiple declarations; these are processed in the order
42    # that they are given in.
43 
44    Host *.ngs.fi ngs.fi
45      User foo
46 
47    Host fake.com
48      HostName another.host.name.real.org
49      User blaah
50      Port 34289
51      ForwardX11 no
52      ForwardAgent no
53 
54    Host books.com
55      RemoteForward 9999 shadows.cs.hut.fi:9999
56      Cipher 3des
57 
58    Host fascist.blob.com
59      Port 23123
60      User tylonen
61      PasswordAuthentication no
62 
63    Host puukko.hut.fi
64      User t35124p
65      ProxyCommand ssh-proxy %h %p
66 
67    Host *.fr
68      PublicKeyAuthentication no
69 
70    Host *.su
71      Cipher none
72      PasswordAuthentication no
73 
74    # Defaults for various options
75    Host *
76      ForwardAgent no
77      ForwardX11 no
78      PasswordAuthentication yes
79      RSAAuthentication yes
80      RhostsRSAAuthentication yes
81      StrictHostKeyChecking yes
82      TcpKeepAlive no
83      IdentityFile ~/.ssh/identity
84      Port 22
85      EscapeChar ~
86 
87 */
88 
89 /* Keyword tokens. */
90 
91 typedef enum {
92 	oBadOption,
93 	oForwardAgent, oForwardX11, oForwardX11Trusted, oGatewayPorts,
94 	oPasswordAuthentication, oRSAAuthentication,
95 	oChallengeResponseAuthentication, oXAuthLocation,
96 	oIdentityFile, oHostName, oPort, oCipher, oRemoteForward, oLocalForward,
97 	oUser, oHost, oEscapeChar, oRhostsRSAAuthentication, oProxyCommand,
98 	oGlobalKnownHostsFile, oUserKnownHostsFile, oConnectionAttempts,
99 	oBatchMode, oCheckHostIP, oStrictHostKeyChecking, oCompression,
100 	oCompressionLevel, oTCPKeepAlive, oNumberOfPasswordPrompts,
101 	oUsePrivilegedPort, oLogLevel, oCiphers, oProtocol, oMacs,
102 	oGlobalKnownHostsFile2, oUserKnownHostsFile2, oPubkeyAuthentication,
103 	oKbdInteractiveAuthentication, oKbdInteractiveDevices, oHostKeyAlias,
104 	oDynamicForward, oPreferredAuthentications, oHostbasedAuthentication,
105 	oHostKeyAlgorithms, oBindAddress, oSmartcardDevice,
106 	oClearAllForwardings, oNoHostAuthenticationForLocalhost,
107 	oEnableSSHKeysign, oRekeyLimit, oVerifyHostKeyDNS, oConnectTimeout,
108 	oAddressFamily, oGssAuthentication, oGssDelegateCreds,
109 	oServerAliveInterval, oServerAliveCountMax, oIdentitiesOnly,
110 	oSendEnv, oControlPath, oControlMaster, oHashKnownHosts,
111 	oVersionAddendum,
112 	oDeprecated, oUnsupported
113 } OpCodes;
114 
115 /* Textual representations of the tokens. */
116 
117 static struct {
118 	const char *name;
119 	OpCodes opcode;
120 } keywords[] = {
121 	{ "forwardagent", oForwardAgent },
122 	{ "forwardx11", oForwardX11 },
123 	{ "forwardx11trusted", oForwardX11Trusted },
124 	{ "xauthlocation", oXAuthLocation },
125 	{ "gatewayports", oGatewayPorts },
126 	{ "useprivilegedport", oUsePrivilegedPort },
127 	{ "rhostsauthentication", oDeprecated },
128 	{ "passwordauthentication", oPasswordAuthentication },
129 	{ "kbdinteractiveauthentication", oKbdInteractiveAuthentication },
130 	{ "kbdinteractivedevices", oKbdInteractiveDevices },
131 	{ "rsaauthentication", oRSAAuthentication },
132 	{ "pubkeyauthentication", oPubkeyAuthentication },
133 	{ "dsaauthentication", oPubkeyAuthentication },		    /* alias */
134 	{ "rhostsrsaauthentication", oRhostsRSAAuthentication },
135 	{ "hostbasedauthentication", oHostbasedAuthentication },
136 	{ "challengeresponseauthentication", oChallengeResponseAuthentication },
137 	{ "skeyauthentication", oChallengeResponseAuthentication }, /* alias */
138 	{ "tisauthentication", oChallengeResponseAuthentication },  /* alias */
139 	{ "kerberosauthentication", oUnsupported },
140 	{ "kerberostgtpassing", oUnsupported },
141 	{ "afstokenpassing", oUnsupported },
142 #if defined(GSSAPI)
143 	{ "gssapiauthentication", oGssAuthentication },
144 	{ "gssapidelegatecredentials", oGssDelegateCreds },
145 #else
146 	{ "gssapiauthentication", oUnsupported },
147 	{ "gssapidelegatecredentials", oUnsupported },
148 #endif
149 	{ "fallbacktorsh", oDeprecated },
150 	{ "usersh", oDeprecated },
151 	{ "identityfile", oIdentityFile },
152 	{ "identityfile2", oIdentityFile },			/* alias */
153 	{ "identitiesonly", oIdentitiesOnly },
154 	{ "hostname", oHostName },
155 	{ "hostkeyalias", oHostKeyAlias },
156 	{ "proxycommand", oProxyCommand },
157 	{ "port", oPort },
158 	{ "cipher", oCipher },
159 	{ "ciphers", oCiphers },
160 	{ "macs", oMacs },
161 	{ "protocol", oProtocol },
162 	{ "remoteforward", oRemoteForward },
163 	{ "localforward", oLocalForward },
164 	{ "user", oUser },
165 	{ "host", oHost },
166 	{ "escapechar", oEscapeChar },
167 	{ "globalknownhostsfile", oGlobalKnownHostsFile },
168 	{ "userknownhostsfile", oUserKnownHostsFile },		/* obsolete */
169 	{ "globalknownhostsfile2", oGlobalKnownHostsFile2 },
170 	{ "userknownhostsfile2", oUserKnownHostsFile2 },	/* obsolete */
171 	{ "connectionattempts", oConnectionAttempts },
172 	{ "batchmode", oBatchMode },
173 	{ "checkhostip", oCheckHostIP },
174 	{ "stricthostkeychecking", oStrictHostKeyChecking },
175 	{ "compression", oCompression },
176 	{ "compressionlevel", oCompressionLevel },
177 	{ "tcpkeepalive", oTCPKeepAlive },
178 	{ "keepalive", oTCPKeepAlive },				/* obsolete */
179 	{ "numberofpasswordprompts", oNumberOfPasswordPrompts },
180 	{ "loglevel", oLogLevel },
181 	{ "dynamicforward", oDynamicForward },
182 	{ "preferredauthentications", oPreferredAuthentications },
183 	{ "hostkeyalgorithms", oHostKeyAlgorithms },
184 	{ "bindaddress", oBindAddress },
185 #ifdef SMARTCARD
186 	{ "smartcarddevice", oSmartcardDevice },
187 #else
188 	{ "smartcarddevice", oUnsupported },
189 #endif
190 	{ "clearallforwardings", oClearAllForwardings },
191 	{ "enablesshkeysign", oEnableSSHKeysign },
192 	{ "verifyhostkeydns", oVerifyHostKeyDNS },
193 	{ "nohostauthenticationforlocalhost", oNoHostAuthenticationForLocalhost },
194 	{ "rekeylimit", oRekeyLimit },
195 	{ "connecttimeout", oConnectTimeout },
196 	{ "addressfamily", oAddressFamily },
197 	{ "serveraliveinterval", oServerAliveInterval },
198 	{ "serveralivecountmax", oServerAliveCountMax },
199 	{ "sendenv", oSendEnv },
200 	{ "controlpath", oControlPath },
201 	{ "controlmaster", oControlMaster },
202 	{ "hashknownhosts", oHashKnownHosts },
203 	{ "versionaddendum", oVersionAddendum },
204 	{ NULL, oBadOption }
205 };
206 
207 /*
208  * Adds a local TCP/IP port forward to options.  Never returns if there is an
209  * error.
210  */
211 
212 void
213 add_local_forward(Options *options, const Forward *newfwd)
214 {
215 	Forward *fwd;
216 #ifndef NO_IPPORT_RESERVED_CONCEPT
217 	extern uid_t original_real_uid;
218 	if (newfwd->listen_port < IPPORT_RESERVED && original_real_uid != 0)
219 		fatal("Privileged ports can only be forwarded by root.");
220 #endif
221 	if (options->num_local_forwards >= SSH_MAX_FORWARDS_PER_DIRECTION)
222 		fatal("Too many local forwards (max %d).", SSH_MAX_FORWARDS_PER_DIRECTION);
223 	fwd = &options->local_forwards[options->num_local_forwards++];
224 
225 	fwd->listen_host = (newfwd->listen_host == NULL) ?
226 	    NULL : xstrdup(newfwd->listen_host);
227 	fwd->listen_port = newfwd->listen_port;
228 	fwd->connect_host = xstrdup(newfwd->connect_host);
229 	fwd->connect_port = newfwd->connect_port;
230 }
231 
232 /*
233  * Adds a remote TCP/IP port forward to options.  Never returns if there is
234  * an error.
235  */
236 
237 void
238 add_remote_forward(Options *options, const Forward *newfwd)
239 {
240 	Forward *fwd;
241 	if (options->num_remote_forwards >= SSH_MAX_FORWARDS_PER_DIRECTION)
242 		fatal("Too many remote forwards (max %d).",
243 		    SSH_MAX_FORWARDS_PER_DIRECTION);
244 	fwd = &options->remote_forwards[options->num_remote_forwards++];
245 
246 	fwd->listen_host = (newfwd->listen_host == NULL) ?
247 	    NULL : xstrdup(newfwd->listen_host);
248 	fwd->listen_port = newfwd->listen_port;
249 	fwd->connect_host = xstrdup(newfwd->connect_host);
250 	fwd->connect_port = newfwd->connect_port;
251 }
252 
253 static void
254 clear_forwardings(Options *options)
255 {
256 	int i;
257 
258 	for (i = 0; i < options->num_local_forwards; i++) {
259 		if (options->local_forwards[i].listen_host != NULL)
260 			xfree(options->local_forwards[i].listen_host);
261 		xfree(options->local_forwards[i].connect_host);
262 	}
263 	options->num_local_forwards = 0;
264 	for (i = 0; i < options->num_remote_forwards; i++) {
265 		if (options->remote_forwards[i].listen_host != NULL)
266 			xfree(options->remote_forwards[i].listen_host);
267 		xfree(options->remote_forwards[i].connect_host);
268 	}
269 	options->num_remote_forwards = 0;
270 }
271 
272 /*
273  * Returns the number of the token pointed to by cp or oBadOption.
274  */
275 
276 static OpCodes
277 parse_token(const char *cp, const char *filename, int linenum)
278 {
279 	u_int i;
280 
281 	for (i = 0; keywords[i].name; i++)
282 		if (strcasecmp(cp, keywords[i].name) == 0)
283 			return keywords[i].opcode;
284 
285 	error("%s: line %d: Bad configuration option: %s",
286 	    filename, linenum, cp);
287 	return oBadOption;
288 }
289 
290 /*
291  * Processes a single option line as used in the configuration files. This
292  * only sets those values that have not already been set.
293  */
294 #define WHITESPACE " \t\r\n"
295 
296 int
297 process_config_line(Options *options, const char *host,
298 		    char *line, const char *filename, int linenum,
299 		    int *activep)
300 {
301 	char *s, **charptr, *endofnumber, *keyword, *arg, *arg2, fwdarg[256];
302 	int opcode, *intptr, value;
303 	size_t len;
304 	Forward fwd;
305 
306 	/* Strip trailing whitespace */
307 	for (len = strlen(line) - 1; len > 0; len--) {
308 		if (strchr(WHITESPACE, line[len]) == NULL)
309 			break;
310 		line[len] = '\0';
311 	}
312 
313 	s = line;
314 	/* Get the keyword. (Each line is supposed to begin with a keyword). */
315 	keyword = strdelim(&s);
316 	/* Ignore leading whitespace. */
317 	if (*keyword == '\0')
318 		keyword = strdelim(&s);
319 	if (keyword == NULL || !*keyword || *keyword == '\n' || *keyword == '#')
320 		return 0;
321 
322 	opcode = parse_token(keyword, filename, linenum);
323 
324 	switch (opcode) {
325 	case oBadOption:
326 		/* don't panic, but count bad options */
327 		return -1;
328 		/* NOTREACHED */
329 	case oConnectTimeout:
330 		intptr = &options->connection_timeout;
331 parse_time:
332 		arg = strdelim(&s);
333 		if (!arg || *arg == '\0')
334 			fatal("%s line %d: missing time value.",
335 			    filename, linenum);
336 		if ((value = convtime(arg)) == -1)
337 			fatal("%s line %d: invalid time value.",
338 			    filename, linenum);
339 		if (*intptr == -1)
340 			*intptr = value;
341 		break;
342 
343 	case oForwardAgent:
344 		intptr = &options->forward_agent;
345 parse_flag:
346 		arg = strdelim(&s);
347 		if (!arg || *arg == '\0')
348 			fatal("%.200s line %d: Missing yes/no argument.", filename, linenum);
349 		value = 0;	/* To avoid compiler warning... */
350 		if (strcmp(arg, "yes") == 0 || strcmp(arg, "true") == 0)
351 			value = 1;
352 		else if (strcmp(arg, "no") == 0 || strcmp(arg, "false") == 0)
353 			value = 0;
354 		else
355 			fatal("%.200s line %d: Bad yes/no argument.", filename, linenum);
356 		if (*activep && *intptr == -1)
357 			*intptr = value;
358 		break;
359 
360 	case oForwardX11:
361 		intptr = &options->forward_x11;
362 		goto parse_flag;
363 
364 	case oForwardX11Trusted:
365 		intptr = &options->forward_x11_trusted;
366 		goto parse_flag;
367 
368 	case oGatewayPorts:
369 		intptr = &options->gateway_ports;
370 		goto parse_flag;
371 
372 	case oUsePrivilegedPort:
373 		intptr = &options->use_privileged_port;
374 		goto parse_flag;
375 
376 	case oPasswordAuthentication:
377 		intptr = &options->password_authentication;
378 		goto parse_flag;
379 
380 	case oKbdInteractiveAuthentication:
381 		intptr = &options->kbd_interactive_authentication;
382 		goto parse_flag;
383 
384 	case oKbdInteractiveDevices:
385 		charptr = &options->kbd_interactive_devices;
386 		goto parse_string;
387 
388 	case oPubkeyAuthentication:
389 		intptr = &options->pubkey_authentication;
390 		goto parse_flag;
391 
392 	case oRSAAuthentication:
393 		intptr = &options->rsa_authentication;
394 		goto parse_flag;
395 
396 	case oRhostsRSAAuthentication:
397 		intptr = &options->rhosts_rsa_authentication;
398 		goto parse_flag;
399 
400 	case oHostbasedAuthentication:
401 		intptr = &options->hostbased_authentication;
402 		goto parse_flag;
403 
404 	case oChallengeResponseAuthentication:
405 		intptr = &options->challenge_response_authentication;
406 		goto parse_flag;
407 
408 	case oGssAuthentication:
409 		intptr = &options->gss_authentication;
410 		goto parse_flag;
411 
412 	case oGssDelegateCreds:
413 		intptr = &options->gss_deleg_creds;
414 		goto parse_flag;
415 
416 	case oBatchMode:
417 		intptr = &options->batch_mode;
418 		goto parse_flag;
419 
420 	case oCheckHostIP:
421 		intptr = &options->check_host_ip;
422 		goto parse_flag;
423 
424 	case oVerifyHostKeyDNS:
425 		intptr = &options->verify_host_key_dns;
426 		goto parse_yesnoask;
427 
428 	case oStrictHostKeyChecking:
429 		intptr = &options->strict_host_key_checking;
430 parse_yesnoask:
431 		arg = strdelim(&s);
432 		if (!arg || *arg == '\0')
433 			fatal("%.200s line %d: Missing yes/no/ask argument.",
434 			    filename, linenum);
435 		value = 0;	/* To avoid compiler warning... */
436 		if (strcmp(arg, "yes") == 0 || strcmp(arg, "true") == 0)
437 			value = 1;
438 		else if (strcmp(arg, "no") == 0 || strcmp(arg, "false") == 0)
439 			value = 0;
440 		else if (strcmp(arg, "ask") == 0)
441 			value = 2;
442 		else
443 			fatal("%.200s line %d: Bad yes/no/ask argument.", filename, linenum);
444 		if (*activep && *intptr == -1)
445 			*intptr = value;
446 		break;
447 
448 	case oCompression:
449 		intptr = &options->compression;
450 		goto parse_flag;
451 
452 	case oTCPKeepAlive:
453 		intptr = &options->tcp_keep_alive;
454 		goto parse_flag;
455 
456 	case oNoHostAuthenticationForLocalhost:
457 		intptr = &options->no_host_authentication_for_localhost;
458 		goto parse_flag;
459 
460 	case oNumberOfPasswordPrompts:
461 		intptr = &options->number_of_password_prompts;
462 		goto parse_int;
463 
464 	case oCompressionLevel:
465 		intptr = &options->compression_level;
466 		goto parse_int;
467 
468 	case oRekeyLimit:
469 		intptr = &options->rekey_limit;
470 		arg = strdelim(&s);
471 		if (!arg || *arg == '\0')
472 			fatal("%.200s line %d: Missing argument.", filename, linenum);
473 		if (arg[0] < '0' || arg[0] > '9')
474 			fatal("%.200s line %d: Bad number.", filename, linenum);
475 		value = strtol(arg, &endofnumber, 10);
476 		if (arg == endofnumber)
477 			fatal("%.200s line %d: Bad number.", filename, linenum);
478 		switch (toupper(*endofnumber)) {
479 		case 'K':
480 			value *= 1<<10;
481 			break;
482 		case 'M':
483 			value *= 1<<20;
484 			break;
485 		case 'G':
486 			value *= 1<<30;
487 			break;
488 		}
489 		if (*activep && *intptr == -1)
490 			*intptr = value;
491 		break;
492 
493 	case oIdentityFile:
494 		arg = strdelim(&s);
495 		if (!arg || *arg == '\0')
496 			fatal("%.200s line %d: Missing argument.", filename, linenum);
497 		if (*activep) {
498 			intptr = &options->num_identity_files;
499 			if (*intptr >= SSH_MAX_IDENTITY_FILES)
500 				fatal("%.200s line %d: Too many identity files specified (max %d).",
501 				    filename, linenum, SSH_MAX_IDENTITY_FILES);
502 			charptr =  &options->identity_files[*intptr];
503 			*charptr = xstrdup(arg);
504 			*intptr = *intptr + 1;
505 		}
506 		break;
507 
508 	case oXAuthLocation:
509 		charptr=&options->xauth_location;
510 		goto parse_string;
511 
512 	case oUser:
513 		charptr = &options->user;
514 parse_string:
515 		arg = strdelim(&s);
516 		if (!arg || *arg == '\0')
517 			fatal("%.200s line %d: Missing argument.", filename, linenum);
518 		if (*activep && *charptr == NULL)
519 			*charptr = xstrdup(arg);
520 		break;
521 
522 	case oGlobalKnownHostsFile:
523 		charptr = &options->system_hostfile;
524 		goto parse_string;
525 
526 	case oUserKnownHostsFile:
527 		charptr = &options->user_hostfile;
528 		goto parse_string;
529 
530 	case oGlobalKnownHostsFile2:
531 		charptr = &options->system_hostfile2;
532 		goto parse_string;
533 
534 	case oUserKnownHostsFile2:
535 		charptr = &options->user_hostfile2;
536 		goto parse_string;
537 
538 	case oHostName:
539 		charptr = &options->hostname;
540 		goto parse_string;
541 
542 	case oHostKeyAlias:
543 		charptr = &options->host_key_alias;
544 		goto parse_string;
545 
546 	case oPreferredAuthentications:
547 		charptr = &options->preferred_authentications;
548 		goto parse_string;
549 
550 	case oBindAddress:
551 		charptr = &options->bind_address;
552 		goto parse_string;
553 
554 	case oSmartcardDevice:
555 		charptr = &options->smartcard_device;
556 		goto parse_string;
557 
558 	case oProxyCommand:
559 		if (s == NULL)
560 			fatal("%.200s line %d: Missing argument.", filename, linenum);
561 		charptr = &options->proxy_command;
562 		len = strspn(s, WHITESPACE "=");
563 		if (*activep && *charptr == NULL)
564 			*charptr = xstrdup(s + len);
565 		return 0;
566 
567 	case oPort:
568 		intptr = &options->port;
569 parse_int:
570 		arg = strdelim(&s);
571 		if (!arg || *arg == '\0')
572 			fatal("%.200s line %d: Missing argument.", filename, linenum);
573 		if (arg[0] < '0' || arg[0] > '9')
574 			fatal("%.200s line %d: Bad number.", filename, linenum);
575 
576 		/* Octal, decimal, or hex format? */
577 		value = strtol(arg, &endofnumber, 0);
578 		if (arg == endofnumber)
579 			fatal("%.200s line %d: Bad number.", filename, linenum);
580 		if (*activep && *intptr == -1)
581 			*intptr = value;
582 		break;
583 
584 	case oConnectionAttempts:
585 		intptr = &options->connection_attempts;
586 		goto parse_int;
587 
588 	case oCipher:
589 		intptr = &options->cipher;
590 		arg = strdelim(&s);
591 		if (!arg || *arg == '\0')
592 			fatal("%.200s line %d: Missing argument.", filename, linenum);
593 		value = cipher_number(arg);
594 		if (value == -1)
595 			fatal("%.200s line %d: Bad cipher '%s'.",
596 			    filename, linenum, arg ? arg : "<NONE>");
597 		if (*activep && *intptr == -1)
598 			*intptr = value;
599 		break;
600 
601 	case oCiphers:
602 		arg = strdelim(&s);
603 		if (!arg || *arg == '\0')
604 			fatal("%.200s line %d: Missing argument.", filename, linenum);
605 		if (!ciphers_valid(arg))
606 			fatal("%.200s line %d: Bad SSH2 cipher spec '%s'.",
607 			    filename, linenum, arg ? arg : "<NONE>");
608 		if (*activep && options->ciphers == NULL)
609 			options->ciphers = xstrdup(arg);
610 		break;
611 
612 	case oMacs:
613 		arg = strdelim(&s);
614 		if (!arg || *arg == '\0')
615 			fatal("%.200s line %d: Missing argument.", filename, linenum);
616 		if (!mac_valid(arg))
617 			fatal("%.200s line %d: Bad SSH2 Mac spec '%s'.",
618 			    filename, linenum, arg ? arg : "<NONE>");
619 		if (*activep && options->macs == NULL)
620 			options->macs = xstrdup(arg);
621 		break;
622 
623 	case oHostKeyAlgorithms:
624 		arg = strdelim(&s);
625 		if (!arg || *arg == '\0')
626 			fatal("%.200s line %d: Missing argument.", filename, linenum);
627 		if (!key_names_valid2(arg))
628 			fatal("%.200s line %d: Bad protocol 2 host key algorithms '%s'.",
629 			    filename, linenum, arg ? arg : "<NONE>");
630 		if (*activep && options->hostkeyalgorithms == NULL)
631 			options->hostkeyalgorithms = xstrdup(arg);
632 		break;
633 
634 	case oProtocol:
635 		intptr = &options->protocol;
636 		arg = strdelim(&s);
637 		if (!arg || *arg == '\0')
638 			fatal("%.200s line %d: Missing argument.", filename, linenum);
639 		value = proto_spec(arg);
640 		if (value == SSH_PROTO_UNKNOWN)
641 			fatal("%.200s line %d: Bad protocol spec '%s'.",
642 			    filename, linenum, arg ? arg : "<NONE>");
643 		if (*activep && *intptr == SSH_PROTO_UNKNOWN)
644 			*intptr = value;
645 		break;
646 
647 	case oLogLevel:
648 		intptr = (int *) &options->log_level;
649 		arg = strdelim(&s);
650 		value = log_level_number(arg);
651 		if (value == SYSLOG_LEVEL_NOT_SET)
652 			fatal("%.200s line %d: unsupported log level '%s'",
653 			    filename, linenum, arg ? arg : "<NONE>");
654 		if (*activep && (LogLevel) *intptr == SYSLOG_LEVEL_NOT_SET)
655 			*intptr = (LogLevel) value;
656 		break;
657 
658 	case oLocalForward:
659 	case oRemoteForward:
660 		arg = strdelim(&s);
661 		if (arg == NULL || *arg == '\0')
662 			fatal("%.200s line %d: Missing port argument.",
663 			    filename, linenum);
664 		arg2 = strdelim(&s);
665 		if (arg2 == NULL || *arg2 == '\0')
666 			fatal("%.200s line %d: Missing target argument.",
667 			    filename, linenum);
668 
669 		/* construct a string for parse_forward */
670 		snprintf(fwdarg, sizeof(fwdarg), "%s:%s", arg, arg2);
671 
672 		if (parse_forward(&fwd, fwdarg) == 0)
673 			fatal("%.200s line %d: Bad forwarding specification.",
674 			    filename, linenum);
675 
676 		if (*activep) {
677 			if (opcode == oLocalForward)
678 				add_local_forward(options, &fwd);
679 			else if (opcode == oRemoteForward)
680 				add_remote_forward(options, &fwd);
681 		}
682 		break;
683 
684 	case oDynamicForward:
685 		arg = strdelim(&s);
686 		if (!arg || *arg == '\0')
687 			fatal("%.200s line %d: Missing port argument.",
688 			    filename, linenum);
689 		memset(&fwd, '\0', sizeof(fwd));
690 		fwd.connect_host = "socks";
691 		fwd.listen_host = hpdelim(&arg);
692 		if (fwd.listen_host == NULL ||
693 		    strlen(fwd.listen_host) >= NI_MAXHOST)
694 			fatal("%.200s line %d: Bad forwarding specification.",
695 			    filename, linenum);
696 		if (arg) {
697 			fwd.listen_port = a2port(arg);
698 			fwd.listen_host = cleanhostname(fwd.listen_host);
699 		} else {
700 			fwd.listen_port = a2port(fwd.listen_host);
701 			fwd.listen_host = "";
702 		}
703 		if (fwd.listen_port == 0)
704 			fatal("%.200s line %d: Badly formatted port number.",
705 			    filename, linenum);
706 		if (*activep)
707 			add_local_forward(options, &fwd);
708 		break;
709 
710 	case oClearAllForwardings:
711 		intptr = &options->clear_forwardings;
712 		goto parse_flag;
713 
714 	case oHost:
715 		*activep = 0;
716 		while ((arg = strdelim(&s)) != NULL && *arg != '\0')
717 			if (match_pattern(host, arg)) {
718 				debug("Applying options for %.100s", arg);
719 				*activep = 1;
720 				break;
721 			}
722 		/* Avoid garbage check below, as strdelim is done. */
723 		return 0;
724 
725 	case oEscapeChar:
726 		intptr = &options->escape_char;
727 		arg = strdelim(&s);
728 		if (!arg || *arg == '\0')
729 			fatal("%.200s line %d: Missing argument.", filename, linenum);
730 		if (arg[0] == '^' && arg[2] == 0 &&
731 		    (u_char) arg[1] >= 64 && (u_char) arg[1] < 128)
732 			value = (u_char) arg[1] & 31;
733 		else if (strlen(arg) == 1)
734 			value = (u_char) arg[0];
735 		else if (strcmp(arg, "none") == 0)
736 			value = SSH_ESCAPECHAR_NONE;
737 		else {
738 			fatal("%.200s line %d: Bad escape character.",
739 			    filename, linenum);
740 			/* NOTREACHED */
741 			value = 0;	/* Avoid compiler warning. */
742 		}
743 		if (*activep && *intptr == -1)
744 			*intptr = value;
745 		break;
746 
747 	case oAddressFamily:
748 		arg = strdelim(&s);
749 		intptr = &options->address_family;
750 		if (strcasecmp(arg, "inet") == 0)
751 			value = AF_INET;
752 		else if (strcasecmp(arg, "inet6") == 0)
753 			value = AF_INET6;
754 		else if (strcasecmp(arg, "any") == 0)
755 			value = AF_UNSPEC;
756 		else
757 			fatal("Unsupported AddressFamily \"%s\"", arg);
758 		if (*activep && *intptr == -1)
759 			*intptr = value;
760 		break;
761 
762 	case oEnableSSHKeysign:
763 		intptr = &options->enable_ssh_keysign;
764 		goto parse_flag;
765 
766 	case oIdentitiesOnly:
767 		intptr = &options->identities_only;
768 		goto parse_flag;
769 
770 	case oServerAliveInterval:
771 		intptr = &options->server_alive_interval;
772 		goto parse_time;
773 
774 	case oServerAliveCountMax:
775 		intptr = &options->server_alive_count_max;
776 		goto parse_int;
777 
778 	case oSendEnv:
779 		while ((arg = strdelim(&s)) != NULL && *arg != '\0') {
780 			if (strchr(arg, '=') != NULL)
781 				fatal("%s line %d: Invalid environment name.",
782 				    filename, linenum);
783 			if (!*activep)
784 				continue;
785 			if (options->num_send_env >= MAX_SEND_ENV)
786 				fatal("%s line %d: too many send env.",
787 				    filename, linenum);
788 			options->send_env[options->num_send_env++] =
789 			    xstrdup(arg);
790 		}
791 		break;
792 
793 	case oControlPath:
794 		charptr = &options->control_path;
795 		goto parse_string;
796 
797 	case oControlMaster:
798 		intptr = &options->control_master;
799 		goto parse_yesnoask;
800 
801 	case oHashKnownHosts:
802 		intptr = &options->hash_known_hosts;
803 		goto parse_flag;
804 
805 	case oVersionAddendum:
806 		ssh_version_set_addendum(strtok(s, "\n"));
807 		do {
808 			arg = strdelim(&s);
809 		} while (arg != NULL && *arg != '\0');
810 		break;
811 
812 	case oDeprecated:
813 		debug("%s line %d: Deprecated option \"%s\"",
814 		    filename, linenum, keyword);
815 		return 0;
816 
817 	case oUnsupported:
818 		error("%s line %d: Unsupported option \"%s\"",
819 		    filename, linenum, keyword);
820 		return 0;
821 
822 	default:
823 		fatal("process_config_line: Unimplemented opcode %d", opcode);
824 	}
825 
826 	/* Check that there is no garbage at end of line. */
827 	if ((arg = strdelim(&s)) != NULL && *arg != '\0') {
828 		fatal("%.200s line %d: garbage at end of line; \"%.200s\".",
829 		     filename, linenum, arg);
830 	}
831 	return 0;
832 }
833 
834 
835 /*
836  * Reads the config file and modifies the options accordingly.  Options
837  * should already be initialized before this call.  This never returns if
838  * there is an error.  If the file does not exist, this returns 0.
839  */
840 
841 int
842 read_config_file(const char *filename, const char *host, Options *options,
843     int checkperm)
844 {
845 	FILE *f;
846 	char line[1024];
847 	int active, linenum;
848 	int bad_options = 0;
849 
850 	/* Open the file. */
851 	if ((f = fopen(filename, "r")) == NULL)
852 		return 0;
853 
854 	if (checkperm) {
855 		struct stat sb;
856 
857 		if (fstat(fileno(f), &sb) == -1)
858 			fatal("fstat %s: %s", filename, strerror(errno));
859 		if (((sb.st_uid != 0 && sb.st_uid != getuid()) ||
860 		    (sb.st_mode & 022) != 0))
861 			fatal("Bad owner or permissions on %s", filename);
862 	}
863 
864 	debug("Reading configuration data %.200s", filename);
865 
866 	/*
867 	 * Mark that we are now processing the options.  This flag is turned
868 	 * on/off by Host specifications.
869 	 */
870 	active = 1;
871 	linenum = 0;
872 	while (fgets(line, sizeof(line), f)) {
873 		/* Update line number counter. */
874 		linenum++;
875 		if (process_config_line(options, host, line, filename, linenum, &active) != 0)
876 			bad_options++;
877 	}
878 	fclose(f);
879 	if (bad_options > 0)
880 		fatal("%s: terminating, %d bad configuration options",
881 		    filename, bad_options);
882 	return 1;
883 }
884 
885 /*
886  * Initializes options to special values that indicate that they have not yet
887  * been set.  Read_config_file will only set options with this value. Options
888  * are processed in the following order: command line, user config file,
889  * system config file.  Last, fill_default_options is called.
890  */
891 
892 void
893 initialize_options(Options * options)
894 {
895 	memset(options, 'X', sizeof(*options));
896 	options->forward_agent = -1;
897 	options->forward_x11 = -1;
898 	options->forward_x11_trusted = -1;
899 	options->xauth_location = NULL;
900 	options->gateway_ports = -1;
901 	options->use_privileged_port = -1;
902 	options->rsa_authentication = -1;
903 	options->pubkey_authentication = -1;
904 	options->challenge_response_authentication = -1;
905 	options->gss_authentication = -1;
906 	options->gss_deleg_creds = -1;
907 	options->password_authentication = -1;
908 	options->kbd_interactive_authentication = -1;
909 	options->kbd_interactive_devices = NULL;
910 	options->rhosts_rsa_authentication = -1;
911 	options->hostbased_authentication = -1;
912 	options->batch_mode = -1;
913 	options->check_host_ip = -1;
914 	options->strict_host_key_checking = -1;
915 	options->compression = -1;
916 	options->tcp_keep_alive = -1;
917 	options->compression_level = -1;
918 	options->port = -1;
919 	options->address_family = -1;
920 	options->connection_attempts = -1;
921 	options->connection_timeout = -1;
922 	options->number_of_password_prompts = -1;
923 	options->cipher = -1;
924 	options->ciphers = NULL;
925 	options->macs = NULL;
926 	options->hostkeyalgorithms = NULL;
927 	options->protocol = SSH_PROTO_UNKNOWN;
928 	options->num_identity_files = 0;
929 	options->hostname = NULL;
930 	options->host_key_alias = NULL;
931 	options->proxy_command = NULL;
932 	options->user = NULL;
933 	options->escape_char = -1;
934 	options->system_hostfile = NULL;
935 	options->user_hostfile = NULL;
936 	options->system_hostfile2 = NULL;
937 	options->user_hostfile2 = NULL;
938 	options->num_local_forwards = 0;
939 	options->num_remote_forwards = 0;
940 	options->clear_forwardings = -1;
941 	options->log_level = SYSLOG_LEVEL_NOT_SET;
942 	options->preferred_authentications = NULL;
943 	options->bind_address = NULL;
944 	options->smartcard_device = NULL;
945 	options->enable_ssh_keysign = - 1;
946 	options->no_host_authentication_for_localhost = - 1;
947 	options->identities_only = - 1;
948 	options->rekey_limit = - 1;
949 	options->verify_host_key_dns = -1;
950 	options->server_alive_interval = -1;
951 	options->server_alive_count_max = -1;
952 	options->num_send_env = 0;
953 	options->control_path = NULL;
954 	options->control_master = -1;
955 	options->hash_known_hosts = -1;
956 }
957 
958 /*
959  * Called after processing other sources of option data, this fills those
960  * options for which no value has been specified with their default values.
961  */
962 
963 void
964 fill_default_options(Options * options)
965 {
966 	int len;
967 
968 	if (options->forward_agent == -1)
969 		options->forward_agent = 0;
970 	if (options->forward_x11 == -1)
971 		options->forward_x11 = 0;
972 	if (options->forward_x11_trusted == -1)
973 		options->forward_x11_trusted = 0;
974 	if (options->xauth_location == NULL)
975 		options->xauth_location = _PATH_XAUTH;
976 	if (options->gateway_ports == -1)
977 		options->gateway_ports = 0;
978 	if (options->use_privileged_port == -1)
979 		options->use_privileged_port = 0;
980 	if (options->rsa_authentication == -1)
981 		options->rsa_authentication = 1;
982 	if (options->pubkey_authentication == -1)
983 		options->pubkey_authentication = 1;
984 	if (options->challenge_response_authentication == -1)
985 		options->challenge_response_authentication = 1;
986 	if (options->gss_authentication == -1)
987 		options->gss_authentication = 0;
988 	if (options->gss_deleg_creds == -1)
989 		options->gss_deleg_creds = 0;
990 	if (options->password_authentication == -1)
991 		options->password_authentication = 1;
992 	if (options->kbd_interactive_authentication == -1)
993 		options->kbd_interactive_authentication = 1;
994 	if (options->rhosts_rsa_authentication == -1)
995 		options->rhosts_rsa_authentication = 0;
996 	if (options->hostbased_authentication == -1)
997 		options->hostbased_authentication = 0;
998 	if (options->batch_mode == -1)
999 		options->batch_mode = 0;
1000 	if (options->check_host_ip == -1)
1001 		options->check_host_ip = 0;
1002 	if (options->strict_host_key_checking == -1)
1003 		options->strict_host_key_checking = 2;	/* 2 is default */
1004 	if (options->compression == -1)
1005 		options->compression = 0;
1006 	if (options->tcp_keep_alive == -1)
1007 		options->tcp_keep_alive = 1;
1008 	if (options->compression_level == -1)
1009 		options->compression_level = 6;
1010 	if (options->port == -1)
1011 		options->port = 0;	/* Filled in ssh_connect. */
1012 	if (options->address_family == -1)
1013 		options->address_family = AF_UNSPEC;
1014 	if (options->connection_attempts == -1)
1015 		options->connection_attempts = 1;
1016 	if (options->number_of_password_prompts == -1)
1017 		options->number_of_password_prompts = 3;
1018 	/* Selected in ssh_login(). */
1019 	if (options->cipher == -1)
1020 		options->cipher = SSH_CIPHER_NOT_SET;
1021 	/* options->ciphers, default set in myproposals.h */
1022 	/* options->macs, default set in myproposals.h */
1023 	/* options->hostkeyalgorithms, default set in myproposals.h */
1024 	if (options->protocol == SSH_PROTO_UNKNOWN)
1025 		options->protocol = SSH_PROTO_1|SSH_PROTO_2;
1026 	if (options->num_identity_files == 0) {
1027 		if (options->protocol & SSH_PROTO_1) {
1028 			len = 2 + strlen(_PATH_SSH_CLIENT_IDENTITY) + 1;
1029 			options->identity_files[options->num_identity_files] =
1030 			    xmalloc(len);
1031 			snprintf(options->identity_files[options->num_identity_files++],
1032 			    len, "~/%.100s", _PATH_SSH_CLIENT_IDENTITY);
1033 		}
1034 		if (options->protocol & SSH_PROTO_2) {
1035 			len = 2 + strlen(_PATH_SSH_CLIENT_ID_RSA) + 1;
1036 			options->identity_files[options->num_identity_files] =
1037 			    xmalloc(len);
1038 			snprintf(options->identity_files[options->num_identity_files++],
1039 			    len, "~/%.100s", _PATH_SSH_CLIENT_ID_RSA);
1040 
1041 			len = 2 + strlen(_PATH_SSH_CLIENT_ID_DSA) + 1;
1042 			options->identity_files[options->num_identity_files] =
1043 			    xmalloc(len);
1044 			snprintf(options->identity_files[options->num_identity_files++],
1045 			    len, "~/%.100s", _PATH_SSH_CLIENT_ID_DSA);
1046 		}
1047 	}
1048 	if (options->escape_char == -1)
1049 		options->escape_char = '~';
1050 	if (options->system_hostfile == NULL)
1051 		options->system_hostfile = _PATH_SSH_SYSTEM_HOSTFILE;
1052 	if (options->user_hostfile == NULL)
1053 		options->user_hostfile = _PATH_SSH_USER_HOSTFILE;
1054 	if (options->system_hostfile2 == NULL)
1055 		options->system_hostfile2 = _PATH_SSH_SYSTEM_HOSTFILE2;
1056 	if (options->user_hostfile2 == NULL)
1057 		options->user_hostfile2 = _PATH_SSH_USER_HOSTFILE2;
1058 	if (options->log_level == SYSLOG_LEVEL_NOT_SET)
1059 		options->log_level = SYSLOG_LEVEL_INFO;
1060 	if (options->clear_forwardings == 1)
1061 		clear_forwardings(options);
1062 	if (options->no_host_authentication_for_localhost == - 1)
1063 		options->no_host_authentication_for_localhost = 0;
1064 	if (options->identities_only == -1)
1065 		options->identities_only = 0;
1066 	if (options->enable_ssh_keysign == -1)
1067 		options->enable_ssh_keysign = 0;
1068 	if (options->rekey_limit == -1)
1069 		options->rekey_limit = 0;
1070 	if (options->verify_host_key_dns == -1)
1071 		options->verify_host_key_dns = 0;
1072 	if (options->server_alive_interval == -1)
1073 		options->server_alive_interval = 0;
1074 	if (options->server_alive_count_max == -1)
1075 		options->server_alive_count_max = 3;
1076 	if (options->control_master == -1)
1077 		options->control_master = 0;
1078 	if (options->hash_known_hosts == -1)
1079 		options->hash_known_hosts = 0;
1080 	/* options->proxy_command should not be set by default */
1081 	/* options->user will be set in the main program if appropriate */
1082 	/* options->hostname will be set in the main program if appropriate */
1083 	/* options->host_key_alias should not be set by default */
1084 	/* options->preferred_authentications will be set in ssh */
1085 }
1086 
1087 /*
1088  * parse_forward
1089  * parses a string containing a port forwarding specification of the form:
1090  *	[listenhost:]listenport:connecthost:connectport
1091  * returns number of arguments parsed or zero on error
1092  */
1093 int
1094 parse_forward(Forward *fwd, const char *fwdspec)
1095 {
1096 	int i;
1097 	char *p, *cp, *fwdarg[4];
1098 
1099 	memset(fwd, '\0', sizeof(*fwd));
1100 
1101 	cp = p = xstrdup(fwdspec);
1102 
1103 	/* skip leading spaces */
1104 	while (*cp && isspace(*cp))
1105 		cp++;
1106 
1107 	for (i = 0; i < 4; ++i)
1108 		if ((fwdarg[i] = hpdelim(&cp)) == NULL)
1109 			break;
1110 
1111 	/* Check for trailing garbage in 4-arg case*/
1112 	if (cp != NULL)
1113 		i = 0;	/* failure */
1114 
1115 	switch (i) {
1116 	case 3:
1117 		fwd->listen_host = NULL;
1118 		fwd->listen_port = a2port(fwdarg[0]);
1119 		fwd->connect_host = xstrdup(cleanhostname(fwdarg[1]));
1120 		fwd->connect_port = a2port(fwdarg[2]);
1121 		break;
1122 
1123 	case 4:
1124 		fwd->listen_host = xstrdup(cleanhostname(fwdarg[0]));
1125 		fwd->listen_port = a2port(fwdarg[1]);
1126 		fwd->connect_host = xstrdup(cleanhostname(fwdarg[2]));
1127 		fwd->connect_port = a2port(fwdarg[3]);
1128 		break;
1129 	default:
1130 		i = 0; /* failure */
1131 	}
1132 
1133 	xfree(p);
1134 
1135 	if (fwd->listen_port == 0 && fwd->connect_port == 0)
1136 		goto fail_free;
1137 
1138 	if (fwd->connect_host != NULL &&
1139 	    strlen(fwd->connect_host) >= NI_MAXHOST)
1140 		goto fail_free;
1141 
1142 	return (i);
1143 
1144  fail_free:
1145 	if (fwd->connect_host != NULL)
1146 		xfree(fwd->connect_host);
1147 	if (fwd->listen_host != NULL)
1148 		xfree(fwd->listen_host);
1149 	return (0);
1150 }
1151