PolicyKit: Branch 'master'

David Zeuthen david at kemper.freedesktop.org
Sun Feb 8 13:29:07 PST 2009


 configure.ac                                    |    1 
 docs/polkitbackend/polkitbackend-sections.txt   |    2 
 src/Makefile.am                                 |    2 
 src/nullbackend/50-nullbackend.conf             |   15 +
 src/nullbackend/Makefile.am                     |   46 +++
 src/nullbackend/nullbackend.c                   |   34 ++
 src/nullbackend/polkitbackendnullauthority.c    |  281 ++++++++++++++++++++++++
 src/nullbackend/polkitbackendnullauthority.h    |   59 +++++
 src/polkitbackend/Makefile.am                   |    1 
 src/polkitbackend/polkitbackend.h               |    2 
 src/polkitbackend/polkitbackendauthority.c      |   56 ++++
 src/polkitbackend/polkitbackendauthority.h      |    9 
 src/polkitbackend/polkitbackendlocalauthority.c |    6 
 src/polkitd/main.c                              |   15 -
 14 files changed, 514 insertions(+), 15 deletions(-)

New commits:
commit 21e21e97cd2b663ae96efe62c8f6cc69edbd1d3c
Author: David Zeuthen <davidz at redhat.com>
Date:   Sun Feb 8 16:23:45 2009 -0500

    load and choose what backend to use; also write a simple null backend
    
    The thinking is that if someone wants to turn off PolicyKit, they
    simply drop a file /etc/polkit-1/nullbackend.conf.d/99-i-hate-polkit.conf
    with the contents
    
    [Configuration]
    priority=1000
    
    This also provides a good cut-n-paste template / example etc. of how
    to implement a PolicyKit backend.

diff --git a/configure.ac b/configure.ac
index d98a0bc..a235ab8 100644
--- a/configure.ac
+++ b/configure.ac
@@ -416,6 +416,7 @@ src/polkitagent/Makefile
 src/polkitd/Makefile
 src/programs/Makefile
 src/examples/Makefile
+src/nullbackend/Makefile
 docs/version.xml
 docs/Makefile
 docs/polkit/Makefile
diff --git a/docs/polkitbackend/polkitbackend-sections.txt b/docs/polkitbackend/polkitbackend-sections.txt
index 4bbdb9a..5af0b97 100644
--- a/docs/polkitbackend/polkitbackend-sections.txt
+++ b/docs/polkitbackend/polkitbackend-sections.txt
@@ -1,6 +1,7 @@
 <SECTION>
 <FILE>polkitbackendauthority</FILE>
 <TITLE>PolkitBackendAuthority</TITLE>
+POLKIT_BACKEND_AUTHORITY_EXTENSION_POINT_NAME
 PolkitBackendAuthority
 PolkitBackendAuthorityClass
 polkit_backend_authority_check_authorization
@@ -15,6 +16,7 @@ polkit_backend_authority_enumerate_authorizations
 polkit_backend_authority_add_authorization
 polkit_backend_authority_remove_authorization
 polkit_backend_authority_system_bus_name_owner_changed
+polkit_backend_authority_get
 polkit_backend_register_authority
 <SUBSECTION Standard>
 POLKIT_BACKEND_AUTHORITY
diff --git a/src/Makefile.am b/src/Makefile.am
index d0d1d18..a90dba2 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -1,5 +1,5 @@
 
-SUBDIRS = polkit polkitbackend polkitagent polkitd programs examples
+SUBDIRS = polkit polkitbackend polkitagent polkitd nullbackend programs examples
 
 clean-local :
 	rm -f *~
diff --git a/src/nullbackend/50-nullbackend.conf b/src/nullbackend/50-nullbackend.conf
new file mode 100644
index 0000000..1c91137
--- /dev/null
+++ b/src/nullbackend/50-nullbackend.conf
@@ -0,0 +1,15 @@
+#
+# Configuration file for the PolicyKit null backend.
+#
+# Do not edit this file, it will be overwritten on update.
+#
+# To change configuration, create another file in this directory with
+# a filename that is sorted after the 50-nullback.conf.
+#
+# Only a single configuration item is supported now. The priority of
+# the null backend. It defaults to -10. See the PolicyKit documentation
+# for more information about PolicyKit backends.
+#
+
+[Configuration]
+priority=-10
diff --git a/src/nullbackend/Makefile.am b/src/nullbackend/Makefile.am
new file mode 100644
index 0000000..7ffee19
--- /dev/null
+++ b/src/nullbackend/Makefile.am
@@ -0,0 +1,46 @@
+
+NULL =
+
+module_flags = -export_dynamic -avoid-version -module -no-undefined -export-symbols-regex '^g_io_module_(load|unload)'
+
+INCLUDES =                                              	\
+	-I$(top_builddir)/src                           	\
+	-I$(top_srcdir)/src                             	\
+	-DPACKAGE_LIBEXEC_DIR=\""$(libexecdir)"\"       	\
+	-DPACKAGE_SYSCONF_DIR=\""$(sysconfdir)"\"       	\
+	-DPACKAGE_DATA_DIR=\""$(datadir)"\"             	\
+	-DPACKAGE_BIN_DIR=\""$(bindir)"\"               	\
+	-DPACKAGE_LOCALSTATE_DIR=\""$(localstatedir)"\" 	\
+	-DPACKAGE_LOCALE_DIR=\""$(localedir)"\"         	\
+	-DPACKAGE_LIB_DIR=\""$(libdir)"\"               	\
+	-D_POSIX_PTHREAD_SEMANTICS                      	\
+	-D_REENTRANT	                                	\
+	$(NULL)
+
+polkitmodulesdir = $(libdir)/polkit-1/backends
+polkitmodules_LTLIBRARIES = libpolkit-nullbackend.la
+
+libpolkit_nullbackend_la_SOURCES = 					\
+	nullbackend.c							\
+	polkitbackendnullauthority.c	polkitbackendnullauthority.h	\
+	$(NULL)
+
+libpolkit_nullbackend_la_CFLAGS =                             		\
+	-DG_LOG_DOMAIN=\"PolkitNullBackend\"				\
+	$(GLIB_CFLAGS)							\
+	$(NULL)
+
+libpolkit_nullbackend_la_LDFLAGS =  	                      		\
+	$(module_flags)               					\
+	$(GLIB_LDADD)							\
+	$(top_builddir)/src/polkitbackend/libpolkit-backend-1.la	\
+	$(NULL)
+
+libpolkit_nullbackend_la_LIBADD =  	                      		\
+	$(NULL)
+
+nullconfigdir = $(sysconfdir)/polkit-1/nullbackend.conf.d
+nullconfig_DATA = 50-nullbackend.conf
+
+clean-local :
+	rm -f *~
diff --git a/src/nullbackend/nullbackend.c b/src/nullbackend/nullbackend.c
new file mode 100644
index 0000000..0436cf0
--- /dev/null
+++ b/src/nullbackend/nullbackend.c
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2009 Red Hat, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General
+ * Public License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+ * Boston, MA 02111-1307, USA.
+ *
+ * Author: David Zeuthen <davidz at redhat.com>
+ */
+
+#include "polkitbackendnullauthority.h"
+
+void
+g_io_module_load (GIOModule *module)
+{
+  polkit_backend_null_authority_register (module);
+}
+
+void
+g_io_module_unload (GIOModule *module)
+{
+}
+
diff --git a/src/nullbackend/polkitbackendnullauthority.c b/src/nullbackend/polkitbackendnullauthority.c
new file mode 100644
index 0000000..543d2cd
--- /dev/null
+++ b/src/nullbackend/polkitbackendnullauthority.c
@@ -0,0 +1,281 @@
+/*
+ * Copyright (C) 2008 Red Hat, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General
+ * Public License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+ * Boston, MA 02111-1307, USA.
+ *
+ * Author: David Zeuthen <davidz at redhat.com>
+ */
+
+#include "config.h"
+#include <errno.h>
+#include <pwd.h>
+#include <grp.h>
+#include <string.h>
+#include <glib/gstdio.h>
+
+#include "polkitbackendnullauthority.h"
+
+struct _PolkitBackendNullAuthorityPrivate
+{
+  gint foo;
+};
+
+static GList *authority_enumerate_actions  (PolkitBackendAuthority   *authority,
+                                            PolkitSubject            *caller,
+                                            const gchar              *locale,
+                                            GError                  **error);
+
+static void authority_check_authorization (PolkitBackendAuthority        *authority,
+                                           PolkitSubject                 *caller,
+                                           PolkitSubject                 *subject,
+                                           const gchar                   *action_id,
+                                           PolkitCheckAuthorizationFlags  flags,
+                                           GCancellable                  *cancellable,
+                                           GAsyncReadyCallback            callback,
+                                           gpointer                       user_data);
+
+static PolkitAuthorizationResult authority_check_authorization_finish (PolkitBackendAuthority  *authority,
+                                                                       GAsyncResult            *res,
+                                                                       GError                 **error);
+
+G_DEFINE_DYNAMIC_TYPE (PolkitBackendNullAuthority, polkit_backend_null_authority,POLKIT_BACKEND_TYPE_AUTHORITY);
+
+static void
+polkit_backend_null_authority_init (PolkitBackendNullAuthority *authority)
+{
+  authority->priv = G_TYPE_INSTANCE_GET_PRIVATE (authority,
+                                                 POLKIT_BACKEND_TYPE_NULL_AUTHORITY,
+                                                 PolkitBackendNullAuthorityPrivate);
+}
+
+static void
+polkit_backend_null_authority_finalize (GObject *object)
+{
+  PolkitBackendNullAuthority *authority;
+
+  authority = POLKIT_BACKEND_NULL_AUTHORITY (object);
+
+  G_OBJECT_CLASS (polkit_backend_null_authority_parent_class)->finalize (object);
+}
+
+static void
+polkit_backend_null_authority_class_init (PolkitBackendNullAuthorityClass *klass)
+{
+  GObjectClass *gobject_class;
+  PolkitBackendAuthorityClass *authority_class;
+
+  gobject_class = G_OBJECT_CLASS (klass);
+  authority_class = POLKIT_BACKEND_AUTHORITY_CLASS (klass);
+
+  gobject_class->finalize = polkit_backend_null_authority_finalize;
+
+  authority_class->enumerate_actions               = authority_enumerate_actions;
+  authority_class->check_authorization             = authority_check_authorization;
+  authority_class->check_authorization_finish      = authority_check_authorization_finish;
+
+  g_type_class_add_private (klass, sizeof (PolkitBackendNullAuthorityPrivate));
+}
+
+static void
+polkit_backend_null_authority_class_finalize (PolkitBackendNullAuthorityClass *klass)
+{
+}
+
+static gint
+compare_filename (GFile *a, GFile *b)
+{
+  gchar *a_uri;
+  gchar *b_uri;
+  gint ret;
+
+  a_uri = g_file_get_uri (a);
+  b_uri = g_file_get_uri (b);
+
+  ret = g_strcmp0 (a_uri, b_uri);
+
+  return ret;
+}
+
+/* Loads and process all .conf files in /etc/polkit-1/nullbackend.conf.d/ in order */
+static void
+load_config (gint *out_priority)
+{
+  GFileEnumerator *enumerator;
+  GFile *directory;
+  GFileInfo *file_info;
+  GError *error;
+  GList *files;
+  GList *l;
+
+  directory = g_file_new_for_path (PACKAGE_SYSCONF_DIR "/polkit-1/nullbackend.conf.d");
+
+  files = NULL;
+
+  error = NULL;
+  enumerator = g_file_enumerate_children (directory,
+                                          "standard::*",
+                                          G_FILE_QUERY_INFO_NONE,
+                                          NULL,
+                                          &error);
+  if (error != NULL)
+    {
+      g_warning ("Error enumerating files: %s", error->message);
+      goto out;
+    }
+
+  while ((file_info = g_file_enumerator_next_file (enumerator, NULL, &error)) != NULL)
+    {
+      const gchar *name;
+
+      name = g_file_info_get_name (file_info);
+
+      /* only consider files ending in .conf */
+      if (g_str_has_suffix (name, ".conf"))
+        files = g_list_prepend (files, g_file_get_child (directory, name));
+
+      g_object_unref (file_info);
+    }
+  if (error != NULL)
+    {
+      g_warning ("Error enumerating files: %s", error->message);
+      goto out;
+    }
+  g_object_unref (enumerator);
+
+  files = g_list_sort (files, (GCompareFunc) compare_filename);
+
+  for (l = files; l != NULL; l = l->next)
+    {
+      GFile *file = G_FILE (l->data);
+      gchar *filename;
+      GKeyFile *key_file;
+
+      filename = g_file_get_path (file);
+
+      key_file = g_key_file_new ();
+      error = NULL;
+      if (!g_key_file_load_from_file (key_file,
+                                      filename,
+                                      G_KEY_FILE_NONE,
+                                      NULL))
+        {
+          g_warning ("Error loading file %s: %s", filename, error->message);
+          g_error_free (error);
+          error = NULL;
+        }
+      else
+        {
+          gint priority;
+
+          priority = g_key_file_get_integer (key_file,
+                                             "Configuration",
+                                             "priority",
+                                             &error);
+          if (error != NULL)
+            {
+              /* don't warn, not all config files may have this key */
+              g_error_free (error);
+            }
+          else
+            {
+              *out_priority = priority;
+            }
+
+          g_key_file_free (key_file);
+        }
+
+      g_free (filename);
+    }
+
+ out:
+  g_object_unref (directory);
+  g_list_foreach (files, (GFunc) g_object_unref, NULL);
+  g_list_free (files);
+}
+
+void
+polkit_backend_null_authority_register (GIOModule *module)
+{
+  gint priority;
+
+  priority = -1;
+
+  load_config (&priority);
+
+  polkit_backend_null_authority_register_type (G_TYPE_MODULE (module));
+
+  g_print ("Registering null backend at priority %d\n", priority);
+
+  g_io_extension_point_implement (POLKIT_BACKEND_AUTHORITY_EXTENSION_POINT_NAME,
+                                  POLKIT_BACKEND_TYPE_NULL_AUTHORITY,
+                                  "null backend " PACKAGE_VERSION,
+                                  priority);
+}
+
+/* ---------------------------------------------------------------------------------------------------- */
+
+static GList *
+authority_enumerate_actions  (PolkitBackendAuthority   *authority,
+                              PolkitSubject            *caller,
+                              const gchar              *locale,
+                              GError                  **error)
+{
+  /* We don't know any actions */
+  return NULL;
+}
+
+static void
+authority_check_authorization (PolkitBackendAuthority        *authority,
+                               PolkitSubject                 *caller,
+                               PolkitSubject                 *subject,
+                               const gchar                   *action_id,
+                               PolkitCheckAuthorizationFlags  flags,
+                               GCancellable                  *cancellable,
+                               GAsyncReadyCallback            callback,
+                               gpointer                       user_data)
+{
+  GSimpleAsyncResult *simple;
+
+  /* complete immediately */
+  simple = g_simple_async_result_new (G_OBJECT (authority),
+                                      callback,
+                                      user_data,
+                                      authority_check_authorization);
+  g_simple_async_result_complete (simple);
+  g_object_unref (simple);
+}
+
+static PolkitAuthorizationResult
+authority_check_authorization_finish (PolkitBackendAuthority  *authority,
+                                      GAsyncResult            *res,
+                                      GError                 **error)
+{
+  GSimpleAsyncResult *simple;
+  PolkitAuthorizationResult result;
+
+  simple = G_SIMPLE_ASYNC_RESULT (res);
+
+  g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == authority_check_authorization);
+
+  /* we always return NOT_AUTHORIZED, never an error */
+  result = POLKIT_AUTHORIZATION_RESULT_NOT_AUTHORIZED;
+
+  if (g_simple_async_result_propagate_error (simple, error))
+    goto out;
+
+ out:
+  return result;
+}
diff --git a/src/nullbackend/polkitbackendnullauthority.h b/src/nullbackend/polkitbackendnullauthority.h
new file mode 100644
index 0000000..318e482
--- /dev/null
+++ b/src/nullbackend/polkitbackendnullauthority.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright (C) 2009 Red Hat, Inc.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General
+ * Public License along with this library; if not, write to the
+ * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
+ * Boston, MA 02111-1307, USA.
+ *
+ * Author: David Zeuthen <davidz at redhat.com>
+ */
+
+#ifndef __POLKIT_BACKEND_NULL_AUTHORITY_H
+#define __POLKIT_BACKEND_NULL_AUTHORITY_H
+
+#include <polkitbackend/polkitbackend.h>
+
+G_BEGIN_DECLS
+
+#define POLKIT_BACKEND_TYPE_NULL_AUTHORITY         (polkit_backend_null_authority_get_type ())
+#define POLKIT_BACKEND_NULL_AUTHORITY(o)           (G_TYPE_CHECK_INSTANCE_CAST ((o), POLKIT_BACKEND_TYPE_NULL_AUTHORITY, PolkitBackendNullAuthority))
+#define POLKIT_BACKEND_NULL_AUTHORITY_CLASS(k)     (G_TYPE_CHECK_CLASS_CAST ((k), POLKIT_BACKEND_TYPE_NULL_AUTHORITY, PolkitBackendNullAuthorityClass))
+#define POLKIT_BACKEND_NULL_AUTHORITY_GET_CLASS(o) (G_TYPE_INSTANCE_GET_CLASS ((o), POLKIT_BACKEND_TYPE_NULL_AUTHORITY,PolkitBackendNullAuthorityClass))
+#define POLKIT_BACKEND_IS_NULL_AUTHORITY(o)        (G_TYPE_CHECK_INSTANCE_TYPE ((o), POLKIT_BACKEND_TYPE_NULL_AUTHORITY))
+#define POLKIT_BACKEND_IS_NULL_AUTHORITY_CLASS(k)  (G_TYPE_CHECK_CLASS_TYPE ((k), POLKIT_BACKEND_TYPE_NULL_AUTHORITY))
+
+typedef struct _PolkitBackendNullAuthority PolkitBackendNullAuthority;
+typedef struct _PolkitBackendNullAuthorityClass PolkitBackendNullAuthorityClass;
+typedef struct _PolkitBackendNullAuthorityPrivate PolkitBackendNullAuthorityPrivate;
+
+struct _PolkitBackendNullAuthority
+{
+  PolkitBackendAuthority parent_instance;
+  PolkitBackendNullAuthorityPrivate *priv;
+};
+
+struct _PolkitBackendNullAuthorityClass
+{
+  PolkitBackendAuthorityClass parent_class;
+
+};
+
+GType  polkit_backend_null_authority_get_type (void) G_GNUC_CONST;
+
+void   polkit_backend_null_authority_register (GIOModule *module);
+
+G_END_DECLS
+
+#endif /* __POLKIT_BACKEND_NULL_AUTHORITY_H */
+
diff --git a/src/polkitbackend/Makefile.am b/src/polkitbackend/Makefile.am
index 5f10f9e..a505fa7 100644
--- a/src/polkitbackend/Makefile.am
+++ b/src/polkitbackend/Makefile.am
@@ -84,3 +84,4 @@ clean-local :
 install-exec-hook:
 	mkdir -p $(DESTDIR)$(localstatedir)/lib/polkit-1
 	-chmod 600 $(DESTDIR)$(localstatedir)/lib/polkit-1
+	mkdir -p $(DESTDIR)$(libdir)/polkit-1/backends
diff --git a/src/polkitbackend/polkitbackend.h b/src/polkitbackend/polkitbackend.h
index 3da728d..6ff0439 100644
--- a/src/polkitbackend/polkitbackend.h
+++ b/src/polkitbackend/polkitbackend.h
@@ -22,6 +22,8 @@
 #ifndef __POLKIT_BACKEND_H
 #define __POLKIT_BACKEND_H
 
+#include <polkit/polkit.h>
+
 #define _POLKIT_BACKEND_INSIDE_POLKIT_BACKEND_H 1
 #include <polkitbackend/polkitbackendtypes.h>
 #include <polkitbackend/polkitbackendauthority.h>
diff --git a/src/polkitbackend/polkitbackendauthority.c b/src/polkitbackend/polkitbackendauthority.c
index f81fba8..bf40283 100644
--- a/src/polkitbackend/polkitbackendauthority.c
+++ b/src/polkitbackend/polkitbackendauthority.c
@@ -26,6 +26,7 @@
 #include <polkit/polkit.h>
 #include <polkit/polkitprivate.h>
 #include "polkitbackendauthority.h"
+#include "polkitbackendlocalauthority.h"
 
 #include "polkitbackendprivate.h"
 
@@ -85,7 +86,8 @@ polkit_backend_authority_system_bus_name_owner_changed (PolkitBackendAuthority
 
   klass = POLKIT_BACKEND_AUTHORITY_GET_CLASS (authority);
 
-  klass->system_bus_name_owner_changed (authority, name, old_owner, new_owner);
+  if (klass->system_bus_name_owner_changed != NULL)
+    klass->system_bus_name_owner_changed (authority, name, old_owner, new_owner);
 }
 
 /**
@@ -1261,3 +1263,55 @@ polkit_backend_register_authority (PolkitBackendAuthority   *authority,
   g_object_unref (server);
   return FALSE;
 }
+
+
+/**
+ * polkit_backend_authority_get:
+ *
+ * Loads all #GIOModule<!-- -->s from <literal>$(libdir)/polkit-1/backends</literal> to determine
+ * what implementation of #PolkitBackendAuthority to use. Then instantiates an object of the
+ * implementation with the highest priority and unloads all other modules.
+ *
+ * Returns: A #PolkitBackendAuthority. Free with g_object_unref().
+ **/
+PolkitBackendAuthority *
+polkit_backend_authority_get (void)
+{
+  static GIOExtensionPoint *ep = NULL;
+  static volatile GType local_authority_type = G_TYPE_INVALID;
+  GList *modules;
+  GList *authority_implementations;
+  GType authority_type;
+  PolkitBackendAuthority *authority;
+
+  /* define the extension point */
+  if (ep == NULL)
+    {
+      ep = g_io_extension_point_register (POLKIT_BACKEND_AUTHORITY_EXTENSION_POINT_NAME);
+      g_io_extension_point_set_required_type (ep, POLKIT_BACKEND_TYPE_AUTHORITY);
+    }
+
+  /* make sure local types are registered */
+  if (local_authority_type == G_TYPE_INVALID)
+    {
+      local_authority_type = POLKIT_BACKEND_TYPE_LOCAL_AUTHORITY;
+    }
+
+  /* load all modules */
+  modules = g_io_modules_load_all_in_directory (PACKAGE_LIB_DIR "/polkit-1/backends");
+
+  /* find all extensions; we have at least one here since we've registered the local backend */
+  authority_implementations = g_io_extension_point_get_extensions (ep);
+
+  /* the returned list is sorted according to priority so just take the highest one */
+  authority_type = g_io_extension_get_type ((GIOExtension*) authority_implementations->data);
+  authority = POLKIT_BACKEND_AUTHORITY (g_object_new (authority_type, NULL));
+
+  /* unload all modules; the module our instantiated authority is in won't be unloaded because
+   * we've instantiated a reference to a type in this module
+   */
+  g_list_foreach (modules, (GFunc) g_type_module_unuse, NULL);
+  g_list_free (modules);
+
+  return authority;
+}
diff --git a/src/polkitbackend/polkitbackendauthority.h b/src/polkitbackend/polkitbackendauthority.h
index 25c0ce0..e08360b 100644
--- a/src/polkitbackend/polkitbackendauthority.h
+++ b/src/polkitbackend/polkitbackendauthority.h
@@ -41,6 +41,13 @@ G_BEGIN_DECLS
 typedef struct _PolkitBackendAuthorityClass    PolkitBackendAuthorityClass;
 
 /**
+ * POLKIT_BACKEND_AUTHORITY_EXTENSION_POINT_NAME:
+ *
+ * Extension point name for authority backend implementations.
+ */
+#define POLKIT_BACKEND_AUTHORITY_EXTENSION_POINT_NAME "polkit-backend-authority-1"
+
+/**
  * PolkitBackendAuthority:
  *
  * The #PolkitBackendAuthority struct should not be accessed directly.
@@ -258,6 +265,8 @@ gboolean polkit_backend_authority_authentication_agent_response (PolkitBackendAu
 
 /* --- */
 
+PolkitBackendAuthority *polkit_backend_authority_get (void);
+
 gboolean polkit_backend_register_authority (PolkitBackendAuthority   *authority,
                                             const gchar              *well_known_name,
                                             const gchar              *object_path,
diff --git a/src/polkitbackend/polkitbackendlocalauthority.c b/src/polkitbackend/polkitbackendlocalauthority.c
index 15a7f8f..c735c8c 100644
--- a/src/polkitbackend/polkitbackendlocalauthority.c
+++ b/src/polkitbackend/polkitbackendlocalauthority.c
@@ -220,7 +220,11 @@ action_pool_changed (PolkitBackendActionPool *action_pool,
 
 /* ---------------------------------------------------------------------------------------------------- */
 
-G_DEFINE_TYPE (PolkitBackendLocalAuthority, polkit_backend_local_authority, POLKIT_BACKEND_TYPE_AUTHORITY);
+G_DEFINE_TYPE_WITH_CODE (PolkitBackendLocalAuthority, polkit_backend_local_authority,POLKIT_BACKEND_TYPE_AUTHORITY,
+                         g_io_extension_point_implement (POLKIT_BACKEND_AUTHORITY_EXTENSION_POINT_NAME,
+                                                         g_define_type_id,
+                                                         "local-files " PACKAGE_VERSION,
+                                                         0));
 
 #define POLKIT_BACKEND_LOCAL_AUTHORITY_GET_PRIVATE(o) (G_TYPE_INSTANCE_GET_PRIVATE ((o), POLKIT_BACKEND_TYPE_LOCAL_AUTHORITY, PolkitBackendLocalAuthorityPrivate))
 
diff --git a/src/polkitd/main.c b/src/polkitd/main.c
index 00f82fe..432d02b 100644
--- a/src/polkitd/main.c
+++ b/src/polkitd/main.c
@@ -26,17 +26,6 @@
 #include <polkit/polkit.h>
 #include <polkitbackend/polkitbackend.h>
 
-static PolkitBackendAuthority *
-get_authority_backend (void)
-{
-  PolkitBackendAuthority *authority;
-
-  /* TODO: use extension points etc. */
-  authority = polkit_backend_local_authority_new ();
-
-  return authority;
-}
-
 int
 main (int argc, char **argv)
 {
@@ -53,7 +42,9 @@ main (int argc, char **argv)
 
   loop = g_main_loop_new (NULL, FALSE);
 
-  authority = get_authority_backend ();
+  authority = polkit_backend_authority_get ();
+
+  g_print ("Using authority class %s\n", g_type_name (G_TYPE_FROM_INSTANCE (authority)));
 
   if (!polkit_backend_register_authority (authority,
                                           "org.freedesktop.PolicyKit1",


More information about the hal-commit mailing list