I'm starting to take a stab at supporting SSH_AUTH_PARTIAL in x2goclient.
Here's what I have at the moment.  I think there still is work to be done for
userAuthKeyboardInteractive() and userChallengeAuth() and userAuthWithPass(),
but they would be similar to what was done for userAuthAuto and userAuthWithKey.

This also requires work in libssh - see https://bugs.libssh.org/T82

-- 
Orion Poplawski
Manager of NWRA Technical Systems          720-772-5637
NWRA, Boulder/CoRA Office             FAX: 303-415-9702
3380 Mitchell Lane                       or...@nwra.com
Boulder, CO 80301                 https://www.nwra.com/
diff --git a/src/sshmasterconnection.cpp b/src/sshmasterconnection.cpp
index be327c6..bd8d18e 100644
--- a/src/sshmasterconnection.cpp
+++ b/src/sshmasterconnection.cpp
@@ -1244,12 +1244,14 @@ bool SshMasterConnection::userChallengeAuth()
 }
 
 
-bool SshMasterConnection::userAuthWithPass()
+bool SshMasterConnection::userAuthWithPass(bool partial)
 {
     bool ret = false;
 
-    // Populate the userauth_list
-    ssh_userauth_none(my_ssh_session, NULL);
+    // Populate the userauth_list, unless we're already partially authenticated
+    if (!partial) {
+        ssh_userauth_none(my_ssh_session, NULL);
+    }
 
     int method = ssh_userauth_list(my_ssh_session, NULL);
 
@@ -1316,11 +1318,12 @@ bool SshMasterConnection::userAuthWithPass()
 }
 
 
-bool SshMasterConnection::userAuthAuto()
+int SshMasterConnection::userAuthAuto()
 {
-    int rc = ssh_userauth_autopubkey ( my_ssh_session, "" );
+    x2goDebug << "userAuthAuto calling ssh_userauth_publickey_auto()" << endl;
+    int rc = ssh_userauth_publickey_auto ( my_ssh_session, NULL, "" );
     int i=0;
-    while(rc != SSH_AUTH_SUCCESS)
+    while(rc != SSH_AUTH_SUCCESS && rc != SSH_AUTH_PARTIAL)
     {
         if (SSH_AUTH_DENIED == rc) {
           /* No need to continue, all keys have been rejected by the server. */
@@ -1343,23 +1346,23 @@ bool SshMasterConnection::userAuthAuto()
         }
         if(keyPhrase==QString::null)
             break;
-        rc = ssh_userauth_autopubkey ( my_ssh_session, keyPhrase.toLatin1() );
+        rc = ssh_userauth_publickey_auto ( my_ssh_session, NULL, keyPhrase.toLatin1() );
         if(i++==2)
         {
             break;
         }
     }
 
-    if ( rc != SSH_AUTH_SUCCESS )
+    if ( rc != SSH_AUTH_SUCCESS && rc != SSH_AUTH_PARTIAL )
     {
         QString err=ssh_get_error ( my_ssh_session );
         authErrors<<err;
 #ifdef DEBUG
         x2goDebug << "userAuthAuto failed:" << err << " (code " << rc << ")" << endl;
 #endif
-        return false;
+        return rc;
     }
-    return true;
+    return rc;
 }
 
 void SshMasterConnection::setKeyPhrase(QString phrase)
@@ -1371,7 +1374,7 @@ void SshMasterConnection::setKeyPhrase(QString phrase)
 }
 
 
-bool SshMasterConnection::userAuthWithKey()
+int SshMasterConnection::userAuthWithKey()
 {
 #ifdef DEBUG
     x2goDebug<<"Trying to authenticate user with private key.";
@@ -1408,7 +1411,7 @@ bool SshMasterConnection::userAuthWithKey()
 
         ssh_key_free (priv_key);
 
-        return (false);
+        return (SSH_AUTH_ERROR);
     }
     else if (SSH_OK != rc) {
         x2goDebug << "Failed to get private key from " << keyName << "; trying to query passphrase.";
@@ -1425,7 +1428,7 @@ bool SshMasterConnection::userAuthWithKey()
       }
       else {
         /* Don't pass invalid files to privatekey_from_file () - it crashes in this case. */
-        return (false);
+        return (SSH_AUTH_ERROR);
       }
     }
     ssh_private_key priv_key = privatekey_from_file (my_ssh_session, tmp_ba.data (), 0, NULL);
@@ -1483,7 +1486,7 @@ bool SshMasterConnection::userAuthWithKey()
 #endif
         if ( autoRemove )
             QFile::remove ( keyName );
-        return false;
+        return (SSH_AUTH_ERROR);
     }
 
 #if LIBSSH_VERSION_INT >= SSH_VERSION_INT (0, 6, 0)
@@ -1514,7 +1517,7 @@ bool SshMasterConnection::userAuthWithKey()
 #endif
         if ( autoRemove )
             QFile::remove ( keyName );
-        return false;
+        return (SSH_AUTH_ERROR);
     }
 
 #if LIBSSH_VERSION_INT >= SSH_VERSION_INT (0, 6, 0)
@@ -1525,8 +1528,7 @@ bool SshMasterConnection::userAuthWithKey()
     ssh_key_free (pub_key);
     pub_key = NULL;
 
-    /* FIXME: handle SSH_AUTH_PARTIAL correctly! */
-    if (SSH_AUTH_SUCCESS != rc) {
+    if (rc != SSH_AUTH_SUCCESS && rc != SSH_AUTH_PARTIAL ) {
         x2goDebug << "Unable to authenticate with public key.";
 
         ssh_key_free (priv_key);
@@ -1536,7 +1538,7 @@ bool SshMasterConnection::userAuthWithKey()
             QFile::remove (keyName);
         }
 
-        return (false);
+        return (SSH_AUTH_ERROR);
     }
 
     do {
@@ -1560,8 +1562,7 @@ bool SshMasterConnection::userAuthWithKey()
     if ( autoRemove )
         QFile::remove ( keyName );
 
-    /* FIXME: handle SSH_AUTH_PARTIAL correctly! */
-    if ( rc != SSH_AUTH_SUCCESS )
+    if ( rc != SSH_AUTH_SUCCESS && rc != SSH_AUTH_PARTIAL )
     {
         QString err=ssh_get_error ( my_ssh_session );
         authErrors<<err;
@@ -1570,9 +1571,9 @@ bool SshMasterConnection::userAuthWithKey()
         x2goDebug<<"userAuthWithKey failed:" <<err<<endl;
 #endif
 
-        return false;
+        return (SSH_AUTH_ERROR);
     }
-    return true;
+    return (rc);
 }
 
 bool SshMasterConnection::userAuthKrb()
@@ -1829,17 +1830,22 @@ bool SshMasterConnection::checkLogin()
 
 bool SshMasterConnection::userAuth()
 {
+    int rc = 0;
     if (kerberos)
         return userAuthKrb();
     if ( autologin && key=="" )
-        if ( userAuthAuto() )
+    {
+        rc = userAuthAuto();
+        if ( rc == SSH_AUTH_SUCCESS )
             return true;
+    }
     if ( key!="" )
     {
-        if ( userAuthWithKey() )
+        rc = userAuthWithKey();
+        if ( rc == SSH_AUTH_SUCCESS )
             return true;
     }
-    return userAuthWithPass();
+    return userAuthWithPass(rc == SSH_AUTH_PARTIAL);
 }
 
 
diff --git a/src/sshmasterconnection.h b/src/sshmasterconnection.h
index ad6776b..70efb3f 100644
--- a/src/sshmasterconnection.h
+++ b/src/sshmasterconnection.h
@@ -125,9 +125,9 @@ public:
 
 private:
     bool sshConnect();
-    bool userAuthWithPass();
-    bool userAuthAuto();
-    bool userAuthWithKey();
+    bool userAuthWithPass(bool partial);
+    int userAuthAuto();
+    int userAuthWithKey();
     bool userChallengeAuth();
     bool checkLogin();
     bool userAuth();
_______________________________________________
x2go-dev mailing list
x2go-dev@lists.x2go.org
https://lists.x2go.org/listinfo/x2go-dev

Reply via email to