[gvfs/wip/oholy/dav-403: 2/2] dav: Try authenticate again even if 403 was returned



commit e9653aa9a2e670fb75b2b7d4afec22fa70751fef
Author: Ondrej Holy <oholy redhat com>
Date:   Thu Dec 20 13:44:00 2018 +0100

    dav: Try authenticate again even if 403 was returned
    
    Some servers e.g. davs://webdav.mc.gmx.net returns 403 status code
    instead of 401 in case of invalid credentials. This causes that libsoup
    fails immediately after the first login attempt, which is especially
    problem in case of the wrong credentials stored in the keyring. A user
    doesn't have any chance to manually specify correct credentials. Clear
    the credentials cache and force libsoup to call the authentication
    callback again...
    
    Closes: https://gitlab.gnome.org/GNOME/gvfs/issues/351

 daemon/gvfsbackenddav.c | 31 +++++++++++++++++++++++++++++--
 1 file changed, 29 insertions(+), 2 deletions(-)
---
diff --git a/daemon/gvfsbackenddav.c b/daemon/gvfsbackenddav.c
index 203363d7..fd319758 100644
--- a/daemon/gvfsbackenddav.c
+++ b/daemon/gvfsbackenddav.c
@@ -94,6 +94,7 @@ struct _MountAuthData {
 
   SoupSession  *session;
   GMountSource *mount_source;
+  gboolean retrying_after_403;
 
   AuthInfo server_auth;
   AuthInfo proxy_auth;
@@ -1503,11 +1504,13 @@ soup_authenticate_interactive (SoupSession *session,
   char              *new_password;
   char              *prompt;
 
+  data = (MountAuthData *) user_data;
+
+  retrying = (retrying || data->retrying_after_403);
+
   g_debug ("+ soup_authenticate_interactive (%s) \n",
            retrying ? "retrying" : "first auth");
 
-  data = (MountAuthData *) user_data;
-
   new_username = NULL;
   new_password = NULL;
   realm        = NULL;
@@ -1913,6 +1916,30 @@ do_mount (GVfsBackend  *backend,
     is_success = SOUP_STATUS_IS_SUCCESSFUL (status);
     is_webdav = sm_has_header (msg_opts, "DAV");
 
+    /* Workaround for servers which response with 403 instead of 401 in case of
+     * wrong credentials to let the user specify its credentials again. */
+    if (status == SOUP_STATUS_FORBIDDEN &&
+        (data->server_auth.password != NULL ||
+         data->proxy_auth.password != NULL))
+      {
+        SoupSessionFeature *auth_manager;
+
+        data->retrying_after_403 = TRUE;
+
+        g_clear_pointer (&data->server_auth.username, g_free);
+        data->server_auth.username = g_strdup (mount_base->user);
+        g_clear_pointer (&data->server_auth.password, g_free);
+        g_clear_pointer (&data->proxy_auth.password, g_free);
+
+        auth_manager = soup_session_get_feature (session, SOUP_TYPE_AUTH_MANAGER);
+        soup_auth_manager_clear_cached_credentials (SOUP_AUTH_MANAGER (auth_manager));
+
+        g_object_unref (msg_opts);
+        msg_opts = soup_message_new_from_uri (SOUP_METHOD_OPTIONS, mount_base);
+
+        continue;
+      }
+
     /* If SSL is used and the certificate verifies OK, then ssl-strict remains
      * on for all further connections.
      * If SSL is used and the certificate does not verify OK, then the user


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]