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