upstream: big refactor of sshd config management code.

This generates much of the initialisation, defaults and keyword table
code from a set of macros rather than hand coding them. These same
macros are also used to generate serialisation and deserialisation
code.

The macros are admittedly ugly but have the advantage of forcing a
good degree of consistency across places that need to stay in sync
with each other.

The new de/serialisation code is used to pass configurations across
the various sshd-* process boundaries. This removes the need to pass
around raw text configurations that need to be re-parsed as well as
eliminating some raw pointer leakage across the processes where
structures were previously clumsily serialised.

feedback/ok markus@

OpenBSD-Commit-ID: 9a5109a480637e08c290eeb82aa8ef2ca7e848ce
This commit is contained in:
djm@openbsd.org authored and Damien Miller committed 2026-05-31 22:23:40 +10:00
1 parent a1dd1c8068
commit bebc855fdb
6 files changed
+1713 -850

No files matched your search

+16 -42
View File
@@ -1,4 +1,4 @@
/* $OpenBSD: monitor.c,v 1.255 2026/03/28 05:06:16 djm Exp $ */
/* $OpenBSD: monitor.c,v 1.256 2026/05/31 11:30:50 djm Exp $ */
/*
* Copyright 2002 Niels Provos <provos@citi.umich.edu>
* Copyright 2002 Markus Friedl <markus@openbsd.org>
@@ -592,34 +592,26 @@ monitor_reset_key_state(void)
int
mm_answer_state(struct ssh *ssh, int sock, struct sshbuf *unused)
{
struct sshbuf *m = NULL, *inc = NULL, *hostkeys = NULL;
struct sshbuf *m = NULL, *config = NULL, *hostkeys = NULL;
struct sshbuf *opts = NULL, *confdata = NULL;
struct include_item *item = NULL;
int postauth;
int r;
debug_f("config len %zu", sshbuf_len(cfg));
if ((m = sshbuf_new()) == NULL ||
(inc = sshbuf_new()) == NULL ||
(config = sshbuf_new()) == NULL ||
(opts = sshbuf_new()) == NULL ||
(confdata = sshbuf_new()) == NULL)
fatal_f("sshbuf_new failed");
/* XXX unnecessary? */
/* pack includes into a string */
TAILQ_FOREACH(item, &includes, entry) {
if ((r = sshbuf_put_cstring(inc, item->selector)) != 0 ||
(r = sshbuf_put_cstring(inc, item->filename)) != 0 ||
(r = sshbuf_put_stringb(inc, item->contents)) != 0)
fatal_fr(r, "compose includes");
}
hostkeys = pack_hostkeys();
if ((r = serialise_server_options(&options, &config)) != 0)
fatal_fr(r, "serialise_server_options");
/*
* Protocol from monitor to unpriv privsep process:
* string configuration
* string configuration_blob
* uint64 timing_secret XXX move delays to monitor and remove
* string host_keys[] {
* string public_key
@@ -627,23 +619,17 @@ mm_answer_state(struct ssh *ssh, int sock, struct sshbuf *unused)
* }
* string server_banner
* string client_banner
* string included_files[] {
* string selector
* string filename
* string contents
* }
* string configuration_data (postauth)
* string keystate (postauth)
* string authenticated_user (postauth)
* string session_info (postauth)
* string authopts (postauth)
*/
if ((r = sshbuf_put_stringb(m, cfg)) != 0 ||
if ((r = sshbuf_put_stringb(m, config)) != 0 ||
(r = sshbuf_put_u64(m, options.timing_secret)) != 0 ||
(r = sshbuf_put_stringb(m, hostkeys)) != 0 ||
(r = sshbuf_put_stringb(m, ssh->kex->server_version)) != 0 ||
(r = sshbuf_put_stringb(m, ssh->kex->client_version)) != 0 ||
(r = sshbuf_put_stringb(m, inc)) != 0)
(r = sshbuf_put_stringb(m, ssh->kex->client_version)) != 0)
fatal_fr(r, "compose config");
postauth = (authctxt && authctxt->pw && authctxt->authenticated);
@@ -652,7 +638,7 @@ mm_answer_state(struct ssh *ssh, int sock, struct sshbuf *unused)
fatal_f("internal error: called in postauth");
}
sshbuf_free(inc);
sshbuf_free(config);
sshbuf_free(opts);
sshbuf_free(confdata);
sshbuf_free(hostkeys);
@@ -832,27 +818,15 @@ void
mm_encode_server_options(struct sshbuf *m)
{
int r;
u_int i;
struct sshbuf *config;
/* XXX this leaks raw pointers to the unpriv child processes */
if ((r = sshbuf_put_string(m, &options, sizeof(options))) != 0)
if ((config = sshbuf_new()) == NULL)
fatal_f("sshbuf_new failed");
if ((r = serialise_server_options(&options, &config)) != 0)
fatal_fr(r, "serialise_server_options");
if ((r = sshbuf_put_stringb(m, config)) != 0)
fatal_fr(r, "assemble options");
#define M_CP_STROPT(x) do { \
if (options.x != NULL && \
(r = sshbuf_put_cstring(m, options.x)) != 0) \
fatal_fr(r, "assemble %s", #x); \
} while (0)
#define M_CP_STRARRAYOPT(x, nx, clobber) do { \
for (i = 0; i < options.nx; i++) { \
if ((r = sshbuf_put_cstring(m, options.x[i])) != 0) \
fatal_fr(r, "assemble %s", #x); \
} \
} while (0)
/* See comment in servconf.h */
COPY_MATCH_STRING_OPTS();
#undef M_CP_STROPT
#undef M_CP_STRARRAYOPT
sshbuf_free(config);
}
/* Retrieves the password entry and also checks if the user is permitted */
+16 -68
View File
@@ -1,4 +1,4 @@
/* $OpenBSD: monitor_wrap.c,v 1.146 2026/03/02 02:40:15 djm Exp $ */
/* $OpenBSD: monitor_wrap.c,v 1.147 2026/05/31 11:30:50 djm Exp $ */
/*
* Copyright 2002 Niels Provos <provos@citi.umich.edu>
* Copyright 2002 Markus Friedl <markus@openbsd.org>
@@ -302,55 +302,20 @@ mm_sshkey_sign(struct ssh *ssh, struct sshkey *key, u_char **sigp, size_t *lenp,
void
mm_decode_activate_server_options(struct ssh *ssh, struct sshbuf *m)
{
const u_char *p;
size_t len;
u_int i;
ServerOptions *newopts;
struct sshbuf *config;
int r;
u_int i;
if ((r = sshbuf_get_string_direct(m, &p, &len)) != 0)
if ((r = sshbuf_froms(m, &config)) != 0)
fatal_fr(r, "parse opts");
if (len != sizeof(*newopts))
fatal_f("option block size mismatch");
newopts = xcalloc(sizeof(*newopts), 1);
memcpy(newopts, p, sizeof(*newopts));
if ((r = deserialise_server_options(config, &options)) != 0)
fatal_fr(r, "deserialise_server_options");
sshbuf_free(config);
#define M_CP_STROPT(x) do { \
if (newopts->x != NULL && \
(r = sshbuf_get_cstring(m, &newopts->x, NULL)) != 0) \
fatal_fr(r, "parse %s", #x); \
} while (0)
#define M_CP_STRARRAYOPT(x, nx, clobber) do { \
newopts->x = newopts->nx == 0 ? \
NULL : xcalloc(newopts->nx, sizeof(*newopts->x)); \
for (i = 0; i < newopts->nx; i++) { \
if ((r = sshbuf_get_cstring(m, \
&newopts->x[i], NULL)) != 0) \
fatal_fr(r, "parse %s", #x); \
} \
} while (0)
/* See comment in servconf.h */
COPY_MATCH_STRING_OPTS();
#undef M_CP_STROPT
#undef M_CP_STRARRAYOPT
copy_set_server_options(&options, newopts, 1);
log_change_level(options.log_level);
log_verbose_reset();
for (i = 0; i < options.num_log_verbose; i++)
log_verbose_add(options.log_verbose[i]);
/* use the macro hell to clean up too */
#define M_CP_STROPT(x) free(newopts->x)
#define M_CP_STRARRAYOPT(x, nx, clobber) do { \
for (i = 0; i < newopts->nx; i++) \
free(newopts->x[i]); \
free(newopts->x); \
} while (0)
COPY_MATCH_STRING_OPTS();
#undef M_CP_STROPT
#undef M_CP_STRARRAYOPT
free(newopts);
}
#define GETPW(b, id) \
@@ -885,22 +850,19 @@ mm_terminate(void)
/* Request state information */
void
mm_get_state(struct ssh *ssh, struct include_list *includes,
struct sshbuf *conf, struct sshbuf **confdatap,
mm_get_state(struct ssh *ssh,
ServerOptions *opts, struct sshbuf **confdatap,
uint64_t *timing_secretp,
struct sshbuf **hostkeysp, struct sshbuf **keystatep,
u_char **pw_namep,
struct sshbuf **authinfop, struct sshbuf **auth_optsp)
{
struct sshbuf *m, *inc;
u_char *cp;
size_t len;
struct sshbuf *m, *config;
int r;
struct include_item *item;
debug3_f("entering");
if ((m = sshbuf_new()) == NULL || (inc = sshbuf_new()) == NULL)
if ((m = sshbuf_new()) == NULL || (config = sshbuf_new()) == NULL)
fatal_f("sshbuf_new failed");
mm_request_send(pmonitor->m_recvfd, MONITOR_REQ_STATE, m);
@@ -909,12 +871,11 @@ mm_get_state(struct ssh *ssh, struct include_list *includes,
mm_request_receive_expect(pmonitor->m_recvfd,
MONITOR_ANS_STATE, m);
if ((r = sshbuf_get_string(m, &cp, &len)) != 0 ||
if ((r = sshbuf_froms(m, &config)) != 0 ||
(r = sshbuf_get_u64(m, timing_secretp)) != 0 ||
(r = sshbuf_froms(m, hostkeysp)) != 0 ||
(r = sshbuf_get_stringb(m, ssh->kex->server_version)) != 0 ||
(r = sshbuf_get_stringb(m, ssh->kex->client_version)) != 0 ||
(r = sshbuf_get_stringb(m, inc)) != 0)
(r = sshbuf_get_stringb(m, ssh->kex->client_version)) != 0)
fatal_fr(r, "parse config");
/* postauth */
@@ -926,24 +887,11 @@ mm_get_state(struct ssh *ssh, struct include_list *includes,
(r = sshbuf_froms(m, auth_optsp)) != 0)
fatal_fr(r, "parse config postauth");
}
if ((r = deserialise_server_options(config, opts)) != 0)
fatal_fr(r, "deserialise_server_options");
if (conf != NULL && (r = sshbuf_put(conf, cp, len)))
fatal_fr(r, "sshbuf_put");
while (sshbuf_len(inc) != 0) {
item = xcalloc(1, sizeof(*item));
if ((item->contents = sshbuf_new()) == NULL)
fatal_f("sshbuf_new failed");
if ((r = sshbuf_get_cstring(inc, &item->selector, NULL)) != 0 ||
(r = sshbuf_get_cstring(inc, &item->filename, NULL)) != 0 ||
(r = sshbuf_get_stringb(inc, item->contents)) != 0)
fatal_fr(r, "parse includes");
TAILQ_INSERT_TAIL(includes, item, entry);
}
free(cp);
sshbuf_free(m);
sshbuf_free(inc);
sshbuf_free(config);
debug3_f("done");
}
+3 -3
View File
@@ -1,4 +1,4 @@
/* $OpenBSD: monitor_wrap.h,v 1.54 2026/03/02 02:40:15 djm Exp $ */
/* $OpenBSD: monitor_wrap.h,v 1.55 2026/05/31 11:30:50 djm Exp $ */
/*
* Copyright 2002 Niels Provos <provos@citi.umich.edu>
@@ -96,8 +96,8 @@ void mm_session_pty_cleanup2(struct Session *);
void mm_send_keystate(struct ssh *, struct monitor*);
/* state */
struct include_list;
void mm_get_state(struct ssh *, struct include_list *, struct sshbuf *,
struct ServerOptions;
void mm_get_state(struct ssh *, struct ServerOptions *,
struct sshbuf **, uint64_t *, struct sshbuf **, struct sshbuf **,
u_char **, struct sshbuf **, struct sshbuf **);
+1379 -508
View File
File diff suppressed because it is too large. Load diff
+285 -186
View File
@@ -1,4 +1,4 @@
/* $OpenBSD: servconf.h,v 1.176 2026/03/03 09:57:25 dtucker Exp $ */
/* $OpenBSD: servconf.h,v 1.177 2026/05/31 11:30:50 djm Exp $ */
/*
* Author: Tatu Ylonen <ylo@cs.hut.fi>
@@ -18,6 +18,8 @@
#include <sys/queue.h>
struct sshbuf;
#define MAX_PORTS 256 /* Max # ports. */
/* permit_root_login */
@@ -46,6 +48,15 @@
#define PUBKEYAUTH_TOUCH_REQUIRED (1)
#define PUBKEYAUTH_VERIFY_REQUIRED (1<<1)
/* Various defaults */
#define SSHD_DEFAULT_LOGIN_GRACE_TIME 120
#define SSHD_DEFAULT_X11_DISPLAY_OFFSET 10
#ifdef WITH_ZLIB
#define SSHD_DEFAULT_COMPRESSION COMP_DELAYED
#else
#define SSHD_DEFAULT_COMPRESSION COMP_NONE
#endif
struct ssh;
/*
@@ -83,179 +94,306 @@ struct per_source_penalty {
double penalty_min;
};
typedef struct {
/* Options for whether config entries are copied after Match processing */
#define SSHCFG_COPY_NONE(action)
#define SSHCFG_COPY_MATCH(action) action
#define SSHCFG_COPY_MANUAL(action)
/*
* This macro is used to generate most of ServerOptions and some of the
* parsing and de/serialisation code in servconf.c. Every variable in
* ServerOptions *must* be represented here.
*
* Variables and configuration options that need special handling (e.g.
* those that represent a struct or use a single option to populate multiple
* values) use the SSHCONF_CUSTOM macro and get manual variable entries in
* ServerOptions below.
*
* Variables that exist in ServerOptions but aren't populated by a keyword
* use the SSHCONF_NONCONF macro and also get manual entries in ServerOptions.
*
* Everything else uses one of the SSHCONF_INT, SSHCONF_INTFLAG,
* SSHCONF_STRING, or SSHCONF_STRARRAY macros. These automatically populate
* their corresponding variable definitions in ServerOptions. The integer
* options also include defaults for initialisation.
*
* Unsupported, deprecated and ignored options use SSHCONF_NOSUPPORT and
* don't populate ServerOptions. Deprecated aliases that still work use
* SSHCONF_ALIAS.
*
* Why go to all this trouble? It ensures a level of consistency between
* the configuration structure and the parsing code and helps us write
* serialisation/deserialisation functions that we can be pretty sure will
* capture every value in the configuration file.
*
* Entry formats:
* SSHCONF_INT(field, keyword, scope, multistate, default, copy)
* SSHCONF_INTFLAG(field, keyword, scope, default, copy)
* SSHCONF_STRING(field, keyword, scope, copy)
* SSHCONF_STRARRAY(field, nfield, keyword, scope, copy)
* SSHCONF_CUSTOM(keyword, suffix, scope, copy)
* SSHCONF_NONCONF(suffix)
* SSHCONF_NOSUPPORT(field, keyword, token, scope)
* SSHCONF_ALIAS(old_keyword, keyword, scope)
*/
#define SSHD_CONFIG_ENTRIES_CUSTOM \
SSHCONF_CUSTOM(Port, port, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(ListenAddress, listenaddress, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(HostKey, hostkeyfile, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(IPQoS, ipqos, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_CUSTOM(GatewayPorts, gatewayports, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_CUSTOM(StreamLocalBindMask, streamlocalbindmask, SSHCFG_ALL, SSHCFG_COPY_MANUAL) \
SSHCONF_CUSTOM(StreamLocalBindUnlink, streamlocalbindunlink, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_CUSTOM(SyslogFacility, logfacility, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(LogLevel, loglevel, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_CUSTOM(PermitUserEnvironment, permituserenv, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(Subsystem, subsystem, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_CUSTOM(MaxStartups, maxstartups, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(PerSourceNetBlockSize, persourcenetblocksize, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(PerSourcePenalties, persourcepenalties, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_CUSTOM(RekeyLimit, rekeylimit, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_NONCONF(timingsecret)
#define SSHD_CONFIG_ENTRIES_MAIN \
SSHCONF_INT(address_family, AddressFamily, SSHCFG_GLOBAL, multistate_addressfamily, AF_UNSPEC, SSHCFG_COPY_NONE) \
SSHCONF_STRING(routing_domain, RDomain, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(host_cert_files, num_host_cert_files, HostCertificate, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRING(host_key_agent, HostKeyAgent, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRING(pid_file, PidFile, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRING(moduli_file, ModuliFile, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_INT(login_grace_time, LoginGraceTime, SSHCFG_GLOBAL, NULL, SSHD_DEFAULT_LOGIN_GRACE_TIME, SSHCFG_COPY_NONE) \
SSHCONF_INT(permit_root_login, PermitRootLogin, SSHCFG_ALL, multistate_permitrootlogin, PERMIT_NO_PASSWD, SSHCFG_COPY_MATCH) \
SSHCONF_INT(ignore_rhosts, IgnoreRhosts, SSHCFG_ALL, multistate_ignore_rhosts, 1, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(ignore_user_known_hosts, IgnoreUserKnownHosts, SSHCFG_GLOBAL, 0, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(print_motd, PrintMotd, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(x11_forwarding, X11Forwarding, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_INT(x11_display_offset, X11DisplayOffset, SSHCFG_ALL, NULL, SSHD_DEFAULT_X11_DISPLAY_OFFSET, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(x11_use_localhost, X11UseLocalhost, SSHCFG_ALL, 1, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(xauth_location, XAuthLocation, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(permit_tty, PermitTTY, SSHCFG_ALL, 1, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(permit_user_rc, PermitUserRC, SSHCFG_ALL, 1, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(strict_modes, StrictModes, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(tcp_keep_alive, TCPKeepAlive, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE) \
SSHCONF_STRING(ciphers, Ciphers, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRING(macs, Macs, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRING(kex_algorithms, KexAlgorithms, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRARRAY(log_verbose, num_log_verbose, LogVerbose, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(hostbased_authentication, HostbasedAuthentication, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(hostbased_uses_name_from_packet_only, HostbasedUsesNameFromPacketOnly, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(hostbased_accepted_algos, HostbasedAcceptedAlgorithms, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(hostkeyalgorithms, HostKeyAlgorithms, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRING(ca_sign_algorithms, CASignatureAlgorithms, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_INT(pubkey_auth_options, PubkeyAuthOptions, SSHCFG_ALL, NULL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(pubkey_authentication, PubkeyAuthentication, SSHCFG_ALL, 1, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(pubkey_accepted_algos, PubkeyAcceptedAlgorithms, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(password_authentication, PasswordAuthentication, SSHCFG_ALL, 1, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(kbd_interactive_authentication, KbdInteractiveAuthentication, SSHCFG_ALL, 1, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(permit_empty_passwd, PermitEmptyPasswords, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_INT(compression, Compression, SSHCFG_GLOBAL, multistate_compression, SSHD_DEFAULT_COMPRESSION, SSHCFG_COPY_NONE) \
SSHCONF_INT(allow_tcp_forwarding, AllowTcpForwarding, SSHCFG_ALL, multistate_tcpfwd, FORWARD_ALLOW, SSHCFG_COPY_MATCH) \
SSHCONF_INT(allow_streamlocal_forwarding, AllowStreamLocalForwarding, SSHCFG_ALL, multistate_tcpfwd, FORWARD_ALLOW, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(allow_agent_forwarding, AllowAgentForwarding, SSHCFG_ALL, 1, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(disable_forwarding, DisableForwarding, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(allow_users, num_allow_users, AllowUsers, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(deny_users, num_deny_users, DenyUsers, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(allow_groups, num_allow_groups, AllowGroups, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(deny_groups, num_deny_groups, DenyGroups, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(accept_env, num_accept_env, AcceptEnv, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(setenv, num_setenv, SetEnv, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_INT(per_source_max_startups, PerSourceMaxStartups, SSHCFG_GLOBAL, NULL, INT_MAX, SSHCFG_COPY_NONE) \
SSHCONF_STRING(per_source_penalty_exempt, PerSourcePenaltyExemptList, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_INT(max_authtries, MaxAuthTries, SSHCFG_ALL, NULL, DEFAULT_AUTH_FAIL_MAX, SSHCFG_COPY_MATCH) \
SSHCONF_INT(max_sessions, MaxSessions, SSHCFG_ALL, NULL, DEFAULT_SESSIONS_MAX, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(banner, Banner, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(use_dns, UseDNS, SSHCFG_GLOBAL, 0, SSHCFG_COPY_NONE) \
SSHCONF_INT(client_alive_interval, ClientAliveInterval, SSHCFG_ALL, NULL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_INT(client_alive_count_max, ClientAliveCountMax, SSHCFG_ALL, NULL, 3, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(authorized_keys_files, num_authkeys_files, AuthorizedKeysFile, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(adm_forced_command, ForceCommand, SSHCFG_ALL, SSHCFG_COPY_MANUAL) \
SSHCONF_INTFLAG(permit_tun, PermitTunnel, SSHCFG_ALL, SSH_TUNMODE_NO, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(permitted_opens, num_permitted_opens, PermitOpen, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(permitted_listens, num_permitted_listens, PermitListen, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(chroot_directory, ChrootDirectory, SSHCFG_ALL, SSHCFG_COPY_MANUAL) \
SSHCONF_STRARRAY(revoked_keys_files, num_revoked_keys_files, RevokedKeys, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(trusted_user_ca_keys, TrustedUserCAKeys, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(authorized_keys_command, AuthorizedKeysCommand, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(authorized_keys_command_user, AuthorizedKeysCommandUser, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(authorized_principals_file, AuthorizedPrincipalsFile, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(authorized_principals_command, AuthorizedPrincipalsCommand, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(authorized_principals_command_user, AuthorizedPrincipalsCommandUser, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(version_addendum, VersionAddendum, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRARRAY(auth_methods, num_auth_methods, AuthenticationMethods, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_INT(fingerprint_hash, FingerprintHash, SSHCFG_GLOBAL, NULL, SSH_FP_HASH_DEFAULT, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(expose_userauth_info, ExposeAuthInfo, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(sk_provider, SecurityKeyProvider, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_INT(required_rsa_size, RequiredRSASize, SSHCFG_ALL, NULL, SSH_RSA_MINIMUM_MODULUS_SIZE, SSHCFG_COPY_MATCH) \
SSHCONF_STRARRAY(channel_timeouts, num_channel_timeouts, ChannelTimeout, SSHCFG_ALL, SSHCFG_COPY_MATCH) \
SSHCONF_INT(unused_connection_timeout, UnusedConnectionTimeout, SSHCFG_ALL, NULL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_STRING(sshd_session_path, SshdSessionPath, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_STRING(sshd_auth_path, SshdAuthPath, SSHCFG_GLOBAL, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(refuse_connection, RefuseConnection, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH)
#define SSHD_CONFIG_ENTRIES_LEGACY \
SSHCONF_NOSUPPORT(server_key_bits, ServerKeyBits, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(key_regeneration_interval, KeyRegenerationInterval, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(rhosts_authentication, RHostsAuthentication, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(rhosts_rsa_authentication, RhostsRSAAuthentication, SSHCONF_DEPRECATED, SSHCFG_ALL) \
SSHCONF_NOSUPPORT(rsa_authentication, RSAAuthentication, SSHCONF_DEPRECATED, SSHCFG_ALL) \
SSHCONF_NOSUPPORT(check_mail, CheckMail, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(use_login, UseLogin, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(verify_reverse_mapping, VerifyReverseMapping, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(reverse_mapping_check, ReverseMappingCheck, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(authorized_keys_file2, AuthorizedKeysFile2, SSHCONF_DEPRECATED, SSHCFG_ALL) \
SSHCONF_NOSUPPORT(use_privilege_separation, UsePrivilegeSeparation, SSHCONF_DEPRECATED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(protocol, Protocol, SSHCONF_IGNORE, SSHCFG_GLOBAL)
#define SSHD_CONFIG_ENTRIES_ALIASES \
SSHCONF_ALIAS(HostDSAKey, HostKey, SSHCFG_GLOBAL) \
SSHCONF_ALIAS(HostBasedAcceptedKeyTypes, HostbasedAcceptedAlgorithms, SSHCFG_ALL) \
SSHCONF_ALIAS(PubkeyAcceptedKeyTypes, PubkeyAcceptedAlgorithms, SSHCFG_ALL) \
SSHCONF_ALIAS(DSAAuthentication, PubkeyAuthentication, SSHCFG_GLOBAL) \
SSHCONF_ALIAS(ChallengeResponseAuthentication, KbdInteractiveAuthentication, SSHCFG_ALL) \
SSHCONF_ALIAS(SKeyAuthentication, KbdInteractiveAuthentication, SSHCFG_ALL) \
SSHCONF_ALIAS(KeepAlive, TCPKeepAlive, SSHCFG_GLOBAL)
#define SSHD_CONFIG_ENTRIES_BASE \
SSHD_CONFIG_ENTRIES_CUSTOM \
SSHD_CONFIG_ENTRIES_MAIN \
SSHD_CONFIG_ENTRIES_LEGACY \
SSHD_CONFIG_ENTRIES_ALIASES \
SSHD_CONFIG_ENTRIES_LASTLOG
#ifdef DISABLE_LASTLOG
#define SSHD_CONFIG_ENTRIES_LASTLOG \
SSHCONF_NOSUPPORT(print_lastlog, PrintLastLog, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL)
#else
#define SSHD_CONFIG_ENTRIES_LASTLOG \
SSHCONF_INTFLAG(print_lastlog, PrintLastLog, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE)
#endif
/* Compile-time enabled options */
#ifdef KRB5
#ifdef USE_AFS
#define SSHD_CONFIG_KRB5_AFS \
SSHCONF_INTFLAG(kerberos_get_afs_token, KerberosGetAFSToken, SSHCFG_GLOBAL, 0, SSHCFG_COPY_NONE)
#else /* USE_AFS */
#define SSHD_CONFIG_KRB5_AFS \
SSHCONF_NOSUPPORT(kerberos_get_afs_token, KerberosGetAFSToken, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL)
#endif /* USE_AFS */
#define SSHD_CONFIG_ENTRIES_KRB5 \
SSHCONF_INTFLAG(kerberos_authentication, KerberosAuthentication, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(kerberos_or_local_passwd, KerberosOrLocalPasswd, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(kerberos_ticket_cleanup, KerberosTicketCleanup, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE) \
SSHD_CONFIG_KRB5_AFS
#else /* KRB5 */
#define SSHD_CONFIG_ENTRIES_KRB5 \
SSHCONF_NOSUPPORT(kerberos_authentication, KerberosAuthentication, SSHCONF_UNSUPPORTED, SSHCFG_ALL) \
SSHCONF_NOSUPPORT(kerberos_or_local_passwd, KerberosOrLocalPasswd, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(kerberos_ticket_cleanup, KerberosTicketCleanup, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(kerberos_get_afs_token, KerberosGetAFSToken, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(kerberos_tgt_passing, KerberosTgtPassing, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(afs_token_passing, AFSTokenPassing, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL)
#endif /* KRB5 */
#ifdef GSSAPI
#define SSHD_CONFIG_ENTRIES_GSS \
SSHCONF_INTFLAG(gss_authentication, GssAuthentication, SSHCFG_ALL, 0, SSHCFG_COPY_MATCH) \
SSHCONF_INTFLAG(gss_cleanup_creds, GssCleanupCreds, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(gss_deleg_creds, GssDelegateCreds, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE) \
SSHCONF_INTFLAG(gss_strict_acceptor, GssStrictAcceptor, SSHCFG_GLOBAL, 1, SSHCFG_COPY_NONE)
#else /* GSSAPI */
#define SSHD_CONFIG_ENTRIES_GSS \
SSHCONF_NOSUPPORT(gss_authentication, GssAuthentication, SSHCONF_UNSUPPORTED, SSHCFG_ALL) \
SSHCONF_NOSUPPORT(gss_cleanup_creds, GssCleanupCreds, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(gss_deleg_creds, GssDelegateCreds, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL) \
SSHCONF_NOSUPPORT(gss_strict_acceptor, GssStrictAcceptor, SSHCONF_UNSUPPORTED, SSHCFG_GLOBAL)
#endif /* GSSAPI */
#define SSHD_CONFIG_ENTRIES \
SSHD_CONFIG_ENTRIES_BASE \
SSHD_CONFIG_ENTRIES_KRB5 \
SSHD_CONFIG_ENTRIES_GSS \
/* Macros to declare ServerOptions member variables */
#define SSHCONF_INT(var, conf, flags, ms, def, cp) int var;
#define SSHCONF_INTFLAG(var, conf, flags, def, cp) int var;
#define SSHCONF_STRING(var, conf, flags, cp) char *var;
#define SSHCONF_STRARRAY(var, nvar, conf, flags, cp) \
char **var; \
u_int nvar;
#define SSHCONF_CUSTOM(conf, funcsuffix, flags, cp) /* empty */
#define SSHCONF_NONCONF(funcsuffix) /* empty */
#define SSHCONF_NOSUPPORT(var, conf, opcode, flags) /* empty */
#define SSHCONF_ALIAS(old, conf, flags) /* empty */
typedef struct ServerOptions {
SSHD_CONFIG_ENTRIES
/* Ports */
u_int num_ports;
u_int ports_from_cmdline;
int ports[MAX_PORTS]; /* Port number to listen on. */
/* ListenAddress */
struct queued_listenaddr *queued_listen_addrs;
u_int num_queued_listens;
struct listenaddr *listen_addrs;
u_int num_listen_addrs;
int address_family; /* Address family used by the server. */
char *routing_domain; /* Bind session to routing domain */
/* HostKey */
char **host_key_files; /* Files containing host keys. */
int *host_key_file_userprovided; /* Key was specified by user. */
u_int num_host_key_files; /* Number of files for host keys. */
char **host_cert_files; /* Files containing host certs. */
u_int num_host_cert_files; /* Number of files for host certs. */
char *host_key_agent; /* ssh-agent socket for host keys. */
char *pid_file; /* Where to put our pid */
char *moduli_file; /* moduli file for DH-GEX */
int login_grace_time; /* Disconnect if no auth in this time
* (sec). */
int permit_root_login; /* PERMIT_*, see above */
int ignore_rhosts; /* Ignore .rhosts and .shosts. */
int ignore_user_known_hosts; /* Ignore ~/.ssh/known_hosts
* for RhostsRsaAuth */
int print_motd; /* If true, print /etc/motd. */
int print_lastlog; /* If true, print lastlog */
int x11_forwarding; /* If true, permit inet (spoofing) X11 fwd. */
int x11_display_offset; /* What DISPLAY number to start
* searching at */
int x11_use_localhost; /* If true, use localhost for fake X11 server. */
char *xauth_location; /* Location of xauth program */
int permit_tty; /* If false, deny pty allocation */
int permit_user_rc; /* If false, deny ~/.ssh/rc execution */
int strict_modes; /* If true, require string home dir modes. */
int tcp_keep_alive; /* If true, set SO_KEEPALIVE. */
/* IPQoS */
int ip_qos_interactive; /* IP ToS/DSCP/class for interactive */
int ip_qos_bulk; /* IP ToS/DSCP/class for bulk traffic */
char *ciphers; /* Supported SSH2 ciphers. */
char *macs; /* Supported SSH2 macs. */
char *kex_algorithms; /* SSH2 kex methods in order of preference. */
/* GatewayPorts, StreamLocalBindMask, StreamLocalBindUnlink */
struct ForwardOptions fwd_opts; /* forwarding options */
/* LogFacility */
SyslogFacility log_facility; /* Facility for system logging. */
/* LogLevel */
LogLevel log_level; /* Level for system logging. */
u_int num_log_verbose; /* Verbose log overrides */
char **log_verbose;
int hostbased_authentication; /* If true, permit ssh2 hostbased auth */
int hostbased_uses_name_from_packet_only; /* experimental */
char *hostbased_accepted_algos; /* Algos allowed for hostbased */
char *hostkeyalgorithms; /* SSH2 server key types */
char *ca_sign_algorithms; /* Allowed CA signature algorithms */
int pubkey_authentication; /* If true, permit ssh2 pubkey authentication. */
char *pubkey_accepted_algos; /* Signature algos allowed for pubkey */
int pubkey_auth_options; /* -1 or mask of PUBKEYAUTH_* flags */
int kerberos_authentication; /* If true, permit Kerberos
* authentication. */
int kerberos_or_local_passwd; /* If true, permit kerberos
* and any other password
* authentication mechanism,
* such as SecurID or
* /etc/passwd */
int kerberos_ticket_cleanup; /* If true, destroy ticket
* file on logout. */
int kerberos_get_afs_token; /* If true, try to get AFS token if
* authenticated with Kerberos. */
int gss_authentication; /* If true, permit GSSAPI authentication */
int gss_cleanup_creds; /* If true, destroy cred cache on logout */
int gss_deleg_creds; /* If true, accept delegated GSS credentials */
int gss_strict_acceptor; /* If true, restrict the GSSAPI acceptor name */
int password_authentication; /* If true, permit password
* authentication. */
int kbd_interactive_authentication; /* If true, permit */
int permit_empty_passwd; /* If false, do not permit empty
* passwords. */
/* PermitUserEnvironment */
int permit_user_env; /* If true, read ~/.ssh/environment */
char *permit_user_env_allowlist; /* pattern-list of allowed env names */
int compression; /* If true, compression is allowed */
int allow_tcp_forwarding; /* One of FORWARD_* */
int allow_streamlocal_forwarding; /* One of FORWARD_* */
int allow_agent_forwarding;
int disable_forwarding;
u_int num_allow_users;
char **allow_users;
u_int num_deny_users;
char **deny_users;
u_int num_allow_groups;
char **allow_groups;
u_int num_deny_groups;
char **deny_groups;
/* Subsystem */
u_int num_subsystems;
char **subsystem_name;
char **subsystem_command;
char **subsystem_args;
u_int num_accept_env;
char **accept_env;
u_int num_setenv;
char **setenv;
/* MaxStartups */
int max_startups_begin;
int max_startups_rate;
int max_startups;
int per_source_max_startups;
/* PerSourceNetBlockSize */
int per_source_masklen_ipv4;
int per_source_masklen_ipv6;
char *per_source_penalty_exempt;
/* PerSourcePenalties */
struct per_source_penalty per_source_penalty;
int max_authtries;
int max_sessions;
char *banner; /* SSH-2 banner message */
int use_dns;
int client_alive_interval; /*
* poke the client this often to
* see if it's still there
*/
int client_alive_count_max; /*
* If the client is unresponsive
* for this many intervals above,
* disconnect the session
*/
u_int num_authkeys_files; /* Files containing public keys */
char **authorized_keys_files;
char *adm_forced_command;
int use_pam; /* Enable auth via PAM */
char *pam_service_name;
int permit_tun;
char **permitted_opens; /* May also be one of PERMITOPEN_* */
u_int num_permitted_opens;
char **permitted_listens; /* May also be one of PERMITOPEN_* */
u_int num_permitted_listens;
char *chroot_directory;
uint num_revoked_keys_files;
char **revoked_keys_files;
char *trusted_user_ca_keys;
char *authorized_keys_command;
char *authorized_keys_command_user;
char *authorized_principals_file;
char *authorized_principals_command;
char *authorized_principals_command_user;
/* RekeyLimit */
int64_t rekey_limit;
int rekey_interval;
char *version_addendum; /* Appended to SSH banner */
u_int num_auth_methods;
char **auth_methods;
int fingerprint_hash;
int expose_userauth_info;
/* Passed by config but not keyword for this */
uint64_t timing_secret;
char *sk_provider;
int required_rsa_size; /* minimum size of RSA keys */
char **channel_timeouts; /* inactivity timeout by channel type */
u_int num_channel_timeouts;
int unused_connection_timeout;
char *sshd_session_path;
char *sshd_auth_path;
int refuse_connection;
/* Placeholders for compile-time disabled things */
/* XXX djm redo macros to remove these */
#ifndef WITH_PAM
int use_pam;
#endif
#ifdef DISABLE_LASTLOG
int print_lastlog;
#endif
#ifndef KRB5
int kerberos_authentication;
#endif
} ServerOptions;
#undef SSHCONF_INT
#undef SSHCONF_INTFLAG
#undef SSHCONF_STRING
#undef SSHCONF_STRARRAY
#undef SSHCONF_CUSTOM
#undef SSHCONF_NONCONF
#undef SSHCONF_NOSUPPORT
#undef SSHCONF_ALIAS
/* Information about the incoming connection as used by Match */
struct connection_info {
@@ -280,49 +418,6 @@ struct include_item {
TAILQ_HEAD(include_list, include_item);
/*
* These are string config options that must be copied between the
* Match sub-config and the main config, and must be sent from the
* privsep child to the privsep master. We use a macro to ensure all
* the options are copied and the copies are done in the correct order.
*
* NB. an option must appear in servconf.c:copy_set_server_options() or
* COPY_MATCH_STRING_OPTS here but never both.
*/
#define COPY_MATCH_STRING_OPTS() do { \
M_CP_STROPT(banner); \
M_CP_STROPT(trusted_user_ca_keys); \
M_CP_STROPT(authorized_keys_command); \
M_CP_STROPT(authorized_keys_command_user); \
M_CP_STROPT(authorized_principals_file); \
M_CP_STROPT(authorized_principals_command); \
M_CP_STROPT(authorized_principals_command_user); \
M_CP_STROPT(hostbased_accepted_algos); \
M_CP_STROPT(pubkey_accepted_algos); \
M_CP_STROPT(ca_sign_algorithms); \
M_CP_STROPT(routing_domain); \
M_CP_STROPT(permit_user_env_allowlist); \
M_CP_STROPT(pam_service_name); \
M_CP_STRARRAYOPT(authorized_keys_files, num_authkeys_files, 1);\
M_CP_STRARRAYOPT(revoked_keys_files, \
num_revoked_keys_files, 1); \
M_CP_STRARRAYOPT(allow_users, num_allow_users, 1); \
M_CP_STRARRAYOPT(deny_users, num_deny_users, 1); \
M_CP_STRARRAYOPT(allow_groups, num_allow_groups, 1); \
M_CP_STRARRAYOPT(deny_groups, num_deny_groups, 1); \
M_CP_STRARRAYOPT(accept_env, num_accept_env, 1); \
M_CP_STRARRAYOPT(setenv, num_setenv, 1); \
M_CP_STRARRAYOPT(auth_methods, num_auth_methods, 1); \
M_CP_STRARRAYOPT(permitted_opens, num_permitted_opens, 1); \
M_CP_STRARRAYOPT(permitted_listens, num_permitted_listens, 1); \
M_CP_STRARRAYOPT(channel_timeouts, num_channel_timeouts, 1); \
M_CP_STRARRAYOPT(log_verbose, num_log_verbose, 1); \
/* Note: don't clobber num_subsystems until all copied */ \
M_CP_STRARRAYOPT(subsystem_name, num_subsystems, 0); \
M_CP_STRARRAYOPT(subsystem_command, num_subsystems, 0); \
M_CP_STRARRAYOPT(subsystem_args, num_subsystems, 1); \
} while (0)
void initialize_server_options(ServerOptions *);
void fill_default_server_options(ServerOptions *);
int process_server_config_line(ServerOptions *, char *, const char *, int,
@@ -342,4 +437,8 @@ void servconf_add_hostkey(const char *, const int,
void servconf_add_hostcert(const char *, const int,
ServerOptions *, const char *path);
int serialise_server_options(const ServerOptions *, struct sshbuf **);
int deserialise_server_options(struct sshbuf *, ServerOptions *);
void free_server_options(ServerOptions *);
#endif /* SERVCONF_H */
+14 -43
View File
@@ -1,4 +1,4 @@
/* $OpenBSD: sshd-auth.c,v 1.14 2026/03/11 09:10:59 dtucker Exp $ */
/* $OpenBSD: sshd-auth.c,v 1.15 2026/05/31 11:30:50 djm Exp $ */
/*
* SSH2 implementation:
* Privilege Separation:
@@ -412,14 +412,13 @@ parse_hostkeys(struct sshbuf *hostkeys)
}
static void
recv_privsep_state(struct ssh *ssh, struct sshbuf *conf,
uint64_t *timing_secretp)
recv_privsep_state(struct ssh *ssh, ServerOptions *o, uint64_t *timing_secretp)
{
struct sshbuf *hostkeys;
debug3_f("begin");
mm_get_state(ssh, &includes, conf, NULL, timing_secretp,
mm_get_state(ssh, o, NULL, timing_secretp,
&hostkeys, NULL, NULL, NULL, NULL);
parse_hostkeys(hostkeys);
@@ -439,11 +438,9 @@ main(int ac, char **av)
extern int optind;
int r, opt, have_key = 0;
int sock_in = -1, sock_out = -1, rexeced_flag = 0;
char *line;
u_int i;
mode_t new_umask;
Authctxt *authctxt;
struct connection_info *connection_info = NULL;
sigset_t sigmask;
uint64_t timing_secret = 0;
@@ -482,17 +479,16 @@ main(int ac, char **av)
"C:E:b:c:f:g:h:k:o:p:u:46DGQRTdeiqrtV")) != -1) {
switch (opt) {
case '4':
options.address_family = AF_INET;
/* ignore */
break;
case '6':
options.address_family = AF_INET6;
/* ignore */
break;
case 'f':
config_file_name = optarg;
/* ignore */
break;
case 'c':
servconf_add_hostcert("[command-line]", 0,
&options, optarg);
/* ignore */
break;
case 'd':
if (debug_flag == 0) {
@@ -519,46 +515,28 @@ main(int ac, char **av)
/* ignored */
break;
case 'q':
options.log_level = SYSLOG_LEVEL_QUIET;
/* ignored */
break;
case 'b':
/* protocol 1, ignored */
break;
case 'p':
options.ports_from_cmdline = 1;
if (options.num_ports >= MAX_PORTS) {
fprintf(stderr, "too many ports.\n");
exit(1);
}
options.ports[options.num_ports++] = a2port(optarg);
if (options.ports[options.num_ports-1] <= 0) {
fprintf(stderr, "Bad port number.\n");
exit(1);
}
/* ignored */
break;
case 'g':
if ((options.login_grace_time = convtime(optarg)) == -1) {
fprintf(stderr, "Invalid login grace time.\n");
exit(1);
}
/* ignored */
break;
case 'k':
/* protocol 1, ignored */
break;
case 'h':
servconf_add_hostkey("[command-line]", 0,
&options, optarg, 1);
/* ignored */
break;
case 't':
case 'T':
case 'G':
fatal("test/dump modes not supported");
break;
case 'C':
connection_info = server_get_connection_info(ssh, 0, 0);
if (parse_server_match_testspec(connection_info,
optarg) == -1)
exit(1);
fatal("test/dump modes not supported");
break;
case 'u':
utmp_len = (u_int)strtonum(optarg, 0, HOST_NAME_MAX+1+1, NULL);
@@ -568,11 +546,7 @@ main(int ac, char **av)
}
break;
case 'o':
line = xstrdup(optarg);
if (process_server_config_line(&options, line,
"command-line", 0, NULL, NULL, &includes) != 0)
exit(1);
free(line);
/* ignored */
break;
case 'V':
fprintf(stderr, "%s, %s\n",
@@ -637,10 +611,7 @@ main(int ac, char **av)
if ((cfg = sshbuf_new()) == NULL)
fatal("sshbuf_new config buf failed");
setproctitle("%s", "[session-auth early]");
recv_privsep_state(ssh, cfg, &timing_secret);
parse_server_config(&options, "rexec", cfg, &includes, NULL, 1);
/* Fill in default values for those options not explicitly set. */
fill_default_server_options(&options);
recv_privsep_state(ssh, &options, &timing_secret);
options.timing_secret = timing_secret; /* XXX eliminate from unpriv */
ssh_packet_set_qos(ssh, options.ip_qos_interactive,
options.ip_qos_bulk);