Merge pull request #1263 from flatcar-linux/wrl/polkit-0.119

sys-auth/polkit: bump to 0.119 and apply duktape patchset
This commit is contained in:
william light 2021-10-19 13:20:50 +02:00 committed by GitHub
commit 76a5f89ca5
14 changed files with 1773 additions and 959 deletions

View File

@ -5,5 +5,3 @@ net-dns/bind-tools -gssapi
# FIXME: why isn't this set by default???
sys-libs/ncurses unicode
sys-auth/polkit -introspection

View File

@ -1,4 +1,3 @@
sys-auth/polkit -introspection
sys-apps/systemd -introspection
# Matt Turner <mattst88@gentoo.org> (2020-03-28)

View File

@ -75,9 +75,6 @@ dev-libs/cyrus-sasl kerberos -berkdb -gdbm
# don't build manpages for sssd
sys-auth/sssd -python samba kerberos gssapi ssh sudo
# needed for realmd build
sys-auth/polkit introspection
# enable logging command-line options in update_engine
dev-cpp/glog gflags
@ -147,3 +144,6 @@ dev-lang/perl minimal
# Disable cgroup-hybrid as we use the unified mode
sys-apps/systemd -cgroup-hybrid
# Remove support for GObject introspection
sys-auth/polkit -introspection

View File

@ -1 +1 @@
DIST polkit-0.113.tar.gz 1448865 SHA256 e1c095093c654951f78f8618d427faf91cf62abdefed98de40ff65eca6413c81 SHA512 ab177c89a20eeb2978ddbe28afb205d3619f9c5defe833eb68a85e71a0f2c905367f1295cbbfb85da5eafdd661bce474d5d84aca9195cd425a18c9b4170eb5f9 WHIRLPOOL 106db7e6085a4ce49da44929138671eff2fd6007c80533518abe2d91ede9242b1e3cd0a1801190eeac5d4d5c1e978a30a18e47a6b604497b38853fa60c935a81
DIST polkit-0.119.tar.gz 1387409 BLAKE2B aeb605598393d1cab40f7c77954008a0392600584c5fe8cc9acaa0e122418ee48b9cce0b6839189ea415277ff0ae4dbd5b7c71cb910aa349dcaf7e1f3f70ef06 SHA512 0260fb15da1c4c1f429e8223260981e64e297f1be8ced42f6910f09ea6581b8205aca06c9c601eb4a128acba2f468de0223118f96862ba769f95721894cf1578

View File

@ -1,188 +0,0 @@
From 2cb40c4d5feeaa09325522bd7d97910f1b59e379 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Zbigniew=20J=C4=99drzejewski-Szmek?= <zbyszek@in.waw.pl>
Date: Mon, 3 Dec 2018 10:28:58 +0100
Subject: [PATCH] Allow negative uids/gids in PolkitUnixUser and Group objects
(uid_t) -1 is still used as placeholder to mean "unset". This is OK, since
there should be no users with such number, see
https://systemd.io/UIDS-GIDS#special-linux-uids.
(uid_t) -1 is used as the default value in class initialization.
When a user or group above INT32_MAX is created, the numeric uid or
gid wraps around to negative when the value is assigned to gint, and
polkit gets confused. Let's accept such gids, except for -1.
A nicer fix would be to change the underlying type to e.g. uint32 to
not have negative values. But this cannot be done without breaking the
API, so likely new functions will have to be added (a
polkit_unix_user_new variant that takes a unsigned, and the same for
_group_new, _set_uid, _get_uid, _set_gid, _get_gid, etc.). This will
require a bigger patch.
Fixes https://gitlab.freedesktop.org/polkit/polkit/issues/74.
---
src/polkit/polkitunixgroup.c | 15 +++++++++++----
src/polkit/polkitunixprocess.c | 12 ++++++++----
src/polkit/polkitunixuser.c | 13 ++++++++++---
3 files changed, 29 insertions(+), 11 deletions(-)
diff --git a/src/polkit/polkitunixgroup.c b/src/polkit/polkitunixgroup.c
index c57a1aa..309f689 100644
--- a/src/polkit/polkitunixgroup.c
+++ b/src/polkit/polkitunixgroup.c
@@ -71,6 +71,7 @@ G_DEFINE_TYPE_WITH_CODE (PolkitUnixGroup, polkit_unix_group, G_TYPE_OBJECT,
static void
polkit_unix_group_init (PolkitUnixGroup *unix_group)
{
+ unix_group->gid = -1; /* (git_t) -1 is not a valid GID under Linux */
}
static void
@@ -100,11 +101,14 @@ polkit_unix_group_set_property (GObject *object,
GParamSpec *pspec)
{
PolkitUnixGroup *unix_group = POLKIT_UNIX_GROUP (object);
+ gint val;
switch (prop_id)
{
case PROP_GID:
- unix_group->gid = g_value_get_int (value);
+ val = g_value_get_int (value);
+ g_return_if_fail (val != -1);
+ unix_group->gid = val;
break;
default:
@@ -131,9 +135,9 @@ polkit_unix_group_class_init (PolkitUnixGroupClass *klass)
g_param_spec_int ("gid",
"Group ID",
"The UNIX group ID",
- 0,
+ G_MININT,
G_MAXINT,
- 0,
+ -1,
G_PARAM_CONSTRUCT |
G_PARAM_READWRITE |
G_PARAM_STATIC_NAME |
@@ -166,9 +170,10 @@ polkit_unix_group_get_gid (PolkitUnixGroup *group)
*/
void
polkit_unix_group_set_gid (PolkitUnixGroup *group,
- gint gid)
+ gint gid)
{
g_return_if_fail (POLKIT_IS_UNIX_GROUP (group));
+ g_return_if_fail (gid != -1);
group->gid = gid;
}
@@ -183,6 +188,8 @@ polkit_unix_group_set_gid (PolkitUnixGroup *group,
PolkitIdentity *
polkit_unix_group_new (gint gid)
{
+ g_return_val_if_fail (gid != -1, NULL);
+
return POLKIT_IDENTITY (g_object_new (POLKIT_TYPE_UNIX_GROUP,
"gid", gid,
NULL));
diff --git a/src/polkit/polkitunixprocess.c b/src/polkit/polkitunixprocess.c
index 972b777..b02b258 100644
--- a/src/polkit/polkitunixprocess.c
+++ b/src/polkit/polkitunixprocess.c
@@ -159,9 +159,14 @@ polkit_unix_process_set_property (GObject *object,
polkit_unix_process_set_pid (unix_process, g_value_get_int (value));
break;
- case PROP_UID:
- polkit_unix_process_set_uid (unix_process, g_value_get_int (value));
+ case PROP_UID: {
+ gint val;
+
+ val = g_value_get_int (value);
+ g_return_if_fail (val != -1);
+ polkit_unix_process_set_uid (unix_process, val);
break;
+ }
case PROP_START_TIME:
polkit_unix_process_set_start_time (unix_process, g_value_get_uint64 (value));
@@ -239,7 +244,7 @@ polkit_unix_process_class_init (PolkitUnixProcessClass *klass)
g_param_spec_int ("uid",
"User ID",
"The UNIX user ID",
- -1,
+ G_MININT,
G_MAXINT,
-1,
G_PARAM_CONSTRUCT |
@@ -303,7 +308,6 @@ polkit_unix_process_set_uid (PolkitUnixProcess *process,
gint uid)
{
g_return_if_fail (POLKIT_IS_UNIX_PROCESS (process));
- g_return_if_fail (uid >= -1);
process->uid = uid;
}
diff --git a/src/polkit/polkitunixuser.c b/src/polkit/polkitunixuser.c
index 8bfd3a1..234a697 100644
--- a/src/polkit/polkitunixuser.c
+++ b/src/polkit/polkitunixuser.c
@@ -72,6 +72,7 @@ G_DEFINE_TYPE_WITH_CODE (PolkitUnixUser, polkit_unix_user, G_TYPE_OBJECT,
static void
polkit_unix_user_init (PolkitUnixUser *unix_user)
{
+ unix_user->uid = -1; /* (uid_t) -1 is not a valid UID under Linux */
unix_user->name = NULL;
}
@@ -112,11 +113,14 @@ polkit_unix_user_set_property (GObject *object,
GParamSpec *pspec)
{
PolkitUnixUser *unix_user = POLKIT_UNIX_USER (object);
+ gint val;
switch (prop_id)
{
case PROP_UID:
- unix_user->uid = g_value_get_int (value);
+ val = g_value_get_int (value);
+ g_return_if_fail (val != -1);
+ unix_user->uid = val;
break;
default:
@@ -144,9 +148,9 @@ polkit_unix_user_class_init (PolkitUnixUserClass *klass)
g_param_spec_int ("uid",
"User ID",
"The UNIX user ID",
- 0,
+ G_MININT,
G_MAXINT,
- 0,
+ -1,
G_PARAM_CONSTRUCT |
G_PARAM_READWRITE |
G_PARAM_STATIC_NAME |
@@ -182,6 +186,7 @@ polkit_unix_user_set_uid (PolkitUnixUser *user,
gint uid)
{
g_return_if_fail (POLKIT_IS_UNIX_USER (user));
+ g_return_if_fail (uid != -1);
user->uid = uid;
}
@@ -196,6 +201,8 @@ polkit_unix_user_set_uid (PolkitUnixUser *user,
PolkitIdentity *
polkit_unix_user_new (gint uid)
{
+ g_return_val_if_fail (uid != -1, NULL);
+
return POLKIT_IDENTITY (g_object_new (POLKIT_TYPE_UNIX_USER,
"uid", uid,
NULL));
--
2.18.1

View File

@ -1,47 +0,0 @@
From 87aec8b7275665c85fe22bcc8e74d2a0422535ce Mon Sep 17 00:00:00 2001
From: Matthew Leeds <matthew.leeds@endlessm.com>
Date: Tue, 11 Dec 2018 12:04:26 -0800
Subject: [PATCH] Allow uid of -1 for a PolkitUnixProcess
Commit 2cb40c4d5 changed PolkitUnixUser, PolkitUnixGroup, and
PolkitUnixProcess to allow negative values for their uid/gid properties,
since these are values above INT_MAX which wrap around but are still
valid, with the exception of -1 which is not valid. However,
PolkitUnixProcess allows a uid of -1 to be passed to
polkit_unix_process_new_for_owner() which means polkit is expected to
figure out the uid on its own (this happens in the _constructed
function). So this commit removes the check in
polkit_unix_process_set_property() so that new_for_owner() can be used
as documented without producing a critical error message.
This does not affect the protection against CVE-2018-19788 which is
based on creating a user with a UID up to but not including 4294967295
(-1).
---
src/polkit/polkitunixprocess.c | 9 ++-------
1 file changed, 2 insertions(+), 7 deletions(-)
diff --git a/src/polkit/polkitunixprocess.c b/src/polkit/polkitunixprocess.c
index 2c57813..93dea3c 100644
--- a/src/polkit/polkitunixprocess.c
+++ b/src/polkit/polkitunixprocess.c
@@ -142,14 +142,9 @@ polkit_unix_process_set_property (GObject *object,
polkit_unix_process_set_pid (unix_process, g_value_get_int (value));
break;
- case PROP_UID: {
- gint val;
-
- val = g_value_get_int (value);
- g_return_if_fail (val != -1);
- polkit_unix_process_set_uid (unix_process, val);
+ case PROP_UID:
+ polkit_unix_process_set_uid (unix_process, g_value_get_int (value));
break;
- }
case PROP_START_TIME:
polkit_unix_process_set_start_time (unix_process, g_value_get_uint64 (value));
--
2.21.0

View File

@ -1,572 +0,0 @@
From 82494ed6bcff05b5a65c00bcf5212dcd2b559f70 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Miloslav=20Trma=C4=8D?= <mitr@redhat.com>
Date: Fri, 23 Aug 2019 20:31:11 -0400
Subject: [PATCH] Fix CVE-2018-1116: Trusting client-supplied UID
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
As part of CVE-2013-4288, the D-Bus clients were allowed (and
encouraged) to submit the UID of the subject of authorization checks
to avoid races against UID changes (notably using executables
set-UID to root).
However, that also allowed any client to submit an arbitrary UID, and
that could be used to bypass "can only ask about / affect the same UID"
checks in CheckAuthorization / RegisterAuthenticationAgent /
UnregisterAuthenticationAgent. This allowed an attacker:
- With CheckAuthorization, to cause the registered authentication
agent in victim's session to pop up a dialog, or to determine whether
the victim currently has a temporary authorization to perform an
operation.
(In principle, the attacker can also determine whether JavaScript
rules allow the victim process to perform an operation; however,
usually rules base their decisions on information determined from
the supplied UID, so the attacker usually won't learn anything new.)
- With RegisterAuthenticationAgent, to prevent the victim's
authentication agent to work (for a specific victim process),
or to learn about which operations requiring authorization
the victim is attempting.
To fix this, expose internal _polkit_unix_process_get_owner() /
obsolete polkit_unix_process_get_owner() as a private
polkit_unix_process_get_racy_uid__() (being more explicit about the
dangers on relying on it), and use it in
polkit_backend_session_monitor_get_user_for_subject() to return
a boolean indicating whether the subject UID may be caller-chosen.
Then, in the permission checks that require the subject to be
equal to the caller, fail on caller-chosen UIDs (and continue
through the pre-existing code paths which allow root, or root-designated
server processes, to ask about arbitrary subjects.)
Signed-off-by: Miloslav Trmač <mitr@redhat.com>
---
src/polkit/polkitprivate.h | 2 +
src/polkit/polkitunixprocess.c | 60 +++++++++++++++----
.../polkitbackendinteractiveauthority.c | 39 +++++++-----
.../polkitbackendsessionmonitor-systemd.c | 38 ++++++++++--
.../polkitbackendsessionmonitor.c | 40 +++++++++++--
.../polkitbackendsessionmonitor.h | 1 +
6 files changed, 147 insertions(+), 33 deletions(-)
diff --git a/src/polkit/polkitprivate.h b/src/polkit/polkitprivate.h
index 9f07063..c80142d 100644
--- a/src/polkit/polkitprivate.h
+++ b/src/polkit/polkitprivate.h
@@ -44,6 +44,8 @@ GVariant *polkit_action_description_to_gvariant (PolkitActionDescription *action
GVariant *polkit_subject_to_gvariant (PolkitSubject *subject);
GVariant *polkit_identity_to_gvariant (PolkitIdentity *identity);
+gint polkit_unix_process_get_racy_uid__ (PolkitUnixProcess *process, GError **error);
+
PolkitSubject *polkit_subject_new_for_gvariant (GVariant *variant, GError **error);
PolkitIdentity *polkit_identity_new_for_gvariant (GVariant *variant, GError **error);
diff --git a/src/polkit/polkitunixprocess.c b/src/polkit/polkitunixprocess.c
index 93dea3c..f799942 100644
--- a/src/polkit/polkitunixprocess.c
+++ b/src/polkit/polkitunixprocess.c
@@ -49,6 +49,14 @@
* To uniquely identify processes, both the process id and the start
* time of the process (a monotonic increasing value representing the
* time since the kernel was started) is used.
+ *
+ * NOTE: This object stores, and provides access to, the real UID of the
+ * process. That value can change over time (with set*uid*(2) and exec*(2)).
+ * Checks whether an operation is allowed need to take care to use the UID
+ * value as of the time when the operation was made (or, following the open()
+ * privilege check model, when the connection making the operation possible
+ * was initiated). That is usually done by initializing this with
+ * polkit_unix_process_new_for_owner() with trusted data.
*/
/**
@@ -83,9 +91,6 @@ static void subject_iface_init (PolkitSubjectIface *subject_iface);
static guint64 get_start_time_for_pid (gint pid,
GError **error);
-static gint _polkit_unix_process_get_owner (PolkitUnixProcess *process,
- GError **error);
-
#ifdef HAVE_FREEBSD
static gboolean get_kinfo_proc (gint pid, struct kinfo_proc *p);
#endif
@@ -170,7 +175,7 @@ polkit_unix_process_constructed (GObject *object)
{
GError *error;
error = NULL;
- process->uid = _polkit_unix_process_get_owner (process, &error);
+ process->uid = polkit_unix_process_get_racy_uid__ (process, &error);
if (error != NULL)
{
process->uid = -1;
@@ -259,6 +264,12 @@ polkit_unix_process_class_init (PolkitUnixProcessClass *klass)
* Gets the user id for @process. Note that this is the real user-id,
* not the effective user-id.
*
+ * NOTE: The UID may change over time, so the returned value may not match the
+ * current state of the underlying process; or the UID may have been set by
+ * polkit_unix_process_new_for_owner() or polkit_unix_process_set_uid(),
+ * in which case it may not correspond to the actual UID of the referenced
+ * process at all (at any point in time).
+ *
* Returns: The user id for @process or -1 if unknown.
*/
gint
@@ -654,18 +665,26 @@ out:
return start_time;
}
-static gint
-_polkit_unix_process_get_owner (PolkitUnixProcess *process,
- GError **error)
+/*
+ * Private: Return the "current" UID. Note that this is inherently racy,
+ * and the value may already be obsolete by the time this function returns;
+ * this function only guarantees that the UID was valid at some point during
+ * its execution.
+ */
+gint
+polkit_unix_process_get_racy_uid__ (PolkitUnixProcess *process,
+ GError **error)
{
gint result;
gchar *contents;
gchar **lines;
+ guint64 start_time;
#ifdef HAVE_FREEBSD
struct kinfo_proc p;
#else
gchar filename[64];
guint n;
+ GError *local_error;
#endif
g_return_val_if_fail (POLKIT_IS_UNIX_PROCESS (process), 0);
@@ -688,6 +707,7 @@ _polkit_unix_process_get_owner (PolkitUnixProcess *process,
}
result = p.ki_uid;
+ start_time = (guint64) p.ki_start.tv_sec;
#else
/* see 'man proc' for layout of the status file
@@ -721,17 +741,37 @@ _polkit_unix_process_get_owner (PolkitUnixProcess *process,
else
{
result = real_uid;
- goto out;
+ goto found;
}
}
-
g_set_error (error,
POLKIT_ERROR,
POLKIT_ERROR_FAILED,
"Didn't find any line starting with `Uid:' in file %s",
filename);
+ goto out;
+
+found:
+ /* The UID and start time are, sadly, not available in a single file. So,
+ * read the UID first, and then the start time; if the start time is the same
+ * before and after reading the UID, it couldn't have changed.
+ */
+ local_error = NULL;
+ start_time = get_start_time_for_pid (process->pid, &local_error);
+ if (local_error != NULL)
+ {
+ g_propagate_error (error, local_error);
+ goto out;
+ }
#endif
+ if (process->start_time != start_time)
+ {
+ g_set_error (error, POLKIT_ERROR, POLKIT_ERROR_FAILED,
+ "process with PID %d has been replaced", process->pid);
+ goto out;
+ }
+
out:
g_strfreev (lines);
g_free (contents);
@@ -750,5 +790,5 @@ gint
polkit_unix_process_get_owner (PolkitUnixProcess *process,
GError **error)
{
- return _polkit_unix_process_get_owner (process, error);
+ return polkit_unix_process_get_racy_uid__ (process, error);
}
diff --git a/src/polkitbackend/polkitbackendinteractiveauthority.c b/src/polkitbackend/polkitbackendinteractiveauthority.c
index 7019356..0b587a3 100644
--- a/src/polkitbackend/polkitbackendinteractiveauthority.c
+++ b/src/polkitbackend/polkitbackendinteractiveauthority.c
@@ -572,7 +572,7 @@ log_result (PolkitBackendInteractiveAuthority *authority,
if (polkit_authorization_result_get_is_authorized (result))
log_result_str = "ALLOWING";
- user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, subject, NULL);
+ user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, subject, NULL, NULL);
subject_str = polkit_subject_to_string (subject);
@@ -844,6 +844,7 @@ polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority
gchar *subject_str;
PolkitIdentity *user_of_caller;
PolkitIdentity *user_of_subject;
+ gboolean user_of_subject_matches;
gchar *user_of_caller_str;
gchar *user_of_subject_str;
PolkitAuthorizationResult *result;
@@ -889,7 +890,7 @@ polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority
action_id);
user_of_caller = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor,
- caller,
+ caller, NULL,
&error);
if (error != NULL)
{
@@ -904,7 +905,7 @@ polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority
g_debug (" user of caller is %s", user_of_caller_str);
user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor,
- subject,
+ subject, &user_of_subject_matches,
&error);
if (error != NULL)
{
@@ -934,7 +935,10 @@ polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority
* 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)
+ * if details are passed (otherwise you'd be able to spoof the dialog);
+ * the caller supplies the user_of_subject value, so we additionally
+ * require it to match at least at one point in time (via
+ * user_of_subject_matches).
*
* - processes running as uid 0 may check anything and pass any details
*
@@ -942,7 +946,9 @@ polkit_backend_interactive_authority_check_authorization (PolkitBackendAuthority
* 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)
+ if (!user_of_subject_matches
+ || !polkit_identity_equal (user_of_caller, user_of_subject)
+ || has_details)
{
if (!may_identity_check_authorization (interactive_authority, action_id, user_of_caller))
{
@@ -1107,9 +1113,10 @@ check_authorization_sync (PolkitBackendAuthority *authority,
goto out;
}
- /* every subject has a user */
+ /* every subject has a user; this is supplied by the client, so we rely
+ * on the caller to validate its acceptability. */
user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor,
- subject,
+ subject, NULL,
error);
if (user_of_subject == NULL)
goto out;
@@ -2475,6 +2482,7 @@ polkit_backend_interactive_authority_register_authentication_agent (PolkitBacken
PolkitSubject *session_for_caller;
PolkitIdentity *user_of_caller;
PolkitIdentity *user_of_subject;
+ gboolean user_of_subject_matches;
AuthenticationAgent *agent;
gboolean ret;
gchar *caller_cmdline;
@@ -2527,7 +2535,7 @@ polkit_backend_interactive_authority_register_authentication_agent (PolkitBacken
goto out;
}
- user_of_caller = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, caller, NULL);
+ user_of_caller = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, caller, NULL, NULL);
if (user_of_caller == NULL)
{
g_set_error (error,
@@ -2536,7 +2544,7 @@ polkit_backend_interactive_authority_register_authentication_agent (PolkitBacken
"Cannot determine user of caller");
goto out;
}
- user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, subject, NULL);
+ user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, subject, &user_of_subject_matches, NULL);
if (user_of_subject == NULL)
{
g_set_error (error,
@@ -2545,7 +2553,8 @@ polkit_backend_interactive_authority_register_authentication_agent (PolkitBacken
"Cannot determine user of subject");
goto out;
}
- if (!polkit_identity_equal (user_of_caller, user_of_subject))
+ if (!user_of_subject_matches
+ || !polkit_identity_equal (user_of_caller, user_of_subject))
{
if (identity_is_root_user (user_of_caller))
{
@@ -2638,6 +2647,7 @@ polkit_backend_interactive_authority_unregister_authentication_agent (PolkitBack
PolkitSubject *session_for_caller;
PolkitIdentity *user_of_caller;
PolkitIdentity *user_of_subject;
+ gboolean user_of_subject_matches;
AuthenticationAgent *agent;
gboolean ret;
gchar *scope_str;
@@ -2686,7 +2696,7 @@ polkit_backend_interactive_authority_unregister_authentication_agent (PolkitBack
goto out;
}
- user_of_caller = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, caller, NULL);
+ user_of_caller = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, caller, NULL, NULL);
if (user_of_caller == NULL)
{
g_set_error (error,
@@ -2695,7 +2705,7 @@ polkit_backend_interactive_authority_unregister_authentication_agent (PolkitBack
"Cannot determine user of caller");
goto out;
}
- user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, subject, NULL);
+ user_of_subject = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor, subject, &user_of_subject_matches, NULL);
if (user_of_subject == NULL)
{
g_set_error (error,
@@ -2704,7 +2714,8 @@ polkit_backend_interactive_authority_unregister_authentication_agent (PolkitBack
"Cannot determine user of subject");
goto out;
}
- if (!polkit_identity_equal (user_of_caller, user_of_subject))
+ if (!user_of_subject_matches
+ || !polkit_identity_equal (user_of_caller, user_of_subject))
{
if (identity_is_root_user (user_of_caller))
{
@@ -2814,7 +2825,7 @@ polkit_backend_interactive_authority_authentication_agent_response (PolkitBacken
identity_str);
user_of_caller = polkit_backend_session_monitor_get_user_for_subject (priv->session_monitor,
- caller,
+ caller, NULL,
error);
if (user_of_caller == NULL)
goto out;
diff --git a/src/polkitbackend/polkitbackendsessionmonitor-systemd.c b/src/polkitbackend/polkitbackendsessionmonitor-systemd.c
index 2a6c739..b00cdbd 100644
--- a/src/polkitbackend/polkitbackendsessionmonitor-systemd.c
+++ b/src/polkitbackend/polkitbackendsessionmonitor-systemd.c
@@ -29,6 +29,7 @@
#include <stdlib.h>
#include <polkit/polkit.h>
+#include <polkit/polkitprivate.h>
#include "polkitbackendsessionmonitor.h"
/* <internal>
@@ -246,26 +247,40 @@ polkit_backend_session_monitor_get_sessions (PolkitBackendSessionMonitor *monito
* polkit_backend_session_monitor_get_user:
* @monitor: A #PolkitBackendSessionMonitor.
* @subject: A #PolkitSubject.
+ * @result_matches: If not %NULL, set to indicate whether the return value matches current (RACY) state.
* @error: Return location for error.
*
* Gets the user corresponding to @subject or %NULL if no user exists.
*
+ * NOTE: For a #PolkitUnixProcess, the UID is read from @subject (which may
+ * come from e.g. a D-Bus client), so it may not correspond to the actual UID
+ * of the referenced process (at any point in time). This is indicated by
+ * setting @result_matches to %FALSE; the caller may reject such subjects or
+ * require additional privileges. @result_matches == %TRUE only indicates that
+ * the UID matched the underlying process at ONE point in time, it may not match
+ * later.
+ *
* Returns: %NULL if @error is set otherwise a #PolkitUnixUser that should be freed with g_object_unref().
*/
PolkitIdentity *
polkit_backend_session_monitor_get_user_for_subject (PolkitBackendSessionMonitor *monitor,
PolkitSubject *subject,
+ gboolean *result_matches,
GError **error)
{
PolkitIdentity *ret;
- guint32 uid;
+ gboolean matches;
ret = NULL;
+ matches = FALSE;
if (POLKIT_IS_UNIX_PROCESS (subject))
{
- uid = polkit_unix_process_get_uid (POLKIT_UNIX_PROCESS (subject));
- if ((gint) uid == -1)
+ gint subject_uid, current_uid;
+ GError *local_error;
+
+ subject_uid = polkit_unix_process_get_uid (POLKIT_UNIX_PROCESS (subject));
+ if (subject_uid == -1)
{
g_set_error (error,
POLKIT_ERROR,
@@ -273,14 +288,24 @@ polkit_backend_session_monitor_get_user_for_subject (PolkitBackendSessionMonitor
"Unix process subject does not have uid set");
goto out;
}
- ret = polkit_unix_user_new (uid);
+ local_error = NULL;
+ current_uid = polkit_unix_process_get_racy_uid__ (POLKIT_UNIX_PROCESS (subject), &local_error);
+ if (local_error != NULL)
+ {
+ g_propagate_error (error, local_error);
+ goto out;
+ }
+ ret = polkit_unix_user_new (subject_uid);
+ matches = (subject_uid == current_uid);
}
else if (POLKIT_IS_SYSTEM_BUS_NAME (subject))
{
ret = (PolkitIdentity*)polkit_system_bus_name_get_user_sync (POLKIT_SYSTEM_BUS_NAME (subject), NULL, error);
+ matches = TRUE;
}
else if (POLKIT_IS_UNIX_SESSION (subject))
{
+ uid_t uid;
if (sd_session_get_uid (polkit_unix_session_get_session_id (POLKIT_UNIX_SESSION (subject)), &uid) < 0)
{
@@ -292,9 +317,14 @@ polkit_backend_session_monitor_get_user_for_subject (PolkitBackendSessionMonitor
}
ret = polkit_unix_user_new (uid);
+ matches = TRUE;
}
out:
+ if (result_matches != NULL)
+ {
+ *result_matches = matches;
+ }
return ret;
}
diff --git a/src/polkitbackend/polkitbackendsessionmonitor.c b/src/polkitbackend/polkitbackendsessionmonitor.c
index e1a9ab3..ed30755 100644
--- a/src/polkitbackend/polkitbackendsessionmonitor.c
+++ b/src/polkitbackend/polkitbackendsessionmonitor.c
@@ -27,6 +27,7 @@
#include <glib/gstdio.h>
#include <polkit/polkit.h>
+#include <polkit/polkitprivate.h>
#include "polkitbackendsessionmonitor.h"
#define CKDB_PATH "/var/run/ConsoleKit/database"
@@ -273,28 +274,40 @@ polkit_backend_session_monitor_get_sessions (PolkitBackendSessionMonitor *monito
* polkit_backend_session_monitor_get_user:
* @monitor: A #PolkitBackendSessionMonitor.
* @subject: A #PolkitSubject.
+ * @result_matches: If not %NULL, set to indicate whether the return value matches current (RACY) state.
* @error: Return location for error.
*
* Gets the user corresponding to @subject or %NULL if no user exists.
*
+ * NOTE: For a #PolkitUnixProcess, the UID is read from @subject (which may
+ * come from e.g. a D-Bus client), so it may not correspond to the actual UID
+ * of the referenced process (at any point in time). This is indicated by
+ * setting @result_matches to %FALSE; the caller may reject such subjects or
+ * require additional privileges. @result_matches == %TRUE only indicates that
+ * the UID matched the underlying process at ONE point in time, it may not match
+ * later.
+ *
* Returns: %NULL if @error is set otherwise a #PolkitUnixUser that should be freed with g_object_unref().
*/
PolkitIdentity *
polkit_backend_session_monitor_get_user_for_subject (PolkitBackendSessionMonitor *monitor,
PolkitSubject *subject,
+ gboolean *result_matches,
GError **error)
{
PolkitIdentity *ret;
+ gboolean matches;
GError *local_error;
- gchar *group;
- guint32 uid;
ret = NULL;
+ matches = FALSE;
if (POLKIT_IS_UNIX_PROCESS (subject))
{
- uid = polkit_unix_process_get_uid (POLKIT_UNIX_PROCESS (subject));
- if ((gint) uid == -1)
+ gint subject_uid, current_uid;
+
+ subject_uid = polkit_unix_process_get_uid (POLKIT_UNIX_PROCESS (subject));
+ if (subject_uid == -1)
{
g_set_error (error,
POLKIT_ERROR,
@@ -302,14 +315,26 @@ polkit_backend_session_monitor_get_user_for_subject (PolkitBackendSessionMonitor
"Unix process subject does not have uid set");
goto out;
}
- ret = polkit_unix_user_new (uid);
+ local_error = NULL;
+ current_uid = polkit_unix_process_get_racy_uid__ (POLKIT_UNIX_PROCESS (subject), &local_error);
+ if (local_error != NULL)
+ {
+ g_propagate_error (error, local_error);
+ goto out;
+ }
+ ret = polkit_unix_user_new (subject_uid);
+ matches = (subject_uid == current_uid);
}
else if (POLKIT_IS_SYSTEM_BUS_NAME (subject))
{
ret = (PolkitIdentity*)polkit_system_bus_name_get_user_sync (POLKIT_SYSTEM_BUS_NAME (subject), NULL, error);
+ matches = TRUE;
}
else if (POLKIT_IS_UNIX_SESSION (subject))
{
+ gint uid;
+ gchar *group;
+
if (!ensure_database (monitor, error))
{
g_prefix_error (error, "Error getting user for session: Error ensuring CK database at " CKDB_PATH ": ");
@@ -328,9 +353,14 @@ polkit_backend_session_monitor_get_user_for_subject (PolkitBackendSessionMonitor
g_free (group);
ret = polkit_unix_user_new (uid);
+ matches = TRUE;
}
out:
+ if (result_matches != NULL)
+ {
+ *result_matches = matches;
+ }
return ret;
}
diff --git a/src/polkitbackend/polkitbackendsessionmonitor.h b/src/polkitbackend/polkitbackendsessionmonitor.h
index 8f8a2ca..3972326 100644
--- a/src/polkitbackend/polkitbackendsessionmonitor.h
+++ b/src/polkitbackend/polkitbackendsessionmonitor.h
@@ -47,6 +47,7 @@ GList *polkit_backend_session_monitor_get_sessions (Polkit
PolkitIdentity *polkit_backend_session_monitor_get_user_for_subject (PolkitBackendSessionMonitor *monitor,
PolkitSubject *subject,
+ gboolean *result_matches,
GError **error);
PolkitSubject *polkit_backend_session_monitor_get_session_for_subject (PolkitBackendSessionMonitor *monitor,
--
2.21.0

View File

@ -1,21 +0,0 @@
--- polkit-0.113.orig/configure 2015-06-19 13:31:13.000000000 -0700
+++ polkit-0.113/configure 2016-04-27 16:00:31.800252583 -0700
@@ -14949,14 +14949,14 @@
INTROSPECTION_GIRDIR=
INTROSPECTION_TYPELIBDIR=
if test "x$found_introspection" = "xyes"; then
- INTROSPECTION_SCANNER=`$PKG_CONFIG --variable=g_ir_scanner gobject-introspection-1.0`
- INTROSPECTION_COMPILER=`$PKG_CONFIG --variable=g_ir_compiler gobject-introspection-1.0`
- INTROSPECTION_GENERATE=`$PKG_CONFIG --variable=g_ir_generate gobject-introspection-1.0`
+ INTROSPECTION_SCANNER=${SYSROOT}/`$PKG_CONFIG --variable=g_ir_scanner gobject-introspection-1.0`
+ INTROSPECTION_COMPILER=${SYROOT}/`$PKG_CONFIG --variable=g_ir_compiler gobject-introspection-1.0`
+ INTROSPECTION_GENERATE=${SYSROOT}/`$PKG_CONFIG --variable=g_ir_generate gobject-introspection-1.0`
INTROSPECTION_GIRDIR=`$PKG_CONFIG --variable=girdir gobject-introspection-1.0`
INTROSPECTION_TYPELIBDIR="$($PKG_CONFIG --variable=typelibdir gobject-introspection-1.0)"
INTROSPECTION_CFLAGS=`$PKG_CONFIG --cflags gobject-introspection-1.0`
INTROSPECTION_LIBS=`$PKG_CONFIG --libs gobject-introspection-1.0`
- INTROSPECTION_MAKEFILE=`$PKG_CONFIG --variable=datadir gobject-introspection-1.0`/gobject-introspection-1.0/Makefile.introspection
+ INTROSPECTION_MAKEFILE=${SYSROOT}/`$PKG_CONFIG --variable=datadir gobject-introspection-1.0`/gobject-introspection-1.0/Makefile.introspection
fi

View File

@ -0,0 +1,28 @@
From 08bb656496cd3d6213bbe9473f63f2d4a110da6e Mon Sep 17 00:00:00 2001
From: Rasmus Thomsen <cogitri@exherbo.org>
Date: Wed, 11 Apr 2018 13:14:14 +0200
Subject: [PATCH] configure: fix elogind support
HAVE_LIBSYSTEMD is used to determine which source files to use.
We have to check if either have_libsystemd or have_libelogind is
true, as both of these need the source files which are used when
HAVE_LIBSYSTEMD is true.
---
configure.ac | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/configure.ac b/configure.ac
index 36df239..da47ecb 100644
--- a/configure.ac
+++ b/configure.ac
@@ -221,7 +221,7 @@ AS_IF([test "x$cross_compiling" != "xyes" ], [
AC_SUBST(LIBSYSTEMD_CFLAGS)
AC_SUBST(LIBSYSTEMD_LIBS)
-AM_CONDITIONAL(HAVE_LIBSYSTEMD, [test "$have_libsystemd" = "yes"], [Using libsystemd])
+AM_CONDITIONAL(HAVE_LIBSYSTEMD, [test "$have_libsystemd" = "yes" || test "$have_libelogind" = "yes" ], [Using libsystemd])
dnl ---------------------------------------------------------------------------
dnl - systemd unit / service files
--
2.17.0

View File

@ -1,11 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE pkgmetadata SYSTEM "http://www.gentoo.org/dtd/metadata.dtd">
<pkgmetadata>
<herd>freedesktop</herd>
<maintainer>
<maintainer type="project">
<email>freedesktop-bugs@gentoo.org</email>
</maintainer>
<use>
<flag name='systemd'>Use <pkg>sys-apps/systemd</pkg> instead of <pkg>sys-auth/consolekit</pkg> for session tracking</flag>
<flag name="elogind">Use <pkg>sys-auth/elogind</pkg> for session tracking</flag>
<flag name="systemd">Use <pkg>sys-apps/systemd</pkg> for session tracking</flag>
</use>
</pkgmetadata>

View File

@ -1,120 +0,0 @@
# Copyright 1999-2015 Gentoo Foundation
# Distributed under the terms of the GNU General Public License v2
# $Id$
EAPI=5
inherit eutils multilib pam pax-utils toolchain-funcs systemd user
DESCRIPTION="Policy framework for controlling privileges for system-wide services"
HOMEPAGE="http://www.freedesktop.org/wiki/Software/polkit"
SRC_URI="http://www.freedesktop.org/software/${PN}/releases/${P}.tar.gz"
LICENSE="LGPL-2"
SLOT="0"
KEYWORDS="alpha amd64 arm64 arm hppa ia64 ~mips ppc ppc64 ~s390 ~sh ~sparc x86"
IUSE="examples gtk +introspection jit kde nls pam selinux systemd test"
CDEPEND="
dev-lang/spidermonkey:0/mozjs185[-debug]
>=dev-libs/glib-2.32:2
>=dev-libs/expat-2:=
pam? (
sys-auth/pambase
sys-libs/pam
)
systemd? ( sys-apps/systemd:0= )
"
DEPEND="${CDEPEND}
app-text/docbook-xml-dtd:4.1.2
app-text/docbook-xsl-stylesheets
introspection? ( >=dev-libs/gobject-introspection-1:= )
dev-libs/libxslt
dev-util/gtk-doc-am
dev-util/intltool
virtual/pkgconfig
"
RDEPEND="${CDEPEND}
selinux? ( sec-policy/selinux-policykit )
"
PDEPEND="
gtk? ( || (
>=gnome-extra/polkit-gnome-0.105
lxde-base/lxpolkit
) )
kde? ( || (
kde-plasma/polkit-kde-agent
sys-auth/polkit-kde-agent
) )
!systemd? ( sys-auth/consolekit[policykit] )
"
QA_MULTILIB_PATHS="
usr/lib/polkit-1/polkit-agent-helper-1
usr/lib/polkit-1/polkitd"
pkg_setup() {
local u=polkitd
local g=polkitd
local h=/var/lib/polkit-1
enewgroup ${g}
enewuser ${u} -1 -1 ${h} ${g}
esethome ${u} ${h}
}
src_prepare() {
sed -i -e 's|unix-group:wheel|unix-user:0|' src/polkitbackend/*-default.rules || die #401513
epatch ${FILESDIR}/polkit-0.113-gir-cross-compile.patch
epatch ${FILESDIR}/polkit-0.113-allow-negative-uids-gids.patch
epatch ${FILESDIR}/polkit-0.113-allow-uid-of-1-for-a-PolkitUnixProcess.patch
epatch ${FILESDIR}/polkit-0.113-fix-CVE-2018-1116-Trusting-client-supplied-UID.patch
}
src_configure() {
tc-export CC
econf \
--localstatedir="${EPREFIX}"/var \
--disable-static \
--enable-man-pages \
--disable-gtk-doc \
$(use_enable systemd libsystemd-login) \
$(use_enable introspection) \
--disable-examples \
$(use_enable nls) \
--with-mozjs=mozjs185 \
"$(systemd_with_unitdir)" \
--with-authfw=$(usex pam pam shadow) \
$(use pam && echo --with-pam-module-dir="$(getpam_mod_dir)") \
$(use_enable test) \
--with-os-type=gentoo
}
src_compile() {
default
# Required for polkitd on hardened/PaX due to spidermonkey's JIT
pax-mark mr src/polkitbackend/.libs/polkitd test/polkitbackend/.libs/polkitbackendjsauthoritytest
}
src_install() {
emake DESTDIR="${D}" install
dodoc docs/TODO HACKING NEWS README
# relocate default configs from /etc to /usr
dodir /usr/share/dbus-1/system.d
mv "${D}"/{etc,usr/share}/dbus-1/system.d/org.freedesktop.PolicyKit1.conf || die
mv "${D}"/{etc,usr/share}/polkit-1/rules.d/50-default.rules || die
rmdir "${D}"/etc/dbus-1/system.d "${D}"/etc/dbus-1 || die
systemd_dotmpfilesd "${FILESDIR}/polkit.conf"
diropts -m0700 -o polkitd -g polkitd
dodir /var/lib/polkit-1
if use examples; then
insinto /usr/share/doc/${PF}/examples
doins src/examples/{*.c,*.policy*}
fi
prune_libtool_files
}

View File

@ -0,0 +1,141 @@
# Copyright 1999-2021 Gentoo Authors
# Distributed under the terms of the GNU General Public License v2
EAPI=7
inherit autotools pam pax-utils systemd xdg-utils
DESCRIPTION="Policy framework for controlling privileges for system-wide services"
HOMEPAGE="https://www.freedesktop.org/wiki/Software/polkit https://gitlab.freedesktop.org/polkit/polkit"
SRC_URI="https://www.freedesktop.org/software/${PN}/releases/${P}.tar.gz"
LICENSE="LGPL-2"
SLOT="0"
KEYWORDS="amd64 arm arm64 ~mips ppc64 ~riscv ~s390 x86"
IUSE="elogind examples gtk +introspection kde nls pam selinux systemd test"
RESTRICT="!test? ( test )"
REQUIRED_USE="^^ ( elogind systemd )"
BDEPEND="
acct-user/polkitd
app-text/docbook-xml-dtd:4.1.2
app-text/docbook-xsl-stylesheets
dev-libs/glib
dev-libs/gobject-introspection-common
dev-libs/libxslt
dev-util/glib-utils
dev-util/gtk-doc-am
dev-util/intltool
sys-devel/gettext
virtual/pkgconfig
introspection? ( dev-libs/gobject-introspection )
"
DEPEND="
dev-lang/duktape
dev-libs/glib:2
dev-libs/expat
elogind? ( sys-auth/elogind )
pam? (
sys-auth/pambase
sys-libs/pam
)
!pam? ( virtual/libcrypt:= )
systemd? ( sys-apps/systemd:0=[policykit] )
"
RDEPEND="${DEPEND}
acct-user/polkitd
selinux? ( sec-policy/selinux-policykit )
"
PDEPEND="
gtk? ( || (
>=gnome-extra/polkit-gnome-0.105
>=lxde-base/lxsession-0.5.2
) )
kde? ( kde-plasma/polkit-kde-agent )
"
DOCS=( docs/TODO HACKING NEWS README )
PATCHES=(
"${FILESDIR}"/${PN}-0.115-elogind.patch # bug 660880
# from https://gitlab.freedesktop.org/polkit/polkit/-/merge_requests/35
"${FILESDIR}"/35_WIP_Add_duktape_as_javascript_engine.patch
)
QA_MULTILIB_PATHS="
usr/lib/polkit-1/polkit-agent-helper-1
usr/lib/polkit-1/polkitd"
src_prepare() {
default
sed -i -e 's|unix-group:wheel|unix-user:0|' src/polkitbackend/*-default.rules || die #401513
# Workaround upstream hack around standard gtk-doc behavior, bug #552170
sed -i -e 's/@ENABLE_GTK_DOC_TRUE@\(TARGET_DIR\)/\1/' \
-e '/install-data-local:/,/uninstall-local:/ s/@ENABLE_GTK_DOC_TRUE@//' \
-e 's/@ENABLE_GTK_DOC_FALSE@install-data-local://' \
docs/polkit/Makefile.in || die
# disable broken test - bug #624022
sed -i -e "/^SUBDIRS/s/polkitbackend//" test/Makefile.am || die
# Fix cross-building, bug #590764, elogind patch, bug #598615
eautoreconf
}
src_configure() {
xdg_environment_reset
local myeconfargs=(
--localstatedir="${EPREFIX}"/var
--disable-static
--enable-man-pages
--disable-gtk-doc
--disable-examples
--with-duktape
$(use_enable elogind libelogind)
$(use_enable introspection)
$(use_enable nls)
$(usex pam "--with-pam-module-dir=$(getpam_mod_dir)" '')
--with-authfw=$(usex pam pam shadow)
$(use_enable systemd libsystemd-login)
--with-systemdsystemunitdir="$(systemd_get_systemunitdir)"
$(use_enable test)
--with-os-type=gentoo
)
econf "${myeconfargs[@]}"
}
src_compile() {
default
# Required for polkitd on hardened/PaX due to spidermonkey's JIT
pax-mark mr src/polkitbackend/.libs/polkitd test/polkitbackend/.libs/polkitbackendjsauthoritytest
}
src_install() {
default
dodir /usr/share/polkit-1/rules.d
dodir /usr/lib/pam.d
mv "${D}"/{etc,usr/share}/polkit-1/rules.d/50-default.rules || die
mv "${D}"/{etc,usr/lib}/pam.d/polkit-1 || die
rmdir "${D}"/etc/polkit-1/rules.d "${D}"/etc/polkit-1 || die
rmdir "${D}"/etc/pam.d || die
systemd_dotmpfilesd "${FILESDIR}/polkit.conf"
if use examples; then
docinto examples
dodoc src/examples/{*.c,*.policy*}
fi
diropts -m 0700 -o polkitd
keepdir /usr/share/polkit-1/rules.d
find "${ED}" -name '*.la' -delete || die
}

View File

@ -14,7 +14,7 @@ SLOT="0"
KEYWORDS="amd64 x86 arm64"
IUSE="systemd"
DEPEND="sys-auth/polkit[introspection]
DEPEND="sys-auth/polkit
sys-devel/gettext
dev-libs/glib:2
net-nds/openldap