Compare commits

...

No commits in common. "c8" and "c9s" have entirely different histories.
c8 ... c9s

29 changed files with 7298 additions and 3448 deletions

1
.fmf/version Normal file
View File

@ -0,0 +1 @@
1

62
.gitignore vendored
View File

@ -1,2 +1,60 @@
SOURCES/libssh-0.9.6.tar.xz
SOURCES/libssh.keyring
libssh-0.4.4.tar.gz
libssh-0.4.4.tar.gz.asc
/libssh-0.4.6.tar.gz
/libssh-0.4.6.tar.gz.asc
/libssh-0.4.8.tar.gz
/libssh-0.4.8.tar.gz.asc
/libssh-0.5.0.tar.gz
/libssh-0.5.0.tar.gz.asc
/libssh-0.5.2.tar.gz
/libssh-0.5.2.tar.gz.asc
/libssh-0.5.3.tar.gz
/libssh-0.5.3.tar.asc
/libssh-0.5.4.tar.gz
/libssh-0.5.4.tar.asc
/libssh-0.5.5.tar.gz
/libssh-0.5.5.tar.asc
/libssh-0.6.0.tar.xz
/libssh-0.6.1.tar.xz
/libssh-0.6.3.tar.xz
/libssh-0.6.4.tar.gz
/libssh-0.6.5.tar.xz
/libssh-0.7.0.tar.xz
/libssh-0.7.1.tar.xz
/libssh-0.7.2.tar.xz
/libssh-0.7.3.tar.xz
/libssh-0.7.4.tar.xz
/libssh-0.7.5.tar.xz
/libssh-0.8.0.tar.xz
/libssh-0.8.0.tar.xz.asc
/libssh-0.8.1.tar.xz
/libssh-0.8.1.tar.xz.asc
/libssh-0.8.2.tar.xz
/libssh-0.8.2.tar.xz.asc
/libssh-0.8.3.tar.xz
/libssh-0.8.3.tar.xz.asc
/libssh-0.8.4.tar.xz
/libssh-0.8.4.tar.xz.asc
/libssh-0.8.5.tar.xz
/libssh-0.8.5.tar.xz.asc
/libssh-0.8.6.tar.xz
/libssh-0.8.6.tar.xz.asc
/libssh-0.8.7.tar.xz
/libssh-0.8.7.tar.xz.asc
/libssh-0.8.91.tar.xz
/libssh_client.config
/libssh_server.config
/libssh-0.9.0.tar.xz
/libssh-0.9.0.tar.xz.asc
/libssh-0.9.2.tar.xz
/libssh-0.9.2.tar.xz.asc
/libssh-0.9.3.tar.xz
/libssh-0.9.3.tar.xz.asc
/libssh-0.9.4.tar.xz
/libssh-0.9.4.tar.xz.asc
/libssh-0.9.5.tar.xz
/libssh-0.9.5.tar.xz.asc
/libssh-0.9.6.tar.xz
/libssh-0.9.6.tar.xz.asc
/libssh-0.10.4.tar.xz
/libssh-0.10.4.tar.xz.asc

View File

@ -1,2 +1,2 @@
1b2dd673b58e1eaf20fde45cd8de2197cfab2f78 SOURCES/libssh-0.9.6.tar.xz
3f2ab0bca02893402ba0ad172a6bd44456a65f86 SOURCES/libssh.keyring
4c48350a0a688ad82080175ed26a2019928a99c4 libssh-0.10.4.tar.xz
26dc75d73479b063f0c8cedb8736763e98b6e02d libssh-0.10.4.tar.xz.asc

View File

@ -1,4 +1,4 @@
From 87b93be5a2071be782aa84aa5a91544b18959d5e Mon Sep 17 00:00:00 2001
From 4cef5e965a46e9271aed62631b152e4bd23c1e3c Mon Sep 17 00:00:00 2001
From: Aris Adamantiadis <aris@0xbadc0de.be>
Date: Tue, 12 Dec 2023 23:09:57 +0100
Subject: [PATCH 1/4] CVE-2023-48795: client side mitigation
@ -22,10 +22,10 @@ Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
12 files changed, 126 insertions(+), 69 deletions(-)
diff --git a/include/libssh/packet.h b/include/libssh/packet.h
index 561bba8e..c6fbc3fc 100644
index 7f10a709..f0c8cb20 100644
--- a/include/libssh/packet.h
+++ b/include/libssh/packet.h
@@ -63,6 +63,7 @@ SSH_PACKET_CALLBACK(ssh_packet_ext_info);
@@ -67,6 +67,7 @@ SSH_PACKET_CALLBACK(ssh_packet_ext_info);
SSH_PACKET_CALLBACK(ssh_packet_kexdh_init);
#endif
@ -34,10 +34,10 @@ index 561bba8e..c6fbc3fc 100644
int ssh_packet_parse_type(ssh_session session);
//int packet_flush(ssh_session session, int enforce_blocking);
diff --git a/include/libssh/session.h b/include/libssh/session.h
index 64e118ef..3cde0dd4 100644
index eb14e97a..97936195 100644
--- a/include/libssh/session.h
+++ b/include/libssh/session.h
@@ -80,6 +80,12 @@ enum ssh_pending_call_e {
@@ -81,6 +81,12 @@ enum ssh_pending_call_e {
* sending it twice during key exchange to simplify the state machine. */
#define SSH_SESSION_FLAG_KEXINIT_SENT 4
@ -51,7 +51,7 @@ index 64e118ef..3cde0dd4 100644
/* Infinite timeout */
#define SSH_TIMEOUT_INFINITE -1
diff --git a/src/curve25519.c b/src/curve25519.c
index 37654438..6b7b4238 100644
index 66291b5f..4aeb4756 100644
--- a/src/curve25519.c
+++ b/src/curve25519.c
@@ -335,16 +335,10 @@ static SSH_PACKET_CALLBACK(ssh_packet_client_curve25519_reply){
@ -95,10 +95,10 @@ index 37654438..6b7b4238 100644
return SSH_PACKET_USED;
error:
diff --git a/src/dh-gex.c b/src/dh-gex.c
index 4a298542..f1880270 100644
index 91617081..642a88ae 100644
--- a/src/dh-gex.c
+++ b/src/dh-gex.c
@@ -287,15 +287,10 @@ static SSH_PACKET_CALLBACK(ssh_packet_client_dhgex_reply)
@@ -297,15 +297,10 @@ static SSH_PACKET_CALLBACK(ssh_packet_client_dhgex_reply)
}
/* Send the MSG_NEWKEYS */
@ -116,10 +116,10 @@ index 4a298542..f1880270 100644
return SSH_PACKET_USED;
diff --git a/src/dh.c b/src/dh.c
index c265efcb..1d519c63 100644
index 011d97b3..e19e43d1 100644
--- a/src/dh.c
+++ b/src/dh.c
@@ -386,16 +386,10 @@ SSH_PACKET_CALLBACK(ssh_packet_client_dh_reply){
@@ -398,16 +398,10 @@ SSH_PACKET_CALLBACK(ssh_packet_client_dh_reply){
}
/* Send the MSG_NEWKEYS */
@ -137,7 +137,7 @@ index c265efcb..1d519c63 100644
session->dh_handshake_state = DH_STATE_NEWKEYS_SENT;
return SSH_PACKET_USED;
error:
@@ -532,15 +526,12 @@ int ssh_server_dh_process_init(ssh_session session, ssh_buffer packet)
@@ -551,15 +545,12 @@ int ssh_server_dh_process_init(ssh_session session, ssh_buffer packet)
}
SSH_LOG(SSH_LOG_DEBUG, "Sent KEX_DH_[GEX]_REPLY");
@ -179,10 +179,10 @@ index e5b11ba9..af80beec 100644
return SSH_PACKET_USED;
diff --git a/src/ecdh_crypto.c b/src/ecdh_crypto.c
index a1de27fd..62578c1b 100644
index 51084b7a..069b1372 100644
--- a/src/ecdh_crypto.c
+++ b/src/ecdh_crypto.c
@@ -323,18 +323,12 @@ SSH_PACKET_CALLBACK(ssh_packet_server_ecdh_init){
@@ -619,18 +619,12 @@ SSH_PACKET_CALLBACK(ssh_packet_server_ecdh_init){
goto error;
}
@ -205,7 +205,7 @@ index a1de27fd..62578c1b 100644
return SSH_PACKET_USED;
error:
diff --git a/src/ecdh_gcrypt.c b/src/ecdh_gcrypt.c
index d9c41bf9..dd4332d7 100644
index 235f2904..3d9d426f 100644
--- a/src/ecdh_gcrypt.c
+++ b/src/ecdh_gcrypt.c
@@ -372,17 +372,13 @@ SSH_PACKET_CALLBACK(ssh_packet_server_ecdh_init){
@ -230,10 +230,10 @@ index d9c41bf9..dd4332d7 100644
gcry_sexp_release(param);
gcry_sexp_release(key);
diff --git a/src/ecdh_mbedcrypto.c b/src/ecdh_mbedcrypto.c
index 718f1522..45251a42 100644
index cfe017a0..dda73922 100644
--- a/src/ecdh_mbedcrypto.c
+++ b/src/ecdh_mbedcrypto.c
@@ -300,16 +300,13 @@ SSH_PACKET_CALLBACK(ssh_packet_server_ecdh_init){
@@ -318,16 +318,13 @@ SSH_PACKET_CALLBACK(ssh_packet_server_ecdh_init){
goto out;
}
@ -255,10 +255,10 @@ index 718f1522..45251a42 100644
mbedtls_ecp_group_free(&grp);
if (rc == SSH_ERROR) {
diff --git a/src/kex.c b/src/kex.c
index 3e5ca6ad..0772cae8 100644
index b9455d2d..3818297b 100644
--- a/src/kex.c
+++ b/src/kex.c
@@ -163,6 +163,9 @@
@@ -188,6 +188,9 @@
/* RFC 8308 */
#define KEX_EXTENSION_CLIENT "ext-info-c"
@ -268,7 +268,7 @@ index 3e5ca6ad..0772cae8 100644
/* Allowed algorithms in FIPS mode */
#define FIPS_ALLOWED_CIPHERS "aes256-gcm@openssh.com,"\
@@ -491,6 +494,27 @@ SSH_PACKET_CALLBACK(ssh_packet_kexinit)
@@ -516,6 +519,27 @@ SSH_PACKET_CALLBACK(ssh_packet_kexinit)
session->first_kex_follows_guess_wrong ? "wrong" : "right");
}
@ -296,7 +296,7 @@ index 3e5ca6ad..0772cae8 100644
if (server_kex) {
/*
* If client sent a ext-info-c message in the kex list, it supports
@@ -767,21 +791,21 @@ int ssh_set_client_kex(ssh_session session)
@@ -792,21 +816,21 @@ int ssh_set_client_kex(ssh_session session)
return SSH_OK;
}
@ -324,10 +324,10 @@ index 3e5ca6ad..0772cae8 100644
return SSH_OK;
diff --git a/src/packet.c b/src/packet.c
index ca7a03b7..82965fb3 100644
index eb7eb42a..ea73f9ad 100644
--- a/src/packet.c
+++ b/src/packet.c
@@ -1309,6 +1309,19 @@ int ssh_packet_socket_callback(const void *data, size_t receivedlen, void *user)
@@ -1314,6 +1314,19 @@ ssh_packet_socket_callback(const void *data, size_t receivedlen, void *user)
}
#endif /* WITH_ZLIB */
payloadsize = ssh_buffer_get_len(session->in_buffer);
@ -347,27 +347,7 @@ index ca7a03b7..82965fb3 100644
session->recv_seq++;
if (crypto != NULL) {
struct ssh_cipher_struct *cipher = NULL;
@@ -1331,7 +1344,19 @@ int ssh_packet_socket_callback(const void *data, size_t receivedlen, void *user)
SSH_LOG(SSH_LOG_PACKET,
"packet: read type %hhd [len=%d,padding=%hhd,comp=%d,payload=%d]",
session->in_packet.type, packet_len, padding, compsize, payloadsize);
+ if (crypto == NULL) {
+ /* In strict kex, only a few packets are allowed. Taint the session
+ * if we received packets that are normally allowed but to be
+ * refused if we are in strict kex when KEX is over.
+ */
+ uint8_t type = session->in_packet.type;
+ if (type != SSH2_MSG_KEXINIT && type != SSH2_MSG_NEWKEYS &&
+ (type < SSH2_MSG_KEXDH_INIT ||
+ type > SSH2_MSG_KEX_DH_GEX_REQUEST)) {
+ session->flags |= SSH_SESSION_FLAG_KEX_TAINTED;
+ }
+ }
/* Check if the packet is expected */
filter_result = ssh_packet_incoming_filter(session);
@@ -1347,6 +1372,9 @@ int ssh_packet_socket_callback(const void *data, size_t receivedlen, void *user)
@@ -1354,6 +1379,9 @@ ssh_packet_socket_callback(const void *data, size_t receivedlen, void *user)
session->in_packet.type);
goto error;
case SSH_PACKET_UNKNOWN:
@ -377,7 +357,7 @@ index ca7a03b7..82965fb3 100644
ssh_packet_send_unimplemented(session, session->recv_seq - 1);
break;
}
@@ -1521,7 +1549,33 @@ void ssh_packet_process(ssh_session session, uint8_t type)
@@ -1529,7 +1557,33 @@ void ssh_packet_process(ssh_session session, uint8_t type)
SSH_LOG(SSH_LOG_RARE, "Failed to send unimplemented: %s",
ssh_get_error(session));
}
@ -411,7 +391,7 @@ index ca7a03b7..82965fb3 100644
}
/** @internal
@@ -1829,6 +1883,10 @@ int ssh_packet_send(ssh_session session)
@@ -1842,6 +1896,10 @@ int ssh_packet_send(ssh_session session)
if (rc == SSH_OK && type == SSH2_MSG_NEWKEYS) {
struct ssh_iterator *it;
@ -423,10 +403,10 @@ index ca7a03b7..82965fb3 100644
it != NULL;
it = ssh_list_get_iterator(session->out_queue)) {
diff --git a/src/packet_cb.c b/src/packet_cb.c
index 3e4d5f6d..a08f1d8a 100644
index 0ecf8771..2f364c26 100644
--- a/src/packet_cb.c
+++ b/src/packet_cb.c
@@ -110,6 +110,18 @@ SSH_PACKET_CALLBACK(ssh_packet_newkeys){
@@ -115,6 +115,18 @@ SSH_PACKET_CALLBACK(ssh_packet_newkeys){
goto error;
}
@ -449,7 +429,7 @@ index 3e4d5f6d..a08f1d8a 100644
2.41.0
From fd4948255560039b51c2d61f0a62784ed8b6f5a6 Mon Sep 17 00:00:00 2001
From 0870c8db28be9eb457ee3d4f9a168959d9507efd Mon Sep 17 00:00:00 2001
From: Aris Adamantiadis <aris@0xbadc0de.be>
Date: Tue, 12 Dec 2023 23:30:26 +0100
Subject: [PATCH 2/4] CVE-2023-48795: Server side mitigations
@ -464,10 +444,10 @@ Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
3 files changed, 44 insertions(+), 11 deletions(-)
diff --git a/include/libssh/kex.h b/include/libssh/kex.h
index 2ace69b6..40da4ef2 100644
index ede7fa8a..ba98fded 100644
--- a/include/libssh/kex.h
+++ b/include/libssh/kex.h
@@ -36,6 +36,7 @@ SSH_PACKET_CALLBACK(ssh_packet_kexinit);
@@ -40,6 +40,7 @@ SSH_PACKET_CALLBACK(ssh_packet_kexinit);
int ssh_send_kex(ssh_session session);
void ssh_list_kex(struct ssh_kex_struct *kex);
int ssh_set_client_kex(ssh_session session);
@ -476,10 +456,10 @@ index 2ace69b6..40da4ef2 100644
int ssh_verify_existing_algo(enum ssh_kex_types_e algo, const char *name);
char *ssh_keep_known_algos(enum ssh_kex_types_e algo, const char *list);
diff --git a/src/kex.c b/src/kex.c
index 0772cae8..e37c176c 100644
index 3818297b..9ad671db 100644
--- a/src/kex.c
+++ b/src/kex.c
@@ -738,11 +738,8 @@ int ssh_set_client_kex(ssh_session session)
@@ -763,11 +763,8 @@ int ssh_set_client_kex(ssh_session session)
{
struct ssh_kex_struct *client = &session->next_crypto->client_kex;
const char *wanted;
@ -491,7 +471,7 @@ index 0772cae8..e37c176c 100644
/* Skip if already set, for example for the rekey or when we do the guessing
* it could have been already used to make some protocol decisions. */
@@ -791,11 +788,33 @@ int ssh_set_client_kex(ssh_session session)
@@ -816,11 +813,33 @@ int ssh_set_client_kex(ssh_session session)
return SSH_OK;
}
@ -529,7 +509,7 @@ index 0772cae8..e37c176c 100644
if (kex_len >= MAX_PACKET_LEN) {
/* Overflow */
return SSH_ERROR;
@@ -805,9 +824,16 @@ int ssh_set_client_kex(ssh_session session)
@@ -830,9 +849,16 @@ int ssh_set_client_kex(ssh_session session)
ssh_set_error_oom(session);
return SSH_ERROR;
}
@ -550,7 +530,7 @@ index 0772cae8..e37c176c 100644
}
diff --git a/src/server.c b/src/server.c
index ed73e7fb..35e84465 100644
index dc070a73..70b90899 100644
--- a/src/server.c
+++ b/src/server.c
@@ -195,7 +195,13 @@ int server_set_kex(ssh_session session)
@ -572,7 +552,7 @@ index ed73e7fb..35e84465 100644
2.41.0
From 03bbbc9e4c93aae2ccdd302d6123e4809be37746 Mon Sep 17 00:00:00 2001
From 5846e57538c750c5ce67df887d09fa99861c79c6 Mon Sep 17 00:00:00 2001
From: Jakub Jelen <jjelen@redhat.com>
Date: Thu, 14 Dec 2023 12:22:01 +0100
Subject: [PATCH 3/4] CVE-2023-48795: Strip extensions from both kex lists for
@ -585,10 +565,10 @@ Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
1 file changed, 12 insertions(+), 4 deletions(-)
diff --git a/src/kex.c b/src/kex.c
index e37c176c..eea3604b 100644
index 9ad671db..fbc70cf4 100644
--- a/src/kex.c
+++ b/src/kex.c
@@ -936,11 +936,19 @@ int ssh_kex_select_methods (ssh_session session)
@@ -961,11 +961,19 @@ int ssh_kex_select_methods (ssh_session session)
enum ssh_key_exchange_e kex_type;
int i;
@ -616,7 +596,7 @@ index e37c176c..eea3604b 100644
2.41.0
From 768d1ed30cf4b3cb9628254ef3ee24b9c38abdbc Mon Sep 17 00:00:00 2001
From 89df759200d31fc79fbbe213d8eda0d329eebf6d Mon Sep 17 00:00:00 2001
From: Jakub Jelen <jjelen@redhat.com>
Date: Thu, 14 Dec 2023 12:47:48 +0100
Subject: [PATCH 4/4] CVE-2023-48795: tests: Adjust calculation to strict kex
@ -624,11 +604,11 @@ Subject: [PATCH 4/4] CVE-2023-48795: tests: Adjust calculation to strict kex
Signed-off-by: Jakub Jelen <jjelen@redhat.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
---
tests/client/torture_rekey.c | 56 ++++++++++++++++++++----------------
1 file changed, 32 insertions(+), 24 deletions(-)
tests/client/torture_rekey.c | 55 ++++++++++++++++++++----------------
1 file changed, 31 insertions(+), 24 deletions(-)
diff --git a/tests/client/torture_rekey.c b/tests/client/torture_rekey.c
index 13c9a7fe..bfb273af 100644
index ccd5ae2c..57e03e3f 100644
--- a/tests/client/torture_rekey.c
+++ b/tests/client/torture_rekey.c
@@ -148,6 +148,29 @@ static void torture_rekey_default(void **state)
@ -681,25 +661,7 @@ index 13c9a7fe..bfb273af 100644
secret_hash = malloc(c->digest_len);
assert_non_null(secret_hash);
memcpy(secret_hash, c->secret_hash, c->digest_len);
@@ -272,14 +289,10 @@ static void torture_rekey_recv(void **state)
sftp_file file;
mode_t mask;
- /* The blocks limit is set correctly */
- c = s->ssh.session->current_crypto;
- assert_int_equal(c->in_cipher->max_blocks, bytes / c->in_cipher->blocksize);
- assert_int_equal(c->out_cipher->max_blocks, bytes / c->out_cipher->blocksize);
- /* We should have less encrypted packets than transfered (first are not encrypted) */
- assert_true(c->out_cipher->packets < s->ssh.session->send_seq);
- assert_true(c->in_cipher->packets < s->ssh.session->recv_seq);
+ sanity_check_session(state);
/* Copy the initial secret hash = session_id so we know we changed keys later */
+ c = s->ssh.session->current_crypto;
+ assert_non_null(c);
secret_hash = malloc(c->digest_len);
assert_non_null(secret_hash);
memcpy(secret_hash, c->secret_hash, c->digest_len);
@@ -464,15 +477,10 @@ static void torture_rekey_different_kex(void **state)
@@ -468,15 +480,10 @@ static void torture_rekey_different_kex(void **state)
assert_ssh_return_code(s->ssh.session, rc);
/* The blocks limit is set correctly */
@ -721,3 +683,47 @@ index 13c9a7fe..bfb273af 100644
--
2.41.0
diff -up libssh-0.10.4/src/packet.c.CVE-2023-48795.patch libssh-0.10.4/src/packet.c
--- libssh-0.10.4/src/packet.c.CVE-2023-48795.patch 2024-01-09 05:46:53.064383034 +0100
+++ libssh-0.10.4/src/packet.c 2024-01-09 05:48:28.360340184 +0100
@@ -1345,6 +1345,19 @@ size_t ssh_packet_socket_callback(const
"packet: read type %hhd [len=%d,padding=%hhd,comp=%d,payload=%d]",
session->in_packet.type, packet_len, padding, compsize, payloadsize);
+ if (crypto == NULL) {
+ /* In strict kex, only a few packets are allowed. Taint the session
+ * if we received packets that are normally allowed but to be
+ * refused if we are in strict kex when KEX is over.
+ */
+ uint8_t type = session->in_packet.type;
+
+ if (type != SSH2_MSG_KEXINIT && type != SSH2_MSG_NEWKEYS &&
+ (type < SSH2_MSG_KEXDH_INIT ||
+ type > SSH2_MSG_KEX_DH_GEX_REQUEST)) {
+ session->flags |= SSH_SESSION_FLAG_KEX_TAINTED;
+ }
+ }
/* Check if the packet is expected */
filter_result = ssh_packet_incoming_filter(session);
diff -up libssh-0.10.4/tests/client/torture_rekey.c.CVE-2023-48795.patch libssh-0.10.4/tests/client/torture_rekey.c
--- libssh-0.10.4/tests/client/torture_rekey.c.CVE-2023-48795.patch 2024-01-09 18:48:16.684366049 +0100
+++ libssh-0.10.4/tests/client/torture_rekey.c 2024-01-09 18:50:49.135897268 +0100
@@ -290,14 +290,10 @@ static void torture_rekey_recv(void **st
mode_t mask;
int rc;
- /* The blocks limit is set correctly */
- c = s->ssh.session->current_crypto;
- assert_int_equal(c->in_cipher->max_blocks, bytes / c->in_cipher->blocksize);
- assert_int_equal(c->out_cipher->max_blocks, bytes / c->out_cipher->blocksize);
- /* We should have less encrypted packets than transfered (first are not encrypted) */
- assert_true(c->out_cipher->packets < s->ssh.session->send_seq);
- assert_true(c->in_cipher->packets < s->ssh.session->recv_seq);
+ sanity_check_session(state);
/* Copy the initial secret hash = session_id so we know we changed keys later */
+ c = s->ssh.session->current_crypto;
+ assert_non_null(c);
secret_hash = malloc(c->digest_len);
assert_non_null(secret_hash);
memcpy(secret_hash, c->secret_hash, c->digest_len);

View File

@ -1,4 +1,4 @@
From 11bd6e6ad926a38cd7b9f8308a4c2fd8dfd9200c Mon Sep 17 00:00:00 2001
From c2c56bacab00766d01671413321d564227aabf19 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Sun, 5 Nov 2023 13:12:47 +0100
Subject: [PATCH 01/12] CVE-2023-6004: torture_config: Allow multiple '@' in
@ -6,86 +6,98 @@ Subject: [PATCH 01/12] CVE-2023-6004: torture_config: Allow multiple '@' in
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/unittests/torture_config.c | 44 ++++++++++++++++++--------------
1 file changed, 25 insertions(+), 19 deletions(-)
tests/unittests/torture_config.c | 56 +++++++++++++++++---------------
1 file changed, 30 insertions(+), 26 deletions(-)
diff --git a/tests/unittests/torture_config.c b/tests/unittests/torture_config.c
index f91112a9..3a5a74bf 100644
index 406f1985..b7c763af 100644
--- a/tests/unittests/torture_config.c
+++ b/tests/unittests/torture_config.c
@@ -671,24 +671,40 @@ static void torture_config_proxyjump(void **state) {
@@ -995,23 +995,22 @@ static void torture_config_proxyjump(void **state,
assert_string_equal(session->opts.ProxyCommand,
"ssh -W [%h]:%p 2620:52:0::fed");
- /* In this part, we try various other config files and strings. */
-
- /* Try to create some invalid configurations */
- /* Non-numeric port */
- config = "Host bad-port\n"
- "\tProxyJump jumpbox:22bad22\n";
+ /* Multiple @ is allowed in second jump */
torture_write_file(LIBSSH_TESTCONFIG11,
- "Host bad-port\n"
- "\tProxyJump jumpbox:22bad22\n"
+ "Host allowed-hostname\n"
+ "\tProxyJump localhost,user@principal.com@jumpbox:22\n"
"");
+ config = "Host allowed-hostname\n"
+ "\tProxyJump localhost,user@principal.com@jumpbox:22\n";
if (file != NULL) {
torture_write_file(file, config);
} else {
string = config;
}
torture_reset_config(session);
- ssh_options_set(session, SSH_OPTIONS_HOST, "bad-port");
- _parse_config(session, file, string, SSH_ERROR);
+ ssh_options_set(session, SSH_OPTIONS_HOST, "allowed-hostname");
ret = ssh_config_parse_file(session, LIBSSH_TESTCONFIG11);
- assert_ssh_return_code_equal(session, ret, SSH_ERROR);
+ assert_ssh_return_code(session, ret);
+ _parse_config(session, file, string, SSH_OK);
+ assert_string_equal(session->opts.ProxyCommand,
+ "ssh -J user@principal.com@jumpbox:22 -W [%h]:%p localhost");
+ "ssh -J user@principal.com@jumpbox:22 -W '[%h]:%p' localhost");
- /* Too many @ */
- config = "Host bad-hostname\n"
+ /* Multiple @ is allowed */
torture_write_file(LIBSSH_TESTCONFIG11,
- "Host bad-hostname\n"
+ "Host allowed-hostname\n"
"\tProxyJump user@principal.com@jumpbox:22\n"
"");
+ config = "Host allowed-hostname\n"
"\tProxyJump user@principal.com@jumpbox:22\n";
if (file != NULL) {
torture_write_file(file, config);
@@ -1019,7 +1018,24 @@ static void torture_config_proxyjump(void **state,
string = config;
}
torture_reset_config(session);
- ssh_options_set(session, SSH_OPTIONS_HOST, "bad-hostname");
+ ssh_options_set(session, SSH_OPTIONS_HOST, "allowed-hostname");
+ ret = ssh_config_parse_file(session, LIBSSH_TESTCONFIG11);
+ assert_ssh_return_code(session, ret);
+ _parse_config(session, file, string, SSH_OK);
+ assert_string_equal(session->opts.ProxyCommand,
+ "ssh -l user@principal.com -p 22 -W [%h]:%p jumpbox");
+ "ssh -l user@principal.com -p 22 -W '[%h]:%p' jumpbox");
+
+ /* In this part, we try various other config files and strings. */
+
+ /* Try to create some invalid configurations */
+ /* Non-numeric port */
+ torture_write_file(LIBSSH_TESTCONFIG11,
+ "Host bad-port\n"
+ "\tProxyJump jumpbox:22bad22\n"
+ "");
+ config = "Host bad-port\n"
+ "\tProxyJump jumpbox:22bad22\n";
+ if (file != NULL) {
+ torture_write_file(file, config);
+ } else {
+ string = config;
+ }
+ torture_reset_config(session);
+ ssh_options_set(session, SSH_OPTIONS_HOST, "bad-port");
ret = ssh_config_parse_file(session, LIBSSH_TESTCONFIG11);
assert_ssh_return_code_equal(session, ret, SSH_ERROR);
_parse_config(session, file, string, SSH_ERROR);
@@ -752,16 +768,6 @@ static void torture_config_proxyjump(void **state) {
ret = ssh_config_parse_file(session, LIBSSH_TESTCONFIG11);
assert_ssh_return_code_equal(session, ret, SSH_ERROR);
/* Braces mismatch in hostname */
@@ -1094,18 +1110,6 @@ static void torture_config_proxyjump(void **state,
ssh_options_set(session, SSH_OPTIONS_HOST, "bad-port-2");
_parse_config(session, file, string, SSH_ERROR);
- /* Too many @ in second jump */
- torture_write_file(LIBSSH_TESTCONFIG11,
- "Host bad-hostname\n"
- "\tProxyJump localhost,user@principal.com@jumpbox:22\n"
- "");
- config = "Host bad-hostname\n"
- "\tProxyJump localhost,user@principal.com@jumpbox:22\n";
- if (file != NULL) {
- torture_write_file(file, config);
- } else {
- string = config;
- }
- torture_reset_config(session);
- ssh_options_set(session, SSH_OPTIONS_HOST, "bad-hostname");
- ret = ssh_config_parse_file(session, LIBSSH_TESTCONFIG11);
- assert_ssh_return_code_equal(session, ret, SSH_ERROR);
- _parse_config(session, file, string, SSH_ERROR);
-
/* Braces mismatch in second jump */
torture_write_file(LIBSSH_TESTCONFIG11,
"Host mismatch\n"
config = "Host mismatch\n"
"\tProxyJump localhost,[::1:20\n";
--
2.41.0
From c3234e5f94b96d6e29f0c1c82821c1e3ebb181ed Mon Sep 17 00:00:00 2001
From a66b4a6eae6614d200a3625862d77565b96a7cd3 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Wed, 1 Nov 2023 11:24:43 +0100
Subject: [PATCH 02/12] CVE-2023-6004: config_parser: Allow multiple '@' in
@ -93,15 +105,16 @@ Subject: [PATCH 02/12] CVE-2023-6004: config_parser: Allow multiple '@' in
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
src/config_parser.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/config_parser.c b/src/config_parser.c
index ae2aa2c8..76cca224 100644
index 0d988fec..cf83e2c5 100644
--- a/src/config_parser.c
+++ b/src/config_parser.c
@@ -152,7 +152,7 @@ int ssh_config_parse_uri(const char *tok,
@@ -180,7 +180,7 @@ int ssh_config_parse_uri(const char *tok,
}
/* Username part (optional) */
@ -114,7 +127,7 @@ index ae2aa2c8..76cca224 100644
2.41.0
From a5b8bd0d8841296cf71d927824d60f576581243f Mon Sep 17 00:00:00 2001
From 8615c24647f773a5e04203c7459512715d698be1 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Tue, 31 Oct 2023 09:48:52 +0100
Subject: [PATCH 03/12] CVE-2023-6004: options: Simplify the hostname parsing
@ -125,15 +138,16 @@ parsing inside the function of ssh_options_set
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
src/options.c | 40 ++++++++++++++++------------------------
1 file changed, 16 insertions(+), 24 deletions(-)
diff --git a/src/options.c b/src/options.c
index b5f951ac..7c03e7ab 100644
index 6f2c9397..38511455 100644
--- a/src/options.c
+++ b/src/options.c
@@ -36,6 +36,7 @@
@@ -37,6 +37,7 @@
#include "libssh/session.h"
#include "libssh/misc.h"
#include "libssh/options.h"
@ -141,7 +155,7 @@ index b5f951ac..7c03e7ab 100644
#ifdef WITH_SERVER
#include "libssh/server.h"
#include "libssh/bind.h"
@@ -490,33 +491,24 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
@@ -515,33 +516,24 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
ssh_set_error_invalid(session);
return -1;
} else {
@ -153,7 +167,7 @@ index b5f951ac..7c03e7ab 100644
+ if (rc != SSH_OK) {
return -1;
}
- p = strchr(q, '@');
- p = strrchr(q, '@');
-
- SAFE_FREE(session->opts.host);
-
@ -194,7 +208,7 @@ index b5f951ac..7c03e7ab 100644
2.41.0
From efb24b6472e8b87c5832c0590f14e99e82fcdeeb Mon Sep 17 00:00:00 2001
From c6180409677c765e6b9ae2b18a3a7a9671ac1dbe Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Tue, 10 Oct 2023 12:44:16 +0200
Subject: [PATCH 04/12] CVE-2023-6004: misc: Add function to check allowed
@ -205,37 +219,18 @@ allowed because of IPv6 even it is prohibited in domain names.
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
include/libssh/misc.h | 2 ++
include/libssh/misc.h | 3 ++
src/misc.c | 68 +++++++++++++++++++++++++++++++++++++++++++
2 files changed, 70 insertions(+)
2 files changed, 71 insertions(+)
diff --git a/include/libssh/misc.h b/include/libssh/misc.h
index 3cc3b113..a5bee930 100644
--- a/include/libssh/misc.h
+++ b/include/libssh/misc.h
@@ -97,4 +97,6 @@ int ssh_mkdirs(const char *pathname, mode_t mode);
int ssh_quote_file_name(const char *file_name, char *buf, size_t buf_len);
int ssh_newline_vis(const char *string, char *buf, size_t buf_len);
+int ssh_check_hostname_syntax(const char *hostname);
+
#endif /* MISC_H_ */
diff --git a/src/misc.c b/src/misc.c
index 149eb85e..e4239e81 100644
index 7c478a77..be6ee836 100644
--- a/src/misc.c
+++ b/src/misc.c
@@ -94,6 +94,8 @@
#define ZLIB_STRING ""
#endif
+#define ARPA_DOMAIN_MAX_LEN 63
+
/**
* @defgroup libssh_misc The SSH helper functions.
* @ingroup libssh
@@ -1734,4 +1736,70 @@ int ssh_newline_vis(const char *string, char *buf, size_t buf_len)
return out - buf;
@@ -1974,4 +1976,70 @@ char *ssh_strerror(int err_num, char *buf, size_t buflen)
#endif /* defined(__linux__) && defined(__GLIBC__) && defined(_GNU_SOURCE) */
}
+/**
@ -309,7 +304,7 @@ index 149eb85e..e4239e81 100644
2.41.0
From 234ecdf4d9705efa3727a54dcc1ddfe6377c7bf6 Mon Sep 17 00:00:00 2001
From 9bbb817c0c5434f03613d0783b2ef5f52235b901 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Tue, 10 Oct 2023 12:45:28 +0200
Subject: [PATCH 05/12] CVE-2023-6004: torture_misc: Add test for
@ -317,16 +312,17 @@ Subject: [PATCH 05/12] CVE-2023-6004: torture_misc: Add test for
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/unittests/torture_misc.c | 73 ++++++++++++++++++++++++++++++++++
1 file changed, 73 insertions(+)
diff --git a/tests/unittests/torture_misc.c b/tests/unittests/torture_misc.c
index 0a48abbe..d14f4254 100644
index 9e346ff8..e682b6d4 100644
--- a/tests/unittests/torture_misc.c
+++ b/tests/unittests/torture_misc.c
@@ -656,6 +656,78 @@ static void torture_ssh_newline_vis(UNUSED_PARAM(void **state))
assert_string_equal(buffer, "a\\nb\\n");
@@ -760,6 +760,78 @@ static void torture_ssh_strerror(void **state)
assert_non_null(out);
}
+static void torture_ssh_check_hostname_syntax(void **state)
@ -404,10 +400,10 @@ index 0a48abbe..d14f4254 100644
int torture_run_tests(void) {
int rc;
struct CMUnitTest tests[] = {
@@ -678,6 +750,7 @@ int torture_run_tests(void) {
cmocka_unit_test(torture_ssh_newline_vis),
cmocka_unit_test(torture_ssh_mkdirs),
@@ -784,6 +856,7 @@ int torture_run_tests(void) {
cmocka_unit_test(torture_ssh_quote_file_name),
cmocka_unit_test(torture_ssh_strreplace),
cmocka_unit_test(torture_ssh_strerror),
+ cmocka_unit_test(torture_ssh_check_hostname_syntax),
};
@ -416,7 +412,7 @@ index 0a48abbe..d14f4254 100644
2.41.0
From 4d7ae19e9cd8c407012b40f3f2eaf480bfb1da7d Mon Sep 17 00:00:00 2001
From 22492b69bba22b102342afc574800d354a08e405 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Tue, 10 Oct 2023 18:33:56 +0200
Subject: [PATCH 06/12] CVE-2023-6004: config_parser: Check for valid syntax of
@ -427,12 +423,13 @@ The domain name syntax checker is based on RFC1035.
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
src/config_parser.c | 10 ++++++++++
1 file changed, 10 insertions(+)
src/config_parser.c | 12 +++++++++++-
1 file changed, 11 insertions(+), 1 deletion(-)
diff --git a/src/config_parser.c b/src/config_parser.c
index 76cca224..87bac5d4 100644
index cf83e2c5..b8b94611 100644
--- a/src/config_parser.c
+++ b/src/config_parser.c
@@ -30,6 +30,7 @@
@ -441,9 +438,9 @@ index 76cca224..87bac5d4 100644
#include "libssh/priv.h"
+#include "libssh/misc.h"
char *ssh_config_get_cmd(char **str)
{
@@ -139,6 +140,7 @@ int ssh_config_parse_uri(const char *tok,
/* Returns the original string after skipping the leading whitespace
* and optional quotes.
@@ -167,6 +168,7 @@ int ssh_config_parse_uri(const char *tok,
{
char *endp = NULL;
long port_n;
@ -451,7 +448,7 @@ index 76cca224..87bac5d4 100644
/* Sanitize inputs */
if (username != NULL) {
@@ -196,6 +198,14 @@ int ssh_config_parse_uri(const char *tok,
@@ -224,6 +226,14 @@ int ssh_config_parse_uri(const char *tok,
if (*hostname == NULL) {
goto error;
}
@ -470,7 +467,7 @@ index 76cca224..87bac5d4 100644
2.41.0
From 8cf4f4bfda968ab526c1a601ea1030bbaccaba17 Mon Sep 17 00:00:00 2001
From d7467498fd988949edde9c6384973250fd454a8b Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Tue, 10 Oct 2023 10:28:47 +0200
Subject: [PATCH 07/12] CVE-2023-6004: torture_proxycommand: Add test for
@ -478,15 +475,16 @@ Subject: [PATCH 07/12] CVE-2023-6004: torture_proxycommand: Add test for
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/client/torture_proxycommand.c | 53 +++++++++++++++++++++++++++++
1 file changed, 53 insertions(+)
diff --git a/tests/client/torture_proxycommand.c b/tests/client/torture_proxycommand.c
index c04ff2ab..dc17f3d8 100644
index 9b8019ca..1bad4ccc 100644
--- a/tests/client/torture_proxycommand.c
+++ b/tests/client/torture_proxycommand.c
@@ -161,6 +161,56 @@ static void torture_options_set_proxycommand_ssh_stderr(void **state)
@@ -166,6 +166,56 @@ static void torture_options_set_proxycommand_ssh_stderr(void **state)
assert_int_equal(rc & O_RDWR, O_RDWR);
}
@ -543,7 +541,7 @@ index c04ff2ab..dc17f3d8 100644
int torture_run_tests(void) {
int rc;
struct CMUnitTest tests[] = {
@@ -176,6 +226,9 @@ int torture_run_tests(void) {
@@ -181,6 +231,9 @@ int torture_run_tests(void) {
cmocka_unit_test_setup_teardown(torture_options_set_proxycommand_ssh_stderr,
session_setup,
session_teardown),
@ -557,22 +555,23 @@ index c04ff2ab..dc17f3d8 100644
2.41.0
From a0dbe0d556e073804cc549802569577bb24757d9 Mon Sep 17 00:00:00 2001
From 62d3101c1f76b6891b70c50154e0e934d6b8cb57 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Mon, 6 Nov 2023 20:11:38 +0100
Subject: [PATCH 08/12] CVE-2023-6004: torture_misc: Add test for ssh_is_ipaddr
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/unittests/torture_misc.c | 26 ++++++++++++++++++++++++++
1 file changed, 26 insertions(+)
diff --git a/tests/unittests/torture_misc.c b/tests/unittests/torture_misc.c
index d14f4254..073bc54c 100644
index e682b6d4..b07392ab 100644
--- a/tests/unittests/torture_misc.c
+++ b/tests/unittests/torture_misc.c
@@ -728,6 +728,31 @@ static void torture_ssh_check_hostname_syntax(void **state)
@@ -832,6 +832,31 @@ static void torture_ssh_check_hostname_syntax(void **state)
assert_int_equal(rc, SSH_ERROR);
}
@ -604,9 +603,9 @@ index d14f4254..073bc54c 100644
int torture_run_tests(void) {
int rc;
struct CMUnitTest tests[] = {
@@ -751,6 +776,7 @@ int torture_run_tests(void) {
cmocka_unit_test(torture_ssh_mkdirs),
cmocka_unit_test(torture_ssh_quote_file_name),
@@ -857,6 +882,7 @@ int torture_run_tests(void) {
cmocka_unit_test(torture_ssh_strreplace),
cmocka_unit_test(torture_ssh_strerror),
cmocka_unit_test(torture_ssh_check_hostname_syntax),
+ cmocka_unit_test(torture_ssh_is_ipaddr),
};
@ -616,57 +615,35 @@ index d14f4254..073bc54c 100644
2.41.0
From cdaec0d6273243a03f460cc5ba1a2265b4afb93a Mon Sep 17 00:00:00 2001
From cea841d71c025f9c998b7d5fc9f2a2839df62921 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Tue, 28 Nov 2023 15:26:45 +0100
Subject: [PATCH 09/12] CVE-2023-6004: misc: Add ipv6 link-local check for an
ip address
Subject: [PATCH 09/12] CVE-2023-6004 misc: Add ipv6 link-local check for an ip
address
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
src/CMakeLists.txt | 17 ++++++++++-------
src/CMakeLists.txt | 1 +
src/connect.c | 2 +-
src/misc.c | 44 ++++++++++++++++++++++++++++++++++++++------
3 files changed, 49 insertions(+), 14 deletions(-)
3 files changed, 40 insertions(+), 7 deletions(-)
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index a576cf71..fc401793 100644
index d6245c0d..807313b5 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -9,13 +9,6 @@ set(LIBSSH_LINK_LIBRARIES
${LIBSSH_REQUIRED_LIBRARIES}
)
-if (WIN32)
- set(LIBSSH_LINK_LIBRARIES
- ${LIBSSH_LINK_LIBRARIES}
- ws2_32
- )
-endif (WIN32)
-
if (OPENSSL_CRYPTO_LIBRARIES)
set(LIBSSH_PRIVATE_INCLUDE_DIRS
${LIBSSH_PRIVATE_INCLUDE_DIRS}
@@ -93,6 +86,16 @@ if (MINGW AND Threads_FOUND)
)
endif()
+# This needs to be last for mingw to build
+# https://gitlab.com/libssh/libssh-mirror/-/issues/84
+if (WIN32)
+ set(LIBSSH_LINK_LIBRARIES
+ ${LIBSSH_LINK_LIBRARIES}
@@ -91,6 +91,7 @@ endif()
if (WIN32)
set(LIBSSH_LINK_LIBRARIES
${LIBSSH_LINK_LIBRARIES}
+ iphlpapi
+ ws2_32
+ )
+endif (WIN32)
+
if (BUILD_STATIC_LIB)
set(LIBSSH_STATIC_LIBRARY
ssh_static
ws2_32
)
endif (WIN32)
diff --git a/src/connect.c b/src/connect.c
index ce4d58df..ca62dcf0 100644
index 57e37e63..15cae644 100644
--- a/src/connect.c
+++ b/src/connect.c
@@ -136,7 +136,7 @@ static int getai(const char *host, int port, struct addrinfo **ai)
@ -679,7 +656,7 @@ index ce4d58df..ca62dcf0 100644
SSH_LOG(SSH_LOG_PACKET, "host %s matches an IP address", host);
hints.ai_flags |= AI_NUMERICHOST;
diff --git a/src/misc.c b/src/misc.c
index e4239e81..6f5d2d60 100644
index be6ee836..7081f12a 100644
--- a/src/misc.c
+++ b/src/misc.c
@@ -32,6 +32,7 @@
@ -698,9 +675,9 @@ index e4239e81..6f5d2d60 100644
#ifdef HAVE_IO_H
#include <io.h>
@@ -216,22 +218,37 @@ int ssh_is_ipaddr_v4(const char *str) {
int ssh_is_ipaddr(const char *str) {
@@ -222,22 +224,37 @@ int ssh_is_ipaddr_v4(const char *str)
int ssh_is_ipaddr(const char *str)
{
int rc = SOCKET_ERROR;
+ char *s = strdup(str);
@ -739,9 +716,9 @@ index e4239e81..6f5d2d60 100644
return ssh_is_ipaddr_v4(str);
}
#else /* _WIN32 */
@@ -335,17 +352,32 @@ int ssh_is_ipaddr_v4(const char *str) {
int ssh_is_ipaddr(const char *str) {
@@ -343,17 +360,32 @@ int ssh_is_ipaddr_v4(const char *str)
int ssh_is_ipaddr(const char *str)
{
int rc = -1;
+ char *s = strdup(str);
@ -779,7 +756,7 @@ index e4239e81..6f5d2d60 100644
2.41.0
From 6a8a18c73e73a338283dfbade0a7d83e5cfafe3b Mon Sep 17 00:00:00 2001
From 2c492ee179d5caa2718c5e768bab6e0b2b64a8b0 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <norbertpocs0@gmail.com>
Date: Tue, 28 Nov 2023 15:27:31 +0100
Subject: [PATCH 10/12] CVE-2023-6004: torture_misc: Add tests for ipv6
@ -787,16 +764,17 @@ Subject: [PATCH 10/12] CVE-2023-6004: torture_misc: Add tests for ipv6
Signed-off-by: Norbert Pocs <norbertpocs0@gmail.com>
Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/unittests/torture_misc.c | 20 ++++++++++++++++++++
1 file changed, 20 insertions(+)
diff --git a/tests/unittests/torture_misc.c b/tests/unittests/torture_misc.c
index 073bc54c..f16b766e 100644
index b07392ab..77166759 100644
--- a/tests/unittests/torture_misc.c
+++ b/tests/unittests/torture_misc.c
@@ -17,7 +17,14 @@
#include "misc.c"
#include "torture.h"
#include "error.c"
+#ifdef _WIN32
@ -810,7 +788,7 @@ index 073bc54c..f16b766e 100644
const char template[] = "temp_dir_XXXXXX";
@@ -730,14 +737,27 @@ static void torture_ssh_check_hostname_syntax(void **state)
@@ -834,14 +841,27 @@ static void torture_ssh_check_hostname_syntax(void **state)
static void torture_ssh_is_ipaddr(void **state) {
int rc;
@ -842,7 +820,7 @@ index 073bc54c..f16b766e 100644
2.41.0
From 72f59157e6ccbd4c0bb806690931413169a0886f Mon Sep 17 00:00:00 2001
From 1a02364b5107a4125ea3cb76fcdb6beabaebf3be Mon Sep 17 00:00:00 2001
From: Jakub Jelen <jjelen@redhat.com>
Date: Fri, 22 Dec 2023 10:32:40 +0100
Subject: [PATCH 11/12] Fix regression in IPv6 addresses in hostname parsing
@ -858,10 +836,10 @@ Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
4 files changed, 23 insertions(+), 18 deletions(-)
diff --git a/include/libssh/config_parser.h b/include/libssh/config_parser.h
index e974917c..ee647bfb 100644
index a7dd42a2..ca353432 100644
--- a/include/libssh/config_parser.h
+++ b/include/libssh/config_parser.h
@@ -26,6 +26,8 @@
@@ -30,6 +30,8 @@
#ifndef CONFIG_PARSER_H_
#define CONFIG_PARSER_H_
@ -870,31 +848,11 @@ index e974917c..ee647bfb 100644
char *ssh_config_get_cmd(char **str);
char *ssh_config_get_token(char **str);
@@ -45,13 +47,16 @@ int ssh_config_get_yesno(char **str, int notfound);
* be stored or NULL if we do not care about the result.
* @param[out] port Pointer to the location, where the new port will
* be stored or NULL if we do not care about the result.
+ * @param[in] ignore_port Set to true if the we should not attempt to parse
+ * port number.
*
* @returns SSH_OK if the provided string is in format of SSH URI,
* SSH_ERROR on failure
*/
int ssh_config_parse_uri(const char *tok,
- char **username,
- char **hostname,
- char **port);
+ char **username,
+ char **hostname,
+ char **port,
+ bool ignore_port);
#endif /* LIBSSH_CONFIG_H_ */
diff --git a/src/config.c b/src/config.c
index 54ada276..a813568d 100644
index c5c40125..273db7c8 100644
--- a/src/config.c
+++ b/src/config.c
@@ -324,7 +324,7 @@ ssh_config_parse_proxy_jump(ssh_session session, const char *s, bool do_parsing)
@@ -464,7 +464,7 @@ ssh_config_parse_proxy_jump(ssh_session session, const char *s, bool do_parsing)
}
if (parse_entry) {
/* We actually care only about the first item */
@ -903,7 +861,7 @@ index 54ada276..a813568d 100644
/* The rest of the list needs to be passed on */
if (endp != NULL) {
next = strdup(endp + 1);
@@ -335,7 +335,7 @@ ssh_config_parse_proxy_jump(ssh_session session, const char *s, bool do_parsing)
@@ -475,7 +475,7 @@ ssh_config_parse_proxy_jump(ssh_session session, const char *s, bool do_parsing)
}
} else {
/* The rest is just sanity-checked to avoid failures later */
@ -913,10 +871,10 @@ index 54ada276..a813568d 100644
if (rv != SSH_OK) {
goto out;
diff --git a/src/config_parser.c b/src/config_parser.c
index 87bac5d4..a2da0a62 100644
index b8b94611..d4b2d2c3 100644
--- a/src/config_parser.c
+++ b/src/config_parser.c
@@ -134,9 +134,10 @@ int ssh_config_get_yesno(char **str, int notfound)
@@ -162,9 +162,10 @@ int ssh_config_get_yesno(char **str, int notfound)
}
int ssh_config_parse_uri(const char *tok,
@ -930,7 +888,7 @@ index 87bac5d4..a2da0a62 100644
{
char *endp = NULL;
long port_n;
@@ -182,12 +183,17 @@ int ssh_config_parse_uri(const char *tok,
@@ -210,12 +211,17 @@ int ssh_config_parse_uri(const char *tok,
if (endp == NULL) {
goto error;
}
@ -951,10 +909,10 @@ index 87bac5d4..a2da0a62 100644
if (tok == endp) {
/* Zero-length hostnames are not valid */
diff --git a/src/options.c b/src/options.c
index 7c03e7ab..0890ff2e 100644
index 38511455..b3ecffe1 100644
--- a/src/options.c
+++ b/src/options.c
@@ -491,17 +491,11 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
@@ -516,17 +516,11 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
ssh_set_error_invalid(session);
return -1;
} else {
@ -978,7 +936,7 @@ index 7c03e7ab..0890ff2e 100644
2.41.0
From 5dc10ff63ca2e8db91abfdccf1d095f5b4261b8e Mon Sep 17 00:00:00 2001
From 6f1b1e76bb38bc89819132e1810e4301ec9034a4 Mon Sep 17 00:00:00 2001
From: Jakub Jelen <jjelen@redhat.com>
Date: Fri, 22 Dec 2023 09:52:18 +0100
Subject: [PATCH 12/12] tests: Increase test coverage for IPv6 address parsing
@ -993,23 +951,15 @@ Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
(cherry picked from commit 6f6e453d7b0ad4ee6a6f6a1c96a9a6b27821410d)
---
tests/unittests/torture_config.c | 49 +++++++++++++++++++++++++++++++
tests/unittests/torture_options.c | 22 ++++++++++++++
2 files changed, 71 insertions(+)
tests/unittests/torture_options.c | 16 ++++++++++
2 files changed, 65 insertions(+)
diff --git a/tests/unittests/torture_config.c b/tests/unittests/torture_config.c
index 3a5a74bf..d8097e79 100644
index b7c763af..26a24215 100644
--- a/tests/unittests/torture_config.c
+++ b/tests/unittests/torture_config.c
@@ -2,6 +2,7 @@
#define LIBSSH_STATIC
+#include <errno.h>
#include "torture.h"
#include "libssh/options.h"
#include "libssh/session.h"
@@ -997,6 +998,53 @@ static void torture_config_match_pattern(void **state)
@@ -1850,6 +1850,53 @@ static void torture_config_make_absolute_no_sshdir(void **state)
torture_config_make_absolute_int(state, 1);
}
+static void torture_config_parse_uri(void **state)
@ -1059,22 +1009,23 @@ index 3a5a74bf..d8097e79 100644
+ SAFE_FREE(hostname);
+}
+
int torture_run_tests(void) {
int torture_run_tests(void)
{
int rc;
@@ -1012,6 +1060,7 @@ int torture_run_tests(void) {
cmocka_unit_test(torture_config_rekey),
cmocka_unit_test(torture_config_pubkeyacceptedkeytypes),
cmocka_unit_test(torture_config_match_pattern),
+ cmocka_unit_test(torture_config_parse_uri),
@@ -1922,6 +1969,8 @@ int torture_run_tests(void)
setup, teardown),
cmocka_unit_test_setup_teardown(torture_config_make_absolute_no_sshdir,
setup_no_sshdir, teardown),
+ cmocka_unit_test_setup_teardown(torture_config_parse_uri,
+ setup, teardown),
};
diff --git a/tests/unittests/torture_options.c b/tests/unittests/torture_options.c
index d0fdaed1..576ca9cd 100644
index 425d7295..8a5505a1 100644
--- a/tests/unittests/torture_options.c
+++ b/tests/unittests/torture_options.c
@@ -59,12 +59,34 @@ static void torture_options_set_host(void **state) {
@@ -60,6 +60,20 @@ static void torture_options_set_host(void **state) {
assert_non_null(session->opts.host);
assert_string_equal(session->opts.host, "localhost");
@ -1095,20 +1046,67 @@ index d0fdaed1..576ca9cd 100644
rc = ssh_options_set(session, SSH_OPTIONS_HOST, "guru@meditation");
assert_true(rc == 0);
assert_non_null(session->opts.host);
assert_string_equal(session->opts.host, "meditation");
@@ -67,12 +81,14 @@ static void torture_options_set_host(void **state) {
assert_non_null(session->opts.username);
assert_string_equal(session->opts.username, "guru");
+
+ /* more @ in uri is OK -- it should go to the username */
+ rc = ssh_options_set(session, SSH_OPTIONS_HOST, "at@login@hostname");
+ assert_true(rc == 0);
+ assert_non_null(session->opts.host);
+ assert_string_equal(session->opts.host, "hostname");
+ assert_non_null(session->opts.username);
+ assert_string_equal(session->opts.username, "at@login");
rc = ssh_options_set(session, SSH_OPTIONS_HOST, "at@login@hostname");
assert_true(rc == 0);
assert_non_null(session->opts.host);
assert_string_equal(session->opts.host, "hostname");
assert_non_null(session->opts.username);
assert_string_equal(session->opts.username, "at@login");
+
}
static void torture_options_set_ciphers(void **state) {
--
2.41.0
diff -up libssh-0.10.4/include/libssh/config_parser.h.CVE-2023-6004.patch libssh-0.10.4/include/libssh/config_parser.h
--- libssh-0.10.4/include/libssh/config_parser.h.CVE-2023-6004.patch 2024-01-08 19:48:48.964006647 +0100
+++ libssh-0.10.4/include/libssh/config_parser.h 2024-01-08 19:56:38.850726165 +0100
@@ -47,13 +47,16 @@ int ssh_config_get_yesno(char **str, int
* be stored or NULL if we do not care about the result.
* @param[out] port Pointer to the location, where the new port will
* be stored or NULL if we do not care about the result.
+ * @param[in] ignore_port Set to true if the we should not attempt to parse
+ * port number.
*
* @returns SSH_OK if the provided string is in format of SSH URI,
* SSH_ERROR on failure
*/
int ssh_config_parse_uri(const char *tok,
- char **username,
- char **hostname,
- char **port);
+ char **username,
+ char **hostname,
+ char **port,
+ bool ignore_port);
#endif /* LIBSSH_CONFIG_H_ */
diff -up libssh-0.10.4/include/libssh/misc.h.CVE-2023-6004.patch libssh-0.10.4/include/libssh/misc.h
--- libssh-0.10.4/include/libssh/misc.h.CVE-2023-6004.patch 2024-01-08 19:48:07.422589393 +0100
+++ libssh-0.10.4/include/libssh/misc.h 2024-01-08 19:53:33.830867829 +0100
@@ -99,4 +99,7 @@ int ssh_newline_vis(const char *string,
int ssh_tmpname(char *template);
char *ssh_strreplace(const char *src, const char *pattern, const char *repl);
+
+int ssh_check_hostname_syntax(const char *hostname);
+
#endif /* MISC_H_ */
diff -up libssh-0.10.4/src/misc.c.CVE-2023-6004.patch libssh-0.10.4/src/misc.c
--- libssh-0.10.4/src/misc.c.CVE-2023-6004.patch 2024-01-08 19:48:26.779783823 +0100
+++ libssh-0.10.4/src/misc.c 2024-01-08 19:54:55.209685193 +0100
@@ -96,6 +96,8 @@
#define ZLIB_STRING ""
#endif
+#define ARPA_DOMAIN_MAX_LEN 63
+
/**
* @defgroup libssh_misc The SSH helper functions.
* @ingroup libssh

File diff suppressed because it is too large Load Diff

View File

@ -1,668 +0,0 @@
diff --color -ru ../libssh-0.9.6/examples/sshnetcat.c ./examples/sshnetcat.c
--- ../libssh-0.9.6/examples/sshnetcat.c 2021-08-26 14:27:42.000000000 +0200
+++ ./examples/sshnetcat.c 2023-05-02 10:36:00.793381735 +0200
@@ -233,9 +233,10 @@
}
void cleanup_pcap(void);
-void cleanup_pcap(){
+void cleanup_pcap(void)
+{
ssh_pcap_file_free(pcap);
- pcap=NULL;
+ pcap = NULL;
}
#endif
diff --color -ru ../libssh-0.9.6/src/init.c ./src/init.c
--- ../libssh-0.9.6/src/init.c 2021-03-15 08:11:33.000000000 +0100
+++ ./src/init.c 2023-05-02 10:36:00.793381735 +0200
@@ -269,7 +269,7 @@
*
* @see ssh_init()
*/
-bool is_ssh_initialized() {
+bool is_ssh_initialized(void) {
bool is_initialized = false;
diff --color -ru ../libssh-0.9.6/tests/client/torture_auth.c ./tests/client/torture_auth.c
--- ../libssh-0.9.6/tests/client/torture_auth.c 2021-08-26 14:27:42.000000000 +0200
+++ ./tests/client/torture_auth.c 2023-05-02 10:36:00.815381960 +0200
@@ -200,7 +200,8 @@
assert_non_null(ssh_agent_pidfile);
/* kill agent pid */
- torture_terminate_process(ssh_agent_pidfile);
+ rc = torture_terminate_process(ssh_agent_pidfile);
+ assert_return_code(rc, errno);
unlink(ssh_agent_pidfile);
@@ -551,6 +552,7 @@
static void torture_auth_agent_cert(void **state)
{
+#if OPENSSH_VERSION_MAJOR < 8 || (OPENSSH_VERSION_MAJOR == 8 && OPENSSH_VERSION_MINOR == 0)
struct torture_state *s = *state;
ssh_session session = s->ssh.session;
int rc;
@@ -570,6 +572,7 @@
"ssh-rsa-cert-v01@openssh.com");
assert_int_equal(rc, SSH_OK);
}
+#endif /* OPENSSH_VERSION_MAJOR < 8.1 */
/* Setup loads a different key, tests are exactly the same. */
torture_auth_agent(state);
@@ -577,6 +580,7 @@
static void torture_auth_agent_cert_nonblocking(void **state)
{
+#if OPENSSH_VERSION_MAJOR < 8 || (OPENSSH_VERSION_MAJOR == 8 && OPENSSH_VERSION_MINOR == 0)
struct torture_state *s = *state;
ssh_session session = s->ssh.session;
int rc;
@@ -596,6 +600,7 @@
"ssh-rsa-cert-v01@openssh.com");
assert_int_equal(rc, SSH_OK);
}
+#endif /* OPENSSH_VERSION_MAJOR < 8.1 */
torture_auth_agent_nonblocking(state);
}
diff --color -ru ../libssh-0.9.6/tests/client/torture_rekey.c ./tests/client/torture_rekey.c
--- ../libssh-0.9.6/tests/client/torture_rekey.c 2023-04-28 17:26:41.472315318 +0200
+++ ./tests/client/torture_rekey.c 2023-05-02 10:36:00.805381857 +0200
@@ -38,6 +38,8 @@
#include <fcntl.h>
#include <pwd.h>
+#define KEX_RETRY 32
+
static uint64_t bytes = 2048; /* 2KB (more than the authentication phase) */
static int sshd_setup(void **state)
@@ -190,10 +192,11 @@
rc = ssh_userauth_publickey_auto(s->ssh.session, NULL, NULL);
assert_int_equal(rc, SSH_AUTH_SUCCESS);
- /* send ignore packets of up to 1KB to trigger rekey */
+ /* send ignore packets of up to 1KB to trigger rekey. Send little bit more
+ * to make sure it completes with all different ciphers */
memset(data, 0, sizeof(data));
memset(data, 'A', 128);
- for (i = 0; i < 16; i++) {
+ for (i = 0; i < KEX_RETRY; i++) {
ssh_send_ignore(s->ssh.session, data);
ssh_handle_packets(s->ssh.session, 50);
}
@@ -496,9 +499,15 @@
* to make sure the rekey it completes with all different ciphers (paddings */
memset(data, 0, sizeof(data));
memset(data, 'A', 128);
- for (i = 0; i < 20; i++) {
+ for (i = 0; i < KEX_RETRY; i++) {
ssh_send_ignore(s->ssh.session, data);
- ssh_handle_packets(s->ssh.session, 50);
+ ssh_handle_packets(s->ssh.session, 100);
+
+ c = s->ssh.session->current_crypto;
+ /* SHA256 len */
+ if (c->digest_len != 32) {
+ break;
+ }
}
/* The rekey limit was restored in the new crypto to the same value */
@@ -568,9 +577,15 @@
* to make sure the rekey it completes with all different ciphers (paddings */
memset(data, 0, sizeof(data));
memset(data, 'A', 128);
- for (i = 0; i < 25; i++) {
+ for (i = 0; i < KEX_RETRY; i++) {
ssh_send_ignore(s->ssh.session, data);
- ssh_handle_packets(s->ssh.session, 50);
+ ssh_handle_packets(s->ssh.session, 100);
+
+ c = s->ssh.session->current_crypto;
+ /* SHA256 len */
+ if (c->digest_len != 32) {
+ break;
+ }
}
/* Check that the secret hash is different than initially */
diff --color -ru ../libssh-0.9.6/tests/CMakeLists.txt ./tests/CMakeLists.txt
--- ../libssh-0.9.6/tests/CMakeLists.txt 2021-08-26 14:27:42.000000000 +0200
+++ ./tests/CMakeLists.txt 2023-05-02 10:32:03.964511860 +0200
@@ -153,6 +153,17 @@
execute_process(COMMAND ${ID_EXECUTABLE} -u OUTPUT_VARIABLE LOCAL_UID OUTPUT_STRIP_TRAILING_WHITESPACE)
endif()
+ find_program(TIMEOUT_EXECUTABLE
+ NAME
+ timeout
+ PATHS
+ /bin
+ /usr/bin
+ /usr/local/bin)
+ if (TIMEOUT_EXECUTABLE)
+ set(WITH_TIMEOUT "1")
+ endif()
+
# chroot_wrapper
add_library(chroot_wrapper SHARED chroot_wrapper.c)
set(CHROOT_WRAPPER_LIBRARY ${libssh_BINARY_DIR}/lib/${CMAKE_SHARED_LIBRARY_PREFIX}chroot_wrapper${CMAKE_SHARED_LIBRARY_SUFFIX})
diff --color -ru ../libssh-0.9.6/tests/pkd/pkd_keyutil.c ./tests/pkd/pkd_keyutil.c
--- ../libssh-0.9.6/tests/pkd/pkd_keyutil.c 2021-03-15 08:11:33.000000000 +0100
+++ ./tests/pkd/pkd_keyutil.c 2023-05-02 10:36:00.793381735 +0200
@@ -22,7 +22,7 @@
#include "pkd_keyutil.h"
#include "pkd_util.h"
-void setup_rsa_key() {
+void setup_rsa_key(void) {
int rc = 0;
if (access(LIBSSH_RSA_TESTKEY, F_OK) != 0) {
rc = system_checked(OPENSSH_KEYGEN " -t rsa -q -N \"\" -f "
@@ -31,7 +31,7 @@
assert_int_equal(rc, 0);
}
-void setup_ed25519_key() {
+void setup_ed25519_key(void) {
int rc = 0;
if (access(LIBSSH_ED25519_TESTKEY, F_OK) != 0) {
rc = system_checked(OPENSSH_KEYGEN " -t ed25519 -q -N \"\" -f "
@@ -41,7 +41,7 @@
}
#ifdef HAVE_DSA
-void setup_dsa_key() {
+void setup_dsa_key(void) {
int rc = 0;
if (access(LIBSSH_DSA_TESTKEY, F_OK) != 0) {
rc = system_checked(OPENSSH_KEYGEN " -t dsa -q -N \"\" -f "
@@ -51,7 +51,7 @@
}
#endif
-void setup_ecdsa_keys() {
+void setup_ecdsa_keys(void) {
int rc = 0;
if (access(LIBSSH_ECDSA_256_TESTKEY, F_OK) != 0) {
@@ -71,27 +71,27 @@
}
}
-void cleanup_rsa_key() {
+void cleanup_rsa_key(void) {
cleanup_key(LIBSSH_RSA_TESTKEY);
}
-void cleanup_ed25519_key() {
+void cleanup_ed25519_key(void) {
cleanup_key(LIBSSH_ED25519_TESTKEY);
}
#ifdef HAVE_DSA
-void cleanup_dsa_key() {
+void cleanup_dsa_key(void) {
cleanup_key(LIBSSH_DSA_TESTKEY);
}
#endif
-void cleanup_ecdsa_keys() {
+void cleanup_ecdsa_keys(void) {
cleanup_key(LIBSSH_ECDSA_256_TESTKEY);
cleanup_key(LIBSSH_ECDSA_384_TESTKEY);
cleanup_key(LIBSSH_ECDSA_521_TESTKEY);
}
-void setup_openssh_client_keys() {
+void setup_openssh_client_keys(void) {
int rc = 0;
if (access(OPENSSH_CA_TESTKEY, F_OK) != 0) {
@@ -184,7 +184,7 @@
}
}
-void cleanup_openssh_client_keys() {
+void cleanup_openssh_client_keys(void) {
cleanup_key(OPENSSH_CA_TESTKEY);
cleanup_key(OPENSSH_RSA_TESTKEY);
cleanup_file(OPENSSH_RSA_TESTKEY "-sha256-cert.pub");
@@ -199,7 +199,7 @@
}
}
-void setup_dropbear_client_rsa_key() {
+void setup_dropbear_client_rsa_key(void) {
int rc = 0;
if (access(DROPBEAR_RSA_TESTKEY, F_OK) != 0) {
rc = system_checked(DROPBEAR_KEYGEN " -t rsa -f "
@@ -208,6 +208,6 @@
assert_int_equal(rc, 0);
}
-void cleanup_dropbear_client_rsa_key() {
+void cleanup_dropbear_client_rsa_key(void) {
unlink(DROPBEAR_RSA_TESTKEY);
}
diff --color -ru ../libssh-0.9.6/tests/server/torture_server_config.c ./tests/server/torture_server_config.c
--- ../libssh-0.9.6/tests/server/torture_server_config.c 2021-08-26 14:27:42.000000000 +0200
+++ ./tests/server/torture_server_config.c 2023-05-02 10:36:00.815381960 +0200
@@ -285,9 +285,7 @@
assert_non_null(s);
rc = torture_terminate_process(s->srv_pidfile);
- if (rc != 0) {
- fprintf(stderr, "XXXXXX Failed to terminate sshd\n");
- }
+ assert_return_code(rc, errno);
unlink(s->srv_pidfile);
@@ -513,6 +511,12 @@
/* Try each algorithm individually */
j = 0;
while(tokens->tokens[j] != NULL) {
+ char *cmp = strstr(OPENSSH_CIPHERS, tokens->tokens[j]);
+ if (cmp == NULL) {
+ /* This cipher is not supported by the OpenSSH. Skip it */
+ j++;
+ continue;
+ }
snprintf(config_content,
sizeof(config_content),
"HostKey %s\nCiphers %s\n",
diff --color -ru ../libssh-0.9.6/tests/tests_config.h.cmake ./tests/tests_config.h.cmake
--- ../libssh-0.9.6/tests/tests_config.h.cmake 2021-08-26 14:27:42.000000000 +0200
+++ ./tests/tests_config.h.cmake 2023-05-02 10:32:03.964511860 +0200
@@ -66,4 +66,6 @@
#cmakedefine NC_EXECUTABLE "${NC_EXECUTABLE}"
#cmakedefine SSHD_EXECUTABLE "${SSHD_EXECUTABLE}"
-#cmakedefine SSH_EXECUTABLE "${SSH_EXECUTABLE}"
\ No newline at end of file
+#cmakedefine SSH_EXECUTABLE "${SSH_EXECUTABLE}"
+#cmakedefine WITH_TIMEOUT ${WITH_TIMEOUT}
+#cmakedefine TIMEOUT_EXECUTABLE "${TIMEOUT_EXECUTABLE}"
diff --color -ru ../libssh-0.9.6/tests/torture.c ./tests/torture.c
--- ../libssh-0.9.6/tests/torture.c 2021-08-26 14:27:44.000000000 +0200
+++ ./tests/torture.c 2023-05-02 10:36:00.815381960 +0200
@@ -51,6 +51,7 @@
#include "torture.h"
#include "torture_key.h"
#include "libssh/misc.h"
+#include "libssh/token.h"
#define TORTURE_SSHD_SRV_IPV4 "127.0.0.10"
/* socket wrapper IPv6 prefix fd00::5357:5fxx */
@@ -250,8 +251,12 @@
rc = kill(pid, 0);
if (rc != 0) {
- is_running = 0;
- break;
+ /* Process not found */
+ if (errno == ESRCH) {
+ is_running = 0;
+ rc = 0;
+ break;
+ }
}
}
@@ -260,7 +265,7 @@
"WARNING: The process with pid %u is still running!\n", pid);
}
- return 0;
+ return rc;
}
ssh_session torture_ssh_session(struct torture_state *s,
@@ -611,6 +616,112 @@
*state = s;
}
+/**
+ * @brief Create a libssh server configuration file
+ *
+ * It is expected the socket directory to be already created before by calling
+ * torture_setup_socket_dir(). The created configuration file will be stored in
+ * the socket directory and the srv_config pointer in the state will be
+ * initialized.
+ *
+ * @param[in] state A pointer to a pointer to an initialized torture_state
+ * structure
+ */
+void torture_setup_create_libssh_config(void **state)
+{
+ struct torture_state *s = *state;
+ char ed25519_hostkey[1024] = {0};
+#ifdef HAVE_DSA
+ char dsa_hostkey[1024];
+#endif /* HAVE_DSA */
+ char rsa_hostkey[1024];
+ char ecdsa_hostkey[1024];
+ char sshd_config[2048];
+ char sshd_path[1024];
+ const char *additional_config = NULL;
+ struct stat sb;
+ const char config_string[]=
+ "LogLevel DEBUG3\n"
+ "Port 22\n"
+ "ListenAddress 127.0.0.10\n"
+ "%s %s\n"
+ "%s %s\n"
+ "%s %s\n"
+#ifdef HAVE_DSA
+ "%s %s\n"
+#endif /* HAVE_DSA */
+ "%s\n"; /* The space for test-specific options */
+ bool written = false;
+ int rc;
+
+ assert_non_null(s->socket_dir);
+
+ snprintf(sshd_path,
+ sizeof(sshd_path),
+ "%s/sshd",
+ s->socket_dir);
+
+ rc = lstat(sshd_path, &sb);
+ if (rc == 0 ) { /* The directory is already in place */
+ written = true;
+ }
+
+ if (!written) {
+ rc = mkdir(sshd_path, 0755);
+ assert_return_code(rc, errno);
+ }
+
+ snprintf(ed25519_hostkey,
+ sizeof(ed25519_hostkey),
+ "%s/sshd/ssh_host_ed25519_key",
+ s->socket_dir);
+
+ snprintf(rsa_hostkey,
+ sizeof(rsa_hostkey),
+ "%s/sshd/ssh_host_rsa_key",
+ s->socket_dir);
+
+ snprintf(ecdsa_hostkey,
+ sizeof(ecdsa_hostkey),
+ "%s/sshd/ssh_host_ecdsa_key",
+ s->socket_dir);
+
+#ifdef HAVE_DSA
+ snprintf(dsa_hostkey,
+ sizeof(dsa_hostkey),
+ "%s/sshd/ssh_host_dsa_key",
+ s->socket_dir);
+#endif /* HAVE_DSA */
+
+ if (!written) {
+ torture_write_file(ed25519_hostkey,
+ torture_get_openssh_testkey(SSH_KEYTYPE_ED25519, 0));
+ torture_write_file(rsa_hostkey,
+ torture_get_testkey(SSH_KEYTYPE_RSA, 0));
+ torture_write_file(ecdsa_hostkey,
+ torture_get_testkey(SSH_KEYTYPE_ECDSA_P521, 0));
+#ifdef HAVE_DSA
+ torture_write_file(dsa_hostkey,
+ torture_get_testkey(SSH_KEYTYPE_DSS, 0));
+#endif /* HAVE_DSA */
+ }
+
+ additional_config = (s->srv_additional_config != NULL ?
+ s->srv_additional_config : "");
+
+ snprintf(sshd_config, sizeof(sshd_config),
+ config_string,
+ "HostKey", ed25519_hostkey,
+ "HostKey", rsa_hostkey,
+ "HostKey", ecdsa_hostkey,
+#ifdef HAVE_DSA
+ "HostKey", dsa_hostkey,
+#endif /* HAVE_DSA */
+ additional_config);
+
+ torture_write_file(s->srv_config, sshd_config);
+}
+
static void torture_setup_create_sshd_config(void **state, bool pam)
{
struct torture_state *s = *state;
@@ -856,21 +967,140 @@
return 1;
}
-void torture_setup_sshd_server(void **state, bool pam)
+/**
+ * @brief Run a libssh based server under timeout.
+ *
+ * It is expected that the socket directory and libssh configuration file were
+ * already created before by calling torture_setup_socket_dir() and
+ * torture_setup_create_libssh_config() (or alternatively setup the state with
+ * the correct values).
+ *
+ * @param[in] state The content of the address pointed by this variable must be
+ * a pointer to an initialized instance of torture_state
+ * structure; it can be obtained by calling
+ * torture_setup_socket_dir() and
+ * torture_setup_create_libssh_config().
+ * @param[in] server_path The path to the server executable.
+ *
+ * @note This function will use the state->srv_additional_config field as
+ * additional command line option used when starting the server instead of extra
+ * configuration file options.
+ * */
+void torture_setup_libssh_server(void **state, const char *server_path)
{
struct torture_state *s;
- char sshd_start_cmd[1024];
+ char start_cmd[1024];
+ char timeout_cmd[512];
+ char env[1024];
+ char extra_options[1024];
int rc;
+ char *ld_preload = NULL;
+ const char *force_fips = NULL;
- torture_setup_socket_dir(state);
- torture_setup_create_sshd_config(state, pam);
+ struct ssh_tokens_st *env_tokens;
+ struct ssh_tokens_st *arg_tokens;
+
+ pid_t pid;
+ ssize_t printed;
+
+ s = *state;
+
+ /* Get all the wrapper libraries to be pre-loaded */
+ ld_preload = getenv("LD_PRELOAD");
+
+ if (s->srv_additional_config != NULL) {
+ printed = snprintf(extra_options, sizeof(extra_options), " %s ",
+ s->srv_additional_config);
+ if (printed < 0) {
+ fail_msg("Failed to print additional config!");
+ }
+ } else {
+ printed = snprintf(extra_options, sizeof(extra_options), " ");
+ if (printed < 0) {
+ fail_msg("Failed to print empty additional config!");
+ }
+ }
+
+ if (ssh_fips_mode()) {
+ force_fips = "OPENSSL_FORCE_FIPS_MODE=1 ";
+ } else {
+ force_fips = "";
+ }
+
+ /* Write the environment setting */
+ printed = snprintf(env, sizeof(env),
+ "SOCKET_WRAPPER_DIR=%s "
+ "SOCKET_WRAPPER_DEFAULT_IFACE=10 "
+ "LD_PRELOAD=%s "
+ "%s",
+ s->socket_dir, ld_preload, force_fips);
+ if (printed < 0) {
+ fail_msg("Failed to print env!");
+ }
+
+#ifdef WITH_TIMEOUT
+ snprintf(timeout_cmd, sizeof(timeout_cmd),
+ "%s %s ", TIMEOUT_EXECUTABLE, "5m");
+#else
+ timeout_cmd[0] = '\0';
+#endif
+
+ /* Write the start command */
+ printed = snprintf(start_cmd, sizeof(start_cmd),
+ "%s"
+ "%s -f%s -v4 -p22 -i%s -C%s%s%s",
+ timeout_cmd,
+ server_path, s->pcap_file, s->srv_pidfile,
+ s->srv_config, extra_options, TORTURE_SSH_SERVER);
+ if (printed < 0) {
+ fail_msg("Failed to print start command!");
+ }
+
+ pid = fork();
+ switch(pid) {
+ case 0:
+ env_tokens = ssh_tokenize(env, ' ');
+ if (env_tokens == NULL || env_tokens->tokens == NULL) {
+ fail_msg("Failed to tokenize env!");
+ }
+
+ arg_tokens = ssh_tokenize(start_cmd, ' ');
+ if (arg_tokens == NULL || arg_tokens->tokens == NULL) {
+ ssh_tokens_free(env_tokens);
+ fail_msg("Failed to tokenize args!");
+ }
+
+ rc = execve(arg_tokens->tokens[0], (char **)arg_tokens->tokens,
+ (char **)env_tokens->tokens);
+
+ /* execve returns only in case of error */
+ ssh_tokens_free(env_tokens);
+ ssh_tokens_free(arg_tokens);
+ fail_msg("Error in execve: %s", strerror(errno));
+ case -1:
+ fail_msg("Failed to fork!");
+ default:
+ /* The parent continues the execution of the tests */
+ setenv("SOCKET_WRAPPER_DEFAULT_IFACE", "21", 1);
+ unsetenv("PAM_WRAPPER");
+
+ /* Wait until the server is ready to accept connections */
+ rc = torture_wait_for_daemon(15);
+ assert_int_equal(rc, 0);
+ break;
+ }
+}
+
+static int torture_start_sshd_server(void **state)
+{
+ struct torture_state *s = *state;
+ char sshd_start_cmd[1024];
+ int rc;
/* Set the default interface for the server */
setenv("SOCKET_WRAPPER_DEFAULT_IFACE", "10", 1);
setenv("PAM_WRAPPER", "1", 1);
- s = *state;
-
snprintf(sshd_start_cmd, sizeof(sshd_start_cmd),
SSHD_EXECUTABLE " -r -f %s -E %s/sshd/daemon.log 2> %s/sshd/cwrap.log",
s->srv_config, s->socket_dir, s->socket_dir);
@@ -882,7 +1112,20 @@
unsetenv("PAM_WRAPPER");
/* Wait until the sshd is ready to accept connections */
- rc = torture_wait_for_daemon(5);
+ rc = torture_wait_for_daemon(15);
+ assert_int_equal(rc, 0);
+
+ return SSH_OK;
+}
+
+void torture_setup_sshd_server(void **state, bool pam)
+{
+ int rc;
+
+ torture_setup_socket_dir(state);
+ torture_setup_create_sshd_config(state, pam);
+
+ rc = torture_start_sshd_server(state);
assert_int_equal(rc, 0);
}
@@ -922,29 +1165,12 @@
torture_reload_sshd_server(void **state)
{
struct torture_state *s = *state;
- pid_t pid;
int rc;
- /* read the pidfile */
- pid = torture_read_pidfile(s->srv_pidfile);
- assert_int_not_equal(pid, -1);
-
- kill(pid, SIGHUP);
-
- /* 10 ms */
- usleep(10 * 1000);
-
- rc = kill(pid, 0);
- if (rc != 0) {
- fprintf(stderr,
- "ERROR: SSHD process %u died during reload!\n", pid);
- return SSH_ERROR;
- }
+ rc = torture_terminate_process(s->srv_pidfile);
+ assert_return_code(rc, errno);
- /* Wait until the sshd is ready to accept connections */
- rc = torture_wait_for_daemon(5);
- assert_int_equal(rc, 0);
- return SSH_OK;
+ return torture_start_sshd_server(state);
}
/* @brief: Updates SSHD server configuration with more options and
@@ -980,9 +1206,7 @@
int rc;
rc = torture_terminate_process(s->srv_pidfile);
- if (rc != 0) {
- fprintf(stderr, "XXXXXX Failed to terminate sshd\n");
- }
+ assert_return_code(rc, errno);
torture_teardown_socket_dir(state);
}
diff --color -ru ../libssh-0.9.6/tests/torture.h ./tests/torture.h
--- ../libssh-0.9.6/tests/torture.h 2021-08-26 14:27:44.000000000 +0200
+++ ./tests/torture.h 2023-05-02 10:32:03.964511860 +0200
@@ -132,6 +132,10 @@
void torture_reset_config(ssh_session session);
+void torture_setup_create_libssh_config(void **state);
+
+void torture_setup_libssh_server(void **state, const char *server_path);
+
/*
* This function must be defined in every unit test file.
*/

View File

@ -1,16 +0,0 @@
-----BEGIN PGP SIGNATURE-----
iQIzBAABCgAdFiEEjf9T4Y8qvI2PPJIjfuD8TcwBTj0FAmEniOkACgkQfuD8TcwB
Tj0TKQ/9HiMAGSMHoQ+iPVLP06iTc6Cy7rNyON2nPDQwAz0V/dfvkrKAAEflfgYd
3pt3dbE/qgh2kgQLb9kpbCUmFoGuLgKz36RPOsggwuOsN+eD1n65q8W39sMOQid3
bjUIOKRdYWC1suZ9fMAO1Ignl69Opd8dAq1Has9YzglaeQaV/lnYQOW4UG0xKHck
ZOp2qLfjmaQiBAI61eRyxqIYC0F67WKd0bo9D2csoocDVvHLq4syPdbMOfDTB+LL
KZSAZVW1R1JUVZMkp/P/HU11jNNy3wKoLafocnq8bXkPVrqhyuo+hDJV/OPUvFLa
VE/BzIRoMNG+1R+GJpwE7ut2DIHPxnZTThRkeVN5qP1+hbhgLJhW62I+HeAnD4s+
+W7fwJovN28I+wqSjVEP8JguprVuoDAX5jVHbeZoMT7p8ATA4Nh3KCbYELEwTtFG
zsEIlBvoNXD3ce7xGXL3MPqfgKqrZQjRG/iOWvKwDV7WrqK1cFFyL7aeBfK2+dQq
1Ew7aYlTsH6Hap7XByeSsy4Z5ts3VXIoFix/h+Br5OTYKYgITM7bijNAQ6A2ZWQN
TxCv8X0sVyaGyXhxG6QhrEWZjFe496MneZkq9e6HKZyaSbzwFwMgOvrUUC7fa8e5
o1Rvozah81U0nsikwTmDrm15RSK3mr2X34zPW2Ahzr1I5tGZzOk=
=cO0k
-----END PGP SIGNATURE-----

View File

@ -1,19 +0,0 @@
diff --git a/src/packet.c b/src/packet.c
index ec4a7203..a81eb8e3 100644
--- a/src/packet.c
+++ b/src/packet.c
@@ -1752,10 +1752,12 @@ static bool
ssh_packet_in_rekey(ssh_session session)
{
/* We know we are rekeying if we are authenticated and the DH
- * status is not finished
+ * status is not finished, but we only queue packets until we've
+ * sent our NEWKEYS.
*/
return (session->flags & SSH_SESSION_FLAG_AUTHENTICATED) &&
- (session->dh_handshake_state != DH_STATE_FINISHED);
+ (session->dh_handshake_state != DH_STATE_FINISHED) &&
+ (session->dh_handshake_state != DH_STATE_NEWKEYS_SENT);
}
int ssh_packet_send(ssh_session session)

View File

@ -1,7 +1,7 @@
diff --color -ru ../libssh-0.9.6/src/pki_crypto.c ./src/pki_crypto.c
--- ../libssh-0.9.6/src/pki_crypto.c 2023-04-27 12:59:08.463259052 +0200
+++ ./src/pki_crypto.c 2023-04-27 13:05:24.020610873 +0200
@@ -2291,8 +2291,12 @@
diff --color -ru ../libssh-0.10.4/src/pki_crypto.c ./src/pki_crypto.c
--- ../libssh-0.10.4/src/pki_crypto.c 2023-04-27 13:24:03.105744519 +0200
+++ ./src/pki_crypto.c 2023-04-27 13:30:24.016756496 +0200
@@ -3186,8 +3186,12 @@
unsigned char *raw_sig_data = NULL;
unsigned int raw_sig_len;
@ -15,7 +15,7 @@ diff --color -ru ../libssh-0.9.6/src/pki_crypto.c ./src/pki_crypto.c
if (pubkey == NULL || ssh_key_is_private(pubkey) || input == NULL ||
signature == NULL || (signature->raw_sig == NULL
@@ -2307,8 +2311,8 @@
@@ -3202,8 +3206,8 @@
}
/* Check if public key and hash type are compatible */
@ -26,7 +26,7 @@ diff --color -ru ../libssh-0.9.6/src/pki_crypto.c ./src/pki_crypto.c
return SSH_ERROR;
}
@@ -2351,8 +2355,8 @@
@@ -3248,8 +3252,8 @@
}
/* Verify the signature */
@ -37,7 +37,7 @@ diff --color -ru ../libssh-0.9.6/src/pki_crypto.c ./src/pki_crypto.c
SSH_LOG(SSH_LOG_TRACE,
"EVP_DigestVerifyInit() failed: %s",
ERR_error_string(ERR_get_error(), NULL));
@@ -2360,35 +2364,31 @@
@@ -3257,32 +3261,30 @@
}
#ifdef HAVE_OPENSSL_EVP_DIGESTVERIFY
@ -76,11 +76,7 @@ diff --color -ru ../libssh-0.9.6/src/pki_crypto.c ./src/pki_crypto.c
- if (ctx != NULL) {
- EVP_MD_CTX_free(ctx);
- }
- if (pkey != NULL) {
- EVP_PKEY_free(pkey);
- }
+ EVP_MD_CTX_free(ctx);
+ EVP_PKEY_free(pkey);
EVP_PKEY_free(pkey);
return rc;
}

16
ci.fmf Normal file
View File

@ -0,0 +1,16 @@
summary: Upstreamed tier tests
discover:
# upstreamed tests (public)
- how: fmf
url: https://gitlab.com/redhat-crypto/tests/libssh.git
filter: 'tier: 0,1,2,3'
execute:
how: tmt
adjust:
# discover step adjustments
- when: distro = rhel
discover+:
# internal tests
- how: fmf
url: git://pkgs.devel.redhat.com/tests/libssh
filter: 'tier: 0,1,2,3'

23
coverity_scan.patch Normal file
View File

@ -0,0 +1,23 @@
diff --git a/src/dh_crypto.c b/src/dh_crypto.c
index a847c6a2..1eb94307 100644
--- a/src/dh_crypto.c
+++ b/src/dh_crypto.c
@@ -341,8 +341,16 @@ int ssh_dh_set_parameters(struct dh_ctx *ctx,
goto done;
}
- OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_P, modulus);
- OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_G, generator);
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_P, modulus);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto done;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_G, generator);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto done;
+ }
params = OSSL_PARAM_BLD_to_param(param_bld);
if (params == NULL) {
OSSL_PARAM_BLD_free(param_bld);

View File

@ -1,6 +1,6 @@
diff --color -ru ../libssh-0.9.6/src/buffer.c ./src/buffer.c
--- ../libssh-0.9.6/src/buffer.c 2023-05-03 11:53:48.710217753 +0200
+++ ./src/buffer.c 2023-05-03 11:58:21.995200990 +0200
diff --color -ru ../libssh-0.10.4/src/buffer.c ./src/buffer.c
--- ../libssh-0.10.4/src/buffer.c 2023-05-03 12:22:40.304114511 +0200
+++ ./src/buffer.c 2023-05-03 12:24:11.578110236 +0200
@@ -747,7 +747,8 @@
*/
int ssh_buffer_validate_length(struct ssh_buffer_struct *buffer, size_t len)
@ -11,10 +11,10 @@ diff --color -ru ../libssh-0.9.6/src/buffer.c ./src/buffer.c
return SSH_ERROR;
}
diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
--- ../libssh-0.9.6/src/gssapi.c 2023-05-03 11:53:48.732217993 +0200
+++ ./src/gssapi.c 2023-05-03 11:58:21.976200782 +0200
@@ -437,11 +437,18 @@
diff --color -ru ../libssh-0.10.4/src/gssapi.c ./src/gssapi.c
--- ../libssh-0.10.4/src/gssapi.c 2023-05-03 12:22:40.356115078 +0200
+++ ./src/gssapi.c 2023-05-03 12:24:11.566110105 +0200
@@ -444,11 +444,18 @@
hexa = ssh_get_hexa(output_token.value, output_token.length);
SSH_LOG(SSH_LOG_PACKET, "GSSAPI: sending token %s",hexa);
SAFE_FREE(hexa);
@ -38,7 +38,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_packet_send(session);
}
@@ -846,6 +853,7 @@
@@ -857,6 +864,7 @@
}
SSH_PACKET_CALLBACK(ssh_packet_userauth_gssapi_response){
@ -46,7 +46,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_string oid_s;
gss_uint32 maj_stat, min_stat;
gss_buffer_desc input_token = GSS_C_EMPTY_BUFFER;
@@ -897,11 +905,15 @@
@@ -908,11 +916,15 @@
hexa = ssh_get_hexa(output_token.value, output_token.length);
SSH_LOG(SSH_LOG_PACKET, "GSSAPI: sending token %s", hexa);
SAFE_FREE(hexa);
@ -67,7 +67,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_packet_send(session);
session->auth.state = SSH_AUTH_STATE_GSSAPI_TOKEN;
}
@@ -963,6 +975,7 @@
@@ -975,6 +987,7 @@
}
SSH_PACKET_CALLBACK(ssh_packet_userauth_gssapi_token_client){
@ -75,7 +75,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_string token;
char *hexa;
OM_uint32 maj_stat, min_stat;
@@ -1015,11 +1028,15 @@
@@ -1027,11 +1040,15 @@
hexa = ssh_get_hexa(output_token.value, output_token.length);
SSH_LOG(SSH_LOG_PACKET, "GSSAPI: sending token %s",hexa);
SAFE_FREE(hexa);
@ -96,10 +96,10 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_packet_send(session);
}
diff --color -ru ../libssh-0.9.6/src/options.c ./src/options.c
--- ../libssh-0.9.6/src/options.c 2021-08-26 14:27:42.000000000 +0200
+++ ./src/options.c 2023-05-03 11:58:22.000201044 +0200
@@ -547,7 +547,9 @@
diff --color -ru ../libssh-0.10.4/src/options.c ./src/options.c
--- ../libssh-0.10.4/src/options.c 2023-05-03 12:22:40.342114926 +0200
+++ ./src/options.c 2023-05-03 12:24:11.582110280 +0200
@@ -614,7 +614,9 @@
}
i = strtol(q, &p, 10);
if (q == p) {
@ -109,7 +109,7 @@ diff --color -ru ../libssh-0.9.6/src/options.c ./src/options.c
}
SAFE_FREE(q);
if (i <= 0) {
@@ -743,7 +745,9 @@
@@ -816,7 +818,9 @@
}
i = strtol(q, &p, 10);
if (q == p) {
@ -119,7 +119,7 @@ diff --color -ru ../libssh-0.9.6/src/options.c ./src/options.c
}
SAFE_FREE(q);
if (i < 0) {
@@ -1818,7 +1822,9 @@
@@ -2035,7 +2039,9 @@
}
i = strtol(q, &p, 10);
if (q == p) {
@ -130,7 +130,7 @@ diff --color -ru ../libssh-0.9.6/src/options.c ./src/options.c
}
SAFE_FREE(q);
@@ -1845,7 +1851,9 @@
@@ -2062,7 +2068,9 @@
}
i = strtol(q, &p, 10);
if (q == p) {
@ -141,9 +141,9 @@ diff --color -ru ../libssh-0.9.6/src/options.c ./src/options.c
}
SAFE_FREE(q);
diff --color -ru ../libssh-0.9.6/src/pki_container_openssh.c ./src/pki_container_openssh.c
--- ../libssh-0.9.6/src/pki_container_openssh.c 2023-05-03 11:53:48.713217785 +0200
+++ ./src/pki_container_openssh.c 2023-05-03 11:58:21.976200782 +0200
diff --color -ru ../libssh-0.10.4/src/pki_container_openssh.c ./src/pki_container_openssh.c
--- ../libssh-0.10.4/src/pki_container_openssh.c 2023-05-03 12:22:40.314114620 +0200
+++ ./src/pki_container_openssh.c 2023-05-03 12:24:11.566110105 +0200
@@ -630,7 +630,11 @@
goto error;
}
@ -157,10 +157,10 @@ diff --color -ru ../libssh-0.9.6/src/pki_container_openssh.c ./src/pki_container
kdf_options = ssh_string_new(ssh_buffer_get_len(kdf_buf));
if (kdf_options == NULL){
SSH_BUFFER_FREE(kdf_buf);
diff --color -ru ../libssh-0.9.6/tests/unittests/torture_options.c ./tests/unittests/torture_options.c
--- ../libssh-0.9.6/tests/unittests/torture_options.c 2021-08-26 14:27:42.000000000 +0200
+++ ./tests/unittests/torture_options.c 2023-05-03 11:59:21.726853027 +0200
@@ -311,6 +311,7 @@
diff --color -ru ../libssh-0.10.4/tests/unittests/torture_options.c ./tests/unittests/torture_options.c
--- ../libssh-0.10.4/tests/unittests/torture_options.c 2023-05-03 12:22:40.343114937 +0200
+++ ./tests/unittests/torture_options.c 2023-05-03 12:24:11.587110335 +0200
@@ -319,6 +319,7 @@
rc = ssh_options_set(session, SSH_OPTIONS_PORT_STR, "five");
assert_true(rc == -1);
@ -168,8 +168,8 @@ diff --color -ru ../libssh-0.9.6/tests/unittests/torture_options.c ./tests/unitt
rc = ssh_options_set(session, SSH_OPTIONS_PORT, NULL);
assert_true(rc == -1);
@@ -853,6 +854,26 @@
ssh_free(new);
@@ -1496,6 +1497,26 @@
ssh_list_free(awaited_list);
}
+static void torture_options_set_verbosity (void **state)
@ -195,7 +195,7 @@ diff --color -ru ../libssh-0.9.6/tests/unittests/torture_options.c ./tests/unitt
#ifdef WITH_SERVER
const char template[] = "temp_dir_XXXXXX";
@@ -1107,6 +1128,10 @@
@@ -1750,6 +1771,10 @@
rc = ssh_bind_options_set(bind, SSH_BIND_OPTIONS_BINDPORT_STR, "23");
assert_int_equal(rc, 0);
assert_int_equal(bind->bindport, 23);
@ -206,7 +206,7 @@ diff --color -ru ../libssh-0.9.6/tests/unittests/torture_options.c ./tests/unitt
}
static void torture_bind_options_log_verbosity(void **state)
@@ -1156,6 +1181,11 @@
@@ -1799,6 +1824,11 @@
new_level = ssh_get_log_level();
assert_int_equal(new_level, SSH_LOG_PACKET);
@ -218,10 +218,10 @@ diff --color -ru ../libssh-0.9.6/tests/unittests/torture_options.c ./tests/unitt
rc = ssh_set_log_level(previous_level);
assert_int_equal(rc, SSH_OK);
}
@@ -1643,6 +1673,7 @@
cmocka_unit_test_setup_teardown(torture_options_config_host, setup, teardown),
cmocka_unit_test_setup_teardown(torture_options_config_match,
@@ -2297,6 +2327,7 @@
cmocka_unit_test_setup_teardown(torture_options_caret_sign,
setup, teardown),
cmocka_unit_test_setup_teardown(torture_options_apply, setup, teardown),
+ cmocka_unit_test_setup_teardown(torture_options_set_verbosity, setup, teardown),
};

57
covscan23_1.patch Normal file
View File

@ -0,0 +1,57 @@
File ../libssh-0.10.4/.git is a regular file while file ./.git is a directory
diff --color -ru ../libssh-0.10.4/src/sftp.c ./src/sftp.c
--- ../libssh-0.10.4/src/sftp.c 2023-05-22 12:45:48.383509085 +0200
+++ ./src/sftp.c 2023-05-22 12:54:31.004037650 +0200
@@ -1755,6 +1755,10 @@
int sftp_close(sftp_file file){
int err = SSH_NO_ERROR;
+ if (file == NULL) {
+ return err;
+ }
+
SAFE_FREE(file->name);
if (file->handle){
err = sftp_handle_close(file->sftp,file->handle);
@@ -1917,7 +1921,7 @@
/* Read from a file using an opened sftp file handle. */
ssize_t sftp_read(sftp_file handle, void *buf, size_t count) {
- sftp_session sftp = handle->sftp;
+ sftp_session sftp;
sftp_message msg = NULL;
sftp_status_message status;
ssh_string datastring;
@@ -1926,6 +1930,11 @@
uint32_t id;
int rc;
+ if (handle == NULL) {
+ return -1;
+ }
+ sftp = handle->sftp;
+
if (handle->eof) {
return 0;
}
@@ -2147,7 +2156,7 @@
}
ssize_t sftp_write(sftp_file file, const void *buf, size_t count) {
- sftp_session sftp = file->sftp;
+ sftp_session sftp;
sftp_message msg = NULL;
sftp_status_message status;
ssh_buffer buffer;
@@ -2156,6 +2165,11 @@
size_t packetlen;
int rc;
+ if (file == NULL) {
+ return -1;
+ }
+ sftp = file->sftp;
+
buffer = ssh_buffer_new();
if (buffer == NULL) {
ssh_set_error_oom(sftp->session);

View File

@ -0,0 +1,105 @@
diff --git a/src/kex.c b/src/kex.c
index 1155b9c7..528cb182 100644
--- a/src/kex.c
+++ b/src/kex.c
@@ -101,12 +101,19 @@
#ifdef HAVE_ECDH
#define ECDH "ecdh-sha2-nistp256,ecdh-sha2-nistp384,ecdh-sha2-nistp521,"
-#define EC_HOSTKEYS "ecdsa-sha2-nistp521,ecdsa-sha2-nistp384,ecdsa-sha2-nistp256,"
-#define EC_PUBLIC_KEY_ALGORITHMS "ecdsa-sha2-nistp521-cert-v01@openssh.com," \
+#define EC_HOSTKEYS "ecdsa-sha2-nistp521," \
+ "ecdsa-sha2-nistp384," \
+ "ecdsa-sha2-nistp256,"
+#define EC_SK_HOSTKEYS "sk-ecdsa-sha2-nistp256@openssh.com,"
+#define EC_FIPS_PUBLIC_KEY_ALGOS "ecdsa-sha2-nistp521-cert-v01@openssh.com," \
"ecdsa-sha2-nistp384-cert-v01@openssh.com," \
"ecdsa-sha2-nistp256-cert-v01@openssh.com,"
+#define EC_PUBLIC_KEY_ALGORITHMS EC_FIPS_PUBLIC_KEY_ALGOS \
+ "sk-ecdsa-sha2-nistp256-cert-v01@openssh.com,"
#else
#define EC_HOSTKEYS ""
+#define EC_SK_HOSTKEYS ""
+#define EC_FIPS_PUBLIC_KEY_ALGOS ""
#define EC_PUBLIC_KEY_ALGORITHMS ""
#define ECDH ""
#endif /* HAVE_ECDH */
@@ -127,16 +134,21 @@
#define HOSTKEYS "ssh-ed25519," \
EC_HOSTKEYS \
+ "sk-ssh-ed25519@openssh.com," \
+ EC_SK_HOSTKEYS \
"rsa-sha2-512," \
"rsa-sha2-256," \
"ssh-rsa" \
DSA_HOSTKEYS
#define DEFAULT_HOSTKEYS "ssh-ed25519," \
EC_HOSTKEYS \
+ "sk-ssh-ed25519@openssh.com," \
+ EC_SK_HOSTKEYS \
"rsa-sha2-512," \
"rsa-sha2-256"
#define PUBLIC_KEY_ALGORITHMS "ssh-ed25519-cert-v01@openssh.com," \
+ "sk-ssh-ed25519-cert-v01@openssh.com," \
EC_PUBLIC_KEY_ALGORITHMS \
"rsa-sha2-512-cert-v01@openssh.com," \
"rsa-sha2-256-cert-v01@openssh.com," \
@@ -186,7 +198,7 @@
"rsa-sha2-512," \
"rsa-sha2-256"
-#define FIPS_ALLOWED_PUBLIC_KEY_ALGORITHMS EC_PUBLIC_KEY_ALGORITHMS \
+#define FIPS_ALLOWED_PUBLIC_KEY_ALGORITHMS EC_FIPS_PUBLIC_KEY_ALGOS \
"rsa-sha2-512-cert-v01@openssh.com," \
"rsa-sha2-256-cert-v01@openssh.com," \
FIPS_ALLOWED_HOSTKEYS
diff --git a/src/knownhosts.c b/src/knownhosts.c
index 1f52dedc..94618fe2 100644
--- a/src/knownhosts.c
+++ b/src/knownhosts.c
@@ -480,6 +480,8 @@ static const char *ssh_known_host_sigs_from_hostkey_type(enum ssh_keytypes_e typ
return "rsa-sha2-512,rsa-sha2-256,ssh-rsa";
case SSH_KEYTYPE_ED25519:
return "ssh-ed25519";
+ case SSH_KEYTYPE_SK_ED25519:
+ return "sk-ssh-ed25519@openssh.com";
#ifdef HAVE_DSA
case SSH_KEYTYPE_DSS:
return "ssh-dss";
@@ -494,6 +496,8 @@ static const char *ssh_known_host_sigs_from_hostkey_type(enum ssh_keytypes_e typ
return "ecdsa-sha2-nistp384";
case SSH_KEYTYPE_ECDSA_P521:
return "ecdsa-sha2-nistp521";
+ case SSH_KEYTYPE_SK_ECDSA:
+ return "sk-ecdsa-sha2-nistp256@openssh.com";
#else
case SSH_KEYTYPE_ECDSA_P256:
case SSH_KEYTYPE_ECDSA_P384:
diff --git a/tests/unittests/torture_knownhosts_parsing.c b/tests/unittests/torture_knownhosts_parsing.c
index fffa8296..7fd21f05 100644
--- a/tests/unittests/torture_knownhosts_parsing.c
+++ b/tests/unittests/torture_knownhosts_parsing.c
@@ -634,7 +634,9 @@ static void torture_knownhosts_algorithms(void **state)
bool process_config = false;
const char *expect = "ssh-ed25519,rsa-sha2-512,rsa-sha2-256,"
"ecdsa-sha2-nistp521,ecdsa-sha2-nistp384,"
- "ecdsa-sha2-nistp256";
+ "ecdsa-sha2-nistp256,"
+ "sk-ssh-ed25519@openssh.com,"
+ "sk-ecdsa-sha2-nistp256@openssh.com";
const char *expect_fips = "rsa-sha2-512,rsa-sha2-256,ecdsa-sha2-nistp521,"
"ecdsa-sha2-nistp384,ecdsa-sha2-nistp256";
@@ -669,7 +671,9 @@ static void torture_knownhosts_algorithms_global(void **state)
bool process_config = false;
const char *expect = "ssh-ed25519,rsa-sha2-512,rsa-sha2-256,"
"ecdsa-sha2-nistp521,ecdsa-sha2-nistp384,"
- "ecdsa-sha2-nistp256";
+ "ecdsa-sha2-nistp256,"
+ "sk-ssh-ed25519@openssh.com,"
+ "sk-ecdsa-sha2-nistp256@openssh.com";
const char *expect_fips = "rsa-sha2-512,rsa-sha2-256,ecdsa-sha2-nistp521,"
"ecdsa-sha2-nistp384,ecdsa-sha2-nistp256";

View File

@ -0,0 +1,94 @@
From bccb8513fa4a836aef0519d65eb33bb212606fe1 Mon Sep 17 00:00:00 2001
From: Thomas Baag <libssh-git@spam.b2ag.de>
Date: Wed, 21 Sep 2022 20:55:27 +0200
Subject: [PATCH] config: Escape brackets in ProxyCommand build from ProxyJump
Missing escaping results in syntax errors in Zsh shell because of square
brackets getting interpreted as being a pattern for globbing.
Signed-off-by: Thomas Baag <libssh-git@spam.b2ag.de>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
src/config.c | 2 +-
tests/unittests/torture_config.c | 14 +++++++-------
2 files changed, 8 insertions(+), 8 deletions(-)
diff --git a/src/config.c b/src/config.c
index c048418ec..308928429 100644
--- a/src/config.c
+++ b/src/config.c
@@ -491,7 +491,7 @@ ssh_config_parse_proxy_jump(ssh_session session, const char *s, bool do_parsing)
if (hostname != NULL && do_parsing) {
char com[512] = {0};
- rv = snprintf(com, sizeof(com), "ssh%s%s%s%s%s%s -W [%%h]:%%p %s",
+ rv = snprintf(com, sizeof(com), "ssh%s%s%s%s%s%s -W '[%%h]:%%p' %s",
username ? " -l " : "",
username ? username : "",
port ? " -p " : "",
diff --git a/tests/unittests/torture_config.c b/tests/unittests/torture_config.c
index 31dadae37..5ff20c99a 100644
--- a/tests/unittests/torture_config.c
+++ b/tests/unittests/torture_config.c
@@ -649,7 +649,7 @@ static void torture_config_unknown(void **state,
/* test corner cases */
_parse_config(session, file, string, SSH_OK);
assert_string_equal(session->opts.ProxyCommand,
- "ssh -W [%h]:%p many-spaces.com");
+ "ssh -W '[%h]:%p' many-spaces.com");
assert_string_equal(session->opts.host, "equal.sign");
ret = ssh_config_parse_file(session, "/etc/ssh/ssh_config");
@@ -945,28 +945,28 @@ static void torture_config_proxyjump(void **state,
torture_reset_config(session);
ssh_options_set(session, SSH_OPTIONS_HOST, "simple");
_parse_config(session, file, string, SSH_OK);
- assert_string_equal(session->opts.ProxyCommand, "ssh -W [%h]:%p jumpbox");
+ assert_string_equal(session->opts.ProxyCommand, "ssh -W '[%h]:%p' jumpbox");
/* With username */
torture_reset_config(session);
ssh_options_set(session, SSH_OPTIONS_HOST, "user");
_parse_config(session, file, string, SSH_OK);
assert_string_equal(session->opts.ProxyCommand,
- "ssh -l user -W [%h]:%p jumpbox");
+ "ssh -l user -W '[%h]:%p' jumpbox");
/* With port */
torture_reset_config(session);
ssh_options_set(session, SSH_OPTIONS_HOST, "port");
_parse_config(session, file, string, SSH_OK);
assert_string_equal(session->opts.ProxyCommand,
- "ssh -p 2222 -W [%h]:%p jumpbox");
+ "ssh -p 2222 -W '[%h]:%p' jumpbox");
/* Two step jump */
torture_reset_config(session);
ssh_options_set(session, SSH_OPTIONS_HOST, "two-step");
_parse_config(session, file, string, SSH_OK);
assert_string_equal(session->opts.ProxyCommand,
- "ssh -l u1 -p 222 -J u2@second:33 -W [%h]:%p first");
+ "ssh -l u1 -p 222 -J u2@second:33 -W '[%h]:%p' first");
/* none */
torture_reset_config(session);
@@ -985,14 +985,14 @@ static void torture_config_proxyjump(void **state,
ssh_options_set(session, SSH_OPTIONS_HOST, "only-jump");
_parse_config(session, file, string, SSH_OK);
assert_string_equal(session->opts.ProxyCommand,
- "ssh -W [%h]:%p jumpbox");
+ "ssh -W '[%h]:%p' jumpbox");
/* IPv6 address */
torture_reset_config(session);
ssh_options_set(session, SSH_OPTIONS_HOST, "ipv6");
_parse_config(session, file, string, SSH_OK);
assert_string_equal(session->opts.ProxyCommand,
- "ssh -W [%h]:%p 2620:52:0::fed");
+ "ssh -W '[%h]:%p' 2620:52:0::fed");
/* Multiple @ is allowed in second jump */
config = "Host allowed-hostname\n"
--
GitLab

25
gating.yaml Normal file
View File

@ -0,0 +1,25 @@
--- !Policy
product_versions:
- fedora-*
decision_context: bodhi_update_push_testing
subject_type: koji_build
rules:
- !PassingTestCaseRule {test_case_name: fedora-ci.koji-build.tier0.functional}
--- !Policy
product_versions:
- fedora-*
decision_context: bodhi_update_push_stable
subject_type: koji_build
rules:
- !PassingTestCaseRule {test_case_name: fedora-ci.koji-build.tier0.functional}
--- !Policy
product_versions:
- rhel-9
decision_context: osci_compose_gate
rules:
- !PassingTestCaseRule {test_case_name: baseos-ci.brew-build.tier1.functional}
- !PassingTestCaseRule {test_case_name: baseos-ci.brew-build.userspace-fips-mode.functional}
- !PassingTestCaseRule {test_case_name: osci.brew-build.tier0.functional}
- !PassingTestCaseRule {test_case_name: baseos-ci.brew-build.tedude.validation}

BIN
libssh.keyring Normal file

Binary file not shown.

View File

@ -1,54 +1,61 @@
Name: libssh
Version: 0.9.6
Release: 14%{?dist}
Version: 0.10.4
Release: 13%{?dist}
Summary: A library implementing the SSH protocol
License: LGPLv2+
URL: http://www.libssh.org
Source0: https://www.libssh.org/files/0.9/%{name}-%{version}.tar.xz
Source1: https://www.libssh.org/files/0.9/%{name}-%{version}.tar.xz.asc
Source0: https://www.libssh.org/files/0.10/%{name}-%{version}.tar.xz
Source1: https://www.libssh.org/files/0.10/%{name}-%{version}.tar.xz.asc
Source2: https://cryptomilk.org/gpgkey-8DFF53E18F2ABC8D8F3C92237EE0FC4DCC014E3D.gpg#/%{name}.keyring
Source3: libssh_client.config
Source4: libssh_server.config
Patch0: loglevel.patch
Patch1: s390x_fix.patch
Patch2: null_dereference_rekey.patch
Patch3: auth_bypass.patch
Patch4: fix_tests.patch
Patch5: covscan23.patch
Patch6: CVE-2023-48795.patch
Patch7: CVE-2023-6004.patch
Patch8: CVE-2023-6918.patch
BuildRequires: cmake
BuildRequires: doxygen
BuildRequires: gcc-c++
BuildRequires: gnupg2
BuildRequires: openssl-devel
BuildRequires: openssl-pkcs11
BuildRequires: pkgconfig
BuildRequires: zlib-devel
BuildRequires: krb5-devel
BuildRequires: libcmocka-devel
BuildRequires: openssh-clients
BuildRequires: openssh-server
BuildRequires: pam_wrapper
BuildRequires: socket_wrapper
BuildRequires: nss_wrapper
BuildRequires: uid_wrapper
BuildRequires: openssh-clients
BuildRequires: openssh-server
BuildRequires: nmap-ncat
BuildRequires: softhsm
BuildRequires: gnutls-utils
Requires: crypto-policies
Requires: %{name}-config = %{version}-%{release}
Requires: crypto-policies
%ifarch aarch64 ppc64 ppc64le s390x x86_64
Provides: libssh_threads.so()(64bit)
Provides: libssh_threads.so.4()(64bit)
%else
Provides: libssh_threads.so
Provides: libssh_threads.so.4
%endif
Patch1: coverity_scan.patch
Patch2: pkcs11_test_fix.patch
Patch3: loglevel.patch
Patch4: plus_sign.patch
Patch5: memory_leak.patch
Patch6: options_apply.patch
Patch7: enable_sk_keys_by_config.patch
Patch8: null_dereference_rekey.patch
Patch9: auth_bypass.patch
Patch10: covscan23.patch
Patch11: rekey_test_fixup.patch
Patch12: covscan23_1.patch
Patch13: CVE-2023-6004.patch
Patch14: CVE-2023-48795.patch
Patch15: CVE-2023-6918.patch
Patch16: escape-brackets-in-proxycommand.patch
%description
The ssh library was designed to be used by programmers needing a working SSH
implementation by the mean of a library. The complete control of the client is
@ -68,7 +75,7 @@ applications that use %{name}.
%package config
Summary: Configuration files for %{name}
BuildArch: noarch
Obsoletes: %{name} < 0.9.0-1
Obsoletes: %{name} < 0.9.0-3
%description config
The %{name}-config package provides the default configuration files for %{name}.
@ -78,26 +85,18 @@ gpgv2 --quiet --keyring %{SOURCE2} %{SOURCE1} %{SOURCE0}
%autosetup -p1
%build
if test ! -e "obj"; then
mkdir obj
fi
pushd obj
%cmake .. \
%cmake \
-DUNIT_TESTING=ON \
-DCLIENT_TESTING=ON \
-DSERVER_TESTING=ON \
-DWITH_PKCS11_URI=ON \
-DGLOBAL_CLIENT_CONFIG="%{_sysconfdir}/libssh/libssh_client.config" \
-DGLOBAL_BIND_CONFIG="%{_sysconfdir}/libssh/libssh_server.config"
%make_build VERBOSE=1
make docs
popd
%cmake_build
%install
make DESTDIR=%{buildroot} install/fast -C obj
%cmake_install
install -d -m755 %{buildroot}%{_sysconfdir}/libssh
install -m644 %{SOURCE3} %{buildroot}%{_sysconfdir}/libssh/libssh_client.config
install -m644 %{SOURCE4} %{buildroot}%{_sysconfdir}/libssh/libssh_server.config
@ -109,7 +108,7 @@ install -m644 %{SOURCE4} %{buildroot}%{_sysconfdir}/libssh/libssh_server.config
# requiring it to continue working.
#
pushd %{buildroot}%{_libdir}
for i in libssh.so.4*;
for i in libssh.so*;
do
_target="${i}"
_link_name="${i%libssh*}libssh_threads${i##*libssh}"
@ -123,24 +122,24 @@ popd
%ldconfig_scriptlets
%check
pushd obj
ctest --output-on-failure
popd
# Tests are randomly failing when run in parallel
%global _smp_build_ncpus 1
%ctest
%files
%doc AUTHORS BSD ChangeLog README
%doc AUTHORS BSD CHANGELOG README
%license COPYING
%{_libdir}/libssh.so.4*
%{_libdir}/libssh_threads.so.4*
%files devel
%doc obj/doc/html
%{_includedir}/libssh/
# own this to avoid dep on cmake -- rex
%dir %{_libdir}/cmake/
%{_libdir}/cmake/libssh/
%{_libdir}/pkgconfig/libssh.pc
%{_libdir}/libssh.so
%{_libdir}/libssh_threads.so
%files config
%attr(0755,root,root) %dir %{_sysconfdir}/libssh
@ -148,168 +147,233 @@ popd
%attr(0644,root,root) %config(noreplace) %{_sysconfdir}/libssh/libssh_server.config
%changelog
* Mon Feb 26 2024 Sahana Prasad <sahana@redhat.com> - 0.9.6-14
* Mon Feb 19 2024 Sahana Prasad <sahana@redhat.com> - 0.10.4-13
- Bump up the version so that the version in 9.3 is lower.
- Resolves: RHEL-19310, RHEL-19691, RHEL-17245
* Tue Jan 09 2024 Sahana Prasad <sahana@redhat.com> - 0.10.4-12
- Fix CVE-2023-48795 Prefix truncation attack on Binary Packet Protocol (BPP)
- Fix CVE-2023-6918 Missing checks for return values for digests
- Fix CVE-2023-6004 ProxyCommand/ProxyJump features allow injection
of malicious code through hostname
- Note: version is bumped from 12 to 14 directly, as the z-stream
version in 8.9 also has 13. So bumping it to 14, will prevent
upgrade conflicts.
- Resolves:RHEL-19690, RHEL-17244, RHEL-19312
- Resolves: RHEL-19310, RHEL-19691, RHEL-17245
* Mon May 15 2023 Norbert Pocs <npocs@redhat.com> - 0.9.6-12
* Wed Jun 21 2023 Norbert Pocs <npocs@redhat.com> - 0.10.4-11
- Fix loglevel regression
- Related: rhbz#2182251, rhbz#2189742
- Related: rhbz#2182252, rhbz#2189740
* Thu May 04 2023 Norbert Pocs <npocs@redhat.com> - 0.9.6-11
- .fmf/version is needed to run the tests
- Related: rhbz#2182251, rhbz#2189742
* Mon May 22 2023 Norbert Pocs <npocs@redhat.com> - 0.10.4.10
- Fix null dereference issues found by covscan
- Related: rhbz#2182252, rhbz#2189740
* Wed May 03 2023 Norbert Pocs <npocs@redhat.com> - 0.9.6-10
- Add missing ci.fmf file
- Related: rhbz#2182251, rhbz#2189742
* Wed May 10 2023 Norbert Pocs <npocs@redhat.com> - 0.10.4-9
- Fix CVE-2023-1667 and CVE-2023-2283
- Fix issues found by cosvcan
- Resolves: rhbz#2182252, rhbz#2189740
* Wed May 03 2023 Norbert Pocs <npocs@redhat.com> - 0.9.6-9
- Fix covscan errors found at gating
- Related: rhbz#2182251, rhbz#2189742
* Mon Jan 23 2023 Stanislav Zidek <szidek@redhat.com> - 0.10.4-8
+ libssh-0.10.4-8
- Extended CI to run internal tests in RHEL
- Related: rhbz#2160080
* Tue May 02 2023 Norbert Pocs <npocs@redhat.com> - 0.9.6-8
- Backport test fixing commits to make the build pass
- Related: rhbz#2182251, rhbz#2189742
* Wed Jan 4 2023 Norbert Pocs <npocs@redhat.com> - 0.10.4-7
- Add sk-keys to configuration parsing allowing to turn on-off by config
- Related: rhbz#2026449
* Thu Apr 27 2023 Norbert Pocs <npocs@redhat.com> - 0.9.6-7
- Fix NULL dereference during rekeying with algorithm guessing
GHSL-2023-032 / CVE-2023-1667
- Fix possible authentication bypass
GHSL 2023-085 / CVE-2023-2283
- Resolves: rhbz#2182251, rhbz#2189742
* Thu Dec 1 2022 Norbert Pocs <npocs@redhat.com> - 0.10.4-6
- Fix covscan error
- Remove unwanted test with yet unimplemented feature
- Related: rhbz#2137839, rhbz#2136824
* Fri Jan 06 2023 Norbert Pocs <npocs@redhat.com> - 0.9.6-6
- Enable client and server testing build time
- Fix failing rekey test on arch s390x
- Resolves: rhbz#2126342
* Thu Dec 01 2022 Stanislav Zidek <szidek@redhat.com> - 0.10.4-5
+ libssh-0.10.4-5
- Fixed CI configuration due to TMT changes
* Mon Dec 05 2022 Stanislav Zidek <szidek@redhat.com> - 0.9.6-5
- Fix CI configuration for new TMT
- Resolves: rhbz#2149910
* Wed Nov 30 2022 Norbert Pocs <npocs@redhat.com> - 0.10.4-4
- Move loglevel closer to openssh loglevel
- Add openssh config feature of +,-,^ for algorithm lists
- Fix memory leaks of bignum
- Prevent multiple expansion of escape characters
- Resolves: rhbz#2132407, rhbz#2137839, rhbz#2144795, rhbz#2136824
* Mon Nov 28 2022 Norbert Pocs <npocs@redhat.com> - 0.9.6-4
- Make VERBOSE and lower log levels less verbose
- Resolves: rhbz#2091512
* Tue Oct 4 2022 Norbert Pocs <npocs@redhat.com> - 0.10.4-3
- Enable pkcs11 support
- Fix broken libsofthsm path on i686
- Add missing bugzilla references from the rebase commit
- Related: rhbz#2026449
- Resolves: rhbz#1977913, rhbz#1975500
* Fri Nov 05 2021 Norbert Pocs <npocs@redhat.com> - 0.9.6-3
- Remove STI tests
* Tue Sep 27 2022 Norbert Pocs <npocs@redhat.com> - 0.10.4-2
- Fix coverity scan issues
- Resolves: rhbz#2130126
* Thu Oct 21 2021 Norbert Pocs <npocs@redhat.com> - 0.9.6-2
- Remove bad patch causing errors
- Adding BuildRequires for openssh (SSHD support)
* Mon Sep 19 2022 Norbert pocs <npocs@redhat.com> - 0.10.4-1
- Rebase to version 0.10.4
- Add pkcs11 support
- Disallow ssh-rsa key in FIPS mode
- Fix openssl KDF check at build
- ChangeLog was renamed to CHANGELOG
- Resolves: rhbz#2068475, rhbz#2026449, rhbz#2004021,
rhbz#1977913, rhbz#1975500
* Thu Oct 14 2021 Norbert Pocs <npocs@redhat.com> - 0.9.6-1
- Fix CVE-2021-3634: Fix possible heap-buffer overflow when
rekeying with different key exchange mechanism
* Fri Nov 12 2021 Stanislav Zidek <szidek@redhat.com> - 0.9.6-3
+ libssh-0.9.6-3
- Disabled gating on osci.brew-build.revdeps.integration
Related: rhbz#2022034
* Thu Nov 11 2021 Stanislav Zidek <szidek@redhat.com> - 0.9.6-2
- STI, FMF, and gating fixes
Resolves: rhbz#2022034
* Tue Oct 05 2021 Norbert Pocs <npocs@redhat.com> - 0.9.6-1
- Fix CVE-CVE-2021-3634 libssh: possible heap-based buffer
overflow when rekeying
- Fix static analyzer issues in rhbz#1938795
- Rebase to version 0.9.6
- Rename SSHD_EXECUTABLE to SSH_EXECUTABLE in tests/torture.c
- Resolves: rhbz#1896651, rhbz#1994600
- Resolves: rhbz#1994607, rhbz#1938795, rhbz#2009669
* Thu Oct 14 2021 Sahana Prasad <sahana@redhat.com> - 0.9.4-4
- Revert previous commit as it is incorrect.
* Mon Aug 09 2021 Mohan Boddu <mboddu@redhat.com> - 0.9.5-6
- Rebuilt for IMA sigs, glibc 2.34, aarch64 flags
Related: rhbz#1991688
* Thu Oct 14 2021 Norbert Pocs <npocs@redhat.com> - 0.9.6-1
- Fix CVE-2021-3634: Fix possible heap-buffer overflow when
rekeying with different key exchange mechanism (#1978810)
* Wed Jun 16 2021 Mohan Boddu <mboddu@redhat.com> - 0.9.5-5
- Rebuilt for RHEL 9 BETA for openssl 3.0
Related: rhbz#1971065
* Wed Apr 21 2021 Sahana Prasad <sahana@redhat.com> - 0.9.4-3
- Fix CVE-2020-16135 NULL pointer dereference in sftpserver.c if
ssh_buffer_new returns NULL (#1862646)
* Tue Apr 27 2021 Sahana Prasad <sahana@redhat.com> - 0.9.5-4
- Change crypto-policies from recommends to requires
Resolves: rhbz#1947863
* Wed Jun 24 2020 Anderson Sasaki <ansasaki@redhat.com> - 0.9.4-2
- Do not return error when server properly closed the channel (#1849071)
* Fri Apr 16 2021 Mohan Boddu <mboddu@redhat.com> - 0.9.5-3
- Rebuilt for RHEL 9 BETA on Apr 15th 2021. Related: rhbz#1947937
* Tue Jan 26 2021 Fedora Release Engineering <releng@fedoraproject.org> - 0.9.5-2
- Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild
* Thu Sep 10 2020 Anderson Sasaki <ansasaki@redhat.com> - 0.9.5-1
- Update to version 0.9.5
https://www.libssh.org/2020/09/10/libssh-0-9-5/
- Removed patch to re-enable algorithms using sha1 in sshd for testing
- The algorithms supported by sshd are now automatically detected for testing
- Resolves: #1862457 - CVE-2020-16135
* Sat Aug 01 2020 Fedora Release Engineering <releng@fedoraproject.org> - 0.9.4-5
- Second attempt - Rebuilt for
https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild
* Tue Jul 28 2020 Fedora Release Engineering <releng@fedoraproject.org> - 0.9.4-4
- Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild
* Mon Jun 22 2020 Anderson Sasaki <ansasaki@redhat.com> - 0.9.4-3
- Do not return error when server properly closed the channel (#1849069)
- Add a test for CVE-2019-14889
- Do not parse configuration file in torture_knownhosts test
* Tue May 26 2020 Anderson Sasaki <ansasaki@redhat.com> - 0.9.4-1
* Wed Apr 15 2020 Anderson Sasaki <ansasaki@redhat.com> - 0.9.4-2
- Added patch to fix returned version
* Thu Apr 09 2020 Anderson Sasaki <ansasaki@redhat.com> - 0.9.4-1
- Update to version 0.9.4
https://www.libssh.org/2020/04/09/libssh-0-9-4-and-libssh-0-8-9-security-release/
- Fixed CVE-2019-14889 (#1781782)
- Fixed CVE-2020-1730 (#1802422)
- Create missing directories in the path provided for known_hosts files (#1733914)
- Removed inclusion of OpenSSH server configuration file from
libssh_server.config (#1821339)
libssh_server.config
- Added patch to re-enable algorithms using sha1 in sshd for testing
- resolves: #1822529 - CVE-2020-1730
* Mon Aug 05 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-4
- Skip 1024 bits RSA key generation test in FIPS mode (#1734485)
* Wed Jan 29 2020 Fedora Release Engineering <releng@fedoraproject.org> - 0.9.3-2
- Rebuilt for https://fedoraproject.org/wiki/Fedora_32_Mass_Rebuild
* Thu Jul 11 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-3
* Tue Dec 10 2019 Andreas Schneider <asn@redhat.com> - 0.9.3-1
- Update to version 0.9.3
- resolves: #1781780 - Fixes CVE-2019-14889
* Thu Nov 07 2019 Andreas Schneider <asn@redhat.com> - 0.9.2-1
- Upate to version 0.9.2
- resolves #1769370 - Remove the docs, they can be found on https://api.libssh.org/
* Thu Jul 25 2019 Fedora Release Engineering <releng@fedoraproject.org> - 0.9.0-6
- Rebuilt for https://fedoraproject.org/wiki/Fedora_31_Mass_Rebuild
* Thu Jul 11 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-5
- Add Obsoletes in libssh-config to avoid conflict with old libssh which
installed the configuration files.
* Wed Jul 10 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-2
* Wed Jul 10 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-4
- Eliminate circular dependency with libssh-config subpackage
* Wed Jul 10 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-1
- Update to version 0.9.0
https://www.libssh.org/2019/06/28/libssh-0-9-0/
- Added explicit Requires for crypto-policies
- Do not ignore known_hosts keys when SSH_OPTIONS_HOSTKEYS is set
* Wed Jul 10 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-3
- Provide the configuration files in a separate libssh-config subpackage
* Mon Jun 17 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.8.91-0.1
* Thu Jul 04 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-2
- Do not ignore keys from known_hosts when SSH_OPTIONS_HOSTKEYS is set
* Fri Jun 28 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-1
- Fixed Release number to released format
* Fri Jun 28 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.9.0-0.1
- Update to version 0.9.0
https://www.libssh.org/2019/06/28/libssh-0-9-0/
* Wed Jun 19 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.8.91-0.1
- Update to 0.9.0 pre release version (0.8.91)
- Added default configuration files for client and server
- Removed unused patch files left behind
- Fixed issues found to run upstream test suite with SELinux
- Follow system-wide crypto configuration (crypto-policies)
- Added Recommends for crypto-policies
- Use OpenSSL implementation for KDF, DH, and signatures.
- Detect FIPS mode and use only allowed algorithms
- Run client and server tests during build
* Fri Dec 14 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.5-2
- Fix more regressions introduced by the fixes for CVE-2018-10933
* Mon Feb 25 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.8.7-1
- Update to version 0.8.7
https://www.libssh.org/2019/02/25/libssh-0-8-7/
* Thu Nov 29 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.5-1
* Fri Feb 01 2019 Fedora Release Engineering <releng@fedoraproject.org> - 0.8.6-3
- Rebuilt for https://fedoraproject.org/wiki/Fedora_30_Mass_Rebuild
* Tue Jan 15 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.8.6-2
- Fix rsa-sha2 extension handling (#1666342)
* Thu Jan 03 2019 Anderson Sasaki <ansasaki@redhat.com> - 0.8.6-1
- Update to version 0.8.6
https://www.libssh.org/2018/12/24/libssh-0-8-6-xmas-edition/
* Mon Oct 29 2018 Andreas Schneider <asn@redhat.com> - 0.8.5-1
- Update to version 0.8.5
* Fixed an issue where global known_hosts file was ignored (#1649321)
* Fixed ssh_get_fd() to return writable file descriptor (#1649319)
* Fixed regression introduced in known_hosts parsing (#1649315)
* Fixed a regression which caused only the first algorithm in known_hosts to
be considered (#1638790)
https://www.libssh.org/2018/10/29/libssh-0-8-5-and-libssh-0-7-7/
* Thu Nov 08 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.3-5
- Fix regressions introduced by the fixes for CVE-2018-10933
* Tue Oct 16 2018 Andreas Schneider <asn@redhat.com> - 0.8.4-1
- Update to version 0.8.4
https://www.libssh.org/2018/10/16/libssh-0-8-4-and-0-7-6-security-and-bugfix-release
- Fixes CVE-2018-10933
* Wed Oct 17 2018 Nikos Mavrogiannopoulos <nmav@redhat.com> - 0.8.3-4
- Fix for authentication bypass issue in server implementation (#1639926)
* Mon Oct 01 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.3-3
- Fixed errors found by static code analysis
* Tue Oct 02 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.3-3
- Fixed errors found by static code analysis (#1602594)
* Tue Sep 25 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.3-2
- Add missing libssh_threads.so link to libssh-devel package
* Fri Sep 21 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.3-1
* Fri Sep 21 2018 Andreas Schneider <asn@redhat.com> - 0.8.3-1
- Update to version 0.8.3
* Added support for rsa-sha2 (#1610882)
* Added support to parse private keys in openssh container format (other than
ed25519) (#1622983)
* Added support for diffie-hellman-group18-sha512 and
diffie-hellman-group16-sha512 (#1610885)
* Added ssh_get_fingerprint_hash()
* Added ssh_pki_export_privkey_base64()
* Added support for Match keyword in config file
* Improved performance and reduced memory footprint for sftp
* Fixed ecdsa publickey auth
* Fixed reading a closed channel
* Added support to announce posix-rename@openssh.com and hardlink@openssh.com
in the sftp server
* Use -fstack-protector-strong if possible (#1624135)
https://www.libssh.org/2018/09/21/libssh-0-8-3/
* Wed Aug 15 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.1-4
- Fix the creation of symbolic links for libssh_threads.so.4
* Thu Aug 30 2018 Andreas Schneider <asn@redhat.com> - 0.8.2-1
- Update to version 0.8.2
https://www.libssh.org/2018/08/30/libssh-0-8-2
* Wed Aug 15 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.1-3
- Add missing Provides for libssh_threads.so.4
* Thu Aug 16 2018 Andreas Schneider <asn@redhat.com> - 0.8.1-4
- Fix link creation or RPM doesn't install it
* Tue Aug 14 2018 Anderson Sasaki <ansasaki@redhat.com> - 0.8.1-2
* Wed Aug 15 2018 Andreas Schneider <asn@redhat.com> - 0.8.1-3
- Add missing so version for libssh_threads.so.4
* Tue Aug 14 2018 Andreas Schneider <asn@redhat.com> - 0.8.1-2
- Add Provides for libssh_threads.so to unbreak applications
- Fix ABIMap detection to not depend on python to build
* Mon Aug 13 2018 Andreas Schneider <asn@redhat.com> - 0.8.1-1
- Update to version 0.8.1
https://www.libssh.org/2018/08/13/libssh-0-8-1/
https://www.libssh.org/2018/08/13/libssh-0-8-1
- resolves: #1615248 - pkg-config --modversion
- resolves: #1615132 - library initialization
* Fri Aug 10 2018 Andreas Schneider <asn@redhat.com> - 0.8.0-1
- Update to version 0.8.0
@ -323,7 +387,6 @@ popd
* Wed Feb 07 2018 Fedora Release Engineering <releng@fedoraproject.org> - 0.7.5-7
- Rebuilt for https://fedoraproject.org/wiki/Fedora_28_Mass_Rebuild
- Related: bug#1614611
* Thu Feb 01 2018 Andreas Schneider <asn@redhat.com> - 0.7.5-6
- resolves: #1540021 - Build against OpenSSL 1.1

File diff suppressed because it is too large Load Diff

514
memory_leak.patch Normal file
View File

@ -0,0 +1,514 @@
From 8795d8912c8a83aaf900c0260e252a35f64eb200 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <npocs@redhat.com>
Date: Fri, 18 Nov 2022 17:22:46 +0100
Subject: [PATCH] Fix memory leaks of bignums when openssl >= 3.0
The openssl 3.0 support has introduced some memory leaks at key build as
OSSL_PARAM_BLD_push_BN duplicates the bignum and does not save the pointer
itself.
Signed-off-by: Norbert Pocs <npocs@redhat.com>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
include/libssh/dh.h | 2 +-
src/dh_crypto.c | 28 ++---
src/pki_crypto.c | 262 ++++++++++++++++++++++++--------------------
3 files changed, 151 insertions(+), 141 deletions(-)
diff --git a/include/libssh/dh.h b/include/libssh/dh.h
index 353dc233..9b9bb472 100644
--- a/include/libssh/dh.h
+++ b/include/libssh/dh.h
@@ -53,7 +53,7 @@ int ssh_dh_keypair_get_keys(struct dh_ctx *ctx, int peer,
bignum *priv, bignum *pub);
#endif /* OPENSSL_VERSION_NUMBER */
int ssh_dh_keypair_set_keys(struct dh_ctx *ctx, int peer,
- const bignum priv, const bignum pub);
+ bignum priv, bignum pub);
int ssh_dh_compute_shared_secret(struct dh_ctx *ctx, int local, int remote,
bignum *dest);
diff --git a/src/dh_crypto.c b/src/dh_crypto.c
index a847c6a2..b578ddec 100644
--- a/src/dh_crypto.c
+++ b/src/dh_crypto.c
@@ -154,12 +154,9 @@ int ssh_dh_keypair_get_keys(struct dh_ctx *ctx, int peer,
#endif /* OPENSSL_VERSION_NUMBER */
int ssh_dh_keypair_set_keys(struct dh_ctx *ctx, int peer,
- const bignum priv, const bignum pub)
+ bignum priv, bignum pub)
{
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
- bignum priv_key = NULL;
- bignum pub_key = NULL;
-#else
+#if OPENSSL_VERSION_NUMBER >= 0x30000000L
int rc;
OSSL_PARAM *params = NULL, *out_params = NULL, *merged_params = NULL;
OSSL_PARAM_BLD *param_bld = NULL;
@@ -172,7 +169,11 @@ int ssh_dh_keypair_set_keys(struct dh_ctx *ctx, int peer,
return SSH_ERROR;
}
-#if OPENSSL_VERSION_NUMBER >= 0x30000000L
+#if OPENSSL_VERSION_NUMBER < 0x30000000L
+ (void)DH_set0_key(ctx->keypair[peer], pub, priv);
+
+ return SSH_OK;
+#else
rc = EVP_PKEY_todata(ctx->keypair[peer], EVP_PKEY_KEYPAIR, &out_params);
if (rc != 1) {
return SSH_ERROR;
@@ -195,35 +196,22 @@ int ssh_dh_keypair_set_keys(struct dh_ctx *ctx, int peer,
rc = SSH_ERROR;
goto out;
}
-#endif /* OPENSSL_VERSION_NUMBER */
if (priv) {
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
- priv_key = priv;
-#else
rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PRIV_KEY, priv);
if (rc != 1) {
rc = SSH_ERROR;
goto out;
}
-#endif /* OPENSSL_VERSION_NUMBER */
}
if (pub) {
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
- pub_key = pub;
-#else
rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PUB_KEY, pub);
if (rc != 1) {
rc = SSH_ERROR;
goto out;
}
-#endif /* OPENSSL_VERSION_NUMBER */
}
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
- (void)DH_set0_key(ctx->keypair[peer], pub_key, priv_key);
- return SSH_OK;
-#else
params = OSSL_PARAM_BLD_to_param(param_bld);
if (params == NULL) {
rc = SSH_ERROR;
@@ -248,6 +236,8 @@ int ssh_dh_keypair_set_keys(struct dh_ctx *ctx, int peer,
rc = SSH_OK;
out:
+ bignum_safe_free(priv);
+ bignum_safe_free(pub);
EVP_PKEY_CTX_free(evp_ctx);
OSSL_PARAM_free(out_params);
OSSL_PARAM_free(params);
diff --git a/src/pki_crypto.c b/src/pki_crypto.c
index 0a5003da..d3359e2d 100644
--- a/src/pki_crypto.c
+++ b/src/pki_crypto.c
@@ -1492,18 +1492,18 @@ int pki_privkey_build_dss(ssh_key key,
ssh_string privkey)
{
int rc;
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
BIGNUM *bp, *bq, *bg, *bpub_key, *bpriv_key;
+#if OPENSSL_VERSION_NUMBER >= 0x30000000L
+ OSSL_PARAM_BLD *param_bld = OSSL_PARAM_BLD_new();
+ if (param_bld == NULL) {
+ return SSH_ERROR;
+ }
#else
- const BIGNUM *pb, *qb, *gb, *pubb, *privb;
- OSSL_PARAM_BLD *param_bld;
-#endif /* OPENSSL_VERSION_NUMBER */
-
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
key->dsa = DSA_new();
if (key->dsa == NULL) {
return SSH_ERROR;
}
+#endif /* OPENSSL_VERSION_NUMBER */
bp = ssh_make_string_bn(p);
bq = ssh_make_string_bn(q);
@@ -1512,9 +1512,11 @@ int pki_privkey_build_dss(ssh_key key,
bpriv_key = ssh_make_string_bn(privkey);
if (bp == NULL || bq == NULL ||
bg == NULL || bpub_key == NULL) {
+ rc = SSH_ERROR;
goto fail;
}
+#if OPENSSL_VERSION_NUMBER < 0x30000000L
/* Memory management of bp, qq and bg is transferred to DSA object */
rc = DSA_set0_pqg(key->dsa, bp, bq, bg);
if (rc == 0) {
@@ -1532,39 +1534,43 @@ fail:
DSA_free(key->dsa);
return SSH_ERROR;
#else
- param_bld = OSSL_PARAM_BLD_new();
- if (param_bld == NULL)
- goto err;
-
- pb = ssh_make_string_bn(p);
- qb = ssh_make_string_bn(q);
- gb = ssh_make_string_bn(g);
- pubb = ssh_make_string_bn(pubkey);
- privb = ssh_make_string_bn(privkey);
-
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_P, pb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_Q, qb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_G, gb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PUB_KEY, pubb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PRIV_KEY, privb);
- if (rc != 1)
- goto err;
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_P, bp);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_Q, bq);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_G, bg);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PUB_KEY, bpub_key);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PRIV_KEY, bpriv_key);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
rc = evp_build_pkey("DSA", param_bld, &(key->key), EVP_PKEY_KEYPAIR);
+
+fail:
OSSL_PARAM_BLD_free(param_bld);
+ bignum_safe_free(bp);
+ bignum_safe_free(bq);
+ bignum_safe_free(bg);
+ bignum_safe_free(bpub_key);
+ bignum_safe_free(bpriv_key);
return rc;
-err:
- OSSL_PARAM_BLD_free(param_bld);
- return -1;
#endif /* OPENSSL_VERSION_NUMBER */
}
@@ -1574,18 +1580,18 @@ int pki_pubkey_build_dss(ssh_key key,
ssh_string g,
ssh_string pubkey) {
int rc;
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
BIGNUM *bp = NULL, *bq = NULL, *bg = NULL, *bpub_key = NULL;
+#if OPENSSL_VERSION_NUMBER >= 0x30000000L
+ OSSL_PARAM_BLD *param_bld = OSSL_PARAM_BLD_new();
+ if (param_bld == NULL) {
+ return SSH_ERROR;
+ }
#else
- const BIGNUM *pb, *qb, *gb, *pubb;
- OSSL_PARAM_BLD *param_bld;
-#endif /* OPENSSL_VERSION_NUMBER */
-
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
key->dsa = DSA_new();
if (key->dsa == NULL) {
return SSH_ERROR;
}
+#endif /* OPENSSL_VERSION_NUMBER */
bp = ssh_make_string_bn(p);
bq = ssh_make_string_bn(q);
@@ -1593,9 +1599,11 @@ int pki_pubkey_build_dss(ssh_key key,
bpub_key = ssh_make_string_bn(pubkey);
if (bp == NULL || bq == NULL ||
bg == NULL || bpub_key == NULL) {
+ rc = SSH_ERROR;
goto fail;
}
+#if OPENSSL_VERSION_NUMBER < 0x30000000L
/* Memory management of bp, bq and bg is transferred to DSA object */
rc = DSA_set0_pqg(key->dsa, bp, bq, bg);
if (rc == 0) {
@@ -1613,35 +1621,37 @@ fail:
DSA_free(key->dsa);
return SSH_ERROR;
#else
- param_bld = OSSL_PARAM_BLD_new();
- if (param_bld == NULL)
- goto err;
-
- pb = ssh_make_string_bn(p);
- qb = ssh_make_string_bn(q);
- gb = ssh_make_string_bn(g);
- pubb = ssh_make_string_bn(pubkey);
-
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_P, pb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_Q, qb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_G, gb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PUB_KEY, pubb);
- if (rc != 1)
- goto err;
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_P, bp);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_Q, bq);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_FFC_G, bg);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_PUB_KEY, bpub_key);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
rc = evp_build_pkey("DSA", param_bld, &(key->key), EVP_PKEY_PUBLIC_KEY);
+
+fail:
OSSL_PARAM_BLD_free(param_bld);
+ bignum_safe_free(bp);
+ bignum_safe_free(bq);
+ bignum_safe_free(bg);
+ bignum_safe_free(bpub_key);
return rc;
-err:
- OSSL_PARAM_BLD_free(param_bld);
- return -1;
#endif /* OPENSSL_VERSION_NUMBER */
}
@@ -1654,18 +1664,18 @@ int pki_privkey_build_rsa(ssh_key key,
ssh_string q)
{
int rc;
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
BIGNUM *be, *bn, *bd/*, *biqmp*/, *bp, *bq;
+#if OPENSSL_VERSION_NUMBER >= 0x30000000L
+ OSSL_PARAM_BLD *param_bld = OSSL_PARAM_BLD_new();
+ if (param_bld == NULL) {
+ return SSH_ERROR;
+ }
#else
- const BIGNUM *nb, *eb, *db, *pb, *qb;
- OSSL_PARAM_BLD *param_bld;
-#endif /* OPENSSL_VERSION_NUMBER */
-
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
key->rsa = RSA_new();
if (key->rsa == NULL) {
return SSH_ERROR;
}
+#endif /* OPENSSL_VERSION_NUMBER */
bn = ssh_make_string_bn(n);
be = ssh_make_string_bn(e);
@@ -1675,9 +1685,11 @@ int pki_privkey_build_rsa(ssh_key key,
bq = ssh_make_string_bn(q);
if (be == NULL || bn == NULL || bd == NULL ||
/*biqmp == NULL ||*/ bp == NULL || bq == NULL) {
+ rc = SSH_ERROR;
goto fail;
}
+#if OPENSSL_VERSION_NUMBER < 0x30000000L
/* Memory management of be, bn and bd is transferred to RSA object */
rc = RSA_set0_key(key->rsa, bn, be, bd);
if (rc == 0) {
@@ -1702,41 +1714,49 @@ fail:
RSA_free(key->rsa);
return SSH_ERROR;
#else
- param_bld = OSSL_PARAM_BLD_new();
- if (param_bld == NULL)
- goto err;
-
- nb = ssh_make_string_bn(n);
- eb = ssh_make_string_bn(e);
- db = ssh_make_string_bn(d);
- pb = ssh_make_string_bn(p);
- qb = ssh_make_string_bn(q);
-
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_N, nb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_E, eb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_D, db);
- if (rc != 1)
- goto err;
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_N, bn);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_E, be);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_D, bd);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
rc = evp_build_pkey("RSA", param_bld, &(key->key), EVP_PKEY_KEYPAIR);
- OSSL_PARAM_BLD_free(param_bld);
+ if (rc != SSH_OK) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
- rc = EVP_PKEY_set_bn_param(key->key, OSSL_PKEY_PARAM_RSA_FACTOR1, pb);
- if (rc != 1)
- goto err;
+ rc = EVP_PKEY_set_bn_param(key->key, OSSL_PKEY_PARAM_RSA_FACTOR1, bp);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
- rc = EVP_PKEY_set_bn_param(key->key, OSSL_PKEY_PARAM_RSA_FACTOR2, qb);
- if (rc != 1)
- goto err;
+ rc = EVP_PKEY_set_bn_param(key->key, OSSL_PKEY_PARAM_RSA_FACTOR2, bq);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
- return rc;
-err:
+fail:
OSSL_PARAM_BLD_free(param_bld);
- return -1;
+ bignum_safe_free(bn);
+ bignum_safe_free(be);
+ bignum_safe_free(bd);
+ bignum_safe_free(bp);
+ bignum_safe_free(bq);
+
+ return rc;
#endif /* OPENSSL_VERSION_NUMBER */
}
@@ -1744,25 +1764,27 @@ int pki_pubkey_build_rsa(ssh_key key,
ssh_string e,
ssh_string n) {
int rc;
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
BIGNUM *be = NULL, *bn = NULL;
+#if OPENSSL_VERSION_NUMBER >= 0x30000000L
+ OSSL_PARAM_BLD *param_bld = OSSL_PARAM_BLD_new();
+ if (param_bld == NULL) {
+ return SSH_ERROR;
+ }
#else
- const BIGNUM *eb, *nb;
- OSSL_PARAM_BLD *param_bld;
-#endif /* OPENSSL_VERSION_NUMBER */
-
-#if OPENSSL_VERSION_NUMBER < 0x30000000L
key->rsa = RSA_new();
if (key->rsa == NULL) {
return SSH_ERROR;
}
+#endif /* OPENSSL_VERSION_NUMBER */
be = ssh_make_string_bn(e);
bn = ssh_make_string_bn(n);
if (be == NULL || bn == NULL) {
+ rc = SSH_ERROR;
goto fail;
}
+#if OPENSSL_VERSION_NUMBER < 0x30000000L
/* Memory management of bn and be is transferred to RSA object */
rc = RSA_set0_key(key->rsa, bn, be, NULL);
if (rc == 0) {
@@ -1774,27 +1796,25 @@ fail:
RSA_free(key->rsa);
return SSH_ERROR;
#else
- nb = ssh_make_string_bn(n);
- eb = ssh_make_string_bn(e);
-
- param_bld = OSSL_PARAM_BLD_new();
- if (param_bld == NULL)
- goto err;
-
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_N, nb);
- if (rc != 1)
- goto err;
- rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_E, eb);
- if (rc != 1)
- goto err;
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_N, bn);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
+ rc = OSSL_PARAM_BLD_push_BN(param_bld, OSSL_PKEY_PARAM_RSA_E, be);
+ if (rc != 1) {
+ rc = SSH_ERROR;
+ goto fail;
+ }
rc = evp_build_pkey("RSA", param_bld, &(key->key), EVP_PKEY_PUBLIC_KEY);
+
+fail:
OSSL_PARAM_BLD_free(param_bld);
+ bignum_safe_free(bn);
+ bignum_safe_free(be);
return rc;
-err:
- OSSL_PARAM_BLD_free(param_bld);
- return -1;
#endif /* OPENSSL_VERSION_NUMBER */
}
--
2.38.1

View File

@ -1,6 +1,6 @@
diff --color -ru ../libssh-0.9.6/include/libssh/curve25519.h ./include/libssh/curve25519.h
--- ../libssh-0.9.6/include/libssh/curve25519.h 2021-03-15 08:11:33.000000000 +0100
+++ ./include/libssh/curve25519.h 2023-04-27 12:21:30.257820636 +0200
diff --color -ru ../libssh-0.10.4/include/libssh/curve25519.h ./include/libssh/curve25519.h
--- ../libssh-0.10.4/include/libssh/curve25519.h 2022-07-07 15:53:51.000000000 +0200
+++ ./include/libssh/curve25519.h 2023-04-27 14:35:27.030113530 +0200
@@ -48,6 +48,7 @@
@ -9,9 +9,9 @@ diff --color -ru ../libssh-0.9.6/include/libssh/curve25519.h ./include/libssh/cu
#ifdef WITH_SERVER
void ssh_server_curve25519_init(ssh_session session);
diff --color -ru ../libssh-0.9.6/include/libssh/dh-gex.h ./include/libssh/dh-gex.h
--- ../libssh-0.9.6/include/libssh/dh-gex.h 2021-03-15 08:11:33.000000000 +0100
+++ ./include/libssh/dh-gex.h 2023-04-27 12:21:30.257820636 +0200
diff --color -ru ../libssh-0.10.4/include/libssh/dh-gex.h ./include/libssh/dh-gex.h
--- ../libssh-0.10.4/include/libssh/dh-gex.h 2022-07-07 15:53:51.000000000 +0200
+++ ./include/libssh/dh-gex.h 2023-04-27 14:35:27.030113530 +0200
@@ -24,6 +24,7 @@
#define SRC_DH_GEX_H_
@ -20,10 +20,10 @@ diff --color -ru ../libssh-0.9.6/include/libssh/dh-gex.h ./include/libssh/dh-gex
#ifdef WITH_SERVER
void ssh_server_dhgex_init(ssh_session session);
diff --color -ru ../libssh-0.9.6/include/libssh/dh.h ./include/libssh/dh.h
--- ../libssh-0.9.6/include/libssh/dh.h 2021-03-15 08:11:33.000000000 +0100
+++ ./include/libssh/dh.h 2023-04-27 12:21:30.257820636 +0200
@@ -63,8 +63,10 @@
diff --color -ru ../libssh-0.10.4/include/libssh/dh.h ./include/libssh/dh.h
--- ../libssh-0.10.4/include/libssh/dh.h 2023-04-27 14:25:46.353381599 +0200
+++ ./include/libssh/dh.h 2023-04-27 14:36:02.691475297 +0200
@@ -73,8 +73,10 @@
ssh_key ssh_dh_get_next_server_publickey(ssh_session session);
int ssh_dh_get_next_server_publickey_blob(ssh_session session,
ssh_string *pubkey_blob);
@ -34,9 +34,9 @@ diff --color -ru ../libssh-0.9.6/include/libssh/dh.h ./include/libssh/dh.h
#ifdef WITH_SERVER
void ssh_server_dh_init(ssh_session session);
#endif /* WITH_SERVER */
diff --color -ru ../libssh-0.9.6/include/libssh/ecdh.h ./include/libssh/ecdh.h
--- ../libssh-0.9.6/include/libssh/ecdh.h 2021-03-15 08:11:33.000000000 +0100
+++ ./include/libssh/ecdh.h 2023-04-27 12:21:30.257820636 +0200
diff --color -ru ../libssh-0.10.4/include/libssh/ecdh.h ./include/libssh/ecdh.h
--- ../libssh-0.10.4/include/libssh/ecdh.h 2022-07-07 15:53:51.000000000 +0200
+++ ./include/libssh/ecdh.h 2023-04-27 14:35:27.030113530 +0200
@@ -45,6 +45,7 @@
extern struct ssh_packet_callbacks_struct ssh_ecdh_client_callbacks;
/* Backend-specific functions. */
@ -45,9 +45,9 @@ diff --color -ru ../libssh-0.9.6/include/libssh/ecdh.h ./include/libssh/ecdh.h
int ecdh_build_k(ssh_session session);
#ifdef WITH_SERVER
diff --color -ru ../libssh-0.9.6/include/libssh/kex.h ./include/libssh/kex.h
--- ../libssh-0.9.6/include/libssh/kex.h 2021-03-15 08:11:33.000000000 +0100
+++ ./include/libssh/kex.h 2023-04-27 12:21:30.257820636 +0200
diff --color -ru ../libssh-0.10.4/include/libssh/kex.h ./include/libssh/kex.h
--- ../libssh-0.10.4/include/libssh/kex.h 2023-04-27 14:25:46.346381527 +0200
+++ ./include/libssh/kex.h 2023-04-27 14:34:36.438602800 +0200
@@ -33,7 +33,7 @@
SSH_PACKET_CALLBACK(ssh_packet_kexinit);
@ -57,10 +57,10 @@ diff --color -ru ../libssh-0.9.6/include/libssh/kex.h ./include/libssh/kex.h
void ssh_list_kex(struct ssh_kex_struct *kex);
int ssh_set_client_kex(ssh_session session);
int ssh_kex_select_methods(ssh_session session);
diff --color -ru ../libssh-0.9.6/include/libssh/session.h ./include/libssh/session.h
--- ../libssh-0.9.6/include/libssh/session.h 2021-08-26 14:27:42.000000000 +0200
+++ ./include/libssh/session.h 2023-04-27 12:24:04.679475777 +0200
@@ -75,6 +75,11 @@
diff --color -ru ../libssh-0.10.4/include/libssh/session.h ./include/libssh/session.h
--- ../libssh-0.10.4/include/libssh/session.h 2023-04-27 14:25:46.361381682 +0200
+++ ./include/libssh/session.h 2023-04-27 14:36:02.692475307 +0200
@@ -76,6 +76,11 @@
/* Client successfully authenticated */
#define SSH_SESSION_FLAG_AUTHENTICATED 2
@ -72,7 +72,7 @@ diff --color -ru ../libssh-0.9.6/include/libssh/session.h ./include/libssh/sessi
/* codes to use with ssh_handle_packets*() */
/* Infinite timeout */
#define SSH_TIMEOUT_INFINITE -1
@@ -131,10 +136,8 @@
@@ -138,10 +143,8 @@
/* Extensions negotiated using RFC 8308 */
uint32_t extensions;
@ -82,10 +82,10 @@ diff --color -ru ../libssh-0.9.6/include/libssh/session.h ./include/libssh/sessi
- the remote host */
+ ssh_string banner; /* that's the issue banner from the server */
+ char *discon_msg; /* disconnect message from the remote host */
char *disconnect_message; /* disconnect message to be set */
ssh_buffer in_buffer;
PACKET in_packet;
ssh_buffer out_buffer;
@@ -158,25 +161,33 @@
@@ -166,25 +169,33 @@
uint32_t current_method;
} auth;
@ -116,7 +116,7 @@ diff --color -ru ../libssh-0.9.6/include/libssh/session.h ./include/libssh/sessi
+ struct ssh_crypto_struct *next_crypto;
struct ssh_list *channels; /* linked list of channels */
int maxchannel;
uint32_t maxchannel;
ssh_agent agent; /* ssh agent */
-/* keyb interactive data */
@ -124,7 +124,7 @@ diff --color -ru ../libssh-0.9.6/include/libssh/session.h ./include/libssh/sessi
struct ssh_kbdint_struct *kbdint;
struct ssh_gssapi_struct *gssapi;
@@ -193,7 +204,8 @@
@@ -201,7 +212,8 @@
/* auths accepted by server */
struct ssh_list *ssh_message_list; /* list of delayed SSH messages */
@ -134,17 +134,16 @@ diff --color -ru ../libssh-0.9.6/include/libssh/session.h ./include/libssh/sessi
void *ssh_message_callback_data;
ssh_server_callbacks server_callbacks;
void (*ssh_connection_callback)( struct ssh_session_struct *session);
diff --color -ru ../libssh-0.9.6/src/client.c ./src/client.c
--- ../libssh-0.9.6/src/client.c 2023-04-27 12:22:39.797925403 +0200
+++ ./src/client.c 2023-04-27 12:24:04.680475778 +0200
@@ -243,10 +243,13 @@
diff --color -ru ../libssh-0.10.4/src/client.c ./src/client.c
--- ../libssh-0.10.4/src/client.c 2023-04-27 14:25:46.339381455 +0200
+++ ./src/client.c 2023-04-27 14:36:02.692475307 +0200
@@ -246,10 +246,13 @@
* @warning this function returning is no proof that DH handshake is
* completed
*/
-static int dh_handshake(ssh_session session) {
-
-static int dh_handshake(ssh_session session)
+int dh_handshake(ssh_session session)
+{
{
int rc = SSH_AGAIN;
+ SSH_LOG(SSH_LOG_TRACE, "dh_handshake_state = %d, kex_type = %d",
@ -153,7 +152,7 @@ diff --color -ru ../libssh-0.9.6/src/client.c ./src/client.c
switch (session->dh_handshake_state) {
case DH_STATE_INIT:
switch(session->next_crypto->kex_type){
@@ -386,96 +389,102 @@
@@ -392,96 +395,103 @@
{
int rc;
@ -208,10 +207,10 @@ diff --color -ru ../libssh-0.9.6/src/client.c ./src/client.c
+ session->serverbanner);
+ goto error;
+ }
+
+ ssh_packet_register_socket_callback(session, session->socket);
- ssh_packet_register_socket_callback(session, session->socket);
+ ssh_packet_register_socket_callback(session, session->socket);
+
+ ssh_packet_set_default_callbacks(session);
+ session->session_state = SSH_SESSION_STATE_INITIAL_KEX;
+ rc = ssh_set_client_kex(session);
@ -322,15 +321,15 @@ diff --color -ru ../libssh-0.9.6/src/client.c ./src/client.c
ssh_socket_close(session->socket);
session->alive = 0;
- session->session_state=SSH_SESSION_STATE_ERROR;
- SSH_LOG(SSH_LOG_WARN, "%s", ssh_get_error(session));
+ session->session_state = SSH_SESSION_STATE_ERROR;
SSH_LOG(SSH_LOG_WARN, "%s", ssh_get_error(session));
+
}
/** @internal
diff --color -ru ../libssh-0.9.6/src/curve25519.c ./src/curve25519.c
--- ../libssh-0.9.6/src/curve25519.c 2023-04-27 12:22:39.797925403 +0200
+++ ./src/curve25519.c 2023-04-27 12:24:04.680475778 +0200
diff --color -ru ../libssh-0.10.4/src/curve25519.c ./src/curve25519.c
--- ../libssh-0.10.4/src/curve25519.c 2023-04-27 14:25:46.333381393 +0200
+++ ./src/curve25519.c 2023-04-27 14:35:27.031113541 +0200
@@ -172,6 +172,11 @@
return rc;
}
@ -352,10 +351,10 @@ diff --color -ru ../libssh-0.9.6/src/curve25519.c ./src/curve25519.c
pubkey_blob = ssh_buffer_get_ssh_string(packet);
if (pubkey_blob == NULL) {
diff --color -ru ../libssh-0.9.6/src/dh.c ./src/dh.c
--- ../libssh-0.9.6/src/dh.c 2023-04-27 12:22:39.798925404 +0200
+++ ./src/dh.c 2023-04-27 12:24:04.680475778 +0200
@@ -342,6 +342,11 @@
diff --color -ru ../libssh-0.10.4/src/dh.c ./src/dh.c
--- ../libssh-0.10.4/src/dh.c 2023-04-27 14:25:46.333381393 +0200
+++ ./src/dh.c 2023-04-27 14:35:27.032113551 +0200
@@ -352,6 +352,11 @@
return SSH_ERROR;
}
@ -367,7 +366,7 @@ diff --color -ru ../libssh-0.9.6/src/dh.c ./src/dh.c
SSH_PACKET_CALLBACK(ssh_packet_client_dh_reply){
struct ssh_crypto_struct *crypto=session->next_crypto;
ssh_string pubkey_blob = NULL;
@@ -351,7 +356,7 @@
@@ -361,7 +366,7 @@
(void)type;
(void)user;
@ -376,10 +375,10 @@ diff --color -ru ../libssh-0.9.6/src/dh.c ./src/dh.c
rc = ssh_buffer_unpack(packet, "SBS", &pubkey_blob, &server_pubkey,
&crypto->dh_server_signature);
diff --color -ru ../libssh-0.9.6/src/dh-gex.c ./src/dh-gex.c
--- ../libssh-0.9.6/src/dh-gex.c 2023-04-27 12:22:39.797925403 +0200
+++ ./src/dh-gex.c 2023-04-27 12:24:04.680475778 +0200
@@ -238,6 +238,11 @@
diff --color -ru ../libssh-0.10.4/src/dh-gex.c ./src/dh-gex.c
--- ../libssh-0.10.4/src/dh-gex.c 2023-04-27 14:25:46.333381393 +0200
+++ ./src/dh-gex.c 2023-04-27 14:35:27.031113541 +0200
@@ -248,6 +248,11 @@
return SSH_PACKET_USED;
}
@ -391,7 +390,7 @@ diff --color -ru ../libssh-0.9.6/src/dh-gex.c ./src/dh-gex.c
static SSH_PACKET_CALLBACK(ssh_packet_client_dhgex_reply)
{
struct ssh_crypto_struct *crypto=session->next_crypto;
@@ -248,7 +253,7 @@
@@ -258,7 +263,7 @@
(void)user;
SSH_LOG(SSH_LOG_DEBUG, "SSH_MSG_KEX_DH_GEX_REPLY received");
@ -400,9 +399,9 @@ diff --color -ru ../libssh-0.9.6/src/dh-gex.c ./src/dh-gex.c
rc = ssh_buffer_unpack(packet,
"SBS",
&pubkey_blob, &server_pubkey,
diff --color -ru ../libssh-0.9.6/src/ecdh.c ./src/ecdh.c
--- ../libssh-0.9.6/src/ecdh.c 2023-04-27 12:22:39.798925404 +0200
+++ ./src/ecdh.c 2023-04-27 12:24:04.680475778 +0200
diff --color -ru ../libssh-0.10.4/src/ecdh.c ./src/ecdh.c
--- ../libssh-0.10.4/src/ecdh.c 2023-04-27 14:25:46.333381393 +0200
+++ ./src/ecdh.c 2023-04-27 14:35:27.032113551 +0200
@@ -43,6 +43,11 @@
.user = NULL
};
@ -424,10 +423,10 @@ diff --color -ru ../libssh-0.9.6/src/ecdh.c ./src/ecdh.c
pubkey_blob = ssh_buffer_get_ssh_string(packet);
if (pubkey_blob == NULL) {
ssh_set_error(session,SSH_FATAL, "No public key in packet");
diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
--- ../libssh-0.9.6/src/gssapi.c 2023-04-27 12:22:39.798925404 +0200
+++ ./src/gssapi.c 2023-04-27 12:24:04.681475778 +0200
@@ -223,6 +223,7 @@
diff --color -ru ../libssh-0.10.4/src/gssapi.c ./src/gssapi.c
--- ../libssh-0.10.4/src/gssapi.c 2023-04-27 14:25:46.333381393 +0200
+++ ./src/gssapi.c 2023-04-27 14:29:22.606512115 +0200
@@ -229,6 +229,7 @@
"indicate mechs",
maj_stat,
min_stat);
@ -435,7 +434,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
return SSH_ERROR;
}
@@ -259,8 +260,10 @@
@@ -265,8 +266,10 @@
return SSH_OK;
}
/* from now we have room for context */
@ -447,7 +446,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
name_buf.value = service_name;
name_buf.length = strlen(name_buf.value) + 1;
@@ -272,6 +275,7 @@
@@ -278,6 +281,7 @@
"importing name",
maj_stat,
min_stat);
@ -455,7 +454,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
return -1;
}
@@ -338,6 +342,7 @@
@@ -345,6 +349,7 @@
min_stat);
ptr = malloc(buffer.length + 1);
if (ptr == NULL) {
@ -463,7 +462,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
return NULL;
}
memcpy(ptr, buffer.value, buffer.length);
@@ -421,6 +426,7 @@
@@ -428,6 +433,7 @@
"Gssapi error",
maj_stat,
min_stat);
@ -471,7 +470,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_auth_reply_default(session,0);
ssh_gssapi_free(session);
session->gssapi=NULL;
@@ -438,6 +444,9 @@
@@ -445,6 +451,9 @@
(size_t)output_token.length, output_token.value);
ssh_packet_send(session);
}
@ -481,7 +480,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
if(maj_stat == GSS_S_COMPLETE){
session->gssapi->state = SSH_GSSAPI_STATE_RCV_MIC;
}
@@ -638,7 +647,7 @@
@@ -648,7 +657,7 @@
static int ssh_gssapi_match(ssh_session session, gss_OID_set *valid_oids)
{
OM_uint32 maj_stat, min_stat, lifetime;
@ -490,7 +489,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
gss_buffer_desc namebuf;
gss_name_t client_id = GSS_C_NO_NAME;
gss_OID oid;
@@ -700,6 +709,7 @@
@@ -710,6 +719,7 @@
ret = SSH_OK;
end:
@ -498,16 +497,16 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
gss_release_name(&min_stat, &client_id);
return ret;
}
@@ -713,7 +723,7 @@
*/
int ssh_gssapi_auth_mic(ssh_session session){
@@ -724,7 +734,7 @@
int ssh_gssapi_auth_mic(ssh_session session)
{
size_t i;
- gss_OID_set selected; /* oid selected for authentication */
+ gss_OID_set selected = GSS_C_NO_OID_SET; /* oid selected for authentication */
ssh_string *oids = NULL;
int rc;
size_t n_oids = 0;
@@ -790,6 +800,8 @@
@@ -801,6 +811,8 @@
SSH_STRING_FREE(oids[i]);
}
free(oids);
@ -516,7 +515,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
if (rc != SSH_ERROR) {
return SSH_AUTH_AGAIN;
}
@@ -893,6 +905,8 @@
@@ -904,6 +916,8 @@
ssh_packet_send(session);
session->auth.state = SSH_AUTH_STATE_GSSAPI_TOKEN;
}
@ -525,7 +524,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
return SSH_PACKET_USED;
error:
@@ -921,8 +935,10 @@
@@ -933,8 +947,10 @@
maj_stat = gss_get_mic(&min_stat,session->gssapi->ctx, GSS_C_QOP_DEFAULT,
&mic_buf, &mic_token_buf);
@ -537,7 +536,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_gssapi_log_error(SSH_LOG_DEBUG,
"generating MIC",
maj_stat,
@@ -935,8 +951,10 @@
@@ -947,8 +963,10 @@
SSH2_MSG_USERAUTH_GSSAPI_MIC,
mic_token_buf.length,
(size_t)mic_token_buf.length, mic_token_buf.value);
@ -549,7 +548,7 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
ssh_set_error_oom(session);
return SSH_ERROR;
}
@@ -1005,6 +1023,8 @@
@@ -1017,6 +1035,8 @@
ssh_packet_send(session);
}
@ -558,9 +557,9 @@ diff --color -ru ../libssh-0.9.6/src/gssapi.c ./src/gssapi.c
if (maj_stat == GSS_S_COMPLETE) {
ssh_gssapi_send_mic(session);
session->auth.state = SSH_AUTH_STATE_GSSAPI_MIC_SENT;
diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
--- ../libssh-0.9.6/src/kex.c 2023-04-27 12:22:39.798925404 +0200
+++ ./src/kex.c 2023-04-27 12:24:08.450478574 +0200
diff --color -ru ../libssh-0.10.4/src/kex.c ./src/kex.c
--- ../libssh-0.10.4/src/kex.c 2023-04-27 14:25:46.368381754 +0200
+++ ./src/kex.c 2023-04-27 14:36:02.692475307 +0200
@@ -28,6 +28,7 @@
#include <stdio.h>
#include <stdbool.h>
@ -569,7 +568,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
#include "libssh/priv.h"
#include "libssh/buffer.h"
#include "libssh/dh.h"
@@ -305,6 +306,10 @@
@@ -328,6 +329,10 @@
int is_wrong = 1;
@ -580,7 +579,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
colon = strchr(client_str, ',');
if (colon == NULL) {
client_kex_len = strlen(client_str);
@@ -331,6 +336,7 @@
@@ -354,6 +359,7 @@
SSH_PACKET_CALLBACK(ssh_packet_kexinit)
{
int i, ok;
@ -588,7 +587,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
int server_kex = session->server;
ssh_string str = NULL;
char *strings[SSH_KEX_METHODS] = {0};
@@ -344,35 +350,67 @@
@@ -367,35 +373,67 @@
(void)type;
(void)user;
@ -666,7 +665,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
goto error;
}
}
@@ -385,7 +423,8 @@
@@ -408,7 +446,8 @@
rc = ssh_buffer_add_ssh_string(session->in_hashbuf, str);
if (rc < 0) {
@ -676,7 +675,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
goto error;
}
@@ -398,14 +437,14 @@
@@ -421,14 +460,14 @@
str = NULL;
}
@ -694,7 +693,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
}
}
@@ -419,30 +458,48 @@
@@ -442,30 +481,48 @@
* that its value is included when computing the session ID (see
* 'make_sessionid').
*/
@ -758,7 +757,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
/* The client supports extension negotiation */
session->extensions |= SSH_EXT_NEGOTIATION;
@@ -452,14 +509,14 @@
@@ -475,14 +532,14 @@
* by the client and enable the respective extensions to provide
* correct signature in the next packet if RSA is negotiated
*/
@ -778,7 +777,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
if (is_allowed != NULL) {
session->extensions |= SSH_EXT_SIG_RSA_SHA512;
}
@@ -469,10 +526,9 @@
@@ -492,10 +549,9 @@
ok = ssh_match_group(hostkeys, "rsa-sha2-256");
if (ok) {
/* Check if rsa-sha2-256 is allowed by config */
@ -792,7 +791,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
if (is_allowed != NULL) {
session->extensions |= SSH_EXT_SIG_RSA_SHA256;
}
@@ -488,7 +544,7 @@
@@ -511,7 +567,7 @@
(session->extensions & SSH_EXT_SIG_RSA_SHA512)) {
session->extensions &= ~(SSH_EXT_SIG_RSA_SHA256 | SSH_EXT_SIG_RSA_SHA512);
rsa_sig_ext = ssh_find_matching("rsa-sha2-512,rsa-sha2-256",
@ -801,7 +800,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
if (rsa_sig_ext == NULL) {
goto error; /* should never happen */
} else if (strcmp(rsa_sig_ext, "rsa-sha2-512") == 0) {
@@ -507,24 +563,16 @@
@@ -530,24 +586,16 @@
session->extensions & SSH_EXT_SIG_RSA_SHA256 ? "SHA256" : "",
session->extensions & SSH_EXT_SIG_RSA_SHA512 ? " SHA512" : "");
}
@ -832,7 +831,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
session->ssh_connection_callback(session);
return SSH_PACKET_USED;
@@ -672,14 +720,18 @@
@@ -695,14 +743,18 @@
int i;
size_t kex_len, len;
@ -853,7 +852,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
/* Set the list of allowed algorithms in order of preference, if it hadn't
* been set yet. */
for (i = 0; i < SSH_KEX_METHODS; i++) {
@@ -749,15 +801,89 @@
@@ -772,15 +824,89 @@
return NULL;
}
@ -945,7 +944,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
int i;
/* Here we should drop the ext-info-c from the list so we avoid matching.
@@ -768,52 +894,41 @@
@@ -791,52 +917,41 @@
}
for (i = 0; i < SSH_KEX_METHODS; i++) {
@ -1023,7 +1022,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
session->next_crypto->kex_methods[SSH_KEX],
session->next_crypto->kex_methods[SSH_HOSTKEYS],
session->next_crypto->kex_methods[SSH_CRYPT_C_S],
@@ -830,63 +945,116 @@
@@ -853,63 +968,116 @@
/* this function only sends the predefined set of kex methods */
@ -1185,7 +1184,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
}
/*
@@ -929,7 +1097,7 @@
@@ -952,7 +1120,7 @@
}
session->dh_handshake_state = DH_STATE_INIT;
@ -1194,7 +1193,7 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
if (rc < 0) {
SSH_LOG(SSH_LOG_PACKET, "Failed to send kex");
return rc;
@@ -1006,33 +1174,6 @@
@@ -1142,33 +1310,6 @@
client_hash = session->in_hashbuf;
}
@ -1228,11 +1227,11 @@ diff --color -ru ../libssh-0.9.6/src/kex.c ./src/kex.c
rc = ssh_dh_get_next_server_publickey_blob(session, &server_pubkey_blob);
if (rc != SSH_OK) {
goto error;
diff --color -ru ../libssh-0.9.6/src/packet.c ./src/packet.c
--- ../libssh-0.9.6/src/packet.c 2023-04-27 12:22:39.811925413 +0200
+++ ./src/packet.c 2023-04-27 12:24:04.682475779 +0200
diff --color -ru ../libssh-0.10.4/src/packet.c ./src/packet.c
--- ../libssh-0.10.4/src/packet.c 2023-04-27 14:25:46.334381403 +0200
+++ ./src/packet.c 2023-04-27 14:34:36.432602740 +0200
@@ -366,6 +366,11 @@
* - session->dh_handhsake_state = DH_STATE_NEWKEYS_SENT
* - session->dh_handshake_state = DH_STATE_NEWKEYS_SENT
* */
+ if (!session->server) {
@ -1309,7 +1308,7 @@ diff --color -ru ../libssh-0.9.6/src/packet.c ./src/packet.c
}
/** @internal
@@ -1928,7 +1944,7 @@
@@ -1930,7 +1946,7 @@
memcpy(session->next_crypto->session_id,
session->current_crypto->session_id,
session_id_len);
@ -1318,9 +1317,9 @@ diff --color -ru ../libssh-0.9.6/src/packet.c ./src/packet.c
return SSH_OK;
}
diff --color -ru ../libssh-0.9.6/src/packet_cb.c ./src/packet_cb.c
--- ../libssh-0.9.6/src/packet_cb.c 2023-04-27 12:22:39.799925404 +0200
+++ ./src/packet_cb.c 2023-04-27 12:24:04.682475779 +0200
diff --color -ru ../libssh-0.10.4/src/packet_cb.c ./src/packet_cb.c
--- ../libssh-0.10.4/src/packet_cb.c 2023-04-27 14:25:46.334381403 +0200
+++ ./src/packet_cb.c 2023-04-27 14:34:36.428602699 +0200
@@ -156,6 +156,9 @@
session->next_crypto->digest_len);
SSH_SIGNATURE_FREE(sig);
@ -1331,9 +1330,9 @@ diff --color -ru ../libssh-0.9.6/src/packet_cb.c ./src/packet_cb.c
goto error;
}
SSH_LOG(SSH_LOG_DEBUG,"Signature verified and valid");
diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
--- ../libssh-0.9.6/src/server.c 2023-04-27 12:22:39.800925405 +0200
+++ ./src/server.c 2023-04-27 12:24:04.683475780 +0200
diff --color -ru ../libssh-0.10.4/src/server.c ./src/server.c
--- ../libssh-0.10.4/src/server.c 2023-04-27 14:25:46.347381537 +0200
+++ ./src/server.c 2023-04-27 14:35:27.041113642 +0200
@@ -92,7 +92,11 @@
size_t len;
int ok;
@ -1347,7 +1346,7 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
ok = ssh_get_random(server->cookie, 16, 0);
if (!ok) {
@@ -335,117 +339,121 @@
@@ -336,116 +340,119 @@
* @brief A function to be called each time a step has been done in the
* connection.
*/
@ -1363,6 +1362,20 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
- break;
- case SSH_SESSION_STATE_BANNER_RECEIVED:
- if (session->clientbanner == NULL) {
- goto error;
- }
- set_status(session, 0.4f);
- SSH_LOG(SSH_LOG_DEBUG,
- "SSH client banner: %s", session->clientbanner);
-
- /* Here we analyze the different protocols the server allows. */
- rc = ssh_analyze_banner(session, 1);
- if (rc < 0) {
- ssh_set_error(session, SSH_FATAL,
- "No version of SSH protocol usable (banner: %s)",
- session->clientbanner);
- goto error;
- }
+ switch (session->session_state) {
+ case SSH_SESSION_STATE_NONE:
+ case SSH_SESSION_STATE_CONNECTING:
@ -1384,11 +1397,16 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
+ session->clientbanner);
+ goto error;
+ }
+
- /* from now, the packet layer is handling incoming packets */
- ssh_packet_register_socket_callback(session, session->socket);
+ /* from now, the packet layer is handling incoming packets */
+ session->socket_callbacks.data = ssh_packet_socket_callback;
+ ssh_packet_register_socket_callback(session, session->socket);
+
- ssh_packet_set_default_callbacks(session);
- set_status(session, 0.5f);
- session->session_state=SSH_SESSION_STATE_INITIAL_KEX;
- if (ssh_send_kex(session, 1) < 0) {
+ ssh_packet_set_default_callbacks(session);
+ set_status(session, 0.5f);
+ session->session_state = SSH_SESSION_STATE_INITIAL_KEX;
@ -1405,43 +1423,6 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
+ if (server_set_kex(session) == SSH_ERROR)
goto error;
- }
- set_status(session, 0.4f);
- SSH_LOG(SSH_LOG_DEBUG,
- "SSH client banner: %s", session->clientbanner);
-
- /* Here we analyze the different protocols the server allows. */
- rc = ssh_analyze_banner(session, 1);
- if (rc < 0) {
- ssh_set_error(session, SSH_FATAL,
- "No version of SSH protocol usable (banner: %s)",
- session->clientbanner);
+ /* We are in a rekeying, so we need to send the server kex */
+ if (ssh_send_kex(session) < 0)
goto error;
- }
+ }
+ ssh_list_kex(&session->next_crypto->client_kex); // log client kex
+ if (ssh_kex_select_methods(session) < 0) {
+ goto error;
+ }
+ if (crypt_set_algorithms_server(session) == SSH_ERROR)
+ goto error;
+ set_status(session, 0.8f);
+ session->session_state = SSH_SESSION_STATE_DH;
+ break;
+ case SSH_SESSION_STATE_DH:
+ if (session->dh_handshake_state == DH_STATE_FINISHED) {
- /* from now, the packet layer is handling incoming packets */
- session->socket_callbacks.data=ssh_packet_socket_callback;
- ssh_packet_register_socket_callback(session, session->socket);
-
- ssh_packet_set_default_callbacks(session);
- set_status(session, 0.5f);
- session->session_state=SSH_SESSION_STATE_INITIAL_KEX;
- if (ssh_send_kex(session, 1) < 0) {
- goto error;
- }
- break;
- case SSH_SESSION_STATE_INITIAL_KEX:
- /* TODO: This state should disappear in favor of get_key handle */
@ -1457,12 +1438,27 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
- }
- ssh_list_kex(&session->next_crypto->client_kex); // log client kex
- if (ssh_kex_select_methods(session) < 0) {
+ /* We are in a rekeying, so we need to send the server kex */
+ if (ssh_send_kex(session) < 0)
goto error;
- }
- if (crypt_set_algorithms_server(session) == SSH_ERROR)
+ }
+ ssh_list_kex(&session->next_crypto->client_kex); // log client kex
+ if (ssh_kex_select_methods(session) < 0) {
+ goto error;
+ }
+ if (crypt_set_algorithms_server(session) == SSH_ERROR)
+ goto error;
+ set_status(session, 0.8f);
+ session->session_state = SSH_SESSION_STATE_DH;
+ break;
+ case SSH_SESSION_STATE_DH:
+ if (session->dh_handshake_state == DH_STATE_FINISHED) {
+
+ rc = ssh_packet_set_newkeys(session, SSH_DIRECTION_IN);
+ if (rc != SSH_OK) {
goto error;
}
- if (crypt_set_algorithms_server(session) == SSH_ERROR)
- goto error;
- set_status(session,0.8f);
- session->session_state=SSH_SESSION_STATE_DH;
- break;
@ -1473,7 +1469,8 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
- if (rc != SSH_OK) {
- goto error;
- }
+
+ }
+ /*
+ * If the client supports extension negotiation, we will send
+ * our supported extensions now. This is the first message after
@ -1481,7 +1478,6 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
+ */
+ if (session->extensions & SSH_EXT_NEGOTIATION &&
+ session->session_state != SSH_SESSION_STATE_AUTHENTICATED) {
/*
- * If the client supports extension negotiation, we will send
- * our supported extensions now. This is the first message after
@ -1561,20 +1557,20 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
}
/**
@@ -459,16 +467,17 @@
@@ -459,16 +466,17 @@
* @param user is a pointer to session
* @returns Number of bytes processed, or zero if the banner is not complete.
*/
-static int callback_receive_banner(const void *data, size_t len, void *user) {
-static size_t callback_receive_banner(const void *data, size_t len, void *user) {
- char *buffer = (char *) data;
- ssh_session session = (ssh_session) user;
+static int callback_receive_banner(const void *data, size_t len, void *user)
+static size_t callback_receive_banner(const void *data, size_t len, void *user)
+{
+ char *buffer = (char *)data;
+ ssh_session session = (ssh_session)user;
char *str = NULL;
size_t i;
int ret=0;
size_t processed = 0;
for (i = 0; i < len; i++) {
#ifdef WITH_PCAP
@ -1583,7 +1579,7 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
ssh_pcap_context_write(session->pcap_ctx,
SSH_PCAP_DIR_IN,
buffer,
@@ -477,11 +486,11 @@
@@ -477,11 +485,11 @@
}
#endif
if (buffer[i] == '\r') {
@ -1597,8 +1593,8 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
str = strdup(buffer);
/* number of bytes read */
@@ -494,10 +503,11 @@
return ret;
@@ -494,10 +502,11 @@
return processed;
}
- if(i > 127) {
@ -1611,7 +1607,7 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
return 0;
}
@@ -525,10 +535,14 @@
@@ -549,10 +558,14 @@
}
/* Do the banner and key exchange */
@ -1629,7 +1625,7 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
rc = ssh_send_banner(session, 1);
if (rc < 0) {
return SSH_ERROR;
@@ -539,27 +553,28 @@
@@ -563,27 +576,28 @@
session->ssh_connection_callback = ssh_server_connection_callback;
session->session_state = SSH_SESSION_STATE_SOCKET_CONNECTED;
ssh_socket_set_callbacks(session->socket,&session->socket_callbacks);
@ -1668,9 +1664,9 @@ diff --color -ru ../libssh-0.9.6/src/server.c ./src/server.c
}
/* messages */
diff --color -ru ../libssh-0.9.6/src/token.c ./src/token.c
--- ../libssh-0.9.6/src/token.c 2021-03-15 08:11:33.000000000 +0100
+++ ./src/token.c 2023-04-27 12:21:30.260820657 +0200
diff --color -ru ../libssh-0.10.4/src/token.c ./src/token.c
--- ../libssh-0.10.4/src/token.c 2023-04-27 14:25:46.346381527 +0200
+++ ./src/token.c 2023-04-27 14:34:36.426602679 +0200
@@ -87,7 +87,7 @@
return NULL;
}
@ -1680,10 +1676,10 @@ diff --color -ru ../libssh-0.9.6/src/token.c ./src/token.c
if (tokens->buffer == NULL) {
goto error;
}
diff --color -ru ../libssh-0.9.6/src/wrapper.c ./src/wrapper.c
--- ../libssh-0.9.6/src/wrapper.c 2021-08-26 14:27:44.000000000 +0200
+++ ./src/wrapper.c 2023-04-27 12:21:30.260820657 +0200
@@ -147,15 +147,16 @@
diff --color -ru ../libssh-0.10.4/src/wrapper.c ./src/wrapper.c
--- ../libssh-0.10.4/src/wrapper.c 2022-08-30 13:26:05.000000000 +0200
+++ ./src/wrapper.c 2023-04-27 14:31:16.130584204 +0200
@@ -150,15 +150,16 @@
SAFE_FREE(cipher);
}
@ -1708,10 +1704,24 @@ diff --color -ru ../libssh-0.9.6/src/wrapper.c ./src/wrapper.c
}
void crypto_free(struct ssh_crypto_struct *crypto)
diff --color -ru ../libssh-0.9.6/tests/client/torture_rekey.c ./tests/client/torture_rekey.c
--- ../libssh-0.9.6/tests/client/torture_rekey.c 2021-08-26 14:27:44.000000000 +0200
+++ ./tests/client/torture_rekey.c 2023-04-27 12:24:04.684475780 +0200
@@ -651,6 +651,92 @@
diff --color -ru ../libssh-0.10.4/tests/client/torture_rekey.c ./tests/client/torture_rekey.c
--- ../libssh-0.10.4/tests/client/torture_rekey.c 2022-09-02 09:56:54.000000000 +0200
+++ ./tests/client/torture_rekey.c 2023-04-27 14:38:20.352896968 +0200
@@ -192,10 +192,11 @@
rc = ssh_userauth_publickey_auto(s->ssh.session, NULL, NULL);
assert_int_equal(rc, SSH_AUTH_SUCCESS);
- /* send ignore packets of up to 1KB to trigger rekey */
+ /* send ignore packets of up to 1KB to trigger rekey. Send little bit more
+ * to make sure it completes with all different ciphers */
memset(data, 0, sizeof(data));
memset(data, 'A', 128);
- for (i = 0; i < 16; i++) {
+ for (i = 0; i < KEX_RETRY; i++) {
ssh_send_ignore(s->ssh.session, data);
ssh_handle_packets(s->ssh.session, 50);
}
@@ -671,6 +672,92 @@
#endif /* WITH_SFTP */
@ -1804,12 +1814,10 @@ diff --color -ru ../libssh-0.9.6/tests/client/torture_rekey.c ./tests/client/tor
int torture_run_tests(void) {
int rc;
struct CMUnitTest tests[] = {
@@ -671,19 +757,34 @@
cmocka_unit_test_setup_teardown(torture_rekey_different_kex,
@@ -704,6 +791,33 @@
session_setup,
session_teardown),
- /* Note, that this modifies the sshd_config */
+ /* TODO verify the two rekey are possible and the states are not broken after rekey */
/* TODO verify the two rekey are possible and the states are not broken after rekey */
+
+ cmocka_unit_test_setup_teardown(torture_rekey_server_different_kex,
+ session_setup,
@ -1817,25 +1825,22 @@ diff --color -ru ../libssh-0.9.6/tests/client/torture_rekey.c ./tests/client/tor
+ /* Note, that these tests modify the sshd_config so follow-up tests
+ * might get unexpected behavior if they do not update the server with
+ * torture_update_sshd_config() too */
cmocka_unit_test_setup_teardown(torture_rekey_server_send,
session_setup,
session_teardown),
+ cmocka_unit_test_setup_teardown(torture_rekey_server_send,
+ session_setup,
+ session_teardown),
+ cmocka_unit_test_setup_teardown(torture_rekey_guess_send,
+ session_setup,
+ session_teardown),
+ cmocka_unit_test_setup_teardown(torture_rekey_guess_wrong_send,
+ session_setup,
+ session_teardown),
#ifdef WITH_SFTP
cmocka_unit_test_setup_teardown(torture_rekey_server_recv,
session_setup_sftp_server,
session_teardown),
-#endif /* WITH_SFTP */
- cmocka_unit_test_setup_teardown(torture_rekey_server_different_kex,
+#ifdef WITH_SFTP
+ cmocka_unit_test_setup_teardown(torture_rekey_server_recv,
+ session_setup_sftp_server,
+ session_teardown),
+ cmocka_unit_test_setup_teardown(torture_rekey_guess_recv,
session_setup,
session_teardown),
- /* TODO verify the two rekey are possible and the states are not broken after rekey */
+ session_setup,
+ session_teardown),
+ cmocka_unit_test_setup_teardown(torture_rekey_guess_wrong_recv,
+ session_setup,
+ session_teardown),
@ -1843,3 +1848,14 @@ diff --color -ru ../libssh-0.9.6/tests/client/torture_rekey.c ./tests/client/tor
};
ssh_init();
diff --color -ru ../libssh-0.10.4/tests/fuzz/ssh_server_fuzzer.c ./tests/fuzz/ssh_server_fuzzer.c
--- ../libssh-0.10.4/tests/fuzz/ssh_server_fuzzer.c 2022-07-07 15:53:51.000000000 +0200
+++ ./tests/fuzz/ssh_server_fuzzer.c 2023-04-27 14:28:50.620219301 +0200
@@ -186,6 +186,7 @@
ssh_set_auth_methods(session, SSH_AUTH_METHOD_NONE);
ssh_callbacks_init(&server_cb);
+ ssh_set_server_callbacks(session, &server_cb);
rc = ssh_bind_accept_fd(sshbind, session, socket_fds[0]);
assert(rc == SSH_OK);

842
options_apply.patch Normal file
View File

@ -0,0 +1,842 @@
From 11c0d687a081fe64501e21c95def7f893611d029 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <npocs@redhat.com>
Date: Wed, 16 Nov 2022 10:40:38 +0100
Subject: [PATCH 1/5] Add a placehohlder for non-expanded identities
Expanding a string twice could lead to unwanted behaviour.
This solution creates a ssh_list (`opts.identites_non_exp`) to store the strings
before expansion and by using ssh_apply it moves the string to the
`opts.identities`. This way the expanded strings are separated.
Signed-off-by: Norbert Pocs <npocs@redhat.com>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
include/libssh/session.h | 1 +
src/options.c | 86 +++++++++++++++++++++++++---------------
src/session.c | 23 +++++++++--
3 files changed, 75 insertions(+), 35 deletions(-)
diff --git a/include/libssh/session.h b/include/libssh/session.h
index d3e5787c..e22b0d67 100644
--- a/include/libssh/session.h
+++ b/include/libssh/session.h
@@ -209,6 +209,7 @@ struct ssh_session_struct {
#endif
struct {
struct ssh_list *identity;
+ struct ssh_list *identity_non_exp;
char *username;
char *host;
char *bindaddr; /* bind the client to an ip addr */
diff --git a/src/options.c b/src/options.c
index 56e09c65..bb085384 100644
--- a/src/options.c
+++ b/src/options.c
@@ -52,7 +52,7 @@
* @brief Duplicate the options of a session structure.
*
* If you make several sessions with the same options this is useful. You
- * cannot use twice the same option structure in ssh_session_connect.
+ * cannot use twice the same option structure in ssh_connect.
*
* @param src The session to use to copy the options.
*
@@ -61,13 +61,14 @@
*
* @returns 0 on success, -1 on error with errno set.
*
- * @see ssh_session_connect()
+ * @see ssh_connect()
* @see ssh_free()
*/
int ssh_options_copy(ssh_session src, ssh_session *dest)
{
ssh_session new;
struct ssh_iterator *it = NULL;
+ struct ssh_list *list = NULL;
char *id = NULL;
int i;
@@ -105,14 +106,15 @@ int ssh_options_copy(ssh_session src, ssh_session *dest)
}
/* Remove the default identities */
- for (id = ssh_list_pop_head(char *, new->opts.identity);
+ for (id = ssh_list_pop_head(char *, new->opts.identity_non_exp);
id != NULL;
- id = ssh_list_pop_head(char *, new->opts.identity)) {
+ id = ssh_list_pop_head(char *, new->opts.identity_non_exp)) {
SAFE_FREE(id);
}
/* Copy the new identities from the source list */
- if (src->opts.identity != NULL) {
- it = ssh_list_get_iterator(src->opts.identity);
+ list = new->opts.identity_non_exp;
+ it = ssh_list_get_iterator(src->opts.identity_non_exp);
+ for (i = 0; i < 2; i++) {
while (it) {
int rc;
@@ -122,7 +124,7 @@ int ssh_options_copy(ssh_session src, ssh_session *dest)
return -1;
}
- rc = ssh_list_append(new->opts.identity, id);
+ rc = ssh_list_append(list, id);
if (rc < 0) {
free(id);
ssh_free(new);
@@ -130,6 +132,10 @@ int ssh_options_copy(ssh_session src, ssh_session *dest)
}
it = it->next;
}
+
+ /* copy the identity list if there is any already */
+ list = new->opts.identity;
+ it = ssh_list_get_iterator(src->opts.identity);
}
if (src->opts.sshdir != NULL) {
@@ -331,7 +337,7 @@ int ssh_options_set_algo(ssh_session session,
* Add a new identity file (const char *, format string) to
* the identity list.\n
* \n
- * By default identity, id_dsa and id_rsa are checked.\n
+ * By default id_rsa, id_ecdsa and id_ed25519 files are used.\n
* \n
* The identity used to authenticate with public key will be
* prepended to the list.
@@ -700,7 +706,11 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
if (q == NULL) {
return -1;
}
- rc = ssh_list_prepend(session->opts.identity, q);
+ if (session->opts.exp_flags & SSH_OPT_EXP_FLAG_IDENTITY) {
+ rc = ssh_list_append(session->opts.identity_non_exp, q);
+ } else {
+ rc = ssh_list_prepend(session->opts.identity_non_exp, q);
+ }
if (rc < 0) {
free(q);
return -1;
@@ -1202,7 +1212,7 @@ int ssh_options_get_port(ssh_session session, unsigned int* port_target) {
* - SSH_OPTIONS_IDENTITY:
* Get the first identity file name (const char *).\n
* \n
- * By default identity, id_dsa and id_rsa are checked.
+ * By default id_rsa, id_ecdsa and id_ed25519 files are used.
*
* - SSH_OPTIONS_PROXYCOMMAND:
* Get the proxycommand necessary to log into the
@@ -1246,7 +1256,11 @@ int ssh_options_get(ssh_session session, enum ssh_options_e type, char** value)
break;
}
case SSH_OPTIONS_IDENTITY: {
- struct ssh_iterator *it = ssh_list_get_iterator(session->opts.identity);
+ struct ssh_iterator *it;
+ it = ssh_list_get_iterator(session->opts.identity);
+ if (it == NULL) {
+ it = ssh_list_get_iterator(session->opts.identity_non_exp);
+ }
if (it == NULL) {
return SSH_ERROR;
}
@@ -1541,7 +1555,6 @@ out:
int ssh_options_apply(ssh_session session)
{
- struct ssh_iterator *it;
char *tmp;
int rc;
@@ -1586,15 +1599,17 @@ int ssh_options_apply(ssh_session session)
size_t plen = strlen(session->opts.ProxyCommand) +
5 /* strlen("exec ") */;
- p = malloc(plen + 1 /* \0 */);
- if (p == NULL) {
- return -1;
- }
+ if (strncmp(session->opts.ProxyCommand, "exec ", 5) != 0) {
+ p = malloc(plen + 1 /* \0 */);
+ if (p == NULL) {
+ return -1;
+ }
- rc = snprintf(p, plen + 1, "exec %s", session->opts.ProxyCommand);
- if ((size_t)rc != plen) {
- free(p);
- return -1;
+ rc = snprintf(p, plen + 1, "exec %s", session->opts.ProxyCommand);
+ if ((size_t)rc != plen) {
+ free(p);
+ return -1;
+ }
}
tmp = ssh_path_expand_escape(session, p);
@@ -1606,24 +1621,33 @@ int ssh_options_apply(ssh_session session)
session->opts.ProxyCommand = tmp;
}
- for (it = ssh_list_get_iterator(session->opts.identity);
- it != NULL;
- it = it->next) {
- char *id = (char *) it->data;
- if (strncmp(id, "pkcs11:", 6) == 0) {
+ for (tmp = ssh_list_pop_head(char *, session->opts.identity_non_exp);
+ tmp != NULL;
+ tmp = ssh_list_pop_head(char *, session->opts.identity_non_exp)) {
+ char *id = tmp;
+ if (strncmp(id, "pkcs11:", 6) != 0) {
/* PKCS#11 URIs are using percent-encoding so we can not mix
* it with ssh expansion of ssh escape characters.
- * Skip these identities now, before we will have PKCS#11 support
*/
- continue;
+ tmp = ssh_path_expand_escape(session, id);
+ if (tmp == NULL) {
+ return -1;
+ }
+ free(id);
}
- tmp = ssh_path_expand_escape(session, id);
- if (tmp == NULL) {
+
+ /* use append to keep the order at first call and use prepend
+ * to put anything that comes on the nth calls to the beginning */
+ if (session->opts.exp_flags & SSH_OPT_EXP_FLAG_IDENTITY) {
+ rc = ssh_list_prepend(session->opts.identity, tmp);
+ } else {
+ rc = ssh_list_append(session->opts.identity, tmp);
+ }
+ if (rc != SSH_OK) {
return -1;
}
- free(id);
- it->data = tmp;
}
+ session->opts.exp_flags |= SSH_OPT_EXP_FLAG_IDENTITY;
return 0;
}
diff --git a/src/session.c b/src/session.c
index 64e54957..34a492e4 100644
--- a/src/session.c
+++ b/src/session.c
@@ -118,13 +118,17 @@ ssh_session ssh_new(void)
if (session->opts.identity == NULL) {
goto err;
}
+ session->opts.identity_non_exp = ssh_list_new();
+ if (session->opts.identity_non_exp == NULL) {
+ goto err;
+ }
id = strdup("%d/id_ed25519");
if (id == NULL) {
goto err;
}
- rc = ssh_list_append(session->opts.identity, id);
+ rc = ssh_list_append(session->opts.identity_non_exp, id);
if (rc == SSH_ERROR) {
goto err;
}
@@ -134,7 +138,7 @@ ssh_session ssh_new(void)
if (id == NULL) {
goto err;
}
- rc = ssh_list_append(session->opts.identity, id);
+ rc = ssh_list_append(session->opts.identity_non_exp, id);
if (rc == SSH_ERROR) {
goto err;
}
@@ -144,7 +148,7 @@ ssh_session ssh_new(void)
if (id == NULL) {
goto err;
}
- rc = ssh_list_append(session->opts.identity, id);
+ rc = ssh_list_append(session->opts.identity_non_exp, id);
if (rc == SSH_ERROR) {
goto err;
}
@@ -154,7 +158,7 @@ ssh_session ssh_new(void)
if (id == NULL) {
goto err;
}
- rc = ssh_list_append(session->opts.identity, id);
+ rc = ssh_list_append(session->opts.identity_non_exp, id);
if (rc == SSH_ERROR) {
goto err;
}
@@ -284,6 +288,17 @@ void ssh_free(ssh_session session)
ssh_list_free(session->opts.identity);
}
+ if (session->opts.identity_non_exp) {
+ char *id;
+
+ for (id = ssh_list_pop_head(char *, session->opts.identity_non_exp);
+ id != NULL;
+ id = ssh_list_pop_head(char *, session->opts.identity_non_exp)) {
+ SAFE_FREE(id);
+ }
+ ssh_list_free(session->opts.identity_non_exp);
+ }
+
while ((b = ssh_list_pop_head(struct ssh_buffer_struct *,
session->out_queue)) != NULL) {
SSH_BUFFER_FREE(b);
--
2.38.1
From 4cb84b99fdb1ffd26c0241f5809e4f67ddd407c6 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <npocs@redhat.com>
Date: Wed, 16 Nov 2022 11:03:30 +0100
Subject: [PATCH 2/5] tests: Use opts.identites_non_exp not opts.identities
The configuration of identities are first saved to `opts.identities_non_exp`,
then moved to `opts.identities` after calling ssh_options_apply and expanding
the identity strings. These tests are testing against the proper configuration
Signed-off-by: Norbert Pocs <npocs@redhat.com>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/client/torture_auth_pkcs11.c | 2 +-
tests/unittests/torture_config.c | 3 ++-
tests/unittests/torture_options.c | 14 +++++++-------
3 files changed, 10 insertions(+), 9 deletions(-)
diff --git a/tests/client/torture_auth_pkcs11.c b/tests/client/torture_auth_pkcs11.c
index ee97bff4..e75fea0e 100644
--- a/tests/client/torture_auth_pkcs11.c
+++ b/tests/client/torture_auth_pkcs11.c
@@ -196,7 +196,7 @@ static void torture_auth_autopubkey(void **state, const char *obj_name, const ch
rc = ssh_options_set(session, SSH_OPTIONS_IDENTITY, priv_uri);
assert_int_equal(rc, SSH_OK);
- assert_string_equal(session->opts.identity->root->data, priv_uri);
+ assert_string_equal(session->opts.identity_non_exp->root->data, priv_uri);
rc = ssh_connect(session);
assert_int_equal(rc, SSH_OK);
diff --git a/tests/unittests/torture_config.c b/tests/unittests/torture_config.c
index 354adc2f..100e68f6 100644
--- a/tests/unittests/torture_config.c
+++ b/tests/unittests/torture_config.c
@@ -2078,7 +2078,8 @@ static void torture_config_identity(void **state)
_parse_config(session, NULL, LIBSSH_TESTCONFIG_STRING13, SSH_OK);
- it = ssh_list_get_iterator(session->opts.identity);
+ /* The identities are first added to this temporary list before expanding */
+ it = ssh_list_get_iterator(session->opts.identity_non_exp);
assert_non_null(it);
id = it->data;
/* The identities are prepended to the list so we start with second one */
diff --git a/tests/unittests/torture_options.c b/tests/unittests/torture_options.c
index dc4df383..3be2de8a 100644
--- a/tests/unittests/torture_options.c
+++ b/tests/unittests/torture_options.c
@@ -406,12 +406,12 @@ static void torture_options_set_identity(void **state) {
rc = ssh_options_set(session, SSH_OPTIONS_ADD_IDENTITY, "identity1");
assert_true(rc == 0);
- assert_string_equal(session->opts.identity->root->data, "identity1");
+ assert_string_equal(session->opts.identity_non_exp->root->data, "identity1");
rc = ssh_options_set(session, SSH_OPTIONS_IDENTITY, "identity2");
assert_true(rc == 0);
- assert_string_equal(session->opts.identity->root->data, "identity2");
- assert_string_equal(session->opts.identity->root->next->data, "identity1");
+ assert_string_equal(session->opts.identity_non_exp->root->data, "identity2");
+ assert_string_equal(session->opts.identity_non_exp->root->next->data, "identity1");
}
static void torture_options_get_identity(void **state) {
@@ -429,7 +429,7 @@ static void torture_options_get_identity(void **state) {
rc = ssh_options_set(session, SSH_OPTIONS_IDENTITY, "identity2");
assert_int_equal(rc, SSH_OK);
- assert_string_equal(session->opts.identity->root->data, "identity2");
+ assert_string_equal(session->opts.identity_non_exp->root->data, "identity2");
rc = ssh_options_get(session, SSH_OPTIONS_IDENTITY, &identity);
assert_int_equal(rc, SSH_OK);
assert_non_null(identity);
@@ -867,9 +867,9 @@ static void torture_options_copy(void **state)
assert_non_null(new);
/* Check the identities match */
- it = ssh_list_get_iterator(session->opts.identity);
+ it = ssh_list_get_iterator(session->opts.identity_non_exp);
assert_non_null(it);
- it2 = ssh_list_get_iterator(new->opts.identity);
+ it2 = ssh_list_get_iterator(new->opts.identity_non_exp);
assert_non_null(it2);
while (it != NULL && it2 != NULL) {
assert_string_equal(it->data, it2->data);
@@ -956,7 +956,7 @@ static void torture_options_getopt(void **state)
"aes128-ctr");
assert_string_equal(session->opts.wanted_methods[SSH_CRYPT_S_C],
"aes128-ctr");
- assert_string_equal(session->opts.identity->root->data, "id_rsa");
+ assert_string_equal(session->opts.identity_non_exp->root->data, "id_rsa");
#ifdef WITH_ZLIB
assert_string_equal(session->opts.wanted_methods[SSH_COMP_C_S],
"zlib@openssh.com,zlib,none");
--
2.38.1
From cd30217c9032419ebcf722c0bfc6b5ebfa3518d0 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <npocs@redhat.com>
Date: Wed, 16 Nov 2022 16:51:02 +0100
Subject: [PATCH 3/5] Add flags for escape expand operation
Calling `ssh_options_apply` more times can result in an unwanted behaviour of
expanding the escape characters more times. Adding flags to check if the
expansion was already done on the current string variables.
Signed-off-by: Norbert Pocs <npocs@redhat.com>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
include/libssh/session.h | 7 ++++
src/options.c | 91 ++++++++++++++++++++++++----------------
src/session.c | 2 +
3 files changed, 63 insertions(+), 37 deletions(-)
diff --git a/include/libssh/session.h b/include/libssh/session.h
index e22b0d67..cf219c2a 100644
--- a/include/libssh/session.h
+++ b/include/libssh/session.h
@@ -93,6 +93,12 @@ enum ssh_pending_call_e {
#define SSH_OPT_FLAG_KBDINT_AUTH 0x4
#define SSH_OPT_FLAG_GSSAPI_AUTH 0x8
+/* Escape expansion of different variables */
+#define SSH_OPT_EXP_FLAG_KNOWNHOSTS 0x1
+#define SSH_OPT_EXP_FLAG_GLOBAL_KNOWNHOSTS 0x2
+#define SSH_OPT_EXP_FLAG_PROXYCOMMAND 0x4
+#define SSH_OPT_EXP_FLAG_IDENTITY 0x8
+
/* extensions flags */
/* negotiation enabled */
#define SSH_EXT_NEGOTIATION 0x01
@@ -232,6 +238,7 @@ struct ssh_session_struct {
char *gss_client_identity;
int gss_delegate_creds;
int flags;
+ int exp_flags;
int nodelay;
bool config_processed;
uint8_t options_seen[SOC_MAX];
diff --git a/src/options.c b/src/options.c
index bb085384..c566244b 100644
--- a/src/options.c
+++ b/src/options.c
@@ -730,6 +730,7 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
ssh_set_error_oom(session);
return -1;
}
+ session->opts.exp_flags &= ~SSH_OPT_EXP_FLAG_KNOWNHOSTS;
}
break;
case SSH_OPTIONS_GLOBAL_KNOWNHOSTS:
@@ -751,6 +752,7 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
ssh_set_error_oom(session);
return -1;
}
+ session->opts.exp_flags &= ~SSH_OPT_EXP_FLAG_GLOBAL_KNOWNHOSTS;
}
break;
case SSH_OPTIONS_TIMEOUT:
@@ -1014,6 +1016,7 @@ int ssh_options_set(ssh_session session, enum ssh_options_e type,
return -1;
}
session->opts.ProxyCommand = q;
+ session->opts.exp_flags &= ~SSH_OPT_EXP_FLAG_PROXYCOMMAND;
}
}
break;
@@ -1572,53 +1575,67 @@ int ssh_options_apply(ssh_session session)
}
}
- if (session->opts.knownhosts == NULL) {
- tmp = ssh_path_expand_escape(session, "%d/known_hosts");
- } else {
- tmp = ssh_path_expand_escape(session, session->opts.knownhosts);
- }
- if (tmp == NULL) {
- return -1;
+ if ((session->opts.exp_flags & SSH_OPT_EXP_FLAG_KNOWNHOSTS) == 0) {
+ if (session->opts.knownhosts == NULL) {
+ tmp = ssh_path_expand_escape(session, "%d/known_hosts");
+ } else {
+ tmp = ssh_path_expand_escape(session, session->opts.knownhosts);
+ }
+ if (tmp == NULL) {
+ return -1;
+ }
+ free(session->opts.knownhosts);
+ session->opts.knownhosts = tmp;
+ session->opts.exp_flags |= SSH_OPT_EXP_FLAG_KNOWNHOSTS;
}
- free(session->opts.knownhosts);
- session->opts.knownhosts = tmp;
- if (session->opts.global_knownhosts == NULL) {
- tmp = strdup("/etc/ssh/ssh_known_hosts");
- } else {
- tmp = ssh_path_expand_escape(session, session->opts.global_knownhosts);
- }
- if (tmp == NULL) {
- return -1;
+ if ((session->opts.exp_flags & SSH_OPT_EXP_FLAG_GLOBAL_KNOWNHOSTS) == 0) {
+ if (session->opts.global_knownhosts == NULL) {
+ tmp = strdup("/etc/ssh/ssh_known_hosts");
+ } else {
+ tmp = ssh_path_expand_escape(session,
+ session->opts.global_knownhosts);
+ }
+ if (tmp == NULL) {
+ return -1;
+ }
+ free(session->opts.global_knownhosts);
+ session->opts.global_knownhosts = tmp;
+ session->opts.exp_flags |= SSH_OPT_EXP_FLAG_GLOBAL_KNOWNHOSTS;
}
- free(session->opts.global_knownhosts);
- session->opts.global_knownhosts = tmp;
- if (session->opts.ProxyCommand != NULL) {
- char *p = NULL;
- size_t plen = strlen(session->opts.ProxyCommand) +
- 5 /* strlen("exec ") */;
- if (strncmp(session->opts.ProxyCommand, "exec ", 5) != 0) {
- p = malloc(plen + 1 /* \0 */);
- if (p == NULL) {
- return -1;
- }
+ if ((session->opts.exp_flags & SSH_OPT_EXP_FLAG_PROXYCOMMAND) == 0) {
+ if (session->opts.ProxyCommand != NULL) {
+ char *p = NULL;
+ size_t plen = strlen(session->opts.ProxyCommand) +
+ 5 /* strlen("exec ") */;
+
+ if (strncmp(session->opts.ProxyCommand, "exec ", 5) != 0) {
+ p = malloc(plen + 1 /* \0 */);
+ if (p == NULL) {
+ return -1;
+ }
- rc = snprintf(p, plen + 1, "exec %s", session->opts.ProxyCommand);
- if ((size_t)rc != plen) {
+ rc = snprintf(p, plen + 1, "exec %s", session->opts.ProxyCommand);
+ if ((size_t)rc != plen) {
+ free(p);
+ return -1;
+ }
+ tmp = ssh_path_expand_escape(session, p);
free(p);
- return -1;
+ } else {
+ tmp = ssh_path_expand_escape(session,
+ session->opts.ProxyCommand);
}
- }
- tmp = ssh_path_expand_escape(session, p);
- free(p);
- if (tmp == NULL) {
- return -1;
+ if (tmp == NULL) {
+ return -1;
+ }
+ free(session->opts.ProxyCommand);
+ session->opts.ProxyCommand = tmp;
+ session->opts.exp_flags |= SSH_OPT_EXP_FLAG_PROXYCOMMAND;
}
- free(session->opts.ProxyCommand);
- session->opts.ProxyCommand = tmp;
}
for (tmp = ssh_list_pop_head(char *, session->opts.identity_non_exp);
diff --git a/src/session.c b/src/session.c
index 34a492e4..06f6a26f 100644
--- a/src/session.c
+++ b/src/session.c
@@ -114,6 +114,8 @@ ssh_session ssh_new(void)
SSH_OPT_FLAG_KBDINT_AUTH |
SSH_OPT_FLAG_GSSAPI_AUTH;
+ session->opts.exp_flags = 0;
+
session->opts.identity = ssh_list_new();
if (session->opts.identity == NULL) {
goto err;
--
2.38.1
From ed58082f9706f2ab3bdeca24f632356b9bc325e6 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <npocs@redhat.com>
Date: Wed, 16 Nov 2022 17:17:14 +0100
Subject: [PATCH 4/5] torture_options.c: Add identity test for ssh_options_copy
Test if the ssh_options_apply is called on session before ssh_options_copy,
then `opts.identity` ssh_list will be copied
Signed-off-by: Norbert Pocs <npocs@redhat.com>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/unittests/torture_options.c | 28 ++++++++++++++++++++++++++++
1 file changed, 28 insertions(+)
diff --git a/tests/unittests/torture_options.c b/tests/unittests/torture_options.c
index 3be2de8a..907cc8df 100644
--- a/tests/unittests/torture_options.c
+++ b/tests/unittests/torture_options.c
@@ -918,6 +918,34 @@ static void torture_options_copy(void **state)
sizeof(session->opts.options_seen));
ssh_free(new);
+
+ /* test if ssh_options_apply was called before ssh_options_copy
+ * the opts.identity list gets copied (percent expanded list) */
+ rv = ssh_options_apply(session);
+ assert_ssh_return_code(session, rv);
+
+ rv = ssh_options_copy(session, &new);
+ assert_ssh_return_code(session, rv);
+ assert_non_null(new);
+
+ it = ssh_list_get_iterator(session->opts.identity_non_exp);
+ assert_null(it);
+ it2 = ssh_list_get_iterator(new->opts.identity_non_exp);
+ assert_null(it2);
+
+ it = ssh_list_get_iterator(session->opts.identity);
+ assert_non_null(it);
+ it2 = ssh_list_get_iterator(new->opts.identity);
+ assert_non_null(it2);
+ while (it != NULL && it2 != NULL) {
+ assert_string_equal(it->data, it2->data);
+ it = it->next;
+ it2 = it2->next;
+ }
+ assert_null(it);
+ assert_null(it2);
+
+ ssh_free(new);
}
#define EXECUTABLE_NAME "test-exec"
--
2.38.1
From 89dd4a927b946d4df5c48073ca25cd843e0acde0 Mon Sep 17 00:00:00 2001
From: Norbert Pocs <npocs@redhat.com>
Date: Wed, 16 Nov 2022 17:18:49 +0100
Subject: [PATCH 5/5] torture_options.c: Add test for ssh_options_apply
Test that ssh_options_apply can be called multiple times without expanding
escape characters more than once. If the options are updated after calling
ssh_options_apply keep the last options.
Signed-off-by: Norbert Pocs <npocs@redhat.com>
Reviewed-by: Jakub Jelen <jjelen@redhat.com>
---
tests/unittests/torture_options.c | 165 ++++++++++++++++++++++++++++++
1 file changed, 165 insertions(+)
diff --git a/tests/unittests/torture_options.c b/tests/unittests/torture_options.c
index 907cc8df..ea63b45e 100644
--- a/tests/unittests/torture_options.c
+++ b/tests/unittests/torture_options.c
@@ -1332,6 +1332,170 @@ static void torture_options_caret_sign(void **state)
free(awaited);
}
+static void torture_options_apply (void **state) {
+ ssh_session session = *state;
+ struct ssh_list *awaited_list = NULL;
+ struct ssh_iterator *it1 = NULL, *it2 = NULL;
+ char *id = NULL;
+ int rc;
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_KNOWNHOSTS,
+ "%%d/.ssh/known_hosts");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_GLOBAL_KNOWNHOSTS,
+ "/etc/%%u/libssh/known_hosts");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_PROXYCOMMAND,
+ "exec echo \"Hello libssh %%d!\"");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_ADD_IDENTITY,
+ "%%d/do_not_expand");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_apply(session);
+ assert_ssh_return_code(session, rc);
+
+ /* check that the values got expanded */
+ assert_true(session->opts.exp_flags & SSH_OPT_EXP_FLAG_KNOWNHOSTS);
+ assert_true(session->opts.exp_flags & SSH_OPT_EXP_FLAG_GLOBAL_KNOWNHOSTS);
+ assert_true(session->opts.exp_flags & SSH_OPT_EXP_FLAG_PROXYCOMMAND);
+ assert_true(ssh_list_count(session->opts.identity_non_exp) == 0);
+ assert_true(ssh_list_count(session->opts.identity) > 0);
+
+ /* should not change anything calling it again */
+ rc = ssh_options_apply(session);
+ assert_ssh_return_code(session, rc);
+
+ /* check that the expansion was done only once */
+ assert_string_equal(session->opts.knownhosts, "%d/.ssh/known_hosts");
+ assert_string_equal(session->opts.global_knownhosts,
+ "/etc/%u/libssh/known_hosts");
+ /* no exec should be added if there already is one */
+ assert_string_equal(session->opts.ProxyCommand,
+ "exec echo \"Hello libssh %d!\"");
+ assert_string_equal(session->opts.identity->root->data,
+ "%d/do_not_expand");
+
+ /* apply should keep the freshest setting */
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_KNOWNHOSTS,
+ "hello there");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_GLOBAL_KNOWNHOSTS,
+ "lorem ipsum");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_PROXYCOMMAND,
+ "mission_impossible");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_ADD_IDENTITY,
+ "007");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_ADD_IDENTITY,
+ "3");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_ADD_IDENTITY,
+ "2");
+ assert_ssh_return_code(session, rc);
+
+ rc = ssh_options_set(session,
+ SSH_OPTIONS_ADD_IDENTITY,
+ "1");
+ assert_ssh_return_code(session, rc);
+
+ /* check that flags show need of escape expansion */
+ assert_false(session->opts.exp_flags & SSH_OPT_EXP_FLAG_KNOWNHOSTS);
+ assert_false(session->opts.exp_flags & SSH_OPT_EXP_FLAG_GLOBAL_KNOWNHOSTS);
+ assert_false(session->opts.exp_flags & SSH_OPT_EXP_FLAG_PROXYCOMMAND);
+ assert_false(ssh_list_count(session->opts.identity_non_exp) == 0);
+
+ rc = ssh_options_apply(session);
+ assert_ssh_return_code(session, rc);
+
+ /* check that the values got expanded */
+ assert_true(session->opts.exp_flags & SSH_OPT_EXP_FLAG_KNOWNHOSTS);
+ assert_true(session->opts.exp_flags & SSH_OPT_EXP_FLAG_GLOBAL_KNOWNHOSTS);
+ assert_true(session->opts.exp_flags & SSH_OPT_EXP_FLAG_PROXYCOMMAND);
+ assert_true(ssh_list_count(session->opts.identity_non_exp) == 0);
+
+ assert_string_equal(session->opts.knownhosts, "hello there");
+ assert_string_equal(session->opts.global_knownhosts, "lorem ipsum");
+ /* check that the "exec " was added at the beginning */
+ assert_string_equal(session->opts.ProxyCommand, "exec mission_impossible");
+ assert_string_equal(session->opts.identity->root->data, "1");
+
+ /* check the order of the identity files after double expansion */
+ awaited_list = ssh_list_new();
+ /* append the new data in order */
+ id = strdup("1");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+ id = strdup("2");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+ id = strdup("3");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+ id = strdup("007");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+ id = strdup("%d/do_not_expand");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+ /* append the defaults; this list is copied from ssh_new@src/session.c */
+ id = ssh_path_expand_escape(session, "%d/id_ed25519");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+#ifdef HAVE_ECC
+ id = ssh_path_expand_escape(session, "%d/id_ecdsa");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+#endif
+ id = ssh_path_expand_escape(session, "%d/id_rsa");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+#ifdef HAVE_DSA
+ id = ssh_path_expand_escape(session, "%d/id_dsa");
+ rc = ssh_list_append(awaited_list, id);
+ assert_int_equal(rc, SSH_OK);
+#endif
+
+ assert_int_equal(ssh_list_count(awaited_list),
+ ssh_list_count(session->opts.identity));
+
+ it1 = ssh_list_get_iterator(awaited_list);
+ assert_non_null(it1);
+ it2 = ssh_list_get_iterator(session->opts.identity);
+ assert_non_null(it2);
+ while (it1 != NULL && it2 != NULL) {
+ assert_string_equal(it1->data, it2->data);
+
+ free((void*)it1->data);
+ it1 = it1->next;
+ it2 = it2->next;
+ }
+ assert_null(it1);
+ assert_null(it2);
+
+ ssh_list_free(awaited_list);
+}
+
#ifdef WITH_SERVER
const char template[] = "temp_dir_XXXXXX";
@@ -2132,6 +2296,7 @@ int torture_run_tests(void) {
setup, teardown),
cmocka_unit_test_setup_teardown(torture_options_caret_sign,
setup, teardown),
+ cmocka_unit_test_setup_teardown(torture_options_apply, setup, teardown),
};
#ifdef WITH_SERVER
--
2.38.1

98
pkcs11_test_fix.patch Normal file
View File

@ -0,0 +1,98 @@
diff --git a/tests/pkcs11/setup-softhsm-tokens.sh b/tests/pkcs11/setup-softhsm-tokens.sh
index 532c86a7..9050cea6 100755
--- a/tests/pkcs11/setup-softhsm-tokens.sh
+++ b/tests/pkcs11/setup-softhsm-tokens.sh
@@ -17,10 +17,10 @@ echo "OBJNAME: $OBJNAME"
echo "LOADPUBLIC: $LOADPUBLIC"
# Create temporary directory for tokens
-install -d -m 0755 $TESTDIR/db
+install -d -m 0755 "$TESTDIR/db"
# Create SoftHSM configuration file
-cat >$TESTDIR/softhsm.conf <<EOF
+cat >"$TESTDIR/softhsm.conf" <<EOF
directories.tokendir = $TESTDIR/db
objectstore.backend = file
log.level = DEBUG
@@ -28,12 +28,12 @@ EOF
export SOFTHSM2_CONF=$TESTDIR/softhsm.conf
-cat $TESTDIR/softhsm.conf
+cat "$TESTDIR/softhsm.conf"
#init
-cmd='softhsm2-util --init-token --label "$OBJNAME" --free --pin 1234 --so-pin 1234'
+cmd="softhsm2-util --init-token --label $OBJNAME --free --pin 1234 --so-pin 1234"
eval echo "$cmd"
-out=$(eval $cmd)
+out=$(eval "$cmd")
ret=$?
if [ $ret -ne 0 ]; then
echo "Init token failed"
@@ -41,10 +41,29 @@ if [ $ret -ne 0 ]; then
exit 1
fi
+find_library_path() {
+ echo "$@"
+ for _lib in "$@" ; do
+ if test -f "$_lib" ; then
+ LIBSOFTHSM_PATH="$_lib"
+ echo "Using libsofthsm path: $LIBSOFTHSM_PATH"
+ return
+ fi
+ done
+ echo "libsofthsm2.so not found"
+ exit 1
+}
+
+find_library_path \
+ /usr/lib64/libsofthsm2.so \
+ /usr/lib/libsofthsm2.so \
+ /usr/local/lib/softhsm/libsofthsm2.so \
+ /usr/lib/x86_64-linux-gnu/softhsm/libsofthsm2.so
+
#load private key
-cmd='p11tool --provider /usr/lib64/pkcs11/libsofthsm2.so --write --load-privkey "$PRIVKEY" --label "$OBJNAME" --login --set-pin=1234 "pkcs11:token="$OBJNAME""'
+cmd="p11tool --provider $LIBSOFTHSM_PATH --write --load-privkey $PRIVKEY --label $OBJNAME --login --set-pin=1234 \"pkcs11:token=$OBJNAME\""
eval echo "$cmd"
-out=$(eval $cmd)
+out=$(eval "$cmd")
ret=$?
if [ $ret -ne 0 ]; then
echo "Loading privkey failed"
@@ -52,15 +71,15 @@ if [ $ret -ne 0 ]; then
exit 1
fi
-cat $PUBKEY
+cat "$PUBKEY"
-ls -l $TESTDIR
+ls -l "$TESTDIR"
-if [ $LOADPUBLIC -ne 0 ]; then
+if [ "$LOADPUBLIC" -ne 0 ]; then
#load public key
- cmd='p11tool --provider /usr/lib64/pkcs11/libsofthsm2.so --write --load-pubkey "$PUBKEY" --label "$OBJNAME" --login --set-pin=1234 "pkcs11:token="$OBJNAME""'
+ cmd="p11tool --provider $LIBSOFTHSM_PATH --write --load-pubkey $PUBKEY --label $OBJNAME --login --set-pin=1234 \"pkcs11:token=$OBJNAME\""
eval echo "$cmd"
- out=$(eval $cmd)
+ out=$(eval "$cmd")
ret=$?
if [ $ret -ne 0 ]; then
echo "Loading pubkey failed"
@@ -69,9 +88,9 @@ if [ $LOADPUBLIC -ne 0 ]; then
fi
fi
-cmd='p11tool --list-all --login "pkcs11:token="$OBJNAME"" --set-pin=1234'
+cmd="p11tool --list-all --login \"pkcs11:token=$OBJNAME\" --set-pin=1234"
eval echo "$cmd"
-out=$(eval $cmd)
+out=$(eval "$cmd")
ret=$?
if [ $ret -ne 0 ]; then
echo "Loging failed"

1653
plus_sign.patch Normal file

File diff suppressed because it is too large Load Diff

21
rekey_test_fixup.patch Normal file
View File

@ -0,0 +1,21 @@
diff --color -ru ../libssh-0.10.4/tests/client/torture_rekey.c ./tests/client/torture_rekey.c
--- ../libssh-0.10.4/tests/client/torture_rekey.c 2023-05-17 10:55:23.384684129 +0200
+++ ./tests/client/torture_rekey.c 2023-05-17 10:56:29.819334665 +0200
@@ -504,7 +504,7 @@
memset(data, 'A', 128);
for (i = 0; i < KEX_RETRY; i++) {
ssh_send_ignore(s->ssh.session, data);
- ssh_handle_packets(s->ssh.session, 100);
+ ssh_handle_packets(s->ssh.session, 1000);
c = s->ssh.session->current_crypto;
/* SHA256 len */
@@ -582,7 +582,7 @@
memset(data, 'A', 128);
for (i = 0; i < KEX_RETRY; i++) {
ssh_send_ignore(s->ssh.session, data);
- ssh_handle_packets(s->ssh.session, 100);
+ ssh_handle_packets(s->ssh.session, 1000);
c = s->ssh.session->current_crypto;
/* SHA256 len */

2
sources Normal file
View File

@ -0,0 +1,2 @@
SHA512 (libssh-0.10.4.tar.xz) = 01ee52d480201d9886c15e81137c185334b404d1c8e8b743ddf58e95fe8619c8c013616a49807bd1111fde72fa177cd35f3c22b66cbf5d720b5abfacdf7601ed
SHA512 (libssh-0.10.4.tar.xz.asc) = 8200215d6471851dac8cd8efd07400b9bc4403cf5406a9fdb28a68ef8fe85c227f92a26071fb32d9396b91661568333b5ceb9b23665d22e761b981dd880bbbc8