Home | History | Annotate | Download | only in openssh
      1 /* $OpenBSD: servconf.c,v 1.222 2011/06/22 21:57:01 djm Exp $ */
      2 /*
      3  * Copyright (c) 1995 Tatu Ylonen <ylo (at) cs.hut.fi>, Espoo, Finland
      4  *                    All rights reserved
      5  *
      6  * As far as I am concerned, the code I have written for this software
      7  * can be used freely for any purpose.  Any derived versions of this
      8  * software must be clearly marked as such, and if the derived work is
      9  * incompatible with the protocol description in the RFC file, it must be
     10  * called by a name other than "ssh" or "Secure Shell".
     11  */
     12 
     13 #include "includes.h"
     14 
     15 #include <sys/types.h>
     16 #include <sys/socket.h>
     17 
     18 #include <netinet/in.h>
     19 #include <netinet/in_systm.h>
     20 #include <netinet/ip.h>
     21 
     22 #include <netdb.h>
     23 #include <pwd.h>
     24 #include <stdio.h>
     25 #include <stdlib.h>
     26 #include <string.h>
     27 #include <signal.h>
     28 #include <unistd.h>
     29 #include <stdarg.h>
     30 #include <errno.h>
     31 
     32 #include "openbsd-compat/sys-queue.h"
     33 #include "xmalloc.h"
     34 #include "ssh.h"
     35 #include "log.h"
     36 #include "buffer.h"
     37 #include "servconf.h"
     38 #include "compat.h"
     39 #include "pathnames.h"
     40 #include "misc.h"
     41 #include "cipher.h"
     42 #include "key.h"
     43 #include "kex.h"
     44 #include "mac.h"
     45 #include "match.h"
     46 #include "channels.h"
     47 #include "groupaccess.h"
     48 
     49 #ifdef ANDROID
     50 #include <cutils/properties.h>
     51 #endif
     52 
     53 static void add_listen_addr(ServerOptions *, char *, int);
     54 static void add_one_listen_addr(ServerOptions *, char *, int);
     55 
     56 /* Use of privilege separation or not */
     57 extern int use_privsep;
     58 extern Buffer cfg;
     59 
     60 /* Initializes the server options to their default values. */
     61 
     62 void
     63 initialize_server_options(ServerOptions *options)
     64 {
     65 	memset(options, 0, sizeof(*options));
     66 
     67 	/* Portable-specific options */
     68 	options->use_pam = -1;
     69 
     70 	/* Standard Options */
     71 	options->num_ports = 0;
     72 	options->ports_from_cmdline = 0;
     73 	options->listen_addrs = NULL;
     74 	options->address_family = -1;
     75 	options->num_host_key_files = 0;
     76 	options->num_host_cert_files = 0;
     77 	options->pid_file = NULL;
     78 	options->server_key_bits = -1;
     79 	options->login_grace_time = -1;
     80 	options->key_regeneration_time = -1;
     81 	options->permit_root_login = PERMIT_NOT_SET;
     82 	options->ignore_rhosts = -1;
     83 	options->ignore_user_known_hosts = -1;
     84 	options->print_motd = -1;
     85 	options->print_lastlog = -1;
     86 	options->x11_forwarding = -1;
     87 	options->x11_display_offset = -1;
     88 	options->x11_use_localhost = -1;
     89 	options->xauth_location = NULL;
     90 	options->strict_modes = -1;
     91 	options->tcp_keep_alive = -1;
     92 	options->log_facility = SYSLOG_FACILITY_NOT_SET;
     93 	options->log_level = SYSLOG_LEVEL_NOT_SET;
     94 	options->rhosts_rsa_authentication = -1;
     95 	options->hostbased_authentication = -1;
     96 	options->hostbased_uses_name_from_packet_only = -1;
     97 	options->rsa_authentication = -1;
     98 	options->pubkey_authentication = -1;
     99 	options->kerberos_authentication = -1;
    100 	options->kerberos_or_local_passwd = -1;
    101 	options->kerberos_ticket_cleanup = -1;
    102 	options->kerberos_get_afs_token = -1;
    103 	options->gss_authentication=-1;
    104 	options->gss_cleanup_creds = -1;
    105 	options->password_authentication = -1;
    106 	options->kbd_interactive_authentication = -1;
    107 	options->challenge_response_authentication = -1;
    108 	options->permit_empty_passwd = -1;
    109 	options->permit_user_env = -1;
    110 	options->use_login = -1;
    111 	options->compression = -1;
    112 	options->allow_tcp_forwarding = -1;
    113 	options->allow_agent_forwarding = -1;
    114 	options->num_allow_users = 0;
    115 	options->num_deny_users = 0;
    116 	options->num_allow_groups = 0;
    117 	options->num_deny_groups = 0;
    118 	options->ciphers = NULL;
    119 	options->macs = NULL;
    120 	options->kex_algorithms = NULL;
    121 	options->protocol = SSH_PROTO_UNKNOWN;
    122 	options->gateway_ports = -1;
    123 	options->num_subsystems = 0;
    124 	options->max_startups_begin = -1;
    125 	options->max_startups_rate = -1;
    126 	options->max_startups = -1;
    127 	options->max_authtries = -1;
    128 	options->max_sessions = -1;
    129 	options->banner = NULL;
    130 	options->use_dns = -1;
    131 	options->client_alive_interval = -1;
    132 	options->client_alive_count_max = -1;
    133 	options->num_authkeys_files = 0;
    134 	options->num_accept_env = 0;
    135 	options->permit_tun = -1;
    136 	options->num_permitted_opens = -1;
    137 	options->adm_forced_command = NULL;
    138 	options->chroot_directory = NULL;
    139 	options->zero_knowledge_password_authentication = -1;
    140 	options->revoked_keys_file = NULL;
    141 	options->trusted_user_ca_keys = NULL;
    142 	options->authorized_principals_file = NULL;
    143 	options->ip_qos_interactive = -1;
    144 	options->ip_qos_bulk = -1;
    145 }
    146 
    147 void
    148 fill_default_server_options(ServerOptions *options)
    149 {
    150 	/* Portable-specific options */
    151 	if (options->use_pam == -1)
    152 		options->use_pam = 0;
    153 
    154 	/* Standard Options */
    155 	if (options->protocol == SSH_PROTO_UNKNOWN)
    156 		options->protocol = SSH_PROTO_2;
    157 	if (options->num_host_key_files == 0) {
    158 		/* fill default hostkeys for protocols */
    159 		if (options->protocol & SSH_PROTO_1)
    160 			options->host_key_files[options->num_host_key_files++] =
    161 			    _PATH_HOST_KEY_FILE;
    162 		if (options->protocol & SSH_PROTO_2) {
    163 			options->host_key_files[options->num_host_key_files++] =
    164 			    _PATH_HOST_RSA_KEY_FILE;
    165 			options->host_key_files[options->num_host_key_files++] =
    166 			    _PATH_HOST_DSA_KEY_FILE;
    167 #ifdef OPENSSL_HAS_ECC
    168 			options->host_key_files[options->num_host_key_files++] =
    169 			    _PATH_HOST_ECDSA_KEY_FILE;
    170 #endif
    171 		}
    172 	}
    173 	/* No certificates by default */
    174 	if (options->num_ports == 0)
    175 		options->ports[options->num_ports++] = SSH_DEFAULT_PORT;
    176 	if (options->listen_addrs == NULL)
    177 		add_listen_addr(options, NULL, 0);
    178 	if (options->pid_file == NULL)
    179 		options->pid_file = _PATH_SSH_DAEMON_PID_FILE;
    180 	if (options->server_key_bits == -1)
    181 		options->server_key_bits = 1024;
    182 	if (options->login_grace_time == -1)
    183 		options->login_grace_time = 120;
    184 	if (options->key_regeneration_time == -1)
    185 		options->key_regeneration_time = 3600;
    186 	if (options->permit_root_login == PERMIT_NOT_SET)
    187 		options->permit_root_login = PERMIT_YES;
    188 	if (options->ignore_rhosts == -1)
    189 		options->ignore_rhosts = 1;
    190 	if (options->ignore_user_known_hosts == -1)
    191 		options->ignore_user_known_hosts = 0;
    192 	if (options->print_motd == -1)
    193 		options->print_motd = 1;
    194 	if (options->print_lastlog == -1)
    195 		options->print_lastlog = 1;
    196 	if (options->x11_forwarding == -1)
    197 		options->x11_forwarding = 0;
    198 	if (options->x11_display_offset == -1)
    199 		options->x11_display_offset = 10;
    200 	if (options->x11_use_localhost == -1)
    201 		options->x11_use_localhost = 1;
    202 	if (options->xauth_location == NULL)
    203 		options->xauth_location = _PATH_XAUTH;
    204 	if (options->strict_modes == -1)
    205 		options->strict_modes = 1;
    206 	if (options->tcp_keep_alive == -1)
    207 		options->tcp_keep_alive = 1;
    208 	if (options->log_facility == SYSLOG_FACILITY_NOT_SET)
    209 		options->log_facility = SYSLOG_FACILITY_AUTH;
    210 	if (options->log_level == SYSLOG_LEVEL_NOT_SET)
    211 		options->log_level = SYSLOG_LEVEL_INFO;
    212 	if (options->rhosts_rsa_authentication == -1)
    213 		options->rhosts_rsa_authentication = 0;
    214 	if (options->hostbased_authentication == -1)
    215 		options->hostbased_authentication = 0;
    216 	if (options->hostbased_uses_name_from_packet_only == -1)
    217 		options->hostbased_uses_name_from_packet_only = 0;
    218 	if (options->rsa_authentication == -1)
    219 		options->rsa_authentication = 1;
    220 	if (options->pubkey_authentication == -1)
    221 		options->pubkey_authentication = 1;
    222 	if (options->kerberos_authentication == -1)
    223 		options->kerberos_authentication = 0;
    224 	if (options->kerberos_or_local_passwd == -1)
    225 		options->kerberos_or_local_passwd = 1;
    226 	if (options->kerberos_ticket_cleanup == -1)
    227 		options->kerberos_ticket_cleanup = 1;
    228 	if (options->kerberos_get_afs_token == -1)
    229 		options->kerberos_get_afs_token = 0;
    230 	if (options->gss_authentication == -1)
    231 		options->gss_authentication = 0;
    232 	if (options->gss_cleanup_creds == -1)
    233 		options->gss_cleanup_creds = 1;
    234 	if (options->password_authentication == -1)
    235 		options->password_authentication = 1;
    236 	if (options->kbd_interactive_authentication == -1)
    237 		options->kbd_interactive_authentication = 0;
    238 	if (options->challenge_response_authentication == -1)
    239 		options->challenge_response_authentication = 1;
    240 	if (options->permit_empty_passwd == -1)
    241 		options->permit_empty_passwd = 0;
    242 	if (options->permit_user_env == -1)
    243 		options->permit_user_env = 0;
    244 	if (options->use_login == -1)
    245 		options->use_login = 0;
    246 	if (options->compression == -1)
    247 		options->compression = COMP_DELAYED;
    248 	if (options->allow_tcp_forwarding == -1)
    249 		options->allow_tcp_forwarding = 1;
    250 	if (options->allow_agent_forwarding == -1)
    251 		options->allow_agent_forwarding = 1;
    252 	if (options->gateway_ports == -1)
    253 		options->gateway_ports = 0;
    254 	if (options->max_startups == -1)
    255 		options->max_startups = 10;
    256 	if (options->max_startups_rate == -1)
    257 		options->max_startups_rate = 100;		/* 100% */
    258 	if (options->max_startups_begin == -1)
    259 		options->max_startups_begin = options->max_startups;
    260 	if (options->max_authtries == -1)
    261 		options->max_authtries = DEFAULT_AUTH_FAIL_MAX;
    262 	if (options->max_sessions == -1)
    263 		options->max_sessions = DEFAULT_SESSIONS_MAX;
    264 	if (options->use_dns == -1)
    265 		options->use_dns = 1;
    266 	if (options->client_alive_interval == -1)
    267 		options->client_alive_interval = 0;
    268 	if (options->client_alive_count_max == -1)
    269 		options->client_alive_count_max = 3;
    270 	if (options->num_authkeys_files == 0) {
    271 		options->authorized_keys_files[options->num_authkeys_files++] =
    272 		    xstrdup(_PATH_SSH_USER_PERMITTED_KEYS);
    273 		options->authorized_keys_files[options->num_authkeys_files++] =
    274 		    xstrdup(_PATH_SSH_USER_PERMITTED_KEYS2);
    275 	}
    276 	if (options->permit_tun == -1)
    277 		options->permit_tun = SSH_TUNMODE_NO;
    278 	if (options->zero_knowledge_password_authentication == -1)
    279 		options->zero_knowledge_password_authentication = 0;
    280 	if (options->ip_qos_interactive == -1)
    281 		options->ip_qos_interactive = IPTOS_LOWDELAY;
    282 	if (options->ip_qos_bulk == -1)
    283 		options->ip_qos_bulk = IPTOS_THROUGHPUT;
    284 
    285 	/* Turn privilege separation on by default */
    286 	if (use_privsep == -1)
    287 		use_privsep = PRIVSEP_ON;
    288 
    289 #ifndef HAVE_MMAP
    290 	if (use_privsep && options->compression == 1) {
    291 		error("This platform does not support both privilege "
    292 		    "separation and compression");
    293 		error("Compression disabled");
    294 		options->compression = 0;
    295 	}
    296 #endif
    297 
    298 }
    299 
    300 /* Keyword tokens. */
    301 typedef enum {
    302 	sBadOption,		/* == unknown option */
    303 	/* Portable-specific options */
    304 	sUsePAM,
    305 	/* Standard Options */
    306 	sPort, sHostKeyFile, sServerKeyBits, sLoginGraceTime, sKeyRegenerationTime,
    307 	sPermitRootLogin, sLogFacility, sLogLevel,
    308 	sRhostsRSAAuthentication, sRSAAuthentication,
    309 	sKerberosAuthentication, sKerberosOrLocalPasswd, sKerberosTicketCleanup,
    310 	sKerberosGetAFSToken,
    311 	sKerberosTgtPassing, sChallengeResponseAuthentication,
    312 	sPasswordAuthentication, sKbdInteractiveAuthentication,
    313 	sListenAddress, sAddressFamily,
    314 	sPrintMotd, sPrintLastLog, sIgnoreRhosts,
    315 	sX11Forwarding, sX11DisplayOffset, sX11UseLocalhost,
    316 	sStrictModes, sEmptyPasswd, sTCPKeepAlive,
    317 	sPermitUserEnvironment, sUseLogin, sAllowTcpForwarding, sCompression,
    318 	sAllowUsers, sDenyUsers, sAllowGroups, sDenyGroups,
    319 	sIgnoreUserKnownHosts, sCiphers, sMacs, sProtocol, sPidFile,
    320 	sGatewayPorts, sPubkeyAuthentication, sXAuthLocation, sSubsystem,
    321 	sMaxStartups, sMaxAuthTries, sMaxSessions,
    322 	sBanner, sUseDNS, sHostbasedAuthentication,
    323 	sHostbasedUsesNameFromPacketOnly, sClientAliveInterval,
    324 	sClientAliveCountMax, sAuthorizedKeysFile,
    325 	sGssAuthentication, sGssCleanupCreds, sAcceptEnv, sPermitTunnel,
    326 	sMatch, sPermitOpen, sForceCommand, sChrootDirectory,
    327 	sUsePrivilegeSeparation, sAllowAgentForwarding,
    328 	sZeroKnowledgePasswordAuthentication, sHostCertificate,
    329 	sRevokedKeys, sTrustedUserCAKeys, sAuthorizedPrincipalsFile,
    330 	sKexAlgorithms, sIPQoS,
    331 	sDeprecated, sUnsupported
    332 } ServerOpCodes;
    333 
    334 #define SSHCFG_GLOBAL	0x01	/* allowed in main section of sshd_config */
    335 #define SSHCFG_MATCH	0x02	/* allowed inside a Match section */
    336 #define SSHCFG_ALL	(SSHCFG_GLOBAL|SSHCFG_MATCH)
    337 
    338 /* Textual representation of the tokens. */
    339 static struct {
    340 	const char *name;
    341 	ServerOpCodes opcode;
    342 	u_int flags;
    343 } keywords[] = {
    344 	/* Portable-specific options */
    345 #ifdef USE_PAM
    346 	{ "usepam", sUsePAM, SSHCFG_GLOBAL },
    347 #else
    348 	{ "usepam", sUnsupported, SSHCFG_GLOBAL },
    349 #endif
    350 	{ "pamauthenticationviakbdint", sDeprecated, SSHCFG_GLOBAL },
    351 	/* Standard Options */
    352 	{ "port", sPort, SSHCFG_GLOBAL },
    353 	{ "hostkey", sHostKeyFile, SSHCFG_GLOBAL },
    354 	{ "hostdsakey", sHostKeyFile, SSHCFG_GLOBAL },		/* alias */
    355 	{ "pidfile", sPidFile, SSHCFG_GLOBAL },
    356 	{ "serverkeybits", sServerKeyBits, SSHCFG_GLOBAL },
    357 	{ "logingracetime", sLoginGraceTime, SSHCFG_GLOBAL },
    358 	{ "keyregenerationinterval", sKeyRegenerationTime, SSHCFG_GLOBAL },
    359 	{ "permitrootlogin", sPermitRootLogin, SSHCFG_ALL },
    360 	{ "syslogfacility", sLogFacility, SSHCFG_GLOBAL },
    361 	{ "loglevel", sLogLevel, SSHCFG_GLOBAL },
    362 	{ "rhostsauthentication", sDeprecated, SSHCFG_GLOBAL },
    363 	{ "rhostsrsaauthentication", sRhostsRSAAuthentication, SSHCFG_ALL },
    364 	{ "hostbasedauthentication", sHostbasedAuthentication, SSHCFG_ALL },
    365 	{ "hostbasedusesnamefrompacketonly", sHostbasedUsesNameFromPacketOnly, SSHCFG_ALL },
    366 	{ "rsaauthentication", sRSAAuthentication, SSHCFG_ALL },
    367 	{ "pubkeyauthentication", sPubkeyAuthentication, SSHCFG_ALL },
    368 	{ "dsaauthentication", sPubkeyAuthentication, SSHCFG_GLOBAL }, /* alias */
    369 #ifdef KRB5
    370 	{ "kerberosauthentication", sKerberosAuthentication, SSHCFG_ALL },
    371 	{ "kerberosorlocalpasswd", sKerberosOrLocalPasswd, SSHCFG_GLOBAL },
    372 	{ "kerberosticketcleanup", sKerberosTicketCleanup, SSHCFG_GLOBAL },
    373 #ifdef USE_AFS
    374 	{ "kerberosgetafstoken", sKerberosGetAFSToken, SSHCFG_GLOBAL },
    375 #else
    376 	{ "kerberosgetafstoken", sUnsupported, SSHCFG_GLOBAL },
    377 #endif
    378 #else
    379 	{ "kerberosauthentication", sUnsupported, SSHCFG_ALL },
    380 	{ "kerberosorlocalpasswd", sUnsupported, SSHCFG_GLOBAL },
    381 	{ "kerberosticketcleanup", sUnsupported, SSHCFG_GLOBAL },
    382 	{ "kerberosgetafstoken", sUnsupported, SSHCFG_GLOBAL },
    383 #endif
    384 	{ "kerberostgtpassing", sUnsupported, SSHCFG_GLOBAL },
    385 	{ "afstokenpassing", sUnsupported, SSHCFG_GLOBAL },
    386 #ifdef GSSAPI
    387 	{ "gssapiauthentication", sGssAuthentication, SSHCFG_ALL },
    388 	{ "gssapicleanupcredentials", sGssCleanupCreds, SSHCFG_GLOBAL },
    389 #else
    390 	{ "gssapiauthentication", sUnsupported, SSHCFG_ALL },
    391 	{ "gssapicleanupcredentials", sUnsupported, SSHCFG_GLOBAL },
    392 #endif
    393 	{ "passwordauthentication", sPasswordAuthentication, SSHCFG_ALL },
    394 	{ "kbdinteractiveauthentication", sKbdInteractiveAuthentication, SSHCFG_ALL },
    395 	{ "challengeresponseauthentication", sChallengeResponseAuthentication, SSHCFG_GLOBAL },
    396 	{ "skeyauthentication", sChallengeResponseAuthentication, SSHCFG_GLOBAL }, /* alias */
    397 #ifdef JPAKE
    398 	{ "zeroknowledgepasswordauthentication", sZeroKnowledgePasswordAuthentication, SSHCFG_ALL },
    399 #else
    400 	{ "zeroknowledgepasswordauthentication", sUnsupported, SSHCFG_ALL },
    401 #endif
    402 	{ "checkmail", sDeprecated, SSHCFG_GLOBAL },
    403 	{ "listenaddress", sListenAddress, SSHCFG_GLOBAL },
    404 	{ "addressfamily", sAddressFamily, SSHCFG_GLOBAL },
    405 	{ "printmotd", sPrintMotd, SSHCFG_GLOBAL },
    406 	{ "printlastlog", sPrintLastLog, SSHCFG_GLOBAL },
    407 	{ "ignorerhosts", sIgnoreRhosts, SSHCFG_GLOBAL },
    408 	{ "ignoreuserknownhosts", sIgnoreUserKnownHosts, SSHCFG_GLOBAL },
    409 	{ "x11forwarding", sX11Forwarding, SSHCFG_ALL },
    410 	{ "x11displayoffset", sX11DisplayOffset, SSHCFG_ALL },
    411 	{ "x11uselocalhost", sX11UseLocalhost, SSHCFG_ALL },
    412 	{ "xauthlocation", sXAuthLocation, SSHCFG_GLOBAL },
    413 	{ "strictmodes", sStrictModes, SSHCFG_GLOBAL },
    414 	{ "permitemptypasswords", sEmptyPasswd, SSHCFG_ALL },
    415 	{ "permituserenvironment", sPermitUserEnvironment, SSHCFG_GLOBAL },
    416 	{ "uselogin", sUseLogin, SSHCFG_GLOBAL },
    417 	{ "compression", sCompression, SSHCFG_GLOBAL },
    418 	{ "tcpkeepalive", sTCPKeepAlive, SSHCFG_GLOBAL },
    419 	{ "keepalive", sTCPKeepAlive, SSHCFG_GLOBAL },	/* obsolete alias */
    420 	{ "allowtcpforwarding", sAllowTcpForwarding, SSHCFG_ALL },
    421 	{ "allowagentforwarding", sAllowAgentForwarding, SSHCFG_ALL },
    422 	{ "allowusers", sAllowUsers, SSHCFG_GLOBAL },
    423 	{ "denyusers", sDenyUsers, SSHCFG_GLOBAL },
    424 	{ "allowgroups", sAllowGroups, SSHCFG_GLOBAL },
    425 	{ "denygroups", sDenyGroups, SSHCFG_GLOBAL },
    426 	{ "ciphers", sCiphers, SSHCFG_GLOBAL },
    427 	{ "macs", sMacs, SSHCFG_GLOBAL },
    428 	{ "protocol", sProtocol, SSHCFG_GLOBAL },
    429 	{ "gatewayports", sGatewayPorts, SSHCFG_ALL },
    430 	{ "subsystem", sSubsystem, SSHCFG_GLOBAL },
    431 	{ "maxstartups", sMaxStartups, SSHCFG_GLOBAL },
    432 	{ "maxauthtries", sMaxAuthTries, SSHCFG_ALL },
    433 	{ "maxsessions", sMaxSessions, SSHCFG_ALL },
    434 	{ "banner", sBanner, SSHCFG_ALL },
    435 	{ "usedns", sUseDNS, SSHCFG_GLOBAL },
    436 	{ "verifyreversemapping", sDeprecated, SSHCFG_GLOBAL },
    437 	{ "reversemappingcheck", sDeprecated, SSHCFG_GLOBAL },
    438 	{ "clientaliveinterval", sClientAliveInterval, SSHCFG_GLOBAL },
    439 	{ "clientalivecountmax", sClientAliveCountMax, SSHCFG_GLOBAL },
    440 	{ "authorizedkeysfile", sAuthorizedKeysFile, SSHCFG_ALL },
    441 	{ "authorizedkeysfile2", sDeprecated, SSHCFG_ALL },
    442 	{ "useprivilegeseparation", sUsePrivilegeSeparation, SSHCFG_GLOBAL},
    443 	{ "acceptenv", sAcceptEnv, SSHCFG_GLOBAL },
    444 	{ "permittunnel", sPermitTunnel, SSHCFG_ALL },
    445 	{ "match", sMatch, SSHCFG_ALL },
    446 	{ "permitopen", sPermitOpen, SSHCFG_ALL },
    447 	{ "forcecommand", sForceCommand, SSHCFG_ALL },
    448 	{ "chrootdirectory", sChrootDirectory, SSHCFG_ALL },
    449 	{ "hostcertificate", sHostCertificate, SSHCFG_GLOBAL },
    450 	{ "revokedkeys", sRevokedKeys, SSHCFG_ALL },
    451 	{ "trustedusercakeys", sTrustedUserCAKeys, SSHCFG_ALL },
    452 	{ "authorizedprincipalsfile", sAuthorizedPrincipalsFile, SSHCFG_ALL },
    453 	{ "kexalgorithms", sKexAlgorithms, SSHCFG_GLOBAL },
    454 	{ "ipqos", sIPQoS, SSHCFG_ALL },
    455 	{ NULL, sBadOption, 0 }
    456 };
    457 
    458 static struct {
    459 	int val;
    460 	char *text;
    461 } tunmode_desc[] = {
    462 	{ SSH_TUNMODE_NO, "no" },
    463 	{ SSH_TUNMODE_POINTOPOINT, "point-to-point" },
    464 	{ SSH_TUNMODE_ETHERNET, "ethernet" },
    465 	{ SSH_TUNMODE_YES, "yes" },
    466 	{ -1, NULL }
    467 };
    468 
    469 /*
    470  * Returns the number of the token pointed to by cp or sBadOption.
    471  */
    472 
    473 static ServerOpCodes
    474 parse_token(const char *cp, const char *filename,
    475 	    int linenum, u_int *flags)
    476 {
    477 	u_int i;
    478 
    479 	for (i = 0; keywords[i].name; i++)
    480 		if (strcasecmp(cp, keywords[i].name) == 0) {
    481 			*flags = keywords[i].flags;
    482 			return keywords[i].opcode;
    483 		}
    484 
    485 	error("%s: line %d: Bad configuration option: %s",
    486 	    filename, linenum, cp);
    487 	return sBadOption;
    488 }
    489 
    490 char *
    491 derelativise_path(const char *path)
    492 {
    493 	char *expanded, *ret, cwd[MAXPATHLEN];
    494 
    495 	expanded = tilde_expand_filename(path, getuid());
    496 	if (*expanded == '/')
    497 		return expanded;
    498 	if (getcwd(cwd, sizeof(cwd)) == NULL)
    499 		fatal("%s: getcwd: %s", __func__, strerror(errno));
    500 	xasprintf(&ret, "%s/%s", cwd, expanded);
    501 	xfree(expanded);
    502 	return ret;
    503 }
    504 
    505 static void
    506 add_listen_addr(ServerOptions *options, char *addr, int port)
    507 {
    508 	u_int i;
    509 
    510 	if (options->num_ports == 0)
    511 		options->ports[options->num_ports++] = SSH_DEFAULT_PORT;
    512 	if (options->address_family == -1)
    513 		options->address_family = AF_UNSPEC;
    514 	if (port == 0)
    515 		for (i = 0; i < options->num_ports; i++)
    516 			add_one_listen_addr(options, addr, options->ports[i]);
    517 	else
    518 		add_one_listen_addr(options, addr, port);
    519 }
    520 
    521 static void
    522 add_one_listen_addr(ServerOptions *options, char *addr, int port)
    523 {
    524 	struct addrinfo hints, *ai, *aitop;
    525 	char strport[NI_MAXSERV];
    526 	int gaierr;
    527 
    528 	memset(&hints, 0, sizeof(hints));
    529 	hints.ai_family = options->address_family;
    530 	hints.ai_socktype = SOCK_STREAM;
    531 	hints.ai_flags = (addr == NULL) ? AI_PASSIVE : 0;
    532 	snprintf(strport, sizeof strport, "%d", port);
    533 	if ((gaierr = getaddrinfo(addr, strport, &hints, &aitop)) != 0)
    534 		fatal("bad addr or host: %s (%s)",
    535 		    addr ? addr : "<NULL>",
    536 		    ssh_gai_strerror(gaierr));
    537 	for (ai = aitop; ai->ai_next; ai = ai->ai_next)
    538 		;
    539 	ai->ai_next = options->listen_addrs;
    540 	options->listen_addrs = aitop;
    541 }
    542 
    543 /*
    544  * The strategy for the Match blocks is that the config file is parsed twice.
    545  *
    546  * The first time is at startup.  activep is initialized to 1 and the
    547  * directives in the global context are processed and acted on.  Hitting a
    548  * Match directive unsets activep and the directives inside the block are
    549  * checked for syntax only.
    550  *
    551  * The second time is after a connection has been established but before
    552  * authentication.  activep is initialized to 2 and global config directives
    553  * are ignored since they have already been processed.  If the criteria in a
    554  * Match block is met, activep is set and the subsequent directives
    555  * processed and actioned until EOF or another Match block unsets it.  Any
    556  * options set are copied into the main server config.
    557  *
    558  * Potential additions/improvements:
    559  *  - Add Match support for pre-kex directives, eg Protocol, Ciphers.
    560  *
    561  *  - Add a Tag directive (idea from David Leonard) ala pf, eg:
    562  *	Match Address 192.168.0.*
    563  *		Tag trusted
    564  *	Match Group wheel
    565  *		Tag trusted
    566  *	Match Tag trusted
    567  *		AllowTcpForwarding yes
    568  *		GatewayPorts clientspecified
    569  *		[...]
    570  *
    571  *  - Add a PermittedChannelRequests directive
    572  *	Match Group shell
    573  *		PermittedChannelRequests session,forwarded-tcpip
    574  */
    575 
    576 static int
    577 match_cfg_line_group(const char *grps, int line, const char *user)
    578 {
    579 	int result = 0;
    580 	struct passwd *pw;
    581 
    582 	if (user == NULL)
    583 		goto out;
    584 
    585 	if ((pw = getpwnam(user)) == NULL) {
    586 		debug("Can't match group at line %d because user %.100s does "
    587 		    "not exist", line, user);
    588 	} else if (ga_init(pw->pw_name, pw->pw_gid) == 0) {
    589 		debug("Can't Match group because user %.100s not in any group "
    590 		    "at line %d", user, line);
    591 	} else if (ga_match_pattern_list(grps) != 1) {
    592 		debug("user %.100s does not match group list %.100s at line %d",
    593 		    user, grps, line);
    594 	} else {
    595 		debug("user %.100s matched group list %.100s at line %d", user,
    596 		    grps, line);
    597 		result = 1;
    598 	}
    599 out:
    600 	ga_free();
    601 	return result;
    602 }
    603 
    604 static int
    605 match_cfg_line(char **condition, int line, const char *user, const char *host,
    606     const char *address)
    607 {
    608 	int result = 1;
    609 	char *arg, *attrib, *cp = *condition;
    610 	size_t len;
    611 
    612 	if (user == NULL)
    613 		debug3("checking syntax for 'Match %s'", cp);
    614 	else
    615 		debug3("checking match for '%s' user %s host %s addr %s", cp,
    616 		    user ? user : "(null)", host ? host : "(null)",
    617 		    address ? address : "(null)");
    618 
    619 	while ((attrib = strdelim(&cp)) && *attrib != '\0') {
    620 		if ((arg = strdelim(&cp)) == NULL || *arg == '\0') {
    621 			error("Missing Match criteria for %s", attrib);
    622 			return -1;
    623 		}
    624 		len = strlen(arg);
    625 		if (strcasecmp(attrib, "user") == 0) {
    626 			if (!user) {
    627 				result = 0;
    628 				continue;
    629 			}
    630 			if (match_pattern_list(user, arg, len, 0) != 1)
    631 				result = 0;
    632 			else
    633 				debug("user %.100s matched 'User %.100s' at "
    634 				    "line %d", user, arg, line);
    635 		} else if (strcasecmp(attrib, "group") == 0) {
    636 			switch (match_cfg_line_group(arg, line, user)) {
    637 			case -1:
    638 				return -1;
    639 			case 0:
    640 				result = 0;
    641 			}
    642 		} else if (strcasecmp(attrib, "host") == 0) {
    643 			if (!host) {
    644 				result = 0;
    645 				continue;
    646 			}
    647 			if (match_hostname(host, arg, len) != 1)
    648 				result = 0;
    649 			else
    650 				debug("connection from %.100s matched 'Host "
    651 				    "%.100s' at line %d", host, arg, line);
    652 		} else if (strcasecmp(attrib, "address") == 0) {
    653 			switch (addr_match_list(address, arg)) {
    654 			case 1:
    655 				debug("connection from %.100s matched 'Address "
    656 				    "%.100s' at line %d", address, arg, line);
    657 				break;
    658 			case 0:
    659 			case -1:
    660 				result = 0;
    661 				break;
    662 			case -2:
    663 				return -1;
    664 			}
    665 		} else {
    666 			error("Unsupported Match attribute %s", attrib);
    667 			return -1;
    668 		}
    669 	}
    670 	if (user != NULL)
    671 		debug3("match %sfound", result ? "" : "not ");
    672 	*condition = cp;
    673 	return result;
    674 }
    675 
    676 #define WHITESPACE " \t\r\n"
    677 
    678 /* Multistate option parsing */
    679 struct multistate {
    680 	char *key;
    681 	int value;
    682 };
    683 static const struct multistate multistate_addressfamily[] = {
    684 	{ "inet",			AF_INET },
    685 	{ "inet6",			AF_INET6 },
    686 	{ "any",			AF_UNSPEC },
    687 	{ NULL, -1 }
    688 };
    689 static const struct multistate multistate_permitrootlogin[] = {
    690 	{ "without-password",		PERMIT_NO_PASSWD },
    691 	{ "forced-commands-only",	PERMIT_FORCED_ONLY },
    692 	{ "yes",			PERMIT_YES },
    693 	{ "no",				PERMIT_NO },
    694 	{ NULL, -1 }
    695 };
    696 static const struct multistate multistate_compression[] = {
    697 	{ "delayed",			COMP_DELAYED },
    698 	{ "yes",			COMP_ZLIB },
    699 	{ "no",				COMP_NONE },
    700 	{ NULL, -1 }
    701 };
    702 static const struct multistate multistate_gatewayports[] = {
    703 	{ "clientspecified",		2 },
    704 	{ "yes",			1 },
    705 	{ "no",				0 },
    706 	{ NULL, -1 }
    707 };
    708 static const struct multistate multistate_privsep[] = {
    709 	{ "sandbox",			PRIVSEP_SANDBOX },
    710 	{ "yes",			PRIVSEP_ON },
    711 	{ "no",				PRIVSEP_OFF },
    712 	{ NULL, -1 }
    713 };
    714 
    715 int
    716 process_server_config_line(ServerOptions *options, char *line,
    717     const char *filename, int linenum, int *activep, const char *user,
    718     const char *host, const char *address)
    719 {
    720 	char *cp, **charptr, *arg, *p;
    721 	int cmdline = 0, *intptr, value, value2, n;
    722 	SyslogFacility *log_facility_ptr;
    723 	LogLevel *log_level_ptr;
    724 	ServerOpCodes opcode;
    725 	int port;
    726 	u_int i, flags = 0;
    727 	size_t len;
    728 	const struct multistate *multistate_ptr;
    729 
    730 	cp = line;
    731 	if ((arg = strdelim(&cp)) == NULL)
    732 		return 0;
    733 	/* Ignore leading whitespace */
    734 	if (*arg == '\0')
    735 		arg = strdelim(&cp);
    736 	if (!arg || !*arg || *arg == '#')
    737 		return 0;
    738 	intptr = NULL;
    739 	charptr = NULL;
    740 	opcode = parse_token(arg, filename, linenum, &flags);
    741 
    742 	if (activep == NULL) { /* We are processing a command line directive */
    743 		cmdline = 1;
    744 		activep = &cmdline;
    745 	}
    746 	if (*activep && opcode != sMatch)
    747 		debug3("%s:%d setting %s %s", filename, linenum, arg, cp);
    748 	if (*activep == 0 && !(flags & SSHCFG_MATCH)) {
    749 		if (user == NULL) {
    750 			fatal("%s line %d: Directive '%s' is not allowed "
    751 			    "within a Match block", filename, linenum, arg);
    752 		} else { /* this is a directive we have already processed */
    753 			while (arg)
    754 				arg = strdelim(&cp);
    755 			return 0;
    756 		}
    757 	}
    758 
    759 	switch (opcode) {
    760 	/* Portable-specific options */
    761 	case sUsePAM:
    762 		intptr = &options->use_pam;
    763 		goto parse_flag;
    764 
    765 	/* Standard Options */
    766 	case sBadOption:
    767 		return -1;
    768 	case sPort:
    769 		/* ignore ports from configfile if cmdline specifies ports */
    770 		if (options->ports_from_cmdline)
    771 			return 0;
    772 		if (options->listen_addrs != NULL)
    773 			fatal("%s line %d: ports must be specified before "
    774 			    "ListenAddress.", filename, linenum);
    775 		if (options->num_ports >= MAX_PORTS)
    776 			fatal("%s line %d: too many ports.",
    777 			    filename, linenum);
    778 		arg = strdelim(&cp);
    779 		if (!arg || *arg == '\0')
    780 			fatal("%s line %d: missing port number.",
    781 			    filename, linenum);
    782 		options->ports[options->num_ports++] = a2port(arg);
    783 		if (options->ports[options->num_ports-1] <= 0)
    784 			fatal("%s line %d: Badly formatted port number.",
    785 			    filename, linenum);
    786 		break;
    787 
    788 	case sServerKeyBits:
    789 		intptr = &options->server_key_bits;
    790  parse_int:
    791 		arg = strdelim(&cp);
    792 		if (!arg || *arg == '\0')
    793 			fatal("%s line %d: missing integer value.",
    794 			    filename, linenum);
    795 		value = atoi(arg);
    796 		if (*activep && *intptr == -1)
    797 			*intptr = value;
    798 		break;
    799 
    800 	case sLoginGraceTime:
    801 		intptr = &options->login_grace_time;
    802  parse_time:
    803 		arg = strdelim(&cp);
    804 		if (!arg || *arg == '\0')
    805 			fatal("%s line %d: missing time value.",
    806 			    filename, linenum);
    807 		if ((value = convtime(arg)) == -1)
    808 			fatal("%s line %d: invalid time value.",
    809 			    filename, linenum);
    810 		if (*intptr == -1)
    811 			*intptr = value;
    812 		break;
    813 
    814 	case sKeyRegenerationTime:
    815 		intptr = &options->key_regeneration_time;
    816 		goto parse_time;
    817 
    818 	case sListenAddress:
    819 		arg = strdelim(&cp);
    820 		if (arg == NULL || *arg == '\0')
    821 			fatal("%s line %d: missing address",
    822 			    filename, linenum);
    823 		/* check for bare IPv6 address: no "[]" and 2 or more ":" */
    824 		if (strchr(arg, '[') == NULL && (p = strchr(arg, ':')) != NULL
    825 		    && strchr(p+1, ':') != NULL) {
    826 			add_listen_addr(options, arg, 0);
    827 			break;
    828 		}
    829 		p = hpdelim(&arg);
    830 		if (p == NULL)
    831 			fatal("%s line %d: bad address:port usage",
    832 			    filename, linenum);
    833 		p = cleanhostname(p);
    834 		if (arg == NULL)
    835 			port = 0;
    836 		else if ((port = a2port(arg)) <= 0)
    837 			fatal("%s line %d: bad port number", filename, linenum);
    838 
    839 		add_listen_addr(options, p, port);
    840 
    841 		break;
    842 
    843 	case sAddressFamily:
    844 		intptr = &options->address_family;
    845 		multistate_ptr = multistate_addressfamily;
    846 		if (options->listen_addrs != NULL)
    847 			fatal("%s line %d: address family must be specified "
    848 			    "before ListenAddress.", filename, linenum);
    849  parse_multistate:
    850 		arg = strdelim(&cp);
    851 		if (!arg || *arg == '\0')
    852 			fatal("%s line %d: missing argument.",
    853 			    filename, linenum);
    854 		value = -1;
    855 		for (i = 0; multistate_ptr[i].key != NULL; i++) {
    856 			if (strcasecmp(arg, multistate_ptr[i].key) == 0) {
    857 				value = multistate_ptr[i].value;
    858 				break;
    859 			}
    860 		}
    861 		if (value == -1)
    862 			fatal("%s line %d: unsupported option \"%s\".",
    863 			    filename, linenum, arg);
    864 		if (*activep && *intptr == -1)
    865 			*intptr = value;
    866 		break;
    867 
    868 	case sHostKeyFile:
    869 		intptr = &options->num_host_key_files;
    870 		if (*intptr >= MAX_HOSTKEYS)
    871 			fatal("%s line %d: too many host keys specified (max %d).",
    872 			    filename, linenum, MAX_HOSTKEYS);
    873 		charptr = &options->host_key_files[*intptr];
    874  parse_filename:
    875 		arg = strdelim(&cp);
    876 		if (!arg || *arg == '\0')
    877 			fatal("%s line %d: missing file name.",
    878 			    filename, linenum);
    879 		if (*activep && *charptr == NULL) {
    880 			*charptr = derelativise_path(arg);
    881 			/* increase optional counter */
    882 			if (intptr != NULL)
    883 				*intptr = *intptr + 1;
    884 		}
    885 		break;
    886 
    887 	case sHostCertificate:
    888 		intptr = &options->num_host_cert_files;
    889 		if (*intptr >= MAX_HOSTKEYS)
    890 			fatal("%s line %d: too many host certificates "
    891 			    "specified (max %d).", filename, linenum,
    892 			    MAX_HOSTCERTS);
    893 		charptr = &options->host_cert_files[*intptr];
    894 		goto parse_filename;
    895 		break;
    896 
    897 	case sPidFile:
    898 		charptr = &options->pid_file;
    899 		goto parse_filename;
    900 
    901 	case sPermitRootLogin:
    902 		intptr = &options->permit_root_login;
    903 		multistate_ptr = multistate_permitrootlogin;
    904 		goto parse_multistate;
    905 
    906 	case sIgnoreRhosts:
    907 		intptr = &options->ignore_rhosts;
    908  parse_flag:
    909 		arg = strdelim(&cp);
    910 		if (!arg || *arg == '\0')
    911 			fatal("%s line %d: missing yes/no argument.",
    912 			    filename, linenum);
    913 		value = 0;	/* silence compiler */
    914 		if (strcmp(arg, "yes") == 0)
    915 			value = 1;
    916 		else if (strcmp(arg, "no") == 0)
    917 			value = 0;
    918 		else
    919 			fatal("%s line %d: Bad yes/no argument: %s",
    920 				filename, linenum, arg);
    921 		if (*activep && *intptr == -1)
    922 			*intptr = value;
    923 		break;
    924 
    925 	case sIgnoreUserKnownHosts:
    926 		intptr = &options->ignore_user_known_hosts;
    927 		goto parse_flag;
    928 
    929 	case sRhostsRSAAuthentication:
    930 		intptr = &options->rhosts_rsa_authentication;
    931 		goto parse_flag;
    932 
    933 	case sHostbasedAuthentication:
    934 		intptr = &options->hostbased_authentication;
    935 		goto parse_flag;
    936 
    937 	case sHostbasedUsesNameFromPacketOnly:
    938 		intptr = &options->hostbased_uses_name_from_packet_only;
    939 		goto parse_flag;
    940 
    941 	case sRSAAuthentication:
    942 		intptr = &options->rsa_authentication;
    943 		goto parse_flag;
    944 
    945 	case sPubkeyAuthentication:
    946 		intptr = &options->pubkey_authentication;
    947 		goto parse_flag;
    948 
    949 	case sKerberosAuthentication:
    950 		intptr = &options->kerberos_authentication;
    951 		goto parse_flag;
    952 
    953 	case sKerberosOrLocalPasswd:
    954 		intptr = &options->kerberos_or_local_passwd;
    955 		goto parse_flag;
    956 
    957 	case sKerberosTicketCleanup:
    958 		intptr = &options->kerberos_ticket_cleanup;
    959 		goto parse_flag;
    960 
    961 	case sKerberosGetAFSToken:
    962 		intptr = &options->kerberos_get_afs_token;
    963 		goto parse_flag;
    964 
    965 	case sGssAuthentication:
    966 		intptr = &options->gss_authentication;
    967 		goto parse_flag;
    968 
    969 	case sGssCleanupCreds:
    970 		intptr = &options->gss_cleanup_creds;
    971 		goto parse_flag;
    972 
    973 	case sPasswordAuthentication:
    974 		intptr = &options->password_authentication;
    975 		goto parse_flag;
    976 
    977 	case sZeroKnowledgePasswordAuthentication:
    978 		intptr = &options->zero_knowledge_password_authentication;
    979 		goto parse_flag;
    980 
    981 	case sKbdInteractiveAuthentication:
    982 		intptr = &options->kbd_interactive_authentication;
    983 		goto parse_flag;
    984 
    985 	case sChallengeResponseAuthentication:
    986 		intptr = &options->challenge_response_authentication;
    987 		goto parse_flag;
    988 
    989 	case sPrintMotd:
    990 		intptr = &options->print_motd;
    991 		goto parse_flag;
    992 
    993 	case sPrintLastLog:
    994 		intptr = &options->print_lastlog;
    995 		goto parse_flag;
    996 
    997 	case sX11Forwarding:
    998 		intptr = &options->x11_forwarding;
    999 		goto parse_flag;
   1000 
   1001 	case sX11DisplayOffset:
   1002 		intptr = &options->x11_display_offset;
   1003 		goto parse_int;
   1004 
   1005 	case sX11UseLocalhost:
   1006 		intptr = &options->x11_use_localhost;
   1007 		goto parse_flag;
   1008 
   1009 	case sXAuthLocation:
   1010 		charptr = &options->xauth_location;
   1011 		goto parse_filename;
   1012 
   1013 	case sStrictModes:
   1014 		intptr = &options->strict_modes;
   1015 		goto parse_flag;
   1016 
   1017 	case sTCPKeepAlive:
   1018 		intptr = &options->tcp_keep_alive;
   1019 		goto parse_flag;
   1020 
   1021 	case sEmptyPasswd:
   1022 		intptr = &options->permit_empty_passwd;
   1023 		goto parse_flag;
   1024 
   1025 	case sPermitUserEnvironment:
   1026 		intptr = &options->permit_user_env;
   1027 		goto parse_flag;
   1028 
   1029 	case sUseLogin:
   1030 		intptr = &options->use_login;
   1031 		goto parse_flag;
   1032 
   1033 	case sCompression:
   1034 		intptr = &options->compression;
   1035 		multistate_ptr = multistate_compression;
   1036 		goto parse_multistate;
   1037 
   1038 	case sGatewayPorts:
   1039 		intptr = &options->gateway_ports;
   1040 		multistate_ptr = multistate_gatewayports;
   1041 		goto parse_multistate;
   1042 
   1043 	case sUseDNS:
   1044 		intptr = &options->use_dns;
   1045 		goto parse_flag;
   1046 
   1047 	case sLogFacility:
   1048 		log_facility_ptr = &options->log_facility;
   1049 		arg = strdelim(&cp);
   1050 		value = log_facility_number(arg);
   1051 		if (value == SYSLOG_FACILITY_NOT_SET)
   1052 			fatal("%.200s line %d: unsupported log facility '%s'",
   1053 			    filename, linenum, arg ? arg : "<NONE>");
   1054 		if (*log_facility_ptr == -1)
   1055 			*log_facility_ptr = (SyslogFacility) value;
   1056 		break;
   1057 
   1058 	case sLogLevel:
   1059 		log_level_ptr = &options->log_level;
   1060 		arg = strdelim(&cp);
   1061 		value = log_level_number(arg);
   1062 		if (value == SYSLOG_LEVEL_NOT_SET)
   1063 			fatal("%.200s line %d: unsupported log level '%s'",
   1064 			    filename, linenum, arg ? arg : "<NONE>");
   1065 		if (*log_level_ptr == -1)
   1066 			*log_level_ptr = (LogLevel) value;
   1067 		break;
   1068 
   1069 	case sAllowTcpForwarding:
   1070 		intptr = &options->allow_tcp_forwarding;
   1071 		goto parse_flag;
   1072 
   1073 	case sAllowAgentForwarding:
   1074 		intptr = &options->allow_agent_forwarding;
   1075 		goto parse_flag;
   1076 
   1077 	case sUsePrivilegeSeparation:
   1078 		intptr = &use_privsep;
   1079 		multistate_ptr = multistate_privsep;
   1080 		goto parse_multistate;
   1081 
   1082 	case sAllowUsers:
   1083 		while ((arg = strdelim(&cp)) && *arg != '\0') {
   1084 			if (options->num_allow_users >= MAX_ALLOW_USERS)
   1085 				fatal("%s line %d: too many allow users.",
   1086 				    filename, linenum);
   1087 			options->allow_users[options->num_allow_users++] =
   1088 			    xstrdup(arg);
   1089 		}
   1090 		break;
   1091 
   1092 	case sDenyUsers:
   1093 		while ((arg = strdelim(&cp)) && *arg != '\0') {
   1094 			if (options->num_deny_users >= MAX_DENY_USERS)
   1095 				fatal("%s line %d: too many deny users.",
   1096 				    filename, linenum);
   1097 			options->deny_users[options->num_deny_users++] =
   1098 			    xstrdup(arg);
   1099 		}
   1100 		break;
   1101 
   1102 	case sAllowGroups:
   1103 		while ((arg = strdelim(&cp)) && *arg != '\0') {
   1104 			if (options->num_allow_groups >= MAX_ALLOW_GROUPS)
   1105 				fatal("%s line %d: too many allow groups.",
   1106 				    filename, linenum);
   1107 			options->allow_groups[options->num_allow_groups++] =
   1108 			    xstrdup(arg);
   1109 		}
   1110 		break;
   1111 
   1112 	case sDenyGroups:
   1113 		while ((arg = strdelim(&cp)) && *arg != '\0') {
   1114 			if (options->num_deny_groups >= MAX_DENY_GROUPS)
   1115 				fatal("%s line %d: too many deny groups.",
   1116 				    filename, linenum);
   1117 			options->deny_groups[options->num_deny_groups++] = xstrdup(arg);
   1118 		}
   1119 		break;
   1120 
   1121 	case sCiphers:
   1122 		arg = strdelim(&cp);
   1123 		if (!arg || *arg == '\0')
   1124 			fatal("%s line %d: Missing argument.", filename, linenum);
   1125 		if (!ciphers_valid(arg))
   1126 			fatal("%s line %d: Bad SSH2 cipher spec '%s'.",
   1127 			    filename, linenum, arg ? arg : "<NONE>");
   1128 		if (options->ciphers == NULL)
   1129 			options->ciphers = xstrdup(arg);
   1130 		break;
   1131 
   1132 	case sMacs:
   1133 		arg = strdelim(&cp);
   1134 		if (!arg || *arg == '\0')
   1135 			fatal("%s line %d: Missing argument.", filename, linenum);
   1136 		if (!mac_valid(arg))
   1137 			fatal("%s line %d: Bad SSH2 mac spec '%s'.",
   1138 			    filename, linenum, arg ? arg : "<NONE>");
   1139 		if (options->macs == NULL)
   1140 			options->macs = xstrdup(arg);
   1141 		break;
   1142 
   1143 	case sKexAlgorithms:
   1144 		arg = strdelim(&cp);
   1145 		if (!arg || *arg == '\0')
   1146 			fatal("%s line %d: Missing argument.",
   1147 			    filename, linenum);
   1148 		if (!kex_names_valid(arg))
   1149 			fatal("%s line %d: Bad SSH2 KexAlgorithms '%s'.",
   1150 			    filename, linenum, arg ? arg : "<NONE>");
   1151 		if (options->kex_algorithms == NULL)
   1152 			options->kex_algorithms = xstrdup(arg);
   1153 		break;
   1154 
   1155 	case sProtocol:
   1156 		intptr = &options->protocol;
   1157 		arg = strdelim(&cp);
   1158 		if (!arg || *arg == '\0')
   1159 			fatal("%s line %d: Missing argument.", filename, linenum);
   1160 		value = proto_spec(arg);
   1161 		if (value == SSH_PROTO_UNKNOWN)
   1162 			fatal("%s line %d: Bad protocol spec '%s'.",
   1163 			    filename, linenum, arg ? arg : "<NONE>");
   1164 		if (*intptr == SSH_PROTO_UNKNOWN)
   1165 			*intptr = value;
   1166 		break;
   1167 
   1168 	case sSubsystem:
   1169 		if (options->num_subsystems >= MAX_SUBSYSTEMS) {
   1170 			fatal("%s line %d: too many subsystems defined.",
   1171 			    filename, linenum);
   1172 		}
   1173 		arg = strdelim(&cp);
   1174 		if (!arg || *arg == '\0')
   1175 			fatal("%s line %d: Missing subsystem name.",
   1176 			    filename, linenum);
   1177 		if (!*activep) {
   1178 			arg = strdelim(&cp);
   1179 			break;
   1180 		}
   1181 		for (i = 0; i < options->num_subsystems; i++)
   1182 			if (strcmp(arg, options->subsystem_name[i]) == 0)
   1183 				fatal("%s line %d: Subsystem '%s' already defined.",
   1184 				    filename, linenum, arg);
   1185 		options->subsystem_name[options->num_subsystems] = xstrdup(arg);
   1186 		arg = strdelim(&cp);
   1187 		if (!arg || *arg == '\0')
   1188 			fatal("%s line %d: Missing subsystem command.",
   1189 			    filename, linenum);
   1190 		options->subsystem_command[options->num_subsystems] = xstrdup(arg);
   1191 
   1192 		/* Collect arguments (separate to executable) */
   1193 		p = xstrdup(arg);
   1194 		len = strlen(p) + 1;
   1195 		while ((arg = strdelim(&cp)) != NULL && *arg != '\0') {
   1196 			len += 1 + strlen(arg);
   1197 			p = xrealloc(p, 1, len);
   1198 			strlcat(p, " ", len);
   1199 			strlcat(p, arg, len);
   1200 		}
   1201 		options->subsystem_args[options->num_subsystems] = p;
   1202 		options->num_subsystems++;
   1203 		break;
   1204 
   1205 	case sMaxStartups:
   1206 		arg = strdelim(&cp);
   1207 		if (!arg || *arg == '\0')
   1208 			fatal("%s line %d: Missing MaxStartups spec.",
   1209 			    filename, linenum);
   1210 		if ((n = sscanf(arg, "%d:%d:%d",
   1211 		    &options->max_startups_begin,
   1212 		    &options->max_startups_rate,
   1213 		    &options->max_startups)) == 3) {
   1214 			if (options->max_startups_begin >
   1215 			    options->max_startups ||
   1216 			    options->max_startups_rate > 100 ||
   1217 			    options->max_startups_rate < 1)
   1218 				fatal("%s line %d: Illegal MaxStartups spec.",
   1219 				    filename, linenum);
   1220 		} else if (n != 1)
   1221 			fatal("%s line %d: Illegal MaxStartups spec.",
   1222 			    filename, linenum);
   1223 		else
   1224 			options->max_startups = options->max_startups_begin;
   1225 		break;
   1226 
   1227 	case sMaxAuthTries:
   1228 		intptr = &options->max_authtries;
   1229 		goto parse_int;
   1230 
   1231 	case sMaxSessions:
   1232 		intptr = &options->max_sessions;
   1233 		goto parse_int;
   1234 
   1235 	case sBanner:
   1236 		charptr = &options->banner;
   1237 		goto parse_filename;
   1238 
   1239 	/*
   1240 	 * These options can contain %X options expanded at
   1241 	 * connect time, so that you can specify paths like:
   1242 	 *
   1243 	 * AuthorizedKeysFile	/etc/ssh_keys/%u
   1244 	 */
   1245 	case sAuthorizedKeysFile:
   1246 		if (*activep && options->num_authkeys_files == 0) {
   1247 			while ((arg = strdelim(&cp)) && *arg != '\0') {
   1248 				if (options->num_authkeys_files >=
   1249 				    MAX_AUTHKEYS_FILES)
   1250 					fatal("%s line %d: "
   1251 					    "too many authorized keys files.",
   1252 					    filename, linenum);
   1253 				options->authorized_keys_files[
   1254 				    options->num_authkeys_files++] =
   1255 				    tilde_expand_filename(arg, getuid());
   1256 			}
   1257 		}
   1258 		return 0;
   1259 
   1260 	case sAuthorizedPrincipalsFile:
   1261 		charptr = &options->authorized_principals_file;
   1262 		arg = strdelim(&cp);
   1263 		if (!arg || *arg == '\0')
   1264 			fatal("%s line %d: missing file name.",
   1265 			    filename, linenum);
   1266 		if (*activep && *charptr == NULL) {
   1267 			*charptr = tilde_expand_filename(arg, getuid());
   1268 			/* increase optional counter */
   1269 			if (intptr != NULL)
   1270 				*intptr = *intptr + 1;
   1271 		}
   1272 		break;
   1273 
   1274 	case sClientAliveInterval:
   1275 		intptr = &options->client_alive_interval;
   1276 		goto parse_time;
   1277 
   1278 	case sClientAliveCountMax:
   1279 		intptr = &options->client_alive_count_max;
   1280 		goto parse_int;
   1281 
   1282 	case sAcceptEnv:
   1283 		while ((arg = strdelim(&cp)) && *arg != '\0') {
   1284 			if (strchr(arg, '=') != NULL)
   1285 				fatal("%s line %d: Invalid environment name.",
   1286 				    filename, linenum);
   1287 			if (options->num_accept_env >= MAX_ACCEPT_ENV)
   1288 				fatal("%s line %d: too many allow env.",
   1289 				    filename, linenum);
   1290 			if (!*activep)
   1291 				break;
   1292 			options->accept_env[options->num_accept_env++] =
   1293 			    xstrdup(arg);
   1294 		}
   1295 		break;
   1296 
   1297 	case sPermitTunnel:
   1298 		intptr = &options->permit_tun;
   1299 		arg = strdelim(&cp);
   1300 		if (!arg || *arg == '\0')
   1301 			fatal("%s line %d: Missing yes/point-to-point/"
   1302 			    "ethernet/no argument.", filename, linenum);
   1303 		value = -1;
   1304 		for (i = 0; tunmode_desc[i].val != -1; i++)
   1305 			if (strcmp(tunmode_desc[i].text, arg) == 0) {
   1306 				value = tunmode_desc[i].val;
   1307 				break;
   1308 			}
   1309 		if (value == -1)
   1310 			fatal("%s line %d: Bad yes/point-to-point/ethernet/"
   1311 			    "no argument: %s", filename, linenum, arg);
   1312 		if (*intptr == -1)
   1313 			*intptr = value;
   1314 		break;
   1315 
   1316 	case sMatch:
   1317 		if (cmdline)
   1318 			fatal("Match directive not supported as a command-line "
   1319 			   "option");
   1320 		value = match_cfg_line(&cp, linenum, user, host, address);
   1321 		if (value < 0)
   1322 			fatal("%s line %d: Bad Match condition", filename,
   1323 			    linenum);
   1324 		*activep = value;
   1325 		break;
   1326 
   1327 	case sPermitOpen:
   1328 		arg = strdelim(&cp);
   1329 		if (!arg || *arg == '\0')
   1330 			fatal("%s line %d: missing PermitOpen specification",
   1331 			    filename, linenum);
   1332 		n = options->num_permitted_opens;	/* modified later */
   1333 		if (strcmp(arg, "any") == 0) {
   1334 			if (*activep && n == -1) {
   1335 				channel_clear_adm_permitted_opens();
   1336 				options->num_permitted_opens = 0;
   1337 			}
   1338 			break;
   1339 		}
   1340 		if (*activep && n == -1)
   1341 			channel_clear_adm_permitted_opens();
   1342 		for (; arg != NULL && *arg != '\0'; arg = strdelim(&cp)) {
   1343 			p = hpdelim(&arg);
   1344 			if (p == NULL)
   1345 				fatal("%s line %d: missing host in PermitOpen",
   1346 				    filename, linenum);
   1347 			p = cleanhostname(p);
   1348 			if (arg == NULL || (port = a2port(arg)) <= 0)
   1349 				fatal("%s line %d: bad port number in "
   1350 				    "PermitOpen", filename, linenum);
   1351 			if (*activep && n == -1)
   1352 				options->num_permitted_opens =
   1353 				    channel_add_adm_permitted_opens(p, port);
   1354 		}
   1355 		break;
   1356 
   1357 	case sForceCommand:
   1358 		if (cp == NULL)
   1359 			fatal("%.200s line %d: Missing argument.", filename,
   1360 			    linenum);
   1361 		len = strspn(cp, WHITESPACE);
   1362 		if (*activep && options->adm_forced_command == NULL)
   1363 			options->adm_forced_command = xstrdup(cp + len);
   1364 		return 0;
   1365 
   1366 	case sChrootDirectory:
   1367 		charptr = &options->chroot_directory;
   1368 
   1369 		arg = strdelim(&cp);
   1370 		if (!arg || *arg == '\0')
   1371 			fatal("%s line %d: missing file name.",
   1372 			    filename, linenum);
   1373 		if (*activep && *charptr == NULL)
   1374 			*charptr = xstrdup(arg);
   1375 		break;
   1376 
   1377 	case sTrustedUserCAKeys:
   1378 		charptr = &options->trusted_user_ca_keys;
   1379 		goto parse_filename;
   1380 
   1381 	case sRevokedKeys:
   1382 		charptr = &options->revoked_keys_file;
   1383 		goto parse_filename;
   1384 
   1385 	case sIPQoS:
   1386 		arg = strdelim(&cp);
   1387 		if ((value = parse_ipqos(arg)) == -1)
   1388 			fatal("%s line %d: Bad IPQoS value: %s",
   1389 			    filename, linenum, arg);
   1390 		arg = strdelim(&cp);
   1391 		if (arg == NULL)
   1392 			value2 = value;
   1393 		else if ((value2 = parse_ipqos(arg)) == -1)
   1394 			fatal("%s line %d: Bad IPQoS value: %s",
   1395 			    filename, linenum, arg);
   1396 		if (*activep) {
   1397 			options->ip_qos_interactive = value;
   1398 			options->ip_qos_bulk = value2;
   1399 		}
   1400 		break;
   1401 
   1402 	case sDeprecated:
   1403 		logit("%s line %d: Deprecated option %s",
   1404 		    filename, linenum, arg);
   1405 		while (arg)
   1406 		    arg = strdelim(&cp);
   1407 		break;
   1408 
   1409 	case sUnsupported:
   1410 		logit("%s line %d: Unsupported option %s",
   1411 		    filename, linenum, arg);
   1412 		while (arg)
   1413 		    arg = strdelim(&cp);
   1414 		break;
   1415 
   1416 	default:
   1417 		fatal("%s line %d: Missing handler for opcode %s (%d)",
   1418 		    filename, linenum, arg, opcode);
   1419 	}
   1420 	if ((arg = strdelim(&cp)) != NULL && *arg != '\0')
   1421 		fatal("%s line %d: garbage at end of line; \"%.200s\".",
   1422 		    filename, linenum, arg);
   1423 	return 0;
   1424 }
   1425 
   1426 /* Reads the server configuration file. */
   1427 
   1428 void
   1429 load_server_config(const char *filename, Buffer *conf)
   1430 {
   1431 	char line[1024], *cp;
   1432 	FILE *f;
   1433 
   1434 	debug2("%s: filename %s", __func__, filename);
   1435 	if ((f = fopen(filename, "r")) == NULL) {
   1436 		perror(filename);
   1437 		exit(1);
   1438 	}
   1439 	buffer_clear(conf);
   1440 	while (fgets(line, sizeof(line), f)) {
   1441 		/*
   1442 		 * Trim out comments and strip whitespace
   1443 		 * NB - preserve newlines, they are needed to reproduce
   1444 		 * line numbers later for error messages
   1445 		 */
   1446 		if ((cp = strchr(line, '#')) != NULL)
   1447 			memcpy(cp, "\n", 2);
   1448 		cp = line + strspn(line, " \t\r");
   1449 
   1450 		buffer_append(conf, cp, strlen(cp));
   1451 	}
   1452 	buffer_append(conf, "\0", 1);
   1453 	fclose(f);
   1454 	debug2("%s: done config len = %d", __func__, buffer_len(conf));
   1455 }
   1456 
   1457 void
   1458 parse_server_match_config(ServerOptions *options, const char *user,
   1459     const char *host, const char *address)
   1460 {
   1461 	ServerOptions mo;
   1462 #ifdef ANDROID
   1463 	char value[PROPERTY_VALUE_MAX];
   1464 #endif
   1465 
   1466 	initialize_server_options(&mo);
   1467 	parse_server_config(&mo, "reprocess config", &cfg, user, host, address);
   1468 #ifdef ANDROID
   1469 	/* Allow root login if ro.debuggable is set */
   1470 	property_get("ro.debuggable", value, "");
   1471 	if (strcmp(value, "1") == 0)
   1472 		mo.permit_root_login = PERMIT_YES;
   1473 #endif
   1474 	copy_set_server_options(options, &mo, 0);
   1475 }
   1476 
   1477 /* Helper macros */
   1478 #define M_CP_INTOPT(n) do {\
   1479 	if (src->n != -1) \
   1480 		dst->n = src->n; \
   1481 } while (0)
   1482 #define M_CP_STROPT(n) do {\
   1483 	if (src->n != NULL) { \
   1484 		if (dst->n != NULL) \
   1485 			xfree(dst->n); \
   1486 		dst->n = src->n; \
   1487 	} \
   1488 } while(0)
   1489 #define M_CP_STRARRAYOPT(n, num_n) do {\
   1490 	if (src->num_n != 0) { \
   1491 		for (dst->num_n = 0; dst->num_n < src->num_n; dst->num_n++) \
   1492 			dst->n[dst->num_n] = xstrdup(src->n[dst->num_n]); \
   1493 	} \
   1494 } while(0)
   1495 
   1496 /*
   1497  * Copy any supported values that are set.
   1498  *
   1499  * If the preauth flag is set, we do not bother copying the string or
   1500  * array values that are not used pre-authentication, because any that we
   1501  * do use must be explictly sent in mm_getpwnamallow().
   1502  */
   1503 void
   1504 copy_set_server_options(ServerOptions *dst, ServerOptions *src, int preauth)
   1505 {
   1506 	M_CP_INTOPT(password_authentication);
   1507 	M_CP_INTOPT(gss_authentication);
   1508 	M_CP_INTOPT(rsa_authentication);
   1509 	M_CP_INTOPT(pubkey_authentication);
   1510 	M_CP_INTOPT(kerberos_authentication);
   1511 	M_CP_INTOPT(hostbased_authentication);
   1512 	M_CP_INTOPT(hostbased_uses_name_from_packet_only);
   1513 	M_CP_INTOPT(kbd_interactive_authentication);
   1514 	M_CP_INTOPT(zero_knowledge_password_authentication);
   1515 	M_CP_INTOPT(permit_root_login);
   1516 	M_CP_INTOPT(permit_empty_passwd);
   1517 
   1518 	M_CP_INTOPT(allow_tcp_forwarding);
   1519 	M_CP_INTOPT(allow_agent_forwarding);
   1520 	M_CP_INTOPT(permit_tun);
   1521 	M_CP_INTOPT(gateway_ports);
   1522 	M_CP_INTOPT(x11_display_offset);
   1523 	M_CP_INTOPT(x11_forwarding);
   1524 	M_CP_INTOPT(x11_use_localhost);
   1525 	M_CP_INTOPT(max_sessions);
   1526 	M_CP_INTOPT(max_authtries);
   1527 	M_CP_INTOPT(ip_qos_interactive);
   1528 	M_CP_INTOPT(ip_qos_bulk);
   1529 
   1530 	/* See comment in servconf.h */
   1531 	COPY_MATCH_STRING_OPTS();
   1532 
   1533 	/*
   1534 	 * The only things that should be below this point are string options
   1535 	 * which are only used after authentication.
   1536 	 */
   1537 	if (preauth)
   1538 		return;
   1539 
   1540 	M_CP_STROPT(adm_forced_command);
   1541 	M_CP_STROPT(chroot_directory);
   1542 }
   1543 
   1544 #undef M_CP_INTOPT
   1545 #undef M_CP_STROPT
   1546 #undef M_CP_STRARRAYOPT
   1547 
   1548 void
   1549 parse_server_config(ServerOptions *options, const char *filename, Buffer *conf,
   1550     const char *user, const char *host, const char *address)
   1551 {
   1552 	int active, linenum, bad_options = 0;
   1553 	char *cp, *obuf, *cbuf;
   1554 
   1555 	debug2("%s: config %s len %d", __func__, filename, buffer_len(conf));
   1556 
   1557 	obuf = cbuf = xstrdup(buffer_ptr(conf));
   1558 	active = user ? 0 : 1;
   1559 	linenum = 1;
   1560 	while ((cp = strsep(&cbuf, "\n")) != NULL) {
   1561 		if (process_server_config_line(options, cp, filename,
   1562 		    linenum++, &active, user, host, address) != 0)
   1563 			bad_options++;
   1564 	}
   1565 	xfree(obuf);
   1566 	if (bad_options > 0)
   1567 		fatal("%s: terminating, %d bad configuration options",
   1568 		    filename, bad_options);
   1569 }
   1570 
   1571 static const char *
   1572 fmt_multistate_int(int val, const struct multistate *m)
   1573 {
   1574 	u_int i;
   1575 
   1576 	for (i = 0; m[i].key != NULL; i++) {
   1577 		if (m[i].value == val)
   1578 			return m[i].key;
   1579 	}
   1580 	return "UNKNOWN";
   1581 }
   1582 
   1583 static const char *
   1584 fmt_intarg(ServerOpCodes code, int val)
   1585 {
   1586 	if (val == -1)
   1587 		return "unset";
   1588 	switch (code) {
   1589 	case sAddressFamily:
   1590 		return fmt_multistate_int(val, multistate_addressfamily);
   1591 	case sPermitRootLogin:
   1592 		return fmt_multistate_int(val, multistate_permitrootlogin);
   1593 	case sGatewayPorts:
   1594 		return fmt_multistate_int(val, multistate_gatewayports);
   1595 	case sCompression:
   1596 		return fmt_multistate_int(val, multistate_compression);
   1597 	case sUsePrivilegeSeparation:
   1598 		return fmt_multistate_int(val, multistate_privsep);
   1599 	case sProtocol:
   1600 		switch (val) {
   1601 		case SSH_PROTO_1:
   1602 			return "1";
   1603 		case SSH_PROTO_2:
   1604 			return "2";
   1605 		case (SSH_PROTO_1|SSH_PROTO_2):
   1606 			return "2,1";
   1607 		default:
   1608 			return "UNKNOWN";
   1609 		}
   1610 	default:
   1611 		switch (val) {
   1612 		case 0:
   1613 			return "no";
   1614 		case 1:
   1615 			return "yes";
   1616 		default:
   1617 			return "UNKNOWN";
   1618 		}
   1619 	}
   1620 }
   1621 
   1622 static const char *
   1623 lookup_opcode_name(ServerOpCodes code)
   1624 {
   1625 	u_int i;
   1626 
   1627 	for (i = 0; keywords[i].name != NULL; i++)
   1628 		if (keywords[i].opcode == code)
   1629 			return(keywords[i].name);
   1630 	return "UNKNOWN";
   1631 }
   1632 
   1633 static void
   1634 dump_cfg_int(ServerOpCodes code, int val)
   1635 {
   1636 	printf("%s %d\n", lookup_opcode_name(code), val);
   1637 }
   1638 
   1639 static void
   1640 dump_cfg_fmtint(ServerOpCodes code, int val)
   1641 {
   1642 	printf("%s %s\n", lookup_opcode_name(code), fmt_intarg(code, val));
   1643 }
   1644 
   1645 static void
   1646 dump_cfg_string(ServerOpCodes code, const char *val)
   1647 {
   1648 	if (val == NULL)
   1649 		return;
   1650 	printf("%s %s\n", lookup_opcode_name(code), val);
   1651 }
   1652 
   1653 static void
   1654 dump_cfg_strarray(ServerOpCodes code, u_int count, char **vals)
   1655 {
   1656 	u_int i;
   1657 
   1658 	for (i = 0; i < count; i++)
   1659 		printf("%s %s\n", lookup_opcode_name(code), vals[i]);
   1660 }
   1661 
   1662 static void
   1663 dump_cfg_strarray_oneline(ServerOpCodes code, u_int count, char **vals)
   1664 {
   1665 	u_int i;
   1666 
   1667 	printf("%s", lookup_opcode_name(code));
   1668 	for (i = 0; i < count; i++)
   1669 		printf(" %s",  vals[i]);
   1670 	printf("\n");
   1671 }
   1672 
   1673 void
   1674 dump_config(ServerOptions *o)
   1675 {
   1676 	u_int i;
   1677 	int ret;
   1678 	struct addrinfo *ai;
   1679 	char addr[NI_MAXHOST], port[NI_MAXSERV], *s = NULL;
   1680 
   1681 	/* these are usually at the top of the config */
   1682 	for (i = 0; i < o->num_ports; i++)
   1683 		printf("port %d\n", o->ports[i]);
   1684 	dump_cfg_fmtint(sProtocol, o->protocol);
   1685 	dump_cfg_fmtint(sAddressFamily, o->address_family);
   1686 
   1687 	/* ListenAddress must be after Port */
   1688 	for (ai = o->listen_addrs; ai; ai = ai->ai_next) {
   1689 		if ((ret = getnameinfo(ai->ai_addr, ai->ai_addrlen, addr,
   1690 		    sizeof(addr), port, sizeof(port),
   1691 		    NI_NUMERICHOST|NI_NUMERICSERV)) != 0) {
   1692 			error("getnameinfo failed: %.100s",
   1693 			    (ret != EAI_SYSTEM) ? gai_strerror(ret) :
   1694 			    strerror(errno));
   1695 		} else {
   1696 			if (ai->ai_family == AF_INET6)
   1697 				printf("listenaddress [%s]:%s\n", addr, port);
   1698 			else
   1699 				printf("listenaddress %s:%s\n", addr, port);
   1700 		}
   1701 	}
   1702 
   1703 	/* integer arguments */
   1704 #ifdef USE_PAM
   1705 	dump_cfg_int(sUsePAM, o->use_pam);
   1706 #endif
   1707 	dump_cfg_int(sServerKeyBits, o->server_key_bits);
   1708 	dump_cfg_int(sLoginGraceTime, o->login_grace_time);
   1709 	dump_cfg_int(sKeyRegenerationTime, o->key_regeneration_time);
   1710 	dump_cfg_int(sX11DisplayOffset, o->x11_display_offset);
   1711 	dump_cfg_int(sMaxAuthTries, o->max_authtries);
   1712 	dump_cfg_int(sMaxSessions, o->max_sessions);
   1713 	dump_cfg_int(sClientAliveInterval, o->client_alive_interval);
   1714 	dump_cfg_int(sClientAliveCountMax, o->client_alive_count_max);
   1715 
   1716 	/* formatted integer arguments */
   1717 	dump_cfg_fmtint(sPermitRootLogin, o->permit_root_login);
   1718 	dump_cfg_fmtint(sIgnoreRhosts, o->ignore_rhosts);
   1719 	dump_cfg_fmtint(sIgnoreUserKnownHosts, o->ignore_user_known_hosts);
   1720 	dump_cfg_fmtint(sRhostsRSAAuthentication, o->rhosts_rsa_authentication);
   1721 	dump_cfg_fmtint(sHostbasedAuthentication, o->hostbased_authentication);
   1722 	dump_cfg_fmtint(sHostbasedUsesNameFromPacketOnly,
   1723 	    o->hostbased_uses_name_from_packet_only);
   1724 	dump_cfg_fmtint(sRSAAuthentication, o->rsa_authentication);
   1725 	dump_cfg_fmtint(sPubkeyAuthentication, o->pubkey_authentication);
   1726 #ifdef KRB5
   1727 	dump_cfg_fmtint(sKerberosAuthentication, o->kerberos_authentication);
   1728 	dump_cfg_fmtint(sKerberosOrLocalPasswd, o->kerberos_or_local_passwd);
   1729 	dump_cfg_fmtint(sKerberosTicketCleanup, o->kerberos_ticket_cleanup);
   1730 # ifdef USE_AFS
   1731 	dump_cfg_fmtint(sKerberosGetAFSToken, o->kerberos_get_afs_token);
   1732 # endif
   1733 #endif
   1734 #ifdef GSSAPI
   1735 	dump_cfg_fmtint(sGssAuthentication, o->gss_authentication);
   1736 	dump_cfg_fmtint(sGssCleanupCreds, o->gss_cleanup_creds);
   1737 #endif
   1738 #ifdef JPAKE
   1739 	dump_cfg_fmtint(sZeroKnowledgePasswordAuthentication,
   1740 	    o->zero_knowledge_password_authentication);
   1741 #endif
   1742 	dump_cfg_fmtint(sPasswordAuthentication, o->password_authentication);
   1743 	dump_cfg_fmtint(sKbdInteractiveAuthentication,
   1744 	    o->kbd_interactive_authentication);
   1745 	dump_cfg_fmtint(sChallengeResponseAuthentication,
   1746 	    o->challenge_response_authentication);
   1747 	dump_cfg_fmtint(sPrintMotd, o->print_motd);
   1748 	dump_cfg_fmtint(sPrintLastLog, o->print_lastlog);
   1749 	dump_cfg_fmtint(sX11Forwarding, o->x11_forwarding);
   1750 	dump_cfg_fmtint(sX11UseLocalhost, o->x11_use_localhost);
   1751 	dump_cfg_fmtint(sStrictModes, o->strict_modes);
   1752 	dump_cfg_fmtint(sTCPKeepAlive, o->tcp_keep_alive);
   1753 	dump_cfg_fmtint(sEmptyPasswd, o->permit_empty_passwd);
   1754 	dump_cfg_fmtint(sPermitUserEnvironment, o->permit_user_env);
   1755 	dump_cfg_fmtint(sUseLogin, o->use_login);
   1756 	dump_cfg_fmtint(sCompression, o->compression);
   1757 	dump_cfg_fmtint(sGatewayPorts, o->gateway_ports);
   1758 	dump_cfg_fmtint(sUseDNS, o->use_dns);
   1759 	dump_cfg_fmtint(sAllowTcpForwarding, o->allow_tcp_forwarding);
   1760 	dump_cfg_fmtint(sUsePrivilegeSeparation, use_privsep);
   1761 
   1762 	/* string arguments */
   1763 	dump_cfg_string(sPidFile, o->pid_file);
   1764 	dump_cfg_string(sXAuthLocation, o->xauth_location);
   1765 	dump_cfg_string(sCiphers, o->ciphers);
   1766 	dump_cfg_string(sMacs, o->macs);
   1767 	dump_cfg_string(sBanner, o->banner);
   1768 	dump_cfg_string(sForceCommand, o->adm_forced_command);
   1769 	dump_cfg_string(sChrootDirectory, o->chroot_directory);
   1770 	dump_cfg_string(sTrustedUserCAKeys, o->trusted_user_ca_keys);
   1771 	dump_cfg_string(sRevokedKeys, o->revoked_keys_file);
   1772 	dump_cfg_string(sAuthorizedPrincipalsFile,
   1773 	    o->authorized_principals_file);
   1774 
   1775 	/* string arguments requiring a lookup */
   1776 	dump_cfg_string(sLogLevel, log_level_name(o->log_level));
   1777 	dump_cfg_string(sLogFacility, log_facility_name(o->log_facility));
   1778 
   1779 	/* string array arguments */
   1780 	dump_cfg_strarray_oneline(sAuthorizedKeysFile, o->num_authkeys_files,
   1781 	    o->authorized_keys_files);
   1782 	dump_cfg_strarray(sHostKeyFile, o->num_host_key_files,
   1783 	     o->host_key_files);
   1784 	dump_cfg_strarray(sHostKeyFile, o->num_host_cert_files,
   1785 	     o->host_cert_files);
   1786 	dump_cfg_strarray(sAllowUsers, o->num_allow_users, o->allow_users);
   1787 	dump_cfg_strarray(sDenyUsers, o->num_deny_users, o->deny_users);
   1788 	dump_cfg_strarray(sAllowGroups, o->num_allow_groups, o->allow_groups);
   1789 	dump_cfg_strarray(sDenyGroups, o->num_deny_groups, o->deny_groups);
   1790 	dump_cfg_strarray(sAcceptEnv, o->num_accept_env, o->accept_env);
   1791 
   1792 	/* other arguments */
   1793 	for (i = 0; i < o->num_subsystems; i++)
   1794 		printf("subsystem %s %s\n", o->subsystem_name[i],
   1795 		    o->subsystem_args[i]);
   1796 
   1797 	printf("maxstartups %d:%d:%d\n", o->max_startups_begin,
   1798 	    o->max_startups_rate, o->max_startups);
   1799 
   1800 	for (i = 0; tunmode_desc[i].val != -1; i++)
   1801 		if (tunmode_desc[i].val == o->permit_tun) {
   1802 			s = tunmode_desc[i].text;
   1803 			break;
   1804 		}
   1805 	dump_cfg_string(sPermitTunnel, s);
   1806 
   1807 	printf("ipqos %s ", iptos2str(o->ip_qos_interactive));
   1808 	printf("%s\n", iptos2str(o->ip_qos_bulk));
   1809 
   1810 	channel_print_adm_permitted_opens();
   1811 }
   1812