2 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
5 * As far as I am concerned, the code I have written for this software
6 * can be used freely for any purpose. Any derived versions of this
7 * software must be clearly marked as such, and if the derived work is
8 * incompatible with the protocol description in the RFC file, it must be
9 * called by a name other than "ssh" or "Secure Shell".
13 RCSID("$OpenBSD: servconf.c,v 1.57 2001/01/08 22:29:05 markus Exp $");
20 /* add listen address */
21 void add_listen_addr(ServerOptions *options, char *addr);
23 /* Initializes the server options to their default values. */
26 initialize_server_options(ServerOptions *options)
28 memset(options, 0, sizeof(*options));
29 options->num_ports = 0;
30 options->ports_from_cmdline = 0;
31 options->listen_addrs = NULL;
32 options->num_host_key_files = 0;
33 options->pid_file = NULL;
34 options->server_key_bits = -1;
35 options->login_grace_time = -1;
36 options->key_regeneration_time = -1;
37 options->permit_root_login = -1;
38 options->ignore_rhosts = -1;
39 options->ignore_user_known_hosts = -1;
40 options->print_motd = -1;
41 options->check_mail = -1;
42 options->x11_forwarding = -1;
43 options->x11_display_offset = -1;
44 options->xauth_location = NULL;
45 options->strict_modes = -1;
46 options->keepalives = -1;
47 options->log_facility = (SyslogFacility) - 1;
48 options->log_level = (LogLevel) - 1;
49 options->rhosts_authentication = -1;
50 options->rhosts_rsa_authentication = -1;
51 options->rsa_authentication = -1;
52 options->pubkey_authentication = -1;
54 options->kerberos_authentication = -1;
55 options->kerberos_or_local_passwd = -1;
56 options->kerberos_ticket_cleanup = -1;
59 options->kerberos_tgt_passing = -1;
60 options->afs_token_passing = -1;
62 options->password_authentication = -1;
63 options->kbd_interactive_authentication = -1;
65 options->skey_authentication = -1;
67 options->permit_empty_passwd = -1;
68 options->use_login = -1;
69 options->allow_tcp_forwarding = -1;
70 options->num_allow_users = 0;
71 options->num_deny_users = 0;
72 options->num_allow_groups = 0;
73 options->num_deny_groups = 0;
74 options->ciphers = NULL;
75 options->protocol = SSH_PROTO_UNKNOWN;
76 options->gateway_ports = -1;
77 options->num_subsystems = 0;
78 options->max_startups_begin = -1;
79 options->max_startups_rate = -1;
80 options->max_startups = -1;
81 options->banner = NULL;
85 fill_default_server_options(ServerOptions *options)
87 if (options->protocol == SSH_PROTO_UNKNOWN)
88 options->protocol = SSH_PROTO_1|SSH_PROTO_2;
89 if (options->num_host_key_files == 0) {
90 /* fill default hostkeys for protocols */
91 if (options->protocol & SSH_PROTO_1)
92 options->host_key_files[options->num_host_key_files++] = HOST_KEY_FILE;
93 if (options->protocol & SSH_PROTO_2)
94 options->host_key_files[options->num_host_key_files++] = HOST_DSA_KEY_FILE;
96 if (options->num_ports == 0)
97 options->ports[options->num_ports++] = SSH_DEFAULT_PORT;
98 if (options->listen_addrs == NULL)
99 add_listen_addr(options, NULL);
100 if (options->pid_file == NULL)
101 options->pid_file = SSH_DAEMON_PID_FILE;
102 if (options->server_key_bits == -1)
103 options->server_key_bits = 768;
104 if (options->login_grace_time == -1)
105 options->login_grace_time = 600;
106 if (options->key_regeneration_time == -1)
107 options->key_regeneration_time = 3600;
108 if (options->permit_root_login == -1)
109 options->permit_root_login = 1; /* yes */
110 if (options->ignore_rhosts == -1)
111 options->ignore_rhosts = 1;
112 if (options->ignore_user_known_hosts == -1)
113 options->ignore_user_known_hosts = 0;
114 if (options->check_mail == -1)
115 options->check_mail = 0;
116 if (options->print_motd == -1)
117 options->print_motd = 1;
118 if (options->x11_forwarding == -1)
119 options->x11_forwarding = 0;
120 if (options->x11_display_offset == -1)
121 options->x11_display_offset = 10;
123 if (options->xauth_location == NULL)
124 options->xauth_location = XAUTH_PATH;
125 #endif /* XAUTH_PATH */
126 if (options->strict_modes == -1)
127 options->strict_modes = 1;
128 if (options->keepalives == -1)
129 options->keepalives = 1;
130 if (options->log_facility == (SyslogFacility) (-1))
131 options->log_facility = SYSLOG_FACILITY_AUTH;
132 if (options->log_level == (LogLevel) (-1))
133 options->log_level = SYSLOG_LEVEL_NOTICE;
134 if (options->rhosts_authentication == -1)
135 options->rhosts_authentication = 0;
136 if (options->rhosts_rsa_authentication == -1)
137 options->rhosts_rsa_authentication = 0;
138 if (options->rsa_authentication == -1)
139 options->rsa_authentication = 1;
140 if (options->pubkey_authentication == -1)
141 options->pubkey_authentication = 1;
143 if (options->kerberos_authentication == -1)
144 options->kerberos_authentication = (access(KEYFILE, R_OK) == 0);
145 if (options->kerberos_or_local_passwd == -1)
146 options->kerberos_or_local_passwd = 1;
147 if (options->kerberos_ticket_cleanup == -1)
148 options->kerberos_ticket_cleanup = 1;
151 if (options->kerberos_tgt_passing == -1)
152 options->kerberos_tgt_passing = 0;
153 if (options->afs_token_passing == -1)
154 options->afs_token_passing = k_hasafs();
156 if (options->password_authentication == -1)
157 options->password_authentication = 1;
158 if (options->kbd_interactive_authentication == -1)
159 options->kbd_interactive_authentication = 0;
161 if (options->skey_authentication == -1)
162 options->skey_authentication = 1;
164 if (options->permit_empty_passwd == -1)
165 options->permit_empty_passwd = 0;
166 if (options->use_login == -1)
167 options->use_login = 0;
168 if (options->allow_tcp_forwarding == -1)
169 options->allow_tcp_forwarding = 1;
170 if (options->gateway_ports == -1)
171 options->gateway_ports = 0;
172 if (options->max_startups == -1)
173 options->max_startups = 10;
174 if (options->max_startups_rate == -1)
175 options->max_startups_rate = 100; /* 100% */
176 if (options->max_startups_begin == -1)
177 options->max_startups_begin = options->max_startups;
180 /* Keyword tokens. */
182 sBadOption, /* == unknown option */
183 sPort, sHostKeyFile, sServerKeyBits, sLoginGraceTime, sKeyRegenerationTime,
184 sPermitRootLogin, sLogFacility, sLogLevel,
185 sRhostsAuthentication, sRhostsRSAAuthentication, sRSAAuthentication,
187 sKerberosAuthentication, sKerberosOrLocalPasswd, sKerberosTicketCleanup,
190 sKerberosTgtPassing, sAFSTokenPassing,
195 sPasswordAuthentication, sKbdInteractiveAuthentication, sListenAddress,
196 sPrintMotd, sIgnoreRhosts, sX11Forwarding, sX11DisplayOffset,
197 sStrictModes, sEmptyPasswd, sRandomSeedFile, sKeepAlives, sCheckMail,
198 sUseLogin, sAllowTcpForwarding,
199 sAllowUsers, sDenyUsers, sAllowGroups, sDenyGroups,
200 sIgnoreUserKnownHosts, sCiphers, sProtocol, sPidFile,
201 sGatewayPorts, sPubkeyAuthentication, sXAuthLocation, sSubsystem, sMaxStartups,
205 /* Textual representation of the tokens. */
208 ServerOpCodes opcode;
211 { "hostkey", sHostKeyFile },
212 { "hostdsakey", sHostKeyFile }, /* alias */
213 { "pidfile", sPidFile },
214 { "serverkeybits", sServerKeyBits },
215 { "logingracetime", sLoginGraceTime },
216 { "keyregenerationinterval", sKeyRegenerationTime },
217 { "permitrootlogin", sPermitRootLogin },
218 { "syslogfacility", sLogFacility },
219 { "loglevel", sLogLevel },
220 { "rhostsauthentication", sRhostsAuthentication },
221 { "rhostsrsaauthentication", sRhostsRSAAuthentication },
222 { "rsaauthentication", sRSAAuthentication },
223 { "pubkeyauthentication", sPubkeyAuthentication },
224 { "dsaauthentication", sPubkeyAuthentication }, /* alias */
226 { "kerberosauthentication", sKerberosAuthentication },
227 { "kerberosorlocalpasswd", sKerberosOrLocalPasswd },
228 { "kerberosticketcleanup", sKerberosTicketCleanup },
231 { "kerberostgtpassing", sKerberosTgtPassing },
232 { "afstokenpassing", sAFSTokenPassing },
234 { "passwordauthentication", sPasswordAuthentication },
235 { "kbdinteractiveauthentication", sKbdInteractiveAuthentication },
237 { "skeyauthentication", sSkeyAuthentication },
239 { "checkmail", sCheckMail },
240 { "listenaddress", sListenAddress },
241 { "printmotd", sPrintMotd },
242 { "ignorerhosts", sIgnoreRhosts },
243 { "ignoreuserknownhosts", sIgnoreUserKnownHosts },
244 { "x11forwarding", sX11Forwarding },
245 { "x11displayoffset", sX11DisplayOffset },
246 { "xauthlocation", sXAuthLocation },
247 { "strictmodes", sStrictModes },
248 { "permitemptypasswords", sEmptyPasswd },
249 { "uselogin", sUseLogin },
250 { "randomseed", sRandomSeedFile },
251 { "keepalive", sKeepAlives },
252 { "allowtcpforwarding", sAllowTcpForwarding },
253 { "allowusers", sAllowUsers },
254 { "denyusers", sDenyUsers },
255 { "allowgroups", sAllowGroups },
256 { "denygroups", sDenyGroups },
257 { "ciphers", sCiphers },
258 { "protocol", sProtocol },
259 { "gatewayports", sGatewayPorts },
260 { "subsystem", sSubsystem },
261 { "maxstartups", sMaxStartups },
262 { "banner", sBanner },
267 * Returns the number of the token pointed to by cp of length len. Never
268 * returns if the token is not known.
272 parse_token(const char *cp, const char *filename,
277 for (i = 0; keywords[i].name; i++)
278 if (strcasecmp(cp, keywords[i].name) == 0)
279 return keywords[i].opcode;
281 fprintf(stderr, "%s: line %d: Bad configuration option: %s\n",
282 filename, linenum, cp);
290 add_listen_addr(ServerOptions *options, char *addr)
293 struct addrinfo hints, *ai, *aitop;
294 char strport[NI_MAXSERV];
298 if (options->num_ports == 0)
299 options->ports[options->num_ports++] = SSH_DEFAULT_PORT;
300 for (i = 0; i < options->num_ports; i++) {
301 memset(&hints, 0, sizeof(hints));
302 hints.ai_family = IPv4or6;
303 hints.ai_socktype = SOCK_STREAM;
304 hints.ai_flags = (addr == NULL) ? AI_PASSIVE : 0;
305 snprintf(strport, sizeof strport, "%d", options->ports[i]);
306 if ((gaierr = getaddrinfo(addr, strport, &hints, &aitop)) != 0)
307 fatal("bad addr or host: %s (%s)\n",
308 addr ? addr : "<NULL>",
309 gai_strerror(gaierr));
310 for (ai = aitop; ai->ai_next; ai = ai->ai_next)
312 ai->ai_next = options->listen_addrs;
313 options->listen_addrs = aitop;
317 /* Reads the server configuration file. */
320 read_server_config(ServerOptions *options, const char *filename)
324 char *cp, **charptr, *arg;
325 int linenum, *intptr, value;
327 ServerOpCodes opcode;
330 f = fopen(filename, "r");
336 while (fgets(line, sizeof(line), f)) {
340 /* Ignore leading whitespace */
343 if (!*arg || *arg == '#')
347 opcode = parse_token(arg, filename, linenum);
353 /* ignore ports from configfile if cmdline specifies ports */
354 if (options->ports_from_cmdline)
356 if (options->listen_addrs != NULL)
357 fatal("%s line %d: ports must be specified before "
358 "ListenAdress.\n", filename, linenum);
359 if (options->num_ports >= MAX_PORTS)
360 fatal("%s line %d: too many ports.\n",
363 if (!arg || *arg == '\0')
364 fatal("%s line %d: missing port number.\n",
366 options->ports[options->num_ports++] = atoi(arg);
370 intptr = &options->server_key_bits;
373 if (!arg || *arg == '\0') {
374 fprintf(stderr, "%s line %d: missing integer value.\n",
383 case sLoginGraceTime:
384 intptr = &options->login_grace_time;
387 case sKeyRegenerationTime:
388 intptr = &options->key_regeneration_time;
393 if (!arg || *arg == '\0')
394 fatal("%s line %d: missing inet addr.\n",
396 add_listen_addr(options, arg);
400 intptr = &options->num_host_key_files;
401 if (*intptr >= MAX_HOSTKEYS) {
402 fprintf(stderr, "%s line %d: to many host keys specified (max %d).\n",
403 filename, linenum, MAX_HOSTKEYS);
406 charptr = &options->host_key_files[*intptr];
409 if (!arg || *arg == '\0') {
410 fprintf(stderr, "%s line %d: missing file name.\n",
414 if (*charptr == NULL) {
415 *charptr = tilde_expand_filename(arg, getuid());
416 /* increase optional counter */
418 *intptr = *intptr + 1;
423 charptr = &options->pid_file;
426 case sRandomSeedFile:
427 fprintf(stderr, "%s line %d: \"randomseed\" option is obsolete.\n",
432 case sPermitRootLogin:
433 intptr = &options->permit_root_login;
435 if (!arg || *arg == '\0') {
436 fprintf(stderr, "%s line %d: missing yes/without-password/no argument.\n",
440 if (strcmp(arg, "without-password") == 0)
442 else if (strcmp(arg, "yes") == 0)
444 else if (strcmp(arg, "no") == 0)
447 fprintf(stderr, "%s line %d: Bad yes/without-password/no argument: %s\n",
448 filename, linenum, arg);
456 intptr = &options->ignore_rhosts;
459 if (!arg || *arg == '\0') {
460 fprintf(stderr, "%s line %d: missing yes/no argument.\n",
464 if (strcmp(arg, "yes") == 0)
466 else if (strcmp(arg, "no") == 0)
469 fprintf(stderr, "%s line %d: Bad yes/no argument: %s\n",
470 filename, linenum, arg);
477 case sIgnoreUserKnownHosts:
478 intptr = &options->ignore_user_known_hosts;
481 case sRhostsAuthentication:
482 intptr = &options->rhosts_authentication;
485 case sRhostsRSAAuthentication:
486 intptr = &options->rhosts_rsa_authentication;
489 case sRSAAuthentication:
490 intptr = &options->rsa_authentication;
493 case sPubkeyAuthentication:
494 intptr = &options->pubkey_authentication;
498 case sKerberosAuthentication:
499 intptr = &options->kerberos_authentication;
502 case sKerberosOrLocalPasswd:
503 intptr = &options->kerberos_or_local_passwd;
506 case sKerberosTicketCleanup:
507 intptr = &options->kerberos_ticket_cleanup;
512 case sKerberosTgtPassing:
513 intptr = &options->kerberos_tgt_passing;
516 case sAFSTokenPassing:
517 intptr = &options->afs_token_passing;
521 case sPasswordAuthentication:
522 intptr = &options->password_authentication;
525 case sKbdInteractiveAuthentication:
526 intptr = &options->kbd_interactive_authentication;
530 intptr = &options->check_mail;
534 case sSkeyAuthentication:
535 intptr = &options->skey_authentication;
540 intptr = &options->print_motd;
544 intptr = &options->x11_forwarding;
547 case sX11DisplayOffset:
548 intptr = &options->x11_display_offset;
552 charptr = &options->xauth_location;
556 intptr = &options->strict_modes;
560 intptr = &options->keepalives;
564 intptr = &options->permit_empty_passwd;
568 intptr = &options->use_login;
572 intptr = &options->gateway_ports;
576 intptr = (int *) &options->log_facility;
578 value = log_facility_number(arg);
579 if (value == (SyslogFacility) - 1)
580 fatal("%.200s line %d: unsupported log facility '%s'\n",
581 filename, linenum, arg ? arg : "<NONE>");
583 *intptr = (SyslogFacility) value;
587 intptr = (int *) &options->log_level;
589 value = log_level_number(arg);
590 if (value == (LogLevel) - 1)
591 fatal("%.200s line %d: unsupported log level '%s'\n",
592 filename, linenum, arg ? arg : "<NONE>");
594 *intptr = (LogLevel) value;
597 case sAllowTcpForwarding:
598 intptr = &options->allow_tcp_forwarding;
602 while ((arg = strdelim(&cp)) && *arg != '\0') {
603 if (options->num_allow_users >= MAX_ALLOW_USERS)
604 fatal("%s line %d: too many allow users.\n",
606 options->allow_users[options->num_allow_users++] = xstrdup(arg);
611 while ((arg = strdelim(&cp)) && *arg != '\0') {
612 if (options->num_deny_users >= MAX_DENY_USERS)
613 fatal( "%s line %d: too many deny users.\n",
615 options->deny_users[options->num_deny_users++] = xstrdup(arg);
620 while ((arg = strdelim(&cp)) && *arg != '\0') {
621 if (options->num_allow_groups >= MAX_ALLOW_GROUPS)
622 fatal("%s line %d: too many allow groups.\n",
624 options->allow_groups[options->num_allow_groups++] = xstrdup(arg);
629 while ((arg = strdelim(&cp)) && *arg != '\0') {
630 if (options->num_deny_groups >= MAX_DENY_GROUPS)
631 fatal("%s line %d: too many deny groups.\n",
633 options->deny_groups[options->num_deny_groups++] = xstrdup(arg);
639 if (!arg || *arg == '\0')
640 fatal("%s line %d: Missing argument.", filename, linenum);
641 if (!ciphers_valid(arg))
642 fatal("%s line %d: Bad SSH2 cipher spec '%s'.",
643 filename, linenum, arg ? arg : "<NONE>");
644 if (options->ciphers == NULL)
645 options->ciphers = xstrdup(arg);
649 intptr = &options->protocol;
651 if (!arg || *arg == '\0')
652 fatal("%s line %d: Missing argument.", filename, linenum);
653 value = proto_spec(arg);
654 if (value == SSH_PROTO_UNKNOWN)
655 fatal("%s line %d: Bad protocol spec '%s'.",
656 filename, linenum, arg ? arg : "<NONE>");
657 if (*intptr == SSH_PROTO_UNKNOWN)
662 if(options->num_subsystems >= MAX_SUBSYSTEMS) {
663 fatal("%s line %d: too many subsystems defined.",
667 if (!arg || *arg == '\0')
668 fatal("%s line %d: Missing subsystem name.",
670 for (i = 0; i < options->num_subsystems; i++)
671 if(strcmp(arg, options->subsystem_name[i]) == 0)
672 fatal("%s line %d: Subsystem '%s' already defined.",
673 filename, linenum, arg);
674 options->subsystem_name[options->num_subsystems] = xstrdup(arg);
676 if (!arg || *arg == '\0')
677 fatal("%s line %d: Missing subsystem command.",
679 options->subsystem_command[options->num_subsystems] = xstrdup(arg);
680 options->num_subsystems++;
685 if (!arg || *arg == '\0')
686 fatal("%s line %d: Missing MaxStartups spec.",
688 if (sscanf(arg, "%d:%d:%d",
689 &options->max_startups_begin,
690 &options->max_startups_rate,
691 &options->max_startups) == 3) {
692 if (options->max_startups_begin >
693 options->max_startups ||
694 options->max_startups_rate > 100 ||
695 options->max_startups_rate < 1)
696 fatal("%s line %d: Illegal MaxStartups spec.",
700 intptr = &options->max_startups;
704 charptr = &options->banner;
708 fprintf(stderr, "%s line %d: Missing handler for opcode %s (%d)\n",
709 filename, linenum, arg, opcode);
712 if ((arg = strdelim(&cp)) != NULL && *arg != '\0') {
714 "%s line %d: garbage at end of line; \"%.200s\".\n",
715 filename, linenum, arg);
720 if (bad_options > 0) {
721 fprintf(stderr, "%s: terminating, %d bad configuration options\n",
722 filename, bad_options);