From: Kevin Wolf <kwolf@redhat.com>
To: qemu-block@nongnu.org
Cc: kwolf@redhat.com, peter.maydell@linaro.org, qemu-devel@nongnu.org
Subject: [PULL 17/24] block/ssh: add support for sha256 host key fingerprints
Date: Wed, 30 Jun 2021 18:01:59 +0200 [thread overview]
Message-ID: <20210630160206.276439-18-kwolf@redhat.com> (raw)
In-Reply-To: <20210630160206.276439-1-kwolf@redhat.com>
From: Daniel P. Berrangé <berrange@redhat.com>
Currently the SSH block driver supports MD5 and SHA1 for host key
fingerprints. This is a cryptographically sensitive operation and
so these hash algorithms are inadequate by modern standards. This
adds support for SHA256 which has been supported in libssh since
the 0.8.1 release.
Signed-off-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20210622115156.138458-1-berrange@redhat.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Acked-by: Richard W.M. Jones <rjones@redhat.com>
Signed-off-by: Kevin Wolf <kwolf@redhat.com>
---
qapi/block-core.json | 3 ++-
block/ssh.c | 3 +++
tests/qemu-iotests/207 | 54 ++++++++++++++++++++++++++++++++++++++
tests/qemu-iotests/207.out | 25 ++++++++++++++++++
4 files changed, 84 insertions(+), 1 deletion(-)
diff --git a/qapi/block-core.json b/qapi/block-core.json
index a54f37dbef..3114ba69bb 100644
--- a/qapi/block-core.json
+++ b/qapi/block-core.json
@@ -3190,11 +3190,12 @@
#
# @md5: The given hash is an md5 hash
# @sha1: The given hash is an sha1 hash
+# @sha256: The given hash is an sha256 hash
#
# Since: 2.12
##
{ 'enum': 'SshHostKeyCheckHashType',
- 'data': [ 'md5', 'sha1' ] }
+ 'data': [ 'md5', 'sha1', 'sha256' ] }
##
# @SshHostKeyHash:
diff --git a/block/ssh.c b/block/ssh.c
index b51a031620..d008caf059 100644
--- a/block/ssh.c
+++ b/block/ssh.c
@@ -442,6 +442,9 @@ static int check_host_key(BDRVSSHState *s, SshHostKeyCheck *hkc, Error **errp)
} else if (hkc->u.hash.type == SSH_HOST_KEY_CHECK_HASH_TYPE_SHA1) {
return check_host_key_hash(s, hkc->u.hash.hash,
SSH_PUBLICKEY_HASH_SHA1, errp);
+ } else if (hkc->u.hash.type == SSH_HOST_KEY_CHECK_HASH_TYPE_SHA256) {
+ return check_host_key_hash(s, hkc->u.hash.hash,
+ SSH_PUBLICKEY_HASH_SHA256, errp);
}
g_assert_not_reached();
break;
diff --git a/tests/qemu-iotests/207 b/tests/qemu-iotests/207
index f9f3fd7131..0f5c4bc8a0 100755
--- a/tests/qemu-iotests/207
+++ b/tests/qemu-iotests/207
@@ -73,6 +73,9 @@ with iotests.FilePath('t.img') as disk_path, \
iotests.log("=== Test host-key-check options ===")
iotests.log("")
+ iotests.log("--- no host key checking --")
+ iotests.log("")
+
vm.launch()
blockdev_create(vm, { 'driver': 'ssh',
'location': {
@@ -90,6 +93,9 @@ with iotests.FilePath('t.img') as disk_path, \
iotests.img_info_log(remote_path)
+ iotests.log("--- known_hosts key checking --")
+ iotests.log("")
+
vm.launch()
blockdev_create(vm, { 'driver': 'ssh',
'location': {
@@ -115,6 +121,7 @@ with iotests.FilePath('t.img') as disk_path, \
# Mappings of base64 representations to digests
md5_keys = {}
sha1_keys = {}
+ sha256_keys = {}
for key in keys:
md5_keys[key] = subprocess.check_output(
@@ -125,6 +132,10 @@ with iotests.FilePath('t.img') as disk_path, \
'echo %s | base64 -d | sha1sum -b | cut -d" " -f1' % key,
shell=True).rstrip().decode('ascii')
+ sha256_keys[key] = subprocess.check_output(
+ 'echo %s | base64 -d | sha256sum -b | cut -d" " -f1' % key,
+ shell=True).rstrip().decode('ascii')
+
vm.launch()
# Find correct key first
@@ -150,6 +161,9 @@ with iotests.FilePath('t.img') as disk_path, \
vm.shutdown()
iotests.notrun('Did not find a key that fits 127.0.0.1')
+ iotests.log("--- explicit md5 key checking --")
+ iotests.log("")
+
blockdev_create(vm, { 'driver': 'ssh',
'location': {
'path': disk_path,
@@ -164,6 +178,7 @@ with iotests.FilePath('t.img') as disk_path, \
}
},
'size': 2097152 })
+
blockdev_create(vm, { 'driver': 'ssh',
'location': {
'path': disk_path,
@@ -182,6 +197,9 @@ with iotests.FilePath('t.img') as disk_path, \
iotests.img_info_log(remote_path)
+ iotests.log("--- explicit sha1 key checking --")
+ iotests.log("")
+
vm.launch()
blockdev_create(vm, { 'driver': 'ssh',
'location': {
@@ -215,6 +233,42 @@ with iotests.FilePath('t.img') as disk_path, \
iotests.img_info_log(remote_path)
+ iotests.log("--- explicit sha256 key checking --")
+ iotests.log("")
+
+ vm.launch()
+ blockdev_create(vm, { 'driver': 'ssh',
+ 'location': {
+ 'path': disk_path,
+ 'server': {
+ 'host': '127.0.0.1',
+ 'port': '22'
+ },
+ 'host-key-check': {
+ 'mode': 'hash',
+ 'type': 'sha256',
+ 'hash': 'wrong',
+ }
+ },
+ 'size': 2097152 })
+ blockdev_create(vm, { 'driver': 'ssh',
+ 'location': {
+ 'path': disk_path,
+ 'server': {
+ 'host': '127.0.0.1',
+ 'port': '22'
+ },
+ 'host-key-check': {
+ 'mode': 'hash',
+ 'type': 'sha256',
+ 'hash': sha256_keys[matching_key],
+ }
+ },
+ 'size': 4194304 })
+ vm.shutdown()
+
+ iotests.img_info_log(remote_path)
+
#
# Invalid path and user
#
diff --git a/tests/qemu-iotests/207.out b/tests/qemu-iotests/207.out
index 1239d9d648..aeb8569d77 100644
--- a/tests/qemu-iotests/207.out
+++ b/tests/qemu-iotests/207.out
@@ -16,6 +16,8 @@ virtual size: 4 MiB (4194304 bytes)
=== Test host-key-check options ===
+--- no host key checking --
+
{"execute": "blockdev-create", "arguments": {"job-id": "job0", "options": {"driver": "ssh", "location": {"host-key-check": {"mode": "none"}, "path": "TEST_DIR/PID-t.img", "server": {"host": "127.0.0.1", "port": "22"}}, "size": 8388608}}}
{"return": {}}
{"execute": "job-dismiss", "arguments": {"id": "job0"}}
@@ -25,6 +27,8 @@ image: TEST_IMG
file format: IMGFMT
virtual size: 8 MiB (8388608 bytes)
+--- known_hosts key checking --
+
{"execute": "blockdev-create", "arguments": {"job-id": "job0", "options": {"driver": "ssh", "location": {"host-key-check": {"mode": "known_hosts"}, "path": "TEST_DIR/PID-t.img", "server": {"host": "127.0.0.1", "port": "22"}}, "size": 4194304}}}
{"return": {}}
{"execute": "job-dismiss", "arguments": {"id": "job0"}}
@@ -34,6 +38,8 @@ image: TEST_IMG
file format: IMGFMT
virtual size: 4 MiB (4194304 bytes)
+--- explicit md5 key checking --
+
{"execute": "blockdev-create", "arguments": {"job-id": "job0", "options": {"driver": "ssh", "location": {"host-key-check": {"hash": "wrong", "mode": "hash", "type": "md5"}, "path": "TEST_DIR/PID-t.img", "server": {"host": "127.0.0.1", "port": "22"}}, "size": 2097152}}}
{"return": {}}
Job failed: remote host key does not match host_key_check 'wrong'
@@ -49,6 +55,8 @@ image: TEST_IMG
file format: IMGFMT
virtual size: 8 MiB (8388608 bytes)
+--- explicit sha1 key checking --
+
{"execute": "blockdev-create", "arguments": {"job-id": "job0", "options": {"driver": "ssh", "location": {"host-key-check": {"hash": "wrong", "mode": "hash", "type": "sha1"}, "path": "TEST_DIR/PID-t.img", "server": {"host": "127.0.0.1", "port": "22"}}, "size": 2097152}}}
{"return": {}}
Job failed: remote host key does not match host_key_check 'wrong'
@@ -64,6 +72,23 @@ image: TEST_IMG
file format: IMGFMT
virtual size: 4 MiB (4194304 bytes)
+--- explicit sha256 key checking --
+
+{"execute": "blockdev-create", "arguments": {"job-id": "job0", "options": {"driver": "ssh", "location": {"host-key-check": {"hash": "wrong", "mode": "hash", "type": "sha256"}, "path": "TEST_DIR/PID-t.img", "server": {"host": "127.0.0.1", "port": "22"}}, "size": 2097152}}}
+{"return": {}}
+Job failed: remote host key does not match host_key_check 'wrong'
+{"execute": "job-dismiss", "arguments": {"id": "job0"}}
+{"return": {}}
+
+{"execute": "blockdev-create", "arguments": {"job-id": "job0", "options": {"driver": "ssh", "location": {"host-key-check": {"hash": "HASH", "mode": "hash", "type": "sha256"}, "path": "TEST_DIR/PID-t.img", "server": {"host": "127.0.0.1", "port": "22"}}, "size": 4194304}}}
+{"return": {}}
+{"execute": "job-dismiss", "arguments": {"id": "job0"}}
+{"return": {}}
+
+image: TEST_IMG
+file format: IMGFMT
+virtual size: 4 MiB (4194304 bytes)
+
=== Invalid path and user ===
{"execute": "blockdev-create", "arguments": {"job-id": "job0", "options": {"driver": "ssh", "location": {"host-key-check": {"mode": "none"}, "path": "/this/is/not/an/existing/path", "server": {"host": "127.0.0.1", "port": "22"}}, "size": 4194304}}}
--
2.31.1
next prev parent reply other threads:[~2021-06-30 16:21 UTC|newest]
Thread overview: 26+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-06-30 16:01 [PULL 00/24] Block layer patches Kevin Wolf
2021-06-30 16:01 ` [PULL 01/24] Prevent compiler warning on block.c Kevin Wolf
2021-06-30 16:01 ` [PULL 02/24] block: Move read-only check during truncation earlier Kevin Wolf
2021-06-30 16:01 ` [PULL 03/24] block: BDRV_O_NO_IO for backing file on creation Kevin Wolf
2021-06-30 16:01 ` [PULL 04/24] block: rename bdrv_replace_child to bdrv_replace_child_tran Kevin Wolf
2021-06-30 16:01 ` [PULL 05/24] block: comment graph-modifying function not updating permissions Kevin Wolf
2021-06-30 16:01 ` [PULL 06/24] block: introduce bdrv_remove_file_or_backing_child() Kevin Wolf
2021-06-30 16:01 ` [PULL 07/24] block: introduce bdrv_set_file_or_backing_noperm() Kevin Wolf
2021-06-30 16:01 ` [PULL 08/24] block: bdrv_reopen_parse_backing(): don't check aio context Kevin Wolf
2021-06-30 16:01 ` [PULL 09/24] block: bdrv_reopen_parse_backing(): don't check frozen child Kevin Wolf
2021-06-30 16:01 ` [PULL 10/24] block: bdrv_reopen_parse_backing(): simplify handling implicit filters Kevin Wolf
2021-06-30 16:01 ` [PULL 11/24] block: move supports_backing check to bdrv_set_file_or_backing_noperm() Kevin Wolf
2021-06-30 16:01 ` [PULL 12/24] block: BDRVReopenState: drop replace_backing_bs field Kevin Wolf
2021-06-30 16:01 ` [PULL 13/24] block: Allow changing bs->file on reopen Kevin Wolf
2021-06-30 16:01 ` [PULL 14/24] iotests: Test replacing files with x-blockdev-reopen Kevin Wolf
2021-06-30 16:01 ` [PULL 15/24] introduce QEMU_AUTO_VFREE Kevin Wolf
2021-06-30 16:01 ` [PULL 16/24] block/commit: use QEMU_AUTO_VFREE Kevin Wolf
2021-06-30 16:01 ` Kevin Wolf [this message]
2021-06-30 16:02 ` [PULL 18/24] vhost: Add Error parameter to vhost_dev_init() Kevin Wolf
2021-06-30 16:02 ` [PULL 19/24] vhost: Distinguish errors in vhost_backend_init() Kevin Wolf
2021-06-30 16:02 ` [PULL 20/24] vhost: Return 0/-errno in vhost_dev_init() Kevin Wolf
2021-06-30 16:02 ` [PULL 21/24] vhost-user-blk: Add Error parameter to vhost_user_blk_start() Kevin Wolf
2021-06-30 16:02 ` [PULL 22/24] vhost: Distinguish errors in vhost_dev_get_config() Kevin Wolf
2021-06-30 16:02 ` [PULL 23/24] vhost-user-blk: Factor out vhost_user_blk_realize_connect() Kevin Wolf
2021-06-30 16:02 ` [PULL 24/24] vhost-user-blk: Implement reconnection during realize Kevin Wolf
2021-07-02 13:52 ` [PULL 00/24] Block layer patches Peter Maydell
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20210630160206.276439-18-kwolf@redhat.com \
--to=kwolf@redhat.com \
--cc=peter.maydell@linaro.org \
--cc=qemu-block@nongnu.org \
--cc=qemu-devel@nongnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.