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