Commit c1e0322e authored by David Zeuthen's avatar David Zeuthen

add serialization for subjects and implement Enumerate{Users,Groups}

parent 3559b640
......@@ -92,6 +92,10 @@
<arg name="users" direction="out" type="a(sa{sv})"/>
</method>
<method name="EnumerateGroups">
<arg name="groups" direction="out" type="a(sa{sv})"/>
</method>
<method name="EnumerateActions">
<arg name="locale" direction="in" type="s"/>
<arg name="action_descriptions" direction="out" type="a(ssssssa{ss})"/>
......
......@@ -97,7 +97,7 @@ polkit_action_description_new_for_real (_PolkitActionDescription *real)
_PolkitActionDescription *
polkit_action_description_get_real (PolkitActionDescription *action_description)
{
return action_description->real;
return g_object_ref (action_description->real);
}
const gchar *
......
......@@ -135,6 +135,78 @@ polkit_authority_enumerate_actions_sync (PolkitAuthority *authority,
result = g_list_reverse (result);
g_object_unref (array_seq);
out:
return result;
}
GList *
polkit_authority_enumerate_users_sync (PolkitAuthority *authority,
GCancellable *cancellable,
GError **error)
{
EggDBusArraySeq *array_seq;
GList *result;
guint n;
result = NULL;
if (!_polkit_authority_enumerate_users_sync (authority->real,
EGG_DBUS_CALL_FLAGS_NONE,
&array_seq,
cancellable,
error))
goto out;
for (n = 0; n < array_seq->size; n++)
{
_PolkitSubject *real_subject;
real_subject = array_seq->data.v_ptr[n];
result = g_list_prepend (result, polkit_subject_new_for_real (real_subject));
}
result = g_list_reverse (result);
g_object_unref (array_seq);
out:
return result;
}
GList *
polkit_authority_enumerate_groups_sync (PolkitAuthority *authority,
GCancellable *cancellable,
GError **error)
{
EggDBusArraySeq *array_seq;
GList *result;
guint n;
result = NULL;
if (!_polkit_authority_enumerate_groups_sync (authority->real,
EGG_DBUS_CALL_FLAGS_NONE,
&array_seq,
cancellable,
error))
goto out;
for (n = 0; n < array_seq->size; n++)
{
_PolkitSubject *real_subject;
real_subject = array_seq->data.v_ptr[n];
result = g_list_prepend (result, polkit_subject_new_for_real (real_subject));
}
result = g_list_reverse (result);
g_object_unref (array_seq);
out:
return result;
}
......@@ -48,6 +48,15 @@ GList *polkit_authority_enumerate_actions_sync (PolkitAuthori
const gchar *locale,
GCancellable *cancellable,
GError **error);
GList *polkit_authority_enumerate_users_sync (PolkitAuthority *authority,
GCancellable *cancellable,
GError **error);
GList *polkit_authority_enumerate_groups_sync (PolkitAuthority *authority,
GCancellable *cancellable,
GError **error);
G_END_DECLS
#endif /* __POLKIT_AUTHORITY_H */
......@@ -25,7 +25,19 @@
#include "polkitactiondescription.h"
#include "_polkitbindings.h"
/* notes:
*
* - the _new_for_real() functions will ref the passed arg (you will still own the ref)
* - the _get_real() functions will return a ref (you will own the ref)
*
*/
PolkitActionDescription *polkit_action_description_new_for_real (_PolkitActionDescription *real);
_PolkitActionDescription *polkit_action_description_get_real (PolkitActionDescription *action_description);
_PolkitActionDescription *polkit_action_description_get_real (PolkitActionDescription *action_description);
PolkitSubject *polkit_subject_new_for_real (_PolkitSubject *real);
_PolkitSubject *polkit_subject_get_real (PolkitSubject *subject);
#endif /* __POLKIT_PRIVATE_H */
......@@ -23,7 +23,14 @@
# include "config.h"
#endif
#include <string.h>
#include "polkitsubject.h"
#include "polkitunixuser.h"
#include "polkitunixgroup.h"
#include "polkitunixprocess.h"
#include "polkitsystembusname.h"
#include "polkitprivate.h"
static void
base_init (gpointer g_iface)
......@@ -69,3 +76,111 @@ polkit_subject_equal (PolkitSubject *a,
return POLKIT_SUBJECT_GET_IFACE (a)->equal (a, b);
}
gchar *
polkit_subject_to_string (PolkitSubject *subject)
{
return POLKIT_SUBJECT_GET_IFACE (subject)->to_string (subject);
}
PolkitSubject *
polkit_subject_new_for_real (_PolkitSubject *real)
{
PolkitSubject *s;
const gchar *kind;
EggDBusHashMap *details;
EggDBusVariant *variant;
EggDBusVariant *variant2;
s = NULL;
kind = _polkit_subject_get_subject_kind (real);
details = _polkit_subject_get_subject_details (real);
if (strcmp (kind, "unix-user") == 0)
{
variant = egg_dbus_hash_map_lookup (details, "uid");
s = polkit_unix_user_new (egg_dbus_variant_get_uint (variant));
}
else if (strcmp (kind, "unix-group") == 0)
{
variant = egg_dbus_hash_map_lookup (details, "gid");
s = polkit_unix_group_new (egg_dbus_variant_get_uint (variant));
}
else if (strcmp (kind, "unix-process") == 0)
{
variant = egg_dbus_hash_map_lookup (details, "pid");
variant2 = egg_dbus_hash_map_lookup (details, "start-time");
s = polkit_unix_process_new_full (egg_dbus_variant_get_uint (variant),
egg_dbus_variant_get_uint64 (variant2));
}
else if (strcmp (kind, "system-bus-name") == 0)
{
variant = egg_dbus_hash_map_lookup (details, "name");
s = polkit_system_bus_name_new (egg_dbus_variant_get_string (variant));
}
else
{
g_warning ("Unknown subject kind %s:", kind);
}
return s;
}
_PolkitSubject *
polkit_subject_get_real (PolkitSubject *subject)
{
_PolkitSubject *real;
const gchar *kind;
EggDBusHashMap *details;
real = NULL;
kind = NULL;
details = egg_dbus_hash_map_new (G_TYPE_STRING, NULL, EGG_DBUS_TYPE_VARIANT, (GDestroyNotify) g_object_unref);
if (POLKIT_IS_UNIX_USER (subject))
{
kind = "unix-user";
egg_dbus_hash_map_insert (details,
"uid",
egg_dbus_variant_new_for_uint (polkit_unix_user_get_uid (POLKIT_UNIX_USER (subject))));
}
else if (POLKIT_IS_UNIX_GROUP (subject))
{
kind = "unix-group";
egg_dbus_hash_map_insert (details,
"gid",
egg_dbus_variant_new_for_uint (polkit_unix_group_get_gid (POLKIT_UNIX_GROUP (subject))));
}
else if (POLKIT_IS_UNIX_PROCESS (subject))
{
kind = "unix-process";
egg_dbus_hash_map_insert (details,
"pid",
egg_dbus_variant_new_for_uint (polkit_unix_process_get_pid (POLKIT_UNIX_PROCESS (subject))));
egg_dbus_hash_map_insert (details,
"start-time",
egg_dbus_variant_new_for_uint64 (polkit_unix_process_get_start_time (POLKIT_UNIX_PROCESS (subject))));
}
else if (POLKIT_IS_SYSTEM_BUS_NAME (subject))
{
kind = "system-bus-name";
egg_dbus_hash_map_insert (details,
"name",
egg_dbus_variant_new_for_string (polkit_system_bus_name_get_name (POLKIT_SYSTEM_BUS_NAME (subject))));
}
else
{
g_warning ("Unknown class %s implementing PolkitSubject", g_type_name (G_TYPE_FROM_INSTANCE (subject)));
}
if (kind != NULL)
{
real = _polkit_subject_new (kind, details);
}
if (details != NULL)
g_object_unref (details);
return real;
}
......@@ -42,13 +42,16 @@ struct _PolkitSubjectIface
{
GTypeInterface parent_iface;
gboolean (*equal) (PolkitSubject *a,
PolkitSubject *b);
gboolean (*equal) (PolkitSubject *a,
PolkitSubject *b);
gchar * (*to_string) (PolkitSubject *subject);
};
GType polkit_subject_get_type (void) G_GNUC_CONST;
gboolean polkit_subject_equal (PolkitSubject *a,
PolkitSubject *b);
GType polkit_subject_get_type (void) G_GNUC_CONST;
gboolean polkit_subject_equal (PolkitSubject *a,
PolkitSubject *b);
gchar *polkit_subject_to_string (PolkitSubject *subject);
G_END_DECLS
......
......@@ -176,8 +176,17 @@ polkit_system_bus_name_equal (PolkitSubject *a,
return strcmp (name_a->name, name_b->name) == 0;
}
static gchar *
polkit_system_bus_name_to_string (PolkitSubject *subject)
{
PolkitSystemBusName *system_bus_name = POLKIT_SYSTEM_BUS_NAME (subject);
return g_strdup_printf ("system-bus-name:%s", system_bus_name->name);
}
static void
subject_iface_init (PolkitSubjectIface *subject_iface)
{
subject_iface->equal = polkit_system_bus_name_equal;
subject_iface->equal = polkit_system_bus_name_equal;
subject_iface->to_string = polkit_system_bus_name_to_string;
}
......@@ -24,6 +24,7 @@
#endif
#include <string.h>
#include <grp.h>
#include "polkitunixgroup.h"
#include "polkitsubject.h"
#include "polkitprivate.h"
......@@ -168,8 +169,23 @@ polkit_unix_group_equal (PolkitSubject *a,
return group_a->gid == group_b->gid;
}
static gchar *
polkit_unix_group_to_string (PolkitSubject *subject)
{
PolkitUnixGroup *group = POLKIT_UNIX_GROUP (subject);
struct group *gr;
gr = getgrgid (group->gid);
if (gr == NULL)
return g_strdup_printf ("unix-group:%d", group->gid);
else
return g_strdup_printf ("unix-group:%s", gr->gr_name);
}
static void
subject_iface_init (PolkitSubjectIface *subject_iface)
{
subject_iface->equal = polkit_unix_group_equal;
subject_iface->equal = polkit_unix_group_equal;
subject_iface->to_string = polkit_unix_group_to_string;
}
......@@ -178,7 +178,8 @@ polkit_unix_process_set_pid (PolkitUnixProcess *process,
pid_t pid)
{
process->pid = pid;
process->start_time = get_start_time_for_pid (pid);
if (pid != (pid_t) -1)
process->start_time = get_start_time_for_pid (pid);
}
PolkitSubject *
......@@ -189,6 +190,20 @@ polkit_unix_process_new (pid_t pid)
NULL));
}
PolkitSubject *
polkit_unix_process_new_full (pid_t pid,
guint64 start_time)
{
PolkitUnixProcess *process;
process = POLKIT_UNIX_PROCESS (polkit_unix_process_new ((pid_t) -1));
process->pid = pid;
process->start_time = start_time;
return POLKIT_SUBJECT (process);
}
static gboolean
polkit_unix_process_equal (PolkitSubject *a,
PolkitSubject *b)
......@@ -204,10 +219,19 @@ polkit_unix_process_equal (PolkitSubject *a,
(process_a->start_time == process_b->start_time);
}
static gchar *
polkit_unix_process_to_string (PolkitSubject *subject)
{
PolkitUnixProcess *process = POLKIT_UNIX_PROCESS (subject);
return g_strdup_printf ("unix-process:%d:%" G_GUINT64_FORMAT, process->pid, process->start_time);
}
static void
subject_iface_init (PolkitSubjectIface *subject_iface)
{
subject_iface->equal = polkit_unix_process_equal;
subject_iface->equal = polkit_unix_process_equal;
subject_iface->to_string = polkit_unix_process_to_string;
}
#ifdef HAVE_SOLARIS
......
......@@ -44,6 +44,8 @@ typedef struct _PolkitUnixProcessClass PolkitUnixProcessClass;
GType polkit_unix_process_get_type (void) G_GNUC_CONST;
PolkitSubject *polkit_unix_process_new (pid_t pid);
PolkitSubject *polkit_unix_process_new_full (pid_t pid,
guint64 start_time);
pid_t polkit_unix_process_get_pid (PolkitUnixProcess *process);
guint64 polkit_unix_process_get_start_time (PolkitUnixProcess *process);
......
......@@ -24,6 +24,7 @@
#endif
#include <string.h>
#include <pwd.h>
#include "polkitunixuser.h"
#include "polkitsubject.h"
#include "polkitprivate.h"
......@@ -168,8 +169,23 @@ polkit_unix_user_equal (PolkitSubject *a,
return user_a->uid == user_b->uid;
}
static gchar *
polkit_unix_user_to_string (PolkitSubject *subject)
{
PolkitUnixUser *user = POLKIT_UNIX_USER (subject);
struct passwd *passwd;
passwd = getpwuid (user->uid);
if (passwd == NULL)
return g_strdup_printf ("unix-user:%d", user->uid);
else
return g_strdup_printf ("unix-user:%s", passwd->pw_name);
}
static void
subject_iface_init (PolkitSubjectIface *subject_iface)
{
subject_iface->equal = polkit_unix_user_equal;
subject_iface->equal = polkit_unix_user_equal;
subject_iface->to_string = polkit_unix_user_to_string;
}
......@@ -39,13 +39,35 @@ polkit_backend_authority_class_init (PolkitBackendAuthorityClass *klass)
}
GList *
polkit_backend_authority_enumerate_actions (PolkitBackendAuthority *authority,
const gchar *locale)
polkit_backend_authority_enumerate_actions (PolkitBackendAuthority *authority,
const gchar *locale,
GError **error)
{
PolkitBackendAuthorityClass *klass;
klass = POLKIT_BACKEND_AUTHORITY_GET_CLASS (authority);
return klass->enumerate_actions (authority, locale);
return klass->enumerate_actions (authority, locale, error);
}
GList *
polkit_backend_authority_enumerate_users (PolkitBackendAuthority *authority,
GError **error)
{
PolkitBackendAuthorityClass *klass;
klass = POLKIT_BACKEND_AUTHORITY_GET_CLASS (authority);
return klass->enumerate_users (authority, error);
}
GList *
polkit_backend_authority_enumerate_groups (PolkitBackendAuthority *authority,
GError **error)
{
PolkitBackendAuthorityClass *klass;
klass = POLKIT_BACKEND_AUTHORITY_GET_CLASS (authority);
return klass->enumerate_groups (authority, error);
}
......@@ -51,8 +51,15 @@ struct _PolkitBackendAuthorityClass
/*< public >*/
GList * (*enumerate_actions) (PolkitBackendAuthority *authority,
const gchar *locale);
GList * (*enumerate_actions) (PolkitBackendAuthority *authority,
const gchar *locale,
GError **error);
GList * (*enumerate_users) (PolkitBackendAuthority *authority,
GError **error);
GList * (*enumerate_groups) (PolkitBackendAuthority *authority,
GError **error);
/*< private >*/
/* Padding for future expansion */
......@@ -69,7 +76,14 @@ struct _PolkitBackendAuthorityClass
GType polkit_backend_authority_get_type (void) G_GNUC_CONST;
GList *polkit_backend_authority_enumerate_actions (PolkitBackendAuthority *authority,
const gchar *locale);
const gchar *locale,
GError **error);
GList *polkit_backend_authority_enumerate_users (PolkitBackendAuthority *authority,
GError **error);
GList *polkit_backend_authority_enumerate_groups (PolkitBackendAuthority *authority,
GError **error);
G_END_DECLS
......
......@@ -22,6 +22,7 @@
#include "config.h"
#include <errno.h>
#include <pwd.h>
#include <grp.h>
#include <string.h>
#include <polkit/polkit.h>
#include "polkitbackendlocalauthority.h"
......@@ -33,9 +34,15 @@ typedef struct
} PolkitBackendLocalAuthorityPrivate;
static GList *polkit_backend_local_authority_enumerate_actions (PolkitBackendAuthority *authority,
const gchar *locale);
static GList *polkit_backend_local_authority_enumerate_actions (PolkitBackendAuthority *authority,
const gchar *locale,
GError **error);
static GList *polkit_backend_local_authority_enumerate_users (PolkitBackendAuthority *authority,
GError **error);
static GList *polkit_backend_local_authority_enumerate_groups (PolkitBackendAuthority *authority,
GError **error);
G_DEFINE_TYPE (PolkitBackendLocalAuthority, polkit_backend_local_authority, POLKIT_BACKEND_TYPE_AUTHORITY);
......@@ -81,6 +88,8 @@ polkit_backend_local_authority_class_init (PolkitBackendLocalAuthorityClass *kla
gobject_class->finalize = polkit_backend_local_authority_finalize;
authority_class->enumerate_actions = polkit_backend_local_authority_enumerate_actions;
authority_class->enumerate_users = polkit_backend_local_authority_enumerate_users;
authority_class->enumerate_groups = polkit_backend_local_authority_enumerate_groups;
g_type_class_add_private (klass, sizeof (PolkitBackendLocalAuthorityPrivate));
}
......@@ -95,8 +104,9 @@ polkit_backend_local_authority_new (void)
/* ---------------------------------------------------------------------------------------------------- */
static GList *
polkit_backend_local_authority_enumerate_actions (PolkitBackendAuthority *authority,
const gchar *locale)
polkit_backend_local_authority_enumerate_actions (PolkitBackendAuthority *authority,
const gchar *locale,
GError **error)
{
PolkitBackendLocalAuthority *local_authority;
PolkitBackendLocalAuthorityPrivate *priv;
......@@ -107,6 +117,90 @@ polkit_backend_local_authority_enumerate_actions (PolkitBackendAuthority *author
return polkit_backend_action_pool_get_all_actions (priv->action_pool, locale);
}
static GList *
polkit_backend_local_authority_enumerate_users (PolkitBackendAuthority *authority,
GError **error)
{
PolkitBackendLocalAuthority *local_authority;
PolkitBackendLocalAuthorityPrivate *priv;
struct passwd *passwd;
GList *list;
local_authority = POLKIT_BACKEND_LOCAL_AUTHORITY (authority);
priv = POLKIT_BACKEND_LOCAL_AUTHORITY_GET_PRIVATE (local_authority);
list = NULL;
passwd = getpwent ();
if (passwd == NULL)
{
g_set_error (error,
POLKIT_ERROR,
POLKIT_ERROR_FAILED,
"getpwent failed: %s",
strerror (errno));
goto out;
}
do
{
PolkitSubject *subject;
subject = polkit_unix_user_new (passwd->pw_uid);
list = g_list_prepend (list, subject);
}
while ((passwd = getpwent ()) != NULL);
endpwent ();
list = g_list_reverse (list);
out:
return list;
}
static GList *
polkit_backend_local_authority_enumerate_groups (PolkitBackendAuthority *authority,
GError **error)
{
PolkitBackendLocalAuthority *local_authority;
PolkitBackendLocalAuthorityPrivate *priv;
struct group *group;
GList *list;
local_authority = POLKIT_BACKEND_LOCAL_AUTHORITY (authority);
priv = POLKIT_BACKEND_LOCAL_AUTHORITY_GET_PRIVATE (local_authority);
list = NULL;
group = getgrent ();
if (group == NULL)
{
g_set_error (error,
POLKIT_ERROR,
POLKIT_ERROR_FAILED,
"getgrent failed: %s",
strerror (errno));
goto out;
}
do
{
PolkitSubject *subject;
subject = polkit_unix_group_new (group->gr_gid);
list = g_list_prepend (list, subject);
}
while ((group = getgrent ()) != NULL);
endgrent ();
list = g_list_reverse (list);
out:
return list;
}
#if 0
/* ---------------------------------------------------------------------------------------------------- */