xref: /dragonfly/crypto/openssh/servconf.c (revision 664f4763)
1 
2 /* $OpenBSD: servconf.c,v 1.350 2019/03/25 22:33:44 djm Exp $ */
3 /*
4  * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
5  *                    All rights reserved
6  *
7  * As far as I am concerned, the code I have written for this software
8  * can be used freely for any purpose.  Any derived versions of this
9  * software must be clearly marked as such, and if the derived work is
10  * incompatible with the protocol description in the RFC file, it must be
11  * called by a name other than "ssh" or "Secure Shell".
12  */
13 
14 #include "includes.h"
15 
16 #include <sys/types.h>
17 #include <sys/socket.h>
18 #ifdef HAVE_SYS_SYSCTL_H
19 #include <sys/sysctl.h>
20 #endif
21 
22 #include <netinet/in.h>
23 #include <netinet/in_systm.h>
24 #include <netinet/ip.h>
25 #ifdef HAVE_NET_ROUTE_H
26 #include <net/route.h>
27 #endif
28 
29 #include <ctype.h>
30 #include <netdb.h>
31 #include <pwd.h>
32 #include <stdio.h>
33 #include <stdlib.h>
34 #include <string.h>
35 #include <signal.h>
36 #include <unistd.h>
37 #include <limits.h>
38 #include <stdarg.h>
39 #include <errno.h>
40 #ifdef HAVE_UTIL_H
41 #include <util.h>
42 #endif
43 
44 #include "openbsd-compat/sys-queue.h"
45 #include "xmalloc.h"
46 #include "ssh.h"
47 #include "log.h"
48 #include "sshbuf.h"
49 #include "misc.h"
50 #include "servconf.h"
51 #include "compat.h"
52 #include "pathnames.h"
53 #include "cipher.h"
54 #include "sshkey.h"
55 #include "kex.h"
56 #include "mac.h"
57 #include "match.h"
58 #include "channels.h"
59 #include "groupaccess.h"
60 #include "canohost.h"
61 #include "packet.h"
62 #include "ssherr.h"
63 #include "hostfile.h"
64 #include "auth.h"
65 #include "myproposal.h"
66 #include "digest.h"
67 
68 static void add_listen_addr(ServerOptions *, const char *,
69     const char *, int);
70 static void add_one_listen_addr(ServerOptions *, const char *,
71     const char *, int);
72 
73 /* Use of privilege separation or not */
74 extern int use_privsep;
75 extern struct sshbuf *cfg;
76 
77 /* Initializes the server options to their default values. */
78 
79 void
80 initialize_server_options(ServerOptions *options)
81 {
82 	memset(options, 0, sizeof(*options));
83 
84 	/* Portable-specific options */
85 	options->use_pam = -1;
86 
87 	/* Standard Options */
88 	options->num_ports = 0;
89 	options->ports_from_cmdline = 0;
90 	options->queued_listen_addrs = NULL;
91 	options->num_queued_listens = 0;
92 	options->listen_addrs = NULL;
93 	options->num_listen_addrs = 0;
94 	options->address_family = -1;
95 	options->routing_domain = NULL;
96 	options->num_host_key_files = 0;
97 	options->num_host_cert_files = 0;
98 	options->host_key_agent = NULL;
99 	options->pid_file = NULL;
100 	options->login_grace_time = -1;
101 	options->permit_root_login = PERMIT_NOT_SET;
102 	options->ignore_rhosts = -1;
103 	options->ignore_user_known_hosts = -1;
104 	options->print_motd = -1;
105 	options->print_lastlog = -1;
106 	options->x11_forwarding = -1;
107 	options->x11_display_offset = -1;
108 	options->x11_use_localhost = -1;
109 	options->permit_tty = -1;
110 	options->permit_user_rc = -1;
111 	options->xauth_location = NULL;
112 	options->strict_modes = -1;
113 	options->tcp_keep_alive = -1;
114 	options->log_facility = SYSLOG_FACILITY_NOT_SET;
115 	options->log_level = SYSLOG_LEVEL_NOT_SET;
116 	options->hostbased_authentication = -1;
117 	options->hostbased_uses_name_from_packet_only = -1;
118 	options->hostbased_key_types = NULL;
119 	options->hostkeyalgorithms = NULL;
120 	options->pubkey_authentication = -1;
121 	options->pubkey_key_types = NULL;
122 	options->kerberos_authentication = -1;
123 	options->kerberos_or_local_passwd = -1;
124 	options->kerberos_ticket_cleanup = -1;
125 	options->kerberos_get_afs_token = -1;
126 	options->gss_authentication=-1;
127 	options->gss_cleanup_creds = -1;
128 	options->gss_strict_acceptor = -1;
129 	options->password_authentication = -1;
130 	options->kbd_interactive_authentication = -1;
131 	options->challenge_response_authentication = -1;
132 	options->permit_empty_passwd = -1;
133 	options->permit_user_env = -1;
134 	options->permit_user_env_whitelist = NULL;
135 	options->compression = -1;
136 	options->rekey_limit = -1;
137 	options->rekey_interval = -1;
138 	options->allow_tcp_forwarding = -1;
139 	options->allow_streamlocal_forwarding = -1;
140 	options->allow_agent_forwarding = -1;
141 	options->num_allow_users = 0;
142 	options->num_deny_users = 0;
143 	options->num_allow_groups = 0;
144 	options->num_deny_groups = 0;
145 	options->ciphers = NULL;
146 	options->macs = NULL;
147 	options->kex_algorithms = NULL;
148 	options->ca_sign_algorithms = NULL;
149 	options->fwd_opts.gateway_ports = -1;
150 	options->fwd_opts.streamlocal_bind_mask = (mode_t)-1;
151 	options->fwd_opts.streamlocal_bind_unlink = -1;
152 	options->num_subsystems = 0;
153 	options->max_startups_begin = -1;
154 	options->max_startups_rate = -1;
155 	options->max_startups = -1;
156 	options->max_authtries = -1;
157 	options->max_sessions = -1;
158 	options->banner = NULL;
159 	options->use_dns = -1;
160 	options->client_alive_interval = -1;
161 	options->client_alive_count_max = -1;
162 	options->num_authkeys_files = 0;
163 	options->num_accept_env = 0;
164 	options->num_setenv = 0;
165 	options->permit_tun = -1;
166 	options->permitted_opens = NULL;
167 	options->permitted_listens = NULL;
168 	options->adm_forced_command = NULL;
169 	options->chroot_directory = NULL;
170 	options->authorized_keys_command = NULL;
171 	options->authorized_keys_command_user = NULL;
172 	options->revoked_keys_file = NULL;
173 	options->trusted_user_ca_keys = NULL;
174 	options->authorized_principals_file = NULL;
175 	options->authorized_principals_command = NULL;
176 	options->authorized_principals_command_user = NULL;
177 	options->ip_qos_interactive = -1;
178 	options->ip_qos_bulk = -1;
179 	options->version_addendum = NULL;
180 	options->fingerprint_hash = -1;
181 	options->disable_forwarding = -1;
182 	options->expose_userauth_info = -1;
183 }
184 
185 /* Returns 1 if a string option is unset or set to "none" or 0 otherwise. */
186 static int
187 option_clear_or_none(const char *o)
188 {
189 	return o == NULL || strcasecmp(o, "none") == 0;
190 }
191 
192 static void
193 assemble_algorithms(ServerOptions *o)
194 {
195 	char *all_cipher, *all_mac, *all_kex, *all_key, *all_sig;
196 	int r;
197 
198 	all_cipher = cipher_alg_list(',', 0);
199 	all_mac = mac_alg_list(',');
200 	all_kex = kex_alg_list(',');
201 	all_key = sshkey_alg_list(0, 0, 1, ',');
202 	all_sig = sshkey_alg_list(0, 1, 1, ',');
203 #define ASSEMBLE(what, defaults, all) \
204 	do { \
205 		if ((r = kex_assemble_names(&o->what, defaults, all)) != 0) \
206 			fatal("%s: %s: %s", __func__, #what, ssh_err(r)); \
207 	} while (0)
208 	ASSEMBLE(ciphers, KEX_SERVER_ENCRYPT, all_cipher);
209 	ASSEMBLE(macs, KEX_SERVER_MAC, all_mac);
210 	ASSEMBLE(kex_algorithms, KEX_SERVER_KEX, all_kex);
211 	ASSEMBLE(hostkeyalgorithms, KEX_DEFAULT_PK_ALG, all_key);
212 	ASSEMBLE(hostbased_key_types, KEX_DEFAULT_PK_ALG, all_key);
213 	ASSEMBLE(pubkey_key_types, KEX_DEFAULT_PK_ALG, all_key);
214 	ASSEMBLE(ca_sign_algorithms, SSH_ALLOWED_CA_SIGALGS, all_sig);
215 #undef ASSEMBLE
216 	free(all_cipher);
217 	free(all_mac);
218 	free(all_kex);
219 	free(all_key);
220 	free(all_sig);
221 }
222 
223 static void
224 array_append2(const char *file, const int line, const char *directive,
225     char ***array, int **iarray, u_int *lp, const char *s, int i)
226 {
227 
228 	if (*lp >= INT_MAX)
229 		fatal("%s line %d: Too many %s entries", file, line, directive);
230 
231 	if (iarray != NULL) {
232 		*iarray = xrecallocarray(*iarray, *lp, *lp + 1,
233 		    sizeof(**iarray));
234 		(*iarray)[*lp] = i;
235 	}
236 
237 	*array = xrecallocarray(*array, *lp, *lp + 1, sizeof(**array));
238 	(*array)[*lp] = xstrdup(s);
239 	(*lp)++;
240 }
241 
242 static void
243 array_append(const char *file, const int line, const char *directive,
244     char ***array, u_int *lp, const char *s)
245 {
246 	array_append2(file, line, directive, array, NULL, lp, s, 0);
247 }
248 
249 void
250 servconf_add_hostkey(const char *file, const int line,
251     ServerOptions *options, const char *path, int userprovided)
252 {
253 	char *apath = derelativise_path(path);
254 
255 	array_append2(file, line, "HostKey",
256 	    &options->host_key_files, &options->host_key_file_userprovided,
257 	    &options->num_host_key_files, apath, userprovided);
258 	free(apath);
259 }
260 
261 void
262 servconf_add_hostcert(const char *file, const int line,
263     ServerOptions *options, const char *path)
264 {
265 	char *apath = derelativise_path(path);
266 
267 	array_append(file, line, "HostCertificate",
268 	    &options->host_cert_files, &options->num_host_cert_files, apath);
269 	free(apath);
270 }
271 
272 void
273 fill_default_server_options(ServerOptions *options)
274 {
275 	u_int i;
276 
277 	/* Portable-specific options */
278 	if (options->use_pam == -1)
279 		options->use_pam = 0;
280 
281 	/* Standard Options */
282 	if (options->num_host_key_files == 0) {
283 		/* fill default hostkeys for protocols */
284 		servconf_add_hostkey("[default]", 0, options,
285 		    _PATH_HOST_RSA_KEY_FILE, 0);
286 #ifdef OPENSSL_HAS_ECC
287 		servconf_add_hostkey("[default]", 0, options,
288 		    _PATH_HOST_ECDSA_KEY_FILE, 0);
289 #endif
290 		servconf_add_hostkey("[default]", 0, options,
291 		    _PATH_HOST_ED25519_KEY_FILE, 0);
292 #ifdef WITH_XMSS
293 		servconf_add_hostkey("[default]", 0, options,
294 		    _PATH_HOST_XMSS_KEY_FILE, 0);
295 #endif /* WITH_XMSS */
296 	}
297 	/* No certificates by default */
298 	if (options->num_ports == 0)
299 		options->ports[options->num_ports++] = SSH_DEFAULT_PORT;
300 	if (options->address_family == -1)
301 		options->address_family = AF_UNSPEC;
302 	if (options->listen_addrs == NULL)
303 		add_listen_addr(options, NULL, NULL, 0);
304 	if (options->pid_file == NULL)
305 		options->pid_file = xstrdup(_PATH_SSH_DAEMON_PID_FILE);
306 	if (options->login_grace_time == -1)
307 		options->login_grace_time = 120;
308 	if (options->permit_root_login == PERMIT_NOT_SET)
309 		options->permit_root_login = PERMIT_NO_PASSWD;
310 	if (options->ignore_rhosts == -1)
311 		options->ignore_rhosts = 1;
312 	if (options->ignore_user_known_hosts == -1)
313 		options->ignore_user_known_hosts = 0;
314 	if (options->print_motd == -1)
315 		options->print_motd = 1;
316 	if (options->print_lastlog == -1)
317 		options->print_lastlog = 1;
318 	if (options->x11_forwarding == -1)
319 		options->x11_forwarding = 0;
320 	if (options->x11_display_offset == -1)
321 		options->x11_display_offset = 10;
322 	if (options->x11_use_localhost == -1)
323 		options->x11_use_localhost = 1;
324 	if (options->xauth_location == NULL)
325 		options->xauth_location = xstrdup(_PATH_XAUTH);
326 	if (options->permit_tty == -1)
327 		options->permit_tty = 1;
328 	if (options->permit_user_rc == -1)
329 		options->permit_user_rc = 1;
330 	if (options->strict_modes == -1)
331 		options->strict_modes = 1;
332 	if (options->tcp_keep_alive == -1)
333 		options->tcp_keep_alive = 1;
334 	if (options->log_facility == SYSLOG_FACILITY_NOT_SET)
335 		options->log_facility = SYSLOG_FACILITY_AUTH;
336 	if (options->log_level == SYSLOG_LEVEL_NOT_SET)
337 		options->log_level = SYSLOG_LEVEL_INFO;
338 	if (options->hostbased_authentication == -1)
339 		options->hostbased_authentication = 0;
340 	if (options->hostbased_uses_name_from_packet_only == -1)
341 		options->hostbased_uses_name_from_packet_only = 0;
342 	if (options->pubkey_authentication == -1)
343 		options->pubkey_authentication = 1;
344 	if (options->kerberos_authentication == -1)
345 		options->kerberos_authentication = 0;
346 	if (options->kerberos_or_local_passwd == -1)
347 		options->kerberos_or_local_passwd = 1;
348 	if (options->kerberos_ticket_cleanup == -1)
349 		options->kerberos_ticket_cleanup = 1;
350 	if (options->kerberos_get_afs_token == -1)
351 		options->kerberos_get_afs_token = 0;
352 	if (options->gss_authentication == -1)
353 		options->gss_authentication = 0;
354 	if (options->gss_cleanup_creds == -1)
355 		options->gss_cleanup_creds = 1;
356 	if (options->gss_strict_acceptor == -1)
357 		options->gss_strict_acceptor = 1;
358 	if (options->password_authentication == -1)
359 		options->password_authentication = 1;
360 	if (options->kbd_interactive_authentication == -1)
361 		options->kbd_interactive_authentication = 0;
362 	if (options->challenge_response_authentication == -1)
363 		options->challenge_response_authentication = 1;
364 	if (options->permit_empty_passwd == -1)
365 		options->permit_empty_passwd = 0;
366 	if (options->permit_user_env == -1) {
367 		options->permit_user_env = 0;
368 		options->permit_user_env_whitelist = NULL;
369 	}
370 	if (options->compression == -1)
371 		options->compression = COMP_DELAYED;
372 	if (options->rekey_limit == -1)
373 		options->rekey_limit = 0;
374 	if (options->rekey_interval == -1)
375 		options->rekey_interval = 0;
376 	if (options->allow_tcp_forwarding == -1)
377 		options->allow_tcp_forwarding = FORWARD_ALLOW;
378 	if (options->allow_streamlocal_forwarding == -1)
379 		options->allow_streamlocal_forwarding = FORWARD_ALLOW;
380 	if (options->allow_agent_forwarding == -1)
381 		options->allow_agent_forwarding = 1;
382 	if (options->fwd_opts.gateway_ports == -1)
383 		options->fwd_opts.gateway_ports = 0;
384 	if (options->max_startups == -1)
385 		options->max_startups = 100;
386 	if (options->max_startups_rate == -1)
387 		options->max_startups_rate = 30;		/* 30% */
388 	if (options->max_startups_begin == -1)
389 		options->max_startups_begin = 10;
390 	if (options->max_authtries == -1)
391 		options->max_authtries = DEFAULT_AUTH_FAIL_MAX;
392 	if (options->max_sessions == -1)
393 		options->max_sessions = DEFAULT_SESSIONS_MAX;
394 	if (options->use_dns == -1)
395 		options->use_dns = 0;
396 	if (options->client_alive_interval == -1)
397 		options->client_alive_interval = 0;
398 	if (options->client_alive_count_max == -1)
399 		options->client_alive_count_max = 3;
400 	if (options->num_authkeys_files == 0) {
401 		array_append("[default]", 0, "AuthorizedKeysFiles",
402 		    &options->authorized_keys_files,
403 		    &options->num_authkeys_files,
404 		    _PATH_SSH_USER_PERMITTED_KEYS);
405 		array_append("[default]", 0, "AuthorizedKeysFiles",
406 		    &options->authorized_keys_files,
407 		    &options->num_authkeys_files,
408 		    _PATH_SSH_USER_PERMITTED_KEYS2);
409 	}
410 	if (options->permit_tun == -1)
411 		options->permit_tun = SSH_TUNMODE_NO;
412 	if (options->ip_qos_interactive == -1)
413 		options->ip_qos_interactive = IPTOS_DSCP_AF21;
414 	if (options->ip_qos_bulk == -1)
415 		options->ip_qos_bulk = IPTOS_DSCP_CS1;
416 	if (options->version_addendum == NULL)
417 		options->version_addendum = xstrdup("");
418 	if (options->fwd_opts.streamlocal_bind_mask == (mode_t)-1)
419 		options->fwd_opts.streamlocal_bind_mask = 0177;
420 	if (options->fwd_opts.streamlocal_bind_unlink == -1)
421 		options->fwd_opts.streamlocal_bind_unlink = 0;
422 	if (options->fingerprint_hash == -1)
423 		options->fingerprint_hash = SSH_FP_HASH_DEFAULT;
424 	if (options->disable_forwarding == -1)
425 		options->disable_forwarding = 0;
426 	if (options->expose_userauth_info == -1)
427 		options->expose_userauth_info = 0;
428 
429 	assemble_algorithms(options);
430 
431 	/* Turn privilege separation and sandboxing on by default */
432 	if (use_privsep == -1)
433 		use_privsep = PRIVSEP_ON;
434 
435 #define CLEAR_ON_NONE(v) \
436 	do { \
437 		if (option_clear_or_none(v)) { \
438 			free(v); \
439 			v = NULL; \
440 		} \
441 	} while(0)
442 	CLEAR_ON_NONE(options->pid_file);
443 	CLEAR_ON_NONE(options->xauth_location);
444 	CLEAR_ON_NONE(options->banner);
445 	CLEAR_ON_NONE(options->trusted_user_ca_keys);
446 	CLEAR_ON_NONE(options->revoked_keys_file);
447 	CLEAR_ON_NONE(options->authorized_principals_file);
448 	CLEAR_ON_NONE(options->adm_forced_command);
449 	CLEAR_ON_NONE(options->chroot_directory);
450 	CLEAR_ON_NONE(options->routing_domain);
451 	for (i = 0; i < options->num_host_key_files; i++)
452 		CLEAR_ON_NONE(options->host_key_files[i]);
453 	for (i = 0; i < options->num_host_cert_files; i++)
454 		CLEAR_ON_NONE(options->host_cert_files[i]);
455 #undef CLEAR_ON_NONE
456 
457 	/* Similar handling for AuthenticationMethods=any */
458 	if (options->num_auth_methods == 1 &&
459 	    strcmp(options->auth_methods[0], "any") == 0) {
460 		free(options->auth_methods[0]);
461 		options->auth_methods[0] = NULL;
462 		options->num_auth_methods = 0;
463 	}
464 
465 #ifndef HAVE_MMAP
466 	if (use_privsep && options->compression == 1) {
467 		error("This platform does not support both privilege "
468 		    "separation and compression");
469 		error("Compression disabled");
470 		options->compression = 0;
471 	}
472 #endif
473 }
474 
475 /* Keyword tokens. */
476 typedef enum {
477 	sBadOption,		/* == unknown option */
478 	/* Portable-specific options */
479 	sUsePAM,
480 	/* Standard Options */
481 	sPort, sHostKeyFile, sLoginGraceTime,
482 	sPermitRootLogin, sLogFacility, sLogLevel,
483 	sRhostsRSAAuthentication, sRSAAuthentication,
484 	sKerberosAuthentication, sKerberosOrLocalPasswd, sKerberosTicketCleanup,
485 	sKerberosGetAFSToken, sChallengeResponseAuthentication,
486 	sPasswordAuthentication, sKbdInteractiveAuthentication,
487 	sListenAddress, sAddressFamily,
488 	sPrintMotd, sPrintLastLog, sIgnoreRhosts,
489 	sX11Forwarding, sX11DisplayOffset, sX11UseLocalhost,
490 	sPermitTTY, sStrictModes, sEmptyPasswd, sTCPKeepAlive,
491 	sPermitUserEnvironment, sAllowTcpForwarding, sCompression,
492 	sRekeyLimit, sAllowUsers, sDenyUsers, sAllowGroups, sDenyGroups,
493 	sIgnoreUserKnownHosts, sCiphers, sMacs, sPidFile,
494 	sGatewayPorts, sPubkeyAuthentication, sPubkeyAcceptedKeyTypes,
495 	sXAuthLocation, sSubsystem, sMaxStartups, sMaxAuthTries, sMaxSessions,
496 	sBanner, sUseDNS, sHostbasedAuthentication,
497 	sHostbasedUsesNameFromPacketOnly, sHostbasedAcceptedKeyTypes,
498 	sHostKeyAlgorithms,
499 	sClientAliveInterval, sClientAliveCountMax, sAuthorizedKeysFile,
500 	sGssAuthentication, sGssCleanupCreds, sGssStrictAcceptor,
501 	sAcceptEnv, sSetEnv, sPermitTunnel,
502 	sMatch, sPermitOpen, sPermitListen, sForceCommand, sChrootDirectory,
503 	sUsePrivilegeSeparation, sAllowAgentForwarding,
504 	sHostCertificate,
505 	sRevokedKeys, sTrustedUserCAKeys, sAuthorizedPrincipalsFile,
506 	sAuthorizedPrincipalsCommand, sAuthorizedPrincipalsCommandUser,
507 	sKexAlgorithms, sCASignatureAlgorithms, sIPQoS, sVersionAddendum,
508 	sAuthorizedKeysCommand, sAuthorizedKeysCommandUser,
509 	sAuthenticationMethods, sHostKeyAgent, sPermitUserRC,
510 	sStreamLocalBindMask, sStreamLocalBindUnlink,
511 	sAllowStreamLocalForwarding, sFingerprintHash, sDisableForwarding,
512 	sExposeAuthInfo, sRDomain,
513 	sDeprecated, sIgnore, sUnsupported
514 } ServerOpCodes;
515 
516 #define SSHCFG_GLOBAL	0x01	/* allowed in main section of sshd_config */
517 #define SSHCFG_MATCH	0x02	/* allowed inside a Match section */
518 #define SSHCFG_ALL	(SSHCFG_GLOBAL|SSHCFG_MATCH)
519 
520 /* Textual representation of the tokens. */
521 static struct {
522 	const char *name;
523 	ServerOpCodes opcode;
524 	u_int flags;
525 } keywords[] = {
526 	/* Portable-specific options */
527 #ifdef USE_PAM
528 	{ "usepam", sUsePAM, SSHCFG_GLOBAL },
529 #else
530 	{ "usepam", sUnsupported, SSHCFG_GLOBAL },
531 #endif
532 	{ "pamauthenticationviakbdint", sDeprecated, SSHCFG_GLOBAL },
533 	/* Standard Options */
534 	{ "port", sPort, SSHCFG_GLOBAL },
535 	{ "hostkey", sHostKeyFile, SSHCFG_GLOBAL },
536 	{ "hostdsakey", sHostKeyFile, SSHCFG_GLOBAL },		/* alias */
537 	{ "hostkeyagent", sHostKeyAgent, SSHCFG_GLOBAL },
538 	{ "pidfile", sPidFile, SSHCFG_GLOBAL },
539 	{ "serverkeybits", sDeprecated, SSHCFG_GLOBAL },
540 	{ "logingracetime", sLoginGraceTime, SSHCFG_GLOBAL },
541 	{ "keyregenerationinterval", sDeprecated, SSHCFG_GLOBAL },
542 	{ "permitrootlogin", sPermitRootLogin, SSHCFG_ALL },
543 	{ "syslogfacility", sLogFacility, SSHCFG_GLOBAL },
544 	{ "loglevel", sLogLevel, SSHCFG_ALL },
545 	{ "rhostsauthentication", sDeprecated, SSHCFG_GLOBAL },
546 	{ "rhostsrsaauthentication", sDeprecated, SSHCFG_ALL },
547 	{ "hostbasedauthentication", sHostbasedAuthentication, SSHCFG_ALL },
548 	{ "hostbasedusesnamefrompacketonly", sHostbasedUsesNameFromPacketOnly, SSHCFG_ALL },
549 	{ "hostbasedacceptedkeytypes", sHostbasedAcceptedKeyTypes, SSHCFG_ALL },
550 	{ "hostkeyalgorithms", sHostKeyAlgorithms, SSHCFG_GLOBAL },
551 	{ "rsaauthentication", sDeprecated, SSHCFG_ALL },
552 	{ "pubkeyauthentication", sPubkeyAuthentication, SSHCFG_ALL },
553 	{ "pubkeyacceptedkeytypes", sPubkeyAcceptedKeyTypes, SSHCFG_ALL },
554 	{ "dsaauthentication", sPubkeyAuthentication, SSHCFG_GLOBAL }, /* alias */
555 #ifdef KRB5
556 	{ "kerberosauthentication", sKerberosAuthentication, SSHCFG_ALL },
557 	{ "kerberosorlocalpasswd", sKerberosOrLocalPasswd, SSHCFG_GLOBAL },
558 	{ "kerberosticketcleanup", sKerberosTicketCleanup, SSHCFG_GLOBAL },
559 #ifdef USE_AFS
560 	{ "kerberosgetafstoken", sKerberosGetAFSToken, SSHCFG_GLOBAL },
561 #else
562 	{ "kerberosgetafstoken", sUnsupported, SSHCFG_GLOBAL },
563 #endif
564 #else
565 	{ "kerberosauthentication", sUnsupported, SSHCFG_ALL },
566 	{ "kerberosorlocalpasswd", sUnsupported, SSHCFG_GLOBAL },
567 	{ "kerberosticketcleanup", sUnsupported, SSHCFG_GLOBAL },
568 	{ "kerberosgetafstoken", sUnsupported, SSHCFG_GLOBAL },
569 #endif
570 	{ "kerberostgtpassing", sUnsupported, SSHCFG_GLOBAL },
571 	{ "afstokenpassing", sUnsupported, SSHCFG_GLOBAL },
572 #ifdef GSSAPI
573 	{ "gssapiauthentication", sGssAuthentication, SSHCFG_ALL },
574 	{ "gssapicleanupcredentials", sGssCleanupCreds, SSHCFG_GLOBAL },
575 	{ "gssapistrictacceptorcheck", sGssStrictAcceptor, SSHCFG_GLOBAL },
576 #else
577 	{ "gssapiauthentication", sUnsupported, SSHCFG_ALL },
578 	{ "gssapicleanupcredentials", sUnsupported, SSHCFG_GLOBAL },
579 	{ "gssapistrictacceptorcheck", sUnsupported, SSHCFG_GLOBAL },
580 #endif
581 	{ "passwordauthentication", sPasswordAuthentication, SSHCFG_ALL },
582 	{ "kbdinteractiveauthentication", sKbdInteractiveAuthentication, SSHCFG_ALL },
583 	{ "challengeresponseauthentication", sChallengeResponseAuthentication, SSHCFG_GLOBAL },
584 	{ "skeyauthentication", sDeprecated, SSHCFG_GLOBAL },
585 	{ "checkmail", sDeprecated, SSHCFG_GLOBAL },
586 	{ "listenaddress", sListenAddress, SSHCFG_GLOBAL },
587 	{ "addressfamily", sAddressFamily, SSHCFG_GLOBAL },
588 	{ "printmotd", sPrintMotd, SSHCFG_GLOBAL },
589 #ifdef DISABLE_LASTLOG
590 	{ "printlastlog", sUnsupported, SSHCFG_GLOBAL },
591 #else
592 	{ "printlastlog", sPrintLastLog, SSHCFG_GLOBAL },
593 #endif
594 	{ "ignorerhosts", sIgnoreRhosts, SSHCFG_GLOBAL },
595 	{ "ignoreuserknownhosts", sIgnoreUserKnownHosts, SSHCFG_GLOBAL },
596 	{ "x11forwarding", sX11Forwarding, SSHCFG_ALL },
597 	{ "x11displayoffset", sX11DisplayOffset, SSHCFG_ALL },
598 	{ "x11uselocalhost", sX11UseLocalhost, SSHCFG_ALL },
599 	{ "xauthlocation", sXAuthLocation, SSHCFG_GLOBAL },
600 	{ "strictmodes", sStrictModes, SSHCFG_GLOBAL },
601 	{ "permitemptypasswords", sEmptyPasswd, SSHCFG_ALL },
602 	{ "permituserenvironment", sPermitUserEnvironment, SSHCFG_GLOBAL },
603 	{ "uselogin", sDeprecated, SSHCFG_GLOBAL },
604 	{ "compression", sCompression, SSHCFG_GLOBAL },
605 	{ "rekeylimit", sRekeyLimit, SSHCFG_ALL },
606 	{ "tcpkeepalive", sTCPKeepAlive, SSHCFG_GLOBAL },
607 	{ "keepalive", sTCPKeepAlive, SSHCFG_GLOBAL },	/* obsolete alias */
608 	{ "allowtcpforwarding", sAllowTcpForwarding, SSHCFG_ALL },
609 	{ "allowagentforwarding", sAllowAgentForwarding, SSHCFG_ALL },
610 	{ "allowusers", sAllowUsers, SSHCFG_ALL },
611 	{ "denyusers", sDenyUsers, SSHCFG_ALL },
612 	{ "allowgroups", sAllowGroups, SSHCFG_ALL },
613 	{ "denygroups", sDenyGroups, SSHCFG_ALL },
614 	{ "ciphers", sCiphers, SSHCFG_GLOBAL },
615 	{ "macs", sMacs, SSHCFG_GLOBAL },
616 	{ "protocol", sIgnore, SSHCFG_GLOBAL },
617 	{ "gatewayports", sGatewayPorts, SSHCFG_ALL },
618 	{ "subsystem", sSubsystem, SSHCFG_GLOBAL },
619 	{ "maxstartups", sMaxStartups, SSHCFG_GLOBAL },
620 	{ "maxauthtries", sMaxAuthTries, SSHCFG_ALL },
621 	{ "maxsessions", sMaxSessions, SSHCFG_ALL },
622 	{ "banner", sBanner, SSHCFG_ALL },
623 	{ "usedns", sUseDNS, SSHCFG_GLOBAL },
624 	{ "verifyreversemapping", sDeprecated, SSHCFG_GLOBAL },
625 	{ "reversemappingcheck", sDeprecated, SSHCFG_GLOBAL },
626 	{ "clientaliveinterval", sClientAliveInterval, SSHCFG_ALL },
627 	{ "clientalivecountmax", sClientAliveCountMax, SSHCFG_ALL },
628 	{ "authorizedkeysfile", sAuthorizedKeysFile, SSHCFG_ALL },
629 	{ "authorizedkeysfile2", sDeprecated, SSHCFG_ALL },
630 	{ "useprivilegeseparation", sDeprecated, SSHCFG_GLOBAL},
631 	{ "acceptenv", sAcceptEnv, SSHCFG_ALL },
632 	{ "setenv", sSetEnv, SSHCFG_ALL },
633 	{ "permittunnel", sPermitTunnel, SSHCFG_ALL },
634 	{ "permittty", sPermitTTY, SSHCFG_ALL },
635 	{ "permituserrc", sPermitUserRC, SSHCFG_ALL },
636 	{ "match", sMatch, SSHCFG_ALL },
637 	{ "permitopen", sPermitOpen, SSHCFG_ALL },
638 	{ "permitlisten", sPermitListen, SSHCFG_ALL },
639 	{ "forcecommand", sForceCommand, SSHCFG_ALL },
640 	{ "chrootdirectory", sChrootDirectory, SSHCFG_ALL },
641 	{ "hostcertificate", sHostCertificate, SSHCFG_GLOBAL },
642 	{ "revokedkeys", sRevokedKeys, SSHCFG_ALL },
643 	{ "trustedusercakeys", sTrustedUserCAKeys, SSHCFG_ALL },
644 	{ "authorizedprincipalsfile", sAuthorizedPrincipalsFile, SSHCFG_ALL },
645 	{ "kexalgorithms", sKexAlgorithms, SSHCFG_GLOBAL },
646 	{ "ipqos", sIPQoS, SSHCFG_ALL },
647 	{ "authorizedkeyscommand", sAuthorizedKeysCommand, SSHCFG_ALL },
648 	{ "authorizedkeyscommanduser", sAuthorizedKeysCommandUser, SSHCFG_ALL },
649 	{ "authorizedprincipalscommand", sAuthorizedPrincipalsCommand, SSHCFG_ALL },
650 	{ "authorizedprincipalscommanduser", sAuthorizedPrincipalsCommandUser, SSHCFG_ALL },
651 	{ "versionaddendum", sVersionAddendum, SSHCFG_GLOBAL },
652 	{ "authenticationmethods", sAuthenticationMethods, SSHCFG_ALL },
653 	{ "streamlocalbindmask", sStreamLocalBindMask, SSHCFG_ALL },
654 	{ "streamlocalbindunlink", sStreamLocalBindUnlink, SSHCFG_ALL },
655 	{ "allowstreamlocalforwarding", sAllowStreamLocalForwarding, SSHCFG_ALL },
656 	{ "fingerprinthash", sFingerprintHash, SSHCFG_GLOBAL },
657 	{ "disableforwarding", sDisableForwarding, SSHCFG_ALL },
658 	{ "exposeauthinfo", sExposeAuthInfo, SSHCFG_ALL },
659 	{ "rdomain", sRDomain, SSHCFG_ALL },
660 	{ "casignaturealgorithms", sCASignatureAlgorithms, SSHCFG_ALL },
661 	{ NULL, sBadOption, 0 }
662 };
663 
664 static struct {
665 	int val;
666 	char *text;
667 } tunmode_desc[] = {
668 	{ SSH_TUNMODE_NO, "no" },
669 	{ SSH_TUNMODE_POINTOPOINT, "point-to-point" },
670 	{ SSH_TUNMODE_ETHERNET, "ethernet" },
671 	{ SSH_TUNMODE_YES, "yes" },
672 	{ -1, NULL }
673 };
674 
675 /* Returns an opcode name from its number */
676 
677 static const char *
678 lookup_opcode_name(ServerOpCodes code)
679 {
680 	u_int i;
681 
682 	for (i = 0; keywords[i].name != NULL; i++)
683 		if (keywords[i].opcode == code)
684 			return(keywords[i].name);
685 	return "UNKNOWN";
686 }
687 
688 
689 /*
690  * Returns the number of the token pointed to by cp or sBadOption.
691  */
692 
693 static ServerOpCodes
694 parse_token(const char *cp, const char *filename,
695 	    int linenum, u_int *flags)
696 {
697 	u_int i;
698 
699 	for (i = 0; keywords[i].name; i++)
700 		if (strcasecmp(cp, keywords[i].name) == 0) {
701 			*flags = keywords[i].flags;
702 			return keywords[i].opcode;
703 		}
704 
705 	error("%s: line %d: Bad configuration option: %s",
706 	    filename, linenum, cp);
707 	return sBadOption;
708 }
709 
710 char *
711 derelativise_path(const char *path)
712 {
713 	char *expanded, *ret, cwd[PATH_MAX];
714 
715 	if (strcasecmp(path, "none") == 0)
716 		return xstrdup("none");
717 	expanded = tilde_expand_filename(path, getuid());
718 	if (path_absolute(expanded))
719 		return expanded;
720 	if (getcwd(cwd, sizeof(cwd)) == NULL)
721 		fatal("%s: getcwd: %s", __func__, strerror(errno));
722 	xasprintf(&ret, "%s/%s", cwd, expanded);
723 	free(expanded);
724 	return ret;
725 }
726 
727 static void
728 add_listen_addr(ServerOptions *options, const char *addr,
729     const char *rdomain, int port)
730 {
731 	u_int i;
732 
733 	if (port > 0)
734 		add_one_listen_addr(options, addr, rdomain, port);
735 	else {
736 		for (i = 0; i < options->num_ports; i++) {
737 			add_one_listen_addr(options, addr, rdomain,
738 			    options->ports[i]);
739 		}
740 	}
741 }
742 
743 static void
744 add_one_listen_addr(ServerOptions *options, const char *addr,
745     const char *rdomain, int port)
746 {
747 	struct addrinfo hints, *ai, *aitop;
748 	char strport[NI_MAXSERV];
749 	int gaierr;
750 	u_int i;
751 
752 	/* Find listen_addrs entry for this rdomain */
753 	for (i = 0; i < options->num_listen_addrs; i++) {
754 		if (rdomain == NULL && options->listen_addrs[i].rdomain == NULL)
755 			break;
756 		if (rdomain == NULL || options->listen_addrs[i].rdomain == NULL)
757 			continue;
758 		if (strcmp(rdomain, options->listen_addrs[i].rdomain) == 0)
759 			break;
760 	}
761 	if (i >= options->num_listen_addrs) {
762 		/* No entry for this rdomain; allocate one */
763 		if (i >= INT_MAX)
764 			fatal("%s: too many listen addresses", __func__);
765 		options->listen_addrs = xrecallocarray(options->listen_addrs,
766 		    options->num_listen_addrs, options->num_listen_addrs + 1,
767 		    sizeof(*options->listen_addrs));
768 		i = options->num_listen_addrs++;
769 		if (rdomain != NULL)
770 			options->listen_addrs[i].rdomain = xstrdup(rdomain);
771 	}
772 	/* options->listen_addrs[i] points to the addresses for this rdomain */
773 
774 	memset(&hints, 0, sizeof(hints));
775 	hints.ai_family = options->address_family;
776 	hints.ai_socktype = SOCK_STREAM;
777 	hints.ai_flags = (addr == NULL) ? AI_PASSIVE : 0;
778 	snprintf(strport, sizeof strport, "%d", port);
779 	if ((gaierr = getaddrinfo(addr, strport, &hints, &aitop)) != 0)
780 		fatal("bad addr or host: %s (%s)",
781 		    addr ? addr : "<NULL>",
782 		    ssh_gai_strerror(gaierr));
783 	for (ai = aitop; ai->ai_next; ai = ai->ai_next)
784 		;
785 	ai->ai_next = options->listen_addrs[i].addrs;
786 	options->listen_addrs[i].addrs = aitop;
787 }
788 
789 /* Returns nonzero if the routing domain name is valid */
790 static int
791 valid_rdomain(const char *name)
792 {
793 #if defined(HAVE_SYS_VALID_RDOMAIN)
794 	return sys_valid_rdomain(name);
795 #elif defined(__OpenBSD__)
796 	const char *errstr;
797 	long long num;
798 	struct rt_tableinfo info;
799 	int mib[6];
800 	size_t miblen = sizeof(mib);
801 
802 	if (name == NULL)
803 		return 1;
804 
805 	num = strtonum(name, 0, 255, &errstr);
806 	if (errstr != NULL)
807 		return 0;
808 
809 	/* Check whether the table actually exists */
810 	memset(mib, 0, sizeof(mib));
811 	mib[0] = CTL_NET;
812 	mib[1] = PF_ROUTE;
813 	mib[4] = NET_RT_TABLE;
814 	mib[5] = (int)num;
815 	if (sysctl(mib, 6, &info, &miblen, NULL, 0) == -1)
816 		return 0;
817 
818 	return 1;
819 #else /* defined(__OpenBSD__) */
820 	error("Routing domains are not supported on this platform");
821 	return 0;
822 #endif
823 }
824 
825 /*
826  * Queue a ListenAddress to be processed once we have all of the Ports
827  * and AddressFamily options.
828  */
829 static void
830 queue_listen_addr(ServerOptions *options, const char *addr,
831     const char *rdomain, int port)
832 {
833 	struct queued_listenaddr *qla;
834 
835 	options->queued_listen_addrs = xrecallocarray(
836 	    options->queued_listen_addrs,
837 	    options->num_queued_listens, options->num_queued_listens + 1,
838 	    sizeof(*options->queued_listen_addrs));
839 	qla = &options->queued_listen_addrs[options->num_queued_listens++];
840 	qla->addr = xstrdup(addr);
841 	qla->port = port;
842 	qla->rdomain = rdomain == NULL ? NULL : xstrdup(rdomain);
843 }
844 
845 /*
846  * Process queued (text) ListenAddress entries.
847  */
848 static void
849 process_queued_listen_addrs(ServerOptions *options)
850 {
851 	u_int i;
852 	struct queued_listenaddr *qla;
853 
854 	if (options->num_ports == 0)
855 		options->ports[options->num_ports++] = SSH_DEFAULT_PORT;
856 	if (options->address_family == -1)
857 		options->address_family = AF_UNSPEC;
858 
859 	for (i = 0; i < options->num_queued_listens; i++) {
860 		qla = &options->queued_listen_addrs[i];
861 		add_listen_addr(options, qla->addr, qla->rdomain, qla->port);
862 		free(qla->addr);
863 		free(qla->rdomain);
864 	}
865 	free(options->queued_listen_addrs);
866 	options->queued_listen_addrs = NULL;
867 	options->num_queued_listens = 0;
868 }
869 
870 /*
871  * Inform channels layer of permitopen options for a single forwarding
872  * direction (local/remote).
873  */
874 static void
875 process_permitopen_list(struct ssh *ssh, ServerOpCodes opcode,
876     char **opens, u_int num_opens)
877 {
878 	u_int i;
879 	int port;
880 	char *host, *arg, *oarg, ch;
881 	int where = opcode == sPermitOpen ? FORWARD_LOCAL : FORWARD_REMOTE;
882 	const char *what = lookup_opcode_name(opcode);
883 
884 	channel_clear_permission(ssh, FORWARD_ADM, where);
885 	if (num_opens == 0)
886 		return; /* permit any */
887 
888 	/* handle keywords: "any" / "none" */
889 	if (num_opens == 1 && strcmp(opens[0], "any") == 0)
890 		return;
891 	if (num_opens == 1 && strcmp(opens[0], "none") == 0) {
892 		channel_disable_admin(ssh, where);
893 		return;
894 	}
895 	/* Otherwise treat it as a list of permitted host:port */
896 	for (i = 0; i < num_opens; i++) {
897 		oarg = arg = xstrdup(opens[i]);
898 		ch = '\0';
899 		host = hpdelim2(&arg, &ch);
900 		if (host == NULL || ch == '/')
901 			fatal("%s: missing host in %s", __func__, what);
902 		host = cleanhostname(host);
903 		if (arg == NULL || ((port = permitopen_port(arg)) < 0))
904 			fatal("%s: bad port number in %s", __func__, what);
905 		/* Send it to channels layer */
906 		channel_add_permission(ssh, FORWARD_ADM,
907 		    where, host, port);
908 		free(oarg);
909 	}
910 }
911 
912 /*
913  * Inform channels layer of permitopen options from configuration.
914  */
915 void
916 process_permitopen(struct ssh *ssh, ServerOptions *options)
917 {
918 	process_permitopen_list(ssh, sPermitOpen,
919 	    options->permitted_opens, options->num_permitted_opens);
920 	process_permitopen_list(ssh, sPermitListen,
921 	    options->permitted_listens,
922 	    options->num_permitted_listens);
923 }
924 
925 struct connection_info *
926 get_connection_info(struct ssh *ssh, int populate, int use_dns)
927 {
928 	static struct connection_info ci;
929 
930 	if (ssh == NULL || !populate)
931 		return &ci;
932 	ci.host = auth_get_canonical_hostname(ssh, use_dns);
933 	ci.address = ssh_remote_ipaddr(ssh);
934 	ci.laddress = ssh_local_ipaddr(ssh);
935 	ci.lport = ssh_local_port(ssh);
936 	ci.rdomain = ssh_packet_rdomain_in(ssh);
937 	return &ci;
938 }
939 
940 /*
941  * The strategy for the Match blocks is that the config file is parsed twice.
942  *
943  * The first time is at startup.  activep is initialized to 1 and the
944  * directives in the global context are processed and acted on.  Hitting a
945  * Match directive unsets activep and the directives inside the block are
946  * checked for syntax only.
947  *
948  * The second time is after a connection has been established but before
949  * authentication.  activep is initialized to 2 and global config directives
950  * are ignored since they have already been processed.  If the criteria in a
951  * Match block is met, activep is set and the subsequent directives
952  * processed and actioned until EOF or another Match block unsets it.  Any
953  * options set are copied into the main server config.
954  *
955  * Potential additions/improvements:
956  *  - Add Match support for pre-kex directives, eg. Ciphers.
957  *
958  *  - Add a Tag directive (idea from David Leonard) ala pf, eg:
959  *	Match Address 192.168.0.*
960  *		Tag trusted
961  *	Match Group wheel
962  *		Tag trusted
963  *	Match Tag trusted
964  *		AllowTcpForwarding yes
965  *		GatewayPorts clientspecified
966  *		[...]
967  *
968  *  - Add a PermittedChannelRequests directive
969  *	Match Group shell
970  *		PermittedChannelRequests session,forwarded-tcpip
971  */
972 
973 static int
974 match_cfg_line_group(const char *grps, int line, const char *user)
975 {
976 	int result = 0;
977 	struct passwd *pw;
978 
979 	if (user == NULL)
980 		goto out;
981 
982 	if ((pw = getpwnam(user)) == NULL) {
983 		debug("Can't match group at line %d because user %.100s does "
984 		    "not exist", line, user);
985 	} else if (ga_init(pw->pw_name, pw->pw_gid) == 0) {
986 		debug("Can't Match group because user %.100s not in any group "
987 		    "at line %d", user, line);
988 	} else if (ga_match_pattern_list(grps) != 1) {
989 		debug("user %.100s does not match group list %.100s at line %d",
990 		    user, grps, line);
991 	} else {
992 		debug("user %.100s matched group list %.100s at line %d", user,
993 		    grps, line);
994 		result = 1;
995 	}
996 out:
997 	ga_free();
998 	return result;
999 }
1000 
1001 static void
1002 match_test_missing_fatal(const char *criteria, const char *attrib)
1003 {
1004 	fatal("'Match %s' in configuration but '%s' not in connection "
1005 	    "test specification.", criteria, attrib);
1006 }
1007 
1008 /*
1009  * All of the attributes on a single Match line are ANDed together, so we need
1010  * to check every attribute and set the result to zero if any attribute does
1011  * not match.
1012  */
1013 static int
1014 match_cfg_line(char **condition, int line, struct connection_info *ci)
1015 {
1016 	int result = 1, attributes = 0, port;
1017 	char *arg, *attrib, *cp = *condition;
1018 
1019 	if (ci == NULL)
1020 		debug3("checking syntax for 'Match %s'", cp);
1021 	else
1022 		debug3("checking match for '%s' user %s host %s addr %s "
1023 		    "laddr %s lport %d", cp, ci->user ? ci->user : "(null)",
1024 		    ci->host ? ci->host : "(null)",
1025 		    ci->address ? ci->address : "(null)",
1026 		    ci->laddress ? ci->laddress : "(null)", ci->lport);
1027 
1028 	while ((attrib = strdelim(&cp)) && *attrib != '\0') {
1029 		attributes++;
1030 		if (strcasecmp(attrib, "all") == 0) {
1031 			if (attributes != 1 ||
1032 			    ((arg = strdelim(&cp)) != NULL && *arg != '\0')) {
1033 				error("'all' cannot be combined with other "
1034 				    "Match attributes");
1035 				return -1;
1036 			}
1037 			*condition = cp;
1038 			return 1;
1039 		}
1040 		if ((arg = strdelim(&cp)) == NULL || *arg == '\0') {
1041 			error("Missing Match criteria for %s", attrib);
1042 			return -1;
1043 		}
1044 		if (strcasecmp(attrib, "user") == 0) {
1045 			if (ci == NULL) {
1046 				result = 0;
1047 				continue;
1048 			}
1049 			if (ci->user == NULL)
1050 				match_test_missing_fatal("User", "user");
1051 			if (match_usergroup_pattern_list(ci->user, arg) != 1)
1052 				result = 0;
1053 			else
1054 				debug("user %.100s matched 'User %.100s' at "
1055 				    "line %d", ci->user, arg, line);
1056 		} else if (strcasecmp(attrib, "group") == 0) {
1057 			if (ci == NULL) {
1058 				result = 0;
1059 				continue;
1060 			}
1061 			if (ci->user == NULL)
1062 				match_test_missing_fatal("Group", "user");
1063 			switch (match_cfg_line_group(arg, line, ci->user)) {
1064 			case -1:
1065 				return -1;
1066 			case 0:
1067 				result = 0;
1068 			}
1069 		} else if (strcasecmp(attrib, "host") == 0) {
1070 			if (ci == NULL) {
1071 				result = 0;
1072 				continue;
1073 			}
1074 			if (ci->host == NULL)
1075 				match_test_missing_fatal("Host", "host");
1076 			if (match_hostname(ci->host, arg) != 1)
1077 				result = 0;
1078 			else
1079 				debug("connection from %.100s matched 'Host "
1080 				    "%.100s' at line %d", ci->host, arg, line);
1081 		} else if (strcasecmp(attrib, "address") == 0) {
1082 			if (ci == NULL) {
1083 				result = 0;
1084 				continue;
1085 			}
1086 			if (ci->address == NULL)
1087 				match_test_missing_fatal("Address", "addr");
1088 			switch (addr_match_list(ci->address, arg)) {
1089 			case 1:
1090 				debug("connection from %.100s matched 'Address "
1091 				    "%.100s' at line %d", ci->address, arg, line);
1092 				break;
1093 			case 0:
1094 			case -1:
1095 				result = 0;
1096 				break;
1097 			case -2:
1098 				return -1;
1099 			}
1100 		} else if (strcasecmp(attrib, "localaddress") == 0){
1101 			if (ci == NULL) {
1102 				result = 0;
1103 				continue;
1104 			}
1105 			if (ci->laddress == NULL)
1106 				match_test_missing_fatal("LocalAddress",
1107 				    "laddr");
1108 			switch (addr_match_list(ci->laddress, arg)) {
1109 			case 1:
1110 				debug("connection from %.100s matched "
1111 				    "'LocalAddress %.100s' at line %d",
1112 				    ci->laddress, arg, line);
1113 				break;
1114 			case 0:
1115 			case -1:
1116 				result = 0;
1117 				break;
1118 			case -2:
1119 				return -1;
1120 			}
1121 		} else if (strcasecmp(attrib, "localport") == 0) {
1122 			if ((port = a2port(arg)) == -1) {
1123 				error("Invalid LocalPort '%s' on Match line",
1124 				    arg);
1125 				return -1;
1126 			}
1127 			if (ci == NULL) {
1128 				result = 0;
1129 				continue;
1130 			}
1131 			if (ci->lport == 0)
1132 				match_test_missing_fatal("LocalPort", "lport");
1133 			/* TODO support port lists */
1134 			if (port == ci->lport)
1135 				debug("connection from %.100s matched "
1136 				    "'LocalPort %d' at line %d",
1137 				    ci->laddress, port, line);
1138 			else
1139 				result = 0;
1140 		} else if (strcasecmp(attrib, "rdomain") == 0) {
1141 			if (ci == NULL || ci->rdomain == NULL) {
1142 				result = 0;
1143 				continue;
1144 			}
1145 			if (match_pattern_list(ci->rdomain, arg, 0) != 1)
1146 				result = 0;
1147 			else
1148 				debug("user %.100s matched 'RDomain %.100s' at "
1149 				    "line %d", ci->rdomain, arg, line);
1150 		} else {
1151 			error("Unsupported Match attribute %s", attrib);
1152 			return -1;
1153 		}
1154 	}
1155 	if (attributes == 0) {
1156 		error("One or more attributes required for Match");
1157 		return -1;
1158 	}
1159 	if (ci != NULL)
1160 		debug3("match %sfound", result ? "" : "not ");
1161 	*condition = cp;
1162 	return result;
1163 }
1164 
1165 #define WHITESPACE " \t\r\n"
1166 
1167 /* Multistate option parsing */
1168 struct multistate {
1169 	char *key;
1170 	int value;
1171 };
1172 static const struct multistate multistate_flag[] = {
1173 	{ "yes",			1 },
1174 	{ "no",				0 },
1175 	{ NULL, -1 }
1176 };
1177 static const struct multistate multistate_addressfamily[] = {
1178 	{ "inet",			AF_INET },
1179 	{ "inet6",			AF_INET6 },
1180 	{ "any",			AF_UNSPEC },
1181 	{ NULL, -1 }
1182 };
1183 static const struct multistate multistate_permitrootlogin[] = {
1184 	{ "without-password",		PERMIT_NO_PASSWD },
1185 	{ "prohibit-password",		PERMIT_NO_PASSWD },
1186 	{ "forced-commands-only",	PERMIT_FORCED_ONLY },
1187 	{ "yes",			PERMIT_YES },
1188 	{ "no",				PERMIT_NO },
1189 	{ NULL, -1 }
1190 };
1191 static const struct multistate multistate_compression[] = {
1192 	{ "yes",			COMP_DELAYED },
1193 	{ "delayed",			COMP_DELAYED },
1194 	{ "no",				COMP_NONE },
1195 	{ NULL, -1 }
1196 };
1197 static const struct multistate multistate_gatewayports[] = {
1198 	{ "clientspecified",		2 },
1199 	{ "yes",			1 },
1200 	{ "no",				0 },
1201 	{ NULL, -1 }
1202 };
1203 static const struct multistate multistate_tcpfwd[] = {
1204 	{ "yes",			FORWARD_ALLOW },
1205 	{ "all",			FORWARD_ALLOW },
1206 	{ "no",				FORWARD_DENY },
1207 	{ "remote",			FORWARD_REMOTE },
1208 	{ "local",			FORWARD_LOCAL },
1209 	{ NULL, -1 }
1210 };
1211 
1212 int
1213 process_server_config_line(ServerOptions *options, char *line,
1214     const char *filename, int linenum, int *activep,
1215     struct connection_info *connectinfo)
1216 {
1217 	char ch, *cp, ***chararrayptr, **charptr, *arg, *arg2, *p;
1218 	int cmdline = 0, *intptr, value, value2, n, port;
1219 	SyslogFacility *log_facility_ptr;
1220 	LogLevel *log_level_ptr;
1221 	ServerOpCodes opcode;
1222 	u_int i, *uintptr, uvalue, flags = 0;
1223 	size_t len;
1224 	long long val64;
1225 	const struct multistate *multistate_ptr;
1226 	const char *errstr;
1227 
1228 	/* Strip trailing whitespace. Allow \f (form feed) at EOL only */
1229 	if ((len = strlen(line)) == 0)
1230 		return 0;
1231 	for (len--; len > 0; len--) {
1232 		if (strchr(WHITESPACE "\f", line[len]) == NULL)
1233 			break;
1234 		line[len] = '\0';
1235 	}
1236 
1237 	cp = line;
1238 	if ((arg = strdelim(&cp)) == NULL)
1239 		return 0;
1240 	/* Ignore leading whitespace */
1241 	if (*arg == '\0')
1242 		arg = strdelim(&cp);
1243 	if (!arg || !*arg || *arg == '#')
1244 		return 0;
1245 	intptr = NULL;
1246 	charptr = NULL;
1247 	opcode = parse_token(arg, filename, linenum, &flags);
1248 
1249 	if (activep == NULL) { /* We are processing a command line directive */
1250 		cmdline = 1;
1251 		activep = &cmdline;
1252 	}
1253 	if (*activep && opcode != sMatch)
1254 		debug3("%s:%d setting %s %s", filename, linenum, arg, cp);
1255 	if (*activep == 0 && !(flags & SSHCFG_MATCH)) {
1256 		if (connectinfo == NULL) {
1257 			fatal("%s line %d: Directive '%s' is not allowed "
1258 			    "within a Match block", filename, linenum, arg);
1259 		} else { /* this is a directive we have already processed */
1260 			while (arg)
1261 				arg = strdelim(&cp);
1262 			return 0;
1263 		}
1264 	}
1265 
1266 	switch (opcode) {
1267 	/* Portable-specific options */
1268 	case sUsePAM:
1269 		intptr = &options->use_pam;
1270 		goto parse_flag;
1271 
1272 	/* Standard Options */
1273 	case sBadOption:
1274 		return -1;
1275 	case sPort:
1276 		/* ignore ports from configfile if cmdline specifies ports */
1277 		if (options->ports_from_cmdline)
1278 			return 0;
1279 		if (options->num_ports >= MAX_PORTS)
1280 			fatal("%s line %d: too many ports.",
1281 			    filename, linenum);
1282 		arg = strdelim(&cp);
1283 		if (!arg || *arg == '\0')
1284 			fatal("%s line %d: missing port number.",
1285 			    filename, linenum);
1286 		options->ports[options->num_ports++] = a2port(arg);
1287 		if (options->ports[options->num_ports-1] <= 0)
1288 			fatal("%s line %d: Badly formatted port number.",
1289 			    filename, linenum);
1290 		break;
1291 
1292 	case sLoginGraceTime:
1293 		intptr = &options->login_grace_time;
1294  parse_time:
1295 		arg = strdelim(&cp);
1296 		if (!arg || *arg == '\0')
1297 			fatal("%s line %d: missing time value.",
1298 			    filename, linenum);
1299 		if ((value = convtime(arg)) == -1)
1300 			fatal("%s line %d: invalid time value.",
1301 			    filename, linenum);
1302 		if (*activep && *intptr == -1)
1303 			*intptr = value;
1304 		break;
1305 
1306 	case sListenAddress:
1307 		arg = strdelim(&cp);
1308 		if (arg == NULL || *arg == '\0')
1309 			fatal("%s line %d: missing address",
1310 			    filename, linenum);
1311 		/* check for bare IPv6 address: no "[]" and 2 or more ":" */
1312 		if (strchr(arg, '[') == NULL && (p = strchr(arg, ':')) != NULL
1313 		    && strchr(p+1, ':') != NULL) {
1314 			port = 0;
1315 			p = arg;
1316 		} else {
1317 			arg2 = NULL;
1318 			ch = '\0';
1319 			p = hpdelim2(&arg, &ch);
1320 			if (p == NULL || ch == '/')
1321 				fatal("%s line %d: bad address:port usage",
1322 				    filename, linenum);
1323 			p = cleanhostname(p);
1324 			if (arg == NULL)
1325 				port = 0;
1326 			else if ((port = a2port(arg)) <= 0)
1327 				fatal("%s line %d: bad port number",
1328 				    filename, linenum);
1329 		}
1330 		/* Optional routing table */
1331 		arg2 = NULL;
1332 		if ((arg = strdelim(&cp)) != NULL) {
1333 			if (strcmp(arg, "rdomain") != 0 ||
1334 			    (arg2 = strdelim(&cp)) == NULL)
1335 				fatal("%s line %d: bad ListenAddress syntax",
1336 				    filename, linenum);
1337 			if (!valid_rdomain(arg2))
1338 				fatal("%s line %d: bad routing domain",
1339 				    filename, linenum);
1340 		}
1341 
1342 		queue_listen_addr(options, p, arg2, port);
1343 
1344 		break;
1345 
1346 	case sAddressFamily:
1347 		intptr = &options->address_family;
1348 		multistate_ptr = multistate_addressfamily;
1349  parse_multistate:
1350 		arg = strdelim(&cp);
1351 		if (!arg || *arg == '\0')
1352 			fatal("%s line %d: missing argument.",
1353 			    filename, linenum);
1354 		value = -1;
1355 		for (i = 0; multistate_ptr[i].key != NULL; i++) {
1356 			if (strcasecmp(arg, multistate_ptr[i].key) == 0) {
1357 				value = multistate_ptr[i].value;
1358 				break;
1359 			}
1360 		}
1361 		if (value == -1)
1362 			fatal("%s line %d: unsupported option \"%s\".",
1363 			    filename, linenum, arg);
1364 		if (*activep && *intptr == -1)
1365 			*intptr = value;
1366 		break;
1367 
1368 	case sHostKeyFile:
1369 		arg = strdelim(&cp);
1370 		if (!arg || *arg == '\0')
1371 			fatal("%s line %d: missing file name.",
1372 			    filename, linenum);
1373 		if (*activep) {
1374 			servconf_add_hostkey(filename, linenum,
1375 			    options, arg, 1);
1376 		}
1377 		break;
1378 
1379 	case sHostKeyAgent:
1380 		charptr = &options->host_key_agent;
1381 		arg = strdelim(&cp);
1382 		if (!arg || *arg == '\0')
1383 			fatal("%s line %d: missing socket name.",
1384 			    filename, linenum);
1385 		if (*activep && *charptr == NULL)
1386 			*charptr = !strcmp(arg, SSH_AUTHSOCKET_ENV_NAME) ?
1387 			    xstrdup(arg) : derelativise_path(arg);
1388 		break;
1389 
1390 	case sHostCertificate:
1391 		arg = strdelim(&cp);
1392 		if (!arg || *arg == '\0')
1393 			fatal("%s line %d: missing file name.",
1394 			    filename, linenum);
1395 		if (*activep)
1396 			servconf_add_hostcert(filename, linenum, options, arg);
1397 		break;
1398 
1399 	case sPidFile:
1400 		charptr = &options->pid_file;
1401  parse_filename:
1402 		arg = strdelim(&cp);
1403 		if (!arg || *arg == '\0')
1404 			fatal("%s line %d: missing file name.",
1405 			    filename, linenum);
1406 		if (*activep && *charptr == NULL) {
1407 			*charptr = derelativise_path(arg);
1408 			/* increase optional counter */
1409 			if (intptr != NULL)
1410 				*intptr = *intptr + 1;
1411 		}
1412 		break;
1413 
1414 	case sPermitRootLogin:
1415 		intptr = &options->permit_root_login;
1416 		multistate_ptr = multistate_permitrootlogin;
1417 		goto parse_multistate;
1418 
1419 	case sIgnoreRhosts:
1420 		intptr = &options->ignore_rhosts;
1421  parse_flag:
1422 		multistate_ptr = multistate_flag;
1423 		goto parse_multistate;
1424 
1425 	case sIgnoreUserKnownHosts:
1426 		intptr = &options->ignore_user_known_hosts;
1427 		goto parse_flag;
1428 
1429 	case sHostbasedAuthentication:
1430 		intptr = &options->hostbased_authentication;
1431 		goto parse_flag;
1432 
1433 	case sHostbasedUsesNameFromPacketOnly:
1434 		intptr = &options->hostbased_uses_name_from_packet_only;
1435 		goto parse_flag;
1436 
1437 	case sHostbasedAcceptedKeyTypes:
1438 		charptr = &options->hostbased_key_types;
1439  parse_keytypes:
1440 		arg = strdelim(&cp);
1441 		if (!arg || *arg == '\0')
1442 			fatal("%s line %d: Missing argument.",
1443 			    filename, linenum);
1444 		if (*arg != '-' &&
1445 		    !sshkey_names_valid2(*arg == '+' ? arg + 1 : arg, 1))
1446 			fatal("%s line %d: Bad key types '%s'.",
1447 			    filename, linenum, arg ? arg : "<NONE>");
1448 		if (*activep && *charptr == NULL)
1449 			*charptr = xstrdup(arg);
1450 		break;
1451 
1452 	case sHostKeyAlgorithms:
1453 		charptr = &options->hostkeyalgorithms;
1454 		goto parse_keytypes;
1455 
1456 	case sCASignatureAlgorithms:
1457 		charptr = &options->ca_sign_algorithms;
1458 		goto parse_keytypes;
1459 
1460 	case sPubkeyAuthentication:
1461 		intptr = &options->pubkey_authentication;
1462 		goto parse_flag;
1463 
1464 	case sPubkeyAcceptedKeyTypes:
1465 		charptr = &options->pubkey_key_types;
1466 		goto parse_keytypes;
1467 
1468 	case sKerberosAuthentication:
1469 		intptr = &options->kerberos_authentication;
1470 		goto parse_flag;
1471 
1472 	case sKerberosOrLocalPasswd:
1473 		intptr = &options->kerberos_or_local_passwd;
1474 		goto parse_flag;
1475 
1476 	case sKerberosTicketCleanup:
1477 		intptr = &options->kerberos_ticket_cleanup;
1478 		goto parse_flag;
1479 
1480 	case sKerberosGetAFSToken:
1481 		intptr = &options->kerberos_get_afs_token;
1482 		goto parse_flag;
1483 
1484 	case sGssAuthentication:
1485 		intptr = &options->gss_authentication;
1486 		goto parse_flag;
1487 
1488 	case sGssCleanupCreds:
1489 		intptr = &options->gss_cleanup_creds;
1490 		goto parse_flag;
1491 
1492 	case sGssStrictAcceptor:
1493 		intptr = &options->gss_strict_acceptor;
1494 		goto parse_flag;
1495 
1496 	case sPasswordAuthentication:
1497 		intptr = &options->password_authentication;
1498 		goto parse_flag;
1499 
1500 	case sKbdInteractiveAuthentication:
1501 		intptr = &options->kbd_interactive_authentication;
1502 		goto parse_flag;
1503 
1504 	case sChallengeResponseAuthentication:
1505 		intptr = &options->challenge_response_authentication;
1506 		goto parse_flag;
1507 
1508 	case sPrintMotd:
1509 		intptr = &options->print_motd;
1510 		goto parse_flag;
1511 
1512 	case sPrintLastLog:
1513 		intptr = &options->print_lastlog;
1514 		goto parse_flag;
1515 
1516 	case sX11Forwarding:
1517 		intptr = &options->x11_forwarding;
1518 		goto parse_flag;
1519 
1520 	case sX11DisplayOffset:
1521 		intptr = &options->x11_display_offset;
1522  parse_int:
1523 		arg = strdelim(&cp);
1524 		if ((errstr = atoi_err(arg, &value)) != NULL)
1525 			fatal("%s line %d: integer value %s.",
1526 			    filename, linenum, errstr);
1527 		if (*activep && *intptr == -1)
1528 			*intptr = value;
1529 		break;
1530 
1531 	case sX11UseLocalhost:
1532 		intptr = &options->x11_use_localhost;
1533 		goto parse_flag;
1534 
1535 	case sXAuthLocation:
1536 		charptr = &options->xauth_location;
1537 		goto parse_filename;
1538 
1539 	case sPermitTTY:
1540 		intptr = &options->permit_tty;
1541 		goto parse_flag;
1542 
1543 	case sPermitUserRC:
1544 		intptr = &options->permit_user_rc;
1545 		goto parse_flag;
1546 
1547 	case sStrictModes:
1548 		intptr = &options->strict_modes;
1549 		goto parse_flag;
1550 
1551 	case sTCPKeepAlive:
1552 		intptr = &options->tcp_keep_alive;
1553 		goto parse_flag;
1554 
1555 	case sEmptyPasswd:
1556 		intptr = &options->permit_empty_passwd;
1557 		goto parse_flag;
1558 
1559 	case sPermitUserEnvironment:
1560 		intptr = &options->permit_user_env;
1561 		charptr = &options->permit_user_env_whitelist;
1562 		arg = strdelim(&cp);
1563 		if (!arg || *arg == '\0')
1564 			fatal("%s line %d: missing argument.",
1565 			    filename, linenum);
1566 		value = 0;
1567 		p = NULL;
1568 		if (strcmp(arg, "yes") == 0)
1569 			value = 1;
1570 		else if (strcmp(arg, "no") == 0)
1571 			value = 0;
1572 		else {
1573 			/* Pattern-list specified */
1574 			value = 1;
1575 			p = xstrdup(arg);
1576 		}
1577 		if (*activep && *intptr == -1) {
1578 			*intptr = value;
1579 			*charptr = p;
1580 			p = NULL;
1581 		}
1582 		free(p);
1583 		break;
1584 
1585 	case sCompression:
1586 		intptr = &options->compression;
1587 		multistate_ptr = multistate_compression;
1588 		goto parse_multistate;
1589 
1590 	case sRekeyLimit:
1591 		arg = strdelim(&cp);
1592 		if (!arg || *arg == '\0')
1593 			fatal("%.200s line %d: Missing argument.", filename,
1594 			    linenum);
1595 		if (strcmp(arg, "default") == 0) {
1596 			val64 = 0;
1597 		} else {
1598 			if (scan_scaled(arg, &val64) == -1)
1599 				fatal("%.200s line %d: Bad number '%s': %s",
1600 				    filename, linenum, arg, strerror(errno));
1601 			if (val64 != 0 && val64 < 16)
1602 				fatal("%.200s line %d: RekeyLimit too small",
1603 				    filename, linenum);
1604 		}
1605 		if (*activep && options->rekey_limit == -1)
1606 			options->rekey_limit = val64;
1607 		if (cp != NULL) { /* optional rekey interval present */
1608 			if (strcmp(cp, "none") == 0) {
1609 				(void)strdelim(&cp);	/* discard */
1610 				break;
1611 			}
1612 			intptr = &options->rekey_interval;
1613 			goto parse_time;
1614 		}
1615 		break;
1616 
1617 	case sGatewayPorts:
1618 		intptr = &options->fwd_opts.gateway_ports;
1619 		multistate_ptr = multistate_gatewayports;
1620 		goto parse_multistate;
1621 
1622 	case sUseDNS:
1623 		intptr = &options->use_dns;
1624 		goto parse_flag;
1625 
1626 	case sLogFacility:
1627 		log_facility_ptr = &options->log_facility;
1628 		arg = strdelim(&cp);
1629 		value = log_facility_number(arg);
1630 		if (value == SYSLOG_FACILITY_NOT_SET)
1631 			fatal("%.200s line %d: unsupported log facility '%s'",
1632 			    filename, linenum, arg ? arg : "<NONE>");
1633 		if (*log_facility_ptr == -1)
1634 			*log_facility_ptr = (SyslogFacility) value;
1635 		break;
1636 
1637 	case sLogLevel:
1638 		log_level_ptr = &options->log_level;
1639 		arg = strdelim(&cp);
1640 		value = log_level_number(arg);
1641 		if (value == SYSLOG_LEVEL_NOT_SET)
1642 			fatal("%.200s line %d: unsupported log level '%s'",
1643 			    filename, linenum, arg ? arg : "<NONE>");
1644 		if (*activep && *log_level_ptr == -1)
1645 			*log_level_ptr = (LogLevel) value;
1646 		break;
1647 
1648 	case sAllowTcpForwarding:
1649 		intptr = &options->allow_tcp_forwarding;
1650 		multistate_ptr = multistate_tcpfwd;
1651 		goto parse_multistate;
1652 
1653 	case sAllowStreamLocalForwarding:
1654 		intptr = &options->allow_streamlocal_forwarding;
1655 		multistate_ptr = multistate_tcpfwd;
1656 		goto parse_multistate;
1657 
1658 	case sAllowAgentForwarding:
1659 		intptr = &options->allow_agent_forwarding;
1660 		goto parse_flag;
1661 
1662 	case sDisableForwarding:
1663 		intptr = &options->disable_forwarding;
1664 		goto parse_flag;
1665 
1666 	case sAllowUsers:
1667 		while ((arg = strdelim(&cp)) && *arg != '\0') {
1668 			if (match_user(NULL, NULL, NULL, arg) == -1)
1669 				fatal("%s line %d: invalid AllowUsers pattern: "
1670 				    "\"%.100s\"", filename, linenum, arg);
1671 			if (!*activep)
1672 				continue;
1673 			array_append(filename, linenum, "AllowUsers",
1674 			    &options->allow_users, &options->num_allow_users,
1675 			    arg);
1676 		}
1677 		break;
1678 
1679 	case sDenyUsers:
1680 		while ((arg = strdelim(&cp)) && *arg != '\0') {
1681 			if (match_user(NULL, NULL, NULL, arg) == -1)
1682 				fatal("%s line %d: invalid DenyUsers pattern: "
1683 				    "\"%.100s\"", filename, linenum, arg);
1684 			if (!*activep)
1685 				continue;
1686 			array_append(filename, linenum, "DenyUsers",
1687 			    &options->deny_users, &options->num_deny_users,
1688 			    arg);
1689 		}
1690 		break;
1691 
1692 	case sAllowGroups:
1693 		while ((arg = strdelim(&cp)) && *arg != '\0') {
1694 			if (!*activep)
1695 				continue;
1696 			array_append(filename, linenum, "AllowGroups",
1697 			    &options->allow_groups, &options->num_allow_groups,
1698 			    arg);
1699 		}
1700 		break;
1701 
1702 	case sDenyGroups:
1703 		while ((arg = strdelim(&cp)) && *arg != '\0') {
1704 			if (!*activep)
1705 				continue;
1706 			array_append(filename, linenum, "DenyGroups",
1707 			    &options->deny_groups, &options->num_deny_groups,
1708 			    arg);
1709 		}
1710 		break;
1711 
1712 	case sCiphers:
1713 		arg = strdelim(&cp);
1714 		if (!arg || *arg == '\0')
1715 			fatal("%s line %d: Missing argument.", filename, linenum);
1716 		if (*arg != '-' && !ciphers_valid(*arg == '+' ? arg + 1 : arg))
1717 			fatal("%s line %d: Bad SSH2 cipher spec '%s'.",
1718 			    filename, linenum, arg ? arg : "<NONE>");
1719 		if (options->ciphers == NULL)
1720 			options->ciphers = xstrdup(arg);
1721 		break;
1722 
1723 	case sMacs:
1724 		arg = strdelim(&cp);
1725 		if (!arg || *arg == '\0')
1726 			fatal("%s line %d: Missing argument.", filename, linenum);
1727 		if (*arg != '-' && !mac_valid(*arg == '+' ? arg + 1 : arg))
1728 			fatal("%s line %d: Bad SSH2 mac spec '%s'.",
1729 			    filename, linenum, arg ? arg : "<NONE>");
1730 		if (options->macs == NULL)
1731 			options->macs = xstrdup(arg);
1732 		break;
1733 
1734 	case sKexAlgorithms:
1735 		arg = strdelim(&cp);
1736 		if (!arg || *arg == '\0')
1737 			fatal("%s line %d: Missing argument.",
1738 			    filename, linenum);
1739 		if (*arg != '-' &&
1740 		    !kex_names_valid(*arg == '+' ? arg + 1 : arg))
1741 			fatal("%s line %d: Bad SSH2 KexAlgorithms '%s'.",
1742 			    filename, linenum, arg ? arg : "<NONE>");
1743 		if (options->kex_algorithms == NULL)
1744 			options->kex_algorithms = xstrdup(arg);
1745 		break;
1746 
1747 	case sSubsystem:
1748 		if (options->num_subsystems >= MAX_SUBSYSTEMS) {
1749 			fatal("%s line %d: too many subsystems defined.",
1750 			    filename, linenum);
1751 		}
1752 		arg = strdelim(&cp);
1753 		if (!arg || *arg == '\0')
1754 			fatal("%s line %d: Missing subsystem name.",
1755 			    filename, linenum);
1756 		if (!*activep) {
1757 			arg = strdelim(&cp);
1758 			break;
1759 		}
1760 		for (i = 0; i < options->num_subsystems; i++)
1761 			if (strcmp(arg, options->subsystem_name[i]) == 0)
1762 				fatal("%s line %d: Subsystem '%s' already defined.",
1763 				    filename, linenum, arg);
1764 		options->subsystem_name[options->num_subsystems] = xstrdup(arg);
1765 		arg = strdelim(&cp);
1766 		if (!arg || *arg == '\0')
1767 			fatal("%s line %d: Missing subsystem command.",
1768 			    filename, linenum);
1769 		options->subsystem_command[options->num_subsystems] = xstrdup(arg);
1770 
1771 		/* Collect arguments (separate to executable) */
1772 		p = xstrdup(arg);
1773 		len = strlen(p) + 1;
1774 		while ((arg = strdelim(&cp)) != NULL && *arg != '\0') {
1775 			len += 1 + strlen(arg);
1776 			p = xreallocarray(p, 1, len);
1777 			strlcat(p, " ", len);
1778 			strlcat(p, arg, len);
1779 		}
1780 		options->subsystem_args[options->num_subsystems] = p;
1781 		options->num_subsystems++;
1782 		break;
1783 
1784 	case sMaxStartups:
1785 		arg = strdelim(&cp);
1786 		if (!arg || *arg == '\0')
1787 			fatal("%s line %d: Missing MaxStartups spec.",
1788 			    filename, linenum);
1789 		if ((n = sscanf(arg, "%d:%d:%d",
1790 		    &options->max_startups_begin,
1791 		    &options->max_startups_rate,
1792 		    &options->max_startups)) == 3) {
1793 			if (options->max_startups_begin >
1794 			    options->max_startups ||
1795 			    options->max_startups_rate > 100 ||
1796 			    options->max_startups_rate < 1)
1797 				fatal("%s line %d: Illegal MaxStartups spec.",
1798 				    filename, linenum);
1799 		} else if (n != 1)
1800 			fatal("%s line %d: Illegal MaxStartups spec.",
1801 			    filename, linenum);
1802 		else
1803 			options->max_startups = options->max_startups_begin;
1804 		break;
1805 
1806 	case sMaxAuthTries:
1807 		intptr = &options->max_authtries;
1808 		goto parse_int;
1809 
1810 	case sMaxSessions:
1811 		intptr = &options->max_sessions;
1812 		goto parse_int;
1813 
1814 	case sBanner:
1815 		charptr = &options->banner;
1816 		goto parse_filename;
1817 
1818 	/*
1819 	 * These options can contain %X options expanded at
1820 	 * connect time, so that you can specify paths like:
1821 	 *
1822 	 * AuthorizedKeysFile	/etc/ssh_keys/%u
1823 	 */
1824 	case sAuthorizedKeysFile:
1825 		if (*activep && options->num_authkeys_files == 0) {
1826 			while ((arg = strdelim(&cp)) && *arg != '\0') {
1827 				arg = tilde_expand_filename(arg, getuid());
1828 				array_append(filename, linenum,
1829 				    "AuthorizedKeysFile",
1830 				    &options->authorized_keys_files,
1831 				    &options->num_authkeys_files, arg);
1832 				free(arg);
1833 			}
1834 		}
1835 		return 0;
1836 
1837 	case sAuthorizedPrincipalsFile:
1838 		charptr = &options->authorized_principals_file;
1839 		arg = strdelim(&cp);
1840 		if (!arg || *arg == '\0')
1841 			fatal("%s line %d: missing file name.",
1842 			    filename, linenum);
1843 		if (*activep && *charptr == NULL) {
1844 			*charptr = tilde_expand_filename(arg, getuid());
1845 			/* increase optional counter */
1846 			if (intptr != NULL)
1847 				*intptr = *intptr + 1;
1848 		}
1849 		break;
1850 
1851 	case sClientAliveInterval:
1852 		intptr = &options->client_alive_interval;
1853 		goto parse_time;
1854 
1855 	case sClientAliveCountMax:
1856 		intptr = &options->client_alive_count_max;
1857 		goto parse_int;
1858 
1859 	case sAcceptEnv:
1860 		while ((arg = strdelim(&cp)) && *arg != '\0') {
1861 			if (strchr(arg, '=') != NULL)
1862 				fatal("%s line %d: Invalid environment name.",
1863 				    filename, linenum);
1864 			if (!*activep)
1865 				continue;
1866 			array_append(filename, linenum, "AcceptEnv",
1867 			    &options->accept_env, &options->num_accept_env,
1868 			    arg);
1869 		}
1870 		break;
1871 
1872 	case sSetEnv:
1873 		uvalue = options->num_setenv;
1874 		while ((arg = strdelimw(&cp)) && *arg != '\0') {
1875 			if (strchr(arg, '=') == NULL)
1876 				fatal("%s line %d: Invalid environment.",
1877 				    filename, linenum);
1878 			if (!*activep || uvalue != 0)
1879 				continue;
1880 			array_append(filename, linenum, "SetEnv",
1881 			    &options->setenv, &options->num_setenv, arg);
1882 		}
1883 		break;
1884 
1885 	case sPermitTunnel:
1886 		intptr = &options->permit_tun;
1887 		arg = strdelim(&cp);
1888 		if (!arg || *arg == '\0')
1889 			fatal("%s line %d: Missing yes/point-to-point/"
1890 			    "ethernet/no argument.", filename, linenum);
1891 		value = -1;
1892 		for (i = 0; tunmode_desc[i].val != -1; i++)
1893 			if (strcmp(tunmode_desc[i].text, arg) == 0) {
1894 				value = tunmode_desc[i].val;
1895 				break;
1896 			}
1897 		if (value == -1)
1898 			fatal("%s line %d: Bad yes/point-to-point/ethernet/"
1899 			    "no argument: %s", filename, linenum, arg);
1900 		if (*activep && *intptr == -1)
1901 			*intptr = value;
1902 		break;
1903 
1904 	case sMatch:
1905 		if (cmdline)
1906 			fatal("Match directive not supported as a command-line "
1907 			   "option");
1908 		value = match_cfg_line(&cp, linenum, connectinfo);
1909 		if (value < 0)
1910 			fatal("%s line %d: Bad Match condition", filename,
1911 			    linenum);
1912 		*activep = value;
1913 		break;
1914 
1915 	case sPermitListen:
1916 	case sPermitOpen:
1917 		if (opcode == sPermitListen) {
1918 			uintptr = &options->num_permitted_listens;
1919 			chararrayptr = &options->permitted_listens;
1920 		} else {
1921 			uintptr = &options->num_permitted_opens;
1922 			chararrayptr = &options->permitted_opens;
1923 		}
1924 		arg = strdelim(&cp);
1925 		if (!arg || *arg == '\0')
1926 			fatal("%s line %d: missing %s specification",
1927 			    filename, linenum, lookup_opcode_name(opcode));
1928 		uvalue = *uintptr;	/* modified later */
1929 		if (strcmp(arg, "any") == 0 || strcmp(arg, "none") == 0) {
1930 			if (*activep && uvalue == 0) {
1931 				*uintptr = 1;
1932 				*chararrayptr = xcalloc(1,
1933 				    sizeof(**chararrayptr));
1934 				(*chararrayptr)[0] = xstrdup(arg);
1935 			}
1936 			break;
1937 		}
1938 		for (; arg != NULL && *arg != '\0'; arg = strdelim(&cp)) {
1939 			if (opcode == sPermitListen &&
1940 			    strchr(arg, ':') == NULL) {
1941 				/*
1942 				 * Allow bare port number for PermitListen
1943 				 * to indicate a wildcard listen host.
1944 				 */
1945 				xasprintf(&arg2, "*:%s", arg);
1946 			} else {
1947 				arg2 = xstrdup(arg);
1948 				ch = '\0';
1949 				p = hpdelim2(&arg, &ch);
1950 				if (p == NULL || ch == '/') {
1951 					fatal("%s line %d: missing host in %s",
1952 					    filename, linenum,
1953 					    lookup_opcode_name(opcode));
1954 				}
1955 				p = cleanhostname(p);
1956 			}
1957 			if (arg == NULL ||
1958 			    ((port = permitopen_port(arg)) < 0)) {
1959 				fatal("%s line %d: bad port number in %s",
1960 				    filename, linenum,
1961 				    lookup_opcode_name(opcode));
1962 			}
1963 			if (*activep && uvalue == 0) {
1964 				array_append(filename, linenum,
1965 				    lookup_opcode_name(opcode),
1966 				    chararrayptr, uintptr, arg2);
1967 			}
1968 			free(arg2);
1969 		}
1970 		break;
1971 
1972 	case sForceCommand:
1973 		if (cp == NULL || *cp == '\0')
1974 			fatal("%.200s line %d: Missing argument.", filename,
1975 			    linenum);
1976 		len = strspn(cp, WHITESPACE);
1977 		if (*activep && options->adm_forced_command == NULL)
1978 			options->adm_forced_command = xstrdup(cp + len);
1979 		return 0;
1980 
1981 	case sChrootDirectory:
1982 		charptr = &options->chroot_directory;
1983 
1984 		arg = strdelim(&cp);
1985 		if (!arg || *arg == '\0')
1986 			fatal("%s line %d: missing file name.",
1987 			    filename, linenum);
1988 		if (*activep && *charptr == NULL)
1989 			*charptr = xstrdup(arg);
1990 		break;
1991 
1992 	case sTrustedUserCAKeys:
1993 		charptr = &options->trusted_user_ca_keys;
1994 		goto parse_filename;
1995 
1996 	case sRevokedKeys:
1997 		charptr = &options->revoked_keys_file;
1998 		goto parse_filename;
1999 
2000 	case sIPQoS:
2001 		arg = strdelim(&cp);
2002 		if ((value = parse_ipqos(arg)) == -1)
2003 			fatal("%s line %d: Bad IPQoS value: %s",
2004 			    filename, linenum, arg);
2005 		arg = strdelim(&cp);
2006 		if (arg == NULL)
2007 			value2 = value;
2008 		else if ((value2 = parse_ipqos(arg)) == -1)
2009 			fatal("%s line %d: Bad IPQoS value: %s",
2010 			    filename, linenum, arg);
2011 		if (*activep) {
2012 			options->ip_qos_interactive = value;
2013 			options->ip_qos_bulk = value2;
2014 		}
2015 		break;
2016 
2017 	case sVersionAddendum:
2018 		if (cp == NULL || *cp == '\0')
2019 			fatal("%.200s line %d: Missing argument.", filename,
2020 			    linenum);
2021 		len = strspn(cp, WHITESPACE);
2022 		if (*activep && options->version_addendum == NULL) {
2023 			if (strcasecmp(cp + len, "none") == 0)
2024 				options->version_addendum = xstrdup("");
2025 			else if (strchr(cp + len, '\r') != NULL)
2026 				fatal("%.200s line %d: Invalid argument",
2027 				    filename, linenum);
2028 			else
2029 				options->version_addendum = xstrdup(cp + len);
2030 		}
2031 		return 0;
2032 
2033 	case sAuthorizedKeysCommand:
2034 		if (cp == NULL)
2035 			fatal("%.200s line %d: Missing argument.", filename,
2036 			    linenum);
2037 		len = strspn(cp, WHITESPACE);
2038 		if (*activep && options->authorized_keys_command == NULL) {
2039 			if (cp[len] != '/' && strcasecmp(cp + len, "none") != 0)
2040 				fatal("%.200s line %d: AuthorizedKeysCommand "
2041 				    "must be an absolute path",
2042 				    filename, linenum);
2043 			options->authorized_keys_command = xstrdup(cp + len);
2044 		}
2045 		return 0;
2046 
2047 	case sAuthorizedKeysCommandUser:
2048 		charptr = &options->authorized_keys_command_user;
2049 
2050 		arg = strdelim(&cp);
2051 		if (!arg || *arg == '\0')
2052 			fatal("%s line %d: missing AuthorizedKeysCommandUser "
2053 			    "argument.", filename, linenum);
2054 		if (*activep && *charptr == NULL)
2055 			*charptr = xstrdup(arg);
2056 		break;
2057 
2058 	case sAuthorizedPrincipalsCommand:
2059 		if (cp == NULL)
2060 			fatal("%.200s line %d: Missing argument.", filename,
2061 			    linenum);
2062 		len = strspn(cp, WHITESPACE);
2063 		if (*activep &&
2064 		    options->authorized_principals_command == NULL) {
2065 			if (cp[len] != '/' && strcasecmp(cp + len, "none") != 0)
2066 				fatal("%.200s line %d: "
2067 				    "AuthorizedPrincipalsCommand must be "
2068 				    "an absolute path", filename, linenum);
2069 			options->authorized_principals_command =
2070 			    xstrdup(cp + len);
2071 		}
2072 		return 0;
2073 
2074 	case sAuthorizedPrincipalsCommandUser:
2075 		charptr = &options->authorized_principals_command_user;
2076 
2077 		arg = strdelim(&cp);
2078 		if (!arg || *arg == '\0')
2079 			fatal("%s line %d: missing "
2080 			    "AuthorizedPrincipalsCommandUser argument.",
2081 			    filename, linenum);
2082 		if (*activep && *charptr == NULL)
2083 			*charptr = xstrdup(arg);
2084 		break;
2085 
2086 	case sAuthenticationMethods:
2087 		if (options->num_auth_methods == 0) {
2088 			value = 0; /* seen "any" pseudo-method */
2089 			value2 = 0; /* successfully parsed any method */
2090 			while ((arg = strdelim(&cp)) && *arg != '\0') {
2091 				if (strcmp(arg, "any") == 0) {
2092 					if (options->num_auth_methods > 0) {
2093 						fatal("%s line %d: \"any\" "
2094 						    "must appear alone in "
2095 						    "AuthenticationMethods",
2096 						    filename, linenum);
2097 					}
2098 					value = 1;
2099 				} else if (value) {
2100 					fatal("%s line %d: \"any\" must appear "
2101 					    "alone in AuthenticationMethods",
2102 					    filename, linenum);
2103 				} else if (auth2_methods_valid(arg, 0) != 0) {
2104 					fatal("%s line %d: invalid "
2105 					    "authentication method list.",
2106 					    filename, linenum);
2107 				}
2108 				value2 = 1;
2109 				if (!*activep)
2110 					continue;
2111 				array_append(filename, linenum,
2112 				    "AuthenticationMethods",
2113 				    &options->auth_methods,
2114 				    &options->num_auth_methods, arg);
2115 			}
2116 			if (value2 == 0) {
2117 				fatal("%s line %d: no AuthenticationMethods "
2118 				    "specified", filename, linenum);
2119 			}
2120 		}
2121 		return 0;
2122 
2123 	case sStreamLocalBindMask:
2124 		arg = strdelim(&cp);
2125 		if (!arg || *arg == '\0')
2126 			fatal("%s line %d: missing StreamLocalBindMask "
2127 			    "argument.", filename, linenum);
2128 		/* Parse mode in octal format */
2129 		value = strtol(arg, &p, 8);
2130 		if (arg == p || value < 0 || value > 0777)
2131 			fatal("%s line %d: Bad mask.", filename, linenum);
2132 		if (*activep)
2133 			options->fwd_opts.streamlocal_bind_mask = (mode_t)value;
2134 		break;
2135 
2136 	case sStreamLocalBindUnlink:
2137 		intptr = &options->fwd_opts.streamlocal_bind_unlink;
2138 		goto parse_flag;
2139 
2140 	case sFingerprintHash:
2141 		arg = strdelim(&cp);
2142 		if (!arg || *arg == '\0')
2143 			fatal("%.200s line %d: Missing argument.",
2144 			    filename, linenum);
2145 		if ((value = ssh_digest_alg_by_name(arg)) == -1)
2146 			fatal("%.200s line %d: Invalid hash algorithm \"%s\".",
2147 			    filename, linenum, arg);
2148 		if (*activep)
2149 			options->fingerprint_hash = value;
2150 		break;
2151 
2152 	case sExposeAuthInfo:
2153 		intptr = &options->expose_userauth_info;
2154 		goto parse_flag;
2155 
2156 	case sRDomain:
2157 		charptr = &options->routing_domain;
2158 		arg = strdelim(&cp);
2159 		if (!arg || *arg == '\0')
2160 			fatal("%.200s line %d: Missing argument.",
2161 			    filename, linenum);
2162 		if (strcasecmp(arg, "none") != 0 && strcmp(arg, "%D") != 0 &&
2163 		    !valid_rdomain(arg))
2164 			fatal("%s line %d: bad routing domain",
2165 			    filename, linenum);
2166 		if (*activep && *charptr == NULL)
2167 			*charptr = xstrdup(arg);
2168 		break;
2169 
2170 	case sDeprecated:
2171 	case sIgnore:
2172 	case sUnsupported:
2173 		do_log2(opcode == sIgnore ?
2174 		    SYSLOG_LEVEL_DEBUG2 : SYSLOG_LEVEL_INFO,
2175 		    "%s line %d: %s option %s", filename, linenum,
2176 		    opcode == sUnsupported ? "Unsupported" : "Deprecated", arg);
2177 		while (arg)
2178 		    arg = strdelim(&cp);
2179 		break;
2180 
2181 	default:
2182 		fatal("%s line %d: Missing handler for opcode %s (%d)",
2183 		    filename, linenum, arg, opcode);
2184 	}
2185 	if ((arg = strdelim(&cp)) != NULL && *arg != '\0')
2186 		fatal("%s line %d: garbage at end of line; \"%.200s\".",
2187 		    filename, linenum, arg);
2188 	return 0;
2189 }
2190 
2191 /* Reads the server configuration file. */
2192 
2193 void
2194 load_server_config(const char *filename, struct sshbuf *conf)
2195 {
2196 	char *line = NULL, *cp;
2197 	size_t linesize = 0;
2198 	FILE *f;
2199 	int r, lineno = 0;
2200 
2201 	debug2("%s: filename %s", __func__, filename);
2202 	if ((f = fopen(filename, "r")) == NULL) {
2203 		perror(filename);
2204 		exit(1);
2205 	}
2206 	sshbuf_reset(conf);
2207 	while (getline(&line, &linesize, f) != -1) {
2208 		lineno++;
2209 		/*
2210 		 * Trim out comments and strip whitespace
2211 		 * NB - preserve newlines, they are needed to reproduce
2212 		 * line numbers later for error messages
2213 		 */
2214 		if ((cp = strchr(line, '#')) != NULL)
2215 			memcpy(cp, "\n", 2);
2216 		cp = line + strspn(line, " \t\r");
2217 		if ((r = sshbuf_put(conf, cp, strlen(cp))) != 0)
2218 			fatal("%s: buffer error: %s", __func__, ssh_err(r));
2219 	}
2220 	free(line);
2221 	if ((r = sshbuf_put_u8(conf, 0)) != 0)
2222 		fatal("%s: buffer error: %s", __func__, ssh_err(r));
2223 	fclose(f);
2224 	debug2("%s: done config len = %zu", __func__, sshbuf_len(conf));
2225 }
2226 
2227 void
2228 parse_server_match_config(ServerOptions *options,
2229    struct connection_info *connectinfo)
2230 {
2231 	ServerOptions mo;
2232 
2233 	initialize_server_options(&mo);
2234 	parse_server_config(&mo, "reprocess config", cfg, connectinfo);
2235 	copy_set_server_options(options, &mo, 0);
2236 }
2237 
2238 int parse_server_match_testspec(struct connection_info *ci, char *spec)
2239 {
2240 	char *p;
2241 
2242 	while ((p = strsep(&spec, ",")) && *p != '\0') {
2243 		if (strncmp(p, "addr=", 5) == 0) {
2244 			ci->address = xstrdup(p + 5);
2245 		} else if (strncmp(p, "host=", 5) == 0) {
2246 			ci->host = xstrdup(p + 5);
2247 		} else if (strncmp(p, "user=", 5) == 0) {
2248 			ci->user = xstrdup(p + 5);
2249 		} else if (strncmp(p, "laddr=", 6) == 0) {
2250 			ci->laddress = xstrdup(p + 6);
2251 		} else if (strncmp(p, "rdomain=", 8) == 0) {
2252 			ci->rdomain = xstrdup(p + 8);
2253 		} else if (strncmp(p, "lport=", 6) == 0) {
2254 			ci->lport = a2port(p + 6);
2255 			if (ci->lport == -1) {
2256 				fprintf(stderr, "Invalid port '%s' in test mode"
2257 				   " specification %s\n", p+6, p);
2258 				return -1;
2259 			}
2260 		} else {
2261 			fprintf(stderr, "Invalid test mode specification %s\n",
2262 			   p);
2263 			return -1;
2264 		}
2265 	}
2266 	return 0;
2267 }
2268 
2269 /*
2270  * Copy any supported values that are set.
2271  *
2272  * If the preauth flag is set, we do not bother copying the string or
2273  * array values that are not used pre-authentication, because any that we
2274  * do use must be explicitly sent in mm_getpwnamallow().
2275  */
2276 void
2277 copy_set_server_options(ServerOptions *dst, ServerOptions *src, int preauth)
2278 {
2279 #define M_CP_INTOPT(n) do {\
2280 	if (src->n != -1) \
2281 		dst->n = src->n; \
2282 } while (0)
2283 
2284 	M_CP_INTOPT(password_authentication);
2285 	M_CP_INTOPT(gss_authentication);
2286 	M_CP_INTOPT(pubkey_authentication);
2287 	M_CP_INTOPT(kerberos_authentication);
2288 	M_CP_INTOPT(hostbased_authentication);
2289 	M_CP_INTOPT(hostbased_uses_name_from_packet_only);
2290 	M_CP_INTOPT(kbd_interactive_authentication);
2291 	M_CP_INTOPT(permit_root_login);
2292 	M_CP_INTOPT(permit_empty_passwd);
2293 
2294 	M_CP_INTOPT(allow_tcp_forwarding);
2295 	M_CP_INTOPT(allow_streamlocal_forwarding);
2296 	M_CP_INTOPT(allow_agent_forwarding);
2297 	M_CP_INTOPT(disable_forwarding);
2298 	M_CP_INTOPT(expose_userauth_info);
2299 	M_CP_INTOPT(permit_tun);
2300 	M_CP_INTOPT(fwd_opts.gateway_ports);
2301 	M_CP_INTOPT(fwd_opts.streamlocal_bind_unlink);
2302 	M_CP_INTOPT(x11_display_offset);
2303 	M_CP_INTOPT(x11_forwarding);
2304 	M_CP_INTOPT(x11_use_localhost);
2305 	M_CP_INTOPT(permit_tty);
2306 	M_CP_INTOPT(permit_user_rc);
2307 	M_CP_INTOPT(max_sessions);
2308 	M_CP_INTOPT(max_authtries);
2309 	M_CP_INTOPT(client_alive_count_max);
2310 	M_CP_INTOPT(client_alive_interval);
2311 	M_CP_INTOPT(ip_qos_interactive);
2312 	M_CP_INTOPT(ip_qos_bulk);
2313 	M_CP_INTOPT(rekey_limit);
2314 	M_CP_INTOPT(rekey_interval);
2315 	M_CP_INTOPT(log_level);
2316 
2317 	/*
2318 	 * The bind_mask is a mode_t that may be unsigned, so we can't use
2319 	 * M_CP_INTOPT - it does a signed comparison that causes compiler
2320 	 * warnings.
2321 	 */
2322 	if (src->fwd_opts.streamlocal_bind_mask != (mode_t)-1) {
2323 		dst->fwd_opts.streamlocal_bind_mask =
2324 		    src->fwd_opts.streamlocal_bind_mask;
2325 	}
2326 
2327 	/* M_CP_STROPT and M_CP_STRARRAYOPT should not appear before here */
2328 #define M_CP_STROPT(n) do {\
2329 	if (src->n != NULL && dst->n != src->n) { \
2330 		free(dst->n); \
2331 		dst->n = src->n; \
2332 	} \
2333 } while(0)
2334 #define M_CP_STRARRAYOPT(s, num_s) do {\
2335 	u_int i; \
2336 	if (src->num_s != 0) { \
2337 		for (i = 0; i < dst->num_s; i++) \
2338 			free(dst->s[i]); \
2339 		free(dst->s); \
2340 		dst->s = xcalloc(src->num_s, sizeof(*dst->s)); \
2341 		for (i = 0; i < src->num_s; i++) \
2342 			dst->s[i] = xstrdup(src->s[i]); \
2343 		dst->num_s = src->num_s; \
2344 	} \
2345 } while(0)
2346 
2347 	/* See comment in servconf.h */
2348 	COPY_MATCH_STRING_OPTS();
2349 
2350 	/* Arguments that accept '+...' need to be expanded */
2351 	assemble_algorithms(dst);
2352 
2353 	/*
2354 	 * The only things that should be below this point are string options
2355 	 * which are only used after authentication.
2356 	 */
2357 	if (preauth)
2358 		return;
2359 
2360 	/* These options may be "none" to clear a global setting */
2361 	M_CP_STROPT(adm_forced_command);
2362 	if (option_clear_or_none(dst->adm_forced_command)) {
2363 		free(dst->adm_forced_command);
2364 		dst->adm_forced_command = NULL;
2365 	}
2366 	M_CP_STROPT(chroot_directory);
2367 	if (option_clear_or_none(dst->chroot_directory)) {
2368 		free(dst->chroot_directory);
2369 		dst->chroot_directory = NULL;
2370 	}
2371 }
2372 
2373 #undef M_CP_INTOPT
2374 #undef M_CP_STROPT
2375 #undef M_CP_STRARRAYOPT
2376 
2377 void
2378 parse_server_config(ServerOptions *options, const char *filename,
2379     struct sshbuf *conf, struct connection_info *connectinfo)
2380 {
2381 	int active, linenum, bad_options = 0;
2382 	char *cp, *obuf, *cbuf;
2383 
2384 	debug2("%s: config %s len %zu", __func__, filename, sshbuf_len(conf));
2385 
2386 	if ((obuf = cbuf = sshbuf_dup_string(conf)) == NULL)
2387 		fatal("%s: sshbuf_dup_string failed", __func__);
2388 	active = connectinfo ? 0 : 1;
2389 	linenum = 1;
2390 	while ((cp = strsep(&cbuf, "\n")) != NULL) {
2391 		if (process_server_config_line(options, cp, filename,
2392 		    linenum++, &active, connectinfo) != 0)
2393 			bad_options++;
2394 	}
2395 	free(obuf);
2396 	if (bad_options > 0)
2397 		fatal("%s: terminating, %d bad configuration options",
2398 		    filename, bad_options);
2399 	process_queued_listen_addrs(options);
2400 }
2401 
2402 static const char *
2403 fmt_multistate_int(int val, const struct multistate *m)
2404 {
2405 	u_int i;
2406 
2407 	for (i = 0; m[i].key != NULL; i++) {
2408 		if (m[i].value == val)
2409 			return m[i].key;
2410 	}
2411 	return "UNKNOWN";
2412 }
2413 
2414 static const char *
2415 fmt_intarg(ServerOpCodes code, int val)
2416 {
2417 	if (val == -1)
2418 		return "unset";
2419 	switch (code) {
2420 	case sAddressFamily:
2421 		return fmt_multistate_int(val, multistate_addressfamily);
2422 	case sPermitRootLogin:
2423 		return fmt_multistate_int(val, multistate_permitrootlogin);
2424 	case sGatewayPorts:
2425 		return fmt_multistate_int(val, multistate_gatewayports);
2426 	case sCompression:
2427 		return fmt_multistate_int(val, multistate_compression);
2428 	case sAllowTcpForwarding:
2429 		return fmt_multistate_int(val, multistate_tcpfwd);
2430 	case sAllowStreamLocalForwarding:
2431 		return fmt_multistate_int(val, multistate_tcpfwd);
2432 	case sFingerprintHash:
2433 		return ssh_digest_alg_name(val);
2434 	default:
2435 		switch (val) {
2436 		case 0:
2437 			return "no";
2438 		case 1:
2439 			return "yes";
2440 		default:
2441 			return "UNKNOWN";
2442 		}
2443 	}
2444 }
2445 
2446 static void
2447 dump_cfg_int(ServerOpCodes code, int val)
2448 {
2449 	printf("%s %d\n", lookup_opcode_name(code), val);
2450 }
2451 
2452 static void
2453 dump_cfg_oct(ServerOpCodes code, int val)
2454 {
2455 	printf("%s 0%o\n", lookup_opcode_name(code), val);
2456 }
2457 
2458 static void
2459 dump_cfg_fmtint(ServerOpCodes code, int val)
2460 {
2461 	printf("%s %s\n", lookup_opcode_name(code), fmt_intarg(code, val));
2462 }
2463 
2464 static void
2465 dump_cfg_string(ServerOpCodes code, const char *val)
2466 {
2467 	printf("%s %s\n", lookup_opcode_name(code),
2468 	    val == NULL ? "none" : val);
2469 }
2470 
2471 static void
2472 dump_cfg_strarray(ServerOpCodes code, u_int count, char **vals)
2473 {
2474 	u_int i;
2475 
2476 	for (i = 0; i < count; i++)
2477 		printf("%s %s\n", lookup_opcode_name(code), vals[i]);
2478 }
2479 
2480 static void
2481 dump_cfg_strarray_oneline(ServerOpCodes code, u_int count, char **vals)
2482 {
2483 	u_int i;
2484 
2485 	if (count <= 0 && code != sAuthenticationMethods)
2486 		return;
2487 	printf("%s", lookup_opcode_name(code));
2488 	for (i = 0; i < count; i++)
2489 		printf(" %s",  vals[i]);
2490 	if (code == sAuthenticationMethods && count == 0)
2491 		printf(" any");
2492 	printf("\n");
2493 }
2494 
2495 static char *
2496 format_listen_addrs(struct listenaddr *la)
2497 {
2498 	int r;
2499 	struct addrinfo *ai;
2500 	char addr[NI_MAXHOST], port[NI_MAXSERV];
2501 	char *laddr1 = xstrdup(""), *laddr2 = NULL;
2502 
2503 	/*
2504 	 * ListenAddress must be after Port.  add_one_listen_addr pushes
2505 	 * addresses onto a stack, so to maintain ordering we need to
2506 	 * print these in reverse order.
2507 	 */
2508 	for (ai = la->addrs; ai; ai = ai->ai_next) {
2509 		if ((r = getnameinfo(ai->ai_addr, ai->ai_addrlen, addr,
2510 		    sizeof(addr), port, sizeof(port),
2511 		    NI_NUMERICHOST|NI_NUMERICSERV)) != 0) {
2512 			error("getnameinfo: %.100s", ssh_gai_strerror(r));
2513 			continue;
2514 		}
2515 		laddr2 = laddr1;
2516 		if (ai->ai_family == AF_INET6) {
2517 			xasprintf(&laddr1, "listenaddress [%s]:%s%s%s\n%s",
2518 			    addr, port,
2519 			    la->rdomain == NULL ? "" : " rdomain ",
2520 			    la->rdomain == NULL ? "" : la->rdomain,
2521 			    laddr2);
2522 		} else {
2523 			xasprintf(&laddr1, "listenaddress %s:%s%s%s\n%s",
2524 			    addr, port,
2525 			    la->rdomain == NULL ? "" : " rdomain ",
2526 			    la->rdomain == NULL ? "" : la->rdomain,
2527 			    laddr2);
2528 		}
2529 		free(laddr2);
2530 	}
2531 	return laddr1;
2532 }
2533 
2534 void
2535 dump_config(ServerOptions *o)
2536 {
2537 	char *s;
2538 	u_int i;
2539 
2540 	/* these are usually at the top of the config */
2541 	for (i = 0; i < o->num_ports; i++)
2542 		printf("port %d\n", o->ports[i]);
2543 	dump_cfg_fmtint(sAddressFamily, o->address_family);
2544 
2545 	for (i = 0; i < o->num_listen_addrs; i++) {
2546 		s = format_listen_addrs(&o->listen_addrs[i]);
2547 		printf("%s", s);
2548 		free(s);
2549 	}
2550 
2551 	/* integer arguments */
2552 #ifdef USE_PAM
2553 	dump_cfg_fmtint(sUsePAM, o->use_pam);
2554 #endif
2555 	dump_cfg_int(sLoginGraceTime, o->login_grace_time);
2556 	dump_cfg_int(sX11DisplayOffset, o->x11_display_offset);
2557 	dump_cfg_int(sMaxAuthTries, o->max_authtries);
2558 	dump_cfg_int(sMaxSessions, o->max_sessions);
2559 	dump_cfg_int(sClientAliveInterval, o->client_alive_interval);
2560 	dump_cfg_int(sClientAliveCountMax, o->client_alive_count_max);
2561 	dump_cfg_oct(sStreamLocalBindMask, o->fwd_opts.streamlocal_bind_mask);
2562 
2563 	/* formatted integer arguments */
2564 	dump_cfg_fmtint(sPermitRootLogin, o->permit_root_login);
2565 	dump_cfg_fmtint(sIgnoreRhosts, o->ignore_rhosts);
2566 	dump_cfg_fmtint(sIgnoreUserKnownHosts, o->ignore_user_known_hosts);
2567 	dump_cfg_fmtint(sHostbasedAuthentication, o->hostbased_authentication);
2568 	dump_cfg_fmtint(sHostbasedUsesNameFromPacketOnly,
2569 	    o->hostbased_uses_name_from_packet_only);
2570 	dump_cfg_fmtint(sPubkeyAuthentication, o->pubkey_authentication);
2571 #ifdef KRB5
2572 	dump_cfg_fmtint(sKerberosAuthentication, o->kerberos_authentication);
2573 	dump_cfg_fmtint(sKerberosOrLocalPasswd, o->kerberos_or_local_passwd);
2574 	dump_cfg_fmtint(sKerberosTicketCleanup, o->kerberos_ticket_cleanup);
2575 # ifdef USE_AFS
2576 	dump_cfg_fmtint(sKerberosGetAFSToken, o->kerberos_get_afs_token);
2577 # endif
2578 #endif
2579 #ifdef GSSAPI
2580 	dump_cfg_fmtint(sGssAuthentication, o->gss_authentication);
2581 	dump_cfg_fmtint(sGssCleanupCreds, o->gss_cleanup_creds);
2582 #endif
2583 	dump_cfg_fmtint(sPasswordAuthentication, o->password_authentication);
2584 	dump_cfg_fmtint(sKbdInteractiveAuthentication,
2585 	    o->kbd_interactive_authentication);
2586 	dump_cfg_fmtint(sChallengeResponseAuthentication,
2587 	    o->challenge_response_authentication);
2588 	dump_cfg_fmtint(sPrintMotd, o->print_motd);
2589 #ifndef DISABLE_LASTLOG
2590 	dump_cfg_fmtint(sPrintLastLog, o->print_lastlog);
2591 #endif
2592 	dump_cfg_fmtint(sX11Forwarding, o->x11_forwarding);
2593 	dump_cfg_fmtint(sX11UseLocalhost, o->x11_use_localhost);
2594 	dump_cfg_fmtint(sPermitTTY, o->permit_tty);
2595 	dump_cfg_fmtint(sPermitUserRC, o->permit_user_rc);
2596 	dump_cfg_fmtint(sStrictModes, o->strict_modes);
2597 	dump_cfg_fmtint(sTCPKeepAlive, o->tcp_keep_alive);
2598 	dump_cfg_fmtint(sEmptyPasswd, o->permit_empty_passwd);
2599 	dump_cfg_fmtint(sCompression, o->compression);
2600 	dump_cfg_fmtint(sGatewayPorts, o->fwd_opts.gateway_ports);
2601 	dump_cfg_fmtint(sUseDNS, o->use_dns);
2602 	dump_cfg_fmtint(sAllowTcpForwarding, o->allow_tcp_forwarding);
2603 	dump_cfg_fmtint(sAllowAgentForwarding, o->allow_agent_forwarding);
2604 	dump_cfg_fmtint(sDisableForwarding, o->disable_forwarding);
2605 	dump_cfg_fmtint(sAllowStreamLocalForwarding, o->allow_streamlocal_forwarding);
2606 	dump_cfg_fmtint(sStreamLocalBindUnlink, o->fwd_opts.streamlocal_bind_unlink);
2607 	dump_cfg_fmtint(sFingerprintHash, o->fingerprint_hash);
2608 	dump_cfg_fmtint(sExposeAuthInfo, o->expose_userauth_info);
2609 
2610 	/* string arguments */
2611 	dump_cfg_string(sPidFile, o->pid_file);
2612 	dump_cfg_string(sXAuthLocation, o->xauth_location);
2613 	dump_cfg_string(sCiphers, o->ciphers ? o->ciphers : KEX_SERVER_ENCRYPT);
2614 	dump_cfg_string(sMacs, o->macs ? o->macs : KEX_SERVER_MAC);
2615 	dump_cfg_string(sBanner, o->banner);
2616 	dump_cfg_string(sForceCommand, o->adm_forced_command);
2617 	dump_cfg_string(sChrootDirectory, o->chroot_directory);
2618 	dump_cfg_string(sTrustedUserCAKeys, o->trusted_user_ca_keys);
2619 	dump_cfg_string(sRevokedKeys, o->revoked_keys_file);
2620 	dump_cfg_string(sAuthorizedPrincipalsFile,
2621 	    o->authorized_principals_file);
2622 	dump_cfg_string(sVersionAddendum, *o->version_addendum == '\0'
2623 	    ? "none" : o->version_addendum);
2624 	dump_cfg_string(sAuthorizedKeysCommand, o->authorized_keys_command);
2625 	dump_cfg_string(sAuthorizedKeysCommandUser, o->authorized_keys_command_user);
2626 	dump_cfg_string(sAuthorizedPrincipalsCommand, o->authorized_principals_command);
2627 	dump_cfg_string(sAuthorizedPrincipalsCommandUser, o->authorized_principals_command_user);
2628 	dump_cfg_string(sHostKeyAgent, o->host_key_agent);
2629 	dump_cfg_string(sKexAlgorithms,
2630 	    o->kex_algorithms ? o->kex_algorithms : KEX_SERVER_KEX);
2631 	dump_cfg_string(sCASignatureAlgorithms, o->ca_sign_algorithms ?
2632 	    o->ca_sign_algorithms : SSH_ALLOWED_CA_SIGALGS);
2633 	dump_cfg_string(sHostbasedAcceptedKeyTypes, o->hostbased_key_types ?
2634 	    o->hostbased_key_types : KEX_DEFAULT_PK_ALG);
2635 	dump_cfg_string(sHostKeyAlgorithms, o->hostkeyalgorithms ?
2636 	    o->hostkeyalgorithms : KEX_DEFAULT_PK_ALG);
2637 	dump_cfg_string(sPubkeyAcceptedKeyTypes, o->pubkey_key_types ?
2638 	    o->pubkey_key_types : KEX_DEFAULT_PK_ALG);
2639 	dump_cfg_string(sRDomain, o->routing_domain);
2640 
2641 	/* string arguments requiring a lookup */
2642 	dump_cfg_string(sLogLevel, log_level_name(o->log_level));
2643 	dump_cfg_string(sLogFacility, log_facility_name(o->log_facility));
2644 
2645 	/* string array arguments */
2646 	dump_cfg_strarray_oneline(sAuthorizedKeysFile, o->num_authkeys_files,
2647 	    o->authorized_keys_files);
2648 	dump_cfg_strarray(sHostKeyFile, o->num_host_key_files,
2649 	     o->host_key_files);
2650 	dump_cfg_strarray(sHostCertificate, o->num_host_cert_files,
2651 	     o->host_cert_files);
2652 	dump_cfg_strarray(sAllowUsers, o->num_allow_users, o->allow_users);
2653 	dump_cfg_strarray(sDenyUsers, o->num_deny_users, o->deny_users);
2654 	dump_cfg_strarray(sAllowGroups, o->num_allow_groups, o->allow_groups);
2655 	dump_cfg_strarray(sDenyGroups, o->num_deny_groups, o->deny_groups);
2656 	dump_cfg_strarray(sAcceptEnv, o->num_accept_env, o->accept_env);
2657 	dump_cfg_strarray(sSetEnv, o->num_setenv, o->setenv);
2658 	dump_cfg_strarray_oneline(sAuthenticationMethods,
2659 	    o->num_auth_methods, o->auth_methods);
2660 
2661 	/* other arguments */
2662 	for (i = 0; i < o->num_subsystems; i++)
2663 		printf("subsystem %s %s\n", o->subsystem_name[i],
2664 		    o->subsystem_args[i]);
2665 
2666 	printf("maxstartups %d:%d:%d\n", o->max_startups_begin,
2667 	    o->max_startups_rate, o->max_startups);
2668 
2669 	s = NULL;
2670 	for (i = 0; tunmode_desc[i].val != -1; i++) {
2671 		if (tunmode_desc[i].val == o->permit_tun) {
2672 			s = tunmode_desc[i].text;
2673 			break;
2674 		}
2675 	}
2676 	dump_cfg_string(sPermitTunnel, s);
2677 
2678 	printf("ipqos %s ", iptos2str(o->ip_qos_interactive));
2679 	printf("%s\n", iptos2str(o->ip_qos_bulk));
2680 
2681 	printf("rekeylimit %llu %d\n", (unsigned long long)o->rekey_limit,
2682 	    o->rekey_interval);
2683 
2684 	printf("permitopen");
2685 	if (o->num_permitted_opens == 0)
2686 		printf(" any");
2687 	else {
2688 		for (i = 0; i < o->num_permitted_opens; i++)
2689 			printf(" %s", o->permitted_opens[i]);
2690 	}
2691 	printf("\n");
2692 	printf("permitlisten");
2693 	if (o->num_permitted_listens == 0)
2694 		printf(" any");
2695 	else {
2696 		for (i = 0; i < o->num_permitted_listens; i++)
2697 			printf(" %s", o->permitted_listens[i]);
2698 	}
2699 	printf("\n");
2700 
2701 	if (o->permit_user_env_whitelist == NULL) {
2702 		dump_cfg_fmtint(sPermitUserEnvironment, o->permit_user_env);
2703 	} else {
2704 		printf("permituserenvironment %s\n",
2705 		    o->permit_user_env_whitelist);
2706 	}
2707 
2708 }
2709