gvfs r1510 - in trunk: . daemon



Author: otte
Date: Mon Mar  3 16:08:49 2008
New Revision: 1510
URL: http://svn.gnome.org/viewvc/gvfs?rev=1510&view=rev

Log:
2008-03-03  Benjamin Otte  <otte gnome org>

        * daemon/gvfsbackendftp.c: (ftp_connection_receive),
	(ftp_connection_sendv), (g_vfs_backend_ftp_pop_connection),
	(do_mount):
	fix server disconnect on timeout. Side effect is that the ftp backend
	just spawned multiple connections support.



Modified:
   trunk/ChangeLog
   trunk/daemon/gvfsbackendftp.c

Modified: trunk/daemon/gvfsbackendftp.c
==============================================================================
--- trunk/daemon/gvfsbackendftp.c	(original)
+++ trunk/daemon/gvfsbackendftp.c	Mon Mar  3 16:08:49 2008
@@ -89,6 +89,8 @@
   GQueue *		queue;
   GMutex *		mutex;
   GCond *		cond;
+  guint			connections;
+  guint			max_connections;
 };
 
 G_DEFINE_TYPE (GVfsBackendFtp, g_vfs_backend_ftp, G_VFS_TYPE_BACKEND)
@@ -287,13 +289,14 @@
   } reply_state = FIRST_LINE;
   guint response = 0;
 
+  g_assert (conn->job != NULL);
+
   if (ftp_connection_in_error (conn))
     return 0;
 
   conn->read_bytes = 0;
   while (reply_state != DONE)
     {
-      DEBUG ("%u %u\n", conn->read_buffer_size, conn->read_bytes);
       if (conn->read_buffer_size - conn->read_bytes < 128)
 	{
 	  gsize new_size = conn->read_buffer_size + 1024;
@@ -448,6 +451,8 @@
   gsize n_bytes;
   guint response;
 
+  g_assert (conn->job != NULL);
+
   if (ftp_connection_in_error (conn))
     return 0;
 
@@ -615,31 +620,6 @@
   return TRUE;
 }
 
-#if 0
-static FtpConnection *
-ftp_connection_new (SoupAddress * addr, 
-                    GCancellable *cancellable,
-		    const char *  username,
-		    const char *  password,
-		    GError **	  error)
-{
-  FtpConnection *conn;
-
-  conn = ftp_connection_create (addr, cancellable, error);
-  if (conn == NULL)
-    return NULL;
-
-  if (ftp_connection_login (conn, username, password, error) == 0 ||
-      !ftp_connection_use (conn, error))
-    {
-      ftp_connection_free (conn);
-      return NULL;
-    }
-
-  return conn;
-}
-#endif
-
 static gboolean
 ftp_connection_ensure_data_connection (FtpConnection *conn)
 {
@@ -842,33 +822,67 @@
 g_vfs_backend_ftp_pop_connection (GVfsBackendFtp *ftp, 
 				  GVfsJob *	  job)
 {
-  FtpConnection *conn;
+  FtpConnection *conn = NULL;
+  guint id;
 
   g_mutex_lock (ftp->mutex);
-  conn = ftp->queue ? g_queue_pop_head (ftp->queue) : NULL;
-  if (conn == NULL && ftp->queue != NULL)
+  id = g_signal_connect (job->cancellable, 
+			       "cancelled", 
+			       G_CALLBACK (do_broadcast),
+			       ftp->cond);
+  while (conn == NULL && ftp->queue != NULL)
     {
-      guint id = g_signal_connect (job->cancellable, 
-				   "cancelled", 
-				   G_CALLBACK (do_broadcast),
-				   ftp->cond);
-      while (conn == NULL && ftp->queue == NULL && !g_cancellable_is_cancelled (job->cancellable))
+      if (g_cancellable_is_cancelled (job->cancellable))
+	break;
+      conn = g_queue_pop_head (ftp->queue);
+
+      if (conn != NULL) {
+	/* Figure out if this connection had a timeout sent. If so, skip it. */
+	g_mutex_unlock (ftp->mutex);
+	ftp_connection_push_job (conn, job);
+	if (ftp_connection_send (conn, 0, "NOOP"))
+	  break;
+	    
+	g_clear_error (&conn->error);
+	conn->job = NULL;
+	ftp_connection_free (conn);
+	conn = NULL;
+	g_mutex_lock (ftp->mutex);
+	ftp->connections--;
+	continue;
+      }
+
+      if (ftp->connections < ftp->max_connections)
 	{
-	  g_cond_wait (ftp->cond, ftp->mutex);
-	  conn = g_queue_pop_head (ftp->queue);
+	  ftp->connections++;
+	  g_mutex_unlock (ftp->mutex);
+	  conn = ftp_connection_create (ftp->addr, job);
+	  ftp_connection_login (conn, ftp->user, ftp->password);
+	  ftp_connection_use (conn);
+	  if (!ftp_connection_in_error (conn))
+	    break;
+
+	  ftp_connection_pop_job (conn);
+	  ftp_connection_free (conn);
+	  conn = NULL;
+	  g_mutex_lock (ftp->mutex);
+	  ftp->connections--;
+	  /* FIXME: This assignment is racy due to the mutex unlock above */
+	  ftp->max_connections = ftp->connections;
+	  if (ftp->max_connections == 0)
+	    {
+	      DEBUG ("no more connections left, exiting...");
+	      /* FIXME: shut down properly */
+	      exit (0);
+	    }
+
+	  continue;
 	}
-      g_signal_handler_disconnect (job->cancellable, id);
-    }
-  g_mutex_unlock (ftp->mutex);
 
-  if (conn == NULL)
-    {
-      /* FIXME: need different error on force-unmount? */
-      g_vfs_job_failed (job, G_IO_ERROR, G_IO_ERROR_CANCELLED,
-	                _("Operation was cancelled"));
+      g_cond_wait (ftp->cond, ftp->mutex);
     }
+  g_signal_handler_disconnect (job->cancellable, id);
 
-  ftp_connection_push_job (conn, job);
   return conn;
 }
 
@@ -1033,6 +1047,8 @@
       g_free (display_name);
       g_vfs_backend_set_icon_name (backend, "folder-remote");
 
+      ftp->connections = 1;
+      ftp->max_connections = G_MAXUINT;
       ftp->queue = g_queue_new ();
       g_vfs_backend_ftp_push_connection (ftp, conn);
     }



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