Version
2.12.1
Bug description
To reproduce the bug locally, you can create a temporary SSH Server using docker (c.f. the following one liner):
docker run -it --rm -v ${PWD}:/home/sftpuser/some-directory -p 2222:22 atmoz/sftp sftpuser:pass123:1001
(More information on the atmoz docker image, and github repo associated)
Then, get all the public keys of the server:
ssh-keyscan -p 2222 127.0.0.1
It will typically return something like:
# 127.0.0.1:2222 SSH-2.0-OpenSSH_8.4p1 Debian-5+deb11u3
[127.0.0.1]:2222 ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIPu6ntmyfSOkqLl3qPxD5XxwW7OONwwSG3KO+TGn+PFu
# 127.0.0.1:2222 SSH-2.0-OpenSSH_8.4p1 Debian-5+deb11u3
# 127.0.0.1:2222 SSH-2.0-OpenSSH_8.4p1 Debian-5+deb11u3
[127.0.0.1]:2222 ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQCpxiMvsgF+TbtTm9Pcl7rOqX/j7Xs5nFsfh5dm+GwTlufJDIIM7pbkq6GDSrlrENhk0Rv+HeLVHbuO6jGYaDc7vvvom3lWNE0t6Kj/dSYoXA4KBH1NUgqHlAyGcEr0kbUoZOQL5j5/RkckKngWG2Rg/qUT6ubdF2B/iybP1BAbsktByGlikCvirzPGb6Bwq13ontzd/uF2obQ367d0eyQ3h8a/vJvXTTc4Q6d2bzl86wQ2e8FBktCYxzAdt1ZQJyqzoWuuuyb+SkmeSdryCI3qtvVHBOHrYKzolKRMghmSiaP2t5IcAOGX4wQvo8uBZcFD6oIhBSY5c5/u27GGjOb4iCbdXXjNMLg3P0Y7EazYwD1D6r5EkwGX6MofGtGdKotwdddWyN/jF6jlyAikBzIw2m021uWsvFSWgjmOx8N9EXVW4Ou6aDBNc2bMP6nxU2JrsSzwnrUN51kl/TJrQeH8XaIwTahEtrjyOzipIdHMORMSPLyDsRxjv5RxqEipBUrbrLDALSoYkp+SQsq6g2Qm9LiMIHXA3Q/FNau5gsuQQ7RXp/rd3wEkYRqhz4zVHqOgBPM3TjS1yBjnXvNUarCjI7B0IwJsKzWMneqKxu2oBZ8gIZC0fFkqOCRRiaGE7doI+SuKHULCMdBo6GzH12Tz15Io4N8XVAg43zkl0V0CJQ==
# 127.0.0.1:2222 SSH-2.0-OpenSSH_8.4p1 Debian-5+deb11u3
# 127.0.0.1:2222 SSH-2.0-OpenSSH_8.4p1 Debian-5+deb11u3
Then, in Apache Mina, passing to KnownHostEntry.readKnownHostEntries all the lines above as an input stream (actually, I'm using spring-integration-sftp version 6.3.5 to do that), and then we get the following exception:
java.io.StreamCorruptedException: Failed (IllegalArgumentException) to parse line #2 '[127.0.0.1]:2222 ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIPu6ntmyfSOkqLl3qPxD5XxwW7OONwwSG3KO+TGn+PFu': Bad format (no key data delimiter): AAAAC3NzaC1lZDI1NTE5AAAAIPu6ntmyfSOkqLl3qPxD5XxwW7OONwwSG3KO+TGn+PFu
I've run a debugger up into Apache Mina implementation, and I was able to determined that the algorithm ssh-ed25519 is not supported -- ok fine, not a problem, as we should be able to fallback to ssh-rsa, but this is not the case as the Known Host Parsing is failling as soon as it encounters a non supported key type.
The bug here is that KnownHostEntry.readKnownHostEntries should try to return all the valid and supported KnownHostEntry, and let the unsupported algorithm out of the collection returned on that function (and it could fail if no usable/valid entry would have been found).
Actual behavior
java.io.StreamCorruptedException: Failed (IllegalArgumentException) to parse line #2 '[127.0.0.1]:2222 ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIPu6ntmyfSOkqLl3qPxD5XxwW7OONwwSG3KO+TGn+PFu': Bad format (no key data delimiter): AAAAC3NzaC1lZDI1NTE5AAAAIPu6ntmyfSOkqLl3qPxD5XxwW7OONwwSG3KO+TGn+PFu
at org.apache.sshd.client.config.hosts.KnownHostEntry.readKnownHostEntries(KnownHostEntry.java:208)
at org.apache.sshd.client.config.hosts.KnownHostEntry.readKnownHostEntries(KnownHostEntry.java:165)
at org.apache.sshd.client.config.hosts.KnownHostEntry.readKnownHostEntries(KnownHostEntry.java:159)
at org.springframework.integration.sftp.session.ResourceKnownHostsServerKeyVerifier.lambda$getKnownHostSupplier$3(ResourceKnownHostsServerKeyVerifier.java:90)
at org.apache.sshd.common.util.GenericUtils.lambda$memoizeLock$7(GenericUtils.java:893)
at org.springframework.integration.sftp.session.ResourceKnownHostsServerKeyVerifier.verifyServerKey(ResourceKnownHostsServerKeyVerifier.java:68)
at org.apache.sshd.client.session.AbstractClientSession.checkKeys(AbstractClientSession.java:637)
at org.apache.sshd.common.session.helpers.AbstractSession.handleKexMessage(AbstractSession.java:766)
at org.apache.sshd.common.session.helpers.AbstractSession.doHandleMessage(AbstractSession.java:621)
at org.apache.sshd.common.session.helpers.AbstractSession.lambda$handleMessage$0(AbstractSession.java:545)
at org.apache.sshd.common.util.threads.ThreadUtils.runAsInternal(ThreadUtils.java:68)
at org.apache.sshd.common.session.helpers.AbstractSession.handleMessage(AbstractSession.java:544)
at org.apache.sshd.common.session.helpers.AbstractSession.decode(AbstractSession.java:1688)
at org.apache.sshd.common.session.helpers.AbstractSession.messageReceived(AbstractSession.java:505)
at org.apache.sshd.common.session.helpers.AbstractSessionIoHandler.messageReceived(AbstractSessionIoHandler.java:64)
at org.apache.sshd.common.io.nio2.Nio2Session.handleReadCycleCompletion(Nio2Session.java:409)
at org.apache.sshd.common.io.nio2.Nio2Session$1.onCompleted(Nio2Session.java:382)
at org.apache.sshd.common.io.nio2.Nio2Session$1.onCompleted(Nio2Session.java:377)
at org.apache.sshd.common.io.nio2.Nio2CompletionHandler.lambda$completed$0(Nio2CompletionHandler.java:38)
at java.base/java.security.AccessController.doPrivileged(AccessController.java:319)
at org.apache.sshd.common.io.nio2.Nio2CompletionHandler.completed(Nio2CompletionHandler.java:37)
at java.base/sun.nio.ch.Invoker.invokeUnchecked(Invoker.java:129)
at java.base/sun.nio.ch.Invoker$2.run(Invoker.java:221)
at java.base/sun.nio.ch.AsynchronousChannelGroupImpl$1.run(AsynchronousChannelGroupImpl.java:113)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642)
at java.base/java.lang.Thread.run(Thread.java:1583)
Expected behavior
Have at least the KnownHost entry with the ssh-rsa algorithm, i.e. the following entry:
[127.0.0.1]:2222 ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQCpxiMvsgF+TbtTm9Pcl7rOqX/j7Xs5nFsfh5dm+GwTlufJDIIM7pbkq6GDSrlrENhk0Rv+HeLVHbuO6jGYaDc7vvvom3lWNE0t6Kj/dSYoXA4KBH1NUgqHlAyGcEr0kbUoZOQL5j5/RkckKngWG2Rg/qUT6ubdF2B/iybP1BAbsktByGlikCvirzPGb6Bwq13ontzd/uF2obQ367d0eyQ3h8a/vJvXTTc4Q6d2bzl86wQ2e8FBktCYxzAdt1ZQJyqzoWuuuyb+SkmeSdryCI3qtvVHBOHrYKzolKRMghmSiaP2t5IcAOGX4wQvo8uBZcFD6oIhBSY5c5/u27GGjOb4iCbdXXjNMLg3P0Y7EazYwD1D6r5EkwGX6MofGtGdKotwdddWyN/jF6jlyAikBzIw2m021uWsvFSWgjmOx8N9EXVW4Ou6aDBNc2bMP6nxU2JrsSzwnrUN51kl/TJrQeH8XaIwTahEtrjyOzipIdHMORMSPLyDsRxjv5RxqEipBUrbrLDALSoYkp+SQsq6g2Qm9LiMIHXA3Q/FNau5gsuQQ7RXp/rd3wEkYRqhz4zVHqOgBPM3TjS1yBjnXvNUarCjI7B0IwJsKzWMneqKxu2oBZ8gIZC0fFkqOCRRiaGE7doI+SuKHULCMdBo6GzH12Tz15Io4N8XVAg43zkl0V0CJQ==
Relevant log output
No response
Other information
Thank you for your work guys ! That's awesome to work with well maintained libraries to do SSH/SFTP communication 🙏
Version
2.12.1
Bug description
To reproduce the bug locally, you can create a temporary SSH Server using docker (c.f. the following one liner):
docker run -it --rm -v ${PWD}:/home/sftpuser/some-directory -p 2222:22 atmoz/sftp sftpuser:pass123:1001(More information on the
atmozdocker image, and github repo associated)Then, get all the public keys of the server:
It will typically return something like:
Then, in Apache Mina, passing to
KnownHostEntry.readKnownHostEntriesall the lines above as an input stream (actually, I'm usingspring-integration-sftpversion6.3.5to do that), and then we get the following exception:I've run a debugger up into Apache Mina implementation, and I was able to determined that the algorithm
ssh-ed25519is not supported -- ok fine, not a problem, as we should be able to fallback tossh-rsa, but this is not the case as the Known Host Parsing is failling as soon as it encounters a non supported key type.The bug here is that
KnownHostEntry.readKnownHostEntriesshould try to return all the valid and supportedKnownHostEntry, and let the unsupported algorithm out of the collection returned on that function (and it could fail if no usable/valid entry would have been found).Actual behavior
Expected behavior
Have at least the KnownHost entry with the
ssh-rsaalgorithm, i.e. the following entry:Relevant log output
No response
Other information
Thank you for your work guys ! That's awesome to work with well maintained libraries to do SSH/SFTP communication 🙏