[Git][debian-proftpd-team/proftpd][bookworm] Add patch for Terrapine attack (CVE-2023-48795).
Hilmar Preuße (@hilmar-guest)
gitlab at salsa.debian.org
Fri Dec 22 22:12:24 GMT 2023
Hilmar Preuße pushed to branch bookworm at Debian ProFTPD Team / proftpd
Commits:
0b76e271 by Hilmar Preusse at 2023-12-22T22:12:00+00:00
Add patch for Terrapine attack (CVE-2023-48795).
- - - - -
3 changed files:
- debian/changelog
- + debian/patches/bcec15efe6c53dac40420731013f1cd2fd54123b.diff
- debian/patches/series
Changes:
=====================================
debian/changelog
=====================================
@@ -1,3 +1,9 @@
+proftpd-dfsg (1.3.8+dfsg-4+deb12u3) UNRELEASED; urgency=medium
+
+ * Add patch for Terrapine attack (CVE-2023-48795).
+
+ -- Hilmar Preusse <hille42 at web.de> Fri, 22 Dec 2023 21:58:38 +0000
+
proftpd-dfsg (1.3.8+dfsg-4+deb12u2) bookworm; urgency=medium
* Add patch from upstream to address issue 1694 (Closes: #1051236).
=====================================
debian/patches/bcec15efe6c53dac40420731013f1cd2fd54123b.diff
=====================================
@@ -0,0 +1,745 @@
+--- proftpd.orig/contrib/mod_sftp/kex.c
++++ proftpd/contrib/mod_sftp/kex.c
+@@ -166,6 +166,13 @@
+ static struct sftp_kex *kex_rekey_kex = NULL;
+ static int kex_sent_kexinit = FALSE;
+
++/* Using strict kex? Note that we maintain this value here, rather than
++ * in the sftp_kex struct, so that any "use strict KEX" flag set via the
++ * first KEXINIT is used through any subsequent KEXINITs.
++ */
++static int use_strict_kex = FALSE;
++static int kex_done_first_kex = FALSE;
++
+ /* Diffie-Hellman group moduli */
+
+ static const char *dh_group1_str =
+@@ -1612,6 +1619,16 @@
+ res = pstrcat(p, res, *res ? "," : "", pstrdup(p, "ext-info-s"), NULL);
+ }
+
++ if (!(sftp_opts & SFTP_OPT_NO_STRICT_KEX)) {
++ /* Indicate support for OpenSSH's custom "strict KEX" mode extension,
++ * but only if we have not done/completed our first KEX.
++ */
++ if (kex_done_first_kex == FALSE) {
++ res = pstrcat(p, res, *res ? "," : "",
++ pstrdup(p, "kex-strict-s-v00 at openssh.com"), NULL);
++ }
++ }
++
+ return res;
+ }
+
+@@ -2323,6 +2340,21 @@
+ pr_trace_msg(trace_channel, 20, "client %s EXT_INFO support",
+ kex->use_ext_info ? "signaled" : "did not signal" );
+
++ if (!(sftp_opts & SFTP_OPT_NO_STRICT_KEX)) {
++ /* Did the client indicate "strict kex" support (Issue 1760)?
++ *
++ * Note that we only check for this if it is our first KEXINIT.
++ * The "strict kex" extension is ignored in any subsequent KEXINITs, as
++ * for rekeys.
++ */
++ if (kex_done_first_kex == FALSE) {
++ use_strict_kex = sftp_misc_namelist_contains(kex->pool,
++ client_list, "kex-strict-c-v00 at openssh.com");
++ pr_trace_msg(trace_channel, 20, "client %s strict KEX support",
++ use_strict_kex ? "signaled" : "did not signal" );
++ }
++ }
++
+ } else {
+ (void) pr_log_writefile(sftp_logfd, MOD_SFTP_VERSION,
+ "no shared key exchange algorithm found (client sent '%s', server sent "
+@@ -5048,7 +5080,6 @@
+ destroy_pool(pkt->pool);
+ return 0;
+ }
+-
+ #endif /* PR_USE_OPENSSL_ECC */
+
+ static struct ssh2_packet *read_kex_packet(pool *p, struct sftp_kex *kex,
+@@ -5099,6 +5130,10 @@
+ /* Per RFC 4253, Section 11, DEBUG, DISCONNECT, IGNORE, and UNIMPLEMENTED
+ * messages can occur at any time, even during KEX. We have to be prepared
+ * for this, and Do The Right Thing(tm).
++ *
++ * However, due to the Terrapin attack, if we are using a "strict KEX"
++ * mode, then only DISCONNECT messages can occur during KEX; DEBUG,
++ * IGNORE, and UNIMPLEMENTED messages will lead to disconnecting.
+ */
+
+ msg_type = sftp_ssh2_packet_get_msg_type(pkt);
+@@ -5127,35 +5162,43 @@
+ }
+
+ switch (msg_type) {
+- case SFTP_SSH2_MSG_DEBUG:
+- sftp_ssh2_packet_handle_debug(pkt);
+- pr_response_set_pool(NULL);
+- pkt = NULL;
+- break;
+-
++ /* DISCONNECT messages are always allowed. */
+ case SFTP_SSH2_MSG_DISCONNECT:
+ sftp_ssh2_packet_handle_disconnect(pkt);
+ pr_response_set_pool(NULL);
+ pkt = NULL;
+ break;
+
++ case SFTP_SSH2_MSG_DEBUG:
++ if (use_strict_kex == FALSE) {
++ sftp_ssh2_packet_handle_debug(pkt);
++ pr_response_set_pool(NULL);
++ pkt = NULL;
++ break;
++ }
++
+ case SFTP_SSH2_MSG_IGNORE:
+- sftp_ssh2_packet_handle_ignore(pkt);
+- pr_response_set_pool(NULL);
+- pkt = NULL;
+- break;
++ if (use_strict_kex == FALSE) {
++ sftp_ssh2_packet_handle_ignore(pkt);
++ pr_response_set_pool(NULL);
++ pkt = NULL;
++ break;
++ }
+
+ case SFTP_SSH2_MSG_UNIMPLEMENTED:
+- sftp_ssh2_packet_handle_unimplemented(pkt);
+- pr_response_set_pool(NULL);
+- pkt = NULL;
+- break;
++ if (use_strict_kex == FALSE) {
++ sftp_ssh2_packet_handle_unimplemented(pkt);
++ pr_response_set_pool(NULL);
++ pkt = NULL;
++ break;
++ }
+
+ default:
+ /* For any other message type, it's considered a protocol error. */
+ (void) pr_log_writefile(sftp_logfd, MOD_SFTP_VERSION,
+- "received %s (%d) unexpectedly, disconnecting",
+- sftp_ssh2_packet_get_msg_type_desc(msg_type), msg_type);
++ "received %s (%d) unexpectedly%s, disconnecting",
++ sftp_ssh2_packet_get_msg_type_desc(msg_type), msg_type,
++ use_strict_kex ? " during strict KEX" : "");
+ pr_response_set_pool(NULL);
+ destroy_kex(kex);
+ destroy_pool(pkt->pool);
+@@ -5177,7 +5220,7 @@
+ * initial connect (kex_first_kex not null), or because we
+ * are in a server-initiated rekeying (kex_rekey_kex not null).
+ */
+- if (kex_first_kex) {
++ if (kex_first_kex != NULL) {
+ kex = kex_first_kex;
+
+ /* We need to assign the client/server versions, which this struct
+@@ -5186,7 +5229,7 @@
+ kex->client_version = kex_client_version;
+ kex->server_version = kex_server_version;
+
+- } else if (kex_rekey_kex) {
++ } else if (kex_rekey_kex != NULL) {
+ kex = kex_rekey_kex;
+
+ } else {
+@@ -5222,6 +5265,24 @@
+ return -1;
+ }
+
++ if (use_strict_kex == TRUE &&
++ kex_done_first_kex == FALSE) {
++ uint32_t client_seqno;
++
++ client_seqno = sftp_ssh2_packet_get_client_seqno();
++ if (client_seqno != 1) {
++ /* Receiving any messages other than a KEXINIT as the first client
++ * message indicates the possibility of the Terrapin attack being
++ * conducted (Issue 1760). Thus we disconnect the client in such
++ * cases.
++ */
++ (void) pr_log_writefile(sftp_logfd, MOD_SFTP_VERSION,
++ "'strict KEX' violation, as KEXINIT was not the first message; disconnecting");
++ destroy_kex(kex);
++ SFTP_DISCONNECT_CONN(SFTP_SSH2_DISCONNECT_BY_APPLICATION, NULL);
++ }
++ }
++
+ /* Once we have received the client KEXINIT message, we can compare what we
+ * want to send against what we already received from the client.
+ *
+@@ -5280,7 +5341,7 @@
+
+ destroy_pool(pkt->pool);
+
+- if (!kex_sent_kexinit) {
++ if (kex_sent_kexinit == FALSE) {
+ pkt = sftp_ssh2_packet_create(kex_pool);
+ res = write_kexinit(pkt, kex);
+ if (res < 0) {
+@@ -5303,7 +5364,7 @@
+ }
+ }
+
+- if (!kex_sent_kexinit) {
++ if (kex_sent_kexinit == FALSE) {
+ pkt = sftp_ssh2_packet_create(kex_pool);
+ res = write_kexinit(pkt, kex);
+ if (res < 0) {
+@@ -5434,7 +5495,7 @@
+ NULL, 1, SFTP_SSH2_MSG_NEWKEYS);
+
+ /* If we didn't send our NEWKEYS message earlier, do it now. */
+- if (!sent_newkeys) {
++ if (sent_newkeys == FALSE) {
+ struct ssh2_packet *pkt2;
+
+ pr_trace_msg(trace_channel, 9, "sending NEWKEYS message to client");
+@@ -5458,6 +5519,11 @@
+ destroy_pool(pkt2->pool);
+ }
+
++ if (use_strict_kex == TRUE) {
++ sftp_ssh2_packet_reset_client_seqno();
++ sftp_ssh2_packet_reset_server_seqno();
++ }
++
+ /* Last but certainly not least, set up the keys for encryption and
+ * authentication, based on H and K.
+ */
+@@ -5477,6 +5543,9 @@
+ destroy_pool(pkt->pool);
+ cmd = NULL;
+
++ /* We've now completed our KEX, possibly our first. */
++ kex_done_first_kex = TRUE;
++
+ /* If extension negotiation has not been disabled, AND if we have not
+ * received a service request, AND if the client sent "ext-info-c", THEN
+ * send our EXT_INFO. We do not want send this during rekeys.
+@@ -5529,6 +5598,12 @@
+ }
+ }
+
++ /* Only start the TAP timer after we have completed our first KEX.
++ * Otherwise, we risk sending "illegal" packets prior to, or during,
++ * a "strict KEX" session (Issue 1760).
++ */
++ sftp_tap_start_policy();
++
+ /* Reset this flag for the next time through. */
+ kex_sent_kexinit = FALSE;
+
+@@ -5558,7 +5633,7 @@
+ destroy_kex(rekey_kex);
+ }
+
+- if (kex_pool) {
++ if (kex_pool != NULL) {
+ destroy_pool(kex_pool);
+ kex_pool = NULL;
+ }
+@@ -5734,7 +5809,7 @@
+ struct ssh2_packet *pkt;
+ int res;
+
+- if (!kex_pool) {
++ if (kex_pool == NULL) {
+ kex_pool = make_sub_pool(sftp_pool);
+ pr_pool_tag(kex_pool, "Kex Pool");
+ }
+@@ -5769,4 +5844,3 @@
+ destroy_pool(pkt->pool);
+ return 0;
+ }
+-
+--- proftpd.orig/contrib/mod_sftp/mod_sftp.c
++++ proftpd/contrib/mod_sftp/mod_sftp.c
+@@ -1,6 +1,6 @@
+ /*
+ * ProFTPD - mod_sftp
+- * Copyright (c) 2008-2022 TJ Saunders
++ * Copyright (c) 2008-2023 TJ Saunders
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+@@ -1730,8 +1730,9 @@
+ config_rec *c;
+ unsigned long opts = 0UL;
+
+- if (cmd->argc-1 == 0)
++ if (cmd->argc-1 == 0) {
+ CONF_ERROR(cmd, "wrong number of parameters");
++ }
+
+ CHECK_CONF(cmd, CONF_ROOT|CONF_VIRTUAL|CONF_GLOBAL);
+
+@@ -1798,6 +1799,9 @@
+ } else if (strcmp(cmd->argv[i], "NoHostkeyRotation") == 0) {
+ opts |= SFTP_OPT_NO_HOSTKEY_ROTATION;
+
++ } else if (strcmp(cmd->argv[i], "NoStrictKex") == 0) {
++ opts |= SFTP_OPT_NO_STRICT_KEX;
++
+ } else {
+ CONF_ERROR(cmd, pstrcat(cmd->tmp_pool, ": unknown SFTPOption '",
+ cmd->argv[i], "'", NULL));
+--- proftpd.orig/contrib/mod_sftp/mod_sftp.h.in
++++ proftpd/contrib/mod_sftp/mod_sftp.h.in
+@@ -132,24 +132,25 @@
+ #define SFTP_SESS_STATE_HAVE_EXT_INFO 0x00010
+
+ /* mod_sftp option flags */
+-#define SFTP_OPT_IGNORE_SFTP_UPLOAD_PERMS 0x00001
+-#define SFTP_OPT_IGNORE_SCP_UPLOAD_PERMS 0x00002
+-#define SFTP_OPT_PESSIMISTIC_KEXINIT 0x00004
+-#define SFTP_OPT_OLD_PROTO_COMPAT 0x00008
+-#define SFTP_OPT_MATCH_KEY_SUBJECT 0x00010
+-#define SFTP_OPT_IGNORE_SFTP_SET_PERMS 0x00020
+-#define SFTP_OPT_IGNORE_SFTP_SET_TIMES 0x00040
+-#define SFTP_OPT_IGNORE_SFTP_SET_OWNERS 0x00080
+-#define SFTP_OPT_IGNORE_SCP_UPLOAD_TIMES 0x00100
+-#define SFTP_OPT_ALLOW_INSECURE_LOGIN 0x00200
+-#define SFTP_OPT_INSECURE_HOSTKEY_PERMS 0x00400
+-#define SFTP_OPT_ALLOW_WEAK_DH 0x00800
+-#define SFTP_OPT_IGNORE_FIFOS 0x01000
+-#define SFTP_OPT_IGNORE_SFTP_UPLOAD_XATTRS 0x02000
+-#define SFTP_OPT_IGNORE_SFTP_SET_XATTRS 0x04000
+-#define SFTP_OPT_INCLUDE_SFTP_TIMES 0x08000
+-#define SFTP_OPT_NO_EXT_INFO 0x10000
+-#define SFTP_OPT_NO_HOSTKEY_ROTATION 0x20000
++#define SFTP_OPT_IGNORE_SFTP_UPLOAD_PERMS 0x000001
++#define SFTP_OPT_IGNORE_SCP_UPLOAD_PERMS 0x000002
++#define SFTP_OPT_PESSIMISTIC_KEXINIT 0x000004
++#define SFTP_OPT_OLD_PROTO_COMPAT 0x000008
++#define SFTP_OPT_MATCH_KEY_SUBJECT 0x000010
++#define SFTP_OPT_IGNORE_SFTP_SET_PERMS 0x000020
++#define SFTP_OPT_IGNORE_SFTP_SET_TIMES 0x000040
++#define SFTP_OPT_IGNORE_SFTP_SET_OWNERS 0x000080
++#define SFTP_OPT_IGNORE_SCP_UPLOAD_TIMES 0x000100
++#define SFTP_OPT_ALLOW_INSECURE_LOGIN 0x000200
++#define SFTP_OPT_INSECURE_HOSTKEY_PERMS 0x000400
++#define SFTP_OPT_ALLOW_WEAK_DH 0x000800
++#define SFTP_OPT_IGNORE_FIFOS 0x001000
++#define SFTP_OPT_IGNORE_SFTP_UPLOAD_XATTRS 0x002000
++#define SFTP_OPT_IGNORE_SFTP_SET_XATTRS 0x004000
++#define SFTP_OPT_INCLUDE_SFTP_TIMES 0x008000
++#define SFTP_OPT_NO_EXT_INFO 0x010000
++#define SFTP_OPT_NO_HOSTKEY_ROTATION 0x020000
++#define SFTP_OPT_NO_STRICT_KEX 0x040000
+
+ /* mod_sftp service flags */
+ #define SFTP_SERVICE_FL_SFTP 0x0001
+--- proftpd.orig/contrib/mod_sftp/packet.c
++++ proftpd/contrib/mod_sftp/packet.c
+@@ -2063,6 +2063,18 @@
+ return 0;
+ }
+
++uint32_t sftp_ssh2_packet_get_client_seqno(void) {
++ return packet_client_seqno;
++}
++
++void sftp_ssh2_packet_reset_client_seqno(void) {
++ packet_client_seqno = 0;
++}
++
++void sftp_ssh2_packet_reset_server_seqno(void) {
++ packet_server_seqno = 0;
++}
++
+ int sftp_ssh2_packet_send_version(void) {
+ if (!sent_version_id) {
+ int res;
+--- proftpd.orig/contrib/mod_sftp/packet.h
++++ proftpd/contrib/mod_sftp/packet.h
+@@ -1,6 +1,6 @@
+ /*
+ * ProFTPD - mod_sftp packet IO
+- * Copyright (c) 2008-2021 TJ Saunders
++ * Copyright (c) 2008-2023 TJ Saunders
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+@@ -117,6 +117,13 @@
+ int sftp_ssh2_packet_rekey_set_seqno(uint32_t);
+ int sftp_ssh2_packet_rekey_set_size(off_t);
+
++/* These are used for implementing the "strict KEX" mitigations of the Terrapin
++ * attack (Issue 1760).
++ */
++uint32_t sftp_ssh2_packet_get_client_seqno(void);
++void sftp_ssh2_packet_reset_client_seqno(void);
++void sftp_ssh2_packet_reset_server_seqno(void);
++
+ int sftp_ssh2_packet_send_version(void);
+ int sftp_ssh2_packet_set_poll_timeout(int);
+ int sftp_ssh2_packet_set_version(const char *);
+--- proftpd.orig/contrib/mod_sftp/tap.c
++++ proftpd/contrib/mod_sftp/tap.c
+@@ -1,6 +1,6 @@
+ /*
+ * ProFTPD - mod_sftp traffic analysis protection
+- * Copyright (c) 2008-2016 TJ Saunders
++ * Copyright (c) 2008-2023 TJ Saunders
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+@@ -149,7 +149,6 @@
+ }
+
+ static void set_policy_timer(struct sftp_tap_policy *policy) {
+-
+ /* Start a timer which checks the last times we received and sent packets.
+ * From there, we may want to inject a TAP message, depending on the
+ * policy.
+@@ -177,6 +176,16 @@
+ int rnd;
+ unsigned int chance;
+
++ /* Due to chances of violating client-side "strict KEX" Terrapin
++ * mitigations, we will not send packets if we are in the middle of a KEX.
++ */
++ if (!(sftp_sess_state & SFTP_SESS_STATE_HAVE_KEX) ||
++ (sftp_sess_state & SFTP_SESS_STATE_REKEYING)) {
++ pr_trace_msg(trace_channel, 11,
++ "unwilling to send TAP packet during KEX");
++ return 0;
++ }
++
+ if (!sftp_interop_supports_feature(SFTP_SSH2_FEAT_IGNORE_MSG)) {
+ pr_trace_msg(trace_channel, 3,
+ "unable to send TAP packet: IGNORE not supported by client");
+@@ -205,7 +214,7 @@
+ struct ssh2_packet *pkt;
+ unsigned int max_datalen = 8192;
+
+- if (curr_policy.max_datalen) {
++ if (curr_policy.max_datalen > 0) {
+ max_datalen = curr_policy.max_datalen;
+ }
+
+@@ -246,15 +255,15 @@
+ int sftp_tap_set_policy(const char *policy) {
+ register unsigned int i;
+
+- if (tap_pool) {
++ if (tap_pool != NULL) {
+
+ /* Special case: IFF the existing policy is 'none' AND the given
+ * policy is 'rogaway', just return. The 'none' policy must have been
+ * explicitly configured, and it should override the automatic use of
+ * the 'rogaway' policy.
+ */
+- if (strncmp(curr_policy.policy, "none", 5) == 0 &&
+- strncasecmp(policy, "rogaway", 8) == 0) {
++ if (strcasecmp(curr_policy.policy, "none") == 0 &&
++ strcasecmp(policy, "rogaway") == 0) {
+ (void) pr_log_writefile(sftp_logfd, MOD_SFTP_VERSION,
+ "'none' traffic policy explicitly configured, ignoring '%s' policy",
+ policy);
+@@ -278,7 +287,6 @@
+ if (strcasecmp(tap_policies[i].policy, policy) == 0) {
+ copy_policy(&curr_policy, &(tap_policies[i]));
+ set_policy_chance(&curr_policy);
+- set_policy_timer(&curr_policy);
+ return 0;
+ }
+ }
+@@ -286,3 +294,7 @@
+ errno = ENOENT;
+ return -1;
+ }
++
++void sftp_tap_start_policy(void) {
++ set_policy_timer(&curr_policy);
++}
+--- proftpd.orig/contrib/mod_sftp/tap.h
++++ proftpd/contrib/mod_sftp/tap.h
+@@ -1,6 +1,6 @@
+ /*
+ * ProFTPD - mod_sftp traffic analysis protection
+- * Copyright (c) 2008-2016 TJ Saunders
++ * Copyright (c) 2008-2013 TJ Saunders
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+@@ -63,4 +63,7 @@
+ */
+ int sftp_tap_set_policy(const char *);
+
++/* Sets the configured TAP policy in motion. */
++void sftp_tap_start_policy(void);
++
+ #endif /* MOD_SFTP_TAP_H */
+--- proftpd.orig/doc/contrib/mod_sftp.html
++++ proftpd/doc/contrib/mod_sftp.html
+@@ -1312,6 +1312,19 @@
+ </li>
+
+ <p>
++ <li><code>NoStrictKex</code><br>
++ <p>
++ By default, <code>mod_sftp</code> will honor/support the OpenSSH
++ "strict KEX" mode extension, "kex-strict-c-v00 at openssh.com" and
++ "kex-strict-s-v00 at openssh.com". Use this option to disable support for
++ these custom OpenSSH extensions.
++
++ <p>
++ <b>Note</b> that this option first appeared in
++ <code>proftpd-1.3.9rc1</code>.
++ </li>
++
++ <p>
+ <li><code>OldProtocolCompat</code><br>
+ <p>
+ Older clients identity their protocol versions as "1.99", rather than as
+@@ -2843,7 +2856,7 @@
+ <p>
+ <hr>
+ <font size=2><b><i>
+-© Copyright 2008-2022 TJ Saunders<br>
++© Copyright 2008-2023 TJ Saunders<br>
+ All Rights Reserved<br>
+ </i></b></font>
+ <hr>
+--- proftpd.orig/tests/t/lib/ProFTPD/Tests/Modules/mod_sftp.pm
++++ proftpd/tests/t/lib/ProFTPD/Tests/Modules/mod_sftp.pm
+@@ -87,6 +87,11 @@
+ test_class => [qw(forking ssh2)],
+ },
+
++ ssh2_ext_kex_strict_terrapin_issue1760 => {
++ order => ++$order,
++ test_class => [qw(bug forking ssh2)],
++ },
++
+ ssh2_hostkey_rsa => {
+ order => ++$order,
+ test_class => [qw(forking ssh2)],
+@@ -4012,6 +4017,218 @@
+ unlink($log_file);
+ }
+
++sub ssh2_ext_kex_strict_terrapin_issue1760 {
++ my $self = shift;
++ my $tmpdir = $self->{tmpdir};
++ my $setup = test_setup($tmpdir, 'sftp');
++
++ my $rsa_host_key = File::Spec->rel2abs('t/etc/modules/mod_sftp/ssh_host_rsa_key');
++ my $dsa_host_key = File::Spec->rel2abs('t/etc/modules/mod_sftp/ssh_host_dsa_key');
++
++ my $rsa_priv_key = File::Spec->rel2abs('t/etc/modules/mod_sftp/test_rsa_key');
++ my $rsa_pub_key = File::Spec->rel2abs('t/etc/modules/mod_sftp/test_rsa_key.pub');
++ my $rsa_rfc4716_key = File::Spec->rel2abs('t/etc/modules/mod_sftp/authorized_rsa_keys');
++
++ my $authorized_keys = File::Spec->rel2abs("$tmpdir/.authorized_keys");
++ unless (copy($rsa_rfc4716_key, $authorized_keys)) {
++ die("Can't copy $rsa_rfc4716_key to $authorized_keys: $!");
++ }
++
++ my $ssh_config = File::Spec->rel2abs("$tmpdir/ssh.conf");
++ if (open(my $fh, "> $ssh_config")) {
++ print $fh <<EOC;
++HostKeyAlgorithms rsa-sha2-256
++IdentityAgent none
++PubkeyAcceptedKeyTypes rsa-sha2-256
++EOC
++ unless (close($fh)) {
++ die("Can't write $ssh_config: $!");
++ }
++
++ } else {
++ die("Can't open $ssh_config: $!");
++ }
++
++ my $batch_file = File::Spec->rel2abs("$tmpdir/sftp-batch.conf");
++ if (open(my $fh, "> $batch_file")) {
++ print $fh "ls -l\n";
++
++ unless (close($fh)) {
++ die("Can't write $batch_file: $!");
++ }
++
++ } else {
++ die("Can't open $batch_file: $!");
++ }
++
++ my $config = {
++ PidFile => $setup->{pid_file},
++ ScoreboardFile => $setup->{scoreboard_file},
++ SystemLog => $setup->{log_file},
++ TraceLog => $setup->{log_file},
++ Trace => 'ssh2:30 sftp:20 scp:20',
++
++ AuthUserFile => $setup->{auth_user_file},
++ AuthGroupFile => $setup->{auth_group_file},
++ AuthOrder => 'mod_auth_file.c',
++
++ IfModules => {
++ 'mod_delay.c' => {
++ DelayEngine => 'off',
++ },
++
++ 'mod_sftp.c' => [
++ "SFTPEngine on",
++ "SFTPLog $setup->{log_file}",
++
++ "SFTPHostKey $rsa_host_key",
++ "SFTPHostKey $dsa_host_key",
++
++ "SFTPAuthorizedUserKeys file:~/.authorized_keys",
++ ],
++ },
++ };
++
++ my ($port, $config_user, $config_group) = config_write($setup->{config_file},
++ $config);
++
++ # Open pipes, for use between the parent and child processes. Specifically,
++ # the child will indicate when it's done with its test by writing a message
++ # to the parent.
++ my ($rfh, $wfh);
++ unless (pipe($rfh, $wfh)) {
++ die("Can't open pipe: $!");
++ }
++
++ require Net::SSH2;
++
++ my $ex;
++
++ # Fork child
++ $self->handle_sigchld();
++ defined(my $pid = fork()) or die("Can't fork: $!");
++ if ($pid) {
++ eval {
++ # We use OpenSSH-9.6p1 to test our "strict KEX" Terrapin mitigations.
++ my $sftp = '/Users/tj/local/openssh-9.6p1/bin/sftp';
++
++ my @cmd = (
++ $sftp,
++ '-F',
++ $ssh_config,
++ '-oBatchMode=yes',
++ '-oCheckHostIP=no',
++ '-oCompression=yes',
++ "-oPort=$port",
++ "-oIdentityFile=$rsa_priv_key",
++ '-oPubkeyAuthentication=yes',
++ '-oStrictHostKeyChecking=no',
++ '-oUserKnownHostsFile=/dev/null',
++ '-vvv',
++ '-b',
++ $batch_file,
++ "$setup->{user}\@127.0.0.1",
++ );
++
++ my $sftp_rh = IO::Handle->new();
++ my $sftp_wh = IO::Handle->new();
++ my $sftp_eh = IO::Handle->new();
++
++ $sftp_wh->autoflush(1);
++
++ sleep(1);
++
++ local $SIG{CHLD} = 'DEFAULT';
++
++ # Make sure that the perms on the priv key are what OpenSSH wants
++ unless (chmod(0400, $rsa_priv_key)) {
++ die("Can't set perms on $rsa_priv_key to 0400: $!");
++ }
++
++ if ($ENV{TEST_VERBOSE}) {
++ print STDERR "Executing: ", join(' ', @cmd), "\n";
++ }
++
++ my $sftp_pid = open3($sftp_wh, $sftp_rh, $sftp_eh, @cmd);
++ waitpid($sftp_pid, 0);
++ my $exit_status = $?;
++
++ # Restore the perms on the priv key
++ unless (chmod(0644, $rsa_priv_key)) {
++ die("Can't set perms on $rsa_priv_key to 0644: $!");
++ }
++
++ my ($res, $errstr);
++ if ($exit_status >> 8 == 0) {
++ $errstr = join('', <$sftp_eh>);
++ $res = 0;
++
++ } else {
++ $errstr = join('', <$sftp_eh>);
++ if ($ENV{TEST_VERBOSE}) {
++ print STDERR "Stderr: $errstr\n";
++ }
++
++ $res = 1;
++ }
++
++ unless ($res == 0) {
++ die("Can't list files on server: $errstr");
++ }
++ };
++ if ($@) {
++ $ex = $@;
++ }
++
++ $wfh->print("done\n");
++ $wfh->flush();
++
++ } else {
++ eval { server_wait($setup->{config_file}, $rfh) };
++ if ($@) {
++ warn($@);
++ exit 1;
++ }
++
++ exit 0;
++ }
++
++ # Stop server
++ server_stop($setup->{pid_file});
++ $self->assert_child_ok($pid);
++
++ eval {
++ if (open(my $fh, "< $setup->{log_file}")) {
++ my $ok = 0;
++
++ while (my $line = <$fh>) {
++ chomp($line);
++
++ if ($ENV{TEST_VERBOSE}) {
++ print STDERR "# $line\n";
++ }
++
++ if ($line =~ /client signaled strict KEX support/) {
++ $ok = 1;
++ last;
++ }
++ }
++
++ close($fh);
++
++ $self->assert($ok, test_msg("Did not see expected 'strict KEX' TraceLog message"));
++
++ } else {
++ die("Can't read $setup->{log_file}: $!");
++ }
++ };
++ if ($@) {
++ $ex = $@;
++ }
++
++ test_cleanup($setup->{log_file}, $ex);
++}
++
+ sub ssh2_hostkey_rsa {
+ my $self = shift;
+ my $tmpdir = $self->{tmpdir};
=====================================
debian/patches/series
=====================================
@@ -18,3 +18,4 @@ upstream_bug_1597.diff
02_disable_redis_sentinel_conn_new_test.diff
03_disable_all_non_api_tests.diff
upstream_1707.diff
+bcec15efe6c53dac40420731013f1cd2fd54123b.diff
View it on GitLab: https://salsa.debian.org/debian-proftpd-team/proftpd/-/commit/0b76e271ca9ecf13e20016a4add36730d57ef1cb
--
View it on GitLab: https://salsa.debian.org/debian-proftpd-team/proftpd/-/commit/0b76e271ca9ecf13e20016a4add36730d57ef1cb
You're receiving this email because of your account on salsa.debian.org.
More information about the Pkg-proftpd-maintainers
mailing list