From c1c2ca1365b3f7b626683690bd2c68265f6d8ffd Mon Sep 17 00:00:00 2001 From: "djm@openbsd.org" Date: Wed, 21 Jun 2023 05:10:26 +0000 Subject: [PATCH] upstream: better validate CASignatureAlgorithms in ssh_config and sshd_config. Previously this directive would accept certificate algorithm names, but these were unusable in practice as OpenSSH does not support CA chains. part of bz3577; ok dtucker@ OpenBSD-Commit-ID: a992d410c8a78ec982701bc3f91043dbdb359912 --- readconf.c | 10 +++++++--- servconf.c | 10 ++++++++-- sshkey.c | 7 +++++-- sshkey.h | 4 ++-- 4 files changed, 22 insertions(+), 9 deletions(-) diff --git a/readconf.c b/readconf.c index 0816ef6b3..bb3bf767b 100644 --- a/readconf.c +++ b/readconf.c @@ -1,4 +1,4 @@ -/* $OpenBSD: readconf.c,v 1.376 2023/03/31 04:23:02 djm Exp $ */ +/* $OpenBSD: readconf.c,v 1.377 2023/06/21 05:10:26 djm Exp $ */ /* * Author: Tatu Ylonen * Copyright (c) 1995 Tatu Ylonen , Espoo, Finland @@ -945,7 +945,7 @@ process_config_line_depth(Options *options, struct passwd *pw, const char *host, char **cpptr, ***cppptr, fwdarg[256]; u_int i, *uintptr, uvalue, max_entries = 0; int r, oactive, negated, opcode, *intptr, value, value2, cmdline = 0; - int remotefwd, dynamicfwd; + int remotefwd, dynamicfwd, ca_only = 0; LogLevel *log_level_ptr; SyslogFacility *log_facility_ptr; long long val64; @@ -1441,6 +1441,7 @@ parse_int: case oHostKeyAlgorithms: charptr = &options->hostkeyalgorithms; + ca_only = 0; parse_pubkey_algos: arg = argv_next(&ac, &av); if (!arg || *arg == '\0') { @@ -1450,7 +1451,7 @@ parse_pubkey_algos: } if (*arg != '-' && !sshkey_names_valid2(*arg == '+' || *arg == '^' ? - arg + 1 : arg, 1)) { + arg + 1 : arg, 1, ca_only)) { error("%s line %d: Bad key types '%s'.", filename, linenum, arg ? arg : ""); goto out; @@ -1461,6 +1462,7 @@ parse_pubkey_algos: case oCASignatureAlgorithms: charptr = &options->ca_sign_algorithms; + ca_only = 1; goto parse_pubkey_algos; case oLogLevel: @@ -2117,10 +2119,12 @@ parse_pubkey_algos: case oHostbasedAcceptedAlgorithms: charptr = &options->hostbased_accepted_algos; + ca_only = 0; goto parse_pubkey_algos; case oPubkeyAcceptedAlgorithms: charptr = &options->pubkey_accepted_algos; + ca_only = 0; goto parse_pubkey_algos; case oAddKeysToAgent: diff --git a/servconf.c b/servconf.c index 0e6b606bb..603a1ab4e 100644 --- a/servconf.c +++ b/servconf.c @@ -1,5 +1,5 @@ -/* $OpenBSD: servconf.c,v 1.394 2023/06/05 13:24:36 millert Exp $ */ +/* $OpenBSD: servconf.c,v 1.395 2023/06/21 05:10:26 djm Exp $ */ /* * Copyright (c) 1995 Tatu Ylonen , Espoo, Finland * All rights reserved @@ -1333,6 +1333,7 @@ process_server_config_line_depth(ServerOptions *options, char *line, { char *str, ***chararrayptr, **charptr, *arg, *arg2, *p, *keyword; int cmdline = 0, *intptr, value, value2, n, port, oactive, r, found; + int ca_only = 0; SyslogFacility *log_facility_ptr; LogLevel *log_level_ptr; ServerOpCodes opcode; @@ -1574,6 +1575,7 @@ process_server_config_line_depth(ServerOptions *options, char *line, case sHostbasedAcceptedAlgorithms: charptr = &options->hostbased_accepted_algos; + ca_only = 0; parse_pubkey_algos: arg = argv_next(&ac, &av); if (!arg || *arg == '\0') @@ -1581,7 +1583,7 @@ process_server_config_line_depth(ServerOptions *options, char *line, filename, linenum); if (*arg != '-' && !sshkey_names_valid2(*arg == '+' || *arg == '^' ? - arg + 1 : arg, 1)) + arg + 1 : arg, 1, ca_only)) fatal("%s line %d: Bad key types '%s'.", filename, linenum, arg ? arg : ""); if (*activep && *charptr == NULL) @@ -1590,18 +1592,22 @@ process_server_config_line_depth(ServerOptions *options, char *line, case sHostKeyAlgorithms: charptr = &options->hostkeyalgorithms; + ca_only = 0; goto parse_pubkey_algos; case sCASignatureAlgorithms: charptr = &options->ca_sign_algorithms; + ca_only = 1; goto parse_pubkey_algos; case sPubkeyAuthentication: intptr = &options->pubkey_authentication; + ca_only = 0; goto parse_flag; case sPubkeyAcceptedAlgorithms: charptr = &options->pubkey_accepted_algos; + ca_only = 0; goto parse_pubkey_algos; case sPubkeyAuthOptions: diff --git a/sshkey.c b/sshkey.c index 01a1c09a9..498922093 100644 --- a/sshkey.c +++ b/sshkey.c @@ -1,4 +1,4 @@ -/* $OpenBSD: sshkey.c,v 1.135 2023/03/31 03:22:49 djm Exp $ */ +/* $OpenBSD: sshkey.c,v 1.136 2023/06/21 05:10:26 djm Exp $ */ /* * Copyright (c) 2000, 2001 Markus Friedl. All rights reserved. * Copyright (c) 2008 Alexander von Gernler. All rights reserved. @@ -340,7 +340,7 @@ sshkey_alg_list(int certs_only, int plain_only, int include_sigonly, char sep) } int -sshkey_names_valid2(const char *names, int allow_wildcard) +sshkey_names_valid2(const char *names, int allow_wildcard, int plain_only) { char *s, *cp, *p; const struct sshkey_impl *impl; @@ -373,6 +373,9 @@ sshkey_names_valid2(const char *names, int allow_wildcard) } free(s); return 0; + } else if (plain_only && sshkey_type_is_cert(type)) { + free(s); + return 0; } } free(s); diff --git a/sshkey.h b/sshkey.h index 771c4bcee..708f2da86 100644 --- a/sshkey.h +++ b/sshkey.h @@ -1,4 +1,4 @@ -/* $OpenBSD: sshkey.h,v 1.61 2022/10/28 00:44:44 djm Exp $ */ +/* $OpenBSD: sshkey.h,v 1.62 2023/06/21 05:10:26 djm Exp $ */ /* * Copyright (c) 2000, 2001 Markus Friedl. All rights reserved. @@ -264,7 +264,7 @@ int sshkey_ec_validate_public(const EC_GROUP *, const EC_POINT *); int sshkey_ec_validate_private(const EC_KEY *); const char *sshkey_ssh_name(const struct sshkey *); const char *sshkey_ssh_name_plain(const struct sshkey *); -int sshkey_names_valid2(const char *, int); +int sshkey_names_valid2(const char *, int, int); char *sshkey_alg_list(int, int, int, char); int sshkey_from_blob(const u_char *, size_t, struct sshkey **); -- 2.47.3