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