Blame SOURCES/gvfsdaemon-Check-that-the-connecting-client-is-the-s.patch

7d234d
From e3808a1b4042761055b1d975333a8243d67b8bfe Mon Sep 17 00:00:00 2001
7d234d
From: Simon McVittie <smcv@collabora.com>
7d234d
Date: Wed, 5 Jun 2019 13:33:38 +0100
7d234d
Subject: [PATCH] gvfsdaemon: Check that the connecting client is the same user
7d234d
7d234d
Otherwise, an attacker who learns the abstract socket address from
7d234d
netstat(8) or similar could connect to it and issue D-Bus method
7d234d
calls.
7d234d
7d234d
Signed-off-by: Simon McVittie <smcv@collabora.com>
7d234d
---
7d234d
 daemon/gvfsdaemon.c | 36 +++++++++++++++++++++++++++++++++++-
7d234d
 1 file changed, 35 insertions(+), 1 deletion(-)
7d234d
7d234d
diff --git a/daemon/gvfsdaemon.c b/daemon/gvfsdaemon.c
7d234d
index 406d4f8e..be148a7b 100644
7d234d
--- a/daemon/gvfsdaemon.c
7d234d
+++ b/daemon/gvfsdaemon.c
7d234d
@@ -79,6 +79,7 @@ struct _GVfsDaemon
7d234d
   
7d234d
   gint mount_counter;
7d234d
   
7d234d
+  GDBusAuthObserver *auth_observer;
7d234d
   GDBusConnection *conn;
7d234d
   GVfsDBusDaemon *daemon_skeleton;
7d234d
   GVfsDBusMountable *mountable_skeleton;
7d234d
@@ -171,6 +172,8 @@ g_vfs_daemon_finalize (GObject *object)
7d234d
     }
7d234d
   if (daemon->conn != NULL)
7d234d
     g_object_unref (daemon->conn);
7d234d
+  if (daemon->auth_observer != NULL)
7d234d
+    g_object_unref (daemon->auth_observer);
7d234d
   
7d234d
   g_hash_table_destroy (daemon->registered_paths);
7d234d
   g_hash_table_destroy (daemon->client_connections);
7d234d
@@ -236,6 +239,35 @@ name_vanished_handler (GDBusConnection *connection,
7d234d
   daemon->lost_main_daemon = TRUE;
7d234d
 }
7d234d
 
7d234d
+/*
7d234d
+ * Authentication observer signal handler that authorizes connections
7d234d
+ * from the same uid as this process. This matches the behaviour of a
7d234d
+ * libdbus DBusServer/DBusConnection when no DBusAllowUnixUserFunction
7d234d
+ * has been set, but is not the default in GDBus.
7d234d
+ */
7d234d
+static gboolean
7d234d
+authorize_authenticated_peer_cb (GDBusAuthObserver *observer,
7d234d
+                                 G_GNUC_UNUSED GIOStream *stream,
7d234d
+                                 GCredentials *credentials,
7d234d
+                                 G_GNUC_UNUSED gpointer user_data)
7d234d
+{
7d234d
+  gboolean authorized = FALSE;
7d234d
+
7d234d
+  if (credentials != NULL)
7d234d
+    {
7d234d
+      GCredentials *own_credentials;
7d234d
+
7d234d
+      own_credentials = g_credentials_new ();
7d234d
+
7d234d
+      if (g_credentials_is_same_user (credentials, own_credentials, NULL))
7d234d
+        authorized = TRUE;
7d234d
+
7d234d
+      g_object_unref (own_credentials);
7d234d
+    }
7d234d
+
7d234d
+  return authorized;
7d234d
+}
7d234d
+
7d234d
 static void
7d234d
 g_vfs_daemon_init (GVfsDaemon *daemon)
7d234d
 {
7d234d
@@ -265,6 +297,8 @@ g_vfs_daemon_init (GVfsDaemon *daemon)
7d234d
 
7d234d
   daemon->conn = g_bus_get_sync (G_BUS_TYPE_SESSION, NULL, NULL);
7d234d
   g_assert (daemon->conn != NULL);
7d234d
+  daemon->auth_observer = g_dbus_auth_observer_new ();
7d234d
+  g_signal_connect (daemon->auth_observer, "authorize-authenticated-peer", G_CALLBACK (authorize_authenticated_peer_cb), NULL);
7d234d
 
7d234d
   daemon->daemon_skeleton = gvfs_dbus_daemon_skeleton_new ();
7d234d
   g_signal_connect (daemon->daemon_skeleton, "handle-get-connection", G_CALLBACK (handle_get_connection), daemon);
7d234d
@@ -876,7 +910,7 @@ handle_get_connection (GVfsDBusDaemon *object,
7d234d
   server = g_dbus_server_new_sync (address1,
7d234d
                                    G_DBUS_SERVER_FLAGS_NONE,
7d234d
                                    guid,
7d234d
-                                   NULL, /* GDBusAuthObserver */
7d234d
+                                   daemon->auth_observer,
7d234d
                                    NULL, /* GCancellable */
7d234d
                                    &error);
7d234d
   g_free (guid);
7d234d
-- 
7d234d
2.21.0
7d234d