I have been using OpenSSH clients against a number of embedded SSH
servers with no problem up till now. Starting with version 6.4p1
password authentication has stopped working against such servers. What
happens is that the client enters an infinite loop during the
authentication phase.
I built OpenSSH 5.9p1 and 6.4p1 in a Linux box so that the client
prints out to the screen all of the SSH messages sent to, and received
from, the server. What follows is a condensed account of my
observations based on the output generated by the 5.9p1 and 6.4p1,
respectively, displaying only the relevant data.
The output is organized in two columns. The left column contains the
messages sent by the client, and the right column contains the
messages sent by the server. Time is assumed to flow from top to
bottom, so the message exchange ordering may be immediately noticed.
The output is constrained to the authentication phase, after the
session keys have been derived by both parties, and before any
channels are opened. The asymmetric keys and user name are exactly the
same in both cases.
OpenSSH client 5.9p1
Embedded SSH server
SSH_MSG_USERAUTH_REQUEST
Method name: none
SSH_MSG_USERAUTH_FAILURE
Supported auth. methods: password, publickey
Partial success Boolean: FALSE
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: FALSE
SSH_MSG_USERAUTH_PK_OK
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: TRUE
SSH_MSG_USERAUTH_FAILURE
Supported auth. methods: password, publickey
Partial success Boolean: TRUE
SSH_MSG_USERAUTH_REQUEST
Method name: password
Boolean: FALSE
SSH_MSG_USERAUTH_SUCCESS
After this the client opens a channel and the interactive session gets
established.
OpenSSH client 6.4p1
Embedded SSH server
SSH_MSG_USERAUTH_REQUEST
Method name: none
SSH_MSG_USERAUTH_FAILURE
Supported auth. methods: password, publickey
Partial success Boolean: FALSE
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: FALSE
SSH_MSG_USERAUTH_PK_OK
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: TRUE
SSH_MSG_USERAUTH_FAILURE
Supported auth. methods: password, publickey
Partial success Boolean: TRUE
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: FALSE
SSH_MSG_USERAUTH_PK_OK
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: TRUE
SSH_MSG_USERAUTH_FAILURE
Supported auth. methods: password, publickey
Partial success Boolean: TRUE
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: FALSE
SSH_MSG_USERAUTH_PK_OK
SSH_MSG_USERAUTH_REQUEST
Method name: publickey
Boolean: TRUE
SSH_MSG_USERAUTH_FAILURE
Supported auth. methods: password, publickey
Partial success Boolean: TRUE
The first six messages exchanged are identical in both cases, as far
as their payloads are concerned. However, after the sixth message (an
SSH_MSG_USERAUTH_FAILURE sent by the server) things change
dramatically. The 5.9p1 client at that point gives up attempting
public-key-based authentication, falling back on to password
authentication. This is as it should be, for there is no public key
for this particular user in the server.
On the other hand, at the same point in the exchange the 6.4p1 client
sends another public key authentication request, this time, like the
very first one, with the Boolean field set to FALSE. This is the
start of the infinite loop on the client side, which just prints out
the 'Authenticated with partial success.' line ad infinitum, without
ever prompting the person at the keyboard for a password. The loop is
in the last four messages depicted in the traces above.
Why is the 6.4p1 client attempting to probe for public key
authentication again, when the server has already indicated that the
public key received will not authenticate the user? In every
SSH_MSG_USERAUTH_REQUEST that contains a public key (an RSA one, in
this case) the client always sends the same public key. As it happens,
should there be a matching public key for that user in the server, the
authentication phase succeeds and the interactive session gets
established without any issues.
I am hoping that this is a bug in the OpenSSH 6.4p1 code (and later -
at least, the same seems to be true of 6.6p1) that is tickled by the
embedded server (things work fine against OpenSSH servers) for it
would be far easier to change SSH client than fixing the server.
However, a reading of RFC 4252 seems to indicate that the 6.4p1 client
is not doing the right thing here, but I may be misinterpreting the
RFC. Hopefully experts in this forum will be able to clarify this
situation one way or the other.