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