You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@mina.apache.org by "Sergey Panov (Jira)" <ji...@apache.org> on 2021/11/23 15:12:00 UTC

[jira] [Updated] (SSHD-1229) Infinite clientMethods iteration in ClientUserAuthService

     [ https://issues.apache.org/jira/browse/SSHD-1229?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel ]

Sergey Panov updated SSHD-1229:
-------------------------------
    Description: 
Hello,

 

I've come across that the org.apache.sshd.client.session.ClientUserAuthService#clientMethods list could be iterated over and over again until a client terminates connection. This happens when a server requires two-factor authentication. Despite RFC 4252 [Page 5] ([https://www.ietf.org/rfc/rfc4252.txt)] recommends the server returning only authentication methods that have not been successfully completed, some implementations ignore this. If the authentication is partially successful, but the server returns the same list of authentication methods, the 0th client authentication method will be used repeatedly.
{code:java}
protected void processUserAuth(Buffer buffer) throws Exception {
        ...
        if (cmd == SshConstants.SSH_MSG_USERAUTH_FAILURE) {
            String mths = buffer.getString();
            boolean partial = buffer.getBoolean();
            if (log.isDebugEnabled()) {
                log.debug("processUserAuth({}) Received SSH_MSG_USERAUTH_FAILURE - partial={}, methods={}",
                        session, partial, mths);
            }
            if (partial || (serverMethods == null)) {
                serverMethods = Arrays.asList(GenericUtils.split(mths, ','));   // If a server is always returning the same list of methods, the "next" client method in clientMethods will be on index 0
                currentMethod = 0;
                if (userAuth != null) {
                    try {
                        try {
                            userAuth.signalAuthMethodFailure(
                                    session, service, partial, Collections.unmodifiableList(serverMethods), buffer);
                        } finally {
                            userAuth.destroy();
                        }
                    } finally {
                        userAuth = null;
                    }
                }
            }            tryNext(cmd);
            return;
        }
        ...
    }{code}
 
{code:java}
protected void tryNext(int cmd) throws Exception {
    ClientSession session = getClientSession();
    // Loop until we find something to try
    for (boolean debugEnabled = log.isDebugEnabled();; debugEnabled = log.isDebugEnabled()) {
        ...
        String method = null;
        for (; currentMethod < clientMethods.size(); currentMethod++) {
            method = clientMethods.get(currentMethod);  // Always selects the 0th client method when the previous authentication method was "partially successful"
            if (serverMethods.contains(method)) {
                break;
            }
        }
        ...
    }
} {code}

  was:
Hello,

 

I've come across that the org.apache.sshd.client.session.ClientUserAuthService#clientMethods list could be iterated over and over again until a client terminates connection. This happens when a server requires two-factor authentication. Despite RFC 4252 ([https://www.ietf.org/rfc/rfc4252.txt)] recommends the server returning only authentication methods that have not been successfully completed, some implementations ignore this. If the authentication is partially successful, but the server returns the same list of authentication methods, the 0th client authentication method will be used repeatedly.



{code:java}
protected void processUserAuth(Buffer buffer) throws Exception {
        ...
        if (cmd == SshConstants.SSH_MSG_USERAUTH_FAILURE) {
            String mths = buffer.getString();
            boolean partial = buffer.getBoolean();
            if (log.isDebugEnabled()) {
                log.debug("processUserAuth({}) Received SSH_MSG_USERAUTH_FAILURE - partial={}, methods={}",
                        session, partial, mths);
            }
            if (partial || (serverMethods == null)) {
                serverMethods = Arrays.asList(GenericUtils.split(mths, ','));   // If a server is always returning the same list of methods, the "next" client method in clientMethods will be on index 0
                currentMethod = 0;
                if (userAuth != null) {
                    try {
                        try {
                            userAuth.signalAuthMethodFailure(
                                    session, service, partial, Collections.unmodifiableList(serverMethods), buffer);
                        } finally {
                            userAuth.destroy();
                        }
                    } finally {
                        userAuth = null;
                    }
                }
            }            tryNext(cmd);
            return;
        }
        ...
    }{code}
 
{code:java}
protected void tryNext(int cmd) throws Exception {
    ClientSession session = getClientSession();
    // Loop until we find something to try
    for (boolean debugEnabled = log.isDebugEnabled();; debugEnabled = log.isDebugEnabled()) {
        ...
        String method = null;
        for (; currentMethod < clientMethods.size(); currentMethod++) {
            method = clientMethods.get(currentMethod);  // Always selects the 0th client method when the previous authentication method was "partially successful"
            if (serverMethods.contains(method)) {
                break;
            }
        }
        ...
    }
} {code}


> Infinite clientMethods iteration in ClientUserAuthService
> ---------------------------------------------------------
>
>                 Key: SSHD-1229
>                 URL: https://issues.apache.org/jira/browse/SSHD-1229
>             Project: MINA SSHD
>          Issue Type: Bug
>    Affects Versions: 2.7.0
>            Reporter: Sergey Panov
>            Priority: Major
>
> Hello,
>  
> I've come across that the org.apache.sshd.client.session.ClientUserAuthService#clientMethods list could be iterated over and over again until a client terminates connection. This happens when a server requires two-factor authentication. Despite RFC 4252 [Page 5] ([https://www.ietf.org/rfc/rfc4252.txt)] recommends the server returning only authentication methods that have not been successfully completed, some implementations ignore this. If the authentication is partially successful, but the server returns the same list of authentication methods, the 0th client authentication method will be used repeatedly.
> {code:java}
> protected void processUserAuth(Buffer buffer) throws Exception {
>         ...
>         if (cmd == SshConstants.SSH_MSG_USERAUTH_FAILURE) {
>             String mths = buffer.getString();
>             boolean partial = buffer.getBoolean();
>             if (log.isDebugEnabled()) {
>                 log.debug("processUserAuth({}) Received SSH_MSG_USERAUTH_FAILURE - partial={}, methods={}",
>                         session, partial, mths);
>             }
>             if (partial || (serverMethods == null)) {
>                 serverMethods = Arrays.asList(GenericUtils.split(mths, ','));   // If a server is always returning the same list of methods, the "next" client method in clientMethods will be on index 0
>                 currentMethod = 0;
>                 if (userAuth != null) {
>                     try {
>                         try {
>                             userAuth.signalAuthMethodFailure(
>                                     session, service, partial, Collections.unmodifiableList(serverMethods), buffer);
>                         } finally {
>                             userAuth.destroy();
>                         }
>                     } finally {
>                         userAuth = null;
>                     }
>                 }
>             }            tryNext(cmd);
>             return;
>         }
>         ...
>     }{code}
>  
> {code:java}
> protected void tryNext(int cmd) throws Exception {
>     ClientSession session = getClientSession();
>     // Loop until we find something to try
>     for (boolean debugEnabled = log.isDebugEnabled();; debugEnabled = log.isDebugEnabled()) {
>         ...
>         String method = null;
>         for (; currentMethod < clientMethods.size(); currentMethod++) {
>             method = clientMethods.get(currentMethod);  // Always selects the 0th client method when the previous authentication method was "partially successful"
>             if (serverMethods.contains(method)) {
>                 break;
>             }
>         }
>         ...
>     }
> } {code}



--
This message was sent by Atlassian Jira
(v8.20.1#820001)

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@mina.apache.org
For additional commands, e-mail: dev-help@mina.apache.org