diff options
Diffstat (limited to 'servconf.c')
-rw-r--r-- | servconf.c | 176 |
1 files changed, 142 insertions, 34 deletions
diff --git a/servconf.c b/servconf.c index 318546290..df93fc450 100644 --- a/servconf.c +++ b/servconf.c | |||
@@ -1,5 +1,4 @@ | |||
1 | 1 | /* $OpenBSD: servconf.c,v 1.274 2015/07/01 02:32:17 djm Exp $ */ | |
2 | /* $OpenBSD: servconf.c,v 1.260 2015/02/02 01:57:44 deraadt Exp $ */ | ||
3 | /* | 2 | /* |
4 | * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland | 3 | * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland |
5 | * All rights reserved | 4 | * All rights reserved |
@@ -78,6 +77,8 @@ initialize_server_options(ServerOptions *options) | |||
78 | /* Standard Options */ | 77 | /* Standard Options */ |
79 | options->num_ports = 0; | 78 | options->num_ports = 0; |
80 | options->ports_from_cmdline = 0; | 79 | options->ports_from_cmdline = 0; |
80 | options->queued_listen_addrs = NULL; | ||
81 | options->num_queued_listens = 0; | ||
81 | options->listen_addrs = NULL; | 82 | options->listen_addrs = NULL; |
82 | options->address_family = -1; | 83 | options->address_family = -1; |
83 | options->num_host_key_files = 0; | 84 | options->num_host_key_files = 0; |
@@ -115,6 +116,7 @@ initialize_server_options(ServerOptions *options) | |||
115 | options->kerberos_get_afs_token = -1; | 116 | options->kerberos_get_afs_token = -1; |
116 | options->gss_authentication=-1; | 117 | options->gss_authentication=-1; |
117 | options->gss_cleanup_creds = -1; | 118 | options->gss_cleanup_creds = -1; |
119 | options->gss_strict_acceptor = -1; | ||
118 | options->password_authentication = -1; | 120 | options->password_authentication = -1; |
119 | options->kbd_interactive_authentication = -1; | 121 | options->kbd_interactive_authentication = -1; |
120 | options->challenge_response_authentication = -1; | 122 | options->challenge_response_authentication = -1; |
@@ -159,6 +161,8 @@ initialize_server_options(ServerOptions *options) | |||
159 | options->revoked_keys_file = NULL; | 161 | options->revoked_keys_file = NULL; |
160 | options->trusted_user_ca_keys = NULL; | 162 | options->trusted_user_ca_keys = NULL; |
161 | options->authorized_principals_file = NULL; | 163 | options->authorized_principals_file = NULL; |
164 | options->authorized_principals_command = NULL; | ||
165 | options->authorized_principals_command_user = NULL; | ||
162 | options->ip_qos_interactive = -1; | 166 | options->ip_qos_interactive = -1; |
163 | options->ip_qos_bulk = -1; | 167 | options->ip_qos_bulk = -1; |
164 | options->version_addendum = NULL; | 168 | options->version_addendum = NULL; |
@@ -205,6 +209,8 @@ fill_default_server_options(ServerOptions *options) | |||
205 | /* No certificates by default */ | 209 | /* No certificates by default */ |
206 | if (options->num_ports == 0) | 210 | if (options->num_ports == 0) |
207 | options->ports[options->num_ports++] = SSH_DEFAULT_PORT; | 211 | options->ports[options->num_ports++] = SSH_DEFAULT_PORT; |
212 | if (options->address_family == -1) | ||
213 | options->address_family = AF_UNSPEC; | ||
208 | if (options->listen_addrs == NULL) | 214 | if (options->listen_addrs == NULL) |
209 | add_listen_addr(options, NULL, 0); | 215 | add_listen_addr(options, NULL, 0); |
210 | if (options->pid_file == NULL) | 216 | if (options->pid_file == NULL) |
@@ -271,6 +277,8 @@ fill_default_server_options(ServerOptions *options) | |||
271 | options->gss_authentication = 0; | 277 | options->gss_authentication = 0; |
272 | if (options->gss_cleanup_creds == -1) | 278 | if (options->gss_cleanup_creds == -1) |
273 | options->gss_cleanup_creds = 1; | 279 | options->gss_cleanup_creds = 1; |
280 | if (options->gss_strict_acceptor == -1) | ||
281 | options->gss_strict_acceptor = 0; | ||
274 | if (options->password_authentication == -1) | 282 | if (options->password_authentication == -1) |
275 | options->password_authentication = 1; | 283 | options->password_authentication = 1; |
276 | if (options->kbd_interactive_authentication == -1) | 284 | if (options->kbd_interactive_authentication == -1) |
@@ -349,6 +357,7 @@ fill_default_server_options(ServerOptions *options) | |||
349 | CLEAR_ON_NONE(options->banner); | 357 | CLEAR_ON_NONE(options->banner); |
350 | CLEAR_ON_NONE(options->trusted_user_ca_keys); | 358 | CLEAR_ON_NONE(options->trusted_user_ca_keys); |
351 | CLEAR_ON_NONE(options->revoked_keys_file); | 359 | CLEAR_ON_NONE(options->revoked_keys_file); |
360 | CLEAR_ON_NONE(options->authorized_principals_file); | ||
352 | for (i = 0; i < options->num_host_key_files; i++) | 361 | for (i = 0; i < options->num_host_key_files; i++) |
353 | CLEAR_ON_NONE(options->host_key_files[i]); | 362 | CLEAR_ON_NONE(options->host_key_files[i]); |
354 | for (i = 0; i < options->num_host_cert_files; i++) | 363 | for (i = 0; i < options->num_host_cert_files; i++) |
@@ -391,11 +400,13 @@ typedef enum { | |||
391 | sBanner, sUseDNS, sHostbasedAuthentication, | 400 | sBanner, sUseDNS, sHostbasedAuthentication, |
392 | sHostbasedUsesNameFromPacketOnly, sHostbasedAcceptedKeyTypes, | 401 | sHostbasedUsesNameFromPacketOnly, sHostbasedAcceptedKeyTypes, |
393 | sClientAliveInterval, sClientAliveCountMax, sAuthorizedKeysFile, | 402 | sClientAliveInterval, sClientAliveCountMax, sAuthorizedKeysFile, |
394 | sGssAuthentication, sGssCleanupCreds, sAcceptEnv, sPermitTunnel, | 403 | sGssAuthentication, sGssCleanupCreds, sGssStrictAcceptor, |
404 | sAcceptEnv, sPermitTunnel, | ||
395 | sMatch, sPermitOpen, sForceCommand, sChrootDirectory, | 405 | sMatch, sPermitOpen, sForceCommand, sChrootDirectory, |
396 | sUsePrivilegeSeparation, sAllowAgentForwarding, | 406 | sUsePrivilegeSeparation, sAllowAgentForwarding, |
397 | sHostCertificate, | 407 | sHostCertificate, |
398 | sRevokedKeys, sTrustedUserCAKeys, sAuthorizedPrincipalsFile, | 408 | sRevokedKeys, sTrustedUserCAKeys, sAuthorizedPrincipalsFile, |
409 | sAuthorizedPrincipalsCommand, sAuthorizedPrincipalsCommandUser, | ||
399 | sKexAlgorithms, sIPQoS, sVersionAddendum, | 410 | sKexAlgorithms, sIPQoS, sVersionAddendum, |
400 | sAuthorizedKeysCommand, sAuthorizedKeysCommandUser, | 411 | sAuthorizedKeysCommand, sAuthorizedKeysCommandUser, |
401 | sAuthenticationMethods, sHostKeyAgent, sPermitUserRC, | 412 | sAuthenticationMethods, sHostKeyAgent, sPermitUserRC, |
@@ -462,9 +473,11 @@ static struct { | |||
462 | #ifdef GSSAPI | 473 | #ifdef GSSAPI |
463 | { "gssapiauthentication", sGssAuthentication, SSHCFG_ALL }, | 474 | { "gssapiauthentication", sGssAuthentication, SSHCFG_ALL }, |
464 | { "gssapicleanupcredentials", sGssCleanupCreds, SSHCFG_GLOBAL }, | 475 | { "gssapicleanupcredentials", sGssCleanupCreds, SSHCFG_GLOBAL }, |
476 | { "gssapistrictacceptorcheck", sGssStrictAcceptor, SSHCFG_GLOBAL }, | ||
465 | #else | 477 | #else |
466 | { "gssapiauthentication", sUnsupported, SSHCFG_ALL }, | 478 | { "gssapiauthentication", sUnsupported, SSHCFG_ALL }, |
467 | { "gssapicleanupcredentials", sUnsupported, SSHCFG_GLOBAL }, | 479 | { "gssapicleanupcredentials", sUnsupported, SSHCFG_GLOBAL }, |
480 | { "gssapistrictacceptorcheck", sUnsupported, SSHCFG_GLOBAL }, | ||
468 | #endif | 481 | #endif |
469 | { "passwordauthentication", sPasswordAuthentication, SSHCFG_ALL }, | 482 | { "passwordauthentication", sPasswordAuthentication, SSHCFG_ALL }, |
470 | { "kbdinteractiveauthentication", sKbdInteractiveAuthentication, SSHCFG_ALL }, | 483 | { "kbdinteractiveauthentication", sKbdInteractiveAuthentication, SSHCFG_ALL }, |
@@ -528,6 +541,8 @@ static struct { | |||
528 | { "ipqos", sIPQoS, SSHCFG_ALL }, | 541 | { "ipqos", sIPQoS, SSHCFG_ALL }, |
529 | { "authorizedkeyscommand", sAuthorizedKeysCommand, SSHCFG_ALL }, | 542 | { "authorizedkeyscommand", sAuthorizedKeysCommand, SSHCFG_ALL }, |
530 | { "authorizedkeyscommanduser", sAuthorizedKeysCommandUser, SSHCFG_ALL }, | 543 | { "authorizedkeyscommanduser", sAuthorizedKeysCommandUser, SSHCFG_ALL }, |
544 | { "authorizedprincipalscommand", sAuthorizedPrincipalsCommand, SSHCFG_ALL }, | ||
545 | { "authorizedprincipalscommanduser", sAuthorizedPrincipalsCommandUser, SSHCFG_ALL }, | ||
531 | { "versionaddendum", sVersionAddendum, SSHCFG_GLOBAL }, | 546 | { "versionaddendum", sVersionAddendum, SSHCFG_GLOBAL }, |
532 | { "authenticationmethods", sAuthenticationMethods, SSHCFG_ALL }, | 547 | { "authenticationmethods", sAuthenticationMethods, SSHCFG_ALL }, |
533 | { "streamlocalbindmask", sStreamLocalBindMask, SSHCFG_ALL }, | 548 | { "streamlocalbindmask", sStreamLocalBindMask, SSHCFG_ALL }, |
@@ -591,10 +606,6 @@ add_listen_addr(ServerOptions *options, char *addr, int port) | |||
591 | { | 606 | { |
592 | u_int i; | 607 | u_int i; |
593 | 608 | ||
594 | if (options->num_ports == 0) | ||
595 | options->ports[options->num_ports++] = SSH_DEFAULT_PORT; | ||
596 | if (options->address_family == -1) | ||
597 | options->address_family = AF_UNSPEC; | ||
598 | if (port == 0) | 609 | if (port == 0) |
599 | for (i = 0; i < options->num_ports; i++) | 610 | for (i = 0; i < options->num_ports; i++) |
600 | add_one_listen_addr(options, addr, options->ports[i]); | 611 | add_one_listen_addr(options, addr, options->ports[i]); |
@@ -624,6 +635,51 @@ add_one_listen_addr(ServerOptions *options, char *addr, int port) | |||
624 | options->listen_addrs = aitop; | 635 | options->listen_addrs = aitop; |
625 | } | 636 | } |
626 | 637 | ||
638 | /* | ||
639 | * Queue a ListenAddress to be processed once we have all of the Ports | ||
640 | * and AddressFamily options. | ||
641 | */ | ||
642 | static void | ||
643 | queue_listen_addr(ServerOptions *options, char *addr, int port) | ||
644 | { | ||
645 | options->queued_listen_addrs = xreallocarray( | ||
646 | options->queued_listen_addrs, options->num_queued_listens + 1, | ||
647 | sizeof(addr)); | ||
648 | options->queued_listen_ports = xreallocarray( | ||
649 | options->queued_listen_ports, options->num_queued_listens + 1, | ||
650 | sizeof(port)); | ||
651 | options->queued_listen_addrs[options->num_queued_listens] = | ||
652 | xstrdup(addr); | ||
653 | options->queued_listen_ports[options->num_queued_listens] = port; | ||
654 | options->num_queued_listens++; | ||
655 | } | ||
656 | |||
657 | /* | ||
658 | * Process queued (text) ListenAddress entries. | ||
659 | */ | ||
660 | static void | ||
661 | process_queued_listen_addrs(ServerOptions *options) | ||
662 | { | ||
663 | u_int i; | ||
664 | |||
665 | if (options->num_ports == 0) | ||
666 | options->ports[options->num_ports++] = SSH_DEFAULT_PORT; | ||
667 | if (options->address_family == -1) | ||
668 | options->address_family = AF_UNSPEC; | ||
669 | |||
670 | for (i = 0; i < options->num_queued_listens; i++) { | ||
671 | add_listen_addr(options, options->queued_listen_addrs[i], | ||
672 | options->queued_listen_ports[i]); | ||
673 | free(options->queued_listen_addrs[i]); | ||
674 | options->queued_listen_addrs[i] = NULL; | ||
675 | } | ||
676 | free(options->queued_listen_addrs); | ||
677 | options->queued_listen_addrs = NULL; | ||
678 | free(options->queued_listen_ports); | ||
679 | options->queued_listen_ports = NULL; | ||
680 | options->num_queued_listens = 0; | ||
681 | } | ||
682 | |||
627 | struct connection_info * | 683 | struct connection_info * |
628 | get_connection_info(int populate, int use_dns) | 684 | get_connection_info(int populate, int use_dns) |
629 | { | 685 | { |
@@ -709,7 +765,6 @@ match_cfg_line(char **condition, int line, struct connection_info *ci) | |||
709 | { | 765 | { |
710 | int result = 1, attributes = 0, port; | 766 | int result = 1, attributes = 0, port; |
711 | char *arg, *attrib, *cp = *condition; | 767 | char *arg, *attrib, *cp = *condition; |
712 | size_t len; | ||
713 | 768 | ||
714 | if (ci == NULL) | 769 | if (ci == NULL) |
715 | debug3("checking syntax for 'Match %s'", cp); | 770 | debug3("checking syntax for 'Match %s'", cp); |
@@ -736,13 +791,12 @@ match_cfg_line(char **condition, int line, struct connection_info *ci) | |||
736 | error("Missing Match criteria for %s", attrib); | 791 | error("Missing Match criteria for %s", attrib); |
737 | return -1; | 792 | return -1; |
738 | } | 793 | } |
739 | len = strlen(arg); | ||
740 | if (strcasecmp(attrib, "user") == 0) { | 794 | if (strcasecmp(attrib, "user") == 0) { |
741 | if (ci == NULL || ci->user == NULL) { | 795 | if (ci == NULL || ci->user == NULL) { |
742 | result = 0; | 796 | result = 0; |
743 | continue; | 797 | continue; |
744 | } | 798 | } |
745 | if (match_pattern_list(ci->user, arg, len, 0) != 1) | 799 | if (match_pattern_list(ci->user, arg, 0) != 1) |
746 | result = 0; | 800 | result = 0; |
747 | else | 801 | else |
748 | debug("user %.100s matched 'User %.100s' at " | 802 | debug("user %.100s matched 'User %.100s' at " |
@@ -763,7 +817,7 @@ match_cfg_line(char **condition, int line, struct connection_info *ci) | |||
763 | result = 0; | 817 | result = 0; |
764 | continue; | 818 | continue; |
765 | } | 819 | } |
766 | if (match_hostname(ci->host, arg, len) != 1) | 820 | if (match_hostname(ci->host, arg) != 1) |
767 | result = 0; | 821 | result = 0; |
768 | else | 822 | else |
769 | debug("connection from %.100s matched 'Host " | 823 | debug("connection from %.100s matched 'Host " |
@@ -940,9 +994,6 @@ process_server_config_line(ServerOptions *options, char *line, | |||
940 | /* ignore ports from configfile if cmdline specifies ports */ | 994 | /* ignore ports from configfile if cmdline specifies ports */ |
941 | if (options->ports_from_cmdline) | 995 | if (options->ports_from_cmdline) |
942 | return 0; | 996 | return 0; |
943 | if (options->listen_addrs != NULL) | ||
944 | fatal("%s line %d: ports must be specified before " | ||
945 | "ListenAddress.", filename, linenum); | ||
946 | if (options->num_ports >= MAX_PORTS) | 997 | if (options->num_ports >= MAX_PORTS) |
947 | fatal("%s line %d: too many ports.", | 998 | fatal("%s line %d: too many ports.", |
948 | filename, linenum); | 999 | filename, linenum); |
@@ -978,7 +1029,7 @@ process_server_config_line(ServerOptions *options, char *line, | |||
978 | if ((value = convtime(arg)) == -1) | 1029 | if ((value = convtime(arg)) == -1) |
979 | fatal("%s line %d: invalid time value.", | 1030 | fatal("%s line %d: invalid time value.", |
980 | filename, linenum); | 1031 | filename, linenum); |
981 | if (*intptr == -1) | 1032 | if (*activep && *intptr == -1) |
982 | *intptr = value; | 1033 | *intptr = value; |
983 | break; | 1034 | break; |
984 | 1035 | ||
@@ -994,7 +1045,7 @@ process_server_config_line(ServerOptions *options, char *line, | |||
994 | /* check for bare IPv6 address: no "[]" and 2 or more ":" */ | 1045 | /* check for bare IPv6 address: no "[]" and 2 or more ":" */ |
995 | if (strchr(arg, '[') == NULL && (p = strchr(arg, ':')) != NULL | 1046 | if (strchr(arg, '[') == NULL && (p = strchr(arg, ':')) != NULL |
996 | && strchr(p+1, ':') != NULL) { | 1047 | && strchr(p+1, ':') != NULL) { |
997 | add_listen_addr(options, arg, 0); | 1048 | queue_listen_addr(options, arg, 0); |
998 | break; | 1049 | break; |
999 | } | 1050 | } |
1000 | p = hpdelim(&arg); | 1051 | p = hpdelim(&arg); |
@@ -1007,16 +1058,13 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1007 | else if ((port = a2port(arg)) <= 0) | 1058 | else if ((port = a2port(arg)) <= 0) |
1008 | fatal("%s line %d: bad port number", filename, linenum); | 1059 | fatal("%s line %d: bad port number", filename, linenum); |
1009 | 1060 | ||
1010 | add_listen_addr(options, p, port); | 1061 | queue_listen_addr(options, p, port); |
1011 | 1062 | ||
1012 | break; | 1063 | break; |
1013 | 1064 | ||
1014 | case sAddressFamily: | 1065 | case sAddressFamily: |
1015 | intptr = &options->address_family; | 1066 | intptr = &options->address_family; |
1016 | multistate_ptr = multistate_addressfamily; | 1067 | multistate_ptr = multistate_addressfamily; |
1017 | if (options->listen_addrs != NULL) | ||
1018 | fatal("%s line %d: address family must be specified " | ||
1019 | "before ListenAddress.", filename, linenum); | ||
1020 | parse_multistate: | 1068 | parse_multistate: |
1021 | arg = strdelim(&cp); | 1069 | arg = strdelim(&cp); |
1022 | if (!arg || *arg == '\0') | 1070 | if (!arg || *arg == '\0') |
@@ -1170,6 +1218,10 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1170 | intptr = &options->gss_cleanup_creds; | 1218 | intptr = &options->gss_cleanup_creds; |
1171 | goto parse_flag; | 1219 | goto parse_flag; |
1172 | 1220 | ||
1221 | case sGssStrictAcceptor: | ||
1222 | intptr = &options->gss_strict_acceptor; | ||
1223 | goto parse_flag; | ||
1224 | |||
1173 | case sPasswordAuthentication: | 1225 | case sPasswordAuthentication: |
1174 | intptr = &options->password_authentication; | 1226 | intptr = &options->password_authentication; |
1175 | goto parse_flag; | 1227 | goto parse_flag; |
@@ -1444,7 +1496,7 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1444 | len = strlen(p) + 1; | 1496 | len = strlen(p) + 1; |
1445 | while ((arg = strdelim(&cp)) != NULL && *arg != '\0') { | 1497 | while ((arg = strdelim(&cp)) != NULL && *arg != '\0') { |
1446 | len += 1 + strlen(arg); | 1498 | len += 1 + strlen(arg); |
1447 | p = xrealloc(p, 1, len); | 1499 | p = xreallocarray(p, 1, len); |
1448 | strlcat(p, " ", len); | 1500 | strlcat(p, " ", len); |
1449 | strlcat(p, arg, len); | 1501 | strlcat(p, arg, len); |
1450 | } | 1502 | } |
@@ -1559,7 +1611,7 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1559 | if (value == -1) | 1611 | if (value == -1) |
1560 | fatal("%s line %d: Bad yes/point-to-point/ethernet/" | 1612 | fatal("%s line %d: Bad yes/point-to-point/ethernet/" |
1561 | "no argument: %s", filename, linenum, arg); | 1613 | "no argument: %s", filename, linenum, arg); |
1562 | if (*intptr == -1) | 1614 | if (*activep && *intptr == -1) |
1563 | *intptr = value; | 1615 | *intptr = value; |
1564 | break; | 1616 | break; |
1565 | 1617 | ||
@@ -1612,7 +1664,7 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1612 | break; | 1664 | break; |
1613 | 1665 | ||
1614 | case sForceCommand: | 1666 | case sForceCommand: |
1615 | if (cp == NULL) | 1667 | if (cp == NULL || *cp == '\0') |
1616 | fatal("%.200s line %d: Missing argument.", filename, | 1668 | fatal("%.200s line %d: Missing argument.", filename, |
1617 | linenum); | 1669 | linenum); |
1618 | len = strspn(cp, WHITESPACE); | 1670 | len = strspn(cp, WHITESPACE); |
@@ -1657,7 +1709,7 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1657 | break; | 1709 | break; |
1658 | 1710 | ||
1659 | case sVersionAddendum: | 1711 | case sVersionAddendum: |
1660 | if (cp == NULL) | 1712 | if (cp == NULL || *cp == '\0') |
1661 | fatal("%.200s line %d: Missing argument.", filename, | 1713 | fatal("%.200s line %d: Missing argument.", filename, |
1662 | linenum); | 1714 | linenum); |
1663 | len = strspn(cp, WHITESPACE); | 1715 | len = strspn(cp, WHITESPACE); |
@@ -1697,8 +1749,36 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1697 | *charptr = xstrdup(arg); | 1749 | *charptr = xstrdup(arg); |
1698 | break; | 1750 | break; |
1699 | 1751 | ||
1752 | case sAuthorizedPrincipalsCommand: | ||
1753 | if (cp == NULL) | ||
1754 | fatal("%.200s line %d: Missing argument.", filename, | ||
1755 | linenum); | ||
1756 | len = strspn(cp, WHITESPACE); | ||
1757 | if (*activep && | ||
1758 | options->authorized_principals_command == NULL) { | ||
1759 | if (cp[len] != '/' && strcasecmp(cp + len, "none") != 0) | ||
1760 | fatal("%.200s line %d: " | ||
1761 | "AuthorizedPrincipalsCommand must be " | ||
1762 | "an absolute path", filename, linenum); | ||
1763 | options->authorized_principals_command = | ||
1764 | xstrdup(cp + len); | ||
1765 | } | ||
1766 | return 0; | ||
1767 | |||
1768 | case sAuthorizedPrincipalsCommandUser: | ||
1769 | charptr = &options->authorized_principals_command_user; | ||
1770 | |||
1771 | arg = strdelim(&cp); | ||
1772 | if (!arg || *arg == '\0') | ||
1773 | fatal("%s line %d: missing " | ||
1774 | "AuthorizedPrincipalsCommandUser argument.", | ||
1775 | filename, linenum); | ||
1776 | if (*activep && *charptr == NULL) | ||
1777 | *charptr = xstrdup(arg); | ||
1778 | break; | ||
1779 | |||
1700 | case sAuthenticationMethods: | 1780 | case sAuthenticationMethods: |
1701 | if (*activep && options->num_auth_methods == 0) { | 1781 | if (options->num_auth_methods == 0) { |
1702 | while ((arg = strdelim(&cp)) && *arg != '\0') { | 1782 | while ((arg = strdelim(&cp)) && *arg != '\0') { |
1703 | if (options->num_auth_methods >= | 1783 | if (options->num_auth_methods >= |
1704 | MAX_AUTH_METHODS) | 1784 | MAX_AUTH_METHODS) |
@@ -1709,6 +1789,8 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1709 | fatal("%s line %d: invalid " | 1789 | fatal("%s line %d: invalid " |
1710 | "authentication method list.", | 1790 | "authentication method list.", |
1711 | filename, linenum); | 1791 | filename, linenum); |
1792 | if (!*activep) | ||
1793 | continue; | ||
1712 | options->auth_methods[ | 1794 | options->auth_methods[ |
1713 | options->num_auth_methods++] = xstrdup(arg); | 1795 | options->num_auth_methods++] = xstrdup(arg); |
1714 | } | 1796 | } |
@@ -1718,13 +1800,14 @@ process_server_config_line(ServerOptions *options, char *line, | |||
1718 | case sStreamLocalBindMask: | 1800 | case sStreamLocalBindMask: |
1719 | arg = strdelim(&cp); | 1801 | arg = strdelim(&cp); |
1720 | if (!arg || *arg == '\0') | 1802 | if (!arg || *arg == '\0') |
1721 | fatal("%s line %d: missing StreamLocalBindMask argument.", | 1803 | fatal("%s line %d: missing StreamLocalBindMask " |
1722 | filename, linenum); | 1804 | "argument.", filename, linenum); |
1723 | /* Parse mode in octal format */ | 1805 | /* Parse mode in octal format */ |
1724 | value = strtol(arg, &p, 8); | 1806 | value = strtol(arg, &p, 8); |
1725 | if (arg == p || value < 0 || value > 0777) | 1807 | if (arg == p || value < 0 || value > 0777) |
1726 | fatal("%s line %d: Bad mask.", filename, linenum); | 1808 | fatal("%s line %d: Bad mask.", filename, linenum); |
1727 | options->fwd_opts.streamlocal_bind_mask = (mode_t)value; | 1809 | if (*activep) |
1810 | options->fwd_opts.streamlocal_bind_mask = (mode_t)value; | ||
1728 | break; | 1811 | break; |
1729 | 1812 | ||
1730 | case sStreamLocalBindUnlink: | 1813 | case sStreamLocalBindUnlink: |
@@ -1951,6 +2034,7 @@ parse_server_config(ServerOptions *options, const char *filename, Buffer *conf, | |||
1951 | if (bad_options > 0) | 2034 | if (bad_options > 0) |
1952 | fatal("%s: terminating, %d bad configuration options", | 2035 | fatal("%s: terminating, %d bad configuration options", |
1953 | filename, bad_options); | 2036 | filename, bad_options); |
2037 | process_queued_listen_addrs(options); | ||
1954 | } | 2038 | } |
1955 | 2039 | ||
1956 | static const char * | 2040 | static const char * |
@@ -2028,6 +2112,12 @@ dump_cfg_int(ServerOpCodes code, int val) | |||
2028 | } | 2112 | } |
2029 | 2113 | ||
2030 | static void | 2114 | static void |
2115 | dump_cfg_oct(ServerOpCodes code, int val) | ||
2116 | { | ||
2117 | printf("%s 0%o\n", lookup_opcode_name(code), val); | ||
2118 | } | ||
2119 | |||
2120 | static void | ||
2031 | dump_cfg_fmtint(ServerOpCodes code, int val) | 2121 | dump_cfg_fmtint(ServerOpCodes code, int val) |
2032 | { | 2122 | { |
2033 | printf("%s %s\n", lookup_opcode_name(code), fmt_intarg(code, val)); | 2123 | printf("%s %s\n", lookup_opcode_name(code), fmt_intarg(code, val)); |
@@ -2056,6 +2146,8 @@ dump_cfg_strarray_oneline(ServerOpCodes code, u_int count, char **vals) | |||
2056 | { | 2146 | { |
2057 | u_int i; | 2147 | u_int i; |
2058 | 2148 | ||
2149 | if (count <= 0) | ||
2150 | return; | ||
2059 | printf("%s", lookup_opcode_name(code)); | 2151 | printf("%s", lookup_opcode_name(code)); |
2060 | for (i = 0; i < count; i++) | 2152 | for (i = 0; i < count; i++) |
2061 | printf(" %s", vals[i]); | 2153 | printf(" %s", vals[i]); |
@@ -2069,6 +2161,7 @@ dump_config(ServerOptions *o) | |||
2069 | int ret; | 2161 | int ret; |
2070 | struct addrinfo *ai; | 2162 | struct addrinfo *ai; |
2071 | char addr[NI_MAXHOST], port[NI_MAXSERV], *s = NULL; | 2163 | char addr[NI_MAXHOST], port[NI_MAXSERV], *s = NULL; |
2164 | char *laddr1 = xstrdup(""), *laddr2 = NULL; | ||
2072 | 2165 | ||
2073 | /* these are usually at the top of the config */ | 2166 | /* these are usually at the top of the config */ |
2074 | for (i = 0; i < o->num_ports; i++) | 2167 | for (i = 0; i < o->num_ports; i++) |
@@ -2076,7 +2169,11 @@ dump_config(ServerOptions *o) | |||
2076 | dump_cfg_fmtint(sProtocol, o->protocol); | 2169 | dump_cfg_fmtint(sProtocol, o->protocol); |
2077 | dump_cfg_fmtint(sAddressFamily, o->address_family); | 2170 | dump_cfg_fmtint(sAddressFamily, o->address_family); |
2078 | 2171 | ||
2079 | /* ListenAddress must be after Port */ | 2172 | /* |
2173 | * ListenAddress must be after Port. add_one_listen_addr pushes | ||
2174 | * addresses onto a stack, so to maintain ordering we need to | ||
2175 | * print these in reverse order. | ||
2176 | */ | ||
2080 | for (ai = o->listen_addrs; ai; ai = ai->ai_next) { | 2177 | for (ai = o->listen_addrs; ai; ai = ai->ai_next) { |
2081 | if ((ret = getnameinfo(ai->ai_addr, ai->ai_addrlen, addr, | 2178 | if ((ret = getnameinfo(ai->ai_addr, ai->ai_addrlen, addr, |
2082 | sizeof(addr), port, sizeof(port), | 2179 | sizeof(addr), port, sizeof(port), |
@@ -2085,16 +2182,22 @@ dump_config(ServerOptions *o) | |||
2085 | (ret != EAI_SYSTEM) ? gai_strerror(ret) : | 2182 | (ret != EAI_SYSTEM) ? gai_strerror(ret) : |
2086 | strerror(errno)); | 2183 | strerror(errno)); |
2087 | } else { | 2184 | } else { |
2185 | laddr2 = laddr1; | ||
2088 | if (ai->ai_family == AF_INET6) | 2186 | if (ai->ai_family == AF_INET6) |
2089 | printf("listenaddress [%s]:%s\n", addr, port); | 2187 | xasprintf(&laddr1, "listenaddress [%s]:%s\n%s", |
2188 | addr, port, laddr2); | ||
2090 | else | 2189 | else |
2091 | printf("listenaddress %s:%s\n", addr, port); | 2190 | xasprintf(&laddr1, "listenaddress %s:%s\n%s", |
2191 | addr, port, laddr2); | ||
2192 | free(laddr2); | ||
2092 | } | 2193 | } |
2093 | } | 2194 | } |
2195 | printf("%s", laddr1); | ||
2196 | free(laddr1); | ||
2094 | 2197 | ||
2095 | /* integer arguments */ | 2198 | /* integer arguments */ |
2096 | #ifdef USE_PAM | 2199 | #ifdef USE_PAM |
2097 | dump_cfg_int(sUsePAM, o->use_pam); | 2200 | dump_cfg_fmtint(sUsePAM, o->use_pam); |
2098 | #endif | 2201 | #endif |
2099 | dump_cfg_int(sServerKeyBits, o->server_key_bits); | 2202 | dump_cfg_int(sServerKeyBits, o->server_key_bits); |
2100 | dump_cfg_int(sLoginGraceTime, o->login_grace_time); | 2203 | dump_cfg_int(sLoginGraceTime, o->login_grace_time); |
@@ -2104,6 +2207,7 @@ dump_config(ServerOptions *o) | |||
2104 | dump_cfg_int(sMaxSessions, o->max_sessions); | 2207 | dump_cfg_int(sMaxSessions, o->max_sessions); |
2105 | dump_cfg_int(sClientAliveInterval, o->client_alive_interval); | 2208 | dump_cfg_int(sClientAliveInterval, o->client_alive_interval); |
2106 | dump_cfg_int(sClientAliveCountMax, o->client_alive_count_max); | 2209 | dump_cfg_int(sClientAliveCountMax, o->client_alive_count_max); |
2210 | dump_cfg_oct(sStreamLocalBindMask, o->fwd_opts.streamlocal_bind_mask); | ||
2107 | 2211 | ||
2108 | /* formatted integer arguments */ | 2212 | /* formatted integer arguments */ |
2109 | dump_cfg_fmtint(sPermitRootLogin, o->permit_root_login); | 2213 | dump_cfg_fmtint(sPermitRootLogin, o->permit_root_login); |
@@ -2147,6 +2251,7 @@ dump_config(ServerOptions *o) | |||
2147 | dump_cfg_fmtint(sGatewayPorts, o->fwd_opts.gateway_ports); | 2251 | dump_cfg_fmtint(sGatewayPorts, o->fwd_opts.gateway_ports); |
2148 | dump_cfg_fmtint(sUseDNS, o->use_dns); | 2252 | dump_cfg_fmtint(sUseDNS, o->use_dns); |
2149 | dump_cfg_fmtint(sAllowTcpForwarding, o->allow_tcp_forwarding); | 2253 | dump_cfg_fmtint(sAllowTcpForwarding, o->allow_tcp_forwarding); |
2254 | dump_cfg_fmtint(sAllowAgentForwarding, o->allow_agent_forwarding); | ||
2150 | dump_cfg_fmtint(sAllowStreamLocalForwarding, o->allow_streamlocal_forwarding); | 2255 | dump_cfg_fmtint(sAllowStreamLocalForwarding, o->allow_streamlocal_forwarding); |
2151 | dump_cfg_fmtint(sUsePrivilegeSeparation, use_privsep); | 2256 | dump_cfg_fmtint(sUsePrivilegeSeparation, use_privsep); |
2152 | dump_cfg_fmtint(sFingerprintHash, o->fingerprint_hash); | 2257 | dump_cfg_fmtint(sFingerprintHash, o->fingerprint_hash); |
@@ -2163,9 +2268,12 @@ dump_config(ServerOptions *o) | |||
2163 | dump_cfg_string(sRevokedKeys, o->revoked_keys_file); | 2268 | dump_cfg_string(sRevokedKeys, o->revoked_keys_file); |
2164 | dump_cfg_string(sAuthorizedPrincipalsFile, | 2269 | dump_cfg_string(sAuthorizedPrincipalsFile, |
2165 | o->authorized_principals_file); | 2270 | o->authorized_principals_file); |
2166 | dump_cfg_string(sVersionAddendum, o->version_addendum); | 2271 | dump_cfg_string(sVersionAddendum, *o->version_addendum == '\0' |
2272 | ? "none" : o->version_addendum); | ||
2167 | dump_cfg_string(sAuthorizedKeysCommand, o->authorized_keys_command); | 2273 | dump_cfg_string(sAuthorizedKeysCommand, o->authorized_keys_command); |
2168 | dump_cfg_string(sAuthorizedKeysCommandUser, o->authorized_keys_command_user); | 2274 | dump_cfg_string(sAuthorizedKeysCommandUser, o->authorized_keys_command_user); |
2275 | dump_cfg_string(sAuthorizedPrincipalsCommand, o->authorized_principals_command); | ||
2276 | dump_cfg_string(sAuthorizedPrincipalsCommandUser, o->authorized_principals_command_user); | ||
2169 | dump_cfg_string(sHostKeyAgent, o->host_key_agent); | 2277 | dump_cfg_string(sHostKeyAgent, o->host_key_agent); |
2170 | dump_cfg_string(sKexAlgorithms, | 2278 | dump_cfg_string(sKexAlgorithms, |
2171 | o->kex_algorithms ? o->kex_algorithms : KEX_SERVER_KEX); | 2279 | o->kex_algorithms ? o->kex_algorithms : KEX_SERVER_KEX); |
@@ -2183,7 +2291,7 @@ dump_config(ServerOptions *o) | |||
2183 | o->authorized_keys_files); | 2291 | o->authorized_keys_files); |
2184 | dump_cfg_strarray(sHostKeyFile, o->num_host_key_files, | 2292 | dump_cfg_strarray(sHostKeyFile, o->num_host_key_files, |
2185 | o->host_key_files); | 2293 | o->host_key_files); |
2186 | dump_cfg_strarray(sHostKeyFile, o->num_host_cert_files, | 2294 | dump_cfg_strarray(sHostCertificate, o->num_host_cert_files, |
2187 | o->host_cert_files); | 2295 | o->host_cert_files); |
2188 | dump_cfg_strarray(sAllowUsers, o->num_allow_users, o->allow_users); | 2296 | dump_cfg_strarray(sAllowUsers, o->num_allow_users, o->allow_users); |
2189 | dump_cfg_strarray(sDenyUsers, o->num_deny_users, o->deny_users); | 2297 | dump_cfg_strarray(sDenyUsers, o->num_deny_users, o->deny_users); |