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