From 3811e51b81320a574bb31aa64b6af56340012527 Mon Sep 17 00:00:00 2001
From: David Zeuthen
Date: Tue, 18 Oct 2011 13:13:16 -0400
Subject: [PATCH 2/3] Add --no-debug option and use this for D-Bus activation
From 5cd68a3aa8d5d0fdbbd3baef0601350bd43a0e4d Mon Sep 17 00:00:00 2001
From: David Zeuthen
Date: Tue, 18 Oct 2011 15:45:40 -0400
Subject: [PATCH 3/3] =?UTF-8?q?Bug=2041025=20=E2=80=93=20Add=20org.freedesktop.policykit.owner=20annotation?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
This allows daemons running as a designated uid to check
authorizations. Based on a patch from Christopher James Halse Rogers
.
https://bugs.freedesktop.org/show_bug.cgi?id=41025
Signed-off-by: David Zeuthen
---
docs/man/polkit.xml | 13 +++
.../polkitbackendinteractiveauthority.c | 81 +++++++++++++++++--
2 files changed, 85 insertions(+), 9 deletions(-)
diff --git a/docs/man/polkit.xml b/docs/man/polkit.xml
index bfa5ccd..ae67f7c 100644
--- a/docs/man/polkit.xml
+++ b/docs/man/polkit.xml
@@ -417,6 +417,19 @@ System Context | |
single lock button that should unlock multiple actions from
distinct mechanisms.
</para>
+ <para>
+ The <literal>org.freedesktop.policykit.owner</literal>
+ annotation can be used to define a set of users who can query
+ whether a client is authorized to perform this action. If this
+ annotation is not specified then only root can query whether a
+ client running as a different user is authorized for an action.
+ The value of this annotation is a string containing a space
+ separated list of PolkitIdentity</link> entries,
+ for example <literal>"unix-user:42 unix-user:colord"</literal>.
+ A typical use of this annotation is for a daemon process that
+ runs as a system user rather than root.
+ </para>
</refsect2>
</refsect1>
diff --git a/src/polkitbackend/polkitbackendinteractiveauthority.c b/src/polkitbackend/polkitbackendinteractiveauthority.c
index 3566248..99c4782 100644
--- a/src/polkitbackend/polkitbackendinteractiveauthority.c
+++ b/src/polkitbackend/polkitbackendinteractiveauthority.c
@@ -749,6 +749,62 @@ polkit_backend_interactive_authority_check_authorization_finish (PolkitBackendAu
return result;
}
+static gboolean
+may_identity_check_authorization (PolkitBackendInteractiveAuthority *interactive_authority,
+ const gchar *action_id,
+ PolkitIdentity *identity)
+{
+ PolkitBackendInteractiveAuthorityPrivate *priv = POLKIT_BACKEND_INTERACTIVE_AUTHORITY_GET_PRIVATE (interactive_authority);
+ gboolean ret = FALSE;
+ PolkitActionDescription *action_desc = NULL;
+ const gchar *owners = NULL;
+ gchar **tokens = NULL;
+ guint n;
+
+ /* uid 0 may check anything */
+ if (POLKIT_IS_UNIX_USER (identity) && polkit_unix_user_get_uid (POLKIT_UNIX_USER (identity)) == 0)
+ {
+ ret = TRUE;
+ goto out;
+ }
+
+ action_desc = polkit_backend_action_pool_get_action (priv->action_pool, action_id, NULL);
+ if (action_desc == NULL)
+ goto out;
+
+ owners = polkit_action_description_get_annotation (action_desc, "org.freedesktop.policykit.owner");
+ if (owners == NULL)
+ goto out;
+
+ tokens = g_strsplit (owners, " ", 0);
+ for (n = 0; tokens != NULL && tokens[n] != NULL; n++)
+ {
+ PolkitIdentity *owner_identity;
+ GError *error = NULL;
+ owner_identity = polkit_identity_from_string (tokens[n], &error);
+ if (owner_identity == NULL)
+ {
+ g_warning ("Error parsing owner identity %d of action_id %s: %s (%s, %d)",
+ n, action_id, error->message, g_quark_to_string (error->domain), error->code);
+ g_error_free (error);
+ continue;
+ }
+ if (polkit_identity_equal (identity, owner_identity))
+ {
+ ret = TRUE;
+ g_object_unref (owner_identity);
+ goto out;
+ }
+ g_object_unref (owner_identity);
+ }
+
+ out:
+ g_clear_object (&action_desc);
+ g_strfreev (tokens);
+
+ return ret;
+}
+
static void
polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority *authority,
PolkitSubject *caller,
@@ -851,22 +907,29 @@ polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority
g_strfreev (detail_keys);
}
}
+
+ /* Not anyone is allowed to check that process XYZ is allowed to do ABC.
+ * We only allow this if, and only if,
+ *
+ * - processes may check for another process owned by the *same* user but not
+ * if details are passed (otherwise you'd be able to spoof the dialog)
+ *
+ * - processes running as uid 0 may check anything and pass any details
+ *
+ * - if the action_id has the "org.freedesktop.policykit.owner" annotation
+ * then any uid referenced by that annotation is also allowed to check
+ * to check anything and pass any details
+ */
if (!polkit_identity_equal (user_of_caller, user_of_subject) || has_details)
{
- /* we only allow trusted callers (uid 0 + others) to check authorizations for subjects
- * they don't own - and only if there are no details passed (to avoid spoofing dialogs).
- *
- * TODO: allow other uids like 'haldaemon'?
- */
- if (!POLKIT_IS_UNIX_USER (user_of_caller) ||
- polkit_unix_user_get_uid (POLKIT_UNIX_USER (user_of_caller)) != 0)
+ if (!may_identity_check_authorization (interactive_authority, action_id, user_of_caller))
{
if (has_details)
{
g_simple_async_result_set_error (simple,
POLKIT_ERROR,
POLKIT_ERROR_NOT_AUTHORIZED,
- "Only trusted callers (e.g. uid 0) can use CheckAuthorization() and "
+ "Only trusted callers (e.g. uid 0 or an action owner) can use CheckAuthorization() and "
"pass details");
}
else
@@ -874,7 +937,7 @@ polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority
g_simple_async_result_set_error (simple,
POLKIT_ERROR,
POLKIT_ERROR_NOT_AUTHORIZED,
- "Only trusted callers (e.g. uid 0) can use CheckAuthorization() for "
+ "Only trusted callers (e.g. uid 0 or an action owner) can use CheckAuthorization() for "
"subjects belonging to other identities");
}
g_simple_async_result_complete (simple);
--
1.7.3.4
--
To unsubscribe, e-mail: opensuse-commit+unsubscribe@opensuse.org
For additional commands, e-mail: opensuse-commit+help@opensuse.org